Are goroutines garbage collected together with their channels?

Issue

Imagine the following code:

func waitForOneOfTwoProcesses() {

    c := make(chan bool)
    go func() {
        time.Sleep(1 * time.Second)
        c<-true
    }()
    go func() {
        time.Sleep(2 * time.Second)
        c<-true
    }()
    <-c

}

Does this leak a channel and a goroutine or does Go recognize that c is gone and the goroutine can exit?

Would the answer be any different if the channel had a buffer size of 2?

Solution

If the channel is unbuffered, then one of the anonymous functions will not return. The program leaks a goroutine and channel.

If the channel has a buffer size greater than or equal to one, then both of the anonymous functions will return. The resources used by the goroutines and channel will be reclaimed.

A buffer size of one is sufficient to prevent the leak. The function waitForOneOfTwoProcesses receives one of the values sent to c. The second value sent to c is buffered in the channel (which is collected by the GC).

Another way to ensure that the goroutines return is to use non-blocking send. Replace the c <- true lines with:

 select {
 case c <- true:
 default:
 }

Answered By – Bayta Darell

Answer Checked By – Dawn Plyler (GoLangFix Volunteer)

Leave a Reply

Your email address will not be published.