Я написал виртуальную машину на C, которая имеет приличную производительность для не-JIT VM, но я хочу изучить что-то новое и улучшить производительность. Моя текущая реализация просто использует переключатель для перевода из байт-кода виртуальной машины в инструкции, которые компилируются в таблицу переходов. Как я уже сказал, достойная производительность, какая она есть, но я столкнулся с барьером, который можно преодолеть только с помощью JIT-компилятора.
Я уже недавно задавал подобный вопрос о самомодифицирующемся коде, но я понял, что не задаю правильный вопрос.
Итак, моя цель - написать JIT-компилятор для этой виртуальной машины C, и я хочу сделать это в сборке x86. (Я использую NASM в качестве моего ассемблера) Я не совсем уверен, как это сделать. Я хорошо разбираюсь в ассемблере, и я просмотрел несколько примеров самоизменяющегося кода, но я пока не пришел, чтобы понять, как сделать генерацию кода.
Пока мой главный блок - копирование инструкций в исполняемый фрагмент памяти, с моими аргументами. Я знаю, что могу пометить определенную строку в NASM и скопировать всю строку с этого адреса со статическими аргументами, но это не очень динамично и не работает для JIT-компилятора. Мне нужно иметь возможность интерпретировать инструкцию из байт-кода, скопировать ее в исполняемую память, интерпретировать первый аргумент, скопировать в память, затем интерпретировать второй аргумент и скопировать в память.
Мне сообщили о нескольких библиотеках, которые облегчили бы эту задачу, таких как GNU Lightning и даже LLVM. Однако я хотел бы сначала написать это вручную, чтобы понять, как это работает, прежде чем использовать внешние ресурсы.
Существуют ли какие-либо ресурсы или примеры, которые это сообщество может предоставить, чтобы помочь мне начать выполнение этой задачи? Простой пример, показывающий две или три инструкции, такие как «add» и «mov», используемые для генерации исполняемого кода, с аргументами, динамически в памяти, может творить чудеса.