• Virtio-user使用简介


    一、简述​

            DPDK支持几种方式让用户空间的报文重新进入内核协议栈(这种dpdk和kernel直接通信的路径叫做exception path),例如tap/tun设备使用,kni,Virtio-user。这里主要讲Virtio-user使用,Virtio-user是virtio PMD的虚拟设备,启动DPDK virtio-user,系统就会创建一个内核态的虚拟设备tap。下面介绍Virtio-user的使用和使用前驱动的安装。​​

    二、驱动安装过程​

    现在内核基本都自带vfio-pci或者uio_pci_generic驱动,基本不需要igb_uio,igb_uio在20.11版本已经从dpdk目录内移除,Virtio-user依赖vfio-pci.ko驱动,安装好驱动后需要将网卡绑定到该驱动。

    2.1 vfio-pci.ko驱动安装

    在安装驱动前需要注意看下系统是否支持虚拟IO技术(例如intel@VT-d),或是否支持并开启了IOMMU(Input/Output Memory Management Unit),如果支持IOMMU那么使用2.1.1小节中的安装方式,如果不支持,使用2.1.2小节中的安装方式。Linux是否支持虚拟IO技术可使用下面的命令查看:

    1. cat /proc/cpuinfo | grep vmx #有结果说明支持intel-vt虚拟化
    2. cat /proc/cpuinfo | grep svm #有结果说明支持amd-vt虚拟化

    如果不支持虚拟化则建议换no-IOMMU的方式启动。如果是虚拟机环境,在虚拟机的cpu选项中可以将虚拟化引擎都进行勾选。

    2.1.1 IOMMU模式驱动安装

    使用IOMMU模式安装驱动,在驱动安装之前需要设置或者启用iommu,需要在linux启动配置中添加intel_iommu=on iommu=pt,如果是amd的cpu使用amd_iommu=on iommu=pt置方式如下:

    1. $ sudo vim /etc/default/grub # 在GRUB_CMDLINE_LINUX行添加intel_iommu=on iommu=pt
    2. $ sudo update-grub #更新linux启动配置文件,这里是Ubuntu环境,若centos使用命令:grub2-mkconfig -o /boot/grub2/grub.cfg
    3. $ sudo reboot #重启系统
    4. #重启之后可以使用cat /proc/cmdline查看有“intel_iommu=on iommu=pt”标识

    待iommu设置好了之后按照下面的命令安装驱动即可。

    sudo modprobe vfio-pci

    2.1.2 no-IOMMU模式驱动安装

    如果设备硬件不支持IO虚拟化,那么就不能够使用IOMMU模式加载驱动,需要使用下面的方式加载驱动。如果之前已经使用安装了vfio-pci了,那需要卸载所有vfio相关的驱动,然后重新按照下面的方式安装:

    1. 将vfio相关的驱动都卸载掉
    2. rmmod vfio_iommu_type1
    3. rmmod vfio-pci
    4. rmmod vfio
    5. #重新安装驱动
    6. modprobe vfio enable_unsafe_noiommu_mode=1
    7. modprobe vfio-pci

    2.2 绑定网卡

    使用脚本查看当前的网卡设备绑定情况:​

    1. root#./usertools/dpdk-devbind.py -s
    2. # Network devices using kernel driver
    3. ===================================
    4. 0000:00:03.0 '82540EM Gigabit Ethernet Controller 100e' if=enp0s3 drv=e1000 unused=vfio-pci *Active*
    5. 0000:00:08.0 '82540EM Gigabit Ethernet Controller 100e' if=enp0s8 drv=e1000 unused=vfio-pci *Active*
    6. 0000:00:09.0 '82540EM Gigabit Ethernet Controller 100e' if=enp0s9 drv=e1000 unused=vfio-pci *Active*
    7. No 'Baseband' devices detected
    8. ==============================
    9. ... ...

    从上面可以看到系统有3张网卡,这里使用第三个enp0s9 网卡,因为该设备是在使用状态,所以需要将网卡down之后再绑定,操作命令如下:

    1. >ifconfig enp0s9 down #将要绑定的网卡状态设置为down
    2. >./usertools/dpdk-devbind.py -b vfio-pci 0000:00:09.0 #将网卡和驱动绑定,这里填写的网卡的pci地址
    3. >./usertools/dpdk-devbind.py -s #再次查看绑定的情况
    4. Network devices using DPDK-compatible driver
    5. ============================================
    6. 0000:00:09.0 '82540EM Gigabit Ethernet Controller 100e' drv=vfio-pci unused=e1000
    7. Network devices using kernel driver
    8. ===================================
    9. 0000:00:03.0 '82540EM Gigabit Ethernet Controller 100e' if=enp0s3 drv=e1000 unused=vfio-pci *Active*
    10. 0000:00:08.0 '82540EM Gigabit Ethernet Controller 100e' if=enp0s8 drv=e1000 unused=vfio-pci *Active*
    11. No 'Baseband' devices detected
    12. ==============================
    13. ... ...

    当“Network devices using DPDK-compatible driver”下出现需要的Ethernet设备之后就表示绑定成功,后面dpdk程序就可以使用该网络设备(Network devices)。

    ​三、启动并使用

    在启动程序前,假设大页内存等都已经设置好。

    3.1 使用启动参数添加虚拟网卡

    dpdk应用程序都会有EAL环境初始化,使用rte_eal_init初始化中可以解析入参是否需要增加虚拟设备,例如使用testpmd启动方式如下:

    1. 形式如下:
    2. ./dpdk-testpmd -l -a --vdev=virtio_user0,path=/dev/vhost-net,queues=,queue_size=
    3. 例如:
    4. ./dpdk-testpmd -a 0000:00:09.0 --vdev=virtio_user0,path=/dev/vhost-net,queues=1,queue_size=512

    其中涉及到的启动参数主要是:

    --vdev :启动程序时添加一个虚拟设备。

    在--vdev参数后面还可以接:

            path :内核vhost-net设备的路径。

            queue_size :默认是256,以防度队列过短我们可以最大设置到1024。

            queues :虚拟队列的数量,每个队列由一个内核线程管理。

            iface :虚拟设备的名字

    启动程序之后可以使用ifconfig -a命令看到有个设备名为tap0,即表示虚拟设备添加成功​,如下:

    1. root@ubuntu:~/dpdk/dpdk-stable-21.11.1/usertools#
    2. ... ...
    3. tap0: flags=4098 mtu 1500
    4. ether ca:6f:0b:ac:36:4c txqueuelen 1000 (Ethernet)
    5. RX packets 0 bytes 0 (0.0 B)
    6. RX errors 0 dropped 0 overruns 0 frame 0
    7. TX packets 0 bytes 0 (0.0 B)
    8. TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
    9. ... ...

    3.2 使用代码添加虚拟网卡

    如果不使用启动参数,也可以在程序中添加代码的方式增加虚拟设备,具体代码如下:

    1. #define RX_RING_SIZE 1024
    2. nb_ports = rte_eth_dev_count_avail(); /* 获取所有可用的网卡 */
    3. /* Create a vhost_user port for each physical port */
    4. unsigned port_count = 0;
    5. RTE_ETH_FOREACH_DEV(portid) {
    6. char portname[32];
    7. char portargs[256];
    8. struct rte_ether_addr addr = {0};
    9. /* once we have created a virtio port for each physical port, stop creating more */
    10. if (++port_count > nb_ports)
    11. break;
    12. /* get MAC address of physical port to use as MAC of virtio_user port */
    13. rte_eth_macaddr_get(portid, &addr);
    14. /* set the name and arguments */
    15. snprintf(portname, sizeof(portname), "virtio_user%u", portid);
    16. snprintf(portargs, sizeof(portargs),
    17. "path=/dev/vhost-net,queues=1,queue_size=%u,iface=%s,mac=" RTE_ETHER_ADDR_PRT_FMT,
    18. RX_RING_SIZE, portname, RTE_ETHER_ADDR_BYTES(&addr)); //这里的portname名字可以更改为其他标识,例如tap
    19. /* add the vdev for virtio_user */
    20. if (rte_eal_hotplug_add("vdev", portname, portargs) < 0) //这里的portname必须是virtio_user0,virtio_user1...
    21. rte_exit(EXIT_FAILURE, "Cannot create paired port for port %u\n", portid);
    22. }

    ​添加上述代码需要添加头文件:

    1. #include
    2. #include

    四、参考文档

    dpdk官方文档参考:9. Virtio_user as Exception Path — Data Plane Development Kit 23.07.0 documentation

    VFIO驱动安装参考:7. Linux Drivers — Data Plane Development Kit 23.07.0 documentation

    虚拟机设置dpdk环境:DPDK-1:概述 - 墨天轮

    ​virtio 与vhost_net介绍:virtio 与vhost_net介绍_virtio vhost-CSDN博客

    ​​

  • 相关阅读:
    吉力宝:智能科技鞋品牌步力宝引领传统产业创新思维
    设计模式13、模版方法模式 Template Method
    ShardingSphere实现数据库读写分离,主从库分离,docker详细教程
    R语言使用混合模型进行聚类
    WaveletPool:抗混叠在微小目标检测中的重要性
    Codeforces Round #787 (Div. 3) F. Vlad and Unfinished Business
    Leetcode 16.07 最大数值
    图像处理与计算机视觉--第三章-颜色与纹理分析-6问
    杰理之充电仓升级及 dut 测试功能【篇】
    【操作系统笔记十三】Shell脚本编程
  • 原文地址:https://blog.csdn.net/Ang_ie/article/details/133364857