Search in sources :

Example 16 with Protocol

use of org.batfish.symbolic.Protocol in project batfish by batfish.

the class EncoderSlice method addChoicePerProtocolConstraints.

/*
   * Constraints that define a choice for a given protocol
   * to be when a particular import is equal to the best choice.
   * For example:
   *
   * choice_bgp_Serial0 = (import_Serial0 = best_bgp)
   */
private void addChoicePerProtocolConstraints() {
    for (Entry<String, Configuration> entry : getGraph().getConfigurations().entrySet()) {
        String router = entry.getKey();
        Configuration conf = entry.getValue();
        for (Protocol proto : getProtocols().get(router)) {
            SymbolicRoute bestVars = _symbolicDecisions.getBestVars(_optimizations, router, proto);
            assert (bestVars != null);
            for (LogicalEdge e : collectAllImportLogicalEdges(router, conf, proto)) {
                SymbolicRoute vars = correctVars(e);
                BoolExpr choice = _symbolicDecisions.getChoiceVariables().get(router, proto, e);
                assert (choice != null);
                BoolExpr isBest = equal(conf, proto, bestVars, vars, e, false);
                add(mkEq(choice, mkAnd(vars.getPermitted(), isBest)));
            }
        }
    }
}
Also used : BoolExpr(com.microsoft.z3.BoolExpr) Configuration(org.batfish.datamodel.Configuration) IpProtocol(org.batfish.datamodel.IpProtocol) RoutingProtocol(org.batfish.datamodel.RoutingProtocol) Protocol(org.batfish.symbolic.Protocol) MatchProtocol(org.batfish.datamodel.routing_policy.expr.MatchProtocol)

Example 17 with Protocol

use of org.batfish.symbolic.Protocol in project batfish by batfish.

the class EncoderSlice method addTransferFunction.

/*
   * Constraints that define relationships between various messages
   * in the network. The same transfer function abstraction is used
   * for both import and export constraints by relating different collections
   * of variables.
   */
private void addTransferFunction() {
    for (Entry<String, Configuration> entry : getGraph().getConfigurations().entrySet()) {
        String router = entry.getKey();
        Configuration conf = entry.getValue();
        for (Protocol proto : getProtocols().get(router)) {
            Boolean usedExport = false;
            boolean hasEdge = false;
            List<ArrayList<LogicalEdge>> les = _logicalGraph.getLogicalEdges().get(router, proto);
            assert (les != null);
            for (ArrayList<LogicalEdge> eList : les) {
                for (LogicalEdge e : eList) {
                    GraphEdge ge = e.getEdge();
                    if (!getGraph().isEdgeUsed(conf, proto, ge)) {
                        continue;
                    }
                    hasEdge = true;
                    SymbolicRoute varsOther;
                    switch(e.getEdgeType()) {
                        case IMPORT:
                            varsOther = _logicalGraph.findOtherVars(e);
                            addImportConstraint(e, varsOther, conf, proto, ge, router);
                            break;
                        case EXPORT:
                            // OSPF export is tricky because it does not depend on being
                            // in the FIB. So it can come from either a redistributed route
                            // or another OSPF route. We always take the direct OSPF
                            SymbolicRoute ospfRedistribVars = null;
                            SymbolicRoute overallBest = null;
                            if (proto.isOspf()) {
                                varsOther = getBestNeighborPerProtocol(router, proto);
                                if (_ospfRedistributed.containsKey(router)) {
                                    ospfRedistribVars = _ospfRedistributed.get(router);
                                    overallBest = _symbolicDecisions.getBestNeighbor().get(router);
                                }
                            } else {
                                varsOther = _symbolicDecisions.getBestNeighbor().get(router);
                            }
                            Set<Prefix> originations = _originatedNetworks.get(router, proto);
                            assert varsOther != null;
                            assert originations != null;
                            addExportConstraint(e, varsOther, ospfRedistribVars, overallBest, conf, proto, ge, router, usedExport, originations);
                            usedExport = true;
                            break;
                        default:
                            break;
                    }
                }
            }
            // If no edge used, then just set the best record to be false for that protocol
            if (!hasEdge) {
                SymbolicRoute protoBest;
                if (_optimizations.getSliceHasSingleProtocol().contains(router)) {
                    protoBest = _symbolicDecisions.getBestNeighbor().get(router);
                } else {
                    protoBest = _symbolicDecisions.getBestNeighborPerProtocol().get(router, proto);
                }
                assert protoBest != null;
                add(mkNot(protoBest.getPermitted()));
            }
        }
    }
}
Also used : Configuration(org.batfish.datamodel.Configuration) ArrayList(java.util.ArrayList) Prefix(org.batfish.datamodel.Prefix) IpProtocol(org.batfish.datamodel.IpProtocol) RoutingProtocol(org.batfish.datamodel.RoutingProtocol) Protocol(org.batfish.symbolic.Protocol) MatchProtocol(org.batfish.datamodel.routing_policy.expr.MatchProtocol) GraphEdge(org.batfish.symbolic.GraphEdge)

Example 18 with Protocol

use of org.batfish.symbolic.Protocol in project batfish by batfish.

the class EncoderSlice method addControlForwardingConstraints.

/*
   * Constraints that define control-plane forwarding.
   * If there is some valid import, then control plane forwarding
   * will occur out an interface when this is the best choice.
   * Otherwise, it will not occur.
   */
private void addControlForwardingConstraints() {
    for (Entry<String, Configuration> entry : getGraph().getConfigurations().entrySet()) {
        String router = entry.getKey();
        Configuration conf = entry.getValue();
        boolean someEdge = false;
        SymbolicRoute best = _symbolicDecisions.getBestNeighbor().get(router);
        Map<GraphEdge, BoolExpr> cfExprs = new HashMap<>();
        Set<GraphEdge> constrained = new HashSet<>();
        for (Protocol proto : getProtocols().get(router)) {
            for (LogicalEdge e : collectAllImportLogicalEdges(router, conf, proto)) {
                someEdge = true;
                constrained.add(e.getEdge());
                SymbolicRoute vars = correctVars(e);
                BoolExpr choice = _symbolicDecisions.getChoiceVariables().get(router, proto, e);
                BoolExpr isBest = mkAnd(choice, equal(conf, proto, best, vars, e, false));
                GraphEdge ge = e.getEdge();
                // Connected routes should only forward if not absorbed by interface
                GraphEdge other = getGraph().getOtherEnd().get(ge);
                BoolExpr connectedWillSend;
                if (other == null || getGraph().isHost(ge.getPeer())) {
                    Ip ip = ge.getStart().getAddress().getIp();
                    BitVecExpr val = getCtx().mkBV(ip.asLong(), 32);
                    connectedWillSend = mkNot(mkEq(_symbolicPacket.getDstIp(), val));
                } else {
                    Ip ip = other.getStart().getAddress().getIp();
                    BitVecExpr val = getCtx().mkBV(ip.asLong(), 32);
                    connectedWillSend = mkEq(_symbolicPacket.getDstIp(), val);
                }
                BoolExpr canSend = (proto.isConnected() ? connectedWillSend : mkTrue());
                BoolExpr sends = mkAnd(canSend, isBest);
                BoolExpr cForward = _symbolicDecisions.getControlForwarding().get(router, ge);
                assert (cForward != null);
                add(mkImplies(sends, cForward));
                // record the negation as well
                cfExprs.merge(ge, sends, (a, b) -> mkOr(a, b));
            }
        }
        // For edges that are never used, we constraint them to not be forwarded out of
        for (GraphEdge ge : getGraph().getEdgeMap().get(router)) {
            if (!constrained.contains(ge)) {
                BoolExpr cForward = _symbolicDecisions.getControlForwarding().get(router, ge);
                assert (cForward != null);
                add(mkNot(cForward));
            }
        }
        // Handle the case that the router has no protocol running
        if (!someEdge) {
            for (GraphEdge ge : getGraph().getEdgeMap().get(router)) {
                BoolExpr cForward = _symbolicDecisions.getControlForwarding().get(router, ge);
                assert (cForward != null);
                add(mkNot(cForward));
            }
        } else {
            // If no best route, then no forwarding
            Map<Protocol, List<ArrayList<LogicalEdge>>> map = _logicalGraph.getLogicalEdges().get(router);
            Set<GraphEdge> seen = new HashSet<>();
            for (List<ArrayList<LogicalEdge>> eList : map.values()) {
                for (ArrayList<LogicalEdge> edges : eList) {
                    for (LogicalEdge le : edges) {
                        GraphEdge ge = le.getEdge();
                        if (seen.contains(ge)) {
                            continue;
                        }
                        seen.add(ge);
                        BoolExpr expr = cfExprs.get(ge);
                        BoolExpr cForward = _symbolicDecisions.getControlForwarding().get(router, ge);
                        assert (cForward != null);
                        if (expr != null) {
                            add(mkImplies(mkNot(expr), mkNot(cForward)));
                        } else {
                            add(mkNot(cForward));
                        }
                    }
                }
            }
        }
    }
}
Also used : BoolExpr(com.microsoft.z3.BoolExpr) Configuration(org.batfish.datamodel.Configuration) HashMap(java.util.HashMap) Ip(org.batfish.datamodel.Ip) ArrayList(java.util.ArrayList) BitVecExpr(com.microsoft.z3.BitVecExpr) IpAccessList(org.batfish.datamodel.IpAccessList) ArrayList(java.util.ArrayList) List(java.util.List) IpProtocol(org.batfish.datamodel.IpProtocol) RoutingProtocol(org.batfish.datamodel.RoutingProtocol) Protocol(org.batfish.symbolic.Protocol) MatchProtocol(org.batfish.datamodel.routing_policy.expr.MatchProtocol) GraphEdge(org.batfish.symbolic.GraphEdge) HashSet(java.util.HashSet)

Example 19 with Protocol

use of org.batfish.symbolic.Protocol in project batfish by batfish.

the class EncoderSlice method initRedistributionProtocols.

/*
   * Initialize the map of redistributed protocols.
   */
private void initRedistributionProtocols() {
    for (Entry<String, Configuration> entry : getGraph().getConfigurations().entrySet()) {
        String router = entry.getKey();
        Configuration conf = entry.getValue();
        for (Protocol proto : getProtocols().get(router)) {
            Set<Protocol> redistributed = new HashSet<>();
            redistributed.add(proto);
            _logicalGraph.getRedistributedProtocols().put(router, proto, redistributed);
            RoutingPolicy pol = Graph.findCommonRoutingPolicy(conf, proto);
            if (pol != null) {
                Set<Protocol> ps = getGraph().findRedistributedProtocols(conf, pol, proto);
                for (Protocol p : ps) {
                    // Make sure there is actually a routing process for the other protocol
                    // For example, it might get sliced away if not relevant
                    boolean isProto = getProtocols().get(router).contains(p);
                    if (isProto) {
                        redistributed.add(p);
                    }
                }
            }
        }
    }
}
Also used : Configuration(org.batfish.datamodel.Configuration) RoutingPolicy(org.batfish.datamodel.routing_policy.RoutingPolicy) IpProtocol(org.batfish.datamodel.IpProtocol) RoutingProtocol(org.batfish.datamodel.RoutingProtocol) Protocol(org.batfish.symbolic.Protocol) MatchProtocol(org.batfish.datamodel.routing_policy.expr.MatchProtocol) HashSet(java.util.HashSet)

Example 20 with Protocol

use of org.batfish.symbolic.Protocol in project batfish by batfish.

the class EncoderSlice method addChoiceVariables.

/*
   * Initialize variables representing if a router chooses
   * to use a particular interface for control-plane forwarding
   */
private void addChoiceVariables() {
    for (String router : getGraph().getRouters()) {
        Configuration conf = getGraph().getConfigurations().get(router);
        Map<Protocol, Map<LogicalEdge, BoolExpr>> map = new HashMap<>();
        _symbolicDecisions.getChoiceVariables().put(router, map);
        for (Protocol proto : getProtocols().get(router)) {
            Map<LogicalEdge, BoolExpr> edgeMap = new HashMap<>();
            map.put(proto, edgeMap);
            for (LogicalEdge e : collectAllImportLogicalEdges(router, conf, proto)) {
                String chName = e.getSymbolicRecord().getName() + "_choice";
                BoolExpr choiceVar = getCtx().mkBoolConst(chName);
                getAllVariables().put(choiceVar.toString(), choiceVar);
                edgeMap.put(e, choiceVar);
            }
        }
    }
}
Also used : BoolExpr(com.microsoft.z3.BoolExpr) Configuration(org.batfish.datamodel.Configuration) HashMap(java.util.HashMap) IpProtocol(org.batfish.datamodel.IpProtocol) RoutingProtocol(org.batfish.datamodel.RoutingProtocol) Protocol(org.batfish.symbolic.Protocol) MatchProtocol(org.batfish.datamodel.routing_policy.expr.MatchProtocol) HashMap(java.util.HashMap) Map(java.util.Map)

Aggregations

Protocol (org.batfish.symbolic.Protocol)27 IpProtocol (org.batfish.datamodel.IpProtocol)16 RoutingProtocol (org.batfish.datamodel.RoutingProtocol)15 Configuration (org.batfish.datamodel.Configuration)14 MatchProtocol (org.batfish.datamodel.routing_policy.expr.MatchProtocol)14 ArrayList (java.util.ArrayList)12 GraphEdge (org.batfish.symbolic.GraphEdge)11 BoolExpr (com.microsoft.z3.BoolExpr)10 Prefix (org.batfish.datamodel.Prefix)10 HashMap (java.util.HashMap)8 HashSet (java.util.HashSet)6 List (java.util.List)6 Map (java.util.Map)5 BatfishException (org.batfish.common.BatfishException)5 RoutingPolicy (org.batfish.datamodel.routing_policy.RoutingPolicy)5 Interface (org.batfish.datamodel.Interface)4 IpAccessList (org.batfish.datamodel.IpAccessList)4 Graph (org.batfish.symbolic.Graph)4 BgpNeighbor (org.batfish.datamodel.BgpNeighbor)3 Ip (org.batfish.datamodel.Ip)3