校验和(Checksum)是网络协议使用的数据错误检测方法,并且被认为比LRC(纵向冗余校验,Longitudinal Redundancy Check,LRC),VRC和CRC(循环冗余校验(Cyclic Redundancy Codes,CRC))更可靠。此方法在发送方使用校验和生成器,在接收方使用校验和校验器。
累加和校验算法的实现
发送方:对要数据累加,得到一个数据和,对和求反,即得到我们的校验值。然后把要发的数据和这个校验值一起发送给接收方。
接收方:对接收的数据(包括校验和)进行累加,然后加1,如果得到0,那么说明数据没有出现传输错误。
注意,此处发送方和接收方用于保存累加结果的类型一定要一致,否则加1就无法实现溢出从而无法得到0,校验就会无效。
步骤
- 校验数据以16bit为单位进行累加求和,校验数据需为偶字节数(不然无法以16bit为累加单位),奇字节数末尾填充0变为偶字节数;
- 累加和超过16bit,产生进位,将进位当作高16bit,其他数为低16bit,进行相加;
- 循环步骤2,直到没有进位产生为止,得到sum值
- 累加和取反得到校验和,即checksum值,存入数据的checksum字段即可。
两个例子
- 需要发送数据(8bit 2进制) 10101001 00111001 00001010
奇字节补0:10101001 00111001 00001010 00000000
10101001 + 00111001 + 00001010 + 00000000 = 11101100(sum值)
~11101100 = 00010011(checksum值)
所以发送的数据就是: 10101001 00111001 00001010 00010011
接收方接收到的数据是: 10101001 00111001 00001010 00010011
10101001 + 00111001 + 00001010 + 00010011 = 11111111(sum值)
~11111111 = 00000000(结果是0,校验完成,没有错误)
> 8位保存累加和
- 需要发送的数据(16bit 16进制) 1234 003c 1c46 4000 4006 'checksum' ac00 0a63 ac10 0a0c
根据原始数据计算出checksum(至于checksum段的位置,我想可能是自定义的,在哪都不影响), 才是发送出去的完成数据
先将checksum段置0,1234 003c 1c46 4000 4006 0000 ac00 0a63 ac10 0a0c
sum = 1234 + 003c + 1c46 + 4000 + 4006 + 0000 + ac00 + 0a63 + ac10 + 0a0c = 21b3b (进位加到低16bit末尾)
checksum = ~1b3d = e4c2(即checksum值)
所以发送方发送的数据为:1234 003c 1c46 4000 4006 e4c2 ac00 0a63 ac10 0a0c(补全 cehcksum字段)
sum = 1234 + 003c + 1c46 + 4000 + 4006 + e4c2 + ac00 + 0a63 + ac10 + 0a0c = 2fffd(再回加)
checksum = ~ffff=0000
接收方checksum=0,校验成功
> 16位保存累加和
标签:和校验,--,checksum,校验,累加,算法,00111001,10101001,16bit
From: https://www.cnblogs.com/pikacq/p/18408076