]> Cypherpunks repositories - gostls13.git/commitdiff
cmd/go: fix detached heads that are remnants of bad git clones.
authorDavid Symonds <dsymonds@golang.org>
Wed, 14 Aug 2013 23:44:23 +0000 (09:44 +1000)
committerDavid Symonds <dsymonds@golang.org>
Wed, 14 Aug 2013 23:44:23 +0000 (09:44 +1000)
Fixes #6042.

R=adg
CC=golang-dev
https://golang.org/cl/12923043

src/cmd/go/vcs.go

index d857c1446277ecebc687060812ec932fef69be4d..ec5dc17c5fd5391e55a9e20dbd3f43523d252ba7 100644 (file)
@@ -223,9 +223,36 @@ func (v *vcsCmd) create(dir, repo string) error {
 
 // download downloads any new changes for the repo in dir.
 func (v *vcsCmd) download(dir string) error {
+       if err := v.fixDetachedHead(dir); err != nil {
+               return err
+       }
        return v.run(dir, v.downloadCmd)
 }
 
+// fixDetachedHead switches a Git repository in dir from a detached head to the master branch.
+// Go versions before 1.2 downloaded Git repositories in an unfortunate way
+// that resulted in the working tree state being on a detached head.
+// That meant the repository was not usable for normal Git operations.
+// Go 1.2 fixed that, but we can't pull into a detached head, so if this is
+// a Git repository we check for being on a detached head and switch to the
+// real branch, almost always called "master".
+// TODO(dsymonds): Consider removing this for Go 1.3.
+func (v *vcsCmd) fixDetachedHead(dir string) error {
+       if v != vcsGit {
+               return nil
+       }
+
+       // "git symbolic-ref HEAD" succeeds iff we are not on a detached head.
+       if err := v.runVerboseOnly(dir, "symbolic-ref HEAD"); err == nil {
+               // not on a detached head
+               return nil
+       }
+       if buildV {
+               log.Printf("%s on detached head; repairing", dir)
+       }
+       return v.run(dir, "checkout master")
+}
+
 // tags returns the list of available tags for the repo in dir.
 func (v *vcsCmd) tags(dir string) ([]string, error) {
        var tags []string