예제 #1
0
    def _detach(self, fcp, assigner_id, target_wwpns, target_lun,
                multipath, os_version, mount_point, is_root_volume):
        """Detach a volume from a guest"""
        LOG.info('Start to detach device from %s' % assigner_id)
        connections = self.fcp_mgr.decrease_fcp_usage(fcp, assigner_id)
        if is_root_volume:
            LOG.info('Detaching device from %s is done.' % assigner_id)
            return

        try:
            self._remove_disk(fcp, assigner_id, target_wwpns, target_lun,
                              multipath, os_version, mount_point, connections)
            if not connections:
                self._undedicate_fcp(fcp, assigner_id)
        except (exception.SDKBaseException,
                exception.SDKSMTRequestFailed) as err:
            errmsg = 'detach failed with error:' + err.format_message()
            LOG.error(errmsg)
            self.fcp_mgr.increase_fcp_usage(fcp, assigner_id)
            with zvmutils.ignore_errors():
                new = (connections == 0)
                self._add_disk(fcp, assigner_id, target_wwpns, target_lun,
                               multipath, os_version, mount_point, new)
            raise exception.SDKBaseException(msg=errmsg)

        # Unreserved fcp device after undedicate all FCP devices
        if not connections:
            LOG.info("Unreserve fcp device %s from detach", fcp)
            self.fcp_mgr.unreserve_fcp(fcp)
        LOG.info('Detaching device from %s is done.' % assigner_id)
예제 #2
0
    def _attach(self, fcp, assigner_id, target_wwpns, target_lun, multipath,
                os_version, mount_point, path_count, is_root_volume):
        """Attach a volume

        First, we need translate fcp into local wwpn, then
        dedicate fcp to the user if it's needed, after that
        call smt layer to call linux command
        """
        LOG.info('Start to attach device to %s' % assigner_id)
        # TODO: init_fcp should be called in contructor function
        # but no assinger_id in contructor
        self.fcp_mgr.init_fcp(assigner_id)
        new = self.fcp_mgr.add_fcp_for_assigner(path_count, fcp, assigner_id)
        if is_root_volume:
            LOG.info('Attaching device to %s is done.' % assigner_id)
            return
        try:
            if new:
                self._dedicate_fcp(fcp, assigner_id)

            self._add_disk(fcp, assigner_id, target_wwpns, target_lun,
                           multipath, os_version, mount_point, new)
        except exception.SDKBaseException as err:
            errmsg = 'rollback attach because error:' + err.format_message()
            LOG.error(errmsg)
            connections = self.fcp_mgr.decrease_fcp_usage(fcp, assigner_id)
            # if connections less than 1, undedicate the device
            if not connections:
                with zvmutils.ignore_errors():
                    self._undedicate_fcp(fcp, assigner_id)
            raise exception.SDKBaseException(msg=errmsg)
        # TODO: other exceptions?

        LOG.info('Attaching device to %s is done.' % assigner_id)
예제 #3
0
    def _detach(self, fcp, assigner_id, target_wwpn, target_lun, multipath,
                os_version, mount_point):
        """Detach a volume from a guest"""
        LOG.info('Start to detach device from %s' % assigner_id)
        self.fcp_mgr.reverse_fcp(fcp)
        connections = self.fcp_mgr.decrease_fcp_usage(fcp, assigner_id)

        try:
            self._remove_disk(fcp, assigner_id, target_wwpn, target_lun,
                              multipath, os_version, mount_point)
            if not connections:
                self._undedicate_fcp(fcp, assigner_id)
        except (exception.SDKBaseException,
                exception.SDKSMTRequestFailed) as err:
            errmsg = 'rollback detach because error:' + err.format_message()
            LOG.error(errmsg)
            self.fcp_mgr.increase_fcp_usage(fcp, assigner_id)
            with zvmutils.ignore_errors():
                self._add_disk(fcp, assigner_id, target_wwpn, target_lun,
                               multipath, os_version, mount_point)
            raise exception.SDKBaseException(msg=errmsg)

        self.fcp_mgr.unreserve_fcp(fcp)

        LOG.info('Detaching device to %s is done.' % assigner_id)
예제 #4
0
    def _attach(self, fcp, assigner_id, target_wwpn, target_lun, multipath,
                os_version, mount_point):
        """Attach a volume

        First, we need translate fcp into local wwpn, then
        dedicate fcp to the user if it's needed, after that
        call smut layer to call linux command
        """
        LOG.info('Start to attach device to %s' % assigner_id)
        self.fcp_mgr.init_fcp(assigner_id)
        new = self.fcp_mgr.increase_fcp_usage(fcp, assigner_id)
        try:
            if new:
                self._dedicate_fcp(fcp, assigner_id)

            self._add_disk(fcp, assigner_id, target_wwpn, target_lun,
                           multipath, os_version, mount_point)
        except exception.SDKBaseException as err:
            errmsg = 'rollback attach because error:' + err.format_message()
            LOG.error(errmsg)
            connections = self.fcp_mgr.decrease_fcp_usage(fcp, assigner_id)
            # if connections less than 1, undedicate the device
            if not connections:
                with zvmutils.ignore_errors():
                    self._undedicate_fcp(fcp, assigner_id)
            raise exception.SDKBaseException(msg=errmsg)

        LOG.info('Attaching device to %s is done.' % assigner_id)
예제 #5
0
 def _rollback_dedicated_fcp(self, fcp_list, assigner_id,
                             all_fcp_list=None):
     # fcp param should be a list
     for fcp in fcp_list:
         with zvmutils.ignore_errors():
             LOG.info("Rolling back dedicated FCP: %s" % fcp)
             connections = self.fcp_mgr.decrease_fcp_usage(fcp, assigner_id)
             if connections == 0:
                 self._undedicate_fcp(fcp, assigner_id)
     # If attach volume fails, we need to unreserve all FCP devices.
     if all_fcp_list:
         for fcp in all_fcp_list:
             if not self.db.get_connections_from_fcp(fcp):
                 LOG.info("Unreserve the fcp device %s", fcp)
                 self.db.unreserve(fcp)
예제 #6
0
    def _detach(self, fcp, assigner_id, target_wwpns, target_lun,
                multipath, os_version, mount_point, is_root_volume,
                need_restart):
        """Detach a volume from a guest"""
        LOG.info('Start to detach device %s from %s' % (fcp, assigner_id))
        try:
            connections = self.fcp_mgr.decrease_fcp_usage(fcp, assigner_id)
        except exception.SDKObjectNotExistError:
            connections = 0
            LOG.warning("The connections of FCP device %s is 0.", fcp)

        if is_root_volume:
            LOG.info('Detaching device from %s is done.' % assigner_id)
            return

        try:
            self._remove_disk(fcp, assigner_id, target_wwpns, target_lun,
                              multipath, os_version, mount_point, connections,
                              need_restart)
            if not connections:
                self._undedicate_fcp(fcp, assigner_id)
        except (exception.SDKBaseException,
                exception.SDKSMTRequestFailed) as err:
            rc = err.results['rc']
            rs = err.results['rs']
            if rc == 404 or rc == 204 and rs == 8:
                # We ignore the already undedicate FCP device exception.
                LOG.warning("The FCP device %s has already undedicdated", fcp)
            else:
                errmsg = 'detach failed with error:' + err.format_message()
                LOG.error(errmsg)
                self.fcp_mgr.increase_fcp_usage(fcp, assigner_id)
                with zvmutils.ignore_errors():
                    new = (connections == 0)
                    self._add_disk(fcp, assigner_id, target_wwpns, target_lun,
                                   multipath, os_version, mount_point, new)
                raise exception.SDKBaseException(msg=errmsg)

        # Unreserved fcp device after undedicate all FCP devices
        if not connections:
            LOG.info("Unreserve fcp device %s from detach", fcp)
            self.fcp_mgr.unreserve_fcp(fcp)
        LOG.info('Detaching device from %s is done.' % assigner_id)
예제 #7
0
    def _detach(self, fcp_list, assigner_id, target_wwpns, target_lun,
                multipath, os_version, mount_point, is_root_volume):
        """Detach a volume from a guest"""
        LOG.info("Start to detach volume on machine %s from "
                 "FCP devices %s" % (assigner_id, fcp_list))
        # fcp_connections is like {'1a10': 0, '1b10': 3}
        # the values are the connections colume value in database
        fcp_connections = {}
        try:
            for fcp in fcp_list:
                connections = self.fcp_mgr.decrease_fcp_usage(fcp, assigner_id)
                fcp_connections[fcp] = connections
        except exception.SDKObjectNotExistError:
            connections = 0
            LOG.warning("The connections of FCP device %s is 0.", fcp)

        if is_root_volume:
            LOG.info("Is root volume, deleting FCP records %s from %s is "
                     "done." % (fcp_list, assigner_id))
            return

        # when detaching volumes, if userid not exist, no need to
        # raise exception. we stop here after the database operations done.
        if not zvmutils.check_userid_exist(assigner_id):
            LOG.warning(
                "Found %s not exist when trying to detach volumes "
                "from it.", assigner_id)
            return

        try:
            self._remove_disks(fcp_list, assigner_id, target_wwpns, target_lun,
                               multipath, os_version, mount_point, connections)
            for fcp in fcp_list:
                if not fcp_connections.get(fcp, 0):
                    LOG.info("Start to undedicate FCP %s from "
                             "%s." % (fcp, assigner_id))
                    self._undedicate_fcp(fcp, assigner_id)
                    LOG.info("FCP %s undedicated from %s is "
                             "done." % (fcp, assigner_id))
                else:
                    LOG.info("Found still have volumes on FCP %s, "
                             "skip undedicating FCP device." % fcp)
        except (exception.SDKBaseException,
                exception.SDKSMTRequestFailed) as err:
            rc = err.results['rc']
            rs = err.results['rs']
            if rc == 404 or rc == 204 and rs == 8:
                # We ignore the already undedicate FCP device exception.
                LOG.warning("The FCP device %s has already undedicdated", fcp)
            else:
                errmsg = "detach failed with error:" + err.format_message()
                LOG.error(errmsg)
                for fcp in fcp_list:
                    # rollback the connections data before remove disks
                    self.fcp_mgr.increase_fcp_usage(fcp, assigner_id)
                with zvmutils.ignore_errors():
                    self._add_disks(fcp_list, assigner_id, target_wwpns,
                                    target_lun, multipath, os_version,
                                    mount_point)
                raise exception.SDKBaseException(msg=errmsg)
        LOG.info("Detaching volume on machine %s from FCP devices %s is "
                 "done." % (assigner_id, fcp_list))