#include "openflow/openflow.h"
#include "openvswitch/types.h"
-#define NICIRA_OUI_STR "002320"
-
/* The following vendor extensions, proposed by Nicira Networks, are not yet
* standardized, so they are not included in openflow.h. Some of them may be
* suitable for standardization; others we never expect to standardize. */
/* NXT_TUN_ID_FROM_COOKIE request. */
struct nxt_tun_id_cookie {
struct ofp_header header;
- uint32_t vendor; /* NX_VENDOR_ID. */
- uint32_t subtype; /* NXT_TUN_ID_FROM_COOKIE */
+ ovs_be32 vendor; /* NX_VENDOR_ID. */
+ ovs_be32 subtype; /* NXT_TUN_ID_FROM_COOKIE */
uint8_t set; /* Nonzero to enable, zero to disable. */
uint8_t pad[7];
};
* OpenFlow features. In particular attempts to modify the flow table
* will be rejected with an OFPBRC_EPERM error.
*
- * Slave controllers also do not receive asynchronous messages
- * (OFPT_PACKET_IN, OFPT_FLOW_REMOVED, OFPT_PORT_STATUS).
+ * Slave controllers do not receive OFPT_PACKET_IN or OFPT_FLOW_REMOVED
+ * messages, but they do receive OFPT_PORT_STATUS messages.
*/
struct nx_role_request {
struct nicira_header nxh;
- uint32_t role; /* One of NX_ROLE_*. */
+ ovs_be32 role; /* One of NX_ROLE_*. */
};
enum nx_role {
NXAST_POP_QUEUE, /* struct nx_action_pop_queue */
NXAST_REG_MOVE, /* struct nx_action_reg_move */
NXAST_REG_LOAD, /* struct nx_action_reg_load */
+ NXAST_NOTE, /* struct nx_action_note */
+ NXAST_SET_TUNNEL64, /* struct nx_action_set_tunnel64 */
};
/* Header for Nicira-defined actions. */
struct nx_action_header {
- uint16_t type; /* OFPAT_VENDOR. */
- uint16_t len; /* Length is 16. */
- uint32_t vendor; /* NX_VENDOR_ID. */
- uint16_t subtype; /* NXAST_*. */
+ ovs_be16 type; /* OFPAT_VENDOR. */
+ ovs_be16 len; /* Length is 16. */
+ ovs_be32 vendor; /* NX_VENDOR_ID. */
+ ovs_be16 subtype; /* NXAST_*. */
uint8_t pad[6];
};
OFP_ASSERT(sizeof(struct nx_action_header) == 16);
* ignored. (Open vSwitch 1.0.1 and earlier did not support recursion.)
*/
struct nx_action_resubmit {
- uint16_t type; /* OFPAT_VENDOR. */
- uint16_t len; /* Length is 16. */
- uint32_t vendor; /* NX_VENDOR_ID. */
- uint16_t subtype; /* NXAST_RESUBMIT. */
- uint16_t in_port; /* New in_port for checking flow table. */
+ ovs_be16 type; /* OFPAT_VENDOR. */
+ ovs_be16 len; /* Length is 16. */
+ ovs_be32 vendor; /* NX_VENDOR_ID. */
+ ovs_be16 subtype; /* NXAST_RESUBMIT. */
+ ovs_be16 in_port; /* New in_port for checking flow table. */
uint8_t pad[4];
};
OFP_ASSERT(sizeof(struct nx_action_resubmit) == 16);
/* Action structure for NXAST_SET_TUNNEL.
*
- * Sets the encapsulating tunnel ID. */
+ * Sets the encapsulating tunnel ID to a 32-bit value. The most-significant 32
+ * bits of the tunnel ID are set to 0. */
struct nx_action_set_tunnel {
- uint16_t type; /* OFPAT_VENDOR. */
- uint16_t len; /* Length is 16. */
- uint32_t vendor; /* NX_VENDOR_ID. */
- uint16_t subtype; /* NXAST_SET_TUNNEL. */
+ ovs_be16 type; /* OFPAT_VENDOR. */
+ ovs_be16 len; /* Length is 16. */
+ ovs_be32 vendor; /* NX_VENDOR_ID. */
+ ovs_be16 subtype; /* NXAST_SET_TUNNEL. */
uint8_t pad[2];
- uint32_t tun_id; /* Tunnel ID. */
+ ovs_be32 tun_id; /* Tunnel ID. */
};
OFP_ASSERT(sizeof(struct nx_action_set_tunnel) == 16);
+/* Action structure for NXAST_SET_TUNNEL64.
+ *
+ * Sets the encapsulating tunnel ID to a 64-bit value. */
+struct nx_action_set_tunnel64 {
+ ovs_be16 type; /* OFPAT_VENDOR. */
+ ovs_be16 len; /* Length is 16. */
+ ovs_be32 vendor; /* NX_VENDOR_ID. */
+ ovs_be16 subtype; /* NXAST_SET_TUNNEL64. */
+ uint8_t pad[6];
+ ovs_be64 tun_id; /* Tunnel ID. */
+};
+OFP_ASSERT(sizeof(struct nx_action_set_tunnel64) == 24);
+
/* Action structure for NXAST_DROP_SPOOFED_ARP.
*
* Stops processing further actions, if the packet being processed is an
* Ethernet addresses inside ARP packets, so there is no other way to drop
* spoofed ARPs other than sending every ARP packet to a controller. */
struct nx_action_drop_spoofed_arp {
- uint16_t type; /* OFPAT_VENDOR. */
- uint16_t len; /* Length is 16. */
- uint32_t vendor; /* NX_VENDOR_ID. */
- uint16_t subtype; /* NXAST_DROP_SPOOFED_ARP. */
+ ovs_be16 type; /* OFPAT_VENDOR. */
+ ovs_be16 len; /* Length is 16. */
+ ovs_be32 vendor; /* NX_VENDOR_ID. */
+ ovs_be16 subtype; /* NXAST_DROP_SPOOFED_ARP. */
uint8_t pad[6];
};
OFP_ASSERT(sizeof(struct nx_action_drop_spoofed_arp) == 16);
* an argument. This allows the queue to be defined before the port is
* known. */
struct nx_action_set_queue {
- uint16_t type; /* OFPAT_VENDOR. */
- uint16_t len; /* Length is 16. */
- uint32_t vendor; /* NX_VENDOR_ID. */
- uint16_t subtype; /* NXAST_SET_QUEUE. */
+ ovs_be16 type; /* OFPAT_VENDOR. */
+ ovs_be16 len; /* Length is 16. */
+ ovs_be32 vendor; /* NX_VENDOR_ID. */
+ ovs_be16 subtype; /* NXAST_SET_QUEUE. */
uint8_t pad[2];
- uint32_t queue_id; /* Where to enqueue packets. */
+ ovs_be32 queue_id; /* Where to enqueue packets. */
};
OFP_ASSERT(sizeof(struct nx_action_set_queue) == 16);
* were used. Only the original queue can be restored this way; no stack is
* maintained. */
struct nx_action_pop_queue {
- uint16_t type; /* OFPAT_VENDOR. */
- uint16_t len; /* Length is 16. */
- uint32_t vendor; /* NX_VENDOR_ID. */
- uint16_t subtype; /* NXAST_POP_QUEUE. */
+ ovs_be16 type; /* OFPAT_VENDOR. */
+ ovs_be16 len; /* Length is 16. */
+ ovs_be32 vendor; /* NX_VENDOR_ID. */
+ ovs_be16 subtype; /* NXAST_POP_QUEUE. */
uint8_t pad[6];
};
OFP_ASSERT(sizeof(struct nx_action_pop_queue) == 16);
* bit 'c'). Bit numbering starts at 0 for the least-significant bit, 1 for
* the next most significant bit, and so on.
*
- * 'src' and 'dst' are nxm_header values with nxm_hasmask=0. The following
- * nxm_header values are potentially acceptable as 'src':
+ * 'src' and 'dst' are nxm_header values with nxm_hasmask=0. (It doesn't make
+ * sense to use nxm_hasmask=1 because the action does not do any kind of
+ * matching; it uses the actual value of a field.)
+ *
+ * The following nxm_header values are potentially acceptable as 'src':
*
* - NXM_OF_IN_PORT
* - NXM_OF_ETH_DST
* starts at 0 for the least-significant bit, 1 for the next most significant
* bit, and so on.
*
- * 'dst' must be one of the following:
+ * 'dst' is an nxm_header with nxm_hasmask=0. It must be one of the following:
*
* - NXM_NX_REG(idx) for idx in the switch's accepted range.
*
};
OFP_ASSERT(sizeof(struct nx_action_reg_load) == 24);
+/* Action structure for NXAST_NOTE.
+ *
+ * This action has no effect. It is variable length. The switch does not
+ * attempt to interpret the user-defined 'note' data in any way. A controller
+ * can use this action to attach arbitrary metadata to a flow.
+ *
+ * This action might go away in the future.
+ */
+struct nx_action_note {
+ ovs_be16 type; /* OFPAT_VENDOR. */
+ ovs_be16 len; /* A multiple of 8, but at least 16. */
+ ovs_be32 vendor; /* NX_VENDOR_ID. */
+ ovs_be16 subtype; /* NXAST_NOTE. */
+ uint8_t note[6]; /* Start of user-defined data. */
+ /* Possibly followed by additional user-defined data. */
+};
+OFP_ASSERT(sizeof(struct nx_action_note) == 16);
+
/* Wildcard for tunnel ID. */
#define NXFW_TUN_ID (1 << 25)
*
* Format: 48-bit Ethernet MAC address.
*
- * Masking: Not maskable. */
+ * Masking: The nxm_mask patterns 01:00:00:00:00:00 and FE:FF:FF:FF:FF:FF must
+ * be supported for NXM_OF_ETH_DST_W (as well as the trivial patterns that
+ * are all-0-bits or all-1-bits). Support for other patterns and for masking
+ * of NXM_OF_ETH_SRC is optional. */
#define NXM_OF_ETH_DST NXM_HEADER (0x0000, 1, 6)
+#define NXM_OF_ETH_DST_W NXM_HEADER_W(0x0000, 1, 6)
#define NXM_OF_ETH_SRC NXM_HEADER (0x0000, 2, 6)
/* Packet's Ethernet type.
* - Testing with a specific PCP and CFI=1, with nxm_mask=0xf000, matches
* packets that have an 802.1Q header with that PCP (and any VID).
*
- * - Testing with nxm_value=0, nxm_mask=0xe000 matches packets with no 802.1Q
+ * - Testing with nxm_value=0, nxm_mask=0x0fff matches packets with no 802.1Q
* header or with an 802.1Q header with a VID of 0.
+ *
+ * - Testing with nxm_value=0, nxm_mask=0xe000 matches packets with no 802.1Q
+ * header or with an 802.1Q header with a PCP of 0.
+ *
+ * - Testing with nxm_value=0, nxm_mask=0xefff matches packets with no 802.1Q
+ * header or with an 802.1Q header with both VID and PCP of 0.
*/
#define NXM_OF_VLAN_TCI NXM_HEADER (0x0000, 4, 2)
#define NXM_OF_VLAN_TCI_W NXM_HEADER_W(0x0000, 4, 2)
#define NXM_NX_REG(IDX) NXM_HEADER (0x0001, IDX, 4)
#define NXM_NX_REG_W(IDX) NXM_HEADER_W(0x0001, IDX, 4)
#define NXM_NX_REG_IDX(HEADER) NXM_FIELD(HEADER)
-#define NXM_IS_NX_REG(HEADER) (!((((HEADER) ^ NXM_NX_REG(0))) & 0xffffe0ff))
+#define NXM_IS_NX_REG(HEADER) (!((((HEADER) ^ NXM_NX_REG0)) & 0xffffe1ff))
+#define NXM_IS_NX_REG_W(HEADER) (!((((HEADER) ^ NXM_NX_REG0_W)) & 0xffffe1ff))
#define NXM_NX_REG0 NXM_HEADER (0x0001, 0, 4)
#define NXM_NX_REG0_W NXM_HEADER_W(0x0001, 0, 4)
#define NXM_NX_REG1 NXM_HEADER (0x0001, 1, 4)
/* ## Requests and replies. ## */
/* ## --------------------- ## */
-enum {
+enum nx_flow_format {
NXFF_OPENFLOW10 = 0, /* Standard OpenFlow 1.0 compatible. */
NXFF_TUN_ID_FROM_COOKIE = 1, /* OpenFlow 1.0, plus obtain tunnel ID from
* cookie. */