Lock Hierarchy Violation
Occurs when two or more locks are acquired in a different order in two task executions, potentially leading to a deadlock when the program's tasks execute in parallel.
A
Lock hierarchy violation
problem indicates the following timeline:
Task 1
|
|
Task 2
|
|
If these time lines are interleaved when the two tasks execute in parallel, a
Deadlock
occurs:
- Task 1: Acquire lock A.
- Task 2: Acquire lock B.
- Task 1: Try to acquire lock B; wait until task 2 releases it.
- Task 2: Try to acquire lock A; wait until task 1 releases it.
The Dependencies tool reports a
Lock hierarchy violation
as multiple problems in a problem set. Each problem shows a portion of the
Lock hierarchy violation
from the perspective of a single thread.
Lock hierarchy violation
problems are the most common cause of
Deadlock
problems, and a report of a
Lock hierarchy violation
problem indicates a
Deadlock
problem might occur when the target executes in parallel.
Syntax

ID
| Code Location
| Description
|
---|---|---|
1
| Allocation site
| If present, represents the location and its associated call stack where the synchronization object acquired by a thread (usually the object acquired first) was created.
|
2
| Parallel site
| If present, represents the location and associated call stack of the parallel site containing the Lock Hierarchy Violation problem.
|
3
| Lock owned
| Represents the location and associated call stack where a task acquired a lock.
|
4
| Lock owned
| Represents the location and associated call stack where a task acquired a second lock while the task still held the first lock.
|
Example
// in task 1
|
|
// in task 2
|
|
Possible Correction Strategies
Determine if interleaving is possible, or whether some other synchronization exists that might prevent interleaving. If interleaving is possible, consider the following options.
Use a single lock instead of multiple locks:
// in task 1
|
|
// in task 2
|
|
Try to define a consistent order for your locks, so that any task that acquires the same set of locks, will acquire them in the same order:
// in task 1
|
|
// in task 2
|
|
When a task acquires multiple locks, make sure that it always releases them in the opposite order that it acquired them.