quinn-rs / quinn

Async-friendly QUIC implementation in Rust
Apache License 2.0
3.76k stars 380 forks source link

Panic when being sent malformed packet #1334

Closed 5225225 closed 2 years ago

5225225 commented 2 years ago

Reproduction:

  1. Run the example server (cargo run --example server ./). I suspect any server will work, but the example server is good.
  2. echo "iQAAAAEBAAAbG4QbAAAAAD8A" | base64 -d | nc -u localhost 4433

This results in

listening on [::1]:4433
thread 'tokio-runtime-worker' panicked at 'assertion failed: pos <= self.get_ref().as_ref().len()', /home/jess/.cargo/registry/src/github.com-1ecc6299db9ec823/bytes-1.1.0/src/buf/buf_impl.rs:1067:9
note: run with `RUST_BACKTRACE=1` environment variable to display a backtrace
thread 'tokio-runtime-worker' panicked at 'called `Result::unwrap()` on an `Err` value: PoisonError { .. }', quinn/src/endpoint.rs:297:42

The fuzzer I used to find this (I'll make it more powerful and make a PR with it, but if I forget to, feel free to just put it in yourself) is

#![no_main]
use libfuzzer_sys::fuzz_target;

use std::sync::Arc;
use proto::{Endpoint, EndpointConfig};
use std::time::Instant;

fuzz_target!(|data: &[u8]| {
    let mut e = Endpoint::new(Arc::new(EndpointConfig::default()), None);

    e.handle(
        Instant::now(), "1.1.1.1:1111".parse().unwrap(),
        None,
        None,
        data.into(),
    );
});
5225225 commented 2 years ago

Ah, turns out the existing packet fuzzer catches this.

Ralith commented 2 years ago

We clearly need a better setup for actually getting the fuzzers regular runtime...

5225225 commented 2 years ago

https://google.github.io/clusterfuzzlite/running-clusterfuzzlite/ maybe? Never used it, nor have I worked with anyone who's used it. But it looks decent.

That, or get this project to be part of oss-fuzz so google fuzzes it continuously for you. Or both.