AppData – что лежит в этом таинственном каталоге и как избавиться от всего ненужного в нем
AppData – что лежит в этом таинственном каталоге и как избавиться от всего ненужного в нем
Как отключить мини-приложения в 11
Как вернуть старое контекстное меню в 11
Не запускается PC Health Check на 11
Не могу обновиться до 11
0xc190011f при обновлении до 11
Операционная система Windows скрывает в себе множество тайн, но некоторые из них более интересны, чем другие, и если вы возьметесь их распутывать, то можете получить неоспоримую пользу.
Возьмем, к примеру, каталог, который впервые появился в Windows Vista и о существовании которого мало кто подозревает. Причина заключается в том, что он скрыт от глаз пользователей, так как в нем хранится исключительно важная системная информация. Однако понимание его природы может помочь вам сэкономить драгоценное дисковое пространство на вашем основном разделе и, возможно, повысить производительность всей системы.
AppData (или Application Data) – это скрытая (по умолчанию) системная папка, подкаталог папки Users с личными файлами всех зарегистрированных пользователей. Папка содержит всю информацию, порожденную установленными программами на компьютере и невидима для пользователей, потому что (по крайней мере, в теории) хранящиеся в ней файлы не должны представлять для них никакого интереса.
Тем не менее, реальность часто расходится с первоначальным замыслом Microsoft. При продолжительном и активном использовании Windows без переустановки системы размер этой папки будет стремительно расти, и вскоре вы можете столкнуться с недостатком свободного пространства на системном разделе – особенно если вы используете SSD-устройство относительно скромного объема, на котором каждый мегабайт имеет значение.
Давайте подробно рассмотрим структуру AppData и выясним, какие из файлов, хранящихся в этой папке, имеют критическое значение, а какие нет.
Как уже упоминалось, AppData по умолчанию скрыта, поэтому, чтобы добраться до нее, вы должны будете изменить некоторые системные настройки Windows. Для этого откройте «Панель управления» и перейдите в раздел «Оформление и персонализация». Затем откройте диалоговое окно «Параметры папок» и на вкладке «Вид» в списке параметров найдите опцию «Скрытые файлы и папки». Теперь просто измените настройки по умолчанию («Не показывать скрытые файлы, папки и диски») на «Показывать скрытые файлы, папки и диски».
Это сделает видимой не только AppData, но и ряд других системных каталогов и файлов, а также файлы и папки, которые были скрыты вами.
AppData находится в папке C:\Users, но обратите внимание, что каждый зарегистрированный в системе пользователь имеет свой собственный каталог AppData, так что ищите папку в директории с вашим именем пользователя.
По умолчанию в этом каталоге находятся три подкаталога: Local, LocalLow и Roaming. Каждый из них хранит данные различных профилей.
Local содержит файлы, созданные в процессе работы установленных программ. Эта информация строго специфична для конкретного пользователя компьютера и не может быть перемещена на новую машину. Здесь вы найдете и папку с именем Microsoft, содержащую историю всей активности Windows.
В Local находится и папка с временными файлами (Temp), созданными во время работы различных приложений. Ее содержимое (временные файлы) можно удалить полностью, так как очень часто эти записи являются ненужными и только занимают место на диске.
Папка Roaming хранит определенные пользовательские файлы, которые могут быть перенесены с компьютера на компьютер.
Папка LocalLow предназначена в основном для буферных данных, генерируемых Internet Explorer, Java и программами от Adobe.
Очень часто в этих подкаталогах AppData накапливается довольно много софтверных «отходов», которые со временем могут разрастись до невероятных размеров. Для очистки системы от всех этих мусорных файлов вовсе не обязательно лезть в глубины AppData. До папки с временными файлами, подлежащими удалению, можно добраться и более простым способом.
Если в адресной строке проводника написать shell:history и нажать Enter, вы мгновенно окажитесь в папке с историей Internet Explorer. shell:cache открывает директорию с офлайн буфером браузера, shell:cookies показывает все записанные файлы «куки», а с shell:sendto вы можете удалять и добавлять ярлыки в меню «Отправить».
Ну а самый простой и лучший способ очистки не только AppData, но и всего ненужного на жестком диске, по-прежнему заключается в периодическом сканировании системы чудесным инструментом CCleaner от Piriform.
Исследуем защиту Obsidium
Данная защита появилась достаточно недавно, поэтому найти программу стороннего разработчика для исследования мне не удалось.
Да и зачем, учитывая, что исполняемый файл защищен этой же защитой. Лично я думаю, что нигде нельзя увидеть защиту во всей красе, кроме как на программном продукте этого же разработчика.
Tools: Soft-Ice, HIEW, Lord PE, Import Reconstructor.
Obsidium использует вот такие приколы для затруднения анализа:
Кстати, хочу заметить, что работу с dll данная защита пока не поддерживает.
Практически все производимые операции obsidium реализует на основе нескольких функций, которые записаны вот в такую структуру:
| Смешение | Описание |
| +0 | Базовый адрес, по которому находится новый образ исполняемого файла. |
| +20 | Вызывает процедуру, CRC имени которой ей передана в качестве параметра. |
| +24 | Определяет длину инструкции, адрес на которую передан в качестве параметра. |
| +30 | Считает контрольную сумму строки переданной в параметре. |
| +39 | Старый базовый адрес исполняемого файла(до обработки защитой) |
| +40 | Ищет адрес функции, по CRC имени. |
| +44 | Ищет адрес начала образа библиотеки. |
| +48 | Базовый адрес библиотеки kernel32.dll |
| +4C | Базовый адрес библиотеки user32.dll |
| +50 | Размер образа исполняемого файла. |
| +68 | Используя релоки, производит настройку кода на новый базовый адрес. |
| +С8 | Полная распаковка необходимого участка. |
Сразу хочу заметить, что здесь представлены описания не всех полей структуры, да и те, которые помещены, могут быть не совсем правильными, т.к. я заходил не во все из них и о некоторых судил, только путем анализа входных и выходных данных, хотя учитывая, что я еще не видел ни одной программы защищенной им,
думаю этих сведений вполне достаточно.
Небольшое примечание: немного забегу вперед, но вот что я заметил
— Obsidium несколько видоизменяет релоки таким образом, что он использует их не только для настройки на новый базовый адрес, но и для дописывания некоторого кода. Например, у меня при динамической расшифровке один кусок расшифровывался неправильно без релоков, а с релоками в программе появились специально вставленные инструкции, вызывающие ошибки, которые обрабатывает сама защита.
Итак, при распаковке происходят следующие вещи:
Также хочу заметить, что все место, выделяемое защитой для работы исполняемого файла легко выделить, т.к. на этих участках стоит атрибут
Read+Write+Execute.
| № | Смещение | Размер |
| 1 | 1000 | C1000 |
| 2 | C2000 | C200 |
| 3 | D3000 | 200 |
Поиск OEP и спертых байт
Найти предположительную OEP можно, если после дампа забить все байтом СС и в SI поставить бряк на int 3(bpint 3). Но это только предположительно, т.к. есть еще те байты, которые защита забрал к себе и до них
придется топать самостоятельно. Желательно предварительно поставить бряк на VirtualFree (bpx VirtualFree+3). Выход к OEP выглядит следующим образом:
Импорт тут представляет собой достаточно занимательное зрелище.
Вставляются переходники, которые выглядят вот так:
seg000:007F3E60 pusha
seg000:007F3E61 mov ax, 0 ; смещение в этом Thunck’е
seg000:007F3E65 mov dl, 0 ; Thunck
seg000:007F3E67 jmp loc_7F314C
Потом выполняется функция, которая и выполняет все работу. Эта функция берет из специально таблички атрибут данной функции и в зависимости от него решает, что дальше делать с этой функцией. Всего возможно 4 варианта:
Интересный момент, что Obsidium заполняет в IAT на 1 больше ячеек, таким образом если IAT нескольких библиотек шли подряд, то после обработки их Obsidium’ом ImpRec распознает только одну большую IAT. Так же интересным моментом является то, что защита использует нечто вроде «кэширования», т.е. в связи с тем, что операция поиска адреса функции по CRC её имени может занимать достаточно много времени, то чтобы не вызывать эту функцию несколько раз он берет и записывает адрес искомой функции вместо адреса переходника. Я функции, относящиеся ко 2 и 3-му типу, восстанавливал путем написания плагина к ImpRec’ку, который просто создавал приблизительно такую конструкцию
nop
call reducer
nop
ret
где reducer – это текущий переходник, потом вызывал её и после её обработки получал, вместо reducer относительный адрес системной функции.
Конечно, пришлось несколько подредактировать процедуру, находящуюся по адресу 7F314C, т.к. она проверяла, принадлежит ли вызывающий код исполняемому файлу.
00457F55 50 push eax
00457F56 51 push ecx
00457А57 FFD2 call edx ; вызов приведенной ниже функции
…
seg000:007F5214 mov edx, [ebx]
seg000:007F521B cmp eax, edx
seg000:007F5220 jb loc_7F5354 ; забиваем прыжок
seg000:007F522A add edx, [ebx+50h]
seg000:007F5232 cmp eax, edx
seg000:007F5239 jnb loc_7F5354 ; забиваем прыжок
seg000:007F5248 cmp word ptr [eax-6], 15FFh
seg000:007F5251 jnz short loc_7F52BF
.
seg000:007F52C2 cmp byte ptr [eax-5], 0E8h
seg000:007F52CB jnz loc_7F5354
seg000:007F52D7 mov edx, eax
seg000:007F52DC add edx, [eax-4]
seg000:007F52E8 mov ecx, [esi+172h]
seg000:007F52F3 add ecx, [ebx]
seg000:007F52F8 cmp edx, ecx
seg000:007F52FF jb short loc_7F5354 ; забиваем прыжок
seg000:007F5305 add ecx, [esi+176h]
seg000:007F530B cmp edx, ecx
seg000:007F5311 jnb short loc_7F5354 ; забиваем прыжок
seg000:007F531D cmp word ptr [edx], 25FFh
seg000:007F5328 jnz short loc_7F5354 ; забиваем прыжок
seg000:007F5333 mov edx, [ebp+0Ch]
seg000:007F5339 mov byte ptr [eax-5], 0E8h
seg000:007F5343 sub edx, eax
seg000:007F5348 mov [eax-4], edx
seg000:007F5357 pop ebx
seg000:007F5358 pop esi
seg000:007F5359 leave
seg000:007F535A retn 8
Теперь пару слов о функциях, значение которых не меняется на протяжении всего времени выполнения программы
(GetVersion, GetCommandLineA, GetCurrentProcessId). Они имеют переходники вида:
mov eax,some_value
ret
Для их восстановления достаточно просто по очереди вызвать эти функций и проверить на равенство результата значению, помещаемому в
eax. Таким образом, мы восстановили почти всю таблицу импорта, кроме функции VirtualQuery, т.к. она единственная обрабатывается 4 способом.
Получаем восстановленный импорт(API Obsidium’а пока оставим в покое) и переходим к сборке исполняемого файла с нормальным PE-заголовком.
Я взял PE-заголовок у старого exe’шника и стал добавлять секции. Размеры и RVA могут отличаться от тех, которые мы получили выше, потому что я ставил для себя цель получить для начала работающий исполняемый файл, из-за этого я специально увеличил размер дабы исключить появления дыр между секциями, т.к. разные версии Windows на это по разному реагируют.
Так же не забудьте перенести из старого исполняемого файла TLS структуру настроив её предварительно на новое местоположение.
4. Четвёртая секция будет с полученным ранее импортом.
5. Пятая секция с ресурсами. В связи с тем, что ресурсы зашифрованы, то берем
и дампим запущенный процесс, и применяем к нему утилиту Resource Rebuilder by Dr.Golova, чтобы получить новую секцию с расшифрованными ресурсами, перестроенными под новый базовый адрес.
6. Необязательная шестая секция с релоками. Релоки в первоначальном виде можно найти в участке памяти, который защита выделяет в первый раз (обычно в районе адреса 7E0000) по характерным байтам: 00 00 10 00 00 10 02 00 00
Итак, полученный исполняемый файл все равно не запускается. Причиной тому является динамическое шифрование. Если посмотреть, где происходит ошибка, то можно заметить:
009C20AE push 00000517
009C20B3 call dword ptr [004010A9] ; расшифровка
.
мусор
.
009C25D0 push 00000517
009C25D5 call dword ptr [004010AD] ; обратно зашифровываем
Хочу заметить, что между этими двумя вызовами как раз 517h байт. Теперь просто делаем дамп этого участка после расшифровки и вставляем в наш дамп. Вызовы функция для шифрования теперь можно забить nop’ами.
Таких участков я нашел 7 штук. Вот они:
В принципе с API ничего сложного нет, просто нужно найти место, чтобы вставить код, эмулирующий работу этих функций. Названия API в порядке их следования в старой таблице импорта:
Защита оказалась достаточно интересная, единственное, что меня удивило, так это то, что мне удалось получить практически полнофункциональную программу (практически, потому что я мог что-то не заметить) без генерирования лицензии, а учитывая, что там используется шифрование с открытым ключом, то это было бы очень серьезным (если не непреодолимым) препятствием к получению полнофункциональной программы.
Obsidium fatality. Обходим триальную защиту популярного протектора
warning
Статья имеет ознакомительный характер и предназначена для специалистов по безопасности, проводящих тестирование в рамках контракта. Автор и редакция не несут ответственности за любой вред, причиненный с применением изложенной информации. Распространение вредоносных программ, нарушение работы систем и нарушение тайны переписки преследуются по закону.
На примере программы, использующей одну из последних версий Obsidium, попробуем разобрать слабые и сильные места этой защиты. В статье, посвященной другому известному протектору — Enigmа, я рассказывал о популярном у разработчиков способе защиты приложения: пользователю предоставляется ознакомительный период работы с программой — можно использовать ее определенное время или выполнить определенное количество запусков. Есть такая возможность и у Obsidium. Скачав с официального сайта демоверсию защиты (последняя актуальная версия — 1.7.3.3), запускаем ее.
Для начала, как нам советуют, создадим новый проект и в его настройках укажем защиту приложения в виде триального периода. Для этого жмем в левой вертикальной панели графическую кнопку с шестеренками Settings и открываем вторую справа вкладку Time trial.

Как видишь, здесь присутствует такой же джентльменский набор функций, как и в Enigma:

После установки нужных параметров защиты жмем вторую снизу кнопку в левой панели с надписью PROTECT, затем на вкладке Executables выбираем файл защищаемой программы и, наконец, нажимаем кнопку Protect all. Теперь наше приложение под защитой демоверсии Obsidium, о чем нам будет напоминать раздражающее окошко при каждом ее запуске.
Потренировавшись на кошках, перейдем к взлому приложения. Итак, у нас имеется триальная версия программы, которую DIE идентифицирует следующим образом:
С первого взгляда очевидно, что загружать такое в дизассемблер совершенно бесполезно: код сильно сжат или зашифрован (на самом деле и то и другое). Секции пустые, из импорта имеются в наличии всего четыре функции. Попробуем сразу загрузить ее в отладчик.
Продолжение доступно только участникам
Вариант 1. Присоединись к сообществу «Xakep.ru», чтобы читать все материалы на сайте
Членство в сообществе в течение указанного срока откроет тебе доступ ко ВСЕМ материалам «Хакера», позволит скачивать выпуски в PDF, отключит рекламу на сайте и увеличит личную накопительную скидку! Подробнее
Obsidium fatality. Обходим триальную защиту популярного протектора
warning
Статья имеет ознакомительный характер и предназначена для специалистов по безопасности, проводящих тестирование в рамках контракта. Автор и редакция не несут ответственности за любой вред, причиненный с применением изложенной информации. Распространение вредоносных программ, нарушение работы систем и нарушение тайны переписки преследуются по закону.
На примере программы, использующей одну из последних версий Obsidium, попробуем разобрать слабые и сильные места этой защиты. В статье, посвященной другому популярному протектору — Enigmа, я рассказывал о популярном у разработчиков способе защиты приложения: пользователю предоставляется ознакомительный период работы с программой — можно использовать ее определенное время или выполнить определенное количество запусков. Есть такая возможность и у Obsidium. Скачав с официального сайта демоверсию защиты (последняя актуальная версия — 1.7.3.3), запускаем ее.

Для начала, как нам советуют, создадим новый проект и в его настройках укажем защиту приложения в виде триального периода. Для этого жмем в левой вертикальной панели графическую кнопку с шестеренками Settings и открываем вторую справа вкладку Time trial.

Как видишь, здесь присутствует такой же джентльменский набор функций, как и в Enigma:

После установки нужных параметров защиты жмем вторую снизу кнопку в левой панели с надписью PROTECT, затем во вкладке Executables выбираем файл защищаемой программы и, наконец, нажимаем кнопку Protect All. Теперь наше приложение под защитой демоверсии Obsidium, о чем нам будет напоминать раздражающее окошко при каждом ее запуске.
Потренировавшись на кошках, перейдем к взлому приложения. Итак, у нас имеется триальная версия программы, которую DIE идентифицирует следующим образом:
С первого взгляда очевидно, что загружать такое в дизассемблер совершенно бесполезно: код сильно сжат или зашифрован (на самом деле и то и другое). Секции пустые, из импорта имеются в наличии всего четыре функции. Попробуем сразу загрузить ее в отладчик.
Obsidium что это за программа
Материал из Справочник исследователя программ
Obsidium — программа для обеспечения защиты программного обеспечения и операционных систем от несанкционированной модификации (взлома), а также создания безопасных систем лицензирования и регистрации.
Содержание
Основные возможности
История развития
Obsidium 1.0.0.69 первая версия, которая была доступна широкому кругу лиц. Уже тогда Obsidium поддерживал антиотладочные приемы, защиту оригинальной точки входа, мусорные команды и систему лицензирования. Позже с версии 1.4.0.0 в протектор добавилась, пожалуй самая мощная опция защиты под названием Code Virtualization. На 1 января 2011 года последней версией протектора является 1.4.4.11.
Антиотладка
Obsidium использует достаточно интересные анти-отладочные трюки, в числе которых:
IsDebuggerPresent
API-функция IsDebuggerPresent показывает, находится ли процесс, который её вызывает, в контексте отладчика, то есть отлаживается ли он.Эта функция экспортируется из KERNEL32.dll, и если программа находится под отладкой, то возвращаемое значение равно единице, а если нет, то нулю.
FindWindowA
Находит pодительское окно веpхнего уpовня с совпадающими ClassName и WindowName. Не осуществляет поиск дочеpних окон
CheckRemoteDebuggerPresent
Эта функция, в принципе, аналогична IsDebuggerPresent, но только по возвращаемым результатам. А ее начинка не похожа на IsDebuggerPresent совсем. Она, как видно, может проверять и другой процесс на наличие отладки, и способ проверки отличается от простого просмотра байта в PEB. Впервые она появилась в Windows XP SP1, поэтому ее использование не универсально. Функцию CheckRemoteDebuggerPresent можно, как обычно, перехватывать, а возвращаемые ею значения – подменять.
UnhandledExceptionFilter
Если процесс не отлаживают, то на финальном исключении (не обработанном SEH), которое намеренно делает протектор (к примеру деление на ноль), управление переходит на установленный с помощью SetUnhandledExceptionFilter обработчик, после которого программа спокойно продолжает выполнять свои действия. Если же это происходит во время отладки, то управление передастся не на финальный обработчик, а отладчику, и программа падает, так как отладчик не знает, что делать.
Проверка установленных брекпоинтов
Obsidium проводит проверку наличия CC в первом байте абсолютно любой апи (непосредственно перед вызовом). Огородить себя от данной анти-отладки можно очень просто: не устанавливать брекпоинты на начало вызова WINAPI Пример
Использование исключений и SEH
Протектор очень активно использует команды приводящие к исключениям (DIV, int3 и т.д).Хоть это и не является очень сильным препятствим, но всё-таки мешает отладке программы. Также Obsidum для очистки аппартных брекпоинтов использует SEH
Потоки
Obsidum создаёт один или два дополнительных потока (Threads), которые в некоторых случаях для нормальной отладки приходиться «убивать».
Антидамп
Защита Оригинальной точки входа (OEP)
Кража OEP не является «фишкой» протектора. Крадёт он байт не много, а в некоторых программах (написанных, например на Borland C++) их даже не нужно восстанавливать. В первых версиях протектора краденные с OEP байты отрабатывались в выделенной памяти, что немного затрудняло распаковку программы.
Защита таблицы импорта
Защита таблицы импорта в Obsidium довольно серьёзная вещь. Протектор умеет получать имена API четырьмя способами (через четыре переходника):
Также протектор активно эмулирует некоторые Windows API (например GetCommandLine, GetVersion, GetCurrentProcessID и т.д), отрабатывает первые команды функций в своём защищённом коде и имеет свои собственные апи.
Runtime Patching
Obsidium позволяет помечать участки кода, которые будут расшифрованны только при непосредственном обращении к ним. Таким образом получается, что в распакованной программе эти участки кода будут не расшифрованны и обращение к ним будут приводить к краху программы. Восстановление этих участков вещь не сложная, но требующая затраты некоторого времени.
Code Virtualization
Опция защиты протектора, которая появилась в версии 1.4. Это своеобразная виртуальная машина которая отрабатывает защищённый код,который для полной распаковки программы приходится восстанавливать. Code Virtualization значительно снижает скорость работы приложения, поэтому данную защиту необходимо применять только в местах особенно критичных для взлома (например, проверка регистрации).
Другие опции
Доступные модели лицензирования
При использовании Obsidium для защиты приложения можно воспользоваться одной из встроенных в систему лицензирования моделью или придерживаться своей собственной системы регистрации.
Внутренняя система протектора
Obsidium предоставляет две надежные и простые в реализации системы лицензирования на основе сильной криптографии с открытым ключом (например, различные ключи используются для шифрования и дешифрования данных лицензирования, что делает практически невозможным создание поддельных ключей лицензии).
Внешняя система, созданная программистом
Программист может сам создать стойкий алгоритм и с помощю API протектора setExternalKey использовать его при защите своей программы.
Сохранение лицензии при регистрации программы
Obsidum при регистрации программы позволяет сохранять информацию в следующих местах:
Ключевой файл может иметь любое имя (по умолчанию key.dat), может находиться в папке с программой, в папке Документы пользователя или в папке Общие документы.
Автоматические распаковщики
На данный момент в сети не возможно найти ни один автоматический распаковщик к этому протектору. Радует только то, что к старым версиям протектора можно найти скрипты к OllyDbg для «полу-автомотической» распаковки.
Данная защита появилась достаточно недавно, поэтому найти программу стороннего разработчика для исследования мне не удалось.
Да и зачем, учитывая, что исполняемый файл защищен этой же защитой. Лично я думаю, что нигде нельзя увидеть защиту во всей красе, кроме как на программном продукте этого же разработчика.
Tools: Soft-Ice, HIEW, Lord PE, Import Reconstructor.
Obsidium использует вот такие приколы для затруднения анализа:
Кстати, хочу заметить, что работу с dll данная защита пока не поддерживает.
Практически все производимые операции obsidium реализует на основе нескольких функций, которые записаны вот в такую структуру:
| Смешение | Описание |
| +0 | Базовый адрес, по которому находится новый образ исполняемого файла. |
| +20 | Вызывает процедуру, CRC имени которой ей передана в качестве параметра. |
| +24 | Определяет длину инструкции, адрес на которую передан в качестве параметра. |
| +30 | Считает контрольную сумму строки переданной в параметре. |
| +39 | Старый базовый адрес исполняемого файла(до обработки защитой) |
| +40 | Ищет адрес функции, по CRC имени. |
| +44 | Ищет адрес начала образа библиотеки. |
| +48 | Базовый адрес библиотеки kernel32.dll |
| +4C | Базовый адрес библиотеки user32.dll |
| +50 | Размер образа исполняемого файла. |
| +68 | Используя релоки, производит настройку кода на новый базовый адрес. |
| +С8 | Полная распаковка необходимого участка. |
Сразу хочу заметить, что здесь представлены описания не всех полей структуры, да и те, которые помещены, могут быть не совсем правильными, т.к. я заходил не во все из них и о некоторых судил, только путем анализа входных и выходных данных, хотя учитывая, что я еще не видел ни одной программы защищенной им,
думаю этих сведений вполне достаточно.
Небольшое примечание: немного забегу вперед, но вот что я заметил
— Obsidium несколько видоизменяет релоки таким образом, что он использует их не только для настройки на новый базовый адрес, но и для дописывания некоторого кода. Например, у меня при динамической расшифровке один кусок расшифровывался неправильно без релоков, а с релоками в программе появились специально вставленные инструкции, вызывающие ошибки, которые обрабатывает сама защита.
Итак, при распаковке происходят следующие вещи:
Также хочу заметить, что все место, выделяемое защитой для работы исполняемого файла легко выделить, т.к. на этих участках стоит атрибут
Read+Write+Execute.
Итак, ставим бряк на VirtualAlloc (bpx VirtualAlloc+3) и ждем, когда вызов произойдет в 3 раз, потом выходим и топаем до тех пор, пока новый выделенный участок не заполниться данными (у меня он почти всегда находился по адресу 009С0000). Если попутно вы будете обходить все вызовы [ebx+68], то получите данные без использования релоков. Вызов функции [ebx+68] полезен тем, что он дает возможность узнать какие бывшие секции, куда “проецируются”. Узнать это можно посмотрев на передаваемые ей параметры, один из них — это смещение относительно базового адреса и размер. В итоге получаем:
Поиск OEP и спертых байт
Найти предположительную OEP можно, если после дампа забить все байтом СС и в SI поставить бряк на int 3(bpint 3). Но это только предположительно, т.к. есть еще те байты, которые защита забрал к себе и до них
придется топать самостоятельно. Желательно предварительно поставить бряк на VirtualFree (bpx VirtualFree+3). Выход к OEP выглядит следующим образом:
seg000:007F5C08 mov byte ptr [ebp+eax+40C228h], 0E9h ; ‘щ’
seg000:007F5C16 mov edx, [ebp+40C334h]
seg000:007F5C21 add edx, [esi]
seg000:007F5C26 lea ecx, [ebp+eax+40C22Dh]
seg000:007F5C32 sub edx, ecx
seg000:007F5C38 mov [ebp+eax+40C229h], edx
seg000:007F5C44 popa
seg000:007F5C4A popf
// —————————Далее идут украденные байты
————————— //
seg000:007F5C53 mov eax, ds:0A8208Bh
seg000:007F5C5B shl eax, 2
seg000:007F5C64 mov ds:0A8208Fh, eax
seg000:007F5C6C push edx
seg000:007F5C71 push 0
seg000:007F5C79 jmp near ptr 9C144Ah ;
дальнейшее выполнение программы
(Для хорошей читабельности мусор и постоянные jmp удалены).
Импорт тут представляет собой достаточно занимательное зрелище.
Вставляются переходники, которые выглядят вот так:
seg000:007F3E60 pusha
seg000:007F3E61 mov ax, 0 ; смещение в этом Thunck’е
seg000:007F3E65 mov dl, 0 ; Thunck
seg000:007F3E67 jmp loc_7F314C
Потом выполняется функция, которая и выполняет все работу. Эта функция берет из специально таблички атрибут данной функции и в зависимости от него решает, что дальше делать с этой функцией. Всего возможно 4 варианта:
Интересный момент, что Obsidium заполняет в IAT на 1 больше ячеек, таким образом если IAT нескольких библиотек шли подряд, то после обработки их Obsidium’ом ImpRec распознает только одну большую IAT. Так же интересным моментом является то, что защита использует нечто вроде «кэширования», т.е. в связи с тем, что операция поиска адреса функции по CRC её имени может занимать достаточно много времени, то чтобы не вызывать эту функцию несколько раз он берет и записывает адрес искомой функции вместо адреса переходника. Я функции, относящиеся ко 2 и 3-му типу, восстанавливал путем написания плагина к ImpRec’ку, который просто создавал приблизительно такую конструкцию
nop
call reducer
nop
ret
где reducer – это текущий переходник, потом вызывал её и после её обработки получал, вместо reducer относительный адрес системной функции.
Конечно, пришлось несколько подредактировать процедуру, находящуюся по адресу 7F314C, т.к. она проверяла, принадлежит ли вызывающий код исполняемому файлу.
00457F55 50 push eax
00457F56 51 push ecx
00457А57 FFD2 call edx ; вызов приведенной ниже функции
…
seg000:007F5214 mov edx, [ebx]
seg000:007F521B cmp eax, edx
seg000:007F5220 jb loc_7F5354 ; забиваем прыжок
seg000:007F522A add edx, [ebx+50h]
seg000:007F5232 cmp eax, edx
seg000:007F5239 jnb loc_7F5354 ; забиваем прыжок
seg000:007F5248 cmp word ptr [eax-6], 15FFh
seg000:007F5251 jnz short loc_7F52BF
.
seg000:007F52C2 cmp byte ptr [eax-5], 0E8h
seg000:007F52CB jnz loc_7F5354
seg000:007F52D7 mov edx, eax
seg000:007F52DC add edx, [eax-4]
seg000:007F52E8 mov ecx, [esi+172h]
seg000:007F52F3 add ecx, [ebx]
seg000:007F52F8 cmp edx, ecx
seg000:007F52FF jb short loc_7F5354 ; забиваем прыжок
seg000:007F5305 add ecx, [esi+176h]
seg000:007F530B cmp edx, ecx
seg000:007F5311 jnb short loc_7F5354 ; забиваем прыжок
seg000:007F531D cmp word ptr [edx], 25FFh
seg000:007F5328 jnz short loc_7F5354 ; забиваем прыжок
seg000:007F5333 mov edx, [ebp+0Ch]
seg000:007F5339 mov byte ptr [eax-5], 0E8h
seg000:007F5343 sub edx, eax
seg000:007F5348 mov [eax-4], edx
seg000:007F5357 pop ebx
seg000:007F5358 pop esi
seg000:007F5359 leave
seg000:007F535A retn 8
Теперь пару слов о функциях, значение которых не меняется на протяжении всего времени выполнения программы
(GetVersion, GetCommandLineA, GetCurrentProcessId). Они имеют переходники вида:
mov eax,some_value
ret
Для их восстановления достаточно просто по очереди вызвать эти функций и проверить на равенство результата значению, помещаемому в
eax. Таким образом, мы восстановили почти всю таблицу импорта, кроме функции VirtualQuery, т.к. она единственная обрабатывается 4 способом.
Получаем восстановленный импорт(API Obsidium’а пока оставим в покое) и переходим к сборке исполняемого файла с нормальным PE-заголовком.
Я взял PE-заголовок у старого exe’шника и стал добавлять секции. Размеры и RVA могут отличаться от тех, которые мы получили выше, потому что я ставил для себя цель получить для начала работающий исполняемый файл, из-за этого я специально увеличил размер дабы исключить появления дыр между секциями, т.к. разные версии Windows на это по разному реагируют.
Так же не забудьте перенести из старого исполняемого файла TLS структуру настроив её предварительно на новое местоположение.
4. Четвёртая секция будет с полученным ранее импортом.
5. Пятая секция с ресурсами. В связи с тем, что ресурсы зашифрованы, то берем
и дампим запущенный процесс, и применяем к нему утилиту Resource Rebuilder by Dr.Golova, чтобы получить новую секцию с расшифрованными ресурсами, перестроенными под новый базовый адрес.
6. Необязательная шестая секция с релоками. Релоки в первоначальном виде можно найти в участке памяти, который защита выделяет в первый раз (обычно в районе адреса 7E0000) по характерным байтам: 00 00 10 00 00 10 02 00 00
Итак, полученный исполняемый файл все равно не запускается. Причиной тому является динамическое шифрование. Если посмотреть, где происходит ошибка, то можно заметить:
009C20AE push 00000517
009C20B3 call dword ptr [004010A9] ; расшифровка
.
мусор
.
009C25D0 push 00000517
009C25D5 call dword ptr [004010AD] ; обратно зашифровываем
Хочу заметить, что между этими двумя вызовами как раз 517h байт. Теперь просто делаем дамп этого участка после расшифровки и вставляем в наш дамп. Вызовы функция для шифрования теперь можно забить nop’ами.
Таких участков я нашел 7 штук. Вот они:
1. 9C20B9 — 517
2. 9C38FE — 30B
3. 9C54AB — 17
4. 9C5FB6 — D5
5. 9C668E — 8E
6. 9C6ACB — 10
7. 9E874B — 5E
В принципе с API ничего сложного нет, просто нужно найти место, чтобы вставить код, эмулирующий работу этих функций. Названия API в порядке их следования в старой таблице импорта:
Защита оказалась достаточно интересная, единственное, что меня удивило, так это то, что мне удалось получить практически полнофункциональную программу (практически, потому что я мог что-то не заметить) без генерирования лицензии, а учитывая, что там используется шифрование с открытым ключом, то это было бы очень серьезным (если не непреодолимым) препятствием к получению полнофункциональной программы.
Obsidium is a feature-rich professional software protection and licensing system that was designed as a cost effective and easy to implement, yet reliable and non-invasive way to protect your 32- and 64-bit Windows software applications and games from reverse engineering, unauthorized modifications («cracking») and redistribution («software piracy») while providing a secure and flexible licensing/registration system.
It is primarily aimed at software companies and individual developers who would like to provide feature- or time-limited evaluation versions of their software products, but also allows for the implementation of a wide range of custom licensing scenarios.
Visit the Details page for a list of key features.
A functionally limited demo version of Obsidium is available for download and may be evaluated without a time limit.













