作者简介:闫亮,软件工程师,从事存储软件的测试和优化工作。
文章转载自DPDK与SPDK开源社区
基本概念
SPDK 用户态iSCSI 客户端库是通过 Linux iSCSI 客户端工具包的用户端实现。iSCSI 协议是基于IP协议存储网络标准,用于连接数据存储设备。该协议通过基于TCP/IP网络执行SCSI命令实现存储设备的块等级访问。iSCSI 协议可帮助数据使用内部网传输,来管理远距离的存储设备。它可用于基于局域网,广域网,或者互联网的数据传输,实现不依赖于地理位置的数据存储和检索。基本使用场景见下图:
Linux 系统的默认iSCSI工具库是由open-iscsi项目提供。该工具库提供了一些常用的iSCSI操作命令, 比如iscsiadm提供发现,连接远端iSCSI目标机。SPDK则提供完全用户态解决方案。参考下图:
相关代码文件在spdk/lib/bdev/iscsi/目录上,其中主要文件是bdev_iscsi,c, bdev_iscsi,h, bdev_iscsi_rpc.c。由目录结构可以看出,SPDK iSCSI用户态代码主要以bdev模块形式实现,连接到远端iSCSI节点逻辑盘,在逻辑盘创建bdev后可以用来给SPDK使用。函数bdev_iscsi_initialize是iscsi bdev模块的初始化函数。这个函数在解析完配置后,会调用create_iscsi_disk,同时可以设置iSCSI和bdev参数,并尝试链接到远端iSCSI节点。如果链接成功,就会调用iscsi_connect_cb函数。这个函数将会执行iSCSI查询任务,同时会调用bdev_iscsi_inquiry_cb回调函数。这个回调函数会执行iSCSIreadcapacity16任务,同时iscsi_readcapacity16_cb回调函数也会被调用。这个回调函数会执行create_iscsi_lun函数来创建iSCSI逻辑单元盘。在这个过程中,会注册io_device,SPDK bdev和poller,然后SPDK就可以使用这个iSCSIbdev了。可参考下面的流程图:
Bdev_iscsi_rpc.c 文件主要实现了construct_iscsi_bdev和delete_iscsi_bdev RPC命令,一个用于创建iSCSI盘,另一个用于删除iSCSI盘。具体使用方法可以查看两个命令的帮助信息。需要注意的是,编译SPDK时加上”—with-iscsi-initiator”,这两个RPC 命令才可以使用。
使用介绍
以下内容是SPDK用户态iSCSI 客户端库的基本使用介绍。
目标机器端的配置:
1.从github 获取 spdk软件源,进行编译。
命令如下:
1 2 3 |
[user@] git clone https://github.com/spdk/spdk.git [user@] cd spdk && git submodule update –init [user@]./configure && make |
2.通过iscsi配置文件或者RPC命令配置和启动iscsi target(相当于iscsi存储服务器),本文以配置文件为例。具体配置请参考附录1。启动SPDK命令如下:
1 |
[user@]./app/iscsi_tgt/iscsi_tgt -c iscsi.conf |
测试端的配置:
1.安装libiscsi软件包, 推荐从源码安装, 步骤如下:
1 2 3 4 5 6 |
[user@] git clone https://github.com/sahlberg/libiscsi.git [user@] cd libiscsi [user@] ./autogen.sh [user@] ./configure –prefix=/usr/ [user@] make [user@] sudo make install |
2.下载和编译SPDK,参考目标机器端的配置步骤1。SPDK编译时需要加上—with-iscsi-initiator选项 。命令如下:
1 |
[user@] ./configure --with-iscsi-initiator |
如果需要跑fio_plugin, 需要配置fio的源码路径:
1 |
[user@] ./configure --with-iscsi-initiator –with-fio=/path/to/fio |
3.需要配置bdev文件bdev.conf, 具体内容请见附录2。
4.运行bdevperf测试iSCSI Target。命令如下:
1 |
[user@]LD_LIBRARY_PATH=/usr/lib ./test/bdev/bdevperf/bdevperf –c bdev.conf –q 128 –o 4096 –w randread –t 600 –m 0x2 |
“-w” 后面的参数可以是 “read write rw randread randwrite randrw flush reset unmap verify”其中一个。
”-m”参数是core的个数, 本例使用一个core。目前推荐使用一个core。
5.还可以使用spdk的bdev层的fio_plugin使用SPDK iSCSI initiator测试SPDK iSCSI Target。Fiojob的配置见附录3。
1 |
[user@] LD_LIBRARY_PATH=/usr/lib/ LD_PRELOAD=/home/storage/spdk-latest/examples/bdev/fio_plugin/fio_plugin fio fioex.job |
备注:建议使用SPDK bdevperf来测试,可以更好地评估软件的性能,SPDK FIO plugin会引入更多的FIO软件开销。
附录1
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 |
[Global] [Bdev] [iSCSI] NodeBase "iqn.2016-06.io.spdk" AuthFile /usr/local/etc/spdk/auth.conf MinConnectionsPerCore 4 Timeout 30 DiscoveryAuthMethod Auto DefaultTime2Wait 2 DefaultTime2Retain 60 FirstBurstLength 8192 ImmediateData Yes ErrorRecoveryLevel 0 [PortalGroup1] Portal DA1 192.168.123.11:3260 [InitiatorGroup1] InitiatorName ANY Netmask 192.168.123.0/24 [Null] Dev Nvme0n1 10240 512 Dev Nvme1n1 10240 512 Dev Nvme2n1 10240 512 Dev Nvme3n1 10240 512 Dev Nvme4n1 10240 512 Dev Nvme5n1 10240 512 Dev Nvme6n1 10240 512 Dev Nvme7n1 10240 512 [TargetNode1] TargetName disk1 TargetAlias "Data Disk1" Mapping PortalGroup1 InitiatorGroup1 AuthMethod Auto AuthGroup AuthGroup1 UseDigest Auto LUN0 Nvme0n1 QueueDepth 128 [TargetNode2] TargetName disk2 TargetAlias "Data Disk2" Mapping PortalGroup1 InitiatorGroup1 AuthMethod Auto AuthGroup AuthGroup1 UseDigest Auto LUN0 Nvme1n1 QueueDepth 128 [TargetNode3] TargetName disk3 TargetAlias "Data Disk3" Mapping PortalGroup1 InitiatorGroup1 AuthMethod Auto AuthGroup AuthGroup1 UseDigest Auto LUN0 Nvme2n1 QueueDepth 128 [TargetNode4] TargetName disk4 TargetAlias "Data Disk4" Mapping PortalGroup1 InitiatorGroup1 AuthMethod Auto AuthGroup AuthGroup1 UseDigest Auto LUN0 Nvme3n1 QueueDepth 128 [TargetNode5] TargetName disk5 TargetAlias "Data Disk5" Mapping PortalGroup1 InitiatorGroup1 AuthMethod Auto AuthGroup AuthGroup1 UseDigest Auto LUN0 Nvme4n1 QueueDepth 128 [TargetNode6] TargetName disk6 TargetAlias "Data Disk6" Mapping PortalGroup1 InitiatorGroup1 AuthMethod Auto AuthGroup AuthGroup1 UseDigest Auto LUN0 Nvme5n1 QueueDepth 128 [TargetNode7] TargetName disk7 TargetAlias "Data Disk7" Mapping PortalGroup1 InitiatorGroup1 AuthMethod Auto AuthGroup AuthGroup1 UseDigest Auto LUN0 Nvme6n1 QueueDepth 128 [TargetNode8] TargetName disk8 TargetAlias "Data Disk8" Mapping PortalGroup1 InitiatorGroup1 AuthMethod Auto AuthGroup AuthGroup1 UseDigest Auto LUN0 Nvme7n1 QueueDepth 128 |
附录2
1 2 3 4 5 6 7 8 9 |
[iSCSI_Initiator] URL iscsi://192.168.123.11/iqn.2016-06.io.spdk:disk1/0 iSCSI0 URL iscsi://192.168.123.11/iqn.2016-06.io.spdk:disk2/0 iSCSI1 URL iscsi://192.168.123.11/iqn.2016-06.io.spdk:disk3/0 iSCSI2 URL iscsi://192.168.123.11/iqn.2016-06.io.spdk:disk4/0 iSCSI3 URL iscsi://192.168.123.11/iqn.2016-06.io.spdk:disk5/0 iSCSI4 URL iscsi://192.168.123.11/iqn.2016-06.io.spdk:disk6/0 iSCSI5 URL iscsi://192.168.123.11/iqn.2016-06.io.spdk:disk7/0 iSCSI6 URL iscsi://192.168.123.11/iqn.2016-06.io.spdk:disk8/0 iSCSI7 |
附录3
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 |
[global] ioengine=spdk_bdev spdk_conf=bdev.conf thread=1 cpumask=0x2 group_reporting=1 direct=1 time_based=1 ramp_time=30 runtime=600 iodepth=128 rw=randread bs=4k norandommap=1 invalidate=1 [Job0] filename=iSCSI0 [Job1] filename=iSCSI1 [Job2] filename=iSCSI2 [Job3] filename=iSCSI3 [Job4] filename=iSCSI4 [Job5] filename=iSCSI5 [Job6] filename=iSCSI6 [Job7] filename=iSCSI7 |