Skip to content
This repository has been archived by the owner on May 9, 2022. It is now read-only.

Panic on remove() #13

Open
ccakes opened this issue Jun 7, 2019 · 2 comments
Open

Panic on remove() #13

ccakes opened this issue Jun 7, 2019 · 2 comments

Comments

@ccakes
Copy link
Contributor

ccakes commented Jun 7, 2019

I'm getting an occasional panic using this library on calling IpLookupTable.remove(). Panic location is below:

thread '<unnamed>' panicked at 'index out of bounds: the len is 0 but the index is 0', /cargo/registry/src/github.com-1ecc6299db9ec823/treebitmap-0.4.0/src/tree_bitmap/mod.rs:297:22

The Rust binary in question is processing a couple hundred full BGP feeds but the list of prefixes which trigger the panic is suspiciously small... 49.255.11.17/32 is by far the most frequent culprit. It doesn't seem to happen every time and I have yet to be able to reliably reproduce it in a simple example. All the prefixes that trigger the crashes are /32 IPv4 prefixes.

I added some debug logging and something looks odd. I started logging whenever I insert that prefix so I know it's been seen. Immediately before the panic I dump the table to a file and the prefix exists, however if I try to lookup the prefix using either exact_match() or longest_match() I get a None back..

I realise this is probably tricky to troubleshoot without a reliable reproduction, but any tips on where I can start looking? I tried a build with this line changed to an assert!() but it still gets past that, so something seems to be happening in remove_child()

@ccakes
Copy link
Contributor Author

ccakes commented Jun 9, 2019

Actually - I can reproduce it with a pretty small example. This is using 0.4 from crates.io

use treebitmap::IpLookupTable;

use std::error::Error;
use std::net::Ipv4Addr;

const ADDR: Ipv4Addr = Ipv4Addr::new(49, 255, 11, 17);

fn main() -> Result<(), Box<dyn Error>> {
    let mut table = IpLookupTable::new();

    table.insert( Ipv4Addr::new(49, 255, 11, 16), 28, ());
    table.insert( ADDR, 32, ());

    println!("exact_match: {:?}", table.exact_match(ADDR, 32));
    println!("longest_match: {:?}", table.longest_match(ADDR));

    let v = table.remove(ADDR, 32);
    println!("removed: {:?}", v);

    Ok(())
}

@pusateri
Copy link

pusateri commented Jun 9, 2019

Looks like a bug with overlapping subnets.

jiegec added a commit to jiegec/treebitmap that referenced this issue Jun 29, 2019
jiegec added a commit to jiegec/treebitmap that referenced this issue Jun 29, 2019
JakubOnderka pushed a commit to JakubOnderka/treebitmap that referenced this issue Feb 21, 2020
JakubOnderka pushed a commit to JakubOnderka/treebitmap that referenced this issue Feb 21, 2020
JakubOnderka added a commit to JakubOnderka/treebitmap that referenced this issue Feb 21, 2020
JakubOnderka added a commit to JakubOnderka/treebitmap that referenced this issue Feb 22, 2020
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants