diff --git a/dash-pipeline/SAI/specs/dash_outbound_ca_to_pa.yaml b/dash-pipeline/SAI/specs/dash_outbound_ca_to_pa.yaml index 945fecfc8..4dda7b61f 100644 --- a/dash-pipeline/SAI/specs/dash_outbound_ca_to_pa.yaml +++ b/dash-pipeline/SAI/specs/dash_outbound_ca_to_pa.yaml @@ -257,6 +257,19 @@ sai_apis: valid_only: null is_vlan: false deprecated: false + - !!python/object:utils.sai_spec.sai_attribute.SaiAttribute + name: SAI_OUTBOUND_CA_TO_PA_ENTRY_ATTR_OUTBOUND_PORT_MAP_ID + description: Action parameter outbound port map id + type: sai_object_id_t + attr_value_field: u16 + default: SAI_NULL_OBJECT_ID + isresourcetype: false + flags: CREATE_AND_SET + object_name: SAI_OBJECT_TYPE_OUTBOUND_PORT_MAP + allow_null: true + valid_only: SAI_OUTBOUND_CA_TO_PA_ENTRY_ATTR_ACTION == SAI_OUTBOUND_CA_TO_PA_ENTRY_ACTION_SET_PRIVATE_LINK_MAPPING + is_vlan: false + deprecated: false stats: [] p4_meta: !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4Meta tables: @@ -373,26 +386,32 @@ sai_apis: bitwidth: 24 ip_is_v6_field_id: 0 skipattr: null - SAI_OUTBOUND_CA_TO_PA_ENTRY_ATTR_METER_CLASS_OR: !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4MetaActionParam + SAI_OUTBOUND_CA_TO_PA_ENTRY_ATTR_OUTBOUND_PORT_MAP_ID: !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4MetaActionParam id: 8 + field: u16 + bitwidth: 16 + ip_is_v6_field_id: 0 + skipattr: null + SAI_OUTBOUND_CA_TO_PA_ENTRY_ATTR_METER_CLASS_OR: !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4MetaActionParam + id: 9 field: u32 bitwidth: 32 ip_is_v6_field_id: 0 skipattr: null SAI_OUTBOUND_CA_TO_PA_ENTRY_ATTR_DASH_TUNNEL_ID: !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4MetaActionParam - id: 9 + id: 10 field: u16 bitwidth: 16 ip_is_v6_field_id: 0 skipattr: null SAI_OUTBOUND_CA_TO_PA_ENTRY_ATTR_FLOW_RESIMULATION_REQUESTED: !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4MetaActionParam - id: 10 + id: 11 field: booldata bitwidth: 1 ip_is_v6_field_id: 0 skipattr: null SAI_OUTBOUND_CA_TO_PA_ENTRY_ATTR_ROUTING_ACTIONS_DISABLED_IN_FLOW_RESIMULATION: !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4MetaActionParam - id: 11 + id: 12 field: u32 bitwidth: 32 ip_is_v6_field_id: 0 diff --git a/dash-pipeline/SAI/specs/dash_outbound_port_map.yaml b/dash-pipeline/SAI/specs/dash_outbound_port_map.yaml new file mode 100644 index 000000000..69fda5893 --- /dev/null +++ b/dash-pipeline/SAI/specs/dash_outbound_port_map.yaml @@ -0,0 +1,207 @@ +!!python/object:utils.sai_spec.sai_api_group.SaiApiGroup +name: dash_outbound_port_map +description: DASH outbound port map +api_type: overlay +sai_apis: +- !!python/object:utils.sai_spec.sai_api.SaiApi + name: outbound_port_map + description: outbound port map + is_object: true + enums: [] + structs: [] + attributes: + - !!python/object:utils.sai_spec.sai_attribute.SaiAttribute + name: SAI_OUTBOUND_PORT_MAP_ATTR_COUNTER_ID + description: Attach a counter. When it is empty, then packet hits won't be counted. + type: sai_object_id_t + attr_value_field: null + default: SAI_NULL_OBJECT_ID + isresourcetype: false + flags: CREATE_AND_SET + object_name: SAI_OBJECT_TYPE_COUNTER + allow_null: true + valid_only: null + is_vlan: false + deprecated: false + stats: [] + p4_meta: !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4Meta + tables: + - !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4MetaTable + id: 42579810 + stage: null + keys: + - !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4MetaKey + name: outbound_port_map_id + id: 1 + match_type: exact + field: u16 + bitwidth: 16 + ip_is_v6_field_id: 0 + is_object_key: true + actions: + SAI_OUTBOUND_PORT_MAP_ACTION_SET_PORT_MAP_ATTR: !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4MetaAction + name: SAI_OUTBOUND_PORT_MAP_ACTION_SET_PORT_MAP_ATTR + id: 32437678 + attr_params: {} +- !!python/object:utils.sai_spec.sai_api.SaiApi + name: outbound_port_map_port_range_entry + description: outbound port map port range entry + is_object: false + enums: + - !!python/object:utils.sai_spec.sai_enum.SaiEnum + name: sai_outbound_port_map_port_range_entry_action_t + description: 'Attribute data for #SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ATTR_ACTION' + members: + - !!python/object:utils.sai_spec.sai_enum_member.SaiEnumMember + name: SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ACTION_SKIP_MAPPING + description: '' + value: '0' + - !!python/object:utils.sai_spec.sai_enum_member.SaiEnumMember + name: SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ACTION_MAP_TO_PRIVATE_LINK_SERVICE + description: '' + value: '1' + structs: + - !!python/object:utils.sai_spec.sai_struct.SaiStruct + name: sai_outbound_port_map_port_range_entry_t + description: Entry for outbound_port_map_port_range_entry + members: + - !!python/object:utils.sai_spec.sai_struct_entry.SaiStructEntry + name: switch_id + description: Switch ID + type: sai_object_id_t + objects: SAI_OBJECT_TYPE_SWITCH + valid_only: null + - !!python/object:utils.sai_spec.sai_struct_entry.SaiStructEntry + name: outbound_port_map_id + description: Exact matched key outbound_port_map_id + type: sai_object_id_t + objects: SAI_OBJECT_TYPE_OUTBOUND_PORT_MAP + valid_only: null + - !!python/object:utils.sai_spec.sai_struct_entry.SaiStructEntry + name: dst_port_range + description: Range matched key dst_port_range + type: sai_u32_range_t + objects: null + valid_only: null + - !!python/object:utils.sai_spec.sai_struct_entry.SaiStructEntry + name: priority + description: Rule priority in table + type: sai_uint32_t + objects: null + valid_only: null + attributes: + - !!python/object:utils.sai_spec.sai_attribute.SaiAttribute + name: SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ATTR_ACTION + description: Action + type: sai_outbound_port_map_port_range_entry_action_t + attr_value_field: null + default: SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ACTION_SKIP_MAPPING + isresourcetype: false + flags: CREATE_AND_SET + object_name: null + allow_null: false + valid_only: null + is_vlan: false + deprecated: false + - !!python/object:utils.sai_spec.sai_attribute.SaiAttribute + name: SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ATTR_BACKEND_IP + description: Action parameter back end IP + type: sai_ip_address_t + attr_value_field: ipaddr + default: 0.0.0.0 + isresourcetype: false + flags: CREATE_AND_SET + object_name: null + allow_null: false + valid_only: SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ATTR_ACTION == SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ACTION_MAP_TO_PRIVATE_LINK_SERVICE + is_vlan: false + deprecated: false + - !!python/object:utils.sai_spec.sai_attribute.SaiAttribute + name: SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ATTR_MATCH_PORT_BASE + description: Action parameter match port base + type: sai_uint16_t + attr_value_field: u16 + default: '0' + isresourcetype: false + flags: CREATE_AND_SET + object_name: null + allow_null: false + valid_only: SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ATTR_ACTION == SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ACTION_MAP_TO_PRIVATE_LINK_SERVICE + is_vlan: true + deprecated: false + - !!python/object:utils.sai_spec.sai_attribute.SaiAttribute + name: SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ATTR_BACKEND_PORT_BASE + description: Action parameter back end port base + type: sai_uint16_t + attr_value_field: u16 + default: '0' + isresourcetype: false + flags: CREATE_AND_SET + object_name: null + allow_null: false + valid_only: SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ATTR_ACTION == SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ACTION_MAP_TO_PRIVATE_LINK_SERVICE + is_vlan: true + deprecated: false + - !!python/object:utils.sai_spec.sai_attribute.SaiAttribute + name: SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ATTR_COUNTER_ID + description: Attach a counter. When it is empty, then packet hits won't be counted. + type: sai_object_id_t + attr_value_field: null + default: SAI_NULL_OBJECT_ID + isresourcetype: false + flags: CREATE_AND_SET + object_name: SAI_OBJECT_TYPE_COUNTER + allow_null: true + valid_only: null + is_vlan: false + deprecated: false + stats: [] + p4_meta: !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4Meta + tables: + - !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4MetaTable + id: 35152152 + stage: null + keys: + - !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4MetaKey + name: outbound_port_map_id + id: 1 + match_type: exact + field: u16 + bitwidth: 16 + ip_is_v6_field_id: 0 + is_object_key: false + - !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4MetaKey + name: dst_port_range + id: 2 + match_type: range + field: u32range + bitwidth: 16 + ip_is_v6_field_id: 0 + is_object_key: false + actions: + SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ACTION_SKIP_MAPPING: !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4MetaAction + name: SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ACTION_SKIP_MAPPING + id: 22713701 + attr_params: {} + SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ACTION_MAP_TO_PRIVATE_LINK_SERVICE: !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4MetaAction + name: SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ACTION_MAP_TO_PRIVATE_LINK_SERVICE + id: 23926714 + attr_params: + SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ATTR_BACKEND_IP: !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4MetaActionParam + id: 1 + field: ipaddr + bitwidth: 32 + ip_is_v6_field_id: 0 + skipattr: null + SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ATTR_MATCH_PORT_BASE: !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4MetaActionParam + id: 2 + field: u16 + bitwidth: 16 + ip_is_v6_field_id: 0 + skipattr: null + SAI_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY_ATTR_BACKEND_PORT_BASE: !!python/object:utils.sai_spec.sai_api_p4_meta.SaiApiP4MetaActionParam + id: 3 + field: u16 + bitwidth: 16 + ip_is_v6_field_id: 0 + skipattr: null diff --git a/dash-pipeline/SAI/specs/sai_spec.yaml b/dash-pipeline/SAI/specs/sai_spec.yaml index 9d8bc26df..4305e7171 100644 --- a/dash-pipeline/SAI/specs/sai_spec.yaml +++ b/dash-pipeline/SAI/specs/sai_spec.yaml @@ -15,6 +15,7 @@ api_types: - SAI_API_DASH_TUNNEL - SAI_API_DASH_FLOW - SAI_API_DASH_APPLIANCE +- SAI_API_DASH_OUTBOUND_PORT_MAP object_types: - SAI_OBJECT_TYPE_DASH_ACL_GROUP - SAI_OBJECT_TYPE_DASH_ACL_RULE @@ -43,6 +44,8 @@ object_types: - SAI_OBJECT_TYPE_DASH_APPLIANCE - SAI_OBJECT_TYPE_DASH_TUNNEL_MEMBER - SAI_OBJECT_TYPE_DASH_TUNNEL_NEXT_HOP +- SAI_OBJECT_TYPE_OUTBOUND_PORT_MAP +- SAI_OBJECT_TYPE_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY object_entries: - !!python/object:utils.sai_spec.sai_struct_entry.SaiStructEntry name: direction_lookup_entry @@ -104,6 +107,12 @@ object_entries: type: sai_meter_bucket_entry_t objects: null valid_only: object_type == SAI_OBJECT_TYPE_METER_BUCKET_ENTRY, +- !!python/object:utils.sai_spec.sai_struct_entry.SaiStructEntry + name: outbound_port_map_port_range_entry + description: Object entry for DASH API outbound_port_map_port_range_entry + type: sai_outbound_port_map_port_range_entry_t + objects: null + valid_only: object_type == SAI_OBJECT_TYPE_OUTBOUND_PORT_MAP_PORT_RANGE_ENTRY, enums: - !!python/object:utils.sai_spec.sai_enum.SaiEnum name: sai_dash_direction_t @@ -566,3 +575,4 @@ api_groups: - !inc 'dash_tunnel.yaml' - !inc 'dash_flow.yaml' - !inc 'dash_appliance.yaml' +- !inc 'dash_outbound_port_map.yaml' diff --git a/dash-pipeline/SAI/utils/sai_spec/sai_spec_utils.py b/dash-pipeline/SAI/utils/sai_spec/sai_spec_utils.py index 791a4896e..5cd81f549 100644 --- a/dash-pipeline/SAI/utils/sai_spec/sai_spec_utils.py +++ b/dash-pipeline/SAI/utils/sai_spec/sai_spec_utils.py @@ -25,7 +25,8 @@ def load_word_fixers() -> None: "proto": "protocol", "smac": "source MAC", "dest": "destination", - "dpu": "DPU" + "dpu": "DPU", + "backend": "back end" } # Load all SAI acronyms diff --git a/dash-pipeline/bmv2/dash_headers.p4 b/dash-pipeline/bmv2/dash_headers.p4 index 02c0a9001..2697f2d26 100644 --- a/dash-pipeline/bmv2/dash_headers.p4 +++ b/dash-pipeline/bmv2/dash_headers.p4 @@ -60,6 +60,8 @@ header overlay_rewrite_data_t { IPv4ORv6Address dip; IPv6Address sip_mask; IPv6Address dip_mask; + bit<16> sport; + bit<16> dport; bit<7> reserved; bit<1> is_ipv6; } diff --git a/dash-pipeline/bmv2/dash_metadata.p4 b/dash-pipeline/bmv2/dash_metadata.p4 index bcbbe8ba6..b79522cac 100644 --- a/dash-pipeline/bmv2/dash_metadata.p4 +++ b/dash-pipeline/bmv2/dash_metadata.p4 @@ -66,6 +66,10 @@ struct eni_data_t { IPv4Address vip; } +struct port_map_context_t { + bit<16> map_id; +} + struct meter_context_t { bit<32> meter_class_or; bit<32> meter_class_and; @@ -134,7 +138,6 @@ struct ha_data_t { struct meta_flow_data_t { bit<7> reserved; bit<1> is_unidirectional; - dash_flow_sync_state_t sync_state; dash_direction_t direction; bit<32> version; dash_flow_action_t actions; @@ -156,6 +159,8 @@ struct meta_overlay_rewrite_data_t { IPv4ORv6Address dip; IPv6Address sip_mask; IPv6Address dip_mask; + bit<16> sport; + bit<16> dport; bit<7> reserved; bit<1> is_ipv6; } @@ -198,6 +203,7 @@ struct metadata_t { bit<16> tunnel_pointer; bool is_fast_path_icmp_flow_redirection_packet; bit<1> fast_path_icmp_flow_redirection_disabled; + port_map_context_t port_map_ctx; meter_context_t meter_context; // HA diff --git a/dash-pipeline/bmv2/dash_routing_types.p4 b/dash-pipeline/bmv2/dash_routing_types.p4 index dca3d1f52..75b1699a6 100644 --- a/dash-pipeline/bmv2/dash_routing_types.p4 +++ b/dash-pipeline/bmv2/dash_routing_types.p4 @@ -178,6 +178,7 @@ action set_private_link_mapping( IPv6Address overlay_dip_mask, @SaiVal[type="sai_dash_encapsulation_t"] dash_encapsulation_t dash_encapsulation, bit<24> tunnel_key, + @SaiVal[type="sai_object_id_t"] bit<16> outbound_port_map_id, bit<32> meter_class_or, @SaiVal[type="sai_object_id_t"] bit<16> dash_tunnel_id, bit<1> flow_resimulation_requested, @@ -212,6 +213,8 @@ action set_private_link_mapping( sip_mask = 0xffffffffffffffffffffffff); #endif /* DISABLE_128BIT_ARITHMETIC */ + meta.port_map_ctx.map_id = outbound_port_map_id; + set_meter_attrs(meta, meter_class_or, 0xffffffff); } diff --git a/dash-pipeline/bmv2/routing_actions/routing_action_nat_port.p4 b/dash-pipeline/bmv2/routing_actions/routing_action_nat_port.p4 new file mode 100644 index 000000000..dbe4a79ee --- /dev/null +++ b/dash-pipeline/bmv2/routing_actions/routing_action_nat_port.p4 @@ -0,0 +1,56 @@ +#ifndef _DASH_ROUTING_ACTION_NAT_PORT_P4_ +#define _DASH_ROUTING_ACTION_NAT_PORT_P4_ + +action push_action_snat_port( + in headers_t hdr, + inout metadata_t meta, + in bit<16> sport) +{ + meta.routing_actions = meta.routing_actions | dash_routing_actions_t.SNAT_PORT; + meta.overlay_data.sport = sport; +} + +action push_action_dnat_port( + in headers_t hdr, + inout metadata_t meta, + in bit<16> dport) +{ + meta.routing_actions = meta.routing_actions | dash_routing_actions_t.DNAT_PORT; + meta.overlay_data.dport = dport; +} + +control do_action_snat_port( + inout headers_t hdr, + in metadata_t meta) +{ + apply { + if (meta.routing_actions & dash_routing_actions_t.SNAT_PORT == 0) { + return; + } + + if (hdr.customer_tcp.isValid()) { + hdr.customer_tcp.src_port = meta.overlay_data.sport; + } else if (hdr.customer_udp.isValid()) { + hdr.customer_udp.src_port = meta.overlay_data.sport; + } + } +} + +control do_action_dnat_port( + inout headers_t hdr, + in metadata_t meta) +{ + apply { + if (meta.routing_actions & dash_routing_actions_t.DNAT_PORT == 0) { + return; + } + + if (hdr.customer_tcp.isValid()) { + hdr.customer_tcp.dst_port = meta.overlay_data.dport; + } else if (hdr.customer_udp.isValid()) { + hdr.customer_udp.dst_port = meta.overlay_data.dport; + } + } +} + +#endif /* _DASH_ROUTING_ACTION_NAT_PORT_P4_ */ diff --git a/dash-pipeline/bmv2/routing_actions/routing_actions.p4 b/dash-pipeline/bmv2/routing_actions/routing_actions.p4 index eb228c9a4..e4a6968c4 100644 --- a/dash-pipeline/bmv2/routing_actions/routing_actions.p4 +++ b/dash-pipeline/bmv2/routing_actions/routing_actions.p4 @@ -5,5 +5,6 @@ #include "routing_action_set_mac.p4" #include "routing_action_nat46.p4" #include "routing_action_nat64.p4" +#include "routing_action_nat_port.p4" #endif /* _DASH_ROUTING_ACTIONS_P4_ */ diff --git a/dash-pipeline/bmv2/stages/outbound_port_map.p4 b/dash-pipeline/bmv2/stages/outbound_port_map.p4 new file mode 100644 index 000000000..b035891aa --- /dev/null +++ b/dash-pipeline/bmv2/stages/outbound_port_map.p4 @@ -0,0 +1,84 @@ +#ifndef _DASH_STAGE_PORT_MAP_P4_ +#define _DASH_STAGE_PORT_MAP_P4_ + +#include "../dash_routing_types.p4" + +control outbound_port_map_stage(inout headers_t hdr, + inout metadata_t meta) +{ + action set_port_map_attr() {} + + DEFINE_TABLE_COUNTER(outbound_port_map_counter) + + @SaiTable[api = "dash_outbound_port_map", order = 0, isobject="true"] + table outbound_port_map { + key = { + meta.port_map_ctx.map_id: exact @SaiVal[name = "outbound_port_map_id", type = "sai_object_id_t"]; + } + + actions = { + set_port_map_attr; + @defaultonly drop(meta); + } + const default_action = drop(meta); + + ATTACH_TABLE_COUNTER(outbound_port_map_counter) + } + + action skip_mapping() {} + + action map_to_private_link_service( + @SaiVal[type="sai_ip_address_t"] IPv4Address backend_ip, + bit<16> match_port_base, + bit<16> backend_port_base) + { + REQUIRES((meta.routing_actions & dash_routing_actions_t.NAT46) != 0); + + // For private link, once the service is redirected, we need to update 2 things: + // 1. The underlay IP to point to the new backend IP in order to route the packet there. + // 2. The overlay IP and port to the new backend ip and port, so that the overlay packet will + // look like being sent from the new backend IP. + + // Update underlay + meta.u0_encap_data.underlay_dip = backend_ip; + +#ifndef DISABLE_128BIT_ARITHMETIC + // Update overlay IP + meta.overlay_data.dip = (meta.overlay_data.dip & ~((bit<128>)0xFFFFFFFF)) | (bit<128>)backend_ip; +#endif + + // Update overlay port + push_action_dnat_port( + hdr, + meta, + meta.dst_l4_port - match_port_base + backend_port_base); + } + + DEFINE_TABLE_COUNTER(outbound_port_map_port_range_counter) + + @SaiTable[api = "dash_outbound_port_map", order = 1] + table outbound_port_map_port_range { + key = { + meta.port_map_ctx.map_id: exact @SaiVal[name = "outbound_port_map_id", type = "sai_object_id_t"]; + meta.dst_l4_port: range @SaiVal[name = "dst_port_range"]; + } + + actions = { + skip_mapping; + map_to_private_link_service; + } + + ATTACH_TABLE_COUNTER(outbound_port_map_port_range_counter) + } + + apply { + if (meta.port_map_ctx.map_id == 0) { + return; + } + + outbound_port_map.apply(); + outbound_port_map_port_range.apply(); + } +} + +#endif /* _DASH_STAGE_PORT_MAP_P4_ */ diff --git a/dash-pipeline/bmv2/stages/outbound_pre_routing_action_apply.p4 b/dash-pipeline/bmv2/stages/outbound_pre_routing_action_apply.p4 index 5b536e959..3df23fdd0 100644 --- a/dash-pipeline/bmv2/stages/outbound_pre_routing_action_apply.p4 +++ b/dash-pipeline/bmv2/stages/outbound_pre_routing_action_apply.p4 @@ -3,6 +3,8 @@ #include "tunnel_stage.p4" +#include "outbound_port_map.p4" + control outbound_pre_routing_action_apply_stage( inout headers_t hdr, inout metadata_t meta) @@ -13,6 +15,8 @@ control outbound_pre_routing_action_apply_stage( return; } + outbound_port_map_stage.apply(hdr, meta); + tunnel_stage.apply(hdr, meta); // Once it is done, move to routing action apply stage. diff --git a/dash-pipeline/bmv2/stages/routing_action_apply.p4 b/dash-pipeline/bmv2/stages/routing_action_apply.p4 index bb54c4245..511e9f08d 100644 --- a/dash-pipeline/bmv2/stages/routing_action_apply.p4 +++ b/dash-pipeline/bmv2/stages/routing_action_apply.p4 @@ -10,6 +10,8 @@ control routing_action_apply( apply { do_action_nat46.apply(hdr, meta); do_action_nat64.apply(hdr, meta); + do_action_snat_port.apply(hdr, meta); + do_action_dnat_port.apply(hdr, meta); do_action_set_dmac.apply(hdr, meta); // Encaps needs to be added after all other transforms, from inner ones to outer ones,