162306a36Sopenharmony_ci/* SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0 */ 262306a36Sopenharmony_ci/* Copyright (c) 2020-2021 Marvell International Ltd. All rights reserved. */ 362306a36Sopenharmony_ci 462306a36Sopenharmony_ci#ifndef _PRESTERA_ACL_H_ 562306a36Sopenharmony_ci#define _PRESTERA_ACL_H_ 662306a36Sopenharmony_ci 762306a36Sopenharmony_ci#include <linux/types.h> 862306a36Sopenharmony_ci#include "prestera_counter.h" 962306a36Sopenharmony_ci 1062306a36Sopenharmony_ci#define PRESTERA_ACL_KEYMASK_PCL_ID 0x3FF 1162306a36Sopenharmony_ci#define PRESTERA_ACL_KEYMASK_PCL_ID_USER \ 1262306a36Sopenharmony_ci (PRESTERA_ACL_KEYMASK_PCL_ID & 0x00FF) 1362306a36Sopenharmony_ci#define PRESTERA_ACL_KEYMASK_PCL_ID_CHAIN \ 1462306a36Sopenharmony_ci (PRESTERA_ACL_KEYMASK_PCL_ID & 0xFF00) 1562306a36Sopenharmony_ci#define PRESTERA_ACL_CHAIN_MASK \ 1662306a36Sopenharmony_ci (PRESTERA_ACL_KEYMASK_PCL_ID >> 8) 1762306a36Sopenharmony_ci 1862306a36Sopenharmony_ci#define PRESTERA_ACL_PCL_ID_MAKE(uid, chain_id) \ 1962306a36Sopenharmony_ci (((uid) & PRESTERA_ACL_KEYMASK_PCL_ID_USER) | \ 2062306a36Sopenharmony_ci (((chain_id) << 8) & PRESTERA_ACL_KEYMASK_PCL_ID_CHAIN)) 2162306a36Sopenharmony_ci 2262306a36Sopenharmony_ci#define rule_match_set_n(match_p, type, val_p, size) \ 2362306a36Sopenharmony_ci memcpy(&(match_p)[PRESTERA_ACL_RULE_MATCH_TYPE_##type], \ 2462306a36Sopenharmony_ci val_p, size) 2562306a36Sopenharmony_ci#define rule_match_set(match_p, type, val) \ 2662306a36Sopenharmony_ci memcpy(&(match_p)[PRESTERA_ACL_RULE_MATCH_TYPE_##type], \ 2762306a36Sopenharmony_ci &(val), sizeof(val)) 2862306a36Sopenharmony_ci 2962306a36Sopenharmony_cienum prestera_acl_match_type { 3062306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_PCL_ID, 3162306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_ETH_TYPE, 3262306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_ETH_DMAC_0, 3362306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_ETH_DMAC_1, 3462306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_ETH_SMAC_0, 3562306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_ETH_SMAC_1, 3662306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_IP_PROTO, 3762306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_SYS_PORT, 3862306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_SYS_DEV, 3962306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_IP_SRC, 4062306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_IP_DST, 4162306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_L4_PORT_SRC, 4262306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_L4_PORT_DST, 4362306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_L4_PORT_RANGE_SRC, 4462306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_L4_PORT_RANGE_DST, 4562306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_VLAN_ID, 4662306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_VLAN_TPID, 4762306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_ICMP_TYPE, 4862306a36Sopenharmony_ci PRESTERA_ACL_RULE_MATCH_TYPE_ICMP_CODE, 4962306a36Sopenharmony_ci 5062306a36Sopenharmony_ci __PRESTERA_ACL_RULE_MATCH_TYPE_MAX 5162306a36Sopenharmony_ci}; 5262306a36Sopenharmony_ci 5362306a36Sopenharmony_cienum prestera_acl_rule_action { 5462306a36Sopenharmony_ci PRESTERA_ACL_RULE_ACTION_ACCEPT = 0, 5562306a36Sopenharmony_ci PRESTERA_ACL_RULE_ACTION_DROP = 1, 5662306a36Sopenharmony_ci PRESTERA_ACL_RULE_ACTION_TRAP = 2, 5762306a36Sopenharmony_ci PRESTERA_ACL_RULE_ACTION_JUMP = 5, 5862306a36Sopenharmony_ci PRESTERA_ACL_RULE_ACTION_COUNT = 7, 5962306a36Sopenharmony_ci PRESTERA_ACL_RULE_ACTION_POLICE = 8, 6062306a36Sopenharmony_ci 6162306a36Sopenharmony_ci PRESTERA_ACL_RULE_ACTION_MAX 6262306a36Sopenharmony_ci}; 6362306a36Sopenharmony_ci 6462306a36Sopenharmony_cienum { 6562306a36Sopenharmony_ci PRESTERA_ACL_IFACE_TYPE_PORT, 6662306a36Sopenharmony_ci PRESTERA_ACL_IFACE_TYPE_INDEX 6762306a36Sopenharmony_ci}; 6862306a36Sopenharmony_ci 6962306a36Sopenharmony_cistruct prestera_acl_match { 7062306a36Sopenharmony_ci __be32 key[__PRESTERA_ACL_RULE_MATCH_TYPE_MAX]; 7162306a36Sopenharmony_ci __be32 mask[__PRESTERA_ACL_RULE_MATCH_TYPE_MAX]; 7262306a36Sopenharmony_ci}; 7362306a36Sopenharmony_ci 7462306a36Sopenharmony_cistruct prestera_acl_action_jump { 7562306a36Sopenharmony_ci u32 index; 7662306a36Sopenharmony_ci}; 7762306a36Sopenharmony_ci 7862306a36Sopenharmony_cistruct prestera_acl_action_police { 7962306a36Sopenharmony_ci u32 id; 8062306a36Sopenharmony_ci}; 8162306a36Sopenharmony_ci 8262306a36Sopenharmony_cistruct prestera_acl_action_count { 8362306a36Sopenharmony_ci u32 id; 8462306a36Sopenharmony_ci}; 8562306a36Sopenharmony_ci 8662306a36Sopenharmony_cistruct prestera_acl_rule_entry_key { 8762306a36Sopenharmony_ci u32 prio; 8862306a36Sopenharmony_ci struct prestera_acl_match match; 8962306a36Sopenharmony_ci}; 9062306a36Sopenharmony_ci 9162306a36Sopenharmony_cistruct prestera_acl_hw_action_info { 9262306a36Sopenharmony_ci enum prestera_acl_rule_action id; 9362306a36Sopenharmony_ci union { 9462306a36Sopenharmony_ci struct prestera_acl_action_police police; 9562306a36Sopenharmony_ci struct prestera_acl_action_count count; 9662306a36Sopenharmony_ci struct prestera_acl_action_jump jump; 9762306a36Sopenharmony_ci }; 9862306a36Sopenharmony_ci}; 9962306a36Sopenharmony_ci 10062306a36Sopenharmony_ci/* This struct (arg) used only to be passed as parameter for 10162306a36Sopenharmony_ci * acl_rule_entry_create. Must be flat. Can contain object keys, which will be 10262306a36Sopenharmony_ci * resolved to object links, before saving to acl_rule_entry struct 10362306a36Sopenharmony_ci */ 10462306a36Sopenharmony_cistruct prestera_acl_rule_entry_arg { 10562306a36Sopenharmony_ci u32 vtcam_id; 10662306a36Sopenharmony_ci struct { 10762306a36Sopenharmony_ci struct { 10862306a36Sopenharmony_ci u8 valid:1; 10962306a36Sopenharmony_ci } accept, drop, trap; 11062306a36Sopenharmony_ci struct { 11162306a36Sopenharmony_ci struct prestera_acl_action_jump i; 11262306a36Sopenharmony_ci u8 valid:1; 11362306a36Sopenharmony_ci } jump; 11462306a36Sopenharmony_ci struct { 11562306a36Sopenharmony_ci u8 valid:1; 11662306a36Sopenharmony_ci u64 rate; 11762306a36Sopenharmony_ci u64 burst; 11862306a36Sopenharmony_ci bool ingress; 11962306a36Sopenharmony_ci } police; 12062306a36Sopenharmony_ci struct { 12162306a36Sopenharmony_ci u8 valid:1; 12262306a36Sopenharmony_ci u32 client; 12362306a36Sopenharmony_ci } count; 12462306a36Sopenharmony_ci }; 12562306a36Sopenharmony_ci}; 12662306a36Sopenharmony_ci 12762306a36Sopenharmony_cistruct prestera_acl_rule { 12862306a36Sopenharmony_ci struct rhash_head ht_node; /* Member of acl HT */ 12962306a36Sopenharmony_ci struct list_head list; 13062306a36Sopenharmony_ci struct prestera_acl_ruleset *ruleset; 13162306a36Sopenharmony_ci struct prestera_acl_ruleset *jump_ruleset; 13262306a36Sopenharmony_ci unsigned long cookie; 13362306a36Sopenharmony_ci u32 chain_index; 13462306a36Sopenharmony_ci u32 priority; 13562306a36Sopenharmony_ci struct prestera_acl_rule_entry_key re_key; 13662306a36Sopenharmony_ci struct prestera_acl_rule_entry_arg re_arg; 13762306a36Sopenharmony_ci struct prestera_acl_rule_entry *re; 13862306a36Sopenharmony_ci}; 13962306a36Sopenharmony_ci 14062306a36Sopenharmony_cistruct prestera_acl_iface { 14162306a36Sopenharmony_ci union { 14262306a36Sopenharmony_ci struct prestera_port *port; 14362306a36Sopenharmony_ci u32 index; 14462306a36Sopenharmony_ci }; 14562306a36Sopenharmony_ci u8 type; 14662306a36Sopenharmony_ci}; 14762306a36Sopenharmony_ci 14862306a36Sopenharmony_cistruct prestera_acl; 14962306a36Sopenharmony_cistruct prestera_switch; 15062306a36Sopenharmony_cistruct prestera_flow_block; 15162306a36Sopenharmony_ci 15262306a36Sopenharmony_ciint prestera_acl_init(struct prestera_switch *sw); 15362306a36Sopenharmony_civoid prestera_acl_fini(struct prestera_switch *sw); 15462306a36Sopenharmony_ci 15562306a36Sopenharmony_cistruct prestera_acl_rule * 15662306a36Sopenharmony_ciprestera_acl_rule_create(struct prestera_acl_ruleset *ruleset, 15762306a36Sopenharmony_ci unsigned long cookie, u32 chain_index); 15862306a36Sopenharmony_civoid prestera_acl_rule_priority_set(struct prestera_acl_rule *rule, 15962306a36Sopenharmony_ci u32 priority); 16062306a36Sopenharmony_civoid prestera_acl_rule_destroy(struct prestera_acl_rule *rule); 16162306a36Sopenharmony_cistruct prestera_acl_rule * 16262306a36Sopenharmony_ciprestera_acl_rule_lookup(struct prestera_acl_ruleset *ruleset, 16362306a36Sopenharmony_ci unsigned long cookie); 16462306a36Sopenharmony_ciint prestera_acl_rule_add(struct prestera_switch *sw, 16562306a36Sopenharmony_ci struct prestera_acl_rule *rule); 16662306a36Sopenharmony_civoid prestera_acl_rule_del(struct prestera_switch *sw, 16762306a36Sopenharmony_ci struct prestera_acl_rule *rule); 16862306a36Sopenharmony_ciint prestera_acl_rule_get_stats(struct prestera_acl *acl, 16962306a36Sopenharmony_ci struct prestera_acl_rule *rule, 17062306a36Sopenharmony_ci u64 *packets, u64 *bytes, u64 *last_use); 17162306a36Sopenharmony_cistruct prestera_acl_rule_entry * 17262306a36Sopenharmony_ciprestera_acl_rule_entry_find(struct prestera_acl *acl, 17362306a36Sopenharmony_ci struct prestera_acl_rule_entry_key *key); 17462306a36Sopenharmony_civoid prestera_acl_rule_entry_destroy(struct prestera_acl *acl, 17562306a36Sopenharmony_ci struct prestera_acl_rule_entry *e); 17662306a36Sopenharmony_cistruct prestera_acl_rule_entry * 17762306a36Sopenharmony_ciprestera_acl_rule_entry_create(struct prestera_acl *acl, 17862306a36Sopenharmony_ci struct prestera_acl_rule_entry_key *key, 17962306a36Sopenharmony_ci struct prestera_acl_rule_entry_arg *arg); 18062306a36Sopenharmony_cistruct prestera_acl_ruleset * 18162306a36Sopenharmony_ciprestera_acl_ruleset_get(struct prestera_acl *acl, 18262306a36Sopenharmony_ci struct prestera_flow_block *block, 18362306a36Sopenharmony_ci u32 chain_index); 18462306a36Sopenharmony_cistruct prestera_acl_ruleset * 18562306a36Sopenharmony_ciprestera_acl_ruleset_lookup(struct prestera_acl *acl, 18662306a36Sopenharmony_ci struct prestera_flow_block *block, 18762306a36Sopenharmony_ci u32 chain_index); 18862306a36Sopenharmony_ciint prestera_acl_ruleset_keymask_set(struct prestera_acl_ruleset *ruleset, 18962306a36Sopenharmony_ci void *keymask); 19062306a36Sopenharmony_cibool prestera_acl_ruleset_is_offload(struct prestera_acl_ruleset *ruleset); 19162306a36Sopenharmony_ciint prestera_acl_ruleset_offload(struct prestera_acl_ruleset *ruleset); 19262306a36Sopenharmony_civoid prestera_acl_ruleset_put(struct prestera_acl_ruleset *ruleset); 19362306a36Sopenharmony_ciint prestera_acl_ruleset_bind(struct prestera_acl_ruleset *ruleset, 19462306a36Sopenharmony_ci struct prestera_port *port); 19562306a36Sopenharmony_ciint prestera_acl_ruleset_unbind(struct prestera_acl_ruleset *ruleset, 19662306a36Sopenharmony_ci struct prestera_port *port); 19762306a36Sopenharmony_ciu32 prestera_acl_ruleset_index_get(const struct prestera_acl_ruleset *ruleset); 19862306a36Sopenharmony_civoid prestera_acl_ruleset_prio_get(struct prestera_acl_ruleset *ruleset, 19962306a36Sopenharmony_ci u32 *prio_min, u32 *prio_max); 20062306a36Sopenharmony_civoid 20162306a36Sopenharmony_ciprestera_acl_rule_keymask_pcl_id_set(struct prestera_acl_rule *rule, 20262306a36Sopenharmony_ci u16 pcl_id); 20362306a36Sopenharmony_ci 20462306a36Sopenharmony_ciint prestera_acl_vtcam_id_get(struct prestera_acl *acl, u8 lookup, u8 dir, 20562306a36Sopenharmony_ci void *keymask, u32 *vtcam_id); 20662306a36Sopenharmony_ciint prestera_acl_vtcam_id_put(struct prestera_acl *acl, u32 vtcam_id); 20762306a36Sopenharmony_ciint prestera_acl_chain_to_client(u32 chain_index, bool ingress, u32 *client); 20862306a36Sopenharmony_ci 20962306a36Sopenharmony_ci#endif /* _PRESTERA_ACL_H_ */ 210