use of com.emc.storageos.db.client.model.FCZoneReference in project coprhd-controller by CoprHD.
the class NetworkDeviceController method addRemoveZones.
/**
* Add/remove a group of zones as given by their NetworkFabricInfo structures.
* ALL fabricInfos must be using the same NetworkDevice, and the same fabricId. There is a higher level
* subroutine to split complex requests into sets of requests with the same NetworkDevice and fabricId.
*
* @param networkSystem NetworkDevice
* @param fabricId String
* @param exportGroupUri The ExportGroup URI. Used for reference counting.
* @param fabricInfos - Describe each zone.
* @param activateZones - activate active zoneset after zones change
* @param retryAltNetworkDevice - a boolean to indicate if re-try to be done.
* This is to stop this function from running again after the alternate
* system is retried once.
* @return BiosCommandResult
* @throws ControllerException
*/
private BiosCommandResult addRemoveZones(NetworkSystem networkSystem, String fabricId, String fabricWwn, URI exportGroupUri, List<NetworkFCZoneInfo> fabricInfos, boolean doRemove, boolean retryAltNetworkDevice) throws ControllerException {
BiosCommandResult result = null;
String taskId = UUID.randomUUID().toString();
List<Zone> zones = new ArrayList<Zone>();
// Make the zone operations. Don't make the same zone more than once,
// as determined by its key. The same zone shows up multiple times because it
// must be recorded for each volume in the FCZoneReference table.
HashSet<String> keySet = new HashSet<String>();
for (NetworkFCZoneInfo fabricInfo : fabricInfos) {
String key = fabricInfo.makeEndpointsKey();
if (false == keySet.contains(key)) {
keySet.add(key);
// neither create nor delete zones found on the switch
if (fabricInfo.isExistingZone()) {
_log.info("Zone {} will not be created or removed on {}, as it is not vipr created. ", fabricInfo.getZoneName(), fabricInfo.toString());
// neither create nor delete zones found on the switch
continue;
}
// Don't actually remove the zone if it's not the last reference
if (doRemove && !fabricInfo._isLastReference) {
_log.info("Zone {} will not be removed on {}, as still the zone is used to expose other volumes in export groups ", fabricInfo.getZoneName(), fabricInfo.toString());
continue;
}
Zone zone = new Zone(fabricInfo.getZoneName());
for (String address : fabricInfo.getEndPoints()) {
ZoneMember member = new ZoneMember(address, ConnectivityMemberType.WWPN);
zone.getMembers().add(member);
}
zones.add(zone);
}
}
// Get the network device reference for the type of network device managed
// by the controller.
NetworkSystemDevice networkDevice = getDevice(networkSystem.getSystemType());
if (networkDevice == null) {
throw NetworkDeviceControllerException.exceptions.addRemoveZonesFailedNull(networkSystem.getSystemType());
}
// Lock to prevent concurrent operations on the same VSAN / FABRIC.
InterProcessLock fabricLock = NetworkFabricLocker.lockFabric(fabricId, _coordinator);
try {
if (doRemove) {
/* Removing zones */
result = networkDevice.removeZones(networkSystem, zones, fabricId, fabricWwn, true);
if (result.isCommandSuccess()) {
for (NetworkFCZoneInfo fabricInfo : fabricInfos) {
String refKey = fabricInfo.getZoneName() + " " + fabricInfo.getFcZoneReferenceId().toString();
try {
FCZoneReference ref = deleteFCZoneReference(fabricInfo);
if (ref != null && !zones.isEmpty()) {
recordZoneEvent(ref, OperationTypeEnum.REMOVE_SAN_ZONE.name(), OperationTypeEnum.REMOVE_SAN_ZONE.getDescription());
}
} catch (DatabaseException ex) {
_log.error("Could not delete FCZoneReference: " + refKey);
}
}
}
} else {
/* Adding zones */
_log.debug("Adding zones on network system {} ", networkSystem.getNativeGuid());
result = networkDevice.addZones(networkSystem, zones, fabricId, fabricWwn, true);
if (result.isCommandSuccess()) {
for (NetworkFCZoneInfo fabricInfo : fabricInfos) {
String refKey = fabricInfo.getZoneName() + " " + fabricInfo.getVolumeId().toString();
try {
String[] newOrExisting = new String[1];
FCZoneReference ref = addZoneReference(exportGroupUri, fabricInfo, newOrExisting);
// this is needed for rollback
fabricInfo.setFcZoneReferenceId(ref.getId());
_log.info(String.format("%s FCZoneReference key: %s volume %s group %s", newOrExisting[0], ref.getPwwnKey(), ref.getVolumeUri(), exportGroupUri));
if (!zones.isEmpty()) {
recordZoneEvent(ref, OperationTypeEnum.ADD_SAN_ZONE.name(), OperationTypeEnum.ADD_SAN_ZONE.getDescription());
}
} catch (DatabaseException ex) {
_log.error("Could not persist FCZoneReference: " + refKey);
}
}
}
}
// Update the FCZoneInfo structures if we changed device state for rollback.
Map<String, String> map = (Map<String, String>) result.getObjectList().get(0);
for (NetworkFCZoneInfo info : fabricInfos) {
if (NetworkSystemDevice.SUCCESS.equals(map.get(info.getZoneName()))) {
info.setCanBeRolledBack(true);
} else {
info.setCanBeRolledBack(false);
}
}
if (!result.isCommandSuccess()) {
ServiceError serviceError = NetworkDeviceControllerException.errors.addRemoveZonesFailed(networkSystem.getSystemType());
setStatus(ExportGroup.class, exportGroupUri, taskId, false, serviceError);
} else {
setStatus(ExportGroup.class, exportGroupUri, taskId, true, null);
}
return result;
} catch (ControllerException ex) {
String operation = doRemove ? "Remove Zones" : "Add Zones";
_log.info(String.format("waiting for 2 min before retrying %s with alternate device", operation));
try {
Thread.sleep(1000 * 120);
} catch (InterruptedException e) {
_log.warn("Thread sleep interrupted. Allowing to continue without sleep");
}
NetworkFCZoneInfo fabricInfo = fabricInfos.get(0);
URI primaryUri = fabricInfo.getNetworkDeviceId();
URI altUri = fabricInfo.getAltNetworkDeviceId();
// If we took an error, attempt a retry with an alternate device if possible.
if (altUri != null && retryAltNetworkDevice) {
NetworkFabricLocker.unlockFabric(fabricId, fabricLock);
fabricLock = null;
_log.error("Zone operation failed using device: " + primaryUri + " retrying with alternate device: " + altUri);
fabricInfo.setNetworkDeviceId(altUri);
networkSystem = getNetworkSystemObject(altUri);
return addRemoveZones(networkSystem, fabricId, fabricWwn, exportGroupUri, fabricInfos, doRemove, false);
} else {
if (result != null) {
if (!result.isCommandSuccess()) {
ServiceError serviceError = NetworkDeviceControllerException.errors.addRemoveZonesFailed(networkSystem.getSystemType());
setStatus(ExportGroup.class, exportGroupUri, taskId, false, serviceError);
} else {
setStatus(ExportGroup.class, exportGroupUri, taskId, true, null);
}
}
throw ex;
}
} finally {
NetworkFabricLocker.unlockFabric(fabricId, fabricLock);
}
}
use of com.emc.storageos.db.client.model.FCZoneReference in project coprhd-controller by CoprHD.
the class NetworkDeviceController method removeZone.
/**
* Remove a zone.
*
* @param volUri URI of the Volume
* @param fabricInfo NetworkFabricInfo generated by NetworkScheduler
* @return BiosCommandResult
*/
public BiosCommandResult removeZone(URI volUri, NetworkFCZoneInfo fabricInfo, boolean activateZones) throws ControllerException {
ServiceError serviceError = NetworkDeviceControllerException.errors.zoningFailedArgs(volUri.toString());
BiosCommandResult result = BiosCommandResult.createErrorResult(serviceError);
List<Zone> zones = new ArrayList<Zone>();
Zone zone = new Zone(fabricInfo.getZoneName());
zones.add(zone);
String taskId = UUID.randomUUID().toString();
for (String address : fabricInfo.getEndPoints()) {
ZoneMember member = new ZoneMember(address, ConnectivityMemberType.WWPN);
zone.getMembers().add(member);
}
// Lock to prevent concurrent operations on the same VSAN / FABRIC.
InterProcessLock fabricLock = NetworkFabricLocker.lockFabric(fabricInfo.getFabricId(), _coordinator);
try {
NetworkSystem device = getNetworkSystemObject(fabricInfo.getNetworkDeviceId());
// Get the file device reference for the type of file device managed
// by the controller.
NetworkSystemDevice networkDevice = getDevice(device.getSystemType());
if (networkDevice == null) {
throw NetworkDeviceControllerException.exceptions.removeZoneFailedNull(device.getSystemType());
}
if (fabricInfo.isLastReference() == true && !fabricInfo.isExistingZone()) {
result = networkDevice.removeZones(device, zones, fabricInfo.getFabricId(), fabricInfo.getFabricWwn(), activateZones);
} else {
// This is not the last reference, just mark our FCZoneReference for deletion
result = BiosCommandResult.createSuccessfulResult();
}
if (result.isCommandSuccess()) {
if (fabricInfo.getFcZoneReferenceId() != null) {
try {
// Mark our FcZoneReference object for removal
FCZoneReference reference = _dbClient.queryObject(FCZoneReference.class, fabricInfo.getFcZoneReferenceId());
if (reference != null) {
_dbClient.markForDeletion(reference);
recordZoneEvent(reference, OperationTypeEnum.REMOVE_SAN_ZONE.name(), OperationTypeEnum.REMOVE_SAN_ZONE.getDescription());
}
} catch (Exception ex) {
_log.error("Can't mark object for removal: " + fabricInfo.getFcZoneReferenceId());
}
}
}
if (!result.isCommandSuccess()) {
ServiceError svcError = NetworkDeviceControllerException.errors.removeZoneFailed(volUri.toString(), device.getSystemType());
setStatus(Volume.class, volUri, taskId, false, svcError);
} else {
setStatus(Volume.class, volUri, taskId, true, null);
}
} catch (ControllerException ex) {
_log.info("waiting for 2 min before retrying removeZone with alternate device");
try {
Thread.sleep(1000 * 120);
} catch (InterruptedException e) {
_log.warn("Thread sleep interrupted. Allowing to continue without sleep");
}
URI primaryUri = fabricInfo.getNetworkDeviceId();
URI altUri = fabricInfo.getAltNetworkDeviceId();
if (altUri != null && altUri != primaryUri) {
NetworkFabricLocker.unlockFabric(fabricInfo.getFabricId(), fabricLock);
fabricLock = null;
_log.error("Remove Zone failed using device: " + primaryUri + " retrying with alternate device: " + altUri);
fabricInfo.setNetworkDeviceId(altUri);
return removeZone(volUri, fabricInfo, activateZones);
} else {
ServiceError svcError = NetworkDeviceControllerException.errors.removeZoneFailedExc(volUri.toString());
setStatus(Volume.class, volUri, taskId, false, svcError);
throw ex;
}
} finally {
NetworkFabricLocker.unlockFabric(fabricInfo.getFabricId(), fabricLock);
}
return result;
}
use of com.emc.storageos.db.client.model.FCZoneReference in project coprhd-controller by CoprHD.
the class NetworkScheduler method makeExportToReferenceMap.
/**
* Makes a map from a volume/export group key to the FCZoneReference.
*
* @param key - Endpoint key consisting of concatenated WWNs
* @return Map of volume/export group key to FCZoneReference
*/
public Map<String, FCZoneReference> makeExportToReferenceMap(String key) {
Map<String, FCZoneReference> volRefMap = new HashMap<String, FCZoneReference>();
List<FCZoneReference> refs = getFCZoneReferencesForKey(key);
for (FCZoneReference ref : refs) {
String uri2key = make2UriKey(ref.getVolumeUri(), ref.getGroupUri());
volRefMap.put(uri2key, ref);
}
return volRefMap;
}
use of com.emc.storageos.db.client.model.FCZoneReference in project coprhd-controller by CoprHD.
the class NetworkScheduler method placeZones.
/**
* Select the network device and VSAN or Brocade Fabric for the host/volume zoning.
*
* The selection is based on the end points (initiator and storage port) and
* the availability of a network device that has ports connections to both
* end points. If a fabric can't be identified with both endpoints, we fall back to
* looking for a fabric with at least the storagePort discovered.
*
* @param exportGroupUri Export Group URI
* @param varrayUri Virtual Array URI
* @param protocol String (FC for this to do anything)
* @param initiatorPort The WWN of the initiator
* @param storagePort The StoragePort object
* @param hostName Used for generating the zone name.
* @param existingZones a list of existing zones for the initiator
* @param checkZones Flag to enable or disable zoning check on a Network System
*
* @return NetworkFabricInfo configured for adding zones
*/
private NetworkFCZoneInfo placeZones(URI exportGroupUri, URI varrayUri, String protocol, String initiatorPort, StoragePort storagePort, String hostName, List<Zone> existingZones, boolean checkZones) throws DeviceControllerException {
initiatorPort = formatWWN(initiatorPort);
String storagePortWwn = formatWWN(storagePort.getPortNetworkId());
if (Transport.FC != StorageProtocol.block2Transport(protocol)) {
return null;
}
_log.info("Placing a zone for initiator {} and port {}", initiatorPort, storagePortWwn);
// do some validation
NetworkLite iniNet = NetworkUtil.getEndpointNetworkLite(initiatorPort, _dbClient);
NetworkLite portNet = getStoragePortNetwork(storagePort);
if (iniNet == null || portNet == null || !NetworkUtil.checkInitiatorAndPortConnected(iniNet, portNet)) {
_log.debug(String.format("Initiator %s could not be paired with port %s", initiatorPort, storagePortWwn));
return null;
}
// False we will use the existing FCZoneReference info
if (!checkZones) {
_log.debug("Check Zones flag is false. Finding FCZoneReference for initiator {} and port {}", initiatorPort, storagePortWwn);
// Find the FCZoneReference in ViPR for the port-initiator key and the network
String key = FCZoneReference.makeEndpointsKey(initiatorPort, storagePortWwn);
List<FCZoneReference> fcZoneRefs = getFCZoneReferencesForKey(key);
FCZoneReference refTemplate = DataObjectUtils.findByProperty(fcZoneRefs, "groupUri", exportGroupUri);
if (refTemplate != null) {
_log.info("Already existing FCZoneReferences for initiator {} and port {} will be replicated for new volumes.", initiatorPort, storagePortWwn);
return createZoneInfoForRef(refTemplate, null, initiatorPort, storagePortWwn, NetworkUtil.getEndpointNetworkLite(initiatorPort, _dbClient), exportGroupUri);
} else {
_log.info("FCZoneReferences doesnt exist for initiator {} and port {} for replication.", initiatorPort, storagePortWwn);
return null;
}
} else {
_log.debug("Check Zones flag is false. Placing a zone for initiator {} and port {}", initiatorPort, storagePortWwn);
// If the zone already exists, just return its reference
NetworkFCZoneInfo zoneInfo = getZoneInfoForExistingZone(iniNet, initiatorPort, storagePort.getPortNetworkId(), existingZones);
if (zoneInfo != null) {
zoneInfo.setExportGroup(exportGroupUri);
_log.info("Already existing zone {} for initiator {} and port {} will be used.", new Object[] { zoneInfo.getZoneName(), initiatorPort, storagePortWwn });
return zoneInfo;
}
_log.debug("Could not find an existing zone for initiator {} and port {} to use." + "A new zone will be created.", new Object[] { initiatorPort, storagePortWwn });
// Create a the list of end points -
List<String> endPoints = Arrays.asList(new String[] { initiatorPort, storagePortWwn });
List<NetworkSystem> networkSystems = getZoningNetworkSystems(iniNet, portNet);
if (networkSystems.isEmpty()) {
_log.info(String.format("Could not find a network system with connection to storage port %s", storagePortWwn));
throw DeviceControllerException.exceptions.cannotFindSwitchConnectionToStoragePort(storagePortWwn);
}
// 2. Select the network system to use
NetworkSystem networkSystem = networkSystems.get(0);
// 3. identify an alternate network device, if any
_log.debug("Network system {} was selected to be the primary network system. " + "Trying to select an alternate network system.", networkSystem.getNativeGuid());
NetworkSystem altNetworkSystem = networkSystem;
for (NetworkSystem system : networkSystems) {
if (altNetworkSystem != system) {
altNetworkSystem = system;
_log.debug("Network system {} was selected to be the alternate network system.", altNetworkSystem.getNativeGuid());
break;
}
}
// 4. create the response
NetworkFCZoneInfo networkFabricInfo = null;
if (networkSystem != null) {
networkFabricInfo = new NetworkFCZoneInfo(networkSystem.getId(), iniNet.getNativeId(), NetworkUtil.getNetworkWwn(iniNet));
networkFabricInfo.getEndPoints().addAll(endPoints);
networkFabricInfo.setAltNetworkDeviceId(URI.create(altNetworkSystem.getId().toString()));
networkFabricInfo.setExportGroup(exportGroupUri);
networkFabricInfo.setCanBeRolledBack(false);
nameZone(networkFabricInfo, networkSystem.getSystemType(), hostName, initiatorPort, storagePort, !portNet.equals(iniNet));
}
return networkFabricInfo;
}
}
use of com.emc.storageos.db.client.model.FCZoneReference in project coprhd-controller by CoprHD.
the class NetworkUtil method getFCZoneReferencesFromExportGroup.
/**
* Find all FCZoneReferencethat are referencing the Export Group
*
* @param dbClient db client
* @param exportGroup export Group
* @return list of FCZoneReferencethat referring to the Export Group
*/
public static List<FCZoneReference> getFCZoneReferencesFromExportGroup(DbClient dbClient, ExportGroup exportGroup) {
List<FCZoneReference> resultFCRef = new ArrayList<FCZoneReference>();
List<URI> fcZoneReferenceURIs = dbClient.queryByType(FCZoneReference.class, true);
Iterator<FCZoneReference> fcZoneReferenceListIterator = dbClient.queryIterativeObjects(FCZoneReference.class, fcZoneReferenceURIs);
while (fcZoneReferenceListIterator.hasNext()) {
FCZoneReference fcRef = fcZoneReferenceListIterator.next();
if ((fcRef == null) || fcRef.getInactive()) {
continue;
}
if (fcRef.getGroupUri().toString().equals(exportGroup.getId().toString())) {
resultFCRef.add(fcRef);
}
}
return resultFCRef;
}
Aggregations