Зашифровать память процесса и расшифровывать поблочно. Как?

Тема в разделе "WASM.WIN32", создана пользователем dyn, 19 сен 2010.

  1. dyn

    dyn New Member

    Публикаций:
    0
    Регистрация:
    30 окт 2009
    Сообщения:
    566
    А есть какой-то способ подружить ваш ехе с WINх64-системами?
     
  2. onSide

    onSide New Member

    Публикаций:
    0
    Регистрация:
    18 июн 2008
    Сообщения:
    476
    вот тут то вы и почувствуете всю силу ассемблера))))))
     
  3. Clerk

    Clerk Забанен

    Публикаций:
    0
    Регистрация:
    4 янв 2008
    Сообщения:
    6.689
    Адрес:
    РБ, Могилёв
    onSide
    Точнее это вы почувствовали всю силу скрипта. Для начала найдите качественный дизасм длин под x64. Та переносимость о который вы говорите обеспечивается компилятором, в случае асма нужно переписывать на x64.
     
  4. z0mailbox

    z0mailbox z0

    Публикаций:
    0
    Регистрация:
    3 фев 2005
    Сообщения:
    635
    Адрес:
    Russia СПБ
    можно в начале функции ставить что-нибудь ужасное например UD2 и в хендлере расшифровывать её
    примерно так было (сейчас не знаю) в старых дровах хаспа - работало
     
  5. Toxasoft

    Toxasoft New Member

    Публикаций:
    0
    Регистрация:
    20 сен 2010
    Сообщения:
    188
    Если не хочешь чтобы антивирус не нашел, то сделай самомодифицирующийся код, или перед каждым зашифрованым кодом поставь дешифратор.
     
  6. MSoft

    MSoft New Member

    Публикаций:
    0
    Регистрация:
    16 дек 2006
    Сообщения:
    2.854
    спасибо, кэп
    ты хоть мысленно представляешь сложность? :)
    в мультипоточных приложениях тоже?
     
  7. Clerk

    Clerk Забанен

    Публикаций:
    0
    Регистрация:
    4 янв 2008
    Сообщения:
    6.689
    Адрес:
    РБ, Могилёв
    В ядре просто. Вот в юзермоде проблема.
    Расшифровывать исполнять нужно по одной инструкции. Выше использовался блок заполненый однобайтовыми инструкциями генерящими сепшен. Это позволяет получать управление при вызове калбэков, тоесть передача управления по загруженной ссылке приводит к останову. Но при этом блок не должен содержать данных. Первая мысль сделать регион доступным только к исполнению, но за это отвечает не PTE/PDE, а дескриптор сегмента. Тоесть использовать дефолтные селекторы дескрипторов GDT нельзя. Если создать дескриптор в LDT и загрузить его в Cs, то это позволит отследить обращения к текущему кодовому сегменту. Но вот проблема - обычно адресация выполняется посредством селектора в Ds. В этот регистр нельзя загрузить селектор дескриптора сегмента доступного только для исполнения. Можно изменить селектор в Ds, создав для текущего региона новый не доступный сегмент, но это приведёт к смещению всего адресного пространства. Если сместить вверх кодовый сегмент, а исходный сделать не доступным это позволит отследить выборку данных, но при этом возникает проблемы со сторонними вызовами - смещения ссылок в сторонние модуля совпадают с их виртуальными адресами, так как сегменты имеют нулевые базы. Тоесть хардварным путём нельзя отследить выборку данных из текущего сегмента. Решения может быть два:
    1. Не использовать данные в коде.
    2. Выполнять дизассемблирование и анализировать выбираемую из потока инструкцию.
    При этом выполняется расшифровка очередной инструкции и её трассировка в буфере. Есчо одна проблема это ссылки на калбэки. При вызове их должен возникать останов. Это может быть достигнуто записью останова, но мы приходим к изначальному решению. Тоесть второй способ не оптимален для решения данной задачи. При отказе от использования данных в коде мы приходим к mi-/p- кодам. Надстройка может предоставлять специальные вызовы для загрузки ссылок. В этом случае можно создать таблицу калбэков, где на каждый калбэк отводится один байт для брейка и соответствующий адрес/смещение калбэка.
     
  8. ziral2088

    ziral2088 New Member

    Публикаций:
    0
    Регистрация:
    16 авг 2009
    Сообщения:
    283
    такое возможно сделать и в мультипоточных.
    Только делать нужно не трогая шифрованный кусок кода, то есть:
    1. InitShell - шифрованная функция
    2. crypted_proc - процедура для вызова шифрованных функций.

    Код (Text):
    1. call crypted_proc , InitShell
    2. ...
    3. crypted_proc:
    4. pUncryptetProc = alloc(sizeof.InitShell)
    5. memcpy( InitShell , pUncryptetProc , sizeof.InitShell )
    6. uncrypt( pUncryptetProc )
    7. jmp pUncryptetProc
    8.  
    9. pUncryptetProc:
    10. тут уже расшифрованная процедура которая и будет выполняться.
    конечно и тут будут подводные камни, как и везде.
     
  9. Clerk

    Clerk Забанен

    Публикаций:
    0
    Регистрация:
    4 янв 2008
    Сообщения:
    6.689
    Адрес:
    РБ, Могилёв
    ziral2088
    Вы предлогаете динамический морфинг.
     
  10. IceCrashLdr

    IceCrashLdr New Member

    Публикаций:
    0
    Регистрация:
    29 июн 2010
    Сообщения:
    193
    Разбить код на регионы памяти.
    Установить NO_EXECUTABLE.
    По хукать DispatchException.
    Reference counter на участки кода(для много поточности).
    В новом DispatchException, отлавливать нужное событие, декрипт если счетчик 0, и устанавливаем в единицу, иначе инкрементируем счетчик 1.
    При смене региона память, делать декременту если ноль, то делаем крипт.
    Короче баян.
     
  11. Clerk

    Clerk Забанен

    Публикаций:
    0
    Регистрация:
    4 янв 2008
    Сообщения:
    6.689
    Адрес:
    РБ, Могилёв
    IceCrashLdr
    Минимальный размер региона одна страница.
     
  12. IceCrashLdr

    IceCrashLdr New Member

    Публикаций:
    0
    Регистрация:
    29 июн 2010
    Сообщения:
    193
    Clerk
    И?
    Дешифрованный регион памяти, не должен превышать 32 байт. Сложностью будет валидировать размер инструкции.
     
  13. IceCrashLdr

    IceCrashLdr New Member

    Публикаций:
    0
    Регистрация:
    29 июн 2010
    Сообщения:
    193
    П.С.
    Да и скорость будет не велика.
     
  14. Clerk

    Clerk Забанен

    Публикаций:
    0
    Регистрация:
    4 янв 2008
    Сообщения:
    6.689
    Адрес:
    РБ, Могилёв
    IceCrashLdr
    Опишите подробнее. Если вся страница не доступна, то как будите в ней код исполнять, темболее в многопоточном приложении ?
     
  15. Toxasoft

    Toxasoft New Member

    Публикаций:
    0
    Регистрация:
    20 сен 2010
    Сообщения:
    188
    Напиши что будет делать прога и зачем тебе шифровать отдельные части кода? И зачем развивать прогу на блоки?
     
  16. Clerk

    Clerk Забанен

    Публикаций:
    0
    Регистрация:
    4 янв 2008
    Сообщения:
    6.689
    Адрес:
    РБ, Могилёв
    Toxasoft
    #4.
     
  17. Toxasoft

    Toxasoft New Member

    Публикаций:
    0
    Регистрация:
    20 сен 2010
    Сообщения:
    188
    Сори протупил.
     
  18. Toxasoft

    Toxasoft New Member

    Публикаций:
    0
    Регистрация:
    20 сен 2010
    Сообщения:
    188
    Возможно я дурак. Но при написании можно вычислить размер кода вот так: sizeofcode dd beginofcode-$.
     
  19. IceCrashLdr

    IceCrashLdr New Member

    Публикаций:
    0
    Регистрация:
    29 июн 2010
    Сообщения:
    193
    Clerk
    Страницу по умочаюнию можно запить int 3.
    дешифрованный код можно загрузить или в выделеную память, или mapview, что бы ускорить копирования когда это необходимо, так как сигнатуры все равно будут иметь офсеты.
    А вот копировать, в страницу только N байт( N < 32 байт, так как это минимальный размер для сигнатурного паттерна. ) При перемещении ip за пределы копированного участка(оригинального кода), этот участок должен занулится(точнее за "СС").
    И так
    eip попадает в участок код.
    Создаем описатель региона память. Устанавливаем счетчик использования в 1. Если описатель уже был создан, то делаем инкременту, на счетчик использования
    eip попадает в участок код, при этом выход из старого участка кода. Это будет происходит постоянно, исключения будет новый поток, или же стартап код.
    Берем описатель региона памяти из которого eip вышел. Декрементируем счетчик использования, если ноль тогда зануляем память(СС байтами).

    К стати можно было бы еще и перехватить Nt Api, и сново таки занулить память из него + убить стек, по выходу из api восстановить стек и копировать память.

    Но это будет очень медленно работать, медленнее чем Java.

    Да и к тому же как можно определить длину кода, что бы не разорвать инструкции?
     
  20. Clerk

    Clerk Забанен

    Публикаций:
    0
    Регистрация:
    4 янв 2008
    Сообщения:
    6.689
    Адрес:
    РБ, Могилёв
    IceCrashLdr
    Зачем вы мне описываете мой семпл =)
    Проблемы описаны в #27.