mirror of
https://github.com/golang/go
synced 2024-11-26 14:26:51 -07:00
go/build: prefer //go:build over // +build lines
Part of //go:build change (#41184). See https://golang.org/design/draft-gobuild - Reject files with multiple //go:build lines. - If a file has both //go:build and // +build lines, only use the //go:build line. - Otherwise fall back to // +build lines - Use go/build/constraint for parsing both //go:build and // +build lines. For Go 1.17. Change-Id: I32e2404d8ce266230f767718dc7cc24e77b425e8 Reviewed-on: https://go-review.googlesource.com/c/go/+/240607 Trust: Russ Cox <rsc@golang.org> Run-TryBot: Russ Cox <rsc@golang.org> TryBot-Result: Go Bot <gobot@golang.org> Reviewed-by: Jay Conrod <jayconrod@google.com>
This commit is contained in:
parent
a8942d2cff
commit
5b76343a10
@ -9,6 +9,7 @@ import (
|
|||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
"go/ast"
|
"go/ast"
|
||||||
|
"go/build/constraint"
|
||||||
"go/doc"
|
"go/doc"
|
||||||
"go/token"
|
"go/token"
|
||||||
exec "internal/execabs"
|
exec "internal/execabs"
|
||||||
@ -1423,7 +1424,7 @@ func (ctxt *Context) matchFile(dir, name string, allTags map[string]bool, binary
|
|||||||
// Look for +build comments to accept or reject the file.
|
// Look for +build comments to accept or reject the file.
|
||||||
ok, sawBinaryOnly, err := ctxt.shouldBuild(info.header, allTags)
|
ok, sawBinaryOnly, err := ctxt.shouldBuild(info.header, allTags)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, fmt.Errorf("%s: %v", name, err)
|
||||||
}
|
}
|
||||||
if !ok && !ctxt.UseAllFiles {
|
if !ok && !ctxt.UseAllFiles {
|
||||||
return nil, nil
|
return nil, nil
|
||||||
@ -1459,11 +1460,12 @@ var (
|
|||||||
bSlashSlash = []byte(slashSlash)
|
bSlashSlash = []byte(slashSlash)
|
||||||
bStarSlash = []byte(starSlash)
|
bStarSlash = []byte(starSlash)
|
||||||
bSlashStar = []byte(slashStar)
|
bSlashStar = []byte(slashStar)
|
||||||
|
bPlusBuild = []byte("+build")
|
||||||
|
|
||||||
goBuildComment = []byte("//go:build")
|
goBuildComment = []byte("//go:build")
|
||||||
|
|
||||||
errGoBuildWithoutBuild = errors.New("//go:build comment without // +build comment")
|
errGoBuildWithoutBuild = errors.New("//go:build comment without // +build comment")
|
||||||
errMultipleGoBuild = errors.New("multiple //go:build comments") // unused in Go 1.(N-1)
|
errMultipleGoBuild = errors.New("multiple //go:build comments")
|
||||||
)
|
)
|
||||||
|
|
||||||
func isGoBuildComment(line []byte) bool {
|
func isGoBuildComment(line []byte) bool {
|
||||||
@ -1498,8 +1500,7 @@ var binaryOnlyComment = []byte("//go:binary-only-package")
|
|||||||
// shouldBuild reports whether the file should be built
|
// shouldBuild reports whether the file should be built
|
||||||
// and whether a //go:binary-only-package comment was found.
|
// and whether a //go:binary-only-package comment was found.
|
||||||
func (ctxt *Context) shouldBuild(content []byte, allTags map[string]bool) (shouldBuild, binaryOnly bool, err error) {
|
func (ctxt *Context) shouldBuild(content []byte, allTags map[string]bool) (shouldBuild, binaryOnly bool, err error) {
|
||||||
|
// Identify leading run of // comments and blank lines,
|
||||||
// Pass 1. Identify leading run of // comments and blank lines,
|
|
||||||
// which must be followed by a blank line.
|
// which must be followed by a blank line.
|
||||||
// Also identify any //go:build comments.
|
// Also identify any //go:build comments.
|
||||||
content, goBuild, sawBinaryOnly, err := parseFileHeader(content)
|
content, goBuild, sawBinaryOnly, err := parseFileHeader(content)
|
||||||
@ -1507,10 +1508,19 @@ func (ctxt *Context) shouldBuild(content []byte, allTags map[string]bool) (shoul
|
|||||||
return false, false, err
|
return false, false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
// Pass 2. Process each +build line in the run.
|
// If //go:build line is present, it controls.
|
||||||
p := content
|
// Otherwise fall back to +build processing.
|
||||||
|
switch {
|
||||||
|
case goBuild != nil:
|
||||||
|
x, err := constraint.Parse(string(goBuild))
|
||||||
|
if err != nil {
|
||||||
|
return false, false, fmt.Errorf("parsing //go:build line: %v", err)
|
||||||
|
}
|
||||||
|
shouldBuild = ctxt.eval(x, allTags)
|
||||||
|
|
||||||
|
default:
|
||||||
shouldBuild = true
|
shouldBuild = true
|
||||||
sawBuild := false
|
p := content
|
||||||
for len(p) > 0 {
|
for len(p) > 0 {
|
||||||
line := p
|
line := p
|
||||||
if i := bytes.IndexByte(line, '\n'); i >= 0 {
|
if i := bytes.IndexByte(line, '\n'); i >= 0 {
|
||||||
@ -1519,32 +1529,21 @@ func (ctxt *Context) shouldBuild(content []byte, allTags map[string]bool) (shoul
|
|||||||
p = p[len(p):]
|
p = p[len(p):]
|
||||||
}
|
}
|
||||||
line = bytes.TrimSpace(line)
|
line = bytes.TrimSpace(line)
|
||||||
if !bytes.HasPrefix(line, bSlashSlash) {
|
if !bytes.HasPrefix(line, bSlashSlash) || !bytes.Contains(line, bPlusBuild) {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
line = bytes.TrimSpace(line[len(bSlashSlash):])
|
text := string(line)
|
||||||
if len(line) > 0 && line[0] == '+' {
|
if !constraint.IsPlusBuild(text) {
|
||||||
// Looks like a comment +line.
|
continue
|
||||||
f := strings.Fields(string(line))
|
|
||||||
if f[0] == "+build" {
|
|
||||||
sawBuild = true
|
|
||||||
ok := false
|
|
||||||
for _, tok := range f[1:] {
|
|
||||||
if ctxt.match(tok, allTags) {
|
|
||||||
ok = true
|
|
||||||
}
|
}
|
||||||
}
|
if x, err := constraint.Parse(text); err == nil {
|
||||||
if !ok {
|
if !ctxt.eval(x, allTags) {
|
||||||
shouldBuild = false
|
shouldBuild = false
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if goBuild != nil && !sawBuild {
|
|
||||||
return false, false, errGoBuildWithoutBuild
|
|
||||||
}
|
|
||||||
|
|
||||||
return shouldBuild, sawBinaryOnly, nil
|
return shouldBuild, sawBinaryOnly, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1580,7 +1579,7 @@ Lines:
|
|||||||
}
|
}
|
||||||
|
|
||||||
if !inSlashStar && isGoBuildComment(line) {
|
if !inSlashStar && isGoBuildComment(line) {
|
||||||
if false && goBuild != nil { // enabled in Go 1.N
|
if goBuild != nil {
|
||||||
return nil, nil, false, errMultipleGoBuild
|
return nil, nil, false, errMultipleGoBuild
|
||||||
}
|
}
|
||||||
goBuild = line
|
goBuild = line
|
||||||
@ -1649,7 +1648,7 @@ func (ctxt *Context) saveCgo(filename string, di *Package, cg *ast.CommentGroup)
|
|||||||
if len(cond) > 0 {
|
if len(cond) > 0 {
|
||||||
ok := false
|
ok := false
|
||||||
for _, c := range cond {
|
for _, c := range cond {
|
||||||
if ctxt.match(c, nil) {
|
if ctxt.matchAuto(c, nil) {
|
||||||
ok = true
|
ok = true
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
@ -1831,49 +1830,43 @@ func splitQuoted(s string) (r []string, err error) {
|
|||||||
return args, err
|
return args, err
|
||||||
}
|
}
|
||||||
|
|
||||||
// match reports whether the name is one of:
|
// matchAuto interprets text as either a +build or //go:build expression (whichever works),
|
||||||
|
// reporting whether the expression matches the build context.
|
||||||
//
|
//
|
||||||
|
// matchAuto is only used for testing of tag evaluation
|
||||||
|
// and in #cgo lines, which accept either syntax.
|
||||||
|
func (ctxt *Context) matchAuto(text string, allTags map[string]bool) bool {
|
||||||
|
if strings.ContainsAny(text, "&|()") {
|
||||||
|
text = "//go:build " + text
|
||||||
|
} else {
|
||||||
|
text = "// +build " + text
|
||||||
|
}
|
||||||
|
x, err := constraint.Parse(text)
|
||||||
|
if err != nil {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
return ctxt.eval(x, allTags)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (ctxt *Context) eval(x constraint.Expr, allTags map[string]bool) bool {
|
||||||
|
return x.Eval(func(tag string) bool { return ctxt.matchTag(tag, allTags) })
|
||||||
|
}
|
||||||
|
|
||||||
|
// matchTag reports whether the name is one of:
|
||||||
|
//
|
||||||
|
// cgo (if cgo is enabled)
|
||||||
// $GOOS
|
// $GOOS
|
||||||
// $GOARCH
|
// $GOARCH
|
||||||
// cgo (if cgo is enabled)
|
|
||||||
// !cgo (if cgo is disabled)
|
|
||||||
// ctxt.Compiler
|
// ctxt.Compiler
|
||||||
// !ctxt.Compiler
|
// linux (if GOOS = android)
|
||||||
|
// solaris (if GOOS = illumos)
|
||||||
// tag (if tag is listed in ctxt.BuildTags or ctxt.ReleaseTags)
|
// tag (if tag is listed in ctxt.BuildTags or ctxt.ReleaseTags)
|
||||||
// !tag (if tag is not listed in ctxt.BuildTags or ctxt.ReleaseTags)
|
|
||||||
// a comma-separated list of any of these
|
|
||||||
//
|
//
|
||||||
func (ctxt *Context) match(name string, allTags map[string]bool) bool {
|
// It records all consulted tags in allTags.
|
||||||
if name == "" {
|
func (ctxt *Context) matchTag(name string, allTags map[string]bool) bool {
|
||||||
if allTags != nil {
|
if allTags != nil {
|
||||||
allTags[name] = true
|
allTags[name] = true
|
||||||
}
|
}
|
||||||
return false
|
|
||||||
}
|
|
||||||
if i := strings.Index(name, ","); i >= 0 {
|
|
||||||
// comma-separated list
|
|
||||||
ok1 := ctxt.match(name[:i], allTags)
|
|
||||||
ok2 := ctxt.match(name[i+1:], allTags)
|
|
||||||
return ok1 && ok2
|
|
||||||
}
|
|
||||||
if strings.HasPrefix(name, "!!") { // bad syntax, reject always
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
if strings.HasPrefix(name, "!") { // negation
|
|
||||||
return len(name) > 1 && !ctxt.match(name[1:], allTags)
|
|
||||||
}
|
|
||||||
|
|
||||||
if allTags != nil {
|
|
||||||
allTags[name] = true
|
|
||||||
}
|
|
||||||
|
|
||||||
// Tags must be letters, digits, underscores or dots.
|
|
||||||
// Unlike in Go identifiers, all digits are fine (e.g., "386").
|
|
||||||
for _, c := range name {
|
|
||||||
if !unicode.IsLetter(c) && !unicode.IsDigit(c) && c != '_' && c != '.' {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// special tags
|
// special tags
|
||||||
if ctxt.CgoEnabled && name == "cgo" {
|
if ctxt.CgoEnabled && name == "cgo" {
|
||||||
@ -1946,10 +1939,10 @@ func (ctxt *Context) goodOSArchFile(name string, allTags map[string]bool) bool {
|
|||||||
}
|
}
|
||||||
n := len(l)
|
n := len(l)
|
||||||
if n >= 2 && knownOS[l[n-2]] && knownArch[l[n-1]] {
|
if n >= 2 && knownOS[l[n-2]] && knownArch[l[n-1]] {
|
||||||
return ctxt.match(l[n-1], allTags) && ctxt.match(l[n-2], allTags)
|
return ctxt.matchTag(l[n-1], allTags) && ctxt.matchTag(l[n-2], allTags)
|
||||||
}
|
}
|
||||||
if n >= 1 && (knownOS[l[n-1]] || knownArch[l[n-1]]) {
|
if n >= 1 && (knownOS[l[n-1]] || knownArch[l[n-1]]) {
|
||||||
return ctxt.match(l[n-1], allTags)
|
return ctxt.matchTag(l[n-1], allTags)
|
||||||
}
|
}
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
@ -30,7 +30,7 @@ func TestMatch(t *testing.T) {
|
|||||||
match := func(tag string, want map[string]bool) {
|
match := func(tag string, want map[string]bool) {
|
||||||
t.Helper()
|
t.Helper()
|
||||||
m := make(map[string]bool)
|
m := make(map[string]bool)
|
||||||
if !ctxt.match(tag, m) {
|
if !ctxt.matchAuto(tag, m) {
|
||||||
t.Errorf("%s context should match %s, does not", what, tag)
|
t.Errorf("%s context should match %s, does not", what, tag)
|
||||||
}
|
}
|
||||||
if !reflect.DeepEqual(m, want) {
|
if !reflect.DeepEqual(m, want) {
|
||||||
@ -40,7 +40,7 @@ func TestMatch(t *testing.T) {
|
|||||||
nomatch := func(tag string, want map[string]bool) {
|
nomatch := func(tag string, want map[string]bool) {
|
||||||
t.Helper()
|
t.Helper()
|
||||||
m := make(map[string]bool)
|
m := make(map[string]bool)
|
||||||
if ctxt.match(tag, m) {
|
if ctxt.matchAuto(tag, m) {
|
||||||
t.Errorf("%s context should NOT match %s, does", what, tag)
|
t.Errorf("%s context should NOT match %s, does", what, tag)
|
||||||
}
|
}
|
||||||
if !reflect.DeepEqual(m, want) {
|
if !reflect.DeepEqual(m, want) {
|
||||||
@ -153,6 +153,13 @@ var shouldBuildTests = []struct {
|
|||||||
tags: map[string]bool{"yes": true},
|
tags: map[string]bool{"yes": true},
|
||||||
shouldBuild: true,
|
shouldBuild: true,
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "Yes2",
|
||||||
|
content: "//go:build yes\n" +
|
||||||
|
"package main\n",
|
||||||
|
tags: map[string]bool{"yes": true},
|
||||||
|
shouldBuild: true,
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "Or",
|
name: "Or",
|
||||||
content: "// +build no yes\n\n" +
|
content: "// +build no yes\n\n" +
|
||||||
@ -160,6 +167,13 @@ var shouldBuildTests = []struct {
|
|||||||
tags: map[string]bool{"yes": true, "no": true},
|
tags: map[string]bool{"yes": true, "no": true},
|
||||||
shouldBuild: true,
|
shouldBuild: true,
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "Or2",
|
||||||
|
content: "//go:build no || yes\n" +
|
||||||
|
"package main\n",
|
||||||
|
tags: map[string]bool{"yes": true, "no": true},
|
||||||
|
shouldBuild: true,
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "And",
|
name: "And",
|
||||||
content: "// +build no,yes\n\n" +
|
content: "// +build no,yes\n\n" +
|
||||||
@ -167,6 +181,13 @@ var shouldBuildTests = []struct {
|
|||||||
tags: map[string]bool{"yes": true, "no": true},
|
tags: map[string]bool{"yes": true, "no": true},
|
||||||
shouldBuild: false,
|
shouldBuild: false,
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "And2",
|
||||||
|
content: "//go:build no && yes\n" +
|
||||||
|
"package main\n",
|
||||||
|
tags: map[string]bool{"yes": true, "no": true},
|
||||||
|
shouldBuild: false,
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "Cgo",
|
name: "Cgo",
|
||||||
content: "// +build cgo\n\n" +
|
content: "// +build cgo\n\n" +
|
||||||
@ -177,12 +198,23 @@ var shouldBuildTests = []struct {
|
|||||||
tags: map[string]bool{"cgo": true},
|
tags: map[string]bool{"cgo": true},
|
||||||
shouldBuild: false,
|
shouldBuild: false,
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "Cgo2",
|
||||||
|
content: "//go:build cgo\n" +
|
||||||
|
"// Copyright The Go Authors.\n\n" +
|
||||||
|
"// This package implements parsing of tags like\n" +
|
||||||
|
"// +build tag1\n" +
|
||||||
|
"package build",
|
||||||
|
tags: map[string]bool{"cgo": true},
|
||||||
|
shouldBuild: false,
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "AfterPackage",
|
name: "AfterPackage",
|
||||||
content: "// Copyright The Go Authors.\n\n" +
|
content: "// Copyright The Go Authors.\n\n" +
|
||||||
"package build\n\n" +
|
"package build\n\n" +
|
||||||
"// shouldBuild checks tags given by lines of the form\n" +
|
"// shouldBuild checks tags given by lines of the form\n" +
|
||||||
"// +build tag\n" +
|
"// +build tag\n" +
|
||||||
|
"//go:build tag\n" +
|
||||||
"func shouldBuild(content []byte)\n",
|
"func shouldBuild(content []byte)\n",
|
||||||
tags: map[string]bool{},
|
tags: map[string]bool{},
|
||||||
shouldBuild: true,
|
shouldBuild: true,
|
||||||
@ -194,6 +226,13 @@ var shouldBuildTests = []struct {
|
|||||||
tags: map[string]bool{},
|
tags: map[string]bool{},
|
||||||
shouldBuild: true,
|
shouldBuild: true,
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "TooClose2",
|
||||||
|
content: "//go:build yes\n" +
|
||||||
|
"package main\n",
|
||||||
|
tags: map[string]bool{"yes": true},
|
||||||
|
shouldBuild: true,
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "TooCloseNo",
|
name: "TooCloseNo",
|
||||||
content: "// +build no\n" +
|
content: "// +build no\n" +
|
||||||
@ -201,6 +240,13 @@ var shouldBuildTests = []struct {
|
|||||||
tags: map[string]bool{},
|
tags: map[string]bool{},
|
||||||
shouldBuild: true,
|
shouldBuild: true,
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "TooCloseNo2",
|
||||||
|
content: "//go:build no\n" +
|
||||||
|
"package main\n",
|
||||||
|
tags: map[string]bool{"no": true},
|
||||||
|
shouldBuild: false,
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "BinaryOnly",
|
name: "BinaryOnly",
|
||||||
content: "//go:binary-only-package\n" +
|
content: "//go:binary-only-package\n" +
|
||||||
@ -210,21 +256,22 @@ var shouldBuildTests = []struct {
|
|||||||
binaryOnly: true,
|
binaryOnly: true,
|
||||||
shouldBuild: true,
|
shouldBuild: true,
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "BinaryOnly2",
|
||||||
|
content: "//go:binary-only-package\n" +
|
||||||
|
"//go:build no\n" +
|
||||||
|
"package main\n",
|
||||||
|
tags: map[string]bool{"no": true},
|
||||||
|
binaryOnly: true,
|
||||||
|
shouldBuild: false,
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "ValidGoBuild",
|
name: "ValidGoBuild",
|
||||||
content: "// +build yes\n\n" +
|
content: "// +build yes\n\n" +
|
||||||
"//go:build no\n" +
|
"//go:build no\n" +
|
||||||
"package main\n",
|
"package main\n",
|
||||||
tags: map[string]bool{"yes": true},
|
tags: map[string]bool{"no": true},
|
||||||
shouldBuild: true,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
name: "MissingBuild",
|
|
||||||
content: "//go:build no\n" +
|
|
||||||
"package main\n",
|
|
||||||
tags: map[string]bool{},
|
|
||||||
shouldBuild: false,
|
shouldBuild: false,
|
||||||
err: errGoBuildWithoutBuild,
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "MissingBuild2",
|
name: "MissingBuild2",
|
||||||
@ -232,20 +279,8 @@ var shouldBuildTests = []struct {
|
|||||||
"// +build yes\n\n" +
|
"// +build yes\n\n" +
|
||||||
"//go:build no\n" +
|
"//go:build no\n" +
|
||||||
"package main\n",
|
"package main\n",
|
||||||
tags: map[string]bool{},
|
tags: map[string]bool{"no": true},
|
||||||
shouldBuild: false,
|
shouldBuild: false,
|
||||||
err: errGoBuildWithoutBuild,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
name: "MissingBuild2",
|
|
||||||
content: "/*\n" +
|
|
||||||
"// +build yes\n\n" +
|
|
||||||
"*/\n" +
|
|
||||||
"//go:build no\n" +
|
|
||||||
"package main\n",
|
|
||||||
tags: map[string]bool{},
|
|
||||||
shouldBuild: false,
|
|
||||||
err: errGoBuildWithoutBuild,
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "Comment1",
|
name: "Comment1",
|
||||||
@ -263,9 +298,8 @@ var shouldBuildTests = []struct {
|
|||||||
"*/\n\n" +
|
"*/\n\n" +
|
||||||
"//go:build no\n" +
|
"//go:build no\n" +
|
||||||
"package main\n",
|
"package main\n",
|
||||||
tags: map[string]bool{},
|
tags: map[string]bool{"no": true},
|
||||||
shouldBuild: false,
|
shouldBuild: false,
|
||||||
err: errGoBuildWithoutBuild,
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "Comment3",
|
name: "Comment3",
|
||||||
@ -274,9 +308,8 @@ var shouldBuildTests = []struct {
|
|||||||
"*/\n\n" +
|
"*/\n\n" +
|
||||||
"//go:build no\n" +
|
"//go:build no\n" +
|
||||||
"package main\n",
|
"package main\n",
|
||||||
tags: map[string]bool{},
|
tags: map[string]bool{"no": true},
|
||||||
shouldBuild: false,
|
shouldBuild: false,
|
||||||
err: errGoBuildWithoutBuild,
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "Comment4",
|
name: "Comment4",
|
||||||
@ -290,9 +323,8 @@ var shouldBuildTests = []struct {
|
|||||||
content: "/**/\n" +
|
content: "/**/\n" +
|
||||||
"//go:build no\n" +
|
"//go:build no\n" +
|
||||||
"package main\n",
|
"package main\n",
|
||||||
tags: map[string]bool{},
|
tags: map[string]bool{"no": true},
|
||||||
shouldBuild: false,
|
shouldBuild: false,
|
||||||
err: errGoBuildWithoutBuild,
|
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -295,7 +295,7 @@ var depsRules = `
|
|||||||
FMT
|
FMT
|
||||||
< go/build/constraint;
|
< go/build/constraint;
|
||||||
|
|
||||||
go/doc, go/parser, internal/goroot, internal/goversion
|
go/build/constraint, go/doc, go/parser, internal/goroot, internal/goversion
|
||||||
< go/build;
|
< go/build;
|
||||||
|
|
||||||
DEBUG, go/build, go/types, text/scanner
|
DEBUG, go/build, go/types, text/scanner
|
||||||
|
Loading…
Reference in New Issue
Block a user