nat: documentation and parsing fixes.
authorJarno Rajahalme <jarno@ovn.org>
Wed, 18 May 2016 23:28:36 +0000 (16:28 -0700)
committerJarno Rajahalme <jarno@ovn.org>
Wed, 18 May 2016 23:28:36 +0000 (16:28 -0700)
Add the missing NAT documentation to ovs-ofctl man page and add
validation of the NAT flags to NAT action decoding and parsing.

Signed-off-by: Jarno Rajahalme <jarno@ovn.org>
include/openvswitch/ofp-actions.h
lib/ofp-actions.c
utilities/ovs-ofctl.8.in

index 0608ac1..038ef87 100644 (file)
@@ -562,11 +562,12 @@ void ofpacts_execute_action_set(struct ofpbuf *action_list,
 /* Bits for 'flags' in struct nx_action_nat.
  */
 enum nx_nat_flags {
-    NX_NAT_F_SRC          = 1 << 0,
+    NX_NAT_F_SRC          = 1 << 0, /* Mutually exclusive with NX_NAT_F_DST. */
     NX_NAT_F_DST          = 1 << 1,
     NX_NAT_F_PERSISTENT   = 1 << 2,
-    NX_NAT_F_PROTO_HASH   = 1 << 3,
+    NX_NAT_F_PROTO_HASH   = 1 << 3, /* Mutually exclusive with PROTO_RANDOM. */
     NX_NAT_F_PROTO_RANDOM = 1 << 4,
+    NX_NAT_F_MASK = (NX_NAT_F_SRC | NX_NAT_F_DST | NX_NAT_F_PERSISTENT | NX_NAT_F_PROTO_HASH | NX_NAT_F_PROTO_RANDOM)
 };
 
 /* OFPACT_NAT.
index 0c2e31b..b102f74 100644 (file)
@@ -5277,6 +5277,14 @@ decode_NXAST_RAW_NAT(const struct nx_action_nat *nan,
     nat = ofpact_put_NAT(out);
     nat->flags = ntohs(nan->flags);
 
+    /* Check for unknown or mutually exclusive flags. */
+    if ((nat->flags & ~NX_NAT_F_MASK)
+        || (nat->flags & NX_NAT_F_SRC && nat->flags & NX_NAT_F_DST)
+        || (nat->flags & NX_NAT_F_PROTO_HASH
+            && nat->flags & NX_NAT_F_PROTO_RANDOM)) {
+        return OFPERR_OFPBAC_BAD_ARGUMENT;
+    }
+
 #define NX_NAT_GET_OPT(DST, SRC, LEN, TYPE)                     \
     (LEN >= sizeof(TYPE)                                        \
      ? (memcpy(DST, SRC, sizeof(TYPE)), LEN -= sizeof(TYPE),    \
@@ -5515,16 +5523,20 @@ parse_NAT(char *arg, struct ofpbuf *ofpacts,
         }
     }
     if (on->flags & NX_NAT_F_SRC && on->flags & NX_NAT_F_DST) {
-        return xasprintf("May only specify one of \"snat\" or \"dnat\".");
+        return xasprintf("May only specify one of \"src\" or \"dst\".");
     }
     if (!(on->flags & NX_NAT_F_SRC || on->flags & NX_NAT_F_DST)) {
         if (on->flags) {
-            return xasprintf("Flags allowed only with \"snat\" or \"dnat\".");
+            return xasprintf("Flags allowed only with \"src\" or \"dst\".");
         }
         if (on->range_af != AF_UNSPEC) {
-            return xasprintf("Range allowed only with \"snat\" or \"dnat\".");
+            return xasprintf("Range allowed only with \"src\" or \"dst\".");
         }
     }
+    if (on->flags & NX_NAT_F_PROTO_HASH && on->flags & NX_NAT_F_PROTO_RANDOM) {
+        return xasprintf("Both \"hash\" and \"random\" are not allowed.");
+    }
+
     return NULL;
 }
 
index 1b25145..e2e26f7 100644 (file)
@@ -1407,8 +1407,15 @@ modules are not loaded.
 This packet is tracked, meaning that it has previously traversed the connection
 tracker. If this flag is not set, then no other flags will be set. If this flag
 is set, then the packet is tracked and other flags may also be set.
+.IP "\fB0x40: snat\fR"
+This packet was transformed by source address/port translation by a
+preceding \fBct\fR action.
+.IP "\fB0x80: dnat\fR"
+This packet was transformed by destination address/port translation by
+a preceding \fBct\fR action.
 .PP
-This field was introduced in Open vSwitch 2.5.
+This field was introduced in Open vSwitch 2.5.  The \fBsnat\fR and
+\fBdnat\fR bits were added in Open vSwitch 2.6.
 .RE
 .
 .PP
@@ -1776,6 +1783,74 @@ The \fBcommit\fR parameter must be specified to use \fBalg=\fIalg\fR.
 When committing related connections, the \fBct_mark\fR for that connection is
 inherited from the current \fBct_mark\fR stored with the original connection
 (ie, the connection created by \fBct(alg=...)\fR).
+.
+.IP \fBnat\fR[\fB(\fR(\fBsrc\fR|\fBdst\fR)\fB=\fIaddr1\fR[\fB-\fIaddr2\fR][\fB:\fIport1\fR[\fB-\fIport2\fR]][\fB,\fIflags\fR]\fB)\fR]
+.
+Specify address and port translation for the connection being tracked.
+For new connections either \fBsrc\fR or \fBdst\fR argument must be
+provided to set up either source address/port translation (SNAT) or
+destination address/port translation (DNAT), respectively.  Setting up
+address translation for a new connection takes effect only if the
+\fBcommit\fR flag is also provided for the enclosing \fBct\fR action.
+A bare \fBnat\fR action will only translate the packet being processed
+in the way the connection has been set up with an earlier \fBct\fR
+action.  Also a \fBnat\fR action with \fBsrc\fR or \fBdst\fR, when
+applied to a packet belonging to an established (rather than new)
+connection, will behave the same as a bare \fBnat\fR.
+.IP
+\fBsrc\fR and \fBdst\fR options take the following arguments:
+.RS
+.IP \fIaddr1\fR[\fB-\fIaddr2\fR]
+The address range from which the translated address should be
+selected.  If only one address is given, then that address will always
+be selected, otherwise the address selection can be informed by the
+optional \fBpersistent\fR flag as described below.  Either IPv4 or
+IPv6 addresses can be provided, but both addresses must be of the same
+type, and the datapath behavior is undefined in case of providing IPv4
+address range for an IPv6 packet, or IPv6 address range for an IPv4
+packet.  IPv6 addresses must be bracketed with '[' and ']' if a port
+range is also given.
+.RE
+.
+.RS
+.IP \fIport1\fR[\fB-\fIport2\fR]
+The port range from which the translated port should be selected.  If
+only one port number is provided, then that should be selected.  In
+case of a mapping conflict the datapath may choose any other
+non-conflicting port number instead, even when no port range is
+specified.  The port number selection can be informed by the optional
+\fBrandom\fR and \fBhash\fR flags as described below.
+.RE
+.IP
+The optional flags are:
+.RS
+.IP \fBrandom\fR
+The selection of the port from the given range should be done using a
+fresh random number.  This flag is mutually exclusive with \fBhash\fR.
+.RE
+.
+.RS
+.IP \fBhash\fR
+The selection of the port from the given range should be done using a
+datapath specific hash of the packet's IP addresses and the other,
+non-mapped port number.  This flag is mutually exclusive with
+\fBrandom\fR.
+.RE
+.
+.RS
+.IP \fBpersistent\fR
+The selection of the IP address from the given range should be done so
+that the same mapping can be provided after the system restarts.
+.RE
+.IP
+If an \fBalg\fR is specified for the committing \fBct\fR action that
+also includes \fBnat\fR with a \fBsrc\fR or \fBdst\fR attribute,
+then the datapath tries to set up the helper to be NAT aware.  This
+functionality is datapath specific and may not be supported by all
+datapaths.
+.IP
+\fBnat\fR was introduced in Open vSwitch 2.6.  The first datapath that
+implements \fBct nat\fR support is the one that ships with Linux 4.6.
 .RE
 .IP
 The \fBct\fR action may be used as a primitive to construct stateful firewalls