《TCP/IP详解 卷2:实现》 —2.6.3 m_pullup函数和连续的协议首部

举报
华章计算机 发表于 2019/11/20 16:36:15 2019/11/20
【摘要】 本节书摘来自华章计算机《TCP/IP详解 卷2:实现》一书中第2章,第2.6.3节,作者是[美]加里R.赖特(Gary R.Wright),W. 理查德史蒂文斯(W.Richard Stevens),陆雪莹 蒋慧 等译 谢希仁 校。

2.6.3   m_pullup函数和连续的协议首部

函数m_pullup有两个用途。第一个是当一个协议(IP、ICMP、IGMP、UDP或TCP)发现在第一个mbuf的数据量(m_len)小于协议首部的最小长度(例如:IP是20,UDP是8,TCP是20)时,调用m_pullup是基于假定协议首部的剩余部分存放在链表的下一个mbuf,m_pullup重新安排mbuf链表,使得前N字节的数据被连续地存放在链表的第一个mbuf中。N是这个函数的一个参数,它必须小于或等于100(MHLEN)。如果前N字节连续存放在第一个mbuf中,则可以使用宏mtod和dtom。

例如,我们在IP输入例程中会遇到下面这样的代码:

image.png

如果第一个mbuf中的数据量小于20(标准IP首部的大小),m_pullup被调用。函数m_pullup失败的原因有两个:(1)如果它需要其他mbuf并且调用MGET失败;(2)如果整个mbuf链表中的数据量总数少于要求的连续字节数(即我们所说的N,在本例中是20)。通常,第二个原因是主要的。在此例中,如果m_pullup失败,一个IP计数器加1,并且此IP数据报被丢弃。注意,这段代码假设失败的原因是mbuf 链表中数据量少于20字节。

实际上,在这种情况下,m_pullup很少能被调用(注意,C语言的&&操作符仅当mbuf长度小于期待值时才调用它),并且当它被调用时,通常会失败。通过查看图2-14~图2-16,我们可以找到原因:在第一个mbuf中,或在簇中,从IP首部开始至少有100字节的连续字节。这允许60字节的最大IP首部,并且后面跟着40字节的TCP首部(其他协议如ICMP、IGMP和UDP的协议首部不到40字节)。如果mbuf链表中的数据可用(分组不小于协议要求的最小值),则所要求的字节数总能连续地存放在第一个mbuf中。但是,如果接收的分组太小(m_len小于期待的最小值),则m_pullup被调用,并且它返回一个差错,因为在mbuf链表中没有所要求数目的可用数据量。

源于伯克利的内核维护一个叫MPFail的变量,每次m_pullup失败时,它都加1。在一个Net/3系统中曾经接收了超过2700万的IP数据报,而MPFail只有9。计数器ipstat.ips_toosmall也是9,并且所有其他协议计数器(ICMP、IGMP、UDP和TCP等)所计的m_pullup失败次数为0。这证实了我们的断言:大多数m_pullup的失败是因为接收的IP数据报太小。


【版权声明】本文为华为云社区用户转载文章,如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。