1 /* crc.c
2 * crc checksum generation and calculation functions: crc.c
3 *
4 * Copyright (c) 2007 by Intel Corporation.
5 *
6 * Author: Mike Harvey <michael.harvey@intel.com>
7 *
8 * Wireshark - Network traffic analyzer
9 * By Gerald Combs <gerald@wireshark.org>
10 * Copyright 1999 Gerald Combs
11 *
12 * SPDX-License-Identifier: GPL-2.0-or-later
13 */
14
15 #include "crc.h"
16
17 #define WMAX_MAC_CRC32_POLYNOMIAL 0x04c11db7U /* polynomial used in calculating the CRC-32 checksum */
18 #define CCITT_X25_CRC16_POLYNOMIAL 0x1021 /* polynomial used in calculating the CRC-16 checksum */
19 #define WMAX_MAC_CRC8_POLYNOMIAL 0x07 /* polynomial used in calculating the CRC-8 checksum */
20 #define CRC32_INITIAL_VALUE 0xFFFFFFFF
21 #define CRC16_INITIAL_VALUE 0xFFFF
22
23 #ifndef STATIC_DATA
24 static guint8 crc8_table[256];
25 static guint32 crc32_table[256];
26
27 extern guint16 crc16_table[256];
28
29 /*
30 void wimax_mac_gen_crc32_table(void)
31
32 REQUIRES: The functions must be called only once to initialze CRC table
33
34 DESCRIPTION: Generate the table of CRC remainders
35 for all possible bytes
36
37 ARGS:
38
39 RETURNS:
40
41 SIDE EFFECTS:
42
43 */
wimax_mac_gen_crc32_table(void)44 void wimax_mac_gen_crc32_table(void)
45 {
46 guint32 i, bit;
47 guint32 crc;
48
49 /* little-endian (reflected) algorithm */
50 for ( i = 0; i < G_N_ELEMENTS(crc32_table); i++ )
51 {
52 crc = ( i << 24 );
53 for ( bit = 0; bit < 8; bit++ )
54 {
55 if ( crc & 0x80000000U )
56 crc = ( crc << 1 ) ^ WMAX_MAC_CRC32_POLYNOMIAL;
57 else
58 crc = ( crc << 1 );
59 }
60 crc32_table[i] = crc;
61 }
62 }
63
64 /*
65 void wimax_mac_gen_crc8_table(void)
66
67 REQUIRES: The functions must be called only once to initialze CRC table
68
69 DESCRIPTION: Generate the table of CRC remainders
70 for all possible bytes
71
72 ARGS:
73
74 RETURNS:
75
76 SIDE EFFECTS:
77
78 */
wimax_mac_gen_crc8_table(void)79 void wimax_mac_gen_crc8_table(void)
80 {
81 guint i, bit;
82 guint8 crc;
83
84 for ( i = 0; i < G_N_ELEMENTS(crc8_table); i++ )
85 {
86 crc = i;
87 for ( bit = 0; bit < 8; bit++ )
88 {
89 if ( crc & 0x80 )
90 crc = ( crc << 1 ) ^ WMAX_MAC_CRC8_POLYNOMIAL;
91 else
92 crc = ( crc << 1 );
93 }
94 crc8_table[i] = crc;
95 }
96 }
97 #endif
98
99 /*
100
101 guint32 wimax_mac_calc_crc32(guint8 *data, guint data_len)
102
103 REQUIRES: wimax_mac_gen_crc32_table() must be called before
104
105 DESCRIPTION: Calculate the 32-bit CRC from a given data block
106
107 ARGS: data - pointer to data
108 data_len - length of data (in bytes)
109
110 RETURNS: calculated crc32
111
112 SIDE EFFECTS:
113
114 */
wimax_mac_calc_crc32(const guint8 * data,guint data_len)115 guint32 wimax_mac_calc_crc32(const guint8 *data, guint data_len)
116 {
117 guint32 crc=CRC32_INITIAL_VALUE;
118 guint i, j;
119
120 for ( j = 0; j < data_len; j++ )
121 {
122 i = ( (guint8)(crc>>24) ^ data[j] ) & 0xff;
123 crc = ( crc<<8 ) ^ crc32_table[i];
124 }
125 return ~crc;
126 }
127
128 /*
129
130 guint16 wimax_mac_calc_crc16(guint8 *data, guint data_len)
131
132 REQUIRES: crc16_table[] in crc_data.c
133
134 DESCRIPTION: Calculate the 16-bit CRC from a given data block
135
136 ARGS: data - pointer to data
137 data_len - length of data (in bytes)
138
139 RETURNS: calculated crc16
140
141 SIDE EFFECTS:
142
143 */
wimax_mac_calc_crc16(const guint8 * data,guint data_len)144 guint16 wimax_mac_calc_crc16(const guint8 *data, guint data_len)
145 {
146 guint32 crc=CRC16_INITIAL_VALUE;
147 guint j;
148
149 for ( j = 0; j < data_len; j++ )
150 {
151 crc ^= data[j] << 8;
152 crc = (crc << 8) ^ crc16_table[(crc & 0xff00) >> 8];
153 }
154 crc ^= 0xFFFF; /* Invert the output. */
155 crc &= 0xFFFF;
156 return crc;
157 }
158
159 /*
160
161 guint8 wimax_mac_calc_crc8(guint8 *data, guint data_len)
162
163 REQUIRES: wimax_mac_gen_crc8_table() must be called before
164
165 DESCRIPTION: Calculate the 8-bit CRC from a given data block
166
167 ARGS: data - pointer to data
168 data_len - length of data (in bytes)
169
170 RETURNS: calculated crc8
171
172 SIDE EFFECTS:
173
174 */
wimax_mac_calc_crc8(const guint8 * data,guint data_len)175 guint8 wimax_mac_calc_crc8(const guint8 *data, guint data_len)
176 {
177 guint8 crc=0;
178 guint i;
179
180 for(i = 0; i < data_len; i++)
181 {
182 crc = crc8_table[data[i]^crc];
183 }
184 return crc;
185 }
186
187 /*
188 * Editor modelines - https://www.wireshark.org/tools/modelines.html
189 *
190 * Local Variables:
191 * c-basic-offset: 2
192 * tab-width: 8
193 * indent-tabs-mode: nil
194 * End:
195 *
196 * ex: set shiftwidth=2 tabstop=8 expandtab:
197 * :indentSize=2:tabSize=8:noTabs=true:
198 */
199