net: mscc: ocelot: offload tc action "ok" using an empty action vector
authorVladimir Oltean <vladimir.oltean@nxp.com>
Sun, 22 May 2022 09:27:01 +0000 (12:27 +0300)
committerDavid S. Miller <davem@davemloft.net>
Sun, 22 May 2022 21:15:19 +0000 (22:15 +0100)
The "ok" tc action is useful when placed in front of a more generic
filter to exclude some more specific rules from matching it.

The ocelot switches can offload this tc action by creating an empty
action vector (no _ENA fields set to 1). This makes sense for all of
VCAP IS1, IS2 and ES0 (but not for PSFP).

Add support for this action. Note that this makes the
gact_drop_and_ok_test() selftest pass, where "action ok" is used in
front of an "action drop" rule, both offloaded to VCAP IS2.

Signed-off-by: Vladimir Oltean <vladimir.oltean@nxp.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
drivers/net/ethernet/mscc/ocelot_flower.c

index 51cf241..7c0897e 100644 (file)
@@ -279,6 +279,22 @@ static int ocelot_flower_parse_action(struct ocelot *ocelot, int port,
                        filter->action.pol_ix = OCELOT_POLICER_DISCARD;
                        filter->type = OCELOT_VCAP_FILTER_OFFLOAD;
                        break;
+               case FLOW_ACTION_ACCEPT:
+                       if (filter->block_id != VCAP_ES0 &&
+                           filter->block_id != VCAP_IS1 &&
+                           filter->block_id != VCAP_IS2) {
+                               NL_SET_ERR_MSG_MOD(extack,
+                                                  "Accept action can only be offloaded to VCAP chains");
+                               return -EOPNOTSUPP;
+                       }
+                       if (filter->block_id != VCAP_ES0 &&
+                           filter->goto_target != -1) {
+                               NL_SET_ERR_MSG_MOD(extack,
+                                                  "Last action must be GOTO");
+                               return -EOPNOTSUPP;
+                       }
+                       filter->type = OCELOT_VCAP_FILTER_OFFLOAD;
+                       break;
                case FLOW_ACTION_TRAP:
                        if (filter->block_id != VCAP_IS2 ||
                            filter->lookup != 0) {