Skip to content

Commit 54cf1b1

Browse files
committed
runtime: convert prof.hz to atomic type
This converts several unsynchronized reads (reads without holding prof.signalLock) into atomic reads. For #53821. For #52912. Change-Id: I421b96a22fbe26d699bcc21010c8a9e0f4efc276 Reviewed-on: https://go-review.googlesource.com/c/go/+/420196 Reviewed-by: Austin Clements <[email protected]> Run-TryBot: Michael Pratt <[email protected]> TryBot-Result: Gopher Robot <[email protected]>
1 parent 3121c2b commit 54cf1b1

File tree

3 files changed

+11
-8
lines changed

3 files changed

+11
-8
lines changed

src/runtime/cpuprof.go

+1-1
Original file line numberDiff line numberDiff line change
@@ -110,7 +110,7 @@ func (p *cpuProfile) add(tagPtr *unsafe.Pointer, stk []uintptr) {
110110
osyield()
111111
}
112112

113-
if prof.hz != 0 { // implies cpuprof.log != nil
113+
if prof.hz.Load() != 0 { // implies cpuprof.log != nil
114114
if p.numExtra > 0 || p.lostExtra > 0 || p.lostAtomic > 0 {
115115
p.addExtra()
116116
}

src/runtime/proc.go

+8-5
Original file line numberDiff line numberDiff line change
@@ -4475,7 +4475,10 @@ func mcount() int32 {
44754475

44764476
var prof struct {
44774477
signalLock atomic.Uint32
4478-
hz int32
4478+
4479+
// Must hold signalLock to write. Reads may be lock-free, but
4480+
// signalLock should be taken to synchronize with changes.
4481+
hz atomic.Int32
44794482
}
44804483

44814484
func _System() { _System() }
@@ -4490,7 +4493,7 @@ func _VDSO() { _VDSO() }
44904493
//
44914494
//go:nowritebarrierrec
44924495
func sigprof(pc, sp, lr uintptr, gp *g, mp *m) {
4493-
if prof.hz == 0 {
4496+
if prof.hz.Load() == 0 {
44944497
return
44954498
}
44964499

@@ -4587,7 +4590,7 @@ func sigprof(pc, sp, lr uintptr, gp *g, mp *m) {
45874590
}
45884591
}
45894592

4590-
if prof.hz != 0 {
4593+
if prof.hz.Load() != 0 {
45914594
// Note: it can happen on Windows that we interrupted a system thread
45924595
// with no g, so gp could nil. The other nil checks are done out of
45934596
// caution, but not expected to be nil in practice.
@@ -4631,9 +4634,9 @@ func setcpuprofilerate(hz int32) {
46314634
for !prof.signalLock.CompareAndSwap(0, 1) {
46324635
osyield()
46334636
}
4634-
if prof.hz != hz {
4637+
if prof.hz.Load() != hz {
46354638
setProcessCPUProfiler(hz)
4636-
prof.hz = hz
4639+
prof.hz.Store(hz)
46374640
}
46384641
prof.signalLock.Store(0)
46394642

src/runtime/signal_unix.go

+2-2
Original file line numberDiff line numberDiff line change
@@ -502,7 +502,7 @@ var sigprofCallersUse uint32
502502
//go:nosplit
503503
//go:nowritebarrierrec
504504
func sigprofNonGo(sig uint32, info *siginfo, ctx unsafe.Pointer) {
505-
if prof.hz != 0 {
505+
if prof.hz.Load() != 0 {
506506
c := &sigctxt{info, ctx}
507507
// Some platforms (Linux) have per-thread timers, which we use in
508508
// combination with the process-wide timer. Avoid double-counting.
@@ -525,7 +525,7 @@ func sigprofNonGo(sig uint32, info *siginfo, ctx unsafe.Pointer) {
525525
//go:nosplit
526526
//go:nowritebarrierrec
527527
func sigprofNonGoPC(pc uintptr) {
528-
if prof.hz != 0 {
528+
if prof.hz.Load() != 0 {
529529
stk := []uintptr{
530530
pc,
531531
abi.FuncPCABIInternal(_ExternalCode) + sys.PCQuantum,

0 commit comments

Comments
 (0)