net: mscc: ocelot: offload redirect action to VCAP IS2
Via the OCELOT_MASK_MODE_REDIRECT flag put in the IS2 action vector, it is possible to replace previous forwarding decisions with the port mask installed in this rule. I have studied Table 54 "MASK_MODE and PORT_MASK Combinations" from the VSC7514 documentation and it appears to behave sanely when this rule is installed in either lookup 0 or 1. Namely, a redirect in lookup 1 will overwrite the forwarding decision taken by any entry in lookup 0. Signed-off-by: Vladimir Oltean <vladimir.oltean@nxp.com> Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
parent
f854e6f6f4
commit
16a7a15f4b
@ -142,14 +142,15 @@ ocelot_find_vcap_filter_that_points_at(struct ocelot *ocelot, int chain)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static int ocelot_flower_parse_action(struct flow_cls_offload *f, bool ingress,
|
||||
static int ocelot_flower_parse_action(struct ocelot *ocelot, bool ingress,
|
||||
struct flow_cls_offload *f,
|
||||
struct ocelot_vcap_filter *filter)
|
||||
{
|
||||
struct netlink_ext_ack *extack = f->common.extack;
|
||||
bool allow_missing_goto_target = false;
|
||||
const struct flow_action_entry *a;
|
||||
enum ocelot_tag_tpid_sel tpid;
|
||||
int i, chain;
|
||||
int i, chain, egress_port;
|
||||
u64 rate;
|
||||
|
||||
if (!flow_action_basic_hw_stats_check(&f->rule->action,
|
||||
@ -224,6 +225,27 @@ static int ocelot_flower_parse_action(struct flow_cls_offload *f, bool ingress,
|
||||
filter->action.pol.burst = a->police.burst;
|
||||
filter->type = OCELOT_VCAP_FILTER_OFFLOAD;
|
||||
break;
|
||||
case FLOW_ACTION_REDIRECT:
|
||||
if (filter->block_id != VCAP_IS2) {
|
||||
NL_SET_ERR_MSG_MOD(extack,
|
||||
"Redirect action can only be offloaded to VCAP IS2");
|
||||
return -EOPNOTSUPP;
|
||||
}
|
||||
if (filter->goto_target != -1) {
|
||||
NL_SET_ERR_MSG_MOD(extack,
|
||||
"Last action must be GOTO");
|
||||
return -EOPNOTSUPP;
|
||||
}
|
||||
egress_port = ocelot->ops->netdev_to_port(a->dev);
|
||||
if (egress_port < 0) {
|
||||
NL_SET_ERR_MSG_MOD(extack,
|
||||
"Destination not an ocelot port");
|
||||
return -EOPNOTSUPP;
|
||||
}
|
||||
filter->action.mask_mode = OCELOT_MASK_MODE_REDIRECT;
|
||||
filter->action.port_mask = BIT(egress_port);
|
||||
filter->type = OCELOT_VCAP_FILTER_OFFLOAD;
|
||||
break;
|
||||
case FLOW_ACTION_VLAN_POP:
|
||||
if (filter->block_id != VCAP_IS1) {
|
||||
NL_SET_ERR_MSG_MOD(extack,
|
||||
@ -579,7 +601,7 @@ static int ocelot_flower_parse(struct ocelot *ocelot, int port, bool ingress,
|
||||
filter->prio = f->common.prio;
|
||||
filter->id = f->cookie;
|
||||
|
||||
ret = ocelot_flower_parse_action(f, ingress, filter);
|
||||
ret = ocelot_flower_parse_action(ocelot, ingress, f, filter);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user