Хабрахабр

Виртуальная машина на ESP8266 для запуска игр

VM, написанная неуверенной рукой гуманитария в среде программирования Arduino с использованием быдлокода и велосипедов. А еще есть компилятор для нее из си-подобного языка, написанный на JavaScript теми же методами. Да. Уже можно спешить в комментарии, бросать камни. Ну а тех, кому все же интересно, приглашаю продолжить чтение.

Но на тот момент был скорее сферический в вакууме прототип. Троллейбус из буханки
В общем-то мою поделку уже немного осветил уважаемый tormozedison вот тут. Зовется сие устройство ESPboy. А сейчас у меня появилось устройство работы RomanS, которое он любезно предоставил мне для опытов совершенно безвозмездно. Тут о нем можно узнать больше. От остальных поделок оно отличается компактностью и слотом расширения, использующим микросхему MCP23017.

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

Предыстория

Когда-то в школе я увлекся гейммэкером от йойогеймс, и, как многие, клепал на нем не пойми что. Этими криво написанными и плохо нарисованными демками еще можно было похвастаться друзьям, но в интернете они тонули среди похожих. Я понял, как тяжело самому написать даже простую игру, не говоря уже о серьезной, в которой можно было бы грабить корованы. Но желание писать игры не пропало. Когда у меня появился мобильный телефон, я открыл для себя Midlet Pascal и несколько лет развлекался им. Ведь я понимал, что написать игру для слабого устройства проще, чем для его более мощного большого брата. По крайней мере, всегда можно было бы говорить не о кривых руках, а о ограниченных возможностях платформы. Однако кнопочники сменились сенсорами очередной шанс завоевать мир был упущен. Все же, в какой-то момент я понял, что могу возродить свои мечты, используя микроконтроллер.

Тогда она у меня была единственная, и я очень волновался за ее работоспособность. Начал я с написания игры под ардуино уно, куда же без нее. Но путь граблей идется маленькими шажками. Старался прошивать как можно реже. И я решил написать стековую виртуальную машину. Каждая небольшая правка кода заставляла прошивать снова и снова. Но какой же она была медленной, а памяти почему то постоянно не хватало. Как-никак на борту огромные два килобайта оперативной памяти для байт кода и данных. Тогда я решил написать эмулятор chip-8 на только что пришедшую из Китая ардуино мега. Наверное, все дело в том, что все мои велосипеды были с квадратными колесами и медленно ехали. В результате я понял главное. Конечно же, потом я хотел написать для нее же еще и эмулятор геймбоя, первой плейстейшн и какого-нибудь суперкомпьютера попроще. Настолько, что при написании своих игр для умножения или деления приходилось писать отдельную медленную подпрограмму. Виртуальная машина chip-8 была очень простой, чрезмерно простой. В это время еще и несколько esp8266 приехало, со своими космическими 160MHz.
А значит нужно написать свою VM, избавившись от фатального недостатка.

Если вам кажется, что виртуальная машина это пустая трата ресурсов, то я еще и переписал под нее свой эмулятор chip-8. Получилась виртуальная машина в виртуальной машине на микроконтроллере. Наверное, можно пойти дальше, и написать машину тьюринга на chip-8.

Технические характеристики ESP Little Game Engine

Виртуальная машина содержит 16 регистров по 16 бит, нулевой регистр является указателем стека. Каждая инструкция двухбайтовая, некоторые инструкции содержат после себя два байта данных. Адресуемая память 64KB. В случае ESP8266 доступно 20KB. Возможна загрузка программы из SPIFFS и UART. При желании можно добавить загрузка с карты памяти или через WiFi. Кроме обычных арифметических инструкций и инструкций перемещения данных, есть отдельные инструкции для работы со спрайтами, экраном и звуком. Размер экрана 128 на 128 пикселей. При 16 цветах на точку экран занимает 8KB памяти, еще столько же занимает буфер для рисования спрайтов и частиц. Хоть используемая мной библиотека TFT_eSPI способна обновлять экран более 60 раз в секунду, пришлось ограничиться 20 кадрами в секунду. Иначе не хватало процессорного времени для виртуальной машины. Можно рисовать тайлы и 32 спрайта размером до 128х128 пикселей с возможностью вращения и зеркалирования. Для экономии памяти можно использовать однобитные изображения или RLE сжатие. Присутствует упрощенная физика: обнаружение столкновений спрайтов со спрайтами и тайлами, разрешение столкновений, гравитация. Экран обновляется построчно, только если в строке произошло изменение пикселей. Скорость VM в зависимости от того, сколько строк отрисовывается в кадре, варьируется от 100 тысяч до 900 тысяч операций в секунду. Можно использовать разные цветные экраны, есть софтовое растягивание изображения до нужных пропорций.


Некоторые игры, из написанных мной, можно посмотреть тут.

Что бы не редактировать байт-код вручную, был добавлен простенький ассемблер, основанный на моем опыте с ассемблером для MOS6502. Одновременно с VM для ESP8266 я писал эмулятор на JavaScript для браузера. Все же моей основной задачей было быстрое написание простых игр, а не долгая отладка ассемблерного кода. Затем я решил добавить язык более высокого уровня. И я написал его на JavaScript, так как знаю его не так плохо, как другие языки. Мне показалось, что написать свой компилятор будет проще, чем добавить LLVM. Зато он быстр, ведь он занимает меньше 2000 строк. На данный момент ему далеко до поддержки стандартов C и при компиляции можно легко столкнуться с непонятной ошибкой в непонятном месте.

Уже сейчас можно писать и запускать игры. А теперь к вопросу, зачем я вообще все это здесь написал. Если кто захотел мне помочь в доработке ESP LGE, или написать свою собственную игру, то я буду очень рад. Однако до совершенства еще далеко. Предупреждаю, код для Arduino довольно сложно читать. Если Вам моя идея показалась интересной, и Вы хотите узнать больше, то я с радостью отвечу на интересующие вопросы. Отчасти из-за того, что я попытался уменьшить количество вызовов функций, для увеличения скорости работы. Отчасти из-за того, что я самоучка. Так что не подпускайте к экрану беременных и детей. В результате многие функции содержат огромные портянки кода. Постепенно я постараюсь это исправить и улучшить читаемость.

Занимает меньше ста строк и меньше 1KB в скомпилированном виде. А для тех, кто дочитал, пример игры.

int stickCount;
char key,previouseKey,takenSticks; void redraw(){ int i; //выбираем красный цвет setcolor(2); //рисуем видимые палочки for(i = 0; i < stickCount; i++) line(22 + i * 6, 74, 22 + i * 6, 84); //выбираем серый цвет setcolor(11); //рисуем выброшенные for(i = stickCount; i < 15; i++) line(22 + i * 6, 74, 22 + i * 6, 84); //возвращаем белый цвет как основной setcolor(1); //ждем перерисовки экрана delayredraw();
} void playersMove() while(key != KEY_LEFT && key != KEY_DOWN && key != KEY_RIGHT){ key = getkey(); } if(key & KEY_LEFT){ takenSticks = 1; }else if(key & KEY_DOWN){ takenSticks = 2; }else{ takenSticks = 3; } printf("%d, ", takenSticks); stickCount -= takenSticks; previouseKey = key;
} void computersMove(){ if(stickCount % 4){ //компьютер реализует выигрышную стратегию, если выпала возможность takenSticks = stickCount % 4; }else{ //компьютер ждет возможности реализовать выигрышную стратегию takenSticks = 1 + random(1); } stickCount -= takenSticks; printf("%d, ", takenSticks);
} void game(){ //инициализация stickCount = 15; clearscreen(); //переводим каретку на восьмой символ нулевой строки gotoxy(8,0); puts("Баше"); gotoxy(2,1); puts("Возьмите 1,2 или 3 палочки. Проигрывает тот, кому нечего брать. Управление:\n"); //коды 27,25 и 26 соответствуют стрелкам printf(" %c 1 %c 2 %c 3", 27, 25, 26); gotoxy(0,12); redraw(); while(1){ playersMove(); if(stickCount <= 0){ gotoxy(3,8); puts("Вы выиграли"); return; } redraw(); computersMove(); redraw(); if(stickCount <= 0){ gotoxy(3,8); puts("Компьютер выиграл"); return; } }
} void main(){ while(1){ game(); //ждем секунду settimer(1,1000); while(gettimer(1)){} while(getkey() == 0){} previouseKey = key; }
}

Можно сразу и протестировать. Перейдите по ссылке, затем нажмите compile, затем run. Если хотите узнать больше о возможностях IDE можно почитать туториал. Спасибо за внимание.

Теги
Показать больше

Похожие статьи

Добавить комментарий

Ваш e-mail не будет опубликован. Обязательные поля помечены *

Кнопка «Наверх»
Закрыть