]> Cypherpunks repositories - gostls13.git/commitdiff
cmd/go/internal/modload: return error when tidyRoots fail
authorianwoolf <btw515wolf2@gmail.com>
Wed, 31 Aug 2022 15:34:26 +0000 (23:34 +0800)
committerBryan Mills <bcmills@google.com>
Fri, 14 Oct 2022 16:35:15 +0000 (16:35 +0000)
Fixes #51589

Change-Id: Ie9c56110754f4a435b22e2d7a86ae34b0bd28909
Reviewed-on: https://go-review.googlesource.com/c/go/+/427054
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Run-TryBot: Dmitri Shuralyov <dmitshur@golang.org>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Bryan Mills <bcmills@google.com>
src/cmd/go/internal/modload/load.go
src/cmd/go/internal/web/api.go
src/cmd/go/testdata/script/mod_fileproxy_vcs_missing_issue51589.txt [new file with mode: 0644]

index 09572bf1b19251740ad0fd92f51a920fb6ac064d..fcd93ba94b75a7fdcf19f892cd93e302ef039d23 100644 (file)
@@ -1151,22 +1151,23 @@ func loadFromRoots(ctx context.Context, params loaderParams) *loader {
                rs, err := tidyRoots(ctx, ld.requirements, ld.pkgs)
                if err != nil {
                        ld.errorf("go: %v\n", err)
-               }
-
-               if ld.requirements.pruning == pruned {
-                       // We continuously add tidy roots to ld.requirements during loading, so at
-                       // this point the tidy roots should be a subset of the roots of
-                       // ld.requirements, ensuring that no new dependencies are brought inside
-                       // the graph-pruning horizon.
-                       // If that is not the case, there is a bug in the loading loop above.
-                       for _, m := range rs.rootModules {
-                               if v, ok := ld.requirements.rootSelected(m.Path); !ok || v != m.Version {
-                                       ld.errorf("go: internal error: a requirement on %v is needed but was not added during package loading\n", m)
-                                       base.ExitIfErrors()
+                       base.ExitIfErrors()
+               } else {
+                       if ld.requirements.pruning == pruned {
+                               // We continuously add tidy roots to ld.requirements during loading, so at
+                               // this point the tidy roots should be a subset of the roots of
+                               // ld.requirements, ensuring that no new dependencies are brought inside
+                               // the graph-pruning horizon.
+                               // If that is not the case, there is a bug in the loading loop above.
+                               for _, m := range rs.rootModules {
+                                       if v, ok := ld.requirements.rootSelected(m.Path); !ok || v != m.Version {
+                                               ld.errorf("go: internal error: a requirement on %v is needed but was not added during package loading\n", m)
+                                               base.ExitIfErrors()
+                                       }
                                }
                        }
+                       ld.requirements = rs
                }
-               ld.requirements = rs
        }
 
        // Report errors, if any.
index 9053b16b629a688ffa0d120fe378110dd040b040..1e2ba9c4197745f492cf21bcb679208c62a9945f 100644 (file)
@@ -54,12 +54,16 @@ func (e *HTTPError) Error() string {
                return fmt.Sprintf("reading %s: %v\n\tserver response:%s%s", e.URL, e.Status, detailSep, e.Detail)
        }
 
-       if err := e.Err; err != nil {
-               if pErr, ok := e.Err.(*fs.PathError); ok && strings.HasSuffix(e.URL, pErr.Path) {
-                       // Remove the redundant copy of the path.
-                       err = pErr.Err
+       if eErr := e.Err; eErr != nil {
+               if pErr, ok := e.Err.(*fs.PathError); ok {
+                       if u, err := url.Parse(e.URL); err == nil {
+                               if fp, err := urlToFilePath(u); err == nil && pErr.Path == fp {
+                                       // Remove the redundant copy of the path.
+                                       eErr = pErr.Err
+                               }
+                       }
                }
-               return fmt.Sprintf("reading %s: %v", e.URL, err)
+               return fmt.Sprintf("reading %s: %v", e.URL, eErr)
        }
 
        return fmt.Sprintf("reading %s: %v", e.URL, e.Status)
diff --git a/src/cmd/go/testdata/script/mod_fileproxy_vcs_missing_issue51589.txt b/src/cmd/go/testdata/script/mod_fileproxy_vcs_missing_issue51589.txt
new file mode 100644 (file)
index 0000000..2db3978
--- /dev/null
@@ -0,0 +1,42 @@
+# This test checks that "go mod tidy -e" do not panic when
+# using a file goproxy that is missing some modules.
+# Verifies golang.org/issue/51589
+
+# download the modules first
+env GO111MODULE=on
+env GOPATH=$WORK/gopath
+cd $WORK/x
+go mod tidy
+
+# Use download cache as file:/// proxy.
+[windows] env GOPROXY=file:///$WORK/gopath/pkg/mod/cache/download
+[!windows] env GOPROXY=file://$WORK/gopath/pkg/mod/cache/download
+rm $WORK/gopath/pkg/mod/cache/download/golang.org/x/text/
+go mod tidy -e
+stderr '^go: rsc.io/sampler@v1.3.0 requires\n\tgolang.org/x/text@.*: reading file://.*/pkg/mod/cache/download/golang.org/x/text/.*'
+! stderr 'signal SIGSEGV: segmentation violation'
+
+-- $WORK/x/go.mod --
+module example.com/mod
+
+go 1.17
+
+require rsc.io/quote v1.5.2
+
+require (
+       golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c // indirect
+       rsc.io/sampler v1.3.0 // indirect
+)
+
+-- $WORK/x/x.go --
+package mod
+
+import (
+       "fmt"
+
+       "rsc.io/quote"
+)
+
+func Echo() {
+       fmt.Println(quote.Hello())
+}
\ No newline at end of file