netfilter: nft_set_rbtree: check for inactive element after flag mismatch
authorPablo Neira Ayuso <pablo@netfilter.org>
Tue, 12 Mar 2019 11:10:59 +0000 (12:10 +0100)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Sat, 4 May 2019 06:49:06 +0000 (08:49 +0200)
[ Upstream commit 05b7639da55f5555b9866a1f4b7e8995232a6323 ]

Otherwise, we hit bogus ENOENT when removing elements.

Fixes: e701001e7cbe ("netfilter: nft_rbtree: allow adjacent intervals with dynamic updates")
Reported-by: Václav Zindulka <vaclav.zindulka@tlapnet.cz>
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
Signed-off-by: Sasha Levin (Microsoft) <sashal@kernel.org>
net/netfilter/nft_set_rbtree.c

index 93820e0..4ee8acd 100644 (file)
@@ -191,10 +191,6 @@ static void *nft_rbtree_deactivate(const struct net *net,
                else if (d > 0)
                        parent = parent->rb_right;
                else {
-                       if (!nft_set_elem_active(&rbe->ext, genmask)) {
-                               parent = parent->rb_left;
-                               continue;
-                       }
                        if (nft_rbtree_interval_end(rbe) &&
                            !nft_rbtree_interval_end(this)) {
                                parent = parent->rb_left;
@@ -203,6 +199,9 @@ static void *nft_rbtree_deactivate(const struct net *net,
                                   nft_rbtree_interval_end(this)) {
                                parent = parent->rb_right;
                                continue;
+                       } else if (!nft_set_elem_active(&rbe->ext, genmask)) {
+                               parent = parent->rb_left;
+                               continue;
                        }
                        nft_set_elem_change_active(net, set, &rbe->ext);
                        return rbe;