Commit 46be056e authored by Steen Hegelund's avatar Steen Hegelund Committed by David S. Miller

net: microchip: sparx5: Adding port keyset config and callback interface

This provides a default port keyset configuration for the Sparx5 IS2 VCAP
where all ports and all lookups in IS2 use the same keyset (MAC_ETYPE) for
all types of traffic.

This means that no matter what frame type is received on any front port it
will generate the MAC_ETYPE keyset in the IS VCAP and any rule in the IS2
VCAP that uses this keyset will be matched against the keys in the
MAC_ETYPE keyset.

The callback interface used by the VCAP API is populated with Sparx5
specific handler functions that takes care of the actual reading and
writing to data to the Sparx5 IS2 VCAP instance.

A few functions are also added to the VCAP API to support addition of rule
fields such as the ingress port mask and the lookup bit.

The IS2 VCAP in Sparx5 is really divided in two instances with lookup 0
and 1 in the first instance and lookup 2 and 3 in the second instance.
The lookup bit selects lookup 0 or 3 in the respective instance when it is
set.
Signed-off-by: default avatarSteen Hegelund <steen.hegelund@microchip.com>
Tested-by: default avatarCasper Andersson <casper.casan@gmail.com>
Reviewed-by: default avatarCasper Andersson <casper.casan@gmail.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent c9da1ac1
......@@ -21,6 +21,17 @@ struct vcap_rule_internal {
u32 addr; /* address in the VCAP at insertion */
};
/* Return the list of keyfields for the keyset */
static const struct vcap_field *vcap_keyfields(struct vcap_control *vctrl,
enum vcap_type vt,
enum vcap_keyfield_set keyset)
{
/* Check that the keyset exists in the vcap keyset list */
if (keyset >= vctrl->vcaps[vt].keyfield_set_size)
return NULL;
return vctrl->vcaps[vt].keyfield_set_map[keyset];
}
/* Update the keyset for the rule */
int vcap_set_rule_set_keyset(struct vcap_rule *rule,
enum vcap_keyfield_set keyset)
......@@ -227,6 +238,24 @@ int vcap_del_rule(struct vcap_control *vctrl, struct net_device *ndev, u32 id)
}
EXPORT_SYMBOL_GPL(vcap_del_rule);
/* Find information on a key field in a rule */
const struct vcap_field *vcap_lookup_keyfield(struct vcap_rule *rule,
enum vcap_key_field key)
{
struct vcap_rule_internal *ri = (struct vcap_rule_internal *)rule;
enum vcap_keyfield_set keyset = rule->keyset;
enum vcap_type vt = ri->admin->vtype;
const struct vcap_field *fields;
if (keyset == VCAP_KFS_NO_VALUE)
return NULL;
fields = vcap_keyfields(ri->vctrl, vt, keyset);
if (!fields)
return NULL;
return &fields[key];
}
EXPORT_SYMBOL_GPL(vcap_lookup_keyfield);
static void vcap_copy_from_client_keyfield(struct vcap_rule *rule,
struct vcap_client_keyfield *field,
struct vcap_client_keyfield_data *data)
......@@ -253,6 +282,47 @@ static int vcap_rule_add_key(struct vcap_rule *rule,
return 0;
}
static void vcap_rule_set_key_bitsize(struct vcap_u1_key *u1, enum vcap_bit val)
{
switch (val) {
case VCAP_BIT_0:
u1->value = 0;
u1->mask = 1;
break;
case VCAP_BIT_1:
u1->value = 1;
u1->mask = 1;
break;
case VCAP_BIT_ANY:
u1->value = 0;
u1->mask = 0;
break;
}
}
/* Add a bit key with value and mask to the rule */
int vcap_rule_add_key_bit(struct vcap_rule *rule, enum vcap_key_field key,
enum vcap_bit val)
{
struct vcap_client_keyfield_data data;
vcap_rule_set_key_bitsize(&data.u1, val);
return vcap_rule_add_key(rule, key, VCAP_FIELD_BIT, &data);
}
EXPORT_SYMBOL_GPL(vcap_rule_add_key_bit);
/* Add a 32 bit key field with value and mask to the rule */
int vcap_rule_add_key_u32(struct vcap_rule *rule, enum vcap_key_field key,
u32 value, u32 mask)
{
struct vcap_client_keyfield_data data;
data.u32.value = value;
data.u32.mask = mask;
return vcap_rule_add_key(rule, key, VCAP_FIELD_U32, &data);
}
EXPORT_SYMBOL_GPL(vcap_rule_add_key_u32);
/* Add a 48 bit key with value and mask to the rule */
int vcap_rule_add_key_u48(struct vcap_rule *rule, enum vcap_key_field key,
struct vcap_u48_key *fieldval)
......@@ -264,6 +334,17 @@ int vcap_rule_add_key_u48(struct vcap_rule *rule, enum vcap_key_field key,
}
EXPORT_SYMBOL_GPL(vcap_rule_add_key_u48);
/* Add a 72 bit key with value and mask to the rule */
int vcap_rule_add_key_u72(struct vcap_rule *rule, enum vcap_key_field key,
struct vcap_u72_key *fieldval)
{
struct vcap_client_keyfield_data data;
memcpy(&data.u72, fieldval, sizeof(data.u72));
return vcap_rule_add_key(rule, key, VCAP_FIELD_U72, &data);
}
EXPORT_SYMBOL_GPL(vcap_rule_add_key_u72);
static void vcap_copy_from_client_actionfield(struct vcap_rule *rule,
struct vcap_client_actionfield *field,
struct vcap_client_actionfield_data *data)
......
......@@ -174,6 +174,8 @@ int vcap_rule_add_key_u32(struct vcap_rule *rule, enum vcap_key_field key,
u32 value, u32 mask);
int vcap_rule_add_key_u48(struct vcap_rule *rule, enum vcap_key_field key,
struct vcap_u48_key *fieldval);
int vcap_rule_add_key_u72(struct vcap_rule *rule, enum vcap_key_field key,
struct vcap_u72_key *fieldval);
int vcap_rule_add_action_bit(struct vcap_rule *rule,
enum vcap_action_field action, enum vcap_bit val);
int vcap_rule_add_action_u32(struct vcap_rule *rule,
......@@ -182,6 +184,9 @@ int vcap_rule_add_action_u32(struct vcap_rule *rule,
/* VCAP lookup operations */
/* Lookup a vcap instance using chain id */
struct vcap_admin *vcap_find_admin(struct vcap_control *vctrl, int cid);
/* Find information on a key field in a rule */
const struct vcap_field *vcap_lookup_keyfield(struct vcap_rule *rule,
enum vcap_key_field key);
/* Find a rule id with a provided cookie */
int vcap_lookup_rule_by_cookie(struct vcap_control *vctrl, u64 cookie);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment