- 论坛徽章:
- 6
|
《一》RPS是google向内核提交的一个软中断负载均衡的patch。(好像从2.6.35开始,这个patch才进入了linux的main tree)
这里简单说明一下RPS的处理流程:
在3.0.2中所有的网卡,不管是否支持napi,都是通过struct napi_struct结构进行。所有我们先说一下这个结构。- struct napi_struct {
- 354 /* The poll_list must only be managed by the entity which
- 355 * changes the state of the NAPI_STATE_SCHED bit. This means
- 356 * whoever atomically sets that bit can add this napi_struct
- 357 * to the per-cpu poll_list, and whoever clears that bit
- 358 * can remove from the list right before clearing the bit.
- 359 */
- 360 struct list_head poll_list;
- 361
- 362 unsigned long state;
- 363 int weight;
- 364 int (*poll)(struct napi_struct *, int);
- 365 #ifdef CONFIG_NETPOLL
- 366 spinlock_t poll_lock;
- 367 int poll_owner;
- 368 #endif
- 369
- 370 unsigned int gro_count;
- 371
- 372 struct net_device *dev;
- 373 struct list_head dev_list;
- 374 struct sk_buff *gro_list;
- 375 struct sk_buff *skb;
- 376 };
复制代码 对应支持napi的网卡,自己填充这个结构体;而非napi网卡,则使用per cpu的softnet_data->backlog,这个结构的初始化在net_dev_init()中完成。
我们先说一下非napi机制的网卡:
这里还是区分NAPI的网卡和非NAPI的网卡
1. 非NAPI的网卡:
驱动接收到数据包-->dma到内核空间-->netif_rx-->enqueue_to_backlog (根据数据包的hash值,将数据包放到对应的CPU的softnet_data.input_pkt_queue中)-->等待软中断调度
软中断调度后,会执行函数process_backlog。(这个函数最后会调用netif_receive_skb,将skb向上层传递)
2. NAPI的网卡:
驱动接收到数据包-->dma到内核空间-->将数据包放到自动的队列中-->等待软中断调度
在之前的内核版本中(RPS功能添加之前),NAPI的网卡软中断调度,直接从网卡自己的队列中dequeue一个skb,然后netif_receive_skb(),直接将数据包向上层传递。
在RPS的内核中,netif_receive_skb()函数并不是直接向上层传递skb,而是:
dequeue-个skb-->enqueue_to_backlog(根据数据包的hash值,将数据包放到对应的CPU的softnet_data.input_pkt_queue中)-->等待软中断调度。
也就是说,在RPS的内核下,不管你是否是NAPI的驱动,所有的数据包在真正处理之前,都会放到相应的每cpu的softnet_data.input_pkt_queue,然后再被处理。 |
评分
-
查看全部评分
|