Fix fileEncoding violations for checkstyle
[groupbasedpolicy.git] / renderers / ofoverlay / src / test / java / org / opendaylight / groupbasedpolicy / renderer / ofoverlay / flow / ChainActionFlowsTest.java
1 /*
2  * Copyright (c) 2015 Cisco Systems, Inc. and others. All rights reserved.
3  *
4  * This program and the accompanying materials are made available under the
5  * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6  * and is available at http://www.eclipse.org/legal/epl-v10.html
7  */
8
9 package org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow;
10
11 import com.google.common.base.Preconditions;
12 import org.junit.Before;
13 import org.junit.Test;
14 import org.mockito.ArgumentCaptor;
15 import org.mockito.Captor;
16 import org.opendaylight.groupbasedpolicy.dto.EgKey;
17 import org.opendaylight.groupbasedpolicy.dto.PolicyInfo;
18 import org.opendaylight.groupbasedpolicy.renderer.ofoverlay.OfContext;
19 import org.opendaylight.groupbasedpolicy.renderer.ofoverlay.OfWriter;
20 import org.opendaylight.groupbasedpolicy.renderer.ofoverlay.PolicyManager;
21 import org.opendaylight.groupbasedpolicy.renderer.ofoverlay.endpoint.EndpointManager;
22 import org.opendaylight.groupbasedpolicy.renderer.ofoverlay.mapper.MapperUtilsTest;
23 import org.opendaylight.groupbasedpolicy.renderer.ofoverlay.mapper.policyenforcer.NetworkElements;
24 import org.opendaylight.groupbasedpolicy.renderer.ofoverlay.node.SwitchManager;
25 import org.opendaylight.groupbasedpolicy.renderer.ofoverlay.sfcutils.SfcNshHeader;
26 import org.opendaylight.groupbasedpolicy.renderer.ofoverlay.sfcutils.SfcNshHeader.SfcNshHeaderBuilder;
27 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.IpAddress;
28 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.Ipv4Prefix;
29 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.Action;
30 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowId;
31 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.Flow;
32 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.FlowBuilder;
33 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.flow.Match;
34 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.flow.MatchBuilder;
35 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.common.rev140421.TenantId;
36 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.endpoint.rev140421.endpoint.fields.L3Address;
37 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.endpoint.rev140421.endpoints.Endpoint;
38 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.endpoint.rev140421.endpoints.EndpointBuilder;
39 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.policy.rev140421.HasDirection;
40 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.policy.rev140421.tenants.Tenant;
41 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.policy.rev140421.tenants.TenantBuilder;
42 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.NodeId;
43 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.Layer3Match;
44 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.layer._3.match.Ipv4MatchBuilder;
45 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowjava.nx.match.rev140421.NxmNxReg0;
46 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowjava.nx.match.rev140421.NxmNxReg1;
47 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowjava.nx.match.rev140421.NxmNxReg4;
48 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowjava.nx.match.rev140421.NxmNxReg5;
49 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowjava.nx.match.rev140421.NxmNxReg6;
50 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowjava.nx.match.rev140421.NxmNxReg7;
51 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.overlay.rev150105.TunnelTypeVxlanGpe;
52
53 import java.math.BigInteger;
54 import java.util.ArrayList;
55 import java.util.List;
56
57 import static org.junit.Assert.assertArrayEquals;
58 import static org.junit.Assert.assertEquals;
59 import static org.junit.Assert.assertNotNull;
60 import static org.junit.Assert.assertTrue;
61 import static org.mockito.Mockito.any;
62 import static org.mockito.Mockito.mock;
63 import static org.mockito.Mockito.times;
64 import static org.mockito.Mockito.verify;
65 import static org.mockito.Mockito.when;
66 import static org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow.FlowUtils.RegMatch;
67 import static org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow.FlowUtils.addNxNsiMatch;
68 import static org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow.FlowUtils.addNxNspMatch;
69 import static org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow.FlowUtils.addNxRegMatch;
70 import static org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow.FlowUtils.addNxTunIdMatch;
71 import static org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow.FlowUtils.applyActionIns;
72 import static org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow.FlowUtils.base;
73 import static org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow.FlowUtils.gotoTableIns;
74 import static org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow.FlowUtils.instructions;
75 import static org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow.FlowUtils.nxLoadNshc1RegAction;
76 import static org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow.FlowUtils.nxLoadNshc2RegAction;
77 import static org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow.FlowUtils.nxLoadRegAction;
78 import static org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow.FlowUtils.nxLoadTunGpeNpAction;
79 import static org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow.FlowUtils.nxLoadTunIPv4Action;
80 import static org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow.FlowUtils.nxLoadTunIdAction;
81 import static org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow.FlowUtils.nxOutputRegAction;
82 import static org.opendaylight.groupbasedpolicy.renderer.ofoverlay.flow.FlowUtils.nxPopNshAction;
83
84 public class ChainActionFlowsTest extends MapperUtilsTest {
85
86     @Captor
87     private final ArgumentCaptor<NodeId> nodeIdCaptor = ArgumentCaptor.forClass(NodeId.class);
88     private final ArgumentCaptor<Short> tableIdCaptor = ArgumentCaptor.forClass(Short.class);
89     private final ArgumentCaptor<Flow> flowCaptor = ArgumentCaptor.forClass(Flow.class);
90
91     @Before
92     public void init() {
93         ctx = mock(OfContext.class);
94         endpointManager = mock(EndpointManager.class);
95         switchManager = mock(SwitchManager.class);
96         policyManager = mock(PolicyManager.class);
97         policyInfo = mock(PolicyInfo.class);
98         ofWriter = mock(OfWriter.class);
99     }
100
101     @Test
102     public void createChainTunnelFlows_directionIn() throws Exception {
103         // Tenant
104         TenantBuilder tenantBuilder = buildTenant();
105         Tenant tenant = tenantBuilder.build();
106         // Source Endpoint
107         EndpointBuilder sourceEndpointBuilder = buildEndpoint(IPV4_0, MAC_0, CONNECTOR_0);
108         Endpoint sourceEndpoint = sourceEndpointBuilder.build();
109         EgKey sourceEgKey = new EgKey(tenant.getId(), ENDPOINT_GROUP_0);
110         // Destination Endpoint
111         EndpointBuilder destinationEndpointBuilder = buildEndpoint(IPV4_1, MAC_1, CONNECTOR_1);
112         Endpoint destinationEndpoint = destinationEndpointBuilder.build();
113         EgKey destinationEgKey = new EgKey(tenant.getId(), ENDPOINT_GROUP_1);
114         // Nsh header
115         SfcNshHeaderBuilder nshHeaderBuilder = new SfcNshHeaderBuilder();
116         nshHeaderBuilder.setNshMetaC1(Long.valueOf(0L));
117         nshHeaderBuilder.setNshNsiFromChain((short) 250);
118         nshHeaderBuilder.setNshNspFromChain(27L);
119         SfcNshHeader nshHeader = nshHeaderBuilder.build();
120
121         when(ctx.getTenant(any(TenantId.class))).thenReturn(getTestIndexedTenant());
122         when(ctx.getEndpointManager()).thenReturn(endpointManager);
123         when(ctx.getSwitchManager()).thenReturn(switchManager);
124         when(ctx.getPolicyManager()).thenReturn(policyManager);
125         when(ctx.getCurrentPolicy()).thenReturn(policyInfo);
126         when(switchManager.getTunnelPort(NODE_ID, TunnelTypeVxlanGpe.class)).thenReturn(CONNECTOR_2);
127         when(switchManager.getTunnelIP(NODE_ID, TunnelTypeVxlanGpe.class)).thenReturn(new IpAddress(IPV4_2));
128         when(policyManager.getTABLEID_PORTSECURITY()).thenReturn((short) 4);
129         when(policyManager.getTABLEID_SOURCE_MAPPER()).thenReturn((short) 2);
130
131         // Net elements
132         NetworkElements netElements = new NetworkElements(sourceEndpoint, destinationEndpoint, sourceEgKey,
133                 destinationEgKey, NODE_ID, ctx);
134         assertNotNull(netElements);
135
136         ChainActionFlows.createChainTunnelFlows(nshHeader, netElements, ofWriter, ctx, HasDirection.Direction.In);
137
138         // Verify flows and capture arguments
139         verify(ofWriter, times(4)).writeFlow(nodeIdCaptor.capture(), tableIdCaptor.capture(), flowCaptor.capture());
140
141         // Verify nodeIds
142         for (NodeId capturedNodeId : nodeIdCaptor.getAllValues()) {
143             assertEquals(capturedNodeId, NODE_ID);
144         }
145
146         // Verify tableIds
147         List<Short> tableIds = tableIdCaptor.getAllValues();
148         Short expectedTableIds[] = {4, 2, 0, 2};
149         assertArrayEquals(expectedTableIds, tableIds.toArray());
150
151         // Verify flows
152         List<Flow> flows = flowCaptor.getAllValues();
153         assertNotNull(flows);
154         assertTrue(flows.size() == 4);
155         assertEquals(flows.get(0), allowFromChainTestFlow());
156         assertEquals(flows.get(1), createChainTunnelTestFlow(netElements).get(0)); // contains only 1 entry
157         assertEquals(flows.get(2), allowFromChainTunnelTestFlow());
158         assertEquals(flows.get(3), createChainBroadcastTestFlow());
159     }
160
161     @Test
162     public void createChainTunnelFlows_directionOut() throws Exception {
163         // Tenant
164         TenantBuilder tenantBuilder = buildTenant();
165         Tenant tenant = tenantBuilder.build();
166         // Source Endpoint
167         EndpointBuilder sourceEndpointBuilder = buildEndpoint(IPV4_0, MAC_0, CONNECTOR_0);
168         Endpoint sourceEndpoint = sourceEndpointBuilder.build();
169         EgKey sourceEgKey = new EgKey(tenant.getId(), ENDPOINT_GROUP_0);
170         // Destination Endpoint
171         EndpointBuilder destinationEndpointBuilder = buildEndpoint(IPV4_1, MAC_1, CONNECTOR_1);
172         Endpoint destinationEndpoint = destinationEndpointBuilder.build();
173         EgKey destinationEgKey = new EgKey(tenant.getId(), ENDPOINT_GROUP_1);
174         // Nsh header
175         SfcNshHeaderBuilder nshHeaderBuilder = new SfcNshHeaderBuilder();
176         nshHeaderBuilder.setNshMetaC1(Long.valueOf(0L));
177         nshHeaderBuilder.setNshNsiToChain((short) 255);
178         nshHeaderBuilder.setNshNspToChain(27L);
179         nshHeaderBuilder.setNshTunIpDst(IPV4_2);
180         SfcNshHeader nshHeader = nshHeaderBuilder.build();
181
182         when(ctx.getTenant(any(TenantId.class))).thenReturn(getTestIndexedTenant());
183         when(ctx.getEndpointManager()).thenReturn(endpointManager);
184         when(ctx.getSwitchManager()).thenReturn(switchManager);
185         when(ctx.getPolicyManager()).thenReturn(policyManager);
186         when(ctx.getCurrentPolicy()).thenReturn(policyInfo);
187         when(switchManager.getTunnelPort(NODE_ID, TunnelTypeVxlanGpe.class)).thenReturn(CONNECTOR_2);
188         when(switchManager.getTunnelIP(NODE_ID, TunnelTypeVxlanGpe.class)).thenReturn(new IpAddress(IPV4_2));
189         when(policyManager.getTABLEID_EXTERNAL_MAPPER()).thenReturn((short) 6);
190
191
192         // Net elements
193         NetworkElements netElements = new NetworkElements(sourceEndpoint, destinationEndpoint, sourceEgKey,
194                 destinationEgKey, NODE_ID, ctx);
195         assertNotNull(netElements);
196
197         ChainActionFlows.createChainTunnelFlows(nshHeader, netElements, ofWriter, ctx, HasDirection.Direction.Out);
198
199         // Verify flows and capture arguments
200         verify(ofWriter, times(1)).writeFlow(NODE_ID, (short) 6, createExternalTestFlow(netElements));
201     }
202
203     private Flow allowFromChainTestFlow() {
204         MatchBuilder matchBuilder = new MatchBuilder();
205         FlowUtils.addNxNshc1RegMatch(matchBuilder, 0L);
206         FlowUtils.addNxNsiMatch(matchBuilder, (short) 250);
207         FlowUtils.addNxNspMatch(matchBuilder, 27L);
208         Match match = matchBuilder.setInPort(CONNECTOR_2).build();
209
210         FlowId flowId = FlowIdUtils.newFlowId((short) 4, "chainport", match);
211         FlowBuilder flowBuilder = new FlowBuilder().setTableId((short) 4).setBarrier(false).setHardTimeout(0)
212                 .setIdleTimeout(0).setId(flowId).setPriority(1200).setMatch(match)
213                 .setInstructions(FlowUtils.gotoTableInstructions((short) 2));
214         return flowBuilder.build();
215     }
216
217     private List<Flow> createChainTunnelTestFlow(NetworkElements networkElements) {
218         Preconditions.checkNotNull(networkElements);
219         List<Flow> flows = new ArrayList<>();
220         Action segReg = nxLoadRegAction(NxmNxReg0.class, BigInteger.valueOf(1L));
221         Action scgReg = nxLoadRegAction(NxmNxReg1.class, BigInteger.valueOf(0xffffff));
222         Action bdReg = nxLoadRegAction(NxmNxReg4.class, BigInteger.valueOf(3L));
223         Action fdReg = nxLoadRegAction(NxmNxReg5.class, BigInteger.valueOf(4L));
224         Action vrfReg = nxLoadRegAction(NxmNxReg6.class, BigInteger.valueOf(5L));
225         for (L3Address address : networkElements.getDstEp().getL3Address()) {
226             Layer3Match l3Match = new Ipv4MatchBuilder().setIpv4Source(new Ipv4Prefix(address.getIpAddress()
227                     .getIpv4Address().getValue() + IP_PREFIX_32)).build();
228             MatchBuilder mb = new MatchBuilder().setInPort(CONNECTOR_2).setLayer3Match(l3Match)
229                     .setEthernetMatch(FlowUtils.ethernetMatch(null, null, FlowUtils.IPv4));
230             addNxTunIdMatch(mb, networkElements.getSrcEpOrdinals().getTunnelId());
231             addNxNspMatch(mb, 27L);
232             addNxNsiMatch(mb, (short) 250);
233             Match match = mb.build();
234             FlowId flowId = FlowIdUtils.newFlowId((short) 2, "chaintunnel", match);
235             FlowBuilder flowBuilder = base((short) 2).setId(flowId).setPriority(150).setMatch(match).setInstructions(
236                     instructions(applyActionIns(segReg, scgReg, bdReg, fdReg, vrfReg),
237                             gotoTableIns(ctx.getPolicyManager().getTABLEID_DESTINATION_MAPPER())));
238             flows.add(flowBuilder.build());
239         }
240         assertTrue(flows.size() == 1);
241         return flows;
242     }
243
244     private Flow allowFromChainTunnelTestFlow() {
245         MatchBuilder matchBuilder = new MatchBuilder().setInPort(CONNECTOR_2);
246         addNxRegMatch(matchBuilder, RegMatch.of(NxmNxReg1.class, 0xffffffL));
247         Match match = matchBuilder.build();
248         FlowId flowId = FlowIdUtils.newFlowId((short) 0, "chainport", match);
249         FlowBuilder flowBuilder = base((short) 0).setId(flowId).setMatch(match)
250                 .setPriority(65000).setInstructions(instructions(applyActionIns(nxPopNshAction(), nxOutputRegAction(NxmNxReg7.class))));
251         return flowBuilder.build();
252     }
253
254     private Flow createChainBroadcastTestFlow() {
255         MatchBuilder matchBuilder = new MatchBuilder().setInPort(CONNECTOR_2);
256         addNxNsiMatch(matchBuilder, (short) 250);
257         addNxNspMatch(matchBuilder, 27L);
258         addNxTunIdMatch(matchBuilder, 4);
259         Match match = matchBuilder.build();
260         FlowId flowId = FlowIdUtils.newFlowId((short) 2, "chainbroadcast", match);
261         FlowBuilder flowBuilder = base((short) 2).setId(flowId).setPriority(150).setMatch(match)
262                 .setInstructions(instructions(applyActionIns(nxLoadRegAction(NxmNxReg5.class, BigInteger.valueOf(4))),
263                         gotoTableIns(ctx.getPolicyManager().getTABLEID_DESTINATION_MAPPER())));
264         return flowBuilder.build();
265     }
266
267     private Flow createExternalTestFlow(NetworkElements networkElements) {
268         int matchTunnelId = networkElements.getSrcEpOrdinals().getTunnelId();
269         long setTunnelId = networkElements.getDstEpOrdinals().getTunnelId();
270         final short TUN_GPE_NP_NSH = 0x4;
271
272         Action loadC1 = nxLoadNshc1RegAction(Long.valueOf(0));
273         Action loadC2 = nxLoadNshc2RegAction(setTunnelId);
274         Action loadChainTunVnId = nxLoadTunIdAction(BigInteger.valueOf(setTunnelId), false);
275         Action loadChainTunDest = nxLoadTunIPv4Action(IPV4_2.getValue(), false);
276         Action loadTunGpeNp = nxLoadTunGpeNpAction(BigInteger.valueOf(TUN_GPE_NP_NSH), false);
277         Action outputAction = FlowUtils.createActionResubmit(null, (short) 0);
278
279         MatchBuilder matchBuilder = new MatchBuilder();
280         addNxRegMatch(matchBuilder, RegMatch.of(NxmNxReg6.class, 5L));
281         addNxTunIdMatch(matchBuilder, matchTunnelId);
282         addNxNspMatch(matchBuilder, 27L);
283         addNxNsiMatch(matchBuilder, (short) 255);
284
285
286         Match match = matchBuilder.build();
287         FlowId flowId = FlowIdUtils.newFlowId(((short) 6), "chainexternal", match);
288         FlowBuilder flowBuilder = base((short) 6).setId(flowId).setPriority(1000).setMatch(match)
289                 .setInstructions(instructions(applyActionIns(loadC1, loadC2, loadChainTunDest, loadChainTunVnId, loadTunGpeNp,
290                         outputAction)));
291         return flowBuilder.build();
292     }
293 }