看Linux网管员如何进行网络性能优化

发表于:2011-1-04 09:45

字体: | 上一篇 | 下一篇 | 我要投稿

 作者:赵军    来源:51Testing软件测试网采编

分享:

  在该结构体中:

  dev:指向支持 LRO 功能的网络设备

  stats:包含一些统计信息,用于查看 LRO 功能的运行情况

  features:控制 LRO 如何将包送给网络协议栈,其中的 LRO_F_NAPI 表明驱动是 NAPI 兼容的,应该使用 netif_receive_skb() 函数,而 LRO_F_EXTRACT_VLAN_ID 表明驱动支持 VLAN

  ip_summed:表明是否需要网络协议栈支持 checksum 校验

  ip_summed_aggr:表明聚集起来的大数据包是否需要网络协议栈去支持 checksum 校验

  max_desc:表明最大数目的 LRO 描述符,注意,每个 LRO 的描述符描述了一路 TCP 流,所以该值表明了做多同时能处理的 TCP 流的数量

  max_aggr:是最大数目的包将被聚集成一个超级数据包

  lro_arr:是描述符数组,需要驱动自己提供足够的内存或者在内存不足时处理异常

  get_skb_header()/get_frag_header():用于快速定位 IP 或者 TCP 的头,一般驱动只提供其中的一个实现

  一般在驱动中收包,使用的函数是 netif_rx 或者 netif_receive_skb,但在支持 LRO 的驱动中,需要使用下面的函数,这两个函数将进来的数据包根据 LRO 描述符进行分类,如果可以进行聚集,则聚集为一个超级数据包,否者直接传递给内核,走正常途径。需要 lro_receive_frags 函数的原因是某些驱动直接将数据包放入了内存页,之后去构造 sk_buff,对于这样的驱动,应该使用下面的接口:

  LRO 收包函数

void lro_receive_skb(struct net_lro_mgr *lro_mgr,
                  struct sk_buff
*skb,
                  void
*priv);

void lro_receive_frags(struct net_lro_mgr
*lro_mgr,
                       struct skb_frag_struct
*frags,
              
int len, int true_size,
               void
*priv, __wsum sum);

  因为 LRO 需要聚集到 max_aggr 数目的数据包,但有些情况下可能导致延迟比较大,这种情况下,可以在聚集了部分包之后,直接传递给网络协议栈处理,这时可以使用下面的函数,也可以在收到某个特殊的包之后,不经过 LRO,直接传递个网络协议栈:

  LRO flush 函数

void lro_receive_skb(struct net_lro_mgr *lro_mgr,
                  struct sk_buff
*skb,
                  void
*priv);

void lro_receive_frags(struct net_lro_mgr
*lro_mgr,
                       struct skb_frag_struct
*frags,
              
int len, int true_size,
               void
*priv, __wsum sum);

  GRO (Generic Receive Offload)

  前面的 LRO 的核心在于:在接收路径上,将多个数据包聚合成一个大的数据包,然后传递给网络协议栈处理,但 LRO 的实现中存在一些瑕疵:

  1、数据包合并可能会破坏一些状态;

  2、数据包合并条件过于宽泛,导致某些情况下本来需要区分的数据包也被合并了,这对于路由器是不可接收的;

  3、在虚拟化条件下,需要使用桥接功能,但 LRO 使得桥接功能无法使用;

  4、实现中,只支持 IPv4 的 TCP 协议。

  而解决这些问题的办法就是新提出的 GRO(Generic Receive Offload),首先,GRO 的合并条件更加的严格和灵活,并且在设计时,就考虑支持所有的传输协议,因此,后续的驱动,都应该使用 GRO 的接口,而不是 LRO,内核可能在所有先有驱动迁移到 GRO 接口之后将 LRO 从内核中移除。而 Linux 网络子系统的维护者 David S. Miller 就明确指出,现在的网卡驱动,有 2 个功能需要使用,一是使用 NAPI 接口以使得中断缓和 (interrupt mitigation) ,以及简单的互斥,二是使用 GRO 的 NAPI 接口去传递数据包给网路协议栈。

  在 NAPI 实例中,有一个 GRO 的包的列表 gro_list,用堆积收到的包,GRO 层用它来将聚集的包分发到网络协议层,而每个支持 GRO 功能的网络协议层,则需要实现 gro_receive 和 gro_complete 方法。

2023测试行业从业人员调查问卷已开启,千元大奖正在等你~

关注51Testing

联系我们

快捷面板 站点地图 联系我们 广告服务 关于我们 站长统计 发展历程

法律顾问:上海兰迪律师事务所 项棋律师
版权所有 上海博为峰软件技术股份有限公司 Copyright©51testing.com 2003-2023
投诉及意见反馈:webmaster@51testing.com; 业务联系:service@51testing.com 021-64471599-8017

沪ICP备05003035号

沪公网安备 31010102002173号