use of org.onosproject.net.device.DeviceHandshaker in project onos by opennetworkinglab.
the class GeneralDeviceProvider method roleChanged.
@Override
public void roleChanged(DeviceId deviceId, MastershipRole newRole) {
final MastershipInfo mastershipInfo = mastershipService.getMastershipFor(deviceId);
final NodeId localNodeId = clusterService.getLocalNode().id();
if (!mastershipInfo.getRole(localNodeId).equals(newRole)) {
log.warn("Inconsistent mastership info for {}! Requested {}, but " + "mastership service reports {}, will apply the latter...", deviceId, newRole, mastershipInfo.getRole(localNodeId));
newRole = mastershipInfo.getRole(localNodeId);
}
final DeviceHandshaker handshaker = getBehaviour(deviceId, DeviceHandshaker.class);
if (handshaker == null) {
log.error("Null handshaker. Unable to notify role {} to {}", newRole, deviceId);
return;
}
// Derive preference value.
final int preference;
switch(newRole) {
case MASTER:
preference = 0;
break;
case STANDBY:
preference = mastershipInfo.backups().indexOf(localNodeId) + 1;
if (preference == 0) {
// Not found in list.
log.error("Unable to derive mastership preference for {}, " + "requested role {} but local node ID was " + "not found among list of backup nodes " + "reported by mastership service", deviceId, newRole);
return;
}
break;
case NONE:
// No preference for NONE, apply as is.
Pair<MastershipRole, Integer> pairRolePref = Pair.of(newRole, -1);
if (log.isDebugEnabled()) {
log.debug("Notifying role {} to {}", newRole, deviceId);
} else if (!pairRolePref.equals(lastRoleRequest.get(deviceId))) {
log.info("Notifying role {} to {}", newRole, deviceId);
}
lastRoleRequest.put(deviceId, pairRolePref);
handshaker.roleChanged(newRole);
return;
default:
log.error("Unrecognized mastership role {}", newRole);
return;
}
Pair<MastershipRole, Integer> pairRolePref = Pair.of(newRole, preference);
if (log.isDebugEnabled()) {
log.debug("Notifying role {} (preference {}) for term {} to {}", newRole, preference, mastershipInfo.term(), deviceId);
} else if (!pairRolePref.equals(lastRoleRequest.get(deviceId))) {
log.info("Notifying role {} (preference {}) for term {} to {}", newRole, preference, mastershipInfo.term(), deviceId);
}
lastRoleRequest.put(deviceId, pairRolePref);
try {
handshaker.roleChanged(preference, mastershipInfo.term());
} catch (UnsupportedOperationException e) {
// Preference-based method not supported.
handshaker.roleChanged(newRole);
}
}
use of org.onosproject.net.device.DeviceHandshaker in project onos by opennetworkinglab.
the class GeneralDeviceProvider method forgeDeviceDescription.
private DeviceDescription forgeDeviceDescription(DeviceId deviceId, boolean defaultAvailable) {
// Uses handshaker and provider config to get driver data.
final DeviceHandshaker handshaker = getBehaviour(deviceId, DeviceHandshaker.class);
final Driver driver = handshaker != null ? handshaker.handler().driver() : null;
return new DefaultDeviceDescription(deviceId.uri(), Device.Type.SWITCH, driver != null ? driver.manufacturer() : UNKNOWN, driver != null ? driver.hwVersion() : UNKNOWN, driver != null ? driver.swVersion() : UNKNOWN, UNKNOWN, new ChassisId(), defaultAvailable, DefaultAnnotations.EMPTY);
}
use of org.onosproject.net.device.DeviceHandshaker in project onos by opennetworkinglab.
the class PiPipeconfWatchdogManager method probeTask.
private void probeTask(Device device) {
if (!isLocalMaster(device)) {
return;
}
final PiPipeconfId pipeconfId = pipeconfMappingStore.getPipeconfId(device.id());
if (pipeconfId == null || !device.is(PiPipelineProgrammable.class)) {
return;
}
if (pipeconfService.getPipeconf(pipeconfId).isEmpty()) {
log.warn("Pipeconf {} is not registered, skipping probe for {}", pipeconfId, device.id());
return;
}
final PiPipeconf pipeconf = pipeconfService.getPipeconf(pipeconfId).get();
if (!device.is(DeviceHandshaker.class)) {
log.error("Missing DeviceHandshaker behavior for {}", device.id());
return;
}
final boolean success = doSetPipeconfIfRequired(device, pipeconf);
// the mastership after pipeline probe returns.
if (isLocalMaster(device)) {
// (next reconcile interval)
if (success) {
signalStatusReady(device.id());
signalStatusConfigured(device.id());
} else {
// When a network partition occurs watchdog is stuck for LONG_TIMEOUT
// before returning and will mark the device offline. However, in the
// meanwhile the mastership has been passed to another instance which is
// already connected and has already marked the device online.
signalStatusUnknown(device.id());
}
} else {
log.warn("No longer the master for {} aborting probe task", device.id());
}
}
use of org.onosproject.net.device.DeviceHandshaker in project onos by opennetworkinglab.
the class PiPipeconfWatchdogManager method doSetPipeconfIfRequired.
/**
* Returns true if the given device is known to be configured with the given
* pipeline, false otherwise. If necessary, this method enforces setting the
* given pipeconf using drivers.
*
* @param device device
* @param pipeconf pipeconf
* @return boolean
*/
private boolean doSetPipeconfIfRequired(Device device, PiPipeconf pipeconf) {
log.debug("Starting watchdog task for {} ({})", device.id(), pipeconf.id());
final PiPipelineProgrammable pipelineProg = device.as(PiPipelineProgrammable.class);
final DeviceHandshaker handshaker = device.as(DeviceHandshaker.class);
if (!handshaker.hasConnection()) {
log.warn("There is no connectivity with {}", device.id());
return false;
}
if (Futures.getUnchecked(pipelineProg.isPipeconfSet(pipeconf)) && configuredDevices.contains(device.id())) {
log.debug("Pipeconf {} already configured on {}", pipeconf.id(), device.id());
return true;
}
return Futures.getUnchecked(pipelineProg.setPipeconf(pipeconf));
}
use of org.onosproject.net.device.DeviceHandshaker in project onos by opennetworkinglab.
the class GeneralDeviceProvider method handleConnectionSetup.
private void handleConnectionSetup(DeviceId deviceId) {
assertConfig(deviceId);
// Bind pipeconf (if any and if device is capable).
bindPipeconfIfRequired(deviceId);
// Get handshaker.
final DeviceHandshaker handshaker = handshakerOrFail(deviceId);
if (handshaker.hasConnection() || handshakersWithListeners.containsKey(deviceId)) {
throw new DeviceTaskException("connection already exists");
}
// Add device agent listener.
handshakersWithListeners.put(deviceId, handshaker);
handshaker.addDeviceAgentListener(id(), deviceAgentListener);
// Start connection via handshaker.
if (!handshaker.connect()) {
// Failed! Remove listeners.
handshaker.removeDeviceAgentListener(id());
handshakersWithListeners.remove(deviceId);
// Clean up connection state leftovers.
handshaker.disconnect();
throw new DeviceTaskException("connection failed");
}
createOrUpdateDevice(deviceId, false);
// From here we expect a CHANNEL_OPEN event to update availability.
}
Aggregations