+static void
+parse_named_action(enum ofputil_action_code code, const struct flow *flow,
+ char *arg, struct ofpbuf *ofpacts)
+{
+ struct ofpact_tunnel *tunnel;
+ uint16_t vid;
+ uint16_t ethertype;
+ ovs_be32 ip;
+ uint8_t pcp;
+ uint8_t tos;
+
+ switch (code) {
+ case OFPUTIL_ACTION_INVALID:
+ NOT_REACHED();
+
+ case OFPUTIL_OFPAT10_OUTPUT:
+ case OFPUTIL_OFPAT11_OUTPUT:
+ parse_output(arg, ofpacts);
+ break;
+
+ case OFPUTIL_OFPAT10_SET_VLAN_VID:
+ case OFPUTIL_OFPAT11_SET_VLAN_VID:
+ vid = str_to_u32(arg);
+ if (vid & ~VLAN_VID_MASK) {
+ ovs_fatal(0, "%s: not a valid VLAN VID", arg);
+ }
+ ofpact_put_SET_VLAN_VID(ofpacts)->vlan_vid = vid;
+ break;
+
+ case OFPUTIL_OFPAT10_SET_VLAN_PCP:
+ case OFPUTIL_OFPAT11_SET_VLAN_PCP:
+ pcp = str_to_u32(arg);
+ if (pcp & ~7) {
+ ovs_fatal(0, "%s: not a valid VLAN PCP", arg);
+ }
+ ofpact_put_SET_VLAN_PCP(ofpacts)->vlan_pcp = pcp;
+ break;
+
+ case OFPUTIL_OFPAT12_SET_FIELD:
+ set_field_parse(arg, ofpacts);
+ break;
+
+ case OFPUTIL_OFPAT10_STRIP_VLAN:
+ case OFPUTIL_OFPAT11_POP_VLAN:
+ ofpact_put_STRIP_VLAN(ofpacts);
+ break;
+
+ case OFPUTIL_OFPAT11_PUSH_VLAN:
+ ethertype = str_to_u16(arg, "ethertype");
+ if (ethertype != ETH_TYPE_VLAN_8021Q) {
+ /* TODO:XXXX ETH_TYPE_VLAN_8021AD case isn't supported */
+ ovs_fatal(0, "%s: not a valid VLAN ethertype", arg);
+ }
+ ofpact_put_PUSH_VLAN(ofpacts);
+ break;
+
+ case OFPUTIL_OFPAT10_SET_DL_SRC:
+ case OFPUTIL_OFPAT11_SET_DL_SRC:
+ str_to_mac(arg, ofpact_put_SET_ETH_SRC(ofpacts)->mac);
+ break;
+
+ case OFPUTIL_OFPAT10_SET_DL_DST:
+ case OFPUTIL_OFPAT11_SET_DL_DST:
+ str_to_mac(arg, ofpact_put_SET_ETH_DST(ofpacts)->mac);
+ break;
+
+ case OFPUTIL_OFPAT10_SET_NW_SRC:
+ case OFPUTIL_OFPAT11_SET_NW_SRC:
+ str_to_ip(arg, &ip);
+ ofpact_put_SET_IPV4_SRC(ofpacts)->ipv4 = ip;
+ break;
+
+ case OFPUTIL_OFPAT10_SET_NW_DST:
+ case OFPUTIL_OFPAT11_SET_NW_DST:
+ str_to_ip(arg, &ip);
+ ofpact_put_SET_IPV4_DST(ofpacts)->ipv4 = ip;
+ break;
+
+ case OFPUTIL_OFPAT10_SET_NW_TOS:
+ case OFPUTIL_OFPAT11_SET_NW_TOS:
+ tos = str_to_u32(arg);
+ if (tos & ~IP_DSCP_MASK) {
+ ovs_fatal(0, "%s: not a valid TOS", arg);
+ }
+ ofpact_put_SET_IPV4_DSCP(ofpacts)->dscp = tos;
+ break;
+
+ case OFPUTIL_OFPAT11_DEC_NW_TTL:
+ NOT_REACHED();
+
+ case OFPUTIL_OFPAT10_SET_TP_SRC:
+ case OFPUTIL_OFPAT11_SET_TP_SRC:
+ ofpact_put_SET_L4_SRC_PORT(ofpacts)->port = str_to_u32(arg);
+ break;
+
+ case OFPUTIL_OFPAT10_SET_TP_DST:
+ case OFPUTIL_OFPAT11_SET_TP_DST:
+ ofpact_put_SET_L4_DST_PORT(ofpacts)->port = str_to_u32(arg);
+ break;
+
+ case OFPUTIL_OFPAT10_ENQUEUE:
+ parse_enqueue(arg, ofpacts);
+ break;
+
+ case OFPUTIL_NXAST_RESUBMIT:
+ parse_resubmit(arg, ofpacts);
+ break;
+
+ case OFPUTIL_NXAST_SET_TUNNEL:
+ case OFPUTIL_NXAST_SET_TUNNEL64:
+ tunnel = ofpact_put_SET_TUNNEL(ofpacts);
+ tunnel->ofpact.compat = code;
+ tunnel->tun_id = str_to_u64(arg);
+ break;
+
+ case OFPUTIL_NXAST_WRITE_METADATA:
+ parse_metadata(ofpacts, arg);
+ break;
+
+ case OFPUTIL_NXAST_SET_QUEUE:
+ ofpact_put_SET_QUEUE(ofpacts)->queue_id = str_to_u32(arg);
+ break;
+
+ case OFPUTIL_NXAST_POP_QUEUE:
+ ofpact_put_POP_QUEUE(ofpacts);
+ break;
+
+ case OFPUTIL_NXAST_REG_MOVE:
+ nxm_parse_reg_move(ofpact_put_REG_MOVE(ofpacts), arg);
+ break;
+
+ case OFPUTIL_NXAST_REG_LOAD:
+ nxm_parse_reg_load(ofpact_put_REG_LOAD(ofpacts), arg);
+ break;
+
+ case OFPUTIL_NXAST_NOTE:
+ parse_note(arg, ofpacts);
+ break;
+
+ case OFPUTIL_NXAST_MULTIPATH:
+ multipath_parse(ofpact_put_MULTIPATH(ofpacts), arg);
+ break;
+
+ case OFPUTIL_NXAST_AUTOPATH__DEPRECATED:
+ autopath_parse(ofpact_put_AUTOPATH(ofpacts), arg);
+ break;
+
+ case OFPUTIL_NXAST_BUNDLE:
+ bundle_parse(arg, ofpacts);
+ break;
+
+ case OFPUTIL_NXAST_BUNDLE_LOAD:
+ bundle_parse_load(arg, ofpacts);
+ break;
+
+ case OFPUTIL_NXAST_RESUBMIT_TABLE:
+ case OFPUTIL_NXAST_OUTPUT_REG:
+ case OFPUTIL_NXAST_DEC_TTL_CNT_IDS:
+ NOT_REACHED();
+
+ case OFPUTIL_NXAST_LEARN:
+ learn_parse(arg, flow, ofpacts);
+ break;
+
+ case OFPUTIL_NXAST_EXIT:
+ ofpact_put_EXIT(ofpacts);
+ break;
+
+ case OFPUTIL_NXAST_DEC_TTL:
+ parse_dec_ttl(ofpacts, arg);
+ break;
+
+ case OFPUTIL_NXAST_FIN_TIMEOUT:
+ parse_fin_timeout(ofpacts, arg);
+ break;
+
+ case OFPUTIL_NXAST_CONTROLLER:
+ parse_controller(ofpacts, arg);
+ break;
+ }
+}