In what cases can a deadlock occur?
sobes.tech AI
Answer from AI
In Golang, deadlocks most often occur when working with mutexes and channels.
Possible cases:
-
Cyclic dependency of mutexes: Two or more goroutines try to acquire locks on mutexes in different orders, creating a deadlock.
// goroutine 1 mu1.Lock() mu2.Lock() // waits for mu2, which is held by goroutine 2// goroutine 2 mu2.Lock() mu1.Lock() // waits for mu1, which is held by goroutine 1 -
Blocking send on a non-buffered channel that no one reads: A goroutine sends data to a channel, but no other goroutine is ready to receive it.
ch := make(chan int) ch <- 1 // blocks forever if there is no receiver -
Blocking read from a channel that no one writes to: A goroutine tries to read data from a channel, but no one sends data to it.
ch := make(chan int) <-ch // blocks forever if there is no sender -
Using the same mutex in a recursive function without
RWMutex:var mu sync.Mutex func recursiveFunc() { mu.Lock() // attempt to lock the same mutex again // ... // mu.Unlock() // will never be reached } -
Sending to or reading from a closed channel without checking: Sending to a closed channel causes a panic, reading from a closed channel returns the zero value and
false, but if the second return value is not checked, it can lead to incorrect handling and potential deadlock elsewhere. -
Incorrect use of
sync.WaitGroup: For example, callingDone()before the necessary number ofAdd()calls, or callingWait()before all goroutines have finished.
Table with examples:
| Situation | Mechanism | Example |
|---|---|---|
| Cyclic dependency of mutexes | sync.Mutex |
Goroutine A waits for B, Goroutine B waits for A |
| Blocking send on a channel | Unbuffered channel | ch <- data without a receiver |
| Blocking read from a channel | Channel | <-ch without a sender |
| Recursive use of mutex | sync.Mutex |
Re-locking the same mutex in the same goroutine |
| Working with a closed channel without check | Channel | Sending to a closed channel |
Incorrect use of WaitGroup |
sync.WaitGroup |
Errors in Add/Done/Wait logic |