137 lines
5.1 KiB
Python
137 lines
5.1 KiB
Python
# Copyright 2020 toyou Corp.
|
|
# All Rights Reserved.
|
|
#
|
|
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
|
# not use this file except in compliance with the License. You may obtain
|
|
# a copy of the License at
|
|
#
|
|
# http://www.apache.org/licenses/LICENSE-2.0
|
|
#
|
|
# Unless required by applicable law or agreed to in writing, software
|
|
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
|
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
|
# License for the specific language governing permissions and limitations
|
|
# under the License.
|
|
|
|
"""
|
|
acs5000 iSCSI driver
|
|
"""
|
|
|
|
from oslo_config import cfg
|
|
from oslo_log import log as logging
|
|
|
|
from cinder import exception
|
|
from cinder import interface
|
|
from cinder import utils
|
|
from cinder.volume.drivers.toyou.acs5000 import acs5000_common
|
|
|
|
LOG = logging.getLogger(__name__)
|
|
|
|
acs5000_iscsi_opts = [
|
|
cfg.IntOpt(
|
|
'acs5000_target',
|
|
default=0,
|
|
min=0,
|
|
max=127,
|
|
help='A storage system iSCSI support 0 - 127 targets. '
|
|
'Devices connected to the SCSI bus are usually '
|
|
'described by the target ID(also known as the SCSI ID). '
|
|
'Multiple LUN numbers can be supported under a target. '
|
|
'A single device is usually identified '
|
|
'by the target and the LUN.')
|
|
]
|
|
|
|
CONF = cfg.CONF
|
|
CONF.register_opts(acs5000_iscsi_opts)
|
|
|
|
|
|
@interface.volumedriver
|
|
class Acs5000ISCSIDriver(acs5000_common.Acs5000CommonDriver):
|
|
"""TOYOU ACS5000 storage iSCSI volume driver.
|
|
|
|
.. code-block:: none
|
|
|
|
Version history:
|
|
1.0.0 - Initial driver
|
|
|
|
"""
|
|
|
|
VENDOR = 'TOYOU'
|
|
VERSION = '1.0.0'
|
|
PROTOCOL = 'iSCSI'
|
|
|
|
# ThirdPartySystems wiki page
|
|
CI_WIKI_NAME = 'TOYOU_ACS5000_CI'
|
|
|
|
def __init__(self, *args, **kwargs):
|
|
super(Acs5000ISCSIDriver, self).__init__(*args, **kwargs)
|
|
self.protocol = self.PROTOCOL
|
|
self.configuration.append_config_values(
|
|
acs5000_iscsi_opts)
|
|
|
|
@staticmethod
|
|
def get_driver_options():
|
|
return acs5000_common.acs5000c_opts + acs5000_iscsi_opts
|
|
|
|
def validate_connector(self, connector):
|
|
"""Check connector for at least one enabled iSCSI protocol."""
|
|
if 'initiator' not in connector:
|
|
LOG.error('The connector does not '
|
|
'contain the required information.')
|
|
raise exception.InvalidConnectorException(
|
|
missing='initiator')
|
|
|
|
@utils.synchronized('Acs5000A-host', external=True)
|
|
def initialize_connection(self, volume, connector):
|
|
LOG.debug('initialize_connection: volume %(vol)s with connector '
|
|
'%(conn)s', {'vol': volume['id'], 'conn': connector})
|
|
volume_name = acs5000_common.VOLUME_PREFIX + volume['name'][-12:]
|
|
target = self.configuration.acs5000_target
|
|
ret = self._cmd.create_lun_map(volume_name,
|
|
'WITH_ISCSI',
|
|
connector['initiator'],
|
|
str(target))
|
|
if ret['key'] == 303:
|
|
raise exception.VolumeNotFound(volume_id=volume_name)
|
|
elif ret['key'] == 402:
|
|
raise exception.ISCSITargetAttachFailed(volume_id=volume_name)
|
|
else:
|
|
volume_attributes = self._cmd.get_ip_connect(str(target))
|
|
lun_info = ret['arr']
|
|
lun = []
|
|
for i in range(len(volume_attributes['portal'])):
|
|
lun.append(int(lun_info['info']))
|
|
properties = {}
|
|
properties['target_discovered'] = False
|
|
properties['target_iqns'] = volume_attributes['iscsi_name']
|
|
properties['target_portals'] = volume_attributes['portal']
|
|
properties['target_luns'] = lun
|
|
properties['volume_id'] = volume['id']
|
|
properties['auth_method'] = ''
|
|
properties['auth_username'] = ''
|
|
properties['auth_password'] = ''
|
|
properties['discovery_auth_method'] = ''
|
|
properties['discovery_auth_username'] = ''
|
|
properties['discovery_auth_password'] = ''
|
|
return {'driver_volume_type': 'iscsi', 'data': properties}
|
|
|
|
@utils.synchronized('Acs5000A-host', external=True)
|
|
def terminate_connection(self, volume, connector, **kwargs):
|
|
LOG.debug('terminate_connection: volume %(vol)s with connector '
|
|
'%(conn)s', {'vol': volume['id'], 'conn': connector})
|
|
info = {'driver_volume_type': 'iscsi', 'data': {}}
|
|
name = acs5000_common.VOLUME_PREFIX + volume['name'][-12:]
|
|
target = self.configuration.acs5000_target
|
|
# -1 means all lun maps
|
|
initiator = '-1'
|
|
if connector and connector['initiator']:
|
|
initiator = connector['initiator']
|
|
self._cmd.delete_lun_map(name,
|
|
'WITH_ISCSI',
|
|
initiator,
|
|
str(target))
|
|
LOG.debug('leave: terminate_connection: volume %(vol)s with '
|
|
'connector %(conn)s', {'vol': volume['id'],
|
|
'conn': connector})
|
|
return info
|