Extempore is alive on aarch64 (part deux)

26 Feb 26

extempore

A quick update on Extempore on aarch64:

#Compiler guts

NOTE: these compiler & Scheme changes are in a couple of standalone commits and could be reverted in future… experimental stuff. But fun!

The biggest under-the-hood change is a refactor of the xtlang compiler and a migration from TinyScheme to s7 Scheme—Bill Schottstaedt’s embeddable Scheme interpreter from CCRMA. s7 was originally forked from TinyScheme anyway, so the migration path was relatively straightforward, but it’s a much more capable interpreter with proper hash tables, first-class environments, and better performance across the board.

On the compiler side, the old xtlang type checker used assoc-list caches for everything—which was fine when type environments were small, but scaled poorly for libraries with heavy generic instantiation. The refactored compiler replaces those with hash table caches, adds union-find for type unification, and moves to constraint-based solving.

Here are ahead-of-time compilation benchmarks for all the core and external audio libraries1:

LibraryBeforeAfterSpeedup
libs/base/base.xtm5.59s3.24s1.7x
libs/core/math.xtm16.57s4.04s4.1x
libs/core/rational.xtm6.47s3.47s1.9x
libs/core/audiobuffer.xtm7.45s3.49s2.1x
libs/core/audio_dsp.xtm32.14s5.71s5.6x
libs/core/instruments.xtm109.83s8.38s13.1x
libs/external/fft.xtm5.71s3.99s1.4x
libs/external/sndfile.xtm9.17s3.64s2.5x
libs/external/audio_dsp_ext.xtm5.51s4.28s1.3x
libs/external/instruments_ext.xtm12.57s9.26s1.4x
libs/external/portmidi.xtm4.86s3.35s1.5x
Total215.9s52.9s4.1x

The headline number is a 4.1x wall-clock speedup, but each invocation includes ~3s of startup overhead (there’s a hard-coded sleep for NSApp initialisation because reasons). Subtracting that out, the pure compile time went from ~183s to ~20s—a 9x speedup.

The standout is instruments.xtm at 13.1x; it’s a longer file and works the compiler more than some of the others, which is exactly where the new union-find and hash table caches pay off. Libraries showing more modest improvements (1.3–1.5x) are dominated by LLVM JIT time and startup overhead rather than Scheme-level type checking, so there’s not much to squeeze out of those on the compiler side.

This is still all on the aarch64 branch; I’m not ready to merge to master just yet. If you’re an extempore user and you’re willing to get your hands a little dirty and try build from source on the tip of that branch and try out your extempore workloads, then I’d appreciate that—including bug reports of things that don’t work.

#Footnotes

  1. Benchmarked on Linux x86_64 (AMD Zen 4) with LLVM 22.1.0 and ORC JIT. Each library compiled in a separate extempore --nobase --batch process. “Before” is commit 44b7b5c5 (TinyScheme, assoc-list caches); “After” is commit 93dacf79 (s7 Scheme, hash table caches + union-find + constraint solver).

Cite this post
@online{swift2026extemporeIsAliveOnAarch64PartDeux,
  author = {Ben Swift},
  title = {Extempore is alive on aarch64 (part deux)},
  url = {https://benswift.me/blog/2026/02/26/extempore-is-alive-on-aarch64-part-deux/},
  year = {2026},
  month = {02},
  note = {AT-URI: at://did:plc:tevykrhi4kibtsipzci76d76/site.standard.document/2026-02-26-extempore-is-alive-on-aarch64-part-deux},
}