Google has recently made public its plan to bootstrap Go 1.5. According to Russ Cox, Go core developer for almost 6 years now and author of the document, Google has been planning for a year “how to eliminate all C programs from the Go source tree.”

Bootstrapping is “the process of writing a compiler (or assembler) in the target programming language which it is intended to compile.” In the general case, bootstrapping brings several advantages, such as:

putting to test the language being bootstrapped;

allowing to write the compiler in a usually higher-level language which offers more advanced abstractions;

leveraging any improvements to the language so the compiler can benefit of them.

As mentioned, Google started its effort to remove C from the Go source tree over one year ago by defining a five phases conversion plan:

Phase 1 - Develop a C->Go translator capable enough to translate the existing C compiler for Go. This step would take advantage of the fact that a compiler does not make heavy use of C features that would be hard to port to Go, such as macros, unions, pointer arithmetics, etc.

Phase 2 - Convert the compiler source code , which would provide a raw, C-style source code in Go.

Phase 3 - Turn the compiler into an idiomatic Go program , mainly by identifying packages, adding documentation and unit tests.

Phase 4 - Optimize the compiler , this would both address memory and CPU usage of the compiler, and possibly introduce parallelization. Furthermore, an attempt will be made to “introduce a new middle representation between the architecture-independent unordered tree (Node*s) and the architecture-dependent ordered list (Prog*s) used today” with the aim of improving the optimizing capabilities of the compiler in cases such as elimination of redundant nil checks and boundary checks.

Phase 5 - Replace the front end with the latest versions of go/parser and go/types.

According to Russ, several alternatives to this approach were taken into account and ruled out based on various considerations, as it is detailed in the two-year old proposal.

Bootstrapping Go

Bootstrapping a compiler generally entails an “egg and chicken” problem, whereby you must provide a way to compile the language you are trying to create.

In Go’s case, to build Go 1.5, it will be necessary to have Go 1.4, or newer, already installed. The existing Go toolchain will then be used to build a base version of Go 1.5 toolchain. Once the (Go 1.4-compiled) Go 1.5 toolchain is ready, it will be used to build itself again, providing thus a Go 1.5-compiled Go toolchain, which will be further used to build go_bootstrap and the remaining parts of Go standard library and components. This process, which adds an intermediate step where the generated toolchain is used to build itself once again, will be applied to any future Go version.

InfoQ has spoken to Russ to learn more about the plan to bootstrap Go.

Going bootstrapped seems a big milestone for Go. Could you elaborate why you decided to carry through this effort at this moment in the language evolution

Go is a good general purpose language, but the sweet spot it was designed for is writing large-scale, concurrent, server-side software, like what runs on Google’s servers. If the Go compiler had been the first big Go program, that use case would have had undue influence on the language design and distracted us from the real target. There are also good technical reasons not to bootstrap early, like portability, making it easy to compile from source code, and having a stable compiler implementation language early on.

Is there any specific area where you think that using Go to build Go could improve things substantially over using C at that aim?

Ken Thompson remarked to me once that for writing programs, Go feels like a much simpler language than C. One reason is that Go eliminates entire classes of common C bugs: dangling pointer uses, memory leaks, buffer overflows, stack overflow during deep recursion, misuse of void*, and unexpected numeric conversions. The standard Go toolchain has much better support for modularity, unit testing, and profiling than any standard C toolchain, but I’m most excited at the prospect of applying automated program rewrites (like gofix) when making internal API changes or refactoring.

In "Go 1.3+ Compiler Overhaul”, you describe a process to translate the existing compiler from C to Go in 5 phases. Could you clarify which phases have been already completed until now? When do you plan to complete the rest?