I've figured out the mac issue, Using the _fmt_str = '!HIIIH16s6B24sQ6x' and byte array for mac although the pdp_start_epoch is still way off for some reason, any ideas? Thanks, Nick
On Fri, Jun 19, 2020 at 3:42 PM Nick <urchen...@gmail.com> wrote: > Hi, > > I'm trying to modify the NXActionSample2 action and wanted to ask for your > help. Basically I have an OVS patch that modifies the Sampling action and > adds a few custom fields. I currently use it with ovs-ofctl, but It would > be great if I can just modify Ryu to accept the new args. > > I've initially posted this question on this github issue > https://github.com/faucetsdn/ryu/issues/104, it's easier to read there > due to code blocks. > > Here is my ovs-ofctl > ``` > sudo ovs-ofctl add-flow cwag_br0 > "table=15,priority=12,metadata=0x75945885e85,actions=sample(probability=600,collector_set_id=1,obs_domain_id=1,obs_point_id=1,apn_mac_addr=58:bc:27:13:31:50,msisdn=5101006096,apn_name=\"cwc > wifi offload\",pdp_start_epoch=100,sampling_port=gre0),resubmit(,20)" > ``` > > Here is the corresponding OVS flow it creates > ``` > cookie=0x0, duration=33.792s, table=15, n_packets=0, n_bytes=0, > priority=12,metadata=0x75945885e85 > actions=sample(probability=600,collector_set_id=1,obs_domain_id=1,obs_point_id=1,pdp_start_epoch=100,apn_mac_addr=58:bc:27:13:31:50,msisdn=5101006096,apn_name="cwc > wifi offload",sampling_port=gre0),resubmit(,20) > ``` > > The added fields from the standard Sample action are: > ``` > msisdn: > apn_mac_addr > apn_name > pdp_start_epoch > ``` > Here is the struct in ovs: > ``` > struct nx_action_sample2 { > ovs_be16 type; /* OFPAT_VENDOR. */ > ovs_be16 len; /* Length is 32. */ > ovs_be32 vendor; /* NX_VENDOR_ID. */ > ovs_be16 subtype; /* NXAST_SAMPLE. */ > ovs_be16 probability; /* Fraction of packets to sample. */ > ovs_be32 collector_set_id; /* ID of collector set in OVSDB. */ > ovs_be32 obs_domain_id; /* ID of sampling observation domain. > */ > ovs_be32 obs_point_id; /* ID of sampling observation point. */ > ovs_be16 sampling_port; /* Sampling port. */ > uint8_t msisdn[16]; > struct eth_addr apn_mac_addr; > uint8_t apn_name[24]; > uint64_t pdp_start_epoch; > uint8_t direction; /* NXAST_SAMPLE3 only. */ > uint8_t zeros[5]; /* Pad to a multiple of 8 bytes */ > }; > OFP_ASSERT(sizeof(struct nx_action_sample2) == 88); > > /* not sure if this is requried */ > struct ofpact_sample { > OFPACT_PADDED_MEMBERS( > struct ofpact ofpact; > uint16_t probability; /* Always positive. */ > uint32_t collector_set_id; > uint32_t obs_domain_id; > uint32_t obs_point_id; > ofp_port_t sampling_port; > enum nx_action_sample_direction direction; > uint8_t msisdn[16]; > struct eth_addr apn_mac_addr; > uint8_t apn_name[24]; > uint64_t pdp_start_epoch; > ); > }; > ``` > > Currently with some hacking I've achieved this with RYU: > > ``` > parser.NXActionSample2( > probability=self.ipfix_config.probability, > collector_set_id=self.ipfix_config.collector_set_id, > obs_domain_id=self.ipfix_config.obs_domain_id, > obs_point_id=self.ipfix_config.obs_point_id, > apn_mac_addr="0a0027000005", > msisdn="5101006096", apn_name="cwc wifi offload", > pdp_start_epoch=100, > sampling_port=32768, > ) > > cookie=0x0, duration=11.112s, table=203, n_packets=0, n_bytes=0, > priority=12 > actions=sample(probability=65535,collector_set_id=1,obs_domain_id=1,obs_point_id=1,pdp_start_epoch=7205759403792793600,apn_mac_addr=30:61:30:30:32:37,msisdn=5101006096,apn_name="cwc > wifi > offload",sampling_port=gre0),resubmit(,16),set_field:0->reg0,set_field:0->reg3 > ``` > All the fields are correct except the `pdp_start_epoch` and > `apn_mac_addr`. I assume its because I messed up the struct packing as I'm > not sure how to properly pack/encode the mac addr. Here is the relevant RYU > code ( I've tried using `ofp.oxm_from_user_header, > ofp.oxm_serialize_header` functions but didn't get anywhere so just > encoding to ascii worked best for me. > > ``` > > class NXActionSample2(NXAction): > > _subtype = nicira_ext.NXAST_SAMPLE2 > > # probability, collector_set_id, obs_domain_id, > # obs_point_id, msisdn, apn_mac_addr, apn_name, sampling_port > _fmt_str = '!HIIIH16s6s24sQ6x' > > def __init__(self, > probability, > msisdn, > apn_mac_addr, > apn_name, > pdp_start_epoch, > collector_set_id=0, > obs_domain_id=0, > obs_point_id=0, > sampling_port=0, > type_=None, len_=None, experimenter=None, > subtype=None): > super(NXActionSample2, self).__init__() > self.probability = probability > self.collector_set_id = collector_set_id > self.obs_domain_id = obs_domain_id > self.obs_point_id = obs_point_id > > self.msisdn = msisdn.encode('ascii') > self.apn_mac_addr = apn_mac_addr.encode('ascii') > self.apn_name = apn_name.encode('ascii') > self.pdp_start_epoch = pdp_start_epoch > > self.sampling_port = sampling_port > > @classmethod > def parser(cls, buf): > (probability, > collector_set_id, > obs_domain_id, > obs_point_id, > sampling_port, > msisdn, > apn_mac_addr, > apn_name, > pdp_start_epoch) = struct.unpack_from( > cls._fmt_str, buf, 0) > > return cls(probability, > msisdn, > apn_mac_addr, > apn_name, > pdp_start_epoch, > collector_set_id, > obs_domain_id, > obs_point_id, > sampling_port) > > def serialize_body(self): > data = bytearray() > msg_pack_into(self._fmt_str, data, 0, > self.probability, > self.collector_set_id, > self.obs_domain_id, > self.obs_point_id, > self.sampling_port, > self.msisdn, > self.apn_mac_addr, > self.apn_name, > self.pdp_start_epoch) > return data > > ``` > > Would really appreciate your help, thank you! > > Thanks, > Nick >
_______________________________________________ Ryu-devel mailing list Ryu-devel@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/ryu-devel