Skip to content

Commit

Permalink
Merge branch 'main' into feat-more-ecn
Browse files Browse the repository at this point in the history
Signed-off-by: Lars Eggert <[email protected]>
  • Loading branch information
larseggert authored Mar 27, 2024
2 parents 16d73db + f1560ab commit cf90ee6
Show file tree
Hide file tree
Showing 32 changed files with 303 additions and 327 deletions.
33 changes: 33 additions & 0 deletions .github/actions/nss/action.yml
Original file line number Diff line number Diff line change
Expand Up @@ -16,35 +16,68 @@ inputs:
runs:
using: composite
steps:
- name: Check system NSS version
shell: bash
run: |
if ! command -v pkg-config &> /dev/null; then
echo "BUILD_NSS=1" >> "$GITHUB_ENV"
exit 0
fi
if ! pkg-config --exists nss; then
echo "BUILD_NSS=1" >> "$GITHUB_ENV"
exit 0
fi
NSS_VERSION="$(pkg-config --modversion nss)"
if [ "$?" -ne 0 ]; then
echo "BUILD_NSS=1" >> "$GITHUB_ENV"
exit 0
fi
NSS_MAJOR=$(echo "$NSS_VERSION" | cut -d. -f1)
NSS_MINOR=$(echo "$NSS_VERSION" | cut -d. -f2)
REQ_NSS_MAJOR=$(cat neqo-crypto/min_version.txt | cut -d. -f1)
REQ_NSS_MINOR=$(cat neqo-crypto/min_version.txt | cut -d. -f2)
if [ "$NSS_MAJOR" -lt "REQ_NSS_MAJOR" ] || [ "$NSS_MAJOR" -eq "REQ_NSS_MAJOR" -a "$NSS_MINOR" -lt "REQ_NSS_MINOR"]; then
echo "System NSS is too old: $NSS_VERSION"
echo "BUILD_NSS=1" >> "$GITHUB_ENV"
exit 0
fi
echo "System NSS is suitable: $NSS_VERSION"
echo "BUILD_NSS=0" >> "$GITHUB_ENV"
# Ideally, we'd use this. But things are sufficiently flaky that we're better off
# trying both hg and git. Leaving this here in case we want to re-try in the future.
#
# - name: Checkout NSPR
# if: env.BUILD_NSS == '1'
# uses: actions/checkout@v4
# with:
# repository: "nss-dev/nspr"
# path: ${{ github.workspace }}/nspr

# - name: Checkout NSS
# if: env.BUILD_NSS == '1'
# uses: actions/checkout@v4
# with:
# repository: "nss-dev/nss"
# path: ${{ github.workspace }}/nss

- name: Checkout NSPR
shell: bash
if: env.BUILD_NSS == '1'
run: |
hg clone https://hg.mozilla.org/projects/nspr "${{ github.workspace }}/nspr" || \
git clone --depth=1 https://github.com/nss-dev/nspr "${{ github.workspace }}/nspr"
- name: Checkout NSS
shell: bash
if: env.BUILD_NSS == '1'
run: |
hg clone https://hg.mozilla.org/projects/nss "${{ github.workspace }}/nss" || \
git clone --depth=1 https://github.com/nss-dev/nss "${{ github.workspace }}/nss"
- name: Build
shell: bash
if: env.BUILD_NSS == '1'
run: |
if [ "${{ inputs.type }}" != "Debug" ]; then
# We want to do an optimized build for accurate CPU profiling, but
Expand Down
4 changes: 2 additions & 2 deletions .github/actions/quic-interop-runner/action.yml
Original file line number Diff line number Diff line change
Expand Up @@ -92,8 +92,8 @@ runs:
run: |
echo '[**QUIC Interop Runner**](https://github.com/quic-interop/quic-interop-runner)' >> comment
echo '' >> comment
# Ignore all, but table, which starts with "|:--".
cat quic-interop-runner/summary | awk '/^\|:--/{flag=1} flag' >> comment
# Ignore all, but table, which starts with "|".
grep -E '^\|' quic-interop-runner/summary >> comment
echo '' >> comment
shell: bash

Expand Down
22 changes: 5 additions & 17 deletions .github/workflows/check.yml
Original file line number Diff line number Diff line change
Expand Up @@ -49,33 +49,21 @@ jobs:
sudo apt-get install -y --no-install-recommends gyp mercurial ninja-build lld
echo "RUSTFLAGS=-C link-arg=-fuse-ld=lld" >> "$GITHUB_ENV"
# In addition to installing dependencies, first make sure System Integrity Protection (SIP)
# is disabled on this MacOS runner. This is needed to allow the NSS libraries to be loaded
# from the build directory and avoid various other test failures. This seems to always be
# the case on any macos-13 runner, but not consistently on macos-latest (which is currently
# macos-12, FWIW).
- name: Install dependencies (MacOS)
if: runner.os == 'MacOS'
run: |
csrutil status | grep disabled
brew install ninja mercurial llvm
brew update
brew install llvm nss
echo "/opt/homebrew/opt/llvm/bin" >> "$GITHUB_PATH"
ln -s /opt/homebrew/bin/python3 /opt/homebrew/bin/python
# python3 -m pip install gyp-next
# Above does not work, since pypi only has gyp 0.15.0, which is too old
# for the homebrew python3. Install from source instead.
python3 -m pip install git+https://github.com/nodejs/gyp-next
python3 -m pip install packaging
echo "$(python3 -m site --user-base)/bin" >> "$GITHUB_PATH"
echo "RUSTFLAGS=-C link-arg=-fuse-ld=lld" >> "$GITHUB_ENV"
- name: Use MSYS2 environment and install more dependencies (Windows)
- name: Install dependencies (Windows)
if: runner.os == 'Windows'
run: |
# shellcheck disable=SC2028
{
echo "C:\\msys64\\usr\\bin"
echo "C:\\msys64\\mingw64\\bin"
echo C:/msys64/usr/bin
echo C:/msys64/mingw64/bin
} >> "$GITHUB_PATH"
/c/msys64/usr/bin/pacman -S --noconfirm nsinstall
python3 -m pip install git+https://github.com/nodejs/gyp-next
Expand Down
114 changes: 73 additions & 41 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,82 +1,102 @@
# Neqo, an Implementation of QUIC written in Rust
# Neqo, an Implementation of QUIC in Rust

![neqo logo](https://github.com/mozilla/neqo/raw/main/neqo.png "neqo logo")

To run test HTTP/3 programs (neqo-client and neqo-server):
To build Neqo:

* `cargo build`
* `./target/debug/neqo-server '[::]:12345' --db ./test-fixture/db`
* `./target/debug/neqo-client http://127.0.0.1:12345/`

If a "Failure to load dynamic library" error happens at runtime, do
```shell
export LD_LIBRARY_PATH="$(dirname "$(find . -name libssl3.so -print | head -1)")"
cargo build
```

On a macOS, do
This will use a system-installed [NSS][NSS] library if it is new enough. (See "Build with Separate NSS/NSPR" below if NSS is not installed or it is deemed too old.)

To run test HTTP/3 programs (`neqo-client` and `neqo-server`):

```shell
export DYLD_LIBRARY_PATH="$(dirname "$(find . -name libssl3.dylib -print | head -1)")"
./target/debug/neqo-server '[::]:12345'
./target/debug/neqo-client 'https://[::]:12345/'
```

## Faster Builds with Separate NSS/NSPR
## Build with separate NSS/NSPR

You can clone NSS (https://hg.mozilla.org/projects/nss) and NSPR
(https://hg.mozilla.org/projects/nspr) into the same directory and export an
You can clone [NSS][NSS] and [NSPR][NSPR] into the same directory and export an
environment variable called `NSS_DIR` pointing to NSS. This causes the build to
use the existing NSS checkout. However, in order to run anything that depends
on NSS, you need to set `$\[DY]LD\_LIBRARY\_PATH` to point to
`$NSS_DIR/../dist/Debug/lib`.
on NSS, you need to set an environment as follows:

### Linux

```shell
export LD_LIBRARY_PATH="$(dirname "$(find . -name libssl3.so -print | head -1)")"
```

### macOS

```shell
export DYLD_LIBRARY_PATH="$(dirname "$(find . -name libssl3.dylib -print | head -1)")"
```

Note: If you did not compile NSS separately, you need to have mercurial (hg), installed.
NSS builds require gyp, and ninja (or ninja-build) to be present also.
Note: If you did not already compile NSS separately, you need to have
[Mercurial (hg)][HG], installed. NSS builds require [GYP][GYP] and
[Ninja][NINJA] to be installed.

## Debugging Neqo

### QUIC Logging
### QUIC logging

Enable [QLOG](https://datatracker.ietf.org/doc/draft-ietf-quic-qlog-main-schema/) with:
Enable generation of [QLOG][QLOG] logs with:

```
$ mkdir "$logdir"
$ ./target/debug/neqo-server '[::]:12345' --db ./test-fixture/db --qlog-dir "$logdir"
$ ./target/debug/neqo-client 'https://[::]:12345/' --qlog-dir "$logdir"
```shell
target/debug/neqo-server '[::]:12345' --qlog-dir .
target/debug/neqo-client 'https://[::]:12345/' --qlog-dir .
```

You may use https://qvis.quictools.info/ by uploading the QLOG files and visualize the flows.
You can of course specify a different directory for the QLOG files.
You can upload QLOG files to [qvis][QVIS] to visualize the flows.

### Using SSLKEYLOGFILE to decrypt Wireshark logs
### Using `SSLKEYLOGFILE` to decrypt Wireshark logs

[Info here](https://developer.mozilla.org/en-US/docs/Mozilla/Projects/NSS/Key_Log_Format)

TODO: What is the minimum Wireshark version needed?
TODO: Above link may be incorrect, protocol now called TLS instead of SSL?
You can export TLS keys by setting the `SSLKEYLOGFILE` environment variable
to a filename to instruct NSS to dump keys in the
[standard format](https://datatracker.ietf.org/doc/draft-ietf-tls-keylogfile/)
to enable decryption by [Wireshark](https://wiki.wireshark.org/TLS) and other tools.

### Using RUST_LOG effectively

As documented in the [env_logger documentation](https://docs.rs/env_logger/),
the `RUST_LOG` environment variable can be used to selectively enable log messages
from Rust code. This works for Neqo's cmdline tools, as well as for when Neqo is
from Rust code. This works for Neqo's command line tools, as well as for when Neqo is
incorporated into Gecko, although [Gecko needs to be built in debug mode](https://developer.mozilla.org/en-US/docs/Mozilla/Developer_guide/Build_Instructions/Configuring_Build_Options).

Some examples:
1. `RUST_LOG=neqo_transport::dump ./mach run` lists sent and received QUIC
packets and their frames' contents only.
1. `RUST_LOG=neqo_transport=debug,neqo_http3=trace,info ./mach run` sets a
'debug' log level for transport, 'trace' level for http3, and 'info' log

1. ```shell
RUST_LOG=neqo_transport::dump ./mach run
```

lists sent and received QUIC packets and their frames' contents only.

1. ```shell
RUST_LOG=neqo_transport=debug,neqo_http3=trace,info ./mach run
```

sets a `debug` log level for `transport`, `trace` level for `http3`, and `info` log
level for all other Rust crates, both Neqo and others used by Gecko.
1. `RUST_LOG=neqo=trace,error ./mach run` sets `trace` level for all modules
starting with "neqo", and sets `error` as minimum log level for other
unrelated Rust log messages.

1. ```shell
RUST_LOG=neqo=trace,error ./mach run
```

sets `trace` level for all modules starting with `neqo`, and sets `error` as minimum log level for other unrelated Rust log messages.

### Trying In-development Neqo code in Gecko
### Trying in-development Neqo code in Gecko

In a checked-out copy of Gecko source, set `[patches.*]` values for the four
Neqo crates to local versions in the root `Cargo.toml`. For example, if Neqo
was checked out to `/home/alice/git/neqo`, add the following lines to the root
`Cargo.toml`.

```
```toml
[patch."https://github.com/mozilla/neqo"]
neqo-http3 = { path = "/home/alice/git/neqo/neqo-http3" }
neqo-transport = { path = "/home/alice/git/neqo/neqo-transport" }
Expand All @@ -87,11 +107,23 @@ neqo-crypto = { path = "/home/alice/git/neqo/neqo-crypto" }

Then run the following:

```
```shell
./mach vendor rust
```

Compile Gecko as usual with `./mach build`.
Compile Gecko as usual with

```shell
./mach build
```

Note: Using newer Neqo code with Gecko may also require changes (likely to `neqo_glue`) if
something has changed.

[NSS]: https://hg.mozilla.org/projects/nss
[NSPR]: https://hg.mozilla.org/projects/nspr
[GYP]: https://github.com/nodejs/gyp-next
[HG]: https://www.mercurial-scm.org/
[NINJA]: https://ninja-build.org/
[QLOG]: https://datatracker.ietf.org/doc/draft-ietf-quic-qlog-main-schema/
[QVIS]: https://qvis.quictools.info/
18 changes: 6 additions & 12 deletions neqo-bin/src/bin/server/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
// except according to those terms.

use std::{
borrow::Cow,
cell::RefCell,
cmp::min,
collections::HashMap,
Expand Down Expand Up @@ -196,7 +197,7 @@ trait HttpServer: Display {
}

struct ResponseData {
data: Vec<u8>,
data: Cow<'static, [u8]>,
offset: usize,
remaining: usize,
}
Expand All @@ -211,17 +212,17 @@ impl From<Vec<u8>> for ResponseData {
fn from(data: Vec<u8>) -> Self {
let remaining = data.len();
Self {
data,
data: Cow::Owned(data),
offset: 0,
remaining,
}
}
}

impl ResponseData {
fn repeat(buf: &[u8], total: usize) -> Self {
fn repeat(buf: &'static [u8], total: usize) -> Self {
Self {
data: buf.to_owned(),
data: Cow::Borrowed(buf),
offset: 0,
remaining: total,
}
Expand Down Expand Up @@ -260,14 +261,7 @@ struct SimpleServer {
}

impl SimpleServer {
const MESSAGE: &'static [u8] = b"I am the very model of a modern Major-General,\n\
I've information vegetable, animal, and mineral,\n\
I know the kings of England, and I quote the fights historical\n\
From Marathon to Waterloo, in order categorical;\n\
I'm very well acquainted, too, with matters mathematical,\n\
I understand equations, both the simple and quadratical,\n\
About binomial theorem, I'm teeming with a lot o' news,\n\
With many cheerful facts about the square of the hypotenuse.\n";
const MESSAGE: &'static [u8] = &[0; 4096];

pub fn new(
args: &Args,
Expand Down
6 changes: 0 additions & 6 deletions neqo-common/src/datagram.rs
Original file line number Diff line number Diff line change
Expand Up @@ -54,12 +54,6 @@ impl Datagram {
self.ttl
}

#[cfg(feature = "udp")]
#[must_use]
pub(crate) fn into_data(self) -> Vec<u8> {
self.d
}

pub fn set_tos(&mut self, tos: IpTos) {
self.tos = tos;
}
Expand Down
3 changes: 2 additions & 1 deletion neqo-crypto/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ neqo-common = { path = "../neqo-common" }
# Sync with https://searchfox.org/mozilla-central/source/Cargo.lock 2024-02-08
bindgen = { version = "0.69", default-features = false, features = ["runtime"] }
mozbuild = { version = "0.1", default-features = false, optional = true }
semver = { version = "1.0", default-features = false }
serde = { version = "1.0", default-features = false }
serde_derive = { version = "1.0", default-features = false }
toml = { version = "0.5", default-features = false }
Expand All @@ -30,7 +31,7 @@ test-fixture = { path = "../test-fixture" }

[features]
gecko = ["mozbuild"]
fuzzing = []
disable-encryption = []

[lib]
# See https://github.com/bheisler/criterion.rs/blob/master/book/src/faq.md#cargo-bench-gives-unrecognized-option-errors-for-valid-command-line-options
Expand Down
5 changes: 0 additions & 5 deletions neqo-crypto/bindings/bindings.toml
Original file line number Diff line number Diff line change
Expand Up @@ -265,8 +265,3 @@ enums = [
[nspr_time]
types = ["PRTime"]
functions = ["PR_Now"]

[mozpkix]
cplusplus = true
types = ["mozilla::pkix::ErrorCode"]
enums = ["mozilla::pkix::ErrorCode"]
1 change: 0 additions & 1 deletion neqo-crypto/bindings/mozpkix.hpp

This file was deleted.

Loading

0 comments on commit cf90ee6

Please sign in to comment.