Repository navigation
Conversation
…sm on the MSRV and without SIMD
Member
|
Looks good at first glance. I can do a more detailed review later. |
This branch has not been deployed
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Adds a backend for WebAssembly's 128-bit SIMD, selected at compile time when the crate is built with the
simd128target feature (-C target-feature=+simd128), as the NEON backend is selected bytarget_feature = "neon"and assha2selects itswasm32_simd128backend. Todaywasm32uses the software backend, a block at a time;simd128is supported by every major WebAssembly engine (V8, SpiderMonkey, JavaScriptCore, Wasmtime, Wasmer).The backend computes four blocks at a time with each vector holding one state word of the four blocks, so the rounds need no lane rotations (the layout of libsodium's
u4); the blocks are transposed into rows once at the end. A single block (the tail of a message) is computed as its four rows, as the NEON backend does. The 16- and 8-bit rotations are byte shuffles (i8x16.shuffle), the 12- and 7-bit ones shift pairs. It supports both counter widths (Ietf's 32-bit andLegacy's 64-bit) and the RNG path, andchacha20_backend="soft"still forces the software backend. Onlyv128_storeneedsunsafe; the other intrinsics are safe with the target feature enabled.Performance
The crate's own benches (
cargo +nightly bench --target wasm32-wasip1withRUSTFLAGS='-C target-feature=+simd128', the runnerwasmtime runor Node 24's WASI) on an i9-14900K's performance cores, MB/s, the best of two runs; the software backend is the same build with--cfg chacha20_backend="soft":simd128, wasmtimesimd128, Node 24 (V8)From four blocks on, 1.7 times the software backend's throughput under wasmtime and 2.4 times under V8. A single block takes 62 ns straight from the core against the software backend's 70, but the 16 B bench shows the opposite with
cipher0.5.2: its wrapper enters the backend on every call, including the three of four that only read cached keystream, and zeroes a buffer of four blocks each time, which the software backend, with one parallel block, never does. RustCrypto/traits#2505 skips both; with it the 16 B case is 941 MB/s under wasmtime and 888 under V8.ChaCha20Rng::fill_bytesover 64 MiB: 950 → 1,500 MB/s under wasmtime, 900 → 2,000 under V8.Testing
+simd128onwasm32-wasip1for every feature combination (cargo hack test --feature-powersetunder wasmtime), and withchacha20_backend="soft"forced. The backend's output equals the software backend's over every length from 0 to 600 bytes as a stream, over 1 MiB + 77 bytes from nine seek positions, for XChaCha20, ChaCha8 and ChaCha12, and forChaCha20LegacyandChaCha20Rngacross the 64-bit counter's carry at 2^32 blocks, on wasmtime, Wasmer 6.0.1 and Node 24.cargo clippy --all-features --lib --tests -D warningsandcargo fmt --checkare clean, and the crate builds on the MSRV (1.85) with+simd128.cargo hack test --feature-powersetonwasm32-wasip1under wasmtime, on the MSRV and stable, with and withoutsimd128(the matrixsha2's workflow runs).