[Devel] [PATCH RHEL7 COMMIT] ms/netfilter: nft_rbtree: ignore inactive matching element with no descendants

Konstantin Khorenko khorenko at virtuozzo.com
Thu Feb 27 12:31:03 MSK 2020


The commit is pushed to "branch-rh7-3.10.0-1062.12.1.vz7.131.x-ovz" and will appear at https://src.openvz.org/scm/ovz/vzkernel.git
after rh7-3.10.0-1062.12.1.vz7.131.4
------>
commit 8c391c59e3ec4bbe40b30da5199737d79aade06c
Author: Pablo Neira Ayuso <pablo at netfilter.org>
Date:   Mon Aug 1 13:13:08 2016 +0200

    ms/netfilter: nft_rbtree: ignore inactive matching element with no descendants
    
    If we find a matching element that is inactive with no descendants, we
    jump to the found label, then crash because of nul-dereference on the
    left branch.
    
    Fix this by checking that the element is active and not an interval end
    and skipping the logic that only applies to the tree iteration.
    
    Signed-off-by: Pablo Neira Ayuso <pablo at netfilter.org>
    Tested-by: Anders K. Pedersen <akp at akp.dk>
    
    https://jira.sw.ru/browse/PSBM-101492
    
    (cherry picked from commit c1eda3c6394f805886b2afa8c7ea5e04305ec698)
    Signed-off-by: Vasily Averin <vvs at virtuozzo.com>
---
 net/netfilter/nft_rbtree.c | 10 ++++++----
 1 file changed, 6 insertions(+), 4 deletions(-)

diff --git a/net/netfilter/nft_rbtree.c b/net/netfilter/nft_rbtree.c
index b7169fa6e9d63..068731fbbad4e 100644
--- a/net/netfilter/nft_rbtree.c
+++ b/net/netfilter/nft_rbtree.c
@@ -56,7 +56,6 @@ static bool nft_rbtree_lookup(const struct nft_set *set, const u32 *key,
 		} else if (d > 0)
 			parent = parent->rb_right;
 		else {
-found:
 			if (!nft_set_elem_active(&rbe->ext, genmask)) {
 				parent = parent->rb_left;
 				continue;
@@ -70,9 +69,12 @@ static bool nft_rbtree_lookup(const struct nft_set *set, const u32 *key,
 		}
 	}
 
-	if (set->flags & NFT_SET_INTERVAL && interval != NULL) {
-		rbe = interval;
-		goto found;
+	if (set->flags & NFT_SET_INTERVAL && interval != NULL &&
+	    nft_set_elem_active(&interval->ext, genmask) &&
+	    !nft_rbtree_interval_end(interval)) {
+		spin_unlock_bh(&nft_rbtree_lock);
+		*ext = &interval->ext;
+		return true;
 	}
 out:
 	spin_unlock_bh(&nft_rbtree_lock);


More information about the Devel mailing list