[PATCH v2 00/21] kbuild: significantly speed up kernel builds

Lorenzo Stoakes (ARM) posted 21 patches 1 day, 14 hours ago
.gitignore                                   |   1 +
Documentation/kbuild/kbuild.rst              |  22 +
Documentation/kbuild/reproducible-builds.rst |  16 +
Kbuild                                       |   5 +
Makefile                                     |  47 +-
arch/arm64/kernel/pi/Makefile                |   2 +-
arch/riscv/kernel/pi/Makefile                |   2 +-
arch/x86/Kconfig                             |  17 +
arch/x86/Makefile                            |  12 +-
arch/x86/boot/Makefile                       |   2 +-
arch/x86/boot/compressed/Makefile            |   2 +-
drivers/firmware/efi/libstub/Makefile        |   2 +-
include/asm-generic/vmlinux.lds.h            |   2 +-
include/linux/vermagic.h                     |   2 +-
init/Kconfig                                 | 197 +------
init/Kconfig.toolchain                       | 272 ++++++++++
rust/Makefile                                |   5 +
scripts/Makefile                             |   4 +-
scripts/Makefile.build                       |  27 +-
scripts/Makefile.lib                         |   7 +-
scripts/Makefile.modfinal                    |  36 +-
scripts/Makefile.modinst                     |   4 +-
scripts/Makefile.modpost                     |   2 +-
scripts/Makefile.vmlinux                     |  22 +-
scripts/Makefile.warn                        |  28 +-
scripts/basic/.gitignore                     |   1 +
scripts/basic/Makefile                       |   2 +-
scripts/basic/depcheck.c                     | 443 +++++++++++++++
scripts/check-function-names.sh              |   3 +-
scripts/elf-parse.c                          |  48 +-
scripts/elf-parse.h                          |  19 +
scripts/kallsyms-sysmap.c                    | 269 ++++++++++
scripts/kallsyms.c                           | 374 +++++++++----
scripts/kallsyms.h                           |  44 ++
scripts/link-vmlinux.sh                      |  24 +-
scripts/mksysmap                             |  94 ----
scripts/mod/.gitignore                       |   1 +
scripts/mod/Makefile                         |   8 +
scripts/mod/modpost.c                        | 703 ++++++++++++++++++------
scripts/mod/module-offsets.c                 |  35 ++
scripts/tags.sh                              |   5 +-
tools/objtool/Makefile                       |   2 +-
tools/objtool/check.c                        | 768 ++++++++++++++++++++-------
tools/objtool/elf.c                          | 246 ++++++++-
tools/objtool/include/objtool/elf.h          |   2 +
tools/objtool/include/objtool/objtool.h      |   3 +-
tools/objtool/objtool.c                      |  15 +-
47 files changed, 2982 insertions(+), 865 deletions(-)
[PATCH v2 00/21] kbuild: significantly speed up kernel builds
Posted by Lorenzo Stoakes (ARM) 1 day, 14 hours ago
A typical kernel build consists of a frustratingly large amount of time
spent stuck in single-threaded bottlenecks.

It turns out that there's a lot we can do about this and doing so
significantly impacts kernel build times.

This series makes allmodconfig builds up to 36% faster, incremental builds
up to ~70% faster, and noop builds up to ~90% faster.

Builds are faster across the board on every device I tested.

Machines used for perf testing:

* Threadripper -   x86, AMD Threadripper 9980X, 64 cores, 128 threads
* EPYC         -   x86, 2 socket EPYC 9754, 256 cores, 512 threads
* M2           - arm64, 2022 M2 macbook pro, 8 cores, 8 threads
                        (4 perf, 4 efficiency)

Cutting to the chase:

		== IMPORTANT NOTE on dependencies/build configuration ==

Performance numbers are based on a build which:

* Has these series applied (as these supersede changes from a previous
  version of this series):
	https://lore.kernel.org/linux-modules/20260731-module_ver_remove-v2-0-c9163858f382@linuxfoundation.org/
	https://lore.kernel.org/9d4b8ccfed745ac47a954aa2e1de62a85197122d.1788899473.git.jpoimboe@kernel.org/
* Runs `make KBUILD_RUST_THREADS=8 -j $(nproc) ...`.
* Runs with the pigz tool installed locally.

		== allmodconfig FULL build ==

                        before    after     delta
                      ----------------------------------
Threadripper, gcc       344.2s   278.6s    -65.6s (-19%)
Threadripper, clang     342.6s   266.8s    -75.8s (-22%)
EPYC, gcc               188.0s   121.1s    -66.9s (-36%)
EPYC, clang             259.5s   184.6s    -74.9s (-29%)

		== allmodconfig INCREMENTAL build ==

                        before    after     delta
                      ----------------------------------
Threadripper, gcc        40.1s    15.4s    -24.7s (-62%)
Threadripper, clang      40.3s    15.6s    -24.8s (-61%)
EPYC, gcc                70.9s    24.3s    -46.6s (-66%)
EPYC, clang              70.4s    24.3s    -46.1s (-65%)

		== allmodconfig NO-OP build ==

                        before    after     delta
                      ----------------------------------
Threadripper, gcc        15.3s     1.4s    -13.9s (-91%)
Threadripper, clang      16.2s     1.8s    -14.4s (-89%)
EPYC, gcc                30.6s     1.5s    -29.1s (-95%)
EPYC, clang              32.3s     2.2s    -30.1s (-93%)

		== defconfig FULL build ==

                        before    after     delta
                      ----------------------------------
Threadripper, gcc        32.5s    26.3s     -6.1s (-19%)
Threadripper, clang      34.5s    27.2s     -7.3s (-21%)
EPYC, gcc                28.7s    20.6s     -8.1s (-28%)
EPYC, clang              39.8s    32.2s     -7.6s (-19%)
M2, gcc                 519.3s   512.4s     -6.9s (-1%)
M2, clang               634.5s   569.4s    -65.1s (-10%)

		== defconfig INCREMENTAL build ==

                        before    after     delta
                      ----------------------------------
Threadripper, gcc        11.2s     6.0s     -5.3s (-47%)
Threadripper, clang      11.3s     5.4s     -5.9s (-52%)
EPYC, gcc                18.6s     9.2s     -9.4s (-51%)
EPYC, clang              19.6s     8.6s    -11.0s (-56%)
M2, gcc                  18.0s     9.9s     -8.1s (-45%)
M2, clang                18.1s     8.2s     -9.9s (-55%)

		== defconfig NO-OP build ==

                        before    after     delta
                      ----------------------------------
Threadripper, gcc         1.1s    0.60s    -0.50s (-45%)
Threadripper, clang       1.3s    0.66s    -0.63s (-49%)
EPYC, gcc                 1.7s    0.66s     -1.0s (-61%)
EPYC, clang               2.0s    0.80s     -1.2s (-60%)
M2, gcc                   6.4s     1.7s     -4.7s (-74%)
M2, clang                 7.1s     1.7s     -5.4s (-76%)

Further performance numbers are provided for each commit giving a sense of
what each contributes to the final result.

			== Testing ==

Beyond x86, allmodconfig was built with the series for arm64, arm, riscv,
powerpc64, s390 and loongarch, and for arm64, arm, s390 and loongarch the
System.map is identical to what the previous shell mksysmap produces for
the same vmlinux.

Also tested were parisc64 and m68k build as far as mainline lets them
(a driver's static assertion and an undefined-symbol check on parisc, gcc
16 internal compiler errors on m68k, none of it from this series).

Kernels for x86, arm64, arm, riscv, loongarch, powerpc64, s390, m68k and
parisc64 all boot under qemu, every text symbol of System.map is in
/proc/kallsyms at the relocated address, and a module loads and unloads.
The s390, arm and loongarch kernels also pass the kallsyms selftest.

An x86 kernel with CONFIG_MODVERSIONS, CONFIG_EXTENDED_MODVERSIONS and
CONFIG_MODULE_SRCVERSION_ALL boots, loads and unloads modules. External
modules build against both in-tree and O= builds, and every commit builds
on x86 defconfig.

Build times are the best of several runs, no unexpected errors or
warnings were seen.

While some aspects of the build process have been changed, all tooling
should function identically to before.

			== LLM usage ==

An LLM was used to first determine where the bottlenecks were then to
figure out how to improve them.

It generated a lot of code, much of it hideous.

I extensively audited and rewrote a lot of it, and heavily edited commit
messages, the cover letter and comments.

The LLM has also orchestrated build runs, testing, debugging and analysis.

I have manually checked for correctness in both build and running kernels
generated with this series applied.

Performance improvements were also verified manually.

Since an LLM was used extensively, each commit carries an Assisted-by tag.

			== What was changed? ==

Fundamentally the series improves build times by parallelising
single-threaded tasks as much as possible and improving the efficiency of
code used in the build process.

kbuild, kallsyms, modpost, objtool, mksysmap and the rust build system were
all updated as part of this change.

Nothing too controversial was included. There are further improvements that
could be made, but they would either by very invasive (large scale C header
changes) or generate diminishing returns.

			== Patches ==

   kbuild (1):       Make .modinfo an INFO section.

   kallsyms (2, 3):  Some efficiency improvements through use of a cache.

   kbuild (4, 5):    Don't sort nm output unnecessarily, do not include
                     relocations in the kallsyms trial links.

   elf-parse (6):    Section flags, symbol binding and a read-only mapping,
                     for the next patch.

   kallsyms (7):     Don't use nm, read the ELF symbol table directly.

   kbuild (8, 9):    Implement a cache to track objects, check dependency
                     timestamps more efficiently.

   kbuild (10):      Move the toolchain checks into their own Kconfig file.

   kbuild (11):      Probe compiler, linker flags once at top of build.

   modpost (12):     Improve performance through use of a cache.

   modules (13, 14): Emit module descriptors as assembly (*.mod.S) rather
                     than C (*.mod.c), reducing CPU seconds taken by 10x to
                     perform the task. Also shard module finalisation
                     rather than running 10's of thousands of tiny runs.

   objtool (15-17):  Avoid polluting the reloc hash with millions of DWARF
                     relocations, size the instruction hash to the code
                     rather than hard-code it, and decode large objects
                     over multiple threads.

   rust (18-20):     Optionally run the rustc front end on several threads,
                     set correct dependencies and build crates in parallel
                     with C code, retaining the requirement that rust/
                     crates are built first.

   kbuild (21):      Default to using a parallel implementation of gzip
                     (pigz) if available on the system.

Signed-off-by: Lorenzo Stoakes (ARM) <ljs@kernel.org>
---
v2:
* Rebased on Linus's master branch.
* Removed the first 2 fix patches as they have been taken to upstream in
  commit 281b61d408d4 ("scripts/mksysmap: drop the MODULE_INFO() symbols
  from kallsyms") and commit 59351365ac27 ("scripts/mksysmap: fix escape of
  '$' in the __pi_ pattern") - thanks Nicolas!
* Fixed patch 3/21 (previously 4/23) to check error on close via ferror()
  and fclose() as per David Laight.
* Updated 21/21 to not use threads for modules, only for vmlinux, and
  updated docs to reflect this.
* Dropped patches (as was) 13 and 17 as the equivalent work is being
  performed upstream:
  https://lore.kernel.org/linux-modules/20260731-module_ver_remove-v2-0-c9163858f382@linuxfoundation.org/
* Updated the cover letter to mention the dependency on this series for
  perf numbers.
* Fixed various typos.
* Checked all of the hallucinated sashiko reports. Replied inline to emails
  to keep a record of them but not going to repeat here, unless people want
  a list.
* Fixed up 9/21 (was 11/23) to fix the bit of sashiko's report that wasn't
  hallucinated - check ferror() to bring depcheck in line with fixdep and
  kallsyms.
* Fixed up patch 13/21 (was 15/23) to emit the __this_module fields in
  offset order to handle CONFIG_RANDSTRUCT as per Sashiko.
* Fixed up patch 19/23 (now 17/21) to resolve various races. Sashiko
  hallucinated a lot of the report, and missed some stuff thread sanitizer
  found. Resolve call destinations serially to resolve most of the valid
  stuff and add a lock around pv_ops, and instruction hash freed
  properly. Tested and confirmed resolved locally, as per Sashiko.
* Fixed up patch 20/21 (was 22/23) to only build rust/ when modules_prepare
  is one of several make goals, rather than the only one. This matches the
  rest of the Makefile's behaviour on this and ensures rust components are
  built if multiple build choices are passed to make, as per Sashiko.
* Fixed up patch 5/21 (was 6/23) to test CONFIG_ARCH_VMLINUX_NEEDS_RELOCS
  directly in link-vmlinux.sh rather than plumbing a var through, for a far
  smaller patch as per Nathan.
* Moved patch 1/21 (was 9/23) to the front of the series and dropped two
  comments, as per Nathan, so it can go in ahead of the rest.
* Added patch 10/21 moving the existing toolchain checks out of
  init/Kconfig into init/Kconfig.toolchain, as per Nathan, with 11/21
  adding to it.
* In 11/21 (previously 12/23) Moved -fno-stack-clash-protection back to
  the Makefile to fix an issue with ppc32 as per Nathan.
* Updated patch 15/21 (was 18/23) to drop the dead end cache as Josh has
  one in his noreturn series:
  https://lore.kernel.org/9d4b8ccfed745ac47a954aa2e1de62a85197122d.1788899473.git.jpoimboe@kernel.org
* Also updated patch 15/21 (was 18/23) to hash relocation sections objtool
  creates itself and moved cache-to-hash copy into elf_create_reloc(), as
  per Josh.
* Split the instruction hash sizing out of patch 17/21 (was 19/23) into its
  own patch 16/21, as per Josh.
* Made the rustc parallel front end opt-in in patch 18/21 (was 20/23) via
  KBUILD_RUST_THREADS, as its output is not yet reproducible, and dropped
  the probe for the planned -j flag, as per Björn, Miguel and Nicolas.
* Tested changes to ensure any flagged issues were resolved and that
  nothing broke.
* Did a re-run of profiling numbers to reflect changes and updated cover
  letter and commit messages.

v1:
https://lore.kernel.org/r/20260908-build-speedup-v1-0-5dc1ac01672d@kernel.org

---
Lorenzo Stoakes (ARM) (21):
      kbuild: do not allocate .modinfo in vmlinux
      kallsyms: index symbols by token to speed up table compression
      kallsyms: output binary data to speed output and kallsyms assembly
      kbuild: do not sort nm output where the order is irrelevant
      kbuild: only emit vmlinux relocations when required
      elf-parse: add section flags, symbol binding and a read-only mapping
      kallsyms: reimplement mksysmap in C
      kbuild: cache list, composite object state per object
      kbuild: implement and use depcheck to check dependency timestamps
      kbuild: move the toolchain checks into init/Kconfig.toolchain
      kbuild: avoid re-running compiler and linker probes
      modpost: cache section relocation mismatch state
      modpost: emit module descriptors as assembly
      kbuild: batch module finalisation
      objtool: cache relocations, do less work
      objtool: size the instruction hash to the text
      objtool: decode instructions and resolve branch targets in parallel
      kbuild: rust: optionally parallelise rustc front end
      rust: make exports.o depend on the headers generated for it
      kbuild: build rust crates in parallel with the rest of the build
      kbuild: use pigz for gzip compression if available

 .gitignore                                   |   1 +
 Documentation/kbuild/kbuild.rst              |  22 +
 Documentation/kbuild/reproducible-builds.rst |  16 +
 Kbuild                                       |   5 +
 Makefile                                     |  47 +-
 arch/arm64/kernel/pi/Makefile                |   2 +-
 arch/riscv/kernel/pi/Makefile                |   2 +-
 arch/x86/Kconfig                             |  17 +
 arch/x86/Makefile                            |  12 +-
 arch/x86/boot/Makefile                       |   2 +-
 arch/x86/boot/compressed/Makefile            |   2 +-
 drivers/firmware/efi/libstub/Makefile        |   2 +-
 include/asm-generic/vmlinux.lds.h            |   2 +-
 include/linux/vermagic.h                     |   2 +-
 init/Kconfig                                 | 197 +------
 init/Kconfig.toolchain                       | 272 ++++++++++
 rust/Makefile                                |   5 +
 scripts/Makefile                             |   4 +-
 scripts/Makefile.build                       |  27 +-
 scripts/Makefile.lib                         |   7 +-
 scripts/Makefile.modfinal                    |  36 +-
 scripts/Makefile.modinst                     |   4 +-
 scripts/Makefile.modpost                     |   2 +-
 scripts/Makefile.vmlinux                     |  22 +-
 scripts/Makefile.warn                        |  28 +-
 scripts/basic/.gitignore                     |   1 +
 scripts/basic/Makefile                       |   2 +-
 scripts/basic/depcheck.c                     | 443 +++++++++++++++
 scripts/check-function-names.sh              |   3 +-
 scripts/elf-parse.c                          |  48 +-
 scripts/elf-parse.h                          |  19 +
 scripts/kallsyms-sysmap.c                    | 269 ++++++++++
 scripts/kallsyms.c                           | 374 +++++++++----
 scripts/kallsyms.h                           |  44 ++
 scripts/link-vmlinux.sh                      |  24 +-
 scripts/mksysmap                             |  94 ----
 scripts/mod/.gitignore                       |   1 +
 scripts/mod/Makefile                         |   8 +
 scripts/mod/modpost.c                        | 703 ++++++++++++++++++------
 scripts/mod/module-offsets.c                 |  35 ++
 scripts/tags.sh                              |   5 +-
 tools/objtool/Makefile                       |   2 +-
 tools/objtool/check.c                        | 768 ++++++++++++++++++++-------
 tools/objtool/elf.c                          | 246 ++++++++-
 tools/objtool/include/objtool/elf.h          |   2 +
 tools/objtool/include/objtool/objtool.h      |   3 +-
 tools/objtool/objtool.c                      |  15 +-
 47 files changed, 2982 insertions(+), 865 deletions(-)
---
base-commit: 704340f1cd0dcef829eb62f5b48ae95a2ce17bdf
change-id: 20260904-build-speedup-25e11a00b3d0

Best regards,
-- 
Lorenzo Stoakes (ARM) <ljs@kernel.org>

Re: [PATCH v2 00/21] kbuild: significantly speed up kernel builds
Posted by Kees Cook 1 day, 8 hours ago
On Mon, Sep 14, 2026 at 10:21:59AM +0100, Lorenzo Stoakes (ARM) wrote:
> This series makes allmodconfig builds up to 36% faster, ...

This is very nice!

> incremental builds
> up to ~70% faster, and noop builds up to ~90% faster.

Some of the changes for this seem to add complexity that I'm not sure
is balanced against the gain? I am still looking through the series,
though, maybe I'll change my opinion. ;)

> 		== allmodconfig FULL build ==

Did you try Clang CONFIG_LTO=y builds?

> 			== LLM usage ==
> [...]
> I extensively audited and rewrote a lot of it, and heavily edited commit
> messages, the cover letter and comments.

I feel like the commit logs still need a lot of work. The LLM verbosity
problem appears in many of them, for example spending 80% of the commit
log describing every step of some process as background before getting
to the actual change. I think a human writing this would be much more
terse about the background. I have, however, been known to be too terse
in my own commit logs. :P

> [...]
> Nothing too controversial was included. There are further improvements that
> could be made, but they would either by very invasive (large scale C header
> changes) or generate diminishing returns.

One area I think might solved via an LLM is the 3-pass kallsyms stuff.
If we could get a deterministic kallsyms build in 1 pass, that would be
very nice. A lot of people have tried, but it has eluded upstreaming.

-Kees

-- 
Kees Cook
Re: [PATCH v2 00/21] kbuild: significantly speed up kernel builds
Posted by Lorenzo Stoakes (ARM) 1 day, 5 hours ago
On Mon, Sep 14, 2026 at 08:41:39AM -0700, Kees Cook wrote:
> On Mon, Sep 14, 2026 at 10:21:59AM +0100, Lorenzo Stoakes (ARM) wrote:
> > This series makes allmodconfig builds up to 36% faster, ...
>
> This is very nice!

Thanks :)

>
> > incremental builds
> > up to ~70% faster, and noop builds up to ~90% faster.
>
> Some of the changes for this seem to add complexity that I'm not sure
> is balanced against the gain? I am still looking through the series,
> though, maybe I'll change my opinion. ;)

Well, I aggressively stripped all the commits that had a bad RoI on that.

And a lot of these are additive over 21 commits.

So, unfortunately, hacking away at what seem like low cost commits will eat
away at the overall result.

I really did work hard to cut the fat where I could, believe me going
through what remained and a. figuring out what it did, b. rewriting a lot
of the code and c. rewriting commit messages (ahem ;) was NOT fun :)

So I was happy to swing the axe as it saved me in terms of what little
sanity remains ;)

>
> > 		== allmodconfig FULL build ==
>
> Did you try Clang CONFIG_LTO=y builds?

I tried a CONFIG_LTO_CLANG_THIN in order to check that the *.mod.S stuff
worked correctly, all working correctly.

I can try to get some profiling numbers for thin and full if you want?

>
> > 			== LLM usage ==
> > [...]
> > I extensively audited and rewrote a lot of it, and heavily edited commit
> > messages, the cover letter and comments.
>
> I feel like the commit logs still need a lot of work. The LLM verbosity
> problem appears in many of them, for example spending 80% of the commit

Well I rewrote the majority of them, so this is a stinging critique of my
commit message writing I guess :)

> log describing every step of some process as background before getting
> to the actual change. I think a human writing this would be much more
> terse about the background. I have, however, been known to be too terse
> in my own commit logs. :P

I mean no, I did write nearly all of them. So I guess err... yeah :)

The testing results and perf numbers are generated and maybe I missed some
bits but generally this is so.

Anyway, I am known to be critical on-list on occasion, so if you dish it
out you have to take it - if you point out specific commit messages that
need work then I can try to put commit msgs on a diet :)

(N.B. I have had feedback like that on a fair few human-written commit
messages of mine lately so there might be some validity to that ;)

>
> > [...]
> > Nothing too controversial was included. There are further improvements that
> > could be made, but they would either by very invasive (large scale C header
> > changes) or generate diminishing returns.
>
> One area I think might solved via an LLM is the 3-pass kallsyms stuff.
> If we could get a deterministic kallsyms build in 1 pass, that would be
> very nice. A lot of people have tried, but it has eluded upstreaming.

"going from three passes to one would save around 8s on an allmodconfig
build and 2 to 3s on defconfig, out of tails that are currently roughly 25s
and 8s." says the LLM :) so that actually does seem worthwhile.

But I think best as a follow up?

I'd like to land the really low-hanging fruit before maybe digging in to
what else we can cut out :)

>
> -Kees
>
> --
> Kees Cook

--
Cheers, Lorenzo
Re: [PATCH v2 00/21] kbuild: significantly speed up kernel builds
Posted by Kees Cook 1 day, 5 hours ago
On Mon, Sep 14, 2026 at 07:25:28PM +0100, Lorenzo Stoakes (ARM) wrote:
> On Mon, Sep 14, 2026 at 08:41:39AM -0700, Kees Cook wrote:
> > Did you try Clang CONFIG_LTO=y builds?
> 
> I tried a CONFIG_LTO_CLANG_THIN in order to check that the *.mod.S stuff
> worked correctly, all working correctly.

Okay, thanks! I did the same just now too. It seems to be just fine.

> I can try to get some profiling numbers for thin and full if you want?

Mostly I wanted to know if it worked still, and I guess for profiling,
I'd want to make sure it didn't regress how long it took to build. :)

> Well I rewrote the majority of them, so this is a stinging critique of my
> commit message writing I guess :)

Oops! Sorry. I'll go through them again, but I felt like the objtool
commit logs were very long, but perhaps it is justified. ;)

> (N.B. I have had feedback like that on a fair few human-written commit
> messages of mine lately so there might be some validity to that ;)

And as I said, I get told I'm often too terse, so perhaps my sensing
here is broken. :P

> > One area I think might solved via an LLM is the 3-pass kallsyms stuff.
> > If we could get a deterministic kallsyms build in 1 pass, that would be
> > very nice. A lot of people have tried, but it has eluded upstreaming.
> 
> "going from three passes to one would save around 8s on an allmodconfig
> build and 2 to 3s on defconfig, out of tails that are currently roughly 25s
> and 8s." says the LLM :) so that actually does seem worthwhile.

It's what I'm always staring at when I do incrementals. ;)

> But I think best as a follow up?

Yeah, I would imagine it'd be separate. (I think a few of these sets of
changes could be landed separately too, like the pigz work.)

-- 
Kees Cook
Re: [PATCH v2 00/21] kbuild: significantly speed up kernel builds
Posted by Linus Torvalds 1 day, 7 hours ago
On Mon, 14 Sept 2026 at 08:41, Kees Cook <kees@kernel.org> wrote:
>
> One area I think might solved via an LLM is the 3-pass kallsyms stuff.
> If we could get a deterministic kallsyms build in 1 pass, that would be
> very nice. A lot of people have tried, but it has eluded upstreaming.

Even the three-pass one hasn't apparently always been entirely
deterministic. We've had random reports over the years of it failing
in some circumstances.

Maybe we've fixed it all, or maybe the failures just go imperceptibly
rare. Regardless, it has definitely been fragile.

               Linus