Coverage Report

Created: 2026-09-14 06:25

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/php-src/ext/hash/hash_crc32.c
Line
Count
Source
1
/*
2
  +----------------------------------------------------------------------+
3
  | Copyright © The PHP Group and Contributors.                          |
4
  +----------------------------------------------------------------------+
5
  | This source file is subject to the Modified BSD License that is      |
6
  | bundled with this package in the file LICENSE, and is available      |
7
  | through the World Wide Web at <https://www.php.net/license/>.        |
8
  |                                                                      |
9
  | SPDX-License-Identifier: BSD-3-Clause                                |
10
  +----------------------------------------------------------------------+
11
  | Authors: Michael Wallner <mike@php.net>                              |
12
  |          Sara Golemon <pollita@php.net>                              |
13
  +----------------------------------------------------------------------+
14
*/
15
16
#include "php_hash.h"
17
#include "php_hash_crc32.h"
18
#include "php_hash_crc32_tables.h"
19
#include "ext/standard/crc32_x86.h"
20
21
PHP_HASH_API void PHP_CRC32Init(PHP_CRC32_CTX *context, ZEND_ATTRIBUTE_UNUSED HashTable *args)
22
3.03k
{
23
3.03k
  context->state = ~0;
24
3.03k
}
25
26
PHP_HASH_API void PHP_CRC32Update(PHP_CRC32_CTX *context, const unsigned char *input, size_t len)
27
30
{
28
30
  size_t i = 0;
29
30
30
#if defined(ZEND_INTRIN_SSE4_2_PCLMUL_NATIVE) || defined(ZEND_INTRIN_SSE4_2_PCLMUL_RESOLVER)
31
30
  i += crc32_x86_simd_update(X86_CRC32, &context->state, input, len);
32
30
#endif
33
34
63
  for (; i < len; ++i) {
35
33
    context->state = (context->state << 8) ^ crc32_table[(context->state >> 24) ^ (input[i] & 0xff)];
36
33
  }
37
30
}
38
39
PHP_HASH_API void PHP_CRC32BUpdate(PHP_CRC32_CTX *context, const unsigned char *input, size_t len)
40
7
{
41
7
  size_t i = 0;
42
43
7
#if defined(ZEND_INTRIN_SSE4_2_PCLMUL_NATIVE) || defined(ZEND_INTRIN_SSE4_2_PCLMUL_RESOLVER)
44
7
  i += crc32_x86_simd_update(X86_CRC32B, &context->state, input, len);
45
7
#endif
46
47
33
  for (; i < len; ++i) {
48
26
    context->state = (context->state >> 8) ^ crc32b_table[(context->state ^ input[i]) & 0xff];
49
26
  }
50
7
}
51
52
PHP_HASH_API void PHP_CRC32CUpdate(PHP_CRC32_CTX *context, const unsigned char *input, size_t len)
53
38
{
54
38
  size_t i = 0;
55
56
38
#if defined(ZEND_INTRIN_SSE4_2_PCLMUL_NATIVE) || defined(ZEND_INTRIN_SSE4_2_PCLMUL_RESOLVER)
57
38
  i += crc32_x86_simd_update(X86_CRC32C, &context->state, input, len);
58
38
#endif
59
60
187
  for (; i < len; ++i) {
61
149
    context->state = (context->state >> 8) ^ crc32c_table[(context->state ^ input[i]) & 0xff];
62
149
  }
63
38
}
64
65
PHP_HASH_API void PHP_CRC32LEFinal(unsigned char digest[4], PHP_CRC32_CTX *context)
66
30
{
67
30
  context->state=~context->state;
68
30
  digest[3] = (unsigned char) ((context->state >> 24) & 0xff);
69
30
  digest[2] = (unsigned char) ((context->state >> 16) & 0xff);
70
30
  digest[1] = (unsigned char) ((context->state >> 8) & 0xff);
71
30
  digest[0] = (unsigned char) (context->state & 0xff);
72
30
  context->state = 0;
73
30
}
74
75
PHP_HASH_API void PHP_CRC32BEFinal(unsigned char digest[4], PHP_CRC32_CTX *context)
76
45
{
77
45
  context->state=~context->state;
78
45
  digest[0] = (unsigned char) ((context->state >> 24) & 0xff);
79
45
  digest[1] = (unsigned char) ((context->state >> 16) & 0xff);
80
45
  digest[2] = (unsigned char) ((context->state >> 8) & 0xff);
81
45
  digest[3] = (unsigned char) (context->state & 0xff);
82
45
  context->state = 0;
83
45
}
84
85
PHP_HASH_API zend_result PHP_CRC32Copy(const php_hash_ops *ops, const PHP_CRC32_CTX *orig_context, PHP_CRC32_CTX *copy_context)
86
0
{
87
0
  copy_context->state = orig_context->state;
88
0
  return SUCCESS;
89
0
}
90
91
const php_hash_ops php_hash_crc32_ops = {
92
  "crc32",
93
  (php_hash_init_func_t) PHP_CRC32Init,
94
  (php_hash_update_func_t) PHP_CRC32Update,
95
  (php_hash_final_func_t) PHP_CRC32LEFinal,
96
  (php_hash_copy_func_t) PHP_CRC32Copy,
97
  php_hash_serialize,
98
  php_hash_unserialize,
99
  PHP_CRC32_SPEC,
100
  4, /* what to say here? */
101
  4,
102
  sizeof(PHP_CRC32_CTX),
103
  0,
104
  0
105
};
106
107
const php_hash_ops php_hash_crc32b_ops = {
108
  "crc32b",
109
  (php_hash_init_func_t) PHP_CRC32Init,
110
  (php_hash_update_func_t) PHP_CRC32BUpdate,
111
  (php_hash_final_func_t) PHP_CRC32BEFinal,
112
  (php_hash_copy_func_t) PHP_CRC32Copy,
113
  php_hash_serialize,
114
  php_hash_unserialize,
115
  PHP_CRC32_SPEC,
116
  4, /* what to say here? */
117
  4,
118
  sizeof(PHP_CRC32_CTX),
119
  0,
120
  0
121
};
122
123
const php_hash_ops php_hash_crc32c_ops = {
124
  "crc32c",
125
  (php_hash_init_func_t) PHP_CRC32Init,
126
  (php_hash_update_func_t) PHP_CRC32CUpdate,
127
  (php_hash_final_func_t) PHP_CRC32BEFinal,
128
  (php_hash_copy_func_t) PHP_CRC32Copy,
129
  php_hash_serialize,
130
  php_hash_unserialize,
131
  PHP_CRC32_SPEC,
132
  4, /* what to say here? */
133
  4,
134
  sizeof(PHP_CRC32_CTX),
135
  0,
136
  0
137
};