From 78b12c962613340f18d456e8eaef0aa217e60ce6 Mon Sep 17 00:00:00 2001 From: Daniel Baumann Date: Sat, 8 Jun 2024 06:06:25 +0200 Subject: Adding upstream version 1.21.11. Signed-off-by: Daniel Baumann --- src/cmd/go/internal/modfetch/codehost/git.go | 24 +++++++++++++++--------- 1 file changed, 15 insertions(+), 9 deletions(-) (limited to 'src/cmd/go/internal/modfetch') diff --git a/src/cmd/go/internal/modfetch/codehost/git.go b/src/cmd/go/internal/modfetch/codehost/git.go index d1a18a8..294e50f 100644 --- a/src/cmd/go/internal/modfetch/codehost/git.go +++ b/src/cmd/go/internal/modfetch/codehost/git.go @@ -18,6 +18,7 @@ import ( "os/exec" "path/filepath" "runtime" + "slices" "sort" "strconv" "strings" @@ -154,7 +155,7 @@ type gitRepo struct { refsErr error localTagsOnce sync.Once - localTags map[string]bool + localTags sync.Map // map[string]bool } const ( @@ -166,7 +167,6 @@ const ( // loadLocalTags loads tag references from the local git cache // into the map r.localTags. -// Should only be called as r.localTagsOnce.Do(r.loadLocalTags). func (r *gitRepo) loadLocalTags(ctx context.Context) { // The git protocol sends all known refs and ls-remote filters them on the client side, // so we might as well record both heads and tags in one shot. @@ -176,10 +176,9 @@ func (r *gitRepo) loadLocalTags(ctx context.Context) { return } - r.localTags = make(map[string]bool) for _, line := range strings.Split(string(out), "\n") { if line != "" { - r.localTags[line] = true + r.localTags.Store(line, true) } } } @@ -430,7 +429,7 @@ func (r *gitRepo) stat(ctx context.Context, rev string) (info *RevInfo, err erro // Maybe rev is a tag we already have locally. // (Note that we're excluding branches, which can be stale.) r.localTagsOnce.Do(func() { r.loadLocalTags(ctx) }) - if r.localTags[rev] { + if _, ok := r.localTags.Load(rev); ok { return r.statLocal(ctx, rev, "refs/tags/"+rev) } @@ -506,11 +505,18 @@ func (r *gitRepo) stat(ctx context.Context, rev string) (info *RevInfo, err erro // Either way, try a local stat before falling back to network I/O. if !didStatLocal { if info, err := r.statLocal(ctx, rev, hash); err == nil { - if after, found := strings.CutPrefix(ref, "refs/tags/"); found { - // Make sure tag exists, so it will be in localTags next time the go command is run. - Run(ctx, r.dir, "git", "tag", after, hash) + tag, fromTag := strings.CutPrefix(ref, "refs/tags/") + if fromTag && !slices.Contains(info.Tags, tag) { + // The local repo includes the commit hash we want, but it is missing + // the corresponding tag. Add that tag and try again. + _, err := Run(ctx, r.dir, "git", "tag", tag, hash) + if err != nil { + return nil, err + } + r.localTags.Store(tag, true) + return r.statLocal(ctx, rev, ref) } - return info, nil + return info, err } } -- cgit v1.2.3