Вступление

Устаревшие технологии не исчезают. Они просто уходят в подполье: в архивы, на дискеты, в память тех, кто помнит, как это было. DOS-игры не просто программы. Это произведения инженерного искусства, созданные в эпоху, когда каждый байт имел значение, а каждый такт процессора, вес. Они работали на железе, которое сегодня кажется примитивным, но при этом умели то, что многим современным системам не под силу: дышать.

Моя первая игра была на диске. Она называлась Syndicate (1993, Bullfrog Productions), и я не понимал, как она работает. Я видел, как агенты стреляют, как взрываются машины, как звучит саундтрек, но не имел ни малейшего представления, что за этим стоит.

Я знал C, что такое переменные, циклы, указатели. Но я не мог объяснить, как в игре реализован путь юнита, как обрабатывается урон, как генерируется уровень. Тогда я не понимал кода, но код уже управлял мной. Спустя годы я вернулся к этим играм не как игрок, а как исследователь. И понял: они - лучшая школа программирования, которую только можно себе представить.

Современные игры скрывают свою архитектуру за слоями абстракций: виртуальные машины, движки, фреймворки. Чтобы понять, как они работают, нужно разобраться в десятках технологий.

DOS-игры - другое дело: нет виртуальных машин; нет сборщиков мусора; нет драйверов. Есть только процессор, память и код, написанный на C/C++ или ассемблере. Это делает их идеальной школой для изучения реального программирования.

Дизассемблирование таких игр - это не про взлом. Это археология программирования: вы не ломаете систему, а восстанавливаете её логику по обломкам машинного кода, как археолог, собирающий мозаику из черепков.

Именно так рождаются новые возможности:

  • сначала - анализ (вы изучаете поведение игры и её бинарный код);

  • затем - понимание (вы восстанавливаете архитектуру, находите ключевые функции);

  • после - воссоздание (вы переписываете логику на C или C++);

  • итог - развитие (вы исправляете баги, добавляете поддержку современных систем, расширяете контент)

Люди переписывают ретро-игры, потому что:

  • хотят сохранить то, что ускользает от времени;

  • хотят понять, как это было сделано;

  • хотят внести своё: новую механику, новый контент, новую жизнь

Эта статья не руководство по взлому. Это пошаговое руководство по исследованию. Мы не будем запускать ZZT или Lemmings ради ностальгии. Мы будем вскрывать их код, чтобы увидеть, как разработчики принимали решения, как реагировали на ввод, как рисовали графику.

И, возможно, научиться у них.

Что такое дизассемблирование?

Дизассемблирование - это не просто перевод байтов в ассемблер. Это вскрытие "чёрного ящика", чтобы понять, как программа принимает решения, обрабатывает ввод, рисует графику и управляет памятью.

Когда вы дизассемблируете .EXE-файл игры под DOS, вы не просто смотрите на код, вы восстанавливаете логику разработчика, его оптимизации, приёмы, даже ошибки. Вы видите, как он обходил ограничения 640 КБ, как работал с видеопамятью напрямую, как реализовывал ИИ врагов.

Для тех, кто помнит DOS
Для нас, кто рос на этих играх, дизассемблирование - это возможность вернуться к истокам. Это не ностальгия, а творческое воссоздание:

  • восстановить любимую игру;

  • добавить поддержку современных систем;

  • исправить баги;

  • расширить контент

Пример - KeeperFX, где фанаты не просто запустили Dungeon Keeper на Windows 7, 10 и 11, а переписали, расширили, оживили её. Это не ремейк - это наследие, переданное следующему поколению.

Для нового поколения
Для тех, кто вырос на Unity и Python, DOS-игры - это школа настоящего программирования. Здесь нет абстракций, нет виртуальных машин, есть только человек и процессор, в прямом диалоге. Изучая такие игры, вы:

  • понимаете, как работает память, порты, прерывания,

  • учитесь писать эффективный, предсказуемый код,

  • развиваете аналитическое мышление - ведь вы восстанавливаете логику по фрагментам. Это фундамент для создания: собственных ОС, драйверов, игровых движков, систем реального времени.

Дизассемблирование - это реверс-инжиниринг, востребованный навык в:

  • кибербезопасности;

  • анализе вредоносов;

  • восстановлении legacy-систем;

  • разработке совместимых решений

Игры вроде M.A.X., Z или Syndicate - не просто развлечение. Это образцы инженерного мастерства, где каждый байт на счету, а каждая инструкция результат компромисса между скоростью, памятью и возможностями железа.

Дизассемблирование таких игр - это как пройти стажировку у лучших программистов 90-х. Вы не просто читаете код - вы учитесь у него. И, возможно, однажды, создадите что-то своё, ещё лучше.

Шаг 1: Выбираем игру — от простого к сложному

Выбор игры, первый и один из самых важных шагов. От него зависит, будет ли ваш путь обучением или бесконечной головной болью. Я предложил начать с таких игр, как ZZT, Lemmings, Commander Keen, M.A.X. или Z, не потому что они "лучшие", а потому что они:

  • Просты по архитектуре, их движки понятны, логика линейна;

  • Написаны на C или смеси C и ассемблера, проще для анализа, чем чистый ассемблер;

  • Не имеют сложной упаковки или защиты, меньше препятствий на старте;

  • Достаточно документированы, в интернете есть гайды, обсуждения, скриншоты памяти

M.A.X. (1996) - тактическая стратегия с элементами RTS и RPG - отличный выбор. Её движок использует предсказуемую структуру данных для юнитов и карт, и не перегружен графикой. Это позволяет сфокусироваться на логике ИИ, системе строительства и обработке ввода, не теряясь в сложности.

Z (1996) - быстрая изометрическая стратегия - ещё один сильный кандидат. Игра написана компактно, с акцентом на производительность. Её ИИ врагов, физика движения и система уровней - отличные объекты для анализа.

Эти игры не так часто разбираются, как Duke Nukem, что делает их свежим полем для исследования, особенно на платформах, где тема Duke Nukem уже исчерпана.

Но что, если вы хотите большего вызова?

"А что, если выбрать игру на чистом ассемблере?" - Игры на чистом ассемблере - это уже не стартовая площадка, а полигон для глубокого анализа. Они подходят тем, кто уже освоил основы дизассемблирования и хочет испытать себя на коде, где каждая инструкция - результат ручной оптимизации.

  • Prince of Persia (1989);

  • RollerCoaster Tycoon (1999);

  • DOS-демки (demoscene) часто, 100% ассемблер.

Плюсы:

  • Максимальная производительность;

  • Прямой контроль над железом;

  • Чистый, оптимизированный код

Минусы:

  • Нет структур, функций, типов, только метки и прыжки;

  • Тяжело читать логику;

  • Тяжело отличить данные от кода;

  • Легко потерять контекст

"А что, если игра уже с открытым кодом? Например, LBA1 или LBA2?" - есть проекты, где разработчики официально открыли исходный код, например:

  • LBA1 и LBA2 - исходники выложены на GitHub;

  • Wolfenstein 3D, Doom - id Software открыла код ещё в 90-х;

"Почему тогда дизассемблировать, если код уже есть?"

Потому что:

  1. Открытый код ≠ оригинальный бинарник. Исходник может быть переписан, адаптирован, утерян или не соответствовать релизной версии;

  2. Анализ бинарника учит читать "настоящий" код, как он был скомпилирован, оптимизирован, упакован;

  3. Это тренировка для случаев, когда исходников нет, а таких случаев 99%.

Вы можете использовать открытый код как эталон. Дизассемблируйте .EXE, а потом сравните с исходником и увидите, как компилятор превращает C в ASM.

Ещё лучше, самим попробовать пересобрать игру. Возьмите исходный код (например, из репозитория LBA или Doom), скомпилируйте его с помощью Open Watcom, Turbo C++ или современного кросс-компилятора под DOS, и посмотрите, что получится. Затем сравните ваш .EXE с оригинальным релизным файлом в Ghidra или ImHex.

Вы увидите:

  • Какие оптимизации применил компилятор;

  • Как изменилась структура кода;

  • Где появились различия в вызовах;

  • Как обрабатываются данные (уровни, графика, звук)

Иногда ваша сборка будет почти идентична оригиналу и это победа. А иногда, сильно отличаться и тогда вы поймёте, что:

  • использовался другой компилятор;

  • были ручные ассемблерные вставки;

  • применялась упаковка;

  • или код модифицировался после компиляции

Это уникальный шанс увидеть разницу между "чистым" кодом и тем, что попало в руки игрокам. Именно так исследователи поняли, как работали тайминги в Doom, как оптимизирована физика в Duke Nukem 3D, или как реализован ИИ в LBA Remake.

Иногда исходный код не просто недоступен - он уничтожен.

В 2020 году в мировой прессе появились статьи о судьбе исходного кода Fallout 1 и 2. Дизайнер Тим Кейн (Tim Cain) рассказал, что ему приказали удалить весь код и наработки с личного компьютера, включая бумажные зарисовки, заметки и концепты. Компания-издатель (тогда Interplay) боялась утечки. Но спустя время, одна из основательниц Interplay, Ребекка Хайнеман заявила: код не утерян. Он сохранился. Утеряны: личные записи, пометки, логика решений тех, кто создавал игру. А сам код находится у текущего владельца прав - Bethesda и только они могут разрешить его публикацию.

Именно поэтому, реверс-инжиниринг становится актом сохранения культурного наследия. Когда доступ к исходникам закрыт, дизассемблирование - единственный способ понять, как работала игра, и передать её дух следующему поколению.

Совет: начните с малого, но думайте о большом. Выберите игру, которая:

  • вам нравится;

  • не слишком большая;

  • имеет понятную механику (платформер, головоломка, текстовая RPG)

Коротко о .COM и .EXE

При выборе игры для анализа вы можете столкнуться с двумя основными форматами исполняемых файлов под DOS: .COM и .EXE.

  • .COM-файлы - это самый простой формат исполняемых программ в DOS. Весь файл - это "чистый машинный код", который загружается по адресу CS:0100h и начинает сразу выполняться. Нет заголовка, нет сегментов, нет метаданных. Именно поэтому, .COM - идеальный выбор для начала пути в реверс-инжиниринге;

  • .EXE-файлы - более сложные. Они имеют заголовок, могут использовать несколько сегментов, и их точка входа определяется не по смещению 0, а из заголовка. Это делает их сложнее для анализа

Характеристика

.COM

.EXE

Размер

до 64 Kb

могут быть больше

Заголовок

отсутствует

512 байт

Сегментация

упрощённая: весь код загружается по адресу0100h

сложная: сегменты кода, данных, стека

Точка входа (OEP)

всегда первая инструкция

указана в заголовке

Сложность для анализа

низкая

средняя / высокая

Шаг 2: Инструменты — подготовка к анализу

Перед тем как загружать исполняемый файл в дизассемблер, необходимо провести предварительный анализ бинарника. Многие DOS-программы были упакованы, защищены или скомпилированы с нестандартными компиляторами. Если вы пропустите этот этап, Ghidra (или другой дизассемблер) может не распознать формат, неверно определить точку входа или вообще отказаться открыть файл.

  • Detect It Easy (DIE) - Анализ исполняемого файла: определение формата, компилятора, упаковщика, архитектуры. Отлично распознаёт DOS MZ-экзешники, упаковщики (например, UPX, FSG, ASPack), и может подсказать, сдвинута ли точка входа (OEP);

  • ImHex - Hex-редактор с анализом бинарников. Позволяет просматривать структуру, искать строки, сигнатуры. Поддерживает плагины для анализа форматов, включая MZ. Удобен для поиска ресурсов и сжатых данных;

  • DOSBox - Эмулятор MS-DOS для запуска и тестирования игры. Классический DOSBox (0.74) больше не развивается, но стабилен;

  • DOSBox-X - Современный форк DOSBox с точной эмуляцией железа, включая cycle-exact CPU. Активно развивается. Идеален для анализа игр, чувствительных к таймингам;

  • PCEm - Утилита для записи и воспроизведения состояния DOS-системы;

  • Ghidra - Дизассемблер и анализатор бинарников от NSA. Поддерживает DOS MZ-формат, но не работает с упакованными файлами;

  • IDA Free - Мощный дизассемблер, "золотой стандарт" реверс-инжиниринга. Поддерживает 16-битный код. Удобен для анализа после распаковки;

  • OllyDbg 1 и OllyDbg 2- Отладчик для анализа программ в реальном времени. Может использоваться для анализа поведения в эмуляторе;

  • Radare2 (r2) - Открытый фреймворк для анализа бинарников в командной строке. Поддерживает x86-16 и MZ. Отлично подходит для автоматизации;

  • Turbo Debugger (TD) - Входил в пакет Borland Turbo C++/Pascal/Assembler. Работает непосредственно в DOS. Позволяет ставить брейкпоинты, смотреть регистры, память. Примечание: под "свой" эмулятор надо искать стабильную сборку. "Свою" я нашел в TASM 4;

  • Open Watcom / Turbo C++ / Watcom C - Компиляторы для написания и компиляции кода под DOS. Позволяют воссоздать поведение оригинальной игры. Личная рекомендация для Watcom C - используйте версию не менее 10.0, в некоторых случаях (!), могут потребоваться и более ранние версии, например 7.0;

  • VS Code / Notepad++ / VS Studio и другие - Текстовые редакторы для ведения заметок и написания кода. Удобны для аннотирования функций, записи гипотез;

  • SoftIce - Легендарный отладчик и дизассемблер для DOS и Windows 9x. Работал на уровне ядра, позволял ставить брейкпоинты на прерывания, анализировать распаковщики, находить OEP. Требует DOS-режим или точную эмуляцию (PCEm, DOSBox-X);

  • Sourcer - Легендарный дизассемблер для DOS

Вы могли задаться вопросом: "Почему мы не используем QEMU - мощный и точный эмулятор, способный моделировать реальное железо?"
Ответ прост: наша цель не системная эмуляция, а анализ логики программы.

QEMU - отличный выбор для задач, требующих точной настройки железа, анализа драйверов или реверса упакованных программ с защитой. Однако он слишком сложен и избыточен для первого этапа реверс-инжиниринга DOS-игр.

Шаг 3: Запускаем игру и изучаем её поведение

Перед тем как приступать к дизассемблированию, важно понять, как игра работает с точки зрения пользователя и системы. Это ваша "обратная связь", вы будете сравнивать поведение оригинала с тем, что воссоздаёте. Для этого нужно запустить игру в совместимом окружении, которое максимально точно воспроизводит оригинальную DOS-систему. Обычно это делается с помощью эмуляторов ПК, таких как DOSBox, DOSBox-X или PCEm.

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

Что нужно сделать:

  1. Подготовьте игру: убедитесь, что у вас есть оригинальный .EXE или .COM файл, а также, при необходимости, файлы данных (уровни, графика, звук);

  2. Выберите эмулятор:

    • Для высокой совместимости и простоты - DOSBox;

    • Для точного анализа и отладки - DOSBox-X (лучшая поддержка отладочных функций);

    • Для записи состояния и реверс-инжиниринга в реальном времени - PCEm

  3. Настройте эмулятор:

    • Смонтируйте папку с игрой как виртуальный диск;

    • Убедитесь, что установлены правильные настройки: CPU-циклы, видеорежим (VGA, EGA), звуковая карта (AdLib, Sound Blaster);

    • При необходимости, включите режим отладки

Почему поведение может отличаться:

  • PCEm может изменять поведение программы, так как перехватывает системные вызовы для записи состояния.

  • DOSBox иногда упрощает тайминги, что может повлиять на логику игр, зависящих от задержек.

  • DOSBox-X предлагает режимы точной эмуляции, включая cycle-exact CPU и точное поведение DMA, что критично для анализа.

Рекомендация:
Сравнивайте поведение игры в DOSBox-X (для анализа) и PCEm (для записи сценариев). Если вы видите расхождения — это не ошибка, а артефакт эмуляции.
Истинное поведение — то, которое ближе к оригинальному железу.

Что фиксировать: как вести заметки перед дизассемблированием

Прежде чем открывать Ghidra, ваша задача собрать как можно больше "подсказок" из поведения игры. Это сэкономит часы анализа. Ведите заметки в текстовом редакторе (VS Code, Notepad++) или прямо в блокноте. Чем больше вы запишете информации про игру, тем проще вам будет находить в коде ресурсы, им соответствующие, и выявлять логику их вызова.

Что стоит записать:

  • Графический режим - Какой режим используется? Ищите подсказки: Разрешение: 320x200 (Mode 13h), 640x480 (Mode 12h)? Количество цветов? Есть ли текстовый режим (80x25)?

  • Управление - Как работает ввод? Клавиатура? Джойстик? Есть ли поддержка мыши? Используются ли прямые порты (in/out) или BIOS-вызовы?

  • Звук и музыка - Есть ли звук? Какой тип? AdLib? Sound Blaster? Внутренний динамик?

  • Структура игры - Как организовано меню? Как загружаются уровни? Есть ли сохранения? Какие строки в игре выделяются? (например: "Game over", "Level 1")

Теперь вы не просто игрок - вы аналитик. И каждая запись в блокноте - это ключ к следующему фрагменту кода.

Шаг 4: Как работает Ghidra — что происходит под капотом

Когда вы открываете .EXE-файл в Ghidra, она не просто показывает ассемблер. Она пытается восстановить вашу программу так, будто у него есть исходный код. Но исходников нет, только байты. И Ghidra должна "гадать": на основе паттернов, структур, вызовов.

Это не магия, а сложный, многоэтапный процесс, и понимание его поможет вам:

  • не доверять слепо результатам;

  • понимать, почему Ghidra ошибается;

  • вручную исправлять её гипотезы.

Как Ghidra "думает", краткий пайплайн:

  • Разбор бинарника - Ghidra сначала определяет формат файла (DOS MZ, PE и т.д.) и загружает его в память;

  • Декодирование инструкций - с помощью Sleigh - внутреннего языка описания архитектур, Ghidra превращает байты в инструкции x86;

  • Построение графа управления (CFG) - Ghidra строит Control Flow Graph, чтобы понять, какие блоки кода ведут к каким. Без этого нельзя определить границы функций;

  • Преобразование в SSA (Static Single Assignment) - каждая переменная получает уникальное имя. Это помогает анализировать, как значения передаются между инструкциями, особенно после оптимизаций;

  • Анализ типов и структур - Ghidra "гадает", что означают числа: указатель? смещение? часть структуры?

  • Генерация C-подобного кода (псевдо-кода) - на основе анализа Ghidra строит декомпилированный C-код, но это не исходник - это реконструкция, основанная на предположениях.

Ghidra может ошибаться, если:

  • код оптимизирован;

  • использованы косвенные вызовы;

  • функции встроены (inline);

  • нестандартные структуры данных

Понимание того, как работает Ghidra, делает вас умнее, чем если бы вы просто нажимали "Decompile". Только вы можете превратить "гадание" в "понимание".

Как вы можете помочь Ghidra?

  • определяйте и создавайте структуры (Player, Level и т.д.);

  • переименовывайте функции (пример: FUN_00401230 в Init_Video);

  • переопределяйте типы;

  • добавляйте комментарии - они могут помочь в понимании контекста

Шаг 5: Находим ключевые части — архитектура x86 и ассемблер в контексте реверс-инжиниринга

После запуска .EXE-файла в Ghidra вы увидите список инструкций: mov ax, 13h, int 10h, cmp cx, dx. Это не случайный набор команд. Это низкоуровневый код, непосредственно выполняемый процессором. Даже если вы не работали с ассемблером напрямую, понимание основных элементов x86-архитектуры критически важно для анализа. Ведь именно здесь, на уровне регистров, прерываний и машинных инструкций, принимаются ключевые решения: как инициализируется видео, как обрабатывается ввод, как загружаются данные.

Как Ghidra видит типы данных:

Когда вы открываете .EXE-файл в Ghidra, вы увидите такие обозначения, как (примеры):

  • word_00401000

  • dword_00402000

  • undefined2

  • undefined4

Это типы данных, которые Ghidra использует для описания размера значения в памяти.

  • byte - 8 бит (1 байт) - одиночный байт. Эквивалент в C - char

  • word - 16 бит (2 байта) - "слово" в 16-битной архитектуре. Эквивалент в C - short

  • dword - 32 бита (4 байта) - "двойное слово". Эквивалент в C - int или long

  • qword - 64 бита (8 байт) - "64-битное слово". Эквивалент в C - long long

В DOS-играх word - это "стандарт", если процессор работает в 16-битном режиме. Соответственно для 32 бит, "стандартом" будет - dword

В Ghidra вы можете встретить как 16-, так и 32-битные инструкции, особенно если игра была скомпилирована с поддержкой 386+.

Во второй части мы познакомимся с регистрами и основными инструкциями, такими как: mov, add, cmp и другими... будут показаны примеры кода. Эта статья самая первая на Хабре, поэтому жду от вас, уважаемые читатели, конструктивной критики.

Как воссоздать код DOS-игры: пошаговое дизассемблирование ретро-игр (часть 2) - уже в работе... небольшая интрига и для затравки - Randall Hyde...

Используемые инструменты для подготовки материалов для части 2

Эмуляторы

PCEm v.15 - Pentium 133, Win98SE Eng.

DosBox-X v2025.05.03

Языки программирования

Watcom C 10.5 - для .EXE

Дизассемблеры

Ghidra 11.3.2

Turbo Debugger (в комплекте TASM 4)

Комментарии (52)


  1. JordanCpp
    06.08.2025 08:52

    Здравствуйте, возможно ли дизассемблировать хоть в какое-то подобие си к примеру бинарник игры Arcanum и все это добро скомпилировать?


    1. iklin
      06.08.2025 08:52

      Можно попробовать поискать транспайлер asm → c. Хотя зверь, полагаю, достаточно редкий.
      Т.е. сначала бинарник в ассемблер, а потом ассемблер в си. Да только по дороге всё равно что-нибудь где-нибудь да сломается.


      1. NeriaLab Автор
        06.08.2025 08:52

        Всё верно, поэтому каждый шаг придётся отсматривать


        1. JordanCpp
          06.08.2025 08:52

          Понял. Спасибо.


      1. JordanCpp
        06.08.2025 08:52

        Меня больше интересует именно автоматизация процесса. что бы была возможность итоговый си код портировать под windows, linux нативно. Но я понимаю, что такой си будет не понятнее асма;)


        1. NeriaLab Автор
          06.08.2025 08:52

          И Вы чертовски правы


    1. SIISII
      06.08.2025 08:52

      IDA Pro умеет генерировать сишный код из результата дизассемблирования, но тут вопрос ещё в том, может ли она сделать это для конкретного случая (мало ли какие ограничения имеются).

      Плюс, сишный код, полученный таким путём -- он, конечно, сишный, но логика зачастую остаётся непонятной: вполне могут быть if и goto вместо циклов и т.п. вещи.


      1. NeriaLab Автор
        06.08.2025 08:52

        С IDA, честно признаюсь, мало работал, в разы меньше чем Гидрой, но разве IDA даёт чистый код?! У Гидры - это псевдо-код, о чём я писал в статье

        В другой части, кода "перейдём к практике", хочу показать примеры того как все выглядит в Гидре и что бывает проще все написать самому, чем доверятся Гидре и хочу показать пример "хорошей" генерации кода в Гидре


    1. NeriaLab Автор
      06.08.2025 08:52

      Но Arcanum - действительно большая игра. Было дело, играл в неё. Но я бы не рекомендовал бы ее для реверса, если Вы новичок. Начните с чего-то попроще, "набейте" руку


      1. JordanCpp
        06.08.2025 08:52

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

        Пока занимаюсь библиотекой SDL3Lite, но есть наработки по новому движку https://github.com/JordanCpp/ArcanumWorld

        Даже уроки в виде статей по разработке движка аркакнум сделал. Вы правы дизассемблировать арканум, для меня это сверх задача.


        1. NeriaLab Автор
          06.08.2025 08:52

          О, сколько нам открытий чудных
          Готовят просвещенья дух,
          И опыт, сын ошибок трудных,
          И гений, парадоксов друг,
          И случай, бог изобретатель.


          А.С. Пушкин


    1. sa2304
      06.08.2025 08:52

      Про "лучший из лучших" плагин-декомпилятор HexRays к IDA Pro - им декомпилировали Notepad, но компилировать исходник на Си снова не удалось.

      Не полагайтесь на декомпиляторы - они не способны восстановить исходный код.

      Дизассемблируйте, рисуйте граф кода по условным и безусловным переходам, изучайте структуру кода, распознавайте циклы for, do, while, условия циклов, break, continue и поймете логику программы. Ghidra здорово строит графы автоматически.

      Не старайтесь понять весь код сразу - изучайте небольшие функции, давайте им имена. Решайте небольшие задачи по одной: распаковать программу, сменить текст, звук, сделать персонажа бессмертным, увеличить урон колотушки до 9999.


  1. JordanCpp
    06.08.2025 08:52

    Не рекламы ради, а токмо ностальгии ради. Сам веду проект по реализации совместимой SDL3 API библиотеки в том числе и для старых систем. https://github.com/JordanCpp/SDL3Lite

    Библиотека пока в разработке. Но скоро уже первый релиз 0.1.0

    А вот если разработать библиотеку SDL3Lite совместимую со старыми системами и железом То можно разрабатывать игры или софт под новое железо и с минимальными усилиями портировать под старое.


    1. NeriaLab Автор
      06.08.2025 08:52

      Так вот, буквально недавно, несколько дней назад, на Хабре была очередная статья, где каждый желающий мог представить свои пет-проекты. Когда я в "последний раз" видел, то в ней было более 25+ комментариев от Хабровчан: 1 ответ - один пет-проект. Думаю, Вас там быстрее заметили бы


      1. JordanCpp
        06.08.2025 08:52

        Я же не рекламы ради, мой проект это мостик между старым и новым железом. Когда будет первый релиз создам новость. Я лишь привел пример. Ни в коем случае не пиарюсь.


        1. NeriaLab Автор
          06.08.2025 08:52

          Я же не против, пожалуйста, всеми лапками за :)


  1. Quester
    06.08.2025 08:52

    Есть отличный плагин к IDA для отладки в Doxbox-X. Очень помогает в изучении кода старых игр. Hex-rays в IDA, к сожалению, не умеет в реверс 16-битного кода, но зато с этим прекрасно справляется ИИ, тот же DeepSeek, особенно если ему объяснить что за игра, и если ему скармливать результаты отладки отдельных кусков кода.


    1. NeriaLab Автор
      06.08.2025 08:52

      LLM могут помочь в анализе блоков кода, с этим я не спорю, но лучше все перепроверить после "работы" LLM. Как пример, до подготовки статьи я сам специально проверял работу LLM при анализе дизассемблерного кода Раз народ ими пользуется, то я должен был это учесть. Неплохо справляются: Cursor, Qwen


      1. Quester
        06.08.2025 08:52

        Согласен. Иногда ИИ выдаёт дикую отсебятину, особенно через 10-15 запросов. Нередко, основываясь на тематике игры, ИИ решал что функция делает какую-то определённую работу, например, просчитывает поворот руля на 90 градусов (почему на 90?), и переубедить его в этом не удавалось никак.
        Но нередко подаёт какие-то годные идеи, которые оказываются верными.
        Плюс он как-то пугающе хорошо разбирает функции работы со звуковыми устройствами, описывая детально для какой это карты, почему это именно так, и как бы это улучшить.


        1. NeriaLab Автор
          06.08.2025 08:52

          Я объясню во второй части как вы точно сможете сделать то или иное, буду "вести за руку", вернее постараюсь. Конечно, часть вопросов останутся, я как и любой человек, могу что-то забыть или упустить

          Так по работе со звуком и видяшкой - так все просто же. Постараюсь это учесть и немного показать в примерах. Сложность именно в логике, а не при работе с устройствами


  1. JordanCpp
    06.08.2025 08:52

    Вы дальше будете развивать тему по дизассемблингу кода? Очень бы хотелось увидеть реальные примеры.


    1. NeriaLab Автор
      06.08.2025 08:52

      Все будет в последующих частях. Это моя сама первая публикация на Хабре, я не знал много моментов. В меня можно кидаться тапками - так я быстрее учусь. Сразу скажу, дальше будет "хуже" - будет много кода

      В этой статье я постарался акцентировать внимание на подготовку к реверсу, так как это действительно важная часть.


      1. JordanCpp
        06.08.2025 08:52

        Мы программисты, нам нужен код, чем больше тем лучше:) И плиз, побольше скриншотов, что куда тыкать.


        1. NeriaLab Автор
          06.08.2025 08:52

          Про код точно сможете не волноваться, а про скриншоты - хорошо, учту


  1. axe_chita
    06.08.2025 08:52

    DOS-игры - другое дело: нет виртуальных машин;

    Another World, квесты от Sierra и Lucas Arts с удивлением смотрят на вас ;)


    1. NeriaLab Автор
      06.08.2025 08:52

      Спасибо за критику, сегодня сам скачаю их "препарирую" их. Я в квесты не играл, совсем. На чем я учился: Commander Keen, Dune 2, Dune 2000, Syndicate, Syndicate: American Revolt, KKnD, M.A.X.(1993), M.A.X.(1996), M.A.X.2, Z


      1. axe_chita
        06.08.2025 08:52

        Это не критика, это констатация того что "нельзя объять необъятное", всегда можно что то упустить из виду.

        Советую к ознакомлению сайт Фабьена Сангларда, там вы можете почерпнуть много интересного из его анализа игр.

        Часть его статей была переведена и опубликована на Хабре, к примеру вот тут.


        1. NeriaLab Автор
          06.08.2025 08:52

          Да, эту статью я упустил из виду. Хотя меня много материала вдохновило на создание этой статьи. Примеры: "Реверс-инжиниринг ресурсов игры LHX. Часть 1" (https://habr.com/ru/articles/841614/) (unbalanced 17 сен 2024 в 14:23 ), "Занимательная некромантия 01H: ломаем программу под MS-DOS" (https://habr.com/ru/articles/932948/) (sa2304 31 июл 2025 в 18:36 )

          Полный список будет в финальной части


    1. sa2304
      06.08.2025 08:52

      Можно считать такие виртуальные машины игровыми движками?:)


      1. axe_chita
        06.08.2025 08:52

        Де факто с квестами так и было


    1. Quester
      06.08.2025 08:52

      Огромное количество игр использовало VM, это облегчало портирование на разные платформы. Да и без портирования тоже. Серия Ultima, начиная с 6 части - на отдельной VM, почти все РПГ игры SSI, - тоже.


      1. NeriaLab Автор
        06.08.2025 08:52

        Я поклонник игр разработчиков: Bullfrog (играл во все игры, которые были выпущены с 1993), Bioware, Westwood (серия игр: Dune и C&C), я не встречал у них VM. Что самое печальное, к ним, ко всем, прикоснулась "корпорация смерти" - EA. Из всех троих, до 2025 года, "дожила" только Bioware


  1. sa2304
    06.08.2025 08:52

    Супер, увлекающая статья - читал с карандашом.

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

    Игры заканчиваются, но в дизассемблирование можно играть вечно :)


    1. NeriaLab Автор
      06.08.2025 08:52

      Вы правы. Приходит понимание того как устанавливаются флаги, на что они влияют. Или начинаешь понимать разницу между условными и безусловными переходами и т.д.


  1. rabitagorgor
    06.08.2025 08:52

    О, Sourcer+RBIL - столько было времени с ними проведено, изучая потроха всякого разного ))


    1. NeriaLab Автор
      06.08.2025 08:52

      Ссылка на RBIL будет во второй части и не только она... ой.. интригу раскрыл...


  1. yamabusi
    06.08.2025 08:52

    Интересная тема,в бытность Jurassic War пытался поковырять,но больше дизайнер,кодил в детстве и потом отошёл.
    За KeeperFX отдельное большое спасибо,не знал даже о таком проекте.


    1. NeriaLab Автор
      06.08.2025 08:52

      Как сказал один хороший человек: "Привыкаешь в играх к абсолютной власти над юнитами, но юниты Dungeon Keeper живут сами по себе? Получил приказ, пошел выполнять, пока шел - забыл за чем посылали :) Видимо, нечисть древняя, забывчивая. А, может, бессмертная, потому и заряжена пофигизмом. Сегодня один начальник, завтра - другой."


      1. axe_chita
        06.08.2025 08:52

        Не, в DK/DK2 ты мог вселится в существо и порулить им в "ручном" режиме. ЕМНИП то после такого вселения существо получало буст к морали, но я могу и ошибаться. ;)

        А игра с непрямым управлением, где юниты имели "свободу воли", это Majesty: The Fantasy Kingdom Sim где юниты исполняли твои указания по принципу "Утром деньги? Вечером стулья! Вечером деньги? Утром стулья! Нет денег? Приходите когда будут"
        И вообще, по отношению к игроку, они нагло косплеят "Операцию Ы"
        "Бывалый: (грозно) Сумма?!
        Директор базы: Триста!
        Балбес: Ха!.. (замолкает)
        Бывалый: Это несерьёзно!
        Балбес: Не-не-не, так не пойдет!
        Трус: Вы нас не знаете, и мы вас не знаем.
        Балбес: Ищи дурачков!
        Трус: Я на русалках больше заработаю!
        Бывалый: Пошли, пошли!
        Трус: Курам на смех!
        Балбес: Подумаешь, триста!
        Директор базы: Стойте! Ваши условия.
        Балбес: Триста тридцать!
        Директор базы: (быстро) Согласен.
        Бывалый: Каждому!
        Директор базы (поморщившись): Согласен. С Богом."


        1. NeriaLab Автор
          06.08.2025 08:52

          А как же физическое насилие над нечистью? Рукой хлоп по попке и тот полетел вкалывать ( :) и сделал невинное личико, смотреть с 04:10)

          DK (Youtube)


  1. rabitagorgor
    06.08.2025 08:52

    Кстати, из успешных подобных кейсов рекомпиляции старых игр можно назвать проект JJFFE - пересборка для новых компьютеров третьей части элиты Frontier First Encounters.


    1. NeriaLab Автор
      06.08.2025 08:52

      https://github.com/videogamepreservation/jjffe - в архиве :(

      У этого автора - videogamepreservation - много ссылок на проекты, как публичные, так и пересобранные, под разные платформы: Atari, x86, Mac


    1. Quester
      06.08.2025 08:52

      Много лет назад познакомился с DreamZ на elite-games, предложил ему взять код этой игры и заново отреверсить. При помощи IDA Pro, Hex-Rays и крепкого словца он выкатил шикарный собственный порт, который догнали до последнего на тот момент DX, прикрутили новые модели, поправили баги.


      1. Dreamkins
        06.08.2025 08:52

        Привет Quester :D
        Было дело) 5 лет тогда ушло на проект, а звучит как будто за неделю состряпал.


        1. Quester
          06.08.2025 08:52

          Ого, вот это встреча :) Привет!
          Время неумолимо бежит вперёд, сжимаясь в воспоминаниях как архив, вот и кажется, что неделя :)


          1. Dreamkins
            06.08.2025 08:52

            Да, неожиданная встреча)
            Я периодически вспоминаю про проект. Есть желание с помощью ИИ переписать оставшееся на асме на C++ и прикрутить в качестве рендера движок UE5. Времени только нет)


            1. Quester
              06.08.2025 08:52

              Это было бы здорово! Для начала хорошо бы выложить проект на гитхаб (я кое как нашёл исходники в инете), а там, глядишь, и энтузиасты подтянутся.
              Казалось бы, через 15-20 лет время должно было появиться, а всё как раз наоборот.


              1. Dreamkins
                06.08.2025 08:52

                Честно говоря, я был уверен, что это сделает кто-нибудь из тех, кто пилил проект дальше. У меня на руках только сильно сломанный последний коммит. Его нужно привести в порядок, но он сильно отстал по прогрессу от последователей. Возможно я это сделаю, но не факт.
                Сейчас появились инструменты, которые позволяют вообще конфетку из него сделать. Ту же функцию деления треугольников, которая мне мозг сломала, я сейчас для пробы всучил дипсику на асме, он за минуту её разобрал и указал, где я допустил ошибки. Все сильно поменялось)


                1. Quester
                  06.08.2025 08:52

                  Я про это выше и писал. 20 лет назад пытался разобрать TD3, особых успехов не добился. Недавно начал сливать код DeepSeek (мы пахали, я и трактор), так с подсказками за пару дней 50 функций. В идеале, конечно, видится связка в виртуалка+ида+deepseek, последний должен в реальном времени отслеживать дебаггер. Если кто-то реализует такой инструмент, он вернёт к жизни тысячи старых игр, исходники которых были утеряны.


                  1. Dreamkins
                    06.08.2025 08:52

                    Это вопрос времени. Не пройдет и года, появится подобный инструмент. А что из этого в итоге выйдет, вот это интересно будет посмотреть)


                  1. NeriaLab Автор
                    06.08.2025 08:52

                    Не в качестве рекламы, но я делаю что-то вроде такого: "DOS Turbo Debugger for Windows" (у него даже толком названия то и нет). Умеет видеть защиту; часть зашиты умеет снимать; видит "живой" код; частично работает с самораспаковкой; ну и эмулирует работу с текстового режима 80х25 (установщик Dune 2 в нём хорошо отображается). Но там работы еще непочатый край, пример: еще не все прерывания эмулированы. Ниже пример того, как отображается в нём код - точное соответствие того, как код отображается в TD (установщик Dune 2 - первые строчки)

                    mov	dx, 2274
                    mov	cs:[0291], dx
                    je	02b5
                    mov	ah, 30
                    int	21
                    ... и т.д


                    1. NeriaLab Автор
                      06.08.2025 08:52

                      Самораспаковка "приветствует вас на борту нашего корабля":

                      mov	dx, 2274
                      mov	cs:[0291], dx

                      И это только первые строчки SETUP.EXE Dune 2

                      Я уже молчу про то, сколько раз она переписывает DS (Data Segment) и ES. "Урааа - переписываем DS... Вперёд" - строки с 8ой по 11 :\

                      mov	[007d], ax
                      mov	[007b], es
                      mov	[0077]. bx
                      mov	[0091], bp