[ONOS-7333] adapted REST API for bitwise match on TCP/UDP/SCTP source/destination port (flow)

Change-Id: I7f79b22135fbb1663b7757e098ee91f088e243a4
diff --git a/core/common/src/main/java/org/onosproject/codec/impl/CriterionCodec.java b/core/common/src/main/java/org/onosproject/codec/impl/CriterionCodec.java
index 6f34b98..0e23e02 100644
--- a/core/common/src/main/java/org/onosproject/codec/impl/CriterionCodec.java
+++ b/core/common/src/main/java/org/onosproject/codec/impl/CriterionCodec.java
@@ -46,8 +46,11 @@
     protected static final String PROTOCOL = "protocol";
     protected static final String IP = "ip";
     protected static final String TCP_PORT = "tcpPort";
+    protected static final String TCP_MASK = "tcpMask";
     protected static final String UDP_PORT = "udpPort";
+    protected static final String UDP_MASK = "udpMask";
     protected static final String SCTP_PORT = "sctpPort";
+    protected static final String SCTP_MASK = "sctpMask";
     protected static final String ICMP_TYPE = "icmpType";
     protected static final String ICMP_CODE = "icmpCode";
     protected static final String FLOW_LABEL = "flowLabel";
diff --git a/core/common/src/main/java/org/onosproject/codec/impl/DecodeCriterionCodecHelper.java b/core/common/src/main/java/org/onosproject/codec/impl/DecodeCriterionCodecHelper.java
index 5be8392..e8056e2 100644
--- a/core/common/src/main/java/org/onosproject/codec/impl/DecodeCriterionCodecHelper.java
+++ b/core/common/src/main/java/org/onosproject/codec/impl/DecodeCriterionCodecHelper.java
@@ -80,11 +80,17 @@
         decoderMap.put(Criterion.Type.IPV4_SRC.name(), new IpV4SrcDecoder());
         decoderMap.put(Criterion.Type.IPV4_DST.name(), new IpV4DstDecoder());
         decoderMap.put(Criterion.Type.TCP_SRC.name(), new TcpSrcDecoder());
+        decoderMap.put(Criterion.Type.TCP_SRC_MASKED.name(), new TcpSrcMaskDecoder());
         decoderMap.put(Criterion.Type.TCP_DST.name(), new TcpDstDecoder());
+        decoderMap.put(Criterion.Type.TCP_DST_MASKED.name(), new TcpDstMaskDecoder());
         decoderMap.put(Criterion.Type.UDP_SRC.name(), new UdpSrcDecoder());
+        decoderMap.put(Criterion.Type.UDP_SRC_MASKED.name(), new UdpSrcMaskDecoder());
         decoderMap.put(Criterion.Type.UDP_DST.name(), new UdpDstDecoder());
+        decoderMap.put(Criterion.Type.UDP_DST_MASKED.name(), new UdpDstMaskDecoder());
         decoderMap.put(Criterion.Type.SCTP_SRC.name(), new SctpSrcDecoder());
+        decoderMap.put(Criterion.Type.SCTP_SRC_MASKED.name(), new SctpSrcMaskDecoder());
         decoderMap.put(Criterion.Type.SCTP_DST.name(), new SctpDstDecoder());
+        decoderMap.put(Criterion.Type.SCTP_DST_MASKED.name(), new SctpDstMaskDecoder());
         decoderMap.put(Criterion.Type.ICMPV4_TYPE.name(), new IcmpV4TypeDecoder());
         decoderMap.put(Criterion.Type.ICMPV4_CODE.name(), new IcmpV4CodeDecoder());
         decoderMap.put(Criterion.Type.IPV6_SRC.name(), new IpV6SrcDecoder());
@@ -285,6 +291,19 @@
         }
     }
 
+    private class TcpSrcMaskDecoder implements CriterionDecoder {
+        @Override
+        public Criterion decodeCriterion(ObjectNode json) {
+            TpPort tcpPort = TpPort.tpPort(nullIsIllegal(json.get(CriterionCodec.TCP_PORT),
+                    CriterionCodec.TCP_PORT + MISSING_MEMBER_MESSAGE).asInt());
+
+            TpPort tcpMask = TpPort.tpPort(nullIsIllegal(json.get(CriterionCodec.TCP_MASK),
+                    CriterionCodec.TCP_MASK + MISSING_MEMBER_MESSAGE).asInt());
+
+            return Criteria.matchTcpSrcMasked(tcpPort, tcpMask);
+        }
+    }
+
     private class TcpDstDecoder implements CriterionDecoder {
         @Override
         public Criterion decodeCriterion(ObjectNode json) {
@@ -294,6 +313,19 @@
         }
     }
 
+    private class TcpDstMaskDecoder implements CriterionDecoder {
+        @Override
+        public Criterion decodeCriterion(ObjectNode json) {
+            TpPort tcpPort = TpPort.tpPort(nullIsIllegal(json.get(CriterionCodec.TCP_PORT),
+                    CriterionCodec.TCP_PORT + MISSING_MEMBER_MESSAGE).asInt());
+
+            TpPort tcpMask = TpPort.tpPort(nullIsIllegal(json.get(CriterionCodec.TCP_MASK),
+                    CriterionCodec.TCP_MASK + MISSING_MEMBER_MESSAGE).asInt());
+
+            return Criteria.matchTcpDstMasked(tcpPort, tcpMask);
+        }
+    }
+
     private class UdpSrcDecoder implements CriterionDecoder {
         @Override
         public Criterion decodeCriterion(ObjectNode json) {
@@ -303,6 +335,19 @@
         }
     }
 
+    private class UdpSrcMaskDecoder implements CriterionDecoder {
+        @Override
+        public Criterion decodeCriterion(ObjectNode json) {
+            TpPort udpPort = TpPort.tpPort(nullIsIllegal(json.get(CriterionCodec.UDP_PORT),
+                    CriterionCodec.UDP_PORT + MISSING_MEMBER_MESSAGE).asInt());
+
+            TpPort udpMask = TpPort.tpPort(nullIsIllegal(json.get(CriterionCodec.UDP_MASK),
+                    CriterionCodec.UDP_MASK + MISSING_MEMBER_MESSAGE).asInt());
+
+            return Criteria.matchUdpSrcMasked(udpPort, udpMask);
+        }
+    }
+
     private class UdpDstDecoder implements CriterionDecoder {
         @Override
         public Criterion decodeCriterion(ObjectNode json) {
@@ -312,6 +357,19 @@
         }
     }
 
+    private class UdpDstMaskDecoder implements CriterionDecoder {
+        @Override
+        public Criterion decodeCriterion(ObjectNode json) {
+            TpPort udpPort = TpPort.tpPort(nullIsIllegal(json.get(CriterionCodec.UDP_PORT),
+                    CriterionCodec.UDP_PORT + MISSING_MEMBER_MESSAGE).asInt());
+
+            TpPort udpMask = TpPort.tpPort(nullIsIllegal(json.get(CriterionCodec.UDP_MASK),
+                    CriterionCodec.UDP_MASK + MISSING_MEMBER_MESSAGE).asInt());
+
+            return Criteria.matchUdpDstMasked(udpPort, udpMask);
+        }
+    }
+
     private class SctpSrcDecoder implements CriterionDecoder {
         @Override
         public Criterion decodeCriterion(ObjectNode json) {
@@ -321,6 +379,19 @@
         }
     }
 
+    private class SctpSrcMaskDecoder implements CriterionDecoder {
+        @Override
+        public Criterion decodeCriterion(ObjectNode json) {
+            TpPort sctpPort = TpPort.tpPort(nullIsIllegal(json.get(CriterionCodec.SCTP_PORT),
+                    CriterionCodec.SCTP_PORT + MISSING_MEMBER_MESSAGE).asInt());
+
+            TpPort sctpMask = TpPort.tpPort(nullIsIllegal(json.get(CriterionCodec.SCTP_MASK),
+                    CriterionCodec.SCTP_MASK + MISSING_MEMBER_MESSAGE).asInt());
+
+            return Criteria.matchSctpSrcMasked(sctpPort, sctpMask);
+        }
+    }
+
     private class SctpDstDecoder implements CriterionDecoder {
         @Override
         public Criterion decodeCriterion(ObjectNode json) {
@@ -330,6 +401,19 @@
         }
     }
 
+    private class SctpDstMaskDecoder implements CriterionDecoder {
+        @Override
+        public Criterion decodeCriterion(ObjectNode json) {
+            TpPort sctpPort = TpPort.tpPort(nullIsIllegal(json.get(CriterionCodec.SCTP_PORT),
+                    CriterionCodec.SCTP_PORT + MISSING_MEMBER_MESSAGE).asInt());
+
+            TpPort sctpMask = TpPort.tpPort(nullIsIllegal(json.get(CriterionCodec.SCTP_MASK),
+                    CriterionCodec.SCTP_MASK + MISSING_MEMBER_MESSAGE).asInt());
+
+            return Criteria.matchSctpDstMasked(sctpPort, sctpMask);
+        }
+    }
+
     private class IcmpV4TypeDecoder implements CriterionDecoder {
         @Override
         public Criterion decodeCriterion(ObjectNode json) {
diff --git a/core/common/src/main/java/org/onosproject/codec/impl/EncodeCriterionCodecHelper.java b/core/common/src/main/java/org/onosproject/codec/impl/EncodeCriterionCodecHelper.java
index 00798c3..9d8ac65 100644
--- a/core/common/src/main/java/org/onosproject/codec/impl/EncodeCriterionCodecHelper.java
+++ b/core/common/src/main/java/org/onosproject/codec/impl/EncodeCriterionCodecHelper.java
@@ -93,11 +93,17 @@
         formatMap.put(Criterion.Type.IPV4_SRC, new FormatIp());
         formatMap.put(Criterion.Type.IPV4_DST, new FormatIp());
         formatMap.put(Criterion.Type.TCP_SRC, new FormatTcp());
+        formatMap.put(Criterion.Type.TCP_SRC_MASKED, new FormatTcpMask());
         formatMap.put(Criterion.Type.TCP_DST, new FormatTcp());
+        formatMap.put(Criterion.Type.TCP_DST_MASKED, new FormatTcpMask());
         formatMap.put(Criterion.Type.UDP_SRC, new FormatUdp());
+        formatMap.put(Criterion.Type.UDP_SRC_MASKED, new FormatUdpMask());
         formatMap.put(Criterion.Type.UDP_DST, new FormatUdp());
+        formatMap.put(Criterion.Type.UDP_DST_MASKED, new FormatUdpMask());
         formatMap.put(Criterion.Type.SCTP_SRC, new FormatSctp());
+        formatMap.put(Criterion.Type.SCTP_SRC_MASKED, new FormatSctpMask());
         formatMap.put(Criterion.Type.SCTP_DST, new FormatSctp());
+        formatMap.put(Criterion.Type.SCTP_DST_MASKED, new FormatSctpMask());
         formatMap.put(Criterion.Type.ICMPV4_TYPE, new FormatIcmpV4Type());
         formatMap.put(Criterion.Type.ICMPV4_CODE, new FormatIcmpV4Code());
         formatMap.put(Criterion.Type.IPV6_SRC, new FormatIp());
@@ -269,6 +275,19 @@
         }
     }
 
+    private static class FormatTcpMask implements CriterionTypeFormatter {
+        @Override
+        public ObjectNode encodeCriterion(ObjectNode root, Criterion criterion) {
+            final TcpPortCriterion tcpPortCriterion =
+                    (TcpPortCriterion) criterion;
+
+            root.put(CriterionCodec.TCP_PORT, tcpPortCriterion.tcpPort().toInt());
+            root.put(CriterionCodec.TCP_MASK, tcpPortCriterion.mask().toInt());
+
+            return root;
+        }
+    }
+
     private static class FormatUdp implements CriterionTypeFormatter {
         @Override
         public ObjectNode encodeCriterion(ObjectNode root, Criterion criterion) {
@@ -278,6 +297,19 @@
         }
     }
 
+    private static class FormatUdpMask implements CriterionTypeFormatter {
+        @Override
+        public ObjectNode encodeCriterion(ObjectNode root, Criterion criterion) {
+            final UdpPortCriterion udpPortCriterion =
+                    (UdpPortCriterion) criterion;
+
+            root.put(CriterionCodec.UDP_PORT, udpPortCriterion.udpPort().toInt());
+            root.put(CriterionCodec.UDP_MASK, udpPortCriterion.mask().toInt());
+
+            return root;
+        }
+    }
+
     private static class FormatSctp implements CriterionTypeFormatter {
         @Override
         public ObjectNode encodeCriterion(ObjectNode root, Criterion criterion) {
@@ -287,6 +319,19 @@
         }
     }
 
+    private static class FormatSctpMask implements CriterionTypeFormatter {
+        @Override
+        public ObjectNode encodeCriterion(ObjectNode root, Criterion criterion) {
+            final SctpPortCriterion sctpPortCriterion =
+                    (SctpPortCriterion) criterion;
+
+            root.put(CriterionCodec.SCTP_PORT, sctpPortCriterion.sctpPort().toInt());
+            root.put(CriterionCodec.SCTP_MASK, sctpPortCriterion.mask().toInt());
+
+            return root;
+        }
+    }
+
     private static class FormatIcmpV4Type implements CriterionTypeFormatter {
         @Override
         public ObjectNode encodeCriterion(ObjectNode root, Criterion criterion) {