def create(self, sr_uuid, size): # Check whether an SR already exists SRs = self.session.xenapi.SR.get_all_records() for sr in SRs: record = SRs[sr] sm_config = record["sm_config"] if sm_config.has_key('targetIQN') and \ sm_config['targetIQN'] == self.targetIQN: raise xs_errors.XenError('SRInUse') self.attach(sr_uuid) # Wait up to MAX_TIMEOUT for devices to appear util.wait_for_path(self.path, MAX_TIMEOUT) if self._loadvdis() > 0: scanrecord = SR.ScanRecord(self) scanrecord.synchronise() try: self.detach(sr_uuid) except: pass self.sm_config = self.session.xenapi.SR.get_sm_config(self.sr_ref) self.sm_config['disktype'] = 'Raw' self.sm_config['datatype'] = 'ISCSI' self.sm_config['target'] = self.target self.sm_config['targetIQN'] = self.targetIQN self.sm_config['multipathable'] = 'true' self.session.xenapi.SR.set_sm_config(self.sr_ref, self.sm_config) return
def _refresh_DMP(sid, npaths): map_by_scsibus(sid,npaths) path = os.path.join(DEVMAPPERPATH, sid) if not os.path.exists(path): raise xs_errors.XenError('DMP failed to activate mapper path') lvm_path = "/dev/disk/by-scsid/"+sid+"/mapper" util.wait_for_path(lvm_path, 10) activate_MPdev(sid, path)
def _refresh_DMP(sid, npaths): util.retry(lambda: util.pread2(['/usr/sbin/multipath', '-r', sid]), maxretry = 3, period = 4) path = os.path.join(DEVMAPPERPATH, sid) util.wait_for_path(path, 10) if not os.path.exists(path): raise xs_errors.XenError('DMP failed to activate mapper path') lvm_path = "/dev/disk/by-scsid/"+sid+"/mapper" util.wait_for_path(lvm_path, 10) activate_MPdev(sid, path)
def _LUNprint(self, sr_uuid): if self.iscsi.attached: # Force a rescan on the bus, pause for 5 seconds # N.B. Probing for LUNs can always be repeated, so don't wait a long time self.iscsi.refresh() time.sleep(5) # Now call attach (handles the refcounting + session activa) self.iscsi.attach(sr_uuid) # Wait up to 15 seconds for the base iscsi udev path # to show up. This may fail under extreme load or if # LUNs are not mapped to the host util.wait_for_path(self.iscsi.path, ISCSISR.MAX_TIMEOUT) self.iscsi.print_LUNs() self.iscsi.detach(sr_uuid)
def _LUNprint(self, sr_uuid): if self.iscsi.attached: # Force a rescan on the bus. self.iscsi.refresh() # time.sleep(5) # Now call attach (handles the refcounting + session activa) self.iscsi.attach(sr_uuid) util.SMlog("LUNprint: waiting for path: %s" % self.iscsi.path) if util.wait_for_path("%s/LUN*" % self.iscsi.path, BaseISCSI.MAX_TIMEOUT): try: adapter = self.iscsi.adapter[self.iscsi.address] util.SMlog("adapter=%s" % adapter) # find a scsi device on which to issue a report luns command: devs = glob.glob("%s/LUN*" % self.iscsi.path) sgdevs = [] for i in devs: sgdevs.append(int(i.split("LUN")[1])) sgdevs.sort() sgdev = "%s/LUN%d" % (self.iscsi.path, sgdevs[0]) # issue a report luns: luns = util.pread2(["/usr/bin/sg_luns", "-q", sgdev]).split('\n') nluns = len( luns) - 1 # remove the line relating to the final \n # check if the LUNs are MPP-RDAC Luns scsi_id = scsiutil.getSCSIid(sgdev) mpp_lun = False if (mpp_luncheck.is_RdacLun(scsi_id)): mpp_lun = True link = glob.glob('/dev/disk/by-scsibus/%s-*' % scsi_id) mpp_adapter = link[0].split('/')[-1].split('-')[-1].split( ':')[0] # make sure we've got that many sg devices present for i in range(0, 30): luns = scsiutil._dosgscan() sgdevs = filter(lambda r: r[1] == adapter, luns) if mpp_lun: sgdevs.extend( filter(lambda r: r[1] == mpp_adapter, luns)) if len(sgdevs) >= nluns: util.SMlog("Got all %d sg devices" % nluns) break else: util.SMlog("Got %d sg devices - expecting %d" % (len(sgdevs), nluns)) time.sleep(1) util.pread2(["/sbin/udevsettle"]) except: pass # Make sure we don't break the probe... self.iscsi.print_LUNs() self.iscsi.detach(sr_uuid)
def _attach_LUN_bylunid(self, lunid): if not self.attached: raise xs_errors.XenError('SRUnavailable') connected = [] for val in self.adapter: if not self.pathdict.has_key(val): continue rec = self.pathdict[val] path = os.path.join(rec['path'],"LUN%s" % lunid) util.SMlog("path: %s" % path) realpath = os.path.realpath(path) util.SMlog("realpath: %s" % realpath) host = self.adapter[val] if not self.devs.has_key(realpath): l = [realpath, host, 0, 0, lunid] scsiutil.scsi_dev_ctrl(l,"add") if not util.wait_for_path(path, MAX_LUNID_TIMEOUT): util.SMlog("Unable to detect LUN attached to host on path [%s]" % path) continue else: # Verify that we are not seeing a stale LUN map try: real_SCSIid = scsiutil.getSCSIid(realpath) cur_scsibuspath = glob.glob('/dev/disk/by-scsibus/*-%s:0:0:%s' % (host,lunid)) cur_SCSIid = os.path.basename(cur_scsibuspath[0]).split("-")[0] assert(cur_SCSIid == real_SCSIid) except: scsiutil.rescan([host]) if not os.path.exists('/dev/disk/by-scsibus/%s-%s:0:0:%s' % \ (real_SCSIid,host,lunid)): util.SMlog("Unable to detect LUN attached to host after bus re-probe") continue connected.append(path) return connected
def create(self, sr_uuid, size): # Check SCSIid not already in use by other PBDs if util.test_SCSIid(self.session, sr_uuid, self.SCSIid): raise xs_errors.XenError('SRInUse') self.iscsi.attach(sr_uuid) try: if not self.iscsi._attach_LUN_bySCSIid(self.SCSIid): # UPGRADE FROM GEORGE: take care of ill-formed SCSIid upgraded = False matchSCSIid = False for file in filter(self.iscsi.match_lun, util.listdir(self.iscsi.path)): path = os.path.join(self.iscsi.path, file) if not util.wait_for_path(path, BaseISCSI.MAX_TIMEOUT): util.SMlog( "Unable to detect LUN attached to host [%s]" % path) continue try: SCSIid = scsiutil.getSCSIid(path) except: continue try: matchSCSIid = scsiutil.compareSCSIid_2_6_18( self.SCSIid, path) except: continue if (matchSCSIid): util.SMlog("Performing upgrade from George") try: pbd = util.find_my_pbd(self.session, self.host_ref, self.sr_ref) device_config = self.session.xenapi.PBD.get_device_config( pbd) device_config['SCSIid'] = SCSIid self.session.xenapi.PBD.set_device_config( pbd, device_config) self.dconf['SCSIid'] = SCSIid self.SCSIid = self.dconf['SCSIid'] except: continue if not self.iscsi._attach_LUN_bySCSIid(self.SCSIid): raise xs_errors.XenError('InvalidDev') else: upgraded = True break else: util.SMlog( "Not a matching LUN, skip ... scsi_id is: %s" % SCSIid) continue if not upgraded: raise xs_errors.XenError('InvalidDev') self._pathrefresh(LVHDoISCSISR) LVHDSR.LVHDSR.create(self, sr_uuid, size) except Exception, inst: self.iscsi.detach(sr_uuid) raise xs_errors.XenError("SRUnavailable", opterr=inst)
def _refresh_DMP(sid, npaths): if not _is_valid_multipath_device(sid): return path = os.path.join(DEVMAPPERPATH, sid) # If the mapper path doesn't exist force a reload in multipath if not os.path.exists(path): util.retry(lambda: util.pread2(['/usr/sbin/multipath', '-r', sid]), maxretry=3, period=4) util.wait_for_path(path, 10) if not os.path.exists(path): raise xs_errors.XenError( 'MultipathMapperPathMissing', 'Device mapper path {} not found'.format(path)) lvm_path = "/dev/disk/by-scsid/" + sid + "/mapper" util.wait_for_path(lvm_path, 10) activate_MPdev(sid, path)
def _LUNprint(self, sr_uuid): if self.iscsi.attached: # Force a rescan on the bus. self.iscsi.refresh() # time.sleep(5) # Now call attach (handles the refcounting + session activa) self.iscsi.attach(sr_uuid) util.SMlog("LUNprint: waiting for path: %s" % self.iscsi.path) if util.wait_for_path("%s/LUN*" % self.iscsi.path, ISCSISR.MAX_TIMEOUT): try: adapter=self.iscsi.adapter[self.iscsi.address] util.SMlog("adapter=%s" % adapter) # find a scsi device on which to issue a report luns command: devs=glob.glob("%s/LUN*" % self.iscsi.path) sgdevs = [] for i in devs: sgdevs.append(int(i.split("LUN")[1])) sgdevs.sort() sgdev = "%s/LUN%d" % (self.iscsi.path,sgdevs[0]) # issue a report luns: luns=util.pread2(["/usr/bin/sg_luns","-q",sgdev]).split('\n') nluns=len(luns)-1 # remove the line relating to the final \n # check if the LUNs are MPP-RDAC Luns scsi_id = scsiutil.getSCSIid(sgdev) mpp_lun = False if (mpp_luncheck.is_RdacLun(scsi_id)): mpp_lun = True link=glob.glob('/dev/disk/by-scsibus/%s-*' % scsi_id) mpp_adapter = link[0].split('/')[-1].split('-')[-1].split(':')[0] # make sure we've got that many sg devices present for i in range(0,30): luns=scsiutil._dosgscan() sgdevs=filter(lambda r: r[1]==adapter, luns) if mpp_lun: sgdevs.extend(filter(lambda r: r[1]==mpp_adapter, luns)) if len(sgdevs)>=nluns: util.SMlog("Got all %d sg devices" % nluns) break else: util.SMlog("Got %d sg devices - expecting %d" % (len(sgdevs),nluns)) time.sleep(1) if os.path.exists("/sbin/udevsettle"): util.pread2(["/sbin/udevsettle"]) else: util.pread2(["/sbin/udevadm","settle"]) except: util.SMlog("Generic exception caught. Pass") pass # Make sure we don't break the probe... self.iscsi.print_LUNs() self.iscsi.detach(sr_uuid)
def attach(self, sr_uuid, vdi_uuid): self.sr._loadvdis() if not self.sr.vdis.has_key(vdi_uuid): raise xs_errors.XenError('VDIUnavailable') if not util.pathexists(self.path): self.sr.refresh() if not util.wait_for_path(self.path, MAX_TIMEOUT): util.SMlog("Unable to detect LUN attached to host [%s]" % self.sr.path) raise xs_errors.XenError('VDIUnavailable') return super(RAWVDI, self).attach(sr_uuid, vdi_uuid)
def _attach_LUN_bySCSIid(self, SCSIid): if not self.attached: raise xs_errors.XenError("SRUnavailable") path = self.mpathmodule.path(SCSIid) if not util.pathexists(path): self.refresh() if not util.wait_for_path(path, MAX_TIMEOUT): util.SMlog("Unable to detect LUN attached to host [%s]" % path) return False return True
def refresh(sid, npaths): # Refresh the multipath status util.SMlog("Refreshing LUN %s" % sid) if len(sid): path = DEVBYIDPATH + "/scsi-" + sid if not os.path.exists(path): scsiutil.rescan(scsiutil._genHostList("")) if not util.wait_for_path(path, 60): raise xs_errors.XenError('Device not appeared yet') _refresh_DMP(sid, npaths) else: raise xs_errors.XenError('MPath not written yet')
def _attach_LUN_bySCSIid(self, SCSIid): if not self.attached: raise xs_errors.XenError('SRUnavailable') path = self.mpathmodule.path(SCSIid) if not util.pathexists(path): self.refresh() if not util.wait_for_path(path, MAX_TIMEOUT): util.SMlog("Unable to detect LUN attached to host [%s]" \ % path) return False return True
def create(self, sr_uuid, size): # Check SCSIid not already in use by other PBDs if util.test_SCSIid(self.session, sr_uuid, self.SCSIid): raise xs_errors.XenError('SRInUse') self.iscsi.attach(sr_uuid) try: if not self.iscsi._attach_LUN_bySCSIid(self.SCSIid): # UPGRADE FROM GEORGE: take care of ill-formed SCSIid upgraded = False matchSCSIid = False for file in filter(self.iscsi.match_lun, util.listdir(self.iscsi.path)): path = os.path.join(self.iscsi.path,file) if not util.wait_for_path(path, ISCSISR.MAX_TIMEOUT): util.SMlog("Unable to detect LUN attached to host [%s]" % path) continue try: SCSIid = scsiutil.getSCSIid(path) except: continue try: matchSCSIid = scsiutil.compareSCSIid_2_6_18(self.SCSIid, path) except: continue if (matchSCSIid): util.SMlog("Performing upgrade from George") try: pbd = util.find_my_pbd(self.session, self.host_ref, self.sr_ref) device_config = self.session.xenapi.PBD.get_device_config(pbd) device_config['SCSIid'] = SCSIid self.session.xenapi.PBD.set_device_config(pbd, device_config) self.dconf['SCSIid'] = SCSIid self.SCSIid = self.dconf['SCSIid'] except: continue if not self.iscsi._attach_LUN_bySCSIid(self.SCSIid): raise xs_errors.XenError('InvalidDev') else: upgraded = True break else: util.SMlog("Not a matching LUN, skip ... scsi_id is: %s" % SCSIid) continue if not upgraded: raise xs_errors.XenError('InvalidDev') self._pathrefresh(LVHDoISCSISR) LVHDSR.LVHDSR.create(self, sr_uuid, size) except Exception, inst: self.iscsi.detach(sr_uuid) raise xs_errors.XenError("SRUnavailable", opterr=inst)
def _attach_LUN_bylunid(self, lunid): if not self.attached: raise xs_errors.XenError('SRUnavailable') connected = [] for val in self.adapter: if val not in self.pathdict: continue rec = self.pathdict[val] path = os.path.join(rec['path'], "LUN%s" % lunid) realpath = os.path.realpath(path) host = self.adapter[val] l = [realpath, host, 0, 0, lunid] addDevice = True if realpath in self.devs: # if the device is stale remove it before adding again real_SCSIid = None try: real_SCSIid = scsiutil.getSCSIid(realpath) except: pass if real_SCSIid != None: # make sure this is the same scsiid, if not remove the device cur_scsibuspath = glob.glob( '/dev/disk/by-scsibus/*-%s:0:0:%s' % (host, lunid)) cur_SCSIid = os.path.basename( cur_scsibuspath[0]).split("-")[0] if cur_SCSIid != real_SCSIid: # looks stale, remove it scsiutil.scsi_dev_ctrl(l, "remove") else: util.SMlog("Not attaching LUNID %s for adapter %s"\ " since the device exists and the scsi id %s seems"\ " to be valid. " % (lunid, val, real_SCSIid)) addDevice = False else: # looks stale, remove it scsiutil.scsi_dev_ctrl(l, "remove") if addDevice: # add the device scsiutil.scsi_dev_ctrl(l, "add") if not util.wait_for_path(path, MAX_LUNID_TIMEOUT): util.SMlog( "Unable to detect LUN attached to host on path [%s]" % path) continue connected.append(path) return connected
def _getSCSIid_from_LUN(self, sr_uuid): was_attached = True self.iscsi.attach(sr_uuid) dev = self.dconf['LUNid'].split(',') if len(dev) > 1: raise xs_errors.XenError('OCFSOneLUN') path = os.path.join(self.iscsi.path, "LUN%s" % dev[0]) if not util.wait_for_path(path, ISCSISR.MAX_TIMEOUT): util.SMlog("Unable to detect LUN attached to host [%s]" % path) try: SCSIid = scsiutil.getSCSIid(path) except: raise xs_errors.XenError('InvalidDev') self.iscsi.detach(sr_uuid) return SCSIid
def refresh(sid,npaths): # Refresh the multipath status util.SMlog("Refreshing LUN %s" % sid) if len(sid): path = DEVBYIDPATH + "/scsi-" + sid if not os.path.exists(path): scsiutil.rescan(scsiutil._genHostList("")) if not util.wait_for_path(path,60): raise xs_errors.XenError('Device not appeared yet') if not (mpp_luncheck.is_RdacLun(sid)): _refresh_DMP(sid,npaths) else: _refresh_MPP(sid,npaths) else: raise xs_errors.XenError('MPath not written yet')
def _getSCSIid_from_LUN(self, sr_uuid): was_attached = True self.iscsi.attach(sr_uuid) dev = self.dconf['LUNid'].split(',') if len(dev) > 1: raise xs_errors.XenError('LVMOneLUN') path = os.path.join(self.iscsi.path,"LUN%s" % dev[0]) if not util.wait_for_path(path, ISCSISR.MAX_TIMEOUT): util.SMlog("Unable to detect LUN attached to host [%s]" % path) try: SCSIid = scsiutil.getSCSIid(path) except: raise xs_errors.XenError('InvalidDev') self.iscsi.detach(sr_uuid) return SCSIid
def _attach_LUN_bylunid(self, lunid): if not self.attached: raise xs_errors.XenError("SRUnavailable") connected = [] for val in self.adapter: if not self.pathdict.has_key(val): continue rec = self.pathdict[val] path = os.path.join(rec["path"], "LUN%s" % lunid) realpath = os.path.realpath(path) host = self.adapter[val] l = [realpath, host, 0, 0, lunid] addDevice = True if self.devs.has_key(realpath): # if the device is stale remove it before adding again real_SCSIid = None try: real_SCSIid = scsiutil.getSCSIid(realpath) except: pass if real_SCSIid != None: # make sure this is the same scsiid, if not remove the device cur_scsibuspath = glob.glob("/dev/disk/by-scsibus/*-%s:0:0:%s" % (host, lunid)) cur_SCSIid = os.path.basename(cur_scsibuspath[0]).split("-")[0] if cur_SCSIid != real_SCSIid: # looks stale, remove it scsiutil.scsi_dev_ctrl(l, "remove") else: util.SMlog( "Not attaching LUNID %s for adapter %s" " since the device exists and the scsi id %s seems" " to be valid. " % (lunid, val, real_SCSIid) ) addDevice = False else: # looks stale, remove it scsiutil.scsi_dev_ctrl(l, "remove") if addDevice: # add the device scsiutil.scsi_dev_ctrl(l, "add") if not util.wait_for_path(path, MAX_LUNID_TIMEOUT): util.SMlog("Unable to detect LUN attached to host on path [%s]" % path) continue connected.append(path) return connected
def _attach_LUN_byserialid(self, serialid): if not self.attached: raise xs_errors.XenError('SRUnavailable') connected = [] for val in self.adapter: if not self.pathdict.has_key(val): continue rec = self.pathdict[val] path = os.path.join(rec['path'],"SERIAL-%s" % serialid) realpath = os.path.realpath(path) if not self.devs.has_key(realpath): if not util.wait_for_path(path, 5): util.SMlog("Unable to detect LUN attached to host on serial path [%s]" % path) continue connected.append(path) return connected
def _LUNprint(self, sr_uuid): if self.iscsi.attached: # Force a rescan on the bus. self.iscsi.refresh() # time.sleep(5) # Now call attach (handles the refcounting + session activa) self.iscsi.attach(sr_uuid) util.SMlog("LUNprint: waiting for path: %s" % self.iscsi.path) if util.wait_for_path("%s/LUN*" % self.iscsi.path, BaseISCSI.MAX_TIMEOUT): try: adapter=self.iscsi.adapter[self.iscsi.address] util.SMlog("adapter=%s" % adapter) # find a scsi device on which to issue a report luns command: devs=glob.glob("%s/LUN*" % self.iscsi.path) sgdevs = [] for i in devs: sgdevs.append(int(i.split("LUN")[1])) sgdevs.sort() sgdev = "%s/LUN%d" % (self.iscsi.path,sgdevs[0]) # issue a report luns: luns=util.pread2(["/usr/bin/sg_luns","-q",sgdev]).split('\n') nluns=len(luns)-1 # remove the line relating to the final \n # check if the LUNs are MPP-RDAC Luns scsi_id = scsiutil.getSCSIid(sgdev) # make sure we've got that many sg devices present for i in range(0,30): luns=scsiutil._dosgscan() sgdevs=filter(lambda r: r[1]==adapter, luns) if len(sgdevs)>=nluns: util.SMlog("Got all %d sg devices" % nluns) break else: util.SMlog("Got %d sg devices - expecting %d" % (len(sgdevs),nluns)) time.sleep(1) util.pread2(["/sbin/udevsettle"]) except: pass # Make sure we don't break the probe... self.iscsi.print_LUNs() self.iscsi.detach(sr_uuid)
def attach(self, sr_uuid, vdi_uuid): # Does the iscsi login self.iqn = self.validate_iqn() self.path = self.login_target() log("IQN") log(self.iqn) if not util.wait_for_path(self.path, MAX_TIMEOUT): util.SMlog("Unable to detect LUN attached to host [%s]" % self.sr.path) raise xs_errors.XenError('VDIUnavailable') ret = super(VDILUN, self).attach(sr_uuid, vdi_uuid) self.attached = True return ret
def attach(self, sr_uuid, vdi_uuid): self.sr._loadvdis() if vdi_uuid not in self.sr.vdis: raise xs_errors.XenError('VDIUnavailable') if not util.pathexists(self.path): self.sr.refresh() if 'SCSIid' in self.sm_config: if self.sr.mpath == 'true': self.sr.mpathmodule.refresh(self.sm_config['SCSIid'], 0) devs = os.listdir("/dev/disk/by-scsid/%s" % self.sm_config['SCSIid']) for dev in devs: realdev = os.path.realpath("/dev/disk/by-scsid/%s/%s" % (self.sm_config['SCSIid'], dev)) util.set_scheduler(realdev.split("/")[-1], "noop") if not util.wait_for_path(self.path, MAX_TIMEOUT): util.SMlog("Unable to detect LUN attached to host [%s]" % self.sr.path) raise xs_errors.XenError('VDIUnavailable') return super(RAWVDI, self).attach(sr_uuid, vdi_uuid)
def refresh(sid, npaths): # Fix udev bug (?): make sure it updates /dev/disk/by-id # Trigger the old way, if possible if os.path.exists("/sbin/udevtrigger"): util.pread2(["/sbin/udevtrigger"]) else: util.pread2(["/sbin/udevadm", "trigger"]) # Refresh the multipath status util.SMlog("Refreshing LUN %s" % sid) if len(sid): path = DEVBYIDPATH + "/scsi-" + sid if not os.path.exists(path): scsiutil.rescan(scsiutil._genHostList("")) if not util.wait_for_path(path, 60): raise xs_errors.XenError('Device not appeared yet') if not (mpp_luncheck.is_RdacLun(sid)): _refresh_DMP(sid, npaths) else: _refresh_MPP(sid, npaths) else: raise xs_errors.XenError('MPath not written yet')
def refresh_HostID(HostID, fullrescan): LUNs = glob.glob('/sys/class/scsi_disk/%s*' % HostID) li = [] for l in LUNs: chan = re.sub(":[0-9]*$",'',os.path.basename(l)) if chan not in li: li.append(chan) if len(li) and not fullrescan: for c in li: if not refresh_scsi_channel(c): fullrescan = True if fullrescan: util.SMlog("Full rescan of HostID %s" % HostID) path = '/sys/class/scsi_host/host%s/scan' % HostID if os.path.exists(path): try: scanstring = "- - -" f=open(path, 'w') f.write('%s\n' % scanstring) f.close() if len(li): # Channels already exist, allow some time for # undiscovered LUNs/channels to appear time.sleep(2) except: pass # Host Bus scan issued, now try to detect channels if util.wait_for_path("/sys/class/scsi_disk/%s*" % HostID, 5): # At least one LUN is mapped LUNs = glob.glob('/sys/class/scsi_disk/%s*' % HostID) li = [] for l in LUNs: chan = re.sub(":[0-9]*$",'',os.path.basename(l)) if chan not in li: li.append(chan) for c in li: refresh_scsi_channel(c)
def refresh_HostID(HostID, fullrescan): LUNs = glob.glob('/sys/class/scsi_disk/%s*' % HostID) li = [] for l in LUNs: chan = re.sub(":[0-9]*$", '', os.path.basename(l)) if chan not in li: li.append(chan) if len(li) and not fullrescan: for c in li: if not refresh_scsi_channel(c): fullrescan = True if fullrescan: util.SMlog("Full rescan of HostID %s" % HostID) path = '/sys/class/scsi_host/host%s/scan' % HostID if os.path.exists(path): try: scanstring = "- - -" f = open(path, 'w') f.write('%s\n' % scanstring) f.close() if len(li): # Channels already exist, allow some time for # undiscovered LUNs/channels to appear time.sleep(2) except: pass # Host Bus scan issued, now try to detect channels if util.wait_for_path("/sys/class/scsi_disk/%s*" % HostID, 5): # At least one LUN is mapped LUNs = glob.glob('/sys/class/scsi_disk/%s*' % HostID) li = [] for l in LUNs: chan = re.sub(":[0-9]*$", '', os.path.basename(l)) if chan not in li: li.append(chan) for c in li: refresh_scsi_channel(c)
def refresh(sid,npaths): # Fix udev bug (?): make sure it updates /dev/disk/by-id # Trigger the old way, if possible if os.path.exists("/sbin/udevtrigger"): util.pread2(["/sbin/udevtrigger"]) else: util.pread2(["/sbin/udevadm","trigger"]) # Refresh the multipath status util.SMlog("Refreshing LUN %s" % sid) if len(sid): path = DEVBYIDPATH + "/scsi-" + sid if not os.path.exists(path): scsiutil.rescan(scsiutil._genHostList("")) if not util.wait_for_path(path,60): raise xs_errors.XenError('Device not appeared yet') if not (mpp_luncheck.is_RdacLun(sid)): _refresh_DMP(sid,npaths) else: _refresh_MPP(sid,npaths) else: raise xs_errors.XenError('MPath not written yet')
def refresh_HostID(HostID, scanstring): LUNs = glob.glob('/sys/class/scsi_disk/%s*' % HostID) li = [] for l in LUNs: chan = re.sub(":[0-9]*$",'',os.path.basename(l)) if chan not in li: li.append(chan) fullrescan = True if len(li) and scanstring == "- - -": fullrescan = False for c in li: if not refresh_scsi_channel(c): fullrescan = True if fullrescan: util.SMlog("Rescanning HostID %s with %s" % (HostID, scanstring)) path = '/sys/class/scsi_host/host%s/scan' % HostID if os.path.exists(path): try: f=open(path, 'w') f.write('%s\n' % scanstring) f.close() except: pass # Host Bus scan issued, now try to detect channels if util.wait_for_path("/sys/class/scsi_disk/%s*" % HostID, 5): # At least one LUN is mapped LUNs = glob.glob('/sys/class/scsi_disk/%s*' % HostID) li = [] for l in LUNs: chan = re.sub(":[0-9]*$",'',os.path.basename(l)) if chan not in li: li.append(chan) for c in li: refresh_scsi_channel(c)
def refresh_HostID(HostID, scanstring): LUNs = glob.glob('/sys/class/scsi_disk/%s*' % HostID) li = [] for l in LUNs: chan = re.sub(":[0-9]*$", '', os.path.basename(l)) if chan not in li: li.append(chan) fullrescan = True if len(li) and scanstring == "- - -": fullrescan = False for c in li: if not refresh_scsi_channel(c): fullrescan = True if fullrescan: util.SMlog("Rescanning HostID %s with %s" % (HostID, scanstring)) path = '/sys/class/scsi_host/host%s/scan' % HostID if os.path.exists(path): try: f = open(path, 'w') f.write('%s\n' % scanstring) f.close() except: pass # Host Bus scan issued, now try to detect channels if util.wait_for_path("/sys/class/scsi_disk/%s*" % HostID, 5): # At least one LUN is mapped LUNs = glob.glob('/sys/class/scsi_disk/%s*' % HostID) li = [] for l in LUNs: chan = re.sub(":[0-9]*$", '', os.path.basename(l)) if chan not in li: li.append(chan) for c in li: refresh_scsi_channel(c)
def refresh_scsi_channel(channel): DEV_WAIT = 5 util.SMlog("Refreshing channel %s" % channel) util.wait_for_path('/dev/disk/by-scsibus/*-%s*' % channel, DEV_WAIT) LUNs = glob.glob('/dev/disk/by-scsibus/*-%s*' % channel) try: rootdevs = util.dom0_disks() except: util.SMlog("Failed to query root disk, failing operation") return False # a) Find a LUN to issue a Query LUNs command li = [] Query = False for lun in LUNs: try: hbtl = lun.split('-')[-1] h = hbtl.split(':') l=util.pread2(["/usr/bin/sg_luns","-q",lun]).split('\n') li = [] for i in l: if len(i): li.append(int(i[0:4], 16)) util.SMlog("sg_luns query returned %s" % li) Query = True break except: pass if not Query: util.SMlog("Failed to detect or query LUN on Channel %s" % channel) return False # b) Remove stale LUNs current = glob.glob('/dev/disk/by-scsibus/*-%s:%s:%s*' % (h[0],h[1],h[2])) for cur in current: lunID = int(cur.split(':')[-1]) newhbtl = ['',h[0],h[1],h[2],str(lunID)] if os.path.realpath(cur) in rootdevs: # Don't touch the rootdev if lunID in li: li.remove(lunID) continue # Check if LUN is stale, and remove it if not lunID in li: util.SMlog("Stale LUN detected. Removing HBTL: %s" % newhbtl) scsi_dev_ctrl(newhbtl,"remove") util.wait_for_nopath(cur, DEV_WAIT) continue else: li.remove(lunID) # Query SCSIid, check it matches, if not, re-probe cur_SCSIid = os.path.basename(cur).split("-%s:%s:%s" % (h[0],h[1],h[2]))[0] real_SCSIid = getSCSIid(cur) if cur_SCSIid != real_SCSIid: util.SMlog("HBTL %s does not match, re-probing" % newhbtl) scsi_dev_ctrl(newhbtl,"remove") util.wait_for_nopath(cur, DEV_WAIT) scsi_dev_ctrl(newhbtl,"add") util.wait_for_path('/dev/disk/by-scsibus/%s-%s' % (real_SCSIid,hbtl), DEV_WAIT) pass # c) Probe for any LUNs that are not present in the system for l in li: newhbtl = ['',h[0],h[1],h[2],str(l)] util.SMlog("Probing new HBTL: %s" % newhbtl) scsi_dev_ctrl(newhbtl,"add") util.wait_for_path('/dev/disk/by-scsibus/*-%s' % hbtl, DEV_WAIT) return True
def load(self, sr_uuid): if not sr_uuid: # This is a probe call, generate a temp sr_uuid sr_uuid = util.gen_uuid() driver = SR.driver('iscsi') if self.original_srcmd.dconf.has_key('target'): self.original_srcmd.dconf['targetlist'] = self.original_srcmd.dconf['target'] iscsi = driver(self.original_srcmd, sr_uuid) self.iscsiSRs = [] self.iscsiSRs.append(iscsi) if self.dconf['target'].find(',') == 0 or self.dconf['targetIQN'] == "*": # Instantiate multiple sessions self.iscsiSRs = [] if self.dconf['targetIQN'] == "*": IQN = "any" else: IQN = self.dconf['targetIQN'] dict = {} IQNstring = "" IQNs = [] try: if self.dconf.has_key('multiSession'): IQNs = self.dconf['multiSession'].split("|") for IQN in IQNs: if IQN: dict[IQN] = "" else: try: IQNs.remove(IQN) except: # Exceptions are not expected but just in case pass # Order in multiSession must be preserved. It is important for dual-controllers. # IQNstring cannot be built with a dictionary iteration because of this IQNstring = self.dconf['multiSession'] else: for tgt in self.dconf['target'].split(','): try: tgt_ip = util._convertDNS(tgt) except: raise xs_errors.XenError('DNSError') iscsilib.ensure_daemon_running_ok(iscsi.localIQN) map = iscsilib.discovery(tgt_ip,iscsi.port,iscsi.chapuser,iscsi.chappassword,targetIQN=IQN) util.SMlog("Discovery for IP %s returned %s" % (tgt,map)) for i in range(0,len(map)): (portal,tpgt,iqn) = map[i] (ipaddr, port) = iscsilib.parse_IP_port(portal) try: util._testHost(ipaddr, long(port), 'ISCSITarget') except: util.SMlog("Target Not reachable: (%s:%s)" % (ipaddr, port)) continue key = "%s,%s,%s" % (ipaddr,port,iqn) dict[key] = "" # Again, do not mess up with IQNs order. Dual controllers will benefit from that if IQNstring == "": # Compose the IQNstring first for key in dict.iterkeys(): IQNstring += "%s|" % key # Reinitialize and store iterator key_iterator = dict.iterkeys() else: key_iterator = IQNs # Now load the individual iSCSI base classes for key in key_iterator: (ipaddr,port,iqn) = key.split(',') srcmd_copy = copy.deepcopy(self.original_srcmd) srcmd_copy.dconf['target'] = ipaddr srcmd_copy.dconf['targetIQN'] = iqn srcmd_copy.dconf['multiSession'] = IQNstring util.SMlog("Setting targetlist: %s" % srcmd_copy.dconf['targetlist']) self.iscsiSRs.append(driver(srcmd_copy, sr_uuid)) pbd = util.find_my_pbd(self.session, self.host_ref, self.sr_ref) if pbd <> None and not self.dconf.has_key('multiSession'): dconf = self.session.xenapi.PBD.get_device_config(pbd) dconf['multiSession'] = IQNstring self.session.xenapi.PBD.set_device_config(pbd, dconf) except: util.logException("LVHDoISCSISR.load") self.iscsi = self.iscsiSRs[0] # Be extremely careful not to throw exceptions here since this function # is the main one used by all operations including probing and creating pbd = None try: pbd = util.find_my_pbd(self.session, self.host_ref, self.sr_ref) except: pass # Apart from the upgrade case, user must specify a SCSIid if not self.dconf.has_key('SCSIid'): # Dual controller issue self.LUNs = {} # Dict for LUNs from all the iscsi objects for ii in range(0, len(self.iscsiSRs)): self.iscsi = self.iscsiSRs[ii] self._LUNprint(sr_uuid) for key in self.iscsi.LUNs: self.LUNs[key] = self.iscsi.LUNs[key] self.print_LUNs_XML() self.iscsi = self.iscsiSRs[0] # back to original value raise xs_errors.XenError('ConfigSCSIid') self.SCSIid = self.dconf['SCSIid'] # This block checks if the first iscsi target contains the right SCSIid. # If not it scans the other iscsi targets because chances are that more # than one controller is present dev_match = False forced_login = False # No need to check if only one iscsi target is present if len(self.iscsiSRs) == 1: pass else: target_success = False attempt_discovery = False for iii in range(0, len(self.iscsiSRs)): # Check we didn't leave any iscsi session open # If exceptions happened before, the cleanup function has worked on the right target. if forced_login == True: try: iscsilib.ensure_daemon_running_ok(self.iscsi.localIQN) iscsilib.logout(self.iscsi.target, self.iscsi.targetIQN) forced_login = False except: raise xs_errors.XenError('ISCSILogout') self.iscsi = self.iscsiSRs[iii] util.SMlog("path %s" %self.iscsi.path) util.SMlog("iscsci data: targetIQN %s, portal %s" % (self.iscsi.targetIQN, self.iscsi.target)) iscsilib.ensure_daemon_running_ok(self.iscsi.localIQN) if not iscsilib._checkTGT(self.iscsi.targetIQN): attempt_discovery = True try: # Ensure iscsi db has been populated map = iscsilib.discovery( self.iscsi.target, self.iscsi.port, self.iscsi.chapuser, self.iscsi.chappassword, targetIQN=self.iscsi.targetIQN) if len(map) == 0: util.SMlog("Discovery for iscsi data targetIQN %s," " portal %s returned empty list" " Trying another path if available" % (self.iscsi.targetIQN, self.iscsi.target)) continue except: util.SMlog("Discovery failed for iscsi data targetIQN" " %s, portal %s. Trying another path if" " available" % (self.iscsi.targetIQN, self.iscsi.target)) continue try: iscsilib.login(self.iscsi.target, self.iscsi.targetIQN, self.iscsi.chapuser, self.iscsi.chappassword, self.iscsi.incoming_chapuser, self.iscsi.incoming_chappassword, self.mpath == "true") except: util.SMlog("Login failed for iscsi data targetIQN %s," " portal %s. Trying another path" " if available" % (self.iscsi.targetIQN, self.iscsi.target)) continue target_success = True; forced_login = True # A session should be active. if not util.wait_for_path(self.iscsi.path, ISCSISR.MAX_TIMEOUT): util.SMlog("%s has no associated LUNs" % self.iscsi.targetIQN) continue scsiid_path = "/dev/disk/by-id/scsi-" + self.SCSIid if not util.wait_for_path(scsiid_path, ISCSISR.MAX_TIMEOUT): util.SMlog("%s not found" %scsiid_path) continue for file in filter(self.iscsi.match_lun, util.listdir(self.iscsi.path)): lun_path = os.path.join(self.iscsi.path,file) lun_dev = scsiutil.getdev(lun_path) try: lun_scsiid = scsiutil.getSCSIid(lun_dev) except: util.SMlog("getSCSIid failed on %s in iscsi %s: LUN" " offline or iscsi path down" % (lun_dev, self.iscsi.path)) continue util.SMlog("dev from lun %s %s" %(lun_dev, lun_scsiid)) if lun_scsiid == self.SCSIid: util.SMlog("lun match in %s" %self.iscsi.path) dev_match = True # No more need to raise ISCSITarget exception. # Resetting attempt_discovery attempt_discovery = False break if dev_match: if iii == 0: break util.SMlog("IQN reordering needed") new_iscsiSRs = [] IQNs = {} IQNstring = "" # iscsiSRs can be seen as a circular buffer: the head now is the matching one for kkk in range(iii, len(self.iscsiSRs)) + range(0, iii): new_iscsiSRs.append(self.iscsiSRs[kkk]) ipaddr = self.iscsiSRs[kkk].target port = self.iscsiSRs[kkk].port iqn = self.iscsiSRs[kkk].targetIQN key = "%s,%s,%s" % (ipaddr,port,iqn) # The final string must preserve the order without repetition if not IQNs.has_key(key): IQNs[key] = "" IQNstring += "%s|" % key util.SMlog("IQNstring is now %s" %IQNstring) self.iscsiSRs = new_iscsiSRs util.SMlog("iqn %s is leading now" %self.iscsiSRs[0].targetIQN) # Updating pbd entry, if any try: pbd = util.find_my_pbd(self.session, self.host_ref, self.sr_ref) if pbd <> None and self.dconf.has_key('multiSession'): util.SMlog("Updating multiSession in PBD") dconf = self.session.xenapi.PBD.get_device_config(pbd) dconf['multiSession'] = IQNstring self.session.xenapi.PBD.set_device_config(pbd, dconf) except: pass break if not target_success and attempt_discovery: raise xs_errors.XenError('ISCSITarget') # Check for any unneeded open iscsi sessions if forced_login == True: try: iscsilib.ensure_daemon_running_ok(self.iscsi.localIQN) iscsilib.logout(self.iscsi.target, self.iscsi.targetIQN) forced_login = False except: raise xs_errors.XenError('ISCSILogout') self._pathrefresh(LVHDoISCSISR, load = False) LVHDSR.LVHDSR.load(self, sr_uuid)
def refresh_scsi_channel(channel): DEV_WAIT = 5 util.SMlog("Refreshing channel %s" % channel) util.wait_for_path('/dev/disk/by-scsibus/*-%s*' % channel, DEV_WAIT) LUNs = glob.glob('/dev/disk/by-scsibus/*-%s*' % channel) try: rootdevs = util.dom0_disks() except: util.SMlog("Failed to query root disk, failing operation") return False # a) Find a LUN to issue a Query LUNs command li = [] Query = False for lun in LUNs: try: hbtl = lun.split('-')[-1] h = hbtl.split(':') l = util.pread2(["/usr/bin/sg_luns", "-q", lun]).split('\n') li = [] for i in l: if len(i): li.append(int(i[0:4], 16)) util.SMlog("sg_luns query returned %s" % li) Query = True break except: pass if not Query: util.SMlog("Failed to detect or query LUN on Channel %s" % channel) return False # b) Remove stale LUNs current = glob.glob('/dev/disk/by-scsibus/*-%s:%s:%s*' % (h[0], h[1], h[2])) for cur in current: lunID = int(cur.split(':')[-1]) newhbtl = ['', h[0], h[1], h[2], str(lunID)] if os.path.realpath(cur) in rootdevs: # Don't touch the rootdev if lunID in li: li.remove(lunID) continue # Check if LUN is stale, and remove it if not lunID in li: util.SMlog("Stale LUN detected. Removing HBTL: %s" % newhbtl) scsi_dev_ctrl(newhbtl, "remove") util.wait_for_nopath(cur, DEV_WAIT) continue else: li.remove(lunID) # Check if the device is still present if not os.path.exists(cur): continue # Query SCSIid, check it matches, if not, re-probe cur_SCSIid = os.path.basename(cur).split("-%s:%s:%s" % (h[0], h[1], h[2]))[0] real_SCSIid = getSCSIid(cur) if cur_SCSIid != real_SCSIid: util.SMlog("HBTL %s does not match, re-probing" % newhbtl) scsi_dev_ctrl(newhbtl, "remove") util.wait_for_nopath(cur, DEV_WAIT) scsi_dev_ctrl(newhbtl, "add") util.wait_for_path( '/dev/disk/by-scsibus/%s-%s' % (real_SCSIid, hbtl), DEV_WAIT) pass # c) Probe for any LUNs that are not present in the system for l in li: newhbtl = ['', h[0], h[1], h[2], str(l)] newhbtlstr = "%s:%s:%s:%s" % (h[0], h[1], h[2], str(l)) util.SMlog("Probing new HBTL: %s" % newhbtl) scsi_dev_ctrl(newhbtl, "add") util.wait_for_path('/dev/disk/by-scsibus/*-%s' % newhbtlstr, DEV_WAIT) return True
def load(self, sr_uuid): if not sr_uuid: # This is a probe call, generate a temp sr_uuid sr_uuid = util.gen_uuid() driver = SR.driver('iscsi') if self.original_srcmd.dconf.has_key('target'): self.original_srcmd.dconf[ 'targetlist'] = self.original_srcmd.dconf['target'] iscsi = driver(self.original_srcmd, sr_uuid) self.iscsiSRs = [] self.iscsiSRs.append(iscsi) if self.dconf['target'].find( ',') == 0 or self.dconf['targetIQN'] == "*": # Instantiate multiple sessions self.iscsiSRs = [] if self.dconf['targetIQN'] == "*": IQN = "any" else: IQN = self.dconf['targetIQN'] dict = {} IQNstring = "" IQNs = [] try: if self.dconf.has_key('multiSession'): IQNs = self.dconf['multiSession'].split("|") for IQN in IQNs: if IQN: dict[IQN] = "" else: try: IQNs.remove(IQN) except: # Exceptions are not expected but just in case pass # Order in multiSession must be preserved. It is important for dual-controllers. # IQNstring cannot be built with a dictionary iteration because of this IQNstring = self.dconf['multiSession'] else: for tgt in self.dconf['target'].split(','): try: tgt_ip = util._convertDNS(tgt) except: raise xs_errors.XenError('DNSError') iscsilib.ensure_daemon_running_ok(iscsi.localIQN) map = iscsilib.discovery(tgt_ip, iscsi.port, iscsi.chapuser, iscsi.chappassword, targetIQN=IQN) util.SMlog("Discovery for IP %s returned %s" % (tgt, map)) for i in range(0, len(map)): (portal, tpgt, iqn) = map[i] (ipaddr, port) = iscsilib.parse_IP_port(portal) try: util._testHost(ipaddr, long(port), 'ISCSITarget') except: util.SMlog("Target Not reachable: (%s:%s)" % (ipaddr, port)) continue key = "%s,%s,%s" % (ipaddr, port, iqn) dict[key] = "" # Again, do not mess up with IQNs order. Dual controllers will benefit from that if IQNstring == "": # Compose the IQNstring first for key in dict.iterkeys(): IQNstring += "%s|" % key # Reinitialize and store iterator key_iterator = dict.iterkeys() else: key_iterator = IQNs # Now load the individual iSCSI base classes for key in key_iterator: (ipaddr, port, iqn) = key.split(',') srcmd_copy = copy.deepcopy(self.original_srcmd) srcmd_copy.dconf['target'] = ipaddr srcmd_copy.dconf['targetIQN'] = iqn srcmd_copy.dconf['multiSession'] = IQNstring util.SMlog("Setting targetlist: %s" % srcmd_copy.dconf['targetlist']) self.iscsiSRs.append(driver(srcmd_copy, sr_uuid)) pbd = util.find_my_pbd(self.session, self.host_ref, self.sr_ref) if pbd <> None and not self.dconf.has_key('multiSession'): dconf = self.session.xenapi.PBD.get_device_config(pbd) dconf['multiSession'] = IQNstring self.session.xenapi.PBD.set_device_config(pbd, dconf) except: util.logException("OCFSoISCSISR.load") self.iscsi = self.iscsiSRs[0] # Be extremely careful not to throw exceptions here since this function # is the main one used by all operations including probing and creating pbd = None try: pbd = util.find_my_pbd(self.session, self.host_ref, self.sr_ref) except: pass # Apart from the upgrade case, user must specify a SCSIid if not self.dconf.has_key('SCSIid'): # Dual controller issue self.LUNs = {} # Dict for LUNs from all the iscsi objects for ii in range(0, len(self.iscsiSRs)): self.iscsi = self.iscsiSRs[ii] self._LUNprint(sr_uuid) for key in self.iscsi.LUNs: self.LUNs[key] = self.iscsi.LUNs[key] self.print_LUNs_XML() self.iscsi = self.iscsiSRs[0] # back to original value raise xs_errors.XenError('ConfigSCSIid') self.SCSIid = self.dconf['SCSIid'] # This block checks if the first iscsi target contains the right SCSIid. # If not it scans the other iscsi targets because chances are that more # than one controller is present dev_match = False forced_login = False # No need to check if only one iscsi target is present if len(self.iscsiSRs) == 1: pass else: target_success = False attempt_discovery = False for iii in range(0, len(self.iscsiSRs)): # Check we didn't leave any iscsi session open # If exceptions happened before, the cleanup function has worked on the right target. if forced_login == True: try: iscsilib.ensure_daemon_running_ok(self.iscsi.localIQN) iscsilib.logout(self.iscsi.target, self.iscsi.targetIQN) forced_login = False except: raise xs_errors.XenError('ISCSILogout') self.iscsi = self.iscsiSRs[iii] util.SMlog("path %s" % self.iscsi.path) util.SMlog("iscsci data: targetIQN %s, portal %s" % (self.iscsi.targetIQN, self.iscsi.target)) iscsilib.ensure_daemon_running_ok(self.iscsi.localIQN) if not iscsilib._checkTGT(self.iscsi.targetIQN): attempt_discovery = True try: # Ensure iscsi db has been populated map = iscsilib.discovery( self.iscsi.target, self.iscsi.port, self.iscsi.chapuser, self.iscsi.chappassword, targetIQN=self.iscsi.targetIQN) if len(map) == 0: util.SMlog( "Discovery for iscsi data targetIQN %s," " portal %s returned empty list" " Trying another path if available" % (self.iscsi.targetIQN, self.iscsi.target)) continue except: util.SMlog("Discovery failed for iscsi data targetIQN" " %s, portal %s. Trying another path if" " available" % (self.iscsi.targetIQN, self.iscsi.target)) continue try: iscsilib.login(self.iscsi.target, self.iscsi.targetIQN, self.iscsi.chapuser, self.iscsi.chappassword, self.iscsi.incoming_chapuser, self.iscsi.incoming_chappassword, self.mpath == "true") except: util.SMlog("Login failed for iscsi data targetIQN %s," " portal %s. Trying another path" " if available" % (self.iscsi.targetIQN, self.iscsi.target)) continue target_success = True forced_login = True # A session should be active. if not util.wait_for_path(self.iscsi.path, ISCSISR.MAX_TIMEOUT): util.SMlog("%s has no associated LUNs" % self.iscsi.targetIQN) continue scsiid_path = "/dev/disk/by-id/scsi-" + self.SCSIid if not util.wait_for_path(scsiid_path, ISCSISR.MAX_TIMEOUT): util.SMlog("%s not found" % scsiid_path) continue for file in filter(self.iscsi.match_lun, util.listdir(self.iscsi.path)): lun_path = os.path.join(self.iscsi.path, file) lun_dev = scsiutil.getdev(lun_path) try: lun_scsiid = scsiutil.getSCSIid(lun_dev) except: util.SMlog("getSCSIid failed on %s in iscsi %s: LUN" " offline or iscsi path down" % (lun_dev, self.iscsi.path)) continue util.SMlog("dev from lun %s %s" % (lun_dev, lun_scsiid)) if lun_scsiid == self.SCSIid: util.SMlog("lun match in %s" % self.iscsi.path) dev_match = True # No more need to raise ISCSITarget exception. # Resetting attempt_discovery attempt_discovery = False break if dev_match: if iii == 0: break util.SMlog("IQN reordering needed") new_iscsiSRs = [] IQNs = {} IQNstring = "" # iscsiSRs can be seen as a circular buffer: the head now is the matching one for kkk in range(iii, len(self.iscsiSRs)) + range(0, iii): new_iscsiSRs.append(self.iscsiSRs[kkk]) ipaddr = self.iscsiSRs[kkk].target port = self.iscsiSRs[kkk].port iqn = self.iscsiSRs[kkk].targetIQN key = "%s,%s,%s" % (ipaddr, port, iqn) # The final string must preserve the order without repetition if not IQNs.has_key(key): IQNs[key] = "" IQNstring += "%s|" % key util.SMlog("IQNstring is now %s" % IQNstring) self.iscsiSRs = new_iscsiSRs util.SMlog("iqn %s is leading now" % self.iscsiSRs[0].targetIQN) # Updating pbd entry, if any try: pbd = util.find_my_pbd(self.session, self.host_ref, self.sr_ref) if pbd <> None and self.dconf.has_key('multiSession'): util.SMlog("Updating multiSession in PBD") dconf = self.session.xenapi.PBD.get_device_config( pbd) dconf['multiSession'] = IQNstring self.session.xenapi.PBD.set_device_config( pbd, dconf) except: pass break if not target_success and attempt_discovery: raise xs_errors.XenError('ISCSITarget') # Check for any unneeded open iscsi sessions if forced_login == True: try: iscsilib.ensure_daemon_running_ok(self.iscsi.localIQN) iscsilib.logout(self.iscsi.target, self.iscsi.targetIQN) forced_login = False except: raise xs_errors.XenError('ISCSILogout') self._pathrefresh(OCFSoISCSISR, load=False) OCFSSR.OCFSSR.load(self, sr_uuid)