2 * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
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
9 package org.opendaylight.controller.forwardingrulesmanager;
11 import java.io.Serializable;
12 import java.util.Date;
14 import org.opendaylight.controller.sal.core.ContainerFlow;
15 import org.opendaylight.controller.sal.core.Node;
16 import org.opendaylight.controller.sal.flowprogrammer.Flow;
17 import org.opendaylight.controller.sal.match.Match;
18 import org.slf4j.Logger;
19 import org.slf4j.LoggerFactory;
22 * Represents a flow applications request Forwarding Rules Manager to install on
23 * a network node. A FlowEntry is constituted of a flow (match + actions), the
24 * target network node, and the flow name. It also includes a group name. For
25 * instance the flows constituting a policy all share the same group name.
27 public class FlowEntry implements Cloneable, Serializable {
28 protected static final Logger logger = LoggerFactory.getLogger(FlowEntry.class);
29 private static final long serialVersionUID = 1L;
30 private static final Logger log = LoggerFactory.getLogger(FlowEntry.class);
31 private String groupName; // group name
32 private String flowName; // flow name (may be null)
33 private Node node; // network node where to install the flow
34 private Flow flow; // match + action
36 public FlowEntry(String groupName, String flowName, Flow flow, Node node) {
37 this.groupName = groupName;
40 this.flowName = (flowName != null) ? flowName : constructFlowName();
43 public String getGroupName() {
47 public void setGroupName(String name) {
48 this.groupName = name;
52 * Return the actual Flow contained in this entry
56 public Flow getFlow() {
60 public Node getNode() {
64 public void setNode(Node n) {
68 public String getFlowName() {
72 public void setFlowName(String n) {
77 public FlowEntry clone() {
78 FlowEntry cloned = null;
80 cloned = (FlowEntry) super.clone();
81 cloned.flow = this.flow.clone();
82 } catch (CloneNotSupportedException e) {
83 log.warn("exception in clone", e);
89 * Only accounts fields which uniquely identify a flow for collision
90 * purposes: node, match and priority
93 public int hashCode() {
96 result = prime * result + ((node == null) ? 0 : node.hashCode());
97 result = prime * result + ((flow == null) ? 0 : (int) flow.getPriority());
98 result = prime * result + ((flow == null || flow.getMatch() == null) ? 0 : flow.getMatch().hashCode());
104 public boolean equals(Object obj) {
111 if (getClass() != obj.getClass()) {
114 FlowEntry other = (FlowEntry) obj;
117 if (other.node != null) {
120 } else if (!node.equals(other.node)) {
125 return (other.flow == null) ? true : false;
126 } else if (other.flow == null) {
129 if (flow.getPriority() != other.flow.getPriority()) {
132 if (flow.getMatch() == null) {
133 if (other.flow.getMatch() != null) {
136 } else if (!flow.getMatch().equals(other.flow.getMatch())) {
144 public String toString() {
145 return "FlowEntry[flowName = " + flowName + ", groupName = " + groupName + ", node = " + node + ", flow = "
149 private String constructFlowName() {
150 return this.groupName + "_" + new Date().toString();
153 public boolean equalsByNodeAndName(Node node, String flowName) {
154 return this.node.equals(node) && this.flowName.equals(flowName);
158 * Merges the current Flow with the passed Container Flow
160 * Note: Container Flow merging is not an injective function. Be m1 and m2
161 * two different matches, and be f() the flow merge function, such that y1 =
162 * f(m1) and y2 = f(m2) are the two merged matches, we may have: y1 = y2
165 * @param containerFlow
166 * @return this merged FlowEntry
168 public FlowEntry mergeWith(ContainerFlow containerFlow) {
169 Match myMatch = flow.getMatch();
171 // Based on this flow direction, rearrange the match
172 Match match = containerFlow.getMatch();
175 myMatch.mergeWithFilter(match);
177 // Replace this Flow's match with merged version
178 flow.setMatch(myMatch);
184 * Returns whether this entry is the result of an internal generated static
187 * @return true if internal generated static flow, false otherwise
189 public boolean isInternal() {
190 return flowName.startsWith(FlowConfig.INTERNALSTATICFLOWBEGIN)
191 && flowName.endsWith(FlowConfig.INTERNALSTATICFLOWEND);