Skip to content
  • Vishwanath Pai's avatar
    netfilter: ipset: fix race condition in ipset save, swap and delete · 596cf3fe
    Vishwanath Pai authored
    
    
    This fix adds a new reference counter (ref_netlink) for the struct ip_set.
    The other reference counter (ref) can be swapped out by ip_set_swap and we
    need a separate counter to keep track of references for netlink events
    like dump. Using the same ref counter for dump causes a race condition
    which can be demonstrated by the following script:
    
    ipset create hash_ip1 hash:ip family inet hashsize 1024 maxelem 500000 \
    counters
    ipset create hash_ip2 hash:ip family inet hashsize 300000 maxelem 500000 \
    counters
    ipset create hash_ip3 hash:ip family inet hashsize 1024 maxelem 500000 \
    counters
    
    ipset save &
    
    ipset swap hash_ip3 hash_ip2
    ipset destroy hash_ip3 /* will crash the machine */
    
    Swap will exchange the values of ref so destroy will see ref = 0 instead of
    ref = 1. With this fix in place swap will not succeed because ipset save
    still has ref_netlink on the set (ip_set_swap doesn't swap ref_netlink).
    
    Both delete and swap will error out if ref_netlink != 0 on the set.
    
    Note: The changes to *_head functions is because previously we would
    increment ref whenever we called these functions, we don't do that
    anymore.
    
    Reviewed-by: default avatarJoshua Hunt <johunt@akamai.com>
    Signed-off-by: default avatarVishwanath Pai <vpai@akamai.com>
    Signed-off-by: default avatarJozsef Kadlecsik <kadlec@blackhole.kfki.hu>
    Signed-off-by: default avatarPablo Neira Ayuso <pablo@netfilter.org>
    596cf3fe