blob: a36dfdad8b6f328a1fa62a3fd4c7154edd0f0e22 (
plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
|
#include "common.h"
#include "crc.h"
u32 crc32_table[4][256];
u32 Reflect(u32 ref, u8 Count)
{
u32 value = 0;
// Swap bit 0 for bit 7
// bit 1 for bit 6, etc.
for(int i = 1; i < (Count + 1); i++)
{
if(ref & 1)
value |= 1 << (Count - i);
ref >>= 1;
}
return value;
}
void Init_CRC32_Table()
{
// This is the official polynomial used by CRC-32
// in PKZip, WinZip and Ethernet.
u32 ulPolynomial = 0x04c11db7;
// 256 values representing ASCII character codes.
for(int x = 0; x < 4; x++)
{
for(int i = 0; i <= 0xFF; i++)
{
crc32_table[x][i]=Reflect(i, 8) << 24;
for (int j = 0; j < 8; j++)
crc32_table[x][i] = (crc32_table[x][i] << 1) ^ (crc32_table[x][i] & (1 << 31) ? (ulPolynomial + (x * 8)) : 0);
crc32_table[x][i] = Reflect(crc32_table[x][i], 32);
}
}
}
u32 GenerateCRC(u8 *StartAddr, u32 len)
{
u32 ulCRC = -1;
// Perform the algorithm on each character
// in the string, using the lookup table values.
for(; len > 7; len-=8)
{
ulCRC ^= *(u32 *)StartAddr;
ulCRC = crc32_table[3][((ulCRC) & 0xFF)] ^
crc32_table[2][((ulCRC >> 8) & 0xFF)] ^
crc32_table[1][((ulCRC >> 16) & 0xFF)] ^
crc32_table[0][((ulCRC >> 24))];
ulCRC ^= *(u32 *)(StartAddr + 4);
ulCRC = crc32_table[3][((ulCRC) & 0xFF)] ^
crc32_table[2][((ulCRC >> 8) & 0xFF)] ^
crc32_table[1][((ulCRC >> 16) & 0xFF)] ^
crc32_table[0][((ulCRC >> 24))];
StartAddr+=8;
}
if(len > 3)
{
ulCRC ^= *(u32 *)StartAddr;
ulCRC = crc32_table[3][((ulCRC) & 0xFF)] ^
crc32_table[2][((ulCRC >> 8) & 0xFF)] ^
crc32_table[1][((ulCRC >> 16) & 0xFF)] ^
crc32_table[0][((ulCRC >> 24))];
StartAddr+=4;
len -= 4;
}
switch(len)
{
case 3:
ulCRC = crc32_table[0][(ulCRC & 0xFF) ^ *StartAddr] ^ (ulCRC >> 8);
StartAddr++;
case 2:
ulCRC = crc32_table[0][(ulCRC & 0xFF) ^ *StartAddr] ^ (ulCRC >> 8);
StartAddr++;
case 1:
ulCRC = crc32_table[0][(ulCRC & 0xFF) ^ *StartAddr] ^ (ulCRC >> 8);
StartAddr++;
}
return ulCRC;
}
|