用户态协议栈学习,DKDK基本用法介绍

简介: 用户态协议栈学习,DKDK基本用法介绍

网络数据流,先了解一下用户态协议栈在什么位置

这里以DPDK为例:(目的是为了获得原始的网络数据,除了DPDK,socket raw,netmap也能获取获取以太网数据)
在这里插入图片描述

1 默认数据流

默认情况下,网络数据经物理网卡,内核协议栈,VFS,最后到达APP

2 DPDK

DPDK接管网卡,它可以把数据送入用户态协议栈,也可以把数据传到sk_buffer中。
因为dpdk的这种特性,实现的用户态协议栈可以直接读写应用程序内存,更加灵活地控制网络数据流,实现更多自定义功能;可以避免系统调用、内核态切换等开销,减少网络数据包传输时的延迟和CPU使用率,提高处理吞吐量。

DPDK 编译与配置

设置环境变量

sudo su
cd 至 dpdk-stable-19.08.2
export RTE_SDK=“路径/”dpdk-stable-19.08.2/
export RTE_TARGET=x86_64-native-linux-gcc

运行./usertools/dpdk-setup.sh ,部分选项解释

Step 1: Select the DPDK environment to build 选择一种编译器编译


[1] arm64-armada-linuxapp-gcc
[2] arm64-armada-linux-gcc
[3] arm64-armv8a-linuxapp-clang
[4] arm64-armv8a-linuxapp-gcc
[5] arm64-armv8a-linux-clang
[6] arm64-armv8a-linux-gcc
[7] arm64-bluefield-linuxapp-gcc
[8] arm64-bluefield-linux-gcc
[9] arm64-dpaa2-linuxapp-gcc
[10] arm64-dpaa2-linux-gcc
[11] arm64-dpaa-linuxapp-gcc
[12] arm64-dpaa-linux-gcc
[13] arm64-octeontx2-linuxapp-gcc
[14] arm64-octeontx2-linux-gcc
[15] arm64-stingray-linuxapp-gcc
[16] arm64-stingray-linux-gcc
[17] arm64-thunderx2-linuxapp-gcc
[18] arm64-thunderx2-linux-gcc
[19] arm64-thunderx-linuxapp-gcc
[20] arm64-thunderx-linux-gcc
[21] arm64-xgene1-linuxapp-gcc
[22] arm64-xgene1-linux-gcc
[23] arm-armv7a-linuxapp-gcc
[24] arm-armv7a-linux-gcc
[25] i686-native-linuxapp-gcc
[26] i686-native-linuxapp-icc
[27] i686-native-linux-gcc
[28] i686-native-linux-icc
[29] ppc_64-power8-linuxapp-gcc
[30] ppc_64-power8-linux-gcc
[31] x86_64-native-bsdapp-clang
[32] x86_64-native-bsdapp-gcc
[33] x86_64-native-freebsd-clang
[34] x86_64-native-freebsd-gcc
[35] x86_64-native-linuxapp-clang
[36] x86_64-native-linuxapp-gcc
[37] x86_64-native-linuxapp-icc
[38] x86_64-native-linux-clang
[39] x86_64-native-linux-gcc ==我这里选择 x86_64-native-linux-gcc,因为我用的系统 ubuntu server x64==
[40] x86_64-native-linux-icc
[41] x86_x32-native-linuxapp-gcc
[42] x86_x32-native-linux-gcc


Step 2: Setup linux environment


[43] Insert IGB UIO module // 插入Intel Gigabit Ethernet驱动程序的用户态I/O(UIO)模块。这个模块可以帮助操作系统与Intel网卡进行通信,并提供网络连接服务。

[44] Insert VFIO module // 将物理设备分配给虚拟机以进行直接访问。这使得虚拟机可以在不影响主机性能的情况下获得更好的 I/O 性能,并提供更高的安全性和隔离性。

[45] Insert KNI module // (KNI)模块,以支持在用户空间和内核空间之间传输数据包。
[46] Setup hugepage mappings for non-NUMA systems //设置巨页系统,
[47] Setup hugepage mappings for NUMA systems
// NUMA systems是一种多处理器计算机体系结构,在多核,多内存条,实现统一编址访问
// 如果接收10G数据,只设置4k大小的内存页的话,就需要频繁访问页表,内存页置换,效率不高,这里根据实际情况设置巨页就很有必要。
[48] Display current Ethernet/Baseband/Crypto device settings
// 显示当前以太网/基带/加密设备的设置。这通常指的是计算机或网络设备上的硬件设置,例如网络适配器的速度、双工模式、MAC地址和加密协议等
[49] Bind Ethernet/Baseband/Crypto device to IGB UIO module // 将以太网/基带/加密设备绑定到IGB UIO模块
[50] Bind Ethernet/Baseband/Crypto device to VFIO module // 将以太网/基带/加密设备绑定到VFIO模块的
[51] Setup VFIO permissions // 为VFIO设备分配权限,以便可以在虚拟机中使用该设备


Step 3: Run test application for linux environment


[52] Run test application ($RTE_TARGET/app/test)
[53] Run testpmd application in interactive mode ($RTE_TARGET/app/testpmd)


Step 4: Other tools


[54] List hugepage info from /proc/meminfo


Step 5: Uninstall and system cleanup


[55] Unbind devices from IGB UIO or VFIO driver
[56] Remove IGB UIO module
[57] Remove VFIO module
[58] Remove KNI module
[59] Remove hugepage mappings

[60] Exit Script

Option: // 这里输入39回车,就对应step1中的编译环境([39] x86_64-native-linux-gcc)编译了

编译一次即可,编译完成后,就可以按需step2。配置好后,可运行step3中的测试程序。step4,5可根据实际情况使用。

运行./usertools/dpdk-setup.sh shell步骤记录

  1. 输入43, 设置uio module
    ```bash
    Option: 43

Unloading any existing DPDK UIO module
Loading uio module
Loading DPDK UIO module


2. 输入44, 设置VFIO module
```bash
Option: 44

Unloading any existing VFIO module
Loading VFIO module
chmod /dev/vfio
OK
  1. 输入45, 设置KNI module
    ```bash
    Option: 45

Unloading any existing DPDK KNI module
Loading DPDK KNI module

4. 输入46,设置hugepages
```bash
Option: 46

Removing currently reserved hugepages
Unmounting /mnt/huge and removing directory

  Input the number of 1048576kB hugepages
  Example: to have 128MB of hugepages available in a 2MB huge page system,
  enter '64' to reserve 64 * 2MB pages
Number of pages: 512
Reserving hugepages
Creating /mnt/huge and mounting as hugetlbfs
  1. 输入47,设置hugepages for each node
Option: 47

Removing currently reserved hugepages
Unmounting /mnt/huge and removing directory

  Input the number of 1048576kB hugepages for each node
  Example: to have 128MB of hugepages available per node in a 2MB huge page system,
  enter '64' to reserve 64 * 2MB pages on each node
Number of pages for node0: 512
Reserving hugepages
Creating /mnt/huge and mounting as hugetlbfs
  1. 输入48,显示设备
Network devices using kernel driver
===================================
0000:02:01.0 '82545EM Gigabit Ethernet Controller (Copper) 100f' if=eth2 drv=e1000 unused=igb_uio,vfio-pci 
0000:02:06.0 '82545EM Gigabit Ethernet Controller (Copper) 100f' if=eth3 drv=e1000 unused=igb_uio,vfio-pci 
0000:03:00.0 'VMXNET3 Ethernet Controller 07b0' if=eth0 drv=vmxnet3 unused=igb_uio,vfio-pci 
0000:0b:00.0 'VMXNET3 Ethernet Controller 07b0' if=eth1 drv=vmxnet3 unused=igb_uio,vfio-pci *Active*

No 'Baseband' devices detected
==============================

No 'Crypto' devices detected
============================

No 'Eventdev' devices detected
==============================

No 'Mempool' devices detected
=============================

No 'Compress' devices detected
==============================

No 'Misc (rawdev)' devices detected
===================================
  1. 输入49,修改绑定的设备,这里是: bind to IGB UIO driver: eth0(或者填入:0000:03:00.0 都可以)
    ==这里的绑定是为了让DPDK接管网卡==
    ```bash
    Option: 49

    Network devices using kernel driver

    0000:02:01.0 '82545EM Gigabit Ethernet Controller (Copper) 100f' if=eth2 drv=e1000 unused=igb_uio,vfio-pci
    0000:02:06.0 '82545EM Gigabit Ethernet Controller (Copper) 100f' if=eth3 drv=e1000 unused=igb_uio,vfio-pci
    0000:03:00.0 'VMXNET3 Ethernet Controller 07b0' if=eth0 drv=vmxnet3 unused=igb_uio,vfio-pci
    0000:0b:00.0 'VMXNET3 Ethernet Controller 07b0' if=eth1 drv=vmxnet3 unused=igb_uio,vfio-pci Active

No 'Baseband' devices detected

No 'Crypto' devices detected

No 'Eventdev' devices detected

No 'Mempool' devices detected

No 'Compress' devices detected

No 'Misc (rawdev)' devices detected

Enter PCI address of device to bind to IGB UIO driver: (这里输入pci地址)0000:0b:00.0
Warning: routing table indicates that interface 0000:0b:00.0 is active. Not modifying ====> 注意有警告,是因为这个设备被占用了,
这个是后可以另起一个终端,执行sudo ifconfig eth0 down, 把它关掉
(查看网卡信息 lspci -k | grep -A 2 -i "Ethernet")
OK

绑定好的可以通过输入55,删除绑定,如下,vmxnet3正是.vmx文件中设置的 (删除绑定)
Enter PCI address of device to unbind: 0000:03:00.0
Enter name of kernel driver to bind the device to: vmxnet3



### 注意事项
在有多个网卡的情况下,ifconfig 看到的eth0,eth1与.vmx文件中的 ethernet0, ethernet1可能不是一一对应的关系

### 测试

```bash
Option: 53


  Enter hex bitmask of cores to execute testpmd app on
  Example: to execute app on cores 0 to 7, enter 0xff
bitmask: 7
Launching app
EAL: Detected 4 lcore(s)
EAL: Detected 1 NUMA nodes
EAL: Multi-process socket /var/run/dpdk/rte/mp_socket
EAL: Selected IOVA mode 'PA'
EAL: Probing VFIO support...
EAL: VFIO support initialized
EAL: PCI device 0000:02:01.0 on NUMA socket -1
EAL:   Invalid NUMA socket, default to 0
EAL:   probe driver: 8086:100f net_e1000_em
EAL: PCI device 0000:02:06.0 on NUMA socket -1
EAL:   Invalid NUMA socket, default to 0
EAL:   probe driver: 8086:100f net_e1000_em
EAL: PCI device 0000:03:00.0 on NUMA socket -1
EAL:   Invalid NUMA socket, default to 0
EAL:   probe driver: 15ad:7b0 net_vmxnet3
EAL: PCI device 0000:0b:00.0 on NUMA socket -1
EAL:   Invalid NUMA socket, default to 0
EAL:   probe driver: 15ad:7b0 net_vmxnet3
Interactive-mode selected
testpmd: create a new mbuf pool <mbuf_pool_socket_0>: n=163456, size=2176, socket=0
testpmd: preferred mempool ops selected: ring_mp_mc

Warning! port-topology=paired and odd forward ports number, the last port will pair with itself.

Configuring Port 0 (socket 0)
Port 0: 00:0C:29:A3:11:BF
Checking link statuses...
Done
testpmd> help

Help is available for the following sections:

    help control                    : Start and stop forwarding.
    help display                    : Displaying port, stats and config information.
    help config                     : Configuration information.
    help ports                      : Configuring ports.
    help registers                  : Reading and setting port registers.
    help filters                    : Filters configuration help.
    help traffic_management         : Traffic Management commmands.
    help devices                    : Device related cmds.
    help all                        : All of the above sections.

testpmd> help control

Control forwarding:
-------------------

start
    Start packet forwarding with current configuration.

start tx_first
    Start packet forwarding with current config after sending one burst of packets.

stop
    Stop packet forwarding, and display accumulated statistics.

quit
    Quit to prompt.

testpmd> start
io packet forwarding - ports=1 - cores=1 - streams=1 - NUMA support enabled, MP allocation mode: native
Logical Core 1 (socket 0) forwards packets on 1 streams:
  RX P=0/Q=0 (socket 0) -> TX P=0/Q=0 (socket 0) peer=02:00:00:00:00:00

  io packet forwarding packets/burst=32
  nb forwarding cores=1 - nb forwarding ports=1
  port 0: RX queue number: 1 Tx queue number: 1
    Rx offloads=0x0 Tx offloads=0x0
    RX queue: 0
      RX desc=0 - RX free threshold=0
      RX threshold registers: pthresh=0 hthresh=0  wthresh=0
      RX Offloads=0x0
    TX queue: 0
      TX desc=0 - TX free threshold=0
      TX threshold registers: pthresh=0 hthresh=0  wthresh=0
      TX offloads=0x0 - TX RS bit threshold=0
testpmd> show port info 0

********************* Infos for port 0  *********************
MAC address: 00:0C:29:A3:11:BF
Device name: 0000:03:00.0
Driver name: net_vmxnet3
Connect to socket: 0
memory allocation on the socket: 0
Link status: up
Link speed: 10000 Mbps
Link duplex: full-duplex
MTU: 1500
Promiscuous mode: enabled
Allmulticast mode: disabled
Maximum number of MAC addresses: 1
Maximum number of MAC addresses of hash filtering: 0
VLAN offload: 
  strip off 
  filter off 
  qinq(extend) off 
Supported RSS offload flow types:
  ipv4
  ipv4-tcp
  ipv6
  ipv6-tcp
Minimum size of RX buffer: 1646
Maximum configurable length of RX packet: 16384
Current number of RX queues: 1
Max possible RX queues: 16
Max possible number of RXDs per queue: 4096
Min possible number of RXDs per queue: 128
RXDs number alignment: 1
Current number of TX queues: 1
Max possible TX queues: 8
Max possible number of TXDs per queue: 4096
Min possible number of TXDs per queue: 512
TXDs number alignment: 1
Max segment number per packet: 255
Max segment number per MTU/TSO: 16

文章参考与<零声教育>的C/C++linux服务期高级架构系统教程学习:链接

相关文章
|
1月前
|
存储 C语言 C++
【C++数据结构——栈与队列】顺序栈的基本运算(头歌实践教学平台习题)【合集】
本关任务:编写一个程序实现顺序栈的基本运算。开始你的任务吧,祝你成功!​ 相关知识 初始化栈 销毁栈 判断栈是否为空 进栈 出栈 取栈顶元素 1.初始化栈 概念:初始化栈是为栈的使用做准备,包括分配内存空间(如果是动态分配)和设置栈的初始状态。栈有顺序栈和链式栈两种常见形式。对于顺序栈,通常需要定义一个数组来存储栈元素,并设置一个变量来记录栈顶位置;对于链式栈,需要定义节点结构,包含数据域和指针域,同时初始化栈顶指针。 示例(顺序栈): 以下是一个简单的顺序栈初始化示例,假设用C语言实现,栈中存储
156 77
|
13天前
|
DataX
☀☀☀☀☀☀☀有关栈和队列应用的oj题讲解☼☼☼☼☼☼☼
### 简介 本文介绍了三种数据结构的实现方法:用两个队列实现栈、用两个栈实现队列以及设计循环队列。具体思路如下: 1. **用两个队列实现栈**: - 插入元素时,选择非空队列进行插入。 - 移除栈顶元素时,将非空队列中的元素依次转移到另一个队列,直到只剩下一个元素,然后弹出该元素。 - 判空条件为两个队列均为空。 2. **用两个栈实现队列**: - 插入元素时,选择非空栈进行插入。 - 移除队首元素时,将非空栈中的元素依次转移到另一个栈,再将这些元素重新放回原栈以保持顺序。 - 判空条件为两个栈均为空。
|
1月前
|
存储 C++ 索引
【C++数据结构——栈与队列】环形队列的基本运算(头歌实践教学平台习题)【合集】
【数据结构——栈与队列】环形队列的基本运算(头歌实践教学平台习题)【合集】初始化队列、销毁队列、判断队列是否为空、进队列、出队列等。本关任务:编写一个程序实现环形队列的基本运算。(6)出队列序列:yzopq2*(5)依次进队列元素:opq2*(6)出队列序列:bcdef。(2)依次进队列元素:abc。(5)依次进队列元素:def。(2)依次进队列元素:xyz。开始你的任务吧,祝你成功!(4)出队一个元素a。(4)出队一个元素x。
50 13
【C++数据结构——栈与队列】环形队列的基本运算(头歌实践教学平台习题)【合集】
|
1月前
|
存储 C语言 C++
【C++数据结构——栈与队列】链栈的基本运算(头歌实践教学平台习题)【合集】
本关任务:编写一个程序实现链栈的基本运算。开始你的任务吧,祝你成功!​ 相关知识 初始化栈 销毁栈 判断栈是否为空 进栈 出栈 取栈顶元素 初始化栈 概念:初始化栈是为栈的使用做准备,包括分配内存空间(如果是动态分配)和设置栈的初始状态。栈有顺序栈和链式栈两种常见形式。对于顺序栈,通常需要定义一个数组来存储栈元素,并设置一个变量来记录栈顶位置;对于链式栈,需要定义节点结构,包含数据域和指针域,同时初始化栈顶指针。 示例(顺序栈): 以下是一个简单的顺序栈初始化示例,假设用C语言实现,栈中存储整数,最大
49 9
|
1月前
|
C++
【C++数据结构——栈和队列】括号配对(头歌实践教学平台习题)【合集】
【数据结构——栈和队列】括号配对(头歌实践教学平台习题)【合集】(1)遇到左括号:进栈Push()(2)遇到右括号:若栈顶元素为左括号,则出栈Pop();否则返回false。(3)当遍历表达式结束,且栈为空时,则返回true,否则返回false。本关任务:编写一个程序利用栈判断左、右圆括号是否配对。为了完成本关任务,你需要掌握:栈对括号的处理。(1)遇到左括号:进栈Push()开始你的任务吧,祝你成功!测试输入:(()))
43 7
|
3月前
|
存储 缓存 算法
在C语言中,数据结构是构建高效程序的基石。本文探讨了数组、链表、栈、队列、树和图等常见数据结构的特点、应用及实现方式
在C语言中,数据结构是构建高效程序的基石。本文探讨了数组、链表、栈、队列、树和图等常见数据结构的特点、应用及实现方式,强调了合理选择数据结构的重要性,并通过案例分析展示了其在实际项目中的应用,旨在帮助读者提升编程能力。
103 5
|
3月前
|
算法
数据结构之购物车系统(链表和栈)
本文介绍了基于链表和栈的购物车系统的设计与实现。该系统通过命令行界面提供商品管理、购物车查看、结算等功能,支持用户便捷地管理购物清单。核心代码定义了商品、购物车商品节点和购物车的数据结构,并实现了添加、删除商品、查看购物车内容及结算等操作。算法分析显示,系统在处理小规模购物车时表现良好,但在大规模购物车操作下可能存在性能瓶颈。
75 0
|
3月前
|
C语言
【数据结构】栈和队列(c语言实现)(附源码)
本文介绍了栈和队列两种数据结构。栈是一种只能在一端进行插入和删除操作的线性表,遵循“先进后出”原则;队列则在一端插入、另一端删除,遵循“先进先出”原则。文章详细讲解了栈和队列的结构定义、方法声明及实现,并提供了完整的代码示例。栈和队列在实际应用中非常广泛,如二叉树的层序遍历和快速排序的非递归实现等。
364 9
|
3月前
|
存储 算法
非递归实现后序遍历时,如何避免栈溢出?
后序遍历的递归实现和非递归实现各有优缺点,在实际应用中需要根据具体的问题需求、二叉树的特点以及性能和空间的限制等因素来选择合适的实现方式。
58 1
|
3月前
|
存储 算法 Java
数据结构的栈
栈作为一种简单而高效的数据结构,在计算机科学和软件开发中有着广泛的应用。通过合理地使用栈,可以有效地解决许多与数据存储和操作相关的问题。
124 21