xref: /openbmc/linux/drivers/net/ethernet/microchip/lan966x/lan966x_tc_matchall.c (revision 9a87ffc99ec8eb8d35eed7c4f816d75f5cc9662e)
15390334bSHoratiu Vultur // SPDX-License-Identifier: GPL-2.0+
25390334bSHoratiu Vultur 
35390334bSHoratiu Vultur #include "lan966x_main.h"
45390334bSHoratiu Vultur 
lan966x_tc_matchall_add(struct lan966x_port * port,struct tc_cls_matchall_offload * f,bool ingress)55390334bSHoratiu Vultur static int lan966x_tc_matchall_add(struct lan966x_port *port,
65390334bSHoratiu Vultur 				   struct tc_cls_matchall_offload *f,
75390334bSHoratiu Vultur 				   bool ingress)
85390334bSHoratiu Vultur {
95390334bSHoratiu Vultur 	struct flow_action_entry *act;
105390334bSHoratiu Vultur 
115390334bSHoratiu Vultur 	if (!flow_offload_has_one_action(&f->rule->action)) {
125390334bSHoratiu Vultur 		NL_SET_ERR_MSG_MOD(f->common.extack,
135390334bSHoratiu Vultur 				   "Only once action per filter is supported");
145390334bSHoratiu Vultur 		return -EOPNOTSUPP;
155390334bSHoratiu Vultur 	}
165390334bSHoratiu Vultur 
175390334bSHoratiu Vultur 	act = &f->rule->action.entries[0];
185390334bSHoratiu Vultur 	switch (act->id) {
195390334bSHoratiu Vultur 	case FLOW_ACTION_POLICE:
205390334bSHoratiu Vultur 		return lan966x_police_port_add(port, &f->rule->action, act,
215390334bSHoratiu Vultur 					       f->cookie, ingress,
225390334bSHoratiu Vultur 					       f->common.extack);
23b69e9539SHoratiu Vultur 	case FLOW_ACTION_MIRRED:
24b69e9539SHoratiu Vultur 		return lan966x_mirror_port_add(port, act, f->cookie,
25b69e9539SHoratiu Vultur 					       ingress, f->common.extack);
2661caac2dSHoratiu Vultur 	case FLOW_ACTION_GOTO:
27*cfd9e7b7SSteen Hegelund 		return lan966x_goto_port_add(port, f->common.chain_index,
28*cfd9e7b7SSteen Hegelund 					     act->chain_index, f->cookie,
2961caac2dSHoratiu Vultur 					     f->common.extack);
305390334bSHoratiu Vultur 	default:
315390334bSHoratiu Vultur 		NL_SET_ERR_MSG_MOD(f->common.extack,
325390334bSHoratiu Vultur 				   "Unsupported action");
335390334bSHoratiu Vultur 		return -EOPNOTSUPP;
345390334bSHoratiu Vultur 	}
355390334bSHoratiu Vultur 
365390334bSHoratiu Vultur 	return 0;
375390334bSHoratiu Vultur }
385390334bSHoratiu Vultur 
lan966x_tc_matchall_del(struct lan966x_port * port,struct tc_cls_matchall_offload * f,bool ingress)395390334bSHoratiu Vultur static int lan966x_tc_matchall_del(struct lan966x_port *port,
405390334bSHoratiu Vultur 				   struct tc_cls_matchall_offload *f,
415390334bSHoratiu Vultur 				   bool ingress)
425390334bSHoratiu Vultur {
435390334bSHoratiu Vultur 	if (f->cookie == port->tc.police_id) {
445390334bSHoratiu Vultur 		return lan966x_police_port_del(port, f->cookie,
455390334bSHoratiu Vultur 					       f->common.extack);
46b69e9539SHoratiu Vultur 	} else if (f->cookie == port->tc.ingress_mirror_id ||
47b69e9539SHoratiu Vultur 		   f->cookie == port->tc.egress_mirror_id) {
48b69e9539SHoratiu Vultur 		return lan966x_mirror_port_del(port, ingress,
49b69e9539SHoratiu Vultur 					       f->common.extack);
505390334bSHoratiu Vultur 	} else {
51*cfd9e7b7SSteen Hegelund 		return lan966x_goto_port_del(port, f->cookie, f->common.extack);
525390334bSHoratiu Vultur 	}
535390334bSHoratiu Vultur 
545390334bSHoratiu Vultur 	return 0;
555390334bSHoratiu Vultur }
565390334bSHoratiu Vultur 
lan966x_tc_matchall_stats(struct lan966x_port * port,struct tc_cls_matchall_offload * f,bool ingress)575390334bSHoratiu Vultur static int lan966x_tc_matchall_stats(struct lan966x_port *port,
585390334bSHoratiu Vultur 				     struct tc_cls_matchall_offload *f,
595390334bSHoratiu Vultur 				     bool ingress)
605390334bSHoratiu Vultur {
615390334bSHoratiu Vultur 	if (f->cookie == port->tc.police_id) {
625390334bSHoratiu Vultur 		lan966x_police_port_stats(port, &f->stats);
63b69e9539SHoratiu Vultur 	} else if (f->cookie == port->tc.ingress_mirror_id ||
64b69e9539SHoratiu Vultur 		   f->cookie == port->tc.egress_mirror_id) {
65b69e9539SHoratiu Vultur 		lan966x_mirror_port_stats(port, &f->stats, ingress);
665390334bSHoratiu Vultur 	} else {
675390334bSHoratiu Vultur 		NL_SET_ERR_MSG_MOD(f->common.extack,
685390334bSHoratiu Vultur 				   "Unsupported action");
695390334bSHoratiu Vultur 		return -EOPNOTSUPP;
705390334bSHoratiu Vultur 	}
715390334bSHoratiu Vultur 
725390334bSHoratiu Vultur 	return 0;
735390334bSHoratiu Vultur }
745390334bSHoratiu Vultur 
lan966x_tc_matchall(struct lan966x_port * port,struct tc_cls_matchall_offload * f,bool ingress)755390334bSHoratiu Vultur int lan966x_tc_matchall(struct lan966x_port *port,
765390334bSHoratiu Vultur 			struct tc_cls_matchall_offload *f,
775390334bSHoratiu Vultur 			bool ingress)
785390334bSHoratiu Vultur {
795390334bSHoratiu Vultur 	switch (f->command) {
805390334bSHoratiu Vultur 	case TC_CLSMATCHALL_REPLACE:
815390334bSHoratiu Vultur 		return lan966x_tc_matchall_add(port, f, ingress);
825390334bSHoratiu Vultur 	case TC_CLSMATCHALL_DESTROY:
835390334bSHoratiu Vultur 		return lan966x_tc_matchall_del(port, f, ingress);
845390334bSHoratiu Vultur 	case TC_CLSMATCHALL_STATS:
855390334bSHoratiu Vultur 		return lan966x_tc_matchall_stats(port, f, ingress);
865390334bSHoratiu Vultur 	default:
875390334bSHoratiu Vultur 		return -EOPNOTSUPP;
885390334bSHoratiu Vultur 	}
895390334bSHoratiu Vultur 
905390334bSHoratiu Vultur 	return 0;
915390334bSHoratiu Vultur }
92