blob: 1257ea27d409165a3bf5a6d2f180d58b9e843e35 (
plain) (
blame)
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
|
pub const InvalidChecksumError = error{InvalidChecksum};
const crc16tab: [256]u16 = tab: {
@setEvalBranchQuota(5000);
// CRC-16-CCITT/XMODEM
const poly: u32 = 0x1021;
var table: [256]u16 = undefined;
for (&table, 0..) |*crc, i| {
crc.* = @as(u16, i) << 8;
var j = 0;
while (j < 8) : (j += 1) {
if (crc.* >> 15 != 0) {
crc.* = (crc.* << 1) ^ poly;
} else {
crc.* <<= 1;
}
}
}
break :tab table;
};
pub fn update(crc: u16, with_data: []const u8) u16 {
var new_crc = crc;
for (with_data) |b| {
new_crc = (new_crc << 8) ^ crc16tab[@as(u8, @truncate(new_crc >> 8)) ^ b];
}
return new_crc;
}
// make returns the CRC-16 checksum for the data provided.
pub fn make(data: []const u8) u16 {
return update(0, data);
}
// validate will check the calculated CRC-16 checksum for data against the expected.
pub fn validate(data: []const u8, expected: u16) InvalidChecksumError!void {
if (make(data) != expected) return error.InvalidChecksum;
}
|