Other meanings of Bootstrapping (compilers)
COMPILER CONSTRUCTION
Bootstrapping in compiler construction is the process of building a compiler using the language that compiler is intended to compile. A small initial implementation or another existing compiler starts the process; successive versions then compile themselves, producing a self-hosting toolchain.
Bootstrapping creates a compiler for a language by using an earlier compiler, interpreter, or manually translated implementation as its starting point. The defining situation is that the compiler is written in the language it compiles: a C compiler written in C, a Rust compiler written largely in Rust, or a Go compiler written in Go. The first usable compiler is commonly called a seed, while later compilers are described as stage 1, stage 2, and so on.
Bootstrapping is closely related to, but not identical with, self-hosting. A self-hosting compiler can compile its own source; bootstrapping is the broader construction process that reaches that state. The initial seed might be written in assembly, another language, or an older version of the same language. Modern toolchains document these dependencies explicitly: GCC describes bootstrap builds as part of its development and installation process, while Rust documents a staged process in which an existing compiler builds a new compiler.1
A bootstrap chain separates the construction of a compiler from the language implementation it will eventually replace. A seed compiler first translates the source of a new compiler into executable code. That newly built compiler can then compile its own source, producing a second-stage result. Repeating the process can expose accidental dependence on the seed compiler and establish that the compiler is genuinely capable of rebuilding itself.
Toolchains may also use different compilers for different components. LLVM, for example, can be built with an existing C++ compiler and then used to build later versions of LLVM and related projects.2 The practical goal is not always an infinite cycle; it is a sufficiently independent and repeatable path from a known seed to the intended compiler.
Bootstrapping makes a language implementation portable, maintainable, and easier to improve. Once a compiler is expressed in its own language, language features can be used to develop the compiler itself, and contributors need not maintain a separate implementation in an unrelated language. The same source can then be rebuilt for multiple target architectures whenever a suitable compiler and runtime are available.
Bootstrapping also supports compiler validation. A common technique is to build successive stages and compare their outputs or behavior. If stage 2 compiles the same source as stage 1 and produces equivalent results, this provides evidence that the compiler is self-consistent, although it does not prove correctness. GCC's documentation treats bootstrap building as a distinct configuration and testing concern, reflecting the fact that compiler development often depends on a working earlier toolchain.13
The process can be expensive: compiler sources, standard libraries, assemblers, linkers, and target-specific runtime components all have to be available in a suitable order. Projects therefore publish bootstrap binaries or use distribution packages when a complete from-scratch build is unnecessary.
Different language communities choose different bootstrap strategies. Rust uses a staged compiler build in which an existing Rust compiler helps construct a newer compiler, while the Rust compiler development guide describes the relationships among stage 0, stage 1, and stage 2 artifacts. Go's source-installation documentation likewise distinguishes the bootstrap toolchain used to build the Go compiler from the compiler ultimately installed for users.3
Cross-compilation is often central. A compiler built on one machine may produce a compiler or runtime for another architecture, allowing a new platform to acquire its own native toolchain. Historically, this was especially important when computers lacked a compiler for a newly introduced language or architecture. The seed may therefore be a cross-compiler rather than a native compiler.
Bootstrapping can involve more than the compiler front end. Assemblers, linkers, garbage collectors, standard libraries, build systems, and package managers may each have their own dependency chain. A language can be self-hosting while still relying on externally implemented system components.
Bootstrap independence is not the same as software trust. A compiler can reproduce itself while carrying a malicious or unintended behavior hidden in its executable. Ken Thompson's classic discussion, “Reflections on Trusting Trust,” showed how a compromised compiler could insert code into programs and into later compiler builds, making source inspection alone insufficient for complete assurance.4
For this reason, some projects use diverse double compilation, reproducible builds, binary transparency, or multiple independently implemented compilers. These methods attack different risks: reproducible builds test whether the same inputs yield the same outputs, whereas diverse compilation tests whether unrelated implementations agree.
Another subtlety is that “self-hosting” may describe only the main compiler. A project can compile its front end with itself while using a separately written runtime, linker, or code generator. Conversely, a compiler may be bootstrapped through an interpreter or transpiler and later become self-hosting after enough of the language and its libraries are implemented. These edge cases make bootstrapping a process and an engineering property, not a single binary milestone.
The term “bootstrapping” here refers specifically to compiler construction: building a compiler using the language it compiles.
Help improve the encyclopedia. Reports go straight to the site manager.