Open-source project
bluealloy/revm avatar
bluealloy/revm

bluealloy/revm: one Rust EVM, two ways to build on it

Rust implementation of the Ethereum Virtual Machine.

2,244 stars1,025 forksRustMIT

At a glance

What is it?
revm is a Rust implementation of the Ethereum Virtual Machine that is used two different ways, as an executor you hand a block and a transaction, and as a framework that other EVM variants extend, and the README calls the second one somewhat complex to use. The details that decide whether you can depend on it are in the workspace manifest, not in the README.
Who is it for?
revm is a good fit if you need to execute transactions against a real block environment and want tracing without writing an interpreter, and a poor fit if what you actually need is a self contained EVM for tests, since the pieces it is split into are numerous and each carries its own version number.
Can I use it commercially?
Yes. MIT is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
Is it still maintained?
Yes. The repository last received commits 1 day ago.
What is it written in?
Mainly Rust, according to GitHub's language statistics.

Answers come from the project's GitHub data, last synced on October 1, 2026, and from our analysis. They are not legal advice.

Editorial analysis

The executor is three lines; the framework is the harder half

The README names two applications and the difference between them is the whole decision. As an executor, revm is a machine you configure with a block and point at a transaction, and the example is the shortest useful thing in the project:

rust
let mut evm = Context::mainnet().with_block(block).build_mainnet();
let out = evm.transact(tx);

// or you can use powerful inspection tool to trace it
let mut evm = evm.with_inspector(tracer);
let out = evm.inspect_tx(tx);

Two things are visible in those five lines. The mainnet context is constructed rather than configured field by field, so you get a populated environment without assembling one yourself, and attaching an inspector swaps the execution path rather than replacing it, which is the same call shape a tracer uses. As a framework, revm is the base that other EVM variants extend, and the project points at Optimism as the worked example of doing that. Here the README says something it does not say anywhere else in the same document, that the framework API is somewhat complex to use, and that judgement is more useful to you than a marketing sentence would be. It also points out what the framework buys, the ability to extend logic and to plug in different context types, with inspection support built in. So the split is roughly this. If you are replaying or estimating transactions against a real chain, the executor is the product and you can ignore most of the repository. If you are implementing a variant with its own opcodes, precompiles or state rules, you are taking on the framework, and the examples directory exists to show how that is done, from a custom opcode handler to a custom precompile journal.

The inspector is where tracing, cheatcodes and block traces come from

The inspector deserves its own reading because it is the feature that most downstream work actually depends on, and because the workspace manifest shows it is treated as a distinct kind of component. The crates are grouped in comments, and the inspector sits alone under a heading for variants rather than under libraries or utility. Everything else in the list is a part of executing a transaction; the inspector is the part that watches one happen. The example crates show the range of things built on that hook. There is one for block level traces, which means observing a whole block rather than a single call. There is one named for a cheatcode inspector, which is the mechanism behind the Foundry cheatcodes the README mentions, and Foundry is listed among the projects using revm, so this is not a hypothetical use. There is one for a custom opcode handler and one for a custom precompile journal, which are the two extension points an EVM variant needs. The consequence for an adopter is that adding observability does not require forking the interpreter, which is the change that would be most expensive to maintain across versions. It also means traces are a first class output rather than a debugging afterthought, and the README's phrasing about generating traces with the inspector sits alongside its mention of more complex examples of Foundry cheatcodes, which tells you the same hook is expected to carry both simple and elaborate use.

Eleven library crates and fourteen example crates, each versioned separately

The workspace manifest is the place to look before adding revm to a project, and it is more complicated than a single dependency. The member list is annotated by role: one binary, the revme tool; a group of libraries covering primitives, interpreter, precompile, database and its interface, bytecode, state, context and its interface, and handler; the inspector as a variant; two utility crates for state test types and for the Ethereum end to end tests; and then fourteen example crates, from a bare EVM example to a Uniswap v2 USDC swap. Two details have practical consequences. First, the examples are workspace members rather than loose directories, so they are compiled as part of the build, which means an example that stops working against the current API is a build failure rather than something nobody notices. Second, the internal dependencies each carry their own version, so the tree is not uniformly versioned:

toml
revm = { path = "crates/revm", version = "43.0.3", default-features = false }
primitives = { path = "crates/primitives", package = "revm-primitives", version = "43.0.0", default-features = false }

The main crate is at 43.0.3 while the primitives crate it depends on is at 43.0.0, and the database, state and interpreter crates sit at their own patch levels in between. If you depend on the top level crate that is invisible, and if you reach for a sub crate because you need one type, you are now tracking a second version number. Note also that every internal dependency is declared with default features switched off, so feature selection across the tree is explicit rather than inherited, which is deliberate and also means your feature flags are doing more work than usual.

Tags read v120, the crate reads 43.0.3, and the MSRV can move at any time

There are two numbering systems in this project and they will trip up an automated dependency update. The GitHub releases are tagged v120, v119 and v118, all published on 2026-09-24 within about eight minutes of each other, and their titles carry the crate version inside them, so v120 corresponds to revm 43.0.3 and v119 to 43.0.2. Nothing in the tag itself encodes the crate version, so a tool that reads tags and writes a dependency line will produce a version that does not exist on a registry, and a person reading the releases page has to notice that the parenthetical in the title is the real number. The release tooling in the tree, a release configuration file, is what keeps both schemes in step. The second thing is the minimum supported Rust version, and the project states its policy without hedging. Revm aims to stay on the latest stable Rust, and the MSRV may be updated at any time so that new language features can be used. For a library that means a patch release on the 43.x line can raise the compiler you need, with no major version to signal it, so a downstream project pinned to an older toolchain can be broken by an update it would classify as routine. That is a deliberate choice and a defensible one for a project that has to track a specification, but it belongs in the evaluation rather than in the fine print, especially for a build environment that is slow to update.

Correctness is argued with the Ethereum state tests and a revme binary

An EVM implementation is only worth what its conformance evidence is worth, and the project takes that seriously enough to document it as a first class activity. The book has a page on running the Ethereum tests, and the workspace includes two crates dedicated to test handling, one for state test types and one for the end to end suite, so the canonical test corpus is something the repository expects to run rather than something a contributor has to wire up themselves. The driver is revme, a binary in the workspace with a handful of commands, documented separately from the rest of the tooling. Around that sit the conventional safeguards for a Rust project that other people depend on: a continuous integration workflow, a deny configuration file for auditing dependencies and their licences, a typos configuration, and a cross compilation configuration for building on and for other targets. There is also a development container, which suggests the project is set up to be worked on from a clean environment. What the README does not provide is a conformance percentage, a list of skipped tests, or a statement about which hard forks are covered, so if your requirement is a specific specification version, that question has to be taken to the issue tracker rather than answered from the documentation. The changelog and a separate migration guide sit at the top level, and the book has a page explaining the release procedure and the changelog format, which together are the two files to read before an upgrade.

The book is a pull request target, and two agent instruction files sit at the top

Documentation here is a repository artefact rather than a website project, and the README makes that explicit by inviting pull requests when something is not explained well enough. The book configuration and its source directory are in the tree, and the pages a newcomer is pointed at are named: how to build and use revm, an architecture overview, how to use the framework, the release procedure and changelog explanation, and the page on running the Ethereum tests. The distinction the README draws between the book and the generated code documentation is the useful one, since the book explains how components fit together and the code docs explain how to call one thing, and knowing which you need saves reading the wrong one. The architecture page is listed as the best starting resource alongside the book, which is a signal that the crate structure in the manifest is not self explanatory. Two files at the top of the tree are worth a second look. There is an agent instruction file and a Claude instruction file, alongside a devcontainer and a scripts directory, so a good part of how the project expects to be worked on is now written down for tools rather than only for people. On the human side, questions go to a GitHub issue or a public Telegram group, and the list of projects built on revm is maintained in a page in the book under the name awesome-revm, grouped by role, with clients, tooling, layer 2 projects and zkVM projects each named. The value of that list is the variety of jobs the same library does, not the count.

Editorial conclusion

revm is a good fit if you need to execute transactions against a real block environment and want tracing without writing an interpreter, and a poor fit if what you actually need is a self contained EVM for tests, since the pieces it is split into are numerous and each carries its own version number. Read the choice between the two interfaces before anything else, because the executor takes three lines and the framework is what Optimism and the other variants build on, with the project itself warning that it is somewhat complex. Then settle the pinning question, since tags such as v120 and v119 correspond to crate releases 43.0.3 and 43.0.2, so a dependency line written from the wrong number of the two resolves to nothing, and since the minimum supported Rust version may be raised at any time, a patch release can require a newer toolchain than yours. Two checks are worth doing first: run the Ethereum state tests through the revme binary that ships with the project, and read the migration guide, because on a 43.x line the upgrade is where the breakage will be.

Frequently asked questions

What is the difference between using revm as an executor and as a framework?

As an executor you build a mainnet context with a block and call transact on a transaction, which is a few lines. As a framework you extend the execution logic and context types to build a different EVM variant, which is what Optimism does, and the README describes that interface as somewhat complex to use.

How do I trace transactions with revm?

Attach an inspector and use the inspection entry point instead of the plain transact call, in the form of building the machine, then adding an inspector, then inspecting the transaction. The same hook is what the block trace and cheatcode inspector examples in the repository are built on.

Which version of revm should my dependency line use?

The crate version, not the tag. Recent releases are tagged v120, v119 and v118, and their titles carry the crate versions 43.0.3, 43.0.2 and 43.0.1. Sub crates carry their own patch levels, so the primitives crate is at 43.0.0 while the top level crate is at 43.0.3.

What Rust version does revm require?

The project states that it aims to stay on the latest stable Rust release and that the minimum supported Rust version may be updated at any time, in order to use new language features. In practice that means a patch release can raise the compiler requirement without a major version change.

How is revm verified against the Ethereum specification?

The repository ships a binary called revme with commands for running the tests, and the workspace includes crates for state test types and for the end to end suite, so the canonical test corpus is expected to be run in the project. The README does not publish a conformance figure or a list of skipped tests.

Official sources

  1. bluealloy/revm on GitHub
  2. License: MIT
  3. Project website
  4. README
  5. Releases
Add this badge to your README

If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.

Add this badge to your README

markdown
[![Hysen Labs](https://hysenlabs.com/badge/bluealloy-revm.svg)](https://hysenlabs.com/projects/bluealloy-revm)