[Pure Storage] Add TCP transport type to NVMe driver

Add NVMe-TCP to the existing NVMe driver, which currently supports RoCE.
This change extends the parameter ``pure_nvme_transport`` to allow the
option ``tcp``.
Additional checks are performed on the backend to ensure that the
network ports used for connections are of the correct NVMe service
type.

Change-Id: I76166b9305f340a6e085216490d4c6bbecc7d1c1
This commit is contained in:
Simon Dodsley 2023-03-20 19:55:53 -04:00
parent 2e8aff660b
commit dc77207e4c
5 changed files with 81 additions and 18 deletions

View File

@ -4934,14 +4934,54 @@ class PureNVMEDriverTestCase(PureBaseSharedDriverTestCase):
self.driver.initialize_connection(vol, multipath_connector)
def test_get_target_nvme_ports(self):
self.array.list_ports.return_value = NVME_PORTS
ports = [{'name': 'CT0.ETH4',
'wwn': None,
'iqn': None,
'nqn': TARGET_NQN},
{'name': 'CT0.ETH5',
'wwn': None,
'iqn': TARGET_IQN,
'nqn': None},
{'name': 'CT0.ETH20',
'wwn': None,
'iqn': None,
'nqn': TARGET_NQN},
{'name': 'CT0.FC4',
'wwn': TARGET_WWN,
'iqn': None,
'nqn': TARGET_NQN}]
interfaces = [
{'name': 'ct0.eth4', 'services': ['nvme-tcp']},
{'name': 'ct0.eth5', 'services': ['iscsi']},
{'name': 'ct0.eth20', 'services': ['nvme-roce']},
{'name': 'ct0.fc4', 'services': ['nvme-fc']}
]
# Test for the nvme-tcp port
self.driver.configuration.pure_nvme_transport = "tcp"
self.array.get_network_interface.return_value = interfaces[0]
self.array.list_ports.return_value = [ports[0]]
ret = self.driver._get_target_nvme_ports(self.array)
self.assertEqual(NVME_PORTS, ret)
def test_get_target_nvme_ports_with_nvme_and_fc(self):
self.array.list_ports.return_value = NVME_PORTS_WITH
self.assertEqual([ports[0]], ret)
# Test for failure if no NVMe ports
self.array.get_network_interface.return_value = interfaces[1]
self.array.list_ports.return_value = [ports[1]]
self.assertRaises(
pure.PureDriverException,
self.driver._get_target_nvme_ports,
self.array,
)
# Test for the nvme-roce port
self.driver.configuration.pure_nvme_transport = "roce"
self.array.get_network_interface.return_value = interfaces[2]
self.array.list_ports.return_value = [ports[2]]
ret = self.driver._get_target_nvme_ports(self.array)
self.assertEqual(NVME_PORTS, ret)
self.assertEqual([ports[2]], ret)
# Test for empty dict if only nvme-fc port
self.driver.configuration.pure_nvme_transport = "roce"
self.array.get_network_interface.return_value = interfaces[3]
self.array.list_ports.return_value = [ports[3]]
ret = self.driver._get_target_nvme_ports(self.array)
self.assertEqual([], ret)
def test_get_target_nvme_ports_with_no_ports(self):
# Should raise an exception if there are no ports

View File

@ -111,9 +111,8 @@ PURE_OPTS = [
"IPv4 and IPv6 subnets. This parameter supersedes "
"pure_nvme_cidr."),
cfg.StrOpt("pure_nvme_transport", default="roce",
choices=['roce'],
help="The NVMe transport layer to be used by the NVMe driver. "
"This only supports RoCE at this time."),
choices=['roce', 'tcp'],
help="The NVMe transport layer to be used by the NVMe driver."),
cfg.BoolOpt("pure_eradicate_on_delete",
default=False,
help="When enabled, all Pure volumes, snapshots, and "
@ -406,6 +405,13 @@ class PureBaseVolumeDriver(san.SanDriver):
"unsupported. Please upgrade your backend to "
"a supported version.")
raise PureDriverException(msg)
if version.parse(array_info["version"]) < version.parse(
'6.4.2'
) and self._storage_protocol == constants.NVMEOF_TCP:
msg = _("FlashArray Purity version less than 6.4.2 "
"unsupported for NVMe-TCP. Please upgrade your "
"backend to a supported version.")
raise PureDriverException(msg)
self._array.array_name = array_info["array_name"]
self._array.array_id = array_info["id"]
@ -3217,6 +3223,9 @@ class PureNVMEDriver(PureBaseVolumeDriver, driver.BaseVD):
if self.configuration.pure_nvme_transport == "roce":
self.transport_type = "rdma"
self._storage_protocol = constants.NVMEOF_ROCE
else:
self.transport_type = "tcp"
self._storage_protocol = constants.NVMEOF_TCP
def _get_nguid(self, pure_vol_name):
"""Return the NGUID based on the volume's serial number
@ -3331,14 +3340,24 @@ class PureNVMEDriver(PureBaseVolumeDriver, driver.BaseVD):
return props
def _get_target_nvme_ports(self, array):
"""Return list of nvme-enabled port descriptions."""
"""Return list of correct nvme-enabled port descriptions."""
ports = array.list_ports()
valid_nvme_ports = []
nvme_ports = [port for port in ports if port["nqn"]]
for port in range(0, len(nvme_ports)):
if "ETH" in nvme_ports[port]["name"]:
port_detail = array.get_network_interface(
interface=nvme_ports[port]["name"]
)
if port_detail["services"][0] == "nvme-" + \
self.configuration.pure_nvme_transport:
valid_nvme_ports.append(nvme_ports[port])
if not nvme_ports:
raise PureDriverException(
reason=_("No nvme-enabled ports on target array.")
reason=_("No %(type)s enabled ports on target array.") %
{"type": self._storage_protocol}
)
return nvme_ports
return valid_nvme_ports
@utils.retry(PureRetryableException, retries=HOST_CREATE_MAX_RETRIES)
def _connect(self, array, vol_name, connector):

View File

@ -8,12 +8,12 @@ operations.
Support for iSCSI storage protocol is available with the PureISCSIDriver
Volume Driver class, Fibre Channel with the PureFCDriver and
NVMe-ROCE with the PureNVMEDriver.
NVMe-ROCE or NVMe-TCP with the PureNVMEDriver.
iSCSI and Fibre Channel drivers are compatible with Purity FlashArrays
that support the REST API version 1.6 and higher (Purity 4.7.0 and newer).
The NVMe driver is compatible with Purity FlashArrays
iSCSI, Fibre Channel and NVMe-RoCE drivers are compatible with FlashArrays
that support the REST API version 1.16 and higher (Purity 5.2.0 and newer).
The NVMe-TCP driver is compatible with FlashArrays
that are running Purity 6.4.2 and higher.
Some features may require newer versions of Purity.
Limitations and known issues
@ -161,7 +161,7 @@ Pure Storage FlashArray as back-end storage.
NVME connectivity.
If using the NVME driver, specify the ``pure_nvme_transport`` value.
Currently only ``roce`` is supported.
Supported values are ``roce`` or ``tcp``.
IP_PURE_MGMT
The IP address of the Pure Storage array's management interface or a

View File

@ -175,7 +175,7 @@ title=Open-E JovianDSS Storage Driver (iSCSI)
title=ProphetStor Flexvisor Driver (iSCSI, NFS)
[driver.pure]
title=Pure Storage Driver (iSCSI, FC, NVMe-RoCE)
title=Pure Storage Driver (iSCSI, FC, NVMe-RoCE, NVMe-TCP)
[driver.qnap]
title=QNAP Storage Driver (iSCSI)

View File

@ -0,0 +1,4 @@
---
features:
- |
Pure Storage FlashArray driver: Added support NVMe-TCP transport layer.