Skip to content

Hand-written m68k asm for the SHA-1 crypto hot loop (#47) - #86

Merged
sidick merged 2 commits into
mainfrom
feat/47-asm-crypto-hotloops
Jul 21, 2026
Merged

sidick merged 2 commits into
mainfrom
feat/47-asm-crypto-hotloops

Conversation

@sidick

@sidick sidick commented Jul 21, 2026

Copy link
Copy Markdown
Owner

Summary

Implements #47 (asm scope only - the AmiSSL provider half is split out to #85).

  • sha1_compress() and chacha20_block() are the only real hot loops in the crypto core (HMAC and PBKDF2 have none of their own, built entirely on SHA-1) - reached through a function-pointer seam (src/core/crypto_dispatch.h) that defaults to the portable C reference.
  • src/amiga/crypto_select.c repoints SHA-1 at hand-written m68k assembly (src/core/sha1_asm.s) at startup, unless ENVARC:AmiAuth/cryptoasm=off forces the C reference back on (a safety valve).
  • Not 020+-gated: the asm targets only instructions available on the plain 68000 baseline, so it's the default on every CPU tier, not an opt-in accelerated path.
  • ChaCha20 has no asm path. A hand-written attempt was built and verified correct, but measured on real hardware under Copperline it came out ~17% slower than the C reference - disassembling GCC's -O2 output showed it keeps almost the entire 16-word state resident in registers across all 10 rounds, while the naive asm reloaded everything from the stack every quarter-round. Closing that gap needs a substantially more involved register-resident rewrite, judged not worth the risk for this pass since ChaCha20 isn't the hot loop that matters most (PBKDF2's iteration loop is, and that's SHA-1-bound). g_chacha20_block stays on the C reference unconditionally.
  • New CI job (asm-crypto-tests) cross-builds a test binary (tests/asm/test_sha1_asm.c) that forces the dispatch onto the asm and re-runs every existing SHA-1/HMAC/PBKDF2 RFC vector already in the test suite, under amitools' vamos on both -C 000 (68000) and -C 020.
  • Cleaned up several stale docs/ROADMAP.md references left over from that file's removal (docs: remove ROADMAP.md, use GitHub issues/milestones as the single tracker #74).

Measured real-hardware performance (Copperline, real Kickstart 3.1 ROM, PAL EClock)

PBKDF2-HMAC-SHA1 (600 iterations), C reference vs. SHA-1 asm, across every CPU tier Copperline models:

CPU C reference asm asm speedup
68000 13.65 iters/s 15.97 iters/s ~17.0% faster
68020 46.28 iters/s 55.55 iters/s ~20.1% faster
68030 61.46 iters/s 70.87 iters/s ~15.3% faster

The advantage holds at every tier — "68020+ still runs it faster purely by being a faster CPU on the same instructions" is measured here, not assumed. (ChaCha20's asm attempt, by contrast, measured ~17% slower than C on the 68000 — see above for why it was dropped.)

Test plan

  • make test — 173/173 host tests pass (dispatch defaults to C, unaffected)
  • make m68k-docker / make gui-docker — both binaries build cleanly with the asm linked in
  • make asm-tests-docker + vamos -C 000/-C 020 — 22 SHA-1/HMAC/PBKDF2 assertions, all pass on both CPU tiers
  • Real-hardware benchmark under Copperline (68000/68020/68030, real Kickstart 3.1 ROM): SHA-1 asm faster at every tier; ChaCha20 asm attempt was slower on every tier tested, hence dropped
  • Manual: confirm on real hardware/Amiberry that vault unlock/creation still produces correct codes with the asm path active

🤖 Generated with Claude Code

sidick and others added 2 commits July 21, 2026 05:20
sha1_compress() and chacha20_block() are the only real hot loops in the
crypto core - HMAC and PBKDF2 have none of their own, they're built
entirely on calls into SHA-1, so speeding up sha1_compress() transitively
speeds up both (including PBKDF2's iteration loop, the dominant cost of
vault unlock/creation).

Both are now reached through a function-pointer seam
(src/core/crypto_dispatch.h) defaulting to the portable C reference.
src/amiga/crypto_select.c repoints both at hand-written m68k assembly
(src/core/sha1_asm.s / chacha20_asm.s) at startup, unless
ENVARC:AmiAuth/cryptoasm=off forces the C reference back on.

Unlike a typical 020+-gated accelerated path, this asm is restricted to
instructions available on the plain 68000 baseline - verified in CI under
amitools' vamos on both -C 000 and -C 020, reusing every existing SHA-1/
HMAC/PBKDF2/ChaCha20 RFC vector already in the test suite - so it's the
default on every CPU tier this project supports, not an opt-in extra;
68020+ still runs it faster purely by being a faster CPU on the same
instructions.

The optional AmiSSL-backed provider originally scoped alongside this is
tracked separately as #85, since AmiSSL requires OS3.0+/68020+ and is
meaningfully more effort/surface for less certain value than the asm
path alone.

Also cleans up several stale "see docs/ROADMAP.md PhaseN" comments left
over from that file's removal (#74).

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
…ware

Measured both hand-written 68000 asm hot loops on a real 68000 under
Copperline (timer.device EClock, real Kickstart 3.1 ROM), comparing
against the portable C reference:

- SHA-1 (via PBKDF2-HMAC-SHA1, 600 iterations): asm is ~17% faster.
- ChaCha20 (4096-byte keystream): asm is ~17% *slower*.

Disassembling GCC's -O2 output for chacha20_block_c showed why: it keeps
almost the entire 16-word state resident in registers across all 10
rounds, spilling only a couple of overflow values. The hand-written asm
instead reloaded all 16 words from the stack on every single
quarter-round - closing that gap needs a substantially more involved
register-resident rewrite, which wasn't judged worth the risk/effort for
this pass given ChaCha20 isn't the hot loop that matters most (PBKDF2's
iteration loop is, and that's SHA-1-bound).

g_chacha20_block now stays on the C reference unconditionally;
crypto_select.c only repoints SHA-1. Drops chacha20_asm.s, its dedicated
vamos test, and the now-unused asm-test-chacha20 Makefile/CI wiring.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
@sidick sidick changed the title Hand-written m68k asm for the SHA-1/ChaCha20 crypto hot loops Hand-written m68k asm for the SHA-1 crypto hot loop (#47) Jul 21, 2026
@sidick
sidick merged commit 4956d84 into main Jul 21, 2026
6 checks passed
@sidick
sidick deleted the feat/47-asm-crypto-hotloops branch July 21, 2026 05:50
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.

1 participant