Search in sources :

Example 21 with FlowRuleOperations

use of org.onosproject.net.flow.FlowRuleOperations in project onos by opennetworkinglab.

the class SpringOpenTTP method processFilter.

private void processFilter(FilteringObjective filt, boolean install, ApplicationId applicationId) {
    // ports as the key
    if (filt.key().equals(Criteria.dummy()) || filt.key().type() != Criterion.Type.IN_PORT) {
        log.warn("No key defined in filtering objective from app: {}. Not" + "processing filtering objective", applicationId);
        fail(filt, ObjectiveError.UNKNOWN);
        return;
    }
    EthCriterion ethCriterion = null;
    VlanIdCriterion vlanIdCriterion = null;
    // convert filtering conditions for switch-intfs into flowrules
    FlowRuleOperations.Builder ops = FlowRuleOperations.builder();
    for (Criterion criterion : filt.conditions()) {
        if (criterion.type() == Criterion.Type.ETH_DST) {
            ethCriterion = (EthCriterion) criterion;
        } else if (criterion.type() == Criterion.Type.VLAN_VID) {
            vlanIdCriterion = (VlanIdCriterion) criterion;
        } else if (criterion.type() == Criterion.Type.IPV4_DST) {
            log.debug("driver does not process IP filtering rules as it " + "sends all misses in the IP table to the controller");
        } else {
            log.warn("Driver does not currently process filtering condition" + " of type: {}", criterion.type());
            fail(filt, ObjectiveError.UNSUPPORTED);
        }
    }
    VlanId assignedVlan = null;
    VlanId modifiedVlan = null;
    VlanId pushedVlan = null;
    boolean pushVlan = false;
    boolean popVlan = false;
    if (vlanIdCriterion != null) {
        if (filt.meta() != null) {
            for (Instruction i : filt.meta().allInstructions()) {
                if (i instanceof L2ModificationInstruction) {
                    if (((L2ModificationInstruction) i).subtype().equals(L2ModificationInstruction.L2SubType.VLAN_PUSH)) {
                        pushVlan = true;
                    } else if (((L2ModificationInstruction) i).subtype().equals(L2ModificationInstruction.L2SubType.VLAN_POP)) {
                        if (modifiedVlan != null) {
                            log.error("Pop tag is not allowed after modify VLAN operation " + "in filtering objective", deviceId);
                            fail(filt, ObjectiveError.BADPARAMS);
                            return;
                        }
                        popVlan = true;
                    }
                }
                if (i instanceof ModVlanIdInstruction) {
                    if (pushVlan && vlanIdCriterion.vlanId() != VlanId.NONE) {
                        // Modify VLAN should not appear after pushing a new tag
                        if (pushedVlan != null) {
                            log.error("Modify VLAN not allowed after push tag operation " + "in filtering objective", deviceId);
                            fail(filt, ObjectiveError.BADPARAMS);
                            return;
                        }
                        pushedVlan = ((ModVlanIdInstruction) i).vlanId();
                    } else if (vlanIdCriterion.vlanId() == VlanId.NONE) {
                        // For untagged packets the pushed VLAN ID will be saved in assignedVlan
                        // just to ensure the driver works as designed for the fabric use case
                        assignedVlan = ((ModVlanIdInstruction) i).vlanId();
                    } else {
                        // For tagged packets modifiedVlan will contain the modified value of existing tag
                        if (modifiedVlan != null) {
                            log.error("Driver does not allow multiple modify VLAN operations " + "in the same filtering objective", deviceId);
                            fail(filt, ObjectiveError.BADPARAMS);
                            return;
                        }
                        modifiedVlan = ((ModVlanIdInstruction) i).vlanId();
                    }
                }
            }
        }
        // For VLAN cross-connect packets, use the configured VLAN unless there is an explicitly provided VLAN ID
        if (vlanIdCriterion.vlanId() != VlanId.NONE) {
            if (assignedVlan == null) {
                assignedVlan = vlanIdCriterion.vlanId();
            }
        // For untagged packets, assign a VLAN ID
        } else {
            if (filt.meta() == null) {
                log.error("Missing metadata in filtering objective required " + "for vlan assignment in dev {}", deviceId);
                fail(filt, ObjectiveError.BADPARAMS);
                return;
            }
            if (assignedVlan == null) {
                log.error("Driver requires an assigned vlan-id to tag incoming " + "untagged packets. Not processing vlan filters on " + "device {}", deviceId);
                fail(filt, ObjectiveError.BADPARAMS);
                return;
            }
        }
        if (pushVlan && popVlan) {
            log.error("Cannot push and pop vlan in the same filtering objective");
            fail(filt, ObjectiveError.BADPARAMS);
            return;
        }
        if (popVlan && vlanIdCriterion.vlanId() == VlanId.NONE) {
            log.error("Cannot pop vlan for untagged packets");
            fail(filt, ObjectiveError.BADPARAMS);
            return;
        }
        if ((pushVlan && pushedVlan == null) && vlanIdCriterion.vlanId() != VlanId.NONE) {
            log.error("No VLAN ID provided for push tag operation");
            fail(filt, ObjectiveError.BADPARAMS);
            return;
        }
    }
    if (ethCriterion == null) {
        log.debug("filtering objective missing dstMac, cannot program TMAC table");
    } else {
        for (FlowRule tmacRule : processEthDstFilter(ethCriterion, vlanIdCriterion, filt, assignedVlan, applicationId)) {
            log.debug("adding MAC filtering rules in TMAC table: {} for dev: {}", tmacRule, deviceId);
            ops = install ? ops.add(tmacRule) : ops.remove(tmacRule);
        }
    }
    if (vlanIdCriterion == null) {
        log.debug("filtering objective missing VLAN ID criterion, " + "cannot program VLAN Table");
    } else {
        for (FlowRule vlanRule : processVlanIdFilter(vlanIdCriterion, filt, assignedVlan, modifiedVlan, pushedVlan, pushVlan, popVlan, applicationId)) {
            log.debug("adding VLAN filtering rule in VLAN table: {} for dev: {}", vlanRule, deviceId);
            ops = install ? ops.add(vlanRule) : ops.remove(vlanRule);
        }
    }
    // apply filtering flow rules
    flowRuleService.apply(ops.build(new FlowRuleOperationsContext() {

        @Override
        public void onSuccess(FlowRuleOperations ops) {
            pass(filt);
            log.debug("Provisioned tables in {} with fitering " + "rules", deviceId);
        }

        @Override
        public void onError(FlowRuleOperations ops) {
            fail(filt, ObjectiveError.FLOWINSTALLATIONFAILED);
            log.warn("Failed to provision tables in {} with " + "fitering rules", deviceId);
        }
    }));
}
Also used : FlowRuleOperations(org.onosproject.net.flow.FlowRuleOperations) EthCriterion(org.onosproject.net.flow.criteria.EthCriterion) MplsBosCriterion(org.onosproject.net.flow.criteria.MplsBosCriterion) PortCriterion(org.onosproject.net.flow.criteria.PortCriterion) IPCriterion(org.onosproject.net.flow.criteria.IPCriterion) MplsCriterion(org.onosproject.net.flow.criteria.MplsCriterion) EthCriterion(org.onosproject.net.flow.criteria.EthCriterion) Criterion(org.onosproject.net.flow.criteria.Criterion) EthTypeCriterion(org.onosproject.net.flow.criteria.EthTypeCriterion) VlanIdCriterion(org.onosproject.net.flow.criteria.VlanIdCriterion) ModVlanIdInstruction(org.onosproject.net.flow.instructions.L2ModificationInstruction.ModVlanIdInstruction) L2ModificationInstruction(org.onosproject.net.flow.instructions.L2ModificationInstruction) DefaultFlowRule(org.onosproject.net.flow.DefaultFlowRule) FlowRule(org.onosproject.net.flow.FlowRule) L2ModificationInstruction(org.onosproject.net.flow.instructions.L2ModificationInstruction) OutputInstruction(org.onosproject.net.flow.instructions.Instructions.OutputInstruction) ModVlanIdInstruction(org.onosproject.net.flow.instructions.L2ModificationInstruction.ModVlanIdInstruction) Instruction(org.onosproject.net.flow.instructions.Instruction) VlanId(org.onlab.packet.VlanId) FlowRuleOperationsContext(org.onosproject.net.flow.FlowRuleOperationsContext) VlanIdCriterion(org.onosproject.net.flow.criteria.VlanIdCriterion)

Example 22 with FlowRuleOperations

use of org.onosproject.net.flow.FlowRuleOperations in project onos by opennetworkinglab.

the class OvsOfdpaPipeline method initTableMiss.

/**
 * Install table-miss flow entry.
 *
 * If treatment exists, use it directly.
 * Else if treatment does not exist but nextTable > 0, transit to next table.
 * Else apply empty treatment.
 *
 * @param thisTable this table ID
 * @param nextTable next table ID
 * @param treatment traffic treatment to apply.
 */
private void initTableMiss(int thisTable, int nextTable, TrafficTreatment treatment) {
    FlowRuleOperations.Builder ops = FlowRuleOperations.builder();
    TrafficSelector selector = DefaultTrafficSelector.builder().build();
    if (treatment == null) {
        TrafficTreatment.Builder tBuilder = DefaultTrafficTreatment.builder();
        if (nextTable > 0) {
            tBuilder.transition(nextTable);
        }
        treatment = tBuilder.build();
    }
    FlowRule rule = DefaultFlowRule.builder().forDevice(deviceId).withSelector(selector).withTreatment(treatment).withPriority(LOWEST_PRIORITY).fromApp(driverId).makePermanent().forTable(thisTable).build();
    ops = ops.add(rule);
    flowRuleService.apply(ops.build(new FlowRuleOperationsContext() {

        @Override
        public void onSuccess(FlowRuleOperations ops) {
            log.info("Initialized table {} on {}", thisTable, deviceId);
        }

        @Override
        public void onError(FlowRuleOperations ops) {
            log.warn("Failed to initialize table {} on {}", thisTable, deviceId);
        }
    }));
}
Also used : FlowRuleOperations(org.onosproject.net.flow.FlowRuleOperations) TrafficSelector(org.onosproject.net.flow.TrafficSelector) DefaultTrafficSelector(org.onosproject.net.flow.DefaultTrafficSelector) DefaultFlowRule(org.onosproject.net.flow.DefaultFlowRule) FlowRule(org.onosproject.net.flow.FlowRule) DefaultTrafficTreatment(org.onosproject.net.flow.DefaultTrafficTreatment) TrafficTreatment(org.onosproject.net.flow.TrafficTreatment) FlowRuleOperationsContext(org.onosproject.net.flow.FlowRuleOperationsContext)

Example 23 with FlowRuleOperations

use of org.onosproject.net.flow.FlowRuleOperations in project onos by opennetworkinglab.

the class OvsOfdpaPipeline method initPuntTable.

/**
 * Install lldp/bbdp matching rules at table PUNT_TABLE
 * that forward traffic to controller.
 */
private void initPuntTable() {
    FlowRuleOperations.Builder ops = FlowRuleOperations.builder();
    TrafficTreatment treatment = DefaultTrafficTreatment.builder().punt().build();
    // Add punt rule for LLDP and BDDP
    TrafficSelector.Builder lldpSelector = DefaultTrafficSelector.builder();
    lldpSelector.matchEthType(EthType.EtherType.LLDP.ethType().toShort());
    FlowRule lldpRule = DefaultFlowRule.builder().forDevice(deviceId).withSelector(lldpSelector.build()).withTreatment(treatment).withPriority(HIGHEST_PRIORITY).fromApp(driverId).makePermanent().forTable(PUNT_TABLE).build();
    ops = ops.add(lldpRule);
    TrafficSelector.Builder bbdpSelector = DefaultTrafficSelector.builder();
    bbdpSelector.matchEthType(EthType.EtherType.BDDP.ethType().toShort());
    FlowRule bbdpRule = DefaultFlowRule.builder().forDevice(deviceId).withSelector(bbdpSelector.build()).withTreatment(treatment).withPriority(HIGHEST_PRIORITY).fromApp(driverId).makePermanent().forTable(PUNT_TABLE).build();
    ops.add(bbdpRule);
    flowRuleService.apply(ops.build(new FlowRuleOperationsContext() {

        @Override
        public void onSuccess(FlowRuleOperations ops) {
            log.info("Initialized table {} on {}", PUNT_TABLE, deviceId);
        }

        @Override
        public void onError(FlowRuleOperations ops) {
            log.warn("Failed to initialize table {} on {}", PUNT_TABLE, deviceId);
        }
    }));
}
Also used : FlowRuleOperations(org.onosproject.net.flow.FlowRuleOperations) TrafficSelector(org.onosproject.net.flow.TrafficSelector) DefaultTrafficSelector(org.onosproject.net.flow.DefaultTrafficSelector) DefaultFlowRule(org.onosproject.net.flow.DefaultFlowRule) FlowRule(org.onosproject.net.flow.FlowRule) DefaultTrafficTreatment(org.onosproject.net.flow.DefaultTrafficTreatment) TrafficTreatment(org.onosproject.net.flow.TrafficTreatment) FlowRuleOperationsContext(org.onosproject.net.flow.FlowRuleOperationsContext)

Example 24 with FlowRuleOperations

use of org.onosproject.net.flow.FlowRuleOperations in project onos by opennetworkinglab.

the class FlowRuleIntentInstaller method reallocate.

private void reallocate(IntentOperationContext<FlowRuleIntent> context) {
    Optional<IntentData> toUninstall = context.toUninstall();
    Optional<IntentData> toInstall = context.toInstall();
    // TODO: Update the Intent store with this information
    toInstall.get().setState(REALLOCATING);
    store.write(toInstall.get());
    List<FlowRuleIntent> uninstallIntents = Lists.newArrayList(context.intentsToUninstall());
    List<FlowRuleIntent> installIntents = Lists.newArrayList(context.intentsToInstall());
    FlowRuleOperations.Builder firstStageOperationsBuilder = FlowRuleOperations.builder();
    List<FlowRule> secondStageFlowRules = Lists.newArrayList();
    FlowRuleOperations.Builder thirdStageOperationsBuilder = FlowRuleOperations.builder();
    FlowRuleOperations.Builder finalStageOperationsBuilder = FlowRuleOperations.builder();
    prepareReallocation(uninstallIntents, installIntents, firstStageOperationsBuilder, secondStageFlowRules, thirdStageOperationsBuilder, finalStageOperationsBuilder);
    trackIntentResources(toUninstall.get(), uninstallIntents, REMOVE);
    trackIntentResources(toInstall.get(), installIntents, ADD);
    CountDownLatch stageCompleteLatch = new CountDownLatch(1);
    FlowRuleOperations firstStageOperations = firstStageOperationsBuilder.build(new StageOperation(context, stageCompleteLatch));
    flowRuleService.apply(firstStageOperations);
    try {
        stageCompleteLatch.await(nonDisruptiveInstallationWaitingTime, TimeUnit.SECONDS);
        if (isReallocationStageFailed) {
            log.error("Reallocation FAILED in stage one: the following FlowRuleOperations are not executed {}", firstStageOperations);
            return;
        } else {
            log.debug("Reallocation stage one completed");
        }
    } catch (Exception e) {
        log.warn("Latch exception in the reallocation stage one");
    }
    for (FlowRule flowRule : secondStageFlowRules) {
        stageCompleteLatch = new CountDownLatch(1);
        FlowRuleOperations operations = FlowRuleOperations.builder().newStage().remove(flowRule).build(new StageOperation(context, stageCompleteLatch));
        nonDisruptiveIntentInstaller.schedule(new NonDisruptiveInstallation(operations), nonDisruptiveInstallationWaitingTime, TimeUnit.SECONDS);
        try {
            stageCompleteLatch.await(nonDisruptiveInstallationWaitingTime, TimeUnit.SECONDS);
            if (isReallocationStageFailed) {
                log.error("Reallocation FAILED in stage two: " + "the following FlowRuleOperations are not executed {}", operations);
                return;
            } else {
                log.debug("Reallocation stage two completed");
            }
        } catch (Exception e) {
            log.warn("Latch exception in the reallocation stage two");
        }
    }
    stageCompleteLatch = new CountDownLatch(1);
    FlowRuleOperations thirdStageOperations = thirdStageOperationsBuilder.build(new StageOperation(context, stageCompleteLatch));
    nonDisruptiveIntentInstaller.schedule(new NonDisruptiveInstallation(thirdStageOperations), nonDisruptiveInstallationWaitingTime, TimeUnit.SECONDS);
    try {
        stageCompleteLatch.await(nonDisruptiveInstallationWaitingTime, TimeUnit.SECONDS);
        if (isReallocationStageFailed) {
            log.error("Reallocation FAILED in stage three: " + "the following FlowRuleOperations are not executed {}", thirdStageOperations);
            return;
        } else {
            log.debug("Reallocation stage three completed");
        }
    } catch (Exception e) {
        log.warn("Latch exception in the reallocation stage three");
    }
    FlowRuleOperationsContext flowRuleOperationsContext = new FlowRuleOperationsContext() {

        @Override
        public void onSuccess(FlowRuleOperations ops) {
            intentInstallCoordinator.intentInstallSuccess(context);
            log.info("Non-disruptive reallocation completed for intent {}", toInstall.get().key());
        }

        @Override
        public void onError(FlowRuleOperations ops) {
            intentInstallCoordinator.intentInstallFailed(context);
        }
    };
    FlowRuleOperations finalStageOperations = finalStageOperationsBuilder.build(flowRuleOperationsContext);
    flowRuleService.apply(finalStageOperations);
}
Also used : FlowRuleOperations(org.onosproject.net.flow.FlowRuleOperations) IntentData(org.onosproject.net.intent.IntentData) CountDownLatch(java.util.concurrent.CountDownLatch) DefaultFlowRule(org.onosproject.net.flow.DefaultFlowRule) FlowRule(org.onosproject.net.flow.FlowRule) FlowRuleOperationsContext(org.onosproject.net.flow.FlowRuleOperationsContext) FlowRuleIntent(org.onosproject.net.intent.FlowRuleIntent)

Example 25 with FlowRuleOperations

use of org.onosproject.net.flow.FlowRuleOperations in project onos by opennetworkinglab.

the class FlowRuleIntentInstaller method apply.

@Override
public void apply(IntentOperationContext<FlowRuleIntent> context) {
    Optional<IntentData> toUninstall = context.toUninstall();
    Optional<IntentData> toInstall = context.toInstall();
    if (toInstall.isPresent() && toUninstall.isPresent()) {
        Intent intentToInstall = toInstall.get().intent();
        if (requireNonDisruptive(intentToInstall) && INSTALLED.equals(toUninstall.get().state())) {
            reallocate(context);
            return;
        }
    }
    if (!toInstall.isPresent() && !toUninstall.isPresent()) {
        // Nothing to do.
        intentInstallCoordinator.intentInstallSuccess(context);
        return;
    }
    List<FlowRuleIntent> uninstallIntents = context.intentsToUninstall();
    List<FlowRuleIntent> installIntents = context.intentsToInstall();
    List<FlowRule> flowRulesToUninstall;
    List<FlowRule> flowRulesToInstall;
    if (toUninstall.isPresent()) {
        // Remove tracked resource from both Intent and installable Intents.
        trackIntentResources(toUninstall.get(), uninstallIntents, REMOVE);
        // Retrieves all flow rules from all flow rule Intents.
        flowRulesToUninstall = uninstallIntents.stream().map(FlowRuleIntent::flowRules).flatMap(Collection::stream).filter(flowRule -> flowRuleService.getFlowEntry(flowRule) != null).collect(Collectors.toList());
    } else {
        // No flow rules to be uninstalled.
        flowRulesToUninstall = Collections.emptyList();
    }
    if (toInstall.isPresent()) {
        // Track resource from both Intent and installable Intents.
        trackIntentResources(toInstall.get(), installIntents, ADD);
        // Retrieves all flow rules from all flow rule Intents.
        flowRulesToInstall = installIntents.stream().map(FlowRuleIntent::flowRules).flatMap(Collection::stream).collect(Collectors.toList());
    } else {
        // No flow rules to be installed.
        flowRulesToInstall = Collections.emptyList();
    }
    List<FlowRule> flowRuleToModify;
    List<FlowRule> dontTouch;
    // If both uninstall/install list contained equal (=match conditions are equal) FlowRules,
    // omit it from remove list, since it will/should be overwritten by install
    flowRuleToModify = flowRulesToInstall.stream().filter(flowRule -> flowRulesToUninstall.stream().anyMatch(flowRule::equals)).collect(Collectors.toList());
    // If both contained exactMatch-ing FlowRules, remove from both list,
    // since it will result in no-op.
    dontTouch = flowRulesToInstall.stream().filter(flowRule -> flowRulesToUninstall.stream().anyMatch(flowRule::exactMatch)).collect(Collectors.toList());
    flowRulesToUninstall.removeAll(flowRuleToModify);
    flowRulesToUninstall.removeAll(dontTouch);
    flowRulesToInstall.removeAll(flowRuleToModify);
    flowRulesToInstall.removeAll(dontTouch);
    flowRuleToModify.removeAll(dontTouch);
    if (flowRulesToInstall.isEmpty() && flowRulesToUninstall.isEmpty() && flowRuleToModify.isEmpty()) {
        // There is no flow rules to install/uninstall
        intentInstallCoordinator.intentInstallSuccess(context);
        return;
    }
    FlowRuleOperations.Builder builder = FlowRuleOperations.builder();
    // Add flows
    flowRulesToInstall.forEach(builder::add);
    // Modify flows
    flowRuleToModify.forEach(builder::modify);
    // Remove flows
    flowRulesToUninstall.forEach(builder::remove);
    FlowRuleOperationsContext flowRuleOperationsContext = new FlowRuleOperationsContext() {

        @Override
        public void onSuccess(FlowRuleOperations ops) {
            intentInstallCoordinator.intentInstallSuccess(context);
        }

        @Override
        public void onError(FlowRuleOperations ops) {
            intentInstallCoordinator.intentInstallFailed(context);
        }
    };
    FlowRuleOperations operations = builder.build(flowRuleOperationsContext);
    log.debug("applying intent {} -> {} with {} rules: {}", toUninstall.map(x -> x.key().toString()).orElse("<empty>"), toInstall.map(x -> x.key().toString()).orElse("<empty>"), operations.stages().stream().mapToLong(Set::size).sum(), operations.stages());
    flowRuleService.apply(operations);
}
Also used : FlowRuleOperations(org.onosproject.net.flow.FlowRuleOperations) Set(java.util.Set) IntentData(org.onosproject.net.intent.IntentData) FlowRuleIntent(org.onosproject.net.intent.FlowRuleIntent) Intent(org.onosproject.net.intent.Intent) Collection(java.util.Collection) DefaultFlowRule(org.onosproject.net.flow.DefaultFlowRule) FlowRule(org.onosproject.net.flow.FlowRule) FlowRuleOperationsContext(org.onosproject.net.flow.FlowRuleOperationsContext) FlowRuleIntent(org.onosproject.net.intent.FlowRuleIntent)

Aggregations

FlowRuleOperations (org.onosproject.net.flow.FlowRuleOperations)35 FlowRule (org.onosproject.net.flow.FlowRule)30 DefaultFlowRule (org.onosproject.net.flow.DefaultFlowRule)27 FlowRuleOperationsContext (org.onosproject.net.flow.FlowRuleOperationsContext)22 DefaultTrafficTreatment (org.onosproject.net.flow.DefaultTrafficTreatment)13 TrafficTreatment (org.onosproject.net.flow.TrafficTreatment)13 DefaultTrafficSelector (org.onosproject.net.flow.DefaultTrafficSelector)11 TrafficSelector (org.onosproject.net.flow.TrafficSelector)11 Criterion (org.onosproject.net.flow.criteria.Criterion)11 Test (org.junit.Test)10 EthCriterion (org.onosproject.net.flow.criteria.EthCriterion)10 PortCriterion (org.onosproject.net.flow.criteria.PortCriterion)10 VlanIdCriterion (org.onosproject.net.flow.criteria.VlanIdCriterion)10 IntReportConfig (org.stratumproject.fabric.tna.inbandtelemetry.IntReportConfig)10 TestUtils.getIntReportConfig (org.stratumproject.fabric.tna.utils.TestUtils.getIntReportConfig)10 IPCriterion (org.onosproject.net.flow.criteria.IPCriterion)8 EthTypeCriterion (org.onosproject.net.flow.criteria.EthTypeCriterion)7 DefaultFlowEntry (org.onosproject.net.flow.DefaultFlowEntry)6 FlowEntry (org.onosproject.net.flow.FlowEntry)6 Set (java.util.Set)5