Last active
March 5, 2026 16:20
-
-
Save dankox/26f90a308380f3af4e52ea2929a4f8d0 to your computer and use it in GitHub Desktop.
Blocking SIGURG to avoid preempt in critical path
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| package main | |
| import ( | |
| "runtime" | |
| "unsafe" | |
| "golang.org/x/sys/unix" | |
| ) | |
| func backgroundGoroutine() { | |
| // Ensure running on separate thread | |
| runtime.LockOSThread() | |
| defer runtime.UnlockOSThread() | |
| // Block SIGURG signal | |
| var oldSigset, newSigset [8 / unsafe.Sizeof(uintptr(0))]uintptr | |
| newSigset[0] = 1 << (unix.SIGURG - 1) | |
| unix.RawSyscall6( | |
| unix.SYS_RT_SIGPROCMASK, | |
| unix.SIG_BLOCK, | |
| uintptr(unsafe.Pointer(&newSigset)), | |
| uintptr(unsafe.Pointer(&oldSigset)), | |
| uintptr(unsafe.Sizeof(newSigset)), | |
| 0, 0, | |
| ) | |
| defer unix.RawSyscall6( | |
| unix.SYS_RT_SIGPROCMASK, | |
| unix.SIG_SETMASK, | |
| uintptr(unsafe.Pointer(&oldSigset)), | |
| 0, | |
| uintptr(unsafe.Sizeof(oldSigset)), | |
| 0, 0, | |
| ) | |
| // Do critical work here. Note that doing any of the following operations | |
| // could potentially cause preemption: | |
| // | |
| // - Memory allocation | |
| // - Any operation that sleeps or parks the goroutine | |
| // - Calling any function that is not //go:nosplit | |
| println("critical work") | |
| } | |
| func main() { | |
| go backgroundGoroutine() | |
| select {} | |
| } |
Author
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
This is taken as a sample from issue:
golang/go#65874