Merge "Fix Dependency Injection IdManager appears to have to have a LockManager"
[genius.git] / mdsalutil / mdsalutil-api / src / main / java / org / opendaylight / genius / mdsalutil / MDSALUtil.java
1 /*
2  * Copyright (c) 2016 Ericsson India Global Services Pvt Ltd. 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.genius.mdsalutil;
10
11 import java.math.BigInteger;
12 import java.util.ArrayList;
13 import java.util.HashMap;
14 import java.util.List;
15 import java.util.Map;
16 import java.util.concurrent.ExecutionException;
17
18 import org.opendaylight.controller.liblldp.HexEncode;
19 import org.opendaylight.controller.md.sal.binding.api.DataBroker;
20 import org.opendaylight.controller.md.sal.binding.api.ReadOnlyTransaction;
21 import org.opendaylight.controller.md.sal.binding.api.WriteTransaction;
22 import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType;
23 import org.opendaylight.controller.md.sal.common.api.data.TransactionCommitFailedException;
24 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev130715.MacAddress;
25 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.PopVlanActionCaseBuilder;
26 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.SetFieldCaseBuilder;
27 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.pop.vlan.action._case.PopVlanActionBuilder;
28 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.set.field._case.SetFieldBuilder;
29 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.list.Action;
30 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.list.ActionBuilder;
31 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.list.ActionKey;
32 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowCapableNodeConnector;
33 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowId;
34 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.Flow;
35 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.FlowBuilder;
36 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.FlowKey;
37 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.FlowCookie;
38 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.flow.Instructions;
39 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.flow.InstructionsBuilder;
40 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.flow.Match;
41 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.flow.MatchBuilder;
42 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.ApplyActionsCase;
43 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.ApplyActionsCaseBuilder;
44 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.GoToTableCaseBuilder;
45 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.WriteActionsCase;
46 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.WriteActionsCaseBuilder;
47 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.WriteMetadataCaseBuilder;
48 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.apply.actions._case.ApplyActions;
49 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.apply.actions._case.ApplyActionsBuilder;
50 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.go.to.table._case.GoToTableBuilder;
51 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.write.actions._case.WriteActions;
52 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.write.actions._case.WriteActionsBuilder;
53 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.write.metadata._case.WriteMetadataBuilder;
54 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.list.Instruction;
55 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.list.InstructionBuilder;
56 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.list.InstructionKey;
57 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.types.rev131018.BucketId;
58 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.types.rev131018.GroupId;
59 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.types.rev131018.GroupTypes;
60 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.types.rev131018.group.Buckets;
61 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.types.rev131018.group.BucketsBuilder;
62 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.types.rev131018.group.buckets.Bucket;
63 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.types.rev131018.group.buckets.BucketBuilder;
64 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.types.rev131018.group.buckets.BucketKey;
65 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.types.rev131018.groups.Group;
66 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.types.rev131018.groups.GroupBuilder;
67 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.types.rev131018.groups.GroupKey;
68 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.NodeConnectorId;
69 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.NodeConnectorRef;
70 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.NodeId;
71 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.NodeRef;
72 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.Nodes;
73 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.node.NodeConnector;
74 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.node.NodeConnectorKey;
75 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.Node;
76 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.NodeKey;
77 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.TunnelBuilder;
78 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowjava.nx.match.rev140421.NxmNxReg6;
79 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.nicira.action.rev140714.dst.choice.grouping.dst.choice.DstNxRegCaseBuilder;
80 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.nicira.action.rev140714.nodes.node.table.flow.instructions.instruction.instruction.apply.actions._case.apply.actions.action.action.NxActionRegLoadNodesNodeTableFlowApplyActionsCaseBuilder;
81 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.nicira.action.rev140714.nx.action.reg.load.grouping.NxRegLoadBuilder;
82 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.nicira.action.rev140714.nx.action.reg.load.grouping.nx.reg.load.Dst;
83 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.nicira.action.rev140714.nx.action.reg.load.grouping.nx.reg.load.DstBuilder;
84 import org.opendaylight.yang.gen.v1.urn.opendaylight.packet.service.rev130709.TransmitPacketInput;
85 import org.opendaylight.yang.gen.v1.urn.opendaylight.packet.service.rev130709.TransmitPacketInputBuilder;
86 import org.opendaylight.yangtools.yang.binding.DataObject;
87 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
88 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier.InstanceIdentifierBuilder;
89 import org.slf4j.Logger;
90 import org.slf4j.LoggerFactory;
91
92 import com.google.common.base.Joiner;
93 import com.google.common.base.Optional;
94 import com.google.common.primitives.Bytes;
95 import com.google.common.primitives.Ints;
96 import com.google.common.util.concurrent.CheckedFuture;
97
98 public class MDSALUtil {
99
100     public enum MdsalOp {  CREATION_OP, UPDATE_OP, REMOVAL_OP };
101
102     public static final String NODE_PREFIX = "openflow";
103     public static final int GROUP_WEIGHT = 0;
104     public static final long WATCH_PORT = 0xffffffffL;
105     public static final long WATCH_GROUP = 0xffffffffL;
106     public static final String SEPARATOR = ":";
107     private static final Buckets EMPTY_Buckets = new BucketsBuilder().build();
108     private static final Instructions EMPTY_Instructions = new InstructionsBuilder().setInstruction(
109             new ArrayList<Instruction>()).build();
110     private static final Match EMPTY_Matches = new MatchBuilder().build();
111     private static final Logger logger = LoggerFactory.getLogger(MDSALUtil.class);
112
113     public static FlowEntity buildFlowEntity(BigInteger dpnId, short tableId, String flowId, int priority, String flowName,
114             int idleTimeOut, int hardTimeOut, BigInteger cookie, List<? extends MatchInfoBase>  listMatchInfoBase,
115             List<InstructionInfo> listInstructionInfo) {
116
117         FlowEntity flowEntity = new FlowEntity(dpnId);
118
119         flowEntity.setTableId(tableId);
120         flowEntity.setFlowId(flowId);
121         flowEntity.setPriority(priority);
122         flowEntity.setFlowName(flowName);
123         flowEntity.setIdleTimeOut(idleTimeOut);
124         flowEntity.setHardTimeOut(hardTimeOut);
125         flowEntity.setCookie(cookie);
126         flowEntity.setMatchInfoList(listMatchInfoBase);
127         flowEntity.setInstructionInfoList(listInstructionInfo);
128
129         return flowEntity;
130     }
131
132     // TODO: CHECK IF THIS IS USED
133     public static Flow buildFlow(short tableId, String flowId, int priority, String flowName, int idleTimeOut,
134             int hardTimeOut, BigInteger cookie, List<? extends MatchInfoBase> listMatchInfoBase, List<InstructionInfo> listInstructionInfo) {
135         return MDSALUtil.buildFlow(tableId, flowId, priority, flowName, idleTimeOut, hardTimeOut, cookie,
136                 listMatchInfoBase, listInstructionInfo, true);
137     }
138
139     public static Flow buildFlow(short tableId, String flowId, int priority, String flowName, int idleTimeOut,
140             int hardTimeOut, BigInteger cookie, List<? extends MatchInfoBase>  listMatchInfoBase,
141             List<InstructionInfo> listInstructionInfo, boolean isStrict) {
142         FlowKey key = new FlowKey(new FlowId(flowId));
143         return new FlowBuilder().setMatch(buildMatches(listMatchInfoBase)).setKey(key)
144                 .setPriority(Integer.valueOf(priority)).setInstructions(buildInstructions(listInstructionInfo))
145                 .setBarrier(false).setInstallHw(true).setHardTimeout(hardTimeOut).setIdleTimeout(idleTimeOut)
146                 .setFlowName(flowName).setTableId(Short.valueOf(tableId)).setStrict(isStrict)
147                 .setCookie(new FlowCookie(cookie)).build();
148     }
149
150     public static Flow buildFlow(short tableId, String flowId) {
151         return new FlowBuilder().setTableId(tableId).setId(new FlowId(flowId)).build();
152     }
153
154     public static Flow buildFlowNew(short tableId, String flowId, int priority, String flowName, int idleTimeOut,
155                                  int hardTimeOut, BigInteger cookie, List<? extends MatchInfoBase>  listMatchInfoBase, List<Instruction> listInstructionInfo) {
156         return MDSALUtil.buildFlowNew(tableId, flowId, priority, flowName, idleTimeOut, hardTimeOut, cookie,
157                 listMatchInfoBase, listInstructionInfo, true);
158     }
159
160     private static Flow buildFlowNew(short tableId, String flowId, int priority, String flowName, int idleTimeOut,
161                                   int hardTimeOut, BigInteger cookie, List<? extends MatchInfoBase>  listMatchInfoBase,
162                                   List<Instruction> listInstructionInfo, boolean isStrict) {
163         FlowKey key = new FlowKey(new FlowId(flowId));
164         return new FlowBuilder().setMatch(buildMatches(listMatchInfoBase)).setKey(key)
165                 .setPriority(Integer.valueOf(priority)).setInstructions(new InstructionsBuilder().setInstruction(listInstructionInfo).build())
166                 .setBarrier(false).setInstallHw(true).setHardTimeout(hardTimeOut).setIdleTimeout(idleTimeOut)
167                 .setFlowName(flowName).setTableId(Short.valueOf(tableId)).setStrict(isStrict)
168                 .setCookie(new FlowCookie(cookie)).build();
169     }
170
171     public static GroupEntity buildGroupEntity(BigInteger dpnId, long groupId, String groupName, GroupTypes groupType,
172             List<BucketInfo> listBucketInfo) {
173
174         GroupEntity groupEntity = new GroupEntity(dpnId);
175
176         groupEntity.setGroupId(groupId);
177         groupEntity.setGroupName(groupName);
178         groupEntity.setGroupType(groupType);
179         groupEntity.setBucketInfoList(listBucketInfo);
180
181         return groupEntity;
182     }
183
184     public static Group buildGroup(long groupId, String groupName, GroupTypes groupType, Buckets buckets) {
185         GroupId groupIdentifier = new GroupId(groupId);
186         return new GroupBuilder().setGroupId(groupIdentifier).setKey(new GroupKey(groupIdentifier)).setGroupName(groupName)
187                 .setGroupType(groupType).setBuckets(buckets).build();
188     }
189
190     public static TransmitPacketInput getPacketOutDefault(List<ActionInfo> actionInfos, byte[] payload, BigInteger dpnId) {
191         return new TransmitPacketInputBuilder()
192                 .setAction(buildActions(actionInfos))
193                 .setPayload(payload)
194                 .setNode(
195                         new NodeRef(InstanceIdentifier.builder(Nodes.class)
196                                 .child(Node.class, new NodeKey(new NodeId("openflow:" + dpnId))).toInstance()))
197                 .setIngress(getDefaultNodeConnRef(dpnId)).setEgress(getDefaultNodeConnRef(dpnId)).build();
198     }
199
200     public static TransmitPacketInput getPacketOutFromController(List<ActionInfo> actionInfos, byte[] payload,
201             long dpnId, NodeConnectorRef egress) {
202         return new TransmitPacketInputBuilder()
203                 .setAction(buildActions(actionInfos))
204                 .setPayload(payload)
205                 .setNode(
206                         new NodeRef(InstanceIdentifier.builder(Nodes.class)
207                                 .child(Node.class, new NodeKey(new NodeId("openflow:" + dpnId))).toInstance()))
208                 .setEgress(egress).build();
209     }
210
211     public static TransmitPacketInput getPacketOut(List<ActionInfo> actionInfos, byte[] payload, long dpnId,
212             NodeConnectorRef ingress) {
213         return new TransmitPacketInputBuilder()
214                 .setAction(buildActions(actionInfos))
215                 .setPayload(payload)
216                 .setNode(
217                         new NodeRef(InstanceIdentifier.builder(Nodes.class)
218                                 .child(Node.class, new NodeKey(new NodeId("openflow:" + dpnId))).toInstance()))
219                 .setIngress(ingress).setEgress(ingress).build();
220     }
221
222     public static Action retrieveSetTunnelIdAction(BigInteger tunnelId, int actionKey) {
223         return new ActionBuilder().setAction(
224                 new SetFieldCaseBuilder().setSetField(new SetFieldBuilder().setTunnel(new TunnelBuilder()
225                 .setTunnelId(tunnelId).build()).build())
226                 .build()).setKey(new ActionKey(actionKey)).build();
227     }
228
229     public static List<Action> buildActions(List<ActionInfo> actions) {
230         List<Action> actionsList = new ArrayList<>();
231         for (ActionInfo actionInfo : actions) {
232             actionsList.add(actionInfo.buildAction());
233         }
234         return actionsList;
235     }
236
237     public static String longToIp(long ip, long mask) {
238         StringBuilder sb = new StringBuilder(15);
239         Joiner joiner = Joiner.on('.');
240
241         joiner.appendTo(sb, Bytes.asList(Ints.toByteArray((int) ip)));
242
243         sb.append("/" + mask);
244
245         return sb.toString();
246     }
247
248
249     public static Bucket buildBucket(List<Action> actionsList, int weight, int bucketId, long watchPort, long watchGroup) {
250         return  new BucketBuilder().setAction(actionsList).setWeight(weight)
251                 .setWatchGroup(watchGroup).setWatchPort(watchPort).setBucketId(new BucketId(Long.valueOf(bucketId))).setKey(new BucketKey(new BucketId(Long.valueOf(bucketId)))).build();
252
253     }
254
255     public static Buckets buildBucketLists(List<Bucket> bucketList) {
256         return new BucketsBuilder().setBucket(bucketList).build();
257     }
258
259     protected static Buckets buildBuckets(List<BucketInfo> listBucketInfo) {
260         long i = 0;
261         if (listBucketInfo != null) {
262             BucketsBuilder bucketsBuilder = new BucketsBuilder();
263             List<Bucket> bucketList = new ArrayList<>();
264
265             for (BucketInfo bucketInfo : listBucketInfo) {
266                 BucketBuilder bucketBuilder = new BucketBuilder();
267                 bucketBuilder.setAction(bucketInfo.buildActions());
268                 bucketBuilder.setWeight(bucketInfo.getWeight());
269                 bucketBuilder.setBucketId(new BucketId(i++));
270                 bucketBuilder.setWeight(bucketInfo.getWeight()).setWatchPort(bucketInfo.getWatchPort())
271                         .setWatchGroup(bucketInfo.getWatchGroup());
272                 bucketList.add(bucketBuilder.build());
273             }
274
275             bucketsBuilder.setBucket(bucketList);
276             return bucketsBuilder.build();
277         }
278
279         return EMPTY_Buckets;
280     }
281
282     public static Instructions buildInstructions(List<InstructionInfo> listInstructionInfo) {
283         if (listInstructionInfo != null) {
284             List<Instruction> instructions = new ArrayList<>();
285             int instructionKey = 0;
286
287             for (InstructionInfo instructionInfo : listInstructionInfo) {
288                 instructions.add(instructionInfo.buildInstruction(instructionKey));
289                 instructionKey++;
290             }
291
292             return new InstructionsBuilder().setInstruction(instructions).build();
293         }
294
295         return EMPTY_Instructions;
296     }
297
298     public static Match buildMatches(List<? extends MatchInfoBase> listMatchInfoBase) {
299         if (listMatchInfoBase != null) {
300             MatchBuilder matchBuilder = new MatchBuilder();
301             Map<Class<?>, Object> mapMatchBuilder = new HashMap<>();
302
303             for (MatchInfoBase MatchInfoBase : listMatchInfoBase) {
304                 MatchInfoBase.createInnerMatchBuilder(mapMatchBuilder);
305             }
306
307             for (MatchInfoBase MatchInfoBase : listMatchInfoBase) {
308                 MatchInfoBase.setMatch(matchBuilder, mapMatchBuilder);
309             }
310
311             return matchBuilder.build();
312         }
313
314         return EMPTY_Matches;
315     }
316
317     // TODO: Check the port const
318     public static NodeConnectorRef getDefaultNodeConnRef(BigInteger nDpId) {
319         return getNodeConnRef(NODE_PREFIX + SEPARATOR + nDpId, "0xfffffffd");
320     }
321
322     public static NodeConnectorRef getNodeConnRef(BigInteger nDpId, String port) {
323         return getNodeConnRef(NODE_PREFIX + SEPARATOR + nDpId, port);
324     }
325
326     public static NodeConnectorRef getNodeConnRef(String sNodeId, String port) {
327         String sNodeConnectorKey;
328         StringBuilder sbTmp;
329         NodeId nodeId;
330         NodeKey nodeKey;
331         NodeConnectorId nodeConnectorId;
332         NodeConnectorKey nodeConnectorKey;
333         InstanceIdentifierBuilder<Nodes> nodesInstanceIdentifierBuilder;
334         InstanceIdentifierBuilder<Node> nodeInstanceIdentifierBuilder;
335         InstanceIdentifierBuilder<NodeConnector> nodeConnectorInstanceIdentifierBuilder;
336         InstanceIdentifier<NodeConnector> nodeConnectorInstanceIdentifier;
337         NodeConnectorRef nodeConnectorRef;
338
339         sbTmp = new StringBuilder();
340
341         sbTmp.append(sNodeId);
342         sbTmp.append(SEPARATOR);
343         sbTmp.append(port);
344
345         sNodeConnectorKey = sbTmp.toString();
346         nodeConnectorId = new NodeConnectorId(sNodeConnectorKey);
347         nodeConnectorKey = new NodeConnectorKey(nodeConnectorId);
348
349         nodeId = new NodeId(sNodeId);
350         nodeKey = new NodeKey(nodeId);
351
352         nodesInstanceIdentifierBuilder = InstanceIdentifier.<Nodes> builder(Nodes.class);
353         nodeInstanceIdentifierBuilder = nodesInstanceIdentifierBuilder.<Node, NodeKey> child(Node.class, nodeKey);
354         nodeConnectorInstanceIdentifierBuilder = nodeInstanceIdentifierBuilder.<NodeConnector, NodeConnectorKey> child(
355                 NodeConnector.class, nodeConnectorKey);
356         nodeConnectorInstanceIdentifier = nodeConnectorInstanceIdentifierBuilder.toInstance();
357         nodeConnectorRef = new NodeConnectorRef(nodeConnectorInstanceIdentifier);
358         return nodeConnectorRef;
359     }
360
361     public static BigInteger getDpnIdFromNodeName(NodeId nodeId) {
362         return getDpnIdFromNodeName(nodeId.getValue());
363     }
364
365     public static BigInteger getDpnIdFromNodeName(String sMdsalNodeName) {
366         String sDpId = sMdsalNodeName.substring(sMdsalNodeName.lastIndexOf(":") + 1);
367         return new BigInteger(sDpId);
368     }
369
370     public static long getOfPortNumberFromPortName(NodeConnectorId nodeConnectorId) {
371         return getOfPortNumberFromPortName(nodeConnectorId.getValue());
372     }
373
374     public static long getDpnIdFromPortName(NodeConnectorId nodeConnectorId) {
375         try {
376             String ofPortName = nodeConnectorId.getValue();
377             return Long.parseLong(ofPortName.substring(ofPortName.indexOf(":")+1,
378                     ofPortName.lastIndexOf(":")));
379         } catch (Exception e) {
380             logger.error("NodeConnectorId not of expected format openflow:dpnid:portnum");
381             return -1;
382         }
383     }
384
385     public static long getOfPortNumberFromPortName(String sMdsalPortName) {
386         String sPortNumber = sMdsalPortName.substring(sMdsalPortName.lastIndexOf(":") + 1);
387         return Long.parseLong(sPortNumber);
388     }
389
390     public static TransmitPacketInput getPacketOut(List<ActionInfo> actionInfos, byte[] payload, BigInteger dpnId,
391                     NodeConnectorRef nodeConnRef) {
392         // TODO Auto-generated method stub
393         return null;
394     }
395
396     public static Instruction buildAndGetPopVlanActionInstruction(int actionKey, int instructionKey) {
397         Action popVlanAction = new ActionBuilder().setAction(
398                 new PopVlanActionCaseBuilder().setPopVlanAction(new PopVlanActionBuilder().build()).build())
399                 .setKey(new ActionKey(actionKey)).build();
400         List<Action> listAction = new ArrayList<> ();
401         listAction.add(popVlanAction);
402         return buildApplyActionsInstruction(listAction, instructionKey);
403     }
404
405     public static Instruction buildAndGetSetReg6ActionInstruction(int actionKey, int instructionKey,
406                                                                   int startOffSet, int endOffSet, long value) {
407         NxRegLoadBuilder nxRegLoadBuilder = new NxRegLoadBuilder();
408         Dst dst =  new DstBuilder()
409                 .setDstChoice(new DstNxRegCaseBuilder().setNxReg(NxmNxReg6.class).build())
410                 .setStart(startOffSet)
411                 .setEnd(endOffSet)
412                 .build();
413         nxRegLoadBuilder.setDst(dst);
414         nxRegLoadBuilder.setValue(new BigInteger(Long.toString(value)));
415         ActionBuilder ab = new ActionBuilder();
416         ab.setAction(new NxActionRegLoadNodesNodeTableFlowApplyActionsCaseBuilder().setNxRegLoad(nxRegLoadBuilder.build()).build());
417         ab.setKey(new ActionKey(actionKey));
418         List<Action> listAction = new ArrayList<> ();
419         listAction.add(ab.build());
420         return buildApplyActionsInstruction(listAction, instructionKey);
421     }
422
423     public static Instruction buildApplyActionsInstruction(List<Action> actions) {
424         return buildApplyActionsInstruction(actions, 0);
425     }
426
427     public static Instruction buildWriteActionsInstruction(List<Action> actions) {
428         WriteActions writeActions = new WriteActionsBuilder().setAction(actions).build();
429         WriteActionsCase writeActionsCase = new WriteActionsCaseBuilder().setWriteActions(writeActions).build();
430         InstructionBuilder instructionBuilder = new InstructionBuilder();
431
432         instructionBuilder.setInstruction(writeActionsCase);
433         instructionBuilder.setKey(new InstructionKey(0));
434         return instructionBuilder.build();
435     }
436
437     public static Instruction buildApplyActionsInstruction(List<Action> listAction, int instructionKey) {
438         ApplyActions applyActions = new ApplyActionsBuilder().setAction(listAction).build();
439         ApplyActionsCase applyActionsCase = new ApplyActionsCaseBuilder().setApplyActions(applyActions).build();
440         InstructionBuilder instructionBuilder = new InstructionBuilder();
441
442         instructionBuilder.setInstruction(applyActionsCase);
443         instructionBuilder.setKey(new InstructionKey(instructionKey));
444         return instructionBuilder.build();
445     }
446
447     public static List<Instruction> buildInstructionsDrop() {
448         return buildInstructionsDrop(0);
449     }
450
451     public static List<Instruction> buildInstructionsDrop(int instructionKey) {
452         List<Instruction> mkInstructions = new ArrayList<>();
453         List <Action> actionsInfos = new ArrayList <> ();
454         actionsInfos.add(new ActionInfo(ActionType.drop_action, new String[]{}).buildAction());
455         mkInstructions.add(getWriteActionsInstruction(actionsInfos, instructionKey));
456         return mkInstructions;
457     }
458
459
460     public static Instruction getWriteActionsInstruction(List<Action> listAction, int instructionKey) {
461         WriteActions writeActions = new WriteActionsBuilder().setAction(listAction).build();
462         WriteActionsCase writeActionsCase = new WriteActionsCaseBuilder().setWriteActions(writeActions).build();
463         InstructionBuilder instructionBuilder = new InstructionBuilder();
464
465         instructionBuilder.setInstruction(writeActionsCase);
466         instructionBuilder.setKey(new InstructionKey(instructionKey));
467         return instructionBuilder.build();
468     }
469
470     public static Action buildAction(int actionKey, int instruction) {
471         return new ActionBuilder().setAction(
472                 new PopVlanActionCaseBuilder().setPopVlanAction(new PopVlanActionBuilder().build()).build())
473                 .setKey(new ActionKey(actionKey)).build();
474     }
475
476     public static Instruction buildAndGetWriteMetadaInstruction(BigInteger metadata,
477                                                                 BigInteger mask, int instructionKey) {
478         return new InstructionBuilder()
479                 .setInstruction(
480                         new WriteMetadataCaseBuilder().setWriteMetadata(
481                                 new WriteMetadataBuilder().setMetadata(metadata).setMetadataMask(mask).build())
482                                 .build()).setKey(new InstructionKey(instructionKey)).build();
483     }
484
485     public static Instruction buildAndGetGotoTableInstruction(short tableId, int instructionKey) {
486         return new InstructionBuilder()
487             .setInstruction(
488                 new GoToTableCaseBuilder().setGoToTable(
489                     new GoToTableBuilder().setTableId(tableId).build()).build())
490             .setKey(new InstructionKey(instructionKey)).build();
491     }
492
493     public static <T extends DataObject> Optional<T> read(LogicalDatastoreType datastoreType,
494                                                           InstanceIdentifier<T> path, DataBroker broker) {
495
496         ReadOnlyTransaction tx = broker.newReadOnlyTransaction();
497
498         Optional<T> result = Optional.absent();
499         try {
500             result = tx.read(datastoreType, path).get();
501         } catch (Exception e) {
502             logger.error("An error occured while reading data from the path {} with the exception {}", path, e);
503         }
504         return result;
505     }
506
507     public static <T extends DataObject> Optional<T> read(DataBroker broker,
508                                                           LogicalDatastoreType datastoreType, InstanceIdentifier<T> path) {
509
510         ReadOnlyTransaction tx = broker.newReadOnlyTransaction();
511
512         Optional<T> result = Optional.absent();
513         try {
514             result = tx.read(datastoreType, path).get();
515         } catch (Exception e) {
516             throw new RuntimeException(e);
517         }
518         return result;
519     }
520
521     public static <T extends DataObject> void syncWrite(DataBroker broker,
522                                                         LogicalDatastoreType datastoreType, InstanceIdentifier<T> path,
523                                                         T data) {
524         WriteTransaction tx = broker.newWriteOnlyTransaction();
525         tx.put(datastoreType, path, data, true);
526         CheckedFuture<Void, TransactionCommitFailedException> futures = tx.submit();
527         try {
528             futures.get();
529         } catch (InterruptedException | ExecutionException e) {
530             logger.error("Error writing to datastore (path, data) : ({}, {})", path, data);
531             throw new RuntimeException(e.getMessage());
532         }
533     }
534
535     public static <T extends DataObject> void syncUpdate(DataBroker broker,
536                                                          LogicalDatastoreType datastoreType, InstanceIdentifier<T> path,
537                                                          T data) {
538         WriteTransaction tx = broker.newWriteOnlyTransaction();
539         tx.merge(datastoreType, path, data, true);
540         CheckedFuture<Void, TransactionCommitFailedException> futures = tx.submit();
541         try {
542             futures.get();
543         } catch (InterruptedException | ExecutionException e) {
544             logger.error("Error writing to datastore (path, data) : ({}, {})", path, data);
545             throw new RuntimeException(e.getMessage());
546         }
547     }
548
549     public static <T extends DataObject> void syncDelete(DataBroker broker,
550                                                          LogicalDatastoreType datastoreType, InstanceIdentifier<T> obj) {
551         WriteTransaction tx = broker.newWriteOnlyTransaction();
552         tx.delete(datastoreType, obj);
553         CheckedFuture<Void, TransactionCommitFailedException> futures = tx.submit();
554         try {
555             futures.get();
556         } catch (InterruptedException | ExecutionException e) {
557             logger.error("Error deleting from datastore (path) : ({})", obj);
558             throw new RuntimeException(e.getMessage());
559         }
560     }
561
562     public static byte[] getMacAddressForNodeConnector(DataBroker broker,
563             InstanceIdentifier<NodeConnector> nodeConnectorId)  {
564         Optional<NodeConnector> optNc = MDSALDataStoreUtils.read(broker,
565                 LogicalDatastoreType.OPERATIONAL, nodeConnectorId);
566         if(optNc.isPresent()) {
567             NodeConnector nc = optNc.get();
568             FlowCapableNodeConnector fcnc = nc.getAugmentation(FlowCapableNodeConnector.class);
569             MacAddress macAddress = fcnc.getHardwareAddress();
570             return HexEncode.bytesFromHexString(macAddress.getValue());
571         }
572         return null;
573     }
574
575     public static NodeId getNodeIdFromNodeConnectorId(NodeConnectorId ncId) {
576         return new NodeId(ncId.getValue().substring(0,
577                 ncId.getValue().lastIndexOf(":")));
578     }
579
580     public static String getInterfaceName(NodeConnectorRef ref, DataBroker dataBroker) {
581         NodeConnectorId nodeConnectorId = getNodeConnectorId(dataBroker, ref);
582         NodeId nodeId = getNodeIdFromNodeConnectorId(nodeConnectorId);
583         InstanceIdentifier<NodeConnector> ncIdentifier = InstanceIdentifier
584                 .builder(Nodes.class)
585                 .child(Node.class, new NodeKey(nodeId))
586                 .child(NodeConnector.class,
587                         new NodeConnectorKey(nodeConnectorId)).build();
588
589         Optional<NodeConnector> nodeConnectorOptional = read(
590                 dataBroker,
591                 LogicalDatastoreType.OPERATIONAL, ncIdentifier);
592         if (!nodeConnectorOptional.isPresent()) {
593             return null;
594         }
595         NodeConnector nc = nodeConnectorOptional.get();
596         FlowCapableNodeConnector fc = nc
597                 .getAugmentation(FlowCapableNodeConnector.class);
598         return fc.getName();
599     }
600
601     public static NodeConnectorId getNodeConnectorId(DataBroker dataBroker,
602             NodeConnectorRef ref) {
603         Optional<NodeConnector> nc = (Optional<NodeConnector>) read(
604                 dataBroker,
605                 LogicalDatastoreType.OPERATIONAL, ref.getValue());
606         if(nc.isPresent()){
607             return nc.get().getId();
608         }
609         return null;
610     }
611
612     public static TransmitPacketInput getPacketOut(List<Action> actions, byte[] payload, BigInteger dpnId) {
613         NodeConnectorRef ncRef = getDefaultNodeConnRef(dpnId);
614         return new TransmitPacketInputBuilder()
615                 .setAction(actions)
616                 .setPayload(payload)
617                 .setNode(
618                         new NodeRef(InstanceIdentifier.builder(Nodes.class)
619                                 .child(Node.class, new NodeKey(new NodeId("openflow:" + dpnId))).toInstance()))
620                 .setIngress(ncRef).setEgress(ncRef).build();
621     }
622
623 }
624