Table of Contents

macOS Arm64 Apple M4 Hash Benchmarks

Machine Profile

Machine Specification

The benchmarks were run on the following machine:

BenchmarkDotNet v0.15.8, macOS Tahoe 26.3.1 (a) (25D771280a) [Darwin 25.3.0]
Apple M4, 1 CPU, 10 logical and 10 physical cores
.NET SDK 10.0.201
[Host]    : .NET 10.0.5 (10.0.5, 10.0.526.15411), Arm64 RyuJIT armv8.0-a
.NET 10.0 : .NET 10.0.5 (10.0.5, 10.0.526.15411), Arm64 RyuJIT armv8.0-a
Method=TryComputeHash  Job=.NET 10.0  Runtime=.NET 10.0
Toolchain=net10.0

Note: Results are machine-specific and may vary between systems. Run benchmarks locally for your specific hardware.

BenchmarkDotNet measurements for all hash algorithm implementations in CryptoHives.Foundation.Security.Cryptography. Each algorithm is benchmarked across representative payload sizes (128 bytes through 128 KiB) to capture both latency and throughput characteristics.

Implementations are compared against:

  • OS — .NET's built-in System.Security.Cryptography (backed by Apple CommonCrypto on macOS)
  • BouncyCastle — BouncyCastle C# library
  • Native — Platform-specific native libraries (e.g., blake3-dotnet)
  • Managed — CryptoHives managed implementation (scalar)
  • SIMD — CryptoHives SIMD variants (ArmSha256, Neon)

Highlights

Family Leader Key Insight
SHA-2 OS (ArmSha256) Apple CommonCrypto leads: ~2× faster at 128 B, ~13% at 128 KiB; ArmSha256 managed path matches scalar Managed speed
SHA-3/Keccak BouncyCastle BouncyCastle slightly faster than Managed (~6% at bulk sizes); opposite pattern to x86 where scalar Managed leads
BLAKE2b/2s BouncyCastle BouncyCastle ~2× faster than Neon at 128 KiB; Neon ~1.75× faster than Managed
BLAKE3 Native (Rust) Rust ~5.4× faster than BouncyCastle at 128 KiB; Neon ~2.5× faster than BouncyCastle
Streebog Managed ~1.7× faster than OpenGost; ~2.1× faster than BouncyCastle
Kupyna Managed ~1.5× faster than BouncyCastle at all sizes
KMAC Managed ~1.9× faster than BouncyCastle at 128 B; competitive at bulk sizes
Ascon Managed ~42% faster than BouncyCastle across all input sizes
Whirlpool Managed ~4.9× faster than BouncyCastle; ~2.2× faster than Hashify .NET

SHA-2 Family

On Apple M4, System.Security.Cryptography is backed by Apple CommonCrypto which uses the Apple Silicon hardware SHA acceleration. The ArmSha256 managed variant maps to the ARM Cryptography Extension SHA256H/SHA256H2/SHA256SU0/SHA256SU1 instructions — but at these sizes the overhead difference mainly stems from the OS call path being highly optimized. The managed ArmSha256 path provides essentially the same throughput as the scalar Managed path (within 1%), suggesting the JIT already eliminates most overhead once SHA-round dispatch is optimized.

Key observations:

  • OS: Apple Silicon hardware SHA — ~2× faster at 128 B; ~13% faster at 128 KiB
  • ArmSha256 / Managed: Identical throughput; ArmSha256 does not currently provide additional speedup over the scalar path in this .NET version
  • BouncyCastle: ~3.3× slower than OS at 128 B; slower than Managed by ~9.4× at 128 KiB

SHA-224

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · SHA-224 · SHA-224 (ArmSha256) 128B 170.0 ns 0.45 ns 0.40 ns -
TryComputeHash · SHA-224 · Managed 128B 448.9 ns 2.48 ns 2.32 ns -
TryComputeHash · SHA-224 · BouncyCastle 128B 573.5 ns 11.45 ns 16.42 ns -
TryComputeHash · SHA-224 · SHA-224 (ArmSha256) 137B 173.9 ns 0.72 ns 0.64 ns -
TryComputeHash · SHA-224 · Managed 137B 455.1 ns 1.96 ns 1.83 ns -
TryComputeHash · SHA-224 · BouncyCastle 137B 585.5 ns 11.00 ns 11.30 ns -
TryComputeHash · SHA-224 · SHA-224 (ArmSha256) 1KB 458.3 ns 0.20 ns 0.18 ns -
TryComputeHash · SHA-224 · Managed 1KB 2,582.1 ns 15.20 ns 12.69 ns -
TryComputeHash · SHA-224 · BouncyCastle 1KB 3,281.7 ns 54.54 ns 51.02 ns -
TryComputeHash · SHA-224 · SHA-224 (ArmSha256) 1025B 460.7 ns 0.49 ns 0.38 ns -
TryComputeHash · SHA-224 · Managed 1025B 2,586.8 ns 17.83 ns 15.80 ns -
TryComputeHash · SHA-224 · BouncyCastle 1025B 3,291.7 ns 65.63 ns 83.00 ns -
TryComputeHash · SHA-224 · SHA-224 (ArmSha256) 8KB 2,856.0 ns 0.33 ns 0.31 ns -
TryComputeHash · SHA-224 · Managed 8KB 19,502.4 ns 107.67 ns 95.45 ns -
TryComputeHash · SHA-224 · BouncyCastle 8KB 24,739.2 ns 458.45 ns 382.83 ns -
TryComputeHash · SHA-224 · SHA-224 (ArmSha256) 128KB 43,817.6 ns 12.49 ns 11.07 ns -
TryComputeHash · SHA-224 · Managed 128KB 311,483.0 ns 1,365.06 ns 1,210.09 ns -
TryComputeHash · SHA-224 · BouncyCastle 128KB 407,328.5 ns 2,606.36 ns 2,437.99 ns -

SHA-256

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · SHA-256 · OS Native 128B 79.68 ns 0.606 ns 0.567 ns -
TryComputeHash · SHA-256 · SHA-256 (ArmSha256) 128B 175.18 ns 0.638 ns 0.596 ns -
TryComputeHash · SHA-256 · Managed 128B 458.14 ns 2.191 ns 2.050 ns -
TryComputeHash · SHA-256 · BouncyCastle 128B 570.70 ns 11.198 ns 19.014 ns -
TryComputeHash · SHA-256 · OS Native 137B 72.05 ns 0.499 ns 0.467 ns -
TryComputeHash · SHA-256 · SHA-256 (ArmSha256) 137B 176.80 ns 0.664 ns 0.621 ns -
TryComputeHash · SHA-256 · Managed 137B 459.69 ns 1.797 ns 1.681 ns -
TryComputeHash · SHA-256 · BouncyCastle 137B 582.98 ns 11.657 ns 10.904 ns -
TryComputeHash · SHA-256 · OS Native 1KB 340.58 ns 0.494 ns 0.463 ns -
TryComputeHash · SHA-256 · SHA-256 (ArmSha256) 1KB 458.56 ns 0.465 ns 0.435 ns -
TryComputeHash · SHA-256 · Managed 1KB 2,588.03 ns 18.260 ns 16.187 ns -
TryComputeHash · SHA-256 · BouncyCastle 1KB 3,250.13 ns 63.175 ns 84.337 ns -
TryComputeHash · SHA-256 · OS Native 1025B 338.27 ns 2.131 ns 1.993 ns -
TryComputeHash · SHA-256 · SHA-256 (ArmSha256) 1025B 460.46 ns 0.445 ns 0.416 ns -
TryComputeHash · SHA-256 · Managed 1025B 2,591.89 ns 16.700 ns 15.621 ns -
TryComputeHash · SHA-256 · BouncyCastle 1025B 3,272.02 ns 64.334 ns 74.087 ns -
TryComputeHash · SHA-256 · OS Native 8KB 2,444.99 ns 2.162 ns 2.022 ns -
TryComputeHash · SHA-256 · SHA-256 (ArmSha256) 8KB 2,850.38 ns 1.360 ns 1.206 ns -
TryComputeHash · SHA-256 · Managed 8KB 19,641.12 ns 130.529 ns 108.998 ns -
TryComputeHash · SHA-256 · BouncyCastle 8KB 24,775.71 ns 483.461 ns 661.766 ns -
TryComputeHash · SHA-256 · OS Native 128KB 38,582.92 ns 12.580 ns 10.505 ns -
TryComputeHash · SHA-256 · SHA-256 (ArmSha256) 128KB 43,816.48 ns 7.098 ns 6.640 ns -
TryComputeHash · SHA-256 · Managed 128KB 311,959.06 ns 1,520.652 ns 1,269.813 ns -
TryComputeHash · SHA-256 · BouncyCastle 128KB 403,747.61 ns 6,231.446 ns 5,828.898 ns -

SHA-384

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · SHA-384 · OS Native 128B 147.7 ns 0.57 ns 0.53 ns -
TryComputeHash · SHA-384 · Managed 128B 390.0 ns 1.68 ns 1.57 ns -
TryComputeHash · SHA-384 · BouncyCastle 128B 537.1 ns 8.16 ns 7.63 ns -
TryComputeHash · SHA-384 · OS Native 137B 146.2 ns 0.69 ns 0.64 ns -
TryComputeHash · SHA-384 · Managed 137B 391.1 ns 1.25 ns 1.17 ns -
TryComputeHash · SHA-384 · BouncyCastle 137B 536.6 ns 10.37 ns 13.11 ns -
TryComputeHash · SHA-384 · OS Native 1KB 606.8 ns 0.37 ns 0.33 ns -
TryComputeHash · SHA-384 · Managed 1KB 1,734.2 ns 4.89 ns 3.82 ns -
TryComputeHash · SHA-384 · BouncyCastle 1KB 2,358.3 ns 27.23 ns 25.47 ns -
TryComputeHash · SHA-384 · OS Native 1025B 606.5 ns 0.28 ns 0.25 ns -
TryComputeHash · SHA-384 · Managed 1025B 1,735.4 ns 7.23 ns 6.41 ns -
TryComputeHash · SHA-384 · BouncyCastle 1025B 2,348.8 ns 45.02 ns 60.09 ns -
TryComputeHash · SHA-384 · OS Native 8KB 4,368.8 ns 84.52 ns 109.90 ns -
TryComputeHash · SHA-384 · Managed 8KB 12,595.1 ns 70.38 ns 58.77 ns -
TryComputeHash · SHA-384 · BouncyCastle 8KB 17,129.0 ns 328.75 ns 415.77 ns -
TryComputeHash · SHA-384 · OS Native 128KB 68,459.1 ns 917.78 ns 766.39 ns -
TryComputeHash · SHA-384 · Managed 128KB 199,547.9 ns 851.32 ns 710.89 ns -
TryComputeHash · SHA-384 · BouncyCastle 128KB 270,607.2 ns 4,795.72 ns 4,251.28 ns -

SHA-512

Description TestDataSize Mean Error StdDev Median Allocated
TryComputeHash · SHA-512 · OS Native 128B 148.0 ns 0.85 ns 0.80 ns 148.0 ns -
TryComputeHash · SHA-512 · Managed 128B 465.6 ns 2.40 ns 2.24 ns 465.4 ns -
TryComputeHash · SHA-512 · BouncyCastle 128B 542.2 ns 6.98 ns 6.53 ns 544.5 ns -
TryComputeHash · SHA-512 · OS Native 137B 146.4 ns 0.85 ns 0.80 ns 146.1 ns -
TryComputeHash · SHA-512 · Managed 137B 464.2 ns 1.65 ns 1.54 ns 464.5 ns -
TryComputeHash · SHA-512 · BouncyCastle 137B 543.4 ns 6.95 ns 6.50 ns 543.7 ns -
TryComputeHash · SHA-512 · OS Native 1KB 607.2 ns 0.23 ns 0.21 ns 607.2 ns -
TryComputeHash · SHA-512 · BouncyCastle 1KB 2,368.3 ns 45.96 ns 62.91 ns 2,394.2 ns -
TryComputeHash · SHA-512 · Managed 1KB 2,613.0 ns 15.46 ns 14.46 ns 2,610.0 ns -
TryComputeHash · SHA-512 · OS Native 1025B 607.1 ns 0.29 ns 0.28 ns 607.1 ns -
TryComputeHash · SHA-512 · BouncyCastle 1025B 2,371.2 ns 45.99 ns 49.21 ns 2,389.8 ns -
TryComputeHash · SHA-512 · Managed 1025B 2,617.9 ns 17.11 ns 16.00 ns 2,615.1 ns -
TryComputeHash · SHA-512 · OS Native 8KB 4,287.4 ns 1.53 ns 1.35 ns 4,287.7 ns -
TryComputeHash · SHA-512 · BouncyCastle 8KB 16,915.5 ns 334.44 ns 490.21 ns 17,185.1 ns -
TryComputeHash · SHA-512 · Managed 8KB 19,804.6 ns 115.15 ns 107.71 ns 19,809.2 ns -
TryComputeHash · SHA-512 · OS Native 128KB 67,377.1 ns 33.54 ns 28.01 ns 67,384.0 ns -
TryComputeHash · SHA-512 · BouncyCastle 128KB 266,042.6 ns 5,173.74 ns 6,158.97 ns 265,086.0 ns -
TryComputeHash · SHA-512 · Managed 128KB 314,723.8 ns 1,266.49 ns 1,184.68 ns 314,946.9 ns -

SHA-512/224

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · SHA-512/224 · Managed 128B 389.8 ns 1.45 ns 1.36 ns -
TryComputeHash · SHA-512/224 · BouncyCastle 128B 548.4 ns 10.28 ns 10.55 ns -
TryComputeHash · SHA-512/224 · Managed 137B 389.7 ns 1.40 ns 1.24 ns -
TryComputeHash · SHA-512/224 · BouncyCastle 137B 552.8 ns 9.84 ns 9.20 ns -
TryComputeHash · SHA-512/224 · Managed 1KB 1,742.2 ns 6.27 ns 5.56 ns -
TryComputeHash · SHA-512/224 · BouncyCastle 1KB 2,356.8 ns 46.61 ns 65.35 ns -
TryComputeHash · SHA-512/224 · Managed 1025B 1,748.6 ns 7.54 ns 6.69 ns -
TryComputeHash · SHA-512/224 · BouncyCastle 1025B 2,316.2 ns 46.19 ns 53.19 ns -
TryComputeHash · SHA-512/224 · Managed 8KB 12,580.2 ns 62.75 ns 55.63 ns -
TryComputeHash · SHA-512/224 · BouncyCastle 8KB 17,066.2 ns 229.87 ns 215.02 ns -
TryComputeHash · SHA-512/224 · Managed 128KB 198,925.5 ns 903.35 ns 800.80 ns -
TryComputeHash · SHA-512/224 · BouncyCastle 128KB 266,852.4 ns 5,276.13 ns 8,368.50 ns -

SHA-512/256

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · SHA-512/256 · Managed 128B 463.7 ns 1.85 ns 1.73 ns -
TryComputeHash · SHA-512/256 · BouncyCastle 128B 550.1 ns 7.96 ns 7.44 ns -
TryComputeHash · SHA-512/256 · Managed 137B 464.8 ns 1.78 ns 1.67 ns -
TryComputeHash · SHA-512/256 · BouncyCastle 137B 553.2 ns 7.02 ns 6.56 ns -
TryComputeHash · SHA-512/256 · BouncyCastle 1KB 2,374.4 ns 46.72 ns 60.74 ns -
TryComputeHash · SHA-512/256 · Managed 1KB 2,612.7 ns 8.35 ns 7.40 ns -
TryComputeHash · SHA-512/256 · BouncyCastle 1025B 2,372.3 ns 47.19 ns 48.46 ns -
TryComputeHash · SHA-512/256 · Managed 1025B 2,616.9 ns 10.70 ns 8.94 ns -
TryComputeHash · SHA-512/256 · BouncyCastle 8KB 16,802.5 ns 330.58 ns 561.34 ns -
TryComputeHash · SHA-512/256 · Managed 8KB 19,867.2 ns 69.70 ns 65.19 ns -
TryComputeHash · SHA-512/256 · BouncyCastle 128KB 266,985.7 ns 5,245.78 ns 6,244.72 ns -
TryComputeHash · SHA-512/256 · Managed 128KB 313,996.5 ns 2,446.00 ns 1,909.68 ns -

Keccak-derived Families

On Apple M4, BouncyCastle is slightly faster than the CryptoHives managed Keccak core across all payload sizes — the reverse of the x86 Windows result. On x86, the scalar CryptoHives path is ~30% faster than OS SHA-3 due to loop-unrolling and constant elimination that matches well with x86 out-of-order execution. On Apple M4, BouncyCastle's JIT-optimized Keccak permutation is ~6% faster at bulk sizes. Both implementations use scalar arithmetic; neither has an ARM SIMD path yet.

Key observations:

  • BouncyCastle: ~3% faster than Managed at 128 B for SHA3-256; ~6% faster at bulk (1 KiB–128 KiB)
  • No OS SHA-3 comparison available (macOS CommonCrypto does not expose SHA-3 via .NET in current releases)
  • All Keccak variants (SHA-3, SHA-3/SHAKE, cSHAKE, TurboSHAKE, KT) share the same optimized core

SHA-3 Family

SHA3-224

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · SHA3-224 · BouncyCastle 128B 178.4 ns 0.54 ns 0.47 ns -
TryComputeHash · SHA3-224 · Managed 128B 187.9 ns 0.66 ns 0.59 ns -
TryComputeHash · SHA3-224 · Managed 137B 174.0 ns 0.27 ns 0.23 ns -
TryComputeHash · SHA3-224 · BouncyCastle 137B 179.2 ns 0.71 ns 0.67 ns -
TryComputeHash · SHA3-224 · BouncyCastle 1KB 1,263.2 ns 5.30 ns 4.69 ns -
TryComputeHash · SHA3-224 · Managed 1KB 1,488.8 ns 6.39 ns 5.97 ns -
TryComputeHash · SHA3-224 · BouncyCastle 1025B 1,260.1 ns 2.94 ns 2.45 ns -
TryComputeHash · SHA3-224 · Managed 1025B 1,486.6 ns 7.22 ns 6.76 ns -
TryComputeHash · SHA3-224 · BouncyCastle 8KB 8,830.7 ns 34.96 ns 29.19 ns -
TryComputeHash · SHA3-224 · Managed 8KB 9,155.7 ns 7.01 ns 5.85 ns -
TryComputeHash · SHA3-224 · BouncyCastle 128KB 141,121.1 ns 393.86 ns 349.15 ns -
TryComputeHash · SHA3-224 · Managed 128KB 145,538.4 ns 106.83 ns 99.93 ns -

SHA3-256

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · SHA3-256 · Managed 128B 174.5 ns 0.17 ns 0.14 ns -
TryComputeHash · SHA3-256 · BouncyCastle 128B 178.7 ns 0.70 ns 0.62 ns -
TryComputeHash · SHA3-256 · BouncyCastle 137B 326.9 ns 0.82 ns 0.68 ns -
TryComputeHash · SHA3-256 · Managed 137B 537.3 ns 3.41 ns 3.02 ns -
TryComputeHash · SHA3-256 · BouncyCastle 1KB 1,292.7 ns 5.35 ns 5.01 ns -
TryComputeHash · SHA3-256 · Managed 1KB 1,370.9 ns 3.91 ns 3.66 ns -
TryComputeHash · SHA3-256 · BouncyCastle 1025B 1,262.7 ns 5.12 ns 4.79 ns -
TryComputeHash · SHA3-256 · Managed 1025B 1,369.9 ns 2.78 ns 2.46 ns -
TryComputeHash · SHA3-256 · BouncyCastle 8KB 9,422.0 ns 31.33 ns 24.46 ns -
TryComputeHash · SHA3-256 · Managed 8KB 9,904.3 ns 14.91 ns 13.22 ns -
TryComputeHash · SHA3-256 · BouncyCastle 128KB 149,445.9 ns 610.49 ns 571.05 ns -
TryComputeHash · SHA3-256 · Managed 128KB 153,557.5 ns 178.25 ns 166.73 ns -

SHA3-384

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · SHA3-384 · BouncyCastle 128B 325.3 ns 1.03 ns 0.91 ns -
TryComputeHash · SHA3-384 · Managed 128B 442.5 ns 3.24 ns 2.87 ns -
TryComputeHash · SHA3-384 · BouncyCastle 137B 325.3 ns 1.09 ns 0.91 ns -
TryComputeHash · SHA3-384 · Managed 137B 432.3 ns 3.36 ns 3.14 ns -
TryComputeHash · SHA3-384 · BouncyCastle 1KB 1,554.3 ns 1.67 ns 1.30 ns -
TryComputeHash · SHA3-384 · Managed 1KB 1,623.8 ns 2.08 ns 1.94 ns -
TryComputeHash · SHA3-384 · BouncyCastle 1025B 1,555.8 ns 3.74 ns 3.12 ns -
TryComputeHash · SHA3-384 · Managed 1025B 1,621.4 ns 1.68 ns 1.57 ns -
TryComputeHash · SHA3-384 · BouncyCastle 8KB 12,081.3 ns 40.70 ns 33.98 ns -
TryComputeHash · SHA3-384 · Managed 8KB 12,532.1 ns 9.05 ns 8.47 ns -
TryComputeHash · SHA3-384 · BouncyCastle 128KB 192,726.0 ns 553.13 ns 490.34 ns -
TryComputeHash · SHA3-384 · Managed 128KB 199,202.2 ns 237.22 ns 221.89 ns -

SHA3-512

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · SHA3-512 · BouncyCastle 128B 325.5 ns 0.81 ns 0.72 ns -
TryComputeHash · SHA3-512 · Managed 128B 338.9 ns 1.44 ns 1.35 ns -
TryComputeHash · SHA3-512 · Managed 137B 324.9 ns 0.29 ns 0.27 ns -
TryComputeHash · SHA3-512 · BouncyCastle 137B 326.9 ns 0.58 ns 0.52 ns -
TryComputeHash · SHA3-512 · BouncyCastle 1KB 2,297.4 ns 7.32 ns 6.85 ns -
TryComputeHash · SHA3-512 · Managed 1KB 2,464.3 ns 3.70 ns 3.28 ns -
TryComputeHash · SHA3-512 · BouncyCastle 1025B 2,300.1 ns 4.50 ns 3.99 ns -
TryComputeHash · SHA3-512 · Managed 1025B 2,471.6 ns 3.64 ns 3.40 ns -
TryComputeHash · SHA3-512 · BouncyCastle 8KB 17,256.0 ns 13.84 ns 10.80 ns -
TryComputeHash · SHA3-512 · Managed 8KB 17,918.2 ns 26.51 ns 23.50 ns -
TryComputeHash · SHA3-512 · BouncyCastle 128KB 276,340.0 ns 867.90 ns 769.37 ns -
TryComputeHash · SHA3-512 · Managed 128KB 285,566.0 ns 252.29 ns 223.65 ns -

Keccak Family

Keccak-256

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · Keccak-256 · Managed 128B 174.3 ns 0.33 ns 0.27 ns -
TryComputeHash · Keccak-256 · BouncyCastle 128B 177.5 ns 0.43 ns 0.36 ns -
TryComputeHash · Keccak-256 · BouncyCastle 137B 323.8 ns 1.42 ns 1.26 ns -
TryComputeHash · Keccak-256 · Managed 137B 536.2 ns 8.60 ns 8.05 ns -
TryComputeHash · Keccak-256 · BouncyCastle 1KB 1,258.5 ns 1.17 ns 1.04 ns -
TryComputeHash · Keccak-256 · Managed 1KB 1,373.1 ns 6.88 ns 6.44 ns -
TryComputeHash · Keccak-256 · BouncyCastle 1025B 1,270.2 ns 11.39 ns 10.65 ns -
TryComputeHash · Keccak-256 · Managed 1025B 1,380.4 ns 4.54 ns 4.25 ns -
TryComputeHash · Keccak-256 · BouncyCastle 8KB 9,453.5 ns 66.12 ns 61.85 ns -
TryComputeHash · Keccak-256 · Managed 8KB 9,864.7 ns 9.46 ns 7.90 ns -
TryComputeHash · Keccak-256 · BouncyCastle 128KB 148,905.0 ns 576.05 ns 449.74 ns -
TryComputeHash · Keccak-256 · Managed 128KB 153,314.5 ns 124.84 ns 104.24 ns -

Keccak-384

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · Keccak-384 · BouncyCastle 128B 324.3 ns 0.81 ns 0.68 ns -
TryComputeHash · Keccak-384 · Managed 128B 442.3 ns 4.98 ns 4.66 ns -
TryComputeHash · Keccak-384 · BouncyCastle 137B 322.7 ns 1.08 ns 0.96 ns -
TryComputeHash · Keccak-384 · Managed 137B 432.9 ns 4.32 ns 4.04 ns -
TryComputeHash · Keccak-384 · BouncyCastle 1KB 1,553.2 ns 2.35 ns 2.09 ns -
TryComputeHash · Keccak-384 · Managed 1KB 1,620.2 ns 1.50 ns 1.33 ns -
TryComputeHash · Keccak-384 · BouncyCastle 1025B 1,563.9 ns 6.69 ns 5.93 ns -
TryComputeHash · Keccak-384 · Managed 1025B 1,623.0 ns 2.57 ns 2.40 ns -
TryComputeHash · Keccak-384 · BouncyCastle 8KB 12,060.6 ns 30.97 ns 27.45 ns -
TryComputeHash · Keccak-384 · Managed 8KB 12,493.3 ns 13.97 ns 11.67 ns -
TryComputeHash · Keccak-384 · BouncyCastle 128KB 194,692.5 ns 1,329.12 ns 1,243.26 ns -
TryComputeHash · Keccak-384 · Managed 128KB 199,130.7 ns 137.18 ns 121.60 ns -

Keccak-512

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · Keccak-512 · BouncyCastle 128B 332.0 ns 1.61 ns 1.35 ns -
TryComputeHash · Keccak-512 · Managed 128B 339.6 ns 1.09 ns 1.02 ns -
TryComputeHash · Keccak-512 · BouncyCastle 137B 325.5 ns 0.82 ns 0.73 ns -
TryComputeHash · Keccak-512 · Managed 137B 326.6 ns 0.47 ns 0.44 ns -
TryComputeHash · Keccak-512 · BouncyCastle 1KB 2,294.5 ns 13.52 ns 11.99 ns -
TryComputeHash · Keccak-512 · Managed 1KB 2,465.2 ns 6.21 ns 5.50 ns -
TryComputeHash · Keccak-512 · BouncyCastle 1025B 2,293.8 ns 7.79 ns 7.28 ns -
TryComputeHash · Keccak-512 · Managed 1025B 2,471.1 ns 3.73 ns 3.49 ns -
TryComputeHash · Keccak-512 · BouncyCastle 8KB 17,241.7 ns 79.50 ns 74.36 ns -
TryComputeHash · Keccak-512 · Managed 8KB 17,902.8 ns 14.14 ns 11.80 ns -
TryComputeHash · Keccak-512 · BouncyCastle 128KB 276,515.7 ns 1,643.96 ns 1,457.33 ns -
TryComputeHash · Keccak-512 · Managed 128KB 285,609.2 ns 310.91 ns 275.61 ns -

SHAKE Family

SHAKE128

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · SHAKE128 · BouncyCastle 128B 179.4 ns 0.82 ns 0.68 ns -
TryComputeHash · SHAKE128 · Managed 128B 254.2 ns 3.76 ns 3.52 ns -
TryComputeHash · SHAKE128 · BouncyCastle 137B 178.6 ns 0.72 ns 0.64 ns -
TryComputeHash · SHAKE128 · Managed 137B 240.5 ns 2.59 ns 2.43 ns -
TryComputeHash · SHAKE128 · BouncyCastle 1KB 1,117.8 ns 6.34 ns 5.93 ns -
TryComputeHash · SHAKE128 · Managed 1KB 1,398.0 ns 6.15 ns 5.75 ns -
TryComputeHash · SHAKE128 · BouncyCastle 1025B 1,122.5 ns 12.39 ns 11.59 ns -
TryComputeHash · SHAKE128 · Managed 1025B 1,387.5 ns 4.56 ns 4.04 ns -
TryComputeHash · SHAKE128 · BouncyCastle 8KB 7,709.6 ns 70.68 ns 66.12 ns -
TryComputeHash · SHAKE128 · Managed 8KB 7,941.5 ns 14.61 ns 13.66 ns -
TryComputeHash · SHAKE128 · BouncyCastle 128KB 122,470.6 ns 299.87 ns 250.40 ns -
TryComputeHash · SHAKE128 · Managed 128KB 124,864.3 ns 179.57 ns 167.97 ns -

SHAKE256

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · SHAKE256 · BouncyCastle 128B 179.3 ns 1.11 ns 1.03 ns -
TryComputeHash · SHAKE256 · Managed 128B 248.2 ns 4.84 ns 6.29 ns -
TryComputeHash · SHAKE256 · BouncyCastle 137B 324.9 ns 0.80 ns 0.67 ns -
TryComputeHash · SHAKE256 · Managed 137B 588.0 ns 5.33 ns 4.98 ns -
TryComputeHash · SHAKE256 · BouncyCastle 1KB 1,258.7 ns 6.83 ns 6.06 ns -
TryComputeHash · SHAKE256 · Managed 1KB 1,440.3 ns 4.97 ns 4.65 ns -
TryComputeHash · SHAKE256 · BouncyCastle 1025B 1,257.5 ns 2.80 ns 2.48 ns -
TryComputeHash · SHAKE256 · Managed 1025B 1,437.1 ns 3.98 ns 3.53 ns -
TryComputeHash · SHAKE256 · BouncyCastle 8KB 9,350.1 ns 25.95 ns 23.00 ns -
TryComputeHash · SHAKE256 · Managed 8KB 9,956.9 ns 15.32 ns 14.33 ns -
TryComputeHash · SHAKE256 · BouncyCastle 128KB 148,760.9 ns 607.14 ns 567.92 ns -
TryComputeHash · SHAKE256 · Managed 128KB 153,264.9 ns 163.57 ns 153.00 ns -

cSHAKE Family

cSHAKE128

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · cSHAKE128 · BouncyCastle 128B 179.7 ns 0.47 ns 0.44 ns -
TryComputeHash · cSHAKE128 · Managed 128B 257.8 ns 3.90 ns 3.65 ns -
TryComputeHash · cSHAKE128 · BouncyCastle 137B 179.6 ns 0.34 ns 0.26 ns -
TryComputeHash · cSHAKE128 · Managed 137B 244.1 ns 2.45 ns 2.29 ns -
TryComputeHash · cSHAKE128 · BouncyCastle 1KB 1,122.5 ns 3.05 ns 2.85 ns -
TryComputeHash · cSHAKE128 · Managed 1KB 1,438.8 ns 8.04 ns 7.52 ns -
TryComputeHash · cSHAKE128 · BouncyCastle 1025B 1,118.7 ns 4.02 ns 3.57 ns -
TryComputeHash · cSHAKE128 · Managed 1025B 1,399.7 ns 6.28 ns 5.88 ns -
TryComputeHash · cSHAKE128 · BouncyCastle 8KB 7,749.0 ns 25.77 ns 24.10 ns -
TryComputeHash · cSHAKE128 · Managed 8KB 7,931.3 ns 14.68 ns 13.73 ns -
TryComputeHash · cSHAKE128 · BouncyCastle 128KB 122,967.8 ns 963.52 ns 854.13 ns -
TryComputeHash · cSHAKE128 · Managed 128KB 124,838.3 ns 200.26 ns 187.32 ns -

cSHAKE256

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · cSHAKE256 · BouncyCastle 128B 178.1 ns 0.47 ns 0.39 ns -
TryComputeHash · cSHAKE256 · Managed 128B 249.6 ns 4.99 ns 4.90 ns -
TryComputeHash · cSHAKE256 · BouncyCastle 137B 334.4 ns 0.49 ns 0.45 ns -
TryComputeHash · cSHAKE256 · Managed 137B 598.6 ns 7.81 ns 7.31 ns -
TryComputeHash · cSHAKE256 · BouncyCastle 1KB 1,260.1 ns 3.27 ns 2.90 ns -
TryComputeHash · cSHAKE256 · Managed 1KB 1,457.4 ns 6.80 ns 6.36 ns -
TryComputeHash · cSHAKE256 · BouncyCastle 1025B 1,260.0 ns 1.73 ns 1.53 ns -
TryComputeHash · cSHAKE256 · Managed 1025B 1,455.6 ns 5.10 ns 4.52 ns -
TryComputeHash · cSHAKE256 · BouncyCastle 8KB 9,476.6 ns 41.46 ns 34.62 ns -
TryComputeHash · cSHAKE256 · Managed 8KB 9,955.0 ns 14.10 ns 12.50 ns -
TryComputeHash · cSHAKE256 · BouncyCastle 128KB 149,114.3 ns 652.89 ns 610.71 ns -
TryComputeHash · cSHAKE256 · Managed 128KB 153,704.6 ns 208.63 ns 195.15 ns -

KangarooTwelve Family

KT128

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · KT128 · Managed 128B 157.2 ns 0.43 ns 0.40 ns -
TryComputeHash · KT128 · Managed 137B 146.9 ns 0.73 ns 0.69 ns -
TryComputeHash · KT128 · Managed 1KB 843.4 ns 1.92 ns 1.80 ns -
TryComputeHash · KT128 · Managed 1025B 841.1 ns 5.16 ns 4.82 ns -
TryComputeHash · KT128 · Managed 8KB 5,699.2 ns 31.77 ns 29.72 ns -
TryComputeHash · KT128 · Managed 128KB 80,819.1 ns 411.70 ns 364.96 ns -

KT256

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · KT256 · Managed 128B 140.0 ns 0.17 ns 0.15 ns -
TryComputeHash · KT256 · Managed 137B 314.0 ns 1.27 ns 1.18 ns -
TryComputeHash · KT256 · Managed 1KB 777.9 ns 1.07 ns 1.00 ns -
TryComputeHash · KT256 · Managed 1025B 781.2 ns 2.25 ns 2.10 ns -
TryComputeHash · KT256 · Managed 8KB 5,906.3 ns 8.72 ns 6.80 ns -
TryComputeHash · KT256 · Managed 128KB 89,255.0 ns 286.01 ns 223.30 ns -

TurboSHAKE Family

TurboSHAKE128

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · TurboSHAKE128-32 · Managed 128B 179.3 ns 3.19 ns 2.98 ns -
TryComputeHash · TurboSHAKE128-32 · Managed 137B 164.5 ns 3.09 ns 2.89 ns -
TryComputeHash · TurboSHAKE128-32 · Managed 1KB 886.0 ns 6.36 ns 5.64 ns -
TryComputeHash · TurboSHAKE128-32 · Managed 1025B 880.6 ns 7.34 ns 6.87 ns -
TryComputeHash · TurboSHAKE128-32 · Managed 8KB 4,302.0 ns 8.87 ns 7.86 ns -
TryComputeHash · TurboSHAKE128-32 · Managed 128KB 67,024.2 ns 72.88 ns 64.61 ns -
TryComputeHash · TurboSHAKE128-64 · Managed 128B 213.9 ns 4.15 ns 4.94 ns -
TryComputeHash · TurboSHAKE128-64 · Managed 137B 201.9 ns 3.66 ns 3.42 ns -
TryComputeHash · TurboSHAKE128-64 · Managed 1KB 929.0 ns 6.30 ns 5.90 ns -
TryComputeHash · TurboSHAKE128-64 · Managed 1025B 922.3 ns 5.05 ns 4.73 ns -
TryComputeHash · TurboSHAKE128-64 · Managed 8KB 4,338.8 ns 7.22 ns 6.75 ns -
TryComputeHash · TurboSHAKE128-64 · Managed 128KB 67,115.4 ns 118.06 ns 104.66 ns -

TurboSHAKE256

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · TurboSHAKE256 · Managed 128B 167.1 ns 3.33 ns 4.56 ns -
TryComputeHash · TurboSHAKE256 · Managed 137B 439.6 ns 4.10 ns 3.84 ns -
TryComputeHash · TurboSHAKE256 · Managed 1KB 857.3 ns 5.83 ns 5.45 ns -
TryComputeHash · TurboSHAKE256 · Managed 1025B 872.6 ns 4.07 ns 3.61 ns -
TryComputeHash · TurboSHAKE256 · Managed 8KB 5,442.8 ns 6.18 ns 5.48 ns -
TryComputeHash · TurboSHAKE256 · Managed 128KB 81,878.3 ns 110.73 ns 103.58 ns -

BLAKE2 Family

BouncyCastle leads the BLAKE2 benchmarks on Apple M4 — its JIT-compiled implementation is ~2× faster than the CryptoHives NEON path at 128 KiB. The CryptoHives NEON variant uses Vector128<ulong> G-function mixing with AdvSimd rotate-and-shift sequences, providing ~1.75× speedup over the scalar Managed path. The Konscious reference library is the slowest across most sizes and allocates heavily (~130 KB per 128 KiB hash call).

Key observations:

  • BouncyCastle: ~2× faster than Neon at 128 KiB; ~56% faster at 128 B
  • Neon: ~1.75× faster than Managed scalar at 128 KiB; zero allocation
  • Managed: Scalar fallback for non-SIMD platforms; zero allocation
  • Konscious: Allocates ~130 KB per 128 KiB call; slowest option

BLAKE2b-256

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · BLAKE2b-256 · BouncyCastle 128B 126.8 ns 0.13 ns 0.12 ns -
TryComputeHash · BLAKE2b-256 · BLAKE2b-256 (Neon) 128B 224.2 ns 2.35 ns 2.20 ns -
TryComputeHash · BLAKE2b-256 · Managed 128B 386.8 ns 1.52 ns 1.27 ns -
TryComputeHash · BLAKE2b-256 · BLAKE2b-256 (Konscious) 128B 588.5 ns 5.59 ns 4.96 ns 1120 B
TryComputeHash · BLAKE2b-256 · BouncyCastle 137B 231.8 ns 0.39 ns 0.31 ns -
TryComputeHash · BLAKE2b-256 · BLAKE2b-256 (Neon) 137B 440.5 ns 3.09 ns 2.74 ns -
TryComputeHash · BLAKE2b-256 · Managed 137B 763.0 ns 2.62 ns 2.32 ns -
TryComputeHash · BLAKE2b-256 · BLAKE2b-256 (Konscious) 137B 1,119.7 ns 21.75 ns 23.28 ns 1136 B
TryComputeHash · BLAKE2b-256 · BouncyCastle 1KB 869.8 ns 0.86 ns 0.76 ns -
TryComputeHash · BLAKE2b-256 · BLAKE2b-256 (Neon) 1KB 1,758.5 ns 33.42 ns 35.76 ns -
TryComputeHash · BLAKE2b-256 · Managed 1KB 3,018.0 ns 14.26 ns 11.91 ns -
TryComputeHash · BLAKE2b-256 · BLAKE2b-256 (Konscious) 1KB 3,984.4 ns 78.04 ns 146.57 ns 2016 B
TryComputeHash · BLAKE2b-256 · BouncyCastle 1025B 974.9 ns 1.78 ns 1.66 ns -
TryComputeHash · BLAKE2b-256 · BLAKE2b-256 (Neon) 1025B 1,973.8 ns 15.20 ns 13.47 ns -
TryComputeHash · BLAKE2b-256 · Managed 1025B 3,445.9 ns 10.55 ns 9.87 ns -
TryComputeHash · BLAKE2b-256 · BLAKE2b-256 (Konscious) 1025B 4,235.6 ns 23.97 ns 22.42 ns 2024 B
TryComputeHash · BLAKE2b-256 · BouncyCastle 8KB 6,795.9 ns 3.04 ns 2.84 ns -
TryComputeHash · BLAKE2b-256 · BLAKE2b-256 (Neon) 8KB 13,796.2 ns 9.73 ns 9.10 ns -
TryComputeHash · BLAKE2b-256 · Managed 8KB 24,216.6 ns 101.22 ns 89.73 ns -
TryComputeHash · BLAKE2b-256 · BLAKE2b-256 (Konscious) 8KB 28,571.0 ns 69.23 ns 64.75 ns 9184 B
TryComputeHash · BLAKE2b-256 · BouncyCastle 128KB 108,377.6 ns 56.67 ns 47.32 ns -
TryComputeHash · BLAKE2b-256 · BLAKE2b-256 (Neon) 128KB 220,543.9 ns 41.81 ns 37.06 ns -
TryComputeHash · BLAKE2b-256 · Managed 128KB 386,270.7 ns 1,292.85 ns 1,209.33 ns -
TryComputeHash · BLAKE2b-256 · BLAKE2b-256 (Konscious) 128KB 463,095.6 ns 1,105.01 ns 1,033.63 ns 132092 B

BLAKE2b-512

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · BLAKE2b-512 · BouncyCastle 128B 129.2 ns 0.11 ns 0.10 ns -
TryComputeHash · BLAKE2b-512 · BLAKE2b-512 (Neon) 128B 227.1 ns 1.02 ns 0.96 ns -
TryComputeHash · BLAKE2b-512 · Managed 128B 386.6 ns 1.06 ns 0.99 ns -
TryComputeHash · BLAKE2b-512 · BLAKE2b-512 (Konscious) 128B 596.6 ns 2.26 ns 2.12 ns 1216 B
TryComputeHash · BLAKE2b-512 · BouncyCastle 137B 234.0 ns 0.16 ns 0.15 ns -
TryComputeHash · BLAKE2b-512 · BLAKE2b-512 (Neon) 137B 438.1 ns 0.19 ns 0.17 ns -
TryComputeHash · BLAKE2b-512 · Managed 137B 762.1 ns 2.69 ns 2.51 ns -
TryComputeHash · BLAKE2b-512 · BLAKE2b-512 (Konscious) 137B 1,095.4 ns 7.26 ns 6.44 ns 1232 B
TryComputeHash · BLAKE2b-512 · BouncyCastle 1KB 872.5 ns 0.65 ns 0.61 ns -
TryComputeHash · BLAKE2b-512 · BLAKE2b-512 (Neon) 1KB 1,731.2 ns 0.44 ns 0.41 ns -
TryComputeHash · BLAKE2b-512 · Managed 1KB 3,022.8 ns 10.77 ns 10.08 ns -
TryComputeHash · BLAKE2b-512 · BLAKE2b-512 (Konscious) 1KB 3,743.0 ns 19.49 ns 16.27 ns 2112 B
TryComputeHash · BLAKE2b-512 · BouncyCastle 1025B 977.1 ns 1.41 ns 1.17 ns -
TryComputeHash · BLAKE2b-512 · BLAKE2b-512 (Neon) 1025B 1,951.8 ns 4.56 ns 3.81 ns -
TryComputeHash · BLAKE2b-512 · Managed 1025B 3,426.2 ns 12.55 ns 11.13 ns -
TryComputeHash · BLAKE2b-512 · BLAKE2b-512 (Konscious) 1025B 4,273.5 ns 42.90 ns 35.82 ns 2120 B
TryComputeHash · BLAKE2b-512 · BouncyCastle 8KB 6,796.7 ns 14.28 ns 12.66 ns -
TryComputeHash · BLAKE2b-512 · BLAKE2b-512 (Neon) 8KB 13,886.2 ns 83.08 ns 69.37 ns -
TryComputeHash · BLAKE2b-512 · Managed 8KB 24,317.0 ns 95.63 ns 89.45 ns -
TryComputeHash · BLAKE2b-512 · BLAKE2b-512 (Konscious) 8KB 28,806.0 ns 115.69 ns 96.61 ns 9280 B
TryComputeHash · BLAKE2b-512 · BouncyCastle 128KB 108,368.7 ns 341.95 ns 285.54 ns -
TryComputeHash · BLAKE2b-512 · BLAKE2b-512 (Neon) 128KB 222,781.4 ns 1,374.85 ns 1,073.40 ns -
TryComputeHash · BLAKE2b-512 · Managed 128KB 389,464.6 ns 3,276.30 ns 2,735.86 ns -
TryComputeHash · BLAKE2b-512 · BLAKE2b-512 (Konscious) 128KB 467,503.4 ns 1,620.49 ns 1,436.52 ns 132188 B

BLAKE2s-128

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · BLAKE2s-128 · BouncyCastle 128B 196.2 ns 0.16 ns 0.15 ns -
TryComputeHash · BLAKE2s-128 · BLAKE2s-128 (Neon) 128B 355.4 ns 2.65 ns 2.35 ns -
TryComputeHash · BLAKE2s-128 · Managed 128B 631.7 ns 2.46 ns 2.18 ns -
TryComputeHash · BLAKE2s-128 · BouncyCastle 137B 285.0 ns 0.68 ns 0.57 ns -
TryComputeHash · BLAKE2s-128 · BLAKE2s-128 (Neon) 137B 529.6 ns 0.65 ns 0.61 ns -
TryComputeHash · BLAKE2s-128 · Managed 137B 941.2 ns 4.30 ns 3.35 ns -
TryComputeHash · BLAKE2s-128 · BouncyCastle 1KB 1,450.3 ns 4.49 ns 3.50 ns -
TryComputeHash · BLAKE2s-128 · BLAKE2s-128 (Neon) 1KB 2,795.6 ns 5.73 ns 5.08 ns -
TryComputeHash · BLAKE2s-128 · Managed 1KB 4,999.6 ns 36.27 ns 35.62 ns -
TryComputeHash · BLAKE2s-128 · BouncyCastle 1025B 1,539.9 ns 1.46 ns 1.30 ns -
TryComputeHash · BLAKE2s-128 · BLAKE2s-128 (Neon) 1025B 2,967.6 ns 1.33 ns 1.04 ns -
TryComputeHash · BLAKE2s-128 · Managed 1025B 5,303.7 ns 35.66 ns 27.84 ns -
TryComputeHash · BLAKE2s-128 · BouncyCastle 8KB 11,460.3 ns 9.59 ns 8.97 ns -
TryComputeHash · BLAKE2s-128 · BLAKE2s-128 (Neon) 8KB 22,297.2 ns 15.85 ns 14.83 ns -
TryComputeHash · BLAKE2s-128 · Managed 8KB 39,627.8 ns 225.81 ns 200.17 ns -
TryComputeHash · BLAKE2s-128 · BouncyCastle 128KB 182,969.4 ns 589.31 ns 551.24 ns -
TryComputeHash · BLAKE2s-128 · BLAKE2s-128 (Neon) 128KB 356,389.5 ns 56.26 ns 49.87 ns -
TryComputeHash · BLAKE2s-128 · Managed 128KB 633,907.8 ns 3,289.33 ns 2,746.74 ns -

BLAKE2s-256

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · BLAKE2s-256 · BouncyCastle 128B 197.0 ns 0.32 ns 0.28 ns -
TryComputeHash · BLAKE2s-256 · BLAKE2s-256 (Neon) 128B 352.9 ns 1.23 ns 0.96 ns -
TryComputeHash · BLAKE2s-256 · Managed 128B 629.2 ns 3.92 ns 3.47 ns -
TryComputeHash · BLAKE2s-256 · BouncyCastle 137B 285.7 ns 0.61 ns 0.57 ns -
TryComputeHash · BLAKE2s-256 · BLAKE2s-256 (Neon) 137B 529.8 ns 0.88 ns 0.78 ns -
TryComputeHash · BLAKE2s-256 · Managed 137B 941.5 ns 4.14 ns 3.67 ns -
TryComputeHash · BLAKE2s-256 · BouncyCastle 1KB 1,449.8 ns 1.28 ns 1.20 ns -
TryComputeHash · BLAKE2s-256 · BLAKE2s-256 (Neon) 1KB 2,791.0 ns 11.21 ns 9.94 ns -
TryComputeHash · BLAKE2s-256 · Managed 1KB 4,969.1 ns 25.39 ns 23.75 ns -
TryComputeHash · BLAKE2s-256 · BouncyCastle 1025B 1,538.1 ns 2.69 ns 2.38 ns -
TryComputeHash · BLAKE2s-256 · BLAKE2s-256 (Neon) 1025B 2,957.3 ns 2.52 ns 2.23 ns -
TryComputeHash · BLAKE2s-256 · Managed 1025B 5,268.1 ns 22.24 ns 20.80 ns -
TryComputeHash · BLAKE2s-256 · BouncyCastle 8KB 11,454.4 ns 10.12 ns 8.97 ns -
TryComputeHash · BLAKE2s-256 · BLAKE2s-256 (Neon) 8KB 22,208.3 ns 9.78 ns 9.15 ns -
TryComputeHash · BLAKE2s-256 · Managed 8KB 39,507.8 ns 198.24 ns 185.44 ns -
TryComputeHash · BLAKE2s-256 · BouncyCastle 128KB 183,111.0 ns 170.96 ns 159.91 ns -
TryComputeHash · BLAKE2s-256 · BLAKE2s-256 (Neon) 128KB 355,336.3 ns 217.66 ns 192.95 ns -
TryComputeHash · BLAKE2s-256 · Managed 128KB 632,199.8 ns 2,492.04 ns 2,331.06 ns -

BLAKE3

BLAKE3 is a modern hash function designed for extreme parallelism. At 128 KiB, the Native (Rust) variant via blake3-dotnet is ~5.4× faster than BouncyCastle and ~2.6× faster than the NEON path. The gap is smaller than on x86 (where the Rust build uses AVX-512 hash_many for ~12× advantage) because the ARM Rust build uses a single-threaded NEON path that is comparable in architecture to the CryptoHives Neon path — the key difference is that the Rust build also enables tree-hash parallelism via NEON-based chunk merging at 128 KiB, while the CryptoHives implementation processes chunks sequentially.

The CryptoHives Neon path uses Vector128<uint> for the BLAKE3 compression function (same G-function as ChaCha20), yielding ~2.5× speedup over BouncyCastle at 128 KiB. The scalar Managed path is ~1.4× faster than BouncyCastle at 128 B and ~1.3× at 128 KiB.

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · BLAKE3 · Native 128B 99.74 ns 0.154 ns 0.144 ns -
TryComputeHash · BLAKE3 · BLAKE3 (Neon) 128B 240.25 ns 0.670 ns 0.594 ns -
TryComputeHash · BLAKE3 · Managed 128B 505.29 ns 2.636 ns 2.466 ns -
TryComputeHash · BLAKE3 · BouncyCastle 128B 714.68 ns 2.053 ns 1.920 ns -
TryComputeHash · BLAKE3 · Native 137B 145.58 ns 0.719 ns 0.672 ns -
TryComputeHash · BLAKE3 · BLAKE3 (Neon) 137B 362.87 ns 0.268 ns 0.238 ns -
TryComputeHash · BLAKE3 · Managed 137B 747.42 ns 4.896 ns 4.340 ns -
TryComputeHash · BLAKE3 · BouncyCastle 137B 1,056.22 ns 3.525 ns 3.298 ns -
TryComputeHash · BLAKE3 · Native 1KB 755.99 ns 2.791 ns 2.611 ns -
TryComputeHash · BLAKE3 · BLAKE3 (Neon) 1KB 1,932.62 ns 1.334 ns 1.114 ns -
TryComputeHash · BLAKE3 · Managed 1KB 3,831.31 ns 17.674 ns 16.532 ns -
TryComputeHash · BLAKE3 · BouncyCastle 1KB 5,270.17 ns 15.810 ns 14.789 ns -
TryComputeHash · BLAKE3 · Native 1025B 863.61 ns 3.061 ns 2.863 ns -
TryComputeHash · BLAKE3 · BLAKE3 (Neon) 1025B 2,174.50 ns 2.289 ns 1.911 ns -
TryComputeHash · BLAKE3 · Managed 1025B 4,488.02 ns 30.551 ns 28.578 ns -
TryComputeHash · BLAKE3 · BouncyCastle 1025B 6,000.20 ns 17.223 ns 16.110 ns 56 B
TryComputeHash · BLAKE3 · Native 8KB 3,248.31 ns 8.311 ns 7.368 ns -
TryComputeHash · BLAKE3 · BLAKE3 (Neon) 8KB 17,042.59 ns 18.431 ns 16.339 ns -
TryComputeHash · BLAKE3 · Managed 8KB 33,495.59 ns 171.921 ns 160.815 ns -
TryComputeHash · BLAKE3 · BouncyCastle 8KB 44,356.23 ns 151.736 ns 134.510 ns 392 B
TryComputeHash · BLAKE3 · Native 128KB 51,209.95 ns 144.621 ns 120.765 ns -
TryComputeHash · BLAKE3 · BLAKE3 (Neon) 128KB 277,998.47 ns 261.820 ns 232.097 ns -
TryComputeHash · BLAKE3 · Managed 128KB 539,463.51 ns 3,637.687 ns 3,402.694 ns -
TryComputeHash · BLAKE3 · BouncyCastle 128KB 710,528.83 ns 1,396.229 ns 1,237.721 ns 7112 B

Ascon Family

Ascon is a lightweight NIST standard (2023) designed for constrained environments. The CryptoHives managed implementation is ~42% faster than BouncyCastle at all input sizes (128 B through 128 KiB) — a stronger margin than on x86 Windows (~33%). This appears to be due to Apple M4's efficient branch prediction and low-latency ALU pipeline fitting Ascon's simple 5-word permutation structure very well.

Ascon-Hash256

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · Ascon-Hash256 · Managed 128B 598.5 ns 0.99 ns 0.92 ns -
TryComputeHash · Ascon-Hash256 · BouncyCastle 128B 857.9 ns 2.35 ns 2.08 ns -
TryComputeHash · Ascon-Hash256 · Managed 137B 630.6 ns 2.94 ns 2.75 ns -
TryComputeHash · Ascon-Hash256 · BouncyCastle 137B 907.0 ns 2.52 ns 2.24 ns -
TryComputeHash · Ascon-Hash256 · Managed 1KB 4,017.3 ns 24.21 ns 22.65 ns -
TryComputeHash · Ascon-Hash256 · BouncyCastle 1KB 5,714.4 ns 26.47 ns 24.76 ns -
TryComputeHash · Ascon-Hash256 · Managed 1025B 4,020.5 ns 23.74 ns 22.20 ns -
TryComputeHash · Ascon-Hash256 · BouncyCastle 1025B 5,748.5 ns 23.11 ns 21.62 ns -
TryComputeHash · Ascon-Hash256 · Managed 8KB 31,408.1 ns 207.73 ns 194.31 ns -
TryComputeHash · Ascon-Hash256 · BouncyCastle 8KB 44,646.2 ns 173.55 ns 153.84 ns -
TryComputeHash · Ascon-Hash256 · Managed 128KB 493,616.6 ns 3,217.26 ns 2,852.02 ns -
TryComputeHash · Ascon-Hash256 · BouncyCastle 128KB 717,157.4 ns 2,852.67 ns 2,528.82 ns -

Ascon-XOF128

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · Ascon-XOF128 · Managed 128B 600.5 ns 3.50 ns 3.28 ns -
TryComputeHash · Ascon-XOF128 · BouncyCastle 128B 869.1 ns 2.17 ns 2.03 ns -
TryComputeHash · Ascon-XOF128 · Managed 137B 632.1 ns 3.26 ns 2.89 ns -
TryComputeHash · Ascon-XOF128 · BouncyCastle 137B 917.4 ns 2.47 ns 2.31 ns -
TryComputeHash · Ascon-XOF128 · Managed 1KB 4,013.3 ns 26.30 ns 24.60 ns -
TryComputeHash · Ascon-XOF128 · BouncyCastle 1KB 5,746.4 ns 17.95 ns 15.91 ns -
TryComputeHash · Ascon-XOF128 · Managed 1025B 4,012.3 ns 24.79 ns 23.19 ns -
TryComputeHash · Ascon-XOF128 · BouncyCastle 1025B 5,754.4 ns 20.79 ns 19.45 ns -
TryComputeHash · Ascon-XOF128 · Managed 8KB 31,381.1 ns 238.36 ns 222.96 ns -
TryComputeHash · Ascon-XOF128 · BouncyCastle 8KB 44,900.4 ns 152.65 ns 135.32 ns -
TryComputeHash · Ascon-XOF128 · Managed 128KB 501,648.5 ns 3,485.88 ns 3,260.69 ns -
TryComputeHash · Ascon-XOF128 · BouncyCastle 128KB 715,846.4 ns 1,428.30 ns 1,336.03 ns -

KMAC Family

KMAC (NIST SP 800-185) is a Keccak-based keyed hash function. On Apple M4, the Managed CryptoHives implementation is ~1.9× faster than BouncyCastle at 128 B and leads up to ~1 KiB. At larger sizes (128 KiB), the gap narrows to near parity (~BouncyCastle 1.7% faster). This differs from x86 where Managed leads at all sizes. The convergence at bulk sizes reflects the Keccak permutation throughput being similar after the per-call overhead is amortized.

KMAC128

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · KMAC-128 · Managed 128B 557.4 ns 1.25 ns 1.11 ns -
TryComputeHash · KMAC-128 · BouncyCastle 128B 1,074.6 ns 3.61 ns 3.20 ns 256 B
TryComputeHash · KMAC-128 · Managed 137B 546.3 ns 0.87 ns 0.77 ns -
TryComputeHash · KMAC-128 · BouncyCastle 137B 1,075.0 ns 4.42 ns 3.92 ns 256 B
TryComputeHash · KMAC-128 · Managed 1KB 1,594.5 ns 2.98 ns 2.49 ns -
TryComputeHash · KMAC-128 · BouncyCastle 1KB 2,212.7 ns 8.83 ns 7.83 ns 256 B
TryComputeHash · KMAC-128 · Managed 1025B 1,594.4 ns 4.10 ns 3.43 ns -
TryComputeHash · KMAC-128 · BouncyCastle 1025B 2,027.5 ns 5.90 ns 5.23 ns 256 B
TryComputeHash · KMAC-128 · Managed 8KB 8,228.1 ns 23.48 ns 19.61 ns -
TryComputeHash · KMAC-128 · BouncyCastle 8KB 9,826.3 ns 22.68 ns 20.11 ns 256 B
TryComputeHash · KMAC-128 · BouncyCastle 128KB 122,909.7 ns 205.37 ns 182.05 ns 256 B
TryComputeHash · KMAC-128 · Managed 128KB 125,100.2 ns 154.87 ns 129.32 ns -

KMAC256

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · KMAC-256 · Managed 128B 555.8 ns 0.79 ns 0.66 ns -
TryComputeHash · KMAC-256 · BouncyCastle 128B 1,034.9 ns 2.73 ns 2.55 ns 256 B
TryComputeHash · KMAC-256 · Managed 137B 821.6 ns 1.45 ns 1.28 ns -
TryComputeHash · KMAC-256 · BouncyCastle 137B 1,214.1 ns 11.47 ns 9.58 ns 256 B
TryComputeHash · KMAC-256 · Managed 1KB 1,704.5 ns 2.53 ns 2.37 ns -
TryComputeHash · KMAC-256 · BouncyCastle 1KB 2,372.1 ns 10.14 ns 9.49 ns 256 B
TryComputeHash · KMAC-256 · Managed 1025B 1,698.4 ns 3.19 ns 2.66 ns -
TryComputeHash · KMAC-256 · BouncyCastle 1025B 2,176.1 ns 6.17 ns 5.15 ns 256 B
TryComputeHash · KMAC-256 · Managed 8KB 10,157.1 ns 21.27 ns 19.89 ns -
TryComputeHash · KMAC-256 · BouncyCastle 8KB 11,812.2 ns 34.62 ns 30.69 ns 256 B
TryComputeHash · KMAC-256 · BouncyCastle 128KB 150,143.5 ns 255.04 ns 212.97 ns 256 B
TryComputeHash · KMAC-256 · Managed 128KB 153,656.7 ns 223.87 ns 209.41 ns -

Legacy Algorithms

MD5 and SHA-1 are provided exclusively for backward compatibility with legacy protocols and file formats. Both algorithms have known cryptographic weaknesses:

  • MD5: Vulnerable to collision attacks since 2004; should not be used for security
  • SHA-1: Collision attacks demonstrated in 2017 (SHAttered); deprecated by NIST

On Apple M4, BouncyCastle leads MD5 at small sizes (~20% faster than OS at 128 B). For SHA-1, OS leads clearly (~45% faster than BouncyCastle and Managed at 128 B). The OS CommonCrypto benefits from Apple's hardware AES-based SHA-1 acceleration.

MD5

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · MD5 · BouncyCastle 128B 351.5 ns 0.77 ns 0.64 ns -
TryComputeHash · MD5 · OS Native 128B 443.3 ns 7.37 ns 7.24 ns -
TryComputeHash · MD5 · Managed 128B 534.8 ns 10.69 ns 16.64 ns -
TryComputeHash · MD5 · BouncyCastle 137B 358.2 ns 3.81 ns 3.56 ns -
TryComputeHash · MD5 · OS Native 137B 427.5 ns 4.67 ns 4.14 ns -
TryComputeHash · MD5 · Managed 137B 559.8 ns 11.07 ns 14.78 ns -
TryComputeHash · MD5 · OS Native 1KB 1,513.5 ns 1.59 ns 1.41 ns -
TryComputeHash · MD5 · BouncyCastle 1KB 2,040.9 ns 39.59 ns 35.10 ns -
TryComputeHash · MD5 · Managed 1KB 3,207.8 ns 63.14 ns 98.31 ns -
TryComputeHash · MD5 · OS Native 1025B 1,513.2 ns 2.26 ns 2.00 ns -
TryComputeHash · MD5 · BouncyCastle 1025B 2,057.6 ns 38.52 ns 37.84 ns -
TryComputeHash · MD5 · Managed 1025B 3,172.9 ns 63.10 ns 96.37 ns -
TryComputeHash · MD5 · OS Native 8KB 10,150.6 ns 66.04 ns 58.54 ns -
TryComputeHash · MD5 · BouncyCastle 8KB 15,183.2 ns 108.20 ns 90.35 ns -
TryComputeHash · MD5 · Managed 8KB 24,432.0 ns 482.30 ns 792.43 ns -
TryComputeHash · MD5 · OS Native 128KB 157,259.8 ns 172.20 ns 143.79 ns -
TryComputeHash · MD5 · BouncyCastle 128KB 239,630.8 ns 338.56 ns 282.72 ns -
TryComputeHash · MD5 · Managed 128KB 331,676.5 ns 477.01 ns 398.33 ns -

SHA-1

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · SHA-1 · OS Native 128B 268.5 ns 1.77 ns 1.57 ns -
TryComputeHash · SHA-1 · BouncyCastle 128B 484.1 ns 1.26 ns 0.98 ns -
TryComputeHash · SHA-1 · Managed 128B 528.5 ns 0.78 ns 0.69 ns -
TryComputeHash · SHA-1 · OS Native 137B 255.5 ns 2.69 ns 2.39 ns -
TryComputeHash · SHA-1 · BouncyCastle 137B 488.7 ns 2.59 ns 2.02 ns -
TryComputeHash · SHA-1 · Managed 137B 524.0 ns 0.49 ns 0.43 ns -
TryComputeHash · SHA-1 · OS Native 1KB 525.3 ns 0.93 ns 0.82 ns -
TryComputeHash · SHA-1 · BouncyCastle 1KB 2,700.8 ns 3.21 ns 3.00 ns -
TryComputeHash · SHA-1 · Managed 1KB 2,850.0 ns 6.20 ns 5.80 ns -
TryComputeHash · SHA-1 · OS Native 1025B 523.7 ns 1.71 ns 1.33 ns -
TryComputeHash · SHA-1 · BouncyCastle 1025B 2,691.3 ns 3.89 ns 3.45 ns -
TryComputeHash · SHA-1 · Managed 1025B 2,844.0 ns 11.49 ns 10.18 ns -
TryComputeHash · SHA-1 · OS Native 8KB 2,632.5 ns 2.37 ns 2.10 ns -
TryComputeHash · SHA-1 · BouncyCastle 8KB 20,328.0 ns 112.22 ns 99.48 ns -
TryComputeHash · SHA-1 · Managed 8KB 21,302.8 ns 77.97 ns 69.12 ns -
TryComputeHash · SHA-1 · OS Native 128KB 38,798.5 ns 40.70 ns 33.99 ns -
TryComputeHash · SHA-1 · BouncyCastle 128KB 320,712.7 ns 2,903.44 ns 2,573.83 ns -
TryComputeHash · SHA-1 · Managed 128KB 336,643.0 ns 1,221.10 ns 1,082.47 ns -

Regional Standards

These algorithms serve regulatory compliance requirements in specific jurisdictions:

Algorithm Region Use Case
SM3 China Required for Chinese government and financial systems (GB/T 32905-2016)
Streebog Russia Russian federal standard GOST R 34.11-2012, required for government communications
Kupyna Ukraine Ukrainian national standard DSTU 7564:2014, required for government systems
LSH South Korea Korean national standard KS X 3262, approved by KCMVP
Whirlpool ISO/NESSIE European cryptographic standard (ISO/IEC 10118-3)
RIPEMD-160 Europe/Crypto Used in Bitcoin address generation and some European standards

On Apple M4, the managed Streebog implementation is ~1.7× faster than OpenGost and ~2.1× faster than BouncyCastle — consistent with the x86 advantage. Kupyna is ~1.5× faster than BouncyCastle (vs ~1.3–1.45× on x86). The Whirlpool implementation is outstanding at ~4.9× faster than BouncyCastle — the most dominant advantage of any regional algorithm on this platform.

SM3

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · SM3 · BouncyCastle 128B 605.7 ns 3.01 ns 2.82 ns -
TryComputeHash · SM3 · Managed 128B 611.1 ns 3.74 ns 3.13 ns -
TryComputeHash · SM3 · BouncyCastle 137B 604.2 ns 2.26 ns 1.89 ns -
TryComputeHash · SM3 · Managed 137B 612.7 ns 3.05 ns 2.71 ns -
TryComputeHash · SM3 · BouncyCastle 1KB 3,292.2 ns 10.86 ns 10.15 ns -
TryComputeHash · SM3 · Managed 1KB 3,461.9 ns 15.16 ns 13.44 ns -
TryComputeHash · SM3 · BouncyCastle 1025B 3,290.7 ns 10.11 ns 9.46 ns -
TryComputeHash · SM3 · Managed 1025B 3,463.2 ns 20.92 ns 19.57 ns -
TryComputeHash · SM3 · BouncyCastle 8KB 24,702.3 ns 68.42 ns 64.00 ns -
TryComputeHash · SM3 · Managed 8KB 26,546.9 ns 354.59 ns 331.69 ns -
TryComputeHash · SM3 · BouncyCastle 128KB 393,976.3 ns 1,102.63 ns 977.45 ns -
TryComputeHash · SM3 · Managed 128KB 421,592.7 ns 6,234.71 ns 5,831.96 ns -

Streebog-256

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · Streebog-256 · Managed 128B 1.768 μs 0.0056 μs 0.0050 μs -
TryComputeHash · Streebog-256 · OpenGost 128B 2.972 μs 0.0058 μs 0.0055 μs 408 B
TryComputeHash · Streebog-256 · BouncyCastle 128B 3.740 μs 0.0226 μs 0.0200 μs -
TryComputeHash · Streebog-256 · Managed 137B 1.777 μs 0.0069 μs 0.0065 μs -
TryComputeHash · Streebog-256 · OpenGost 137B 2.978 μs 0.0079 μs 0.0074 μs 408 B
TryComputeHash · Streebog-256 · BouncyCastle 137B 3.674 μs 0.0116 μs 0.0108 μs -
TryComputeHash · Streebog-256 · Managed 1KB 6.757 μs 0.0247 μs 0.0231 μs -
TryComputeHash · Streebog-256 · OpenGost 1KB 11.149 μs 0.0223 μs 0.0198 μs 408 B
TryComputeHash · Streebog-256 · BouncyCastle 1KB 13.879 μs 0.0346 μs 0.0307 μs -
TryComputeHash · Streebog-256 · Managed 1025B 6.762 μs 0.0257 μs 0.0241 μs -
TryComputeHash · Streebog-256 · OpenGost 1025B 11.152 μs 0.0262 μs 0.0245 μs 408 B
TryComputeHash · Streebog-256 · BouncyCastle 1025B 14.116 μs 0.0482 μs 0.0427 μs -
TryComputeHash · Streebog-256 · Managed 8KB 46.527 μs 0.1783 μs 0.1668 μs -
TryComputeHash · Streebog-256 · OpenGost 8KB 76.448 μs 0.2728 μs 0.2551 μs 408 B
TryComputeHash · Streebog-256 · BouncyCastle 8KB 95.822 μs 0.2856 μs 0.2671 μs -
TryComputeHash · Streebog-256 · Managed 128KB 734.193 μs 2.7969 μs 2.6162 μs -
TryComputeHash · Streebog-256 · OpenGost 128KB 1,199.888 μs 2.5955 μs 2.4279 μs 408 B
TryComputeHash · Streebog-256 · BouncyCastle 128KB 1,460.785 μs 5.0399 μs 4.7143 μs -

Streebog-512

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · Streebog-512 · Managed 128B 1.783 μs 0.0053 μs 0.0050 μs -
TryComputeHash · Streebog-512 · OpenGost 128B 2.917 μs 0.0076 μs 0.0071 μs 176 B
TryComputeHash · Streebog-512 · BouncyCastle 128B 3.681 μs 0.0094 μs 0.0088 μs -
TryComputeHash · Streebog-512 · Managed 137B 1.783 μs 0.0062 μs 0.0055 μs -
TryComputeHash · Streebog-512 · OpenGost 137B 2.920 μs 0.0065 μs 0.0061 μs 176 B
TryComputeHash · Streebog-512 · BouncyCastle 137B 3.771 μs 0.0119 μs 0.0111 μs -
TryComputeHash · Streebog-512 · Managed 1KB 6.776 μs 0.0235 μs 0.0220 μs -
TryComputeHash · Streebog-512 · OpenGost 1KB 11.084 μs 0.0169 μs 0.0158 μs 176 B
TryComputeHash · Streebog-512 · BouncyCastle 1KB 14.168 μs 0.0303 μs 0.0284 μs -
TryComputeHash · Streebog-512 · Managed 1025B 6.767 μs 0.0212 μs 0.0199 μs -
TryComputeHash · Streebog-512 · OpenGost 1025B 11.091 μs 0.0259 μs 0.0230 μs 176 B
TryComputeHash · Streebog-512 · BouncyCastle 1025B 14.232 μs 0.0319 μs 0.0299 μs -
TryComputeHash · Streebog-512 · Managed 8KB 46.593 μs 0.1759 μs 0.1560 μs -
TryComputeHash · Streebog-512 · OpenGost 8KB 76.431 μs 0.1951 μs 0.1825 μs 176 B
TryComputeHash · Streebog-512 · BouncyCastle 8KB 96.309 μs 0.2186 μs 0.2045 μs -
TryComputeHash · Streebog-512 · Managed 128KB 733.762 μs 4.3234 μs 4.0441 μs -
TryComputeHash · Streebog-512 · OpenGost 128KB 1,201.878 μs 4.9023 μs 4.5856 μs 176 B
TryComputeHash · Streebog-512 · BouncyCastle 128KB 1,522.239 μs 4.5362 μs 4.2432 μs -

Whirlpool

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · Whirlpool · Managed 128B 888.8 ns 0.58 ns 0.55 ns -
TryComputeHash · Whirlpool · Hashify .NET 128B 1,996.3 ns 8.00 ns 7.48 ns 6336 B
TryComputeHash · Whirlpool · BouncyCastle 128B 4,373.2 ns 13.97 ns 13.06 ns 56 B
TryComputeHash · Whirlpool · Managed 137B 887.3 ns 0.41 ns 0.36 ns -
TryComputeHash · Whirlpool · Hashify .NET 137B 1,995.5 ns 6.80 ns 6.36 ns 6328 B
TryComputeHash · Whirlpool · BouncyCastle 137B 4,378.4 ns 12.43 ns 11.63 ns 56 B
TryComputeHash · Whirlpool · Managed 1KB 4,935.2 ns 3.17 ns 2.97 ns -
TryComputeHash · Whirlpool · Hashify .NET 1KB 10,346.6 ns 31.42 ns 29.39 ns 12032 B
TryComputeHash · Whirlpool · BouncyCastle 1KB 27,062.3 ns 66.76 ns 62.44 ns 56 B
TryComputeHash · Whirlpool · Managed 1025B 4,939.5 ns 1.96 ns 1.83 ns -
TryComputeHash · Whirlpool · Hashify .NET 1025B 10,316.1 ns 23.25 ns 21.75 ns 12040 B
TryComputeHash · Whirlpool · BouncyCastle 1025B 27,048.7 ns 69.39 ns 64.91 ns 56 B
TryComputeHash · Whirlpool · Managed 8KB 37,305.3 ns 19.89 ns 18.61 ns -
TryComputeHash · Whirlpool · Hashify .NET 8KB 76,258.5 ns 263.72 ns 246.69 ns 58624 B
TryComputeHash · Whirlpool · BouncyCastle 8KB 208,392.6 ns 532.19 ns 471.77 ns 56 B
TryComputeHash · Whirlpool · Managed 128KB 592,400.6 ns 309.19 ns 289.22 ns -
TryComputeHash · Whirlpool · Hashify .NET 128KB 1,225,115.9 ns 3,663.51 ns 3,426.85 ns 857372 B
TryComputeHash · Whirlpool · BouncyCastle 128KB 3,312,039.0 ns 6,413.94 ns 5,685.79 ns 56 B

RIPEMD-160

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · RIPEMD-160 · Managed 128B 511.5 ns 0.80 ns 0.71 ns -
TryComputeHash · RIPEMD-160 · BouncyCastle 128B 529.5 ns 1.75 ns 1.64 ns -
TryComputeHash · RIPEMD-160 · Managed 137B 516.5 ns 0.75 ns 0.58 ns -
TryComputeHash · RIPEMD-160 · BouncyCastle 137B 532.5 ns 3.56 ns 2.78 ns -
TryComputeHash · RIPEMD-160 · Managed 1KB 2,875.0 ns 2.82 ns 2.35 ns -
TryComputeHash · RIPEMD-160 · BouncyCastle 1KB 2,962.9 ns 5.71 ns 5.07 ns -
TryComputeHash · RIPEMD-160 · Managed 1025B 2,883.9 ns 2.82 ns 2.35 ns -
TryComputeHash · RIPEMD-160 · BouncyCastle 1025B 2,946.2 ns 10.69 ns 9.47 ns -
TryComputeHash · RIPEMD-160 · Managed 8KB 21,756.1 ns 10.99 ns 9.18 ns -
TryComputeHash · RIPEMD-160 · BouncyCastle 8KB 22,089.5 ns 98.26 ns 91.91 ns -
TryComputeHash · RIPEMD-160 · Managed 128KB 345,787.8 ns 348.57 ns 309.00 ns -
TryComputeHash · RIPEMD-160 · BouncyCastle 128KB 350,639.2 ns 1,319.31 ns 1,169.54 ns -

Kupyna-256 (DSTU 7564)

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · Kupyna-256 · Managed 128B 1.708 μs 0.0027 μs 0.0024 μs -
TryComputeHash · Kupyna-256 · BouncyCastle 128B 2.563 μs 0.0044 μs 0.0037 μs -
TryComputeHash · Kupyna-256 · Managed 137B 1.707 μs 0.0056 μs 0.0050 μs -
TryComputeHash · Kupyna-256 · BouncyCastle 137B 2.568 μs 0.0030 μs 0.0027 μs -
TryComputeHash · Kupyna-256 · Managed 1KB 8.415 μs 0.0100 μs 0.0093 μs -
TryComputeHash · Kupyna-256 · BouncyCastle 1KB 12.631 μs 0.0062 μs 0.0052 μs -
TryComputeHash · Kupyna-256 · Managed 1025B 8.431 μs 0.0190 μs 0.0178 μs -
TryComputeHash · Kupyna-256 · BouncyCastle 1025B 12.692 μs 0.0064 μs 0.0053 μs -
TryComputeHash · Kupyna-256 · Managed 8KB 62.277 μs 0.1804 μs 0.1599 μs -
TryComputeHash · Kupyna-256 · BouncyCastle 8KB 93.353 μs 0.1716 μs 0.1433 μs -
TryComputeHash · Kupyna-256 · Managed 128KB 985.255 μs 1.6758 μs 1.5676 μs -
TryComputeHash · Kupyna-256 · BouncyCastle 128KB 1,482.014 μs 1.5342 μs 1.4351 μs -

Kupyna-384 (DSTU 7564)

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · Kupyna-384 · Managed 128B 3.287 μs 0.0032 μs 0.0028 μs -
TryComputeHash · Kupyna-384 · BouncyCastle 128B 4.504 μs 0.0071 μs 0.0060 μs -
TryComputeHash · Kupyna-384 · Managed 137B 3.289 μs 0.0053 μs 0.0050 μs -
TryComputeHash · Kupyna-384 · BouncyCastle 137B 4.518 μs 0.0086 μs 0.0072 μs -
TryComputeHash · Kupyna-384 · Managed 1KB 12.392 μs 0.0316 μs 0.0296 μs -
TryComputeHash · Kupyna-384 · BouncyCastle 1KB 17.372 μs 0.0199 μs 0.0155 μs -
TryComputeHash · Kupyna-384 · Managed 1025B 12.400 μs 0.0243 μs 0.0215 μs -
TryComputeHash · Kupyna-384 · BouncyCastle 1025B 17.177 μs 0.0194 μs 0.0181 μs -
TryComputeHash · Kupyna-384 · Managed 8KB 85.003 μs 0.1565 μs 0.1387 μs -
TryComputeHash · Kupyna-384 · BouncyCastle 8KB 117.318 μs 0.0473 μs 0.0395 μs -
TryComputeHash · Kupyna-384 · Managed 128KB 1,332.974 μs 3.8857 μs 3.6347 μs -
TryComputeHash · Kupyna-384 · BouncyCastle 128KB 1,834.790 μs 2.0326 μs 1.9013 μs -

Kupyna-512 (DSTU 7564)

Description TestDataSize Mean Error StdDev Median Allocated
TryComputeHash · Kupyna-512 · Managed 128B 3.306 μs 0.0141 μs 0.0118 μs 3.305 μs -
TryComputeHash · Kupyna-512 · BouncyCastle 128B 5.500 μs 0.1740 μs 0.5131 μs 5.602 μs -
TryComputeHash · Kupyna-512 · Managed 137B 4.667 μs 0.0931 μs 0.1305 μs 4.658 μs -
TryComputeHash · Kupyna-512 · BouncyCastle 137B 5.864 μs 0.1170 μs 0.2664 μs 5.861 μs -
TryComputeHash · Kupyna-512 · Managed 1KB 14.598 μs 0.5495 μs 1.6201 μs 14.913 μs -
TryComputeHash · Kupyna-512 · BouncyCastle 1KB 17.369 μs 0.0117 μs 0.0104 μs 17.366 μs -
TryComputeHash · Kupyna-512 · Managed 1025B 12.481 μs 0.2107 μs 0.1759 μs 12.400 μs -
TryComputeHash · Kupyna-512 · BouncyCastle 1025B 21.093 μs 0.7174 μs 2.1154 μs 21.539 μs -
TryComputeHash · Kupyna-512 · Managed 8KB 119.648 μs 2.2806 μs 2.4402 μs 119.800 μs -
TryComputeHash · Kupyna-512 · BouncyCastle 8KB 164.373 μs 3.2517 μs 5.8636 μs 165.875 μs -
TryComputeHash · Kupyna-512 · Managed 128KB 1,966.664 μs 38.4295 μs 51.3023 μs 1,953.189 μs -
TryComputeHash · Kupyna-512 · BouncyCastle 128KB 2,040.164 μs 84.1084 μs 247.9954 μs 1,924.539 μs -

LSH-256-256 (KS X 3262)

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · LSH-256-256 · Managed 128B 1.475 μs 0.0018 μs 0.0015 μs -
TryComputeHash · LSH-256-256 · Managed 137B 1.582 μs 0.0023 μs 0.0021 μs -
TryComputeHash · LSH-256-256 · Managed 1KB 6.283 μs 0.0098 μs 0.0082 μs -
TryComputeHash · LSH-256-256 · Managed 1025B 6.776 μs 0.1351 μs 0.1198 μs -
TryComputeHash · LSH-256-256 · Managed 8KB 51.788 μs 1.0144 μs 1.6089 μs -
TryComputeHash · LSH-256-256 · Managed 128KB 810.196 μs 15.9708 μs 25.3314 μs -

LSH-512-256 (KS X 3262)

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · LSH-512-256 · Managed 128B 1.047 μs 0.0208 μs 0.0231 μs -
TryComputeHash · LSH-512-256 · Managed 137B 1.011 μs 0.0199 μs 0.0343 μs -
TryComputeHash · LSH-512-256 · Managed 1KB 4.232 μs 0.0781 μs 0.0731 μs -
TryComputeHash · LSH-512-256 · Managed 1025B 4.359 μs 0.0848 μs 0.0942 μs -
TryComputeHash · LSH-512-256 · Managed 8KB 26.303 μs 0.4062 μs 0.3601 μs -
TryComputeHash · LSH-512-256 · Managed 128KB 406.612 μs 7.7909 μs 7.2876 μs -

LSH-512-512 (KS X 3262)

Description TestDataSize Mean Error StdDev Allocated
TryComputeHash · LSH-512-512 · Managed 128B 1,010.5 ns 19.07 ns 20.40 ns -
TryComputeHash · LSH-512-512 · Managed 137B 984.0 ns 18.65 ns 19.16 ns -
TryComputeHash · LSH-512-512 · Managed 1KB 4,150.9 ns 82.47 ns 128.39 ns -
TryComputeHash · LSH-512-512 · Managed 1025B 4,358.4 ns 85.67 ns 95.22 ns -
TryComputeHash · LSH-512-512 · Managed 8KB 26,296.2 ns 341.21 ns 319.17 ns -
TryComputeHash · LSH-512-512 · Managed 128KB 413,430.0 ns 7,670.15 ns 7,174.67 ns -

XOF Mode

XOF (Extendable Output Function) benchmarks measure the full absorb-then-squeeze cycle: the input is absorbed and an output of equal size is squeezed. The benchmark method is AbsorbSqueeze. All CryptoHives XOF implementations are zero-allocation regardless of output size. BouncyCastle's XOF implementations allocate an internal output buffer proportional to the squeezed length (e.g., ~150 KB for a 128 KiB squeeze), making them unsuitable for high-frequency streaming use.

SHAKE Family

SHAKE128 and SHAKE256 (FIPS 202) are variable-output-length extensions of the SHA-3 permutation with security strengths of 128 and 256 bits respectively. SHAKE128 uses a 1344-bit rate (21 blocks × 64 bytes) while SHAKE256 uses a 1088-bit rate — making SHAKE128 ~14% faster for the same output size due to fewer Keccak permutation calls per byte output.

On Apple M4, BouncyCastle leads both variants at all tested sizes. For SHAKE128: BC ~12% faster at 128 B; ~1.64× faster at 128 KiB. For SHAKE256: BC ~11% faster at 128 B; ~1.53× faster at 128 KiB. This follows the same pattern as the fixed-output SHAKE hash benchmarks (BouncyCastle's Keccak permutation marginally outperforms the CryptoHives scalar implementation on Apple Silicon).

Key observations:

  • BouncyCastle: Fastest on Apple M4 but allocates output-proportional buffers (~150 KB at 128 KiB squeeze)
  • Managed: Zero-allocation; ~1.6× slower than BC at 128 KiB
  • SHAKE128 is ~12% faster than SHAKE256 at the same size due to wider rate

SHAKE128

Description TestDataSize Mean Error StdDev Allocated
AbsorbSqueeze · SHAKE128 · BouncyCastle 128B 2.056 μs 0.0097 μs 0.0090 μs -
AbsorbSqueeze · SHAKE128 · Managed 128B 2.303 μs 0.0044 μs 0.0041 μs -
AbsorbSqueeze · SHAKE128 · BouncyCastle 1KB 3.053 μs 0.0058 μs 0.0055 μs 1152 B
AbsorbSqueeze · SHAKE128 · Managed 1KB 3.850 μs 0.0067 μs 0.0062 μs -
AbsorbSqueeze · SHAKE128 · BouncyCastle 8KB 9.983 μs 0.0175 μs 0.0155 μs 9216 B
AbsorbSqueeze · SHAKE128 · Managed 8KB 15.385 μs 0.0199 μs 0.0177 μs -
AbsorbSqueeze · SHAKE128 · BouncyCastle 128KB 131.153 μs 0.3997 μs 0.3739 μs 149760 B
AbsorbSqueeze · SHAKE128 · Managed 128KB 215.173 μs 0.1408 μs 0.1248 μs -

SHAKE256

Description TestDataSize Mean Error StdDev Allocated
AbsorbSqueeze · SHAKE256 · BouncyCastle 128B 2.483 μs 0.0054 μs 0.0043 μs -
AbsorbSqueeze · SHAKE256 · Managed 128B 2.753 μs 0.0046 μs 0.0043 μs -
AbsorbSqueeze · SHAKE256 · BouncyCastle 1KB 3.704 μs 0.0064 μs 0.0057 μs 1120 B
AbsorbSqueeze · SHAKE256 · Managed 1KB 4.454 μs 0.0086 μs 0.0081 μs -
AbsorbSqueeze · SHAKE256 · BouncyCastle 8KB 12.184 μs 0.0211 μs 0.0197 μs 9600 B
AbsorbSqueeze · SHAKE256 · Managed 8KB 17.629 μs 0.0199 μs 0.0186 μs -
AbsorbSqueeze · SHAKE256 · BouncyCastle 128KB 158.035 μs 0.3933 μs 0.3679 μs 154080 B
AbsorbSqueeze · SHAKE256 · Managed 128KB 242.420 μs 0.2813 μs 0.2631 μs -

cSHAKE Family

cSHAKE128 and cSHAKE256 (NIST SP 800-185) extend SHAKE with domain separation via a function-name string N and a customization string S, enabling distinct hash functions for different applications from the same permutation. When both strings are empty, cSHAKE degenerates exactly to SHAKE.

Performance is essentially identical to the corresponding SHAKE variants — the customization strings add a one-time padding overhead during initialization, negligible in the benchmarked range. BouncyCastle leads by ~12% at 128 B and ~1.63× at 128 KiB; both implementations are zero-allocation at all sizes for the CryptoHives path.

Key observations:

  • Performance matches SHAKE128/256 within measurement noise
  • BouncyCastle: Allocates ~150 KB per 128 KiB squeeze
  • Managed: Zero-allocation; preserves streaming use-case fitness

cSHAKE128

Description TestDataSize Mean Error StdDev Allocated
AbsorbSqueeze · cSHAKE128 · BouncyCastle 128B 2.059 μs 0.0013 μs 0.0010 μs -
AbsorbSqueeze · cSHAKE128 · Managed 128B 2.306 μs 0.0032 μs 0.0028 μs -
AbsorbSqueeze · cSHAKE128 · BouncyCastle 1KB 3.143 μs 0.0067 μs 0.0062 μs 1152 B
AbsorbSqueeze · cSHAKE128 · Managed 1KB 3.862 μs 0.0054 μs 0.0048 μs -
AbsorbSqueeze · cSHAKE128 · BouncyCastle 8KB 10.040 μs 0.0120 μs 0.0100 μs 9216 B
AbsorbSqueeze · cSHAKE128 · Managed 8KB 15.470 μs 0.0230 μs 0.0204 μs -
AbsorbSqueeze · cSHAKE128 · BouncyCastle 128KB 131.999 μs 0.1655 μs 0.1548 μs 149760 B
AbsorbSqueeze · cSHAKE128 · Managed 128KB 215.594 μs 0.1360 μs 0.1206 μs -

cSHAKE256

Description TestDataSize Mean Error StdDev Allocated
AbsorbSqueeze · cSHAKE256 · BouncyCastle 128B 2.509 μs 0.0207 μs 0.0183 μs -
AbsorbSqueeze · cSHAKE256 · Managed 128B 2.759 μs 0.0041 μs 0.0037 μs -
AbsorbSqueeze · cSHAKE256 · BouncyCastle 1KB 3.658 μs 0.0100 μs 0.0094 μs 1120 B
AbsorbSqueeze · cSHAKE256 · Managed 1KB 4.462 μs 0.0092 μs 0.0086 μs -
AbsorbSqueeze · cSHAKE256 · BouncyCastle 8KB 12.246 μs 0.0198 μs 0.0185 μs 9600 B
AbsorbSqueeze · cSHAKE256 · Managed 8KB 17.661 μs 0.0121 μs 0.0101 μs -
AbsorbSqueeze · cSHAKE256 · BouncyCastle 128KB 161.760 μs 0.2484 μs 0.2202 μs 154080 B
AbsorbSqueeze · cSHAKE256 · Managed 128KB 242.726 μs 0.2304 μs 0.2155 μs -

KMAC Family (XOF)

KMAC128 XOF and KMAC256 XOF (NIST SP 800-185) are keyed variants of cSHAKE usable as variable-length PRFs. In XOF mode the output length is not encoded into the padding, enabling stream output of arbitrary length. KMAC128 XOF uses the cSHAKE128 rate (1344 bits); KMAC256 XOF uses the cSHAKE256 rate (1088 bits).

At 128 B absorb + 128 B squeeze, Managed and BouncyCastle are nearly equal (BC ~2% faster) — this is a notable difference from the fixed-output KMAC benchmark where Managed was ~1.9× faster. The larger per-call overhead of the XOF API (absorb + pad + squeeze) dominates at small sizes, favouring neither implementation. At 128 KiB, BC leads by ~1.64×, consistent with the Keccak throughput pattern.

Key observations:

  • Near parity at 128 B between Managed and BC (within ~2%)
  • BouncyCastle: Allocates ~130 B at small sizes, ~150 KB at 128 KiB squeeze
  • Managed: Zero-allocation at all sizes

KMAC128

Description TestDataSize Mean Error StdDev Allocated
AbsorbSqueeze · KMAC-128 · BouncyCastle 128B 2.597 μs 0.0069 μs 0.0064 μs 128 B
AbsorbSqueeze · KMAC-128 · Managed 128B 2.648 μs 0.0037 μs 0.0033 μs -
AbsorbSqueeze · KMAC-128 · BouncyCastle 1KB 3.600 μs 0.0089 μs 0.0083 μs 1280 B
AbsorbSqueeze · KMAC-128 · Managed 1KB 4.205 μs 0.0062 μs 0.0058 μs -
AbsorbSqueeze · KMAC-128 · BouncyCastle 8KB 10.587 μs 0.0122 μs 0.0108 μs 9344 B
AbsorbSqueeze · KMAC-128 · Managed 8KB 15.812 μs 0.0223 μs 0.0197 μs -
AbsorbSqueeze · KMAC-128 · BouncyCastle 128KB 132.440 μs 0.2612 μs 0.2316 μs 149888 B
AbsorbSqueeze · KMAC-128 · Managed 128KB 216.616 μs 0.1450 μs 0.1285 μs -

KMAC256

Description TestDataSize Mean Error StdDev Allocated
AbsorbSqueeze · KMAC-256 · BouncyCastle 128B 3.039 μs 0.0071 μs 0.0067 μs 128 B
AbsorbSqueeze · KMAC-256 · Managed 128B 3.102 μs 0.0060 μs 0.0056 μs -
AbsorbSqueeze · KMAC-256 · BouncyCastle 1KB 4.169 μs 0.0044 μs 0.0034 μs 1248 B
AbsorbSqueeze · KMAC-256 · Managed 1KB 4.810 μs 0.0047 μs 0.0041 μs -
AbsorbSqueeze · KMAC-256 · BouncyCastle 8KB 12.781 μs 0.0186 μs 0.0145 μs 9728 B
AbsorbSqueeze · KMAC-256 · Managed 8KB 18.039 μs 0.0257 μs 0.0240 μs -
AbsorbSqueeze · KMAC-256 · BouncyCastle 128KB 181.133 μs 1.0733 μs 1.0040 μs 154208 B
AbsorbSqueeze · KMAC-256 · Managed 128KB 277.002 μs 0.6686 μs 0.6254 μs -

KangarooTwelve Family (XOF)

KangarooTwelve (KT128 / KT256) are tree-hashing XOFs based on the Keccak permutation with 12 rounds (vs 24 for full SHA-3). The reduced-round design yields ~2× throughput over SHAKE128 while maintaining 128-bit security. No external competitor implementations are available for comparison.

On Apple M4, KT128 XOF delivers approximately the same throughput as SHAKE128 XOF at bulk sizes despite the halved round count, suggesting the M4 execution units are not bottlenecked by round count alone. KT256 follows the same architecture with the narrower cSHAKE256 rate and is marginally slower.

Key observations:

  • KT128 ~1.3× faster than SHAKE128 at 128 B; near parity at 128 KiB (permutation throughput parity)
  • KT256 slightly slower than KT128 due to narrower rate (1088-bit vs 1344-bit)
  • No BouncyCastle or OS comparison available; zero-allocation

KT128

Description TestDataSize Mean Error StdDev Allocated
AbsorbSqueeze · KT128 · Managed 128B 1.552 μs 0.0042 μs 0.0039 μs -
AbsorbSqueeze · KT128 · Managed 1KB 2.594 μs 0.0053 μs 0.0041 μs -
AbsorbSqueeze · KT128 · Managed 8KB 11.325 μs 0.2261 μs 0.2115 μs -
AbsorbSqueeze · KT128 · Managed 128KB 161.106 μs 3.1323 μs 3.6072 μs -

KT256

Description TestDataSize Mean Error StdDev Allocated
AbsorbSqueeze · KT256 · Managed 128B 1.651 μs 0.0198 μs 0.0185 μs -
AbsorbSqueeze · KT256 · Managed 1KB 2.847 μs 0.0562 μs 0.0876 μs -
AbsorbSqueeze · KT256 · Managed 8KB 12.105 μs 0.0264 μs 0.0220 μs -
AbsorbSqueeze · KT256 · Managed 128KB 171.168 μs 0.2586 μs 0.2419 μs -

TurboSHAKE Family (XOF)

TurboSHAKE128 and TurboSHAKE256 (IETF RFC 9562) use 12 Keccak rounds with a simplified padding scheme and expose a plain XOF interface with no tree-hashing overhead. They are the simplest and fastest Keccak-family XOFs available in this library.

On Apple M4, TurboSHAKE128 XOF is the fastest Keccak-based XOF at all sizes: ~1.37× faster than SHAKE128 at bulk sizes and leads KT128 across all payload sizes. No external competitor implementations are available.

Key observations:

  • Fastest Keccak XOF in this library on Apple M4
  • TurboSHAKE128: 1344-bit rate with 12 rounds
  • TurboSHAKE256: 1088-bit rate with 12 rounds; slightly slower
  • Zero-allocation; no OS or BouncyCastle comparison available

TurboSHAKE128

Description TestDataSize Mean Error StdDev Allocated
AbsorbSqueeze · TurboSHAKE128 · Managed 128B 1.327 μs 0.0058 μs 0.0054 μs -
AbsorbSqueeze · TurboSHAKE128 · Managed 1KB 2.442 μs 0.0023 μs 0.0022 μs -
AbsorbSqueeze · TurboSHAKE128 · Managed 8KB 10.901 μs 0.0140 μs 0.0131 μs -
AbsorbSqueeze · TurboSHAKE128 · Managed 128KB 156.953 μs 0.1931 μs 0.1807 μs -

TurboSHAKE256

Description TestDataSize Mean Error StdDev Allocated
AbsorbSqueeze · TurboSHAKE256 · Managed 128B 1.579 μs 0.0032 μs 0.0027 μs -
AbsorbSqueeze · TurboSHAKE256 · Managed 1KB 2.748 μs 0.0026 μs 0.0024 μs -
AbsorbSqueeze · TurboSHAKE256 · Managed 8KB 12.025 μs 0.0093 μs 0.0087 μs -
AbsorbSqueeze · TurboSHAKE256 · Managed 128KB 170.478 μs 0.1908 μs 0.1692 μs -

BLAKE3 (XOF)

BLAKE3 XOF uses the same ChaCha-based compression function but extends the tree hashing mode to produce output of arbitrary length. The output is derived by repeatedly doubling the output chaining value from the root node. This differs from the fixed-output benchmark, which stops at the root hash.

The Native (Rust) implementation via blake3-dotnet is dramatically faster — ~7× at 128 B and ~5.8× at 128 KiB — because the Rust output-reader uses parallel chunk generation for the extended output, exploiting multiple NEON lanes simultaneously. The CryptoHives Neon path squeezed output sequentially. Managed is 1.3× faster than BouncyCastle at 128 B and ~1.3× at 128 KiB.

Key observations:

  • Native: ~7× faster than Managed at 128 B XOF; ~5.8× at 128 KiB
  • Managed: ~1.3× faster than BouncyCastle across all sizes; zero allocation
  • BouncyCastle: Slowest XOF option; allocates 56 B per call regardless of output size
  • BLAKE3 XOF output is deterministic given key and context — suitable for KDF and stream encryption
Description TestDataSize Mean Error StdDev Allocated
AbsorbSqueeze · BLAKE3 · Native 128B 1.614 μs 0.0057 μs 0.0054 μs -
AbsorbSqueeze · BLAKE3 · Managed 128B 8.713 μs 0.0430 μs 0.0381 μs -
AbsorbSqueeze · BLAKE3 · BouncyCastle 128B 11.363 μs 0.0418 μs 0.0391 μs 56 B
AbsorbSqueeze · BLAKE3 · Native 1KB 2.291 μs 0.0113 μs 0.0094 μs -
AbsorbSqueeze · BLAKE3 · Managed 1KB 12.245 μs 0.0468 μs 0.0415 μs -
AbsorbSqueeze · BLAKE3 · BouncyCastle 1KB 17.047 μs 0.3394 μs 0.3485 μs 56 B
AbsorbSqueeze · BLAKE3 · Native 8KB 7.306 μs 0.0066 μs 0.0055 μs -
AbsorbSqueeze · BLAKE3 · Managed 8KB 42.989 μs 0.2234 μs 0.1981 μs -
AbsorbSqueeze · BLAKE3 · BouncyCastle 8KB 54.492 μs 0.0106 μs 0.0094 μs 56 B
AbsorbSqueeze · BLAKE3 · Native 128KB 93.232 μs 0.0389 μs 0.0364 μs -
AbsorbSqueeze · BLAKE3 · Managed 128KB 543.771 μs 2.5659 μs 2.4001 μs -
AbsorbSqueeze · BLAKE3 · BouncyCastle 128KB 690.745 μs 2.0506 μs 1.9181 μs 56 B

Ascon-XOF128

Ascon-XOF128 (NIST Lightweight Cryptography standard 2023) is the XOF variant of the Ascon family using the same 320-bit permutation as Ascon-Hash256. It uses a 128-bit rate, requiring a full 12-round permutation call per 16 bytes of input or output — making it inherently slower than SHAKE/BLAKE XOFs for large outputs.

On Apple M4, the CryptoHives Managed implementation is ~43% faster than BouncyCastle across all sizes — consistent with the fixed-output Ascon-Hash256 advantage. Zero allocation on both paths.

Key observations:

  • Managed: ~43% faster than BouncyCastle at all sizes; zero-allocation
  • Throughput ~3× slower than SHAKE128 at 128 KiB due to the narrow rate (128-bit vs 1344-bit)
  • Optimized for memory-constrained environments, not bulk throughput
Description TestDataSize Mean Error StdDev Allocated
AbsorbSqueeze · Ascon-XOF128 · Managed 128B 8.330 μs 0.0546 μs 0.0511 μs -
AbsorbSqueeze · Ascon-XOF128 · BouncyCastle 128B 11.889 μs 0.0280 μs 0.0262 μs -
AbsorbSqueeze · Ascon-XOF128 · Managed 1KB 11.640 μs 0.0597 μs 0.0529 μs -
AbsorbSqueeze · Ascon-XOF128 · BouncyCastle 1KB 16.615 μs 0.0617 μs 0.0547 μs -
AbsorbSqueeze · Ascon-XOF128 · Managed 8KB 38.525 μs 0.1623 μs 0.1439 μs -
AbsorbSqueeze · Ascon-XOF128 · BouncyCastle 8KB 55.357 μs 0.6130 μs 0.5434 μs -
AbsorbSqueeze · Ascon-XOF128 · Managed 128KB 495.897 μs 1.7416 μs 1.5439 μs -
AbsorbSqueeze · Ascon-XOF128 · BouncyCastle 128KB 718.204 μs 3.4863 μs 3.0905 μs -