net: openvswitch: Fix matching zone id for invalid conns arriving from tc
authorPaul Blakey <paulb@nvidia.com>
Tue, 14 Dec 2021 17:24:35 +0000 (19:24 +0200)
committerJakub Kicinski <kuba@kernel.org>
Sat, 18 Dec 2021 02:06:36 +0000 (18:06 -0800)
Zone id is not restored if we passed ct and ct rejected the connection,
as there is no ct info on the skb.

Save the zone from tc skb cb to tc skb extension and pass it on to
ovs, use that info to restore the zone id for invalid connections.

Fixes: d29334c15d33 ("net/sched: act_api: fix miss set post_ct for ovs after do conntrack in act_ct")
Signed-off-by: Paul Blakey <paulb@nvidia.com>
Signed-off-by: Jakub Kicinski <kuba@kernel.org>
include/linux/skbuff.h
net/openvswitch/flow.c
net/sched/cls_api.c

index 2ecf8cfd22231e50cd14a4ed1a68c8a8da762163..4507d77d6941f2f0182bb8245890e14a6e5e199e 100644 (file)
@@ -286,6 +286,7 @@ struct nf_bridge_info {
 struct tc_skb_ext {
        __u32 chain;
        __u16 mru;
+       __u16 zone;
        bool post_ct;
 };
 #endif
index 9713035b89e3ab2a20f9826621063a66c2f4c994..6d262d9aa10ea1ad48a8bed44b4f65cdb16920db 100644 (file)
@@ -34,6 +34,7 @@
 #include <net/mpls.h>
 #include <net/ndisc.h>
 #include <net/nsh.h>
+#include <net/netfilter/nf_conntrack_zones.h>
 
 #include "conntrack.h"
 #include "datapath.h"
@@ -860,6 +861,7 @@ int ovs_flow_key_extract(const struct ip_tunnel_info *tun_info,
 #endif
        bool post_ct = false;
        int res, err;
+       u16 zone = 0;
 
        /* Extract metadata from packet. */
        if (tun_info) {
@@ -898,6 +900,7 @@ int ovs_flow_key_extract(const struct ip_tunnel_info *tun_info,
                key->recirc_id = tc_ext ? tc_ext->chain : 0;
                OVS_CB(skb)->mru = tc_ext ? tc_ext->mru : 0;
                post_ct = tc_ext ? tc_ext->post_ct : false;
+               zone = post_ct ? tc_ext->zone : 0;
        } else {
                key->recirc_id = 0;
        }
@@ -906,8 +909,11 @@ int ovs_flow_key_extract(const struct ip_tunnel_info *tun_info,
 #endif
 
        err = key_extract(skb, key);
-       if (!err)
+       if (!err) {
                ovs_ct_fill_key(skb, key, post_ct);   /* Must be after key_extract(). */
+               if (post_ct && !skb_get_nfct(skb))
+                       key->ct_zone = zone;
+       }
        return err;
 }
 
index ff8a9383bf1c4a05f9ecef50f352c8b0379edee7..35c74bdde848e2d3e100ffd6589946ce9d3d10eb 100644 (file)
@@ -1625,6 +1625,7 @@ int tcf_classify(struct sk_buff *skb,
                ext->chain = last_executed_chain;
                ext->mru = cb->mru;
                ext->post_ct = cb->post_ct;
+               ext->zone = cb->zone;
        }
 
        return ret;