上面提到的在TC egress中skb->data_end-skb->data实际是IP+TCP+eth的大小,但是ingress中skb->data_end-skb->data实际是IP+TCP+eth+payload的大小的原因就是非线性区的存在导致的。 也就是data_end - data其实是线性区的大小,而skb->len是线性区加非线性区的大小,前者其实是skb->data_len,但是BPF程序中无...
data_len字段:存在分散报文,data_len表示分片的部分大小 如下所示,没有开启分片的报文len = x,data_len = 0: 如下所示在Linux内核中,使用skb_is_nonlinear函数判断是否存在分片,即通过判断data_len的大小是否为0: 在没有开启分片的报文中,数据包长度在struct sk_buff中为len字段的大小,即data到tail的长度,nf...
处理n层协议的函数把本层的指针(例如,L3对应的是skb->nh指针)初始化为skb->data,因为这个指针的值会在处理下一层协议时改变(skb->data将被初始化成缓冲区里的其他地址)。在处理n层协议的函数结束时,在把包传递给n+1层的处理函数前,它会把skb->data指针指向n层协议头的末尾,这正好是n+1层协议的协议头(...
http://blog.csdn.net/kakadiablo/article/details/7948414 struct sk_buff *skb; skb->len 是data长度,包含所带分片长度 skb->data_len 是paged data长度, 即分片数据的长度,也就是skb_shared_info中的长度 skb_headlen skb->len - skb->data_len 是当前片(unpaged data)长度...
Data buffer:用于存储packet data的缓冲区,分为以上两部分。 Sk_buff:缓冲区控制结构sk_buff。 整个sk_buff结构图如图1。 图1 sk_buff结构图 3 struct sk_buff结构体 /* struct sk_buff - socket buffer */ struct sk_buff { /* These two members must be first. */ ...
data指针在数据包头部封装和解封装的过程中移动,指向各层的协议头,skb_push函数将data的指向,向低地址移动(向上),完成协议头空间的占据,skb_pull函数将data的指向,向高地址移动(向下),完成协议头的解封装。 tail指针在增加应用层用户缓冲数据时移动,skb_put函数将该指针向高地址移动(向上),完成用户数据空间的占据...
data:指向实际数据开始位置的指针。 tail:指向当前缓冲区末尾的指针,可以用于添加更多数据。 end:表示缓冲区的结束位置,用于限制写入操作。 len:当前有效数据的长度。 protocol:数据包所使用的协议类型(如 IPv4、IPv6、ARP 等)。 dev:指向与此数据包相关联的网络设备(network device)的指针。
*data;//数据头指针 unsigned int truesize;//此缓存区的大小,包括sk_buff本身结构大小。 refcount_t users;//引用计数,使用缓冲区实例的数目 }; 1.1.1.1 sk_buff_head定义 用于管理套接字缓冲区。 双向列表头,定义如下: struct sk_buff_head { /* These two members must be first. */ struct sk_buff...
sk_buff->headsk_buff->datask_buff->tailsk_buff->end它们表示缓冲区和数据部分的边界。在每一层申请缓冲区时,它会分配比协议头或协议数据大的空间。head和end指向缓冲区的头部和尾部,而data和 tail指向实际数据的头部和尾部。每一层会在head和data之间填充协议头,或者在tail和end之间添加新的协议数据。数据部...
data_len 中存放的是非线性的数据,也就是整体上不是连续的数据; l(1) 表示的是线性的数据,是连续的。 下图解释了struct sk_buff中head, end, data, tail字段的含义: struct sk_buff结构体中的pkt_type字段的取值为: 通过struct sk_buff中的pkt_type字段中的值,可以判断出接收到的数据包是不是发送给本机...