Self-Hosted EVM

close button

Part I


Download quests in Questplay

The EVM (Ethereum Virtual Machine) constitutes several components, namely the stack, memory, state, instruction set, and interpreter. In this quest, we will see how all these moving parts come together by building an almost-complete EVM in a smart-contract. An EVM within an EVM!

Note that our naively implemented recursive EVM will be absurdly impractical in the real world. But, building one is still an amusing way to learn about the EVM!

Our self-hosted EVM (sEVM) will be able to deploy new contracts and execute bytecode. It will also support cross-contract interaction. However, it will not support event logging, gas metering, and self-destructs.

Instructions and Opcodes

In a computer, an instruction is a basic unit of execution, like a command that tells the computer to perform a certain primitive task. Instructions are encoded into opcodes and can take in parameters, just like high-level computer functions. Combined, a series of opcodes and parameters forms a program.

In the EVM, programs manifest themselves as the bytecode of smart contracts. Opcodes are 1-byte values, whereas parameters are 32-byte long. As we will soon see, each EVM opcode instructs the EVM on how to manipulate the different components of the EVM; stack, memory, and storage.

For instance, `0x01` is the opcode for the `ADD` instruction. You can find a comprehensive list of the different EVM opcodes here.

With a better understanding of what a computing machine is, we begin building our EVM with two pre-defined components, State and Interpreter.

The State

The State contract (found in State.sol) manages the world state of the EVM, tracking accounts and their storage. The contract also contains some useful functions that read and write onto the sEVM's State.

The Interpreter

At the core of the EVM sits the interpreter. At a high level, the interpreter reads bytecode opcode-by-opcode and executes the read instructions (i.e., subroutines). The instruction will interact with the Stack, Storage, and State (i.e., the execution scope) as needed.

Reading is done by maintaining a Program Counter (PC) which is an index that tracks the next opcode to read.


For every opcode, the associated instruction is executed and the PC is incremented to point to the next opcode


Your Task

Study contracts/State.sol and contracts/Core.sol, and briefly convince yourself how they implement the sEVM's state and interpreter respectively.

Long ago, the first mages discovered the Weave and worked out how to harness its power, ushering in the age of Wild Magic…