use of org.batfish.datamodel.IpSpace in project batfish by batfish.
the class IpSpaceSimplifier method visitAclIpSpace.
@Override
public IpSpace visitAclIpSpace(AclIpSpace aclIpSpace) {
/*
* To simplify an AclIpSpace: 1) Simplify the IpSpace of each line. 2) Remove EmptyIpSpace
* lines. 3) Remove all lines after the first UniverseIpSpace line - More generally, we could
* remove all lines whose spaces are covered by a previous line, but this is not implemented.
* It's also probably too expensive to implement a complete IpSpace subset operation, so we'll
* stick to the easy and most important case.
*/
List<AclIpSpaceLine> simplifiedLines = new ArrayList<>();
for (AclIpSpaceLine line : aclIpSpace.getLines()) {
IpSpace simplifiedLineIpSpace = line.getIpSpace().accept(this);
if (simplifiedLineIpSpace == EmptyIpSpace.INSTANCE) {
continue;
}
AclIpSpaceLine simplifiedLine = line.rebuild().setIpSpace(simplifiedLineIpSpace).build();
simplifiedLines.add(simplifiedLine);
if (simplifiedLineIpSpace == UniverseIpSpace.INSTANCE) {
break;
}
}
/*
* If there is only one line, and it accepts, then simplify to the space of that line.
*/
if (simplifiedLines.size() == 1 && simplifiedLines.get(0).getAction() == LineAction.ACCEPT) {
return simplifiedLines.get(0).getIpSpace();
}
/*
* If all lines reject (or there are no lines), simplify to EmptyIpSpace.
*/
if (simplifiedLines.stream().allMatch(line -> line.getAction() == LineAction.REJECT)) {
return EmptyIpSpace.INSTANCE;
}
/*
* If all lines are accepts, and the last accepts UniverseIpSpace, then this can be simplified
* to UniverseIpSpace.
*/
if (simplifiedLines.get(simplifiedLines.size() - 1).getIpSpace() == UniverseIpSpace.INSTANCE && simplifiedLines.stream().allMatch(line -> line.getAction() == LineAction.ACCEPT)) {
return UniverseIpSpace.INSTANCE;
}
return AclIpSpace.builder().setLines(simplifiedLines).build();
}
use of org.batfish.datamodel.IpSpace in project batfish by batfish.
the class SynthesizerInputImplTest method testComputeNeighborUnreachable.
@Test
public void testComputeNeighborUnreachable() {
Configuration node = _cb.build();
Vrf vrf = _vb.setOwner(node).build();
Interface iface1 = _ib.setOwner(node).setVrf(vrf).build();
Interface iface2 = _ib.build();
IpSpace ipSpace1 = Ip.ZERO;
IpSpace ipSpace2 = Ip.MAX;
IpSpaceMatchExpr m1 = new IpSpaceMatchExpr(ipSpace1, false, true);
IpSpaceMatchExpr m2 = new IpSpaceMatchExpr(ipSpace2, false, true);
SynthesizerInput inputWithoutDataPlane = _inputBuilder.setConfigurations(ImmutableMap.of(node.getName(), node)).build();
SynthesizerInput inputWithDataPlane = _inputBuilder.setForwardingAnalysis(MockForwardingAnalysis.builder().setNeighborUnreachable(ImmutableMap.of(node.getName(), ImmutableMap.of(vrf.getName(), ImmutableMap.of(iface1.getName(), ipSpace1, iface2.getName(), ipSpace2)))).build()).setTopology(new Topology(ImmutableSortedSet.of())).build();
assertThat(inputWithoutDataPlane, hasNeighborUnreachable(nullValue()));
assertThat(inputWithDataPlane, hasNeighborUnreachable(equalTo(ImmutableMap.of(node.getHostname(), ImmutableMap.of(vrf.getName(), ImmutableMap.of(iface1.getName(), m1, iface2.getName(), m2))))));
}
use of org.batfish.datamodel.IpSpace in project batfish by batfish.
the class SynthesizerInputImplTest method testComputeArpTrueEdge.
@Test
public void testComputeArpTrueEdge() {
Configuration srcNode = _cb.build();
Vrf srcVrf = _vb.setOwner(srcNode).build();
Interface srcInterface = _ib.setOwner(srcNode).setVrf(srcVrf).build();
String nextHop1 = "nextHop1";
String nextHopInterface1 = "nextHopInterface1";
String nextHop2 = "nextHop2";
String nextHopInterface2 = "nextHopInterface2";
IpSpace ipSpace1 = Ip.ZERO;
IpSpace ipSpace2 = Ip.MAX;
IpSpaceMatchExpr m1 = new IpSpaceMatchExpr(ipSpace1, false, true);
IpSpaceMatchExpr m2 = new IpSpaceMatchExpr(ipSpace2, false, true);
Edge edge1 = new Edge(srcNode.getHostname(), srcInterface.getName(), nextHop1, nextHopInterface1);
Edge edge2 = new Edge(srcNode.getHostname(), srcInterface.getName(), nextHop2, nextHopInterface2);
SynthesizerInput inputWithoutDataPlane = _inputBuilder.setConfigurations(ImmutableMap.of(srcNode.getName(), srcNode)).build();
SynthesizerInput inputWithDataPlane = _inputBuilder.setForwardingAnalysis(MockForwardingAnalysis.builder().setArpTrueEdge(ImmutableMap.of(edge1, ipSpace1, edge2, ipSpace2)).build()).setTopology(new Topology(ImmutableSortedSet.of(edge1, edge2))).build();
assertThat(inputWithoutDataPlane, hasArpTrueEdge(nullValue()));
assertThat(inputWithDataPlane, hasArpTrueEdge(equalTo(ImmutableMap.of(srcNode.getHostname(), ImmutableMap.of(srcVrf.getName(), ImmutableMap.of(srcInterface.getName(), ImmutableMap.of(nextHop1, ImmutableMap.of(nextHopInterface1, m1), nextHop2, ImmutableMap.of(nextHopInterface2, m2))))))));
}
use of org.batfish.datamodel.IpSpace in project batfish by batfish.
the class SynthesizerInputImpl method computeArpTrueEdge.
private Map<String, Map<String, Map<String, Map<String, Map<String, BooleanExpr>>>>> computeArpTrueEdge(Map<Edge, IpSpace> arpTrueEdge) {
Map<String, Map<String, Map<String, Map<String, Map<String, BooleanExpr>>>>> output = new HashMap<>();
arpTrueEdge.forEach((edge, ipSpace) -> {
ipSpace = _ipSpaceSpecializer.specialize(ipSpace);
if (ipSpace instanceof EmptyIpSpace) {
return;
}
String hostname = edge.getNode1();
String outInterface = edge.getInt1();
String vrf = _configurations.get(hostname).getInterfaces().get(outInterface).getVrfName();
String recvNode = edge.getNode2();
String recvInterface = edge.getInt2();
output.computeIfAbsent(hostname, n -> new HashMap<>()).computeIfAbsent(vrf, n -> new HashMap<>()).computeIfAbsent(outInterface, n -> new HashMap<>()).computeIfAbsent(recvNode, n -> new HashMap<>()).put(recvInterface, new IpSpaceMatchExpr(ipSpace, false, true));
});
// freeze
return toImmutableMap(output, Entry::getKey, /* node */
outputByHostnameEntry -> toImmutableMap(outputByHostnameEntry.getValue(), Entry::getKey, /* vrf */
outputByVrfEntry -> toImmutableMap(outputByVrfEntry.getValue(), Entry::getKey, /* outInterface */
outputByOutInterfaceEntry -> toImmutableMap(outputByOutInterfaceEntry.getValue(), Entry::getKey, /* recvNode */
outputByRecvNodeEntry -> toImmutableMap(outputByRecvNodeEntry.getValue(), Entry::getKey, /* recvInterface */
Entry::getValue)))));
}
use of org.batfish.datamodel.IpSpace in project batfish by batfish.
the class IpAccessListSpecializer method specialize.
public Optional<IpAccessListLine> specialize(IpAccessListLine ipAccessListLine) {
IpWildcardSetIpSpace.Builder srcIpSpaceBuilder = IpWildcardSetIpSpace.builder().excluding(ipAccessListLine.getNotSrcIps());
if (ipAccessListLine.getSrcIps().isEmpty() && ipAccessListLine.getSrcOrDstIps().isEmpty()) {
srcIpSpaceBuilder.including(IpWildcard.ANY);
} else {
srcIpSpaceBuilder.including(ipAccessListLine.getSrcIps());
srcIpSpaceBuilder.including(ipAccessListLine.getSrcOrDstIps());
}
IpSpace specializedSrcIpSpace = _srcIpSpaceSpecializer.specialize(srcIpSpaceBuilder.build());
IpWildcardSetIpSpace.Builder dstIpSpaceBuilder = IpWildcardSetIpSpace.builder().excluding(ipAccessListLine.getNotDstIps());
if (ipAccessListLine.getDstIps().isEmpty() && ipAccessListLine.getSrcOrDstIps().isEmpty()) {
dstIpSpaceBuilder.including(IpWildcard.ANY);
} else {
dstIpSpaceBuilder.including(ipAccessListLine.getDstIps());
dstIpSpaceBuilder.including(ipAccessListLine.getSrcOrDstIps());
}
IpSpace specializedDstIpSpace = _dstIpSpaceSpecializer.specialize(dstIpSpaceBuilder.build());
if (specializedDstIpSpace instanceof EmptyIpSpace || specializedSrcIpSpace instanceof EmptyIpSpace) {
return Optional.empty();
}
Set<IpWildcard> specializedDstIps;
Set<IpWildcard> specializedNotDstIps;
if (specializedDstIpSpace instanceof UniverseIpSpace) {
// for a HeaderSpace, empty dstIps means Universe
specializedDstIps = ImmutableSet.of();
specializedNotDstIps = ImmutableSet.of();
} else if (specializedDstIpSpace instanceof IpWildcardSetIpSpace) {
IpWildcardSetIpSpace dstIpWildcardSetIpSpace = (IpWildcardSetIpSpace) specializedDstIpSpace;
specializedDstIps = dstIpWildcardSetIpSpace.getWhitelist();
specializedNotDstIps = dstIpWildcardSetIpSpace.getBlacklist();
} else if (specializedDstIpSpace instanceof IpWildcard) {
specializedDstIps = ImmutableSet.of((IpWildcard) specializedDstIpSpace);
specializedNotDstIps = ImmutableSet.of();
} else {
throw new BatfishException("unexpected specializedDstIpSpace type");
}
Set<IpWildcard> specializedSrcIps;
Set<IpWildcard> specializedNotSrcIps;
if (specializedSrcIpSpace instanceof UniverseIpSpace) {
specializedSrcIps = ImmutableSet.of();
specializedNotSrcIps = ImmutableSet.of();
} else if (specializedSrcIpSpace instanceof IpWildcardSetIpSpace) {
IpWildcardSetIpSpace srcIpWildcardSetIpSpace = (IpWildcardSetIpSpace) specializedSrcIpSpace;
specializedSrcIps = srcIpWildcardSetIpSpace.getWhitelist();
specializedNotSrcIps = srcIpWildcardSetIpSpace.getBlacklist();
} else if (specializedSrcIpSpace instanceof IpWildcard) {
specializedSrcIps = ImmutableSet.of((IpWildcard) specializedSrcIpSpace);
specializedNotSrcIps = ImmutableSet.of();
} else {
throw new BatfishException("unexpected specializedSrcIpSpace type");
}
return Optional.of(ipAccessListLine.rebuild().setDstIps(specializedDstIps).setNotDstIps(specializedNotDstIps).setSrcIps(specializedSrcIps).setNotSrcIps(specializedNotSrcIps).build());
}
Aggregations