Skip to content

Improve Snappy CRC32 with crc-fast - #660

Open
houseme wants to merge 4 commits into
apache:mainfrom
houseme:houseme/replace-crc32fast-with-crc-fast
Open

Improve Snappy CRC32 with crc-fast#660
houseme wants to merge 4 commits into
apache:mainfrom
houseme:houseme/replace-crc32fast-with-crc-fast

Conversation

@houseme

@houseme houseme commented Sep 5, 2026

Copy link
Copy Markdown

Summary

  • replace the optional Snappy crc32fast dependency with crc-fast 1.10.0
  • use crc_fast::crc32_iso_hdlc(...) for Avro Snappy block CRC32 calculation
  • add a regression test for the standard CRC-32/ISO-HDLC trailer bytes
  • add avro/benches/crc32_snappy.rs to compare crc32fast and crc-fast across raw CRC, Snappy compression + CRC, and Snappy decompression + CRC
  • document aarch64 and x86_64 benchmark results in avro/benches/crc32_snappy_results.md
  • bump workspace and CI MSRV from 1.88.0 to 1.89.0 because crc-fast 1.10.0 requires Rust 1.89

Closes #659.

Rationale

The Snappy codec only needs CRC32 over contiguous decoded/uncompressed blocks, so crc-fast's specialized one-shot crc32_iso_hdlc helper fits the existing call sites directly. The algorithm remains CRC-32/ISO-HDLC, and the new test locks the public Avro trailer format to the standard b"123456789" -> 0xcbf43926 check value encoded as big-endian bytes.

The benchmark now covers both isolated CRC cost and Snappy-shaped encode/decode cost. On local aarch64, Snappy compression + CRC improved up to 1.58x and decompression + CRC up to 2.29x. On the x86_64 EPYC test host, Snappy compression + CRC improved up to 4.32x and decompression + CRC up to 3.72x.

The SIMD reason is architecture-specific. On aarch64, crc-fast can use PMULL/AES folding, with SHA3/EOR3-assisted variants when available. On x86_64, SSE4.2 CRC32 is CRC32C/ISCSI rather than CRC-32/ISO-HDLC, so the relevant acceleration for this Avro checksum is PCLMULQDQ / VPCLMULQDQ carry-less multiply.

crc-fast is configured with default-features = false, features = ["std"] to avoid its default ffi/panic-handler features while retaining std-backed runtime SIMD detection.

Testing

  • cargo check -p apache-avro --features snappy
  • cargo test -p apache-avro --features snappy,derive snappy
  • cargo fmt --all --check
  • cargo build --all-features --all-targets
  • cargo check -p apache-avro --target aarch64-unknown-linux-gnu --features snappy
  • cargo bench -p apache-avro --bench crc32_snappy --features snappy,derive --no-run
  • cargo bench -p apache-avro --bench crc32_snappy --features snappy,derive on local aarch64
  • cargo bench -p apache-avro --bench crc32_snappy --features snappy,derive on azure-4074205200 x86_64

Not completed locally:

  • wasm32-unknown-unknown CI target validation. Installing the target locally stalled while downloading rust-std, so this should still be watched in CI.

Replace the optional crc32fast dependency with crc-fast 1.10.0 and use its CRC-32/ISO-HDLC helper for Snappy block checksums. This keeps the Avro trailer format unchanged while allowing the checksum path to use crc-fast's SIMD-backed implementation.

Bump the workspace and CI MSRV to 1.89.0 because crc-fast 1.10.0 requires Rust 1.89.

Co-Authored-By: heihutu <heihutu@gmail.com>

Co-Authored-By: zhi22915 <qiuzgang@gmail.com>
@Kriskras99

Copy link
Copy Markdown
Contributor

Do you actually measure a difference when decoding or encoding Avro files?

Add a Criterion benchmark that compares crc32fast and crc-fast for raw CRC-32/ISO-HDLC, Snappy compression plus CRC, and Snappy decompression plus CRC verification.

Document local aarch64 and remote x86_64 benchmark results, including the relevant SIMD instruction-set differences and the remaining MSRV caveat.

Co-Authored-By: heihutu <heihutu@gmail.com>

Co-Authored-By: zhi22915 <qiuzgang@gmail.com>
@houseme

houseme commented Sep 5, 2026

Copy link
Copy Markdown
Author

Yes. I added a dedicated benchmark for this in avro/benches/crc32_snappy.rs.

It now measures three paths on both aarch64 and x86_64:

  • raw CRC-32/ISO-HDLC;
  • Snappy compression plus the Avro CRC32 trailer;
  • Snappy decompression plus CRC32 verification.

The results are documented in avro/benches/crc32_snappy_results.md. The short version is that the isolated CRC gain does carry into the Snappy-shaped encode/decode paths, especially from 1 KiB upward. On the tested aarch64 machine, Snappy compress + CRC improved up to 1.58x and decompress + CRC up to 2.29x. On the tested x86_64 EPYC host, compress + CRC improved up to 4.32x and decompress + CRC up to 3.72x.

The SIMD detail is architecture-specific: on aarch64 the improvement comes from crc-fast using PMULL/AES folding, with SHA3/EOR3-assisted variants when available. On x86_64, SSE4.2 CRC32 is CRC32C/ISCSI rather than CRC-32/ISO-HDLC, so the relevant acceleration is the PCLMULQDQ / VPCLMULQDQ carry-less multiply family.

martin-g and others added 2 commits September 5, 2026 16:28
The benchmark was useful for comparison between `crc32fast` and `crc-fast` but
we're not going to run those benchmarks again.

@Kriskras99 Kriskras99 left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you for providing a benchmark! I still think you won't see much of a performance difference because the Avro encoder/decoder will be the limiting factor (unless your sending Avro objects with large bytes/string).

I have removed the benchmark in a new commit, so it will still be available in the Git history. The benchmark is good, but something we are going to use only once.

If @martin-g agrees with the MSRV bump from 1.88 to 1.89 this can be merged

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Replace crc32fast with crc-fast for faster Snappy CRC32

3 participants