Go: testing: Cleanup races with Logf and Errorf

Created on 19 Aug 2020  路  9Comments  路  Source: golang/go

The program in https://play.golang.org/p/rV-CkJivlXs fails under go test -race:

func TestBackgroundCleanup(t *testing.T) {
    helperDone := make(chan struct{})
    go func() {
        t.Logf("Something happened before cleanup.")
        close(helperDone)
    }()

    t.Cleanup(func() {
        <-helperDone
    })
}
$ go version
go version devel +d3a411b6 Wed Aug 19 03:56:26 2020 +0000 linux/amd64

$ go test -race
==================
WARNING: DATA RACE
Read at 0x00c000001858 by goroutine 8:
  testing.(*common).frameSkip()
      /usr/local/google/home/bcmills/sdk/gotip/src/testing/testing.go:488 +0x26e
  testing.(*common).decorate()
      /usr/local/google/home/bcmills/sdk/gotip/src/testing/testing.go:533 +0x64
  testing.(*common).logDepth()
      /usr/local/google/home/bcmills/sdk/gotip/src/testing/testing.go:760 +0x5ab
  testing.(*common).log()
      /usr/local/google/home/bcmills/sdk/gotip/src/testing/testing.go:729 +0x8f
  testing.(*common).Logf()
      /usr/local/google/home/bcmills/sdk/gotip/src/testing/testing.go:775 +0x21
  example%2ecom.TestBackgroundCleanup.func1()
      /tmp/tmp.BqaVZz8DDs/example.com/main_test.go:8 +0x64

Previous write at 0x00c000001858 by goroutine 7:
  testing.(*common).Cleanup.func1()
      /usr/local/google/home/bcmills/sdk/gotip/src/testing/testing.go:867 +0xba
  testing.(*common).runCleanup()
      /usr/local/google/home/bcmills/sdk/gotip/src/testing/testing.go:945 +0xca
  testing.tRunner.func2()
      /usr/local/google/home/bcmills/sdk/gotip/src/testing/testing.go:1117 +0x74
  testing.tRunner()
      /usr/local/google/home/bcmills/sdk/gotip/src/testing/testing.go:1127 +0x22a

Goroutine 8 (running) created at:
  example%2ecom.TestBackgroundCleanup()
      /tmp/tmp.BqaVZz8DDs/example.com/main_test.go:7 +0x78
  testing.tRunner()
      /usr/local/google/home/bcmills/sdk/gotip/src/testing/testing.go:1123 +0x202

Goroutine 7 (running) created at:
  testing.(*T).Run()
      /usr/local/google/home/bcmills/sdk/gotip/src/testing/testing.go:1174 +0x796
  testing.runTests.func1()
      /usr/local/google/home/bcmills/sdk/gotip/src/testing/testing.go:1445 +0xa6
  testing.tRunner()
      /usr/local/google/home/bcmills/sdk/gotip/src/testing/testing.go:1123 +0x202
  testing.runTests()
      /usr/local/google/home/bcmills/sdk/gotip/src/testing/testing.go:1443 +0x5aa
  testing.(*M).Run()
      /usr/local/google/home/bcmills/sdk/gotip/src/testing/testing.go:1353 +0x4eb
  main.main()
      _testmain.go:43 +0x236
==================
--- FAIL: TestBackgroundCleanup (0.00s)
    main_test.go:8: Something happened before cleanup.
    testing.go:1038: race detected during execution of test
FAIL
exit status 1
FAIL    example.com 0.019s

I think this race should be fixed, because this usage seems reasonable to me: for example, calling t.Logf directly from the Cleanup callback does _not_ race, and it seems very odd to allow t.Logf before and after cleanup begins but not during.

CC @rogpeppe @ianlancetaylor @bradfitz

NeedsFix

Most helpful comment

@bcmills Indeed, thanks for pointing this out. I'll work on a fix.

All 9 comments

Looks like https://go-review.googlesource.com/c/go/+/232237 introduced this issue FWIW.

CC @mlowicki @tklauser

@bcmills Indeed, thanks for pointing this out. I'll work on a fix.

We also ran into this here: https://github.com/knative/serving/pull/9153 when I switched from defer to t.Cleanup.

Change https://golang.org/cl/250078 mentions this issue: testing: fix Cleanup race with Logf and Errorf

@gopherbot, please backport to 1.15. This is a fairly subtle race condition, and the fix is small and contained.

Backport issue(s) opened: #41034 (for 1.15).

Remember to create the cherry-pick CL(s) as soon as the patch is submitted to master, according to https://golang.org/wiki/MinorReleases.

Go 1.14.7 does not seem to be affected, so no backport to 1.14 is needed.

Change https://golang.org/cl/250617 mentions this issue: [release-branch.go1.15] testing: fix Cleanup race with Logf and Errorf

Was this page helpful?
0 / 5 - 0 ratings

Related issues

mingrammer picture mingrammer  路  3Comments

gopherbot picture gopherbot  路  3Comments

enoodle picture enoodle  路  3Comments

natefinch picture natefinch  路  3Comments

bbodenmiller picture bbodenmiller  路  3Comments