Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to artificially increase CPU usage

Tags:

go

cpu

I need a Go code snippet to increase CPU usage, this is to test auto-scaling in a K8s cluster running a pod with my service written in Go. I tried with a loop calculating Sqrt as show below and print the result but it hardly utilizes the CPU.

num += math.Sqrt(num)
fmt.Println(num)

It would be better if it's not an infinite loop since I need to also stop the load and test scaling in.

like image 583
Shariq Avatar asked Nov 28 '22 06:11

Shariq


1 Answers

You don't really need any "CPU-intensive" calculations; you just have to avoid blocking operations (such as waiting for data on a network connection or writing to a file) and you need at least as many goroutines doing this as CPU cores you have available (this can be queried using runtime.NumCPU()).

Note that you don't even have to manually set the max number of CPUs that can execute simultaneously (runtime.GOMAXPROCS()), as this defaults to the number of available cores since Go 1.5.

Using fmt.Println() is a bad idea as it may be directed to a file, a network connection etc., and as such, printing to it may block (I/O wait).

Use an "endless" loop which does nothing except check if it's time to abort. You can do this with a single channel, closing it when you want to abort, as receiving on a closed channel can proceed immediately, yielding the zero value of the element type of the channel, and goroutines may check it using the select statement while also having a default branch, else the select statement would just block forever.

Simplest solution:

done := make(chan int)

for i := 0; i < runtime.NumCPU(); i++ {
    go func() {
        for {
            select {
            case <-done:
                return
            default:
            }
        }
    }()
}

time.Sleep(time.Second * 10)
close(done)
like image 199
icza Avatar answered Dec 15 '22 11:12

icza