Порой случается и такое, что обращаешь внимание на сущую мелочь, безделицу, к изначальному объекту твоего внимания никакого отношения не имеющую. Однако со временем, этот безобидный, на первый взгляд, предмет твоего невольного интереса может запросто превратиться в источник различного рода проблем. Так бывает в жизни и точно таков мир операционных систем, где постоянно изменяющийся код системных компонентов может в какой-то момент кардинально преобразовать ситуацию. Иногда, так сказать по долгу "службы", приходится анализировать системные журналы Windows, представляющие собой один из многочисленных источников информации о состоянии системы. Именно в нем иной раз можно найти записи об уже существующих и даже потенциальных, так сказать предстоящих неисправностях. Так вот, в одной далекой-далекой компании, имя которой не разглашается дабы не скомпрометировать доброе имя :) и не навредить коммерческим интересам, ну а более в целях создания статейной интриги :) специалистами было отмечено, что (иногда) при анализе системных журналов встречались любопытные события. Возникавшие с завидной регулярностью, события эти сводились к ошибкам функционирования одного и того же драйвера aspi32.sys, имели коды 7026, 1060, 7000 и содержали следующее описание:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
Имя журнала: System Имя журнала: System Источник: Service Control Manager Дата: 27.07.2017 8:47:37 Код события: 7026 Категория задачи:Отсутствует Уровень: Ошибка Ключевые слова:Классический Пользователь: Н/Д Компьютер: Описание: Сбой при загрузке драйвера(ов) перезагрузки или запуска системы: ASPI32 . . . |
либо такие вот пары событий, следующих друг за другом:
1 2 3 4 5 6 7 8 9 10 11 12 |
Имя журнала: System Источник: Application Popup Дата: 27.07.2017 11:45:57 Код события: 1060 Категория задачи:Отсутствует Уровень: Ошибка Ключевые слова:Классический Пользователь: Н/Д Компьютер: Описание: Загрузка \SystemRoot\SysWOW64\Drivers\ASPI32.Sys заблокирована из-за несовместимости с данной системой. Обратитесь к поставщику программного обеспечения за совместимой версией драйвера. . . . |
1 2 3 4 5 6 7 8 9 10 11 12 13 |
Имя журнала: System Источник: Service Control Manager Дата: 27.07.2017 11:45:57 Код события: 7000 Категория задачи:Отсутствует Уровень: Ошибка Ключевые слова:Классический Пользователь: Н/Д Компьютер: Описание: Сбой при запуске службы "ASPI32" из-за ошибки Загрузка драйвера была заблокирована . . . |
Тем не менее ошибки эти никак внешне себя не проявляли, ну или об этих проявлениях ничего не было известно, поэтому никто этому особого значения и не предавал. Никаких жалоб и замечаний от сотрудников на данных рабочих местах никогда не поступало. Однако, всё течет, всё меняется, и в один прекрасный момент поступило обращение на тему появившейся ни с того, ни с сего, на ровном месте, продолжительной загрузки операционной системы на одной из клиентских рабочих станций. При анализе деталей происшествия было определено, что визуально задержка происходит после появления экрана заставки с логотипом Windows (значок, флажок).
И на этом этапе, по ориентировочным подсчетам пользователя, система "стоит" порядка полутора минут, что явно выбивается за временные рамки и намекает на внештатную ситуацию. Характер сбоя не критичен, именно поэтому, быть может, большинство пользователей с подобными проблемами воспринимает задержку как нечто само собой разумеющееся, не обращая на неё внимания, ведь система, в итоге, загружается без видимых ошибок. На последующих этапах загрузка проходит в штатном режиме, вслед за логотипом появляется окно авторизации. После инициализации рабочего стола система работает в штатном режиме.
Изучение
Поскольку углубиться в проблему можно лишь при использовании специализированных средств, на ум сразу же приходит вариант исследования инцидента при помощи технологию Event Tracking for Windows с применением утилит xbootmgr и xperf из комплекта Windows Performance Tools. После сбора событий (процесс подробно описан в статье по приведенной выше ссылке) и последующего анализа получившихся логов, были локализованы некоторые любопытные моменты. Во-первых, при изучении результирующего графика Boot Phases
, открылась следующая картина:
..из которой видно, что фаза Pre Session Init (она же PreSMSS: Kernel Initialization) занимает времени более обычного. Необходимо понимать, что происходит с системой на протяжении всей фазы: одним из основных событий тут является загрузка драйверов с флагом BOOT_START и SYSTEM_START. Соответственно, что бы понять, что именно тормозит на этапе PreSMSS, обратимся к графику Generic Events
. Из анализа сводной таблицы (Summary Table) графика, а именно дерева: провайдер: Microsoft-Windows-Kernel-PnP, задача: DriverLoad, я обнаружил вот что:
Очевидно, что драйвер с именем aspi32.sys по какой-то пока что необъяснимой причине пытается инициализироваться в течении 73 (!) секунд. Апофеозом процесса инициализации драйвера является выход с десятичным кодом возврата 3221226347 (шестнадцатеричный эквивалент C000036B), что намекает на NTSTATUS с символическим описанием STATUS_DRIVER_BLOCKED_CRITICAL, фактически указывающим на ошибку инициализации драйвера. Вне зависимости от того, влияет ли это каким-то образом на загрузку остальных драйверов или нет, это ситуация из ряда вон выходящая!!
Что такое ASPI?
Обнаруженный нами драйвер (естественно) сконфигурирован на загрузку в ветке реестра HKLM\SYSTEM\CurrentControlSet\services и помечен флагом SYSTEM_START (параметр Start
= 1). Соответствующий файл драйвера с именем aspi32.sys располагается в директории %Windir%\SysWOW64\Drivers\ и судя по ключевому слову ASPI, содержащемуся в названии, явным образом относится к интерфейсу ASPI.
В определении важно отметить, что не смотря на явное упоминание SCSI в аббревиатуре, на деле интерфейс ASPI может использоваться не только для взаимодействия с устройствами на шине SCSI, но так же и с IDE/ATAPI-устройствами, поскольку ATAPI практически полностью идентичен SCSI на уровне команд, не зря его называют "SCSI поверх IDE" или "SCSI по ATA-кабелю".
Немного истории. В начале 90х ASPI был разработан компанией Adaptec для обеспечения взаимодействия большого количества не придерживающихся стандарта SCSI-адаптеров, поскольку несмотря на использование единой системы команд, выполнение этих команд адаптеры могли обеспечивать по-разному, в зависимости от собственной специфики. Таким образом ASPI был призван преодолеть разного рода несовместимость всего спектра SCSI-устройств, от устаревших до современных, транслируя данные таким образом, чтобы приложения могли общаться со всеми типами SCSI-устройств и контроллеров. В это время на рынке, помимо SCSI присутствовал и другой стандарт для взаимодействия с дисковыми накопителями называемый ATA(IDE), расширенный чуть позже в ATAPI. В определенный момент в интерфейс ASPI была включена поддержка ATAPI, после чего он стал единой универсальной точкой взаимодействия со SCSI/ATAPI-устройствами, которая существенно облегчала разработчикам драйверов/программ написание "универсального" кода работы с большинством типов существовавших в то время на рынке устройств. Поскольку ASPI начал развиваться задолго до появления Windows, к моменту популяризации операционной системы от Microsoft, он предоставлял собой уже довольно развитой и удобный (с точки зрения программирования) интерфейс. По этой, а так же по ряду других причин интерфейс ASPI на долгое время стал своеобразным стандартом де-факто для работы с внешними накопителями (CD/DVD/Blu-ray), предпочтительным по отношению к встроенным механизмам операционных систем от Microsoft. С поддержкой ASPI было написано большое количество приложений, и именно поэтому слой ASPI так долго просуществовал в виде сторонних реализаций (библиотек/драйверов) во многих операционных системах.
Поддержка ASPI в операционных системах
Но давайте посмотрим как реализована поддержка интерфейса в операционных системах Windows. Во времена Windows 95 никакой похожей на ASPI технологии у разработчиков из Microsoft не было, поэтому предлагаемый Adaptec слой ASPI был лицензирован и интегрирован в систему, в подобном варианте просуществовав вплоть до Windows Millenium. Однако линейка Windows NT/2000/XP, по замыслу разработчиков, изначально была лишена поддержки классического ASPI, вместо него в Microsoft был разработан и внедрен собственный, не совместимый со стандартными вызовами ASPI-функций, минимальный интерфейс ASPI (иначе называемый SCSI Pass Through interface, SPTI). Связано это с тем, что в общем смысле Microsoft всегда преследовал цель избавиться в своих операционных системах от нативной (встроенной) поддержки сторонних технологий, разработанных вне Microsoft, а в частном контексте MS не устраивал уровень безопасности ASPI. Закономерным итогом этой тенденции явилось планомерное вытеснение ASPI более жизнеспособными технологиями, которые опирались на интерфейсы, имеющие встроенную поддержку операционной системы. Фактически после Windows 95/98 Microsoft перевел ASPI в статус внешнего интерфейса, поэтому для инсталляции внешней реализации интерфейса ASPI в операционных системах Windows предписывалось использовать сторонние программные комплекты.
Следовательно, если приложению требовалась поддержка интерфейса ASPI, оно должно самостоятельно позаботиться о ней, установив в систему библиотеки/драйвера посредством инсталляции следующих комплектов:
- Комплект (freeware) Adaptec ASPI;
- Многочисленные "сторонние" пакеты, такие как: ForceASPI, FrogASPI, ASAPI или MekugiASPI;
Подобные вышеописанным комплекты поддержки ASPI устанавливали в систему (как минимум) два файла:
- Библиотека wnaspi32.dll -- судя по всему, обеспечивает сопряжение с интерфейсом Win32;
- Драйвер виртуального устройства aspi32.sys -- служит для взаимодействия непосредственно с драйверами устройств;
Но, вернемся к теме нашей статьи. Описываемый мною инцидент был зафиксирован под версией Windows 7 Профессиональная x64, и в этой операционной системе мы не обнаруживаем никакой "встроенной" поддержки ASPI. Из этого следует, что драйвер по отношению к Windows 7 считается мало того что "сторонним", но еще и несовместимым, о чем красноречиво говорит нам ошибка Загрузка ASPI32.Sys заблокирована из-за несовместимости с данной системой, и что подтверждается не совсем правильным местоположением проблемного драйвера в 64-битной системе по пути %Windir%\SysWOW64\Drivers\ (должно быть %Windir%\System32\Drivers\). Почему драйвер не совместим? Да потому что он 32-разрядный, а система 64-разрядная. Microsoft в этом случае, подняв вверх указательный палец, многозначительно изрекает:
Для того, что бы хоть как-то защитить своё хрупкое божественное творение от полчищ диких пользователей, Microsoft разработал и внедрил в 64-битные системы механизм под названием WOW64. На самом деле этот механизм разработан с целью обеспечения работоспособности 32-битного программного обеспечения в 64-битных операционных системах Windows.
Вот именно поэтому, например, любые попытки инсталляции драйвера любой разрядности 32-разрядным пакетом под 64-разрядной операционной системой, перехватываются и перенаправляются. Возникает резонный вопрос, какой смысл перенаправлять сторонний 32-битный драйвер, если он в любом случае будет заблокирован как несмовместимый и даже больше, может вызвать проблемы на этапе загрузки операционной системы? Это ошибочная логика, и далее мы выясним почему.
Кто инсталлирует драйвер aspi32.sys?
Остановимся на том, что драйвер aspi32.sys является 32-битным и не совместим с 64-разрядной системой. Тогда каким образом он сюда попал, или, другими словами, кто этот драйвер установил в систему? Судя по всему, это произошло в процессе установки устаревшего 32-битного программного пакета, По классу это могло быть ПО, предназначающееся для низкоуровневой работы с некими SCSI/ATAPI-приводами (CD/DVD/BluRay/MO), внешними устройствами (сканнеры, цифровые камеры), например программы для снятия образов/записи CD/DVD. Одним словом, в эру развития оптических носителей существовало такое огромное количество различного программного обеспечения для работы с ними, что перечислять их всех не хватит никакой статьи :) С другой стороны, ASPI могло использовать любое ПО, реализующее некий тип защиты от копирования, основанный на взаимодействии с ключевой информацией, каким-либо нестандартным образом размещаемой на оптических (магнитных) носителях, например при помощи тех же суб-каналов (Q/P-каналы).
Но всё же, кто инициатор установки этого драйвера? В директории %Windir%\SysWOW64\Drivers\ мне удалось обнаружить еще один интересный объект - драйвер hwtools.sys, дата и время инсталляции которого в точности совпадали с аналогичными параметрами файла aspi32.sys. В свойствах драйвера можно найти наименование HWTools Driver, авторские права принадлежат ООО "СТМ" 2000-2008. На некоторых других подобных станциях в пределах корпоративной среды, мне так же удалось обнаружить подобные "пары" драйверов по тому же местоположению, и во всех случаях дата и время у них совпадали между собой, либо отличались на очень незначительную величину (одна-две секунды), что само по себе уже наводит на мысль об связанной инсталляции в систему единым источником. На основе продвинутого поиска по файловой системе было выяснено, что в указанное время из комплекта программ СТМ на пользовательские станции инсталлировались такие пакеты как Rail-Тариф, Rail-Атлас, Rail-Инфо и некоторые другие, сама установка была датирована 2011 годом. Из всего этого возникло предположение, что интересующий нас драйвер aspi32.sys тоже был установлен программами СТМ.
Далее, проверка свежесозданных директорий установленных программ СТМ на предмет наличия описанных файлов показала, что указанные драйвера в них отсутствуют. Но откуда же они тогда берутся? Появилось предположение, для подтверждения которого я использовал утилиту Process Monitor и на чистой ОС провел инсталляцию программ СТМ. Непосредственно после инсталляции драйвера действительно отсутствуют, а вот при выполнении процедуры активации программ мы видим, что драйвер hwtools.sys появляется в нужном месте, при этом добиться создания aspi32.sys мне так и не удалось. Из отчета Procmon мы можем наблюдать, что создание и запись данных файла hwtools.sys (а так же файла hwtools.cat) инициируется основным процессом запускаемой программы СТМ (например, для Rail-Тариф это tariff.exe
), впрочем код инсталляции драйвера, как и сами драйвера, могут содержаться не непосредственно в исполняемом модуле, а в подгружаемых в адресное пространство модуля библиотеках DLL. Изучение адресного пространства процесса tariff.exe
в момент записи драйвера обнаружило нам целую серию внутренних библиотек программного пакета, среди которых наибольший интерес представляют две из них с именами comtls32.dll и comtls64.dll.
Реализация защиты
Поскольку изучение и публикация структуры защитного механизма лежат вне правового поля, во избежание различного рода инцидентов, мы ограничимся лишь поверхностными набросками относительно внутреннего устройства библиотек. Основной интерес представляет собой библиотека comtls32.dll, поскольку именно она содержит защитные алгоритмы и участвует в процессе регистрации программ. В самой библиотеке, часть секций которой зашифрованы и расшифровывается стартовым кодом процедуры DllEntryPoint
, содержатся запакованные в секции файлы wnaspi32.dll, aspi32.sys, hwtools.sys. Там же содержатся код регистрации (проверки активации) программ и код взаимодействия со слоем ASPI и функциями драйвера hwtools.sys. Драйвер hwtools.sys создает системное устройство \\Device\\HwTools, обращение к устройству происходит из уже знакомой нам библиотеки comtls32.dll.
Выводы
Какие из всего этого можно сделать умозаключения? Поскольку мне так и не удалось создать условия, при которых в систему был бы инсталлирован драйвер aspi32.sys, могу сделать предположение, что в далеком 2011 году для установки по ошибке был использован 32-разрядный инсталляционный пакет СТМ, содержащий иной (в отличии от современных версий) механизм защиты, кроме всего прочего, опирающийся на низкоуровневый доступ к периферийным IDE/ATAPI-устройствам (CD/DVD) через внешний ASPI интерфейс. Это могла быть защита на основе специальным образом сформированных CD/DVD-дисков. В последних же версиях программ СТМ, драйвер aspi32.sys в систему не инсталлируется.
Имеется так же предположение, что алгоритм проверки несовместимого драйвера в ядре содержит ошибки, в следствии чего, в исключительных случаях, возникают такие вот немыслимые задержки на этапе инициализации уже загруженного драйвера. Но это лишь предположение, подтвердить или опровергнуть которое еще только предстоит..
Решение
Исходя из всего вышенаписанного, у нас есть два возможных решения проблемы:
- Найти в системе программное обеспечение, установившее драйвер aspi32.sys и попытаться переустановить/удалить его, в расчете на то, что вместе с ПО обновится/удалится и драйвер;
- Отключить загрузку проблемного драйвера вручную;
Для "ручного" отключения драйвера используем следующую стратегию:
- Запускаем редактор реестра regedit.exe;
- В реестре находим ключ HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\ASPI32;
- Меняем значение параметра
Start
на 4 (отключен);
Тем, кого драйвер aspi32.sys выбесил уже серьезно, можно порекомендовать удалить ключ ASPI32 полностью :)
А что такое MO-привод ? Никогда не видел...
Давно это было, я помню даже себе такой купил как-то, типа для бэкапа и надежности :) потом осознал всю ущербность идеи и продал. дискеты дорогие были, сложно было достать и совместимость почти нулевая.
подобное устройство было: http://www.pc-1.ru/i_shop/cd/dvd/A047810$31
только меньшей емкости, кажется на 256 или 512 Мб.. не вспомню уже.
Да,как давно это было. (ASPI)
Спасибо!