Fixed Node Properties in Adapter - with exceptions noted below 94/3994/4
authorEd Warnicke <eaw@cisco.com>
Wed, 1 Jan 2014 02:10:34 +0000 (18:10 -0800)
committerEd Warnicke <eaw@cisco.com>
Mon, 6 Jan 2014 12:40:55 +0000 (04:40 -0800)
Still need to fix Supported Actions -

Supported Actions present a bit of an issue.  In OF 1.0,
they come in with the GetFeatures message on switch connection.
In OF 1.3, they are per table, and come in with the response to
an empty bodied TableFeatures Multipart request.  So far,
no switch has been observed in the wild supporting the
empty bodied TableFeature message. OVS 2.0 doesn't, CPQD doesn't.

The net-net is that supported Actions are effectively unreportable
for OF 1.3 switches.

Change-Id: I6f4beab167fa1502cacc767eaf95099ba996a343
Signed-off-by: Ed Warnicke <eaw@cisco.com>
opendaylight/md-sal/compatibility/sal-compatibility/src/main/java/org/opendaylight/controller/sal/compatibility/InventoryAndReadAdapter.xtend
opendaylight/md-sal/compatibility/sal-compatibility/src/main/java/org/opendaylight/controller/sal/compatibility/NodeMapping.xtend
opendaylight/md-sal/compatibility/sal-compatibility/src/main/java/org/opendaylight/controller/sal/compatibility/ToSalConversionsUtils.java

index d5fbd041e4a45d593d3d744e2aa6f5e90bc42288..746d32ff1665a1ee638c5396d2b3f07b1ba28fe9 100644 (file)
@@ -349,7 +349,7 @@ class InventoryAndReadAdapter implements IPluginInReadService,
         if ( this._dataService.readOperationalData(identifier) == null ){
             updateType = UpdateType.ADDED;
         }
         if ( this._dataService.readOperationalData(identifier) == null ){
             updateType = UpdateType.ADDED;
         }
-        inventoryPublisher.updateNode(notification.nodeRef.toADNode, updateType, properties);
+        inventoryPublisher.updateNode(notification.nodeRef.toADNode, updateType, notification.toADNodeProperties);
         
                //Notify the listeners of IPluginOutReadService
         
         
                //Notify the listeners of IPluginOutReadService
         
index 6fa54b2b5db140349872cbd0290511b004685ac7..f77cfcd67d52ec419df2ce2021995945ac74799c 100644 (file)
@@ -7,6 +7,7 @@ import org.opendaylight.yangtools.yang.binding.InstanceIdentifier.IdentifiableIt
 
 import static com.google.common.base.Preconditions.*;
 import static extension org.opendaylight.controller.sal.common.util.Arguments.*;
 
 import static com.google.common.base.Preconditions.*;
 import static extension org.opendaylight.controller.sal.common.util.Arguments.*;
+import static extension org.opendaylight.controller.sal.compatibility.ToSalConversionsUtils.*;
 
 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier
 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.NodeConnectorRef
 
 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier
 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.NodeConnectorRef
@@ -27,6 +28,24 @@ import org.opendaylight.controller.sal.core.Name
 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.port.rev130925.PortConfig
 import org.opendaylight.controller.sal.core.Config
 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.port.rev130925.flow.capable.port.State
 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.port.rev130925.PortConfig
 import org.opendaylight.controller.sal.core.Config
 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.port.rev130925.flow.capable.port.State
+import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.NodeUpdated
+import java.util.HashSet
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowCapableNodeUpdated
+import org.opendaylight.controller.sal.core.Tables
+import java.util.List
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FeatureCapability
+import org.opendaylight.controller.sal.core.Buffers
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowFeatureCapabilityFlowStats
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowFeatureCapabilityTableStats
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowFeatureCapabilityIpReasm
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowFeatureCapabilityPortStats
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowFeatureCapabilityStp
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowFeatureCapabilityQueueStats
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowFeatureCapabilityArpMatchIp
+import org.opendaylight.controller.sal.core.Capabilities
+import org.opendaylight.controller.sal.core.MacAddress
+import java.util.Date
+import org.opendaylight.controller.sal.core.TimeStamp
 
 public class NodeMapping {
 
 
 public class NodeMapping {
 
@@ -134,7 +153,7 @@ public class NodeMapping {
     }
     
     public static def toADNodeConnectorProperties(NodeConnectorUpdated nc) {
     }
     
     public static def toADNodeConnectorProperties(NodeConnectorUpdated nc) {
-        val props = new java.util.HashSet<org.opendaylight.controller.sal.core.Property>();
+        val props = new HashSet<org.opendaylight.controller.sal.core.Property>();
         val fcncu = nc.getAugmentation(FlowCapableNodeConnectorUpdated)
         if(fcncu != null) {
             if(fcncu.currentFeature != null && fcncu.currentFeature.toAdBandwidth != null) {
         val fcncu = nc.getAugmentation(FlowCapableNodeConnectorUpdated)
         if(fcncu != null) {
             if(fcncu.currentFeature != null && fcncu.currentFeature.toAdBandwidth != null) {
@@ -235,5 +254,69 @@ public class NodeMapping {
         return pbw
     }
     
         return pbw
     }
     
+    public static def toADNodeProperties(NodeUpdated nu) {
+        val props = new HashSet<org.opendaylight.controller.sal.core.Property>();
+        val fcnu = nu.getAugmentation(FlowCapableNodeUpdated) 
+        if(fcnu != null) {
+             props.add(toADTimestamp)
+             // props.add(fcnu.supportedActions.toADActions) - TODO
+             if(nu.id != null) {
+                props.add(nu.id.toADMacAddress)
+             }
+             if(fcnu.switchFeatures != null) {
+                 if(fcnu.switchFeatures.maxTables != null) {
+                    props.add(fcnu.switchFeatures.maxTables.toADTables) 
+                 }
+                 if(fcnu.switchFeatures.capabilities != null) {
+                    props.add(fcnu.switchFeatures.capabilities.toADCapabiliities)
+                 } 
+                 if(fcnu.switchFeatures.maxBuffers != null) {
+                    props.add(fcnu.switchFeatures.maxBuffers.toADBuffers)
+                 }   
+             }
+        } 
+        return props;   
+        
+    }
+    
+    public static def toADTimestamp() {
+        val date = new Date();
+        val timestamp = new TimeStamp(date.time,"connectedSince")
+        return timestamp;
+    }
+    
+    public static def toADMacAddress(NodeId id) {
+        return new MacAddress(Long.parseLong(id.value.replaceAll("openflow:","")).longValue.bytesFromDpid)
+    }
+    
+    public static def toADTables(Short tables) {
+        return new Tables(tables.byteValue)
+    }
+    
+    public static def toADCapabiliities(List<Class<? extends FeatureCapability>> capabilities) {
+        var int b
+        for(capability : capabilities) {
+            if(capability.equals(FlowFeatureCapabilityFlowStats)) {
+                b = Capabilities.CapabilitiesType.FLOW_STATS_CAPABILITY.value.bitwiseOr(b)
+            } else if (capability.equals(FlowFeatureCapabilityTableStats)) {
+                b = Capabilities.CapabilitiesType.TABLE_STATS_CAPABILITY.value.bitwiseOr(b)
+            } else if (capability.equals(FlowFeatureCapabilityPortStats)) {
+                b = Capabilities.CapabilitiesType.PORT_STATS_CAPABILITY.value.bitwiseOr(b)
+            } else if (capability.equals(FlowFeatureCapabilityStp)) {
+                b = Capabilities.CapabilitiesType.STP_CAPABILITY.value.bitwiseOr(b)
+            } else if (capability.equals(FlowFeatureCapabilityIpReasm)) {
+                b = Capabilities.CapabilitiesType.IP_REASSEM_CAPABILITY.value.bitwiseOr(b)
+            } else if (capability.equals(FlowFeatureCapabilityQueueStats)) {
+                b = Capabilities.CapabilitiesType.QUEUE_STATS_CAPABILITY.value.bitwiseOr(b)
+            } else if (capability.equals(FlowFeatureCapabilityArpMatchIp)) {
+                b = Capabilities.CapabilitiesType.ARP_MATCH_IP_CAPABILITY.value.bitwiseOr(b)
+            }
+        }
+        return new Capabilities(b)
+    }
+    
+    public static def toADBuffers(Long buffers) {
+        return new Buffers(buffers.intValue)
+    }
     
 }
     
 }
index 37bb2778584dc6deb08add85d63eee4ca9489acd..46fd62f3f2790dbd7223b9cba53af42284c57ef1 100644 (file)
@@ -43,6 +43,7 @@ import org.opendaylight.controller.sal.action.SetVlanCfi;
 import org.opendaylight.controller.sal.action.SetVlanId;
 import org.opendaylight.controller.sal.action.SetVlanPcp;
 import org.opendaylight.controller.sal.action.SwPath;
 import org.opendaylight.controller.sal.action.SetVlanId;
 import org.opendaylight.controller.sal.action.SetVlanPcp;
 import org.opendaylight.controller.sal.action.SwPath;
+import org.opendaylight.controller.sal.core.Capabilities;
 import org.opendaylight.controller.sal.core.NodeConnector;
 import org.opendaylight.controller.sal.flowprogrammer.Flow;
 import org.opendaylight.controller.sal.match.Match;
 import org.opendaylight.controller.sal.core.NodeConnector;
 import org.opendaylight.controller.sal.flowprogrammer.Flow;
 import org.opendaylight.controller.sal.match.Match;
@@ -85,6 +86,7 @@ import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.acti
 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.address.Address;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.address.address.Ipv4;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.address.address.Ipv6;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.address.Address;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.address.address.Ipv4;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.address.address.Ipv6;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FeatureCapability;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.ApplyActionsCase;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.list.Instruction;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.l2.types.rev130827.EtherType;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.ApplyActionsCase;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.list.Instruction;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.l2.types.rev130827.EtherType;
@@ -563,7 +565,7 @@ public class ToSalConversionsUtils {
         }
     }
 
         }
     }
 
-    private static byte[] bytesFrom(MacAddress address) {
+    public static byte[] bytesFrom(MacAddress address) {
         String[] mac = address.getValue().split(":");
         byte[] macAddress = new byte[6]; // mac.length == 6 bytes
         for (int i = 0; i < mac.length; i++) {
         String[] mac = address.getValue().split(":");
         byte[] macAddress = new byte[6]; // mac.length == 6 bytes
         for (int i = 0; i < mac.length; i++) {
@@ -571,4 +573,15 @@ public class ToSalConversionsUtils {
         }
         return macAddress;
     }
         }
         return macAddress;
     }
+    
+    public static byte[] bytesFromDpid(long dpid) {
+        byte[] mac = new byte[] { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
+
+        for (short i = 0; i < 6; i++) {
+            mac[5 - i] = (byte) dpid;
+            dpid >>= 8;
+        }
+
+        return mac;
+    }
 }
 }