TNSM_Latency_Prediction / code / descarter / switch.p4
switch.p4
Raw
/* -*- P4_16 -*- */

#include <core.p4>
#include <tna.p4>

/*************************************************************************
 ************* C O N S T A N T S    A N D   T Y P E S  *******************
**************************************************************************/
const bit<16> ETHERTYPE_TPID = 0x8100;
const bit<16> ETHERTYPE_IPV4 = 0x0800;
const bit<16> ETHERTYPE_TEST = 0xABCD;
const bit<8> PROTOCOL_UDP = 0x11;



const bit<48> ENCAP_MAC_SRC = 0xac1f6b62b9fe;
const bit<48> ENCAP_MAC_DST = 0xac1f6b62b967;
const bit<32> ENCAP_IP_SRC = 0x0A620BFE; // 192.168.11.254
const bit<32> ENCAP_IP_DST = 0x0A620B04; // 192.168.11.4
const bit<16> ENCAP_UDP_DST = 0xD431; //54321


/* Table Sizes */
const int IPV4_HOST_SIZE = 65536;
const int IPV4_LPM_SIZE  = 12288;

/*************************************************************************
 ***********************  H E A D E R S  *********************************
 *************************************************************************/

/*  Define all the headers the program will recognize             */
/*  The actual sets of headers processed by each gress can differ */

/* Standard ethernet header */
header ethernet_h {
    bit<48>   dstAddr;
    bit<48>   srcAddr;
    bit<16>   etherType;
}

header ipv4_h {
    bit<4>    version;
    bit<4>    ihl;
    bit<6>    dscp;
    bit<2>    ecn;
    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;
}//20 bytes

header udp_h {
    bit<16> srcPort;
    bit<16> dstPort;
    bit<16> _length;
    bit<16> checksum;
}

/* Timestamping headers */
header timestamps_ingress_h {
    bit<48> ts2;
    bit<48> ts1;
}

header timestamps_egress_h {
    bit<48> ts5;
    bit<24> ts4;
    bit<24> ts3;
}

header timestamp_ts6_h {
    bit<48> value;
    bit<16> decimal;
}

/*************************************************************************
 **************  I N G R E S S   P R O C E S S I N G   *******************
 *************************************************************************/
 
    /***********************  H E A D E R S  ************************/

struct my_ingress_headers_t {
    ethernet_h            ethernet;
    timestamp_ts6_h       ts6;
    timestamps_egress_h   ts_egress;
    timestamps_ingress_h  ts_ingress;
}

    /******  G L O B A L   I N G R E S S   M E T A D A T A  *********/

struct my_ingress_metadata_t {
}

    /***********************  P A R S E R  **************************/
parser IngressParser(packet_in        pkt,
    /* User */    
    out my_ingress_headers_t          hdr,
    out my_ingress_metadata_t         meta,
    /* Intrinsic */
    out ingress_intrinsic_metadata_t  ig_intr_md)
{
    /* This is a mandatory state, required by Tofino Architecture */
     state start {
        pkt.extract(ig_intr_md);
        pkt.advance(PORT_METADATA_SIZE);
        transition parse_ethernet;
    }

    state parse_ethernet {
        pkt.extract(hdr.ethernet);
        transition parse_ts;
    }

    state parse_ts {
        pkt.extract(hdr.ts6);
        pkt.extract(hdr.ts_egress);
        pkt.extract(hdr.ts_ingress);
        transition accept;
    }

}

    /***************** M A T C H - A C T I O N  *********************/

control Ingress(
    /* User */
    inout my_ingress_headers_t                       hdr,
    inout my_ingress_metadata_t                      meta,
    /* Intrinsic */
    in    ingress_intrinsic_metadata_t               ig_intr_md,
    in    ingress_intrinsic_metadata_from_parser_t   ig_prsr_md,
    inout ingress_intrinsic_metadata_for_deparser_t  ig_dprsr_md,
    inout ingress_intrinsic_metadata_for_tm_t        ig_tm_md)
{

    Random<bit<10>>() randomNum;


    action drop_pkt() {
        ig_dprsr_md.drop_ctl = 1;
    }    

    /*action setBoundaries(bit<10> b) {
        maxNum = b;
    }

    table setUpSampling_t {
        key     = {
        }
        actions = { 
            setBoundaries; 
        }
        default_action = setBoundaries(102);
        size           = 1;
    }*/


    apply {

        
        if(hdr.ethernet.etherType != 0xabcd){
            drop_pkt();
        }else{

            bit<10> num = randomNum.get();

#ifdef PERCENT_10
// When sending 100 million packets
// 0-1023, 1024/10=102.4, 0 to 101.4, choosing 102, just over 10%
            if (num <= 102){ 
#elif PERCENT_1
// When sending billion packets
// 0-1023, 1024/10=10.24, 0 to 9.24, choosing 10, just over 1%
            if (num <= 10){
#endif
                ig_tm_md.ucast_egress_port = (bit<9>)2;
            }else{
                drop_pkt();
            }

        }        

        //setUpSampling_t.apply();

    }    

}


/*********************  D E P A R S E R  ************************/

control IngressDeparser(packet_out pkt,
    /* User */
    inout my_ingress_headers_t                       hdr,
    in    my_ingress_metadata_t                      meta,
    /* Intrinsic */
    in    ingress_intrinsic_metadata_for_deparser_t  ig_dprsr_md)
{
    apply {
        pkt.emit(hdr);
    }
}


/*************************************************************************
 ****************  E G R E S S   P R O C E S S I N G   *******************
 *************************************************************************/

    /***********************  H E A D E R S  ************************/

struct my_egress_headers_t {
    ethernet_h            outer_ethernet;
    ipv4_h                outer_ipv4;
    udp_h                 outer_udp;
    timestamp_ts6_h       ts6;
    timestamps_egress_h   ts_egress;
    timestamps_ingress_h  ts_ingress;
    ethernet_h            ethernet;
}

    /********  G L O B A L   E G R E S S   M E T A D A T A  *********/

struct my_egress_metadata_t {
}

    /***********************  P A R S E R  **************************/

parser EgressParser(packet_in        pkt,
    /* User */
    out my_egress_headers_t          hdr,
    out my_egress_metadata_t         meta,
    /* Intrinsic */
    out egress_intrinsic_metadata_t  eg_intr_md)
{
    /* This is a mandatory state, required by Tofino Architecture */
    state start {
        pkt.extract(eg_intr_md);
        transition parse_ethernet;
    }

    state parse_ethernet {
        pkt.extract(hdr.ethernet);
        transition parse_ts;
    }

    state parse_ts {
        pkt.extract(hdr.ts6);
        pkt.extract(hdr.ts_egress);
        pkt.extract(hdr.ts_ingress);
        transition accept;
    }

}

    /***************** M A T C H - A C T I O N  *********************/

control Egress(
    /* User */
    inout my_egress_headers_t                          hdr,
    inout my_egress_metadata_t                         meta,
    /* Intrinsic */    
    in    egress_intrinsic_metadata_t                  eg_intr_md,
    in    egress_intrinsic_metadata_from_parser_t      eg_prsr_md,
    inout egress_intrinsic_metadata_for_deparser_t     eg_dprsr_md,
    inout egress_intrinsic_metadata_for_output_port_t  eg_oport_md)
{

    Random<bit<16>>() randomPort;

    action encap(){

        hdr.outer_ethernet.setValid();
        hdr.outer_ethernet.srcAddr = ENCAP_MAC_SRC; 
        hdr.outer_ethernet.dstAddr = ENCAP_MAC_DST;
        hdr.outer_ethernet.etherType = ETHERTYPE_IPV4;

        hdr.outer_ipv4.setValid();
        hdr.outer_ipv4.version = 4;
        hdr.outer_ipv4.ihl = 5;
        hdr.outer_ipv4.dscp = 0;
        hdr.outer_ipv4.ecn = 0;
        hdr.outer_ipv4.totalLen = eg_intr_md.pkt_length + 24;
        hdr.outer_ipv4.identification = 0xabcd;
        hdr.outer_ipv4.flags = 4;
        hdr.outer_ipv4.fragOffset = 0;
        hdr.outer_ipv4.ttl = 31;
        hdr.outer_ipv4.hdrChecksum = 0;
        hdr.outer_ipv4.protocol = PROTOCOL_UDP;
        hdr.outer_ipv4.srcAddr = ENCAP_IP_SRC;
        hdr.outer_ipv4.dstAddr = ENCAP_IP_DST;

        hdr.outer_udp.setValid();
        hdr.outer_udp.srcPort = 0;
        hdr.outer_udp.dstPort = ENCAP_UDP_DST;
        hdr.outer_udp._length = eg_intr_md.pkt_length + 4;
        hdr.outer_udp.checksum = 0;        
    }


    table encapsulate_t {
        key = {
        }
        actions = {
            encap;
            NoAction;
        }
        default_action = encap;
        size           = 1;
    }


    apply {
        encapsulate_t.apply();

        bit<16> port = randomPort.get();
        hdr.outer_udp.srcPort = port;
    }
}

    /*********************  D E P A R S E R  ************************/

control EgressDeparser(packet_out                   pkt,
    /* User */
    inout my_egress_headers_t                       hdr,
    in    my_egress_metadata_t                      meta,
    /* Intrinsic */
    in    egress_intrinsic_metadata_for_deparser_t  eg_dprsr_md)
{
    Checksum() ipv4_checksum;

    apply {

        hdr.outer_ipv4.hdrChecksum = ipv4_checksum.update({
            hdr.outer_ipv4.version,
            hdr.outer_ipv4.ihl,
            hdr.outer_ipv4.dscp,
            hdr.outer_ipv4.ecn,
            hdr.outer_ipv4.totalLen,
            hdr.outer_ipv4.identification,
            hdr.outer_ipv4.flags,
            hdr.outer_ipv4.fragOffset,
            hdr.outer_ipv4.ttl,
            hdr.outer_ipv4.protocol,
            hdr.outer_ipv4.srcAddr,
            hdr.outer_ipv4.dstAddr
        });

        pkt.emit(hdr.outer_ethernet);
        pkt.emit(hdr.outer_ipv4);
        pkt.emit(hdr.outer_udp);
        pkt.emit(hdr.ts6);
        pkt.emit(hdr.ts_egress);
        pkt.emit(hdr.ts_ingress);
        pkt.emit(hdr.ethernet);
    }
}


/************ F I N A L   P A C K A G E ******************************/
Pipeline(
    IngressParser(),
    Ingress(),
    IngressDeparser(),
    EgressParser(),
    Egress(),
    EgressDeparser()
) pipe;

Switch(pipe) main;