mbuf
的主要用途是保存在进程和网络接口间互相传递的用户数据。但
mbuf
也用于保存其
他各种数据:源与目标地址、插口选项等等。
下面将要经常会的遇到的四种不同类型的
mbuf
,它们依据在成员mh_flags
中填写的不同标志M_PKTHDR
和M_EXT
而不同。
1)
第一类
mbuf
的mh_flags
等于
0
,
mbuf
只包含数据,在
mbuf
中有
108
字节的数据空间,指针
mh_data
指向这
108
字节缓存中的某个位置。
2)
第二类
mbuf
的mh_flags
值是M_PKTHDR
,它指示这是一个分组首部,描述一个分组数据的第一个
mbuf
。数据仍然保存在这个
mbuf
中,但是由于分组首部占用了
8
字节,只有
100
字节的数据可存储在这个
mbuf
中。
3)
当分组数据超过
208
字节的数据时,如果采用前面提到的
1/2
类
mbuf
,需要
3
个或更多的
mbuf
,
这时我们就要使用一种称之为簇的
mbuf
,就是我们下面讲到的
mbuf
。
第
3
类
m b u f
不包含分组首部
(
没有设置M_PKTHDR
)
,但包含超过
208
字节的数据,这时用到一个叫“簇”的外部缓存
(
设置
M_EXT)
。在此
mbuf
中仍然为分组首部结构分配了空间,但没有用。在这个
mbuf
中,指针mh_data
指向这个簇中的某个位置。
4) 第四类mbuf包含一个分组首部,包含超过208字节的数据,同时设置了标志M_PKTHDR和M_EXT。
4种类型的mbuf结构如下图所示,下面代码中的定义简化了对结构成员变量的访问,是经常使用的一种编程手段,图中都是使用重定义后的名称。
#define
m_next m_hdr.mh_next
#define m_len m_hdr.mh_len
#define m_data m_hdr.mh_data
#define m_type m_hdr.mh_type
#define m_flags m_hdr.mh_flags
#define m_nextpkt m_hdr.mh_nextpkt
#define m_act m_nextpkt
#define m_pkthdr M_dat.MH.MH_pkthdr
#define m_ext M_dat.MH.MH_dat.MH_ext
#define m_pktdat M_dat.MH.MH_dat.MH_databuf
#define m_dat M_dat.M_databuf
#define m_len m_hdr.mh_len
#define m_data m_hdr.mh_data
#define m_type m_hdr.mh_type
#define m_flags m_hdr.mh_flags
#define m_nextpkt m_hdr.mh_nextpkt
#define m_act m_nextpkt
#define m_pkthdr M_dat.MH.MH_pkthdr
#define m_ext M_dat.MH.MH_dat.MH_ext
#define m_pktdat M_dat.MH.MH_dat.MH_databuf
#define m_dat M_dat.M_databuf