blob: 2c864baa0e170169c085794777fbf333d5c2e049 [file] [log] [blame]
Patrick Williams92b42cb2022-09-03 06:53:57 -05001From ef5fddafdec78cab9963d21736e64d71ca520bcc Mon Sep 17 00:00:00 2001
Andrew Geissler595f6302022-01-24 19:11:47 +00002From: Alex Kube <alexander.j.kube@gmail.com>
3Date: Wed, 23 Oct 2019 21:18:12 +0430
4Subject: [PATCH] cmd/dist: separate host and target builds
5
6Upstream-Status: Inappropriate [OE specific]
7
8Change the dist tool to allow for OE-style cross-
9and cross-canadian builds:
10
11 - command flags --host-only and --target only are added;
12 if one is present, the other changes mentioned below
13 take effect, and arguments may also be specified on
14 the command line to enumerate the package(s) to be
15 built.
16
17 - for OE cross builds, go_bootstrap is always built for
18 the current build host, and is moved, along with the supporting
19 toolchain (asm, compile, etc.) to a separate 'native_native'
20 directory under GOROOT/pkg/tool.
21
22 - go_bootstrap is not automatically removed after the build,
23 so it can be reused later (e.g., building both static and
24 shared runtime).
25
26Note that for --host-only builds, it would be nice to specify
27just the "cmd" package to build only the go commands/tools,
28the staleness checks in the dist tool will fail if the "std"
29library has not also been built. So host-only builds have to
30build everything anyway.
31
32Adapted to Go 1.13 from patches originally submitted to
33the meta/recipes-devtools/go tree by
34Matt Madison <matt@madison.systems>.
35
36Signed-off-by: Alexander J Kube <alexander.j.kube@gmail.com>
37
38---
Patrick Williams92b42cb2022-09-03 06:53:57 -050039 src/cmd/dist/build.go | 154 ++++++++++++++++++++++++++++++------------
40 1 file changed, 112 insertions(+), 42 deletions(-)
Andrew Geissler595f6302022-01-24 19:11:47 +000041
Patrick Williams92b42cb2022-09-03 06:53:57 -050042diff --git a/src/cmd/dist/build.go b/src/cmd/dist/build.go
43index 3024d0c..45ebee0 100644
Andrew Geissler595f6302022-01-24 19:11:47 +000044--- a/src/cmd/dist/build.go
45+++ b/src/cmd/dist/build.go
Patrick Williams92b42cb2022-09-03 06:53:57 -050046@@ -45,6 +45,7 @@ var (
Andrew Geissler595f6302022-01-24 19:11:47 +000047 goexperiment string
48 workdir string
49 tooldir string
50+ build_tooldir string
51 oldgoos string
52 oldgoarch string
53 exe string
Patrick Williams92b42cb2022-09-03 06:53:57 -050054@@ -55,6 +56,7 @@ var (
Andrew Geissler595f6302022-01-24 19:11:47 +000055
56 rebuildall bool
57 defaultclang bool
58+ crossBuild bool
59
60 vflag int // verbosity
61 )
Patrick Williams92b42cb2022-09-03 06:53:57 -050062@@ -267,6 +269,8 @@ func xinit() {
Andrew Geissler595f6302022-01-24 19:11:47 +000063 if tooldir = os.Getenv("GOTOOLDIR"); tooldir == "" {
64 tooldir = pathf("%s/pkg/tool/%s_%s", goroot, gohostos, gohostarch)
65 }
66+
67+ build_tooldir = pathf("%s/pkg/tool/native_native", goroot)
68 }
69
70 // compilerEnv returns a map from "goos/goarch" to the
Patrick Williams92b42cb2022-09-03 06:53:57 -050071@@ -468,8 +472,10 @@ func setup() {
Andrew Geissler595f6302022-01-24 19:11:47 +000072 p := pathf("%s/pkg/%s_%s", goroot, gohostos, gohostarch)
73 if rebuildall {
74 xremoveall(p)
75+ xremoveall(build_tooldir)
76 }
77 xmkdirall(p)
78+ xmkdirall(build_tooldir)
79
80 if goos != gohostos || goarch != gohostarch {
81 p := pathf("%s/pkg/%s_%s", goroot, goos, goarch)
Patrick Williams92b42cb2022-09-03 06:53:57 -050082@@ -1248,17 +1254,35 @@ func cmdbootstrap() {
Andrew Geissler595f6302022-01-24 19:11:47 +000083
84 var noBanner, noClean bool
85 var debug bool
86+ var hostOnly bool
87+ var targetOnly bool
88+ var toBuild = []string{"std", "cmd"}
89+
90 flag.BoolVar(&rebuildall, "a", rebuildall, "rebuild all")
91 flag.BoolVar(&debug, "d", debug, "enable debugging of bootstrap process")
92 flag.BoolVar(&noBanner, "no-banner", noBanner, "do not print banner")
93 flag.BoolVar(&noClean, "no-clean", noClean, "print deprecation warning")
94+ flag.BoolVar(&hostOnly, "host-only", hostOnly, "build only host binaries, not target")
95+ flag.BoolVar(&targetOnly, "target-only", targetOnly, "build only target binaries, not host")
96
97- xflagparse(0)
98+ xflagparse(-1)
99
100 if noClean {
101 xprintf("warning: --no-clean is deprecated and has no effect; use 'go install std cmd' instead\n")
102 }
103
104+ if hostOnly && targetOnly {
105+ fatalf("specify only one of --host-only or --target-only\n")
106+ }
107+ crossBuild = hostOnly || targetOnly
108+ if flag.NArg() > 0 {
109+ if crossBuild {
110+ toBuild = flag.Args()
111+ } else {
112+ fatalf("package names not permitted without --host-only or --target-only\n")
113+ }
114+ }
115+
116 // Set GOPATH to an internal directory. We shouldn't actually
117 // need to store files here, since the toolchain won't
118 // depend on modules outside of vendor directories, but if
Patrick Williams92b42cb2022-09-03 06:53:57 -0500119@@ -1326,8 +1350,13 @@ func cmdbootstrap() {
Andrew Geissler595f6302022-01-24 19:11:47 +0000120 xprintf("\n")
121 }
122
123- gogcflags = os.Getenv("GO_GCFLAGS") // we were using $BOOT_GO_GCFLAGS until now
124- goldflags = os.Getenv("GO_LDFLAGS") // we were using $BOOT_GO_LDFLAGS until now
125+ // For split host/target cross/cross-canadian builds, we don't
126+ // want to be setting these flags until after we have compiled
127+ // the toolchain that runs on the build host.
128+ if !crossBuild {
129+ gogcflags = os.Getenv("GO_GCFLAGS") // we were using $BOOT_GO_GCFLAGS until now
130+ goldflags = os.Getenv("GO_LDFLAGS") // we were using $BOOT_GO_LDFLAGS until now
131+ }
132 goBootstrap := pathf("%s/go_bootstrap", tooldir)
Patrick Williams92b42cb2022-09-03 06:53:57 -0500133 cmdGo := pathf("%s/go", gorootBin)
Andrew Geissler595f6302022-01-24 19:11:47 +0000134 if debug {
Patrick Williams92b42cb2022-09-03 06:53:57 -0500135@@ -1356,7 +1385,11 @@ func cmdbootstrap() {
Andrew Geissler595f6302022-01-24 19:11:47 +0000136 xprintf("\n")
137 }
138 xprintf("Building Go toolchain2 using go_bootstrap and Go toolchain1.\n")
139- os.Setenv("CC", compilerEnvLookup(defaultcc, goos, goarch))
140+ if crossBuild {
141+ os.Setenv("CC", defaultcc[""])
142+ } else {
143+ os.Setenv("CC", compilerEnvLookup(defaultcc, goos, goarch))
144+ }
145 // Now that cmd/go is in charge of the build process, enable GOEXPERIMENT.
146 os.Setenv("GOEXPERIMENT", goexperiment)
147 goInstall(goBootstrap, append([]string{"-i"}, toolchain...)...)
Patrick Williams92b42cb2022-09-03 06:53:57 -0500148@@ -1395,50 +1428,84 @@ func cmdbootstrap() {
Andrew Geissler595f6302022-01-24 19:11:47 +0000149 }
150 checkNotStale(goBootstrap, append(toolchain, "runtime/internal/sys")...)
151
152- if goos == oldgoos && goarch == oldgoarch {
153- // Common case - not setting up for cross-compilation.
154- timelog("build", "toolchain")
155- if vflag > 0 {
156- xprintf("\n")
157+ if crossBuild {
158+ gogcflags = os.Getenv("GO_GCFLAGS")
159+ goldflags = os.Getenv("GO_LDFLAGS")
160+ tool_files, _ := filepath.Glob(pathf("%s/*", tooldir))
161+ for _, f := range tool_files {
162+ copyfile(pathf("%s/%s", build_tooldir, filepath.Base(f)), f, writeExec)
163+ xremove(f)
164+ }
165+ os.Setenv("GOTOOLDIR", build_tooldir)
166+ goBootstrap = pathf("%s/go_bootstrap", build_tooldir)
167+ if hostOnly {
168+ timelog("build", "host toolchain")
169+ if vflag > 0 {
170+ xprintf("\n")
171+ }
172+ xprintf("Building %s for host, %s/%s.\n", strings.Join(toBuild, ","), goos, goarch)
173+ goInstall(goBootstrap, toBuild...)
174+ checkNotStale(goBootstrap, toBuild...)
175+ // Skip cmdGo staleness checks here, since we can't necessarily run the cmdGo binary
176+
177+ timelog("build", "target toolchain")
178+ if vflag > 0 {
179+ xprintf("\n")
180+ }
181+ } else if targetOnly {
182+ goos = oldgoos
183+ goarch = oldgoarch
184+ os.Setenv("GOOS", goos)
185+ os.Setenv("GOARCH", goarch)
186+ os.Setenv("CC", compilerEnvLookup(defaultcc, goos, goarch))
187+ xprintf("Building %s for target, %s/%s.\n", strings.Join(toBuild, ","), goos, goarch)
188+ goInstall(goBootstrap, toBuild...)
189+ checkNotStale(goBootstrap, toBuild...)
190+ // Skip cmdGo staleness checks here, since we can't run the target's cmdGo binary
191 }
192- xprintf("Building packages and commands for %s/%s.\n", goos, goarch)
193 } else {
194- // GOOS/GOARCH does not match GOHOSTOS/GOHOSTARCH.
195- // Finish GOHOSTOS/GOHOSTARCH installation and then
196- // run GOOS/GOARCH installation.
197- timelog("build", "host toolchain")
198- if vflag > 0 {
199- xprintf("\n")
Andrew Geissler595f6302022-01-24 19:11:47 +0000200+
201+ if goos == oldgoos && goarch == oldgoarch {
202+ // Common case - not setting up for cross-compilation.
203+ timelog("build", "toolchain")
204+ if vflag > 0 {
205+ xprintf("\n")
206+ }
207+ xprintf("Building packages and commands for %s/%s.\n", goos, goarch)
208+ } else {
209+ // GOOS/GOARCH does not match GOHOSTOS/GOHOSTARCH.
210+ // Finish GOHOSTOS/GOHOSTARCH installation and then
211+ // run GOOS/GOARCH installation.
212+ timelog("build", "host toolchain")
213+ if vflag > 0 {
214+ xprintf("\n")
215+ }
216+ xprintf("Building packages and commands for host, %s/%s.\n", goos, goarch)
217+ goInstall(goBootstrap, "std", "cmd")
218+ checkNotStale(goBootstrap, "std", "cmd")
219+ checkNotStale(cmdGo, "std", "cmd")
220+
221+ timelog("build", "target toolchain")
222+ if vflag > 0 {
223+ xprintf("\n")
224+ }
225+ goos = oldgoos
226+ goarch = oldgoarch
227+ os.Setenv("GOOS", goos)
228+ os.Setenv("GOARCH", goarch)
229+ os.Setenv("CC", compilerEnvLookup(defaultcc, goos, goarch))
230+ xprintf("Building packages and commands for target, %s/%s.\n", goos, goarch)
Patrick Williams03907ee2022-05-01 06:28:52 -0500231 }
232- xprintf("Building packages and commands for host, %s/%s.\n", goos, goarch)
Andrew Geissler595f6302022-01-24 19:11:47 +0000233 goInstall(goBootstrap, "std", "cmd")
234 checkNotStale(goBootstrap, "std", "cmd")
235 checkNotStale(cmdGo, "std", "cmd")
236
237- timelog("build", "target toolchain")
238- if vflag > 0 {
239- xprintf("\n")
Patrick Williams92b42cb2022-09-03 06:53:57 -0500240+ if debug {
241+ run("", ShowOutput|CheckExit, pathf("%s/compile", tooldir), "-V=full")
242+ run("", ShowOutput|CheckExit, pathf("%s/buildid", tooldir), pathf("%s/pkg/%s_%s/runtime/internal/sys.a", goroot, goos, goarch))
243+ checkNotStale(goBootstrap, append(toolchain, "runtime/internal/sys")...)
244+ copyfile(pathf("%s/compile4", tooldir), pathf("%s/compile", tooldir), writeExec)
245 }
Andrew Geissler595f6302022-01-24 19:11:47 +0000246- goos = oldgoos
247- goarch = oldgoarch
248- os.Setenv("GOOS", goos)
249- os.Setenv("GOARCH", goarch)
250- os.Setenv("CC", compilerEnvLookup(defaultcc, goos, goarch))
251- xprintf("Building packages and commands for target, %s/%s.\n", goos, goarch)
252- }
253- targets := []string{"std", "cmd"}
254- if goos == "js" && goarch == "wasm" {
255- // Skip the cmd tools for js/wasm. They're not usable.
256- targets = targets[:1]
257- }
258- goInstall(goBootstrap, targets...)
259- checkNotStale(goBootstrap, targets...)
260- checkNotStale(cmdGo, targets...)
261- if debug {
262- run("", ShowOutput|CheckExit, pathf("%s/compile", tooldir), "-V=full")
263- run("", ShowOutput|CheckExit, pathf("%s/buildid", tooldir), pathf("%s/pkg/%s_%s/runtime/internal/sys.a", goroot, goos, goarch))
264- checkNotStale(goBootstrap, append(toolchain, "runtime/internal/sys")...)
265- copyfile(pathf("%s/compile4", tooldir), pathf("%s/compile", tooldir), writeExec)
266 }
267
268 // Check that there are no new files in $GOROOT/bin other than
Patrick Williams92b42cb2022-09-03 06:53:57 -0500269@@ -1455,8 +1522,11 @@ func cmdbootstrap() {
Andrew Geissler595f6302022-01-24 19:11:47 +0000270 }
271 }
272
273- // Remove go_bootstrap now that we're done.
274- xremove(pathf("%s/go_bootstrap", tooldir))
275+ // Except that for split host/target cross-builds, we need to
276+ // keep it.
277+ if !crossBuild {
278+ xremove(pathf("%s/go_bootstrap", tooldir))
279+ }
280
281 if goos == "android" {
282 // Make sure the exec wrapper will sync a fresh $GOROOT to the device.