Хочешь попрактиковаться в кодинге на ассемблере? Давай вместе шаг за шагом создадим игру и запустим ее прямо из загрузочного сектора твоего компьютера. Если ты думаешь, что 512 байт маловато для полноценной игры, не спеши с выводами. К концу статьи ты сможешь сделать ее своими руками!

Да, затолкать что-то вразумительное в 512 байт загрузочного сектора — та еще задачка. Бутсекторная программа выполняется до запуска операционной системы, а значит, функции ОС ей недоступны.

Даже для такого, казалось бы, простого действия, как вывести число на экран, придется писать свою собственную подпрограмму. Кроме того, забудь о высоком разрешении экрана, простом и удобном доступе к GPU и звуковой карте. А еще учти, что BIOS, выполняя бутсекторную программу, смотрит на процессор твоего Ryzen или Core i9 как на примитивный 16-битный 8088.

Вводные не очень-то обнадеживают! Но базовые функции BIOS у нас никто не отнимал. Мы можем выводить текст, рисовать крупноразмерные пиксели, читать системный таймер, следить за клавиатурой. Этого вполне хватит для несложной игрушки!

На случай, если ты пропустил шумиху в 2013 году, поясню смысл игры. Летящая слева направо по экрану птаха должна облетать торчащие снизу и сверху экрана трубы. Если игрок ничего не делает, она самопроизвольно снижается. Нажатие на кнопку заставляет ее взмахнуть крыльями и немного подняться вверх. Секрет в том, чтобы соблюдать нужный ритм и не врезаться. Вот и вся игруха.

А теперь возьмемся за реализацию!

 

Подготовка

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

Делаем еще несколько подготовительных телодвижений:

  • переходим в текстовый режим 25 × 80 и очищаем экран;
  • сбрасываем «флаг направления», чтобы строки обрабатывались слева направо, а не наоборот (когда будем обращаться к инструкциям вроде stosw);
  • сегментные регистры нацеливаем на область оперативной памяти, которая отображена на видеопамять. Так нам будет удобней отрисовывать игровое поле.

Инициализируем переменные. При этом стараемся сэкономить количество используемых байтов. Когда мы сначала помещаем нужное нам значение в AX, а затем через stosw присваиваем его очередной переменной, получается меньше байтов, чем когда мы самостоятельно инициализируем каждую переменную. Особенно когда присваиваем одинаковые значения — как два нуля вначале.

Надо дать игроку успеть приноровиться к управлению, поэтому первую трубу отрисовываем только после 160-го кадра. В next запишем число 160 (0xA0) и пишем не mov ax, 0x00A0, а mov al, 0xA0. Нам, конечно, важно, чтобы в AH был ноль, но мы точно знаем, что он и так уже там, поэтому тратить целый байт на повторное обнуление мы не будем.

Продолжение доступно только участникам

Материалы из последних выпусков становятся доступны по отдельности только через два месяца после публикации. Чтобы продолжить чтение, необходимо стать участником сообщества «Xakep.ru».

Присоединяйся к сообществу «Xakep.ru»!

Членство в сообществе в течение указанного срока откроет тебе доступ ко ВСЕМ материалам «Хакера», увеличит личную накопительную скидку и позволит накапливать профессиональный рейтинг Xakep Score! Подробнее

Check Also

Игры с неведомым. Как устроены хакерские квесты и почему от них тяжело оторваться

Любопытство — это ключ к совершенству. Один из способов задействовать силу любопытства — х…

4 комментария

  1. Аватар

    Garta

    24.03.2020 at 00:35

    Не возникло желание повторять увиденное, но выглядит очень, очень, очень впечатляюще!

  2. Аватар

    Laglag

    24.03.2020 at 11:32

    Подскажите какой компилятор использовать для асемблера, что бы повторить?

Оставить мнение