python实现checksum校验和计算
校验和概念
- 差错控制编码是为了检查传输中的错误
- 下面将一个报文的数据部分称为d,报文的冗余部分称为r
- 发送方根据约定好的差错控制编码关系(关系指出dr之间的关系)和d生成出r;接收方收到报文后取出d和r,判断是否dr符合约定好的关系
- 如果不符合关系,说明报文传输过程中出错;否则可以认为没错(不考虑残存错误的可能)
- 校验和checksum就是约定好的差错控制编码关系中的一种,类似还有奇偶校验,CRC循环冗余
- 校验和适合软件方式实现,计算速度快,接收方检验的效率也高,CRC和奇偶校验适合硬件实现
发送方校验和计算思路
1.计算和
- 如果d字节数为奇数,末尾加上一个全0字节,使其为偶数
- 将d以两字节单位拆分;比如8字节的数据,那么可以拆成4组,每组两字节
- 每组内部,将两个一字节的二进制表示拼接起来
- 将每组的二进制表示相加,得到整个报文d部分的和(结果应为两字节长度)
- 如果相加过程中最高位出现了一位进位导致溢出,将进位加在最低位上,此操作称为回卷
2.将和取反,即可得到校验码
示例:UDP计算校验和
- UDP报文的冗余部分d指的是校验和字段,数据部分d是整个报文除了校验和的字段
- 之所以把伪头部字段放进d的范围,是为了可以顺带检查伪头部里面的字段是否出错
发送方计算校验和
1.发送方将数据部分d以两字节为单位划分,求和,遇到最高位进位时进行回卷
- 其中,计算校验和的时候,校验和字段是当作全0去计算的
2.算出和之后取反,将取反后的内容放入校验和字段
- 此时数据部分d的二进制表示+冗余部分r的二进制表示=二进制全1
接收方验证
1.将收到的报文的d和r取出,验证dr之和是否等于二进制全1
- r就是校验和字段,d就是除了整个数据包除了校验和的字段
- 其实不用特意取出,直接计算伪头部和UDP数据报之和即可,因为数据报部分本身就包含了校验和字段呀
python模拟checksum校验和计算
实现代码
# @Time : 2022/12/22 23:07
# @Author : tangxibomb
# @File : simulate checksum.py
def calculate(a,b):#返回回卷后的两十六进制之和的字符串表示
res=eval(a)+eval(b)
if res>=0xffff:#回卷
res=1+eval("0x"+hex(res)[-4:])
return str(hex(res))
def get0x(a,b):#返回两字符拼接出来的十六进制的字符串表示
a=hex(ord(a))
if a!='\a':
a+=hex(ord(b))[2:]
else:#特判是不是字符串长度是否奇数
a+="0000"
return a
fd=open('./infile.txt',"r")
words="Hello world."
# words=fd.read()
print("读入的字符串为"+words)
if len(words)&1:#如果字符串长度是奇数,添加一个特殊的字符作为标记
words=words+'\a'
sum="0"
for idx in range(0,len(words),2):#每两位计算
tmp=get0x(words[idx],words[idx+1])
sum=calculate(sum,tmp)
#print(tmp,sum)
print("该字符串的校验和为"+hex(0xffff-eval(sum)))
有帮助的话可以点个赞,我会很开心的~
分类:
一些算法实现
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 理解Rust引用及其生命周期标识(上)
· 浏览器原生「磁吸」效果!Anchor Positioning 锚点定位神器解析
· DeepSeek 开源周回顾「GitHub 热点速览」
· 物流快递公司核心技术能力-地址解析分单基础技术分享
· .NET 10首个预览版发布:重大改进与新特性概览!
· AI与.NET技术实操系列(二):开始使用ML.NET
· 单线程的Redis速度为什么快?