/* * Copyright 2020-present Nehal Baganal * * 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 #include "header.p4" #include "CoDel.p4" parser SwitchIngressParser(packet_in packet, out headers_t hdr, out my_metadata_t meta, out ingress_intrinsic_metadata_t ig_intr_md) { state start { packet.extract(ig_intr_md); packet.advance(PORT_METADATA_SIZE); transition parse_ethernet; } state parse_ethernet{ packet.extract(hdr.ethernet); transition select(hdr.ethernet.etherType) { ether_type_t.IPV4: parse_ipv4; default: accept; } } state parse_ipv4 { packet.extract(hdr.ipv4); transition select(hdr.ipv4.frag_offset, hdr.ipv4.protocol, hdr.ipv4.ihl){ (0, ip_proto_t.ICMP, 5) : parse_icmp; (0, ip_proto_t.TCP, 5) : parse_tcp; (0, ip_proto_t.UDP, 5) : parse_udp; ( _, _, _ ) : accept; } } state parse_tcp { packet.extract(hdr.tcp); //tcp_checksum.subtract({hdr.tcp.checksum}); transition select(hdr.tcp.data_offset){ 4w0x5: parse_tcp_no_opt; 4w0x6: parse_tcp_opt_32b; 4w0x7: parse_tcp_opt_64b; 4w0x8: parse_tcp_opt_96b; 4w0x9: parse_tcp_opt_128b; 4w0xA: parse_tcp_opt_160b; 4w0xB: parse_tcp_opt_192b; 4w0xC: parse_tcp_opt_224b; 4w0xD: parse_tcp_opt_256b; 4w0xE: parse_tcp_opt_288b; 4w0xF: parse_tcp_opt_320b; default: accept; } } state parse_tcp_no_opt { transition parse_my_tstamp; } state parse_tcp_opt_32b { packet.extract(hdr.tcp_opt[0]); transition parse_my_tstamp; } state parse_tcp_opt_64b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); transition parse_my_tstamp; } state parse_tcp_opt_96b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); packet.extract(hdr.tcp_opt[2]); transition parse_my_tstamp; } state parse_tcp_opt_128b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); packet.extract(hdr.tcp_opt[2]); packet.extract(hdr.tcp_opt[3]); transition parse_my_tstamp; } state parse_tcp_opt_160b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); packet.extract(hdr.tcp_opt[2]); packet.extract(hdr.tcp_opt[3]); packet.extract(hdr.tcp_opt[4]); transition parse_my_tstamp; } state parse_tcp_opt_192b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); packet.extract(hdr.tcp_opt[2]); packet.extract(hdr.tcp_opt[3]); packet.extract(hdr.tcp_opt[4]); packet.extract(hdr.tcp_opt[5]); transition parse_my_tstamp; } state parse_tcp_opt_224b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); packet.extract(hdr.tcp_opt[2]); packet.extract(hdr.tcp_opt[3]); packet.extract(hdr.tcp_opt[4]); packet.extract(hdr.tcp_opt[5]); packet.extract(hdr.tcp_opt[6]); transition parse_my_tstamp; } state parse_tcp_opt_256b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); packet.extract(hdr.tcp_opt[2]); packet.extract(hdr.tcp_opt[3]); packet.extract(hdr.tcp_opt[4]); packet.extract(hdr.tcp_opt[5]); packet.extract(hdr.tcp_opt[6]); packet.extract(hdr.tcp_opt[7]); transition parse_my_tstamp; } state parse_tcp_opt_288b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); packet.extract(hdr.tcp_opt[2]); packet.extract(hdr.tcp_opt[3]); packet.extract(hdr.tcp_opt[4]); packet.extract(hdr.tcp_opt[5]); packet.extract(hdr.tcp_opt[6]); packet.extract(hdr.tcp_opt[7]); packet.extract(hdr.tcp_opt[8]); transition parse_my_tstamp; } state parse_tcp_opt_320b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); packet.extract(hdr.tcp_opt[2]); packet.extract(hdr.tcp_opt[3]); packet.extract(hdr.tcp_opt[4]); packet.extract(hdr.tcp_opt[5]); packet.extract(hdr.tcp_opt[6]); packet.extract(hdr.tcp_opt[7]); packet.extract(hdr.tcp_opt[8]); packet.extract(hdr.tcp_opt[9]); transition parse_my_tstamp; } state parse_my_tstamp { //packet.extract(hdr.my_tstamp); //tcp_checksum.subtract({hdr.my_tstamp.drop_tstamp_high}); //tcp_checksum.subtract({hdr.my_tstamp.drop_tstamp_low}); //tcp_checksum.subtract_all_and_deposit(meta.bridged_metadata.temp_tcp_checksum); transition accept; } state parse_icmp { packet.extract(hdr.icmp); transition accept; } state parse_udp { packet.extract(hdr.udp); transition accept; } } control SwitchIngress( inout headers_t hdr, inout my_metadata_t meta, in ingress_intrinsic_metadata_t ig_intr_md, in ingress_intrinsic_metadata_from_parser_t ig_intr_parser_md, inout ingress_intrinsic_metadata_for_deparser_t ig_intr_md_for_dprsr, inout ingress_intrinsic_metadata_for_tm_t ig_intr_tm_md) { action send(bit<9> egress_port) { ig_intr_tm_md.ucast_egress_port = egress_port; } table t_l1_forwarding { key = { hdr.ipv4.dst_addr : exact; //ig_intr_md.ingress_port : exact; } actions = { send; } size = 64; } apply { t_l1_forwarding.apply(); ig_intr_tm_md.qid = 0; meta.bridged_metadata.setValid(); meta.bridged_metadata.ingress_tstamp = ig_intr_parser_md.global_tstamp; meta.bridged_metadata.ingress_port = hdr.ipv4.protocol; meta.bridged_metadata.drop_counter_result = hdr.ipv4.ihl; meta.bridged_metadata.temp_frag_offset = hdr.ipv4.frag_offset; } } control SwitchIngressDeparser(packet_out packet, inout headers_t hdr, in my_metadata_t meta, in ingress_intrinsic_metadata_for_deparser_t ig_dprsr_md) { //Checksum() ipv4_checksum; //Checksum() tcp_checksum; apply { /* if (hdr.ipv4.isValid()) { hdr.ipv4.hdr_checksum = ipv4_checksum.update({ hdr.ipv4.version, hdr.ipv4.ihl, hdr.ipv4.diffserv, hdr.ipv4.ECN, hdr.ipv4.total_len, hdr.ipv4.identification, hdr.ipv4.flags, hdr.ipv4.frag_offset, hdr.ipv4.ttl, hdr.ipv4.protocol, hdr.ipv4.hdr_checksum, hdr.ipv4.src_addr, hdr.ipv4.dst_addr }); } if (hdr.tcp.isValid()) { hdr.tcp.checksum = tcp_checksum.update({ hdr.tcp.src_port, hdr.tcp.dst_port, hdr.tcp.seq_no, hdr.tcp.ack_no, hdr.tcp.data_offset, hdr.tcp.res, hdr.tcp.CWR, hdr.tcp.ECE, hdr.tcp.URG, hdr.tcp.ACK, hdr.tcp.PSH, hdr.tcp.RST, hdr.tcp.SYN, hdr.tcp.FIN, hdr.tcp.window, hdr.tcp.checksum, hdr.tcp.urgent_ptr, hdr.my_tstamp.drop_flag, hdr.my_tstamp.drop_tstamp_high, hdr.my_tstamp.drop_tstamp_low }); }*/ packet.emit(meta.bridged_metadata); packet.emit(hdr); } } parser SwitchEgressParser(packet_in packet, out headers_t hdr, out my_metadata_t meta, out egress_intrinsic_metadata_t eg_intr_md) { state start { packet.extract(eg_intr_md); packet.extract(meta.bridged_metadata); transition parse_ethernet; } state parse_ethernet{ packet.extract(hdr.ethernet); transition select(hdr.ethernet.etherType) { ether_type_t.IPV4: parse_ipv4; default: accept; } } state parse_ipv4 { packet.extract(hdr.ipv4); transition select(hdr.ipv4.frag_offset, hdr.ipv4.protocol, hdr.ipv4.ihl){ (0, ip_proto_t.TCP, 5) : parse_tcp; //(0, ip_proto_t.ICMP, 5) : parse_icmp; //(0, ip_proto_t.UDP, 5) : parse_udp; ( _, _, _ ) : accept; } } state parse_icmp { packet.extract(hdr.icmp); transition accept; } state parse_tcp { packet.extract(hdr.tcp); //tcp_checksum.subtract({hdr.tcp.checksum}); transition select(hdr.tcp.data_offset){ 4w0x5: parse_tcp_no_opt; 4w0x6: parse_tcp_opt_32b; 4w0x7: parse_tcp_opt_64b; 4w0x8: parse_tcp_opt_96b; 4w0x9: parse_tcp_opt_128b; 4w0xA: parse_tcp_opt_160b; 4w0xB: parse_tcp_opt_192b; 4w0xC: parse_tcp_opt_224b; 4w0xD: parse_tcp_opt_256b; 4w0xE: parse_tcp_opt_288b; 4w0xF: parse_tcp_opt_320b; default: accept; } } state parse_tcp_no_opt { transition parse_my_tstamp; } state parse_tcp_opt_32b { packet.extract(hdr.tcp_opt[0]); transition parse_my_tstamp; } state parse_tcp_opt_64b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); transition parse_my_tstamp; } state parse_tcp_opt_96b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); packet.extract(hdr.tcp_opt[2]); transition parse_my_tstamp; } state parse_tcp_opt_128b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); packet.extract(hdr.tcp_opt[2]); packet.extract(hdr.tcp_opt[3]); transition parse_my_tstamp; } state parse_tcp_opt_160b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); packet.extract(hdr.tcp_opt[2]); packet.extract(hdr.tcp_opt[3]); packet.extract(hdr.tcp_opt[4]); transition parse_my_tstamp; } state parse_tcp_opt_192b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); packet.extract(hdr.tcp_opt[2]); packet.extract(hdr.tcp_opt[3]); packet.extract(hdr.tcp_opt[4]); packet.extract(hdr.tcp_opt[5]); transition parse_my_tstamp; } state parse_tcp_opt_224b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); packet.extract(hdr.tcp_opt[2]); packet.extract(hdr.tcp_opt[3]); packet.extract(hdr.tcp_opt[4]); packet.extract(hdr.tcp_opt[5]); packet.extract(hdr.tcp_opt[6]); transition parse_my_tstamp; } state parse_tcp_opt_256b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); packet.extract(hdr.tcp_opt[2]); packet.extract(hdr.tcp_opt[3]); packet.extract(hdr.tcp_opt[4]); packet.extract(hdr.tcp_opt[5]); packet.extract(hdr.tcp_opt[6]); packet.extract(hdr.tcp_opt[7]); transition parse_my_tstamp; } state parse_tcp_opt_288b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); packet.extract(hdr.tcp_opt[2]); packet.extract(hdr.tcp_opt[3]); packet.extract(hdr.tcp_opt[4]); packet.extract(hdr.tcp_opt[5]); packet.extract(hdr.tcp_opt[6]); packet.extract(hdr.tcp_opt[7]); packet.extract(hdr.tcp_opt[8]); transition parse_my_tstamp; } state parse_tcp_opt_320b { packet.extract(hdr.tcp_opt[0]); packet.extract(hdr.tcp_opt[1]); packet.extract(hdr.tcp_opt[2]); packet.extract(hdr.tcp_opt[3]); packet.extract(hdr.tcp_opt[4]); packet.extract(hdr.tcp_opt[5]); packet.extract(hdr.tcp_opt[6]); packet.extract(hdr.tcp_opt[7]); packet.extract(hdr.tcp_opt[8]); packet.extract(hdr.tcp_opt[9]); transition parse_my_tstamp; } state parse_my_tstamp { //packet.extract(hdr.my_tstamp); //tcp_checksum.subtract({hdr.my_tstamp.drop_tstamp_high}); //tcp_checksum.subtract({hdr.my_tstamp.drop_tstamp_low}); //tcp_checksum.subtract_all_and_deposit(meta.bridged_metadata.temp_tcp_checksum); transition accept; } state parse_udp { packet.extract(hdr.udp); transition accept; } } control SwitchEgress( inout headers_t hdr, inout my_metadata_t meta, in egress_intrinsic_metadata_t eg_intr_md, in egress_intrinsic_metadata_from_parser_t eg_intr_parser_md, inout egress_intrinsic_metadata_for_deparser_t eg_intr_md_for_dprsr, inout egress_intrinsic_metadata_for_output_port_t eg_intr_md_for_oport) { CoDelEgress() codel_egress; apply{ codel_egress.apply( meta.bridged_metadata.ingress_tstamp, eg_intr_parser_md.global_tstamp, eg_intr_md.egress_port, hdr, eg_intr_md_for_dprsr); } } control SwitchEgressDeparser(packet_out packet, inout headers_t hdr, in my_metadata_t meta, in egress_intrinsic_metadata_for_deparser_t eg_dprsr_md) { Checksum() ipv4_checksum; //Checksum() tcp_checksum; apply { if (hdr.ipv4.isValid()) { hdr.ipv4.hdr_checksum = ipv4_checksum.update({ hdr.ipv4.version, hdr.ipv4.ihl, hdr.ipv4.diffserv, hdr.ipv4.ECN, hdr.ipv4.total_len, hdr.ipv4.identification, hdr.ipv4.flags, hdr.ipv4.frag_offset, hdr.ipv4.ttl, hdr.ipv4.protocol, hdr.ipv4.src_addr, hdr.ipv4.dst_addr }); } /*if (hdr.tcp.isValid()) { hdr.tcp.checksum = tcp_checksum.update({ hdr.tcp.src_port, hdr.tcp.dst_port, hdr.tcp.seq_no, hdr.tcp.ack_no, hdr.tcp.data_offset, hdr.tcp.res, hdr.tcp.CWR, hdr.tcp.ECE, hdr.tcp.URG, hdr.tcp.ACK, hdr.tcp.PSH, hdr.tcp.RST, hdr.tcp.SYN, hdr.tcp.FIN, hdr.tcp.window, hdr.tcp.checksum, hdr.tcp.urgent_ptr, hdr.my_tstamp.drop_flag, hdr.my_tstamp.drop_tstamp_high, hdr.my_tstamp.drop_tstamp_low }); }*/ //packet.emit(meta.bridged_metadata); packet.emit(hdr); } } Pipeline(SwitchIngressParser(), SwitchIngress(), SwitchIngressDeparser(), SwitchEgressParser(), SwitchEgress(), SwitchEgressDeparser()) pipe; Switch(pipe) main;