diff --git a/go/packages/golist.go b/go/packages/golist.go index c464f698..560d3e3f 100644 --- a/go/packages/golist.go +++ b/go/packages/golist.go @@ -121,20 +121,6 @@ extractQueries: } } - // TODO(matloob): Remove the definition of listfunc and just use golistPackages once go1.12 is released. - var listfunc driver - var isFallback bool - listfunc = func(cfg *Config, words ...string) (*driverResponse, error) { - response, err := golistDriverCurrent(cfg, words...) - if _, ok := err.(goTooOldError); ok { - isFallback = true - listfunc = golistDriverFallback - return listfunc(cfg, words...) - } - listfunc = golistDriverCurrent - return response, err - } - response := &responseDeduper{} var err error @@ -142,7 +128,7 @@ extractQueries: // patterns also requires a go list call, since it's the equivalent of // ".". if len(restPatterns) > 0 || len(patterns) == 0 { - dr, err := listfunc(cfg, restPatterns...) + dr, err := golistDriverCurrent(cfg, restPatterns...) if err != nil { return nil, err } @@ -161,13 +147,13 @@ extractQueries: var containsCandidates []string if len(containFiles) != 0 { - if err := runContainsQueries(cfg, listfunc, isFallback, response, containFiles); err != nil { + if err := runContainsQueries(cfg, golistDriverCurrent, response, containFiles); err != nil { return nil, err } } if len(packagesNamed) != 0 { - if err := runNamedQueries(cfg, listfunc, response, packagesNamed); err != nil { + if err := runNamedQueries(cfg, golistDriverCurrent, response, packagesNamed); err != nil { return nil, err } } @@ -182,7 +168,7 @@ extractQueries: } if len(needPkgs) > 0 { - addNeededOverlayPackages(cfg, listfunc, response, needPkgs) + addNeededOverlayPackages(cfg, golistDriverCurrent, response, needPkgs) if err != nil { return nil, err } @@ -215,7 +201,7 @@ func addNeededOverlayPackages(cfg *Config, driver driver, response *responseDedu return nil } -func runContainsQueries(cfg *Config, driver driver, isFallback bool, response *responseDeduper, queries []string) error { +func runContainsQueries(cfg *Config, driver driver, response *responseDeduper, queries []string) error { for _, query := range queries { // TODO(matloob): Do only one query per directory. fdir := filepath.Dir(query) @@ -225,11 +211,6 @@ func runContainsQueries(cfg *Config, driver driver, isFallback bool, response *r if err != nil { return fmt.Errorf("could not determine absolute path of file= query path %q: %v", query, err) } - if isFallback { - pattern = "." - cfg.Dir = fdir - } - dirResponse, err := driver(cfg, pattern) if err != nil { return err diff --git a/go/packages/golist_fallback.go b/go/packages/golist_fallback.go deleted file mode 100644 index 141fa19a..00000000 --- a/go/packages/golist_fallback.go +++ /dev/null @@ -1,450 +0,0 @@ -// Copyright 2018 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package packages - -import ( - "encoding/json" - "fmt" - "go/build" - "io/ioutil" - "os" - "os/exec" - "path/filepath" - "sort" - "strings" - - "golang.org/x/tools/go/internal/cgo" -) - -// TODO(matloob): Delete this file once Go 1.12 is released. - -// This file provides backwards compatibility support for -// loading for versions of Go earlier than 1.11. This support is meant to -// assist with migration to the Package API until there's -// widespread adoption of these newer Go versions. -// This support will be removed once Go 1.12 is released -// in Q1 2019. - -func golistDriverFallback(cfg *Config, words ...string) (*driverResponse, error) { - // Turn absolute paths into GOROOT and GOPATH-relative paths to provide to go list. - // This will have surprising behavior if GOROOT or GOPATH contain multiple packages with the same - // path and a user provides an absolute path to a directory that's shadowed by an earlier - // directory in GOROOT or GOPATH with the same package path. - words = cleanAbsPaths(cfg, words) - - original, deps, err := getDeps(cfg, words...) - if err != nil { - return nil, err - } - - var tmpdir string // used for generated cgo files - var needsTestVariant []struct { - pkg, xtestPkg *Package - } - - var response driverResponse - allPkgs := make(map[string]bool) - addPackage := func(p *jsonPackage, isRoot bool) { - id := p.ImportPath - - if allPkgs[id] { - return - } - allPkgs[id] = true - - pkgpath := id - - if pkgpath == "unsafe" { - p.GoFiles = nil // ignore fake unsafe.go file - } - - importMap := func(importlist []string) map[string]*Package { - importMap := make(map[string]*Package) - for _, id := range importlist { - - if id == "C" { - for _, path := range []string{"unsafe", "syscall", "runtime/cgo"} { - if pkgpath != path && importMap[path] == nil { - importMap[path] = &Package{ID: path} - } - } - continue - } - importMap[vendorlessPath(id)] = &Package{ID: id} - } - return importMap - } - compiledGoFiles := absJoin(p.Dir, p.GoFiles) - // Use a function to simplify control flow. It's just a bunch of gotos. - var cgoErrors []error - var outdir string - getOutdir := func() (string, error) { - if outdir != "" { - return outdir, nil - } - if tmpdir == "" { - if tmpdir, err = ioutil.TempDir("", "gopackages"); err != nil { - return "", err - } - } - outdir = filepath.Join(tmpdir, strings.Replace(p.ImportPath, "/", "_", -1)) - if err := os.MkdirAll(outdir, 0755); err != nil { - outdir = "" - return "", err - } - return outdir, nil - } - processCgo := func() bool { - // Suppress any cgo errors. Any relevant errors will show up in typechecking. - // TODO(matloob): Skip running cgo if Mode < LoadTypes. - outdir, err := getOutdir() - if err != nil { - cgoErrors = append(cgoErrors, err) - return false - } - files, _, err := runCgo(p.Dir, outdir, cfg.Env) - if err != nil { - cgoErrors = append(cgoErrors, err) - return false - } - compiledGoFiles = append(compiledGoFiles, files...) - return true - } - if len(p.CgoFiles) == 0 || !processCgo() { - compiledGoFiles = append(compiledGoFiles, absJoin(p.Dir, p.CgoFiles)...) // Punt to typechecker. - } - if isRoot { - response.Roots = append(response.Roots, id) - } - pkg := &Package{ - ID: id, - Name: p.Name, - GoFiles: absJoin(p.Dir, p.GoFiles, p.CgoFiles), - CompiledGoFiles: compiledGoFiles, - OtherFiles: absJoin(p.Dir, otherFiles(p)...), - PkgPath: pkgpath, - Imports: importMap(p.Imports), - // TODO(matloob): set errors on the Package to cgoErrors - } - if p.Error != nil { - pkg.Errors = append(pkg.Errors, Error{ - Pos: p.Error.Pos, - Msg: p.Error.Err, - }) - } - response.Packages = append(response.Packages, pkg) - if cfg.Tests && isRoot { - testID := fmt.Sprintf("%s [%s.test]", id, id) - if len(p.TestGoFiles) > 0 || len(p.XTestGoFiles) > 0 { - response.Roots = append(response.Roots, testID) - testPkg := &Package{ - ID: testID, - Name: p.Name, - GoFiles: absJoin(p.Dir, p.GoFiles, p.CgoFiles, p.TestGoFiles), - CompiledGoFiles: append(compiledGoFiles, absJoin(p.Dir, p.TestGoFiles)...), - OtherFiles: absJoin(p.Dir, otherFiles(p)...), - PkgPath: pkgpath, - Imports: importMap(append(p.Imports, p.TestImports...)), - // TODO(matloob): set errors on the Package to cgoErrors - } - response.Packages = append(response.Packages, testPkg) - var xtestPkg *Package - if len(p.XTestGoFiles) > 0 { - xtestID := fmt.Sprintf("%s_test [%s.test]", id, id) - response.Roots = append(response.Roots, xtestID) - // Generate test variants for all packages q where a path exists - // such that xtestPkg -> ... -> q -> ... -> p (where p is the package under test) - // and rewrite all import map entries of p to point to testPkg (the test variant of - // p), and of each q to point to the test variant of that q. - xtestPkg = &Package{ - ID: xtestID, - Name: p.Name + "_test", - GoFiles: absJoin(p.Dir, p.XTestGoFiles), - CompiledGoFiles: absJoin(p.Dir, p.XTestGoFiles), - PkgPath: pkgpath + "_test", - Imports: importMap(p.XTestImports), - } - // Add to list of packages we need to rewrite imports for to refer to test variants. - // We may need to create a test variant of a package that hasn't been loaded yet, so - // the test variants need to be created later. - needsTestVariant = append(needsTestVariant, struct{ pkg, xtestPkg *Package }{pkg, xtestPkg}) - response.Packages = append(response.Packages, xtestPkg) - } - // testmain package - testmainID := id + ".test" - response.Roots = append(response.Roots, testmainID) - imports := map[string]*Package{} - imports[testPkg.PkgPath] = &Package{ID: testPkg.ID} - if xtestPkg != nil { - imports[xtestPkg.PkgPath] = &Package{ID: xtestPkg.ID} - } - testmainPkg := &Package{ - ID: testmainID, - Name: "main", - PkgPath: testmainID, - Imports: imports, - } - response.Packages = append(response.Packages, testmainPkg) - outdir, err := getOutdir() - if err != nil { - testmainPkg.Errors = append(testmainPkg.Errors, Error{ - Pos: "-", - Msg: fmt.Sprintf("failed to generate testmain: %v", err), - Kind: ListError, - }) - return - } - // Don't use a .go extension on the file, so that the tests think the file is inside GOCACHE. - // This allows the same test to test the pre- and post-Go 1.11 go list logic because the Go 1.11 - // go list generates test mains in the cache, and the test code knows not to rely on paths in the - // cache to stay stable. - testmain := filepath.Join(outdir, "testmain-go") - extraimports, extradeps, err := generateTestmain(testmain, testPkg, xtestPkg) - if err != nil { - testmainPkg.Errors = append(testmainPkg.Errors, Error{ - Pos: "-", - Msg: fmt.Sprintf("failed to generate testmain: %v", err), - Kind: ListError, - }) - } - deps = append(deps, extradeps...) - for _, imp := range extraimports { // testing, testing/internal/testdeps, and maybe os - imports[imp] = &Package{ID: imp} - } - testmainPkg.GoFiles = []string{testmain} - testmainPkg.CompiledGoFiles = []string{testmain} - } - } - } - - for _, pkg := range original { - addPackage(pkg, true) - } - if cfg.Mode < LoadImports || len(deps) == 0 { - return &response, nil - } - - buf, err := invokeGo(cfg, golistArgsFallback(cfg, deps)...) - if err != nil { - return nil, err - } - - // Decode the JSON and convert it to Package form. - for dec := json.NewDecoder(buf); dec.More(); { - p := new(jsonPackage) - if err := dec.Decode(p); err != nil { - return nil, fmt.Errorf("JSON decoding failed: %v", err) - } - - addPackage(p, false) - } - - for _, v := range needsTestVariant { - createTestVariants(&response, v.pkg, v.xtestPkg) - } - - return &response, nil -} - -func createTestVariants(response *driverResponse, pkgUnderTest, xtestPkg *Package) { - allPkgs := make(map[string]*Package) - for _, pkg := range response.Packages { - allPkgs[pkg.ID] = pkg - } - needsTestVariant := make(map[string]bool) - needsTestVariant[pkgUnderTest.ID] = true - var needsVariantRec func(p *Package) bool - needsVariantRec = func(p *Package) bool { - if needsTestVariant[p.ID] { - return true - } - for _, imp := range p.Imports { - if needsVariantRec(allPkgs[imp.ID]) { - // Don't break because we want to make sure all dependencies - // have been processed, and all required test variants of our dependencies - // exist. - needsTestVariant[p.ID] = true - } - } - if !needsTestVariant[p.ID] { - return false - } - // Create a clone of the package. It will share the same strings and lists of source files, - // but that's okay. It's only necessary for the Imports map to have a separate identity. - testVariant := *p - testVariant.ID = fmt.Sprintf("%s [%s.test]", p.ID, pkgUnderTest.ID) - testVariant.Imports = make(map[string]*Package) - for imp, pkg := range p.Imports { - testVariant.Imports[imp] = pkg - if needsTestVariant[pkg.ID] { - testVariant.Imports[imp] = &Package{ID: fmt.Sprintf("%s [%s.test]", pkg.ID, pkgUnderTest.ID)} - } - } - response.Packages = append(response.Packages, &testVariant) - return needsTestVariant[p.ID] - } - // finally, update the xtest package's imports - for imp, pkg := range xtestPkg.Imports { - if allPkgs[pkg.ID] == nil { - fmt.Printf("for %s: package %s doesn't exist\n", xtestPkg.ID, pkg.ID) - } - if needsVariantRec(allPkgs[pkg.ID]) { - xtestPkg.Imports[imp] = &Package{ID: fmt.Sprintf("%s [%s.test]", pkg.ID, pkgUnderTest.ID)} - } - } -} - -// cleanAbsPaths replaces all absolute paths with GOPATH- and GOROOT-relative -// paths. If an absolute path is not GOPATH- or GOROOT- relative, it is left as an -// absolute path so an error can be returned later. -func cleanAbsPaths(cfg *Config, words []string) []string { - var searchpaths []string - var cleaned = make([]string, len(words)) - for i := range cleaned { - cleaned[i] = words[i] - // Ignore relative directory paths (they must already be goroot-relative) and Go source files - // (absolute source files are already allowed for ad-hoc packages). - // TODO(matloob): Can there be non-.go files in ad-hoc packages. - if !filepath.IsAbs(cleaned[i]) || strings.HasSuffix(cleaned[i], ".go") { - continue - } - // otherwise, it's an absolute path. Search GOPATH and GOROOT to find it. - if searchpaths == nil { - cmd := exec.Command("go", "env", "GOPATH", "GOROOT") - cmd.Env = cfg.Env - out, err := cmd.Output() - if err != nil { - searchpaths = []string{} - continue // suppress the error, it will show up again when running go list - } - lines := strings.Split(string(out), "\n") - if len(lines) != 3 || lines[0] == "" || lines[1] == "" || lines[2] != "" { - continue // suppress error - } - // first line is GOPATH - for _, path := range filepath.SplitList(lines[0]) { - searchpaths = append(searchpaths, filepath.Join(path, "src")) - } - // second line is GOROOT - searchpaths = append(searchpaths, filepath.Join(lines[1], "src")) - } - for _, sp := range searchpaths { - if strings.HasPrefix(cleaned[i], sp) { - cleaned[i] = strings.TrimPrefix(cleaned[i], sp) - cleaned[i] = strings.TrimLeft(cleaned[i], string(filepath.Separator)) - } - } - } - return cleaned -} - -// vendorlessPath returns the devendorized version of the import path ipath. -// For example, VendorlessPath("foo/bar/vendor/a/b") returns "a/b". -// Copied from golang.org/x/tools/imports/fix.go. -func vendorlessPath(ipath string) string { - // Devendorize for use in import statement. - if i := strings.LastIndex(ipath, "/vendor/"); i >= 0 { - return ipath[i+len("/vendor/"):] - } - if strings.HasPrefix(ipath, "vendor/") { - return ipath[len("vendor/"):] - } - return ipath -} - -// getDeps runs an initial go list to determine all the dependency packages. -func getDeps(cfg *Config, words ...string) (initial []*jsonPackage, deps []string, err error) { - buf, err := invokeGo(cfg, golistArgsFallback(cfg, words)...) - if err != nil { - return nil, nil, err - } - - depsSet := make(map[string]bool) - var testImports []string - - // Extract deps from the JSON. - for dec := json.NewDecoder(buf); dec.More(); { - p := new(jsonPackage) - if err := dec.Decode(p); err != nil { - return nil, nil, fmt.Errorf("JSON decoding failed: %v", err) - } - - initial = append(initial, p) - for _, dep := range p.Deps { - depsSet[dep] = true - } - if cfg.Tests { - // collect the additional imports of the test packages. - pkgTestImports := append(p.TestImports, p.XTestImports...) - for _, imp := range pkgTestImports { - if depsSet[imp] { - continue - } - depsSet[imp] = true - testImports = append(testImports, imp) - } - } - } - // Get the deps of the packages imported by tests. - if len(testImports) > 0 { - buf, err = invokeGo(cfg, golistArgsFallback(cfg, testImports)...) - if err != nil { - return nil, nil, err - } - // Extract deps from the JSON. - for dec := json.NewDecoder(buf); dec.More(); { - p := new(jsonPackage) - if err := dec.Decode(p); err != nil { - return nil, nil, fmt.Errorf("JSON decoding failed: %v", err) - } - for _, dep := range p.Deps { - depsSet[dep] = true - } - } - } - - for _, orig := range initial { - delete(depsSet, orig.ImportPath) - } - - deps = make([]string, 0, len(depsSet)) - for dep := range depsSet { - deps = append(deps, dep) - } - sort.Strings(deps) // ensure output is deterministic - return initial, deps, nil -} - -func golistArgsFallback(cfg *Config, words []string) []string { - fullargs := []string{"list", "-e", "-json"} - fullargs = append(fullargs, cfg.BuildFlags...) - fullargs = append(fullargs, "--") - fullargs = append(fullargs, words...) - return fullargs -} - -func runCgo(pkgdir, tmpdir string, env []string) (files, displayfiles []string, err error) { - // Use go/build to open cgo files and determine the cgo flags, etc, from them. - // This is tricky so it's best to avoid reimplementing as much as we can, and - // we plan to delete this support once Go 1.12 is released anyways. - // TODO(matloob): This isn't completely correct because we're using the Default - // context. Perhaps we should more accurately fill in the context. - bp, err := build.ImportDir(pkgdir, build.ImportMode(0)) - if err != nil { - return nil, nil, err - } - for _, ev := range env { - if v := strings.TrimPrefix(ev, "CGO_CPPFLAGS"); v != ev { - bp.CgoCPPFLAGS = append(bp.CgoCPPFLAGS, strings.Fields(v)...) - } else if v := strings.TrimPrefix(ev, "CGO_CFLAGS"); v != ev { - bp.CgoCFLAGS = append(bp.CgoCFLAGS, strings.Fields(v)...) - } else if v := strings.TrimPrefix(ev, "CGO_CXXFLAGS"); v != ev { - bp.CgoCXXFLAGS = append(bp.CgoCXXFLAGS, strings.Fields(v)...) - } else if v := strings.TrimPrefix(ev, "CGO_LDFLAGS"); v != ev { - bp.CgoLDFLAGS = append(bp.CgoLDFLAGS, strings.Fields(v)...) - } - } - return cgo.Run(bp, pkgdir, tmpdir, true) -} diff --git a/go/packages/golist_fallback_testmain.go b/go/packages/golist_fallback_testmain.go deleted file mode 100644 index 128e00e2..00000000 --- a/go/packages/golist_fallback_testmain.go +++ /dev/null @@ -1,318 +0,0 @@ -// Copyright 2018 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -// This file is largely based on the Go 1.10-era cmd/go/internal/test/test.go -// testmain generation code. - -package packages - -import ( - "errors" - "fmt" - "go/ast" - "go/doc" - "go/parser" - "go/token" - "os" - "sort" - "strings" - "text/template" - "unicode" - "unicode/utf8" -) - -// TODO(matloob): Delete this file once Go 1.12 is released. - -// This file complements golist_fallback.go by providing -// support for generating testmains. - -func generateTestmain(out string, testPkg, xtestPkg *Package) (extraimports, extradeps []string, err error) { - testFuncs, err := loadTestFuncs(testPkg, xtestPkg) - if err != nil { - return nil, nil, err - } - extraimports = []string{"testing", "testing/internal/testdeps"} - if testFuncs.TestMain == nil { - extraimports = append(extraimports, "os") - } - // Transitive dependencies of ("testing", "testing/internal/testdeps"). - // os is part of the transitive closure so it and its transitive dependencies are - // included regardless of whether it's imported in the template below. - extradeps = []string{ - "errors", - "internal/cpu", - "unsafe", - "internal/bytealg", - "internal/race", - "runtime/internal/atomic", - "runtime/internal/sys", - "runtime", - "sync/atomic", - "sync", - "io", - "unicode", - "unicode/utf8", - "bytes", - "math", - "syscall", - "time", - "internal/poll", - "internal/syscall/unix", - "internal/testlog", - "os", - "math/bits", - "strconv", - "reflect", - "fmt", - "sort", - "strings", - "flag", - "runtime/debug", - "context", - "runtime/trace", - "testing", - "bufio", - "regexp/syntax", - "regexp", - "compress/flate", - "encoding/binary", - "hash", - "hash/crc32", - "compress/gzip", - "path/filepath", - "io/ioutil", - "text/tabwriter", - "runtime/pprof", - "testing/internal/testdeps", - } - return extraimports, extradeps, writeTestmain(out, testFuncs) -} - -// The following is adapted from the cmd/go testmain generation code. - -// isTestFunc tells whether fn has the type of a testing function. arg -// specifies the parameter type we look for: B, M or T. -func isTestFunc(fn *ast.FuncDecl, arg string) bool { - if fn.Type.Results != nil && len(fn.Type.Results.List) > 0 || - fn.Type.Params.List == nil || - len(fn.Type.Params.List) != 1 || - len(fn.Type.Params.List[0].Names) > 1 { - return false - } - ptr, ok := fn.Type.Params.List[0].Type.(*ast.StarExpr) - if !ok { - return false - } - // We can't easily check that the type is *testing.M - // because we don't know how testing has been imported, - // but at least check that it's *M or *something.M. - // Same applies for B and T. - if name, ok := ptr.X.(*ast.Ident); ok && name.Name == arg { - return true - } - if sel, ok := ptr.X.(*ast.SelectorExpr); ok && sel.Sel.Name == arg { - return true - } - return false -} - -// isTest tells whether name looks like a test (or benchmark, according to prefix). -// It is a Test (say) if there is a character after Test that is not a lower-case letter. -// We don't want TesticularCancer. -func isTest(name, prefix string) bool { - if !strings.HasPrefix(name, prefix) { - return false - } - if len(name) == len(prefix) { // "Test" is ok - return true - } - rune, _ := utf8.DecodeRuneInString(name[len(prefix):]) - return !unicode.IsLower(rune) -} - -// loadTestFuncs returns the testFuncs describing the tests that will be run. -func loadTestFuncs(ptest, pxtest *Package) (*testFuncs, error) { - t := &testFuncs{ - TestPackage: ptest, - XTestPackage: pxtest, - } - for _, file := range ptest.GoFiles { - if !strings.HasSuffix(file, "_test.go") { - continue - } - if err := t.load(file, "_test", &t.ImportTest, &t.NeedTest); err != nil { - return nil, err - } - } - if pxtest != nil { - for _, file := range pxtest.GoFiles { - if err := t.load(file, "_xtest", &t.ImportXtest, &t.NeedXtest); err != nil { - return nil, err - } - } - } - return t, nil -} - -// writeTestmain writes the _testmain.go file for t to the file named out. -func writeTestmain(out string, t *testFuncs) error { - f, err := os.Create(out) - if err != nil { - return err - } - defer f.Close() - - if err := testmainTmpl.Execute(f, t); err != nil { - return err - } - - return nil -} - -type testFuncs struct { - Tests []testFunc - Benchmarks []testFunc - Examples []testFunc - TestMain *testFunc - TestPackage *Package - XTestPackage *Package - ImportTest bool - NeedTest bool - ImportXtest bool - NeedXtest bool -} - -// Tested returns the name of the package being tested. -func (t *testFuncs) Tested() string { - return t.TestPackage.Name -} - -type testFunc struct { - Package string // imported package name (_test or _xtest) - Name string // function name - Output string // output, for examples - Unordered bool // output is allowed to be unordered. -} - -func (t *testFuncs) load(filename, pkg string, doImport, seen *bool) error { - var fset = token.NewFileSet() - - f, err := parser.ParseFile(fset, filename, nil, parser.ParseComments) - if err != nil { - return errors.New("failed to parse test file " + filename) - } - for _, d := range f.Decls { - n, ok := d.(*ast.FuncDecl) - if !ok { - continue - } - if n.Recv != nil { - continue - } - name := n.Name.String() - switch { - case name == "TestMain": - if isTestFunc(n, "T") { - t.Tests = append(t.Tests, testFunc{pkg, name, "", false}) - *doImport, *seen = true, true - continue - } - err := checkTestFunc(fset, n, "M") - if err != nil { - return err - } - if t.TestMain != nil { - return errors.New("multiple definitions of TestMain") - } - t.TestMain = &testFunc{pkg, name, "", false} - *doImport, *seen = true, true - case isTest(name, "Test"): - err := checkTestFunc(fset, n, "T") - if err != nil { - return err - } - t.Tests = append(t.Tests, testFunc{pkg, name, "", false}) - *doImport, *seen = true, true - case isTest(name, "Benchmark"): - err := checkTestFunc(fset, n, "B") - if err != nil { - return err - } - t.Benchmarks = append(t.Benchmarks, testFunc{pkg, name, "", false}) - *doImport, *seen = true, true - } - } - ex := doc.Examples(f) - sort.Slice(ex, func(i, j int) bool { return ex[i].Order < ex[j].Order }) - for _, e := range ex { - *doImport = true // import test file whether executed or not - if e.Output == "" && !e.EmptyOutput { - // Don't run examples with no output. - continue - } - t.Examples = append(t.Examples, testFunc{pkg, "Example" + e.Name, e.Output, e.Unordered}) - *seen = true - } - return nil -} - -func checkTestFunc(fset *token.FileSet, fn *ast.FuncDecl, arg string) error { - if !isTestFunc(fn, arg) { - name := fn.Name.String() - pos := fset.Position(fn.Pos()) - return fmt.Errorf("%s: wrong signature for %s, must be: func %s(%s *testing.%s)", pos, name, name, strings.ToLower(arg), arg) - } - return nil -} - -var testmainTmpl = template.Must(template.New("main").Parse(` -package main - -import ( -{{if not .TestMain}} - "os" -{{end}} - "testing" - "testing/internal/testdeps" - -{{if .ImportTest}} - {{if .NeedTest}}_test{{else}}_{{end}} {{.TestPackage.PkgPath | printf "%q"}} -{{end}} -{{if .ImportXtest}} - {{if .NeedXtest}}_xtest{{else}}_{{end}} {{.XTestPackage.PkgPath | printf "%q"}} -{{end}} -) - -var tests = []testing.InternalTest{ -{{range .Tests}} - {"{{.Name}}", {{.Package}}.{{.Name}}}, -{{end}} -} - -var benchmarks = []testing.InternalBenchmark{ -{{range .Benchmarks}} - {"{{.Name}}", {{.Package}}.{{.Name}}}, -{{end}} -} - -var examples = []testing.InternalExample{ -{{range .Examples}} - {"{{.Name}}", {{.Package}}.{{.Name}}, {{.Output | printf "%q"}}, {{.Unordered}}}, -{{end}} -} - -func init() { - testdeps.ImportPath = {{.TestPackage.PkgPath | printf "%q"}} -} - -func main() { - m := testing.MainStart(testdeps.TestDeps{}, tests, benchmarks, examples) -{{with .TestMain}} - {{.Package}}.{{.Name}}(m) -{{else}} - os.Exit(m.Run()) -{{end}} -} - -`)) diff --git a/go/packages/packages_test.go b/go/packages/packages_test.go index 82aeb0e5..4424090f 100644 --- a/go/packages/packages_test.go +++ b/go/packages/packages_test.go @@ -26,10 +26,6 @@ import ( "golang.org/x/tools/go/packages/packagestest" ) -// TODO(matloob): remove this once Go 1.12 is released as we will end support -// for versions of go list before Go 1.10.4. -var usesOldGolist = false - // TODO(adonovan): more test cases to write: // // - When the tests fail, make them print a 'cd & load' command @@ -566,11 +562,6 @@ func testLoadTypes(t *testing.T, exporter packagestest.Exporter) { {"golang.org/fake/b", false}, // use export data {"golang.org/fake/c", true}, // need src, no export data for c } { - if usesOldGolist && !test.wantSyntax { - // legacy go list always upgrades to LoadAllSyntax, syntax will be filled in. - // still check that types information is complete. - test.wantSyntax = true - } p := all[test.id] if p == nil { t.Errorf("missing package: %s", test.id) @@ -642,14 +633,6 @@ func testLoadSyntaxOK(t *testing.T, exporter packagestest.Exporter) { {"golang.org/fake/e", false, false}, // export data package {"golang.org/fake/f", false, false}, // export data package } { - // TODO(matloob): The legacy go list based support loads - // everything from source because it doesn't do a build - // and the .a files don't exist. - // Can we simulate its existence? - if usesOldGolist { - test.wantComplete = true - test.wantSyntax = true - } p := all[test.id] if p == nil { t.Errorf("missing package: %s", test.id) @@ -768,10 +751,6 @@ func testLoadSyntaxError(t *testing.T, exporter packagestest.Exporter) { {"golang.org/fake/e", true, true}, {"golang.org/fake/f", false, false}, } { - if usesOldGolist && !test.wantSyntax { - // legacy go list always upgrades to LoadAllSyntax, syntax will be filled in. - test.wantSyntax = true - } p := all[test.id] if p == nil { t.Errorf("missing package: %s", test.id) @@ -1217,10 +1196,6 @@ func testName(t *testing.T, exporter packagestest.Exporter) { } func TestName_Modules(t *testing.T) { - if usesOldGolist { - t.Skip("pre-modules version of Go") - } - // Test the top-level package case described in runNamedQueries. // Note that overriding GOPATH below prevents Export from // creating more than one module. @@ -1265,10 +1240,6 @@ func TestName_Modules(t *testing.T) { } func TestName_ModulesDedup(t *testing.T) { - if usesOldGolist { - t.Skip("pre-modules version of Go") - } - exported := packagestest.Export(t, packagestest.Modules, []packagestest.Module{{ Name: "golang.org/fake", Files: map[string]interface{}{