Я хочу створити віртуальну машину, чи є хороші посилання? [зачинено]


22

Я хочу створити віртуальну машину як незалежний від платформи спосіб запустити якийсь ігровий код (по суті, сценарій).

Віртуальні машини, про які я знаю в іграх, досить старі: Z-Machine Infocom , LucasArts ' SCUMM , id Software's Quake 3 . Як розробник .net, я знайомий з CLR і вивчив інструкції CIL, щоб отримати огляд того, що ви реально реалізуєте на рівні VM (порівняно з мовним рівнем). Я також трохи запитався в 6502 Assembler протягом останнього року.

Справа в тому, що тепер, коли я хочу це здійснити, мені потрібно копати трохи глибше. Я знаю, що існують VM на основі стека та реєстру, але я дійсно не знаю, який з них краще в чому і якщо є більше або гібридні підходи. Мені потрібно розібратися з керуванням пам’яттю, вирішити, які типи низького рівня входять до складу ВМ, і мені потрібно зрозуміти, чому такі речі, як ldstr, працюють так, як це відбувається.

Мій єдиний довідник (крім матеріалів Z-Machine) - це Анотований стандарт CLI , але мені цікаво, чи є краща, більш загальна / фундаментальна лекція для ВМ? В основному щось на кшталт Книги Драконів , але для візиток? Мені відомо про мистецтво комп’ютерного програмування Дональда Кнута, яке використовує VM на основі реєстру, але я не впевнений, наскільки застосовна ця серія досі, тим більше, що вона ще недобудована?

Роз'яснення: мета полягає у створенні спеціалізованого ВМ. Наприклад, Z-Machine Infocom містить OpCodes для встановлення кольору фону або відтворення звуку. Тому мені потрібно розібратися, скільки йде в VM як OpCodes проти компілятора, який бере сценарій (мова TBD) і генерує з нього байт-код, але для цього мені потрібно зрозуміти, що я насправді роблю.


¹ Я знаю, сучасна технологія дозволить мені просто інтерпретувати мову сценаріїв на високому рівні. Але де в цьому веселощі? :) Це також трохи важко в Google, тому що віртуальні машини в наш час часто асоціюються з віртуалізацією ОС VMWare типу ...


6
зауважте, що для того, щоб машина на основі стека була міцною, вона потребує пам'яті поза стеком, інакше це просто КПК
урожай храповика

1
Перше питання: як далеко ви хочете зайти? Я ніколи не дивився на SCUMM / SCUMMVM, але припускаю, що це досить високий рівень знань про графічні речі, що рухаються і т.д. тобто інструкції по асемблеру), а потім перша версія VM - це цикл, do { switch(opcode) {case OP1: ... case OP2: ...} while (nextop);потім, можливо, компілятор ... і тоді починається задоволення - оптимізація для того, щоб вона фактично працювала
johannes

3
Спробуйте почати з впровадження простого виконання Forth.
SK-логіка

1
Як саме це Quake 3віртуальна машина?
Рамхаунд

3
@Ramhound мотори id технологій давно використовують певну форму внутрішньої віртуалізації, ця стаття або інформація Вікіпедії можуть пояснити краще.
Даніель B

Відповіді:


18

Я б почав з перевірки Луї . І як вибіркова реалізація, і як дуже зручна VM / мова поза коробкою, якщо ви нарешті вирішите не скочувати свою.

Вихідний код дуже читабельний, а також є Анотований вихідний код . І деякі проектні документи, написані головним автором, Роберто Ієрусалімщі.

Нарешті, якщо ви вирішите використовувати його замість власного, ви виявите, що він давно був улюбленим серед розробників ігор, і реалізація JIT дуже висока .

Стосовно стека проти реєстру, я думаю, що VM на основі стека спрощені, але компілятор може бути складнішим. Як зазначається в документі Iesualimschy, Lua був одним з перших віртуальних машин на основі реєстру, але згодом з'явилося кілька інших, особливо це стосується LLVM, Dalvik та деяких сучасних віртуальних машин JavaScript.


2
Про машини стека проти реєстру: я пам’ятаю цитату Parrot / Perl6 devs: «побудувати машину на основі реєстру важче, але ми отримуємо користь від тонни існуючих досліджень для нашої компіляторної сторони» (не буквально)
johannes

+1 Lua має чудову реалізацію байт-коду та дуже чіткий дизайн для вивчення віртуальних машин від. Крім того, ви побачите, що багато людей підганяли Lua для власних потреб, показуючи, що це досить розширюється, якщо ви не хочете починати з нуля.
CodexArcanum

Все ще переживаю це. Ще один чудовий документ від розробника про VM: inf.puc-rio.br/~roberto/talks/lua-ll3.pdf
Michael

2

На даний момент я не маю жодних конкретних ресурсів, з якими можна зв’язати вас, але я досліджував подібну тему в минулому і виявив, що Smalltalk VM також є хорошим навчальним посібником. Існує багато наукових праць та статей про байтові коди, які використовуються Smalltalk, а також написання перекладачів та віртуальних машин для використання цього байтового коду. Пошук у Google smalltalk vm implementationчи smalltalk bytecode interpreterповинен отримати багато читального матеріалу.

Якщо ви хочете переглянути якийсь вихідний код або спробувати реалізацію, я рекомендую версії Squeak або Pharo.

Зв'язана мова / VM Self також може вас зацікавити, оскільки Self - це в основному Smalltalk з об'єктами на основі прототипу (схожий на JavaScript).


0

Я б почав з аналізу того, як [скрипт] вихідного коду потрапляє у вашу машину чи середовище виконання.

Якщо у вас є щось на кшталт документів HTML, <a onclick="dosomething();">вам знадобиться дуже швидкий компілятор, швидкість виконання байт-коду насправді не має великого значення в цьому випадку. Якщо випадки використання ближче до Java / .NET, де ви можете дозволити повноцінну компіляцію, то архітектура VM та структура байт-коду будуть ближчими байт-кодами Java або IL.

Ще один критерій - це те, що я називаю «клейкості». Спочатку сценарії розроблялися як мови клею - скрипти просто визначають спосіб з'єднання різних нативних функцій разом (Perl, Python, Ruby, JS). У цьому випадку ефективність VM та байт-коду набагато менш важлива, ніж у випадку Java / .NET, коли більшість вашого коду - це функції, написані на самій мові.

І останній головний критерій, який я б використав, - це розширюваність вашої мови. Якщо ви плануєте додати до мовного виконання багато рідних об'єктів / функцій, реалізованих, скажімо, на C ++, то ваша архітектура VM повинна бути "зручною" для інтеграції з C ++. Наприклад: якщо ви плануєте піддавати скриптам об'єкти C ++ такими, якими вони є, то єдиним варіантом для вас буде вважати посилання на керування купою (як Python, див. Приклад інтеграції: boost :: python). Якщо ви плануєте використовувати рухому / ущільнювальну купу / GC, це буде інша історія. Спосіб додавання рідних матеріалів до програми Lua трохи складний [для розробників C ++].

Іншими словами, спробуйте визначити спочатку свій типовий варіант використання, і вам буде простіше запропонувати, що вам прочитати.


1
Сучасні компілятори JavaScript є досить складними, і все-таки є питання, яка оптимізація створеного коду ви вводите.
johannes

Продуктивність виконання Javascript має значення. Не для крихітних сценаріїв, а для великих JS-важких сайтів, які в кращу чи гіршу сторону становлять значну частину більш популярних сайтів. Існує причина, що JS-двигуни використовують компілятори JIT (у V8 навіть немає перекладача, це іде безпосередньо до машинного коду).

@delnan: Випадок використання JS сильно відрізняється від, скажімо, Python. У Python, коли вам потрібно щось на зразок реалізації алгоритму відстеження променів, ви будете робити рідну бібліотеку і викликати її з скрипту. Це завжди буде швидше (або принаймні не повільніше), ніж будь-яке рішення JIT. У царині JS у вас немає такої розкоші, як рідний код, тому єдиний варіант для вас - спробувати зробити свій JS VM якомога швидшим. Але знову ж таки, з ціною. Оцінка "dosomethingnative ()" в HTML "<button onclick =" dosomethingnative () "> у простому інтерпретаторі може бути на порядок швидше, ніж у V8.
c-smile

@ c-smile Моя річ точно.

@delnan: але моя суть зовсім інша: проаналізуйте випадки поширеного використання і лише тоді ви можете вирішити, яку архітектуру VM, синтаксис мови тощо вам знадобиться.
c-smile
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.