diff --git a/backends/dpdk/CMakeLists.txt b/backends/dpdk/CMakeLists.txt index 726a82ff26c..845690d4077 100644 --- a/backends/dpdk/CMakeLists.txt +++ b/backends/dpdk/CMakeLists.txt @@ -58,6 +58,7 @@ set(P4C_DPDK_SOURCES dpdkArch.cpp dpdkContext.cpp dpdkAsmOpt.cpp + dpdkMetadata.cpp dpdkUtils.cpp options.cpp control-plane/bfruntime_ext.cpp @@ -74,6 +75,7 @@ set(P4C_DPDK_HEADERS dpdkContext.h constants.h dpdkAsmOpt.h + dpdkMetadata.h printUtils.h dpdkUtils.h dpdkProgramStructure.h diff --git a/backends/dpdk/DpdkXfail.cmake b/backends/dpdk/DpdkXfail.cmake index d742873ed95..cf485f05491 100644 --- a/backends/dpdk/DpdkXfail.cmake +++ b/backends/dpdk/DpdkXfail.cmake @@ -71,10 +71,6 @@ p4c_add_xfail_reason("dpdk" testdata/p4_16_samples/psa-dpdk-lpm-match-err2.p4 ) -p4c_add_xfail_reason("dpdk" - "Non Type_Bits type bool for expression" - ) - p4c_add_xfail_reason("dpdk" "mirror_packet cannot be used in the" testdata/p4_16_samples/pna-example-mirror-packet-ctxt-error.p4 @@ -96,6 +92,11 @@ p4c_add_xfail_reason("dpdk" testdata/p4_16_samples/pna-example-mirror-packet-error3.p4 ) +p4c_add_xfail_reason("dpdk" + "declaration not found" + testdata/p4_16_samples/pna-direction-main-parser-err.p4 + ) + p4c_add_xfail_reason("dpdk" "All table keys together with holes in the underlying structure should fit in 64 bytes" testdata/p4_16_samples/psa-dpdk-table-key-error.p4 diff --git a/backends/dpdk/backend.cpp b/backends/dpdk/backend.cpp index a451b8878dd..ca925b89570 100644 --- a/backends/dpdk/backend.cpp +++ b/backends/dpdk/backend.cpp @@ -29,6 +29,7 @@ limitations under the License. #include "ir/ir.h" #include "lib/stringify.h" #include "../bmv2/common/lower.h" +#include "dpdkMetadata.h" namespace DPDK { @@ -122,6 +123,14 @@ void DpdkBackend::convert(const IR::ToplevelBlock *tlb) { dpdk_program = convertToDpdk->getDpdkProgram(); if (!dpdk_program) return; + if (structure.p4arch == "pna") { + PassManager post_code_gen = { + new DirectionToRegRead(), + new AddNewMetadataFields(), + }; + dpdk_program = dpdk_program->apply(post_code_gen)->to(); + } + PassManager post_code_gen = { new EliminateUnusedAction(), new DpdkAsmOptimization, diff --git a/backends/dpdk/dpdkAsmOpt.cpp b/backends/dpdk/dpdkAsmOpt.cpp index 054d4eabbde..eaac710cf05 100644 --- a/backends/dpdk/dpdkAsmOpt.cpp +++ b/backends/dpdk/dpdkAsmOpt.cpp @@ -15,6 +15,7 @@ limitations under the License. */ #include "dpdkAsmOpt.h" +#include "dpdkUtils.h" namespace DPDK { // The assumption is compiler can only produce forward jumps. @@ -178,12 +179,8 @@ bool RemoveUnusedMetadataFields::isByteSizeField(const IR::Type *field_type) { const IR::Node* RemoveUnusedMetadataFields::preorder(IR::DpdkAsmProgram *p) { IR::IndexedVector usedStruct; - bool isMetadataStruct = false; for (auto st : p->structType) { - if (!isMetadataStruct) { - for (auto anno : st->annotations->annotations) { - if (anno->name == "__metadata__") { - isMetadataStruct = true; + if (isMetadataStruct(st)) { IR::IndexedVector usedMetadataFields; for (auto field : st->fields) { if (used_fields.count(field->name.name)) { @@ -198,11 +195,6 @@ const IR::Node* RemoveUnusedMetadataFields::preorder(IR::DpdkAsmProgram *p) { auto newSt = new IR::DpdkStructType(st->srcInfo, st->name, st->annotations, usedMetadataFields); usedStruct.push_back(newSt); - } - } - if (!isMetadataStruct) { - usedStruct.push_back(st); - } } else { usedStruct.push_back(st); } @@ -227,15 +219,6 @@ int ValidateTableKeys::getFieldSizeBits(const IR::Type *field_type) { return -1; } -bool ValidateTableKeys::isMetadataStruct(const IR::Type_Struct *st) { - for (auto anno : st->annotations->annotations) { - if (anno->name == "__metadata__") { - return true; - } - } - return false; -} - bool ValidateTableKeys::preorder(const IR::DpdkAsmProgram *p) { const IR::DpdkStructType *metaStruct = nullptr; for (auto st : p->structType) { @@ -256,7 +239,8 @@ bool ValidateTableKeys::preorder(const IR::DpdkAsmProgram *p) { "%1% is not a structure field", key); auto keyMem = key->expression->to(); auto type = keyMem->expr->type; - if (type->is() && isMetadataStruct(type->to())) { + if (type->is() + && isMetadataStruct(type->to())) { auto offset = metaStruct->getFieldBitOffset(keyMem->member.name); if (min == -1 || min > offset) min = offset; diff --git a/backends/dpdk/dpdkAsmOpt.h b/backends/dpdk/dpdkAsmOpt.h index c5268217f4d..9a0c2038918 100644 --- a/backends/dpdk/dpdkAsmOpt.h +++ b/backends/dpdk/dpdkAsmOpt.h @@ -169,7 +169,6 @@ class ValidateTableKeys : public Inspector { public: ValidateTableKeys() {} bool preorder(const IR::DpdkAsmProgram *p) override; - bool isMetadataStruct(const IR::Type_Struct *st); int getFieldSizeBits(const IR::Type *field_type); }; diff --git a/backends/dpdk/dpdkMetadata.cpp b/backends/dpdk/dpdkMetadata.cpp new file mode 100644 index 00000000000..3e8a18841c7 --- /dev/null +++ b/backends/dpdk/dpdkMetadata.cpp @@ -0,0 +1,151 @@ +/* +Copyright 2022 Intel Corp. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +#include "dpdkMetadata.h" +#include "dpdkUtils.h" + +namespace DPDK { +const IR::Node* AddNewMetadataFields::preorder(IR::DpdkStructType *st) { + if (isMetadataStruct(st)) { + for (auto nf : newMetadataFields) { + st->fields.push_back(nf); + } + auto newSt = new IR::DpdkStructType(st->srcInfo, st->name, + st->annotations, st->fields); + newMetadataFields.clear(); + return newSt; + } + return st; +} + +// make sure new decls and fields name are unique +void DirectionToRegRead::uniqueNames(IR::DpdkAsmProgram *p) { + P4::MinimalNameGenerator mng; + for (auto st : p->structType) { + if (isMetadataStruct(st)) { + for (auto field : st->fields) + mng.usedName(field->name); + } + } + reg_read_tmp = mng.newName("reg_read_tmp"); + left_shift_tmp = mng.newName("left_shift_tmp"); + + // "network_port_mask" name is used in dpdk for initialzing direction port mask + // make sure no such decls exist with that name + registerInstanceName = "network_port_mask"; + for (auto decl : p->externDeclarations) { + usedNames.insert(decl->name); + } + + if (usedNames.count(registerInstanceName)) + ::error(ErrorType::ERR_UNSUPPORTED_ON_TARGET,"decl name %s is reserved for dpdk pna", + registerInstanceName); +} + +const IR::Node* DirectionToRegRead::preorder(IR::DpdkAsmProgram *p) { + uniqueNames(p); + addMetadataField(reg_read_tmp); + addMetadataField(left_shift_tmp); + p->externDeclarations.push_back(addRegDeclInstance(registerInstanceName)); + return p; +} + +// create and add register declaration instance to program +IR::DpdkExternDeclaration* DirectionToRegRead::addRegDeclInstance(cstring instanceName) { + auto typepath = new IR::Path("Register"); + auto type = new IR::Type_Name(typepath); + auto typeargs = new IR::Vector({IR::Type::Bits::get(32), + IR::Type::Bits::get(32)}); + auto spectype = new IR::Type_Specialized(type, typeargs); + auto args = new IR::Vector(); + args->push_back(new IR::Argument(new IR::Constant(IR::Type::Bits::get(32), 1))); + auto annot = IR::Annotations::empty; + annot->addAnnotationIfNew(IR::Annotation::nameAnnotation, + new IR::StringLiteral(instanceName)); + auto decl = new IR::DpdkExternDeclaration(instanceName, annot, spectype, args, + nullptr); + return decl; +} + +// add new fields in metadata structure +void DirectionToRegRead::addMetadataField(cstring fieldName) { + newMetadataFields.push_back(new IR::StructField(IR::ID(fieldName), + IR::Type::Bits::get(32))); +} + +// check member expression using metadata direction field +bool DirectionToRegRead::isDirection(const IR::Member *m) { + if (m == nullptr) + return false; + return m->member.name == "pna_main_input_metadata_direction" + || m->member.name == "pna_pre_input_metadata_direction" + || m->member.name == "pna_main_parser_input_metadata_direction"; +} + +const IR::Node *DirectionToRegRead::postorder(IR::DpdkListStatement *l) { + l->statements = replaceDirectionWithRegRead(l->statements); + newStmts.clear(); + return l; +} + +const IR::Node *DirectionToRegRead::postorder(IR::DpdkAction *a) { + a->statements = replaceDirectionWithRegRead(a->statements); + newStmts.clear(); + return a; +} + +// replace direction field uses with register read i.e. +// istd.direction -> (direction_port_mask.read(0) & (32w0x1 << istd.input_port)) +void DirectionToRegRead::replaceDirection(const IR::Member *m) { + auto reade = new IR::Member(new IR::PathExpression(IR::ID("m")), + IR::ID(reg_read_tmp)); + auto reads = new IR::DpdkRegisterReadStatement(reade, registerInstanceName, + new IR::Constant(IR::Type::Bits::get(32), + 0)); + auto shld = new IR::Member(new IR::PathExpression(IR::ID("m")), + IR::ID(left_shift_tmp)); + auto mov = new IR::DpdkMovStatement(shld, new IR::Constant(IR::Type::Bits::get(32), 1)); + auto shl = new IR::DpdkShlStatement(shld, shld, + new IR::Member(new IR::PathExpression(IR::ID("m")), + IR::ID(dirToInput[m->member.name]))); + auto mov1 = new IR::DpdkMovStatement(m, reade); + auto and0 = new IR::DpdkAndStatement(m, m, shld); + newStmts.push_back(reads); + newStmts.push_back(mov); + newStmts.push_back(shl); + newStmts.push_back(mov1); + newStmts.push_back(and0); +} + +IR::IndexedVector +DirectionToRegRead::replaceDirectionWithRegRead(IR::IndexedVector stmts) { + for (auto s : stmts) { + if (auto jc = s->to()) { + if (isDirection(jc->src1->to())) + replaceDirection(jc->src1->to()); + else if (isDirection(jc->src2->to())) + replaceDirection(jc->src2->to()); + } else if (auto u = s->to()) { + if (isDirection(u->src->to())) + replaceDirection(u->src->to()); + } + newStmts.push_back(s); + } + return newStmts; +} + +IR::IndexedVector AddNewMetadataFields::newMetadataFields = {}; +} // namespace DPDK diff --git a/backends/dpdk/dpdkMetadata.h b/backends/dpdk/dpdkMetadata.h new file mode 100644 index 00000000000..4e0ca5afee6 --- /dev/null +++ b/backends/dpdk/dpdkMetadata.h @@ -0,0 +1,73 @@ +/* +Copyright 2022 Intel Corp. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +#ifndef BACKENDS_DPDK_DPDKMETADATA_H_ +#define BACKENDS_DPDK_DPDKMETADATA_H_ + +#include "frontends/common/resolveReferences/referenceMap.h" +#include "ir/ir.h" + +namespace DPDK { + +// If any pass requires to add metadata field to metadata structure +// then just have to create and append struct field to static member newMetadataFields +// In passmanager's passes list AddNewMetadataFields should follow the pass which +// added fields into newMetadataFields +class AddNewMetadataFields : public Transform { + public: + static IR::IndexedVector newMetadataFields; + const IR::Node* preorder(IR::DpdkStructType *st) override; +}; + +// This pass adds decl instance of Register extern in dpdk pna program which will +// be used by dpdk backend for initializing the mask for calculating packet direction +// and all the use point of istd.direction will follow below calculation and assignment +// istd.direction = network_port_mask.read(0) & (32w0x1 << istd.input_port) +class DirectionToRegRead : public Transform { + ordered_map dirToInput; + IR::IndexedVector newStmts; + IR::IndexedVector &newMetadataFields = AddNewMetadataFields::newMetadataFields; + ordered_set usedNames; + cstring reg_read_tmp; + cstring left_shift_tmp; + cstring registerInstanceName; + + public: + DirectionToRegRead() { + // direction to input metadata field name mapping + dirToInput.insert(std::make_pair(cstring("pna_main_input_metadata_direction"), + cstring("pna_main_input_metadata_input_port"))); + dirToInput.insert(std::make_pair(cstring("pna_pre_input_metadata_direction"), + cstring("pna_pre_input_metadata_input_port"))); + dirToInput.insert(std::make_pair(cstring("pna_main_parser_input_metadata_direction"), + cstring("pna_main_parser_input_metadata_input_port"))); + } + void uniqueNames(IR::DpdkAsmProgram *p); + const IR::Node* preorder(IR::DpdkAsmProgram *p) override; + + IR::DpdkExternDeclaration* + addRegDeclInstance(cstring instanceName); + void addMetadataField(cstring fieldName); + bool isDirection(const IR::Member *m); + const IR::Node *postorder(IR::DpdkAction *a); + const IR::Node *postorder(IR::DpdkListStatement *l) override; + void replaceDirection(const IR::Member *m); + IR::IndexedVector + replaceDirectionWithRegRead(IR::IndexedVector stmts); +}; + +} // namespace DPDK +#endif // BACKENDS_DPDK_DPDKMETADATA_H_ diff --git a/backends/dpdk/dpdkUtils.cpp b/backends/dpdk/dpdkUtils.cpp index 53879267686..5406d50a3fa 100644 --- a/backends/dpdk/dpdkUtils.cpp +++ b/backends/dpdk/dpdkUtils.cpp @@ -53,4 +53,14 @@ bool isStandardMetadata(cstring name) { name == "pna_main_parser_input_metadata_t"; return isStdMeta; } + +bool isMetadataStruct(const IR::Type_Struct *st) { + for (auto anno : st->annotations->annotations) { + if (anno->name == "__metadata__") { + return true; + } + } + return false; +} + } // namespace DPDK diff --git a/backends/dpdk/dpdkUtils.h b/backends/dpdk/dpdkUtils.h index cc7a244ef82..c644448bb64 100644 --- a/backends/dpdk/dpdkUtils.h +++ b/backends/dpdk/dpdkUtils.h @@ -23,6 +23,6 @@ bool isSimpleExpression(const IR::Expression *e); bool isNonConstantSimpleExpression(const IR::Expression *e); bool isCommutativeBinaryOperation(const IR::Operation_Binary *bin); bool isStandardMetadata(cstring name); +bool isMetadataStruct(const IR::Type_Struct *st); } // namespace DPDK - #endif /* BACKENDS_DPDK_DPDKUTILS_H_ */ diff --git a/testdata/p4_16_samples/pna-direction-main-parser-err.p4 b/testdata/p4_16_samples/pna-direction-main-parser-err.p4 new file mode 100644 index 00000000000..d7033cebeab --- /dev/null +++ b/testdata/p4_16_samples/pna-direction-main-parser-err.p4 @@ -0,0 +1,171 @@ +/* +Copyright 2022 Intel Corporation + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +#include +#include "pna.p4" + + +typedef bit<48> EthernetAddress; + +header ethernet_t { + EthernetAddress dstAddr; + EthernetAddress srcAddr; + bit<16> etherType; +} + +header ipv4_t { + bit<4> version; + bit<4> ihl; + bit<8> diffserv; + bit<16> totalLen; + bit<16> identification; + bit<3> flags; + bit<13> fragOffset; + bit<8> ttl; + bit<8> protocol; + bit<16> hdrChecksum; + bit<32> srcAddr; + bit<32> dstAddr; +} + +struct empty_metadata_t { +} + +////////////////////////////////////////////////////////////////////// +// Struct types for holding user-defined collections of headers and +// metadata in the P4 developer's program. +// +// Note: The names of these struct types are completely up to the P4 +// developer, as are their member fields, with the only restriction +// being that the structs intended to contain headers should only +// contain members whose types are header, header stack, or +// header_union. +////////////////////////////////////////////////////////////////////// + +struct main_metadata_t { + // empty for this skeleton + bit<32> tmpDir; +} + +// User-defined struct containing all of those headers parsed in the +// main parser. +struct headers_t { + ethernet_t ethernet; + ipv4_t ipv4; +} + +control PreControlImpl( + in headers_t hdr, + inout main_metadata_t meta, + in pna_pre_input_metadata_t istd, + inout pna_pre_output_metadata_t ostd) +{ + + apply { + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + meta.tmpDir = hdr.ipv4.srcAddr; + } else { + meta.tmpDir = hdr.ipv4.dstAddr; + } + } + +} + +parser MainParserImpl( + packet_in pkt, + out headers_t hdr, + inout main_metadata_t main_meta, + in pna_main_parser_input_metadata_t istd) +{ + bit<32> tmpDir; + state start { + pkt.extract(hdr.ethernet); + transition select(hdr.ethernet.etherType) { + 0x0800: parse_ipv4; + default: accept; + } + } + state parse_ipv4 { + pkt.extract(hdr.ipv4); + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + tmpDir = hdr.ipv4.srcAddr; + } else { + tmpDir = hdr.ipv4.dstAddr; + } + transition accept; + } +} + +control MainControlImpl( + inout headers_t hdr, // from main parser + inout main_metadata_t user_meta, // from main parser, to "next block" + in pna_main_input_metadata_t istd, + inout pna_main_output_metadata_t ostd) +{ + bit<32> tmpDir; + action next_hop(PortId_t vport) { + send_to_port(vport); + } + action default_route_drop() { + drop_packet(); + } + table ipv4_da_lpm { + key = { + tmpDir :lpm @name ("ipv4_addr"); + } + actions = { + next_hop; + default_route_drop; + } + const default_action = default_route_drop; + } + apply { + + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + tmpDir = hdr.ipv4.srcAddr; + } else { + tmpDir = hdr.ipv4.dstAddr; + } + if (hdr.ipv4.isValid()) { + ipv4_da_lpm.apply(); + } + } +} + +control MainDeparserImpl( + packet_out pkt, + in headers_t hdr, // from main control + in main_metadata_t user_meta, // from main control + in pna_main_output_metadata_t ostd) +{ + apply { + pkt.emit(hdr.ethernet); + pkt.emit(hdr.ipv4); + } +} + +// BEGIN:Package_Instantiation_Example +PNA_NIC( + MainParserImpl(), + PreControlImpl(), + MainControlImpl(), + MainDeparserImpl() + // Hoping to make this optional parameter later, but not supported + // by p4c yet. + //, PreParserImpl() + ) main; +// END:Package_Instantiation_Example + diff --git a/testdata/p4_16_samples/pna-direction.p4 b/testdata/p4_16_samples/pna-direction.p4 new file mode 100644 index 00000000000..78afcafbda5 --- /dev/null +++ b/testdata/p4_16_samples/pna-direction.p4 @@ -0,0 +1,169 @@ +/* +Copyright 2022 Intel Corporation + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +#include +#include "pna.p4" + + +typedef bit<48> EthernetAddress; + +header ethernet_t { + EthernetAddress dstAddr; + EthernetAddress srcAddr; + bit<16> etherType; +} + +header ipv4_t { + bit<4> version; + bit<4> ihl; + bit<8> diffserv; + bit<16> totalLen; + bit<16> identification; + bit<3> flags; + bit<13> fragOffset; + bit<8> ttl; + bit<8> protocol; + bit<16> hdrChecksum; + bit<32> srcAddr; + bit<32> dstAddr; +} + +struct empty_metadata_t { +} + +////////////////////////////////////////////////////////////////////// +// Struct types for holding user-defined collections of headers and +// metadata in the P4 developer's program. +// +// Note: The names of these struct types are completely up to the P4 +// developer, as are their member fields, with the only restriction +// being that the structs intended to contain headers should only +// contain members whose types are header, header stack, or +// header_union. +////////////////////////////////////////////////////////////////////// + +struct main_metadata_t { + // empty for this skeleton + bit<32> tmpDir; + PNA_Direction_t t1; + bool b; +} + +// User-defined struct containing all of those headers parsed in the +// main parser. +struct headers_t { + ethernet_t ethernet; + ipv4_t ipv4; +} + +control PreControlImpl( + in headers_t hdr, + inout main_metadata_t meta, + in pna_pre_input_metadata_t istd, + inout pna_pre_output_metadata_t ostd) +{ + + apply { + meta.b = istd.direction != PNA_Direction_t.NET_TO_HOST; + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + meta.tmpDir = hdr.ipv4.srcAddr; + } else { + meta.tmpDir = hdr.ipv4.dstAddr; + } + + } + +} + +parser MainParserImpl( + packet_in pkt, + out headers_t hdr, + inout main_metadata_t main_meta, + in pna_main_parser_input_metadata_t istd) +{ + state start { + pkt.extract(hdr.ethernet); + transition select(hdr.ethernet.etherType) { + 0x0800: parse_ipv4; + default: accept; + } + } + state parse_ipv4 { + pkt.extract(hdr.ipv4); + transition accept; + } +} + +control MainControlImpl( + inout headers_t hdr, // from main parser + inout main_metadata_t user_meta, // from main parser, to "next block" + in pna_main_input_metadata_t istd, + inout pna_main_output_metadata_t ostd) +{ + bit<32> tmpDir; + action next_hop(PortId_t vport) { + send_to_port(vport); + } + action default_route_drop() { + drop_packet(); + } + table ipv4_da_lpm { + key = { + tmpDir :lpm @name ("ipv4_addr"); + } + actions = { + next_hop; + default_route_drop; + } + const default_action = default_route_drop; + } + apply { + + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + tmpDir = hdr.ipv4.srcAddr; + } else { + tmpDir = hdr.ipv4.dstAddr; + } + if (hdr.ipv4.isValid()) { + ipv4_da_lpm.apply(); + } + } +} + +control MainDeparserImpl( + packet_out pkt, + in headers_t hdr, // from main control + in main_metadata_t user_meta, // from main control + in pna_main_output_metadata_t ostd) +{ + apply { + pkt.emit(hdr.ethernet); + pkt.emit(hdr.ipv4); + } +} + +// BEGIN:Package_Instantiation_Example +PNA_NIC( + MainParserImpl(), + PreControlImpl(), + MainControlImpl(), + MainDeparserImpl() + // Hoping to make this optional parameter later, but not supported + // by p4c yet. + //, PreParserImpl() + ) main; +// END:Package_Instantiation_Example + diff --git a/testdata/p4_16_samples_outputs/pna-action-selector.p4.spec b/testdata/p4_16_samples_outputs/pna-action-selector.p4.spec index 441449c1c57..d6ede9f2167 100644 --- a/testdata/p4_16_samples_outputs/pna-action-selector.p4.spec +++ b/testdata/p4_16_samples_outputs/pna-action-selector.p4.spec @@ -43,6 +43,8 @@ metadata instanceof main_metadata_t header ethernet instanceof ethernet_t header ipv4 instanceof ipv4_t +regarray network_port_mask size 0x1 initval 0 + action NoAction args none { return } diff --git a/testdata/p4_16_samples_outputs/pna-add-on-miss.p4.spec b/testdata/p4_16_samples_outputs/pna-add-on-miss.p4.spec index f46ef78808a..51ab47a2879 100644 --- a/testdata/p4_16_samples_outputs/pna-add-on-miss.p4.spec +++ b/testdata/p4_16_samples_outputs/pna-add-on-miss.p4.spec @@ -39,6 +39,8 @@ metadata instanceof main_metadata_t header ethernet instanceof ethernet_t header ipv4 instanceof ipv4_t +regarray network_port_mask size 0x1 initval 0 + action next_hop args instanceof next_hop_arg_t { mov m.pna_main_output_metadata_output_port t.vport return diff --git a/testdata/p4_16_samples_outputs/pna-direction-first.p4 b/testdata/p4_16_samples_outputs/pna-direction-first.p4 new file mode 100644 index 00000000000..d887683befa --- /dev/null +++ b/testdata/p4_16_samples_outputs/pna-direction-first.p4 @@ -0,0 +1,103 @@ +#include +#include + +typedef bit<48> EthernetAddress; +header ethernet_t { + EthernetAddress dstAddr; + EthernetAddress srcAddr; + bit<16> etherType; +} + +header ipv4_t { + bit<4> version; + bit<4> ihl; + bit<8> diffserv; + bit<16> totalLen; + bit<16> identification; + bit<3> flags; + bit<13> fragOffset; + bit<8> ttl; + bit<8> protocol; + bit<16> hdrChecksum; + bit<32> srcAddr; + bit<32> dstAddr; +} + +struct empty_metadata_t { +} + +struct main_metadata_t { + bit<32> tmpDir; + PNA_Direction_t t1; + bool b; +} + +struct headers_t { + ethernet_t ethernet; + ipv4_t ipv4; +} + +control PreControlImpl(in headers_t hdr, inout main_metadata_t meta, in pna_pre_input_metadata_t istd, inout pna_pre_output_metadata_t ostd) { + apply { + meta.b = istd.direction != PNA_Direction_t.NET_TO_HOST; + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + meta.tmpDir = hdr.ipv4.srcAddr; + } else { + meta.tmpDir = hdr.ipv4.dstAddr; + } + } +} + +parser MainParserImpl(packet_in pkt, out headers_t hdr, inout main_metadata_t main_meta, in pna_main_parser_input_metadata_t istd) { + state start { + pkt.extract(hdr.ethernet); + transition select(hdr.ethernet.etherType) { + 16w0x800: parse_ipv4; + default: accept; + } + } + state parse_ipv4 { + pkt.extract(hdr.ipv4); + transition accept; + } +} + +control MainControlImpl(inout headers_t hdr, inout main_metadata_t user_meta, in pna_main_input_metadata_t istd, inout pna_main_output_metadata_t ostd) { + bit<32> tmpDir; + action next_hop(PortId_t vport) { + send_to_port(vport); + } + action default_route_drop() { + drop_packet(); + } + table ipv4_da_lpm { + key = { + tmpDir: lpm @name("ipv4_addr") ; + } + actions = { + next_hop(); + default_route_drop(); + } + const default_action = default_route_drop(); + } + apply { + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + tmpDir = hdr.ipv4.srcAddr; + } else { + tmpDir = hdr.ipv4.dstAddr; + } + if (hdr.ipv4.isValid()) { + ipv4_da_lpm.apply(); + } + } +} + +control MainDeparserImpl(packet_out pkt, in headers_t hdr, in main_metadata_t user_meta, in pna_main_output_metadata_t ostd) { + apply { + pkt.emit(hdr.ethernet); + pkt.emit(hdr.ipv4); + } +} + +PNA_NIC(MainParserImpl(), PreControlImpl(), MainControlImpl(), MainDeparserImpl()) main; + diff --git a/testdata/p4_16_samples_outputs/pna-direction-frontend.p4 b/testdata/p4_16_samples_outputs/pna-direction-frontend.p4 new file mode 100644 index 00000000000..ae57c8603cd --- /dev/null +++ b/testdata/p4_16_samples_outputs/pna-direction-frontend.p4 @@ -0,0 +1,103 @@ +#include +#include + +typedef bit<48> EthernetAddress; +header ethernet_t { + EthernetAddress dstAddr; + EthernetAddress srcAddr; + bit<16> etherType; +} + +header ipv4_t { + bit<4> version; + bit<4> ihl; + bit<8> diffserv; + bit<16> totalLen; + bit<16> identification; + bit<3> flags; + bit<13> fragOffset; + bit<8> ttl; + bit<8> protocol; + bit<16> hdrChecksum; + bit<32> srcAddr; + bit<32> dstAddr; +} + +struct empty_metadata_t { +} + +struct main_metadata_t { + bit<32> tmpDir; + PNA_Direction_t t1; + bool b; +} + +struct headers_t { + ethernet_t ethernet; + ipv4_t ipv4; +} + +control PreControlImpl(in headers_t hdr, inout main_metadata_t meta, in pna_pre_input_metadata_t istd, inout pna_pre_output_metadata_t ostd) { + apply { + meta.b = istd.direction != PNA_Direction_t.NET_TO_HOST; + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + meta.tmpDir = hdr.ipv4.srcAddr; + } else { + meta.tmpDir = hdr.ipv4.dstAddr; + } + } +} + +parser MainParserImpl(packet_in pkt, out headers_t hdr, inout main_metadata_t main_meta, in pna_main_parser_input_metadata_t istd) { + state start { + pkt.extract(hdr.ethernet); + transition select(hdr.ethernet.etherType) { + 16w0x800: parse_ipv4; + default: accept; + } + } + state parse_ipv4 { + pkt.extract(hdr.ipv4); + transition accept; + } +} + +control MainControlImpl(inout headers_t hdr, inout main_metadata_t user_meta, in pna_main_input_metadata_t istd, inout pna_main_output_metadata_t ostd) { + @name("MainControlImpl.tmpDir") bit<32> tmpDir_0; + @name("MainControlImpl.next_hop") action next_hop(@name("vport") PortId_t vport) { + send_to_port(vport); + } + @name("MainControlImpl.default_route_drop") action default_route_drop() { + drop_packet(); + } + @name("MainControlImpl.ipv4_da_lpm") table ipv4_da_lpm_0 { + key = { + tmpDir_0: lpm @name("ipv4_addr") ; + } + actions = { + next_hop(); + default_route_drop(); + } + const default_action = default_route_drop(); + } + apply { + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + tmpDir_0 = hdr.ipv4.srcAddr; + } else { + tmpDir_0 = hdr.ipv4.dstAddr; + } + if (hdr.ipv4.isValid()) { + ipv4_da_lpm_0.apply(); + } + } +} + +control MainDeparserImpl(packet_out pkt, in headers_t hdr, in main_metadata_t user_meta, in pna_main_output_metadata_t ostd) { + apply { + pkt.emit(hdr.ethernet); + pkt.emit(hdr.ipv4); + } +} + +PNA_NIC(MainParserImpl(), PreControlImpl(), MainControlImpl(), MainDeparserImpl()) main; + diff --git a/testdata/p4_16_samples_outputs/pna-direction-main-parser-err-first.p4 b/testdata/p4_16_samples_outputs/pna-direction-main-parser-err-first.p4 new file mode 100644 index 00000000000..e4f40565670 --- /dev/null +++ b/testdata/p4_16_samples_outputs/pna-direction-main-parser-err-first.p4 @@ -0,0 +1,115 @@ +#include +#include + +typedef bit<48> EthernetAddress; +header ethernet_t { + EthernetAddress dstAddr; + EthernetAddress srcAddr; + bit<16> etherType; +} + +header ipv4_t { + bit<4> version; + bit<4> ihl; + bit<8> diffserv; + bit<16> totalLen; + bit<16> identification; + bit<3> flags; + bit<13> fragOffset; + bit<8> ttl; + bit<8> protocol; + bit<16> hdrChecksum; + bit<32> srcAddr; + bit<32> dstAddr; +} + +struct empty_metadata_t { +} + +struct main_metadata_t { + bit<32> tmpDir; +} + +struct headers_t { + ethernet_t ethernet; + ipv4_t ipv4; +} + +control PreControlImpl(in headers_t hdr, inout main_metadata_t meta, in pna_pre_input_metadata_t istd, inout pna_pre_output_metadata_t ostd) { + apply { + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + meta.tmpDir = hdr.ipv4.srcAddr; + } else { + meta.tmpDir = hdr.ipv4.dstAddr; + } + } +} + +parser MainParserImpl(packet_in pkt, out headers_t hdr, inout main_metadata_t main_meta, in pna_main_parser_input_metadata_t istd) { + @name("tmpDir") bit<32> tmpDir_0; + state start { + pkt.extract(hdr.ethernet); + transition select(hdr.ethernet.etherType) { + 16w0x800: parse_ipv4; + default: accept; + } + } + state parse_ipv4 { + pkt.extract(hdr.ipv4); + transition select(PNA_Direction_t.NET_TO_HOST == istd.direction) { + true: parse_ipv4_true; + false: parse_ipv4_false; + } + } + state parse_ipv4_true { + tmpDir_0 = hdr.ipv4.srcAddr; + transition parse_ipv4_join; + } + state parse_ipv4_false { + tmpDir_0 = hdr.ipv4.dstAddr; + transition parse_ipv4_join; + } + state parse_ipv4_join { + transition accept; + } +} + +control MainControlImpl(inout headers_t hdr, inout main_metadata_t user_meta, in pna_main_input_metadata_t istd, inout pna_main_output_metadata_t ostd) { + @name("tmpDir") bit<32> tmpDir_1; + @name("next_hop") action next_hop_0(PortId_t vport) { + send_to_port(vport); + } + @name("default_route_drop") action default_route_drop_0() { + drop_packet(); + } + @name("ipv4_da_lpm") table ipv4_da_lpm_0 { + key = { + tmpDir_1: lpm @name("ipv4_addr") ; + } + actions = { + next_hop_0(); + default_route_drop_0(); + } + const default_action = default_route_drop_0(); + } + apply { + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + tmpDir_1 = hdr.ipv4.srcAddr; + } else { + tmpDir_1 = hdr.ipv4.dstAddr; + } + if (hdr.ipv4.isValid()) { + ipv4_da_lpm_0.apply(); + } + } +} + +control MainDeparserImpl(packet_out pkt, in headers_t hdr, in main_metadata_t user_meta, in pna_main_output_metadata_t ostd) { + apply { + pkt.emit(hdr.ethernet); + pkt.emit(hdr.ipv4); + } +} + +PNA_NIC(MainParserImpl(), PreControlImpl(), MainControlImpl(), MainDeparserImpl()) main; + diff --git a/testdata/p4_16_samples_outputs/pna-direction-main-parser-err-frontend.p4 b/testdata/p4_16_samples_outputs/pna-direction-main-parser-err-frontend.p4 new file mode 100644 index 00000000000..540160830a3 --- /dev/null +++ b/testdata/p4_16_samples_outputs/pna-direction-main-parser-err-frontend.p4 @@ -0,0 +1,112 @@ +#include +#include + +typedef bit<48> EthernetAddress; +header ethernet_t { + EthernetAddress dstAddr; + EthernetAddress srcAddr; + bit<16> etherType; +} + +header ipv4_t { + bit<4> version; + bit<4> ihl; + bit<8> diffserv; + bit<16> totalLen; + bit<16> identification; + bit<3> flags; + bit<13> fragOffset; + bit<8> ttl; + bit<8> protocol; + bit<16> hdrChecksum; + bit<32> srcAddr; + bit<32> dstAddr; +} + +struct empty_metadata_t { +} + +struct main_metadata_t { + bit<32> tmpDir; +} + +struct headers_t { + ethernet_t ethernet; + ipv4_t ipv4; +} + +control PreControlImpl(in headers_t hdr, inout main_metadata_t meta, in pna_pre_input_metadata_t istd, inout pna_pre_output_metadata_t ostd) { + apply { + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + meta.tmpDir = hdr.ipv4.srcAddr; + } else { + meta.tmpDir = hdr.ipv4.dstAddr; + } + } +} + +parser MainParserImpl(packet_in pkt, out headers_t hdr, inout main_metadata_t main_meta, in pna_main_parser_input_metadata_t istd) { + state start { + pkt.extract(hdr.ethernet); + transition select(hdr.ethernet.etherType) { + 16w0x800: parse_ipv4; + default: accept; + } + } + state parse_ipv4 { + pkt.extract(hdr.ipv4); + transition select(PNA_Direction_t.NET_TO_HOST == istd.direction) { + true: parse_ipv4_true; + false: parse_ipv4_false; + } + } + state parse_ipv4_true { + transition parse_ipv4_join; + } + state parse_ipv4_false { + transition parse_ipv4_join; + } + state parse_ipv4_join { + transition accept; + } +} + +control MainControlImpl(inout headers_t hdr, inout main_metadata_t user_meta, in pna_main_input_metadata_t istd, inout pna_main_output_metadata_t ostd) { + @name("MainControlImpl.tmpDir") bit<32> tmpDir_1; + @name("MainControlImpl.next_hop") action next_hop_0(@name("vport") PortId_t vport) { + send_to_port(vport); + } + @name("MainControlImpl.default_route_drop") action default_route_drop_0() { + drop_packet(); + } + @name("MainControlImpl.ipv4_da_lpm") table ipv4_da_lpm { + key = { + tmpDir_1: lpm @name("ipv4_addr") ; + } + actions = { + next_hop_0(); + default_route_drop_0(); + } + const default_action = default_route_drop_0(); + } + apply { + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + tmpDir_1 = hdr.ipv4.srcAddr; + } else { + tmpDir_1 = hdr.ipv4.dstAddr; + } + if (hdr.ipv4.isValid()) { + ipv4_da_lpm.apply(); + } + } +} + +control MainDeparserImpl(packet_out pkt, in headers_t hdr, in main_metadata_t user_meta, in pna_main_output_metadata_t ostd) { + apply { + pkt.emit(hdr.ethernet); + pkt.emit(hdr.ipv4); + } +} + +PNA_NIC(MainParserImpl(), PreControlImpl(), MainControlImpl(), MainDeparserImpl()) main; + diff --git a/testdata/p4_16_samples_outputs/pna-direction-main-parser-err-midend.p4 b/testdata/p4_16_samples_outputs/pna-direction-main-parser-err-midend.p4 new file mode 100644 index 00000000000..a4e7f1d5585 --- /dev/null +++ b/testdata/p4_16_samples_outputs/pna-direction-main-parser-err-midend.p4 @@ -0,0 +1,162 @@ +#include +#include + +typedef bit<48> EthernetAddress; +header ethernet_t { + EthernetAddress dstAddr; + EthernetAddress srcAddr; + bit<16> etherType; +} + +header ipv4_t { + bit<4> version; + bit<4> ihl; + bit<8> diffserv; + bit<16> totalLen; + bit<16> identification; + bit<3> flags; + bit<13> fragOffset; + bit<8> ttl; + bit<8> protocol; + bit<16> hdrChecksum; + bit<32> srcAddr; + bit<32> dstAddr; +} + +struct empty_metadata_t { +} + +struct main_metadata_t { + bit<32> tmpDir; +} + +struct headers_t { + ethernet_t ethernet; + ipv4_t ipv4; +} + +control PreControlImpl(in headers_t hdr, inout main_metadata_t meta, in pna_pre_input_metadata_t istd, inout pna_pre_output_metadata_t ostd) { + @hidden action pnadirectionmainparsererr79() { + meta.tmpDir = hdr.ipv4.srcAddr; + } + @hidden action pnadirectionmainparsererr81() { + meta.tmpDir = hdr.ipv4.dstAddr; + } + @hidden table tbl_pnadirectionmainparsererr79 { + actions = { + pnadirectionmainparsererr79(); + } + const default_action = pnadirectionmainparsererr79(); + } + @hidden table tbl_pnadirectionmainparsererr81 { + actions = { + pnadirectionmainparsererr81(); + } + const default_action = pnadirectionmainparsererr81(); + } + apply { + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + tbl_pnadirectionmainparsererr79.apply(); + } else { + tbl_pnadirectionmainparsererr81.apply(); + } + } +} + +parser MainParserImpl(packet_in pkt, out headers_t hdr, inout main_metadata_t main_meta, in pna_main_parser_input_metadata_t istd) { + state start { + pkt.extract(hdr.ethernet); + transition select(hdr.ethernet.etherType) { + 16w0x800: parse_ipv4; + default: accept; + } + } + state parse_ipv4 { + pkt.extract(hdr.ipv4); + transition select((bit<1>)(PNA_Direction_t.NET_TO_HOST == istd.direction)) { + 1w1: parse_ipv4_true; + 1w0: parse_ipv4_false; + default: noMatch; + } + } + state parse_ipv4_true { + transition parse_ipv4_join; + } + state parse_ipv4_false { + transition parse_ipv4_join; + } + state parse_ipv4_join { + transition accept; + } + state noMatch { + verify(false, error.NoMatch); + transition reject; + } +} + +control MainControlImpl(inout headers_t hdr, inout main_metadata_t user_meta, in pna_main_input_metadata_t istd, inout pna_main_output_metadata_t ostd) { + @name("MainControlImpl.tmpDir") bit<32> tmpDir_1; + @name("MainControlImpl.next_hop") action next_hop_0(@name("vport") PortId_t vport) { + send_to_port(vport); + } + @name("MainControlImpl.default_route_drop") action default_route_drop_0() { + drop_packet(); + } + @name("MainControlImpl.ipv4_da_lpm") table ipv4_da_lpm { + key = { + tmpDir_1: lpm @name("ipv4_addr") ; + } + actions = { + next_hop_0(); + default_route_drop_0(); + } + const default_action = default_route_drop_0(); + } + @hidden action pnadirectionmainparsererr138() { + tmpDir_1 = hdr.ipv4.srcAddr; + } + @hidden action pnadirectionmainparsererr140() { + tmpDir_1 = hdr.ipv4.dstAddr; + } + @hidden table tbl_pnadirectionmainparsererr138 { + actions = { + pnadirectionmainparsererr138(); + } + const default_action = pnadirectionmainparsererr138(); + } + @hidden table tbl_pnadirectionmainparsererr140 { + actions = { + pnadirectionmainparsererr140(); + } + const default_action = pnadirectionmainparsererr140(); + } + apply { + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + tbl_pnadirectionmainparsererr138.apply(); + } else { + tbl_pnadirectionmainparsererr140.apply(); + } + if (hdr.ipv4.isValid()) { + ipv4_da_lpm.apply(); + } + } +} + +control MainDeparserImpl(packet_out pkt, in headers_t hdr, in main_metadata_t user_meta, in pna_main_output_metadata_t ostd) { + @hidden action pnadirectionmainparsererr155() { + pkt.emit(hdr.ethernet); + pkt.emit(hdr.ipv4); + } + @hidden table tbl_pnadirectionmainparsererr155 { + actions = { + pnadirectionmainparsererr155(); + } + const default_action = pnadirectionmainparsererr155(); + } + apply { + tbl_pnadirectionmainparsererr155.apply(); + } +} + +PNA_NIC(MainParserImpl(), PreControlImpl(), MainControlImpl(), MainDeparserImpl()) main; + diff --git a/testdata/p4_16_samples_outputs/pna-direction-main-parser-err.p4 b/testdata/p4_16_samples_outputs/pna-direction-main-parser-err.p4 new file mode 100644 index 00000000000..f3965fab658 --- /dev/null +++ b/testdata/p4_16_samples_outputs/pna-direction-main-parser-err.p4 @@ -0,0 +1,106 @@ +#include +#include + +typedef bit<48> EthernetAddress; +header ethernet_t { + EthernetAddress dstAddr; + EthernetAddress srcAddr; + bit<16> etherType; +} + +header ipv4_t { + bit<4> version; + bit<4> ihl; + bit<8> diffserv; + bit<16> totalLen; + bit<16> identification; + bit<3> flags; + bit<13> fragOffset; + bit<8> ttl; + bit<8> protocol; + bit<16> hdrChecksum; + bit<32> srcAddr; + bit<32> dstAddr; +} + +struct empty_metadata_t { +} + +struct main_metadata_t { + bit<32> tmpDir; +} + +struct headers_t { + ethernet_t ethernet; + ipv4_t ipv4; +} + +control PreControlImpl(in headers_t hdr, inout main_metadata_t meta, in pna_pre_input_metadata_t istd, inout pna_pre_output_metadata_t ostd) { + apply { + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + meta.tmpDir = hdr.ipv4.srcAddr; + } else { + meta.tmpDir = hdr.ipv4.dstAddr; + } + } +} + +parser MainParserImpl(packet_in pkt, out headers_t hdr, inout main_metadata_t main_meta, in pna_main_parser_input_metadata_t istd) { + bit<32> tmpDir; + state start { + pkt.extract(hdr.ethernet); + transition select(hdr.ethernet.etherType) { + 0x800: parse_ipv4; + default: accept; + } + } + state parse_ipv4 { + pkt.extract(hdr.ipv4); + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + tmpDir = hdr.ipv4.srcAddr; + } else { + tmpDir = hdr.ipv4.dstAddr; + } + transition accept; + } +} + +control MainControlImpl(inout headers_t hdr, inout main_metadata_t user_meta, in pna_main_input_metadata_t istd, inout pna_main_output_metadata_t ostd) { + bit<32> tmpDir; + action next_hop(PortId_t vport) { + send_to_port(vport); + } + action default_route_drop() { + drop_packet(); + } + table ipv4_da_lpm { + key = { + tmpDir: lpm @name("ipv4_addr") ; + } + actions = { + next_hop; + default_route_drop; + } + const default_action = default_route_drop; + } + apply { + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + tmpDir = hdr.ipv4.srcAddr; + } else { + tmpDir = hdr.ipv4.dstAddr; + } + if (hdr.ipv4.isValid()) { + ipv4_da_lpm.apply(); + } + } +} + +control MainDeparserImpl(packet_out pkt, in headers_t hdr, in main_metadata_t user_meta, in pna_main_output_metadata_t ostd) { + apply { + pkt.emit(hdr.ethernet); + pkt.emit(hdr.ipv4); + } +} + +PNA_NIC(MainParserImpl(), PreControlImpl(), MainControlImpl(), MainDeparserImpl()) main; + diff --git a/testdata/p4_16_samples_outputs/pna-direction-main-parser-err.p4-error b/testdata/p4_16_samples_outputs/pna-direction-main-parser-err.p4-error new file mode 100644 index 00000000000..e69de29bb2d diff --git a/testdata/p4_16_samples_outputs/pna-direction-main-parser-err.p4-stderr b/testdata/p4_16_samples_outputs/pna-direction-main-parser-err.p4-stderr new file mode 100644 index 00000000000..e69de29bb2d diff --git a/testdata/p4_16_samples_outputs/pna-direction-main-parser-err.p4.bfrt.json b/testdata/p4_16_samples_outputs/pna-direction-main-parser-err.p4.bfrt.json new file mode 100644 index 00000000000..13b95e4a64b --- /dev/null +++ b/testdata/p4_16_samples_outputs/pna-direction-main-parser-err.p4.bfrt.json @@ -0,0 +1,61 @@ +{ + "schema_version" : "1.0.0", + "tables" : [ + { + "name" : "pipe.MainControlImpl.ipv4_da_lpm", + "id" : 40097106, + "table_type" : "MatchAction_Direct", + "size" : 1024, + "annotations" : [], + "depends_on" : [], + "has_const_default_action" : true, + "key" : [ + { + "id" : 1, + "name" : "ipv4_addr", + "repeated" : false, + "annotations" : [], + "mandatory" : false, + "match_type" : "LPM", + "type" : { + "type" : "bytes", + "width" : 32 + } + } + ], + "action_specs" : [ + { + "id" : 25584005, + "name" : "MainControlImpl.next_hop", + "action_scope" : "TableAndDefault", + "annotations" : [], + "data" : [ + { + "id" : 1, + "name" : "vport", + "repeated" : false, + "mandatory" : true, + "read_only" : false, + "annotations" : [], + "type" : { + "type" : "bytes", + "width" : 32 + } + } + ] + }, + { + "id" : 19071441, + "name" : "MainControlImpl.default_route_drop", + "action_scope" : "TableAndDefault", + "annotations" : [], + "data" : [] + } + ], + "data" : [], + "supported_operations" : [], + "attributes" : ["EntryScope"] + } + ], + "learn_filters" : [] +} \ No newline at end of file diff --git a/testdata/p4_16_samples_outputs/pna-direction-main-parser-err.p4.spec b/testdata/p4_16_samples_outputs/pna-direction-main-parser-err.p4.spec new file mode 100644 index 00000000000..2711d8b221e --- /dev/null +++ b/testdata/p4_16_samples_outputs/pna-direction-main-parser-err.p4.spec @@ -0,0 +1,106 @@ + +struct ethernet_t { + bit<48> dstAddr + bit<48> srcAddr + bit<16> etherType +} + +struct ipv4_t { + bit<8> version_ihl + bit<8> diffserv + bit<16> totalLen + bit<16> identification + bit<16> flags_fragOffset + bit<8> ttl + bit<8> protocol + bit<16> hdrChecksum + bit<32> srcAddr + bit<32> dstAddr +} + +struct next_hop_0_arg_t { + bit<32> vport +} + +struct main_metadata_t { + bit<32> pna_pre_input_metadata_input_port + bit<32> pna_pre_input_metadata_direction + bit<32> pna_main_parser_input_metadata_direction + bit<32> pna_main_parser_input_metadata_input_port + bit<32> pna_main_input_metadata_input_port + bit<32> local_metadata_tmpDir + bit<32> pna_main_output_metadata_output_port + bit<32> MainParserT_parser_tmp + bit<32> reg_read_tmp + bit<32> left_shift_tmp +} +metadata instanceof main_metadata_t + +header ethernet instanceof ethernet_t +header ipv4 instanceof ipv4_t + +regarray network_port_mask size 0x1 initval 0 + +action next_hop_0 args instanceof next_hop_0_arg_t { + mov m.pna_main_output_metadata_output_port t.vport + return +} + +action default_route_drop_0 args none { + drop + return +} + +table ipv4_da_lpm { + key { + m.local_metadata_tmpDir lpm + } + actions { + next_hop_0 + default_route_drop_0 + } + default_action default_route_drop_0 args none + size 0x10000 +} + + +apply { + rx m.pna_main_input_metadata_input_port + extract h.ethernet + jmpeq MAINPARSERIMPL_PARSE_IPV4 h.ethernet.etherType 0x800 + jmp MAINPARSERIMPL_ACCEPT + MAINPARSERIMPL_PARSE_IPV4 : extract h.ipv4 + jmpeq MAINPARSERIMPL_PARSE_IPV4_TRUE m.MainParserT_parser_tmp 0x1 + jmpeq MAINPARSERIMPL_PARSE_IPV4_FALSE m.MainParserT_parser_tmp 0x0 + jmp MAINPARSERIMPL_NOMATCH + MAINPARSERIMPL_PARSE_IPV4_TRUE : mov m.local_metadata_tmpDir h.ipv4.srcAddr + jmp MAINPARSERIMPL_ACCEPT + MAINPARSERIMPL_PARSE_IPV4_FALSE : regrd m.reg_read_tmp network_port_mask 0x0 + mov m.left_shift_tmp 0x1 + shl m.left_shift_tmp m.pna_main_parser_input_metadata_input_port + mov m.pna_main_parser_input_metadata_direction m.reg_read_tmp + and m.pna_main_parser_input_metadata_direction m.left_shift_tmp + jmpneq LABEL_FALSE 0x0 m.pna_main_parser_input_metadata_direction + mov m.MainParserT_parser_tmp 0x1 + jmp LABEL_END + LABEL_FALSE : mov m.MainParserT_parser_tmp 0x0 + LABEL_END : mov m.local_metadata_tmpDir h.ipv4.dstAddr + jmp MAINPARSERIMPL_ACCEPT + MAINPARSERIMPL_NOMATCH : mov m.pna_pre_input_metadata_parser_error 0x2 + MAINPARSERIMPL_ACCEPT : regrd m.reg_read_tmp network_port_mask 0x0 + mov m.left_shift_tmp 0x1 + shl m.left_shift_tmp m.pna_pre_input_metadata_input_port + mov m.pna_pre_input_metadata_direction m.reg_read_tmp + and m.pna_pre_input_metadata_direction m.left_shift_tmp + jmpneq LABEL_FALSE_0 0x0 m.pna_pre_input_metadata_direction + mov m.local_metadata_tmpDir h.ipv4.srcAddr + jmp LABEL_END_1 + LABEL_FALSE_0 : mov m.local_metadata_tmpDir h.ipv4.dstAddr + LABEL_END_1 : jmpnv LABEL_END_2 h.ipv4 + table ipv4_da_lpm + LABEL_END_2 : emit h.ethernet + emit h.ipv4 + tx m.pna_main_output_metadata_output_port +} + + diff --git a/testdata/p4_16_samples_outputs/pna-direction-midend.p4 b/testdata/p4_16_samples_outputs/pna-direction-midend.p4 new file mode 100644 index 00000000000..1b98cd4673d --- /dev/null +++ b/testdata/p4_16_samples_outputs/pna-direction-midend.p4 @@ -0,0 +1,157 @@ +#include +#include + +typedef bit<48> EthernetAddress; +header ethernet_t { + EthernetAddress dstAddr; + EthernetAddress srcAddr; + bit<16> etherType; +} + +header ipv4_t { + bit<4> version; + bit<4> ihl; + bit<8> diffserv; + bit<16> totalLen; + bit<16> identification; + bit<3> flags; + bit<13> fragOffset; + bit<8> ttl; + bit<8> protocol; + bit<16> hdrChecksum; + bit<32> srcAddr; + bit<32> dstAddr; +} + +struct empty_metadata_t { +} + +struct main_metadata_t { + bit<32> tmpDir; + PNA_Direction_t t1; + bool b; +} + +struct headers_t { + ethernet_t ethernet; + ipv4_t ipv4; +} + +control PreControlImpl(in headers_t hdr, inout main_metadata_t meta, in pna_pre_input_metadata_t istd, inout pna_pre_output_metadata_t ostd) { + @hidden action pnadirection82() { + meta.tmpDir = hdr.ipv4.srcAddr; + } + @hidden action pnadirection84() { + meta.tmpDir = hdr.ipv4.dstAddr; + } + @hidden action pnadirection80() { + meta.b = istd.direction != PNA_Direction_t.NET_TO_HOST; + } + @hidden table tbl_pnadirection80 { + actions = { + pnadirection80(); + } + const default_action = pnadirection80(); + } + @hidden table tbl_pnadirection82 { + actions = { + pnadirection82(); + } + const default_action = pnadirection82(); + } + @hidden table tbl_pnadirection84 { + actions = { + pnadirection84(); + } + const default_action = pnadirection84(); + } + apply { + tbl_pnadirection80.apply(); + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + tbl_pnadirection82.apply(); + } else { + tbl_pnadirection84.apply(); + } + } +} + +parser MainParserImpl(packet_in pkt, out headers_t hdr, inout main_metadata_t main_meta, in pna_main_parser_input_metadata_t istd) { + state start { + pkt.extract(hdr.ethernet); + transition select(hdr.ethernet.etherType) { + 16w0x800: parse_ipv4; + default: accept; + } + } + state parse_ipv4 { + pkt.extract(hdr.ipv4); + transition accept; + } +} + +control MainControlImpl(inout headers_t hdr, inout main_metadata_t user_meta, in pna_main_input_metadata_t istd, inout pna_main_output_metadata_t ostd) { + @name("MainControlImpl.tmpDir") bit<32> tmpDir_0; + @name("MainControlImpl.next_hop") action next_hop(@name("vport") PortId_t vport) { + send_to_port(vport); + } + @name("MainControlImpl.default_route_drop") action default_route_drop() { + drop_packet(); + } + @name("MainControlImpl.ipv4_da_lpm") table ipv4_da_lpm_0 { + key = { + tmpDir_0: lpm @name("ipv4_addr") ; + } + actions = { + next_hop(); + default_route_drop(); + } + const default_action = default_route_drop(); + } + @hidden action pnadirection136() { + tmpDir_0 = hdr.ipv4.srcAddr; + } + @hidden action pnadirection138() { + tmpDir_0 = hdr.ipv4.dstAddr; + } + @hidden table tbl_pnadirection136 { + actions = { + pnadirection136(); + } + const default_action = pnadirection136(); + } + @hidden table tbl_pnadirection138 { + actions = { + pnadirection138(); + } + const default_action = pnadirection138(); + } + apply { + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + tbl_pnadirection136.apply(); + } else { + tbl_pnadirection138.apply(); + } + if (hdr.ipv4.isValid()) { + ipv4_da_lpm_0.apply(); + } + } +} + +control MainDeparserImpl(packet_out pkt, in headers_t hdr, in main_metadata_t user_meta, in pna_main_output_metadata_t ostd) { + @hidden action pnadirection153() { + pkt.emit(hdr.ethernet); + pkt.emit(hdr.ipv4); + } + @hidden table tbl_pnadirection153 { + actions = { + pnadirection153(); + } + const default_action = pnadirection153(); + } + apply { + tbl_pnadirection153.apply(); + } +} + +PNA_NIC(MainParserImpl(), PreControlImpl(), MainControlImpl(), MainDeparserImpl()) main; + diff --git a/testdata/p4_16_samples_outputs/pna-direction.p4 b/testdata/p4_16_samples_outputs/pna-direction.p4 new file mode 100644 index 00000000000..1fa336d3cb3 --- /dev/null +++ b/testdata/p4_16_samples_outputs/pna-direction.p4 @@ -0,0 +1,103 @@ +#include +#include + +typedef bit<48> EthernetAddress; +header ethernet_t { + EthernetAddress dstAddr; + EthernetAddress srcAddr; + bit<16> etherType; +} + +header ipv4_t { + bit<4> version; + bit<4> ihl; + bit<8> diffserv; + bit<16> totalLen; + bit<16> identification; + bit<3> flags; + bit<13> fragOffset; + bit<8> ttl; + bit<8> protocol; + bit<16> hdrChecksum; + bit<32> srcAddr; + bit<32> dstAddr; +} + +struct empty_metadata_t { +} + +struct main_metadata_t { + bit<32> tmpDir; + PNA_Direction_t t1; + bool b; +} + +struct headers_t { + ethernet_t ethernet; + ipv4_t ipv4; +} + +control PreControlImpl(in headers_t hdr, inout main_metadata_t meta, in pna_pre_input_metadata_t istd, inout pna_pre_output_metadata_t ostd) { + apply { + meta.b = istd.direction != PNA_Direction_t.NET_TO_HOST; + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + meta.tmpDir = hdr.ipv4.srcAddr; + } else { + meta.tmpDir = hdr.ipv4.dstAddr; + } + } +} + +parser MainParserImpl(packet_in pkt, out headers_t hdr, inout main_metadata_t main_meta, in pna_main_parser_input_metadata_t istd) { + state start { + pkt.extract(hdr.ethernet); + transition select(hdr.ethernet.etherType) { + 0x800: parse_ipv4; + default: accept; + } + } + state parse_ipv4 { + pkt.extract(hdr.ipv4); + transition accept; + } +} + +control MainControlImpl(inout headers_t hdr, inout main_metadata_t user_meta, in pna_main_input_metadata_t istd, inout pna_main_output_metadata_t ostd) { + bit<32> tmpDir; + action next_hop(PortId_t vport) { + send_to_port(vport); + } + action default_route_drop() { + drop_packet(); + } + table ipv4_da_lpm { + key = { + tmpDir: lpm @name("ipv4_addr") ; + } + actions = { + next_hop; + default_route_drop; + } + const default_action = default_route_drop; + } + apply { + if (PNA_Direction_t.NET_TO_HOST == istd.direction) { + tmpDir = hdr.ipv4.srcAddr; + } else { + tmpDir = hdr.ipv4.dstAddr; + } + if (hdr.ipv4.isValid()) { + ipv4_da_lpm.apply(); + } + } +} + +control MainDeparserImpl(packet_out pkt, in headers_t hdr, in main_metadata_t user_meta, in pna_main_output_metadata_t ostd) { + apply { + pkt.emit(hdr.ethernet); + pkt.emit(hdr.ipv4); + } +} + +PNA_NIC(MainParserImpl(), PreControlImpl(), MainControlImpl(), MainDeparserImpl()) main; + diff --git a/testdata/p4_16_samples_outputs/pna-direction.p4-error b/testdata/p4_16_samples_outputs/pna-direction.p4-error new file mode 100644 index 00000000000..e69de29bb2d diff --git a/testdata/p4_16_samples_outputs/pna-direction.p4-stderr b/testdata/p4_16_samples_outputs/pna-direction.p4-stderr new file mode 100644 index 00000000000..e69de29bb2d diff --git a/testdata/p4_16_samples_outputs/pna-direction.p4.bfrt.json b/testdata/p4_16_samples_outputs/pna-direction.p4.bfrt.json new file mode 100644 index 00000000000..13b95e4a64b --- /dev/null +++ b/testdata/p4_16_samples_outputs/pna-direction.p4.bfrt.json @@ -0,0 +1,61 @@ +{ + "schema_version" : "1.0.0", + "tables" : [ + { + "name" : "pipe.MainControlImpl.ipv4_da_lpm", + "id" : 40097106, + "table_type" : "MatchAction_Direct", + "size" : 1024, + "annotations" : [], + "depends_on" : [], + "has_const_default_action" : true, + "key" : [ + { + "id" : 1, + "name" : "ipv4_addr", + "repeated" : false, + "annotations" : [], + "mandatory" : false, + "match_type" : "LPM", + "type" : { + "type" : "bytes", + "width" : 32 + } + } + ], + "action_specs" : [ + { + "id" : 25584005, + "name" : "MainControlImpl.next_hop", + "action_scope" : "TableAndDefault", + "annotations" : [], + "data" : [ + { + "id" : 1, + "name" : "vport", + "repeated" : false, + "mandatory" : true, + "read_only" : false, + "annotations" : [], + "type" : { + "type" : "bytes", + "width" : 32 + } + } + ] + }, + { + "id" : 19071441, + "name" : "MainControlImpl.default_route_drop", + "action_scope" : "TableAndDefault", + "annotations" : [], + "data" : [] + } + ], + "data" : [], + "supported_operations" : [], + "attributes" : ["EntryScope"] + } + ], + "learn_filters" : [] +} \ No newline at end of file diff --git a/testdata/p4_16_samples_outputs/pna-direction.p4.spec b/testdata/p4_16_samples_outputs/pna-direction.p4.spec new file mode 100644 index 00000000000..0725eac114d --- /dev/null +++ b/testdata/p4_16_samples_outputs/pna-direction.p4.spec @@ -0,0 +1,107 @@ + +struct ethernet_t { + bit<48> dstAddr + bit<48> srcAddr + bit<16> etherType +} + +struct ipv4_t { + bit<8> version_ihl + bit<8> diffserv + bit<16> totalLen + bit<16> identification + bit<16> flags_fragOffset + bit<8> ttl + bit<8> protocol + bit<16> hdrChecksum + bit<32> srcAddr + bit<32> dstAddr +} + +struct next_hop_arg_t { + bit<32> vport +} + +struct main_metadata_t { + bit<32> pna_pre_input_metadata_input_port + bit<32> pna_pre_input_metadata_direction + bit<32> pna_main_input_metadata_direction + bit<32> pna_main_input_metadata_input_port + bit<32> local_metadata_tmpDir + bit<8> local_metadata_b + bit<32> pna_main_output_metadata_output_port + bit<32> MainControlT_tmpDir + bit<32> reg_read_tmp + bit<32> left_shift_tmp +} +metadata instanceof main_metadata_t + +header ethernet instanceof ethernet_t +header ipv4 instanceof ipv4_t + +regarray network_port_mask size 0x1 initval 0 + +action next_hop args instanceof next_hop_arg_t { + mov m.pna_main_output_metadata_output_port t.vport + return +} + +action default_route_drop args none { + drop + return +} + +table ipv4_da_lpm { + key { + m.MainControlT_tmpDir lpm + } + actions { + next_hop + default_route_drop + } + default_action default_route_drop args none + size 0x10000 +} + + +apply { + rx m.pna_main_input_metadata_input_port + extract h.ethernet + jmpeq MAINPARSERIMPL_PARSE_IPV4 h.ethernet.etherType 0x800 + jmp MAINPARSERIMPL_ACCEPT + MAINPARSERIMPL_PARSE_IPV4 : extract h.ipv4 + MAINPARSERIMPL_ACCEPT : regrd m.reg_read_tmp network_port_mask 0x0 + mov m.left_shift_tmp 0x1 + shl m.left_shift_tmp m.pna_pre_input_metadata_input_port + mov m.pna_pre_input_metadata_direction m.reg_read_tmp + and m.pna_pre_input_metadata_direction m.left_shift_tmp + jmpneq LABEL_TRUE m.pna_pre_input_metadata_direction 0x0 + mov m.local_metadata_b 0x0 + jmp LABEL_END + LABEL_TRUE : mov m.local_metadata_b 0x1 + LABEL_END : regrd m.reg_read_tmp network_port_mask 0x0 + mov m.left_shift_tmp 0x1 + shl m.left_shift_tmp m.pna_pre_input_metadata_input_port + mov m.pna_pre_input_metadata_direction m.reg_read_tmp + and m.pna_pre_input_metadata_direction m.left_shift_tmp + jmpneq LABEL_FALSE_0 0x0 m.pna_pre_input_metadata_direction + mov m.local_metadata_tmpDir h.ipv4.srcAddr + jmp LABEL_END_0 + LABEL_FALSE_0 : mov m.local_metadata_tmpDir h.ipv4.dstAddr + LABEL_END_0 : regrd m.reg_read_tmp network_port_mask 0x0 + mov m.left_shift_tmp 0x1 + shl m.left_shift_tmp m.pna_main_input_metadata_input_port + mov m.pna_main_input_metadata_direction m.reg_read_tmp + and m.pna_main_input_metadata_direction m.left_shift_tmp + jmpneq LABEL_FALSE_1 0x0 m.pna_main_input_metadata_direction + mov m.MainControlT_tmpDir h.ipv4.srcAddr + jmp LABEL_END_1 + LABEL_FALSE_1 : mov m.MainControlT_tmpDir h.ipv4.dstAddr + LABEL_END_1 : jmpnv LABEL_END_2 h.ipv4 + table ipv4_da_lpm + LABEL_END_2 : emit h.ethernet + emit h.ipv4 + tx m.pna_main_output_metadata_output_port +} + + diff --git a/testdata/p4_16_samples_outputs/pna-dpdk-parser-state-err.p4.spec b/testdata/p4_16_samples_outputs/pna-dpdk-parser-state-err.p4.spec index 2351ef62513..fe5df671ee3 100644 --- a/testdata/p4_16_samples_outputs/pna-dpdk-parser-state-err.p4.spec +++ b/testdata/p4_16_samples_outputs/pna-dpdk-parser-state-err.p4.spec @@ -69,6 +69,8 @@ header ipv4 instanceof ipv4_t header tcp instanceof tcp_t header MainControlT_hdr_3_tcp instanceof tcp_t +regarray network_port_mask size 0x1 initval 0 + action do_range_checks_1 args instanceof do_range_checks_1_arg_t { mov h.MainControlT_hdr_3_tcp h.tcp jmpgt LABEL_FALSE_2 t.min1 h.MainControlT_hdr_3_tcp.srcPort diff --git a/testdata/p4_16_samples_outputs/pna-dpdk-table-key-use-annon.p4.spec b/testdata/p4_16_samples_outputs/pna-dpdk-table-key-use-annon.p4.spec index 936ae0f967e..da7d00e63f5 100644 --- a/testdata/p4_16_samples_outputs/pna-dpdk-table-key-use-annon.p4.spec +++ b/testdata/p4_16_samples_outputs/pna-dpdk-table-key-use-annon.p4.spec @@ -40,6 +40,8 @@ metadata instanceof main_metadata_t header ethernet instanceof ethernet_t header ipv4 instanceof ipv4_t +regarray network_port_mask size 0x1 initval 0 + action next_hop args instanceof next_hop_arg_t { mov m.pna_main_output_metadata_output_port t.vport return diff --git a/testdata/p4_16_samples_outputs/pna-example-SelectByDirection.p4.spec b/testdata/p4_16_samples_outputs/pna-example-SelectByDirection.p4.spec index 44d0d4baaa7..2f18d2b4286 100644 --- a/testdata/p4_16_samples_outputs/pna-example-SelectByDirection.p4.spec +++ b/testdata/p4_16_samples_outputs/pna-example-SelectByDirection.p4.spec @@ -27,12 +27,16 @@ struct main_metadata_t { bit<32> pna_main_input_metadata_input_port bit<32> pna_main_output_metadata_output_port bit<32> MainControlT_key + bit<32> reg_read_tmp + bit<32> left_shift_tmp } metadata instanceof main_metadata_t header ethernet instanceof ethernet_t header ipv4 instanceof ipv4_t +regarray network_port_mask size 0x1 initval 0 + action next_hop args instanceof next_hop_arg_t { mov m.pna_main_output_metadata_output_port t.vport return @@ -63,6 +67,11 @@ apply { jmp MAINPARSERIMPL_ACCEPT MAINPARSERIMPL_PARSE_IPV4 : extract h.ipv4 MAINPARSERIMPL_ACCEPT : jmpnv LABEL_END h.ipv4 + regrd m.reg_read_tmp network_port_mask 0x0 + mov m.left_shift_tmp 0x1 + shl m.left_shift_tmp m.pna_main_input_metadata_input_port + mov m.pna_main_input_metadata_direction m.reg_read_tmp + and m.pna_main_input_metadata_direction m.left_shift_tmp jmpeq LABEL_TRUE_0 m.pna_main_input_metadata_direction 0x0 mov m.MainControlT_key h.ipv4.dstAddr jmp LABEL_END_0 diff --git a/testdata/p4_16_samples_outputs/pna-example-SelectByDirection1.p4.spec b/testdata/p4_16_samples_outputs/pna-example-SelectByDirection1.p4.spec index 52b18dacb7e..15956360c91 100644 --- a/testdata/p4_16_samples_outputs/pna-example-SelectByDirection1.p4.spec +++ b/testdata/p4_16_samples_outputs/pna-example-SelectByDirection1.p4.spec @@ -27,12 +27,16 @@ struct main_metadata_t { bit<32> pna_main_input_metadata_input_port bit<32> pna_main_output_metadata_output_port bit<32> MainControlT_tmp + bit<32> reg_read_tmp + bit<32> left_shift_tmp } metadata instanceof main_metadata_t header ethernet instanceof ethernet_t header ipv4 instanceof ipv4_t +regarray network_port_mask size 0x1 initval 0 + action next_hop args instanceof next_hop_arg_t { mov m.pna_main_output_metadata_output_port t.vport return @@ -63,6 +67,11 @@ apply { jmp MAINPARSERIMPL_ACCEPT MAINPARSERIMPL_PARSE_IPV4 : extract h.ipv4 MAINPARSERIMPL_ACCEPT : jmpnv LABEL_END h.ipv4 + regrd m.reg_read_tmp network_port_mask 0x0 + mov m.left_shift_tmp 0x1 + shl m.left_shift_tmp m.pna_main_input_metadata_input_port + mov m.pna_main_input_metadata_direction m.reg_read_tmp + and m.pna_main_input_metadata_direction m.left_shift_tmp jmpeq LABEL_TRUE_0 m.pna_main_input_metadata_direction 0x0 mov m.MainControlT_tmp h.ipv4.dstAddr jmp LABEL_END_0 diff --git a/testdata/p4_16_samples_outputs/pna-example-SelectByDirection2.p4.spec b/testdata/p4_16_samples_outputs/pna-example-SelectByDirection2.p4.spec index f017818e68e..aa8234c1eb7 100644 --- a/testdata/p4_16_samples_outputs/pna-example-SelectByDirection2.p4.spec +++ b/testdata/p4_16_samples_outputs/pna-example-SelectByDirection2.p4.spec @@ -28,12 +28,16 @@ struct main_metadata_t { bit<32> local_metadata_meta bit<32> pna_main_output_metadata_output_port bit<32> MainControlT_addr + bit<32> reg_read_tmp + bit<32> left_shift_tmp } metadata instanceof main_metadata_t header ethernet instanceof ethernet_t header ipv4 instanceof ipv4_t +regarray network_port_mask size 0x1 initval 0 + action forward args instanceof forward_arg_t { mov m.local_metadata_meta t.addr return @@ -64,6 +68,11 @@ apply { jmp MAINPARSERIMPL_ACCEPT MAINPARSERIMPL_PARSE_IPV4 : extract h.ipv4 MAINPARSERIMPL_ACCEPT : jmpnv LABEL_END h.ipv4 + regrd m.reg_read_tmp network_port_mask 0x0 + mov m.left_shift_tmp 0x1 + shl m.left_shift_tmp m.pna_main_input_metadata_input_port + mov m.pna_main_input_metadata_direction m.reg_read_tmp + and m.pna_main_input_metadata_direction m.left_shift_tmp jmpeq LABEL_TRUE_0 m.pna_main_input_metadata_direction 0x0 mov m.MainControlT_addr h.ipv4.dstAddr jmp LABEL_END_0 diff --git a/testdata/p4_16_samples_outputs/pna-example-dpdk-varbit.p4.spec b/testdata/p4_16_samples_outputs/pna-example-dpdk-varbit.p4.spec index 8c5a9ca5ad6..32e5f3d9cbe 100644 --- a/testdata/p4_16_samples_outputs/pna-example-dpdk-varbit.p4.spec +++ b/testdata/p4_16_samples_outputs/pna-example-dpdk-varbit.p4.spec @@ -59,6 +59,8 @@ header MainParserT_parser_tmp_hdr instanceof option_t ;oldname:MainParserT_parser_lookahead_tmp header MainParserT_parser_lookahead_0 instanceof lookahead_tmp_hdr +regarray network_port_mask size 0x1 initval 0 + action NoAction args none { return } diff --git a/testdata/p4_16_samples_outputs/pna-example-mirror-packet.p4.spec b/testdata/p4_16_samples_outputs/pna-example-mirror-packet.p4.spec index ce9d2b3c929..ae622c4c823 100644 --- a/testdata/p4_16_samples_outputs/pna-example-mirror-packet.p4.spec +++ b/testdata/p4_16_samples_outputs/pna-example-mirror-packet.p4.spec @@ -35,6 +35,8 @@ struct main_metadata_t { } metadata instanceof main_metadata_t +regarray network_port_mask size 0x1 initval 0 + action NoAction args none { return } diff --git a/testdata/p4_16_samples_outputs/pna-example-template.p4.spec b/testdata/p4_16_samples_outputs/pna-example-template.p4.spec index da270a64826..955d3e5cc82 100644 --- a/testdata/p4_16_samples_outputs/pna-example-template.p4.spec +++ b/testdata/p4_16_samples_outputs/pna-example-template.p4.spec @@ -31,6 +31,8 @@ metadata instanceof main_metadata_t header ethernet instanceof ethernet_t header ipv4 instanceof ipv4_t +regarray network_port_mask size 0x1 initval 0 + action next_hop args instanceof next_hop_arg_t { mov m.pna_main_output_metadata_output_port t.vport return diff --git a/testdata/p4_16_samples_outputs/pna-example-tunnel.p4.spec b/testdata/p4_16_samples_outputs/pna-example-tunnel.p4.spec index 61de18c83c2..2b7a37ef8f1 100644 --- a/testdata/p4_16_samples_outputs/pna-example-tunnel.p4.spec +++ b/testdata/p4_16_samples_outputs/pna-example-tunnel.p4.spec @@ -43,9 +43,13 @@ struct local_metadata_t { bit<32> main_control_tunnel_decap_ipv4_tunnel_term_table_outer_ipv41 ;oldname:main_control_tunnel_decap_ipv4_tunnel_term_table_outer_ipv4_dst_addr bit<32> main_control_tunnel_decap_ipv4_tunnel_term_table_outer_ipv42 + bit<32> reg_read_tmp + bit<32> left_shift_tmp } metadata instanceof local_metadata_t +regarray network_port_mask size 0x1 initval 0 + action NoAction args none { return } @@ -94,7 +98,12 @@ apply { jmpeq PACKET_PARSER_PARSE_IPV4_OTR h.outer_ethernet.ether_type 0x800 jmp PACKET_PARSER_ACCEPT PACKET_PARSER_PARSE_IPV4_OTR : extract h.outer_ipv4 - PACKET_PARSER_ACCEPT : jmpneq LABEL_FALSE m.pna_main_input_metadata_direction 0x0 + PACKET_PARSER_ACCEPT : regrd m.reg_read_tmp network_port_mask 0x0 + mov m.left_shift_tmp 0x1 + shl m.left_shift_tmp m.pna_main_input_metadata_input_port + mov m.pna_main_input_metadata_direction m.reg_read_tmp + and m.pna_main_input_metadata_direction m.left_shift_tmp + jmpneq LABEL_FALSE m.pna_main_input_metadata_direction 0x0 mov m.main_control_tunnel_decap_ipv4_tunnel_term_table_outer_ipv41 h.outer_ipv4.src_addr mov m.main_control_tunnel_decap_ipv4_tunnel_term_table_outer_ipv42 h.outer_ipv4.dst_addr table tunnel_decap_ipv4_tunnel_term_table diff --git a/testdata/p4_16_samples_outputs/pna-extract-local-header.p4.spec b/testdata/p4_16_samples_outputs/pna-extract-local-header.p4.spec index 409fa9af2ae..8a3312ab24a 100644 --- a/testdata/p4_16_samples_outputs/pna-extract-local-header.p4.spec +++ b/testdata/p4_16_samples_outputs/pna-extract-local-header.p4.spec @@ -15,6 +15,8 @@ header h1 instanceof my_header_t header h2 instanceof my_header_t header MainParserT_parser_local_hdr instanceof my_header_t +regarray network_port_mask size 0x1 initval 0 + apply { rx m.pna_main_input_metadata_input_port invalidate h.MainParserT_parser_local_hdr diff --git a/testdata/p4_16_samples_outputs/pna-issue3041.p4.spec b/testdata/p4_16_samples_outputs/pna-issue3041.p4.spec index ff06c8762bc..2f72bc7cbcd 100644 --- a/testdata/p4_16_samples_outputs/pna-issue3041.p4.spec +++ b/testdata/p4_16_samples_outputs/pna-issue3041.p4.spec @@ -54,6 +54,8 @@ header ipv4_base instanceof ipv4_base_t header ipv4_option_timestamp instanceof ipv4_option_timestamp_t header option instanceof option_t +regarray network_port_mask size 0x1 initval 0 + action NoAction args none { return } diff --git a/testdata/p4_16_samples_outputs/pna-lookahead-structure-bit-field.p4.spec b/testdata/p4_16_samples_outputs/pna-lookahead-structure-bit-field.p4.spec index 3e4924110ef..c2432fc152a 100644 --- a/testdata/p4_16_samples_outputs/pna-lookahead-structure-bit-field.p4.spec +++ b/testdata/p4_16_samples_outputs/pna-lookahead-structure-bit-field.p4.spec @@ -25,6 +25,8 @@ header h2 instanceof header2_t ;oldname:MainParserT_parser_lookahead_tmp header MainParserT_parser_lookahead_0 instanceof lookahead_tmp_hdr +regarray network_port_mask size 0x1 initval 0 + apply { rx m.pna_main_input_metadata_input_port lookahead h.MainParserT_parser_lookahead_0 diff --git a/testdata/p4_16_samples_outputs/pna-lookahead-structure.p4.spec b/testdata/p4_16_samples_outputs/pna-lookahead-structure.p4.spec index 31f08717e1e..e20d0b86526 100644 --- a/testdata/p4_16_samples_outputs/pna-lookahead-structure.p4.spec +++ b/testdata/p4_16_samples_outputs/pna-lookahead-structure.p4.spec @@ -34,6 +34,8 @@ header MainParserT_parser_lookahead_0 instanceof lookahead_tmp_hdr ;oldname:MainParserT_parser_lookahead_tmp_0 header MainParserT_parser_lookahead_1 instanceof lookahead_tmp_hdr_0 +regarray network_port_mask size 0x1 initval 0 + apply { rx m.pna_main_input_metadata_input_port lookahead h.MainParserT_parser_lookahead_1 diff --git a/testdata/p4_16_samples_outputs/pna-mux-dismantle.p4.spec b/testdata/p4_16_samples_outputs/pna-mux-dismantle.p4.spec index c185b840d4a..5779a1af083 100644 --- a/testdata/p4_16_samples_outputs/pna-mux-dismantle.p4.spec +++ b/testdata/p4_16_samples_outputs/pna-mux-dismantle.p4.spec @@ -69,6 +69,8 @@ header ipv4 instanceof ipv4_t header tcp instanceof tcp_t header MainControlT_hdr_3_tcp instanceof tcp_t +regarray network_port_mask size 0x1 initval 0 + action do_range_checks_1 args instanceof do_range_checks_1_arg_t { mov h.MainControlT_hdr_3_tcp h.tcp jmpgt LABEL_FALSE_1 t.min1 h.MainControlT_hdr_3_tcp.srcPort diff --git a/testdata/p4_16_samples_outputs/pna-subparser.p4.spec b/testdata/p4_16_samples_outputs/pna-subparser.p4.spec index 1c4c6bddc59..bb1edb4864d 100644 --- a/testdata/p4_16_samples_outputs/pna-subparser.p4.spec +++ b/testdata/p4_16_samples_outputs/pna-subparser.p4.spec @@ -27,6 +27,8 @@ metadata instanceof main_metadata_t header ethernet instanceof ethernet_t header ipv4 instanceof ipv4_t +regarray network_port_mask size 0x1 initval 0 + apply { rx m.pna_main_input_metadata_input_port invalidate h.ethernet