Почему CreateProcess не должен вызываться из функции DllMain?
Я прочитал в нескольких источниках, что CreateProcess
не должен вызываться из DllMain
функция.
Не вызывайте CreateProcess из функции DllMain. Это приводит к тому, что приложение перестает отвечать на запросы.
Рекомендации библиотеки Dynamic-Link:
Вы никогда не должны выполнять следующие задачи из DllMain: Вызов CreateProcess. Создание процесса может загрузить другую DLL.
Вопрос
Это почему? в нем говорится, что приложение перестает отвечать на запросы, но это только симптом. в чем реальная причина?
Причина, по которой я спрашиваю, состоит в том, что я пытался создать процесс из DllMain
функция, и он видит, чтобы работать просто отлично.
2 ответа
DllMain
выполняется, пока удерживается блокировка загрузчика. Как объясняется в документации, на которую вы ссылались, CreateProcess
может привести к загрузке DLL. И это может привести к полной блокировке блокировки загрузчика. Сбой блокировки происходит потому, что блокировка загрузчика уже удерживается.
Документация понятна. Не звони CreateProcess
от DllMain
, Стандартный способ добиться цели от DllMain
это создать поток, чтобы сделать работу. Хотя вы не должны ждать в этом потоке, потому что это приводит к точно такой же мертвой блокировке.
MSDN говорит:
Поэтому функция точки входа может вызывать функции в Kernel32.dll, которые не загружают другие библиотеки DLL. [...] К сожалению, в Kernel32.dll нет полного списка безопасных функций.
Затем он расширяет оператор, объясняя, что более сложные API (включая CreateProcess) могут включать в себя вызов API-интерфейсов:
Вызов функций, которым требуются библиотеки DLL, отличные от Kernel32.dll, может привести к проблемам, которые трудно диагностировать. Например, вызов функций User, Shell и COM может привести к ошибкам нарушения доступа, поскольку некоторые функции загружают другие компоненты системы. И наоборот, вызов таких функций во время завершения может привести к ошибкам нарушения доступа, поскольку соответствующий компонент уже может быть выгружен или не инициализирован.
Это то, что стоит за лучшими практиками, советуем не вызывать CreateProcess. Вы не можете контролировать, будет ли CreateProcess загружать или не загружать другие библиотеки DLL. В вашем распоряжении избегать небезопасных вызовов API и создавать процесс позже.