int receive(int port_num, const char *buffer, int len) { static int pkt_id = 0; auto packet = new_packet_ptr(port_num, pkt_id++, len, PacketBuffer(2048, buffer, len)); ELOGGER->packet_in(*packet); input_buffer.push_front(std::move(packet)); return 0; }
int SimpleSwitch::receive(int port_num, const char *buffer, int len) { static int pkt_id = 0; // this is a good place to call this, because blocking this thread will not // block the processing of existing packet instances, which is a requirement if (do_swap() == 0) { check_queueing_metadata(); } // we limit the packet buffer to original size + 512 bytes, which means we // cannot add more than 512 bytes of header data to the packet, which should // be more than enough auto packet = new_packet_ptr(port_num, pkt_id++, len, bm::PacketBuffer(len + 512, buffer, len)); BMELOG(packet_in, *packet); PHV *phv = packet->get_phv(); // many current P4 programs assume this // it is also part of the original P4 spec phv->reset_metadata(); // setting standard metadata phv->get_field("standard_metadata.ingress_port").set(port_num); // using packet register 0 to store length, this register will be updated for // each add_header / remove_header primitive call packet->set_register(PACKET_LENGTH_REG_IDX, len); phv->get_field("standard_metadata.packet_length").set(len); Field &f_instance_type = phv->get_field("standard_metadata.instance_type"); f_instance_type.set(PKT_INSTANCE_TYPE_NORMAL); if (phv->has_field("intrinsic_metadata.ingress_global_timestamp")) { phv->get_field("intrinsic_metadata.ingress_global_timestamp") .set(get_ts().count()); } input_buffer.push_front(std::move(packet)); return 0; }