use of org.onosproject.net.flowobjective.NextObjective in project onos by opennetworkinglab.
the class Ofdpa2GroupHandler method removeBucket.
/**
* Removes top-level buckets from a group that represents the given next objective.
*
* @param chainsToRemove a list of group bucket chains to remove
* @param nextObjective the next objective that contains information for the
* buckets to be removed from the group
*/
protected void removeBucket(List<Deque<GroupKey>> chainsToRemove, NextObjective nextObjective) {
List<GroupBucket> bucketsToRemove = Lists.newArrayList();
// first group key is the one we want to modify
GroupKey modGroupKey = chainsToRemove.get(0).peekFirst();
Group modGroup = groupService.getGroup(deviceId, modGroupKey);
if (modGroup == null) {
log.warn("removeBucket(): Attempt to modify non-existent group {} for device {}", modGroupKey, deviceId);
return;
}
for (Deque<GroupKey> foundChain : chainsToRemove) {
// second group key is the one we wish to remove the reference to
if (foundChain.size() < 2) {
// additional check to make sure second group key exists in
// the chain.
log.warn("Can't find second group key from chain {}", foundChain);
continue;
}
GroupKey pointedGroupKey = foundChain.stream().collect(Collectors.toList()).get(1);
Group pointedGroup = groupService.getGroup(deviceId, pointedGroupKey);
if (pointedGroup == null) {
continue;
}
GroupBucket bucket;
if (nextObjective.type() == NextObjective.Type.HASHED) {
bucket = DefaultGroupBucket.createSelectGroupBucket(DefaultTrafficTreatment.builder().group(pointedGroup.id()).build());
} else {
bucket = DefaultGroupBucket.createAllGroupBucket(DefaultTrafficTreatment.builder().group(pointedGroup.id()).build());
}
bucketsToRemove.add(bucket);
}
GroupBuckets removeBuckets = new GroupBuckets(bucketsToRemove);
// for debug log
List<String> pointedGroupIds;
pointedGroupIds = bucketsToRemove.stream().map(GroupBucket::treatment).map(TrafficTreatment::allInstructions).flatMap(List::stream).filter(inst -> inst instanceof Instructions.GroupInstruction).map(inst -> (Instructions.GroupInstruction) inst).map(Instructions.GroupInstruction::groupId).map(GroupId::id).map(Integer::toHexString).map(id -> HEX_PREFIX + id).collect(Collectors.toList());
log.debug("Removing buckets from group id 0x{} pointing to group id(s) {} " + "for next id {} in device {}", Integer.toHexString(modGroup.id().id()), pointedGroupIds, nextObjective.id(), deviceId);
addPendingUpdateNextObjective(modGroupKey, nextObjective);
groupService.removeBucketsFromGroup(deviceId, modGroupKey, removeBuckets, modGroupKey, nextObjective.appId());
// potentially stale copy of allActiveKeys
synchronized (flowObjectiveStore) {
// get a fresh copy of what the store holds
NextGroup next = flowObjectiveStore.getNextGroup(nextObjective.id());
List<Deque<GroupKey>> allActiveKeys = appKryo.deserialize(next.data());
allActiveKeys = Lists.newArrayList(allActiveKeys);
// Note that since we got a new object, and ArrayDeque does not implement
// Object.equals(), we have to check the deque elems one by one
allActiveKeys.removeIf(active -> chainsToRemove.stream().anyMatch(remove -> Arrays.equals(remove.toArray(new GroupKey[0]), active.toArray(new GroupKey[0]))));
// top level group which still exists.
if (allActiveKeys.isEmpty()) {
ArrayDeque<GroupKey> top = new ArrayDeque<>();
top.add(modGroupKey);
allActiveKeys.add(top);
}
flowObjectiveStore.putNextGroup(nextObjective.id(), new OfdpaNextGroup(allActiveKeys, nextObjective));
}
}
use of org.onosproject.net.flowobjective.NextObjective in project onos by opennetworkinglab.
the class LinkCollectionIntentFlowObjectiveCompiler method createBroadcastObjective.
private List<Objective> createBroadcastObjective(ForwardingInstructions instructions, Set<TrafficTreatment> treatmentsWithDifferentPort, LinkCollectionIntent intent) {
List<Objective> objectives = Lists.newArrayList();
ForwardingObjective forwardingObjective;
NextObjective nextObjective;
Integer nextId = flowObjectiveService.allocateNextId();
forwardingObjective = buildForwardingObjective(instructions.selector(), nextId, intent.priority());
DefaultNextObjective.Builder nxBuilder = DefaultNextObjective.builder();
nxBuilder.withId(nextId).withMeta(instructions.selector()).withType(NextObjective.Type.BROADCAST).fromApp(appId).withPriority(intent.priority()).makePermanent();
treatmentsWithDifferentPort.forEach(nxBuilder::addTreatment);
nextObjective = nxBuilder.add();
objectives.add(forwardingObjective);
objectives.add(nextObjective);
return objectives;
}
use of org.onosproject.net.flowobjective.NextObjective in project onos by opennetworkinglab.
the class InOrderFlowObjectiveManager method execute.
/**
* Submit the flow objective. Starting from this point on, the execution order is not guaranteed.
* Therefore we must be certain that this method is called in-order.
*
* @param deviceId Device ID
* @param obj Flow objective
*/
private void execute(DeviceId deviceId, Objective obj) {
LogLevel logLevel = (obj.op() == Objective.Operation.VERIFY) ? LogLevel.TRACE : LogLevel.DEBUG;
Tools.log(log, logLevel, "Submit objective installer, deviceId {}, obj {}", deviceId, obj);
int priority = obj.priority();
if (obj instanceof FilteringObjective) {
FilteringObjQueueKey k = new FilteringObjQueueKey(deviceId, priority, ((FilteringObjective) obj).key());
filtObjQueueHead.put(k, obj);
super.filter(deviceId, (FilteringObjective) obj);
} else if (obj instanceof ForwardingObjective) {
ForwardingObjQueueKey k = new ForwardingObjQueueKey(deviceId, priority, ((ForwardingObjective) obj).selector());
fwdObjQueueHead.put(k, obj);
super.forward(deviceId, (ForwardingObjective) obj);
} else if (obj instanceof NextObjective) {
NextObjQueueKey k = new NextObjQueueKey(deviceId, obj.id());
nextObjQueueHead.put(k, obj);
super.next(deviceId, (NextObjective) obj);
} else {
log.error("Unknown flow objective instance: {}", obj.getClass().getName());
}
}
use of org.onosproject.net.flowobjective.NextObjective in project onos by opennetworkinglab.
the class InOrderFlowObjectiveManager method enqueue.
/**
* Enqueue flow objective. Execute the flow objective if there is no pending objective ahead.
*
* @param deviceId Device ID
* @param obj Flow objective
*/
private synchronized void enqueue(DeviceId deviceId, Objective obj) {
int queueSize;
int priority = obj.priority();
LogLevel logLevel = (obj.op() == Objective.Operation.VERIFY) ? LogLevel.TRACE : LogLevel.DEBUG;
Tools.log(log, logLevel, "Enqueue {}", obj);
if (obj instanceof FilteringObjective) {
FilteringObjQueueKey k = new FilteringObjQueueKey(deviceId, priority, ((FilteringObjective) obj).key());
filtObjQueue.put(k, obj);
queueSize = filtObjQueue.get(k).size();
} else if (obj instanceof ForwardingObjective) {
ForwardingObjQueueKey k = new ForwardingObjQueueKey(deviceId, priority, ((ForwardingObjective) obj).selector());
fwdObjQueue.put(k, obj);
queueSize = fwdObjQueue.get(k).size();
} else if (obj instanceof NextObjective) {
NextObjQueueKey k = new NextObjQueueKey(deviceId, obj.id());
nextObjQueue.put(k, obj);
queueSize = nextObjQueue.get(k).size();
} else {
log.error("Unknown flow objective instance: {}", obj.getClass().getName());
return;
}
log.trace("{} queue size {}", obj.getClass().getSimpleName(), queueSize);
// Execute immediately if there is no pending obj ahead
if (queueSize == 1) {
execute(deviceId, obj);
}
}
use of org.onosproject.net.flowobjective.NextObjective in project onos by opennetworkinglab.
the class FibInstallerTest method testRouteUpdate.
/**
* Tests updating a route.
*
* We verify that the flowObjectiveService records the correct state and that the
* correct flow is submitted to the flowObjectiveService.
*/
@Test
public void testRouteUpdate() {
// Firstly add a route
testRouteAdd();
reset(flowObjectiveService);
ResolvedRoute oldRoute = createRoute(PREFIX1, NEXT_HOP1, MAC1);
ResolvedRoute route = createRoute(PREFIX1, NEXT_HOP2, MAC2);
// Create the next objective
NextObjective nextObjective = createNextObjective(MAC2, MAC2, SW1_ETH2.port(), VLAN1, true);
flowObjectiveService.next(DEVICE_ID, nextObjective);
// Create the flow objective
ForwardingObjective fwd = createForwardingObjective(PREFIX1, true);
flowObjectiveService.forward(DEVICE_ID, fwd);
EasyMock.expectLastCall().once();
setUpFlowObjectiveService();
// Send in the update event
routeListener.event(new RouteEvent(RouteEvent.Type.ROUTE_UPDATED, route, oldRoute));
verify(flowObjectiveService);
}
Aggregations