Критический раздел, содержащий другой критический раздел?
Допустимо ли размещать критический раздел, как показано ниже:
void somefunction()
{
EnterCriticalSection(&g_List);
...
EnterCriticalSection(&g_Variable);
...
LeaveCriticalSection(&g_Variable);
...
LeaveCriticalSection(&g_List);
}
1 ответ
Решение
Да, это приемлемо Для любой слегка сложной программы является нормой иметь многоуровневое вложение мест.
Единственное, о чем вам нужно знать, это то, что вы всегда должны брать замки в одном и том же порядке.
Если вы этого не сделаете, вы рискуете тупиков в таких сценариях, как
Поток A запускает такой код:
EnterCriticalSection(&g_List);
EnterCriticalSection(&g_Variable);
...
LeaveCriticalSection(&g_Variable);
LeaveCriticalSection(&g_List);
но поток B работает
EnterCriticalSection(&g_Variable);
EnterCriticalSection(&g_List);
...
LeaveCriticalSection(&g_List);
LeaveCriticalSection(&g_Variable);
Это может привести к тупику, когда поток А блокирует g_List
затем блокирует ожидание g_Variable
в то время как поток B заблокирован g_Variable
и заблокирован в ожидании g_List