多队列网卡简介以及Linux通过网卡发送数据包源码解读

首先我们看一下一个主流多队列网卡(E1000)跟多核CPU之间的关系图:

非多队列:

linux的网卡由结构体net_device表示,一个该结构体对应一个可以调度的数据包发送队列。

数据包的实体在内核中以结构体sk_buff(skb),形如:

多队列:

一个网卡可以拥有多个队列

接下来,看看TX引擎是如何工作的(注:对于发送和接收数据包有两个名词,分别应对TX,RX)

解释:

函数-dev_queue_xmit():入队一个buffer以传输到网络驱动设备。

配合该函数的源码来解释上图的传输过程:

步骤一:可以看到如果设备支持队列,则数据包入设备队列。在入队操作前后,有加锁和释放队列锁的过程。

步骤二:调出设备的qdisc(该对象是队列的排队规则)

QDisc(排队规则)是queueingdiscipline的简写,它是理解流量控制(traffic
control)的基础。无论何时,内核如果需要通过某个网络接口发送数据包,它都需要按照为这个接口配置的qdisc(排队规则)把数据包加入队列。然后,内核会尽可能多地从qdisc里面取出数据包,把它们交给网络适配器驱动模块。最简单的QDisc是pfifo它不对进入的数据包做任何的处理,数据包采用先入先出的方式通过队列。不过,它会保存网络接口一时无法处理的数据包。

步骤三:重置skb的队列映射,置为0

步骤四:tx lock->hard_start_xmit

到这里,我们好像没有看到tx_lock、hard_start_xmit函数,反而我们在无队列的设备分支中看到了这些:

Dev_hard_start_xmit的定义:

很明显我们应该拨开云雾看到一些本质,再次回到设备支持队列的分支中(这才是我们关心的):

不管怎么样,你总该有发送的函数调用吧,就是下面圈起来的这个:

果不其然,这是一个封装函数:

参考:

http://www.landley.net/kdocs/ols/2007/ols2007v2-pages-305-310.pdf

http://vger.kernel.org/~davem/davem_nyc09.pdf

http://www.chineselinuxuniversity.net/kerneldocs/networking/API-dev-queue-xmit.html

http://apps.hi.baidu.com/share/detail/36206005

http://cache.baidu.com/c?m=9d78d513d98017f419bc837f7d01d0120e55f0237b8bc7150ec3e54c84145d563164f4cd25351174c4b5777075d95e2cebe74703234460e99492ce0c9fac935b3295776a2d499141658243f4971532c157c304b2ff4ab7e9e732e4ff8f8cc2040d97061832daabc8015c41ca65ed4771a5fdc816424240b8fa3013a4537d2c992742b750f997682858df&p=ce7ddc1187904eac59b5c4710e14d625&user=baidu&fm=sc&query=qdisc%5Frun+%D6%B4%D0%D0%B9%FD%B3%CC&qid=f6ae9cf00151dde4&p1=1

http://lwn.net/Articles/289137/

原文发布时间为:2012-04-21

时间: 2024-09-18 11:12:36

多队列网卡简介以及Linux通过网卡发送数据包源码解读的相关文章

Linux+Nginx+MySql+Php既LNMP源码安装

我们都知道Apache作为一款出色的web服务器占据了市场大半个江山,他的地位目前还无人能取代,但是除了Apache,,在web服务器软件行列,Nginx以其性能稳定.功能丰富.运维简单.处理静静态文件速度快且消耗系统资源极少的优势,也同样赢得了许多人的青睐. 下面让我们能来了解一下linux下Nginx+mysql+php的源码安装方法. 准备工具: mysql-5.5.15-linux2.6-i686.tar.gz nginx-1.0.11.tar.gz pcre-devel-6.6-2.e

linux下mysql 5.1.73 源码安装笔记

linux下安装mysql有多种方式,相对而言源码安装速度最快,兼容性也会好些.相反,源码安装更麻烦一些. 第一步,下载和解压安装包: mysql 5.1.73官方下载地址. http://dev.mysql.com/get/Downloads/MySQL-5.1/mysql-5.1.73.tar.gz md5:887f869bcc757957067b9198f707f32f 1 md5sum mysql-5.5.38.tar.gz      #计算md5校验和 2 tar -zxf mysql

代码-linux的xterm开启的终端里使用原始套接字发送数据包出错,求助

问题描述 linux的xterm开启的终端里使用原始套接字发送数据包出错,求助 xterm下原始套接字可以接收数据包,但是发送数据包时出错,怎么解决? 错误是[error 101]network is unreachable. 代码如下: proto = socket.getprotobyname('tcp') # only tcp sock = socket.socket( socket.AF_INET, socket.SOCK_RAW, proto ) packet_base = sock.

linux下mysql 5.5.38 源码安装笔记

接上一篇<linux下mysql 5.1.73 源码安装笔记>,继续安装一个mysql 5.5.38 版.同样使用源码安装.并且实现两个实例同时运行,互不冲突. 这篇笔记记录的简单些,省略一些和上篇笔记相同的步骤. 第一步,下载: mysql 5.5.38官方下载地址: http://dev.mysql.com/get/Downloads/MySQL-5.5/mysql-5.5.38.tar.gz df5071c49764c3ad65df04ff20866a86 解压的步骤就不重复了. 第二步

网络编程-Linux socket udp发送数据返回socket错误22

问题描述 Linux socket udp发送数据返回socket错误22 linux下用c网络编程用sendto发送数据,总返回socket error代号22是什么错误呢? 解决方案 http://blog.csdn.net/dog250/article/details/9569855

网络编程-winpcap 发送队列发送数据包的问题

问题描述 winpcap 发送队列发送数据包的问题 我用winpcap的发送队列发送数据包,文件大小100M左右可以正常发送,抓包工具可以抓到包,但200M左右就发不了,运行黑框界面一闪而过,这是为什么,咋解决, 解决方案 WINPCAP发送自己构造的数据包问题winpcap使用:发送数据包

Socket使用Linux SSH代理发送数据

Socket使用Linux SSH代理发送数据 写这篇文章是为了解决项目开发中,在处理第三方接口时,在本地开发调试的问题. 场景: 某应用需要调用发送短信接口发送短信(或调用其他第三方接口),但是这些接口都有服务器IP鉴权,只允许从局方提供的服务器上才能调用. 需求: 接入第三方接口需要一个开发和反复调试的过程,每次将写好的程序上传到服务器上测试很是麻烦,看日志和断点调试又都不方便,现在需要让第三方接口把自己电脑认作是服务器,这样就方便开发调试了. 前提条件: 服务器要可以进行SSH连接,但又没

c# 截止 网卡-用C#怎么阻止网络卡的数据包交付给其他联网程序

问题描述 用C#怎么阻止网络卡的数据包交付给其他联网程序 现在可以用SharpPcap 4.2.0抓到数据包了,也能分析了,就是没有办法阻止网卡将数据包交付给其上层应用程序.请问大神们,怎么做到C#阻止将网卡的数据包交付给其他联网程序 解决方案 我的4.2为啥不能用呀,我从官网上下的列子,一运行就报错unable to open the adapter.但是我3.4用着挺正常的. 解决方案二: 同求,我的4.2也用不了

SEDA简介与源码解读(一)

简介: -------------------------------------------------------------------------------------------------------------------------------------------------------------------- /* *分割线内内容纯粹引用 *原文作者:朱之光 *原文地址:http://larryzhu.bokee.com/6779982.html */ 一.前言 Sta