[PATCH net-next v3 03/10] net/sched: cls_flower: prepare fl_{set,dump}_key_flags() for ENC_FLAGS

Asbjørn Sloth Tønnesen posted 10 patches 1 year, 7 months ago
There is a newer version of this series
[PATCH net-next v3 03/10] net/sched: cls_flower: prepare fl_{set,dump}_key_flags() for ENC_FLAGS
Posted by Asbjørn Sloth Tønnesen 1 year, 7 months ago
Prepare fl_set_key_flags/fl_dump_key_flags() for use with
TCA_FLOWER_KEY_ENC_FLAGS{,_MASK}.

This patch adds an encap argument, similar to fl_set_key_ip/
fl_dump_key_ip(), and determine the flower keys based on the
encap argument, and use them in the rest of the two functions.

Since these functions are so far, only called with encap set false,
then there is no functional change.

Signed-off-by: Asbjørn Sloth Tønnesen <ast@fiberby.net>
Tested-by: Davide Caratti <dcaratti@redhat.com>
---
 net/sched/cls_flower.c | 40 ++++++++++++++++++++++++++++++----------
 1 file changed, 30 insertions(+), 10 deletions(-)

diff --git a/net/sched/cls_flower.c b/net/sched/cls_flower.c
index eef570c577ac7..6a5cecfd95619 100644
--- a/net/sched/cls_flower.c
+++ b/net/sched/cls_flower.c
@@ -1166,19 +1166,28 @@ static void fl_set_key_flag(u32 flower_key, u32 flower_mask,
 	}
 }
 
-static int fl_set_key_flags(struct nlattr **tb, u32 *flags_key,
+static int fl_set_key_flags(struct nlattr **tb, bool encap, u32 *flags_key,
 			    u32 *flags_mask, struct netlink_ext_ack *extack)
 {
+	int fl_key, fl_mask;
 	u32 key, mask;
 
+	if (encap) {
+		fl_key = TCA_FLOWER_KEY_ENC_FLAGS;
+		fl_mask = TCA_FLOWER_KEY_ENC_FLAGS_MASK;
+	} else {
+		fl_key = TCA_FLOWER_KEY_FLAGS;
+		fl_mask = TCA_FLOWER_KEY_FLAGS_MASK;
+	}
+
 	/* mask is mandatory for flags */
-	if (!tb[TCA_FLOWER_KEY_FLAGS_MASK]) {
+	if (NL_REQ_ATTR_CHECK(extack, NULL, tb, fl_mask)) {
 		NL_SET_ERR_MSG(extack, "Missing flags mask");
 		return -EINVAL;
 	}
 
-	key = be32_to_cpu(nla_get_be32(tb[TCA_FLOWER_KEY_FLAGS]));
-	mask = be32_to_cpu(nla_get_be32(tb[TCA_FLOWER_KEY_FLAGS_MASK]));
+	key = be32_to_cpu(nla_get_be32(tb[fl_key]));
+	mask = be32_to_cpu(nla_get_be32(tb[fl_mask]));
 
 	*flags_key  = 0;
 	*flags_mask = 0;
@@ -2086,7 +2095,7 @@ static int fl_set_key(struct net *net, struct nlattr **tb,
 		return ret;
 
 	if (tb[TCA_FLOWER_KEY_FLAGS]) {
-		ret = fl_set_key_flags(tb, &key->control.flags,
+		ret = fl_set_key_flags(tb, false, &key->control.flags,
 				       &mask->control.flags, extack);
 		if (ret)
 			return ret;
@@ -3084,12 +3093,22 @@ static void fl_get_key_flag(u32 dissector_key, u32 dissector_mask,
 	}
 }
 
-static int fl_dump_key_flags(struct sk_buff *skb, u32 flags_key, u32 flags_mask)
+static int fl_dump_key_flags(struct sk_buff *skb, bool encap,
+			     u32 flags_key, u32 flags_mask)
 {
-	u32 key, mask;
+	int fl_key, fl_mask;
 	__be32 _key, _mask;
+	u32 key, mask;
 	int err;
 
+	if (encap) {
+		fl_key = TCA_FLOWER_KEY_ENC_FLAGS;
+		fl_mask = TCA_FLOWER_KEY_ENC_FLAGS_MASK;
+	} else {
+		fl_key = TCA_FLOWER_KEY_FLAGS;
+		fl_mask = TCA_FLOWER_KEY_FLAGS_MASK;
+	}
+
 	if (!memchr_inv(&flags_mask, 0, sizeof(flags_mask)))
 		return 0;
 
@@ -3105,11 +3124,11 @@ static int fl_dump_key_flags(struct sk_buff *skb, u32 flags_key, u32 flags_mask)
 	_key = cpu_to_be32(key);
 	_mask = cpu_to_be32(mask);
 
-	err = nla_put(skb, TCA_FLOWER_KEY_FLAGS, 4, &_key);
+	err = nla_put(skb, fl_key, 4, &_key);
 	if (err)
 		return err;
 
-	return nla_put(skb, TCA_FLOWER_KEY_FLAGS_MASK, 4, &_mask);
+	return nla_put(skb, fl_mask, 4, &_mask);
 }
 
 static int fl_dump_key_geneve_opt(struct sk_buff *skb,
@@ -3632,7 +3651,8 @@ static int fl_dump_key(struct sk_buff *skb, struct net *net,
 	if (fl_dump_key_ct(skb, &key->ct, &mask->ct))
 		goto nla_put_failure;
 
-	if (fl_dump_key_flags(skb, key->control.flags, mask->control.flags))
+	if (fl_dump_key_flags(skb, false, key->control.flags,
+			      mask->control.flags))
 		goto nla_put_failure;
 
 	if (fl_dump_key_val(skb, &key->hash.hash, TCA_FLOWER_KEY_HASH,
-- 
2.45.2

Re: [PATCH net-next v3 03/10] net/sched: cls_flower: prepare fl_{set,dump}_key_flags() for ENC_FLAGS
Posted by Jakub Kicinski 1 year, 7 months ago
On Tue,  9 Jul 2024 16:38:17 +0000 Asbjørn Sloth Tønnesen wrote:
> +	if (NL_REQ_ATTR_CHECK(extack, NULL, tb, fl_mask)) {

Does this work with nest as NULL? 

tb here is corresponding to attrs from tca[TCA_OPTIONS], so IIRC we need
to pass tca[TCA_OPTIONS] as nest here. Otherwise the decoder will look
for attribute with ID fl_mask at the root level, and the root attrs are
from the TCA_ enum.

Looks like Donald covered flower in Documentation/netlink/specs/tc.yaml
so you should be able to try to hit this using the Python ynl CLI:
https://docs.kernel.org/next/userspace-api/netlink/intro-specs.html#simple-cli
But to be honest I'm not 100% sure if the YNL reverse parser works with
TC and its "sub-message" polymorphism ;)
-- 
pw-bot: cr
Re: [PATCH net-next v3 03/10] net/sched: cls_flower: prepare fl_{set,dump}_key_flags() for ENC_FLAGS
Posted by Asbjørn Sloth Tønnesen 1 year, 7 months ago
Hi Jakub,

On 7/12/24 1:54 AM, Jakub Kicinski wrote:
> On Tue,  9 Jul 2024 16:38:17 +0000 Asbjørn Sloth Tønnesen wrote:
>> +	if (NL_REQ_ATTR_CHECK(extack, NULL, tb, fl_mask)) {
> 
> Does this work with nest as NULL?

It does, but it gives less information:

  * struct netlink_ext_ack - netlink extended ACK report struct
  [..]
  * @miss_nest: nest missing an attribute (%NULL if missing top level attr)

NL_REQ_ATTR_CHECK() doesn't check the value of nest, it just sets it.

That line originates from Davide's patch and is already in net-next:
1d17568e74de ("net/sched: cls_flower: add support for matching tunnel control flags")

It was added to that patch, after Jamal requested it.
https://lore.kernel.org/CAM0EoMkE3kzL28jg-nZiwQ0HnrFtm9HNBJwU1SJk7Z++yHzrMw@mail.gmail.com/

> tb here is corresponding to attrs from tca[TCA_OPTIONS], so IIRC we need
> to pass tca[TCA_OPTIONS] as nest here. Otherwise the decoder will look
> for attribute with ID fl_mask at the root level, and the root attrs are
> from the TCA_ enum.
> 
> Looks like Donald covered flower in Documentation/netlink/specs/tc.yaml
> so you should be able to try to hit this using the Python ynl CLI:
> https://docs.kernel.org/next/userspace-api/netlink/intro-specs.html#simple-cli
> But to be honest I'm not 100% sure if the YNL reverse parser works with
> TC and its "sub-message" polymorphism ;)

After extending the spec to know about the enc_flags keys, I get this:

$ sudo ./tools/net/ynl/cli.py --spec Documentation/netlink/specs/tc.yaml --do newtfilter --json '{"chain": 0, "family": 
0, "handle": 4, "ifindex": 22, "info": 262152, "kind": "flower", "options": { "flags": 0, "key-enc-flags": 8, 
"key-eth-type": 2048}, "parent": 4294967283}'
Netlink error: Invalid argument
nl_len = 68 (52) nl_flags = 0x300 nl_type = 2
         error: -22
         extack: {'msg': 'Missing flags mask', 'miss-type': 111}

After propagating tca[TCA_OPTIONS] through:

Netlink error: Invalid argument
nl_len = 76 (60) nl_flags = 0x300 nl_type = 2
         error: -22
         extack: {'msg': 'Missing flags mask', 'miss-type': 111, 'miss-nest': 56}

In v4, I have added the propagation as the last patch.

-- 
Best regards
Asbjørn Sloth Tønnesen
Network Engineer
Fiberby - AS42541
Re: [PATCH net-next v3 03/10] net/sched: cls_flower: prepare fl_{set,dump}_key_flags() for ENC_FLAGS
Posted by Jakub Kicinski 1 year, 7 months ago
On Sat, 13 Jul 2024 01:14:57 +0000 Asbjørn Sloth Tønnesen wrote:
> After propagating tca[TCA_OPTIONS] through:
> 
> Netlink error: Invalid argument
> nl_len = 76 (60) nl_flags = 0x300 nl_type = 2
>          error: -22
>          extack: {'msg': 'Missing flags mask', 'miss-type': 111, 'miss-nest': 56}
> 
> In v4, I have added the propagation as the last patch.

Sorry for the misdirection, I realized this morning that the Python
code can't descend at all. I only implemented decoding missing attrs
to names if they are at the root level. C YNL code can decode.. but 
it can only do genetlink.. :)