]> git.proxmox.com Git - ovs.git/blame - lib/ofp-actions.c
ovn-controller: Configure interface QoS only if it would actually be used.
[ovs.git] / lib / ofp-actions.c
CommitLineData
f25d0cf3 1/*
72fe7578 2 * Copyright (c) 2008-2017 Nicira, Inc.
f25d0cf3
BP
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at:
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#include <config.h>
d787ad39
JS
18#include <netinet/in.h>
19
f25d0cf3
BP
20#include "bundle.h"
21#include "byte-order.h"
b1c5bf1f 22#include "colors.h"
f25d0cf3 23#include "compiler.h"
d4abaff5 24#include "dummy.h"
ee89ea7b 25#include "openvswitch/hmap.h"
f25d0cf3 26#include "learn.h"
f25d0cf3
BP
27#include "multipath.h"
28#include "nx-match.h"
9ac0aada 29#include "odp-netlink.h"
b598f214
BW
30#include "openvswitch/dynamic-string.h"
31#include "openvswitch/meta-flow.h"
32#include "openvswitch/ofp-actions.h"
f4248336 33#include "openvswitch/ofp-util.h"
b598f214 34#include "openvswitch/ofp-parse.h"
66bd43fa 35#include "openvswitch/ofp-prop.h"
64c96779 36#include "openvswitch/ofpbuf.h"
b598f214 37#include "openvswitch/vlog.h"
c2d936a4 38#include "unaligned.h"
cb22974d 39#include "util.h"
f25d0cf3
BP
40
41VLOG_DEFINE_THIS_MODULE(ofp_actions);
42
43static struct vlog_rate_limit rl = VLOG_RATE_LIMIT_INIT(1, 5);
f25d0cf3 44
c2d936a4
BP
45struct ofp_action_header;
46
aad28f47
BP
47/* Header for Open vSwitch and ONF vendor extension actions.
48 *
49 * This is the entire header for a few Open vSwitch vendor extension actions,
50 * the ones that either have no arguments or for which variable-length
51 * arguments follow the header.
52 *
53 * This cannot be used as an entirely generic vendor extension action header,
54 * because OpenFlow does not specify the location or size of the action
55 * subtype; it just happens that ONF extensions and Nicira extensions share
56 * this format. */
57struct ext_action_header {
58 ovs_be16 type; /* OFPAT_VENDOR. */
59 ovs_be16 len; /* At least 16. */
60 ovs_be32 vendor; /* NX_VENDOR_ID or ONF_VENDOR_ID. */
61 ovs_be16 subtype; /* See enum ofp_raw_action_type. */
62 uint8_t pad[6];
63};
64OFP_ASSERT(sizeof(struct ext_action_header) == 16);
65
c2d936a4
BP
66/* Raw identifiers for OpenFlow actions.
67 *
68 * Decoding and encoding OpenFlow actions across multiple versions is difficult
69 * to do in a clean, consistent way. This enumeration lays out all of the
70 * forms of actions that Open vSwitch supports.
71 *
72 * The comments here must follow a stylized form because the
73 * "extract-ofp-actions" program parses them at build time to generate data
74 * tables.
75 *
76 * - The first part of each comment specifies the vendor, OpenFlow versions,
77 * and type for each protocol that supports the action:
78 *
79 * # The vendor is OF for standard OpenFlow actions, NX for Nicira
80 * extension actions. (Support for other vendors can be added, but
81 * it can't be done just based on a vendor ID definition alone
82 * because OpenFlow doesn't define a standard way to specify a
83 * subtype for vendor actions, so other vendors might do it different
84 * from Nicira.)
85 *
86 * # The version can specify a specific OpenFlow version, a version
87 * range delimited by "-", or an open-ended range with "+".
88 *
89 * # The type, in parentheses, is the action type number (for standard
90 * OpenFlow actions) or subtype (for vendor extension actions).
91 *
92 * # Optionally one may add "is deprecated" followed by a
93 * human-readable reason in parentheses (which will be used in log
94 * messages), if a particular action should no longer be used.
95 *
96 * Multiple such specifications may be separated by commas.
97 *
98 * - The second part describes the action's wire format. It may be:
99 *
100 * # "struct <name>": The struct fully specifies the wire format. The
101 * action is exactly the size of the struct. (Thus, the struct must
102 * be an exact multiple of 8 bytes in size.)
103 *
104 * # "struct <name>, ...": The struct specifies the beginning of the
105 * wire format. An instance of the action is either the struct's
106 * exact size, or a multiple of 8 bytes longer.
107 *
108 * # "uint<N>_t" or "ovs_be<N>": The action consists of a (standard or
109 * vendor extension) header, followed by 0 or more pad bytes to align
110 * to a multiple of <N> bits, followed by an argument of the given
111 * type, followed by 0 or more pad bytes to bring the total action up
112 * to a multiple of 8 bytes.
113 *
114 * # "void": The action is just a (standard or vendor extension)
115 * header.
116 *
117 * - Optional additional text enclosed in square brackets is commentary for
118 * the human reader.
119 */
120enum ofp_raw_action_type {
121/* ## ----------------- ## */
122/* ## Standard actions. ## */
123/* ## ----------------- ## */
124
125 /* OF1.0(0): struct ofp10_action_output. */
126 OFPAT_RAW10_OUTPUT,
127 /* OF1.1+(0): struct ofp11_action_output. */
128 OFPAT_RAW11_OUTPUT,
129
130 /* OF1.0(1): uint16_t. */
131 OFPAT_RAW10_SET_VLAN_VID,
132 /* OF1.0(2): uint8_t. */
133 OFPAT_RAW10_SET_VLAN_PCP,
134
135 /* OF1.1(1), OF1.2+(1) is deprecated (use Set-Field): uint16_t.
136 *
137 * [Semantics differ slightly between the 1.0 and 1.1 versions of the VLAN
138 * modification actions: the 1.0 versions push a VLAN header if none is
139 * present, but the 1.1 versions do not. That is the only reason that we
140 * distinguish their raw action types.] */
141 OFPAT_RAW11_SET_VLAN_VID,
142 /* OF1.1(2), OF1.2+(2) is deprecated (use Set-Field): uint8_t. */
143 OFPAT_RAW11_SET_VLAN_PCP,
144
145 /* OF1.1+(17): ovs_be16.
146 *
147 * [The argument is the Ethertype, e.g. ETH_TYPE_VLAN_8021Q, not the VID or
148 * TCI.] */
149 OFPAT_RAW11_PUSH_VLAN,
150
151 /* OF1.0(3): void. */
152 OFPAT_RAW10_STRIP_VLAN,
153 /* OF1.1+(18): void. */
154 OFPAT_RAW11_POP_VLAN,
155
156 /* OF1.0(4), OF1.1(3), OF1.2+(3) is deprecated (use Set-Field): struct
157 * ofp_action_dl_addr. */
158 OFPAT_RAW_SET_DL_SRC,
159
160 /* OF1.0(5), OF1.1(4), OF1.2+(4) is deprecated (use Set-Field): struct
161 * ofp_action_dl_addr. */
162 OFPAT_RAW_SET_DL_DST,
163
164 /* OF1.0(6), OF1.1(5), OF1.2+(5) is deprecated (use Set-Field):
165 * ovs_be32. */
166 OFPAT_RAW_SET_NW_SRC,
167
168 /* OF1.0(7), OF1.1(6), OF1.2+(6) is deprecated (use Set-Field):
169 * ovs_be32. */
170 OFPAT_RAW_SET_NW_DST,
171
172 /* OF1.0(8), OF1.1(7), OF1.2+(7) is deprecated (use Set-Field): uint8_t. */
173 OFPAT_RAW_SET_NW_TOS,
174
175 /* OF1.1(8), OF1.2+(8) is deprecated (use Set-Field): uint8_t. */
176 OFPAT_RAW11_SET_NW_ECN,
177
178 /* OF1.0(9), OF1.1(9), OF1.2+(9) is deprecated (use Set-Field):
179 * ovs_be16. */
180 OFPAT_RAW_SET_TP_SRC,
181
182 /* OF1.0(10), OF1.1(10), OF1.2+(10) is deprecated (use Set-Field):
183 * ovs_be16. */
184 OFPAT_RAW_SET_TP_DST,
185
186 /* OF1.0(11): struct ofp10_action_enqueue. */
187 OFPAT_RAW10_ENQUEUE,
188
189 /* NX1.0(30), OF1.1(13), OF1.2+(13) is deprecated (use Set-Field):
190 * ovs_be32. */
191 OFPAT_RAW_SET_MPLS_LABEL,
192
193 /* NX1.0(31), OF1.1(14), OF1.2+(14) is deprecated (use Set-Field):
194 * uint8_t. */
195 OFPAT_RAW_SET_MPLS_TC,
196
197 /* NX1.0(25), OF1.1(15), OF1.2+(15) is deprecated (use Set-Field):
198 * uint8_t. */
199 OFPAT_RAW_SET_MPLS_TTL,
200
201 /* NX1.0(26), OF1.1+(16): void. */
202 OFPAT_RAW_DEC_MPLS_TTL,
203
204 /* NX1.0(23), OF1.1+(19): ovs_be16.
205 *
206 * [The argument is the Ethertype, e.g. ETH_TYPE_MPLS, not the label.] */
207 OFPAT_RAW_PUSH_MPLS,
208
209 /* NX1.0(24), OF1.1+(20): ovs_be16.
210 *
211 * [The argument is the Ethertype, e.g. ETH_TYPE_IPV4 if at BoS or
212 * ETH_TYPE_MPLS otherwise, not the label.] */
213 OFPAT_RAW_POP_MPLS,
214
215 /* NX1.0(4), OF1.1+(21): uint32_t. */
216 OFPAT_RAW_SET_QUEUE,
217
88c8ca26
BP
218 /* NX1.0(40), OF1.1+(22): uint32_t. */
219 OFPAT_RAW_GROUP,
c2d936a4
BP
220
221 /* OF1.1+(23): uint8_t. */
222 OFPAT_RAW11_SET_NW_TTL,
223
224 /* NX1.0(18), OF1.1+(24): void. */
225 OFPAT_RAW_DEC_NW_TTL,
226 /* NX1.0+(21): struct nx_action_cnt_ids, ... */
227 NXAST_RAW_DEC_TTL_CNT_IDS,
228
7eb4b1f1 229 /* OF1.2-1.4(25): struct ofp12_action_set_field, ... */
c2d936a4 230 OFPAT_RAW12_SET_FIELD,
7eb4b1f1
BP
231 /* OF1.5+(25): struct ofp12_action_set_field, ... */
232 OFPAT_RAW15_SET_FIELD,
233 /* NX1.0-1.4(7): struct nx_action_reg_load.
234 *
235 * [In OpenFlow 1.5, set_field is a superset of reg_load functionality, so
236 * we drop reg_load.] */
c2d936a4 237 NXAST_RAW_REG_LOAD,
aad28f47 238 /* NX1.0-1.4(33): struct ext_action_header, ...
bad8a439
BP
239 *
240 * [In OpenFlow 1.5, set_field is a superset of reg_load2 functionality, so
241 * we drop reg_load2.] */
242 NXAST_RAW_REG_LOAD2,
c2d936a4 243
f13cdd73 244 /* OF1.5+(28): struct ofp15_action_copy_field, ... */
73178f20 245 OFPAT_RAW15_COPY_FIELD,
914624f8
BP
246 /* ONF1.3-1.4(3200): struct onf_action_copy_field, ... */
247 ONFACT_RAW13_COPY_FIELD,
bad8a439 248 /* NX1.0-1.4(6): struct nx_action_reg_move, ... */
73178f20
BP
249 NXAST_RAW_REG_MOVE,
250
c2d936a4
BP
251/* ## ------------------------- ## */
252/* ## Nicira extension actions. ## */
253/* ## ------------------------- ## */
254
255/* Actions similar to standard actions are listed with the standard actions. */
256
257 /* NX1.0+(1): uint16_t. */
258 NXAST_RAW_RESUBMIT,
259 /* NX1.0+(14): struct nx_action_resubmit. */
260 NXAST_RAW_RESUBMIT_TABLE,
261
262 /* NX1.0+(2): uint32_t. */
263 NXAST_RAW_SET_TUNNEL,
264 /* NX1.0+(9): uint64_t. */
265 NXAST_RAW_SET_TUNNEL64,
266
267 /* NX1.0+(5): void. */
268 NXAST_RAW_POP_QUEUE,
269
c2d936a4
BP
270 /* NX1.0+(8): struct nx_action_note, ... */
271 NXAST_RAW_NOTE,
272
273 /* NX1.0+(10): struct nx_action_multipath. */
274 NXAST_RAW_MULTIPATH,
275
276 /* NX1.0+(12): struct nx_action_bundle, ... */
277 NXAST_RAW_BUNDLE,
278 /* NX1.0+(13): struct nx_action_bundle, ... */
279 NXAST_RAW_BUNDLE_LOAD,
280
281 /* NX1.0+(15): struct nx_action_output_reg. */
282 NXAST_RAW_OUTPUT_REG,
bad8a439
BP
283 /* NX1.0+(32): struct nx_action_output_reg2. */
284 NXAST_RAW_OUTPUT_REG2,
c2d936a4
BP
285
286 /* NX1.0+(16): struct nx_action_learn, ... */
287 NXAST_RAW_LEARN,
288
289 /* NX1.0+(17): void. */
290 NXAST_RAW_EXIT,
291
292 /* NX1.0+(19): struct nx_action_fin_timeout. */
293 NXAST_RAW_FIN_TIMEOUT,
294
295 /* NX1.0+(20): struct nx_action_controller. */
296 NXAST_RAW_CONTROLLER,
aad28f47 297 /* NX1.0+(37): struct ext_action_header, ... */
bdcad671 298 NXAST_RAW_CONTROLLER2,
c2d936a4
BP
299
300 /* NX1.0+(22): struct nx_action_write_metadata. */
301 NXAST_RAW_WRITE_METADATA,
302
303 /* NX1.0+(27): struct nx_action_stack. */
304 NXAST_RAW_STACK_PUSH,
305
306 /* NX1.0+(28): struct nx_action_stack. */
307 NXAST_RAW_STACK_POP,
308
309 /* NX1.0+(29): struct nx_action_sample. */
310 NXAST_RAW_SAMPLE,
f69f713b
BY
311 /* NX1.0+(38): struct nx_action_sample2. */
312 NXAST_RAW_SAMPLE2,
4930ea56
BP
313 /* NX1.0+(41): struct nx_action_sample2. */
314 NXAST_RAW_SAMPLE3,
18080541
BP
315
316 /* NX1.0+(34): struct nx_action_conjunction. */
317 NXAST_RAW_CONJUNCTION,
d4abaff5 318
07659514
JS
319 /* NX1.0+(35): struct nx_action_conntrack, ... */
320 NXAST_RAW_CT,
321
9ac0aada
JR
322 /* NX1.0+(36): struct nx_action_nat, ... */
323 NXAST_RAW_NAT,
324
aaca4fe0
WT
325 /* NX1.0+(39): struct nx_action_output_trunc. */
326 NXAST_RAW_OUTPUT_TRUNC,
327
7ae62a67
WT
328 /* NX1.0+(42): struct ext_action_header, ... */
329 NXAST_RAW_CLONE,
330
72fe7578
BP
331 /* NX1.0+(43): void. */
332 NXAST_RAW_CT_CLEAR,
333
d4abaff5
BP
334/* ## ------------------ ## */
335/* ## Debugging actions. ## */
336/* ## ------------------ ## */
337
338/* These are intentionally undocumented, subject to change, and ovs-vswitchd */
339/* accepts them only if started with --enable-dummy. */
340
341 /* NX1.0+(255): void. */
342 NXAST_RAW_DEBUG_RECIRC,
c2d936a4
BP
343};
344
345/* OpenFlow actions are always a multiple of 8 bytes in length. */
346#define OFP_ACTION_ALIGN 8
347
348/* Define a few functions for working with instructions. */
349#define DEFINE_INST(ENUM, STRUCT, EXTENSIBLE, NAME) \
350 static inline const struct STRUCT * OVS_UNUSED \
351 instruction_get_##ENUM(const struct ofp11_instruction *inst)\
352 { \
353 ovs_assert(inst->type == htons(ENUM)); \
354 return ALIGNED_CAST(struct STRUCT *, inst); \
355 } \
356 \
357 static inline void OVS_UNUSED \
358 instruction_init_##ENUM(struct STRUCT *s) \
359 { \
360 memset(s, 0, sizeof *s); \
361 s->type = htons(ENUM); \
362 s->len = htons(sizeof *s); \
363 } \
364 \
365 static inline struct STRUCT * OVS_UNUSED \
366 instruction_put_##ENUM(struct ofpbuf *buf) \
367 { \
368 struct STRUCT *s = ofpbuf_put_uninit(buf, sizeof *s); \
369 instruction_init_##ENUM(s); \
370 return s; \
371 }
372OVS_INSTRUCTIONS
373#undef DEFINE_INST
374
375static void ofpacts_update_instruction_actions(struct ofpbuf *openflow,
376 size_t ofs);
178742f9 377static void pad_ofpat(struct ofpbuf *openflow, size_t start_ofs);
c2d936a4
BP
378
379static enum ofperr ofpacts_verify(const struct ofpact[], size_t ofpacts_len,
d824b5b7
JS
380 uint32_t allowed_ovsinsts,
381 enum ofpact_type outer_action);
c2d936a4 382
128684a6
JR
383static void put_set_field(struct ofpbuf *openflow, enum ofp_version,
384 enum mf_field_id, uint64_t value);
c2d936a4 385
4b684612
BP
386static void put_reg_load(struct ofpbuf *openflow,
387 const struct mf_subfield *, uint64_t value);
388
c2d936a4
BP
389static enum ofperr ofpact_pull_raw(struct ofpbuf *, enum ofp_version,
390 enum ofp_raw_action_type *, uint64_t *arg);
391static void *ofpact_put_raw(struct ofpbuf *, enum ofp_version,
392 enum ofp_raw_action_type, uint64_t arg);
393
cab50449 394static char *OVS_WARN_UNUSED_RESULT ofpacts_parse(
c2d936a4 395 char *str, struct ofpbuf *ofpacts, enum ofputil_protocol *usable_protocols,
d824b5b7 396 bool allow_instructions, enum ofpact_type outer_action);
07659514
JS
397static enum ofperr ofpacts_pull_openflow_actions__(
398 struct ofpbuf *openflow, unsigned int actions_len,
399 enum ofp_version version, uint32_t allowed_ovsinsts,
400 struct ofpbuf *ofpacts, enum ofpact_type outer_action);
8e53fe8c
JS
401static char * OVS_WARN_UNUSED_RESULT ofpacts_parse_copy(
402 const char *s_, struct ofpbuf *ofpacts,
403 enum ofputil_protocol *usable_protocols,
404 bool allow_instructions, enum ofpact_type outer_action);
d824b5b7 405
4f20179d
BP
406/* Returns the ofpact following 'ofpact', except that if 'ofpact' contains
407 * nested ofpacts it returns the first one. */
408struct ofpact *
409ofpact_next_flattened(const struct ofpact *ofpact)
410{
411 switch (ofpact->type) {
412 case OFPACT_OUTPUT:
413 case OFPACT_GROUP:
414 case OFPACT_CONTROLLER:
415 case OFPACT_ENQUEUE:
416 case OFPACT_OUTPUT_REG:
aaca4fe0 417 case OFPACT_OUTPUT_TRUNC:
4f20179d
BP
418 case OFPACT_BUNDLE:
419 case OFPACT_SET_FIELD:
420 case OFPACT_SET_VLAN_VID:
421 case OFPACT_SET_VLAN_PCP:
422 case OFPACT_STRIP_VLAN:
423 case OFPACT_PUSH_VLAN:
424 case OFPACT_SET_ETH_SRC:
425 case OFPACT_SET_ETH_DST:
426 case OFPACT_SET_IPV4_SRC:
427 case OFPACT_SET_IPV4_DST:
428 case OFPACT_SET_IP_DSCP:
429 case OFPACT_SET_IP_ECN:
430 case OFPACT_SET_IP_TTL:
431 case OFPACT_SET_L4_SRC_PORT:
432 case OFPACT_SET_L4_DST_PORT:
433 case OFPACT_REG_MOVE:
434 case OFPACT_STACK_PUSH:
435 case OFPACT_STACK_POP:
436 case OFPACT_DEC_TTL:
437 case OFPACT_SET_MPLS_LABEL:
438 case OFPACT_SET_MPLS_TC:
439 case OFPACT_SET_MPLS_TTL:
440 case OFPACT_DEC_MPLS_TTL:
441 case OFPACT_PUSH_MPLS:
442 case OFPACT_POP_MPLS:
443 case OFPACT_SET_TUNNEL:
444 case OFPACT_SET_QUEUE:
445 case OFPACT_POP_QUEUE:
446 case OFPACT_FIN_TIMEOUT:
447 case OFPACT_RESUBMIT:
448 case OFPACT_LEARN:
449 case OFPACT_CONJUNCTION:
450 case OFPACT_MULTIPATH:
451 case OFPACT_NOTE:
452 case OFPACT_EXIT:
453 case OFPACT_SAMPLE:
454 case OFPACT_UNROLL_XLATE:
72fe7578 455 case OFPACT_CT_CLEAR:
4f20179d
BP
456 case OFPACT_DEBUG_RECIRC:
457 case OFPACT_METER:
458 case OFPACT_CLEAR_ACTIONS:
459 case OFPACT_WRITE_METADATA:
460 case OFPACT_GOTO_TABLE:
461 case OFPACT_NAT:
462 return ofpact_next(ofpact);
463
7ae62a67
WT
464 case OFPACT_CLONE:
465 return ofpact_get_CLONE(ofpact)->actions;
466
4f20179d
BP
467 case OFPACT_CT:
468 return ofpact_get_CT(ofpact)->actions;
469
470 case OFPACT_WRITE_ACTIONS:
471 return ofpact_get_WRITE_ACTIONS(ofpact)->actions;
472 }
473
474 OVS_NOT_REACHED();
475}
476
d824b5b7
JS
477/* Pull off existing actions or instructions. Used by nesting actions to keep
478 * ofpacts_parse() oblivious of actions nesting.
479 *
480 * Push the actions back on after nested parsing, e.g.:
481 *
482 * size_t ofs = ofpacts_pull(ofpacts);
483 * ...nested parsing...
484 * ofpbuf_push_uninit(ofpacts, ofs);
485 */
486static size_t
487ofpacts_pull(struct ofpbuf *ofpacts)
488{
489 size_t ofs;
490
d824b5b7
JS
491 ofs = ofpacts->size;
492 ofpbuf_pull(ofpacts, ofs);
493
494 return ofs;
495}
c2d936a4
BP
496
497#include "ofp-actions.inc1"
498\f
499/* Output actions. */
500
501/* Action structure for OFPAT10_OUTPUT, which sends packets out 'port'.
502 * When the 'port' is the OFPP_CONTROLLER, 'max_len' indicates the max
503 * number of bytes to send. A 'max_len' of zero means no bytes of the
504 * packet should be sent. */
505struct ofp10_action_output {
506 ovs_be16 type; /* OFPAT10_OUTPUT. */
507 ovs_be16 len; /* Length is 8. */
508 ovs_be16 port; /* Output port. */
509 ovs_be16 max_len; /* Max length to send to controller. */
e45e72f1 510};
c2d936a4
BP
511OFP_ASSERT(sizeof(struct ofp10_action_output) == 8);
512
513/* Action structure for OFPAT_OUTPUT, which sends packets out 'port'.
514 * When the 'port' is the OFPP_CONTROLLER, 'max_len' indicates the max
515 * number of bytes to send. A 'max_len' of zero means no bytes of the
516 * packet should be sent.*/
517struct ofp11_action_output {
518 ovs_be16 type; /* OFPAT11_OUTPUT. */
519 ovs_be16 len; /* Length is 16. */
520 ovs_be32 port; /* Output port. */
521 ovs_be16 max_len; /* Max length to send to controller. */
522 uint8_t pad[6]; /* Pad to 64 bits. */
523};
524OFP_ASSERT(sizeof(struct ofp11_action_output) == 16);
e45e72f1 525
f25d0cf3 526static enum ofperr
c2d936a4 527decode_OFPAT_RAW10_OUTPUT(const struct ofp10_action_output *oao,
f3cd3ac7 528 enum ofp_version ofp_version OVS_UNUSED,
c2d936a4 529 struct ofpbuf *out)
f25d0cf3
BP
530{
531 struct ofpact_output *output;
532
533 output = ofpact_put_OUTPUT(out);
4e022ec0 534 output->port = u16_to_ofp(ntohs(oao->port));
f25d0cf3
BP
535 output->max_len = ntohs(oao->max_len);
536
57ad4e9e 537 return ofpact_check_output_port(output->port, OFPP_MAX);
f25d0cf3
BP
538}
539
540static enum ofperr
c2d936a4 541decode_OFPAT_RAW11_OUTPUT(const struct ofp11_action_output *oao,
f3cd3ac7
JS
542 enum ofp_version ofp_version OVS_UNUSED,
543 struct ofpbuf *out)
f25d0cf3 544{
c2d936a4
BP
545 struct ofpact_output *output;
546 enum ofperr error;
f25d0cf3 547
c2d936a4
BP
548 output = ofpact_put_OUTPUT(out);
549 output->max_len = ntohs(oao->max_len);
550
551 error = ofputil_port_from_ofp11(oao->port, &output->port);
552 if (error) {
553 return error;
f25d0cf3 554 }
c2d936a4
BP
555
556 return ofpact_check_output_port(output->port, OFPP_MAX);
f25d0cf3
BP
557}
558
559static void
c2d936a4
BP
560encode_OUTPUT(const struct ofpact_output *output,
561 enum ofp_version ofp_version, struct ofpbuf *out)
f25d0cf3 562{
c2d936a4
BP
563 if (ofp_version == OFP10_VERSION) {
564 struct ofp10_action_output *oao;
f25d0cf3 565
c2d936a4
BP
566 oao = put_OFPAT10_OUTPUT(out);
567 oao->port = htons(ofp_to_u16(output->port));
568 oao->max_len = htons(output->max_len);
569 } else {
570 struct ofp11_action_output *oao;
571
572 oao = put_OFPAT11_OUTPUT(out);
573 oao->port = ofputil_port_to_ofp11(output->port);
574 oao->max_len = htons(output->max_len);
575 }
f25d0cf3
BP
576}
577
aaca4fe0
WT
578static char * OVS_WARN_UNUSED_RESULT
579parse_truncate_subfield(struct ofpact_output_trunc *output_trunc,
580 const char *arg_)
581{
582 char *key, *value;
583 char *arg = CONST_CAST(char *, arg_);
584
585 while (ofputil_parse_key_value(&arg, &key, &value)) {
586 if (!strcmp(key, "port")) {
587 if (!ofputil_port_from_string(value, &output_trunc->port)) {
588 return xasprintf("output to unknown truncate port: %s",
589 value);
590 }
591 if (ofp_to_u16(output_trunc->port) > ofp_to_u16(OFPP_MAX)) {
592 if (output_trunc->port != OFPP_LOCAL &&
593 output_trunc->port != OFPP_IN_PORT)
594 return xasprintf("output to unsupported truncate port: %s",
595 value);
596 }
597 } else if (!strcmp(key, "max_len")) {
598 char *err;
599
600 err = str_to_u32(value, &output_trunc->max_len);
601 if (err) {
602 return err;
603 }
604 } else {
605 return xasprintf("invalid key '%s' in output_trunc argument",
606 key);
607 }
608 }
609 return NULL;
610}
611
cab50449 612static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
613parse_OUTPUT(const char *arg, struct ofpbuf *ofpacts,
614 enum ofputil_protocol *usable_protocols OVS_UNUSED)
f25d0cf3 615{
21b2fa61 616 if (strstr(arg, "port") && strstr(arg, "max_len")) {
aaca4fe0
WT
617 struct ofpact_output_trunc *output_trunc;
618
619 output_trunc = ofpact_put_OUTPUT_TRUNC(ofpacts);
620 return parse_truncate_subfield(output_trunc, arg);
c2d936a4 621 } else {
21b2fa61
JR
622 struct mf_subfield src;
623 char *error = mf_parse_subfield(&src, arg);
624 if (!error) {
625 struct ofpact_output_reg *output_reg;
626
627 output_reg = ofpact_put_OUTPUT_REG(ofpacts);
628 output_reg->max_len = UINT16_MAX;
629 output_reg->src = src;
630 } else {
631 free(error);
632 struct ofpact_output *output;
c2d936a4 633
21b2fa61
JR
634 output = ofpact_put_OUTPUT(ofpacts);
635 if (!ofputil_port_from_string(arg, &output->port)) {
636 return xasprintf("%s: output to unknown port", arg);
637 }
638 output->max_len = output->port == OFPP_CONTROLLER ? UINT16_MAX : 0;
c2d936a4 639 }
c2d936a4 640 return NULL;
f25d0cf3 641 }
c2d936a4 642}
f25d0cf3 643
c2d936a4
BP
644static void
645format_OUTPUT(const struct ofpact_output *a, struct ds *s)
646{
647 if (ofp_to_u16(a->port) < ofp_to_u16(OFPP_MAX)) {
94783c7c 648 ds_put_format(s, "%soutput:%s%"PRIu32,
b1c5bf1f 649 colors.special, colors.end, a->port);
c2d936a4
BP
650 } else {
651 ofputil_format_port(a->port, s);
652 if (a->port == OFPP_CONTROLLER) {
653 ds_put_format(s, ":%"PRIu16, a->max_len);
654 }
655 }
f25d0cf3 656}
c2d936a4
BP
657\f
658/* Group actions. */
f25d0cf3
BP
659
660static enum ofperr
88c8ca26 661decode_OFPAT_RAW_GROUP(uint32_t group_id,
f3cd3ac7
JS
662 enum ofp_version ofp_version OVS_UNUSED,
663 struct ofpbuf *out)
f25d0cf3 664{
c2d936a4
BP
665 ofpact_put_GROUP(out)->group_id = group_id;
666 return 0;
667}
f25d0cf3 668
c2d936a4
BP
669static void
670encode_GROUP(const struct ofpact_group *group,
671 enum ofp_version ofp_version, struct ofpbuf *out)
672{
88c8ca26 673 put_OFPAT_GROUP(out, ofp_version, group->group_id);
c2d936a4 674}
f25d0cf3 675
cab50449 676static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
677parse_GROUP(char *arg, struct ofpbuf *ofpacts,
678 enum ofputil_protocol *usable_protocols OVS_UNUSED)
679{
680 return str_to_u32(arg, &ofpact_put_GROUP(ofpacts)->group_id);
f25d0cf3
BP
681}
682
683static void
c2d936a4 684format_GROUP(const struct ofpact_group *a, struct ds *s)
f25d0cf3 685{
b1c5bf1f
QM
686 ds_put_format(s, "%sgroup:%s%"PRIu32,
687 colors.special, colors.end, a->group_id);
f25d0cf3 688}
c2d936a4
BP
689\f
690/* Action structure for NXAST_CONTROLLER.
691 *
692 * This generalizes using OFPAT_OUTPUT to send a packet to OFPP_CONTROLLER. In
693 * addition to the 'max_len' that OFPAT_OUTPUT supports, it also allows
694 * specifying:
695 *
696 * - 'reason': The reason code to use in the ofp_packet_in or nx_packet_in.
697 *
698 * - 'controller_id': The ID of the controller connection to which the
699 * ofp_packet_in should be sent. The ofp_packet_in or nx_packet_in is
700 * sent only to controllers that have the specified controller connection
701 * ID. See "struct nx_controller_id" for more information. */
702struct nx_action_controller {
703 ovs_be16 type; /* OFPAT_VENDOR. */
704 ovs_be16 len; /* Length is 16. */
705 ovs_be32 vendor; /* NX_VENDOR_ID. */
706 ovs_be16 subtype; /* NXAST_CONTROLLER. */
707 ovs_be16 max_len; /* Maximum length to send to controller. */
708 ovs_be16 controller_id; /* Controller ID to send packet-in. */
709 uint8_t reason; /* enum ofp_packet_in_reason (OFPR_*). */
710 uint8_t zero; /* Must be zero. */
711};
712OFP_ASSERT(sizeof(struct nx_action_controller) == 16);
f25d0cf3 713
77ab5fd2
BP
714/* Properties for NXAST_CONTROLLER2.
715 *
716 * For more information on the effect of NXAC2PT_PAUSE, see the large comment
717 * on NXT_PACKET_IN2 in nicira-ext.h */
bdcad671
BP
718enum nx_action_controller2_prop_type {
719 NXAC2PT_MAX_LEN, /* ovs_be16 max bytes to send (default all). */
720 NXAC2PT_CONTROLLER_ID, /* ovs_be16 dest controller ID (default 0). */
721 NXAC2PT_REASON, /* uint8_t reason (OFPR_*), default 0. */
722 NXAC2PT_USERDATA, /* Data to copy into NXPINT_USERDATA. */
77ab5fd2 723 NXAC2PT_PAUSE, /* Flag to pause pipeline to resume later. */
bdcad671
BP
724};
725
aad28f47
BP
726/* The action structure for NXAST_CONTROLLER2 is "struct ext_action_header",
727 * followed by NXAC2PT_* properties. */
bdcad671 728
c2d936a4
BP
729static enum ofperr
730decode_NXAST_RAW_CONTROLLER(const struct nx_action_controller *nac,
f3cd3ac7 731 enum ofp_version ofp_version OVS_UNUSED,
c2d936a4 732 struct ofpbuf *out)
f25d0cf3
BP
733{
734 struct ofpact_controller *oc;
735
736 oc = ofpact_put_CONTROLLER(out);
bdcad671 737 oc->ofpact.raw = NXAST_RAW_CONTROLLER;
f25d0cf3
BP
738 oc->max_len = ntohs(nac->max_len);
739 oc->controller_id = ntohs(nac->controller_id);
740 oc->reason = nac->reason;
ce058104 741 ofpact_finish_CONTROLLER(out, &oc);
bdcad671
BP
742
743 return 0;
744}
745
746static enum ofperr
aad28f47 747decode_NXAST_RAW_CONTROLLER2(const struct ext_action_header *eah,
bdcad671
BP
748 enum ofp_version ofp_version OVS_UNUSED,
749 struct ofpbuf *out)
750{
aad28f47 751 if (!is_all_zeros(eah->pad, sizeof eah->pad)) {
bdcad671
BP
752 return OFPERR_NXBRC_MUST_BE_ZERO;
753 }
754
755 size_t start_ofs = out->size;
756 struct ofpact_controller *oc = ofpact_put_CONTROLLER(out);
757 oc->ofpact.raw = NXAST_RAW_CONTROLLER2;
758 oc->max_len = UINT16_MAX;
759 oc->reason = OFPR_ACTION;
760
761 struct ofpbuf properties;
aad28f47
BP
762 ofpbuf_use_const(&properties, eah, ntohs(eah->len));
763 ofpbuf_pull(&properties, sizeof *eah);
bdcad671
BP
764
765 while (properties.size > 0) {
766 struct ofpbuf payload;
767 uint64_t type;
768
769 enum ofperr error = ofpprop_pull(&properties, &payload, &type);
770 if (error) {
771 return error;
772 }
773
774 switch (type) {
775 case NXAC2PT_MAX_LEN:
776 error = ofpprop_parse_u16(&payload, &oc->max_len);
777 break;
778
779 case NXAC2PT_CONTROLLER_ID:
780 error = ofpprop_parse_u16(&payload, &oc->controller_id);
781 break;
782
783 case NXAC2PT_REASON: {
784 uint8_t u8;
785 error = ofpprop_parse_u8(&payload, &u8);
786 oc->reason = u8;
787 break;
788 }
789
790 case NXAC2PT_USERDATA:
791 out->size = start_ofs + OFPACT_CONTROLLER_SIZE;
792 ofpbuf_put(out, payload.msg, ofpbuf_msgsize(&payload));
793 oc = ofpbuf_at_assert(out, start_ofs, sizeof *oc);
794 oc->userdata_len = ofpbuf_msgsize(&payload);
795 break;
796
77ab5fd2
BP
797 case NXAC2PT_PAUSE:
798 oc->pause = true;
799 break;
800
bdcad671
BP
801 default:
802 error = OFPPROP_UNKNOWN(false, "NXAST_RAW_CONTROLLER2", type);
803 break;
804 }
805 if (error) {
806 return error;
807 }
808 }
809
ce058104 810 ofpact_finish_CONTROLLER(out, &oc);
bdcad671 811
c2d936a4 812 return 0;
f25d0cf3
BP
813}
814
c2d936a4
BP
815static void
816encode_CONTROLLER(const struct ofpact_controller *controller,
817 enum ofp_version ofp_version OVS_UNUSED,
818 struct ofpbuf *out)
4cceacb9 819{
bdcad671 820 if (controller->userdata_len
77ab5fd2 821 || controller->pause
bdcad671
BP
822 || controller->ofpact.raw == NXAST_RAW_CONTROLLER2) {
823 size_t start_ofs = out->size;
824 put_NXAST_CONTROLLER2(out);
825 if (controller->max_len != UINT16_MAX) {
826 ofpprop_put_u16(out, NXAC2PT_MAX_LEN, controller->max_len);
827 }
828 if (controller->controller_id != 0) {
829 ofpprop_put_u16(out, NXAC2PT_CONTROLLER_ID,
830 controller->controller_id);
831 }
832 if (controller->reason != OFPR_ACTION) {
833 ofpprop_put_u8(out, NXAC2PT_REASON, controller->reason);
834 }
835 if (controller->userdata_len != 0) {
836 ofpprop_put(out, NXAC2PT_USERDATA, controller->userdata,
837 controller->userdata_len);
838 }
77ab5fd2
BP
839 if (controller->pause) {
840 ofpprop_put_flag(out, NXAC2PT_PAUSE);
841 }
bdcad671
BP
842 pad_ofpat(out, start_ofs);
843 } else {
844 struct nx_action_controller *nac;
4cceacb9 845
bdcad671
BP
846 nac = put_NXAST_CONTROLLER(out);
847 nac->max_len = htons(controller->max_len);
848 nac->controller_id = htons(controller->controller_id);
849 nac->reason = controller->reason;
850 }
c2d936a4
BP
851}
852
cab50449 853static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
854parse_CONTROLLER(char *arg, struct ofpbuf *ofpacts,
855 enum ofputil_protocol *usable_protocols OVS_UNUSED)
856{
857 enum ofp_packet_in_reason reason = OFPR_ACTION;
858 uint16_t controller_id = 0;
859 uint16_t max_len = UINT16_MAX;
bdcad671 860 const char *userdata = NULL;
77ab5fd2 861 bool pause = false;
c2d936a4
BP
862
863 if (!arg[0]) {
864 /* Use defaults. */
865 } else if (strspn(arg, "0123456789") == strlen(arg)) {
866 char *error = str_to_u16(arg, "max_len", &max_len);
867 if (error) {
868 return error;
869 }
870 } else {
871 char *name, *value;
872
873 while (ofputil_parse_key_value(&arg, &name, &value)) {
874 if (!strcmp(name, "reason")) {
875 if (!ofputil_packet_in_reason_from_string(value, &reason)) {
876 return xasprintf("unknown reason \"%s\"", value);
877 }
878 } else if (!strcmp(name, "max_len")) {
879 char *error = str_to_u16(value, "max_len", &max_len);
880 if (error) {
881 return error;
882 }
883 } else if (!strcmp(name, "id")) {
884 char *error = str_to_u16(value, "id", &controller_id);
885 if (error) {
886 return error;
887 }
bdcad671
BP
888 } else if (!strcmp(name, "userdata")) {
889 userdata = value;
77ab5fd2
BP
890 } else if (!strcmp(name, "pause")) {
891 pause = true;
c2d936a4
BP
892 } else {
893 return xasprintf("unknown key \"%s\" parsing controller "
894 "action", name);
895 }
896 }
4cceacb9
JS
897 }
898
77ab5fd2 899 if (reason == OFPR_ACTION && controller_id == 0 && !userdata && !pause) {
c2d936a4 900 struct ofpact_output *output;
4cceacb9 901
c2d936a4
BP
902 output = ofpact_put_OUTPUT(ofpacts);
903 output->port = OFPP_CONTROLLER;
904 output->max_len = max_len;
905 } else {
906 struct ofpact_controller *controller;
907
908 controller = ofpact_put_CONTROLLER(ofpacts);
909 controller->max_len = max_len;
910 controller->reason = reason;
911 controller->controller_id = controller_id;
77ab5fd2 912 controller->pause = pause;
bdcad671
BP
913
914 if (userdata) {
915 size_t start_ofs = ofpacts->size;
916 const char *end = ofpbuf_put_hex(ofpacts, userdata, NULL);
917 if (*end) {
918 return xstrdup("bad hex digit in `controller' "
919 "action `userdata'");
920 }
921 size_t userdata_len = ofpacts->size - start_ofs;
922 controller = ofpacts->header;
923 controller->userdata_len = userdata_len;
924 }
ce058104 925 ofpact_finish_CONTROLLER(ofpacts, &controller);
c2d936a4
BP
926 }
927
928 return NULL;
4cceacb9
JS
929}
930
bdcad671
BP
931static void
932format_hex_arg(struct ds *s, const uint8_t *data, size_t len)
933{
934 for (size_t i = 0; i < len; i++) {
935 if (i) {
936 ds_put_char(s, '.');
937 }
938 ds_put_format(s, "%02"PRIx8, data[i]);
939 }
940}
941
f25d0cf3 942static void
c2d936a4 943format_CONTROLLER(const struct ofpact_controller *a, struct ds *s)
f25d0cf3 944{
77ab5fd2
BP
945 if (a->reason == OFPR_ACTION && !a->controller_id && !a->userdata_len
946 && !a->pause) {
b1c5bf1f
QM
947 ds_put_format(s, "%sCONTROLLER:%s%"PRIu16,
948 colors.special, colors.end, a->max_len);
c2d936a4
BP
949 } else {
950 enum ofp_packet_in_reason reason = a->reason;
f25d0cf3 951
b1c5bf1f 952 ds_put_format(s, "%scontroller(%s", colors.paren, colors.end);
c2d936a4
BP
953 if (reason != OFPR_ACTION) {
954 char reasonbuf[OFPUTIL_PACKET_IN_REASON_BUFSIZE];
955
b1c5bf1f 956 ds_put_format(s, "%sreason=%s%s,", colors.param, colors.end,
c2d936a4
BP
957 ofputil_packet_in_reason_to_string(
958 reason, reasonbuf, sizeof reasonbuf));
959 }
960 if (a->max_len != UINT16_MAX) {
b1c5bf1f
QM
961 ds_put_format(s, "%smax_len=%s%"PRIu16",",
962 colors.param, colors.end, a->max_len);
c2d936a4
BP
963 }
964 if (a->controller_id != 0) {
b1c5bf1f
QM
965 ds_put_format(s, "%sid=%s%"PRIu16",",
966 colors.param, colors.end, a->controller_id);
c2d936a4 967 }
bdcad671 968 if (a->userdata_len) {
b1c5bf1f 969 ds_put_format(s, "%suserdata=%s", colors.param, colors.end);
bdcad671
BP
970 format_hex_arg(s, a->userdata, a->userdata_len);
971 ds_put_char(s, ',');
972 }
77ab5fd2 973 if (a->pause) {
b1c5bf1f 974 ds_put_format(s, "%spause%s,", colors.value, colors.end);
77ab5fd2 975 }
c2d936a4 976 ds_chomp(s, ',');
b1c5bf1f 977 ds_put_format(s, "%s)%s", colors.paren, colors.end);
c2d936a4 978 }
f25d0cf3 979}
c2d936a4
BP
980\f
981/* Enqueue action. */
982struct ofp10_action_enqueue {
983 ovs_be16 type; /* OFPAT10_ENQUEUE. */
984 ovs_be16 len; /* Len is 16. */
985 ovs_be16 port; /* Port that queue belongs. Should
986 refer to a valid physical port
987 (i.e. < OFPP_MAX) or OFPP_IN_PORT. */
988 uint8_t pad[6]; /* Pad for 64-bit alignment. */
989 ovs_be32 queue_id; /* Where to enqueue the packets. */
990};
991OFP_ASSERT(sizeof(struct ofp10_action_enqueue) == 16);
f25d0cf3 992
c2d967a5 993static enum ofperr
c2d936a4 994decode_OFPAT_RAW10_ENQUEUE(const struct ofp10_action_enqueue *oae,
f3cd3ac7 995 enum ofp_version ofp_version OVS_UNUSED,
c2d936a4 996 struct ofpbuf *out)
c2d967a5 997{
c2d936a4 998 struct ofpact_enqueue *enqueue;
c2d967a5 999
c2d936a4
BP
1000 enqueue = ofpact_put_ENQUEUE(out);
1001 enqueue->port = u16_to_ofp(ntohs(oae->port));
1002 enqueue->queue = ntohl(oae->queue_id);
1003 if (ofp_to_u16(enqueue->port) >= ofp_to_u16(OFPP_MAX)
1004 && enqueue->port != OFPP_IN_PORT
1005 && enqueue->port != OFPP_LOCAL) {
1006 return OFPERR_OFPBAC_BAD_OUT_PORT;
1007 }
1008 return 0;
c2d967a5
MM
1009}
1010
c2d936a4
BP
1011static void
1012encode_ENQUEUE(const struct ofpact_enqueue *enqueue,
1013 enum ofp_version ofp_version, struct ofpbuf *out)
c2d967a5 1014{
c2d936a4
BP
1015 if (ofp_version == OFP10_VERSION) {
1016 struct ofp10_action_enqueue *oae;
c2d967a5 1017
c2d936a4
BP
1018 oae = put_OFPAT10_ENQUEUE(out);
1019 oae->port = htons(ofp_to_u16(enqueue->port));
1020 oae->queue_id = htonl(enqueue->queue);
1021 } else {
0f2aaee9
BP
1022 put_OFPAT_SET_QUEUE(out, ofp_version, enqueue->queue);
1023
1024 struct ofp11_action_output *oao = put_OFPAT11_OUTPUT(out);
1025 oao->port = ofputil_port_to_ofp11(enqueue->port);
1026 oao->max_len = OVS_BE16_MAX;
1027
1028 put_NXAST_POP_QUEUE(out);
c2d967a5 1029 }
c2d936a4 1030}
c2d967a5 1031
cab50449 1032static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
1033parse_ENQUEUE(char *arg, struct ofpbuf *ofpacts,
1034 enum ofputil_protocol *usable_protocols OVS_UNUSED)
1035{
1036 char *sp = NULL;
1037 char *port = strtok_r(arg, ":q,", &sp);
1038 char *queue = strtok_r(NULL, "", &sp);
1039 struct ofpact_enqueue *enqueue;
c2d967a5 1040
c2d936a4
BP
1041 if (port == NULL || queue == NULL) {
1042 return xstrdup("\"enqueue\" syntax is \"enqueue:PORT:QUEUE\" or "
1043 "\"enqueue(PORT,QUEUE)\"");
c2d967a5
MM
1044 }
1045
c2d936a4
BP
1046 enqueue = ofpact_put_ENQUEUE(ofpacts);
1047 if (!ofputil_port_from_string(port, &enqueue->port)) {
1048 return xasprintf("%s: enqueue to unknown port", port);
1049 }
1050 return str_to_u32(queue, &enqueue->queue);
c2d967a5
MM
1051}
1052
c2d936a4
BP
1053static void
1054format_ENQUEUE(const struct ofpact_enqueue *a, struct ds *s)
29089a54 1055{
b1c5bf1f 1056 ds_put_format(s, "%senqueue:%s", colors.param, colors.end);
c2d936a4
BP
1057 ofputil_format_port(a->port, s);
1058 ds_put_format(s, ":%"PRIu32, a->queue);
1059}
1060\f
1061/* Action structure for NXAST_OUTPUT_REG.
1062 *
1063 * Outputs to the OpenFlow port number written to src[ofs:ofs+nbits].
1064 *
1065 * The format and semantics of 'src' and 'ofs_nbits' are similar to those for
1066 * the NXAST_REG_LOAD action.
1067 *
1068 * The acceptable nxm_header values for 'src' are the same as the acceptable
1069 * nxm_header values for the 'src' field of NXAST_REG_MOVE.
1070 *
1071 * The 'max_len' field indicates the number of bytes to send when the chosen
1072 * port is OFPP_CONTROLLER. Its semantics are equivalent to the 'max_len'
1073 * field of OFPAT_OUTPUT.
1074 *
1075 * The 'zero' field is required to be zeroed for forward compatibility. */
1076struct nx_action_output_reg {
1077 ovs_be16 type; /* OFPAT_VENDOR. */
1078 ovs_be16 len; /* 24. */
1079 ovs_be32 vendor; /* NX_VENDOR_ID. */
1080 ovs_be16 subtype; /* NXAST_OUTPUT_REG. */
29089a54 1081
c2d936a4
BP
1082 ovs_be16 ofs_nbits; /* (ofs << 6) | (n_bits - 1). */
1083 ovs_be32 src; /* Source. */
29089a54 1084
c2d936a4 1085 ovs_be16 max_len; /* Max length to send to controller. */
29089a54 1086
c2d936a4
BP
1087 uint8_t zero[6]; /* Reserved, must be zero. */
1088};
1089OFP_ASSERT(sizeof(struct nx_action_output_reg) == 24);
29089a54 1090
bad8a439
BP
1091/* Action structure for NXAST_OUTPUT_REG2.
1092 *
1093 * Like the NXAST_OUTPUT_REG but organized so that there is room for a 64-bit
1094 * experimenter OXM as 'src'.
1095 */
1096struct nx_action_output_reg2 {
1097 ovs_be16 type; /* OFPAT_VENDOR. */
1098 ovs_be16 len; /* 24. */
1099 ovs_be32 vendor; /* NX_VENDOR_ID. */
1100 ovs_be16 subtype; /* NXAST_OUTPUT_REG2. */
1101
1102 ovs_be16 ofs_nbits; /* (ofs << 6) | (n_bits - 1). */
1103 ovs_be16 max_len; /* Max length to send to controller. */
1104
1105 /* Followed by:
1106 * - 'src', as an OXM/NXM header (either 4 or 8 bytes).
1107 * - Enough 0-bytes to pad the action out to 24 bytes. */
1108 uint8_t pad[10];
1109};
1110OFP_ASSERT(sizeof(struct nx_action_output_reg2) == 24);
1111
a7a2d006 1112static enum ofperr
c2d936a4 1113decode_NXAST_RAW_OUTPUT_REG(const struct nx_action_output_reg *naor,
f3cd3ac7 1114 enum ofp_version ofp_version OVS_UNUSED,
c2d936a4 1115 struct ofpbuf *out)
a7a2d006 1116{
c2d936a4 1117 struct ofpact_output_reg *output_reg;
a7a2d006 1118
c2d936a4 1119 if (!is_all_zeros(naor->zero, sizeof naor->zero)) {
a7a2d006
JS
1120 return OFPERR_OFPBAC_BAD_ARGUMENT;
1121 }
a7a2d006 1122
c2d936a4 1123 output_reg = ofpact_put_OUTPUT_REG(out);
bad8a439 1124 output_reg->ofpact.raw = NXAST_RAW_OUTPUT_REG;
c2d936a4
BP
1125 output_reg->src.field = mf_from_nxm_header(ntohl(naor->src));
1126 output_reg->src.ofs = nxm_decode_ofs(naor->ofs_nbits);
1127 output_reg->src.n_bits = nxm_decode_n_bits(naor->ofs_nbits);
1128 output_reg->max_len = ntohs(naor->max_len);
1129
1130 return mf_check_src(&output_reg->src, NULL);
a7a2d006
JS
1131}
1132
bad8a439
BP
1133static enum ofperr
1134decode_NXAST_RAW_OUTPUT_REG2(const struct nx_action_output_reg2 *naor,
f3cd3ac7
JS
1135 enum ofp_version ofp_version OVS_UNUSED,
1136 struct ofpbuf *out)
bad8a439
BP
1137{
1138 struct ofpact_output_reg *output_reg;
bad8a439
BP
1139 output_reg = ofpact_put_OUTPUT_REG(out);
1140 output_reg->ofpact.raw = NXAST_RAW_OUTPUT_REG2;
1141 output_reg->src.ofs = nxm_decode_ofs(naor->ofs_nbits);
1142 output_reg->src.n_bits = nxm_decode_n_bits(naor->ofs_nbits);
1143 output_reg->max_len = ntohs(naor->max_len);
1144
0a2869d5 1145 struct ofpbuf b = ofpbuf_const_initializer(naor, ntohs(naor->len));
bad8a439 1146 ofpbuf_pull(&b, OBJECT_OFFSETOF(naor, pad));
0a2869d5
BP
1147
1148 enum ofperr error = nx_pull_header(&b, &output_reg->src.field, NULL);
bad8a439
BP
1149 if (error) {
1150 return error;
1151 }
6fd6ed71 1152 if (!is_all_zeros(b.data, b.size)) {
bad8a439
BP
1153 return OFPERR_NXBRC_MUST_BE_ZERO;
1154 }
1155
1156 return mf_check_src(&output_reg->src, NULL);
1157}
1158
c2d936a4
BP
1159static void
1160encode_OUTPUT_REG(const struct ofpact_output_reg *output_reg,
1161 enum ofp_version ofp_version OVS_UNUSED,
1162 struct ofpbuf *out)
f25d0cf3 1163{
bad8a439
BP
1164 /* If 'output_reg' came in as an NXAST_RAW_OUTPUT_REG2 action, or if it
1165 * cannot be encoded in the older form, encode it as
1166 * NXAST_RAW_OUTPUT_REG2. */
1167 if (output_reg->ofpact.raw == NXAST_RAW_OUTPUT_REG2
1168 || !mf_nxm_header(output_reg->src.field->id)) {
1169 struct nx_action_output_reg2 *naor = put_NXAST_OUTPUT_REG2(out);
6fd6ed71 1170 size_t size = out->size;
bad8a439
BP
1171
1172 naor->ofs_nbits = nxm_encode_ofs_nbits(output_reg->src.ofs,
1173 output_reg->src.n_bits);
1174 naor->max_len = htons(output_reg->max_len);
1175
6fd6ed71 1176 out->size = size - sizeof naor->pad;
bad8a439 1177 nx_put_header(out, output_reg->src.field->id, 0, false);
6fd6ed71 1178 out->size = size;
bad8a439
BP
1179 } else {
1180 struct nx_action_output_reg *naor = put_NXAST_OUTPUT_REG(out);
f25d0cf3 1181
bad8a439
BP
1182 naor->ofs_nbits = nxm_encode_ofs_nbits(output_reg->src.ofs,
1183 output_reg->src.n_bits);
1184 naor->src = htonl(mf_nxm_header(output_reg->src.field->id));
1185 naor->max_len = htons(output_reg->max_len);
1186 }
f25d0cf3
BP
1187}
1188
cab50449 1189static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
1190parse_OUTPUT_REG(const char *arg, struct ofpbuf *ofpacts,
1191 enum ofputil_protocol *usable_protocols OVS_UNUSED)
f25d0cf3 1192{
c2d936a4 1193 return parse_OUTPUT(arg, ofpacts, usable_protocols);
f25d0cf3
BP
1194}
1195
c2d936a4
BP
1196static void
1197format_OUTPUT_REG(const struct ofpact_output_reg *a, struct ds *s)
f25d0cf3 1198{
b1c5bf1f 1199 ds_put_format(s, "%soutput:%s", colors.special, colors.end);
c2d936a4
BP
1200 mf_format_subfield(&a->src, s);
1201}
1202\f
1203/* Action structure for NXAST_BUNDLE and NXAST_BUNDLE_LOAD.
1204 *
1205 * The bundle actions choose a slave from a supplied list of options.
1206 * NXAST_BUNDLE outputs to its selection. NXAST_BUNDLE_LOAD writes its
1207 * selection to a register.
1208 *
1209 * The list of possible slaves follows the nx_action_bundle structure. The size
1210 * of each slave is governed by its type as indicated by the 'slave_type'
1211 * parameter. The list of slaves should be padded at its end with zeros to make
1212 * the total length of the action a multiple of 8.
1213 *
1214 * Switches infer from the 'slave_type' parameter the size of each slave. All
1215 * implementations must support the NXM_OF_IN_PORT 'slave_type' which indicates
1216 * that the slaves are OpenFlow port numbers with NXM_LENGTH(NXM_OF_IN_PORT) ==
1217 * 2 byte width. Switches should reject actions which indicate unknown or
1218 * unsupported slave types.
1219 *
1220 * Switches use a strategy dictated by the 'algorithm' parameter to choose a
1221 * slave. If the switch does not support the specified 'algorithm' parameter,
1222 * it should reject the action.
1223 *
1224 * Several algorithms take into account liveness when selecting slaves. The
1225 * liveness of a slave is implementation defined (with one exception), but will
1226 * generally take into account things like its carrier status and the results
1227 * of any link monitoring protocols which happen to be running on it. In order
1228 * to give controllers a place-holder value, the OFPP_NONE port is always
63460a30
TLSC
1229 * considered live, that is, NXAST_BUNDLE_LOAD stores OFPP_NONE in the output
1230 * register if no slave is live.
c2d936a4
BP
1231 *
1232 * Some slave selection strategies require the use of a hash function, in which
1233 * case the 'fields' and 'basis' parameters should be populated. The 'fields'
1234 * parameter (one of NX_HASH_FIELDS_*) designates which parts of the flow to
1235 * hash. Refer to the definition of "enum nx_hash_fields" for details. The
1236 * 'basis' parameter is used as a universal hash parameter. Different values
1237 * of 'basis' yield different hash results.
1238 *
1239 * The 'zero' parameter at the end of the action structure is reserved for
1240 * future use. Switches are required to reject actions which have nonzero
1241 * bytes in the 'zero' field.
1242 *
1243 * NXAST_BUNDLE actions should have 'ofs_nbits' and 'dst' zeroed. Switches
1244 * should reject actions which have nonzero bytes in either of these fields.
1245 *
1246 * NXAST_BUNDLE_LOAD stores the OpenFlow port number of the selected slave in
1247 * dst[ofs:ofs+n_bits]. The format and semantics of 'dst' and 'ofs_nbits' are
1248 * similar to those for the NXAST_REG_LOAD action. */
1249struct nx_action_bundle {
1250 ovs_be16 type; /* OFPAT_VENDOR. */
1251 ovs_be16 len; /* Length including slaves. */
1252 ovs_be32 vendor; /* NX_VENDOR_ID. */
1253 ovs_be16 subtype; /* NXAST_BUNDLE or NXAST_BUNDLE_LOAD. */
f25d0cf3 1254
c2d936a4
BP
1255 /* Slave choice algorithm to apply to hash value. */
1256 ovs_be16 algorithm; /* One of NX_BD_ALG_*. */
4cceacb9 1257
c2d936a4
BP
1258 /* What fields to hash and how. */
1259 ovs_be16 fields; /* One of NX_HASH_FIELDS_*. */
1260 ovs_be16 basis; /* Universal hash parameter. */
f25d0cf3 1261
c2d936a4
BP
1262 ovs_be32 slave_type; /* NXM_OF_IN_PORT. */
1263 ovs_be16 n_slaves; /* Number of slaves. */
f25d0cf3 1264
c2d936a4
BP
1265 ovs_be16 ofs_nbits; /* (ofs << 6) | (n_bits - 1). */
1266 ovs_be32 dst; /* Destination. */
f25d0cf3 1267
c2d936a4
BP
1268 uint8_t zero[4]; /* Reserved. Must be zero. */
1269};
1270OFP_ASSERT(sizeof(struct nx_action_bundle) == 32);
f25d0cf3 1271
c2d936a4
BP
1272static enum ofperr
1273decode_bundle(bool load, const struct nx_action_bundle *nab,
1274 struct ofpbuf *ofpacts)
1275{
1276 static struct vlog_rate_limit rl = VLOG_RATE_LIMIT_INIT(1, 5);
1277 struct ofpact_bundle *bundle;
1278 uint32_t slave_type;
1279 size_t slaves_size, i;
1280 enum ofperr error;
bd85dac1 1281
c2d936a4
BP
1282 bundle = ofpact_put_BUNDLE(ofpacts);
1283
1284 bundle->n_slaves = ntohs(nab->n_slaves);
1285 bundle->basis = ntohs(nab->basis);
1286 bundle->fields = ntohs(nab->fields);
1287 bundle->algorithm = ntohs(nab->algorithm);
1288 slave_type = ntohl(nab->slave_type);
1289 slaves_size = ntohs(nab->len) - sizeof *nab;
1290
1291 error = OFPERR_OFPBAC_BAD_ARGUMENT;
1292 if (!flow_hash_fields_valid(bundle->fields)) {
1293 VLOG_WARN_RL(&rl, "unsupported fields %d", (int) bundle->fields);
1294 } else if (bundle->n_slaves > BUNDLE_MAX_SLAVES) {
1295 VLOG_WARN_RL(&rl, "too many slaves");
1296 } else if (bundle->algorithm != NX_BD_ALG_HRW
1297 && bundle->algorithm != NX_BD_ALG_ACTIVE_BACKUP) {
1298 VLOG_WARN_RL(&rl, "unsupported algorithm %d", (int) bundle->algorithm);
508a9338 1299 } else if (slave_type != mf_nxm_header(MFF_IN_PORT)) {
c2d936a4
BP
1300 VLOG_WARN_RL(&rl, "unsupported slave type %"PRIu16, slave_type);
1301 } else {
1302 error = 0;
1303 }
bd85dac1 1304
c2d936a4
BP
1305 if (!is_all_zeros(nab->zero, sizeof nab->zero)) {
1306 VLOG_WARN_RL(&rl, "reserved field is nonzero");
1307 error = OFPERR_OFPBAC_BAD_ARGUMENT;
1308 }
f25d0cf3 1309
c2d936a4
BP
1310 if (load) {
1311 bundle->dst.field = mf_from_nxm_header(ntohl(nab->dst));
1312 bundle->dst.ofs = nxm_decode_ofs(nab->ofs_nbits);
1313 bundle->dst.n_bits = nxm_decode_n_bits(nab->ofs_nbits);
f25d0cf3 1314
c2d936a4
BP
1315 if (bundle->dst.n_bits < 16) {
1316 VLOG_WARN_RL(&rl, "bundle_load action requires at least 16 bit "
1317 "destination.");
1318 error = OFPERR_OFPBAC_BAD_ARGUMENT;
1319 }
1320 } else {
1321 if (nab->ofs_nbits || nab->dst) {
1322 VLOG_WARN_RL(&rl, "bundle action has nonzero reserved fields");
1323 error = OFPERR_OFPBAC_BAD_ARGUMENT;
1324 }
1325 }
f25d0cf3 1326
c2d936a4
BP
1327 if (slaves_size < bundle->n_slaves * sizeof(ovs_be16)) {
1328 VLOG_WARN_RL(&rl, "Nicira action %s only has %"PRIuSIZE" bytes "
1329 "allocated for slaves. %"PRIuSIZE" bytes are required "
1330 "for %"PRIu16" slaves.",
1331 load ? "bundle_load" : "bundle", slaves_size,
1332 bundle->n_slaves * sizeof(ovs_be16), bundle->n_slaves);
1333 error = OFPERR_OFPBAC_BAD_LEN;
1334 }
f25d0cf3 1335
c2d936a4 1336 for (i = 0; i < bundle->n_slaves; i++) {
117d7249 1337 ofp_port_t ofp_port = u16_to_ofp(ntohs(((ovs_be16 *)(nab + 1))[i]));
c2d936a4 1338 ofpbuf_put(ofpacts, &ofp_port, sizeof ofp_port);
19b58f3c 1339 bundle = ofpacts->header;
c2d936a4 1340 }
f25d0cf3 1341
ce058104 1342 ofpact_finish_BUNDLE(ofpacts, &bundle);
c2d936a4
BP
1343 if (!error) {
1344 error = bundle_check(bundle, OFPP_MAX, NULL);
1345 }
1346 return error;
1347}
f25d0cf3 1348
c2d936a4 1349static enum ofperr
f3cd3ac7
JS
1350decode_NXAST_RAW_BUNDLE(const struct nx_action_bundle *nab,
1351 enum ofp_version ofp_version OVS_UNUSED,
1352 struct ofpbuf *out)
c2d936a4
BP
1353{
1354 return decode_bundle(false, nab, out);
1355}
f25d0cf3 1356
c2d936a4
BP
1357static enum ofperr
1358decode_NXAST_RAW_BUNDLE_LOAD(const struct nx_action_bundle *nab,
f3cd3ac7 1359 enum ofp_version ofp_version OVS_UNUSED,
c2d936a4
BP
1360 struct ofpbuf *out)
1361{
1362 return decode_bundle(true, nab, out);
1363}
c2d967a5 1364
c2d936a4
BP
1365static void
1366encode_BUNDLE(const struct ofpact_bundle *bundle,
1367 enum ofp_version ofp_version OVS_UNUSED,
1368 struct ofpbuf *out)
1369{
1370 int slaves_len = ROUND_UP(2 * bundle->n_slaves, OFP_ACTION_ALIGN);
1371 struct nx_action_bundle *nab;
1372 ovs_be16 *slaves;
1373 size_t i;
f25d0cf3 1374
c2d936a4
BP
1375 nab = (bundle->dst.field
1376 ? put_NXAST_BUNDLE_LOAD(out)
1377 : put_NXAST_BUNDLE(out));
1378 nab->len = htons(ntohs(nab->len) + slaves_len);
1379 nab->algorithm = htons(bundle->algorithm);
1380 nab->fields = htons(bundle->fields);
1381 nab->basis = htons(bundle->basis);
508a9338 1382 nab->slave_type = htonl(mf_nxm_header(MFF_IN_PORT));
c2d936a4
BP
1383 nab->n_slaves = htons(bundle->n_slaves);
1384 if (bundle->dst.field) {
1385 nab->ofs_nbits = nxm_encode_ofs_nbits(bundle->dst.ofs,
1386 bundle->dst.n_bits);
508a9338 1387 nab->dst = htonl(mf_nxm_header(bundle->dst.field->id));
c2d936a4 1388 }
f25d0cf3 1389
c2d936a4
BP
1390 slaves = ofpbuf_put_zeros(out, slaves_len);
1391 for (i = 0; i < bundle->n_slaves; i++) {
1392 slaves[i] = htons(ofp_to_u16(bundle->slaves[i]));
1393 }
1394}
b02475c5 1395
cab50449 1396static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
1397parse_BUNDLE(const char *arg, struct ofpbuf *ofpacts,
1398 enum ofputil_protocol *usable_protocols OVS_UNUSED)
1399{
1400 return bundle_parse(arg, ofpacts);
1401}
b02475c5 1402
cab50449 1403static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
1404parse_bundle_load(const char *arg, struct ofpbuf *ofpacts)
1405{
1406 return bundle_parse_load(arg, ofpacts);
1407}
097d4939 1408
c2d936a4
BP
1409static void
1410format_BUNDLE(const struct ofpact_bundle *a, struct ds *s)
1411{
1412 bundle_format(a, s);
1413}
1414\f
1415/* Set VLAN actions. */
097d4939 1416
c2d936a4
BP
1417static enum ofperr
1418decode_set_vlan_vid(uint16_t vid, bool push_vlan_if_needed, struct ofpbuf *out)
1419{
1420 if (vid & ~0xfff) {
1421 return OFPERR_OFPBAC_BAD_ARGUMENT;
1422 } else {
1423 struct ofpact_vlan_vid *vlan_vid = ofpact_put_SET_VLAN_VID(out);
1424 vlan_vid->vlan_vid = vid;
1425 vlan_vid->push_vlan_if_needed = push_vlan_if_needed;
1426 return 0;
1427 }
1428}
0f3f3c3d 1429
c2d936a4 1430static enum ofperr
f3cd3ac7
JS
1431decode_OFPAT_RAW10_SET_VLAN_VID(uint16_t vid,
1432 enum ofp_version ofp_version OVS_UNUSED,
1433 struct ofpbuf *out)
c2d936a4
BP
1434{
1435 return decode_set_vlan_vid(vid, true, out);
1436}
b676167a 1437
c2d936a4 1438static enum ofperr
f3cd3ac7
JS
1439decode_OFPAT_RAW11_SET_VLAN_VID(uint16_t vid,
1440 enum ofp_version ofp_version OVS_UNUSED,
1441 struct ofpbuf *out)
c2d936a4
BP
1442{
1443 return decode_set_vlan_vid(vid, false, out);
1444}
29089a54 1445
c2d936a4
BP
1446static void
1447encode_SET_VLAN_VID(const struct ofpact_vlan_vid *vlan_vid,
1448 enum ofp_version ofp_version, struct ofpbuf *out)
1449{
1450 uint16_t vid = vlan_vid->vlan_vid;
1451
1452 /* Push a VLAN tag, if none is present and this form of the action calls
1453 * for such a feature. */
1454 if (ofp_version > OFP10_VERSION
1455 && vlan_vid->push_vlan_if_needed
1456 && !vlan_vid->flow_has_vlan) {
1457 put_OFPAT11_PUSH_VLAN(out, htons(ETH_TYPE_VLAN_8021Q));
f25d0cf3
BP
1458 }
1459
c2d936a4
BP
1460 if (ofp_version == OFP10_VERSION) {
1461 put_OFPAT10_SET_VLAN_VID(out, vid);
1462 } else if (ofp_version == OFP11_VERSION) {
1463 put_OFPAT11_SET_VLAN_VID(out, vid);
1464 } else {
128684a6 1465 put_set_field(out, ofp_version, MFF_VLAN_VID, vid | OFPVID12_PRESENT);
c2d936a4 1466 }
f25d0cf3
BP
1467}
1468
cab50449 1469static char * OVS_WARN_UNUSED_RESULT
c2d936a4 1470parse_set_vlan_vid(char *arg, struct ofpbuf *ofpacts, bool push_vlan_if_needed)
d01c980f 1471{
ca287d20 1472 struct ofpact_vlan_vid *vlan_vid;
c2d936a4
BP
1473 uint16_t vid;
1474 char *error;
d01c980f 1475
c2d936a4 1476 error = str_to_u16(arg, "VLAN VID", &vid);
d01c980f
BP
1477 if (error) {
1478 return error;
1479 }
1480
c2d936a4
BP
1481 if (vid & ~VLAN_VID_MASK) {
1482 return xasprintf("%s: not a valid VLAN VID", arg);
d01c980f 1483 }
c2d936a4
BP
1484 vlan_vid = ofpact_put_SET_VLAN_VID(ofpacts);
1485 vlan_vid->vlan_vid = vid;
1486 vlan_vid->push_vlan_if_needed = push_vlan_if_needed;
1487 return NULL;
1488}
d01c980f 1489
cab50449 1490static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
1491parse_SET_VLAN_VID(char *arg, struct ofpbuf *ofpacts,
1492 enum ofputil_protocol *usable_protocols OVS_UNUSED)
1493{
1494 return parse_set_vlan_vid(arg, ofpacts, false);
d01c980f
BP
1495}
1496
c2d936a4
BP
1497static void
1498format_SET_VLAN_VID(const struct ofpact_vlan_vid *a, struct ds *s)
1499{
b1c5bf1f 1500 ds_put_format(s, "%s%s:%s%"PRIu16, colors.param,
c2d936a4 1501 a->push_vlan_if_needed ? "mod_vlan_vid" : "set_vlan_vid",
b1c5bf1f 1502 colors.end, a->vlan_vid);
c2d936a4
BP
1503}
1504\f
1505/* Set PCP actions. */
e3f8f887 1506
c2d936a4
BP
1507static enum ofperr
1508decode_set_vlan_pcp(uint8_t pcp, bool push_vlan_if_needed, struct ofpbuf *out)
f25d0cf3 1509{
c2d936a4
BP
1510 if (pcp & ~7) {
1511 return OFPERR_OFPBAC_BAD_ARGUMENT;
1512 } else {
1513 struct ofpact_vlan_pcp *vlan_pcp = ofpact_put_SET_VLAN_PCP(out);
1514 vlan_pcp->vlan_pcp = pcp;
1515 vlan_pcp->push_vlan_if_needed = push_vlan_if_needed;
1516 return 0;
1517 }
f25d0cf3
BP
1518}
1519
c2d936a4 1520static enum ofperr
f3cd3ac7
JS
1521decode_OFPAT_RAW10_SET_VLAN_PCP(uint8_t pcp,
1522 enum ofp_version ofp_version OVS_UNUSED,
1523 struct ofpbuf *out)
f25d0cf3 1524{
c2d936a4 1525 return decode_set_vlan_pcp(pcp, true, out);
f25d0cf3
BP
1526}
1527
c2d936a4 1528static enum ofperr
f3cd3ac7
JS
1529decode_OFPAT_RAW11_SET_VLAN_PCP(uint8_t pcp,
1530 enum ofp_version ofp_version OVS_UNUSED,
1531 struct ofpbuf *out)
c2d936a4
BP
1532{
1533 return decode_set_vlan_pcp(pcp, false, out);
1534}
f25d0cf3 1535
699dddf1 1536static void
c2d936a4
BP
1537encode_SET_VLAN_PCP(const struct ofpact_vlan_pcp *vlan_pcp,
1538 enum ofp_version ofp_version, struct ofpbuf *out)
699dddf1 1539{
c2d936a4
BP
1540 uint8_t pcp = vlan_pcp->vlan_pcp;
1541
1542 /* Push a VLAN tag, if none is present and this form of the action calls
1543 * for such a feature. */
1544 if (ofp_version > OFP10_VERSION
1545 && vlan_pcp->push_vlan_if_needed
1546 && !vlan_pcp->flow_has_vlan) {
1547 put_OFPAT11_PUSH_VLAN(out, htons(ETH_TYPE_VLAN_8021Q));
1548 }
699dddf1 1549
c2d936a4
BP
1550 if (ofp_version == OFP10_VERSION) {
1551 put_OFPAT10_SET_VLAN_PCP(out, pcp);
1552 } else if (ofp_version == OFP11_VERSION) {
1553 put_OFPAT11_SET_VLAN_PCP(out, pcp);
1554 } else {
128684a6 1555 put_set_field(out, ofp_version, MFF_VLAN_PCP, pcp);
699dddf1
BP
1556 }
1557}
1558
cab50449 1559static char * OVS_WARN_UNUSED_RESULT
c2d936a4 1560parse_set_vlan_pcp(char *arg, struct ofpbuf *ofpacts, bool push_vlan_if_needed)
f25d0cf3 1561{
c2d936a4
BP
1562 struct ofpact_vlan_pcp *vlan_pcp;
1563 uint8_t pcp;
1564 char *error;
e3f8f887 1565
c2d936a4
BP
1566 error = str_to_u8(arg, "VLAN PCP", &pcp);
1567 if (error) {
699dddf1 1568 return error;
f25d0cf3
BP
1569 }
1570
c2d936a4
BP
1571 if (pcp & ~7) {
1572 return xasprintf("%s: not a valid VLAN PCP", arg);
1573 }
1574 vlan_pcp = ofpact_put_SET_VLAN_PCP(ofpacts);
1575 vlan_pcp->vlan_pcp = pcp;
1576 vlan_pcp->push_vlan_if_needed = push_vlan_if_needed;
1577 return NULL;
1578}
1579
cab50449 1580static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
1581parse_SET_VLAN_PCP(char *arg, struct ofpbuf *ofpacts,
1582 enum ofputil_protocol *usable_protocols OVS_UNUSED)
1583{
1584 return parse_set_vlan_pcp(arg, ofpacts, false);
1585}
1586
1587static void
1588format_SET_VLAN_PCP(const struct ofpact_vlan_pcp *a, struct ds *s)
1589{
b1c5bf1f 1590 ds_put_format(s, "%s%s:%s%"PRIu8, colors.param,
c2d936a4 1591 a->push_vlan_if_needed ? "mod_vlan_pcp" : "set_vlan_pcp",
b1c5bf1f 1592 colors.end, a->vlan_pcp);
c2d936a4
BP
1593}
1594\f
1595/* Strip VLAN actions. */
1596
1597static enum ofperr
1598decode_OFPAT_RAW10_STRIP_VLAN(struct ofpbuf *out)
1599{
1600 ofpact_put_STRIP_VLAN(out)->ofpact.raw = OFPAT_RAW10_STRIP_VLAN;
f25d0cf3
BP
1601 return 0;
1602}
1603
8f2cded4 1604static enum ofperr
c2d936a4 1605decode_OFPAT_RAW11_POP_VLAN(struct ofpbuf *out)
8f2cded4 1606{
c2d936a4
BP
1607 ofpact_put_STRIP_VLAN(out)->ofpact.raw = OFPAT_RAW11_POP_VLAN;
1608 return 0;
1609}
f25d0cf3 1610
c2d936a4
BP
1611static void
1612encode_STRIP_VLAN(const struct ofpact_null *null OVS_UNUSED,
1613 enum ofp_version ofp_version, struct ofpbuf *out)
1614{
1615 if (ofp_version == OFP10_VERSION) {
1616 put_OFPAT10_STRIP_VLAN(out);
1617 } else {
1618 put_OFPAT11_POP_VLAN(out);
1619 }
1620}
f25d0cf3 1621
cab50449 1622static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
1623parse_STRIP_VLAN(char *arg OVS_UNUSED, struct ofpbuf *ofpacts,
1624 enum ofputil_protocol *usable_protocols OVS_UNUSED)
1625{
1626 ofpact_put_STRIP_VLAN(ofpacts)->ofpact.raw = OFPAT_RAW10_STRIP_VLAN;
1627 return NULL;
1628}
1629
cab50449 1630static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
1631parse_pop_vlan(struct ofpbuf *ofpacts)
1632{
1633 ofpact_put_STRIP_VLAN(ofpacts)->ofpact.raw = OFPAT_RAW11_POP_VLAN;
1634 return NULL;
1635}
1636
1637static void
1638format_STRIP_VLAN(const struct ofpact_null *a, struct ds *s)
1639{
b1c5bf1f
QM
1640 ds_put_format(s, (a->ofpact.raw == OFPAT_RAW11_POP_VLAN
1641 ? "%spop_vlan%s"
1642 : "%sstrip_vlan%s"),
1643 colors.value, colors.end);
c2d936a4
BP
1644}
1645\f
1646/* Push VLAN action. */
1647
1648static enum ofperr
f3cd3ac7
JS
1649decode_OFPAT_RAW11_PUSH_VLAN(ovs_be16 eth_type,
1650 enum ofp_version ofp_version OVS_UNUSED,
1651 struct ofpbuf *out)
c2d936a4
BP
1652{
1653 if (eth_type != htons(ETH_TYPE_VLAN_8021Q)) {
1654 /* XXX 802.1AD(QinQ) isn't supported at the moment */
1655 return OFPERR_OFPBAC_BAD_ARGUMENT;
f25d0cf3 1656 }
c2d936a4
BP
1657 ofpact_put_PUSH_VLAN(out);
1658 return 0;
1659}
f25d0cf3 1660
c2d936a4
BP
1661static void
1662encode_PUSH_VLAN(const struct ofpact_null *null OVS_UNUSED,
1663 enum ofp_version ofp_version, struct ofpbuf *out)
1664{
1665 if (ofp_version == OFP10_VERSION) {
1666 /* PUSH is a side effect of a SET_VLAN_VID/PCP, which should
1667 * follow this action. */
1668 } else {
1669 /* XXX ETH_TYPE_VLAN_8021AD case */
1670 put_OFPAT11_PUSH_VLAN(out, htons(ETH_TYPE_VLAN_8021Q));
f25d0cf3 1671 }
c2d936a4 1672}
f25d0cf3 1673
cab50449 1674static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
1675parse_PUSH_VLAN(char *arg, struct ofpbuf *ofpacts,
1676 enum ofputil_protocol *usable_protocols OVS_UNUSED)
1677{
1678 uint16_t ethertype;
1679 char *error;
1680
1681 *usable_protocols &= OFPUTIL_P_OF11_UP;
1682 error = str_to_u16(arg, "ethertype", &ethertype);
4cceacb9 1683 if (error) {
4cceacb9
JS
1684 return error;
1685 }
1686
c2d936a4
BP
1687 if (ethertype != ETH_TYPE_VLAN_8021Q) {
1688 /* XXX ETH_TYPE_VLAN_8021AD case isn't supported */
1689 return xasprintf("%s: not a valid VLAN ethertype", arg);
f25d0cf3 1690 }
c2d936a4
BP
1691
1692 ofpact_put_PUSH_VLAN(ofpacts);
1693 return NULL;
d01c980f
BP
1694}
1695
c2d936a4
BP
1696static void
1697format_PUSH_VLAN(const struct ofpact_null *a OVS_UNUSED, struct ds *s)
8f2cded4 1698{
c2d936a4 1699 /* XXX 802.1AD case*/
b1c5bf1f
QM
1700 ds_put_format(s, "%spush_vlan:%s%#"PRIx16,
1701 colors.param, colors.end, ETH_TYPE_VLAN_8021Q);
8f2cded4 1702}
d01c980f 1703\f
c2d936a4
BP
1704/* Action structure for OFPAT10_SET_DL_SRC/DST and OFPAT11_SET_DL_SRC/DST. */
1705struct ofp_action_dl_addr {
1706 ovs_be16 type; /* Type. */
1707 ovs_be16 len; /* Length is 16. */
74ff3298 1708 struct eth_addr dl_addr; /* Ethernet address. */
c2d936a4
BP
1709 uint8_t pad[6];
1710};
1711OFP_ASSERT(sizeof(struct ofp_action_dl_addr) == 16);
d01c980f 1712
d01c980f 1713static enum ofperr
c2d936a4 1714decode_OFPAT_RAW_SET_DL_SRC(const struct ofp_action_dl_addr *a,
f3cd3ac7 1715 enum ofp_version ofp_version OVS_UNUSED,
c2d936a4 1716 struct ofpbuf *out)
d01c980f 1717{
74ff3298 1718 ofpact_put_SET_ETH_SRC(out)->mac = a->dl_addr;
c2d936a4
BP
1719 return 0;
1720}
3ddcaf2d 1721
c2d936a4
BP
1722static enum ofperr
1723decode_OFPAT_RAW_SET_DL_DST(const struct ofp_action_dl_addr *a,
f3cd3ac7 1724 enum ofp_version ofp_version OVS_UNUSED,
c2d936a4
BP
1725 struct ofpbuf *out)
1726{
74ff3298 1727 ofpact_put_SET_ETH_DST(out)->mac = a->dl_addr;
c2d936a4
BP
1728 return 0;
1729}
d01c980f 1730
c2d936a4
BP
1731static void
1732encode_SET_ETH_addr(const struct ofpact_mac *mac, enum ofp_version ofp_version,
1733 enum ofp_raw_action_type raw, enum mf_field_id field,
1734 struct ofpbuf *out)
1735{
c2d936a4
BP
1736 if (ofp_version < OFP12_VERSION) {
1737 struct ofp_action_dl_addr *oada;
1738
1739 oada = ofpact_put_raw(out, ofp_version, raw, 0);
74ff3298 1740 oada->dl_addr = mac->mac;
c2d936a4 1741 } else {
128684a6 1742 put_set_field(out, ofp_version, field, eth_addr_to_uint64(mac->mac));
d01c980f
BP
1743 }
1744}
1745
c2d936a4
BP
1746static void
1747encode_SET_ETH_SRC(const struct ofpact_mac *mac, enum ofp_version ofp_version,
1748 struct ofpbuf *out)
b2dd70be 1749{
c2d936a4
BP
1750 encode_SET_ETH_addr(mac, ofp_version, OFPAT_RAW_SET_DL_SRC, MFF_ETH_SRC,
1751 out);
b2dd70be 1752
c2d936a4 1753}
b2dd70be 1754
c2d936a4
BP
1755static void
1756encode_SET_ETH_DST(const struct ofpact_mac *mac,
1757 enum ofp_version ofp_version,
1758 struct ofpbuf *out)
1759{
1760 encode_SET_ETH_addr(mac, ofp_version, OFPAT_RAW_SET_DL_DST, MFF_ETH_DST,
1761 out);
b2dd70be 1762
c2d936a4 1763}
b2dd70be 1764
cab50449 1765static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
1766parse_SET_ETH_SRC(char *arg, struct ofpbuf *ofpacts,
1767 enum ofputil_protocol *usable_protocols OVS_UNUSED)
1768{
74ff3298 1769 return str_to_mac(arg, &ofpact_put_SET_ETH_SRC(ofpacts)->mac);
c2d936a4
BP
1770}
1771
cab50449 1772static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
1773parse_SET_ETH_DST(char *arg, struct ofpbuf *ofpacts,
1774 enum ofputil_protocol *usable_protocols OVS_UNUSED)
1775{
74ff3298 1776 return str_to_mac(arg, &ofpact_put_SET_ETH_DST(ofpacts)->mac);
b2dd70be
JR
1777}
1778
1779static void
c2d936a4 1780format_SET_ETH_SRC(const struct ofpact_mac *a, struct ds *s)
b2dd70be 1781{
b1c5bf1f
QM
1782 ds_put_format(s, "%smod_dl_src:%s"ETH_ADDR_FMT,
1783 colors.param, colors.end, ETH_ADDR_ARGS(a->mac));
c2d936a4 1784}
b2dd70be 1785
c2d936a4
BP
1786static void
1787format_SET_ETH_DST(const struct ofpact_mac *a, struct ds *s)
1788{
b1c5bf1f
QM
1789 ds_put_format(s, "%smod_dl_dst:%s"ETH_ADDR_FMT,
1790 colors.param, colors.end, ETH_ADDR_ARGS(a->mac));
c2d936a4
BP
1791}
1792\f
1793/* Set IPv4 address actions. */
b2dd70be 1794
c2d936a4 1795static enum ofperr
f3cd3ac7
JS
1796decode_OFPAT_RAW_SET_NW_SRC(ovs_be32 ipv4,
1797 enum ofp_version ofp_version OVS_UNUSED,
1798 struct ofpbuf *out)
c2d936a4
BP
1799{
1800 ofpact_put_SET_IPV4_SRC(out)->ipv4 = ipv4;
1801 return 0;
b2dd70be
JR
1802}
1803
c2d936a4 1804static enum ofperr
f3cd3ac7
JS
1805decode_OFPAT_RAW_SET_NW_DST(ovs_be32 ipv4,
1806 enum ofp_version ofp_version OVS_UNUSED,
1807 struct ofpbuf *out)
b2dd70be 1808{
c2d936a4
BP
1809 ofpact_put_SET_IPV4_DST(out)->ipv4 = ipv4;
1810 return 0;
1811}
b2dd70be 1812
c2d936a4
BP
1813static void
1814encode_SET_IPV4_addr(const struct ofpact_ipv4 *ipv4,
1815 enum ofp_version ofp_version,
1816 enum ofp_raw_action_type raw, enum mf_field_id field,
1817 struct ofpbuf *out)
1818{
1819 ovs_be32 addr = ipv4->ipv4;
1820 if (ofp_version < OFP12_VERSION) {
1821 ofpact_put_raw(out, ofp_version, raw, ntohl(addr));
b2dd70be 1822 } else {
128684a6 1823 put_set_field(out, ofp_version, field, ntohl(addr));
b2dd70be
JR
1824 }
1825}
1826
a6fd70bb 1827static void
c2d936a4
BP
1828encode_SET_IPV4_SRC(const struct ofpact_ipv4 *ipv4,
1829 enum ofp_version ofp_version, struct ofpbuf *out)
a6fd70bb 1830{
c2d936a4
BP
1831 encode_SET_IPV4_addr(ipv4, ofp_version, OFPAT_RAW_SET_NW_SRC, MFF_IPV4_SRC,
1832 out);
1833}
a6fd70bb 1834
c2d936a4
BP
1835static void
1836encode_SET_IPV4_DST(const struct ofpact_ipv4 *ipv4,
1837 enum ofp_version ofp_version, struct ofpbuf *out)
1838{
1839 encode_SET_IPV4_addr(ipv4, ofp_version, OFPAT_RAW_SET_NW_DST, MFF_IPV4_DST,
1840 out);
1841}
a6fd70bb 1842
cab50449 1843static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
1844parse_SET_IPV4_SRC(char *arg, struct ofpbuf *ofpacts,
1845 enum ofputil_protocol *usable_protocols OVS_UNUSED)
1846{
1847 return str_to_ip(arg, &ofpact_put_SET_IPV4_SRC(ofpacts)->ipv4);
1848}
a6fd70bb 1849
cab50449 1850static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
1851parse_SET_IPV4_DST(char *arg, struct ofpbuf *ofpacts,
1852 enum ofputil_protocol *usable_protocols OVS_UNUSED)
1853{
1854 return str_to_ip(arg, &ofpact_put_SET_IPV4_DST(ofpacts)->ipv4);
1855}
a6fd70bb 1856
c2d936a4
BP
1857static void
1858format_SET_IPV4_SRC(const struct ofpact_ipv4 *a, struct ds *s)
1859{
b1c5bf1f
QM
1860 ds_put_format(s, "%smod_nw_src:%s"IP_FMT,
1861 colors.param, colors.end, IP_ARGS(a->ipv4));
c2d936a4 1862}
097d4939 1863
c2d936a4
BP
1864static void
1865format_SET_IPV4_DST(const struct ofpact_ipv4 *a, struct ds *s)
1866{
b1c5bf1f
QM
1867 ds_put_format(s, "%smod_nw_dst:%s"IP_FMT,
1868 colors.param, colors.end, IP_ARGS(a->ipv4));
c2d936a4
BP
1869}
1870\f
1871/* Set IPv4/v6 TOS actions. */
097d4939 1872
c2d936a4 1873static enum ofperr
f3cd3ac7
JS
1874decode_OFPAT_RAW_SET_NW_TOS(uint8_t dscp,
1875 enum ofp_version ofp_version OVS_UNUSED,
1876 struct ofpbuf *out)
c2d936a4
BP
1877{
1878 if (dscp & ~IP_DSCP_MASK) {
1879 return OFPERR_OFPBAC_BAD_ARGUMENT;
1880 } else {
1881 ofpact_put_SET_IP_DSCP(out)->dscp = dscp;
1882 return 0;
a6fd70bb
JR
1883 }
1884}
1885
a6fd70bb 1886static void
c2d936a4
BP
1887encode_SET_IP_DSCP(const struct ofpact_dscp *dscp,
1888 enum ofp_version ofp_version, struct ofpbuf *out)
a6fd70bb 1889{
c2d936a4
BP
1890 if (ofp_version < OFP12_VERSION) {
1891 put_OFPAT_SET_NW_TOS(out, ofp_version, dscp->dscp);
1892 } else {
128684a6 1893 put_set_field(out, ofp_version, MFF_IP_DSCP_SHIFTED, dscp->dscp >> 2);
c2d936a4
BP
1894 }
1895}
a6fd70bb 1896
cab50449 1897static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
1898parse_SET_IP_DSCP(char *arg, struct ofpbuf *ofpacts,
1899 enum ofputil_protocol *usable_protocols OVS_UNUSED)
1900{
1901 uint8_t tos;
1902 char *error;
a6fd70bb 1903
c2d936a4
BP
1904 error = str_to_u8(arg, "TOS", &tos);
1905 if (error) {
1906 return error;
1907 }
a6fd70bb 1908
c2d936a4
BP
1909 if (tos & ~IP_DSCP_MASK) {
1910 return xasprintf("%s: not a valid TOS", arg);
a6fd70bb 1911 }
c2d936a4
BP
1912 ofpact_put_SET_IP_DSCP(ofpacts)->dscp = tos;
1913 return NULL;
a6fd70bb
JR
1914}
1915
b2dd70be 1916static void
c2d936a4 1917format_SET_IP_DSCP(const struct ofpact_dscp *a, struct ds *s)
b2dd70be 1918{
b1c5bf1f 1919 ds_put_format(s, "%smod_nw_tos:%s%d", colors.param, colors.end, a->dscp);
c2d936a4
BP
1920}
1921\f
1922/* Set IPv4/v6 ECN actions. */
b2dd70be 1923
c2d936a4 1924static enum ofperr
f3cd3ac7
JS
1925decode_OFPAT_RAW11_SET_NW_ECN(uint8_t ecn,
1926 enum ofp_version ofp_version OVS_UNUSED,
1927 struct ofpbuf *out)
c2d936a4
BP
1928{
1929 if (ecn & ~IP_ECN_MASK) {
1930 return OFPERR_OFPBAC_BAD_ARGUMENT;
b2dd70be 1931 } else {
c2d936a4
BP
1932 ofpact_put_SET_IP_ECN(out)->ecn = ecn;
1933 return 0;
b2dd70be
JR
1934 }
1935}
1936
c2d936a4
BP
1937static void
1938encode_SET_IP_ECN(const struct ofpact_ecn *ip_ecn,
1939 enum ofp_version ofp_version, struct ofpbuf *out)
d01c980f 1940{
c2d936a4
BP
1941 uint8_t ecn = ip_ecn->ecn;
1942 if (ofp_version == OFP10_VERSION) {
4b684612
BP
1943 struct mf_subfield dst = { .field = mf_from_id(MFF_IP_ECN),
1944 .ofs = 0, .n_bits = 2 };
1945 put_reg_load(out, &dst, ecn);
c2d936a4
BP
1946 } else if (ofp_version == OFP11_VERSION) {
1947 put_OFPAT11_SET_NW_ECN(out, ecn);
1948 } else {
128684a6 1949 put_set_field(out, ofp_version, MFF_IP_ECN, ecn);
c2d936a4
BP
1950 }
1951}
d01c980f 1952
cab50449 1953static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
1954parse_SET_IP_ECN(char *arg, struct ofpbuf *ofpacts,
1955 enum ofputil_protocol *usable_protocols OVS_UNUSED)
1956{
1957 uint8_t ecn;
1958 char *error;
d01c980f 1959
c2d936a4 1960 error = str_to_u8(arg, "ECN", &ecn);
d01c980f
BP
1961 if (error) {
1962 return error;
1963 }
1964
c2d936a4
BP
1965 if (ecn & ~IP_ECN_MASK) {
1966 return xasprintf("%s: not a valid ECN", arg);
1967 }
1968 ofpact_put_SET_IP_ECN(ofpacts)->ecn = ecn;
1969 return NULL;
d01c980f
BP
1970}
1971
c2d936a4
BP
1972static void
1973format_SET_IP_ECN(const struct ofpact_ecn *a, struct ds *s)
1974{
b1c5bf1f
QM
1975 ds_put_format(s, "%smod_nw_ecn:%s%d",
1976 colors.param, colors.end, a->ecn);
c2d936a4
BP
1977}
1978\f
1979/* Set IPv4/v6 TTL actions. */
1980
d01c980f 1981static enum ofperr
f3cd3ac7
JS
1982decode_OFPAT_RAW11_SET_NW_TTL(uint8_t ttl,
1983 enum ofp_version ofp_version OVS_UNUSED,
1984 struct ofpbuf *out)
d01c980f 1985{
c2d936a4
BP
1986 ofpact_put_SET_IP_TTL(out)->ttl = ttl;
1987 return 0;
1988}
1989
1990static void
1991encode_SET_IP_TTL(const struct ofpact_ip_ttl *ttl,
1992 enum ofp_version ofp_version, struct ofpbuf *out)
1993{
1994 if (ofp_version >= OFP11_VERSION) {
1995 put_OFPAT11_SET_NW_TTL(out, ttl->ttl);
1996 } else {
56a91749
BP
1997 struct mf_subfield dst = { .field = mf_from_id(MFF_IP_TTL),
1998 .ofs = 0, .n_bits = 8 };
1999 put_reg_load(out, &dst, ttl->ttl);
c2d936a4
BP
2000 }
2001}
2002
cab50449 2003static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
2004parse_SET_IP_TTL(char *arg, struct ofpbuf *ofpacts,
2005 enum ofputil_protocol *usable_protocols OVS_UNUSED)
2006{
2007 uint8_t ttl;
2008 char *error;
d01c980f 2009
c2d936a4 2010 error = str_to_u8(arg, "TTL", &ttl);
d01c980f
BP
2011 if (error) {
2012 return error;
2013 }
2014
c2d936a4
BP
2015 ofpact_put_SET_IP_TTL(ofpacts)->ttl = ttl;
2016 return NULL;
2017}
d01c980f 2018
c2d936a4
BP
2019static void
2020format_SET_IP_TTL(const struct ofpact_ip_ttl *a, struct ds *s)
2021{
b1c5bf1f 2022 ds_put_format(s, "%smod_nw_ttl:%s%d", colors.param, colors.end, a->ttl);
c2d936a4
BP
2023}
2024\f
2025/* Set TCP/UDP/SCTP port actions. */
d01c980f 2026
c2d936a4 2027static enum ofperr
f3cd3ac7
JS
2028decode_OFPAT_RAW_SET_TP_SRC(ovs_be16 port,
2029 enum ofp_version ofp_version OVS_UNUSED,
2030 struct ofpbuf *out)
c2d936a4
BP
2031{
2032 ofpact_put_SET_L4_SRC_PORT(out)->port = ntohs(port);
2033 return 0;
2034}
d01c980f 2035
c2d936a4 2036static enum ofperr
f3cd3ac7
JS
2037decode_OFPAT_RAW_SET_TP_DST(ovs_be16 port,
2038 enum ofp_version ofp_version OVS_UNUSED,
2039 struct ofpbuf *out)
c2d936a4
BP
2040{
2041 ofpact_put_SET_L4_DST_PORT(out)->port = ntohs(port);
2042 return 0;
2043}
d01c980f 2044
c2d936a4
BP
2045static void
2046encode_SET_L4_port(const struct ofpact_l4_port *l4_port,
2047 enum ofp_version ofp_version, enum ofp_raw_action_type raw,
2048 enum mf_field_id field, struct ofpbuf *out)
2049{
2050 uint16_t port = l4_port->port;
3e34fbdd 2051
c2d936a4 2052 if (ofp_version >= OFP12_VERSION && field != MFF_N_IDS) {
128684a6 2053 put_set_field(out, ofp_version, field, port);
c2d936a4
BP
2054 } else {
2055 ofpact_put_raw(out, ofp_version, raw, port);
2056 }
2057}
8e61c110 2058
c2d936a4
BP
2059static void
2060encode_SET_L4_SRC_PORT(const struct ofpact_l4_port *l4_port,
2061 enum ofp_version ofp_version, struct ofpbuf *out)
2062{
2063 uint8_t proto = l4_port->flow_ip_proto;
2064 enum mf_field_id field = (proto == IPPROTO_TCP ? MFF_TCP_SRC
2065 : proto == IPPROTO_UDP ? MFF_UDP_SRC
2066 : proto == IPPROTO_SCTP ? MFF_SCTP_SRC
2067 : MFF_N_IDS);
276c4e7a 2068
c2d936a4
BP
2069 encode_SET_L4_port(l4_port, ofp_version, OFPAT_RAW_SET_TP_SRC, field, out);
2070}
d01c980f 2071
c2d936a4
BP
2072static void
2073encode_SET_L4_DST_PORT(const struct ofpact_l4_port *l4_port,
2074 enum ofp_version ofp_version,
2075 struct ofpbuf *out)
2076{
2077 uint8_t proto = l4_port->flow_ip_proto;
2078 enum mf_field_id field = (proto == IPPROTO_TCP ? MFF_TCP_DST
2079 : proto == IPPROTO_UDP ? MFF_UDP_DST
2080 : proto == IPPROTO_SCTP ? MFF_SCTP_DST
2081 : MFF_N_IDS);
d01c980f 2082
c2d936a4
BP
2083 encode_SET_L4_port(l4_port, ofp_version, OFPAT_RAW_SET_TP_DST, field, out);
2084}
7bcb1506 2085
cab50449 2086static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
2087parse_SET_L4_SRC_PORT(char *arg, struct ofpbuf *ofpacts,
2088 enum ofputil_protocol *usable_protocols OVS_UNUSED)
2089{
2090 return str_to_u16(arg, "source port",
2091 &ofpact_put_SET_L4_SRC_PORT(ofpacts)->port);
2092}
d01c980f 2093
cab50449 2094static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
2095parse_SET_L4_DST_PORT(char *arg, struct ofpbuf *ofpacts,
2096 enum ofputil_protocol *usable_protocols OVS_UNUSED)
2097{
2098 return str_to_u16(arg, "destination port",
2099 &ofpact_put_SET_L4_DST_PORT(ofpacts)->port);
2100}
d01c980f 2101
c2d936a4
BP
2102static void
2103format_SET_L4_SRC_PORT(const struct ofpact_l4_port *a, struct ds *s)
2104{
b1c5bf1f 2105 ds_put_format(s, "%smod_tp_src:%s%d", colors.param, colors.end, a->port);
c2d936a4 2106}
d01c980f 2107
c2d936a4
BP
2108static void
2109format_SET_L4_DST_PORT(const struct ofpact_l4_port *a, struct ds *s)
2110{
b1c5bf1f 2111 ds_put_format(s, "%smod_tp_dst:%s%d", colors.param, colors.end, a->port);
c2d936a4
BP
2112}
2113\f
73178f20
BP
2114/* Action structure for OFPAT_COPY_FIELD. */
2115struct ofp15_action_copy_field {
2116 ovs_be16 type; /* OFPAT_COPY_FIELD. */
2117 ovs_be16 len; /* Length is padded to 64 bits. */
2118 ovs_be16 n_bits; /* Number of bits to copy. */
2119 ovs_be16 src_offset; /* Starting bit offset in source. */
2120 ovs_be16 dst_offset; /* Starting bit offset in destination. */
650763d8 2121 uint8_t pad[2];
f13cdd73
BP
2122 /* Followed by:
2123 * - OXM header for source field.
2124 * - OXM header for destination field.
2125 * - Padding with 0-bytes to a multiple of 8 bytes.
650763d8
BP
2126 * The "pad2" member is the beginning of the above. */
2127 uint8_t pad2[4];
73178f20 2128};
f13cdd73 2129OFP_ASSERT(sizeof(struct ofp15_action_copy_field) == 16);
73178f20 2130
914624f8
BP
2131/* Action structure for OpenFlow 1.3 extension copy-field action.. */
2132struct onf_action_copy_field {
2133 ovs_be16 type; /* OFPAT_EXPERIMENTER. */
2134 ovs_be16 len; /* Length is padded to 64 bits. */
2135 ovs_be32 experimenter; /* ONF_VENDOR_ID. */
2136 ovs_be16 exp_type; /* 3200. */
2137 uint8_t pad[2]; /* Not used. */
2138 ovs_be16 n_bits; /* Number of bits to copy. */
2139 ovs_be16 src_offset; /* Starting bit offset in source. */
2140 ovs_be16 dst_offset; /* Starting bit offset in destination. */
2141 uint8_t pad2[2]; /* Not used. */
2142 /* Followed by:
2143 * - OXM header for source field.
2144 * - OXM header for destination field.
2145 * - Padding with 0-bytes (either 0 or 4 of them) to a multiple of 8 bytes.
2146 * The "pad3" member is the beginning of the above. */
2147 uint8_t pad3[4]; /* Not used. */
2148};
2149OFP_ASSERT(sizeof(struct onf_action_copy_field) == 24);
2150
c2d936a4
BP
2151/* Action structure for NXAST_REG_MOVE.
2152 *
2153 * Copies src[src_ofs:src_ofs+n_bits] to dst[dst_ofs:dst_ofs+n_bits], where
2154 * a[b:c] denotes the bits within 'a' numbered 'b' through 'c' (not including
2155 * bit 'c'). Bit numbering starts at 0 for the least-significant bit, 1 for
2156 * the next most significant bit, and so on.
2157 *
2158 * 'src' and 'dst' are nxm_header values with nxm_hasmask=0. (It doesn't make
2159 * sense to use nxm_hasmask=1 because the action does not do any kind of
2160 * matching; it uses the actual value of a field.)
2161 *
2162 * The following nxm_header values are potentially acceptable as 'src':
2163 *
2164 * - NXM_OF_IN_PORT
2165 * - NXM_OF_ETH_DST
2166 * - NXM_OF_ETH_SRC
2167 * - NXM_OF_ETH_TYPE
2168 * - NXM_OF_VLAN_TCI
2169 * - NXM_OF_IP_TOS
2170 * - NXM_OF_IP_PROTO
2171 * - NXM_OF_IP_SRC
2172 * - NXM_OF_IP_DST
2173 * - NXM_OF_TCP_SRC
2174 * - NXM_OF_TCP_DST
2175 * - NXM_OF_UDP_SRC
2176 * - NXM_OF_UDP_DST
2177 * - NXM_OF_ICMP_TYPE
2178 * - NXM_OF_ICMP_CODE
2179 * - NXM_OF_ARP_OP
2180 * - NXM_OF_ARP_SPA
2181 * - NXM_OF_ARP_TPA
2182 * - NXM_NX_TUN_ID
2183 * - NXM_NX_ARP_SHA
2184 * - NXM_NX_ARP_THA
2185 * - NXM_NX_ICMPV6_TYPE
2186 * - NXM_NX_ICMPV6_CODE
2187 * - NXM_NX_ND_SLL
2188 * - NXM_NX_ND_TLL
2189 * - NXM_NX_REG(idx) for idx in the switch's accepted range.
2190 * - NXM_NX_PKT_MARK
2191 * - NXM_NX_TUN_IPV4_SRC
2192 * - NXM_NX_TUN_IPV4_DST
2193 *
2194 * The following nxm_header values are potentially acceptable as 'dst':
2195 *
2196 * - NXM_OF_ETH_DST
2197 * - NXM_OF_ETH_SRC
2198 * - NXM_OF_IP_TOS
2199 * - NXM_OF_IP_SRC
2200 * - NXM_OF_IP_DST
2201 * - NXM_OF_TCP_SRC
2202 * - NXM_OF_TCP_DST
2203 * - NXM_OF_UDP_SRC
2204 * - NXM_OF_UDP_DST
f6ecf944
JP
2205 * - NXM_OF_ICMP_TYPE
2206 * - NXM_OF_ICMP_CODE
2207 * - NXM_NX_ICMPV6_TYPE
2208 * - NXM_NX_ICMPV6_CODE
c2d936a4
BP
2209 * - NXM_NX_ARP_SHA
2210 * - NXM_NX_ARP_THA
2211 * - NXM_OF_ARP_OP
2212 * - NXM_OF_ARP_SPA
2213 * - NXM_OF_ARP_TPA
2214 * Modifying any of the above fields changes the corresponding packet
2215 * header.
2216 *
2217 * - NXM_OF_IN_PORT
2218 *
2219 * - NXM_NX_REG(idx) for idx in the switch's accepted range.
2220 *
2221 * - NXM_NX_PKT_MARK
2222 *
2223 * - NXM_OF_VLAN_TCI. Modifying this field's value has side effects on the
2224 * packet's 802.1Q header. Setting a value with CFI=0 removes the 802.1Q
2225 * header (if any), ignoring the other bits. Setting a value with CFI=1
2226 * adds or modifies the 802.1Q header appropriately, setting the TCI field
2227 * to the field's new value (with the CFI bit masked out).
2228 *
2229 * - NXM_NX_TUN_ID, NXM_NX_TUN_IPV4_SRC, NXM_NX_TUN_IPV4_DST. Modifying
2230 * any of these values modifies the corresponding tunnel header field used
2231 * for the packet's next tunnel encapsulation, if allowed by the
2232 * configuration of the output tunnel port.
2233 *
2234 * A given nxm_header value may be used as 'src' or 'dst' only on a flow whose
2235 * nx_match satisfies its prerequisites. For example, NXM_OF_IP_TOS may be
2236 * used only if the flow's nx_match includes an nxm_entry that specifies
2237 * nxm_type=NXM_OF_ETH_TYPE, nxm_hasmask=0, and nxm_value=0x0800.
2238 *
2239 * The switch will reject actions for which src_ofs+n_bits is greater than the
2240 * width of 'src' or dst_ofs+n_bits is greater than the width of 'dst' with
2241 * error type OFPET_BAD_ACTION, code OFPBAC_BAD_ARGUMENT.
2242 *
2243 * This action behaves properly when 'src' overlaps with 'dst', that is, it
2244 * behaves as if 'src' were copied out to a temporary buffer, then the
2245 * temporary buffer copied to 'dst'.
2246 */
2247struct nx_action_reg_move {
2248 ovs_be16 type; /* OFPAT_VENDOR. */
2249 ovs_be16 len; /* Length is 24. */
2250 ovs_be32 vendor; /* NX_VENDOR_ID. */
2251 ovs_be16 subtype; /* NXAST_REG_MOVE. */
2252 ovs_be16 n_bits; /* Number of bits. */
2253 ovs_be16 src_ofs; /* Starting bit offset in source. */
2254 ovs_be16 dst_ofs; /* Starting bit offset in destination. */
bad8a439
BP
2255 /* Followed by:
2256 * - OXM/NXM header for source field (4 or 8 bytes).
2257 * - OXM/NXM header for destination field (4 or 8 bytes).
2258 * - Padding with 0-bytes to a multiple of 8 bytes, if necessary. */
c2d936a4 2259};
bad8a439 2260OFP_ASSERT(sizeof(struct nx_action_reg_move) == 16);
ff14eb7a 2261
73178f20 2262static enum ofperr
914624f8
BP
2263decode_copy_field__(ovs_be16 src_offset, ovs_be16 dst_offset, ovs_be16 n_bits,
2264 const void *action, ovs_be16 action_len, size_t oxm_offset,
2265 struct ofpbuf *ofpacts)
73178f20 2266{
0a2869d5 2267 struct ofpact_reg_move *move = ofpact_put_REG_MOVE(ofpacts);
914624f8
BP
2268 move->ofpact.raw = ONFACT_RAW13_COPY_FIELD;
2269 move->src.ofs = ntohs(src_offset);
2270 move->src.n_bits = ntohs(n_bits);
2271 move->dst.ofs = ntohs(dst_offset);
2272 move->dst.n_bits = ntohs(n_bits);
2273
0a2869d5 2274 struct ofpbuf b = ofpbuf_const_initializer(action, ntohs(action_len));
914624f8 2275 ofpbuf_pull(&b, oxm_offset);
0a2869d5
BP
2276
2277 enum ofperr error = nx_pull_header(&b, &move->src.field, NULL);
f13cdd73
BP
2278 if (error) {
2279 return error;
2280 }
2281 error = nx_pull_header(&b, &move->dst.field, NULL);
2282 if (error) {
2283 return error;
2284 }
f13cdd73 2285
6fd6ed71 2286 if (!is_all_zeros(b.data, b.size)) {
f13cdd73
BP
2287 return OFPERR_NXBRC_MUST_BE_ZERO;
2288 }
2289
73178f20
BP
2290 return nxm_reg_move_check(move, NULL);
2291}
2292
914624f8
BP
2293static enum ofperr
2294decode_OFPAT_RAW15_COPY_FIELD(const struct ofp15_action_copy_field *oacf,
f3cd3ac7 2295 enum ofp_version ofp_version OVS_UNUSED,
914624f8
BP
2296 struct ofpbuf *ofpacts)
2297{
2298 return decode_copy_field__(oacf->src_offset, oacf->dst_offset,
2299 oacf->n_bits, oacf, oacf->len,
2300 OBJECT_OFFSETOF(oacf, pad2), ofpacts);
2301}
2302
2303static enum ofperr
2304decode_ONFACT_RAW13_COPY_FIELD(const struct onf_action_copy_field *oacf,
f3cd3ac7 2305 enum ofp_version ofp_version OVS_UNUSED,
914624f8
BP
2306 struct ofpbuf *ofpacts)
2307{
2308 return decode_copy_field__(oacf->src_offset, oacf->dst_offset,
2309 oacf->n_bits, oacf, oacf->len,
2310 OBJECT_OFFSETOF(oacf, pad3), ofpacts);
2311}
2312
c2d936a4
BP
2313static enum ofperr
2314decode_NXAST_RAW_REG_MOVE(const struct nx_action_reg_move *narm,
f3cd3ac7 2315 enum ofp_version ofp_version OVS_UNUSED,
c2d936a4
BP
2316 struct ofpbuf *ofpacts)
2317{
0a2869d5 2318 struct ofpact_reg_move *move = ofpact_put_REG_MOVE(ofpacts);
914624f8 2319 move->ofpact.raw = NXAST_RAW_REG_MOVE;
c2d936a4
BP
2320 move->src.ofs = ntohs(narm->src_ofs);
2321 move->src.n_bits = ntohs(narm->n_bits);
c2d936a4
BP
2322 move->dst.ofs = ntohs(narm->dst_ofs);
2323 move->dst.n_bits = ntohs(narm->n_bits);
d01c980f 2324
0a2869d5 2325 struct ofpbuf b = ofpbuf_const_initializer(narm, ntohs(narm->len));
bad8a439 2326 ofpbuf_pull(&b, sizeof *narm);
0a2869d5
BP
2327
2328 enum ofperr error = nx_pull_header(&b, &move->src.field, NULL);
bad8a439
BP
2329 if (error) {
2330 return error;
2331 }
2332 error = nx_pull_header(&b, &move->dst.field, NULL);
2333 if (error) {
2334 return error;
2335 }
6fd6ed71 2336 if (!is_all_zeros(b.data, b.size)) {
bad8a439
BP
2337 return OFPERR_NXBRC_MUST_BE_ZERO;
2338 }
2339
c2d936a4
BP
2340 return nxm_reg_move_check(move, NULL);
2341}
d01c980f 2342
c2d936a4
BP
2343static void
2344encode_REG_MOVE(const struct ofpact_reg_move *move,
73178f20
BP
2345 enum ofp_version ofp_version, struct ofpbuf *out)
2346{
914624f8
BP
2347 /* For OpenFlow 1.3, the choice of ONFACT_RAW13_COPY_FIELD versus
2348 * NXAST_RAW_REG_MOVE is somewhat difficult. Neither one is guaranteed to
2349 * be supported by every OpenFlow 1.3 implementation. It would be ideal to
2350 * probe for support. Until we have that ability, we currently prefer
2351 * NXAST_RAW_REG_MOVE for backward compatibility with older Open vSwitch
2352 * versions. */
6fd6ed71 2353 size_t start_ofs = out->size;
73178f20 2354 if (ofp_version >= OFP15_VERSION) {
bad8a439 2355 struct ofp15_action_copy_field *copy = put_OFPAT15_COPY_FIELD(out);
73178f20
BP
2356 copy->n_bits = htons(move->dst.n_bits);
2357 copy->src_offset = htons(move->src.ofs);
2358 copy->dst_offset = htons(move->dst.ofs);
6fd6ed71 2359 out->size = out->size - sizeof copy->pad2;
f13cdd73
BP
2360 nx_put_header(out, move->src.field->id, ofp_version, false);
2361 nx_put_header(out, move->dst.field->id, ofp_version, false);
914624f8
BP
2362 } else if (ofp_version == OFP13_VERSION
2363 && move->ofpact.raw == ONFACT_RAW13_COPY_FIELD) {
2364 struct onf_action_copy_field *copy = put_ONFACT13_COPY_FIELD(out);
2365 copy->n_bits = htons(move->dst.n_bits);
2366 copy->src_offset = htons(move->src.ofs);
2367 copy->dst_offset = htons(move->dst.ofs);
6fd6ed71 2368 out->size = out->size - sizeof copy->pad3;
914624f8
BP
2369 nx_put_header(out, move->src.field->id, ofp_version, false);
2370 nx_put_header(out, move->dst.field->id, ofp_version, false);
73178f20 2371 } else {
bad8a439 2372 struct nx_action_reg_move *narm = put_NXAST_REG_MOVE(out);
73178f20
BP
2373 narm->n_bits = htons(move->dst.n_bits);
2374 narm->src_ofs = htons(move->src.ofs);
2375 narm->dst_ofs = htons(move->dst.ofs);
bad8a439
BP
2376 nx_put_header(out, move->src.field->id, 0, false);
2377 nx_put_header(out, move->dst.field->id, 0, false);
73178f20 2378 }
bad8a439 2379 pad_ofpat(out, start_ofs);
c2d936a4 2380}
e9536ecb 2381
cab50449 2382static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
2383parse_REG_MOVE(const char *arg, struct ofpbuf *ofpacts,
2384 enum ofputil_protocol *usable_protocols OVS_UNUSED)
2385{
2386 struct ofpact_reg_move *move = ofpact_put_REG_MOVE(ofpacts);
21b2fa61 2387 return nxm_parse_reg_move(move, arg);
c2d936a4 2388}
0f3f3c3d 2389
c2d936a4
BP
2390static void
2391format_REG_MOVE(const struct ofpact_reg_move *a, struct ds *s)
2392{
2393 nxm_format_reg_move(a, s);
2394}
2395\f
7eb4b1f1
BP
2396/* Action structure for OFPAT12_SET_FIELD. */
2397struct ofp12_action_set_field {
2398 ovs_be16 type; /* OFPAT12_SET_FIELD. */
2399 ovs_be16 len; /* Length is padded to 64 bits. */
2400
2401 /* Followed by:
2402 * - An OXM header, value, and (in OpenFlow 1.5+) optionally a mask.
2403 * - Enough 0-bytes to pad out to a multiple of 64 bits.
2404 *
2405 * The "pad" member is the beginning of the above. */
2406 uint8_t pad[4];
2407};
2408OFP_ASSERT(sizeof(struct ofp12_action_set_field) == 8);
2409
c2d936a4
BP
2410/* Action structure for NXAST_REG_LOAD.
2411 *
2412 * Copies value[0:n_bits] to dst[ofs:ofs+n_bits], where a[b:c] denotes the bits
2413 * within 'a' numbered 'b' through 'c' (not including bit 'c'). Bit numbering
2414 * starts at 0 for the least-significant bit, 1 for the next most significant
2415 * bit, and so on.
2416 *
2417 * 'dst' is an nxm_header with nxm_hasmask=0. See the documentation for
2418 * NXAST_REG_MOVE, above, for the permitted fields and for the side effects of
2419 * loading them.
2420 *
2421 * The 'ofs' and 'n_bits' fields are combined into a single 'ofs_nbits' field
2422 * to avoid enlarging the structure by another 8 bytes. To allow 'n_bits' to
2423 * take a value between 1 and 64 (inclusive) while taking up only 6 bits, it is
2424 * also stored as one less than its true value:
2425 *
2426 * 15 6 5 0
2427 * +------------------------------+------------------+
2428 * | ofs | n_bits - 1 |
2429 * +------------------------------+------------------+
2430 *
2431 * The switch will reject actions for which ofs+n_bits is greater than the
2432 * width of 'dst', or in which any bits in 'value' with value 2**n_bits or
2433 * greater are set to 1, with error type OFPET_BAD_ACTION, code
2434 * OFPBAC_BAD_ARGUMENT.
2435 */
2436struct nx_action_reg_load {
2437 ovs_be16 type; /* OFPAT_VENDOR. */
2438 ovs_be16 len; /* Length is 24. */
2439 ovs_be32 vendor; /* NX_VENDOR_ID. */
2440 ovs_be16 subtype; /* NXAST_REG_LOAD. */
2441 ovs_be16 ofs_nbits; /* (ofs << 6) | (n_bits - 1). */
2442 ovs_be32 dst; /* Destination register. */
2443 ovs_be64 value; /* Immediate value. */
2444};
2445OFP_ASSERT(sizeof(struct nx_action_reg_load) == 24);
b676167a 2446
aad28f47
BP
2447/* The NXAST_REG_LOAD2 action structure is "struct ext_action_header",
2448 * followed by:
bad8a439 2449 *
aad28f47
BP
2450 * - An NXM/OXM header, value, and optionally a mask.
2451 * - Enough 0-bytes to pad out to a multiple of 64 bits.
2452 *
2453 * The "pad" member is the beginning of the above. */
bad8a439 2454
c2d936a4 2455static enum ofperr
7eb4b1f1
BP
2456decode_ofpat_set_field(const struct ofp12_action_set_field *oasf,
2457 bool may_mask, struct ofpbuf *ofpacts)
7fdb60a7 2458{
0a2869d5 2459 struct ofpbuf b = ofpbuf_const_initializer(oasf, ntohs(oasf->len));
7eb4b1f1 2460 ofpbuf_pull(&b, OBJECT_OFFSETOF(oasf, pad));
0a2869d5 2461
128684a6
JR
2462 union mf_value value, mask;
2463 const struct mf_field *field;
2464 enum ofperr error = nx_pull_entry(&b, &field, &value,
2465 may_mask ? &mask : NULL);
178742f9 2466 if (error) {
178742f9
BP
2467 return (error == OFPERR_OFPBMC_BAD_MASK
2468 ? OFPERR_OFPBAC_BAD_SET_MASK
2469 : error);
c2d936a4 2470 }
7eb4b1f1 2471 if (!may_mask) {
128684a6 2472 memset(&mask, 0xff, field->n_bytes);
7eb4b1f1 2473 }
178742f9 2474
6fd6ed71 2475 if (!is_all_zeros(b.data, b.size)) {
c2d936a4
BP
2476 return OFPERR_OFPBAC_BAD_SET_ARGUMENT;
2477 }
7fdb60a7 2478
178742f9
BP
2479 /* OpenFlow says specifically that one may not set OXM_OF_IN_PORT via
2480 * Set-Field. */
128684a6 2481 if (field->id == MFF_IN_PORT_OXM) {
178742f9 2482 return OFPERR_OFPBAC_BAD_SET_ARGUMENT;
c2d936a4 2483 }
178742f9 2484
c2d936a4 2485 /* oxm_length is now validated to be compatible with mf_value. */
128684a6 2486 if (!field->writable) {
178742f9 2487 VLOG_WARN_RL(&rl, "destination field %s is not writable",
128684a6 2488 field->name);
c2d936a4
BP
2489 return OFPERR_OFPBAC_BAD_SET_ARGUMENT;
2490 }
c2d936a4 2491
d3cb080e 2492 /* The value must be valid for match. OpenFlow 1.5 also says,
7eb4b1f1
BP
2493 * "In an OXM_OF_VLAN_VID set-field action, the OFPVID_PRESENT bit must be
2494 * a 1-bit in oxm_value and in oxm_mask." */
128684a6
JR
2495 if (!mf_is_value_valid(field, &value)
2496 || (field->id == MFF_VLAN_VID
2497 && (!(mask.be16 & htons(OFPVID12_PRESENT))
2498 || !(value.be16 & htons(OFPVID12_PRESENT))))) {
c2d936a4 2499 struct ds ds = DS_EMPTY_INITIALIZER;
128684a6 2500 mf_format(field, &value, NULL, &ds);
c2d936a4 2501 VLOG_WARN_RL(&rl, "Invalid value for set field %s: %s",
128684a6 2502 field->name, ds_cstr(&ds));
c2d936a4
BP
2503 ds_destroy(&ds);
2504
2505 return OFPERR_OFPBAC_BAD_SET_ARGUMENT;
7fdb60a7 2506 }
128684a6
JR
2507
2508 ofpact_put_set_field(ofpacts, field, &value, &mask);
c2d936a4 2509 return 0;
7fdb60a7
SH
2510}
2511
7eb4b1f1
BP
2512static enum ofperr
2513decode_OFPAT_RAW12_SET_FIELD(const struct ofp12_action_set_field *oasf,
f3cd3ac7 2514 enum ofp_version ofp_version OVS_UNUSED,
7eb4b1f1
BP
2515 struct ofpbuf *ofpacts)
2516{
2517 return decode_ofpat_set_field(oasf, false, ofpacts);
2518}
2519
2520static enum ofperr
2521decode_OFPAT_RAW15_SET_FIELD(const struct ofp12_action_set_field *oasf,
f3cd3ac7 2522 enum ofp_version ofp_version OVS_UNUSED,
7eb4b1f1
BP
2523 struct ofpbuf *ofpacts)
2524{
2525 return decode_ofpat_set_field(oasf, true, ofpacts);
2526}
2527
2528static enum ofperr
2529decode_NXAST_RAW_REG_LOAD(const struct nx_action_reg_load *narl,
f3cd3ac7 2530 enum ofp_version ofp_version OVS_UNUSED,
7eb4b1f1
BP
2531 struct ofpbuf *out)
2532{
7eb4b1f1
BP
2533 struct mf_subfield dst;
2534 enum ofperr error;
2535
7eb4b1f1
BP
2536 dst.field = mf_from_nxm_header(ntohl(narl->dst));
2537 dst.ofs = nxm_decode_ofs(narl->ofs_nbits);
2538 dst.n_bits = nxm_decode_n_bits(narl->ofs_nbits);
2539 error = mf_check_dst(&dst, NULL);
2540 if (error) {
2541 return error;
2542 }
2543
2544 /* Reject 'narl' if a bit numbered 'n_bits' or higher is set to 1 in
2545 * narl->value. */
2546 if (dst.n_bits < 64 && ntohll(narl->value) >> dst.n_bits) {
2547 return OFPERR_OFPBAC_BAD_ARGUMENT;
2548 }
2549
128684a6
JR
2550 struct ofpact_set_field *sf = ofpact_put_reg_load(out, dst.field, NULL,
2551 NULL);
7eb4b1f1 2552 bitwise_put(ntohll(narl->value),
128684a6 2553 sf->value, dst.field->n_bytes, dst.ofs,
7eb4b1f1
BP
2554 dst.n_bits);
2555 bitwise_put(UINT64_MAX,
128684a6 2556 ofpact_set_field_mask(sf), dst.field->n_bytes, dst.ofs,
7eb4b1f1 2557 dst.n_bits);
7eb4b1f1
BP
2558 return 0;
2559}
2560
bad8a439 2561static enum ofperr
aad28f47 2562decode_NXAST_RAW_REG_LOAD2(const struct ext_action_header *eah,
f3cd3ac7 2563 enum ofp_version ofp_version OVS_UNUSED,
bad8a439
BP
2564 struct ofpbuf *out)
2565{
aad28f47
BP
2566 struct ofpbuf b = ofpbuf_const_initializer(eah, ntohs(eah->len));
2567 ofpbuf_pull(&b, OBJECT_OFFSETOF(eah, pad));
0a2869d5 2568
128684a6
JR
2569 union mf_value value, mask;
2570 const struct mf_field *field;
2571 enum ofperr error = nx_pull_entry(&b, &field, &value, &mask);
bad8a439
BP
2572 if (error) {
2573 return error;
2574 }
6fd6ed71 2575 if (!is_all_zeros(b.data, b.size)) {
bad8a439
BP
2576 return OFPERR_OFPBAC_BAD_SET_ARGUMENT;
2577 }
2578
128684a6
JR
2579 if (!field->writable) {
2580 VLOG_WARN_RL(&rl, "destination field %s is not writable", field->name);
bad8a439
BP
2581 return OFPERR_OFPBAC_BAD_SET_ARGUMENT;
2582 }
128684a6
JR
2583
2584 /* Put value and mask. */
2585 ofpact_put_reg_load2(out, field, &value, &mask);
bad8a439
BP
2586 return 0;
2587}
2588
7fdb60a7 2589static void
128684a6
JR
2590put_set_field(struct ofpbuf *openflow, enum ofp_version ofp_version,
2591 enum mf_field_id field, uint64_t value_)
7fdb60a7 2592{
7eb4b1f1 2593 struct ofp12_action_set_field *oasf OVS_UNUSED;
178742f9 2594 int n_bytes = mf_from_id(field)->n_bytes;
6fd6ed71 2595 size_t start_ofs = openflow->size;
178742f9 2596 union mf_value value;
7fdb60a7 2597
178742f9 2598 value.be64 = htonll(value_ << (8 * (8 - n_bytes)));
7fdb60a7 2599
7eb4b1f1 2600 oasf = put_OFPAT12_SET_FIELD(openflow);
6fd6ed71 2601 openflow->size = openflow->size - sizeof oasf->pad;
178742f9
BP
2602 nx_put_entry(openflow, field, ofp_version, &value, NULL);
2603 pad_ofpat(openflow, start_ofs);
7fdb60a7
SH
2604}
2605
4b684612
BP
2606static void
2607put_reg_load(struct ofpbuf *openflow,
2608 const struct mf_subfield *dst, uint64_t value)
2609{
2610 ovs_assert(dst->n_bits <= 64);
2611
2612 struct nx_action_reg_load *narl = put_NXAST_REG_LOAD(openflow);
2613 narl->ofs_nbits = nxm_encode_ofs_nbits(dst->ofs, dst->n_bits);
2614 narl->dst = htonl(mf_nxm_header(dst->field->id));
2615 narl->value = htonll(value);
2616}
2617
7eb4b1f1
BP
2618static bool
2619next_load_segment(const struct ofpact_set_field *sf,
2620 struct mf_subfield *dst, uint64_t *value)
2621{
fa078489
BP
2622 int n_bits = sf->field->n_bits;
2623 int n_bytes = sf->field->n_bytes;
7eb4b1f1
BP
2624 int start = dst->ofs + dst->n_bits;
2625
fa078489 2626 if (start < n_bits) {
7eb4b1f1 2627 dst->field = sf->field;
128684a6
JR
2628 dst->ofs = bitwise_scan(ofpact_set_field_mask(sf), n_bytes, 1, start,
2629 n_bits);
fa078489 2630 if (dst->ofs < n_bits) {
128684a6
JR
2631 dst->n_bits = bitwise_scan(ofpact_set_field_mask(sf), n_bytes, 0,
2632 dst->ofs + 1,
fa078489 2633 MIN(dst->ofs + 64, n_bits)) - dst->ofs;
128684a6 2634 *value = bitwise_get(sf->value, n_bytes, dst->ofs, dst->n_bits);
7eb4b1f1
BP
2635 return true;
2636 }
2637 }
2638 return false;
2639}
178742f9 2640
7eb4b1f1 2641/* Convert 'sf' to a series of REG_LOADs. */
7fdb60a7 2642static void
c2d936a4 2643set_field_to_nxast(const struct ofpact_set_field *sf, struct ofpbuf *openflow)
7fdb60a7 2644{
bad8a439 2645 /* If 'sf' cannot be encoded as NXAST_REG_LOAD because it requires an
4fe04a7e
JG
2646 * experimenter OXM or is variable length (or if it came in as
2647 * NXAST_REG_LOAD2), encode as NXAST_REG_LOAD2. Otherwise use
2648 * NXAST_REG_LOAD, which is backward compatible. */
bad8a439 2649 if (sf->ofpact.raw == NXAST_RAW_REG_LOAD2
4fe04a7e 2650 || !mf_nxm_header(sf->field->id) || sf->field->variable_len) {
aad28f47 2651 struct ext_action_header *eah OVS_UNUSED;
6fd6ed71 2652 size_t start_ofs = openflow->size;
bad8a439 2653
aad28f47
BP
2654 eah = put_NXAST_REG_LOAD2(openflow);
2655 openflow->size = openflow->size - sizeof eah->pad;
128684a6
JR
2656 nx_put_entry(openflow, sf->field->id, 0, sf->value,
2657 ofpact_set_field_mask(sf));
bad8a439
BP
2658 pad_ofpat(openflow, start_ofs);
2659 } else {
2660 struct mf_subfield dst;
2661 uint64_t value;
7eb4b1f1 2662
bad8a439
BP
2663 dst.ofs = dst.n_bits = 0;
2664 while (next_load_segment(sf, &dst, &value)) {
4b684612 2665 put_reg_load(openflow, &dst, value);
bad8a439 2666 }
7fdb60a7
SH
2667 }
2668}
2669
7eb4b1f1
BP
2670/* Convert 'sf', which must set an entire field, to standard OpenFlow 1.0/1.1
2671 * actions, if we can, falling back to Nicira extensions if we must.
7fdb60a7 2672 *
c2d936a4
BP
2673 * We check only meta-flow types that can appear within set field actions and
2674 * that have a mapping to compatible action types. These struct mf_field
2675 * definitions have a defined OXM or NXM header value and specify the field as
2676 * writable. */
2677static void
2678set_field_to_legacy_openflow(const struct ofpact_set_field *sf,
2679 enum ofp_version ofp_version,
2680 struct ofpbuf *out)
7fdb60a7 2681{
c2d936a4
BP
2682 switch ((int) sf->field->id) {
2683 case MFF_VLAN_TCI: {
128684a6 2684 ovs_be16 tci = sf->value->be16;
c2d936a4
BP
2685 bool cfi = (tci & htons(VLAN_CFI)) != 0;
2686 uint16_t vid = vlan_tci_to_vid(tci);
2687 uint8_t pcp = vlan_tci_to_pcp(tci);
2688
2689 if (ofp_version < OFP11_VERSION) {
2690 /* NXM_OF_VLAN_TCI to OpenFlow 1.0 mapping:
2691 *
2692 * If CFI=1, Add or modify VLAN VID & PCP.
2693 * If CFI=0, strip VLAN header, if any.
2694 */
2695 if (cfi) {
2696 put_OFPAT10_SET_VLAN_VID(out, vid);
2697 put_OFPAT10_SET_VLAN_PCP(out, pcp);
2698 } else {
2699 put_OFPAT10_STRIP_VLAN(out);
2700 }
2701 } else {
2702 /* NXM_OF_VLAN_TCI to OpenFlow 1.1 mapping:
2703 *
2704 * If CFI=1, Add or modify VLAN VID & PCP.
2705 * OpenFlow 1.1 set actions only apply if the packet
2706 * already has VLAN tags. To be sure that is the case
2707 * we have to push a VLAN header. As we do not support
2708 * multiple layers of VLANs, this is a no-op, if a VLAN
2709 * header already exists. This may backfire, however,
2710 * when we start supporting multiple layers of VLANs.
2711 * If CFI=0, strip VLAN header, if any.
2712 */
2713 if (cfi) {
2714 /* Push a VLAN tag, if one was not seen at action validation
2715 * time. */
2716 if (!sf->flow_has_vlan) {
2717 put_OFPAT11_PUSH_VLAN(out, htons(ETH_TYPE_VLAN_8021Q));
2718 }
2719 put_OFPAT11_SET_VLAN_VID(out, vid);
2720 put_OFPAT11_SET_VLAN_PCP(out, pcp);
2721 } else {
2722 /* If the flow did not match on vlan, we have no way of
2723 * knowing if the vlan tag exists, so we must POP just to be
2724 * sure. */
2725 put_OFPAT11_POP_VLAN(out);
2726 }
2727 }
2728 break;
2729 }
7fdb60a7 2730
c2d936a4 2731 case MFF_VLAN_VID: {
128684a6 2732 uint16_t vid = ntohs(sf->value->be16) & VLAN_VID_MASK;
c2d936a4
BP
2733 if (ofp_version == OFP10_VERSION) {
2734 put_OFPAT10_SET_VLAN_VID(out, vid);
2735 } else {
2736 put_OFPAT11_SET_VLAN_VID(out, vid);
2737 }
2738 break;
2739 }
2740
2741 case MFF_VLAN_PCP:
2742 if (ofp_version == OFP10_VERSION) {
128684a6 2743 put_OFPAT10_SET_VLAN_PCP(out, sf->value->u8);
c2d936a4 2744 } else {
128684a6 2745 put_OFPAT11_SET_VLAN_PCP(out, sf->value->u8);
c2d936a4
BP
2746 }
2747 break;
2748
2749 case MFF_ETH_SRC:
128684a6 2750 put_OFPAT_SET_DL_SRC(out, ofp_version)->dl_addr = sf->value->mac;
c2d936a4
BP
2751 break;
2752
2753 case MFF_ETH_DST:
128684a6 2754 put_OFPAT_SET_DL_DST(out, ofp_version)->dl_addr = sf->value->mac;
c2d936a4
BP
2755 break;
2756
2757 case MFF_IPV4_SRC:
128684a6 2758 put_OFPAT_SET_NW_SRC(out, ofp_version, sf->value->be32);
c2d936a4
BP
2759 break;
2760
2761 case MFF_IPV4_DST:
128684a6 2762 put_OFPAT_SET_NW_DST(out, ofp_version, sf->value->be32);
c2d936a4
BP
2763 break;
2764
2765 case MFF_IP_DSCP:
128684a6 2766 put_OFPAT_SET_NW_TOS(out, ofp_version, sf->value->u8);
c2d936a4
BP
2767 break;
2768
2769 case MFF_IP_DSCP_SHIFTED:
128684a6 2770 put_OFPAT_SET_NW_TOS(out, ofp_version, sf->value->u8 << 2);
c2d936a4
BP
2771 break;
2772
4b684612 2773 case MFF_IP_ECN:
128684a6 2774 put_OFPAT11_SET_NW_ECN(out, sf->value->u8);
4b684612
BP
2775 break;
2776
c2d936a4
BP
2777 case MFF_TCP_SRC:
2778 case MFF_UDP_SRC:
128684a6 2779 put_OFPAT_SET_TP_SRC(out, sf->value->be16);
c2d936a4
BP
2780 break;
2781
2782 case MFF_TCP_DST:
2783 case MFF_UDP_DST:
128684a6 2784 put_OFPAT_SET_TP_DST(out, sf->value->be16);
c2d936a4
BP
2785 break;
2786
2787 default:
2788 set_field_to_nxast(sf, out);
2789 break;
7fdb60a7
SH
2790 }
2791}
2792
7eb4b1f1
BP
2793static void
2794set_field_to_set_field(const struct ofpact_set_field *sf,
2795 enum ofp_version ofp_version, struct ofpbuf *out)
2796{
2797 struct ofp12_action_set_field *oasf OVS_UNUSED;
6fd6ed71 2798 size_t start_ofs = out->size;
7eb4b1f1
BP
2799
2800 oasf = put_OFPAT12_SET_FIELD(out);
6fd6ed71 2801 out->size = out->size - sizeof oasf->pad;
128684a6
JR
2802 nx_put_entry(out, sf->field->id, ofp_version, sf->value,
2803 ofpact_set_field_mask(sf));
7eb4b1f1
BP
2804 pad_ofpat(out, start_ofs);
2805}
2806
c2d936a4
BP
2807static void
2808encode_SET_FIELD(const struct ofpact_set_field *sf,
2809 enum ofp_version ofp_version, struct ofpbuf *out)
2810{
7eb4b1f1 2811 if (ofp_version >= OFP15_VERSION) {
bad8a439
BP
2812 /* OF1.5+ only has Set-Field (reg_load is redundant so we drop it
2813 * entirely). */
7eb4b1f1 2814 set_field_to_set_field(sf, ofp_version, out);
bad8a439
BP
2815 } else if (sf->ofpact.raw == NXAST_RAW_REG_LOAD ||
2816 sf->ofpact.raw == NXAST_RAW_REG_LOAD2) {
2817 /* It came in as reg_load, send it out the same way. */
7eb4b1f1
BP
2818 set_field_to_nxast(sf, out);
2819 } else if (ofp_version < OFP12_VERSION) {
2820 /* OpenFlow 1.0 and 1.1 don't have Set-Field. */
c2d936a4 2821 set_field_to_legacy_openflow(sf, ofp_version, out);
128684a6 2822 } else if (is_all_ones(ofpact_set_field_mask(sf), sf->field->n_bytes)) {
7eb4b1f1
BP
2823 /* We're encoding to OpenFlow 1.2, 1.3, or 1.4. The action sets an
2824 * entire field, so encode it as OFPAT_SET_FIELD. */
2825 set_field_to_set_field(sf, ofp_version, out);
c2d936a4 2826 } else {
7eb4b1f1
BP
2827 /* We're encoding to OpenFlow 1.2, 1.3, or 1.4. The action cannot be
2828 * encoded as OFPAT_SET_FIELD because it does not set an entire field,
2829 * so encode it as reg_load. */
2830 set_field_to_nxast(sf, out);
c2d936a4
BP
2831 }
2832}
2833
36b43aa6
JS
2834/* Parses the input argument 'arg' into the key, value, and delimiter
2835 * components that are common across the reg_load and set_field action format.
2836 *
2837 * With an argument like "1->metadata", sets the following pointers to
2838 * point within 'arg':
2839 * key: "metadata"
2840 * value: "1"
2841 * delim: "->"
2842 *
2843 * Returns NULL if successful, otherwise a malloc()'d string describing the
2844 * error. The caller is responsible for freeing the returned string. */
2845static char * OVS_WARN_UNUSED_RESULT
2846set_field_split_str(char *arg, char **key, char **value, char **delim)
2847{
2848 char *value_end;
2849
2850 *value = arg;
2851 value_end = strstr(arg, "->");
2852 *key = value_end + strlen("->");
2853 if (delim) {
2854 *delim = value_end;
2855 }
2856
2857 if (!value_end) {
2858 return xasprintf("%s: missing `->'", arg);
2859 }
2860 if (strlen(value_end) <= strlen("->")) {
2861 return xasprintf("%s: missing field name following `->'", arg);
2862 }
2863
2864 return NULL;
2865}
2866
c2d936a4
BP
2867/* Parses a "set_field" action with argument 'arg', appending the parsed
2868 * action to 'ofpacts'.
2869 *
2870 * Returns NULL if successful, otherwise a malloc()'d string describing the
2871 * error. The caller is responsible for freeing the returned string. */
cab50449 2872static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
2873set_field_parse__(char *arg, struct ofpbuf *ofpacts,
2874 enum ofputil_protocol *usable_protocols)
7fdb60a7 2875{
c2d936a4
BP
2876 char *value;
2877 char *delim;
2878 char *key;
2879 const struct mf_field *mf;
128684a6 2880 union mf_value sf_value, sf_mask;
c2d936a4 2881 char *error;
7fdb60a7 2882
36b43aa6
JS
2883 error = set_field_split_str(arg, &key, &value, &delim);
2884 if (error) {
2885 return error;
c2d936a4 2886 }
e3f8f887 2887
c2d936a4
BP
2888 mf = mf_from_name(key);
2889 if (!mf) {
2890 return xasprintf("%s is not a valid OXM field name", key);
2891 }
2892 if (!mf->writable) {
2893 return xasprintf("%s is read-only", key);
2894 }
128684a6 2895
c2d936a4 2896 delim[0] = '\0';
128684a6 2897 error = mf_parse(mf, value, &sf_value, &sf_mask);
7fdb60a7
SH
2898 if (error) {
2899 return error;
2900 }
2901
128684a6 2902 if (!mf_is_value_valid(mf, &sf_value)) {
c2d936a4 2903 return xasprintf("%s is not a valid value for field %s", value, key);
7fdb60a7
SH
2904 }
2905
a4ce8b25 2906 *usable_protocols &= mf->usable_protocols_exact;
128684a6
JR
2907
2908 ofpact_put_set_field(ofpacts, mf, &sf_value, &sf_mask);
c2d936a4 2909 return NULL;
7fdb60a7
SH
2910}
2911
c2d936a4
BP
2912/* Parses 'arg' as the argument to a "set_field" action, and appends such an
2913 * action to 'ofpacts'.
2914 *
2915 * Returns NULL if successful, otherwise a malloc()'d string describing the
2916 * error. The caller is responsible for freeing the returned string. */
cab50449 2917static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
2918parse_SET_FIELD(const char *arg, struct ofpbuf *ofpacts,
2919 enum ofputil_protocol *usable_protocols)
2920{
2921 char *copy = xstrdup(arg);
2922 char *error = set_field_parse__(copy, ofpacts, usable_protocols);
2923 free(copy);
2924 return error;
2925}
a359d5ad 2926
cab50449 2927static char * OVS_WARN_UNUSED_RESULT
7eb4b1f1
BP
2928parse_reg_load(char *arg, struct ofpbuf *ofpacts)
2929{
7eb4b1f1 2930 struct mf_subfield dst;
36b43aa6 2931 char *key, *value_str;
81270993 2932 union mf_value value;
7eb4b1f1
BP
2933 char *error;
2934
36b43aa6
JS
2935 error = set_field_split_str(arg, &key, &value_str, NULL);
2936 if (error) {
2937 return error;
7eb4b1f1 2938 }
36b43aa6
JS
2939
2940 error = mf_parse_subfield(&dst, key);
7eb4b1f1
BP
2941 if (error) {
2942 return error;
2943 }
2944
81270993
JS
2945 if (parse_int_string(value_str, (uint8_t *)&value, dst.field->n_bytes,
2946 &key)) {
2947 return xasprintf("%s: cannot parse integer value", arg);
2948 }
2949
2950 if (!bitwise_is_all_zeros(&value, dst.field->n_bytes, dst.n_bits,
2951 dst.field->n_bytes * 8 - dst.n_bits)) {
2952 struct ds ds;
2953
2954 ds_init(&ds);
2955 mf_format(dst.field, &value, NULL, &ds);
2956 error = xasprintf("%s: value %s does not fit into %d bits",
2957 arg, ds_cstr(&ds), dst.n_bits);
2958 ds_destroy(&ds);
2959 return error;
7eb4b1f1
BP
2960 }
2961
128684a6
JR
2962 struct ofpact_set_field *sf = ofpact_put_reg_load(ofpacts, dst.field, NULL,
2963 NULL);
81270993 2964
128684a6
JR
2965 bitwise_copy(&value, dst.field->n_bytes, 0, sf->value,
2966 dst.field->n_bytes, dst.ofs, dst.n_bits);
2967 bitwise_one(ofpact_set_field_mask(sf), dst.field->n_bytes, dst.ofs,
2968 dst.n_bits);
7eb4b1f1
BP
2969 return NULL;
2970}
2971
c2d936a4
BP
2972static void
2973format_SET_FIELD(const struct ofpact_set_field *a, struct ds *s)
2974{
7eb4b1f1
BP
2975 if (a->ofpact.raw == NXAST_RAW_REG_LOAD) {
2976 struct mf_subfield dst;
2977 uint64_t value;
2978
2979 dst.ofs = dst.n_bits = 0;
2980 while (next_load_segment(a, &dst, &value)) {
b1c5bf1f
QM
2981 ds_put_format(s, "%sload:%s%#"PRIx64"%s->%s",
2982 colors.special, colors.end, value,
2983 colors.special, colors.end);
7eb4b1f1
BP
2984 mf_format_subfield(&dst, s);
2985 ds_put_char(s, ',');
2986 }
2987 ds_chomp(s, ',');
2988 } else {
b1c5bf1f 2989 ds_put_format(s, "%sset_field:%s", colors.special, colors.end);
128684a6 2990 mf_format(a->field, a->value, ofpact_set_field_mask(a), s);
b1c5bf1f
QM
2991 ds_put_format(s, "%s->%s%s",
2992 colors.special, colors.end, a->field->name);
7eb4b1f1
BP
2993 }
2994}
2995
128684a6
JR
2996/* Appends an OFPACT_SET_FIELD ofpact with enough space for the value and mask
2997 * for the 'field' to 'ofpacts' and returns it. Fills in the value from
2998 * 'value', if non-NULL, and mask from 'mask' if non-NULL. If 'value' is
2999 * non-NULL and 'mask' is NULL, an all-ones mask will be filled in. */
3000struct ofpact_set_field *
3001ofpact_put_set_field(struct ofpbuf *ofpacts, const struct mf_field *field,
3002 const void *value, const void *mask)
3003{
3004 struct ofpact_set_field *sf = ofpact_put_SET_FIELD(ofpacts);
3005 sf->field = field;
3006
3007 /* Fill in the value and mask if given, otherwise put zeroes so that the
3008 * caller may fill in the value and mask itself. */
3009 if (value) {
3010 ofpbuf_put_uninit(ofpacts, 2 * field->n_bytes);
3011 sf = ofpacts->header;
3012 memcpy(sf->value, value, field->n_bytes);
3013 if (mask) {
3014 memcpy(ofpact_set_field_mask(sf), mask, field->n_bytes);
3015 } else {
3016 memset(ofpact_set_field_mask(sf), 0xff, field->n_bytes);
3017 }
3018 } else {
3019 ofpbuf_put_zeros(ofpacts, 2 * field->n_bytes);
3020 sf = ofpacts->header;
3021 }
3022 /* Update length. */
3023 ofpact_finish_SET_FIELD(ofpacts, &sf);
3024
3025 return sf;
3026}
3027
7eb4b1f1
BP
3028/* Appends an OFPACT_SET_FIELD ofpact to 'ofpacts' and returns it. The ofpact
3029 * is marked such that, if possible, it will be translated to OpenFlow as
3030 * NXAST_REG_LOAD extension actions rather than OFPAT_SET_FIELD, either because
3031 * that was the way that the action was expressed when it came into OVS or for
3032 * backward compatibility. */
3033struct ofpact_set_field *
128684a6
JR
3034ofpact_put_reg_load(struct ofpbuf *ofpacts, const struct mf_field *field,
3035 const void *value, const void *mask)
7eb4b1f1 3036{
128684a6
JR
3037 struct ofpact_set_field *sf = ofpact_put_set_field(ofpacts, field, value,
3038 mask);
7eb4b1f1 3039 sf->ofpact.raw = NXAST_RAW_REG_LOAD;
128684a6 3040
7eb4b1f1 3041 return sf;
c2d936a4 3042}
128684a6
JR
3043
3044struct ofpact_set_field *
3045ofpact_put_reg_load2(struct ofpbuf *ofpacts, const struct mf_field *field,
3046 const void *value, const void *mask)
3047{
3048 struct ofpact_set_field *sf = ofpact_put_set_field(ofpacts, field, value,
3049 mask);
3050 sf->ofpact.raw = NXAST_RAW_REG_LOAD2;
3051
3052 return sf;
3053}
3054
c2d936a4
BP
3055\f
3056/* Action structure for NXAST_STACK_PUSH and NXAST_STACK_POP.
3057 *
3058 * Pushes (or pops) field[offset: offset + n_bits] to (or from)
3059 * top of the stack.
3060 */
3061struct nx_action_stack {
3062 ovs_be16 type; /* OFPAT_VENDOR. */
3063 ovs_be16 len; /* Length is 16. */
3064 ovs_be32 vendor; /* NX_VENDOR_ID. */
3065 ovs_be16 subtype; /* NXAST_STACK_PUSH or NXAST_STACK_POP. */
3066 ovs_be16 offset; /* Bit offset into the field. */
bad8a439
BP
3067 /* Followed by:
3068 * - OXM/NXM header for field to push or pop (4 or 8 bytes).
3069 * - ovs_be16 'n_bits', the number of bits to extract from the field.
3070 * - Enough 0-bytes to pad out the action to 24 bytes. */
3071 uint8_t pad[12]; /* See above. */
a359d5ad 3072};
c2d936a4 3073OFP_ASSERT(sizeof(struct nx_action_stack) == 24);
a359d5ad 3074
bad8a439 3075static enum ofperr
c2d936a4
BP
3076decode_stack_action(const struct nx_action_stack *nasp,
3077 struct ofpact_stack *stack_action)
a359d5ad 3078{
c2d936a4 3079 stack_action->subfield.ofs = ntohs(nasp->offset);
bad8a439 3080
0a2869d5 3081 struct ofpbuf b = ofpbuf_const_initializer(nasp, sizeof *nasp);
bad8a439 3082 ofpbuf_pull(&b, OBJECT_OFFSETOF(nasp, pad));
0a2869d5
BP
3083 enum ofperr error = nx_pull_header(&b, &stack_action->subfield.field,
3084 NULL);
bad8a439
BP
3085 if (error) {
3086 return error;
3087 }
6fd6ed71 3088 stack_action->subfield.n_bits = ntohs(*(const ovs_be16 *) b.data);
bad8a439 3089 ofpbuf_pull(&b, 2);
6fd6ed71 3090 if (!is_all_zeros(b.data, b.size)) {
bad8a439
BP
3091 return OFPERR_NXBRC_MUST_BE_ZERO;
3092 }
3093
3094 return 0;
a359d5ad
IY
3095}
3096
c2d936a4
BP
3097static enum ofperr
3098decode_NXAST_RAW_STACK_PUSH(const struct nx_action_stack *nasp,
f3cd3ac7
JS
3099 enum ofp_version ofp_version OVS_UNUSED,
3100 struct ofpbuf *ofpacts)
a359d5ad 3101{
c2d936a4 3102 struct ofpact_stack *push = ofpact_put_STACK_PUSH(ofpacts);
bad8a439
BP
3103 enum ofperr error = decode_stack_action(nasp, push);
3104 return error ? error : nxm_stack_push_check(push, NULL);
a359d5ad
IY
3105}
3106
c2d936a4
BP
3107static enum ofperr
3108decode_NXAST_RAW_STACK_POP(const struct nx_action_stack *nasp,
f3cd3ac7 3109 enum ofp_version ofp_version OVS_UNUSED,
c2d936a4 3110 struct ofpbuf *ofpacts)
084c53de 3111{
c2d936a4 3112 struct ofpact_stack *pop = ofpact_put_STACK_POP(ofpacts);
bad8a439
BP
3113 enum ofperr error = decode_stack_action(nasp, pop);
3114 return error ? error : nxm_stack_pop_check(pop, NULL);
084c53de
BP
3115}
3116
c2d936a4
BP
3117static void
3118encode_STACK_op(const struct ofpact_stack *stack_action,
3119 struct nx_action_stack *nasp)
c0621c39 3120{
bad8a439
BP
3121 struct ofpbuf b;
3122 ovs_be16 n_bits;
3123
c2d936a4 3124 nasp->offset = htons(stack_action->subfield.ofs);
bad8a439
BP
3125
3126 ofpbuf_use_stack(&b, nasp, ntohs(nasp->len));
3127 ofpbuf_put_uninit(&b, OBJECT_OFFSETOF(nasp, pad));
3128 nx_put_header(&b, stack_action->subfield.field->id, 0, false);
3129 n_bits = htons(stack_action->subfield.n_bits);
3130 ofpbuf_put(&b, &n_bits, sizeof n_bits);
c0621c39
AW
3131}
3132
c2d936a4
BP
3133static void
3134encode_STACK_PUSH(const struct ofpact_stack *stack,
3135 enum ofp_version ofp_version OVS_UNUSED, struct ofpbuf *out)
3136{
3137 encode_STACK_op(stack, put_NXAST_STACK_PUSH(out));
3138}
8e97815e 3139
c2d936a4
BP
3140static void
3141encode_STACK_POP(const struct ofpact_stack *stack,
3142 enum ofp_version ofp_version OVS_UNUSED, struct ofpbuf *out)
8e97815e 3143{
c2d936a4
BP
3144 encode_STACK_op(stack, put_NXAST_STACK_POP(out));
3145}
8e97815e 3146
cab50449 3147static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
3148parse_STACK_PUSH(char *arg, struct ofpbuf *ofpacts,
3149 enum ofputil_protocol *usable_protocols OVS_UNUSED)
3150{
3151 return nxm_parse_stack_action(ofpact_put_STACK_PUSH(ofpacts), arg);
3152}
8e97815e 3153
cab50449 3154static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
3155parse_STACK_POP(char *arg, struct ofpbuf *ofpacts,
3156 enum ofputil_protocol *usable_protocols OVS_UNUSED)
3157{
3158 return nxm_parse_stack_action(ofpact_put_STACK_POP(ofpacts), arg);
8e97815e
BP
3159}
3160
c2d936a4
BP
3161static void
3162format_STACK_PUSH(const struct ofpact_stack *a, struct ds *s)
8e97815e 3163{
c2d936a4
BP
3164 nxm_format_stack_push(a, s);
3165}
8e97815e 3166
c2d936a4
BP
3167static void
3168format_STACK_POP(const struct ofpact_stack *a, struct ds *s)
3169{
3170 nxm_format_stack_pop(a, s);
3171}
3172\f
3173/* Action structure for NXAST_DEC_TTL_CNT_IDS.
3174 *
3175 * If the packet is not IPv4 or IPv6, does nothing. For IPv4 or IPv6, if the
3176 * TTL or hop limit is at least 2, decrements it by 1. Otherwise, if TTL or
3177 * hop limit is 0 or 1, sends a packet-in to the controllers with each of the
3178 * 'n_controllers' controller IDs specified in 'cnt_ids'.
3179 *
3180 * (This differs from NXAST_DEC_TTL in that for NXAST_DEC_TTL the packet-in is
3181 * sent only to controllers with id 0.)
3182 */
3183struct nx_action_cnt_ids {
3184 ovs_be16 type; /* OFPAT_VENDOR. */
3185 ovs_be16 len; /* Length including slaves. */
3186 ovs_be32 vendor; /* NX_VENDOR_ID. */
3187 ovs_be16 subtype; /* NXAST_DEC_TTL_CNT_IDS. */
3188
3189 ovs_be16 n_controllers; /* Number of controllers. */
3190 uint8_t zeros[4]; /* Must be zero. */
3191
3192 /* Followed by 1 or more controller ids.
3193 *
3194 * uint16_t cnt_ids[]; // Controller ids.
3195 * uint8_t pad[]; // Must be 0 to 8-byte align cnt_ids[].
3196 */
3197};
3198OFP_ASSERT(sizeof(struct nx_action_cnt_ids) == 16);
3199
3200static enum ofperr
3201decode_OFPAT_RAW_DEC_NW_TTL(struct ofpbuf *out)
3202{
3203 uint16_t id = 0;
3204 struct ofpact_cnt_ids *ids;
3205 enum ofperr error = 0;
3206
3207 ids = ofpact_put_DEC_TTL(out);
3208 ids->n_controllers = 1;
3209 ofpbuf_put(out, &id, sizeof id);
6fd6ed71 3210 ids = out->header;
ce058104 3211 ofpact_finish_DEC_TTL(out, &ids);
c2d936a4
BP
3212 return error;
3213}
3214
3215static enum ofperr
3216decode_NXAST_RAW_DEC_TTL_CNT_IDS(const struct nx_action_cnt_ids *nac_ids,
f3cd3ac7 3217 enum ofp_version ofp_version OVS_UNUSED,
c2d936a4
BP
3218 struct ofpbuf *out)
3219{
3220 struct ofpact_cnt_ids *ids;
3221 size_t ids_size;
3222 int i;
3223
3224 ids = ofpact_put_DEC_TTL(out);
3225 ids->ofpact.raw = NXAST_RAW_DEC_TTL_CNT_IDS;
3226 ids->n_controllers = ntohs(nac_ids->n_controllers);
3227 ids_size = ntohs(nac_ids->len) - sizeof *nac_ids;
3228
3229 if (!is_all_zeros(nac_ids->zeros, sizeof nac_ids->zeros)) {
3230 return OFPERR_NXBRC_MUST_BE_ZERO;
8e97815e 3231 }
c2d936a4
BP
3232
3233 if (ids_size < ids->n_controllers * sizeof(ovs_be16)) {
3234 VLOG_WARN_RL(&rl, "Nicira action dec_ttl_cnt_ids only has %"PRIuSIZE" "
3235 "bytes allocated for controller ids. %"PRIuSIZE" bytes "
3236 "are required for %"PRIu16" controllers.",
3237 ids_size, ids->n_controllers * sizeof(ovs_be16),
3238 ids->n_controllers);
3239 return OFPERR_OFPBAC_BAD_LEN;
3240 }
3241
3242 for (i = 0; i < ids->n_controllers; i++) {
3243 uint16_t id = ntohs(((ovs_be16 *)(nac_ids + 1))[i]);
3244 ofpbuf_put(out, &id, sizeof id);
6fd6ed71 3245 ids = out->header;
c2d936a4
BP
3246 }
3247
ce058104 3248 ofpact_finish_DEC_TTL(out, &ids);
c2d936a4
BP
3249
3250 return 0;
8e97815e
BP
3251}
3252
c2d936a4
BP
3253static void
3254encode_DEC_TTL(const struct ofpact_cnt_ids *dec_ttl,
3255 enum ofp_version ofp_version, struct ofpbuf *out)
8e97815e 3256{
c2d936a4
BP
3257 if (dec_ttl->ofpact.raw == NXAST_RAW_DEC_TTL_CNT_IDS
3258 || dec_ttl->n_controllers != 1
3259 || dec_ttl->cnt_ids[0] != 0) {
3260 struct nx_action_cnt_ids *nac_ids = put_NXAST_DEC_TTL_CNT_IDS(out);
3261 int ids_len = ROUND_UP(2 * dec_ttl->n_controllers, OFP_ACTION_ALIGN);
3262 ovs_be16 *ids;
3263 size_t i;
8e97815e 3264
c2d936a4
BP
3265 nac_ids->len = htons(ntohs(nac_ids->len) + ids_len);
3266 nac_ids->n_controllers = htons(dec_ttl->n_controllers);
3267
3268 ids = ofpbuf_put_zeros(out, ids_len);
3269 for (i = 0; i < dec_ttl->n_controllers; i++) {
3270 ids[i] = htons(dec_ttl->cnt_ids[i]);
8e97815e 3271 }
c2d936a4
BP
3272 } else {
3273 put_OFPAT_DEC_NW_TTL(out, ofp_version);
8e97815e 3274 }
8e97815e
BP
3275}
3276
c2d936a4
BP
3277static void
3278parse_noargs_dec_ttl(struct ofpbuf *ofpacts)
d01c980f 3279{
c2d936a4
BP
3280 struct ofpact_cnt_ids *ids;
3281 uint16_t id = 0;
3282
3283 ofpact_put_DEC_TTL(ofpacts);
3284 ofpbuf_put(ofpacts, &id, sizeof id);
6fd6ed71 3285 ids = ofpacts->header;
c2d936a4 3286 ids->n_controllers++;
ce058104 3287 ofpact_finish_DEC_TTL(ofpacts, &ids);
d01c980f
BP
3288}
3289
cab50449 3290static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
3291parse_DEC_TTL(char *arg, struct ofpbuf *ofpacts,
3292 enum ofputil_protocol *usable_protocols OVS_UNUSED)
d01c980f 3293{
c2d936a4
BP
3294 if (*arg == '\0') {
3295 parse_noargs_dec_ttl(ofpacts);
3296 } else {
3297 struct ofpact_cnt_ids *ids;
3298 char *cntr;
3299
3300 ids = ofpact_put_DEC_TTL(ofpacts);
3301 ids->ofpact.raw = NXAST_RAW_DEC_TTL_CNT_IDS;
3302 for (cntr = strtok_r(arg, ", ", &arg); cntr != NULL;
3303 cntr = strtok_r(NULL, ", ", &arg)) {
3304 uint16_t id = atoi(cntr);
3305
3306 ofpbuf_put(ofpacts, &id, sizeof id);
6fd6ed71 3307 ids = ofpacts->header;
c2d936a4
BP
3308 ids->n_controllers++;
3309 }
3310 if (!ids->n_controllers) {
3311 return xstrdup("dec_ttl_cnt_ids: expected at least one controller "
3312 "id.");
3313 }
ce058104 3314 ofpact_finish_DEC_TTL(ofpacts, &ids);
c2d936a4
BP
3315 }
3316 return NULL;
d01c980f
BP
3317}
3318
c2d936a4
BP
3319static void
3320format_DEC_TTL(const struct ofpact_cnt_ids *a, struct ds *s)
d01c980f 3321{
c2d936a4 3322 size_t i;
d01c980f 3323
b1c5bf1f 3324 ds_put_format(s, "%sdec_ttl%s", colors.paren, colors.end);
c2d936a4 3325 if (a->ofpact.raw == NXAST_RAW_DEC_TTL_CNT_IDS) {
b1c5bf1f 3326 ds_put_format(s, "%s(%s", colors.paren, colors.end);
c2d936a4
BP
3327 for (i = 0; i < a->n_controllers; i++) {
3328 if (i) {
3329 ds_put_cstr(s, ",");
d01c980f 3330 }
c2d936a4
BP
3331 ds_put_format(s, "%"PRIu16, a->cnt_ids[i]);
3332 }
b1c5bf1f 3333 ds_put_format(s, "%s)%s", colors.paren, colors.end);
d01c980f
BP
3334 }
3335}
c2d936a4
BP
3336\f
3337/* Set MPLS label actions. */
d01c980f
BP
3338
3339static enum ofperr
f3cd3ac7
JS
3340decode_OFPAT_RAW_SET_MPLS_LABEL(ovs_be32 label,
3341 enum ofp_version ofp_version OVS_UNUSED,
3342 struct ofpbuf *out)
d01c980f 3343{
c2d936a4
BP
3344 ofpact_put_SET_MPLS_LABEL(out)->label = label;
3345 return 0;
3346}
d01c980f 3347
c2d936a4
BP
3348static void
3349encode_SET_MPLS_LABEL(const struct ofpact_mpls_label *label,
3350 enum ofp_version ofp_version,
3351 struct ofpbuf *out)
3352{
3353 if (ofp_version < OFP12_VERSION) {
3354 put_OFPAT_SET_MPLS_LABEL(out, ofp_version, label->label);
3355 } else {
128684a6 3356 put_set_field(out, ofp_version, MFF_MPLS_LABEL, ntohl(label->label));
d01c980f 3357 }
c2d936a4 3358}
d01c980f 3359
cab50449 3360static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
3361parse_SET_MPLS_LABEL(char *arg, struct ofpbuf *ofpacts,
3362 enum ofputil_protocol *usable_protocols OVS_UNUSED)
3363{
3364 struct ofpact_mpls_label *mpls_label = ofpact_put_SET_MPLS_LABEL(ofpacts);
3365 if (*arg == '\0') {
3366 return xstrdup("set_mpls_label: expected label.");
d01c980f 3367 }
c2d936a4
BP
3368
3369 mpls_label->label = htonl(atoi(arg));
3370 return NULL;
d01c980f
BP
3371}
3372
3373static void
c2d936a4 3374format_SET_MPLS_LABEL(const struct ofpact_mpls_label *a, struct ds *s)
d01c980f 3375{
b1c5bf1f
QM
3376 ds_put_format(s, "%sset_mpls_label(%s%"PRIu32"%s)%s",
3377 colors.paren, colors.end, ntohl(a->label),
3378 colors.paren, colors.end);
d01c980f 3379}
c2d936a4
BP
3380\f
3381/* Set MPLS TC actions. */
d01c980f 3382
c2d936a4 3383static enum ofperr
f3cd3ac7
JS
3384decode_OFPAT_RAW_SET_MPLS_TC(uint8_t tc,
3385 enum ofp_version ofp_version OVS_UNUSED,
3386 struct ofpbuf *out)
d01c980f 3387{
c2d936a4
BP
3388 ofpact_put_SET_MPLS_TC(out)->tc = tc;
3389 return 0;
3390}
d01c980f 3391
c2d936a4
BP
3392static void
3393encode_SET_MPLS_TC(const struct ofpact_mpls_tc *tc,
3394 enum ofp_version ofp_version, struct ofpbuf *out)
3395{
3396 if (ofp_version < OFP12_VERSION) {
3397 put_OFPAT_SET_MPLS_TC(out, ofp_version, tc->tc);
3398 } else {
128684a6 3399 put_set_field(out, ofp_version, MFF_MPLS_TC, tc->tc);
8f2cded4 3400 }
c2d936a4 3401}
8f2cded4 3402
cab50449 3403static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
3404parse_SET_MPLS_TC(char *arg, struct ofpbuf *ofpacts,
3405 enum ofputil_protocol *usable_protocols OVS_UNUSED)
3406{
3407 struct ofpact_mpls_tc *mpls_tc = ofpact_put_SET_MPLS_TC(ofpacts);
d01c980f 3408
c2d936a4
BP
3409 if (*arg == '\0') {
3410 return xstrdup("set_mpls_tc: expected tc.");
d01c980f
BP
3411 }
3412
c2d936a4
BP
3413 mpls_tc->tc = atoi(arg);
3414 return NULL;
3415}
d01c980f 3416
c2d936a4
BP
3417static void
3418format_SET_MPLS_TC(const struct ofpact_mpls_tc *a, struct ds *s)
3419{
b1c5bf1f
QM
3420 ds_put_format(s, "%sset_mpls_ttl(%s%"PRIu8"%s)%s",
3421 colors.paren, colors.end, a->tc,
3422 colors.paren, colors.end);
c2d936a4
BP
3423}
3424\f
3425/* Set MPLS TTL actions. */
d01c980f 3426
c2d936a4 3427static enum ofperr
f3cd3ac7
JS
3428decode_OFPAT_RAW_SET_MPLS_TTL(uint8_t ttl,
3429 enum ofp_version ofp_version OVS_UNUSED,
3430 struct ofpbuf *out)
c2d936a4
BP
3431{
3432 ofpact_put_SET_MPLS_TTL(out)->ttl = ttl;
3433 return 0;
3434}
638a19b0 3435
c2d936a4
BP
3436static void
3437encode_SET_MPLS_TTL(const struct ofpact_mpls_ttl *ttl,
3438 enum ofp_version ofp_version, struct ofpbuf *out)
3439{
3440 put_OFPAT_SET_MPLS_TTL(out, ofp_version, ttl->ttl);
3441}
638a19b0 3442
c2d936a4
BP
3443/* Parses 'arg' as the argument to a "set_mpls_ttl" action, and appends such an
3444 * action to 'ofpacts'.
3445 *
3446 * Returns NULL if successful, otherwise a malloc()'d string describing the
3447 * error. The caller is responsible for freeing the returned string. */
cab50449 3448static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
3449parse_SET_MPLS_TTL(char *arg, struct ofpbuf *ofpacts,
3450 enum ofputil_protocol *usable_protocols OVS_UNUSED)
3451{
3452 struct ofpact_mpls_ttl *mpls_ttl = ofpact_put_SET_MPLS_TTL(ofpacts);
d01c980f 3453
c2d936a4
BP
3454 if (*arg == '\0') {
3455 return xstrdup("set_mpls_ttl: expected ttl.");
b19e8793 3456 }
7fdb60a7 3457
c2d936a4
BP
3458 mpls_ttl->ttl = atoi(arg);
3459 return NULL;
3460}
4cceacb9 3461
c2d936a4
BP
3462static void
3463format_SET_MPLS_TTL(const struct ofpact_mpls_ttl *a, struct ds *s)
3464{
b1c5bf1f
QM
3465 ds_put_format(s, "%sset_mpls_ttl(%s%"PRIu8"%s)%s",
3466 colors.paren, colors.end, a->ttl,
3467 colors.paren, colors.end);
c2d936a4
BP
3468}
3469\f
3470/* Decrement MPLS TTL actions. */
4cceacb9 3471
c2d936a4
BP
3472static enum ofperr
3473decode_OFPAT_RAW_DEC_MPLS_TTL(struct ofpbuf *out)
3474{
3475 ofpact_put_DEC_MPLS_TTL(out);
3476 return 0;
3477}
8dd54666 3478
c2d936a4
BP
3479static void
3480encode_DEC_MPLS_TTL(const struct ofpact_null *null OVS_UNUSED,
3481 enum ofp_version ofp_version, struct ofpbuf *out)
3482{
3483 put_OFPAT_DEC_MPLS_TTL(out, ofp_version);
3484}
3485
cab50449 3486static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
3487parse_DEC_MPLS_TTL(char *arg OVS_UNUSED, struct ofpbuf *ofpacts,
3488 enum ofputil_protocol *usable_protocols OVS_UNUSED)
3489{
3490 ofpact_put_DEC_MPLS_TTL(ofpacts);
3491 return NULL;
3492}
3493
3494static void
3495format_DEC_MPLS_TTL(const struct ofpact_null *a OVS_UNUSED, struct ds *s)
3496{
b1c5bf1f 3497 ds_put_format(s, "%sdec_mpls_ttl%s", colors.value, colors.end);
c2d936a4
BP
3498}
3499\f
3500/* Push MPLS label action. */
3501
3502static enum ofperr
f3cd3ac7
JS
3503decode_OFPAT_RAW_PUSH_MPLS(ovs_be16 ethertype,
3504 enum ofp_version ofp_version OVS_UNUSED,
3505 struct ofpbuf *out)
c2d936a4
BP
3506{
3507 struct ofpact_push_mpls *oam;
3508
3509 if (!eth_type_mpls(ethertype)) {
3510 return OFPERR_OFPBAC_BAD_ARGUMENT;
8dd54666 3511 }
c2d936a4
BP
3512 oam = ofpact_put_PUSH_MPLS(out);
3513 oam->ethertype = ethertype;
d01c980f 3514
c2d936a4
BP
3515 return 0;
3516}
3517
3518static void
3519encode_PUSH_MPLS(const struct ofpact_push_mpls *push_mpls,
3520 enum ofp_version ofp_version, struct ofpbuf *out)
3521{
3522 put_OFPAT_PUSH_MPLS(out, ofp_version, push_mpls->ethertype);
3523}
3524
cab50449 3525static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
3526parse_PUSH_MPLS(char *arg, struct ofpbuf *ofpacts,
3527 enum ofputil_protocol *usable_protocols OVS_UNUSED)
3528{
3529 uint16_t ethertype;
3530 char *error;
3531
3532 error = str_to_u16(arg, "push_mpls", &ethertype);
3533 if (!error) {
3534 ofpact_put_PUSH_MPLS(ofpacts)->ethertype = htons(ethertype);
d01c980f
BP
3535 }
3536 return error;
3537}
c2d936a4
BP
3538
3539static void
3540format_PUSH_MPLS(const struct ofpact_push_mpls *a, struct ds *s)
3541{
b1c5bf1f
QM
3542 ds_put_format(s, "%spush_mpls:%s0x%04"PRIx16,
3543 colors.param, colors.end, ntohs(a->ethertype));
c2d936a4 3544}
d01c980f 3545\f
c2d936a4
BP
3546/* Pop MPLS label action. */
3547
3548static enum ofperr
f3cd3ac7
JS
3549decode_OFPAT_RAW_POP_MPLS(ovs_be16 ethertype,
3550 enum ofp_version ofp_version OVS_UNUSED,
3551 struct ofpbuf *out)
57ad4e9e 3552{
c2d936a4
BP
3553 ofpact_put_POP_MPLS(out)->ethertype = ethertype;
3554 return 0;
3555}
57ad4e9e 3556
c2d936a4
BP
3557static void
3558encode_POP_MPLS(const struct ofpact_pop_mpls *pop_mpls,
3559 enum ofp_version ofp_version, struct ofpbuf *out)
3560{
3561 put_OFPAT_POP_MPLS(out, ofp_version, pop_mpls->ethertype);
3562}
3563
cab50449 3564static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
3565parse_POP_MPLS(char *arg, struct ofpbuf *ofpacts,
3566 enum ofputil_protocol *usable_protocols OVS_UNUSED)
3567{
3568 uint16_t ethertype;
3569 char *error;
3570
3571 error = str_to_u16(arg, "pop_mpls", &ethertype);
3572 if (!error) {
3573 ofpact_put_POP_MPLS(ofpacts)->ethertype = htons(ethertype);
57ad4e9e 3574 }
c2d936a4 3575 return error;
57ad4e9e
BP
3576}
3577
ba2fe8e9 3578static void
c2d936a4 3579format_POP_MPLS(const struct ofpact_pop_mpls *a, struct ds *s)
ba2fe8e9 3580{
b1c5bf1f
QM
3581 ds_put_format(s, "%spop_mpls:%s0x%04"PRIx16,
3582 colors.param, colors.end, ntohs(a->ethertype));
ba2fe8e9 3583}
c2d936a4
BP
3584\f
3585/* Set tunnel ID actions. */
ba2fe8e9 3586
f25d0cf3 3587static enum ofperr
f3cd3ac7
JS
3588decode_NXAST_RAW_SET_TUNNEL(uint32_t tun_id,
3589 enum ofp_version ofp_version OVS_UNUSED,
3590 struct ofpbuf *out)
f25d0cf3 3591{
c2d936a4
BP
3592 struct ofpact_tunnel *tunnel = ofpact_put_SET_TUNNEL(out);
3593 tunnel->ofpact.raw = NXAST_RAW_SET_TUNNEL;
3594 tunnel->tun_id = tun_id;
3595 return 0;
3596}
f25d0cf3 3597
c2d936a4 3598static enum ofperr
f3cd3ac7
JS
3599decode_NXAST_RAW_SET_TUNNEL64(uint64_t tun_id,
3600 enum ofp_version ofp_version OVS_UNUSED,
3601 struct ofpbuf *out)
c2d936a4
BP
3602{
3603 struct ofpact_tunnel *tunnel = ofpact_put_SET_TUNNEL(out);
3604 tunnel->ofpact.raw = NXAST_RAW_SET_TUNNEL64;
3605 tunnel->tun_id = tun_id;
3606 return 0;
3607}
f25d0cf3 3608
c2d936a4
BP
3609static void
3610encode_SET_TUNNEL(const struct ofpact_tunnel *tunnel,
3611 enum ofp_version ofp_version, struct ofpbuf *out)
3612{
3613 uint64_t tun_id = tunnel->tun_id;
f25d0cf3 3614
c2d936a4
BP
3615 if (ofp_version < OFP12_VERSION) {
3616 if (tun_id <= UINT32_MAX
3617 && tunnel->ofpact.raw != NXAST_RAW_SET_TUNNEL64) {
3618 put_NXAST_SET_TUNNEL(out, tun_id);
3619 } else {
3620 put_NXAST_SET_TUNNEL64(out, tun_id);
f25d0cf3 3621 }
c2d936a4 3622 } else {
128684a6 3623 put_set_field(out, ofp_version, MFF_TUN_ID, tun_id);
c2d936a4
BP
3624 }
3625}
f25d0cf3 3626
cab50449 3627static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
3628parse_set_tunnel(char *arg, struct ofpbuf *ofpacts,
3629 enum ofp_raw_action_type raw)
3630{
3631 struct ofpact_tunnel *tunnel;
ca287d20 3632
c2d936a4
BP
3633 tunnel = ofpact_put_SET_TUNNEL(ofpacts);
3634 tunnel->ofpact.raw = raw;
3635 return str_to_u64(arg, &tunnel->tun_id);
3636}
8621547c 3637
cab50449 3638static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
3639parse_SET_TUNNEL(char *arg, struct ofpbuf *ofpacts,
3640 enum ofputil_protocol *usable_protocols OVS_UNUSED)
3641{
3642 return parse_set_tunnel(arg, ofpacts, NXAST_RAW_SET_TUNNEL);
3643}
8621547c 3644
c2d936a4
BP
3645static void
3646format_SET_TUNNEL(const struct ofpact_tunnel *a, struct ds *s)
3647{
b1c5bf1f 3648 ds_put_format(s, "%sset_tunnel%s:%s%#"PRIx64, colors.param,
c2d936a4
BP
3649 (a->tun_id > UINT32_MAX
3650 || a->ofpact.raw == NXAST_RAW_SET_TUNNEL64 ? "64" : ""),
b1c5bf1f 3651 colors.end, a->tun_id);
c2d936a4
BP
3652}
3653\f
3654/* Set queue action. */
8621547c 3655
c2d936a4 3656static enum ofperr
f3cd3ac7
JS
3657decode_OFPAT_RAW_SET_QUEUE(uint32_t queue_id,
3658 enum ofp_version ofp_version OVS_UNUSED,
3659 struct ofpbuf *out)
c2d936a4
BP
3660{
3661 ofpact_put_SET_QUEUE(out)->queue_id = queue_id;
3662 return 0;
3663}
8621547c 3664
c2d936a4
BP
3665static void
3666encode_SET_QUEUE(const struct ofpact_queue *queue,
3667 enum ofp_version ofp_version, struct ofpbuf *out)
3668{
3669 put_OFPAT_SET_QUEUE(out, ofp_version, queue->queue_id);
3670}
8621547c 3671
cab50449 3672static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
3673parse_SET_QUEUE(char *arg, struct ofpbuf *ofpacts,
3674 enum ofputil_protocol *usable_protocols OVS_UNUSED)
3675{
3676 return str_to_u32(arg, &ofpact_put_SET_QUEUE(ofpacts)->queue_id);
3677}
8621547c 3678
c2d936a4
BP
3679static void
3680format_SET_QUEUE(const struct ofpact_queue *a, struct ds *s)
3681{
b1c5bf1f
QM
3682 ds_put_format(s, "%sset_queue:%s%"PRIu32,
3683 colors.param, colors.end, a->queue_id);
c2d936a4
BP
3684}
3685\f
3686/* Pop queue action. */
1e7db674 3687
c2d936a4
BP
3688static enum ofperr
3689decode_NXAST_RAW_POP_QUEUE(struct ofpbuf *out)
3690{
3691 ofpact_put_POP_QUEUE(out);
3692 return 0;
3693}
f25d0cf3 3694
c2d936a4
BP
3695static void
3696encode_POP_QUEUE(const struct ofpact_null *null OVS_UNUSED,
3697 enum ofp_version ofp_version OVS_UNUSED, struct ofpbuf *out)
3698{
3699 put_NXAST_POP_QUEUE(out);
3700}
f25d0cf3 3701
cab50449 3702static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
3703parse_POP_QUEUE(const char *arg OVS_UNUSED, struct ofpbuf *ofpacts,
3704 enum ofputil_protocol *usable_protocols OVS_UNUSED)
3705{
3706 ofpact_put_POP_QUEUE(ofpacts);
3707 return NULL;
3708}
f25d0cf3 3709
c2d936a4
BP
3710static void
3711format_POP_QUEUE(const struct ofpact_null *a OVS_UNUSED, struct ds *s)
3712{
b1c5bf1f 3713 ds_put_format(s, "%spop_queue%s", colors.value, colors.end);
c2d936a4
BP
3714}
3715\f
3716/* Action structure for NXAST_FIN_TIMEOUT.
3717 *
3718 * This action changes the idle timeout or hard timeout, or both, of this
3719 * OpenFlow rule when the rule matches a TCP packet with the FIN or RST flag.
3720 * When such a packet is observed, the action reduces the rule's idle timeout
3721 * to 'fin_idle_timeout' and its hard timeout to 'fin_hard_timeout'. This
3722 * action has no effect on an existing timeout that is already shorter than the
3723 * one that the action specifies. A 'fin_idle_timeout' or 'fin_hard_timeout'
3724 * of zero has no effect on the respective timeout.
3725 *
3726 * 'fin_idle_timeout' and 'fin_hard_timeout' are measured in seconds.
3727 * 'fin_hard_timeout' specifies time since the flow's creation, not since the
3728 * receipt of the FIN or RST.
3729 *
3730 * This is useful for quickly discarding learned TCP flows that otherwise will
3731 * take a long time to expire.
3732 *
3733 * This action is intended for use with an OpenFlow rule that matches only a
3734 * single TCP flow. If the rule matches multiple TCP flows (e.g. it wildcards
3735 * all TCP traffic, or all TCP traffic to a particular port), then any FIN or
3736 * RST in any of those flows will cause the entire OpenFlow rule to expire
3737 * early, which is not normally desirable.
3738 */
3739struct nx_action_fin_timeout {
3740 ovs_be16 type; /* OFPAT_VENDOR. */
3741 ovs_be16 len; /* 16. */
3742 ovs_be32 vendor; /* NX_VENDOR_ID. */
3743 ovs_be16 subtype; /* NXAST_FIN_TIMEOUT. */
3744 ovs_be16 fin_idle_timeout; /* New idle timeout, if nonzero. */
3745 ovs_be16 fin_hard_timeout; /* New hard timeout, if nonzero. */
3746 ovs_be16 pad; /* Must be zero. */
3747};
3748OFP_ASSERT(sizeof(struct nx_action_fin_timeout) == 16);
f25d0cf3 3749
c2d936a4
BP
3750static enum ofperr
3751decode_NXAST_RAW_FIN_TIMEOUT(const struct nx_action_fin_timeout *naft,
f3cd3ac7 3752 enum ofp_version ofp_version OVS_UNUSED,
c2d936a4
BP
3753 struct ofpbuf *out)
3754{
3755 struct ofpact_fin_timeout *oft;
8621547c 3756
c2d936a4
BP
3757 oft = ofpact_put_FIN_TIMEOUT(out);
3758 oft->fin_idle_timeout = ntohs(naft->fin_idle_timeout);
3759 oft->fin_hard_timeout = ntohs(naft->fin_hard_timeout);
3760 return 0;
3761}
f25d0cf3 3762
c2d936a4
BP
3763static void
3764encode_FIN_TIMEOUT(const struct ofpact_fin_timeout *fin_timeout,
3765 enum ofp_version ofp_version OVS_UNUSED,
3766 struct ofpbuf *out)
3767{
3768 struct nx_action_fin_timeout *naft = put_NXAST_FIN_TIMEOUT(out);
3769 naft->fin_idle_timeout = htons(fin_timeout->fin_idle_timeout);
3770 naft->fin_hard_timeout = htons(fin_timeout->fin_hard_timeout);
3771}
f25d0cf3 3772
cab50449 3773static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
3774parse_FIN_TIMEOUT(char *arg, struct ofpbuf *ofpacts,
3775 enum ofputil_protocol *usable_protocols OVS_UNUSED)
3776{
3777 struct ofpact_fin_timeout *oft = ofpact_put_FIN_TIMEOUT(ofpacts);
3778 char *key, *value;
f25d0cf3 3779
c2d936a4
BP
3780 while (ofputil_parse_key_value(&arg, &key, &value)) {
3781 char *error;
b02475c5 3782
c2d936a4
BP
3783 if (!strcmp(key, "idle_timeout")) {
3784 error = str_to_u16(value, key, &oft->fin_idle_timeout);
3785 } else if (!strcmp(key, "hard_timeout")) {
3786 error = str_to_u16(value, key, &oft->fin_hard_timeout);
3787 } else {
3788 error = xasprintf("invalid key '%s' in 'fin_timeout' argument",
3789 key);
8621547c 3790 }
8dd54666 3791
c2d936a4
BP
3792 if (error) {
3793 return error;
9cae45dc 3794 }
9cae45dc 3795 }
c2d936a4
BP
3796 return NULL;
3797}
e3b56933 3798
c2d936a4
BP
3799static void
3800format_FIN_TIMEOUT(const struct ofpact_fin_timeout *a, struct ds *s)
3801{
b1c5bf1f 3802 ds_put_format(s, "%sfin_timeout(%s", colors.paren, colors.end);
c2d936a4 3803 if (a->fin_idle_timeout) {
b1c5bf1f
QM
3804 ds_put_format(s, "%sidle_timeout=%s%"PRIu16",",
3805 colors.param, colors.end, a->fin_idle_timeout);
7e9f8266 3806 }
c2d936a4 3807 if (a->fin_hard_timeout) {
b1c5bf1f
QM
3808 ds_put_format(s, "%shard_timeout=%s%"PRIu16",",
3809 colors.param, colors.end, a->fin_hard_timeout);
f25d0cf3 3810 }
c2d936a4 3811 ds_chomp(s, ',');
b1c5bf1f 3812 ds_put_format(s, "%s)%s", colors.paren, colors.end);
f25d0cf3 3813}
c2d936a4
BP
3814\f
3815/* Action structures for NXAST_RESUBMIT and NXAST_RESUBMIT_TABLE.
eca39bce 3816 *
c2d936a4 3817 * These actions search one of the switch's flow tables:
ba2fe8e9 3818 *
c2d936a4
BP
3819 * - For NXAST_RESUBMIT_TABLE only, if the 'table' member is not 255, then
3820 * it specifies the table to search.
ca287d20 3821 *
c2d936a4
BP
3822 * - Otherwise (for NXAST_RESUBMIT_TABLE with a 'table' of 255, or for
3823 * NXAST_RESUBMIT regardless of 'table'), it searches the current flow
3824 * table, that is, the OpenFlow flow table that contains the flow from
3825 * which this action was obtained. If this action did not come from a
3826 * flow table (e.g. it came from an OFPT_PACKET_OUT message), then table 0
3827 * is the current table.
3828 *
3829 * The flow table lookup uses a flow that may be slightly modified from the
3830 * original lookup:
3831 *
3832 * - For NXAST_RESUBMIT, the 'in_port' member of struct nx_action_resubmit
3833 * is used as the flow's in_port.
3834 *
3835 * - For NXAST_RESUBMIT_TABLE, if the 'in_port' member is not OFPP_IN_PORT,
3836 * then its value is used as the flow's in_port. Otherwise, the original
3837 * in_port is used.
3838 *
3839 * - If actions that modify the flow (e.g. OFPAT_SET_VLAN_VID) precede the
3840 * resubmit action, then the flow is updated with the new values.
3841 *
3842 * Following the lookup, the original in_port is restored.
3843 *
3844 * If the modified flow matched in the flow table, then the corresponding
3845 * actions are executed. Afterward, actions following the resubmit in the
3846 * original set of actions, if any, are executed; any changes made to the
3847 * packet (e.g. changes to VLAN) by secondary actions persist when those
3848 * actions are executed, although the original in_port is restored.
3849 *
3850 * Resubmit actions may be used any number of times within a set of actions.
3851 *
790c5d26
BP
3852 * Resubmit actions may nest. To prevent infinite loops and excessive resource
3853 * use, the implementation may limit nesting depth and the total number of
3854 * resubmits:
3855 *
3856 * - Open vSwitch 1.0.1 and earlier did not support recursion.
3857 *
3858 * - Open vSwitch 1.0.2 and 1.0.3 limited recursion to 8 levels.
3859 *
3860 * - Open vSwitch 1.1 and 1.2 limited recursion to 16 levels.
3861 *
3862 * - Open vSwitch 1.2 through 1.8 limited recursion to 32 levels.
3863 *
3864 * - Open vSwitch 1.9 through 2.0 limited recursion to 64 levels.
3865 *
3866 * - Open vSwitch 2.1 through 2.5 limited recursion to 64 levels and impose
3867 * a total limit of 4,096 resubmits per flow translation (earlier versions
3868 * did not impose any total limit).
c2d936a4
BP
3869 *
3870 * NXAST_RESUBMIT ignores 'table' and 'pad'. NXAST_RESUBMIT_TABLE requires
3871 * 'pad' to be all-bits-zero.
3872 *
3873 * Open vSwitch 1.0.1 and earlier did not support recursion. Open vSwitch
3874 * before 1.2.90 did not support NXAST_RESUBMIT_TABLE.
3875 */
3876struct nx_action_resubmit {
3877 ovs_be16 type; /* OFPAT_VENDOR. */
3878 ovs_be16 len; /* Length is 16. */
3879 ovs_be32 vendor; /* NX_VENDOR_ID. */
3880 ovs_be16 subtype; /* NXAST_RESUBMIT. */
3881 ovs_be16 in_port; /* New in_port for checking flow table. */
3882 uint8_t table; /* NXAST_RESUBMIT_TABLE: table to use. */
3883 uint8_t pad[3];
3884};
3885OFP_ASSERT(sizeof(struct nx_action_resubmit) == 16);
3886
3887static enum ofperr
f3cd3ac7
JS
3888decode_NXAST_RAW_RESUBMIT(uint16_t port,
3889 enum ofp_version ofp_version OVS_UNUSED,
3890 struct ofpbuf *out)
f25d0cf3 3891{
c2d936a4 3892 struct ofpact_resubmit *resubmit;
f25d0cf3 3893
c2d936a4
BP
3894 resubmit = ofpact_put_RESUBMIT(out);
3895 resubmit->ofpact.raw = NXAST_RAW_RESUBMIT;
3896 resubmit->in_port = u16_to_ofp(port);
3897 resubmit->table_id = 0xff;
3898 return 0;
f25d0cf3 3899}
4cceacb9 3900
c2d936a4
BP
3901static enum ofperr
3902decode_NXAST_RAW_RESUBMIT_TABLE(const struct nx_action_resubmit *nar,
f3cd3ac7 3903 enum ofp_version ofp_version OVS_UNUSED,
c2d936a4 3904 struct ofpbuf *out)
ba2fe8e9 3905{
c2d936a4 3906 struct ofpact_resubmit *resubmit;
ba2fe8e9 3907
c2d936a4
BP
3908 if (nar->pad[0] || nar->pad[1] || nar->pad[2]) {
3909 return OFPERR_OFPBAC_BAD_ARGUMENT;
3910 }
3911
3912 resubmit = ofpact_put_RESUBMIT(out);
3913 resubmit->ofpact.raw = NXAST_RAW_RESUBMIT_TABLE;
3914 resubmit->in_port = u16_to_ofp(ntohs(nar->in_port));
3915 resubmit->table_id = nar->table;
3916 return 0;
ba2fe8e9
BP
3917}
3918
c2d936a4
BP
3919static void
3920encode_RESUBMIT(const struct ofpact_resubmit *resubmit,
3921 enum ofp_version ofp_version OVS_UNUSED, struct ofpbuf *out)
4cceacb9 3922{
c2d936a4 3923 uint16_t in_port = ofp_to_u16(resubmit->in_port);
4cceacb9 3924
c2d936a4
BP
3925 if (resubmit->table_id == 0xff
3926 && resubmit->ofpact.raw != NXAST_RAW_RESUBMIT_TABLE) {
3927 put_NXAST_RESUBMIT(out, in_port);
3928 } else {
3929 struct nx_action_resubmit *nar = put_NXAST_RESUBMIT_TABLE(out);
3930 nar->table = resubmit->table_id;
3931 nar->in_port = htons(in_port);
3932 }
3933}
6813ee7c 3934
cab50449 3935static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
3936parse_RESUBMIT(char *arg, struct ofpbuf *ofpacts,
3937 enum ofputil_protocol *usable_protocols OVS_UNUSED)
3938{
3939 struct ofpact_resubmit *resubmit;
3940 char *in_port_s, *table_s;
6813ee7c 3941
c2d936a4 3942 resubmit = ofpact_put_RESUBMIT(ofpacts);
8f2cded4 3943
c2d936a4
BP
3944 in_port_s = strsep(&arg, ",");
3945 if (in_port_s && in_port_s[0]) {
3946 if (!ofputil_port_from_string(in_port_s, &resubmit->in_port)) {
3947 return xasprintf("%s: resubmit to unknown port", in_port_s);
8f2cded4 3948 }
c2d936a4
BP
3949 } else {
3950 resubmit->in_port = OFPP_IN_PORT;
3951 }
4cceacb9 3952
c2d936a4
BP
3953 table_s = strsep(&arg, ",");
3954 if (table_s && table_s[0]) {
3955 uint32_t table_id = 0;
3956 char *error;
3957
3958 error = str_to_u32(table_s, &table_id);
3959 if (error) {
3960 return error;
3961 }
3962 resubmit->table_id = table_id;
3963 } else {
3964 resubmit->table_id = 255;
4cceacb9
JS
3965 }
3966
c2d936a4
BP
3967 if (resubmit->in_port == OFPP_IN_PORT && resubmit->table_id == 255) {
3968 return xstrdup("at least one \"in_port\" or \"table\" must be "
3969 "specified on resubmit");
3970 }
3971 return NULL;
3972}
3973
3974static void
3975format_RESUBMIT(const struct ofpact_resubmit *a, struct ds *s)
3976{
3977 if (a->in_port != OFPP_IN_PORT && a->table_id == 255) {
b1c5bf1f 3978 ds_put_format(s, "%sresubmit:%s", colors.special, colors.end);
c2d936a4
BP
3979 ofputil_format_port(a->in_port, s);
3980 } else {
b1c5bf1f 3981 ds_put_format(s, "%sresubmit(%s", colors.paren, colors.end);
c2d936a4
BP
3982 if (a->in_port != OFPP_IN_PORT) {
3983 ofputil_format_port(a->in_port, s);
3984 }
3985 ds_put_char(s, ',');
3986 if (a->table_id != 255) {
3987 ds_put_format(s, "%"PRIu8, a->table_id);
3988 }
b1c5bf1f 3989 ds_put_format(s, "%s)%s", colors.paren, colors.end);
c2d936a4
BP
3990 }
3991}
3992\f
3993/* Action structure for NXAST_LEARN.
3994 *
3995 * This action adds or modifies a flow in an OpenFlow table, similar to
3996 * OFPT_FLOW_MOD with OFPFC_MODIFY_STRICT as 'command'. The new flow has the
3997 * specified idle timeout, hard timeout, priority, cookie, and flags. The new
3998 * flow's match criteria and actions are built by applying each of the series
3999 * of flow_mod_spec elements included as part of the action.
4000 *
4001 * A flow_mod_spec starts with a 16-bit header. A header that is all-bits-0 is
4002 * a no-op used for padding the action as a whole to a multiple of 8 bytes in
4003 * length. Otherwise, the flow_mod_spec can be thought of as copying 'n_bits'
4004 * bits from a source to a destination. In this case, the header contains
4005 * multiple fields:
4006 *
4007 * 15 14 13 12 11 10 0
4008 * +------+---+------+---------------------------------+
4009 * | 0 |src| dst | n_bits |
4010 * +------+---+------+---------------------------------+
4011 *
4012 * The meaning and format of a flow_mod_spec depends on 'src' and 'dst'. The
4013 * following table summarizes the meaning of each possible combination.
4014 * Details follow the table:
4015 *
4016 * src dst meaning
4017 * --- --- ----------------------------------------------------------
4018 * 0 0 Add match criteria based on value in a field.
4019 * 1 0 Add match criteria based on an immediate value.
4020 * 0 1 Add NXAST_REG_LOAD action to copy field into a different field.
4021 * 1 1 Add NXAST_REG_LOAD action to load immediate value into a field.
4022 * 0 2 Add OFPAT_OUTPUT action to output to port from specified field.
4023 * All other combinations are undefined and not allowed.
4024 *
4025 * The flow_mod_spec header is followed by a source specification and a
4026 * destination specification. The format and meaning of the source
4027 * specification depends on 'src':
4028 *
4029 * - If 'src' is 0, the source bits are taken from a field in the flow to
4030 * which this action is attached. (This should be a wildcarded field. If
4031 * its value is fully specified then the source bits being copied have
4032 * constant values.)
4033 *
4034 * The source specification is an ovs_be32 'field' and an ovs_be16 'ofs'.
4035 * 'field' is an nxm_header with nxm_hasmask=0, and 'ofs' the starting bit
4036 * offset within that field. The source bits are field[ofs:ofs+n_bits-1].
4037 * 'field' and 'ofs' are subject to the same restrictions as the source
4038 * field in NXAST_REG_MOVE.
4039 *
4040 * - If 'src' is 1, the source bits are a constant value. The source
4041 * specification is (n_bits+15)/16*2 bytes long. Taking those bytes as a
4042 * number in network order, the source bits are the 'n_bits'
4043 * least-significant bits. The switch will report an error if other bits
4044 * in the constant are nonzero.
4045 *
4046 * The flow_mod_spec destination specification, for 'dst' of 0 or 1, is an
4047 * ovs_be32 'field' and an ovs_be16 'ofs'. 'field' is an nxm_header with
4048 * nxm_hasmask=0 and 'ofs' is a starting bit offset within that field. The
4049 * meaning of the flow_mod_spec depends on 'dst':
4050 *
4051 * - If 'dst' is 0, the flow_mod_spec specifies match criteria for the new
4052 * flow. The new flow matches only if bits field[ofs:ofs+n_bits-1] in a
4053 * packet equal the source bits. 'field' may be any nxm_header with
4054 * nxm_hasmask=0 that is allowed in NXT_FLOW_MOD.
4055 *
4056 * Order is significant. Earlier flow_mod_specs must satisfy any
4057 * prerequisites for matching fields specified later, by copying constant
4058 * values into prerequisite fields.
4059 *
4060 * The switch will reject flow_mod_specs that do not satisfy NXM masking
4061 * restrictions.
4062 *
4063 * - If 'dst' is 1, the flow_mod_spec specifies an NXAST_REG_LOAD action for
4064 * the new flow. The new flow copies the source bits into
4065 * field[ofs:ofs+n_bits-1]. Actions are executed in the same order as the
4066 * flow_mod_specs.
4067 *
4068 * A single NXAST_REG_LOAD action writes no more than 64 bits, so n_bits
4069 * greater than 64 yields multiple NXAST_REG_LOAD actions.
4070 *
4071 * The flow_mod_spec destination spec for 'dst' of 2 (when 'src' is 0) is
4072 * empty. It has the following meaning:
4073 *
4074 * - The flow_mod_spec specifies an OFPAT_OUTPUT action for the new flow.
4075 * The new flow outputs to the OpenFlow port specified by the source field.
4076 * Of the special output ports with value OFPP_MAX or larger, OFPP_IN_PORT,
4077 * OFPP_FLOOD, OFPP_LOCAL, and OFPP_ALL are supported. Other special ports
4078 * may not be used.
4079 *
4080 * Resource Management
4081 * -------------------
4082 *
4083 * A switch has a finite amount of flow table space available for learning.
4084 * When this space is exhausted, no new learning table entries will be learned
4085 * until some existing flow table entries expire. The controller should be
4086 * prepared to handle this by flooding (which can be implemented as a
4087 * low-priority flow).
4088 *
4089 * If a learned flow matches a single TCP stream with a relatively long
4090 * timeout, one may make the best of resource constraints by setting
4091 * 'fin_idle_timeout' or 'fin_hard_timeout' (both measured in seconds), or
4092 * both, to shorter timeouts. When either of these is specified as a nonzero
4093 * value, OVS adds a NXAST_FIN_TIMEOUT action, with the specified timeouts, to
4094 * the learned flow.
4095 *
4096 * Examples
4097 * --------
4098 *
4099 * The following examples give a prose description of the flow_mod_specs along
4100 * with informal notation for how those would be represented and a hex dump of
4101 * the bytes that would be required.
4102 *
4103 * These examples could work with various nx_action_learn parameters. Typical
4104 * values would be idle_timeout=OFP_FLOW_PERMANENT, hard_timeout=60,
4105 * priority=OFP_DEFAULT_PRIORITY, flags=0, table_id=10.
4106 *
4107 * 1. Learn input port based on the source MAC, with lookup into
4108 * NXM_NX_REG1[16:31] by resubmit to in_port=99:
4109 *
4110 * Match on in_port=99:
4111 * ovs_be16(src=1, dst=0, n_bits=16), 20 10
4112 * ovs_be16(99), 00 63
4113 * ovs_be32(NXM_OF_IN_PORT), ovs_be16(0) 00 00 00 02 00 00
4114 *
4115 * Match Ethernet destination on Ethernet source from packet:
4116 * ovs_be16(src=0, dst=0, n_bits=48), 00 30
4117 * ovs_be32(NXM_OF_ETH_SRC), ovs_be16(0) 00 00 04 06 00 00
4118 * ovs_be32(NXM_OF_ETH_DST), ovs_be16(0) 00 00 02 06 00 00
4119 *
4120 * Set NXM_NX_REG1[16:31] to the packet's input port:
4121 * ovs_be16(src=0, dst=1, n_bits=16), 08 10
4122 * ovs_be32(NXM_OF_IN_PORT), ovs_be16(0) 00 00 00 02 00 00
4123 * ovs_be32(NXM_NX_REG1), ovs_be16(16) 00 01 02 04 00 10
4124 *
4125 * Given a packet that arrived on port A with Ethernet source address B,
4126 * this would set up the flow "in_port=99, dl_dst=B,
4127 * actions=load:A->NXM_NX_REG1[16..31]".
4128 *
4129 * In syntax accepted by ovs-ofctl, this action is: learn(in_port=99,
4130 * NXM_OF_ETH_DST[]=NXM_OF_ETH_SRC[],
4131 * load:NXM_OF_IN_PORT[]->NXM_NX_REG1[16..31])
4132 *
4133 * 2. Output to input port based on the source MAC and VLAN VID, with lookup
4134 * into NXM_NX_REG1[16:31]:
4135 *
4136 * Match on same VLAN ID as packet:
4137 * ovs_be16(src=0, dst=0, n_bits=12), 00 0c
4138 * ovs_be32(NXM_OF_VLAN_TCI), ovs_be16(0) 00 00 08 02 00 00
4139 * ovs_be32(NXM_OF_VLAN_TCI), ovs_be16(0) 00 00 08 02 00 00
4140 *
4141 * Match Ethernet destination on Ethernet source from packet:
4142 * ovs_be16(src=0, dst=0, n_bits=48), 00 30
4143 * ovs_be32(NXM_OF_ETH_SRC), ovs_be16(0) 00 00 04 06 00 00
4144 * ovs_be32(NXM_OF_ETH_DST), ovs_be16(0) 00 00 02 06 00 00
4145 *
4146 * Output to the packet's input port:
4147 * ovs_be16(src=0, dst=2, n_bits=16), 10 10
4148 * ovs_be32(NXM_OF_IN_PORT), ovs_be16(0) 00 00 00 02 00 00
4149 *
4150 * Given a packet that arrived on port A with Ethernet source address B in
4151 * VLAN C, this would set up the flow "dl_dst=B, vlan_vid=C,
4152 * actions=output:A".
4153 *
4154 * In syntax accepted by ovs-ofctl, this action is:
4155 * learn(NXM_OF_VLAN_TCI[0..11], NXM_OF_ETH_DST[]=NXM_OF_ETH_SRC[],
4156 * output:NXM_OF_IN_PORT[])
4157 *
4158 * 3. Here's a recipe for a very simple-minded MAC learning switch. It uses a
4159 * 10-second MAC expiration time to make it easier to see what's going on
4160 *
4161 * ovs-vsctl del-controller br0
4162 * ovs-ofctl del-flows br0
4163 * ovs-ofctl add-flow br0 "table=0 actions=learn(table=1, \
4164 hard_timeout=10, NXM_OF_VLAN_TCI[0..11], \
4165 NXM_OF_ETH_DST[]=NXM_OF_ETH_SRC[], \
4166 output:NXM_OF_IN_PORT[]), resubmit(,1)"
4167 * ovs-ofctl add-flow br0 "table=1 priority=0 actions=flood"
4168 *
4169 * You can then dump the MAC learning table with:
4170 *
4171 * ovs-ofctl dump-flows br0 table=1
4172 *
4173 * Usage Advice
4174 * ------------
4175 *
4176 * For best performance, segregate learned flows into a table that is not used
4177 * for any other flows except possibly for a lowest-priority "catch-all" flow
4178 * (a flow with no match criteria). If different learning actions specify
4179 * different match criteria, use different tables for the learned flows.
4180 *
4181 * The meaning of 'hard_timeout' and 'idle_timeout' can be counterintuitive.
4182 * These timeouts apply to the flow that is added, which means that a flow with
4183 * an idle timeout will expire when no traffic has been sent *to* the learned
4184 * address. This is not usually the intent in MAC learning; instead, we want
4185 * the MAC learn entry to expire when no traffic has been sent *from* the
4186 * learned address. Use a hard timeout for that.
39c94593
JR
4187 *
4188 *
4189 * Visibility of Changes
4190 * ---------------------
4191 *
4192 * Prior to Open vSwitch 2.4, any changes made by a "learn" action in a given
4193 * flow translation are visible to flow table lookups made later in the flow
4194 * translation. This means that, in the example above, a MAC learned by the
4195 * learn action in table 0 would be found in table 1 (if the packet being
4196 * processed had the same source and destination MAC address).
4197 *
4198 * In Open vSwitch 2.4 and later, changes to a flow table (whether to add or
4199 * modify a flow) by a "learn" action are visible only for later flow
4200 * translations, not for later lookups within the same flow translation. In
4201 * the MAC learning example, a MAC learned by the learn action in table 0 would
4202 * not be found in table 1 if the flow translation would resubmit to table 1
4203 * after the processing of the learn action, meaning that if this MAC had not
4204 * been learned before then the packet would be flooded. */
c2d936a4
BP
4205struct nx_action_learn {
4206 ovs_be16 type; /* OFPAT_VENDOR. */
4207 ovs_be16 len; /* At least 24. */
4208 ovs_be32 vendor; /* NX_VENDOR_ID. */
4209 ovs_be16 subtype; /* NXAST_LEARN. */
4210 ovs_be16 idle_timeout; /* Idle time before discarding (seconds). */
4211 ovs_be16 hard_timeout; /* Max time before discarding (seconds). */
4212 ovs_be16 priority; /* Priority level of flow entry. */
4213 ovs_be64 cookie; /* Cookie for new flow. */
4214 ovs_be16 flags; /* NX_LEARN_F_*. */
4215 uint8_t table_id; /* Table to insert flow entry. */
4216 uint8_t pad; /* Must be zero. */
4217 ovs_be16 fin_idle_timeout; /* Idle timeout after FIN, if nonzero. */
4218 ovs_be16 fin_hard_timeout; /* Hard timeout after FIN, if nonzero. */
4219 /* Followed by a sequence of flow_mod_spec elements, as described above,
4220 * until the end of the action is reached. */
4221};
4222OFP_ASSERT(sizeof(struct nx_action_learn) == 32);
4223
4224static ovs_be16
4225get_be16(const void **pp)
4226{
4227 const ovs_be16 *p = *pp;
4228 ovs_be16 value = *p;
4229 *pp = p + 1;
4230 return value;
4231}
4232
4233static ovs_be32
4234get_be32(const void **pp)
4235{
4236 const ovs_be32 *p = *pp;
4237 ovs_be32 value = get_unaligned_be32(p);
4238 *pp = p + 1;
4239 return value;
4240}
4241
4242static void
4243get_subfield(int n_bits, const void **p, struct mf_subfield *sf)
4244{
4245 sf->field = mf_from_nxm_header(ntohl(get_be32(p)));
4246 sf->ofs = ntohs(get_be16(p));
4247 sf->n_bits = n_bits;
4248}
4249
4250static unsigned int
4251learn_min_len(uint16_t header)
4252{
4253 int n_bits = header & NX_LEARN_N_BITS_MASK;
4254 int src_type = header & NX_LEARN_SRC_MASK;
4255 int dst_type = header & NX_LEARN_DST_MASK;
4256 unsigned int min_len;
4257
4258 min_len = 0;
4259 if (src_type == NX_LEARN_SRC_FIELD) {
4260 min_len += sizeof(ovs_be32); /* src_field */
4261 min_len += sizeof(ovs_be16); /* src_ofs */
4262 } else {
4263 min_len += DIV_ROUND_UP(n_bits, 16);
4264 }
4265 if (dst_type == NX_LEARN_DST_MATCH ||
4266 dst_type == NX_LEARN_DST_LOAD) {
4267 min_len += sizeof(ovs_be32); /* dst_field */
4268 min_len += sizeof(ovs_be16); /* dst_ofs */
4269 }
4270 return min_len;
4271}
4272
4273/* Converts 'nal' into a "struct ofpact_learn" and appends that struct to
4274 * 'ofpacts'. Returns 0 if successful, otherwise an OFPERR_*. */
4275static enum ofperr
4276decode_NXAST_RAW_LEARN(const struct nx_action_learn *nal,
f3cd3ac7 4277 enum ofp_version ofp_version OVS_UNUSED,
c2d936a4
BP
4278 struct ofpbuf *ofpacts)
4279{
4280 struct ofpact_learn *learn;
4281 const void *p, *end;
4282
4283 if (nal->pad) {
4284 return OFPERR_OFPBAC_BAD_ARGUMENT;
4285 }
4286
4287 learn = ofpact_put_LEARN(ofpacts);
4288
4289 learn->idle_timeout = ntohs(nal->idle_timeout);
4290 learn->hard_timeout = ntohs(nal->hard_timeout);
4291 learn->priority = ntohs(nal->priority);
4292 learn->cookie = nal->cookie;
4293 learn->table_id = nal->table_id;
4294 learn->fin_idle_timeout = ntohs(nal->fin_idle_timeout);
4295 learn->fin_hard_timeout = ntohs(nal->fin_hard_timeout);
4296
4297 learn->flags = ntohs(nal->flags);
4298 if (learn->flags & ~(NX_LEARN_F_SEND_FLOW_REM |
4299 NX_LEARN_F_DELETE_LEARNED)) {
4300 return OFPERR_OFPBAC_BAD_ARGUMENT;
4301 }
4302
4303 if (learn->table_id == 0xff) {
4304 return OFPERR_OFPBAC_BAD_ARGUMENT;
4305 }
4306
4307 end = (char *) nal + ntohs(nal->len);
4308 for (p = nal + 1; p != end; ) {
4309 struct ofpact_learn_spec *spec;
4310 uint16_t header = ntohs(get_be16(&p));
4311
4312 if (!header) {
4313 break;
4314 }
4315
4316 spec = ofpbuf_put_zeros(ofpacts, sizeof *spec);
6fd6ed71 4317 learn = ofpacts->header;
c2d936a4
BP
4318
4319 spec->src_type = header & NX_LEARN_SRC_MASK;
4320 spec->dst_type = header & NX_LEARN_DST_MASK;
4321 spec->n_bits = header & NX_LEARN_N_BITS_MASK;
4322
4323 /* Check for valid src and dst type combination. */
4324 if (spec->dst_type == NX_LEARN_DST_MATCH ||
4325 spec->dst_type == NX_LEARN_DST_LOAD ||
4326 (spec->dst_type == NX_LEARN_DST_OUTPUT &&
4327 spec->src_type == NX_LEARN_SRC_FIELD)) {
4328 /* OK. */
4329 } else {
4330 return OFPERR_OFPBAC_BAD_ARGUMENT;
4331 }
4332
4333 /* Check that the arguments don't overrun the end of the action. */
4334 if ((char *) end - (char *) p < learn_min_len(header)) {
4335 return OFPERR_OFPBAC_BAD_LEN;
4336 }
4337
4338 /* Get the source. */
dfe191d5
JR
4339 const uint8_t *imm = NULL;
4340 unsigned int imm_bytes = 0;
c2d936a4
BP
4341 if (spec->src_type == NX_LEARN_SRC_FIELD) {
4342 get_subfield(spec->n_bits, &p, &spec->src);
4343 } else {
4344 int p_bytes = 2 * DIV_ROUND_UP(spec->n_bits, 16);
c2d936a4 4345 p = (const uint8_t *) p + p_bytes;
dfe191d5
JR
4346
4347 imm_bytes = DIV_ROUND_UP(spec->n_bits, 8);
4348 imm = (const uint8_t *) p - imm_bytes;
c2d936a4
BP
4349 }
4350
4351 /* Get the destination. */
4352 if (spec->dst_type == NX_LEARN_DST_MATCH ||
4353 spec->dst_type == NX_LEARN_DST_LOAD) {
4354 get_subfield(spec->n_bits, &p, &spec->dst);
4355 }
dfe191d5
JR
4356
4357 if (imm) {
4358 uint8_t *src_imm = ofpbuf_put_zeros(ofpacts,
4359 OFPACT_ALIGN(imm_bytes));
4360 memcpy(src_imm, imm, imm_bytes);
4361
4362 learn = ofpacts->header;
4363 }
c2d936a4 4364 }
ce058104 4365 ofpact_finish_LEARN(ofpacts, &learn);
c2d936a4
BP
4366
4367 if (!is_all_zeros(p, (char *) end - (char *) p)) {
4368 return OFPERR_OFPBAC_BAD_ARGUMENT;
4369 }
4370
4371 return 0;
4372}
4373
4374static void
4375put_be16(struct ofpbuf *b, ovs_be16 x)
4376{
4377 ofpbuf_put(b, &x, sizeof x);
4378}
4379
4380static void
4381put_be32(struct ofpbuf *b, ovs_be32 x)
4382{
4383 ofpbuf_put(b, &x, sizeof x);
4384}
4385
4386static void
4387put_u16(struct ofpbuf *b, uint16_t x)
4388{
4389 put_be16(b, htons(x));
4390}
4391
4392static void
4393put_u32(struct ofpbuf *b, uint32_t x)
4394{
4395 put_be32(b, htonl(x));
4396}
4397
4398static void
4399encode_LEARN(const struct ofpact_learn *learn,
4400 enum ofp_version ofp_version OVS_UNUSED, struct ofpbuf *out)
4401{
4402 const struct ofpact_learn_spec *spec;
4403 struct nx_action_learn *nal;
4404 size_t start_ofs;
4405
6fd6ed71 4406 start_ofs = out->size;
c2d936a4
BP
4407 nal = put_NXAST_LEARN(out);
4408 nal->idle_timeout = htons(learn->idle_timeout);
4409 nal->hard_timeout = htons(learn->hard_timeout);
4410 nal->fin_idle_timeout = htons(learn->fin_idle_timeout);
4411 nal->fin_hard_timeout = htons(learn->fin_hard_timeout);
4412 nal->priority = htons(learn->priority);
4413 nal->cookie = learn->cookie;
4414 nal->flags = htons(learn->flags);
4415 nal->table_id = learn->table_id;
4416
c65a31e2 4417 OFPACT_LEARN_SPEC_FOR_EACH (spec, learn) {
c2d936a4
BP
4418 put_u16(out, spec->n_bits | spec->dst_type | spec->src_type);
4419
4420 if (spec->src_type == NX_LEARN_SRC_FIELD) {
508a9338 4421 put_u32(out, mf_nxm_header(spec->src.field->id));
c2d936a4
BP
4422 put_u16(out, spec->src.ofs);
4423 } else {
4424 size_t n_dst_bytes = 2 * DIV_ROUND_UP(spec->n_bits, 16);
4425 uint8_t *bits = ofpbuf_put_zeros(out, n_dst_bytes);
507a9a16 4426 unsigned int n_bytes = DIV_ROUND_UP(spec->n_bits, 8);
dfe191d5 4427
507a9a16
JR
4428 memcpy(bits + n_dst_bytes - n_bytes, ofpact_learn_spec_imm(spec),
4429 n_bytes);
c2d936a4
BP
4430 }
4431
4432 if (spec->dst_type == NX_LEARN_DST_MATCH ||
4433 spec->dst_type == NX_LEARN_DST_LOAD) {
508a9338 4434 put_u32(out, mf_nxm_header(spec->dst.field->id));
c2d936a4
BP
4435 put_u16(out, spec->dst.ofs);
4436 }
4437 }
4438
178742f9 4439 pad_ofpat(out, start_ofs);
c2d936a4
BP
4440}
4441
cab50449 4442static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
4443parse_LEARN(char *arg, struct ofpbuf *ofpacts,
4444 enum ofputil_protocol *usable_protocols OVS_UNUSED)
4445{
4446 return learn_parse(arg, ofpacts);
4447}
4448
4449static void
4450format_LEARN(const struct ofpact_learn *a, struct ds *s)
4451{
4452 learn_format(a, s);
4453}
4454\f
18080541
BP
4455/* Action structure for NXAST_CONJUNCTION. */
4456struct nx_action_conjunction {
4457 ovs_be16 type; /* OFPAT_VENDOR. */
4458 ovs_be16 len; /* At least 16. */
4459 ovs_be32 vendor; /* NX_VENDOR_ID. */
4460 ovs_be16 subtype; /* See enum ofp_raw_action_type. */
4461 uint8_t clause;
4462 uint8_t n_clauses;
4463 ovs_be32 id;
4464};
4465OFP_ASSERT(sizeof(struct nx_action_conjunction) == 16);
4466
4467static void
4468add_conjunction(struct ofpbuf *out,
4469 uint32_t id, uint8_t clause, uint8_t n_clauses)
4470{
4471 struct ofpact_conjunction *oc;
4472
4473 oc = ofpact_put_CONJUNCTION(out);
4474 oc->id = id;
4475 oc->clause = clause;
4476 oc->n_clauses = n_clauses;
4477}
4478
4479static enum ofperr
4480decode_NXAST_RAW_CONJUNCTION(const struct nx_action_conjunction *nac,
f3cd3ac7 4481 enum ofp_version ofp_version OVS_UNUSED,
18080541
BP
4482 struct ofpbuf *out)
4483{
4484 if (nac->n_clauses < 2 || nac->n_clauses > 64
4485 || nac->clause >= nac->n_clauses) {
4486 return OFPERR_NXBAC_BAD_CONJUNCTION;
4487 } else {
4488 add_conjunction(out, ntohl(nac->id), nac->clause, nac->n_clauses);
4489 return 0;
4490 }
4491}
4492
4493static void
4494encode_CONJUNCTION(const struct ofpact_conjunction *oc,
4495 enum ofp_version ofp_version OVS_UNUSED, struct ofpbuf *out)
4496{
4497 struct nx_action_conjunction *nac = put_NXAST_CONJUNCTION(out);
4498 nac->clause = oc->clause;
4499 nac->n_clauses = oc->n_clauses;
4500 nac->id = htonl(oc->id);
4501}
4502
4503static void
4504format_CONJUNCTION(const struct ofpact_conjunction *oc, struct ds *s)
4505{
b1c5bf1f
QM
4506 ds_put_format(s, "%sconjunction(%s%"PRIu32",%"PRIu8"/%"PRIu8"%s)%s",
4507 colors.paren, colors.end,
4508 oc->id, oc->clause + 1, oc->n_clauses,
4509 colors.paren, colors.end);
18080541
BP
4510}
4511
4512static char * OVS_WARN_UNUSED_RESULT
4513parse_CONJUNCTION(const char *arg, struct ofpbuf *ofpacts,
4514 enum ofputil_protocol *usable_protocols OVS_UNUSED)
4515{
4516 uint8_t n_clauses;
4517 uint8_t clause;
4518 uint32_t id;
4519 int n;
4520
4521 if (!ovs_scan(arg, "%"SCNi32" , %"SCNu8" / %"SCNu8" %n",
4522 &id, &clause, &n_clauses, &n) || n != strlen(arg)) {
4523 return xstrdup("\"conjunction\" syntax is \"conjunction(id,i/n)\"");
4524 }
4525
4526 if (n_clauses < 2) {
4527 return xstrdup("conjunction must have at least 2 clauses");
4528 } else if (n_clauses > 64) {
4529 return xstrdup("conjunction must have at most 64 clauses");
4530 } else if (clause < 1) {
4531 return xstrdup("clause index must be positive");
4532 } else if (clause > n_clauses) {
4533 return xstrdup("clause index must be less than or equal to "
4534 "number of clauses");
4535 }
4536
4537 add_conjunction(ofpacts, id, clause - 1, n_clauses);
4538 return NULL;
4539}
4540\f
c2d936a4
BP
4541/* Action structure for NXAST_MULTIPATH.
4542 *
4543 * This action performs the following steps in sequence:
4544 *
4545 * 1. Hashes the fields designated by 'fields', one of NX_HASH_FIELDS_*.
4546 * Refer to the definition of "enum nx_mp_fields" for details.
4547 *
4548 * The 'basis' value is used as a universal hash parameter, that is,
4549 * different values of 'basis' yield different hash functions. The
4550 * particular universal hash function used is implementation-defined.
4551 *
4552 * The hashed fields' values are drawn from the current state of the
4553 * flow, including all modifications that have been made by actions up to
4554 * this point.
4555 *
4556 * 2. Applies the multipath link choice algorithm specified by 'algorithm',
4557 * one of NX_MP_ALG_*. Refer to the definition of "enum nx_mp_algorithm"
4558 * for details.
4559 *
4560 * The output of the algorithm is 'link', an unsigned integer less than
4561 * or equal to 'max_link'.
4562 *
4563 * Some algorithms use 'arg' as an additional argument.
4564 *
4565 * 3. Stores 'link' in dst[ofs:ofs+n_bits]. The format and semantics of
4566 * 'dst' and 'ofs_nbits' are similar to those for the NXAST_REG_LOAD
4567 * action.
4568 *
4569 * The switch will reject actions that have an unknown 'fields', or an unknown
4570 * 'algorithm', or in which ofs+n_bits is greater than the width of 'dst', or
4571 * in which 'max_link' is greater than or equal to 2**n_bits, with error type
4572 * OFPET_BAD_ACTION, code OFPBAC_BAD_ARGUMENT.
4573 */
4574struct nx_action_multipath {
4575 ovs_be16 type; /* OFPAT_VENDOR. */
4576 ovs_be16 len; /* Length is 32. */
4577 ovs_be32 vendor; /* NX_VENDOR_ID. */
4578 ovs_be16 subtype; /* NXAST_MULTIPATH. */
4579
4580 /* What fields to hash and how. */
4581 ovs_be16 fields; /* One of NX_HASH_FIELDS_*. */
4582 ovs_be16 basis; /* Universal hash parameter. */
4583 ovs_be16 pad0;
4584
4585 /* Multipath link choice algorithm to apply to hash value. */
4586 ovs_be16 algorithm; /* One of NX_MP_ALG_*. */
4587 ovs_be16 max_link; /* Number of output links, minus 1. */
4588 ovs_be32 arg; /* Algorithm-specific argument. */
4589 ovs_be16 pad1;
4590
4591 /* Where to store the result. */
4592 ovs_be16 ofs_nbits; /* (ofs << 6) | (n_bits - 1). */
4593 ovs_be32 dst; /* Destination. */
4594};
4595OFP_ASSERT(sizeof(struct nx_action_multipath) == 32);
4596
4597static enum ofperr
4598decode_NXAST_RAW_MULTIPATH(const struct nx_action_multipath *nam,
f3cd3ac7 4599 enum ofp_version ofp_version OVS_UNUSED,
c2d936a4
BP
4600 struct ofpbuf *out)
4601{
4602 uint32_t n_links = ntohs(nam->max_link) + 1;
4603 size_t min_n_bits = log_2_ceil(n_links);
4604 struct ofpact_multipath *mp;
4605
4606 mp = ofpact_put_MULTIPATH(out);
4607 mp->fields = ntohs(nam->fields);
4608 mp->basis = ntohs(nam->basis);
4609 mp->algorithm = ntohs(nam->algorithm);
4610 mp->max_link = ntohs(nam->max_link);
4611 mp->arg = ntohl(nam->arg);
4612 mp->dst.field = mf_from_nxm_header(ntohl(nam->dst));
4613 mp->dst.ofs = nxm_decode_ofs(nam->ofs_nbits);
4614 mp->dst.n_bits = nxm_decode_n_bits(nam->ofs_nbits);
4615
4616 if (!flow_hash_fields_valid(mp->fields)) {
4617 VLOG_WARN_RL(&rl, "unsupported fields %d", (int) mp->fields);
4618 return OFPERR_OFPBAC_BAD_ARGUMENT;
4619 } else if (mp->algorithm != NX_MP_ALG_MODULO_N
4620 && mp->algorithm != NX_MP_ALG_HASH_THRESHOLD
4621 && mp->algorithm != NX_MP_ALG_HRW
4622 && mp->algorithm != NX_MP_ALG_ITER_HASH) {
4623 VLOG_WARN_RL(&rl, "unsupported algorithm %d", (int) mp->algorithm);
4624 return OFPERR_OFPBAC_BAD_ARGUMENT;
4625 } else if (mp->dst.n_bits < min_n_bits) {
4626 VLOG_WARN_RL(&rl, "multipath action requires at least %"PRIuSIZE" bits for "
4627 "%"PRIu32" links", min_n_bits, n_links);
4628 return OFPERR_OFPBAC_BAD_ARGUMENT;
4629 }
4630
4631 return multipath_check(mp, NULL);
4632}
4633
4634static void
4635encode_MULTIPATH(const struct ofpact_multipath *mp,
4636 enum ofp_version ofp_version OVS_UNUSED, struct ofpbuf *out)
4637{
4638 struct nx_action_multipath *nam = put_NXAST_MULTIPATH(out);
4639
4640 nam->fields = htons(mp->fields);
4641 nam->basis = htons(mp->basis);
4642 nam->algorithm = htons(mp->algorithm);
4643 nam->max_link = htons(mp->max_link);
4644 nam->arg = htonl(mp->arg);
4645 nam->ofs_nbits = nxm_encode_ofs_nbits(mp->dst.ofs, mp->dst.n_bits);
508a9338 4646 nam->dst = htonl(mf_nxm_header(mp->dst.field->id));
c2d936a4
BP
4647}
4648
cab50449 4649static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
4650parse_MULTIPATH(const char *arg, struct ofpbuf *ofpacts,
4651 enum ofputil_protocol *usable_protocols OVS_UNUSED)
4652{
4653 return multipath_parse(ofpact_put_MULTIPATH(ofpacts), arg);
4654}
4655
4656static void
4657format_MULTIPATH(const struct ofpact_multipath *a, struct ds *s)
4658{
4659 multipath_format(a, s);
4660}
4661\f
4662/* Action structure for NXAST_NOTE.
4663 *
4664 * This action has no effect. It is variable length. The switch does not
4665 * attempt to interpret the user-defined 'note' data in any way. A controller
4666 * can use this action to attach arbitrary metadata to a flow.
4667 *
4668 * This action might go away in the future.
4669 */
4670struct nx_action_note {
4671 ovs_be16 type; /* OFPAT_VENDOR. */
4672 ovs_be16 len; /* A multiple of 8, but at least 16. */
4673 ovs_be32 vendor; /* NX_VENDOR_ID. */
4674 ovs_be16 subtype; /* NXAST_NOTE. */
4675 uint8_t note[6]; /* Start of user-defined data. */
4676 /* Possibly followed by additional user-defined data. */
4677};
4678OFP_ASSERT(sizeof(struct nx_action_note) == 16);
4679
4680static enum ofperr
f3cd3ac7
JS
4681decode_NXAST_RAW_NOTE(const struct nx_action_note *nan,
4682 enum ofp_version ofp_version OVS_UNUSED,
4683 struct ofpbuf *out)
c2d936a4
BP
4684{
4685 struct ofpact_note *note;
4686 unsigned int length;
4687
4688 length = ntohs(nan->len) - offsetof(struct nx_action_note, note);
2bd318de 4689 note = ofpact_put_NOTE(out);
c2d936a4 4690 note->length = length;
2bd318de 4691 ofpbuf_put(out, nan->note, length);
ace39a6f 4692 note = out->header;
ce058104 4693 ofpact_finish_NOTE(out, &note);
c2d936a4
BP
4694
4695 return 0;
4696}
4697
4698static void
4699encode_NOTE(const struct ofpact_note *note,
4700 enum ofp_version ofp_version OVS_UNUSED, struct ofpbuf *out)
4701{
6fd6ed71 4702 size_t start_ofs = out->size;
c2d936a4 4703 struct nx_action_note *nan;
c2d936a4
BP
4704
4705 put_NXAST_NOTE(out);
6fd6ed71 4706 out->size = out->size - sizeof nan->note;
c2d936a4
BP
4707
4708 ofpbuf_put(out, note->data, note->length);
9ac0aada 4709 pad_ofpat(out, start_ofs);
c2d936a4
BP
4710}
4711
cab50449 4712static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
4713parse_NOTE(const char *arg, struct ofpbuf *ofpacts,
4714 enum ofputil_protocol *usable_protocols OVS_UNUSED)
4715{
27aa8793
BP
4716 size_t start_ofs = ofpacts->size;
4717 ofpact_put_NOTE(ofpacts);
4718 arg = ofpbuf_put_hex(ofpacts, arg, NULL);
4719 if (arg[0]) {
4720 return xstrdup("bad hex digit in `note' argument");
4721 }
4722 struct ofpact_note *note = ofpbuf_at_assert(ofpacts, start_ofs,
4723 sizeof *note);
4724 note->length = ofpacts->size - (start_ofs + sizeof *note);
ce058104 4725 ofpact_finish_NOTE(ofpacts, &note);
c2d936a4
BP
4726 return NULL;
4727}
4728
4729static void
4730format_NOTE(const struct ofpact_note *a, struct ds *s)
4731{
b1c5bf1f 4732 ds_put_format(s, "%snote:%s", colors.param, colors.end);
bdcad671 4733 format_hex_arg(s, a->data, a->length);
c2d936a4
BP
4734}
4735\f
4736/* Exit action. */
4737
4738static enum ofperr
4739decode_NXAST_RAW_EXIT(struct ofpbuf *out)
4740{
4741 ofpact_put_EXIT(out);
4742 return 0;
4743}
4744
4745static void
4746encode_EXIT(const struct ofpact_null *null OVS_UNUSED,
4747 enum ofp_version ofp_version OVS_UNUSED, struct ofpbuf *out)
4748{
4749 put_NXAST_EXIT(out);
4750}
4751
cab50449 4752static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
4753parse_EXIT(char *arg OVS_UNUSED, struct ofpbuf *ofpacts,
4754 enum ofputil_protocol *usable_protocols OVS_UNUSED)
4755{
4756 ofpact_put_EXIT(ofpacts);
4757 return NULL;
4758}
4759
4760static void
4761format_EXIT(const struct ofpact_null *a OVS_UNUSED, struct ds *s)
4762{
b1c5bf1f 4763 ds_put_format(s, "%sexit%s", colors.special, colors.end);
c2d936a4
BP
4764}
4765\f
e672ff9b
JR
4766/* Unroll xlate action. */
4767
4768static void
4769encode_UNROLL_XLATE(const struct ofpact_unroll_xlate *unroll OVS_UNUSED,
4770 enum ofp_version ofp_version OVS_UNUSED,
4771 struct ofpbuf *out OVS_UNUSED)
4772{
4773 OVS_NOT_REACHED();
4774}
4775
4776static char * OVS_WARN_UNUSED_RESULT
4777parse_UNROLL_XLATE(char *arg OVS_UNUSED, struct ofpbuf *ofpacts OVS_UNUSED,
4778 enum ofputil_protocol *usable_protocols OVS_UNUSED)
4779{
4780 OVS_NOT_REACHED();
4781 return NULL;
4782}
4783
4784static void
28632a8a 4785format_UNROLL_XLATE(const struct ofpact_unroll_xlate *a, struct ds *s)
e672ff9b 4786{
b1c5bf1f
QM
4787 ds_put_format(s, "%sunroll_xlate(%s%stable=%s%"PRIu8
4788 ", %scookie=%s%"PRIu64"%s)%s",
4789 colors.paren, colors.end,
4790 colors.special, colors.end, a->rule_table_id,
4791 colors.param, colors.end, ntohll(a->rule_cookie),
4792 colors.paren, colors.end);
e672ff9b
JR
4793}
4794\f
7ae62a67
WT
4795/* The NXAST_CLONE action is "struct ext_action_header", followed by zero or
4796 * more embedded OpenFlow actions. */
4797
4798static enum ofperr
4799decode_NXAST_RAW_CLONE(const struct ext_action_header *eah,
4800 enum ofp_version ofp_version,
4801 struct ofpbuf *out)
4802{
4803 int error;
4804 struct ofpbuf openflow;
4805 const size_t clone_offset = ofpacts_pull(out);
4806 struct ofpact_nest *clone = ofpact_put_CLONE(out);
4807
4808 /* decode action list */
4809 ofpbuf_pull(out, sizeof(*clone));
4810 openflow = ofpbuf_const_initializer(
4811 eah + 1, ntohs(eah->len) - sizeof *eah);
4812 error = ofpacts_pull_openflow_actions__(&openflow, openflow.size,
4813 ofp_version,
4814 1u << OVSINST_OFPIT11_APPLY_ACTIONS,
4815 out, 0);
4816 clone = ofpbuf_push_uninit(out, sizeof *clone);
4817 out->header = &clone->ofpact;
4818 ofpact_finish_CLONE(out, &clone);
4819 ofpbuf_push_uninit(out, clone_offset);
4820 return error;
4821}
4822
4823static void
4824encode_CLONE(const struct ofpact_nest *clone,
4825 enum ofp_version ofp_version, struct ofpbuf *out)
4826{
4827 size_t len;
4828 const size_t ofs = out->size;
4829 struct ext_action_header *eah;
4830
4831 eah = put_NXAST_CLONE(out);
4832 len = ofpacts_put_openflow_actions(clone->actions,
4833 ofpact_nest_get_action_len(clone),
4834 out, ofp_version);
4835 len += sizeof *eah;
4836 eah = ofpbuf_at(out, ofs, sizeof *eah);
4837 eah->len = htons(len);
4838}
4839
4840static char * OVS_WARN_UNUSED_RESULT
4841parse_CLONE(char *arg, struct ofpbuf *ofpacts,
4842 enum ofputil_protocol *usable_protocols)
4843{
4844 const size_t clone_offset = ofpacts_pull(ofpacts);
4845 struct ofpact_nest *clone = ofpact_put_CLONE(ofpacts);
4846 char *error;
4847
4848 ofpbuf_pull(ofpacts, sizeof *clone);
4849 error = ofpacts_parse_copy(arg, ofpacts, usable_protocols, false, 0);
4850 /* header points to the action list */
4851 ofpacts->header = ofpbuf_push_uninit(ofpacts, sizeof *clone);
4852 clone = ofpacts->header;
4853
4854 ofpact_finish_CLONE(ofpacts, &clone);
4855 ofpbuf_push_uninit(ofpacts, clone_offset);
4856 return error;
4857}
4858
4859static void
4860format_CLONE(const struct ofpact_nest *a, struct ds *s)
4861{
4862 ds_put_format(s, "%sclone(%s", colors.paren, colors.end);
4863 ofpacts_format(a->actions, ofpact_nest_get_action_len(a), s);
4864 ds_put_format(s, "%s)%s", colors.paren, colors.end);
4865}
4866\f
c2d936a4
BP
4867/* Action structure for NXAST_SAMPLE.
4868 *
4869 * Samples matching packets with the given probability and sends them
4870 * each to the set of collectors identified with the given ID. The
4871 * probability is expressed as a number of packets to be sampled out
4872 * of USHRT_MAX packets, and must be >0.
4873 *
4874 * When sending packet samples to IPFIX collectors, the IPFIX flow
4875 * record sent for each sampled packet is associated with the given
4876 * observation domain ID and observation point ID. Each IPFIX flow
4877 * record contain the sampled packet's headers when executing this
4878 * rule. If a sampled packet's headers are modified by previous
4879 * actions in the flow, those modified headers are sent. */
4880struct nx_action_sample {
4881 ovs_be16 type; /* OFPAT_VENDOR. */
4882 ovs_be16 len; /* Length is 24. */
4883 ovs_be32 vendor; /* NX_VENDOR_ID. */
4884 ovs_be16 subtype; /* NXAST_SAMPLE. */
4885 ovs_be16 probability; /* Fraction of packets to sample. */
4886 ovs_be32 collector_set_id; /* ID of collector set in OVSDB. */
4887 ovs_be32 obs_domain_id; /* ID of sampling observation domain. */
4888 ovs_be32 obs_point_id; /* ID of sampling observation point. */
4889};
4890OFP_ASSERT(sizeof(struct nx_action_sample) == 24);
4891
4930ea56 4892/* Action structure for NXAST_SAMPLE2 and NXAST_SAMPLE3.
f69f713b 4893 *
4930ea56
BP
4894 * NXAST_SAMPLE2 was added in Open vSwitch 2.5.90. Compared to NXAST_SAMPLE,
4895 * it adds support for exporting egress tunnel information.
4896 *
4897 * NXAST_SAMPLE3 was added in Open vSwitch 2.6.90. Compared to NXAST_SAMPLE2,
4898 * it adds support for the 'direction' field. */
f69f713b
BY
4899struct nx_action_sample2 {
4900 ovs_be16 type; /* OFPAT_VENDOR. */
4901 ovs_be16 len; /* Length is 32. */
4902 ovs_be32 vendor; /* NX_VENDOR_ID. */
4903 ovs_be16 subtype; /* NXAST_SAMPLE. */
4904 ovs_be16 probability; /* Fraction of packets to sample. */
4905 ovs_be32 collector_set_id; /* ID of collector set in OVSDB. */
4906 ovs_be32 obs_domain_id; /* ID of sampling observation domain. */
4907 ovs_be32 obs_point_id; /* ID of sampling observation point. */
4908 ovs_be16 sampling_port; /* Sampling port. */
4930ea56
BP
4909 uint8_t direction; /* NXAST_SAMPLE3 only. */
4910 uint8_t zeros[5]; /* Pad to a multiple of 8 bytes */
f69f713b
BY
4911 };
4912 OFP_ASSERT(sizeof(struct nx_action_sample2) == 32);
4913
c2d936a4 4914static enum ofperr
f3cd3ac7
JS
4915decode_NXAST_RAW_SAMPLE(const struct nx_action_sample *nas,
4916 enum ofp_version ofp_version OVS_UNUSED,
4917 struct ofpbuf *out)
c2d936a4
BP
4918{
4919 struct ofpact_sample *sample;
4920
4921 sample = ofpact_put_SAMPLE(out);
f69f713b
BY
4922 sample->ofpact.raw = NXAST_RAW_SAMPLE;
4923 sample->probability = ntohs(nas->probability);
4924 sample->collector_set_id = ntohl(nas->collector_set_id);
4925 sample->obs_domain_id = ntohl(nas->obs_domain_id);
4926 sample->obs_point_id = ntohl(nas->obs_point_id);
f69f713b 4927 sample->sampling_port = OFPP_NONE;
4930ea56 4928 sample->direction = NX_ACTION_SAMPLE_DEFAULT;
f69f713b
BY
4929
4930 if (sample->probability == 0) {
4931 return OFPERR_OFPBAC_BAD_ARGUMENT;
4932 }
4933
4934 return 0;
4935}
4936
4937static enum ofperr
4930ea56
BP
4938decode_SAMPLE2(const struct nx_action_sample2 *nas,
4939 enum ofp_raw_action_type raw,
4940 enum nx_action_sample_direction direction,
4941 struct ofpact_sample *sample)
f69f713b 4942{
4930ea56 4943 sample->ofpact.raw = raw;
c2d936a4
BP
4944 sample->probability = ntohs(nas->probability);
4945 sample->collector_set_id = ntohl(nas->collector_set_id);
4946 sample->obs_domain_id = ntohl(nas->obs_domain_id);
4947 sample->obs_point_id = ntohl(nas->obs_point_id);
f69f713b 4948 sample->sampling_port = u16_to_ofp(ntohs(nas->sampling_port));
4930ea56 4949 sample->direction = direction;
c2d936a4
BP
4950
4951 if (sample->probability == 0) {
4952 return OFPERR_OFPBAC_BAD_ARGUMENT;
4953 }
4954
4955 return 0;
4956}
4957
4930ea56
BP
4958static enum ofperr
4959decode_NXAST_RAW_SAMPLE2(const struct nx_action_sample2 *nas,
4960 enum ofp_version ofp_version OVS_UNUSED,
4961 struct ofpbuf *out)
4962{
4963 return decode_SAMPLE2(nas, NXAST_RAW_SAMPLE2, NX_ACTION_SAMPLE_DEFAULT,
4964 ofpact_put_SAMPLE(out));
4965}
4966
4967static enum ofperr
4968decode_NXAST_RAW_SAMPLE3(const struct nx_action_sample2 *nas,
4969 enum ofp_version ofp_version OVS_UNUSED,
4970 struct ofpbuf *out)
4971{
4972 struct ofpact_sample *sample = ofpact_put_SAMPLE(out);
4973 if (!is_all_zeros(nas->zeros, sizeof nas->zeros)) {
4974 return OFPERR_NXBRC_MUST_BE_ZERO;
4975 }
4976 if (nas->direction != NX_ACTION_SAMPLE_DEFAULT &&
4977 nas->direction != NX_ACTION_SAMPLE_INGRESS &&
4978 nas->direction != NX_ACTION_SAMPLE_EGRESS) {
4979 VLOG_WARN_RL(&rl, "invalid sample direction %"PRIu8, nas->direction);
4980 return OFPERR_OFPBAC_BAD_ARGUMENT;
4981 }
4982 return decode_SAMPLE2(nas, NXAST_RAW_SAMPLE3, nas->direction, sample);
4983}
4984
4985static void
4986encode_SAMPLE2(const struct ofpact_sample *sample,
4987 struct nx_action_sample2 *nas)
4988{
4989 nas->probability = htons(sample->probability);
4990 nas->collector_set_id = htonl(sample->collector_set_id);
4991 nas->obs_domain_id = htonl(sample->obs_domain_id);
4992 nas->obs_point_id = htonl(sample->obs_point_id);
4993 nas->sampling_port = htons(ofp_to_u16(sample->sampling_port));
4994 nas->direction = sample->direction;
4995}
4996
c2d936a4
BP
4997static void
4998encode_SAMPLE(const struct ofpact_sample *sample,
4999 enum ofp_version ofp_version OVS_UNUSED, struct ofpbuf *out)
5000{
4930ea56
BP
5001 if (sample->ofpact.raw == NXAST_RAW_SAMPLE3
5002 || sample->direction != NX_ACTION_SAMPLE_DEFAULT) {
5003 encode_SAMPLE2(sample, put_NXAST_SAMPLE3(out));
5004 } else if (sample->ofpact.raw == NXAST_RAW_SAMPLE2
5005 || sample->sampling_port != OFPP_NONE) {
5006 encode_SAMPLE2(sample, put_NXAST_SAMPLE2(out));
f69f713b
BY
5007 } else {
5008 struct nx_action_sample *nas = put_NXAST_SAMPLE(out);
5009 nas->probability = htons(sample->probability);
5010 nas->collector_set_id = htonl(sample->collector_set_id);
5011 nas->obs_domain_id = htonl(sample->obs_domain_id);
5012 nas->obs_point_id = htonl(sample->obs_point_id);
5013 }
c2d936a4
BP
5014}
5015
5016/* Parses 'arg' as the argument to a "sample" action, and appends such an
5017 * action to 'ofpacts'.
5018 *
5019 * Returns NULL if successful, otherwise a malloc()'d string describing the
5020 * error. The caller is responsible for freeing the returned string. */
cab50449 5021static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
5022parse_SAMPLE(char *arg, struct ofpbuf *ofpacts,
5023 enum ofputil_protocol *usable_protocols OVS_UNUSED)
5024{
5025 struct ofpact_sample *os = ofpact_put_SAMPLE(ofpacts);
f69f713b 5026 os->sampling_port = OFPP_NONE;
4930ea56 5027 os->direction = NX_ACTION_SAMPLE_DEFAULT;
c2d936a4 5028
f69f713b 5029 char *key, *value;
c2d936a4
BP
5030 while (ofputil_parse_key_value(&arg, &key, &value)) {
5031 char *error = NULL;
5032
5033 if (!strcmp(key, "probability")) {
5034 error = str_to_u16(value, "probability", &os->probability);
5035 if (!error && os->probability == 0) {
5036 error = xasprintf("invalid probability value \"%s\"", value);
5037 }
5038 } else if (!strcmp(key, "collector_set_id")) {
5039 error = str_to_u32(value, &os->collector_set_id);
5040 } else if (!strcmp(key, "obs_domain_id")) {
5041 error = str_to_u32(value, &os->obs_domain_id);
5042 } else if (!strcmp(key, "obs_point_id")) {
5043 error = str_to_u32(value, &os->obs_point_id);
f69f713b
BY
5044 } else if (!strcmp(key, "sampling_port")) {
5045 if (!ofputil_port_from_string(value, &os->sampling_port)) {
5046 error = xasprintf("%s: unknown port", value);
5047 }
4930ea56
BP
5048 } else if (!strcmp(key, "ingress")) {
5049 os->direction = NX_ACTION_SAMPLE_INGRESS;
5050 } else if (!strcmp(key, "egress")) {
5051 os->direction = NX_ACTION_SAMPLE_EGRESS;
c2d936a4
BP
5052 } else {
5053 error = xasprintf("invalid key \"%s\" in \"sample\" argument",
5054 key);
5055 }
5056 if (error) {
5057 return error;
5058 }
5059 }
5060 if (os->probability == 0) {
5061 return xstrdup("non-zero \"probability\" must be specified on sample");
5062 }
f69f713b 5063
c2d936a4
BP
5064 return NULL;
5065}
5066
5067static void
5068format_SAMPLE(const struct ofpact_sample *a, struct ds *s)
5069{
b1c5bf1f
QM
5070 ds_put_format(s, "%ssample(%s%sprobability=%s%"PRIu16
5071 ",%scollector_set_id=%s%"PRIu32
5072 ",%sobs_domain_id=%s%"PRIu32
f69f713b 5073 ",%sobs_point_id=%s%"PRIu32,
b1c5bf1f
QM
5074 colors.paren, colors.end,
5075 colors.param, colors.end, a->probability,
5076 colors.param, colors.end, a->collector_set_id,
5077 colors.param, colors.end, a->obs_domain_id,
f69f713b
BY
5078 colors.param, colors.end, a->obs_point_id);
5079 if (a->sampling_port != OFPP_NONE) {
94783c7c 5080 ds_put_format(s, ",%ssampling_port=%s%"PRIu32,
f69f713b
BY
5081 colors.param, colors.end, a->sampling_port);
5082 }
4930ea56
BP
5083 if (a->direction == NX_ACTION_SAMPLE_INGRESS) {
5084 ds_put_format(s, ",%singress%s", colors.param, colors.end);
5085 } else if (a->direction == NX_ACTION_SAMPLE_EGRESS) {
5086 ds_put_format(s, ",%segress%s", colors.param, colors.end);
5087 }
f69f713b 5088 ds_put_format(s, "%s)%s", colors.paren, colors.end);
c2d936a4
BP
5089}
5090\f
d4abaff5
BP
5091/* debug_recirc instruction. */
5092
5093static bool enable_debug;
5094
5095void
5096ofpact_dummy_enable(void)
5097{
5098 enable_debug = true;
5099}
5100
5101static enum ofperr
5102decode_NXAST_RAW_DEBUG_RECIRC(struct ofpbuf *out)
5103{
5104 if (!enable_debug) {
5105 return OFPERR_OFPBAC_BAD_VENDOR_TYPE;
5106 }
5107
5108 ofpact_put_DEBUG_RECIRC(out);
5109 return 0;
5110}
5111
5112static void
5113encode_DEBUG_RECIRC(const struct ofpact_null *n OVS_UNUSED,
5114 enum ofp_version ofp_version OVS_UNUSED,
5115 struct ofpbuf *out)
5116{
5117 put_NXAST_DEBUG_RECIRC(out);
5118}
5119
5120static char * OVS_WARN_UNUSED_RESULT
5121parse_DEBUG_RECIRC(char *arg OVS_UNUSED, struct ofpbuf *ofpacts,
5122 enum ofputil_protocol *usable_protocols OVS_UNUSED)
5123{
5124 ofpact_put_DEBUG_RECIRC(ofpacts);
5125 return NULL;
5126}
5127
5128static void
5129format_DEBUG_RECIRC(const struct ofpact_null *a OVS_UNUSED, struct ds *s)
5130{
b1c5bf1f 5131 ds_put_format(s, "%sdebug_recirc%s", colors.value, colors.end);
d4abaff5 5132}
07659514
JS
5133
5134/* Action structure for NXAST_CT.
5135 *
5136 * Pass traffic to the connection tracker.
5137 *
5138 * There are two important concepts to understanding the connection tracking
5139 * interface: Packet state and Connection state. Packets may be "Untracked" or
5140 * "Tracked". Connections may be "Uncommitted" or "Committed".
5141 *
5142 * - Packet State:
5143 *
5144 * Untracked packets have not yet passed through the connection tracker,
5145 * and the connection state for such packets is unknown. In most cases,
5146 * packets entering the OpenFlow pipeline will initially be in the
5147 * untracked state. Untracked packets may become tracked by executing
5148 * NXAST_CT with a "recirc_table" specified. This makes various aspects
5149 * about the connection available, in particular the connection state.
5150 *
5151 * Tracked packets have previously passed through the connection tracker.
5152 * These packets will remain tracked through until the end of the OpenFlow
5153 * pipeline. Tracked packets which have NXAST_CT executed with a
5154 * "recirc_table" specified will return to the tracked state.
5155 *
5156 * The packet state is only significant for the duration of packet
5157 * processing within the OpenFlow pipeline.
5158 *
5159 * - Connection State:
5160 *
5161 * Multiple packets may be associated with a single connection. Initially,
5162 * all connections are uncommitted. The connection state corresponding to
5163 * a packet is available in the NXM_NX_CT_STATE field for tracked packets.
5164 *
5165 * Uncommitted connections have no state stored about them. Uncommitted
5166 * connections may transition into the committed state by executing
5167 * NXAST_CT with the NX_CT_F_COMMIT flag.
5168 *
5169 * Once a connection becomes committed, information may be gathered about
5170 * the connection by passing subsequent packets through the connection
5171 * tracker, and the state of the connection will be stored beyond the
5172 * lifetime of packet processing.
5173 *
5174 * Connections may transition back into the uncommitted state due to
5175 * external timers, or due to the contents of packets that are sent to the
5176 * connection tracker. This behaviour is outside of the scope of the
5177 * OpenFlow interface.
5178 *
5179 * The "zone" specifies a context within which the tracking is done:
5180 *
5181 * The connection tracking zone is a 16-bit number. Each zone is an
5182 * independent connection tracking context. The connection state for each
5183 * connection is completely separate for each zone, so if a connection
5184 * is committed to zone A, then it will remain uncommitted in zone B.
5185 * If NXAST_CT is executed with the same zone multiple times, later
5186 * executions have no effect.
5187 *
5188 * If 'zone_src' is nonzero, this specifies that the zone should be
5189 * sourced from a field zone_src[ofs:ofs+nbits]. The format and semantics
5190 * of 'zone_src' and 'zone_ofs_nbits' are similar to those for the
5191 * NXAST_REG_LOAD action. The acceptable nxm_header values for 'zone_src'
5192 * are the same as the acceptable nxm_header values for the 'src' field of
5193 * NXAST_REG_MOVE.
5194 *
5195 * If 'zone_src' is zero, then the value of 'zone_imm' will be used as the
5196 * connection tracking zone.
5197 *
5198 * The "recirc_table" allows NXM_NX_CT_* fields to become available:
5199 *
5200 * If "recirc_table" has a value other than NX_CT_RECIRC_NONE, then the
5201 * packet will be logically cloned prior to executing this action. One
5202 * copy will be sent to the connection tracker, then will be re-injected
5203 * into the OpenFlow pipeline beginning at the OpenFlow table specified in
5204 * this field. When the packet re-enters the pipeline, the NXM_NX_CT_*
5205 * fields will be populated. The original instance of the packet will
5206 * continue the current actions list. This can be thought of as similar to
5207 * the effect of the "output" action: One copy is sent out (in this case,
5208 * to the connection tracker), but the current copy continues processing.
5209 *
5210 * It is strongly recommended that this table is later than the current
5211 * table, to prevent loops.
8e53fe8c 5212 *
d787ad39
JS
5213 * The "alg" attaches protocol-specific behaviour to this action:
5214 *
5215 * The ALG is a 16-bit number which specifies that additional
5216 * processing should be applied to this traffic.
5217 *
5218 * Protocol | Value | Meaning
5219 * --------------------------------------------------------------------
5220 * None | 0 | No protocol-specific behaviour.
5221 * FTP | 21 | Parse FTP control connections and observe the
5222 * | | negotiation of related data connections.
5223 * Other | Other | Unsupported protocols.
5224 *
5225 * By way of example, if FTP control connections have this action applied
5226 * with the ALG set to FTP (21), then the connection tracker will observe
5227 * the negotiation of data connections. This allows the connection
5228 * tracker to identify subsequent data connections as "related" to this
5229 * existing connection. The "related" flag will be populated in the
5230 * NXM_NX_CT_STATE field for such connections if the 'recirc_table' is
5231 * specified.
5232 *
8e53fe8c
JS
5233 * Zero or more actions may immediately follow this action. These actions will
5234 * be executed within the context of the connection tracker, and they require
5235 * the NX_CT_F_COMMIT flag to be set.
07659514
JS
5236 */
5237struct nx_action_conntrack {
5238 ovs_be16 type; /* OFPAT_VENDOR. */
5239 ovs_be16 len; /* At least 24. */
5240 ovs_be32 vendor; /* NX_VENDOR_ID. */
5241 ovs_be16 subtype; /* NXAST_CT. */
5242 ovs_be16 flags; /* Zero or more NX_CT_F_* flags.
5243 * Unspecified flag bits must be zero. */
5244 ovs_be32 zone_src; /* Connection tracking context. */
5245 union {
5246 ovs_be16 zone_ofs_nbits;/* Range to use from source field. */
5247 ovs_be16 zone_imm; /* Immediate value for zone. */
5248 };
5249 uint8_t recirc_table; /* Recirculate to a specific table, or
5250 NX_CT_RECIRC_NONE for no recirculation. */
d787ad39
JS
5251 uint8_t pad[3]; /* Zeroes */
5252 ovs_be16 alg; /* Well-known port number for the protocol.
5253 * 0 indicates no ALG is required. */
07659514
JS
5254 /* Followed by a sequence of zero or more OpenFlow actions. The length of
5255 * these is included in 'len'. */
5256};
5257OFP_ASSERT(sizeof(struct nx_action_conntrack) == 24);
5258
5259static enum ofperr
5260decode_ct_zone(const struct nx_action_conntrack *nac,
5261 struct ofpact_conntrack *out)
5262{
5263 if (nac->zone_src) {
5264 enum ofperr error;
5265
5266 out->zone_src.field = mf_from_nxm_header(ntohl(nac->zone_src));
5267 out->zone_src.ofs = nxm_decode_ofs(nac->zone_ofs_nbits);
5268 out->zone_src.n_bits = nxm_decode_n_bits(nac->zone_ofs_nbits);
5269 error = mf_check_src(&out->zone_src, NULL);
5270 if (error) {
5271 return error;
5272 }
5273
5274 if (out->zone_src.n_bits != 16) {
5275 VLOG_WARN_RL(&rl, "zone n_bits %d not within valid range [16..16]",
5276 out->zone_src.n_bits);
5277 return OFPERR_OFPBAC_BAD_SET_LEN;
5278 }
5279 } else {
5280 out->zone_src.field = NULL;
5281 out->zone_imm = ntohs(nac->zone_imm);
5282 }
5283
5284 return 0;
5285}
5286
5287static enum ofperr
5288decode_NXAST_RAW_CT(const struct nx_action_conntrack *nac,
8e53fe8c 5289 enum ofp_version ofp_version, struct ofpbuf *out)
07659514 5290{
8e53fe8c 5291 const size_t ct_offset = ofpacts_pull(out);
0a2869d5 5292 struct ofpact_conntrack *conntrack = ofpact_put_CT(out);
07659514 5293 conntrack->flags = ntohs(nac->flags);
0a2869d5
BP
5294
5295 int error = decode_ct_zone(nac, conntrack);
07659514
JS
5296 if (error) {
5297 goto out;
5298 }
5299 conntrack->recirc_table = nac->recirc_table;
d787ad39 5300 conntrack->alg = ntohs(nac->alg);
07659514 5301
8e53fe8c
JS
5302 ofpbuf_pull(out, sizeof(*conntrack));
5303
0a2869d5
BP
5304 struct ofpbuf openflow = ofpbuf_const_initializer(
5305 nac + 1, ntohs(nac->len) - sizeof(*nac));
8e53fe8c
JS
5306 error = ofpacts_pull_openflow_actions__(&openflow, openflow.size,
5307 ofp_version,
5308 1u << OVSINST_OFPIT11_APPLY_ACTIONS,
5309 out, OFPACT_CT);
5310 if (error) {
5311 goto out;
5312 }
5313
5314 conntrack = ofpbuf_push_uninit(out, sizeof(*conntrack));
5315 out->header = &conntrack->ofpact;
ce058104 5316 ofpact_finish_CT(out, &conntrack);
8e53fe8c
JS
5317
5318 if (conntrack->ofpact.len > sizeof(*conntrack)
5319 && !(conntrack->flags & NX_CT_F_COMMIT)) {
9ac0aada
JR
5320 const struct ofpact *a;
5321 size_t ofpacts_len = conntrack->ofpact.len - sizeof(*conntrack);
5322
5323 OFPACT_FOR_EACH (a, conntrack->actions, ofpacts_len) {
5324 if (a->type != OFPACT_NAT || ofpact_get_NAT(a)->flags
5325 || ofpact_get_NAT(a)->range_af != AF_UNSPEC) {
5326 VLOG_WARN_RL(&rl, "CT action requires commit flag if actions "
5327 "other than NAT without arguments are specified.");
5328 error = OFPERR_OFPBAC_BAD_ARGUMENT;
5329 goto out;
5330 }
5331 }
8e53fe8c
JS
5332 }
5333
07659514 5334out:
8e53fe8c 5335 ofpbuf_push_uninit(out, ct_offset);
07659514
JS
5336 return error;
5337}
5338
5339static void
5340encode_CT(const struct ofpact_conntrack *conntrack,
8e53fe8c 5341 enum ofp_version ofp_version, struct ofpbuf *out)
07659514
JS
5342{
5343 struct nx_action_conntrack *nac;
8e53fe8c
JS
5344 const size_t ofs = out->size;
5345 size_t len;
07659514
JS
5346
5347 nac = put_NXAST_CT(out);
5348 nac->flags = htons(conntrack->flags);
5349 if (conntrack->zone_src.field) {
5350 nac->zone_src = htonl(mf_nxm_header(conntrack->zone_src.field->id));
5351 nac->zone_ofs_nbits = nxm_encode_ofs_nbits(conntrack->zone_src.ofs,
5352 conntrack->zone_src.n_bits);
5353 } else {
5354 nac->zone_src = htonl(0);
5355 nac->zone_imm = htons(conntrack->zone_imm);
5356 }
5357 nac->recirc_table = conntrack->recirc_table;
d787ad39 5358 nac->alg = htons(conntrack->alg);
8e53fe8c
JS
5359
5360 len = ofpacts_put_openflow_actions(conntrack->actions,
5361 ofpact_ct_get_action_len(conntrack),
5362 out, ofp_version);
5363 len += sizeof(*nac);
5364 nac = ofpbuf_at(out, ofs, sizeof(*nac));
5365 nac->len = htons(len);
07659514
JS
5366}
5367
9ac0aada
JR
5368static char * OVS_WARN_UNUSED_RESULT parse_NAT(char *arg, struct ofpbuf *,
5369 enum ofputil_protocol * OVS_UNUSED);
5370
07659514
JS
5371/* Parses 'arg' as the argument to a "ct" action, and appends such an
5372 * action to 'ofpacts'.
5373 *
5374 * Returns NULL if successful, otherwise a malloc()'d string describing the
5375 * error. The caller is responsible for freeing the returned string. */
5376static char * OVS_WARN_UNUSED_RESULT
5377parse_CT(char *arg, struct ofpbuf *ofpacts,
8e53fe8c 5378 enum ofputil_protocol *usable_protocols)
07659514 5379{
8e53fe8c 5380 const size_t ct_offset = ofpacts_pull(ofpacts);
07659514
JS
5381 struct ofpact_conntrack *oc;
5382 char *error = NULL;
5383 char *key, *value;
5384
5385 oc = ofpact_put_CT(ofpacts);
5386 oc->flags = 0;
5387 oc->recirc_table = NX_CT_RECIRC_NONE;
5388 while (ofputil_parse_key_value(&arg, &key, &value)) {
5389 if (!strcmp(key, "commit")) {
5390 oc->flags |= NX_CT_F_COMMIT;
5391 } else if (!strcmp(key, "table")) {
5392 error = str_to_u8(value, "recirc_table", &oc->recirc_table);
5393 if (!error && oc->recirc_table == NX_CT_RECIRC_NONE) {
5394 error = xasprintf("invalid table %#"PRIx16, oc->recirc_table);
5395 }
5396 } else if (!strcmp(key, "zone")) {
5397 error = str_to_u16(value, "zone", &oc->zone_imm);
5398
5399 if (error) {
5400 free(error);
5401 error = mf_parse_subfield(&oc->zone_src, value);
5402 if (error) {
5403 return error;
5404 }
5405 }
d787ad39
JS
5406 } else if (!strcmp(key, "alg")) {
5407 error = str_to_connhelper(value, &oc->alg);
9ac0aada
JR
5408 } else if (!strcmp(key, "nat")) {
5409 const size_t nat_offset = ofpacts_pull(ofpacts);
5410
5411 error = parse_NAT(value, ofpacts, usable_protocols);
9ac0aada
JR
5412 /* Update CT action pointer and length. */
5413 ofpacts->header = ofpbuf_push_uninit(ofpacts, nat_offset);
5414 oc = ofpacts->header;
8e53fe8c
JS
5415 } else if (!strcmp(key, "exec")) {
5416 /* Hide existing actions from ofpacts_parse_copy(), so the
5417 * nesting can be handled transparently. */
76e3e669 5418 enum ofputil_protocol usable_protocols2;
9ac0aada 5419 const size_t exec_offset = ofpacts_pull(ofpacts);
76e3e669 5420
76e3e669
JR
5421 /* Initializes 'usable_protocol2', fold it back to
5422 * '*usable_protocols' afterwards, so that we do not lose
5423 * restrictions already in there. */
5424 error = ofpacts_parse_copy(value, ofpacts, &usable_protocols2,
5425 false, OFPACT_CT);
5426 *usable_protocols &= usable_protocols2;
9ac0aada 5427 ofpacts->header = ofpbuf_push_uninit(ofpacts, exec_offset);
8e53fe8c 5428 oc = ofpacts->header;
07659514
JS
5429 } else {
5430 error = xasprintf("invalid argument to \"ct\" action: `%s'", key);
5431 }
5432 if (error) {
5433 break;
5434 }
5435 }
5436
ce058104 5437 ofpact_finish_CT(ofpacts, &oc);
8e53fe8c 5438 ofpbuf_push_uninit(ofpacts, ct_offset);
07659514
JS
5439 return error;
5440}
5441
d787ad39
JS
5442static void
5443format_alg(int port, struct ds *s)
5444{
40c7b2fc
JS
5445 switch(port) {
5446 case IPPORT_FTP:
b1c5bf1f 5447 ds_put_format(s, "%salg=%sftp,", colors.param, colors.end);
40c7b2fc
JS
5448 break;
5449 case IPPORT_TFTP:
5450 ds_put_format(s, "%salg=%stftp,", colors.param, colors.end);
5451 break;
5452 case 0:
5453 /* Don't print. */
5454 break;
5455 default:
b1c5bf1f 5456 ds_put_format(s, "%salg=%s%d,", colors.param, colors.end, port);
40c7b2fc 5457 break;
d787ad39
JS
5458 }
5459}
5460
9ac0aada
JR
5461static void format_NAT(const struct ofpact_nat *a, struct ds *ds);
5462
07659514
JS
5463static void
5464format_CT(const struct ofpact_conntrack *a, struct ds *s)
5465{
b1c5bf1f 5466 ds_put_format(s, "%sct(%s", colors.paren, colors.end);
07659514 5467 if (a->flags & NX_CT_F_COMMIT) {
b1c5bf1f 5468 ds_put_format(s, "%scommit%s,", colors.value, colors.end);
07659514
JS
5469 }
5470 if (a->recirc_table != NX_CT_RECIRC_NONE) {
b1c5bf1f
QM
5471 ds_put_format(s, "%stable=%s%"PRIu8",",
5472 colors.special, colors.end, a->recirc_table);
07659514
JS
5473 }
5474 if (a->zone_src.field) {
b1c5bf1f 5475 ds_put_format(s, "%szone=%s", colors.param, colors.end);
07659514
JS
5476 mf_format_subfield(&a->zone_src, s);
5477 ds_put_char(s, ',');
5478 } else if (a->zone_imm) {
b1c5bf1f
QM
5479 ds_put_format(s, "%szone=%s%"PRIu16",",
5480 colors.param, colors.end, a->zone_imm);
07659514 5481 }
9ac0aada
JR
5482 /* If the first action is a NAT action, format it outside of the 'exec'
5483 * envelope. */
5484 const struct ofpact *action = a->actions;
5485 size_t actions_len = ofpact_ct_get_action_len(a);
5486 if (actions_len && action->type == OFPACT_NAT) {
5487 format_NAT(ofpact_get_NAT(action), s);
5488 ds_put_char(s, ',');
5489 actions_len -= OFPACT_ALIGN(action->len);
5490 action = ofpact_next(action);
5491 }
5492 if (actions_len) {
b1c5bf1f 5493 ds_put_format(s, "%sexec(%s", colors.paren, colors.end);
9ac0aada 5494 ofpacts_format(action, actions_len, s);
b1c5bf1f 5495 ds_put_format(s, "%s),%s", colors.paren, colors.end);
8e53fe8c 5496 }
d787ad39 5497 format_alg(a->alg, s);
07659514 5498 ds_chomp(s, ',');
b1c5bf1f 5499 ds_put_format(s, "%s)%s", colors.paren, colors.end);
07659514 5500}
9ac0aada 5501\f
72fe7578
BP
5502/* ct_clear action. */
5503
5504static enum ofperr
5505decode_NXAST_RAW_CT_CLEAR(struct ofpbuf *out)
5506{
5507 ofpact_put_CT_CLEAR(out);
5508 return 0;
5509}
5510
5511static void
5512encode_CT_CLEAR(const struct ofpact_null *null OVS_UNUSED,
5513 enum ofp_version ofp_version OVS_UNUSED,
5514 struct ofpbuf *out)
5515{
5516 put_NXAST_CT_CLEAR(out);
5517}
5518
5519static char * OVS_WARN_UNUSED_RESULT
5520parse_CT_CLEAR(char *arg OVS_UNUSED, struct ofpbuf *ofpacts,
5521 enum ofputil_protocol *usable_protocols OVS_UNUSED)
5522{
5523 ofpact_put_CT_CLEAR(ofpacts);
5524 return NULL;
5525}
5526
5527static void
5528format_CT_CLEAR(const struct ofpact_null *a OVS_UNUSED, struct ds *s)
5529{
5530 ds_put_format(s, "%sct_clear%s", colors.value, colors.end);
5531}\f
9ac0aada
JR
5532/* NAT action. */
5533
5534/* Which optional fields are present? */
5535enum nx_nat_range {
5536 NX_NAT_RANGE_IPV4_MIN = 1 << 0, /* ovs_be32 */
5537 NX_NAT_RANGE_IPV4_MAX = 1 << 1, /* ovs_be32 */
5538 NX_NAT_RANGE_IPV6_MIN = 1 << 2, /* struct in6_addr */
5539 NX_NAT_RANGE_IPV6_MAX = 1 << 3, /* struct in6_addr */
5540 NX_NAT_RANGE_PROTO_MIN = 1 << 4, /* ovs_be16 */
5541 NX_NAT_RANGE_PROTO_MAX = 1 << 5, /* ovs_be16 */
5542};
5543
5544/* Action structure for NXAST_NAT. */
5545struct nx_action_nat {
5546 ovs_be16 type; /* OFPAT_VENDOR. */
5547 ovs_be16 len; /* At least 16. */
5548 ovs_be32 vendor; /* NX_VENDOR_ID. */
5549 ovs_be16 subtype; /* NXAST_NAT. */
5550 uint8_t pad[2]; /* Must be zero. */
5551 ovs_be16 flags; /* Zero or more NX_NAT_F_* flags.
5552 * Unspecified flag bits must be zero. */
5553 ovs_be16 range_present; /* NX_NAT_RANGE_* */
5554 /* Followed by optional parameters as specified by 'range_present' */
5555};
5556OFP_ASSERT(sizeof(struct nx_action_nat) == 16);
5557
5558static void
5559encode_NAT(const struct ofpact_nat *nat,
5560 enum ofp_version ofp_version OVS_UNUSED,
5561 struct ofpbuf *out)
5562{
5563 struct nx_action_nat *nan;
5564 const size_t ofs = out->size;
5565 uint16_t range_present = 0;
5566
5567 nan = put_NXAST_NAT(out);
5568 nan->flags = htons(nat->flags);
5569 if (nat->range_af == AF_INET) {
5570 if (nat->range.addr.ipv4.min) {
5571 ovs_be32 *min = ofpbuf_put_uninit(out, sizeof *min);
5572 *min = nat->range.addr.ipv4.min;
5573 range_present |= NX_NAT_RANGE_IPV4_MIN;
5574 }
5575 if (nat->range.addr.ipv4.max) {
5576 ovs_be32 *max = ofpbuf_put_uninit(out, sizeof *max);
5577 *max = nat->range.addr.ipv4.max;
5578 range_present |= NX_NAT_RANGE_IPV4_MAX;
5579 }
5580 } else if (nat->range_af == AF_INET6) {
5581 if (!ipv6_mask_is_any(&nat->range.addr.ipv6.min)) {
5582 struct in6_addr *min = ofpbuf_put_uninit(out, sizeof *min);
5583 *min = nat->range.addr.ipv6.min;
5584 range_present |= NX_NAT_RANGE_IPV6_MIN;
5585 }
5586 if (!ipv6_mask_is_any(&nat->range.addr.ipv6.max)) {
5587 struct in6_addr *max = ofpbuf_put_uninit(out, sizeof *max);
5588 *max = nat->range.addr.ipv6.max;
5589 range_present |= NX_NAT_RANGE_IPV6_MAX;
5590 }
5591 }
5592 if (nat->range_af != AF_UNSPEC) {
5593 if (nat->range.proto.min) {
5594 ovs_be16 *min = ofpbuf_put_uninit(out, sizeof *min);
5595 *min = htons(nat->range.proto.min);
5596 range_present |= NX_NAT_RANGE_PROTO_MIN;
5597 }
5598 if (nat->range.proto.max) {
5599 ovs_be16 *max = ofpbuf_put_uninit(out, sizeof *max);
5600 *max = htons(nat->range.proto.max);
5601 range_present |= NX_NAT_RANGE_PROTO_MAX;
5602 }
5603 }
5604 pad_ofpat(out, ofs);
5605 nan = ofpbuf_at(out, ofs, sizeof *nan);
5606 nan->range_present = htons(range_present);
5607}
5608
5609static enum ofperr
5610decode_NXAST_RAW_NAT(const struct nx_action_nat *nan,
5611 enum ofp_version ofp_version OVS_UNUSED,
5612 struct ofpbuf *out)
5613{
5614 struct ofpact_nat *nat;
5615 uint16_t range_present = ntohs(nan->range_present);
5616 const char *opts = (char *)(nan + 1);
5617 uint16_t len = ntohs(nan->len) - sizeof *nan;
5618
5619 nat = ofpact_put_NAT(out);
5620 nat->flags = ntohs(nan->flags);
5621
ae8b9260
JR
5622 /* Check for unknown or mutually exclusive flags. */
5623 if ((nat->flags & ~NX_NAT_F_MASK)
5624 || (nat->flags & NX_NAT_F_SRC && nat->flags & NX_NAT_F_DST)
5625 || (nat->flags & NX_NAT_F_PROTO_HASH
5626 && nat->flags & NX_NAT_F_PROTO_RANDOM)) {
5627 return OFPERR_OFPBAC_BAD_ARGUMENT;
5628 }
5629
9ac0aada
JR
5630#define NX_NAT_GET_OPT(DST, SRC, LEN, TYPE) \
5631 (LEN >= sizeof(TYPE) \
5632 ? (memcpy(DST, SRC, sizeof(TYPE)), LEN -= sizeof(TYPE), \
5633 SRC += sizeof(TYPE)) \
5634 : NULL)
5635
5636 nat->range_af = AF_UNSPEC;
5637 if (range_present & NX_NAT_RANGE_IPV4_MIN) {
5638 if (range_present & (NX_NAT_RANGE_IPV6_MIN | NX_NAT_RANGE_IPV6_MAX)) {
5639 return OFPERR_OFPBAC_BAD_ARGUMENT;
5640 }
5641
5642 if (!NX_NAT_GET_OPT(&nat->range.addr.ipv4.min, opts, len, ovs_be32)
5643 || !nat->range.addr.ipv4.min) {
5644 return OFPERR_OFPBAC_BAD_ARGUMENT;
5645 }
5646
5647 nat->range_af = AF_INET;
5648
5649 if (range_present & NX_NAT_RANGE_IPV4_MAX) {
5650 if (!NX_NAT_GET_OPT(&nat->range.addr.ipv4.max, opts, len,
5651 ovs_be32)) {
5652 return OFPERR_OFPBAC_BAD_ARGUMENT;
5653 }
5654 if (ntohl(nat->range.addr.ipv4.max)
5655 < ntohl(nat->range.addr.ipv4.min)) {
5656 return OFPERR_OFPBAC_BAD_ARGUMENT;
5657 }
5658 }
5659 } else if (range_present & NX_NAT_RANGE_IPV4_MAX) {
5660 return OFPERR_OFPBAC_BAD_ARGUMENT;
5661 } else if (range_present & NX_NAT_RANGE_IPV6_MIN) {
5662 if (!NX_NAT_GET_OPT(&nat->range.addr.ipv6.min, opts, len,
5663 struct in6_addr)
5664 || ipv6_mask_is_any(&nat->range.addr.ipv6.min)) {
5665 return OFPERR_OFPBAC_BAD_ARGUMENT;
5666 }
5667
5668 nat->range_af = AF_INET6;
5669
5670 if (range_present & NX_NAT_RANGE_IPV6_MAX) {
5671 if (!NX_NAT_GET_OPT(&nat->range.addr.ipv6.max, opts, len,
5672 struct in6_addr)) {
5673 return OFPERR_OFPBAC_BAD_ARGUMENT;
5674 }
5675 if (memcmp(&nat->range.addr.ipv6.max, &nat->range.addr.ipv6.min,
5676 sizeof(struct in6_addr)) < 0) {
5677 return OFPERR_OFPBAC_BAD_ARGUMENT;
5678 }
5679 }
5680 } else if (range_present & NX_NAT_RANGE_IPV6_MAX) {
5681 return OFPERR_OFPBAC_BAD_ARGUMENT;
5682 }
5683
5684 if (range_present & NX_NAT_RANGE_PROTO_MIN) {
5685 ovs_be16 proto;
5686
5687 if (nat->range_af == AF_UNSPEC) {
5688 return OFPERR_OFPBAC_BAD_ARGUMENT;
5689 }
5690 if (!NX_NAT_GET_OPT(&proto, opts, len, ovs_be16) || proto == 0) {
5691 return OFPERR_OFPBAC_BAD_ARGUMENT;
5692 }
5693 nat->range.proto.min = ntohs(proto);
5694 if (range_present & NX_NAT_RANGE_PROTO_MAX) {
5695 if (!NX_NAT_GET_OPT(&proto, opts, len, ovs_be16)) {
5696 return OFPERR_OFPBAC_BAD_ARGUMENT;
5697 }
5698 nat->range.proto.max = ntohs(proto);
5699 if (nat->range.proto.max < nat->range.proto.min) {
5700 return OFPERR_OFPBAC_BAD_ARGUMENT;
5701 }
5702 }
5703 } else if (range_present & NX_NAT_RANGE_PROTO_MAX) {
5704 return OFPERR_OFPBAC_BAD_ARGUMENT;
5705 }
5706
5707 return 0;
5708}
5709
5710static void
5711format_NAT(const struct ofpact_nat *a, struct ds *ds)
5712{
b1c5bf1f 5713 ds_put_format(ds, "%snat%s", colors.paren, colors.end);
9ac0aada
JR
5714
5715 if (a->flags & (NX_NAT_F_SRC | NX_NAT_F_DST)) {
b1c5bf1f
QM
5716 ds_put_format(ds, "%s(%s", colors.paren, colors.end);
5717 ds_put_format(ds, a->flags & NX_NAT_F_SRC ? "%ssrc%s" : "%sdst%s",
5718 colors.param, colors.end);
9ac0aada
JR
5719
5720 if (a->range_af != AF_UNSPEC) {
b1c5bf1f 5721 ds_put_format(ds, "%s=%s", colors.param, colors.end);
9ac0aada
JR
5722
5723 if (a->range_af == AF_INET) {
5724 ds_put_format(ds, IP_FMT, IP_ARGS(a->range.addr.ipv4.min));
5725
5726 if (a->range.addr.ipv4.max
5727 && a->range.addr.ipv4.max != a->range.addr.ipv4.min) {
5728 ds_put_format(ds, "-"IP_FMT,
5729 IP_ARGS(a->range.addr.ipv4.max));
5730 }
5731 } else if (a->range_af == AF_INET6) {
5732 ipv6_format_addr_bracket(&a->range.addr.ipv6.min, ds,
5733 a->range.proto.min);
5734
5735 if (!ipv6_mask_is_any(&a->range.addr.ipv6.max)
5736 && memcmp(&a->range.addr.ipv6.max, &a->range.addr.ipv6.min,
5737 sizeof(struct in6_addr)) != 0) {
5738 ds_put_char(ds, '-');
5739 ipv6_format_addr_bracket(&a->range.addr.ipv6.max, ds,
5740 a->range.proto.min);
5741 }
5742 }
5743 if (a->range.proto.min) {
5744 ds_put_char(ds, ':');
5745 ds_put_format(ds, "%"PRIu16, a->range.proto.min);
5746
5747 if (a->range.proto.max
5748 && a->range.proto.max != a->range.proto.min) {
5749 ds_put_format(ds, "-%"PRIu16, a->range.proto.max);
5750 }
5751 }
5752 ds_put_char(ds, ',');
5753
5754 if (a->flags & NX_NAT_F_PERSISTENT) {
b1c5bf1f
QM
5755 ds_put_format(ds, "%spersistent%s,",
5756 colors.value, colors.end);
9ac0aada
JR
5757 }
5758 if (a->flags & NX_NAT_F_PROTO_HASH) {
b1c5bf1f 5759 ds_put_format(ds, "%shash%s,", colors.value, colors.end);
9ac0aada
JR
5760 }
5761 if (a->flags & NX_NAT_F_PROTO_RANDOM) {
b1c5bf1f 5762 ds_put_format(ds, "%srandom%s,", colors.value, colors.end);
9ac0aada
JR
5763 }
5764 }
5765 ds_chomp(ds, ',');
b1c5bf1f 5766 ds_put_format(ds, "%s)%s", colors.paren, colors.end);
9ac0aada
JR
5767 }
5768}
5769
5770static char * OVS_WARN_UNUSED_RESULT
5771str_to_nat_range(const char *s, struct ofpact_nat *on)
5772{
5773 char ipv6_s[IPV6_SCAN_LEN + 1];
5774 int n = 0;
5775
5776 on->range_af = AF_UNSPEC;
5777 if (ovs_scan_len(s, &n, IP_SCAN_FMT,
5778 IP_SCAN_ARGS(&on->range.addr.ipv4.min))) {
5779 on->range_af = AF_INET;
5780
5781 if (s[n] == '-') {
5782 n++;
5783 if (!ovs_scan_len(s, &n, IP_SCAN_FMT,
5784 IP_SCAN_ARGS(&on->range.addr.ipv4.max))
5785 || (ntohl(on->range.addr.ipv4.max)
5786 < ntohl(on->range.addr.ipv4.min))) {
5787 goto error;
5788 }
5789 }
5790 } else if ((ovs_scan_len(s, &n, IPV6_SCAN_FMT, ipv6_s)
5791 || ovs_scan_len(s, &n, "["IPV6_SCAN_FMT"]", ipv6_s))
5792 && inet_pton(AF_INET6, ipv6_s, &on->range.addr.ipv6.min) == 1) {
5793 on->range_af = AF_INET6;
5794
5795 if (s[n] == '-') {
5796 n++;
5797 if (!(ovs_scan_len(s, &n, IPV6_SCAN_FMT, ipv6_s)
5798 || ovs_scan_len(s, &n, "["IPV6_SCAN_FMT"]", ipv6_s))
5799 || inet_pton(AF_INET6, ipv6_s, &on->range.addr.ipv6.max) != 1
5800 || memcmp(&on->range.addr.ipv6.max, &on->range.addr.ipv6.min,
5801 sizeof on->range.addr.ipv6.max) < 0) {
5802 goto error;
5803 }
5804 }
5805 }
5806 if (on->range_af != AF_UNSPEC && s[n] == ':') {
5807 n++;
5808 if (!ovs_scan_len(s, &n, "%"SCNu16, &on->range.proto.min)) {
5809 goto error;
5810 }
5811 if (s[n] == '-') {
5812 n++;
5813 if (!ovs_scan_len(s, &n, "%"SCNu16, &on->range.proto.max)
5814 || on->range.proto.max < on->range.proto.min) {
5815 goto error;
5816 }
5817 }
5818 }
5819 if (strlen(s) != n) {
5820 return xasprintf("garbage (%s) after nat range \"%s\" (pos: %d)",
5821 &s[n], s, n);
5822 }
5823 return NULL;
5824error:
5825 return xasprintf("invalid nat range \"%s\"", s);
5826}
5827
5828
5829/* Parses 'arg' as the argument to a "nat" action, and appends such an
5830 * action to 'ofpacts'.
5831 *
5832 * Returns NULL if successful, otherwise a malloc()'d string describing the
5833 * error. The caller is responsible for freeing the returned string. */
5834static char * OVS_WARN_UNUSED_RESULT
5835parse_NAT(char *arg, struct ofpbuf *ofpacts,
5836 enum ofputil_protocol *usable_protocols OVS_UNUSED)
5837{
5838 struct ofpact_nat *on = ofpact_put_NAT(ofpacts);
5839 char *key, *value;
5840
5841 on->flags = 0;
5842 on->range_af = AF_UNSPEC;
5843
5844 while (ofputil_parse_key_value(&arg, &key, &value)) {
5845 char *error = NULL;
5846
5847 if (!strcmp(key, "src")) {
5848 on->flags |= NX_NAT_F_SRC;
5849 error = str_to_nat_range(value, on);
5850 } else if (!strcmp(key, "dst")) {
5851 on->flags |= NX_NAT_F_DST;
5852 error = str_to_nat_range(value, on);
5853 } else if (!strcmp(key, "persistent")) {
5854 on->flags |= NX_NAT_F_PERSISTENT;
5855 } else if (!strcmp(key, "hash")) {
5856 on->flags |= NX_NAT_F_PROTO_HASH;
5857 } else if (!strcmp(key, "random")) {
5858 on->flags |= NX_NAT_F_PROTO_RANDOM;
5859 } else {
5860 error = xasprintf("invalid key \"%s\" in \"nat\" argument",
5861 key);
5862 }
5863 if (error) {
5864 return error;
5865 }
5866 }
5867 if (on->flags & NX_NAT_F_SRC && on->flags & NX_NAT_F_DST) {
ae8b9260 5868 return xasprintf("May only specify one of \"src\" or \"dst\".");
9ac0aada
JR
5869 }
5870 if (!(on->flags & NX_NAT_F_SRC || on->flags & NX_NAT_F_DST)) {
5871 if (on->flags) {
ae8b9260 5872 return xasprintf("Flags allowed only with \"src\" or \"dst\".");
9ac0aada
JR
5873 }
5874 if (on->range_af != AF_UNSPEC) {
ae8b9260 5875 return xasprintf("Range allowed only with \"src\" or \"dst\".");
9ac0aada
JR
5876 }
5877 }
ae8b9260
JR
5878 if (on->flags & NX_NAT_F_PROTO_HASH && on->flags & NX_NAT_F_PROTO_RANDOM) {
5879 return xasprintf("Both \"hash\" and \"random\" are not allowed.");
5880 }
5881
9ac0aada
JR
5882 return NULL;
5883}
5884
aaca4fe0
WT
5885/* Truncate output action. */
5886struct nx_action_output_trunc {
5887 ovs_be16 type; /* OFPAT_VENDOR. */
5888 ovs_be16 len; /* At least 16. */
5889 ovs_be32 vendor; /* NX_VENDOR_ID. */
5890 ovs_be16 subtype; /* NXAST_OUTPUT_TRUNC. */
5891 ovs_be16 port; /* Output port */
5892 ovs_be32 max_len; /* Truncate packet to size bytes */
5893};
5894OFP_ASSERT(sizeof(struct nx_action_output_trunc) == 16);
5895
5896static enum ofperr
5897decode_NXAST_RAW_OUTPUT_TRUNC(const struct nx_action_output_trunc *natrc,
5898 enum ofp_version ofp_version OVS_UNUSED,
5899 struct ofpbuf *out)
5900{
5901 struct ofpact_output_trunc *output_trunc;
5902
5903 output_trunc = ofpact_put_OUTPUT_TRUNC(out);
5904 output_trunc->max_len = ntohl(natrc->max_len);
5905 output_trunc->port = u16_to_ofp(ntohs(natrc->port));
5906
5907 if (output_trunc->max_len < ETH_HEADER_LEN) {
5908 return OFPERR_OFPBAC_BAD_ARGUMENT;
5909 }
5910 return 0;
5911}
5912
5913static void
5914encode_OUTPUT_TRUNC(const struct ofpact_output_trunc *output_trunc,
5915 enum ofp_version ofp_version OVS_UNUSED,
5916 struct ofpbuf *out)
5917{
5918 struct nx_action_output_trunc *natrc = put_NXAST_OUTPUT_TRUNC(out);
5919
5920 natrc->max_len = htonl(output_trunc->max_len);
5921 natrc->port = htons(ofp_to_u16(output_trunc->port));
5922}
5923
5924static char * OVS_WARN_UNUSED_RESULT
5925parse_OUTPUT_TRUNC(const char *arg, struct ofpbuf *ofpacts OVS_UNUSED,
5926 enum ofputil_protocol *usable_protocols OVS_UNUSED)
5927{
5928 /* Disable output_trunc parsing. Expose as output(port=N,max_len=M) and
5929 * reuse parse_OUTPUT to parse output_trunc action. */
5930 return xasprintf("unknown action %s", arg);
5931}
5932
5933static void
5934format_OUTPUT_TRUNC(const struct ofpact_output_trunc *a, struct ds *s)
5935{
94783c7c 5936 ds_put_format(s, "%soutput%s(port=%"PRIu32",max_len=%"PRIu32")",
aaca4fe0
WT
5937 colors.special, colors.end, a->port, a->max_len);
5938}
5939
d4abaff5 5940\f
c2d936a4
BP
5941/* Meter instruction. */
5942
5943static void
5944encode_METER(const struct ofpact_meter *meter,
5945 enum ofp_version ofp_version, struct ofpbuf *out)
5946{
5947 if (ofp_version >= OFP13_VERSION) {
5948 instruction_put_OFPIT13_METER(out)->meter_id = htonl(meter->meter_id);
5949 }
5950}
5951
cab50449 5952static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
5953parse_METER(char *arg, struct ofpbuf *ofpacts,
5954 enum ofputil_protocol *usable_protocols)
5955{
5956 *usable_protocols &= OFPUTIL_P_OF13_UP;
5957 return str_to_u32(arg, &ofpact_put_METER(ofpacts)->meter_id);
5958}
5959
5960static void
5961format_METER(const struct ofpact_meter *a, struct ds *s)
5962{
b1c5bf1f
QM
5963 ds_put_format(s, "%smeter:%s%"PRIu32,
5964 colors.param, colors.end, a->meter_id);
c2d936a4
BP
5965}
5966\f
5967/* Clear-Actions instruction. */
5968
5969static void
5970encode_CLEAR_ACTIONS(const struct ofpact_null *null OVS_UNUSED,
5971 enum ofp_version ofp_version OVS_UNUSED,
5972 struct ofpbuf *out OVS_UNUSED)
5973{
5974 if (ofp_version > OFP10_VERSION) {
5975 instruction_put_OFPIT11_CLEAR_ACTIONS(out);
5976 }
5977}
5978
cab50449 5979static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
5980parse_CLEAR_ACTIONS(char *arg OVS_UNUSED, struct ofpbuf *ofpacts,
5981 enum ofputil_protocol *usable_protocols OVS_UNUSED)
5982{
5983 ofpact_put_CLEAR_ACTIONS(ofpacts);
5984 return NULL;
5985}
5986
5987static void
5988format_CLEAR_ACTIONS(const struct ofpact_null *a OVS_UNUSED, struct ds *s)
5989{
b1c5bf1f 5990 ds_put_format(s, "%sclear_actions%s", colors.value, colors.end);
c2d936a4
BP
5991}
5992\f
5993/* Write-Actions instruction. */
5994
5995static void
5996encode_WRITE_ACTIONS(const struct ofpact_nest *actions,
5997 enum ofp_version ofp_version, struct ofpbuf *out)
5998{
5999 if (ofp_version > OFP10_VERSION) {
6fd6ed71 6000 const size_t ofs = out->size;
c2d936a4
BP
6001
6002 instruction_put_OFPIT11_WRITE_ACTIONS(out);
6003 ofpacts_put_openflow_actions(actions->actions,
6004 ofpact_nest_get_action_len(actions),
6005 out, ofp_version);
6006 ofpacts_update_instruction_actions(out, ofs);
6007 }
6008}
6009
cab50449 6010static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
6011parse_WRITE_ACTIONS(char *arg, struct ofpbuf *ofpacts,
6012 enum ofputil_protocol *usable_protocols)
6013{
d824b5b7 6014 size_t ofs = ofpacts_pull(ofpacts);
c2d936a4
BP
6015 struct ofpact_nest *on;
6016 char *error;
c2d936a4
BP
6017
6018 /* Add a Write-Actions instruction and then pull it off. */
6019 ofpact_put(ofpacts, OFPACT_WRITE_ACTIONS, sizeof *on);
6020 ofpbuf_pull(ofpacts, sizeof *on);
6021
6022 /* Parse nested actions.
6023 *
6024 * We pulled off "write-actions" and the previous actions because the
6025 * OFPACT_WRITE_ACTIONS is only partially constructed: its length is such
6026 * that it doesn't actually include the nested actions. That means that
6027 * ofpacts_parse() would reject them as being part of an Apply-Actions that
6028 * follows a Write-Actions, which is an invalid order. */
d824b5b7
JS
6029 error = ofpacts_parse(arg, ofpacts, usable_protocols, false,
6030 OFPACT_WRITE_ACTIONS);
c2d936a4
BP
6031
6032 /* Put the Write-Actions back on and update its length. */
6033 on = ofpbuf_push_uninit(ofpacts, sizeof *on);
6fd6ed71 6034 on->ofpact.len = ofpacts->size;
c2d936a4
BP
6035
6036 /* Put any previous actions or instructions back on. */
6037 ofpbuf_push_uninit(ofpacts, ofs);
6038
6039 return error;
6040}
6041
6042static void
6043format_WRITE_ACTIONS(const struct ofpact_nest *a, struct ds *s)
6044{
b1c5bf1f 6045 ds_put_format(s, "%swrite_actions(%s", colors.paren, colors.end);
c2d936a4 6046 ofpacts_format(a->actions, ofpact_nest_get_action_len(a), s);
b1c5bf1f 6047 ds_put_format(s, "%s)%s", colors.paren, colors.end);
c2d936a4
BP
6048}
6049\f
6050/* Action structure for NXAST_WRITE_METADATA.
6051 *
6052 * Modifies the 'mask' bits of the metadata value. */
6053struct nx_action_write_metadata {
6054 ovs_be16 type; /* OFPAT_VENDOR. */
6055 ovs_be16 len; /* Length is 32. */
6056 ovs_be32 vendor; /* NX_VENDOR_ID. */
6057 ovs_be16 subtype; /* NXAST_WRITE_METADATA. */
6058 uint8_t zeros[6]; /* Must be zero. */
6059 ovs_be64 metadata; /* Metadata register. */
6060 ovs_be64 mask; /* Metadata mask. */
6061};
6062OFP_ASSERT(sizeof(struct nx_action_write_metadata) == 32);
6063
6064static enum ofperr
6065decode_NXAST_RAW_WRITE_METADATA(const struct nx_action_write_metadata *nawm,
f3cd3ac7 6066 enum ofp_version ofp_version OVS_UNUSED,
c2d936a4
BP
6067 struct ofpbuf *out)
6068{
6069 struct ofpact_metadata *om;
6070
6071 if (!is_all_zeros(nawm->zeros, sizeof nawm->zeros)) {
6072 return OFPERR_NXBRC_MUST_BE_ZERO;
6073 }
6074
6075 om = ofpact_put_WRITE_METADATA(out);
6076 om->metadata = nawm->metadata;
6077 om->mask = nawm->mask;
6078
6079 return 0;
6080}
6081
6082static void
6083encode_WRITE_METADATA(const struct ofpact_metadata *metadata,
6084 enum ofp_version ofp_version, struct ofpbuf *out)
6085{
6086 if (ofp_version == OFP10_VERSION) {
6087 struct nx_action_write_metadata *nawm;
6088
6089 nawm = put_NXAST_WRITE_METADATA(out);
6090 nawm->metadata = metadata->metadata;
6091 nawm->mask = metadata->mask;
6092 } else {
6093 struct ofp11_instruction_write_metadata *oiwm;
6094
6095 oiwm = instruction_put_OFPIT11_WRITE_METADATA(out);
6096 oiwm->metadata = metadata->metadata;
6097 oiwm->metadata_mask = metadata->mask;
6098 }
6099}
6100
cab50449 6101static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
6102parse_WRITE_METADATA(char *arg, struct ofpbuf *ofpacts,
6103 enum ofputil_protocol *usable_protocols)
6104{
6105 struct ofpact_metadata *om;
6106 char *mask = strchr(arg, '/');
6107
6108 *usable_protocols &= OFPUTIL_P_NXM_OF11_UP;
6109
6110 om = ofpact_put_WRITE_METADATA(ofpacts);
6111 if (mask) {
6112 char *error;
6113
6114 *mask = '\0';
6115 error = str_to_be64(mask + 1, &om->mask);
6116 if (error) {
6117 return error;
6118 }
6119 } else {
6120 om->mask = OVS_BE64_MAX;
6121 }
6122
6123 return str_to_be64(arg, &om->metadata);
6124}
6125
6126static void
6127format_WRITE_METADATA(const struct ofpact_metadata *a, struct ds *s)
6128{
b1c5bf1f
QM
6129 ds_put_format(s, "%swrite_metadata:%s%#"PRIx64,
6130 colors.param, colors.end, ntohll(a->metadata));
c2d936a4
BP
6131 if (a->mask != OVS_BE64_MAX) {
6132 ds_put_format(s, "/%#"PRIx64, ntohll(a->mask));
6133 }
4cceacb9 6134}
f25d0cf3 6135\f
c2d936a4 6136/* Goto-Table instruction. */
f25d0cf3
BP
6137
6138static void
c2d936a4
BP
6139encode_GOTO_TABLE(const struct ofpact_goto_table *goto_table,
6140 enum ofp_version ofp_version, struct ofpbuf *out)
f25d0cf3 6141{
c2d936a4
BP
6142 if (ofp_version == OFP10_VERSION) {
6143 struct nx_action_resubmit *nar;
f25d0cf3 6144
c2d936a4
BP
6145 nar = put_NXAST_RESUBMIT_TABLE(out);
6146 nar->table = goto_table->table_id;
6147 nar->in_port = htons(ofp_to_u16(OFPP_IN_PORT));
6148 } else {
6149 struct ofp11_instruction_goto_table *oigt;
6150
6151 oigt = instruction_put_OFPIT11_GOTO_TABLE(out);
6152 oigt->table_id = goto_table->table_id;
6153 memset(oigt->pad, 0, sizeof oigt->pad);
6154 }
6155}
6156
cab50449 6157static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
6158parse_GOTO_TABLE(char *arg, struct ofpbuf *ofpacts,
6159 enum ofputil_protocol *usable_protocols OVS_UNUSED)
6160{
6161 struct ofpact_goto_table *ogt = ofpact_put_GOTO_TABLE(ofpacts);
6162 char *table_s = strsep(&arg, ",");
6163 if (!table_s || !table_s[0]) {
6164 return xstrdup("instruction goto-table needs table id");
6165 }
6166 return str_to_u8(table_s, "table", &ogt->table_id);
6167}
6168
6169static void
6170format_GOTO_TABLE(const struct ofpact_goto_table *a, struct ds *s)
6171{
b1c5bf1f
QM
6172 ds_put_format(s, "%sgoto_table:%s%"PRIu8,
6173 colors.param, colors.end, a->table_id);
c2d936a4
BP
6174}
6175\f
6176static void
5ad4b3f8 6177log_bad_action(const struct ofp_action_header *actions, size_t actions_len,
c2d936a4
BP
6178 const struct ofp_action_header *bad_action, enum ofperr error)
6179{
6180 if (!VLOG_DROP_WARN(&rl)) {
6181 struct ds s;
6182
6183 ds_init(&s);
5ad4b3f8 6184 ds_put_hex_dump(&s, actions, actions_len, 0, false);
c2d936a4
BP
6185 VLOG_WARN("bad action at offset %#"PRIxPTR" (%s):\n%s",
6186 (char *)bad_action - (char *)actions,
6187 ofperr_get_name(error), ds_cstr(&s));
6188 ds_destroy(&s);
6189 }
6190}
6191
6192static enum ofperr
6193ofpacts_decode(const void *actions, size_t actions_len,
6194 enum ofp_version ofp_version, struct ofpbuf *ofpacts)
6195{
0a2869d5 6196 struct ofpbuf openflow = ofpbuf_const_initializer(actions, actions_len);
6fd6ed71
PS
6197 while (openflow.size) {
6198 const struct ofp_action_header *action = openflow.data;
c2d936a4
BP
6199 enum ofp_raw_action_type raw;
6200 enum ofperr error;
6201 uint64_t arg;
6202
6203 error = ofpact_pull_raw(&openflow, ofp_version, &raw, &arg);
6204 if (!error) {
f3cd3ac7 6205 error = ofpact_decode(action, raw, ofp_version, arg, ofpacts);
c2d936a4
BP
6206 }
6207
6208 if (error) {
5ad4b3f8 6209 log_bad_action(actions, actions_len, action, error);
c2d936a4
BP
6210 return error;
6211 }
6212 }
c2d936a4
BP
6213 return 0;
6214}
6215
6216static enum ofperr
6217ofpacts_pull_openflow_actions__(struct ofpbuf *openflow,
6218 unsigned int actions_len,
6219 enum ofp_version version,
6220 uint32_t allowed_ovsinsts,
d824b5b7
JS
6221 struct ofpbuf *ofpacts,
6222 enum ofpact_type outer_action)
c2d936a4
BP
6223{
6224 const struct ofp_action_header *actions;
9abca1e5 6225 size_t orig_size = ofpacts->size;
c2d936a4
BP
6226 enum ofperr error;
6227
c2d936a4
BP
6228 if (actions_len % OFP_ACTION_ALIGN != 0) {
6229 VLOG_WARN_RL(&rl, "OpenFlow message actions length %u is not a "
6230 "multiple of %d", actions_len, OFP_ACTION_ALIGN);
6231 return OFPERR_OFPBRC_BAD_LEN;
6232 }
6233
6234 actions = ofpbuf_try_pull(openflow, actions_len);
6235 if (actions == NULL) {
6236 VLOG_WARN_RL(&rl, "OpenFlow message actions length %u exceeds "
6237 "remaining message length (%"PRIu32")",
6fd6ed71 6238 actions_len, openflow->size);
c2d936a4
BP
6239 return OFPERR_OFPBRC_BAD_LEN;
6240 }
6241
6242 error = ofpacts_decode(actions, actions_len, version, ofpacts);
6243 if (error) {
9abca1e5 6244 ofpacts->size = orig_size;
c2d936a4
BP
6245 return error;
6246 }
6247
d824b5b7
JS
6248 error = ofpacts_verify(ofpacts->data, ofpacts->size, allowed_ovsinsts,
6249 outer_action);
c2d936a4 6250 if (error) {
9abca1e5 6251 ofpacts->size = orig_size;
c2d936a4
BP
6252 }
6253 return error;
6254}
6255
9abca1e5
BP
6256/* Attempts to convert 'actions_len' bytes of OpenFlow actions from the front
6257 * of 'openflow' into ofpacts. On success, appends the converted actions to
6258 * 'ofpacts'; on failure, 'ofpacts' is unchanged (but might be reallocated) .
c2d936a4
BP
6259 * Returns 0 if successful, otherwise an OpenFlow error.
6260 *
6261 * Actions are processed according to their OpenFlow version which
6262 * is provided in the 'version' parameter.
6263 *
6264 * In most places in OpenFlow, actions appear encapsulated in instructions, so
6265 * you should call ofpacts_pull_openflow_instructions() instead of this
6266 * function.
6267 *
6268 * The parsed actions are valid generically, but they may not be valid in a
6269 * specific context. For example, port numbers up to OFPP_MAX are valid
6270 * generically, but specific datapaths may only support port numbers in a
6271 * smaller range. Use ofpacts_check() to additional check whether actions are
6272 * valid in a specific context. */
6273enum ofperr
6274ofpacts_pull_openflow_actions(struct ofpbuf *openflow,
6275 unsigned int actions_len,
6276 enum ofp_version version,
6277 struct ofpbuf *ofpacts)
6278{
6279 return ofpacts_pull_openflow_actions__(openflow, actions_len, version,
6280 1u << OVSINST_OFPIT11_APPLY_ACTIONS,
d824b5b7 6281 ofpacts, 0);
c2d936a4
BP
6282}
6283\f
6284/* OpenFlow 1.1 actions. */
6285
6286
6287/* True if an action sets the value of a field
6288 * in a way that is compatibile with the action set.
1b0ee636 6289 * The field can be set via either a set or a move action.
c2d936a4
BP
6290 * False otherwise. */
6291static bool
1b0ee636 6292ofpact_is_set_or_move_action(const struct ofpact *a)
c2d936a4
BP
6293{
6294 switch (a->type) {
6295 case OFPACT_SET_FIELD:
1b0ee636 6296 case OFPACT_REG_MOVE:
c2d936a4
BP
6297 case OFPACT_SET_ETH_DST:
6298 case OFPACT_SET_ETH_SRC:
6299 case OFPACT_SET_IP_DSCP:
6300 case OFPACT_SET_IP_ECN:
6301 case OFPACT_SET_IP_TTL:
6302 case OFPACT_SET_IPV4_DST:
6303 case OFPACT_SET_IPV4_SRC:
6304 case OFPACT_SET_L4_DST_PORT:
6305 case OFPACT_SET_L4_SRC_PORT:
6306 case OFPACT_SET_MPLS_LABEL:
6307 case OFPACT_SET_MPLS_TC:
6308 case OFPACT_SET_MPLS_TTL:
6309 case OFPACT_SET_QUEUE:
6310 case OFPACT_SET_TUNNEL:
6311 case OFPACT_SET_VLAN_PCP:
6312 case OFPACT_SET_VLAN_VID:
6313 return true;
6314 case OFPACT_BUNDLE:
6315 case OFPACT_CLEAR_ACTIONS:
07659514 6316 case OFPACT_CT:
72fe7578 6317 case OFPACT_CT_CLEAR:
7ae62a67 6318 case OFPACT_CLONE:
9ac0aada 6319 case OFPACT_NAT:
c2d936a4
BP
6320 case OFPACT_CONTROLLER:
6321 case OFPACT_DEC_MPLS_TTL:
6322 case OFPACT_DEC_TTL:
6323 case OFPACT_ENQUEUE:
6324 case OFPACT_EXIT:
e672ff9b 6325 case OFPACT_UNROLL_XLATE:
c2d936a4
BP
6326 case OFPACT_FIN_TIMEOUT:
6327 case OFPACT_GOTO_TABLE:
6328 case OFPACT_GROUP:
6329 case OFPACT_LEARN:
18080541 6330 case OFPACT_CONJUNCTION:
c2d936a4
BP
6331 case OFPACT_METER:
6332 case OFPACT_MULTIPATH:
6333 case OFPACT_NOTE:
6334 case OFPACT_OUTPUT:
6335 case OFPACT_OUTPUT_REG:
aaca4fe0 6336 case OFPACT_OUTPUT_TRUNC:
c2d936a4
BP
6337 case OFPACT_POP_MPLS:
6338 case OFPACT_POP_QUEUE:
6339 case OFPACT_PUSH_MPLS:
6340 case OFPACT_PUSH_VLAN:
c2d936a4
BP
6341 case OFPACT_RESUBMIT:
6342 case OFPACT_SAMPLE:
6343 case OFPACT_STACK_POP:
6344 case OFPACT_STACK_PUSH:
6345 case OFPACT_STRIP_VLAN:
6346 case OFPACT_WRITE_ACTIONS:
6347 case OFPACT_WRITE_METADATA:
d4abaff5 6348 case OFPACT_DEBUG_RECIRC:
c2d936a4
BP
6349 return false;
6350 default:
6351 OVS_NOT_REACHED();
6352 }
6353}
6354
6355/* True if an action is allowed in the action set.
6356 * False otherwise. */
6357static bool
6358ofpact_is_allowed_in_actions_set(const struct ofpact *a)
6359{
6360 switch (a->type) {
6361 case OFPACT_DEC_MPLS_TTL:
6362 case OFPACT_DEC_TTL:
6363 case OFPACT_GROUP:
6364 case OFPACT_OUTPUT:
aaca4fe0 6365 case OFPACT_OUTPUT_TRUNC:
c2d936a4
BP
6366 case OFPACT_POP_MPLS:
6367 case OFPACT_PUSH_MPLS:
6368 case OFPACT_PUSH_VLAN:
1b0ee636 6369 case OFPACT_REG_MOVE:
c2d936a4
BP
6370 case OFPACT_SET_FIELD:
6371 case OFPACT_SET_ETH_DST:
6372 case OFPACT_SET_ETH_SRC:
6373 case OFPACT_SET_IP_DSCP:
6374 case OFPACT_SET_IP_ECN:
6375 case OFPACT_SET_IP_TTL:
6376 case OFPACT_SET_IPV4_DST:
6377 case OFPACT_SET_IPV4_SRC:
6378 case OFPACT_SET_L4_DST_PORT:
6379 case OFPACT_SET_L4_SRC_PORT:
6380 case OFPACT_SET_MPLS_LABEL:
6381 case OFPACT_SET_MPLS_TC:
6382 case OFPACT_SET_MPLS_TTL:
6383 case OFPACT_SET_QUEUE:
6384 case OFPACT_SET_TUNNEL:
6385 case OFPACT_SET_VLAN_PCP:
6386 case OFPACT_SET_VLAN_VID:
6387 case OFPACT_STRIP_VLAN:
6388 return true;
6389
6390 /* In general these actions are excluded because they are not part of
6391 * the OpenFlow specification nor map to actions that are defined in
6392 * the specification. Thus the order in which they should be applied
6393 * in the action set is undefined. */
6394 case OFPACT_BUNDLE:
7ae62a67 6395 case OFPACT_CLONE:
c2d936a4 6396 case OFPACT_CONTROLLER:
07659514 6397 case OFPACT_CT:
72fe7578 6398 case OFPACT_CT_CLEAR:
9ac0aada 6399 case OFPACT_NAT:
c2d936a4
BP
6400 case OFPACT_ENQUEUE:
6401 case OFPACT_EXIT:
e672ff9b 6402 case OFPACT_UNROLL_XLATE:
c2d936a4
BP
6403 case OFPACT_FIN_TIMEOUT:
6404 case OFPACT_LEARN:
18080541 6405 case OFPACT_CONJUNCTION:
c2d936a4
BP
6406 case OFPACT_MULTIPATH:
6407 case OFPACT_NOTE:
6408 case OFPACT_OUTPUT_REG:
6409 case OFPACT_POP_QUEUE:
c2d936a4
BP
6410 case OFPACT_RESUBMIT:
6411 case OFPACT_SAMPLE:
6412 case OFPACT_STACK_POP:
6413 case OFPACT_STACK_PUSH:
d4abaff5 6414 case OFPACT_DEBUG_RECIRC:
c2d936a4
BP
6415
6416 /* The action set may only include actions and thus
6417 * may not include any instructions */
6418 case OFPACT_CLEAR_ACTIONS:
6419 case OFPACT_GOTO_TABLE:
6420 case OFPACT_METER:
6421 case OFPACT_WRITE_ACTIONS:
6422 case OFPACT_WRITE_METADATA:
6423 return false;
6424 default:
6425 OVS_NOT_REACHED();
6426 }
f25d0cf3
BP
6427}
6428
c2d936a4 6429/* Append ofpact 'a' onto the tail of 'out' */
f25d0cf3 6430static void
c2d936a4 6431ofpact_copy(struct ofpbuf *out, const struct ofpact *a)
f25d0cf3 6432{
c2d936a4 6433 ofpbuf_put(out, a, OFPACT_ALIGN(a->len));
f25d0cf3
BP
6434}
6435
c2d936a4
BP
6436/* Copies the last ofpact whose type is 'filter' from 'in' to 'out'. */
6437static bool
6438ofpacts_copy_last(struct ofpbuf *out, const struct ofpbuf *in,
6439 enum ofpact_type filter)
f25d0cf3 6440{
c2d936a4
BP
6441 const struct ofpact *target;
6442 const struct ofpact *a;
f25d0cf3 6443
c2d936a4 6444 target = NULL;
6fd6ed71 6445 OFPACT_FOR_EACH (a, in->data, in->size) {
c2d936a4
BP
6446 if (a->type == filter) {
6447 target = a;
6448 }
6449 }
6450 if (target) {
6451 ofpact_copy(out, target);
f25d0cf3 6452 }
c2d936a4 6453 return target != NULL;
f25d0cf3
BP
6454}
6455
c2d936a4
BP
6456/* Append all ofpacts, for which 'filter' returns true, from 'in' to 'out'.
6457 * The order of appended ofpacts is preserved between 'in' and 'out' */
4cceacb9 6458static void
c2d936a4
BP
6459ofpacts_copy_all(struct ofpbuf *out, const struct ofpbuf *in,
6460 bool (*filter)(const struct ofpact *))
4cceacb9 6461{
c2d936a4 6462 const struct ofpact *a;
4cceacb9 6463
6fd6ed71 6464 OFPACT_FOR_EACH (a, in->data, in->size) {
c2d936a4
BP
6465 if (filter(a)) {
6466 ofpact_copy(out, a);
6467 }
6468 }
4cceacb9
JS
6469}
6470
c2d936a4
BP
6471/* Reads 'action_set', which contains ofpacts accumulated by
6472 * OFPACT_WRITE_ACTIONS instructions, and writes equivalent actions to be
6473 * executed directly into 'action_list'. (These names correspond to the
6474 * "Action Set" and "Action List" terms used in OpenFlow 1.1+.)
6475 *
6476 * In general this involves appending the last instance of each action that is
e672ff9b 6477 * admissible in the action set in the order described in the OpenFlow
c2d936a4
BP
6478 * specification.
6479 *
6480 * Exceptions:
6481 * + output action is only appended if no group action was present in 'in'.
6482 * + As a simplification all set actions are copied in the order the are
6483 * provided in 'in' as many set actions applied to a field has the same
6484 * affect as only applying the last action that sets a field and
6485 * duplicates are removed by do_xlate_actions().
6486 * This has an unwanted side-effect of compsoting multiple
6487 * LOAD_REG actions that touch different regions of the same field. */
6488void
6489ofpacts_execute_action_set(struct ofpbuf *action_list,
6490 const struct ofpbuf *action_set)
f25d0cf3 6491{
c2d936a4
BP
6492 /* The OpenFlow spec "Action Set" section specifies this order. */
6493 ofpacts_copy_last(action_list, action_set, OFPACT_STRIP_VLAN);
6494 ofpacts_copy_last(action_list, action_set, OFPACT_POP_MPLS);
6495 ofpacts_copy_last(action_list, action_set, OFPACT_PUSH_MPLS);
6496 ofpacts_copy_last(action_list, action_set, OFPACT_PUSH_VLAN);
6497 ofpacts_copy_last(action_list, action_set, OFPACT_DEC_TTL);
6498 ofpacts_copy_last(action_list, action_set, OFPACT_DEC_MPLS_TTL);
1b0ee636 6499 ofpacts_copy_all(action_list, action_set, ofpact_is_set_or_move_action);
c2d936a4 6500 ofpacts_copy_last(action_list, action_set, OFPACT_SET_QUEUE);
f25d0cf3 6501
c2d936a4
BP
6502 /* If both OFPACT_GROUP and OFPACT_OUTPUT are present, OpenFlow says that
6503 * we should execute only OFPACT_GROUP.
6504 *
6505 * If neither OFPACT_GROUP nor OFPACT_OUTPUT is present, then we can drop
6506 * all the actions because there's no point in modifying a packet that will
6507 * not be sent anywhere. */
6508 if (!ofpacts_copy_last(action_list, action_set, OFPACT_GROUP) &&
2e34a6a3 6509 !ofpacts_copy_last(action_list, action_set, OFPACT_OUTPUT) &&
2c66ebe4
JR
6510 !ofpacts_copy_last(action_list, action_set, OFPACT_RESUBMIT) &&
6511 !ofpacts_copy_last(action_list, action_set, OFPACT_CT)) {
c2d936a4 6512 ofpbuf_clear(action_list);
f25d0cf3 6513 }
f25d0cf3
BP
6514}
6515
f25d0cf3 6516
c2d936a4
BP
6517static enum ofperr
6518ofpacts_decode_for_action_set(const struct ofp_action_header *in,
6519 size_t n_in, enum ofp_version version,
6520 struct ofpbuf *out)
c2d967a5 6521{
c2d936a4
BP
6522 enum ofperr error;
6523 struct ofpact *a;
6fd6ed71 6524 size_t start = out->size;
c2d967a5 6525
c2d936a4 6526 error = ofpacts_decode(in, n_in, version, out);
c2d967a5 6527
c2d936a4
BP
6528 if (error) {
6529 return error;
6530 }
6531
6fd6ed71 6532 OFPACT_FOR_EACH (a, ofpact_end(out->data, start), out->size - start) {
c2d936a4
BP
6533 if (!ofpact_is_allowed_in_actions_set(a)) {
6534 VLOG_WARN_RL(&rl, "disallowed action in action set");
6535 return OFPERR_OFPBAC_BAD_TYPE;
c2d967a5
MM
6536 }
6537 }
c2d936a4
BP
6538
6539 return 0;
c2d967a5 6540}
c2d936a4
BP
6541\f
6542/* OpenFlow 1.1 instructions. */
c2d967a5 6543
c2d936a4
BP
6544struct instruction_type_info {
6545 enum ovs_instruction_type type;
6546 const char *name;
6547};
6548
6549static const struct instruction_type_info inst_info[] = {
6550#define DEFINE_INST(ENUM, STRUCT, EXTENSIBLE, NAME) {OVSINST_##ENUM, NAME},
6551OVS_INSTRUCTIONS
6552#undef DEFINE_INST
6553};
6554
6555const char *
6556ovs_instruction_name_from_type(enum ovs_instruction_type type)
f25d0cf3 6557{
c2d936a4 6558 return inst_info[type].name;
f25d0cf3
BP
6559}
6560
c2d936a4
BP
6561int
6562ovs_instruction_type_from_name(const char *name)
29089a54 6563{
c2d936a4
BP
6564 const struct instruction_type_info *p;
6565 for (p = inst_info; p < &inst_info[ARRAY_SIZE(inst_info)]; p++) {
6566 if (!strcasecmp(name, p->name)) {
6567 return p->type;
6568 }
6569 }
6570 return -1;
29089a54
RL
6571}
6572
c2d936a4
BP
6573enum ovs_instruction_type
6574ovs_instruction_type_from_ofpact_type(enum ofpact_type type)
f25d0cf3 6575{
c2d936a4
BP
6576 switch (type) {
6577 case OFPACT_METER:
6578 return OVSINST_OFPIT13_METER;
6579 case OFPACT_CLEAR_ACTIONS:
6580 return OVSINST_OFPIT11_CLEAR_ACTIONS;
6581 case OFPACT_WRITE_ACTIONS:
6582 return OVSINST_OFPIT11_WRITE_ACTIONS;
6583 case OFPACT_WRITE_METADATA:
6584 return OVSINST_OFPIT11_WRITE_METADATA;
6585 case OFPACT_GOTO_TABLE:
6586 return OVSINST_OFPIT11_GOTO_TABLE;
6587 case OFPACT_OUTPUT:
6588 case OFPACT_GROUP:
7ae62a67 6589 case OFPACT_CLONE:
f25d0cf3 6590 case OFPACT_CONTROLLER:
c2d936a4 6591 case OFPACT_ENQUEUE:
f25d0cf3 6592 case OFPACT_OUTPUT_REG:
aaca4fe0 6593 case OFPACT_OUTPUT_TRUNC:
f25d0cf3 6594 case OFPACT_BUNDLE:
c2d936a4
BP
6595 case OFPACT_SET_VLAN_VID:
6596 case OFPACT_SET_VLAN_PCP:
6597 case OFPACT_STRIP_VLAN:
6598 case OFPACT_PUSH_VLAN:
6599 case OFPACT_SET_ETH_SRC:
6600 case OFPACT_SET_ETH_DST:
6601 case OFPACT_SET_IPV4_SRC:
6602 case OFPACT_SET_IPV4_DST:
6603 case OFPACT_SET_IP_DSCP:
6604 case OFPACT_SET_IP_ECN:
6605 case OFPACT_SET_IP_TTL:
6606 case OFPACT_SET_L4_SRC_PORT:
6607 case OFPACT_SET_L4_DST_PORT:
f25d0cf3 6608 case OFPACT_REG_MOVE:
c2d936a4 6609 case OFPACT_SET_FIELD:
bd85dac1 6610 case OFPACT_STACK_PUSH:
bd85dac1 6611 case OFPACT_STACK_POP:
f25d0cf3 6612 case OFPACT_DEC_TTL:
097d4939 6613 case OFPACT_SET_MPLS_LABEL:
097d4939 6614 case OFPACT_SET_MPLS_TC:
0f3f3c3d 6615 case OFPACT_SET_MPLS_TTL:
b676167a 6616 case OFPACT_DEC_MPLS_TTL:
c2d936a4
BP
6617 case OFPACT_PUSH_MPLS:
6618 case OFPACT_POP_MPLS:
f25d0cf3 6619 case OFPACT_SET_TUNNEL:
c2d936a4
BP
6620 case OFPACT_SET_QUEUE:
6621 case OFPACT_POP_QUEUE:
6622 case OFPACT_FIN_TIMEOUT:
6623 case OFPACT_RESUBMIT:
6624 case OFPACT_LEARN:
18080541 6625 case OFPACT_CONJUNCTION:
c2d936a4
BP
6626 case OFPACT_MULTIPATH:
6627 case OFPACT_NOTE:
6628 case OFPACT_EXIT:
e672ff9b 6629 case OFPACT_UNROLL_XLATE:
c2d936a4 6630 case OFPACT_SAMPLE:
d4abaff5 6631 case OFPACT_DEBUG_RECIRC:
07659514 6632 case OFPACT_CT:
72fe7578 6633 case OFPACT_CT_CLEAR:
9ac0aada 6634 case OFPACT_NAT:
c2d936a4
BP
6635 default:
6636 return OVSINST_OFPIT11_APPLY_ACTIONS;
6637 }
6638}
6639
6640enum ofperr
6641ovs_instruction_type_from_inst_type(enum ovs_instruction_type *instruction_type,
6642 const uint16_t inst_type)
6643{
6644 switch (inst_type) {
6645
6646#define DEFINE_INST(ENUM, STRUCT, EXTENSIBLE, NAME) \
6647 case ENUM: \
6648 *instruction_type = OVSINST_##ENUM; \
6649 return 0;
6650OVS_INSTRUCTIONS
6651#undef DEFINE_INST
6652
6653 default:
6654 return OFPERR_OFPBIC_UNKNOWN_INST;
6655 }
6656}
6657
6658/* Two-way translation between OVS's internal "OVSINST_*" representation of
6659 * instructions and the "OFPIT_*" representation used in OpenFlow. */
6660struct ovsinst_map {
6661 enum ovs_instruction_type ovsinst; /* Internal name for instruction. */
6662 int ofpit; /* OFPIT_* number from OpenFlow spec. */
6663};
6664
6665static const struct ovsinst_map *
6666get_ovsinst_map(enum ofp_version version)
6667{
6668 /* OpenFlow 1.1 and 1.2 instructions. */
6669 static const struct ovsinst_map of11[] = {
6670 { OVSINST_OFPIT11_GOTO_TABLE, 1 },
6671 { OVSINST_OFPIT11_WRITE_METADATA, 2 },
6672 { OVSINST_OFPIT11_WRITE_ACTIONS, 3 },
6673 { OVSINST_OFPIT11_APPLY_ACTIONS, 4 },
6674 { OVSINST_OFPIT11_CLEAR_ACTIONS, 5 },
6675 { 0, -1 },
6676 };
f25d0cf3 6677
c2d936a4
BP
6678 /* OpenFlow 1.3+ instructions. */
6679 static const struct ovsinst_map of13[] = {
6680 { OVSINST_OFPIT11_GOTO_TABLE, 1 },
6681 { OVSINST_OFPIT11_WRITE_METADATA, 2 },
6682 { OVSINST_OFPIT11_WRITE_ACTIONS, 3 },
6683 { OVSINST_OFPIT11_APPLY_ACTIONS, 4 },
6684 { OVSINST_OFPIT11_CLEAR_ACTIONS, 5 },
6685 { OVSINST_OFPIT13_METER, 6 },
6686 { 0, -1 },
6687 };
4cceacb9 6688
c2d936a4
BP
6689 return version < OFP13_VERSION ? of11 : of13;
6690}
f25d0cf3 6691
c2d936a4
BP
6692/* Converts 'ovsinst_bitmap', a bitmap whose bits correspond to OVSINST_*
6693 * values, into a bitmap of instructions suitable for OpenFlow 'version'
6694 * (OFP11_VERSION or later), and returns the result. */
6695ovs_be32
6696ovsinst_bitmap_to_openflow(uint32_t ovsinst_bitmap, enum ofp_version version)
6697{
6698 uint32_t ofpit_bitmap = 0;
6699 const struct ovsinst_map *x;
f25d0cf3 6700
c2d936a4
BP
6701 for (x = get_ovsinst_map(version); x->ofpit >= 0; x++) {
6702 if (ovsinst_bitmap & (1u << x->ovsinst)) {
6703 ofpit_bitmap |= 1u << x->ofpit;
6704 }
6705 }
6706 return htonl(ofpit_bitmap);
6707}
f25d0cf3 6708
c2d936a4
BP
6709/* Converts 'ofpit_bitmap', a bitmap of instructions from an OpenFlow message
6710 * with the given 'version' (OFP11_VERSION or later) into a bitmap whose bits
6711 * correspond to OVSINST_* values, and returns the result. */
6712uint32_t
6713ovsinst_bitmap_from_openflow(ovs_be32 ofpit_bitmap, enum ofp_version version)
6714{
6715 uint32_t ovsinst_bitmap = 0;
6716 const struct ovsinst_map *x;
f25d0cf3 6717
c2d936a4
BP
6718 for (x = get_ovsinst_map(version); x->ofpit >= 0; x++) {
6719 if (ofpit_bitmap & htonl(1u << x->ofpit)) {
6720 ovsinst_bitmap |= 1u << x->ovsinst;
6721 }
6722 }
6723 return ovsinst_bitmap;
6724}
f25d0cf3 6725
c2d936a4
BP
6726static inline struct ofp11_instruction *
6727instruction_next(const struct ofp11_instruction *inst)
6728{
6729 return ((struct ofp11_instruction *) (void *)
6730 ((uint8_t *) inst + ntohs(inst->len)));
6731}
f25d0cf3 6732
c2d936a4
BP
6733static inline bool
6734instruction_is_valid(const struct ofp11_instruction *inst,
6735 size_t n_instructions)
6736{
6737 uint16_t len = ntohs(inst->len);
6738 return (!(len % OFP11_INSTRUCTION_ALIGN)
6739 && len >= sizeof *inst
6740 && len / sizeof *inst <= n_instructions);
6741}
f25d0cf3 6742
c2d936a4
BP
6743/* This macro is careful to check for instructions with bad lengths. */
6744#define INSTRUCTION_FOR_EACH(ITER, LEFT, INSTRUCTIONS, N_INSTRUCTIONS) \
6745 for ((ITER) = (INSTRUCTIONS), (LEFT) = (N_INSTRUCTIONS); \
6746 (LEFT) > 0 && instruction_is_valid(ITER, LEFT); \
6747 ((LEFT) -= (ntohs((ITER)->len) \
6748 / sizeof(struct ofp11_instruction)), \
6749 (ITER) = instruction_next(ITER)))
f25d0cf3 6750
c2d936a4
BP
6751static enum ofperr
6752decode_openflow11_instruction(const struct ofp11_instruction *inst,
6753 enum ovs_instruction_type *type)
6754{
6755 uint16_t len = ntohs(inst->len);
b02475c5 6756
c2d936a4
BP
6757 switch (inst->type) {
6758 case CONSTANT_HTONS(OFPIT11_EXPERIMENTER):
6759 return OFPERR_OFPBIC_BAD_EXPERIMENTER;
b02475c5 6760
c2d936a4
BP
6761#define DEFINE_INST(ENUM, STRUCT, EXTENSIBLE, NAME) \
6762 case CONSTANT_HTONS(ENUM): \
6763 if (EXTENSIBLE \
6764 ? len >= sizeof(struct STRUCT) \
6765 : len == sizeof(struct STRUCT)) { \
6766 *type = OVSINST_##ENUM; \
6767 return 0; \
6768 } else { \
6769 return OFPERR_OFPBIC_BAD_LEN; \
6770 }
6771OVS_INSTRUCTIONS
6772#undef DEFINE_INST
29089a54 6773
c2d936a4
BP
6774 default:
6775 return OFPERR_OFPBIC_UNKNOWN_INST;
f25d0cf3
BP
6776 }
6777}
f25d0cf3 6778
c2d936a4
BP
6779static enum ofperr
6780decode_openflow11_instructions(const struct ofp11_instruction insts[],
6781 size_t n_insts,
6782 const struct ofp11_instruction *out[])
f25d0cf3 6783{
c2d936a4
BP
6784 const struct ofp11_instruction *inst;
6785 size_t left;
f25d0cf3 6786
c2d936a4
BP
6787 memset(out, 0, N_OVS_INSTRUCTIONS * sizeof *out);
6788 INSTRUCTION_FOR_EACH (inst, left, insts, n_insts) {
6789 enum ovs_instruction_type type;
6790 enum ofperr error;
f25d0cf3 6791
c2d936a4
BP
6792 error = decode_openflow11_instruction(inst, &type);
6793 if (error) {
6794 return error;
6795 }
f25d0cf3 6796
c2d936a4
BP
6797 if (out[type]) {
6798 return OFPERR_OFPBIC_DUP_INST;
6799 }
6800 out[type] = inst;
6801 }
6802
6803 if (left) {
6804 VLOG_WARN_RL(&rl, "bad instruction format at offset %"PRIuSIZE,
6805 (n_insts - left) * sizeof *inst);
6806 return OFPERR_OFPBIC_BAD_LEN;
6807 }
6808 return 0;
f25d0cf3
BP
6809}
6810
6811static void
c2d936a4
BP
6812get_actions_from_instruction(const struct ofp11_instruction *inst,
6813 const struct ofp_action_header **actions,
6814 size_t *actions_len)
f25d0cf3 6815{
c2d936a4
BP
6816 *actions = ALIGNED_CAST(const struct ofp_action_header *, inst + 1);
6817 *actions_len = ntohs(inst->len) - sizeof *inst;
6818}
f25d0cf3 6819
c2d936a4
BP
6820enum ofperr
6821ofpacts_pull_openflow_instructions(struct ofpbuf *openflow,
6822 unsigned int instructions_len,
6823 enum ofp_version version,
6824 struct ofpbuf *ofpacts)
6825{
6826 const struct ofp11_instruction *instructions;
6827 const struct ofp11_instruction *insts[N_OVS_INSTRUCTIONS];
6828 enum ofperr error;
f25d0cf3 6829
9abca1e5 6830 ofpbuf_clear(ofpacts);
c2d936a4
BP
6831 if (version == OFP10_VERSION) {
6832 return ofpacts_pull_openflow_actions__(openflow, instructions_len,
6833 version,
6834 (1u << N_OVS_INSTRUCTIONS) - 1,
d824b5b7 6835 ofpacts, 0);
c2d936a4 6836 }
f25d0cf3 6837
c2d936a4
BP
6838 if (instructions_len % OFP11_INSTRUCTION_ALIGN != 0) {
6839 VLOG_WARN_RL(&rl, "OpenFlow message instructions length %u is not a "
6840 "multiple of %d",
6841 instructions_len, OFP11_INSTRUCTION_ALIGN);
6842 error = OFPERR_OFPBIC_BAD_LEN;
6843 goto exit;
6844 }
f25d0cf3 6845
c2d936a4
BP
6846 instructions = ofpbuf_try_pull(openflow, instructions_len);
6847 if (instructions == NULL) {
6848 VLOG_WARN_RL(&rl, "OpenFlow message instructions length %u exceeds "
6849 "remaining message length (%"PRIu32")",
6fd6ed71 6850 instructions_len, openflow->size);
c2d936a4
BP
6851 error = OFPERR_OFPBIC_BAD_LEN;
6852 goto exit;
6853 }
f25d0cf3 6854
c2d936a4
BP
6855 error = decode_openflow11_instructions(
6856 instructions, instructions_len / OFP11_INSTRUCTION_ALIGN,
6857 insts);
6858 if (error) {
6859 goto exit;
6860 }
f25d0cf3 6861
c2d936a4
BP
6862 if (insts[OVSINST_OFPIT13_METER]) {
6863 const struct ofp13_instruction_meter *oim;
6864 struct ofpact_meter *om;
f25d0cf3 6865
c2d936a4
BP
6866 oim = ALIGNED_CAST(const struct ofp13_instruction_meter *,
6867 insts[OVSINST_OFPIT13_METER]);
f25d0cf3 6868
c2d936a4
BP
6869 om = ofpact_put_METER(ofpacts);
6870 om->meter_id = ntohl(oim->meter_id);
6871 }
6872 if (insts[OVSINST_OFPIT11_APPLY_ACTIONS]) {
6873 const struct ofp_action_header *actions;
6874 size_t actions_len;
f25d0cf3 6875
c2d936a4
BP
6876 get_actions_from_instruction(insts[OVSINST_OFPIT11_APPLY_ACTIONS],
6877 &actions, &actions_len);
6878 error = ofpacts_decode(actions, actions_len, version, ofpacts);
6879 if (error) {
6880 goto exit;
6881 }
6882 }
6883 if (insts[OVSINST_OFPIT11_CLEAR_ACTIONS]) {
6884 instruction_get_OFPIT11_CLEAR_ACTIONS(
6885 insts[OVSINST_OFPIT11_CLEAR_ACTIONS]);
6886 ofpact_put_CLEAR_ACTIONS(ofpacts);
6887 }
6888 if (insts[OVSINST_OFPIT11_WRITE_ACTIONS]) {
6889 struct ofpact_nest *on;
6890 const struct ofp_action_header *actions;
6891 size_t actions_len;
2bd318de 6892 size_t start = ofpacts->size;
255a54ea
BP
6893 ofpact_put(ofpacts, OFPACT_WRITE_ACTIONS,
6894 offsetof(struct ofpact_nest, actions));
c2d936a4
BP
6895 get_actions_from_instruction(insts[OVSINST_OFPIT11_WRITE_ACTIONS],
6896 &actions, &actions_len);
6897 error = ofpacts_decode_for_action_set(actions, actions_len,
6898 version, ofpacts);
6899 if (error) {
6900 goto exit;
6901 }
6902 on = ofpbuf_at_assert(ofpacts, start, sizeof *on);
6fd6ed71 6903 on->ofpact.len = ofpacts->size - start;
c2d936a4
BP
6904 }
6905 if (insts[OVSINST_OFPIT11_WRITE_METADATA]) {
6906 const struct ofp11_instruction_write_metadata *oiwm;
6907 struct ofpact_metadata *om;
ca287d20 6908
c2d936a4
BP
6909 oiwm = ALIGNED_CAST(const struct ofp11_instruction_write_metadata *,
6910 insts[OVSINST_OFPIT11_WRITE_METADATA]);
8dd54666 6911
c2d936a4
BP
6912 om = ofpact_put_WRITE_METADATA(ofpacts);
6913 om->metadata = oiwm->metadata;
6914 om->mask = oiwm->metadata_mask;
6915 }
6916 if (insts[OVSINST_OFPIT11_GOTO_TABLE]) {
6917 const struct ofp11_instruction_goto_table *oigt;
6918 struct ofpact_goto_table *ogt;
7395c052 6919
c2d936a4
BP
6920 oigt = instruction_get_OFPIT11_GOTO_TABLE(
6921 insts[OVSINST_OFPIT11_GOTO_TABLE]);
6922 ogt = ofpact_put_GOTO_TABLE(ofpacts);
6923 ogt->table_id = oigt->table_id;
6924 }
e3f8f887 6925
6fd6ed71 6926 error = ofpacts_verify(ofpacts->data, ofpacts->size,
d824b5b7 6927 (1u << N_OVS_INSTRUCTIONS) - 1, 0);
c2d936a4
BP
6928exit:
6929 if (error) {
6930 ofpbuf_clear(ofpacts);
f25d0cf3 6931 }
c2d936a4 6932 return error;
f25d0cf3 6933}
d01c980f 6934
c2d936a4
BP
6935/* Update the length of the instruction that begins at offset 'ofs' within
6936 * 'openflow' and contains nested actions that extend to the end of 'openflow'.
6937 * If the instruction contains no nested actions, deletes it entirely. */
d01c980f 6938static void
c2d936a4 6939ofpacts_update_instruction_actions(struct ofpbuf *openflow, size_t ofs)
d01c980f 6940{
c2d936a4 6941 struct ofp11_instruction_actions *oia;
d01c980f 6942
c2d936a4 6943 oia = ofpbuf_at_assert(openflow, ofs, sizeof *oia);
6fd6ed71
PS
6944 if (openflow->size > ofs + sizeof *oia) {
6945 oia->len = htons(openflow->size - ofs);
c2d936a4 6946 } else {
6fd6ed71 6947 openflow->size = ofs;
c2d936a4 6948 }
d01c980f 6949}
c2d936a4
BP
6950\f
6951/* Checks that 'port' is a valid output port for OFPACT_OUTPUT, given that the
6952 * switch will never have more than 'max_ports' ports. Returns 0 if 'port' is
6953 * valid, otherwise an OpenFlow error code. */
6954enum ofperr
6955ofpact_check_output_port(ofp_port_t port, ofp_port_t max_ports)
99086062 6956{
c2d936a4
BP
6957 switch (port) {
6958 case OFPP_IN_PORT:
6959 case OFPP_TABLE:
6960 case OFPP_NORMAL:
6961 case OFPP_FLOOD:
6962 case OFPP_ALL:
6963 case OFPP_CONTROLLER:
c2d936a4
BP
6964 case OFPP_LOCAL:
6965 return 0;
6966
13d2c689
BP
6967 case OFPP_NONE:
6968 return OFPERR_OFPBAC_BAD_OUT_PORT;
6969
c2d936a4
BP
6970 default:
6971 if (ofp_to_u16(port) < ofp_to_u16(max_ports)) {
6972 return 0;
6973 }
6974 return OFPERR_OFPBAC_BAD_OUT_PORT;
99086062
BP
6975 }
6976}
6977
c2d936a4
BP
6978/* Removes the protocols that require consistency between match and actions
6979 * (that's everything but OpenFlow 1.0) from '*usable_protocols'.
6980 *
6981 * (An example of an inconsistency between match and actions is a flow that
6982 * does not match on an MPLS Ethertype but has an action that pops an MPLS
6983 * label.) */
d01c980f 6984static void
c2d936a4
BP
6985inconsistent_match(enum ofputil_protocol *usable_protocols)
6986{
6987 *usable_protocols &= OFPUTIL_P_OF10_ANY;
6988}
6989
6990/* May modify flow->dl_type, flow->nw_proto and flow->vlan_tci,
6991 * caller must restore them.
6992 *
6993 * Modifies some actions, filling in fields that could not be properly set
6994 * without context. */
6995static enum ofperr
6996ofpact_check__(enum ofputil_protocol *usable_protocols, struct ofpact *a,
6997 struct flow *flow, ofp_port_t max_ports,
6998 uint8_t table_id, uint8_t n_tables)
d01c980f 6999{
c2d936a4
BP
7000 const struct ofpact_enqueue *enqueue;
7001 const struct mf_field *mf;
7002
d01c980f
BP
7003 switch (a->type) {
7004 case OFPACT_OUTPUT:
c2d936a4
BP
7005 return ofpact_check_output_port(ofpact_get_OUTPUT(a)->port,
7006 max_ports);
7007
7008 case OFPACT_CONTROLLER:
7009 return 0;
d01c980f
BP
7010
7011 case OFPACT_ENQUEUE:
c2d936a4
BP
7012 enqueue = ofpact_get_ENQUEUE(a);
7013 if (ofp_to_u16(enqueue->port) >= ofp_to_u16(max_ports)
7014 && enqueue->port != OFPP_IN_PORT
7015 && enqueue->port != OFPP_LOCAL) {
7016 return OFPERR_OFPBAC_BAD_OUT_PORT;
7017 }
7018 return 0;
7019
7020 case OFPACT_OUTPUT_REG:
7021 return mf_check_src(&ofpact_get_OUTPUT_REG(a)->src, flow);
7022
aaca4fe0
WT
7023 case OFPACT_OUTPUT_TRUNC:
7024 return ofpact_check_output_port(ofpact_get_OUTPUT_TRUNC(a)->port,
7025 max_ports);
7026
c2d936a4
BP
7027 case OFPACT_BUNDLE:
7028 return bundle_check(ofpact_get_BUNDLE(a), max_ports, flow);
d01c980f
BP
7029
7030 case OFPACT_SET_VLAN_VID:
c2d936a4
BP
7031 /* Remember if we saw a vlan tag in the flow to aid translating to
7032 * OpenFlow 1.1+ if need be. */
7033 ofpact_get_SET_VLAN_VID(a)->flow_has_vlan =
7034 (flow->vlan_tci & htons(VLAN_CFI)) == htons(VLAN_CFI);
7035 if (!(flow->vlan_tci & htons(VLAN_CFI)) &&
7036 !ofpact_get_SET_VLAN_VID(a)->push_vlan_if_needed) {
7037 inconsistent_match(usable_protocols);
7038 }
7039 /* Temporary mark that we have a vlan tag. */
7040 flow->vlan_tci |= htons(VLAN_CFI);
7041 return 0;
d01c980f
BP
7042
7043 case OFPACT_SET_VLAN_PCP:
c2d936a4
BP
7044 /* Remember if we saw a vlan tag in the flow to aid translating to
7045 * OpenFlow 1.1+ if need be. */
7046 ofpact_get_SET_VLAN_PCP(a)->flow_has_vlan =
7047 (flow->vlan_tci & htons(VLAN_CFI)) == htons(VLAN_CFI);
7048 if (!(flow->vlan_tci & htons(VLAN_CFI)) &&
7049 !ofpact_get_SET_VLAN_PCP(a)->push_vlan_if_needed) {
7050 inconsistent_match(usable_protocols);
7051 }
7052 /* Temporary mark that we have a vlan tag. */
7053 flow->vlan_tci |= htons(VLAN_CFI);
7054 return 0;
d01c980f
BP
7055
7056 case OFPACT_STRIP_VLAN:
c2d936a4
BP
7057 if (!(flow->vlan_tci & htons(VLAN_CFI))) {
7058 inconsistent_match(usable_protocols);
7059 }
7060 /* Temporary mark that we have no vlan tag. */
7061 flow->vlan_tci = htons(0);
7062 return 0;
d01c980f 7063
3e34fbdd 7064 case OFPACT_PUSH_VLAN:
c2d936a4
BP
7065 if (flow->vlan_tci & htons(VLAN_CFI)) {
7066 /* Multiple VLAN headers not supported. */
7067 return OFPERR_OFPBAC_BAD_TAG;
7068 }
7069 /* Temporary mark that we have a vlan tag. */
7070 flow->vlan_tci |= htons(VLAN_CFI);
7071 return 0;
276c4e7a 7072
d01c980f 7073 case OFPACT_SET_ETH_SRC:
d01c980f 7074 case OFPACT_SET_ETH_DST:
c2d936a4 7075 return 0;
d01c980f
BP
7076
7077 case OFPACT_SET_IPV4_SRC:
d01c980f 7078 case OFPACT_SET_IPV4_DST:
c2d936a4
BP
7079 if (flow->dl_type != htons(ETH_TYPE_IP)) {
7080 inconsistent_match(usable_protocols);
7081 }
7082 return 0;
d01c980f 7083
04f01c24 7084 case OFPACT_SET_IP_DSCP:
ff14eb7a 7085 case OFPACT_SET_IP_ECN:
0c20dbe4 7086 case OFPACT_SET_IP_TTL:
7bcb1506 7087 case OFPACT_DEC_TTL:
c2d936a4
BP
7088 if (!is_ip_any(flow)) {
7089 inconsistent_match(usable_protocols);
7090 }
7091 return 0;
b02475c5 7092
c2d936a4 7093 case OFPACT_SET_L4_SRC_PORT:
c2d936a4 7094 case OFPACT_SET_L4_DST_PORT:
b8778a0d 7095 if (!is_ip_any(flow) || (flow->nw_frag & FLOW_NW_FRAG_LATER) ||
c2d936a4
BP
7096 (flow->nw_proto != IPPROTO_TCP && flow->nw_proto != IPPROTO_UDP
7097 && flow->nw_proto != IPPROTO_SCTP)) {
7098 inconsistent_match(usable_protocols);
7099 }
7100 /* Note on which transport protocol the port numbers are set.
7101 * This allows this set action to be converted to an OF1.2 set field
7102 * action. */
b8778a0d
JR
7103 if (a->type == OFPACT_SET_L4_SRC_PORT) {
7104 ofpact_get_SET_L4_SRC_PORT(a)->flow_ip_proto = flow->nw_proto;
7105 } else {
7106 ofpact_get_SET_L4_DST_PORT(a)->flow_ip_proto = flow->nw_proto;
7107 }
c2d936a4 7108 return 0;
b02475c5 7109
c2d936a4
BP
7110 case OFPACT_REG_MOVE:
7111 return nxm_reg_move_check(ofpact_get_REG_MOVE(a), flow);
8dd54666 7112
e3f8f887 7113 case OFPACT_SET_FIELD:
c2d936a4
BP
7114 mf = ofpact_get_SET_FIELD(a)->field;
7115 /* Require OXM_OF_VLAN_VID to have an existing VLAN header. */
aff49b8c 7116 if (!mf_are_prereqs_ok(mf, flow, NULL) ||
c2d936a4
BP
7117 (mf->id == MFF_VLAN_VID && !(flow->vlan_tci & htons(VLAN_CFI)))) {
7118 VLOG_WARN_RL(&rl, "set_field %s lacks correct prerequisities",
7119 mf->name);
7120 return OFPERR_OFPBAC_MATCH_INCONSISTENT;
7121 }
7122 /* Remember if we saw a vlan tag in the flow to aid translating to
7123 * OpenFlow 1.1 if need be. */
7124 ofpact_get_SET_FIELD(a)->flow_has_vlan =
7125 (flow->vlan_tci & htons(VLAN_CFI)) == htons(VLAN_CFI);
7126 if (mf->id == MFF_VLAN_TCI) {
7127 /* The set field may add or remove the vlan tag,
7128 * Mark the status temporarily. */
128684a6 7129 flow->vlan_tci = ofpact_get_SET_FIELD(a)->value->be16;
c2d936a4
BP
7130 }
7131 return 0;
e3f8f887 7132
bd85dac1 7133 case OFPACT_STACK_PUSH:
c2d936a4
BP
7134 return nxm_stack_push_check(ofpact_get_STACK_PUSH(a), flow);
7135
bd85dac1 7136 case OFPACT_STACK_POP:
c2d936a4
BP
7137 return nxm_stack_pop_check(ofpact_get_STACK_POP(a), flow);
7138
7139 case OFPACT_SET_MPLS_LABEL:
7140 case OFPACT_SET_MPLS_TC:
7141 case OFPACT_SET_MPLS_TTL:
7142 case OFPACT_DEC_MPLS_TTL:
7143 if (!eth_type_mpls(flow->dl_type)) {
7144 inconsistent_match(usable_protocols);
7145 }
7146 return 0;
7147
d01c980f 7148 case OFPACT_SET_TUNNEL:
c2d936a4 7149 case OFPACT_SET_QUEUE:
d01c980f 7150 case OFPACT_POP_QUEUE:
d01c980f 7151 case OFPACT_RESUBMIT:
c2d936a4
BP
7152 return 0;
7153
7154 case OFPACT_FIN_TIMEOUT:
7155 if (flow->nw_proto != IPPROTO_TCP) {
7156 inconsistent_match(usable_protocols);
7157 }
7158 return 0;
7159
d01c980f 7160 case OFPACT_LEARN:
c2d936a4
BP
7161 return learn_check(ofpact_get_LEARN(a), flow);
7162
18080541
BP
7163 case OFPACT_CONJUNCTION:
7164 return 0;
7165
d01c980f 7166 case OFPACT_MULTIPATH:
c2d936a4
BP
7167 return multipath_check(ofpact_get_MULTIPATH(a), flow);
7168
d01c980f
BP
7169 case OFPACT_NOTE:
7170 case OFPACT_EXIT:
c2d936a4 7171 return 0;
d01c980f 7172
c2d936a4
BP
7173 case OFPACT_PUSH_MPLS:
7174 flow->dl_type = ofpact_get_PUSH_MPLS(a)->ethertype;
7175 /* The packet is now MPLS and the MPLS payload is opaque.
7176 * Thus nothing can be assumed about the network protocol.
7177 * Temporarily mark that we have no nw_proto. */
7178 flow->nw_proto = 0;
7179 return 0;
1e7db674 7180
c2d936a4
BP
7181 case OFPACT_POP_MPLS:
7182 if (!eth_type_mpls(flow->dl_type)) {
7183 inconsistent_match(usable_protocols);
7184 }
7185 flow->dl_type = ofpact_get_POP_MPLS(a)->ethertype;
7186 return 0;
1e7db674 7187
c2d936a4
BP
7188 case OFPACT_SAMPLE:
7189 return 0;
1e7db674 7190
7ae62a67
WT
7191 case OFPACT_CLONE: {
7192 struct ofpact_nest *on = ofpact_get_CLONE(a);
7193 return ofpacts_check(on->actions, ofpact_nest_get_action_len(on),
7194 flow, max_ports, table_id, n_tables,
7195 usable_protocols);
7196 }
7197
07659514
JS
7198 case OFPACT_CT: {
7199 struct ofpact_conntrack *oc = ofpact_get_CT(a);
7200
7201 if (!dl_type_is_ip_any(flow->dl_type)
8b6d097c 7202 || (flow->ct_state & CS_INVALID && oc->flags & NX_CT_F_COMMIT)
40c7b2fc
JS
7203 || (oc->alg == IPPORT_FTP && flow->nw_proto != IPPROTO_TCP)
7204 || (oc->alg == IPPORT_TFTP && flow->nw_proto != IPPROTO_UDP)) {
ed26e3ea
JR
7205 /* We can't downgrade to OF1.0 and expect inconsistent CT actions
7206 * be silently discarded. Instead, datapath flow install fails, so
7207 * it is better to flag inconsistent CT actions as hard errors. */
7208 return OFPERR_OFPBAC_MATCH_INCONSISTENT;
07659514
JS
7209 }
7210
7211 if (oc->zone_src.field) {
7212 return mf_check_src(&oc->zone_src, flow);
7213 }
8e53fe8c 7214
9f02d70c
JR
7215 return ofpacts_check(oc->actions, ofpact_ct_get_action_len(oc),
7216 flow, max_ports, table_id, n_tables,
7217 usable_protocols);
07659514
JS
7218 }
7219
72fe7578
BP
7220 case OFPACT_CT_CLEAR:
7221 return 0;
7222
9ac0aada
JR
7223 case OFPACT_NAT: {
7224 struct ofpact_nat *on = ofpact_get_NAT(a);
7225
7226 if (!dl_type_is_ip_any(flow->dl_type) ||
7227 (on->range_af == AF_INET && flow->dl_type != htons(ETH_TYPE_IP)) ||
7228 (on->range_af == AF_INET6
7229 && flow->dl_type != htons(ETH_TYPE_IPV6))) {
ed26e3ea 7230 return OFPERR_OFPBAC_MATCH_INCONSISTENT;
9ac0aada
JR
7231 }
7232 return 0;
7233 }
7234
c2d936a4
BP
7235 case OFPACT_CLEAR_ACTIONS:
7236 return 0;
1e7db674 7237
c2d936a4
BP
7238 case OFPACT_WRITE_ACTIONS: {
7239 /* Use a temporary copy of 'usable_protocols' because we can't check
7240 * consistency of an action set. */
7241 struct ofpact_nest *on = ofpact_get_WRITE_ACTIONS(a);
7242 enum ofputil_protocol p = *usable_protocols;
7243 return ofpacts_check(on->actions, ofpact_nest_get_action_len(on),
7244 flow, max_ports, table_id, n_tables, &p);
7245 }
1e7db674 7246
c2d936a4
BP
7247 case OFPACT_WRITE_METADATA:
7248 return 0;
1e7db674 7249
c2d936a4
BP
7250 case OFPACT_METER: {
7251 uint32_t mid = ofpact_get_METER(a)->meter_id;
7252 if (mid == 0 || mid > OFPM13_MAX) {
7253 return OFPERR_OFPMMFC_INVALID_METER;
7254 }
7255 return 0;
7256 }
1e7db674 7257
c2d936a4
BP
7258 case OFPACT_GOTO_TABLE: {
7259 uint8_t goto_table = ofpact_get_GOTO_TABLE(a)->table_id;
7260 if ((table_id != 255 && goto_table <= table_id)
7261 || (n_tables != 255 && goto_table >= n_tables)) {
8c87971e 7262 return OFPERR_OFPBIC_BAD_TABLE_ID;
c2d936a4
BP
7263 }
7264 return 0;
7265 }
1e7db674 7266
c2d936a4
BP
7267 case OFPACT_GROUP:
7268 return 0;
1e7db674 7269
e672ff9b
JR
7270 case OFPACT_UNROLL_XLATE:
7271 /* UNROLL is an internal action that should never be seen via
7272 * OpenFlow. */
7273 return OFPERR_OFPBAC_BAD_TYPE;
7274
d4abaff5
BP
7275 case OFPACT_DEBUG_RECIRC:
7276 return 0;
7277
c2d936a4
BP
7278 default:
7279 OVS_NOT_REACHED();
7280 }
7281}
1e7db674 7282
c2d936a4
BP
7283/* Checks that the 'ofpacts_len' bytes of actions in 'ofpacts' are
7284 * appropriate for a packet with the prerequisites satisfied by 'flow' in a
7285 * switch with no more than 'max_ports' ports.
7286 *
7287 * If 'ofpacts' and 'flow' are inconsistent with one another, un-sets in
7288 * '*usable_protocols' the protocols that forbid the inconsistency. (An
7289 * example of an inconsistency between match and actions is a flow that does
7290 * not match on an MPLS Ethertype but has an action that pops an MPLS label.)
7291 *
7292 * May annotate ofpacts with information gathered from the 'flow'.
7293 *
7294 * May temporarily modify 'flow', but restores the changes before returning. */
7295enum ofperr
7296ofpacts_check(struct ofpact ofpacts[], size_t ofpacts_len,
7297 struct flow *flow, ofp_port_t max_ports,
7298 uint8_t table_id, uint8_t n_tables,
7299 enum ofputil_protocol *usable_protocols)
7300{
7301 struct ofpact *a;
7302 ovs_be16 dl_type = flow->dl_type;
7303 ovs_be16 vlan_tci = flow->vlan_tci;
7304 uint8_t nw_proto = flow->nw_proto;
7305 enum ofperr error = 0;
1e7db674 7306
c2d936a4
BP
7307 OFPACT_FOR_EACH (a, ofpacts, ofpacts_len) {
7308 error = ofpact_check__(usable_protocols, a, flow,
7309 max_ports, table_id, n_tables);
7310 if (error) {
1e7db674 7311 break;
c2d936a4
BP
7312 }
7313 }
7314 /* Restore fields that may have been modified. */
7315 flow->dl_type = dl_type;
7316 flow->vlan_tci = vlan_tci;
7317 flow->nw_proto = nw_proto;
7318 return error;
7319}
1e7db674 7320
c2d936a4
BP
7321/* Like ofpacts_check(), but reports inconsistencies as
7322 * OFPERR_OFPBAC_MATCH_INCONSISTENT rather than clearing bits. */
7323enum ofperr
7324ofpacts_check_consistency(struct ofpact ofpacts[], size_t ofpacts_len,
7325 struct flow *flow, ofp_port_t max_ports,
7326 uint8_t table_id, uint8_t n_tables,
7327 enum ofputil_protocol usable_protocols)
7328{
7329 enum ofputil_protocol p = usable_protocols;
7330 enum ofperr error;
1e7db674 7331
c2d936a4
BP
7332 error = ofpacts_check(ofpacts, ofpacts_len, flow, max_ports,
7333 table_id, n_tables, &p);
7334 return (error ? error
7335 : p != usable_protocols ? OFPERR_OFPBAC_MATCH_INCONSISTENT
7336 : 0);
7337}
097d4939 7338
28f5311f
JS
7339/* Returns the destination field that 'ofpact' would write to, or NULL
7340 * if the action would not write to an mf_field. */
7341const struct mf_field *
7342ofpact_get_mf_dst(const struct ofpact *ofpact)
8e53fe8c 7343{
28f5311f
JS
7344 if (ofpact->type == OFPACT_SET_FIELD) {
7345 const struct ofpact_set_field *orl;
8e53fe8c 7346
28f5311f 7347 orl = CONTAINER_OF(ofpact, struct ofpact_set_field, ofpact);
8e53fe8c 7348 return orl->field;
28f5311f
JS
7349 } else if (ofpact->type == OFPACT_REG_MOVE) {
7350 const struct ofpact_reg_move *orm;
8e53fe8c 7351
28f5311f 7352 orm = CONTAINER_OF(ofpact, struct ofpact_reg_move, ofpact);
8e53fe8c
JS
7353 return orm->dst.field;
7354 }
7355
7356 return NULL;
7357}
7358
7359static enum ofperr
7360unsupported_nesting(enum ofpact_type action, enum ofpact_type outer_action)
7361{
7362 VLOG_WARN("%s action doesn't support nested action %s",
7363 ofpact_name(outer_action), ofpact_name(action));
7364 return OFPERR_OFPBAC_BAD_ARGUMENT;
7365}
7366
7367static bool
7368field_requires_ct(enum mf_field_id field)
7369{
9daf2348 7370 return field == MFF_CT_MARK || field == MFF_CT_LABEL;
8e53fe8c
JS
7371}
7372
7373/* Apply nesting constraints for actions */
d824b5b7
JS
7374static enum ofperr
7375ofpacts_verify_nested(const struct ofpact *a, enum ofpact_type outer_action)
7376{
28f5311f 7377 const struct mf_field *field = ofpact_get_mf_dst(a);
8e53fe8c
JS
7378
7379 if (field && field_requires_ct(field->id) && outer_action != OFPACT_CT) {
7380 VLOG_WARN("cannot set CT fields outside of ct action");
7381 return OFPERR_OFPBAC_BAD_SET_ARGUMENT;
7382 }
9ac0aada
JR
7383 if (a->type == OFPACT_NAT) {
7384 if (outer_action != OFPACT_CT) {
7385 VLOG_WARN("Cannot have NAT action outside of \"ct\" action");
7386 return OFPERR_OFPBAC_BAD_SET_ARGUMENT;
7387 }
7388 return 0;
7389 }
8e53fe8c
JS
7390
7391 if (outer_action) {
7392 ovs_assert(outer_action == OFPACT_WRITE_ACTIONS
7393 || outer_action == OFPACT_CT);
7394
7395 if (outer_action == OFPACT_CT) {
7396 if (!field) {
7397 return unsupported_nesting(a->type, outer_action);
7398 } else if (!field_requires_ct(field->id)) {
7399 VLOG_WARN("%s action doesn't support nested modification "
7400 "of %s", ofpact_name(outer_action), field->name);
7401 return OFPERR_OFPBAC_BAD_ARGUMENT;
7402 }
7403 }
d824b5b7
JS
7404 }
7405
7406 return 0;
7407}
7408
18080541
BP
7409/* Verifies that the 'ofpacts_len' bytes of actions in 'ofpacts' are in the
7410 * appropriate order as defined by the OpenFlow spec and as required by Open
7411 * vSwitch.
7412 *
7413 * 'allowed_ovsinsts' is a bitmap of OVSINST_* values, in which 1-bits indicate
d824b5b7
JS
7414 * instructions that are allowed within 'ofpacts[]'.
7415 *
7416 * If 'outer_action' is not zero, it specifies that the actions are nested
7417 * within another action of type 'outer_action'. */
c2d936a4
BP
7418static enum ofperr
7419ofpacts_verify(const struct ofpact ofpacts[], size_t ofpacts_len,
d824b5b7 7420 uint32_t allowed_ovsinsts, enum ofpact_type outer_action)
c2d936a4
BP
7421{
7422 const struct ofpact *a;
7423 enum ovs_instruction_type inst;
097d4939 7424
c2d936a4
BP
7425 inst = OVSINST_OFPIT13_METER;
7426 OFPACT_FOR_EACH (a, ofpacts, ofpacts_len) {
7427 enum ovs_instruction_type next;
8e53fe8c 7428 enum ofperr error;
1e7db674 7429
18080541
BP
7430 if (a->type == OFPACT_CONJUNCTION) {
7431 OFPACT_FOR_EACH (a, ofpacts, ofpacts_len) {
f08e39dd
BP
7432 if (a->type != OFPACT_CONJUNCTION && a->type != OFPACT_NOTE) {
7433 VLOG_WARN("\"conjunction\" actions may be used along with "
7434 "\"note\" but not any other kind of action "
7435 "(such as the \"%s\" action used here)",
96775a1c 7436 ofpact_name(a->type));
18080541
BP
7437 return OFPERR_NXBAC_BAD_CONJUNCTION;
7438 }
7439 }
7440 return 0;
7441 }
7442
8e53fe8c
JS
7443 error = ofpacts_verify_nested(a, outer_action);
7444 if (error) {
7445 return error;
d824b5b7
JS
7446 }
7447
c2d936a4
BP
7448 next = ovs_instruction_type_from_ofpact_type(a->type);
7449 if (a > ofpacts
7450 && (inst == OVSINST_OFPIT11_APPLY_ACTIONS
7451 ? next < inst
7452 : next <= inst)) {
7453 const char *name = ovs_instruction_name_from_type(inst);
7454 const char *next_name = ovs_instruction_name_from_type(next);
1e7db674 7455
c2d936a4
BP
7456 if (next == inst) {
7457 VLOG_WARN("duplicate %s instruction not allowed, for OpenFlow "
7458 "1.1+ compatibility", name);
7459 } else {
7460 VLOG_WARN("invalid instruction ordering: %s must appear "
7461 "before %s, for OpenFlow 1.1+ compatibility",
7462 next_name, name);
7463 }
7464 return OFPERR_OFPBAC_UNSUPPORTED_ORDER;
7465 }
7466 if (!((1u << next) & allowed_ovsinsts)) {
7467 const char *name = ovs_instruction_name_from_type(next);
1e7db674 7468
c2d936a4
BP
7469 VLOG_WARN("%s instruction not allowed here", name);
7470 return OFPERR_OFPBIC_UNSUP_INST;
1e7db674 7471 }
c2d936a4
BP
7472
7473 inst = next;
7474 }
7475
7476 return 0;
7477}
7478\f
7479/* Converting ofpacts to OpenFlow. */
7480
7481static void
7482encode_ofpact(const struct ofpact *a, enum ofp_version ofp_version,
7483 struct ofpbuf *out)
7484{
7485 switch (a->type) {
7486#define OFPACT(ENUM, STRUCT, MEMBER, NAME) \
7487 case OFPACT_##ENUM: \
355ead69
GS
7488 encode_##ENUM(ofpact_get_##ENUM(a), ofp_version, out); \
7489 return;
c2d936a4
BP
7490 OFPACTS
7491#undef OFPACT
7492 default:
7493 OVS_NOT_REACHED();
1e7db674 7494 }
e3f8f887
JR
7495}
7496
7497/* Converts the 'ofpacts_len' bytes of ofpacts in 'ofpacts' into OpenFlow
7498 * actions in 'openflow', appending the actions to any existing data in
d01c980f 7499 * 'openflow'. */
a07c15bc 7500size_t
e3f8f887
JR
7501ofpacts_put_openflow_actions(const struct ofpact ofpacts[], size_t ofpacts_len,
7502 struct ofpbuf *openflow,
7503 enum ofp_version ofp_version)
d01c980f
BP
7504{
7505 const struct ofpact *a;
6fd6ed71 7506 size_t start_size = openflow->size;
d01c980f
BP
7507
7508 OFPACT_FOR_EACH (a, ofpacts, ofpacts_len) {
c2d936a4 7509 encode_ofpact(a, ofp_version, openflow);
d01c980f 7510 }
6fd6ed71 7511 return openflow->size - start_size;
d01c980f
BP
7512}
7513
c2d936a4
BP
7514static enum ovs_instruction_type
7515ofpact_is_apply_actions(const struct ofpact *a)
d01c980f 7516{
c2d936a4
BP
7517 return (ovs_instruction_type_from_ofpact_type(a->type)
7518 == OVSINST_OFPIT11_APPLY_ACTIONS);
d01c980f 7519}
8dd54666
IY
7520
7521void
e3f8f887
JR
7522ofpacts_put_openflow_instructions(const struct ofpact ofpacts[],
7523 size_t ofpacts_len,
7524 struct ofpbuf *openflow,
7525 enum ofp_version ofp_version)
8dd54666 7526{
c2d936a4 7527 const struct ofpact *end = ofpact_end(ofpacts, ofpacts_len);
8dd54666
IY
7528 const struct ofpact *a;
7529
8f2cded4
BP
7530 if (ofp_version == OFP10_VERSION) {
7531 ofpacts_put_openflow_actions(ofpacts, ofpacts_len, openflow,
7532 ofp_version);
7533 return;
7534 }
e3f8f887 7535
c2d936a4
BP
7536 a = ofpacts;
7537 while (a < end) {
7538 if (ofpact_is_apply_actions(a)) {
6fd6ed71 7539 size_t ofs = openflow->size;
8dd54666
IY
7540
7541 instruction_put_OFPIT11_APPLY_ACTIONS(openflow);
c2d936a4
BP
7542 do {
7543 encode_ofpact(a, ofp_version, openflow);
7544 a = ofpact_next(a);
7545 } while (a < end && ofpact_is_apply_actions(a));
7fdb60a7 7546 ofpacts_update_instruction_actions(openflow, ofs);
c2d936a4
BP
7547 } else {
7548 encode_ofpact(a, ofp_version, openflow);
7549 a = ofpact_next(a);
8dd54666
IY
7550 }
7551 }
7552}
d01c980f 7553\f
08d1e234
BP
7554/* Sets of supported actions. */
7555
7556/* Two-way translation between OVS's internal "OFPACT_*" representation of
7557 * actions and the "OFPAT_*" representation used in some OpenFlow version.
7558 * (OFPAT_* numbering varies from one OpenFlow version to another, so a given
7559 * instance is specific to one OpenFlow version.) */
7560struct ofpact_map {
7561 enum ofpact_type ofpact; /* Internal name for action type. */
7562 int ofpat; /* OFPAT_* number from OpenFlow spec. */
7563};
7564
7565static const struct ofpact_map *
7566get_ofpact_map(enum ofp_version version)
7567{
7568 /* OpenFlow 1.0 actions. */
7569 static const struct ofpact_map of10[] = {
7570 { OFPACT_OUTPUT, 0 },
7571 { OFPACT_SET_VLAN_VID, 1 },
7572 { OFPACT_SET_VLAN_PCP, 2 },
7573 { OFPACT_STRIP_VLAN, 3 },
7574 { OFPACT_SET_ETH_SRC, 4 },
7575 { OFPACT_SET_ETH_DST, 5 },
7576 { OFPACT_SET_IPV4_SRC, 6 },
7577 { OFPACT_SET_IPV4_DST, 7 },
7578 { OFPACT_SET_IP_DSCP, 8 },
7579 { OFPACT_SET_L4_SRC_PORT, 9 },
7580 { OFPACT_SET_L4_DST_PORT, 10 },
7581 { OFPACT_ENQUEUE, 11 },
7582 { 0, -1 },
7583 };
7584
7585 /* OpenFlow 1.1 actions. */
7586 static const struct ofpact_map of11[] = {
7587 { OFPACT_OUTPUT, 0 },
7588 { OFPACT_SET_VLAN_VID, 1 },
7589 { OFPACT_SET_VLAN_PCP, 2 },
7590 { OFPACT_SET_ETH_SRC, 3 },
7591 { OFPACT_SET_ETH_DST, 4 },
7592 { OFPACT_SET_IPV4_SRC, 5 },
7593 { OFPACT_SET_IPV4_DST, 6 },
7594 { OFPACT_SET_IP_DSCP, 7 },
7595 { OFPACT_SET_IP_ECN, 8 },
7596 { OFPACT_SET_L4_SRC_PORT, 9 },
7597 { OFPACT_SET_L4_DST_PORT, 10 },
7598 /* OFPAT_COPY_TTL_OUT (11) not supported. */
7599 /* OFPAT_COPY_TTL_IN (12) not supported. */
7600 { OFPACT_SET_MPLS_LABEL, 13 },
7601 { OFPACT_SET_MPLS_TC, 14 },
7602 { OFPACT_SET_MPLS_TTL, 15 },
7603 { OFPACT_DEC_MPLS_TTL, 16 },
7604 { OFPACT_PUSH_VLAN, 17 },
7605 { OFPACT_STRIP_VLAN, 18 },
7606 { OFPACT_PUSH_MPLS, 19 },
7607 { OFPACT_POP_MPLS, 20 },
7608 { OFPACT_SET_QUEUE, 21 },
7609 { OFPACT_GROUP, 22 },
7610 { OFPACT_SET_IP_TTL, 23 },
7611 { OFPACT_DEC_TTL, 24 },
7612 { 0, -1 },
7613 };
7614
7615 /* OpenFlow 1.2, 1.3, and 1.4 actions. */
7616 static const struct ofpact_map of12[] = {
7617 { OFPACT_OUTPUT, 0 },
7618 /* OFPAT_COPY_TTL_OUT (11) not supported. */
7619 /* OFPAT_COPY_TTL_IN (12) not supported. */
7620 { OFPACT_SET_MPLS_TTL, 15 },
7621 { OFPACT_DEC_MPLS_TTL, 16 },
7622 { OFPACT_PUSH_VLAN, 17 },
7623 { OFPACT_STRIP_VLAN, 18 },
7624 { OFPACT_PUSH_MPLS, 19 },
7625 { OFPACT_POP_MPLS, 20 },
7626 { OFPACT_SET_QUEUE, 21 },
7627 { OFPACT_GROUP, 22 },
7628 { OFPACT_SET_IP_TTL, 23 },
7629 { OFPACT_DEC_TTL, 24 },
7630 { OFPACT_SET_FIELD, 25 },
7631 /* OF1.3+ OFPAT_PUSH_PBB (26) not supported. */
7632 /* OF1.3+ OFPAT_POP_PBB (27) not supported. */
7633 { 0, -1 },
7634 };
7635
7636 switch (version) {
7637 case OFP10_VERSION:
7638 return of10;
7639
7640 case OFP11_VERSION:
7641 return of11;
7642
7643 case OFP12_VERSION:
7644 case OFP13_VERSION:
7645 case OFP14_VERSION:
7646 case OFP15_VERSION:
b79d45a1 7647 case OFP16_VERSION:
08d1e234
BP
7648 default:
7649 return of12;
7650 }
7651}
7652
7653/* Converts 'ofpacts_bitmap', a bitmap whose bits correspond to OFPACT_*
7654 * values, into a bitmap of actions suitable for OpenFlow 'version', and
7655 * returns the result. */
7656ovs_be32
7657ofpact_bitmap_to_openflow(uint64_t ofpacts_bitmap, enum ofp_version version)
7658{
7659 uint32_t openflow_bitmap = 0;
7660 const struct ofpact_map *x;
7661
7662 for (x = get_ofpact_map(version); x->ofpat >= 0; x++) {
7663 if (ofpacts_bitmap & (UINT64_C(1) << x->ofpact)) {
7664 openflow_bitmap |= 1u << x->ofpat;
7665 }
7666 }
7667 return htonl(openflow_bitmap);
7668}
7669
7670/* Converts 'ofpat_bitmap', a bitmap of actions from an OpenFlow message with
7671 * the given 'version' into a bitmap whose bits correspond to OFPACT_* values,
7672 * and returns the result. */
7673uint64_t
7674ofpact_bitmap_from_openflow(ovs_be32 ofpat_bitmap, enum ofp_version version)
7675{
7676 uint64_t ofpact_bitmap = 0;
7677 const struct ofpact_map *x;
7678
7679 for (x = get_ofpact_map(version); x->ofpat >= 0; x++) {
7680 if (ofpat_bitmap & htonl(1u << x->ofpat)) {
7681 ofpact_bitmap |= UINT64_C(1) << x->ofpact;
7682 }
7683 }
7684 return ofpact_bitmap;
7685}
7686
7687/* Appends to 's' a string representation of the set of OFPACT_* represented
7688 * by 'ofpacts_bitmap'. */
7689void
7690ofpact_bitmap_format(uint64_t ofpacts_bitmap, struct ds *s)
7691{
7692 if (!ofpacts_bitmap) {
7693 ds_put_cstr(s, "<none>");
7694 } else {
7695 while (ofpacts_bitmap) {
7696 ds_put_format(s, "%s ",
7697 ofpact_name(rightmost_1bit_idx(ofpacts_bitmap)));
7698 ofpacts_bitmap = zero_rightmost_1bit(ofpacts_bitmap);
7699 }
7700 ds_chomp(s, ' ');
7701 }
7702}
7703\f
f25d0cf3
BP
7704/* Returns true if 'action' outputs to 'port', false otherwise. */
7705static bool
4e022ec0 7706ofpact_outputs_to_port(const struct ofpact *ofpact, ofp_port_t port)
f25d0cf3
BP
7707{
7708 switch (ofpact->type) {
7709 case OFPACT_OUTPUT:
7710 return ofpact_get_OUTPUT(ofpact)->port == port;
7711 case OFPACT_ENQUEUE:
7712 return ofpact_get_ENQUEUE(ofpact)->port == port;
7713 case OFPACT_CONTROLLER:
7714 return port == OFPP_CONTROLLER;
7715
7716 case OFPACT_OUTPUT_REG:
aaca4fe0 7717 case OFPACT_OUTPUT_TRUNC:
f25d0cf3
BP
7718 case OFPACT_BUNDLE:
7719 case OFPACT_SET_VLAN_VID:
7720 case OFPACT_SET_VLAN_PCP:
7721 case OFPACT_STRIP_VLAN:
3e34fbdd 7722 case OFPACT_PUSH_VLAN:
f25d0cf3
BP
7723 case OFPACT_SET_ETH_SRC:
7724 case OFPACT_SET_ETH_DST:
7725 case OFPACT_SET_IPV4_SRC:
7726 case OFPACT_SET_IPV4_DST:
04f01c24 7727 case OFPACT_SET_IP_DSCP:
ff14eb7a 7728 case OFPACT_SET_IP_ECN:
0c20dbe4 7729 case OFPACT_SET_IP_TTL:
f25d0cf3
BP
7730 case OFPACT_SET_L4_SRC_PORT:
7731 case OFPACT_SET_L4_DST_PORT:
7732 case OFPACT_REG_MOVE:
b2dd70be 7733 case OFPACT_SET_FIELD:
bd85dac1
AZ
7734 case OFPACT_STACK_PUSH:
7735 case OFPACT_STACK_POP:
f25d0cf3 7736 case OFPACT_DEC_TTL:
097d4939
JR
7737 case OFPACT_SET_MPLS_LABEL:
7738 case OFPACT_SET_MPLS_TC:
0f3f3c3d 7739 case OFPACT_SET_MPLS_TTL:
b676167a 7740 case OFPACT_DEC_MPLS_TTL:
f25d0cf3 7741 case OFPACT_SET_TUNNEL:
4cceacb9 7742 case OFPACT_WRITE_METADATA:
f25d0cf3
BP
7743 case OFPACT_SET_QUEUE:
7744 case OFPACT_POP_QUEUE:
7745 case OFPACT_FIN_TIMEOUT:
7746 case OFPACT_RESUBMIT:
7747 case OFPACT_LEARN:
18080541 7748 case OFPACT_CONJUNCTION:
f25d0cf3 7749 case OFPACT_MULTIPATH:
f25d0cf3
BP
7750 case OFPACT_NOTE:
7751 case OFPACT_EXIT:
e672ff9b 7752 case OFPACT_UNROLL_XLATE:
b02475c5
SH
7753 case OFPACT_PUSH_MPLS:
7754 case OFPACT_POP_MPLS:
29089a54 7755 case OFPACT_SAMPLE:
b19e8793 7756 case OFPACT_CLEAR_ACTIONS:
7ae62a67 7757 case OFPACT_CLONE:
7fdb60a7 7758 case OFPACT_WRITE_ACTIONS:
8dd54666 7759 case OFPACT_GOTO_TABLE:
638a19b0 7760 case OFPACT_METER:
7395c052 7761 case OFPACT_GROUP:
d4abaff5 7762 case OFPACT_DEBUG_RECIRC:
07659514 7763 case OFPACT_CT:
72fe7578 7764 case OFPACT_CT_CLEAR:
9ac0aada 7765 case OFPACT_NAT:
f25d0cf3
BP
7766 default:
7767 return false;
7768 }
7769}
7770
7771/* Returns true if any action in the 'ofpacts_len' bytes of 'ofpacts' outputs
7772 * to 'port', false otherwise. */
7773bool
7774ofpacts_output_to_port(const struct ofpact *ofpacts, size_t ofpacts_len,
4e022ec0 7775 ofp_port_t port)
c2d936a4
BP
7776{
7777 const struct ofpact *a;
f25d0cf3 7778
4f20179d 7779 OFPACT_FOR_EACH_FLATTENED (a, ofpacts, ofpacts_len) {
c2d936a4
BP
7780 if (ofpact_outputs_to_port(a, port)) {
7781 return true;
7782 }
7783 }
f25d0cf3 7784
c2d936a4
BP
7785 return false;
7786}
f25d0cf3 7787
c2d936a4
BP
7788/* Returns true if any action in the 'ofpacts_len' bytes of 'ofpacts' outputs
7789 * to 'group', false otherwise. */
7790bool
7791ofpacts_output_to_group(const struct ofpact *ofpacts, size_t ofpacts_len,
7792 uint32_t group_id)
7793{
7794 const struct ofpact *a;
b02475c5 7795
4f20179d 7796 OFPACT_FOR_EACH_FLATTENED (a, ofpacts, ofpacts_len) {
c2d936a4
BP
7797 if (a->type == OFPACT_GROUP
7798 && ofpact_get_GROUP(a)->group_id == group_id) {
7799 return true;
7800 }
7801 }
b02475c5 7802
c2d936a4
BP
7803 return false;
7804}
8dd54666 7805
c2d936a4
BP
7806bool
7807ofpacts_equal(const struct ofpact *a, size_t a_len,
7808 const struct ofpact *b, size_t b_len)
7809{
7810 return a_len == b_len && !memcmp(a, b, a_len);
7811}
29089a54 7812
c2d936a4
BP
7813/* Finds the OFPACT_METER action, if any, in the 'ofpacts_len' bytes of
7814 * 'ofpacts'. If found, returns its meter ID; if not, returns 0.
7815 *
7816 * This function relies on the order of 'ofpacts' being correct (as checked by
7817 * ofpacts_verify()). */
7818uint32_t
7819ofpacts_get_meter(const struct ofpact ofpacts[], size_t ofpacts_len)
7820{
7821 const struct ofpact *a;
7fdb60a7 7822
c2d936a4
BP
7823 OFPACT_FOR_EACH (a, ofpacts, ofpacts_len) {
7824 enum ovs_instruction_type inst;
b19e8793 7825
c2d936a4
BP
7826 inst = ovs_instruction_type_from_ofpact_type(a->type);
7827 if (a->type == OFPACT_METER) {
7828 return ofpact_get_METER(a)->meter_id;
7829 } else if (inst > OVSINST_OFPIT13_METER) {
7830 break;
4cceacb9 7831 }
c2d936a4 7832 }
638a19b0 7833
c2d936a4
BP
7834 return 0;
7835}
7836\f
7837/* Formatting ofpacts. */
7395c052 7838
c2d936a4
BP
7839static void
7840ofpact_format(const struct ofpact *a, struct ds *s)
7841{
7842 switch (a->type) {
7843#define OFPACT(ENUM, STRUCT, MEMBER, NAME) \
7844 case OFPACT_##ENUM: \
7845 format_##ENUM(ALIGNED_CAST(const struct STRUCT *, a), s); \
7846 break;
7847 OFPACTS
7848#undef OFPACT
7849 default:
7850 OVS_NOT_REACHED();
f25d0cf3
BP
7851 }
7852}
7853
7854/* Appends a string representing the 'ofpacts_len' bytes of ofpacts in
7855 * 'ofpacts' to 'string'. */
7856void
7857ofpacts_format(const struct ofpact *ofpacts, size_t ofpacts_len,
7858 struct ds *string)
7859{
f25d0cf3 7860 if (!ofpacts_len) {
b1c5bf1f 7861 ds_put_format(string, "%sdrop%s", colors.drop, colors.end);
f25d0cf3
BP
7862 } else {
7863 const struct ofpact *a;
7864
7865 OFPACT_FOR_EACH (a, ofpacts, ofpacts_len) {
7866 if (a != ofpacts) {
b1c5bf1f 7867 ds_put_char(string, ',');
f25d0cf3 7868 }
8dd54666 7869
f25d0cf3
BP
7870 ofpact_format(a, string);
7871 }
7872 }
7873}
7874\f
7875/* Internal use by helpers. */
7876
ce058104 7877/* Implementation of ofpact_put_<ENUM>(). */
f25d0cf3
BP
7878void *
7879ofpact_put(struct ofpbuf *ofpacts, enum ofpact_type type, size_t len)
7880{
7881 struct ofpact *ofpact;
7882
6fd6ed71
PS
7883 ofpacts->header = ofpbuf_put_uninit(ofpacts, len);
7884 ofpact = ofpacts->header;
f25d0cf3
BP
7885 ofpact_init(ofpact, type, len);
7886 return ofpact;
7887}
7888
ce058104 7889/* Implementation of ofpact_init_<ENUM>(). */
f25d0cf3
BP
7890void
7891ofpact_init(struct ofpact *ofpact, enum ofpact_type type, size_t len)
7892{
7893 memset(ofpact, 0, len);
7894 ofpact->type = type;
c2d936a4 7895 ofpact->raw = -1;
f25d0cf3
BP
7896 ofpact->len = len;
7897}
ce058104
BP
7898
7899/* Implementation of ofpact_finish_<ENUM>().
7900 *
7901 * Finishes composing a variable-length action (begun using
2bd318de
BP
7902 * ofpact_put_<NAME>()), by padding the action to a multiple of OFPACT_ALIGNTO
7903 * bytes and updating its embedded length field. See the large comment near
ebe12cd3
JS
7904 * the end of ofp-actions.h for more information.
7905 *
7906 * May reallocate 'ofpacts'. Callers should consider updating their 'ofpact'
7907 * pointer to the return value of this function. */
7908void *
34abaa3d 7909ofpact_finish(struct ofpbuf *ofpacts, struct ofpact *ofpact)
f25d0cf3 7910{
5308056f
JS
7911 ptrdiff_t len;
7912
6fd6ed71 7913 ovs_assert(ofpact == ofpacts->header);
5308056f 7914 len = (char *) ofpbuf_tail(ofpacts) - (char *) ofpact;
847b5649 7915 ovs_assert(len > 0 && len <= UINT16_MAX);
5308056f 7916 ofpact->len = len;
2bd318de 7917 ofpbuf_padto(ofpacts, OFPACT_ALIGN(ofpacts->size));
ebe12cd3
JS
7918
7919 return ofpacts->header;
f25d0cf3 7920}
c2d936a4 7921\f
cab50449 7922static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
7923ofpact_parse(enum ofpact_type type, char *value, struct ofpbuf *ofpacts,
7924 enum ofputil_protocol *usable_protocols)
7925{
7926 switch (type) {
7927#define OFPACT(ENUM, STRUCT, MEMBER, NAME) \
7928 case OFPACT_##ENUM: \
7929 return parse_##ENUM(value, ofpacts, usable_protocols);
7930 OFPACTS
7931#undef OFPACT
7932 default:
7933 OVS_NOT_REACHED();
7934 }
7935}
7936
7937static bool
7938ofpact_type_from_name(const char *name, enum ofpact_type *type)
7939{
7940#define OFPACT(ENUM, STRUCT, MEMBER, NAME) \
7941 if (!strcasecmp(name, NAME)) { \
7942 *type = OFPACT_##ENUM; \
7943 return true; \
7944 }
7945 OFPACTS
7946#undef OFPACT
7947
7948 return false;
7949}
7950
7951/* Parses 'str' as a series of instructions, and appends them to 'ofpacts'.
7952 *
7953 * Returns NULL if successful, otherwise a malloc()'d string describing the
d824b5b7
JS
7954 * error. The caller is responsible for freeing the returned string.
7955 *
7956 * If 'outer_action' is specified, indicates that the actions being parsed
7957 * are nested within another action of the type specified in 'outer_action'. */
cab50449 7958static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
7959ofpacts_parse__(char *str, struct ofpbuf *ofpacts,
7960 enum ofputil_protocol *usable_protocols,
d824b5b7 7961 bool allow_instructions, enum ofpact_type outer_action)
c2d936a4
BP
7962{
7963 int prev_inst = -1;
7964 enum ofperr retval;
7965 char *key, *value;
7966 bool drop = false;
7967 char *pos;
7968
7969 pos = str;
7970 while (ofputil_parse_key_value(&pos, &key, &value)) {
7971 enum ovs_instruction_type inst = OVSINST_OFPIT11_APPLY_ACTIONS;
7972 enum ofpact_type type;
7973 char *error = NULL;
7974 ofp_port_t port;
7975
7976 if (ofpact_type_from_name(key, &type)) {
7977 error = ofpact_parse(type, value, ofpacts, usable_protocols);
7978 inst = ovs_instruction_type_from_ofpact_type(type);
7979 } else if (!strcasecmp(key, "mod_vlan_vid")) {
7980 error = parse_set_vlan_vid(value, ofpacts, true);
7981 } else if (!strcasecmp(key, "mod_vlan_pcp")) {
7982 error = parse_set_vlan_pcp(value, ofpacts, true);
7983 } else if (!strcasecmp(key, "set_nw_ttl")) {
7984 error = parse_SET_IP_TTL(value, ofpacts, usable_protocols);
7985 } else if (!strcasecmp(key, "pop_vlan")) {
7986 error = parse_pop_vlan(ofpacts);
7987 } else if (!strcasecmp(key, "set_tunnel64")) {
7988 error = parse_set_tunnel(value, ofpacts,
7989 NXAST_RAW_SET_TUNNEL64);
7eb4b1f1
BP
7990 } else if (!strcasecmp(key, "load")) {
7991 error = parse_reg_load(value, ofpacts);
c2d936a4
BP
7992 } else if (!strcasecmp(key, "bundle_load")) {
7993 error = parse_bundle_load(value, ofpacts);
7994 } else if (!strcasecmp(key, "drop")) {
7995 drop = true;
7996 } else if (!strcasecmp(key, "apply_actions")) {
7997 return xstrdup("apply_actions is the default instruction");
7998 } else if (ofputil_port_from_string(key, &port)) {
7999 ofpact_put_OUTPUT(ofpacts)->port = port;
8000 } else {
8001 return xasprintf("unknown action %s", key);
8002 }
8003 if (error) {
8004 return error;
8005 }
8006
8007 if (inst != OVSINST_OFPIT11_APPLY_ACTIONS) {
8008 if (!allow_instructions) {
8009 return xasprintf("only actions are allowed here (not "
8010 "instruction %s)",
8011 ovs_instruction_name_from_type(inst));
8012 }
8013 if (inst == prev_inst) {
8014 return xasprintf("instruction %s may be specified only once",
8015 ovs_instruction_name_from_type(inst));
8016 }
8017 }
8018 if (prev_inst != -1 && inst < prev_inst) {
8019 return xasprintf("instruction %s must be specified before %s",
8020 ovs_instruction_name_from_type(inst),
8021 ovs_instruction_name_from_type(prev_inst));
8022 }
8023 prev_inst = inst;
8024 }
c2d936a4 8025
6fd6ed71 8026 if (drop && ofpacts->size) {
c2d936a4
BP
8027 return xstrdup("\"drop\" must not be accompanied by any other action "
8028 "or instruction");
8029 }
8030
6fd6ed71 8031 retval = ofpacts_verify(ofpacts->data, ofpacts->size,
c2d936a4
BP
8032 (allow_instructions
8033 ? (1u << N_OVS_INSTRUCTIONS) - 1
d824b5b7
JS
8034 : 1u << OVSINST_OFPIT11_APPLY_ACTIONS),
8035 outer_action);
c2d936a4
BP
8036 if (retval) {
8037 return xstrdup("Incorrect instruction ordering");
8038 }
8039
8040 return NULL;
8041}
8042
cab50449 8043static char * OVS_WARN_UNUSED_RESULT
c2d936a4 8044ofpacts_parse(char *str, struct ofpbuf *ofpacts,
d824b5b7
JS
8045 enum ofputil_protocol *usable_protocols, bool allow_instructions,
8046 enum ofpact_type outer_action)
c2d936a4 8047{
6fd6ed71 8048 uint32_t orig_size = ofpacts->size;
c2d936a4 8049 char *error = ofpacts_parse__(str, ofpacts, usable_protocols,
d824b5b7 8050 allow_instructions, outer_action);
c2d936a4 8051 if (error) {
6fd6ed71 8052 ofpacts->size = orig_size;
c2d936a4
BP
8053 }
8054 return error;
8055}
8056
cab50449 8057static char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
8058ofpacts_parse_copy(const char *s_, struct ofpbuf *ofpacts,
8059 enum ofputil_protocol *usable_protocols,
d824b5b7 8060 bool allow_instructions, enum ofpact_type outer_action)
c2d936a4
BP
8061{
8062 char *error, *s;
8063
8064 *usable_protocols = OFPUTIL_P_ANY;
8065
8066 s = xstrdup(s_);
d824b5b7
JS
8067 error = ofpacts_parse(s, ofpacts, usable_protocols, allow_instructions,
8068 outer_action);
c2d936a4
BP
8069 free(s);
8070
8071 return error;
8072}
8073
8074/* Parses 's' as a set of OpenFlow actions and appends the actions to
d824b5b7
JS
8075 * 'ofpacts'. 'outer_action', if nonzero, specifies that 's' contains actions
8076 * that are nested within the action of type 'outer_action'.
c2d936a4
BP
8077 *
8078 * Returns NULL if successful, otherwise a malloc()'d string describing the
8079 * error. The caller is responsible for freeing the returned string. */
cab50449 8080char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
8081ofpacts_parse_actions(const char *s, struct ofpbuf *ofpacts,
8082 enum ofputil_protocol *usable_protocols)
8083{
d824b5b7 8084 return ofpacts_parse_copy(s, ofpacts, usable_protocols, false, 0);
c2d936a4
BP
8085}
8086
8087/* Parses 's' as a set of OpenFlow instructions and appends the instructions to
8088 * 'ofpacts'.
8089 *
8090 * Returns NULL if successful, otherwise a malloc()'d string describing the
8091 * error. The caller is responsible for freeing the returned string. */
cab50449 8092char * OVS_WARN_UNUSED_RESULT
c2d936a4
BP
8093ofpacts_parse_instructions(const char *s, struct ofpbuf *ofpacts,
8094 enum ofputil_protocol *usable_protocols)
8095{
d824b5b7 8096 return ofpacts_parse_copy(s, ofpacts, usable_protocols, true, 0);
c2d936a4 8097}
08d1e234
BP
8098
8099const char *
8100ofpact_name(enum ofpact_type type)
8101{
8102 switch (type) {
8103#define OFPACT(ENUM, STRUCT, MEMBER, NAME) case OFPACT_##ENUM: return NAME;
8104 OFPACTS
8105#undef OFPACT
8106 }
8107 return "<unknown>";
8108}
c2d936a4
BP
8109\f
8110/* Low-level action decoding and encoding functions. */
8111
8112/* Everything needed to identify a particular OpenFlow action. */
8113struct ofpact_hdrs {
8114 uint32_t vendor; /* 0 if standard, otherwise a vendor code. */
8115 uint16_t type; /* Type if standard, otherwise subtype. */
8116 uint8_t ofp_version; /* From ofp_header. */
8117};
8118
8119/* Information about a particular OpenFlow action. */
8120struct ofpact_raw_instance {
8121 /* The action's identity. */
8122 struct ofpact_hdrs hdrs;
8123 enum ofp_raw_action_type raw;
8124
8125 /* Looking up the action. */
8126 struct hmap_node decode_node; /* Based on 'hdrs'. */
8127 struct hmap_node encode_node; /* Based on 'raw' + 'hdrs.ofp_version'. */
8128
8129 /* The action's encoded size.
8130 *
8131 * If this action is fixed-length, 'min_length' == 'max_length'.
8132 * If it is variable length, then 'max_length' is ROUND_DOWN(UINT16_MAX,
8133 * OFP_ACTION_ALIGN) == 65528. */
8134 unsigned short int min_length;
8135 unsigned short int max_length;
8136
8137 /* For actions with a simple integer numeric argument, 'arg_ofs' is the
8138 * offset of that argument from the beginning of the action and 'arg_len'
8139 * its length, both in bytes.
8140 *
8141 * For actions that take other forms, these are both zero. */
8142 unsigned short int arg_ofs;
8143 unsigned short int arg_len;
8144
8145 /* The name of the action, e.g. "OFPAT_OUTPUT" or "NXAST_RESUBMIT". */
8146 const char *name;
8147
8148 /* If this action is deprecated, a human-readable string with a brief
8149 * explanation. */
8150 const char *deprecation;
8151};
8152
8153/* Action header. */
8154struct ofp_action_header {
8155 /* The meaning of other values of 'type' generally depends on the OpenFlow
8156 * version (see enum ofp_raw_action_type).
8157 *
8158 * Across all OpenFlow versions, OFPAT_VENDOR indicates that 'vendor'
8159 * designates an OpenFlow vendor ID and that the remainder of the action
8160 * structure has a vendor-defined meaning.
8161 */
8162#define OFPAT_VENDOR 0xffff
8163 ovs_be16 type;
8164
8165 /* Always a multiple of 8. */
8166 ovs_be16 len;
8167
8168 /* For type == OFPAT_VENDOR only, this is a vendor ID, e.g. NX_VENDOR_ID or
8169 * ONF_VENDOR_ID. Other 'type's use this space for some other purpose. */
8170 ovs_be32 vendor;
8171};
8172OFP_ASSERT(sizeof(struct ofp_action_header) == 8);
8173
c2d936a4
BP
8174static bool
8175ofpact_hdrs_equal(const struct ofpact_hdrs *a,
8176 const struct ofpact_hdrs *b)
8177{
8178 return (a->vendor == b->vendor
8179 && a->type == b->type
8180 && a->ofp_version == b->ofp_version);
8181}
8182
8183static uint32_t
8184ofpact_hdrs_hash(const struct ofpact_hdrs *hdrs)
8185{
8186 return hash_2words(hdrs->vendor, (hdrs->type << 16) | hdrs->ofp_version);
8187}
8188
8189#include "ofp-actions.inc2"
8190
8191static struct hmap *
8192ofpact_decode_hmap(void)
8193{
8194 static struct ovsthread_once once = OVSTHREAD_ONCE_INITIALIZER;
8195 static struct hmap hmap;
8196
8197 if (ovsthread_once_start(&once)) {
8198 struct ofpact_raw_instance *inst;
8199
8200 hmap_init(&hmap);
8201 for (inst = all_raw_instances;
8202 inst < &all_raw_instances[ARRAY_SIZE(all_raw_instances)];
8203 inst++) {
8204 hmap_insert(&hmap, &inst->decode_node,
8205 ofpact_hdrs_hash(&inst->hdrs));
8206 }
8207 ovsthread_once_done(&once);
8208 }
8209 return &hmap;
8210}
8211
8212static struct hmap *
8213ofpact_encode_hmap(void)
8214{
8215 static struct ovsthread_once once = OVSTHREAD_ONCE_INITIALIZER;
8216 static struct hmap hmap;
8217
8218 if (ovsthread_once_start(&once)) {
8219 struct ofpact_raw_instance *inst;
8220
8221 hmap_init(&hmap);
8222 for (inst = all_raw_instances;
8223 inst < &all_raw_instances[ARRAY_SIZE(all_raw_instances)];
8224 inst++) {
8225 hmap_insert(&hmap, &inst->encode_node,
8226 hash_2words(inst->raw, inst->hdrs.ofp_version));
8227 }
8228 ovsthread_once_done(&once);
8229 }
8230 return &hmap;
8231}
8232
8233static enum ofperr
8234ofpact_decode_raw(enum ofp_version ofp_version,
8235 const struct ofp_action_header *oah, size_t length,
8236 const struct ofpact_raw_instance **instp)
8237{
8238 const struct ofpact_raw_instance *inst;
8239 struct ofpact_hdrs hdrs;
8240
8241 *instp = NULL;
8242 if (length < sizeof *oah) {
8243 return OFPERR_OFPBAC_BAD_LEN;
8244 }
8245
8246 /* Get base action type. */
8247 if (oah->type == htons(OFPAT_VENDOR)) {
8248 /* Get vendor. */
8249 hdrs.vendor = ntohl(oah->vendor);
232c1e12
BP
8250 if (hdrs.vendor == NX_VENDOR_ID || hdrs.vendor == ONF_VENDOR_ID) {
8251 /* Get extension subtype. */
8252 const struct ext_action_header *nah;
c2d936a4 8253
232c1e12 8254 nah = ALIGNED_CAST(const struct ext_action_header *, oah);
c2d936a4
BP
8255 if (length < sizeof *nah) {
8256 return OFPERR_OFPBAC_BAD_LEN;
8257 }
8258 hdrs.type = ntohs(nah->subtype);
8259 } else {
8260 VLOG_WARN_RL(&rl, "OpenFlow action has unknown vendor %#"PRIx32,
8261 hdrs.vendor);
8262 return OFPERR_OFPBAC_BAD_VENDOR;
8263 }
8264 } else {
8265 hdrs.vendor = 0;
8266 hdrs.type = ntohs(oah->type);
8267 }
8268
8269 hdrs.ofp_version = ofp_version;
8270 HMAP_FOR_EACH_WITH_HASH (inst, decode_node, ofpact_hdrs_hash(&hdrs),
8271 ofpact_decode_hmap()) {
8272 if (ofpact_hdrs_equal(&hdrs, &inst->hdrs)) {
8273 *instp = inst;
8274 return 0;
8275 }
8276 }
8277
8278 return (hdrs.vendor
8279 ? OFPERR_OFPBAC_BAD_VENDOR_TYPE
8280 : OFPERR_OFPBAC_BAD_TYPE);
8281}
8282
8283static enum ofperr
8284ofpact_pull_raw(struct ofpbuf *buf, enum ofp_version ofp_version,
8285 enum ofp_raw_action_type *raw, uint64_t *arg)
8286{
6fd6ed71 8287 const struct ofp_action_header *oah = buf->data;
c2d936a4
BP
8288 const struct ofpact_raw_instance *action;
8289 unsigned int length;
8290 enum ofperr error;
8291
8292 *raw = *arg = 0;
6fd6ed71 8293 error = ofpact_decode_raw(ofp_version, oah, buf->size, &action);
c2d936a4
BP
8294 if (error) {
8295 return error;
8296 }
8297
8298 if (action->deprecation) {
8299 VLOG_INFO_RL(&rl, "%s is deprecated in %s (%s)",
8300 action->name, ofputil_version_to_string(ofp_version),
8301 action->deprecation);
8302 }
8303
8304 length = ntohs(oah->len);
6fd6ed71 8305 if (length > buf->size) {
b153b990 8306 VLOG_WARN_RL(&rl, "OpenFlow action %s length %u exceeds action buffer "
6fd6ed71 8307 "length %"PRIu32, action->name, length, buf->size);
b153b990
BP
8308 return OFPERR_OFPBAC_BAD_LEN;
8309 }
c2d936a4
BP
8310 if (length < action->min_length || length > action->max_length) {
8311 VLOG_WARN_RL(&rl, "OpenFlow action %s length %u not in valid range "
8312 "[%hu,%hu]", action->name, length,
8313 action->min_length, action->max_length);
8314 return OFPERR_OFPBAC_BAD_LEN;
8315 }
8316 if (length % 8) {
8317 VLOG_WARN_RL(&rl, "OpenFlow action %s length %u is not a multiple "
8318 "of 8", action->name, length);
8319 return OFPERR_OFPBAC_BAD_LEN;
8320 }
8321
8322 *raw = action->raw;
8323 *arg = 0;
8324 if (action->arg_len) {
8325 const uint8_t *p;
8326 int i;
8327
8328 p = ofpbuf_at_assert(buf, action->arg_ofs, action->arg_len);
8329 for (i = 0; i < action->arg_len; i++) {
8330 *arg = (*arg << 8) | p[i];
8331 }
8332 }
8333
8334 ofpbuf_pull(buf, length);
8335
8336 return 0;
8337}
8338
8339static const struct ofpact_raw_instance *
8340ofpact_raw_lookup(enum ofp_version ofp_version, enum ofp_raw_action_type raw)
8341{
8342 const struct ofpact_raw_instance *inst;
8343
8344 HMAP_FOR_EACH_WITH_HASH (inst, encode_node, hash_2words(raw, ofp_version),
8345 ofpact_encode_hmap()) {
8346 if (inst->raw == raw && inst->hdrs.ofp_version == ofp_version) {
8347 return inst;
8348 }
8349 }
8350 OVS_NOT_REACHED();
8351}
8352
8353static void *
8354ofpact_put_raw(struct ofpbuf *buf, enum ofp_version ofp_version,
8355 enum ofp_raw_action_type raw, uint64_t arg)
8356{
8357 const struct ofpact_raw_instance *inst;
8358 struct ofp_action_header *oah;
8359 const struct ofpact_hdrs *hdrs;
8360
8361 inst = ofpact_raw_lookup(ofp_version, raw);
8362 hdrs = &inst->hdrs;
8363
8364 oah = ofpbuf_put_zeros(buf, inst->min_length);
8365 oah->type = htons(hdrs->vendor ? OFPAT_VENDOR : hdrs->type);
8366 oah->len = htons(inst->min_length);
8367 oah->vendor = htonl(hdrs->vendor);
8368
8369 switch (hdrs->vendor) {
8370 case 0:
8371 break;
8372
232c1e12
BP
8373 case NX_VENDOR_ID:
8374 case ONF_VENDOR_ID: {
8375 struct ext_action_header *nah = (struct ext_action_header *) oah;
c2d936a4
BP
8376 nah->subtype = htons(hdrs->type);
8377 break;
8378 }
8379
8380 default:
8381 OVS_NOT_REACHED();
8382 }
8383
8384 if (inst->arg_len) {
8385 uint8_t *p = (uint8_t *) oah + inst->arg_ofs + inst->arg_len;
8386 int i;
8387
8388 for (i = 0; i < inst->arg_len; i++) {
8389 *--p = arg;
8390 arg >>= 8;
8391 }
8392 } else {
8393 ovs_assert(!arg);
8394 }
8395
8396 return oah;
8397}
178742f9
BP
8398
8399static void
8400pad_ofpat(struct ofpbuf *openflow, size_t start_ofs)
8401{
8402 struct ofp_action_header *oah;
8403
9ac0aada
JR
8404 ofpbuf_put_zeros(openflow, PAD_SIZE(openflow->size - start_ofs,
8405 OFP_ACTION_ALIGN));
178742f9
BP
8406
8407 oah = ofpbuf_at_assert(openflow, start_ofs, sizeof *oah);
6fd6ed71 8408 oah->len = htons(openflow->size - start_ofs);
178742f9
BP
8409}
8410