@@ -263,11 +263,11 @@ func clearSignalHandlers() {
263
263
}
264
264
}
265
265
266
- // setProcessCPUProfiler is called when the profiling timer changes.
267
- // It is called with prof.lock held. hz is the new timer, and is 0 if
266
+ // setProcessCPUProfilerTimer is called when the profiling timer changes.
267
+ // It is called with prof.signalLock held. hz is the new timer, and is 0 if
268
268
// profiling is being disabled. Enable or disable the signal as
269
269
// required for -buildmode=c-archive.
270
- func setProcessCPUProfiler (hz int32 ) {
270
+ func setProcessCPUProfilerTimer (hz int32 ) {
271
271
if hz != 0 {
272
272
// Enable the Go signal handler if not enabled.
273
273
if atomic .Cas (& handlingSig [_SIGPROF ], 0 , 1 ) {
@@ -309,10 +309,10 @@ func setProcessCPUProfiler(hz int32) {
309
309
}
310
310
}
311
311
312
- // setThreadCPUProfiler makes any thread-specific changes required to
312
+ // setThreadCPUProfilerHz makes any thread-specific changes required to
313
313
// implement profiling at a rate of hz.
314
- // No changes required on Unix systems.
315
- func setThreadCPUProfiler (hz int32 ) {
314
+ // No changes required on Unix systems when using setitimer .
315
+ func setThreadCPUProfilerHz (hz int32 ) {
316
316
getg ().m .profilehz = hz
317
317
}
318
318
@@ -423,7 +423,11 @@ func sigtrampgo(sig uint32, info *siginfo, ctx unsafe.Pointer) {
423
423
setg (g )
424
424
if g == nil {
425
425
if sig == _SIGPROF {
426
- sigprofNonGoPC (c .sigpc ())
426
+ // Some platforms (Linux) have per-thread timers, which we use in
427
+ // combination with the process-wide timer. Avoid double-counting.
428
+ if validSIGPROF (nil , c ) {
429
+ sigprofNonGoPC (c .sigpc ())
430
+ }
427
431
return
428
432
}
429
433
if sig == sigPreempt && preemptMSupported && debug .asyncpreemptoff == 0 {
@@ -540,7 +544,12 @@ func sighandler(sig uint32, info *siginfo, ctxt unsafe.Pointer, gp *g) {
540
544
c := & sigctxt {info , ctxt }
541
545
542
546
if sig == _SIGPROF {
543
- sigprof (c .sigpc (), c .sigsp (), c .siglr (), gp , _g_ .m )
547
+ mp := _g_ .m
548
+ // Some platforms (Linux) have per-thread timers, which we use in
549
+ // combination with the process-wide timer. Avoid double-counting.
550
+ if validSIGPROF (mp , c ) {
551
+ sigprof (c .sigpc (), c .sigsp (), c .siglr (), gp , mp )
552
+ }
544
553
return
545
554
}
546
555
0 commit comments