quinn-rs / quinn

Async-friendly QUIC implementation in Rust
Apache License 2.0
3.85k stars 394 forks source link

Fix parsing of IPV6 URLs in client example #1745

Closed gretchenfrage closed 10 months ago

gretchenfrage commented 10 months ago

Hi all! My name's Phoenix. I've been interesting in contributing to this project for a while and thought I'd start with trying to get the examples working on my machine. Let me know if you have any feedback :)

I'm running Ubuntu 22.04.3, and even after enabling IPV6, when running the examples in the way suggested in the README:

$ cargo run --example server ./
$ cargo run --example client https://localhost:4433/Cargo.toml

The client timed out. If I passed --listen 127.0.0.1:4433 or --listen 0.0.0.0:4433 when running the server, it worked fine. But weirder yet, if I passed --listen [::]:4433 on the server, it also works fine. So it seems like my system allows 127.0.0.1 to connect to [::] but not to [::1].

In any case, I figured that I should be able to get the client to work without changing the server command by running:

cargo run --example client https://[::1]:4433/Cargo.toml --host localhost

But it failed to convert the URL to a socket address. So I fixed that, which is what this PR is.

Commit message

Currently, when trying to run the client example with an IPV6 address URL, such as by running:

cargo run --example client https://[::1]:4433/Cargo.toml --host localhost

A "failed to lookup address information: Name or service not known" error is raised. This is because url.host_str() is "[::1]", which is wrapped in brackets. These brackets, specified by by RFC 2732, are part of the URL syntax, not the IP address syntax.

Although this code succeeds, because the standard library treats this like a URL:

use std::net::ToSocketAddrs;
"[::1]:4433".to_socket_addrs()

This code does not:

use std::net::Ipv6Addr;
"[::1]".parse::<Ipv6Addr>()

As the stdlib expects to just receive "::1". Consequentially, this does not succeed, counterintuitively:

use std::net::ToSocketAddrs;
("[::1]", 4433).to_socket_addrs()

This code fixes the client example's URL parsing behavior by stripping out such brackets in the same way as is done in tokio-tungstenite.