kernel version:2.6.32.61
驱动收包完成后,触发硬中断,会调用到以下中断处理函数:
驱动收包完成后,触发硬中断,会调用到以下中断处理函数:
net/core/dev.c
2016 int netif_rx(struct sk_buff *skb)
2017 {
2018 struct softnet_data *queue;
2019 unsigned long flags;
2020
2021 /* if netpoll wants it, pretend we never saw it */
// 查看netpoll是否关注这个包,如果关注则丢弃这个包。
2022 if (netpoll_rx(skb))
2023 return NET_RX_DROP;
2024
// 记录收包时间。
2025 if (!skb->tstamp.tv64)
2026 net_timestamp(skb);
2027
2028 /*
2029 * The code is rearranged so that the path is the most
2030 * short when CPU is congested, but is still operating.
2031 */
// 关闭中断。
2032 local_irq_save(flags);
// 得到当前CPU变量
2033 queue = &__get_cpu_var(softnet_data);
2034
// 统计信息。
2035 __get_cpu_var(netdev_rx_stat).total++;
2036 if (queue->input_pkt_queue.qlen <= netdev_max_backlog) {
2037 if (queue->input_pkt_queue.qlen) {
2038 enqueue:
// 如果队列长度不为0,则说明队列中还有未处理完的包,此时仅将包加入队列中,打开中断,并退出。
2039 __skb_queue_tail(&queue->input_pkt_queue, skb);
2040 local_irq_restore(flags);
2041 return NET_RX_SUCCESS;
2042 }
2043
// 队列长度为0时,触发软中断。
2044 napi_schedule(&queue->backlog);
2045 goto enqueue;
2046 }
2047
// 统计信息。
2048 __get_cpu_var(netdev_rx_stat).dropped++;
// 打开中断。
2049 local_irq_restore(flags);
2050
2051 kfree_skb(skb);
2052 return NET_RX_DROP;
2053 }