Commit 4a45ac57 authored by Dmitry Vyukov's avatar Dmitry Vyukov

runtime: fix false race report during tracing

Currently race detector produces the following reports on pprof tests:

WARNING: DATA RACE
Read by goroutine 4:
  runtime/pprof_test.TestTraceStartStop()
      src/runtime/pprof/trace_test.go:38 +0x1da
  testing.tRunner()
      src/testing/testing.go:448 +0x13a

Previous write by goroutine 5:
  bytes.(*Buffer).grow()
      src/bytes/buffer.go:102 +0x190
  bytes.(*Buffer).Write()
      src/bytes/buffer.go:127 +0x75
  runtime/pprof.func·002()
      src/runtime/pprof/pprof.go:633 +0xae

Trace writer goroutine synchronizes with StopTrace
using trace.shutdownSema runtime semaphore.
But race detector does not see that synchronization
and so produces false reports.
Teach race detector about the synchronization.

Change-Id: I1219817325d4e16b423f29a0cbee94c929793881
Reviewed-on: https://go-review.googlesource.com/3746Reviewed-by: 's avatarRuss Cox <rsc@golang.org>
parent fc5baec3
......@@ -231,6 +231,9 @@ func StopTrace() {
// The world is started but we've set trace.shutdown, so new tracing can't start.
// Wait for the trace reader to flush pending buffers and stop.
semacquire(&trace.shutdownSema, false)
if raceenabled {
raceacquire(unsafe.Pointer(&trace.shutdownSema))
}
// The lock protects us from races with StartTrace/StopTrace because they do stop-the-world.
lock(&trace.lock)
......@@ -331,6 +334,12 @@ func ReadTrace() []byte {
if trace.shutdown {
trace.lockOwner = nil
unlock(&trace.lock)
if raceenabled {
// Model synchronization on trace.shutdownSema, which race
// detector does not see. This is required to avoid false
// race reports on writer passed to pprof.StartTrace.
racerelease(unsafe.Pointer(&trace.shutdownSema))
}
// trace.enabled is already reset, so can call traceable functions.
semrelease(&trace.shutdownSema)
return 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