LWIP的tot_len长度修改后发生错误_IP帧格式_UDP帧格式_STM32移植LWIP后的使用问题_UDP帧格式WireShark抓包详解

作者在STM32平台上移植LWIP后遇到UDP数据包传输问题,通过WireShark分析发现IP头中的数据长度字段错误。错误在于LWIP中len字段用于截取字符串,而tot_len字段才表示UDP负载长度,需两者一致。不匹配会导致PC接收端计算校验和错误,从而丢弃数据包。解决方案是确保tot_len与len设置相同。
摘要由CSDN通过智能技术生成

问题

作者在STM32平台移植LWIP后计划向PC传输数据,再传输之前修改一些必要的参数值,tot_len和len,如下图所示:

但是网络助手无法接收到数据,作者采取了WireShark抓包的方式分析了PC-STM32开发板之间的UDP数据包,发现开发板传来的数据包IP头中的数据长度出现了错误。

那么错误具体是什么呢?

UDP echo 正常数据包分析

如下图所示,IP头中的版本号和包头长是正确的,协议版本号为IPV4,UDP包头长度20Bytes。

下一个字段的IP数据包总长度,如下图所示,为38,也是正确的。

整个MAC帧一行16Bytes,总共4行,64-4=60Bytes,其中含有以太网的14+8=22Bytes,剩余的就是38Bytes的IP部分。

换言之,整个以太网包共有60bytes,其中38Bytes是IP包内容,也就是以太网的数据段,这个IP包里面有地址和端口信息和真正要传输的数据。

如下图所示,这个字段是生存时间TTL,再跳255次,此包将被认为不可达,进而被删除。

如下图所示的字段标识IP的上一层的协议内容,这里就是UDP了。

如下图所示的红黄两个方框标识的是发送IP和接收IP,分别为192.168.240和接收192.168.1.68。

r如下图所示的两个字段是源端口和目的端口,分别为2040和2041。注意端口号16bits,最大为FFFF也就是是65535,所以端口号不会大于65535.

如下图所示的字段是数据段长度,IP部分共38Bytes,除去头的20Bytes,就是此数据段的18Bytes。

这18Bytes里面含源端口目的端口,数据段长度以及校验和之类的其他数据(也就是UDP头),真正传输的数据部分长度为10,这里是66666666/n/r

UDP负载长度10bytes如下图所示,这里是66666666/n/r。

这里就是UDP的真实负载了。

UDP Send 错误数据包分析

如下图左所示,hellooooooooooooooooo oooooooooooo!这个字符串以及数组越界的UDP负载长度为52,也就是我们设置的len,可见len这部分(如下图右所示)并不会被写入网络帧,只是用于记录待发送数据包有多长。

我的UDP负载字段是52,那么UDP包长度就应该为52+8 = 60,加上IP头,IP包总长度应该是60+20=80,但是如下图所示的总长度字段为122=94+20+8。

可见LWIP中len字段是用于截取字符串的,tot_len才是表示UDP payload长度的变量,因而此变量会被加上UDP头长度8和IP头长度20作为IP头中的总长度字段。

因此此值如下图所示设置为与len一致即可。

若不一致接收端(PC)计算检验和时对不上,认为有错误,就不会显示了。

参考资料

IP头格式(https://blog.csdn.net/u011425939/article/details/103135282):

UDP头格式(https://blog.csdn.net/zuochao_2013/article/details/80561793):

检验和计算方法(https://blog.csdn.net/gao1440156051/article/details/51210320):

最后对上述过程举个例子:
IP头:
45 00    00 31
89 F5    00 00
6E 06    00 00(校验字段)
DE B7   45 5D       ->    222.183.69.93
C0 A8   00 DC     ->    192.168.0.220
计算:  
4500 + 0031 +89F5 + 0000 + 6e06+ 0000 + DEB7 + 455D + C0A8 + 00DC =3 22C4
0003 + 22C4 = 22C7
~22C7 = DD38      ->即为应填充的校验和
当接受到IP数据包时,要检查IP头是否正确,则对IP头进行检验,方法同上:
计算:
4500 + 0031 +89F5 + 0000 + 6E06+ DD38 + DEB7 + 455D + C0A8 + 00DC =3 FFFC
0003 + FFFC = FFFF
得到的结果是全一,正确。

 

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值