nfp: flower-ct: fill ct metadata check function

Fill in check_meta stub to check that ct_metadata action fields in
the nft flow matches the ct_match data of the post_ct flow.

Signed-off-by: Louis Peens <louis.peens@corigine.com>
Signed-off-by: Yinjun Zhang <yinjun.zhang@corigine.com>
Signed-off-by: Simon Horman <simon.horman@corigine.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
Louis Peens 2021-06-16 12:02:06 +02:00 committed by David S. Miller
parent c698e2adcc
commit 5e5f08168d
1 changed files with 32 additions and 5 deletions

View File

@ -19,6 +19,9 @@ const struct rhashtable_params nfp_nft_ct_merge_params = {
.automatic_shrinking = true,
};
static struct flow_action_entry *get_flow_act(struct flow_rule *rule,
enum flow_action_id act_id);
/**
* get_hashentry() - Wrapper around hashtable lookup.
* @ht: hashtable where entry could be found
@ -258,7 +261,31 @@ static int nfp_ct_merge_act_check(struct nfp_fl_ct_flow_entry *pre_ct_entry,
static int nfp_ct_check_meta(struct nfp_fl_ct_flow_entry *post_ct_entry,
struct nfp_fl_ct_flow_entry *nft_entry)
{
return 0;
struct flow_dissector *dissector = post_ct_entry->rule->match.dissector;
struct flow_action_entry *ct_met;
struct flow_match_ct ct;
int i;
ct_met = get_flow_act(nft_entry->rule, FLOW_ACTION_CT_METADATA);
if (ct_met && (dissector->used_keys & BIT(FLOW_DISSECTOR_KEY_CT))) {
u32 *act_lbl;
act_lbl = ct_met->ct_metadata.labels;
flow_rule_match_ct(post_ct_entry->rule, &ct);
for (i = 0; i < 4; i++) {
if ((ct.key->ct_labels[i] & ct.mask->ct_labels[i]) ^
(act_lbl[i] & ct.mask->ct_labels[i]))
return -EINVAL;
}
if ((ct.key->ct_mark & ct.mask->ct_mark) ^
(ct_met->ct_metadata.mark & ct.mask->ct_mark))
return -EINVAL;
return 0;
}
return -EINVAL;
}
static int nfp_fl_ct_add_offload(struct nfp_fl_nft_tc_merge *m_entry)
@ -727,13 +754,13 @@ void nfp_fl_ct_clean_flow_entry(struct nfp_fl_ct_flow_entry *entry)
kfree(entry);
}
static struct flow_action_entry *get_flow_act(struct flow_cls_offload *flow,
static struct flow_action_entry *get_flow_act(struct flow_rule *rule,
enum flow_action_id act_id)
{
struct flow_action_entry *act = NULL;
int i;
flow_action_for_each(i, act, &flow->rule->action) {
flow_action_for_each(i, act, &rule->action) {
if (act->id == act_id)
return act;
}
@ -791,14 +818,14 @@ int nfp_fl_ct_handle_pre_ct(struct nfp_flower_priv *priv,
struct nfp_fl_ct_zone_entry *zt;
int err;
ct_act = get_flow_act(flow, FLOW_ACTION_CT);
ct_act = get_flow_act(flow->rule, FLOW_ACTION_CT);
if (!ct_act) {
NL_SET_ERR_MSG_MOD(extack,
"unsupported offload: Conntrack action empty in conntrack offload");
return -EOPNOTSUPP;
}
ct_goto = get_flow_act(flow, FLOW_ACTION_GOTO);
ct_goto = get_flow_act(flow->rule, FLOW_ACTION_GOTO);
if (!ct_goto) {
NL_SET_ERR_MSG_MOD(extack,
"unsupported offload: Conntrack requires ACTION_GOTO");