Перейти к содержанию

Лидеры

Популярный контент

Показан контент с высокой репутацией 28.09.2021 во всех областях

  1. Предисловие: Я хотел сделать эту статью сообщением под статьей пользователя roma912, но потом решил вынести её отдельно, так как здесь мы будем описывать новую версию движка и более конкретно описывать те или иные действия. Использовать мы будем тот-же SDK GEN, что и в его статье, но здесь мы рассмотрим ситуацию, когда игр, нам нужных для разбора нет в пресетах (как чаще всего и бывает), и будем искать всеми нужные GNames и GObjects, ручками. Для этого нам понадобятся инструменты. Из обязательных: GHIDRA/IDA, Cheat Engine, ReClass. Опционально: исходный код Unreal Engine конкретной версии, как его получить, смотрите здесь -- https://github.com/EpicGames/Signup, также сам движок подходящий по версии с вашей игрой. Что есть звери эти? Для того, чтобы понять, как искать эти самые GNames и GObjects, нужно понять, что они из себя представляют. Важно понимать, что в Unreal Engine 4 используется в основном язык C++, так что этот движок образный «ООП на стероидах». В нем используется сложная система наследования, практически каждый тип данных заменен на свой, с добавлением приставки “U”, такие как «UField», «UObject», «UArray», именно поэтому в нем будет разобраться не просто, даже имея исходный код на руках. Начнем с GObjects. Что это такое? Судя по названию, можно предположить, что это глобальная переменная, в которой хранятся все объекты. Это отчасти верно, однако даже поиск по исходному коду движка этого названия нам ничего не даст. Нужно подумать, объектом какого класса может быть эта переменная. Достаточно длительный разбор исходного кода движка приводит нас к следующей картине: в файле UObjectArray.h есть класс с названием «class COREUOBJECT_API FUObjectArray». Звучит интересно. Смотрим в его приватные поля и видим Интересующий нас объект называется ObjObjects. Теперь посмотрим его класс. Объявление его класса находится в том же файле выше. Не забываем про typedef и ищем класс «FFixedUObjectArray». В его приватных полях находим Это то, что нужно! В итоге логика выглядит так: FUObjectArray.ObjObjects->Objects В файле UObjectHash.cpp находим использование этого класса в играх Как видно, это статическая переменная, содержащая в себе класс «массив», который в свою очередь хранит в себе указатель на массив всех объектов в игре. Такие дела. Примечание: на многих источниках этот объект указывают как TArray<Object*>, что не совсем корректно для более поздних движков. GNames. Не буду долго распинаться, поэтому скажу в общих чертах: GNames так же статичная переменная, используемая для хранения имен всех объектов в игре. Имеет тип TNameEntryArray, что является typedef’ом от TStaticIndirectArrayThreadSafeRead<FNameEntry, 4 * 1024 * 1024, 16384> Больший интерес представляет сам класс FNameEntry, который и является классом хранения имени. Выглядит он так: Именно m_ansi нас и интересует. Розыскные мероприятия. Мы знаем, что переменные GUObjectArray и Names, статические, значит, для целей их розыска и поимки, мы можем использовать GHIRA/IDA. Дизассемблируем программу, ждем конца автоанализа. Сейчас я расскажу, как действовать, если вы решили пойти по хитрому пути и скачать движок Unreal Engine версии, совпадающей с исследуемой игрой. Заходим в EGS-> Unreal Engine -> Библиотека. Потому нажимаем на + возле Версии Unreal Engine Выбираете версию движка, нажимаете установить. ВАЖНЫЙ МОМЕНТ! Заходите в настройки установки и отмечаете галочкой эту строку Для того, чтобы потом можно было генерировать .pdb. Когда скачали, запускайте и создавайте новый проект. Желательно выбирать жанр, который совпадает с вашей исследуемой игрой. Ждем загрузки… Далее кликаем File -> Package Project -> Build Configuration -> Shipping Далее File -> Package Project -> Packaging Settings И отмечаем галочку «Include Debug Files» И, время компилировать! File -> Package Project -> Windows -> и выбираем разрядность игры, которую исследуем. Зачем это нужно? Открываем GHIDRA/IDA, пихаем туда нашу скомпилированную игру и грузим .pdb ВНИМАНИЕ: В ГИДРЕ ОТКАЗЫВАЕМСЯ ОТ АВТОАНАЛИЗА И ЗАГРУЖАЕМ .PDB ДО НЕГО! Теперь у нас есть листинг, где мы можем найти все подписанные функции движка. Выглядит это так: Вот, собственно, и всё. Теперь можно просто по паттерну искать функции в нашей исследуемой игре. Для поиска GNames нам понадобиться метод FName::GetNames() Для GObjects GUObjectArray() Подсказка: при поиске по паттерну, может быть очень много похожих функций. Ориентируйтесь на количество аргументов и тип возвращаемого значения. Также можно использовать(«абьюзить») строки, но об этом в другой раз. Зачем ReClass? К сожалению, мы с вами будем работать через SDK генератор, который обновлялся последний раз пять лет назад. А вот Epic Games обновляют движок игры примерно раз в полгода. Поэтому, нам нужно будет ручками реверсить классы в движке, и заносить результаты в отдельный файл. Так же никто не отменял, что некоторые компании изменяют движок под свои нужны и могут использовать кастомные типы данных. Поэтому, всё же, нужно будет знать объявление классов для того, чтобы SDK генератор работал правильно. Брать эти объявления можно из исходников движка, а через ReClass подтверждать, что они указаны верно для конкретно вашей игры. Послесловие. Все сказанное выше актуально только для Unreal Engine версии ниже 4.22, так как в версиях выше для GNames используется класс FNameEntryPool, который работает совершенно по-другому. Спасибо за чтение и удачи в исследованиях!
    1 балл
  2. Нашел 300 адресов, как не пытался сократить их, не получается. Мне нужно получить все их указатели, чтобы узнать название dll файла, который используется у них. Можно ли как - то быстро это сделать? так как в ручную на это уйдет несколько десяток часов)
    -1 балл
×
×
  • Создать...

Важная информация

Находясь на нашем сайте, Вы автоматически соглашаетесь соблюдать наши Условия использования.