Posted on 2021-11-01

It's been almost a year since we announced Fe as a new EVM language and stated its goals. Today we would like to reflect on where Fe currently stands, its path to production, and a possible timeline for it.

Fe is still in early stages of development and all of our releases are marked as alpha. This means that the software being provided is only partially complete. For instance, the current release is v0.8.0-alpha "Haxonite" and comes with a warning that strongly discourages use beyond just tinkering with the language.

Having said that, we feel confident that we can move past this alpha stage and into a beta stage before the end of 2021. In the following section, we will discuss this beta release in further detail and provide a rough idea of where we will go from there.

Defining our beta release goals

Development of a programming language is a marathon, as there exist many features to implement and tools to build. Fully realizing our current goals will take a long time, so we would rather not let this hinder the release of a usable compiler. For this reason, we are making an effort to cut a release in the near term that can be used in production safely and practically. We call this our beta release. In this section, we will define what should be expected from this beta release.

Beta non-goals

Before we dive into any specific beta goals, let us give some explicit NON-GOALS. Without further ado, here are the things one should NOT expect from our first beta release.

Feature stability

Languages should strive for a release policy which ensures that code written in the language doesn't need to be re-written every time the compiler is updated. Having said that, Fe is far from guaranteeing such a thing, so the first beta release will not be considered stable. This means that developers should expect breaking changes between beta releases. These changes should appear less-frequently over time, though.

We follow semver, so stability will be indicated by our first non-zero major version (i.e. 1.0.0). From this version on, breaking changes may only be included in major updates.

Feature completeness

Based on what's written above, one can probably gather that feature completeness is also not a beta goal. We want to emphasize that some important features will be missing, which may hinder development. Be warned!

Here are some of the features that we are excited about, but won't make it into the first beta release:

  • Support for generics over types and constant values
  • Rust style error handling via Result<V, E>
  • Traits for structs and interfaces for contracts

These features may be included in our first stable release, though.

Optimal gas efficiency

In these early stages of development, we have focused more on delivering features rather than minimizing the amount of gas consumed during runtime. We do get some efficiency gains for free from the Yul optimizer, but there are still some simple optimizations that could be performed in the Yul generation phase that are currently not performed.

Actual beta goals

Now that we've explained what you shouldn't expect from our first beta release, let's turn to the actual goals.

Compiler correctness

Smart contracts created using Fe should behave as expected; in other words, the compiler needs to be implemented correctly. If it is not, development teams will have a hard time justifying the use of Fe in their projects. Here we'll discuss the methods used to validate the correctness of the Fe compiler and how we'll demonstrate to the community that these methods have been effective.

First, let's discuss important aspects of the compiler that need to be correct.

Source code validation: The compiler should reject any invalid source code. Code generation: Code generated by the compiler should have the same meaning as the source code. Runtime checks: Values are checked during runtime (e.g. arithmetic overflow, ABI decoding, and array index out of bounds). This is done to prevent undefined runtime behavior.

To make reasoning about the compiler and testing it easier, we've separated compilation into multiple phases. These phases are: static analysis, lowering, Yul generation, and bytecode generation.

Below, we'll discuss the various methods used to validate the behavior of each phase and the whole compiler.

Snapshot Testing: is used to assess the output of each phase and to guarantee regressions don't go unnoticed. Integration testing: Fe source files are written every time a feature is added and are tested using rust-evm. We also run tests against more complicated contracts, like our UniswapV2 demo. Runtime function testing: Yul functions added to the runtime are tested directly on rust-evm. Compilation fuzzing: A continuously running service tries to find crashes in the compiler by invoking it with randomly generated Fe source code. This finds nuanced errors in both source validation and code generation. You can find the fuzzer here. Unit testing: Simple components are validated with unit tests.

Having compilation separated into multiple phases and testing each phase is great, but it alone does not gain trust from the community. In order to do so, the compiler will need to be put to the test. This will of course come naturally with time and use on mainnet, but the initial attempts to find flaws will need to be incentivized. Here are two ways we could incentivize people to find flaws:

  • Have a security firm audit the codebase.
  • Host community bug contests.

Currently, the plan is to start offering bug bounties before the end of the year. These bounties will be open on certain alpha releases and the objective will be to find severe bugs. If this program does not find any serious vulnerabilities within a given timeframe, we will confidently remove the alpha suffix from new releases and use beta in its stead.

When we arrive at a stable release (1.0.0), we might get the codebase audited. This, however, is probably 1-2 years out.

It's also worth mentioning that the Yul IR generated during compilation may be exported and audited on its own. This means that one can verify the behavior of their contract without relying on the Fe compiler.

Developer UX

We are currently working with contributors from the Fe community to make sure Fe is supported by popular tools that are used within the Ethereum smart contract developer community.

We already have some work in progress candidates for some tooling that we believe will become quite important going forward. Shout out to Marek who's been on fire lately to get these off the ground. 🔥

  • fejs - JavaScript bindings for the Fe compiler
  • vscode-fe Fe language support for Visual Studio Code
  • hardhat-fe Fe support for Ethereum's popular development environment hardhat

While all of them are in very early development stages we encourage you to take a look or get involved. We are happy to provide some funding on a per task/project basis for substantial contributions.

Documentation & Spec

We have been working to fill the gaps in our documentation and language specification. Improvement of these resources will continue, with the goal of fully-specifying the language and making the compiler very accessible.

While there is still some uncertainty around the exact timing, we feel reasonably confident in saying that we will deliver a beta release in Q4 of 2021 that meets the expectations laid out in this post.

We are excited to see what the community will start building on and around Fe when that happens.