Hi, This patchset introduces a kernel intermediate representation (IR) to express ACL hardware offloads, this is heavily based on the existing flow dissector infrastructure and the TC actions. This IR can be used by different frontend ACL interfaces such as ethtool_rxnfc, tc and netfilter to represent ACL hardware offloads.
The main goals of this patchset are: * Provide an unified representation that can be passed to the driver for translation to HW IR. This consolidates the code to be maintained in the driver and it also simplifies the development of ACL hardware offloads. Driver developers do not need to add one specific parser for each supported ACL frontend, instead each frontend just generates this flow_rule IR and pass it to drivers to populate the hardware IR. * Do not expose TC software frontend details to the drivers anymore, such as structure layouts. Hence, if TC needs to be updated to support a new software feature, no changes to the drivers will be required. In handcrafted ascii art, the idea is the following: . ethtool_rxnfc tc netfilter | (ioctl) (netlink) (netlink) | | | | translate native Frontend | | | | interface representation | | | | to flow_rule IR | | | | . \/ \/ \/ . ----- flow_rule IR ------ | | Drivers | | parsing of flow_rule IR | | to populate hardware IR | \/ . hardware IR (driver) This patchset only converts tc and ethtool_rxnfc to use this infrastructure. Therefore. this patchset comes with no netfilter changes at this stage. The proposed object that represents rules is the following: struct flow_rule { struct flow_match match; struct flow_action action; }; The flow_match structure wraps Jiri Pirko's existing representation available in cls_flower based on flow dissectors to represent the matching side: struct flow_match { struct flow_dissector *dissector; void *mask; void *key; }; The mask and key layouts are opaque, given the dissector object provides the used_keys flags - to check for rule selectors that are being used - and the offset to the corresponding key and mask in the opaque container structures. Then, the actions to be performed on the matching packets is represented through the flow_action object: struct flow_action { unsigned int num_entries; struct flow_action_entry entries[0]; }; This object comes with a num_entries field that specifies the number of actions - this supports an arbitrary number of actions, the driver will impose its own restrictions on this - and the array that stores flow_action_entries structures (entries). Each flow action entry is defined as it follows: struct flow_action_entry { enum flow_action_id id; union { u32 chain_index; /* FLOW_ACTION_GOTO */ struct net_device *dev; /* FLOW_ACTION_REDIRECT */ struct { /* FLOW_ACTION_VLAN */ u16 vid; __be16 proto; u8 prio; } vlan; struct { /* FLOW_ACTION_PACKET_EDIT */ enum flow_action_mangle_base htype; u32 offset; u32 mask; u32 val; } mangle; const struct ip_tunnel_info *tunnel; /* FLOW_ACTION_TUNNEL_ENCAP */ u32 csum_flags; /* FLOW_ACTION_CSUM */ u32 mark; /* FLOW_ACTION_MARK */ struct { /* FLOW_ACTION_QUEUE */ u32 ctx; u32 index; u8 vf; } queue; }; }; Possible actions are extracted from what existing drivers are already supporting through tc-flower and ethtool_rxnfc interfaces: enum flow_action_id { FLOW_ACTION_ACCEPT = 0, FLOW_ACTION_DROP, FLOW_ACTION_TRAP, FLOW_ACTION_GOTO, FLOW_ACTION_REDIRECT, FLOW_ACTION_MIRRED, FLOW_ACTION_VLAN_PUSH, FLOW_ACTION_VLAN_POP, FLOW_ACTION_VLAN_MANGLE, FLOW_ACTION_TUNNEL_ENCAP, FLOW_ACTION_TUNNEL_DECAP, FLOW_ACTION_MANGLE, FLOW_ACTION_ADD, FLOW_ACTION_CSUM, FLOW_ACTION_MARK, FLOW_ACTION_WAKE, FLOW_ACTION_QUEUE, }; Common code pattern from the drivers to populate the hardware intermediate representation looks like this: if (flow_rule_match_key(rule, FLOW_DISSECTOR_KEY_IPV4_ADDRS)) { struct flow_match_ipv4_addrs match; flow_rule_match_ipv4_addrs(rule, &match); flow->l3_key.ipv4.daddr.s_addr = match.key->dst; flow->l3_mask.ipv4.daddr.s_addr = match.mask->dst; flow->l3_key.ipv4.saddr.s_addr = match.key->src; flow->l3_mask.ipv4.saddr.s_addr = match.mask->src; } Then, flow action code parser should look like: flow_action_for_each(i, act, flow_action) { switch (act->id) { case FLOW_ACTION_DROP: actions->flags |= DRIVER_XYZ_ACTION_FLAG_DROP; break; case ...: break; default: return -EOPNOTSUPP; } } This new infrastructure resides in: net/core/flow_offload.c include/net/flow_offload.h net/core/ethtool.c (translator from ethtool_rxnfc to flow_rule) This patchset is composed of 12 patches: Patch #1 adds the flow_match structure, this includes the flow_rule_match_key() interface to check for existing selectors that are in used in the rule and the flow_rule_match_*() functions to fetch the selector value and the mask. This also introduces the initial flow_rule structure skeleton to avoid a follow up patch that would update the same LoCs. Patch #2 makes changes to packet edit parser of mlx5e driver, to prepare introduction of the new flow_action to mangle packets. Patch #3 Introduce flow_action infrastructure. This infrastructure is based on the TC actions. Patch #8 extends it so it also supports two new actions that are only available through the ethtool_rxnfc interface. Patch #4 Add function to translate TC action to flow_action from cls_flower. Patch #5 Add infrastructure to fetch statistics into container structure and synchronize them to TC actions from cls_flower. Another preparation patch before patch #7, so we can stop exposing the TC action native layout to the drivers. Patch #6 Use flow_action infrastructure from drivers. Patch #7 Do not expose TC actions to drivers anymore, now that drivers have been converted to use the flow_action infrastructure after patch #6. Patch #8 Support for wake-up-on-lan and queue actions for the flow_action infrastructure, two actions supported by the ethtool_rxnfc interface. Patch #9 Add a function to translate from ethtool_rx_flow_spec structure to the flow_action structure. This function maps the ethtool_rxnfc structure to flow_rule. This function resides in net/core/ethtool.c Patch #10 Use ethtool_rxnfc to flow_rule from bcm_sf2 driver. Patch #11 A preparation patch for the qlogic/qede driver coming at #12. Patch #12 Update qlogic/qede driver to use the flow_rule infrastructure. This removes the duplicated parser for ethtool_rxnfc by using flow_rule structure. Please apply, thanks! P.S: Moving forward, my rough plan is to propose and discuss the following changes to use this infrastructure from netfilter for ACL hardware offload: * Rename tc_setup ndo to flow_offload (or similar), so it can be used from netfilter too. Otherwise, I'm open for alternatives. * Add a conversion function from native netfilter representation to flow_rule, including extra new glue code from the two-phase commit protocol to integrate this infrastructure. Pablo Neira Ayuso (12): flow_offload: add flow_rule and flow_match structures and use them net/mlx5e: support for two independent packet edit actions flow_offload: add flow action infrastructure cls_api: add translator to flow_action representation flow_offload: add statistics retrieval infrastructure and use it drivers: net: use flow action infrastructure cls_flower: don't expose TC actions to drivers anymore flow_offload: add wake-up-on-lan and queue to flow_action ethtool: add ethtool_rx_flow_spec to flow_rule structure translator dsa: bcm_sf2: use flow_rule infrastructure qede: place ethtool_rx_flow_spec after code after TC flower codebase qede: use ethtool_rx_flow_rule() to remove duplicated parser code drivers/net/dsa/bcm_sf2_cfp.c | 102 +-- drivers/net/ethernet/broadcom/bnxt/bnxt_tc.c | 252 ++++---- .../net/ethernet/chelsio/cxgb4/cxgb4_tc_flower.c | 450 ++++++------- drivers/net/ethernet/intel/i40e/i40e_main.c | 178 ++---- drivers/net/ethernet/intel/iavf/iavf_main.c | 195 +++--- drivers/net/ethernet/intel/igb/igb_main.c | 64 +- .../net/ethernet/mellanox/mlx5/core/en/tc_tun.c | 68 +- drivers/net/ethernet/mellanox/mlx5/core/en_tc.c | 697 ++++++++++----------- drivers/net/ethernet/mellanox/mlxsw/spectrum_acl.c | 2 +- .../net/ethernet/mellanox/mlxsw/spectrum_flower.c | 258 ++++---- drivers/net/ethernet/netronome/nfp/flower/action.c | 198 +++--- drivers/net/ethernet/netronome/nfp/flower/match.c | 417 ++++++------ .../net/ethernet/netronome/nfp/flower/offload.c | 150 ++--- drivers/net/ethernet/qlogic/qede/qede_filter.c | 572 +++++++---------- include/linux/ethtool.h | 15 + include/net/flow_offload.h | 203 ++++++ include/net/pkt_cls.h | 18 +- net/core/Makefile | 2 +- net/core/ethtool.c | 241 +++++++ net/core/flow_offload.c | 153 +++++ net/sched/cls_api.c | 116 ++++ net/sched/cls_flower.c | 71 ++- 22 files changed, 2416 insertions(+), 2006 deletions(-) create mode 100644 include/net/flow_offload.h create mode 100644 net/core/flow_offload.c -- 2.11.0