我需要对以太网帧实施错误检查。我该如何实施?
我已经阅读了一些文档,以了解如何检查以太网框架是否有效。我试图实现wikipedia page(在Swift 5.1中)描述的算法:
// we run the calculation over all the frame except the CRC itself (last 4 bytes)
var crc : UInt32 = 0xFFFFFFFF
for x in 0..<(packetLength-4) {
let byte = packetBytes[x]
let nLookupIndex : UInt32 = (crc ^ byte) & 0xFF
crc = (crc >> 8) ^ crcTable[Int(nLookupIndex)]
}
// This is the end padding (adding 4 bytes with 0 at the end)
for x in 0..<4 {
let byte : UInt32 = 0
let nLookupIndex : UInt32 = (crc ^ byte) & 0xFF
crc = (crc >> 8) ^ crcTable[Int(nLookupIndex)]
}
crcTable的外观如下:
let crcTable = [0x00000000, 0x77073096, 0xee0e612c, 0x990951ba, 0x076dc419, .... 0x5a05df1b, 0x2d02ef8d]
我可以看到这是错误的,因为它没有像我在以太网框架上看到的那样提供crc。有谁能指出我做错了什么?
此维基百科文章部分介绍了如何检查CRC。
https://en.wikipedia.org/wiki/Ethernet_frame#Frame_check_sequence
将代码更改为:
var crc : UInt32 = 0xFFFFFFFF
for x in 0..<(packetLength) { // fix
let byte = packetBytes[x]
let nLookupIndex : UInt32 = (crc ^ byte) & 0xFF
crc = (crc >> 8) ^ crcTable[Int(nLookupIndex)]
}
if (crc != 0xC704DD7B){ // if CRC != 0xC704DD7B
// ... // it is bad CRC
}
尽管Wiki部分声明要针对0xC704DD7B进行检查,但通常会针对值0x2144DF1C来检查CRC,显然,数据包中有一些数据未用于CRC生成,而是用于CRC检查(或Wiki文章部分有这个错误)。