Blog / Technical

Why We Support Both EVM and Wasm

Technical2024-03-10·8 min read·By Dev Team

Selendra is built on the Substrate framework. One of the key benefits of this architecture is the ability to compose different runtime modules (pallets) to create a chain that suits specific needs.

We chose to include both pallet-contracts (for WebAssembly) and pallet-evm (for Ethereum compatibility). This isn't a unique invention of ours; it's a configuration choice enabled by the modular design of Substrate and the work of the Frontier project.

Why Two Virtual Machines?

Different applications have different requirements. By enabling both modules, we allow developers to use the tools they are most comfortable with.

WebAssembly (Wasm)

Wasm is the native smart contract environment for the Polkadot ecosystem.

Why we included it:

  • Performance: Wasm is designed for near-native execution speed.
  • Language Support: Developers can write contracts in ink! (Rust), which offers strong type safety.
  • Future Proofing: The broader industry is moving towards Wasm for high-performance computing.

Example Wasm Contract (Rust/ink!)

#![cfg_attr(not(feature = "std"), no_std)]

use ink::prelude::*;

#[ink::contract]
mod simple_storage {
    #[ink(storage)]
    pub struct SimpleStorage {
        stored_data: u128,
    }

    impl SimpleStorage {
        #[ink(constructor)]
        pub fn new() -> Self {
            Self {
                stored_data: Default::default(),
            }
        }

        #[ink(message)]
        pub fn set(&mut self, value: u128) {
            self.stored_data = value;
        }

        #[ink(message)]
        pub fn get(&self) -> u128 {
            self.stored_data
        }
    }
}

EVM (Ethereum Virtual Machine)

The EVM needs no introduction. It is the standard for decentralized applications today.

Why we included it:

  • Compatibility: We use the Frontier project's EVM pallet to ensure full compatibility with existing Ethereum tools.
  • Tooling: Developers can use Hardhat, Foundry, and Remix without needing to learn new workflows.
  • Libraries: Access to OpenZeppelin and other standard Solidity libraries.

Example EVM Contract (Solidity)

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.19;

contract SimpleStorage {
    uint256 private storedData;

    event DataStored(uint256 indexed newValue, address indexed caller);

    function set(uint256 _value) public {
        storedData = _value;
        emit DataStored(_value, msg.sender);
    }

    function get() public view returns (uint256) {
        return storedData;
    }
}

How It Works

Selendra runs these two environments side-by-side.

  • Isolation: They share the same consensus and block space but execute in different runtime environments.
  • Interoperability: Through our Unified Accounts implementation (another standard pattern), users can interact with both environments using a single account.

Choosing Your Tool

  • Use Wasm (ink!) if you are building a new project from scratch and want to leverage Rust's safety and performance.
  • Use EVM (Solidity) if you are migrating an existing dApp or want to use the vast ecosystem of Ethereum tools.

Conclusion

Our goal is not to force a specific workflow but to provide a platform where developers can build. By integrating these standard open-source modules, we hope to lower the barrier to entry for building in the Selendra ecosystem.