简体   繁体   中英

Goroutine works even I set runtime.GOMAXPROCS(1). Why?

This simple example prints "done", "finished". How it's possible in case then we have only one physical thread limited by runtime.GOMAXPROCS(1)? Go 1.19

package main

import (
    "fmt"
    "runtime"
)

func main() {
    runtime.GOMAXPROCS(1)

    done := false

    go func() {
        done = true
        fmt.Println("done")
    }()

    for !done {
    }
    fmt.Println("finished")
}

GOMAXPROCS(1) does not limit the program to a single thread. What does it do?

The GOMAXPROCS variable limits the number of operating system threads that can execute user-level Go code simultaneously . There is no limit to the number of threads that can be blocked in system calls on behalf of Go code;

Assuming that the scheduler is not considered "user-level Go code" in this context, it would not be constrained by this number (1).

Even if user code is really occupying all the available threads, user code can still often be preempted to allow other code to run. See the comment in preempt.go for more details.


  1. Maybe "user-level" here is meant in the sense of user code vs. kernel code. In that case, the Go runtime scheduler is obviously not kernel code, but it would seem to be redundant to call it "user-level Go code".

It's amazing to see so many negative ratings. At the same time, no one noticed that the reason for the change in the behavior of the go scheduler in 14.1 ( https://go.dev/doc/go1.14 ) "goroutines are now asynchronously preemptible". This code should hang in versions up to 14.1 and work in later versions.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM