rgoussu@goussu: ~/library/go/toolchain
~/library/go/toolchain cat go-build-and-run.md

go build, go run, go install

# The compile trio — build cache, build tags, ldflags stamping, first-class cross-compilation, race builds, and PGO.

Conceptsaved 2026-08-09 #go#tooling#build#cross-compilation

Overview

go build compiles packages, go run builds-and-executes in one step (dev loop), and go install builds a binary into GOPATH/bin — the standard way to install Go tools (go install tool@version). All three share the content-addressed build cache, so "incremental builds" need no configuration: unchanged packages are never recompiled.

Key points

  • Build cache: keyed by hashes of source, flags, and toolchain; lives in go env GOCACHE; go clean -cache wipes it. Correct by construction — no make clean rituals.
  • Build tags & file suffixes: //go:build linux && amd64 constraints and the _linux.go / _amd64.go / _test.go filename conventions select files per target; this is how the standard library does platform-specific code.
  • -ldflags "-s -w" strips symbol table and DWARF for smaller binaries; -X importpath.Var=value stamps version/commit strings into var declarations at link time — the idiomatic version-injection mechanism.
  • -trimpath removes local filesystem paths from the binary for reproducible builds.
  • Cross-compilation is a variable, not a project: GOOS=linux GOARCH=arm64 go build works from any host with no extra toolchain; go tool dist list prints the full matrix. CGO is disabled by default when cross-compiling, keeping binaries static.
  • -race builds with the race detector (needs CGO on most platforms); slower and hungrier, but the standard CI gate for concurrent code.
  • PGO (1.21+): drop a CPU profile as default.pgo next to main and builds apply profile-guided optimization automatically — typically low-single-digit percent wins.
  • go run is not deployment: it recompiles into a temp location; ship go build artifacts.

Examples

# Static linux binary with version stamped in, reproducible paths
CGO_ENABLED=0 GOOS=linux GOARCH=amd64 \
  go build -trimpath -ldflags "-s -w -X main.version=$(git describe --tags)" -o bin/app ./cmd/app

go install golang.org/x/vuln/cmd/govulncheck@latest   # install a tool

Related