Пикник на обочине или не ходите, дети, в DllMain гулять, а то ноги оторвёт
Jan 30, 2008 · CommentsПрограммированиеЮморWin32
Точка входа в DLL, так же как и точка входа в программу, - это очень специальное место. Зона. В Зоне действуют свои правила касательно того, что можно делать, а что делать нельзя. В Зоне можно инициализировать локальные данные DLL, можно создавать критические секции. В Зоне нельзя динамически загружать другие Модули или создавать потоки. Любой Сталкер знает и следует правилам Зоны. Все остальные рано или поздно нарушают правила и расплачиваются за это.
Что делает Зону особенной? Иные утверждают, что во всем виноват Загрузчик. Загрузчик единственный, кто понимает язык зависимостей между модулями. Он говорит с модулями, загружает их и вызывает из точки входа. Но Загрузчик слаб. Он не в силах совладать с Модулями, нарушающими правила Зоны.
Модули коварны и злы. Они стремятся окружить себя другими Модулями, от которых они зависят. Они любят создавать циклические зависимости между собой. Они загружают другие DLL в ответ на DLL_PROCESS_ATTACH и вызывают функции из непроинициализированных Модулей. Модули пытаются замаскировать и приумножить свое коварство. Они прикрываются статусом “Delay-Loaded DLL” и расставляют ловушки в конструкторах и деструкторах статических объектов.
Это люди сделали их такими. Люди нарушили правила Зоны. И теперь они расплачиваются за это каждый раз, когда идут в Зону.
На прошлой неделе произошел очередной несчастный случай. Access Violation прошил насквозь lodctr.exe:
А всё из-за того, что loadperf решил, что ему всё можно и попытался зарегистрировать источник событий для Event Log прямо из DllMain. Этот фокус ему удавался до поры до времени, пока advapi32 не стала “Delay-Loaded” . Как только это произошло, вызов RegisterEventSourceW стал приводить к её загрузке, что поломало граф зависимостей Загрузчика и вылилось в попытку использования неинициализированной критической секции в rpcrt4 до того, как была вызвана точка входа rpcrt4!DllMain.
Кто будет следующей жертвой?
P.S. Сслылка по теме: http://msdn2.microsoft.com/en-us/library/ms682583.aspx