]> Cypherpunks repositories - gostls13.git/commitdiff
cmd/go: fix linux-amd64-clang builder
authorDave Cheney <dave@cheney.net>
Fri, 1 May 2015 00:49:36 +0000 (10:49 +1000)
committerDave Cheney <dave@cheney.net>
Tue, 5 May 2015 21:29:57 +0000 (21:29 +0000)
Fixes #10660

Fix the clang only builder by passing -extld down to the linker when needed.
The build passed on most hosts because gcc is almost always present. The bug
was verified by symlinking bin/false in place of gcc in my $PATH and running
the build.

Also, resolve a TODO and move the support logic into its own function.

Tested manually

    env CC=clang-3.5 ./all.bash # linux/amd64
    env CC=gcc-4.8 ./all.bash # linux/amd64
    ./all.bash # linux/amd64
    ./all.bash # darwin/amd64

Change-Id: I4e27a1119356e295500a0d19ad7a4ec14207bf10
Reviewed-on: https://go-review.googlesource.com/9526
Run-TryBot: Dave Cheney <dave@cheney.net>
Reviewed-by: Ian Lance Taylor <iant@golang.org>
src/cmd/go/build.go

index de06fe7b1d2c236a4101be7e43544fb1bd3232d0..68cab5b69ebd3de2021d34ad74727ccaeb7b23c2 100644 (file)
@@ -1310,15 +1310,61 @@ func (b *builder) installShlibname(a *action) error {
        return nil
 }
 
+// setextld sets the appropriate linker flags for the specified compiler.
+func setextld(ldflags []string, compiler []string) []string {
+       for _, f := range ldflags {
+               if f == "-extld" || strings.HasPrefix(f, "-extld=") {
+                       // don't override -extld if supplied
+                       return ldflags
+               }
+       }
+       ldflags = append(ldflags, "-extld="+compiler[0])
+       if len(compiler) > 1 {
+               extldflags := false
+               add := strings.Join(compiler[1:], " ")
+               for i, f := range ldflags {
+                       if f == "-extldflags" && i+1 < len(ldflags) {
+                               ldflags[i+1] = add + " " + ldflags[i+1]
+                               extldflags = true
+                               break
+                       } else if strings.HasPrefix(f, "-extldflags=") {
+                               ldflags[i] = "-extldflags=" + add + " " + ldflags[i][len("-extldflags="):]
+                               extldflags = true
+                               break
+                       }
+               }
+               if !extldflags {
+                       ldflags = append(ldflags, "-extldflags="+add)
+               }
+       }
+       return ldflags
+}
+
 func (b *builder) linkShared(a *action) (err error) {
        // TODO(mwhudson): obvious copy pasting from gcToolchain.ld, should make a few
        // changes to that function and then call it. And support gccgo.
        allactions := actionList(a)
        importArgs := b.includeArgs("-L", allactions[:len(allactions)-1])
-       // TODO(mwhudson): this does not check for cxx-ness, extldflags etc
        ldflags := []string{"-installsuffix", buildContext.InstallSuffix}
        ldflags = append(ldflags, "-buildmode="+ldBuildmode)
        ldflags = append(ldflags, buildLdflags...)
+       cxx := a.p != nil && (len(a.p.CXXFiles) > 0 || len(a.p.SwigCXXFiles) > 0)
+       for _, a := range allactions {
+               if a.p != nil && (len(a.p.CXXFiles) > 0 || len(a.p.SwigCXXFiles) > 0) {
+                       cxx = true
+               }
+       }
+       // If the user has not specified the -extld option, then specify the
+       // appropriate linker. In case of C++ code, use the compiler named
+       // by the CXX environment variable or defaultCXX if CXX is not set.
+       // Else, use the CC environment variable and defaultCC as fallback.
+       var compiler []string
+       if cxx {
+               compiler = envList("CXX", defaultCXX)
+       } else {
+               compiler = envList("CC", defaultCC)
+       }
+       ldflags = setextld(ldflags, compiler)
        for _, d := range a.deps {
                if d.target == "" { // omit unsafe etc
                        continue
@@ -2093,40 +2139,13 @@ func (gcToolchain) ld(b *builder, p *Package, out string, allactions []*action,
        // appropriate linker. In case of C++ code, use the compiler named
        // by the CXX environment variable or defaultCXX if CXX is not set.
        // Else, use the CC environment variable and defaultCC as fallback.
-       extld := false
-       for _, f := range ldflags {
-               if f == "-extld" || strings.HasPrefix(f, "-extld=") {
-                       extld = true
-                       break
-               }
-       }
-       if !extld {
-               var compiler []string
-               if cxx {
-                       compiler = envList("CXX", defaultCXX)
-               } else {
-                       compiler = envList("CC", defaultCC)
-               }
-               ldflags = append(ldflags, "-extld="+compiler[0])
-               if len(compiler) > 1 {
-                       extldflags := false
-                       add := strings.Join(compiler[1:], " ")
-                       for i, f := range ldflags {
-                               if f == "-extldflags" && i+1 < len(ldflags) {
-                                       ldflags[i+1] = add + " " + ldflags[i+1]
-                                       extldflags = true
-                                       break
-                               } else if strings.HasPrefix(f, "-extldflags=") {
-                                       ldflags[i] = "-extldflags=" + add + " " + ldflags[i][len("-extldflags="):]
-                                       extldflags = true
-                                       break
-                               }
-                       }
-                       if !extldflags {
-                               ldflags = append(ldflags, "-extldflags="+add)
-                       }
-               }
+       var compiler []string
+       if cxx {
+               compiler = envList("CXX", defaultCXX)
+       } else {
+               compiler = envList("CC", defaultCC)
        }
+       ldflags = setextld(ldflags, compiler)
        ldflags = append(ldflags, "-buildmode="+ldBuildmode)
        ldflags = append(ldflags, buildLdflags...)
        return b.run(".", p.ImportPath, nil, buildToolExec, tool(archChar()+"l"), "-o", out, importArgs, ldflags, mainpkg)