Skip to content

Commit d050ea2

Browse files
authored
Make PAC backends platform-aware (#16)
1 parent 13dc578 commit d050ea2

23 files changed

Lines changed: 741 additions & 267 deletions

‎.github/workflows/ci.yml‎

Lines changed: 25 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -23,15 +23,15 @@ jobs:
2323
# backend — wasm2c is what makes the sandbox reachable there). The
2424
# shipped proxytester artifact is a separate single-backend build:
2525
# Wasmtime everywhere, wasm2c on armv7 (`artifact_features`).
26-
# Single-backend combinations (WinHTTP-only, native-only, ...) are
26+
# Single-backend combinations (WinHTTP fallback, native-only, ...) are
2727
# additionally covered by the `pac-backend-variants` job below.
2828
#
2929
# The native engine needs a C toolchain for the QuickJS sources
3030
# (MSVC on Windows, `cross` images on ARM Linux); wasm2c needs the
3131
# pinned `wasm2c` binary (installed below; the cross containers get
3232
# it via Cross.toml pre-build hooks).
3333

34-
# Windows (WinHTTP still handles normal resolution).
34+
# Windows.
3535
- name: windows x64
3636
os: windows-latest
3737
target: x86_64-pc-windows-msvc
@@ -159,7 +159,7 @@ jobs:
159159
run: ${{ matrix.use_cross && 'cross' || 'cargo' }} test --target ${{ matrix.target }} ${{ matrix.features }}
160160
shell: bash
161161

162-
- name: Build Node addon (wasm2c)
162+
- name: Build Node addon
163163
if: ${{ !matrix.use_cross }}
164164
run: node npm/scripts/build-native.js ${{ matrix.target }}
165165
shell: bash
@@ -183,7 +183,7 @@ jobs:
183183
mkdir -p "$stage"
184184
# The PAC engine (Wasmtime + AOT guest; the wasm2c sandbox on armv7)
185185
# is statically linked into the binary, so proxytester is
186-
# self-contained (WinHTTP handles normal resolution on Windows).
186+
# self-contained.
187187
cp "target/${{ matrix.target }}/release/examples/proxytester${ext}" "$stage/"
188188
shell: bash
189189

@@ -233,17 +233,21 @@ jobs:
233233
# These tests read the real OS proxy config after configuring it, so they
234234
# only run here (gated behind OS_PROXY_RESOLVER_OS_TESTS). On Linux the
235235
# whole thing runs under a private D-Bus session.
236-
# These tests only exercise OS-config reading, not PAC, but the crate
237-
# still needs a backend to compile on non-Windows. Use the default
238-
# (Wasmtime) backend, which needs no C toolchain.
236+
# These tests only exercise OS-config reading, not PAC. Non-Windows still
237+
# needs an explicit backend to compile; Windows intentionally uses its
238+
# backend-less WinHTTP default.
239239
- name: Run OS round-trip tests
240240
env:
241241
OS_PROXY_RESOLVER_OS_TESTS: "1"
242242
run: |
243+
features="tokio"
244+
if [ "${{ matrix.os }}" != "windows-latest" ]; then
245+
features="tokio pac-engine-wasmtime"
246+
fi
243247
if [ "${{ matrix.os }}" = "ubuntu-latest" ]; then
244-
dbus-run-session -- cargo test --features tokio os_roundtrip -- --nocapture
248+
dbus-run-session -- cargo test --features "$features" os_roundtrip -- --nocapture
245249
else
246-
cargo test --features tokio os_roundtrip -- --nocapture
250+
cargo test --features "$features" os_roundtrip -- --nocapture
247251
fi
248252
shell: bash
249253

@@ -257,7 +261,8 @@ jobs:
257261
# Every engine available per OS is built and timed separately on the
258262
# same PAC script and URLs; their captured results are cross-checked
259263
# across processes:
260-
# windows : WinHTTP + native QuickJS + Wasmtime AOT/JIT + wasm2c
264+
# windows : native QuickJS + Wasmtime AOT/JIT + wasm2c;
265+
# WinHTTP in a separate backend-less build
261266
# macos/linux : native QuickJS + Wasmtime AOT/JIT + wasm2c
262267
# linux armv7 : native QuickJS + wasm2c (no Cranelift for 32-bit
263268
# ARM), built with `cross` and run under qemu — the
@@ -395,11 +400,13 @@ jobs:
395400
done
396401
echo "all embedded backends agree on all URLs"
397402
398-
# WinHTTP is part of every Windows binary regardless of embedded
399-
# feature selection. Benchmark it once using the last artifact; it
400-
# is intentionally excluded from the strict result diff because it
401-
# may omit a trailing DIRECT fallback.
403+
# WinHTTP resolution is only compiled when no embedded backend is
404+
# selected. Build that variant separately; its results are excluded
405+
# from the strict diff because WinHTTP may omit trailing DIRECT.
402406
if [ "$RUNNER_OS" = "Windows" ]; then
407+
$CARGO build --release --example pac_bench $TARGET_FLAG \
408+
--no-default-features --features tokio
409+
printf ' %-26s: %s bytes\n' "winhttp" "$(wc -c < "$BIN" | tr -d ' ')"
403410
echo
404411
echo "pac_bench platform performance: winhttp"
405412
"$BIN" --backend winhttp --iterations ${{ matrix.iterations }}
@@ -421,19 +428,18 @@ jobs:
421428
fail-fast: false
422429
matrix:
423430
include:
424-
# WinHTTP-only pure-Rust Windows build: no embedded engine at all.
425-
# Valid on Windows because WinHTTP handles PAC.
426-
- name: windows WinHTTP-only (pure Rust)
431+
# Backend-less Windows build: WinHTTP handles PAC and WPAD.
432+
- name: windows WinHTTP fallback
427433
os: windows-latest
428434
features: --no-default-features --features tokio
429435
# Native-only build (no wasm sandbox) on a 64-bit host.
430436
- name: linux native-only
431437
os: ubuntu-latest
432438
features: --no-default-features --features "tokio pac-engine"
433-
# Wasmtime-only (the default feature set): no C toolchain use at all.
439+
# Wasmtime-only: no native QuickJS.
434440
- name: linux wasmtime-only
435441
os: ubuntu-latest
436-
features: --features tokio
442+
features: --no-default-features --features "tokio pac-engine-wasmtime"
437443
# wasm2c-only: the sandbox without Wasmtime, as an armv7-style build
438444
# would use, but tested on a fast 64-bit host.
439445
- name: linux wasm2c-only

‎Cargo.lock‎

Lines changed: 61 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

‎Cargo.toml‎

Lines changed: 13 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ rust-version = "1.77"
77
# the MIT-licensed quickjs-ng via the `rquickjs-sys` crate; the PAC helper
88
# functions are original, implemented from the public PAC specification.
99
license = "MIT"
10-
description = "Resolve the OS-configured proxy (static, PAC, WPAD) for a URL, with change notification. WinHTTP on Windows; SystemConfiguration/gsettings + an embedded QuickJS PAC engine on macOS/Linux."
10+
description = "Resolve the OS-configured proxy (static, PAC, WPAD) for a URL, with change notification and a sandboxed PAC engine."
1111
repository = "https://github.com/microsoft/os-proxy-resolver"
1212
keywords = ["proxy", "pac", "wpad", "winhttp", "system-proxy"]
1313
categories = ["network-programming", "os"]
@@ -17,18 +17,16 @@ crate-type = ["rlib", "cdylib"]
1717

1818
[features]
1919
# PAC backend selection is explicit: enable at least one of `pac-engine`
20-
# (native QuickJS) and/or `pac-engine-wasmtime` (sandboxed). On non-Windows a
21-
# backend is required (there is no OS PAC evaluator) — building with neither is
22-
# a compile error; on Windows WinHTTP always handles PAC, so a backend-less
23-
# build is valid there. The default set enables the sandboxed Wasmtime backend
24-
# on every platform, which is also the default runtime `pac_backend`.
25-
default = ["pac-engine-wasmtime"]
20+
# (native QuickJS), `pac-engine-wasmtime` (sandboxed), or the other backends
21+
# below. On non-Windows a backend is required (there is no OS PAC evaluator),
22+
# so building with no features is a compile error. On Windows the default
23+
# backend-less build delegates PAC/WPAD resolution to WinHTTP.
24+
default = []
2625
# Async change notification via tokio::sync::watch.
2726
tokio = ["dep:tokio"]
2827
# The embedded native QuickJS PAC engine (compiles the quickjs-ng C sources via
29-
# `rquickjs-sys`). Optional on every platform. Off Windows it is one of the two
30-
# selectable backends; on Windows it is additionally useful for the `pac_bench`
31-
# WinHTTP-vs-embedded comparison.
28+
# `rquickjs-sys`). Optional on every platform and selected for normal PAC
29+
# resolution when it is the configured backend.
3230
pac-engine = ["dep:rquickjs-sys"]
3331
# The sandboxed PAC backend: QuickJS-NG compiled to WebAssembly (see
3432
# pac-wasm-guest/), run under Wasmtime in AOT mode. The runtime dependency is
@@ -91,8 +89,9 @@ wasmtime = { version = "=46.0.1", optional = true, default-features = false, fea
9189
cc = { version = "1", optional = true }
9290

9391
[target.'cfg(not(windows))'.dependencies]
94-
# PAC / wpad.dat fetching. Sync, small, rustls-backed so no OpenSSL cross headaches.
95-
ureq = { version = "2", default-features = false, features = ["tls", "gzip"] }
92+
# PAC / wpad.dat fetching. Sync and rustls-backed, loading roots from the OS
93+
# trust store so locally installed enterprise CAs are honored.
94+
ureq = { version = "2", default-features = false, features = ["tls", "native-certs", "gzip"] }
9695
# Embedded QuickJS-NG (MIT) for the native PAC engine. Vendors and compiles the
9796
# quickjs-ng C sources via `cc`. Optional (feature `pac-engine`) so a
9897
# Wasmtime-only build links no C engine.
@@ -113,10 +112,8 @@ windows-sys = { version = "0.60", features = [
113112
"Win32_System_Registry",
114113
"Win32_System_Threading",
115114
] }
116-
# Optional on Windows so the default build stays pure Rust (WinHTTP handles
117-
# PAC). Enabled by the `pac-engine` feature for the WinHTTP-vs-QuickJS
118-
# benchmark. Off Windows the engine is always built (see the not(windows)
119-
# table above), where this crate is a required dependency.
115+
# Optional on Windows and enabled by the `pac-engine` feature, matching the
116+
# non-Windows dependency above.
120117
rquickjs-sys = { version = "0.12.1", optional = true }
121118

122119
[dev-dependencies]

‎LICENSE.txt‎

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,8 @@ SOFTWARE.
2222

2323
---
2424

25-
The embedded PAC engine (in src/pac/engine) links the QuickJS-NG JavaScript
26-
engine on macOS and Linux via the MIT-licensed rquickjs-sys crate. QuickJS-NG
27-
is also MIT-licensed. See ThirdPartyNotices.txt for details. The MIT license
28-
above applies to the first-party source of this project.
25+
The optional native PAC backend (in src/pac/engine) links the QuickJS-NG
26+
JavaScript engine on every supported platform via the MIT-licensed
27+
rquickjs-sys crate. QuickJS-NG is also MIT-licensed. See
28+
ThirdPartyNotices.txt for details. The MIT license above applies to the
29+
first-party source of this project.

0 commit comments

Comments
 (0)