Commit 94e3a304 authored by Jay Conrod's avatar Jay Conrod Committed by Robert Griesemer

cmd/cover: don't try to attach directives to synthetic decls

Fixed an error that occurred in atomic mode. cover adds a global
variable declaration that forces sync/atomic to be used. fixDirectives
was confused by this declaration since it has an invalid
position. These declarations are now skipped.

Fixes #22309

Change-Id: I84f5fec13ef847fca35ad49f7704fb93b60503e0
Reviewed-on: https://go-review.googlesource.com/71351
Run-TryBot: Jay Conrod <jayconrod@google.com>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: 's avatarRobert Griesemer <gri@golang.org>
parent 5f740d68
......@@ -258,29 +258,48 @@ func (f *File) Visit(node ast.Node) ast.Visitor {
func (f *File) fixDirectives() []*ast.Comment {
// Scan comments in the file and collect directives. Detach all comments.
var directives []*ast.Comment
prev := token.NoPos // smaller than any valid token.Pos
for _, cg := range f.astFile.Comments {
for _, c := range cg.List {
// Skip directives that will be included by initialComments, i.e., those
// before the package declaration but not in the file doc comment group.
if f.isDirective(c) && (c.Pos() >= f.astFile.Package || cg == f.astFile.Doc) {
// Assume (but verify) that comments are sorted by position.
pos := c.Pos()
if !pos.IsValid() {
log.Fatalf("compiler directive has no position: %q", c.Text)
} else if pos < prev {
log.Fatalf("compiler directives are out of order. %s was before %s.",
f.fset.Position(prev), f.fset.Position(pos))
}
prev = pos
directives = append(directives, c)
}
}
cg.List = nil
}
f.astFile.Comments = nil // force printer to use node comments
if len(directives) == 0 {
// Common case: no directives to attach.
return nil
}
// Iterate over top-level declarations and attach preceding directives.
di := 0
var prevPos token.Pos
prev = token.NoPos
for _, decl := range f.astFile.Decls {
// Assume (but verify) that comments are sorted by position.
// Assume (but verify) that declarations are sorted by position.
pos := decl.Pos()
if pos < prevPos {
log.Fatalf("comments are out of order. %s was before %s.",
f.fset.Position(prevPos), f.fset.Position(pos))
if !pos.IsValid() {
// Synthetic decl. Don't add directives.
continue
}
if pos < prev {
log.Fatalf("declarations are out of order. %s was before %s.",
f.fset.Position(prev), f.fset.Position(pos))
}
prevPos = pos
prev = pos
var doc **ast.CommentGroup
switch d := decl.(type) {
......
......@@ -121,8 +121,8 @@ func TestDirectives(t *testing.T) {
}
sourceDirectives := findDirectives(source)
// go tool cover -mode=set ./testdata/directives.go
cmd := exec.Command(testenv.GoToolPath(t), "tool", "cover", "-mode=set", testDirectives)
// go tool cover -mode=atomic ./testdata/directives.go
cmd := exec.Command(testenv.GoToolPath(t), "tool", "cover", "-mode=atomic", testDirectives)
cmd.Stderr = os.Stderr
output, err := cmd.Output()
if err != nil {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment