NAPI中断禁用和处理共享中断线

时间:2016-07-27 08:10:29

标签: linux linux-kernel network-programming linux-device-driver

我正在尝试理解Linux内核中的NAPI实现。这些是我的基本疑虑。

1)NAPI禁用进一步的中断并使用轮询处理skbs

  • 谁禁用它?
  • 中断处理程序是否应禁用它?

    如果是 - 禁用中断和处理实际轮询的SOFTIRQ net_rx_action之间的时间差距是不是太大了。

2)默认情况下,所有启用NAPI的驱动程序在接收单帧时禁用中断并使用下半部分轮询处理剩余帧? 或者是否有逻辑,其中只有框架> 32(在连续接收irq处理程序中的所有帧时)切换到轮询模式?

3)现在来到SHARED IRQ -

  • 其他设备中断会发生什么,其他设备下半部分可能无法运行,因为poll_list中没有这些设备。

1 个答案:

答案 0 :(得分:5)

我写了一本关于understanding, tuning, and optimizing the Linux network stack的综合指南,它解释了有关网络驱动程序,NAPI等的所有内容,请查看。

至于你的问题:

  1. 在启用NAPI后,驱动程序的IRQ处理程序应禁用设备IRQ。是的,存在时间差,但它应该很小。这是您必须做出的权衡决定的一部分:您是否更关心吞吐量或延迟?根据具体情况,您可以适当地优化网络堆栈。在任何情况下,大多数NIC允许用户增加(或减少)跟踪传入网络数据的环形缓冲区的大小。因此,暂停很好,因为数据包将稍后排队等待处理。

  2. 这取决于驱动程序,但通常大多数驱动程序将在IRQ处理程序中启用NAPI轮询模式,只要通过调用napi_schedule(通常)触发它。您可以找到如何NAPI is enabled for the Intel igb driver here.的演练。请注意,不必为每个数据包触发IRQ处理程序。您可以使用名为interrupt coalescing的功能调整IRQ处理程序在大多数卡上触发的速率。某些NIC可能不支持此选项。

  3. 当IRQ被触发时,将执行其他设备的IRQ处理程序,因为IRQ处理程序在CPU上具有非常高的优先级。 NAPI轮询循环(在SoftIRQ中运行)将在设备IRQ处理的任何CPU上运行。因此,如果您有多个NIC和多个CPU,则可以调整每个NIC的IRQ的IRQ亲和性,以防止使特定NIC匮乏。

  4. 至于你在评论中提到的例子:

  5.   假设NIC 1和NIC 2共享IRQ线,假设NIC 1为低负载,NIC 2为高负载且NIC 1接收中断,NIC 1的驱动程序将禁用中断,直到它的softirq被处理为止,称时间间隔为t1 。所以对于时间t1,NIC 2的中断过于禁用,对吧?

    这取决于驱动程序,但在正常情况下,NIC 1仅在执行IRQ处理程序时禁用中断。对napi_schedule的调用告诉softirq代码,如果尚未启动它应该开始运行。 softirq代码异步运行,因此没有NIC 1不等待softirq被处理。

    现在,就共享IRQ而言:再次取决于设备和驱动程序。应该以能够处理共享IRQ的方式编写驱动程序。如果驱动程序禁用正在共享的IRQ,则共享该IRQ的所有设备都不会收到中断。这会很糟糕。某些设备解决此问题的一种方法是允许驱动程序读取/写入特定寄存器,从而导致该特定设备停止生成中断。这是一个首选解决方案,因为它不会阻止生成相同IRQ的其他设备。

    当为NAPI禁用IRQ时,意味着驱动程序要求NIC硬件停止发送IRQ。因此,同一行(对于其他设备)的其他IRQ仍将继续处理。以下是Intel igb driver如何通过写入寄存器来关闭该器件的IRQ的示例。