Trojan-Dropper.Win32.Agent.rek: «легальный» руткит

    В заметке описывается драйвер, который загружается вирусом, рассмотренным в предыдущей части. Драйвер работает на уровне ядра операционной системы, и обеспечивает «привилегированное» прикрытие основной функциональности трояна, которая работает в режиме пользователя (авторское название компоненты — winnt32.dll. Подробнее о ней см. habrahabr.ru/blog/virus/43787.html).

    Краткое описание.
    Программа представляет собой nt-драйвер (так же известны, как legacy-драйвера, то есть не связанные ни с каким физическим устройством). Является руткитом: используя механизмы ядра ОС, лишает другие программы доступа к некоторым файлам и ключам реестра.
    Детектируется касперским как Trojan-Dropper.Win32.Agent.rek. Размер 27548 байтов.
    Лирическое отсутпление. «Обычный» руткит может использовать недостатки в реализации ОС для сокрытия объектов: файлов, сетевых соединений, и так далее вплоть до секторов жесткого диска. Для этого в простейшем случае делается перехват системного вызова. Системный вызов по сути — это вызов функции, а вызов функции — это передача управления по указанному адресу. Руткит записывает по этому адресу свой код, который трансформирует результат оригинальной функции. К примеру, проверяет, пытается ли кто-то открывать файл с телом вируса, и возвращает какой-нибудь код ошибки, например «доступ заперещен».
    Руткит перехватывает обращения с реестру и файлам, используя легальные методы самой ОС.

    Файловая система
    Используя функцию ядра IoRegisterFsRegistrationChange, драйвер подписыватеся на получение события об активизации/отключении файловой системы. То есть ОС сама уведомляет драйвер, да еще и передает ему структуру DEVICE_OBJECT, описывающую «устройство» файловой системы и ее драйвер. «Устройство файловой системы» — это, грубо говоря, то, посредством чего пользователь видит данные на диске, организованные в виде папок и фалов.
    Справочник говорит следующее: The IoRegisterFsRegistrationChange routine registers a file system filter driver's notification routine to be called whenever a file system registers or unregisters itself as an active file system.


    В структуре DEVICE_OBJECT, описывающей устройство, драйвер заменяет обработчик запроса IRP_MJ_CREATE на свой. Запрос IRP_MJ_CREATE генерируется изнутри NtCreateFile при открытии файла. Новый обработчик сравнивает запрошенное имя с именем файла собственно драйвера (которое задается дроппером в форме Wwwdd.sys, например Jer24.sys), и, в случае совпадения, возвращает код ошибки STATUS_ACCESS_DENIED.

    Ключи реестра
    Обращение к ключам реестра реализованно не менее легально: используя функцию CmRegisterCallback, драйвер подписывается на уведомление о всех обращениях к реестру. Стоит ли говорить о том, как начинает тормозить компьютер?

    A driver calls CmRegisterCallback to register a RegistryCallback routine, which is called every time a thread performs an operation on the registry.


    При обращении к ключам реестра:
    HKLM\System\CurrentControlSet\Sevices\DRIVER-NAME
    HKLM\System\ControlSet001\Sevices\DRIVER-NAME
    HKLM\System\ControlSet002\Sevices\DRIVER-NAME
    HKLM\System\CurrentControlSet\Control\SafeBoot\Minimal\DRIVER-NAME
    HKLM\System\CurrentControlSet\Control\SafeBoot\Network\DRIVER-NAME
    HKLM\System\ControlSet001\Control\SafeBoot\Minimal\DRIVER-NAME
    HKLM\System\ControlSet001\Control\SafeBoot\Minimal\DRIVER-NAME
    HKLM\System\ControlSet002\Control\SafeBoot\Network\DRIVER-NAME
    HKLM\System\ControlSet002\Control\SafeBoot\Network\DRIVER-NAME

    драйвер возвращает код ошибки STATUS_ACCESS_DENIED.

    Слайды.

    Запрет на удаление файла:
    Запрет на удаление файла

    Запрет на удаление ключа реестра:
    Запрет на удаление ключа реестра

    Вот система передает руткиту информацию о CDFS:
    kd> kb
    ChildEBP RetAddr  Args to Child              
    f9dfbc10 80568d01 818158b8 00000001 818cff38 Qvk71+0x1970
    f9dfbc2c f9d3d10b 818cff38 f9d3d970 f9dfbc7c nt!IoRegisterFsRegistrationChange+0xab
    f9dfbc3c f9d3cdb0 818cff38 00000000 00000000 Qvk71+0x110b
    f9dfbc7c 805757dc 818cff38 815dd000 00000000 Qvk71+0xdb0
    f9dfbd4c 805758eb 000005b8 00000001 00000000 nt!IopLoadDriver+0x66c
    f9dfbd74 80533fe6 000005b8 00000000 819ca3c8 nt!IopLoadUnloadDriver+0x45
    f9dfbdac 805c4cce f7e48cf4 00000000 00000000 nt!ExpWorkerThread+0x100
    f9dfbddc 805411c2 80533ee6 00000001 00000000 nt!PspSystemThreadStartup+0x34
    00000000 00000000 00000000 00000000 00000000 nt!KiThreadStartup+0x16
    
    kd> dt -r1 _DEVICE_OBJECT poi(esp+4)
    nt!_DEVICE_OBJECT
       +0x000 Type             : 3
       +0x002 Size             : 0xb8
       +0x004 ReferenceCount   : 1
       +0x008 DriverObject     : 0x817eba20 _DRIVER_OBJECT
          +0x000 Type             : 4
          +0x002 Size             : 168
          +0x004 DeviceObject     : 0x8172e020 _DEVICE_OBJECT
          +0x008 Flags            : 0x92
          +0x00c DriverStart      : 0xf9c0c000 
          +0x010 DriverSize       : 0xf900
          +0x014 DriverSection    : 0x818c9960 
          +0x018 DriverExtension  : 0x817ebac8 _DRIVER_EXTENSION
          +0x01c DriverName       : _UNICODE_STRING "\FileSystem\Cdfs"
          +0x024 HardwareDatabase : 0x8066ecd8 _UNICODE_STRING "\REGISTRY\MACHINE\HARDWARE\DESCRIPTION\SYSTEM"
          +0x028 FastIoDispatch   : 0xf9c0e400 _FAST_IO_DISPATCH
          +0x02c DriverInit       : 0xf9c19a85        long  Cdfs!GsDriverEntry+0
          +0x030 DriverStartIo    : (null) 
          +0x034 DriverUnload     : 0xf9c0fca5        void  Cdfs!CdUnload+0
          +0x038 MajorFunction    : [28] 0xf9c0c400        long  Cdfs!CdFsdDispatch+0
       +0x00c NextDevice       : (null) 
       +0x010 AttachedDevice   : (null) 
       +0x014 CurrentIrp       : (null) 
       +0x018 Timer            : (null) 
       +0x01c Flags            : 0x10840
       +0x020 Characteristics  : 0
       +0x024 Vpb              : (null) 
       +0x028 DeviceExtension  : (null) 
       +0x02c DeviceType       : 3
       +0x030 StackSize        : 1 ''
       +0x034 Queue            : __unnamed
       +0x05c AlignmentRequirement : 0
       +0x060 DeviceQueue      : _KDEVICE_QUEUE
       +0x074 Dpc              : _KDPC
       +0x094 ActiveThreadCount : 0
       +0x098 SecurityDescriptor : 0xe139df00 
       +0x09c DeviceLock       : _KEVENT
       +0x0ac SectorSize       : 0x800
       +0x0ae Spare1           : 0
       +0x0b0 DeviceObjectExtension : 0x81815970 _DEVOBJ_EXTENSION
       +0x0b4 Reserved         : (null) 


    Вывод.
    В невидимой борьбе вирусов с антивирусами, когда все на свете перехватыватся и переперехватывается, используемый данным руткитом метод легален, а поэтому наиболее опасен. Со своей большой колокольни могу предположить, что снять такой хук на практике нереально. Либо перехватывать собственно процедуры регистрации таких уведомлений (типа CmRegisterCallback), запретив вызывать ее кому не попадя.
    С другой стороны, грань, разделюящая вирусы и антивирусы, становится все тоньше и терерь едва заметна. Они используют одинаковые механизмы для сокрытия данных или отслеживания работы обычных программ. И, кстати, шаги к этому совершаются больше темной стороной.
    Share post
    AdBlock has stolen the banner, but banners are not teeth — they will be back

    More
    Ads

    Comments 62

      +1
      Спасибо, всегда интересно почитать про оригинальные идеи, воплощённые вирусописателями - ведь кому как не им постоянно приходится изобретать всё новые ухищрения. Особенно интересно читать от лица человека, проводящего реверс-инженеринг, препарируя вирус.

      А вообще разве нельзя при перехвате обращений к файловой системе и реестру модифицировать результат работы функции таким образом, чтобы она просто не показывала что такие файлы/ключи есть? Если такое сделать на уровне ядра, то можно действительно стать невидимкой...
        0
        С диском и реестром это точно можно, но нужно перехватить не два вызова, а немного больше.
        С процессами, это, кажется, тоже возможно.

        А можно ли стать на все 100% невидимым, действительно интересный вопрос.
        Хотелось бы услышать на него аргументированный ответ.
        Причем можно ли стать невидимым как для процессов режима пользователя так и для драйверов (установленных после), полностью сохранив функциональность системы?
        Дело в том, что можно перехватить (по крайней мере документированными способами) только часть вызовов ядра.

        Автор же данного руткита ничего особенного не сделал.
        Описанные возможности реализованы в относительно простых примерах к WDK (Windows Driver Kit) - пакета для разработки драйверов под Windows (бесплатного) от MS.
          0
          невидимых руткитов пруд пруди, вон hxdef погуглите.
          Может скрывать всё, что попросите.

          Обнаружить руткит можно только анализом хуков.
            +3
            hxdef это очень старый публичный концепт, он видим всеми нормальными утилитами и при умении простым ядерным отладчиком :)

            Руткит, работая в ОС, так или иначе с ней взаимодействует, а значит его активность может быть засечена. Написать руткит, который был бы не видим можно только сделав его совершенно независмым от ОС, либо, чтобы он работал на уровень ниже ОС. Под последним я понимаю использование возможностей аппаратной виртуализации современных процессоров(Vanderpool Technology от Intel и Pacifica от AMD), и такие концепты руткитов был представлены уже почти два года назад Джоанной Рутковской на конференции Black Hat (http://en.wikipedia.org/wiki/Blue_Pill_(malware)).
            Есть руткиты, которые переразмечают винт, отводя себе несколько метров в конце hdd, записывая своё тело туда и загружаясь задолго до любой ОС, т.о. это практически невидимый концепт, но он очень сложен, хотя и возможен.

            Поэтому написать невидимый руткит теоретически можно, а практически нафиг никому ненужно :)

            И вот эта последняя тенденция реверса совершенно обыденных зверюшек так многих радует, хотя всё, что здесь описано существует уже несколько лет и ничего нового из себя не представляет, это средний уровень.
              0
              ага, первый в вашем описании - bluepill, это пока за гранью реальности. второй - буткит - выявляется и зачищается из юзерского режима на ура.
                0
                На bluepill я дал ссылку. Но вот про реальность я не понял, он ведь существует и даже работает :) После Рутковской нечто подобное писали и другие. Другое дело, что ITW такого ещё небыло, но раз есть proof-of-concept, значит реально. Уже есть не один антируткит на базе этих технологий(www.northsecuritylabs.com as example).

                Насчёт второго я имел ввиду не тот буткит, который недавно задетектили и который повторял POC выложенный в паблик ещё годом ранее. Но смысл один ага. Примечательность этого руткита в том, что автор довёл его до рабочего состояния в массах.

                PS Что за ограничение по постам :)
                  0
                  всмысле ограничение?
                    0
                    интересно, как буткит защищается от дефрагментации диска?
                      0
                      Если он находится не в секторах, которые принадлежат разделу, то легко. Загрузочный сектор дефрагментаторы точно не трогают, а все что не в разделе - тоже их не касается. Так что не вижу проблемм.
                        0
                        Дело в том, что буткиты хранят в загрузочном секторе только необходимый минимум для запуска основного кода. Этот основной код хранится в других секторах - их контент руткит прячет, перехватывая irp_mj для чтения сектора.

                        Вот про эти сектора было и интерсно - если их "дефрагментируют", то руткит (а то и комп целиком) просто перестанет загружаться.
                          0
                          вот черт, два комметария (
                          0
                          Дело в том, что буткиты хранят в загрузочном секторе только необходимый минимум для запуска основного кода. Этот основной код хранится в других секторах - их контент руткит прячет, перехватывая irp_mj для чтения сектора.

                          Вот про эти сектора и интерсно - если их "дефрагментируют", то руткит (а то и комп целиком) просто перестанет загружаться.
                  0
                  ну, вот давайте возьмем этот руткит. Он патчит IRP_MJ_CREATE в драйвере ntfs. Предположим, что он записал в границы модуля ntfs свою функцию, которая и будет обработчиком. SSDT он не патчит.

                  Какой анализ тут можно провести?
                    0
                    Взять код оригинального обработчика с диска и сравнить с тем, что в памяти. Это обходится, если руткит перехватывает IRP_MJ_READ(который направлен на чтение ntfs.sys) и подсовывает свой код, тогда такое сравнение ничего не даст. Либо работать в обход интерфейсов, которые предоставляет ОС, т.е. спуститься ниже ntfs.sys(т.е. фактически требуется разбор структр ФС целиком) и опять же попытаться прочесть необходимую инфу и сравнить её с той, что в памяти.
                    Ещё один самый простой способ - делать тайминги, хотя это неоднозначный метод детекта(функция, которая перехвачена затратит больше времени, ибо ей надо исполнить ещё и перехватчик). Но это больше эмпирический метод.
                    Это то, что сразу пришло в голову, методов детекта на самом деле предостаточно.
                      0
                      да, и это будет именно то, что наблюдается сейчас - постепенный спуск "на самое дно самого глубокого ущелья". для любого "копка" можно копнуть еще глубже
                  0
                  нет абсолютно невидимых руткитов, как нет и абсолютной защиты от них. Новые ухищрения с любой стороны противостояния заставляет противника эволюционировать)

                  ничего не сделал - ну, да. чем проще - тем лучше.
                  0
                  да, такое делается. данный руткит реагирует только на open/delete, на enumerate - заглушка есть, но пустая. наверное будет в следующих версиях )
                    0
                    Стать невидимкой, допустим. Мы можем просканировать свободное метсо на диске, и, найдя отличия, найти спрятанные файлы. В этом же случае - все файлы видны. Пусть их имена немного отличаются, но парадокс в том, что не прячась, программ вызывают меньше подозрений! Ведь вы не будете пытаться удать каждый файл, чтобы узнать не под руткитом ли он. :)
                    0
                    И снова отличный обзор! Спасибо!
                      0
                      "снять такой хук на практике нереально"

                      Как насчет воткнуть винт в другую машину и тупо поудалять файлы?
                        0
                        можно просто грузануться с livecd)
                          0
                          Ну или так, да.
                          0
                          Учитывая сложность драйвера, можно предположить что автор особо не задумывался о серьезном противостоянии.
                          С большой вероятностью Вам удасться загрузится перед ним, заявив, что вы инфраструктурный фильтр драйвер файловой системы или что-нибудь в этом духе. А после уже Вы будете перехватывать его запросы, а не он Ваши.
                            0
                            это круто, конечно )

                            снять хук - имеется ввиду в рантайме. Поудалять, конечно, можно, правда, надо знать, что удалять.
                            +1
                            Вывод:
                            Не запускайте неизвестный софт с привилегиями на установку драйверов, и прочими из набора прав "Администратора".
                            Права "Администратора" действительно дают очень много возможностей по использованию Вашего компьютера, и вирусописатели все активнее начинают ими пользоваться.
                            В обратном случае остается надеятся, что программисты из антивирусных контор разбираются в предмете лучше, чем вирусописатели.
                              0
                              действительно. в одной статье читал: "в windows уже содержатся компоненты, достаточные для того, чтобы не заразиться вирусом и не дать установиться руткиту. Это ваши руки и голова".
                              +1
                              Ну, возврат акцес денайд — это совсем безобидный руткит.
                              Гораздо забавнее, когда драйвер перехватывает функции листинга каталогов или ветвей реестра — «нежелательные» ключи скрываются от посторонних процессов.

                              Обнаружить такой руткит случайно практически невозможно: в процессах чисто, на диске чисто, в реестре чисто. Лишь анализ хуков позволяет выявить таких ребят.

                              Когда я впервые несколько лет назад прочитал статью об устройстве и возможностях руткитов, было немного жутковато. Когда я испытал на себе один из них — ужаснулся ещё более.
                                0
                                Пожалуйста, расскажите поподробнее про анализ хуков.
                                Разве после подмены адресов системных функций можно понять, что их поменяли?
                                  0
                                  Я давно не интересуюсь темой, так что очень боюсь наговорить ерунды.

                                  Если смотреть данный пример…
                                  Само понятие хука — это же не подмена адреса — это подписка на события. Колбек-функция регистрируется в системе, и эта регистрация прекрасно палится.
                                    0
                                    Насколько я знаю, это зависит от того, что перехватывать.
                                    Системные вызовы подменяются в соответствующей таблице.
                                    А подписки вроде IoRegisterFsRegistrationChange можно не использовать.
                                    +1
                                    ах да, вспомнил один из методов ловли даже самых хитровывернутых руткитов:
                                    программа использует собственные реализации часто подменяемых системных функций, сравнивая результаты с тем, что говорит система.

                                    Тут даже патчинг ядра на ходу, как это было в недавней статье, можно спалить.
                                      0
                                      Это в случае, если Вы загрузитесь до руткира.
                                      Иначе с самого начала у вас будет уже ненастоящий адрес (но что он не настоящий Вы не узнаете), и все что можно будет узнать таким методом - добавилось ли еще перехватчиков после Вас, но о предыдущих узнать так не получится.
                                        0
                                        Хм. Ну можно наверное тем же оружием - мегамега псевдодрайвер пусть будет кусочком антивируса. И этот мегадрайвер каким-то образом пусть грузится самым первым. Хотя это не решение проблемы (честно говоря, не знаю, возможно ли такое). Т.к. следующий руткит найдет способ еще раньше загрузиться, и так до бесконечности. Наверное, в ядре должно быть что-то встроено, счетчик чисто для чтения, чтобы все желающие могли эти перехваты попересчитать...
                                          0
                                          А как в винде определяется порядок загрузки подобных драйверов?
                                            0
                                            изменить его можно например утилитой loadord.exe из пакета sysinternals
                                              0
                                              Я имел в виду, как на уровне ядра системы определяется порядок загрузки? Есть какие-то идентификаторы, списки загрузки, правила и т. п.?

                                              Судя по тому, что есть утилиты наподобие вышеупомянутой, какая-то система приоретизации существует, вот мне и интересно узнать про неё побольше.
                                        0
                                        Метод, описанный artyfarty вполне работает, если руткит был запущен раньше. Данный метод основан на том, что создатель руткита не предусмотрел все возможные функции чтения памяти, но предусмотрел самые популярные. Программа запрашивает сначала чтение памяти распостранённым методом, а потом этот же блок памяти редким. Если ответы различаются, то это сигнализирует о рутките. Такую программу написал Руссонович (неуверен, но вроде бы она называется rootkit hunter).
                                      0
                                      Для этого существуют свои методики. В данном случае рассмотренный руткит использует стандартные публичные методы перехвата. Ничего нового, ничего особенного, такое наблюдалось уже в 2006 году и с тех пор продвинутые техники ушли весьма и весьма :)

                                      Среди достойного софта, который в состоянии такие хуки детектировать можно выделить:
                                      RootkitUnhooker
                                      RkTrap
                                      GMER
                                        0
                                        ну, про русток мы молчим. Таким, как я, чтобы его разобрать, надо пару лет)
                                          0
                                          Вот где не ожидал услышать о нём, так это на хабре :)
                                            0
                                            Да его тут периодически поминают. Кто-то даже ссылку на сэмпл выкладывал :-)
                                        0
                                        можно. в простейшем случае поднимается файл ntosrknl.exe (или какой там работает) с диска, и сравнивается с его образом в памяти. Кстати, руткит Rustok при таком методе отдает подложные данные, и например GMER (антируткит) ничего не видит )

                                        Также берется таблица системных вызовов и в них ищутся адреса, выходящие за пределы образа ntoskrnl в памяти. Найти модуль, на который они ссылаются, довольно просто.
                                      0
                                      Отличная статья!!! Тема реверсивного инженеренга интересна!
                                        0
                                        спасибо, на здоровье)
                                        0
                                        Они используют одинаковые механизмы для сокрытия данных или отслеживания работы обычных программ. И, кстати, шаги к этому совершаются больше темной стороной.
                                        Писателями антивирусов?
                                        %-)
                                          0
                                          Ну это как бы "светлые", пусть даже их программы порой далеки от совершенства.
                                          0
                                          А на основании чего вирусам дается название, вот например
                                          Trojan-Dropper.Win32.Agent.rek
                                          что означает Agent и rek?
                                          я недавно поймал у себя Trojan.Win32.Agent.jox, а информации по нему в сети не нашел, поэтому интересно, что означает jox например.
                                            +2
                                            В данном случае вы говорите о терминологии Касперского. У них последние буквы (.rek/.jox) - номер модификации. В DrWeb используются цифры. Agent - это ни о чем: троян есть, но либо функционал не ясен, либо не отнести ни к какому существующему семейству. Сколько раз под Agent скрывались бэкдоры, Downloader'ы и прочие очевидные вещи - не счесть. Это на основании эмпирических данных :-)

                                            Вообще, названия даются исходя и функционала, либо по "почерку" вируса. Например, Trojan.Downloader - загружает файлы, имя дано по функционалу. А Trojan.PWS.LdPinch - и по функционалу (PWS - крадет пароли) и по "почерку" (LdPinch). Как-то так. Но часто бывает, что названия не отражают сути.
                                              0
                                              просто интересно было узнать, что же этот трой делал...
                                              единственный видимый эффект его присутствия был svchosts.exe в папке system и регулярно слетающий фокус с окон.
                                                0
                                                Анализ надо проводить, так ничего не скажешь :-) Под одним именем может быть довольно большое число разных троянов - это тоже надо учитывать.
                                                  0
                                                  Отправил на virusinfo.info, посмотрим сообщат ли о результате
                                                0
                                                кстати, это раздражает. У симантека, например, другая крайность - крайне малое число разновидностей, Trojan.Downloader и все тут)

                                                Если бы это было возможно, то я бы предложил развернутую классификацию:
                                                - метод заражения - файловый, авторан и так далее
                                                - действия - удаляет, троянит, рассылает спам
                                                - распространение - рассылается сервером, заражает файлы
                                                - упакован - тем-то и темто
                                                - и что-то еще

                                                и закодировать както. Типа F1.F2.D3.D4, по группе на пункт. Хотя есть опасность закопаться)
                                                  0
                                                  Мысль здравая, частично это уже есть: Win32.ИМЯ - вирус, как правило файловый. По функционалу большая часть именуется, но как быть, если троян и инжектит и спам шлет? :-) Распространение... Тоже частично у нас есть: HLLM - почтовый червь, HLLW.Autoruner - autorun.inf. Пакеры точно не нужно в название вносить. Во-первых, многие трояны пакованы несколько раз, во вторых для кучи пакеров просто нет названия, они вирусные. Вирусные пакеры, кстати, идут под именами Trojan.Paked (или Pakes), BitDefender тоже их ловит иногда.
                                                  А пока нет универсально классификации, непонятки будут...
                                                    0
                                                    ясно

                                                    тогда - "народное" название и мд5 хэш :) типа русток или нимда.
                                                      0
                                                      Хэш точно не поможет, поменяется адрес сервера, зашитый в файле - хэш и изменился. А рустоки, нимды, пинчи - это все есть :-)
                                              0
                                              Программа представляет собой nt-драйвер (так же известны, как legacy-драйвера, то есть не связанные ни с каким физическим устройством).
                                              Описываются разные вещи.
                                              NT-драйвер или legacy-драйвер это модель драйверов, разработанная для Windows NT 3.1. Работает на всей линейке NT, вплоть до последних (XP, Vista).
                                              Legacy они называются в противоположность Windows Driver Model (WDM) — модели драйверов, совместимые с Windows 98/ME/2000/XP/Vista.
                                              У Vista имеется собственный вариант модели драйверов Windows Driver Foundation
                                                0
                                                круто
                                                0
                                                как страшно жить Х_Х
                                                • UFO just landed and posted this here
                                                    0
                                                    постоянно их путаю)
                                                    0
                                                    Так что же, только MINIX3 спасёт мир от руткитов? :)

                                                    Only users with full accounts can post comments. Log in, please.