2024.10.08

OptimismのICrosschainERC20紹介

こんにちは。次世代システム研究室のT.M です。

注意

本稿は2024/10/8 時点の情報です。情報が更新されていることがありますので、ご注意ください。

はじめに

先日、Ethereumの開発者のVitalik氏がXにおいて、ICrosschainERC20のインターフェースを紹介していました。これは、L2におけるERC20の新しいインターフェースであり、中立的にmint、burnをすることでUXを向上させるものです。ICrosschainERC20はEthereumのエコシステムの統一の一環であり、Vitalk氏はEthereumの開発者たちに協力を呼びかけていました。本稿では、ICrosschainERC20と、Optimismにおいて実装したSuperchainERC20の変更点を説明します。

既存のSuperchainERC20

SuperchainERC20はOptimismにおけるERC20トークンのコントラクトです。通常のERC20にsendERC20()relayERC20() を追加したものです。

function sendERC20(address _to, uint256 _amount, uint256 _chainId) external virtual {
    if (_to == address(0)) revert ZeroAddress();

    _burn(msg.sender, _amount);

    bytes memory _message = abi.encodeCall(this.relayERC20, (msg.sender, _to, _amount));
    IL2ToL2CrossDomainMessenger(MESSENGER).sendMessage(_chainId, address(this), _message);

    emit SendERC20(msg.sender, _to, _amount, _chainId);
}

function relayERC20(address _from, address _to, uint256 _amount) external virtual {
    if (msg.sender != MESSENGER) revert CallerNotL2ToL2CrossDomainMessenger();

    if (IL2ToL2CrossDomainMessenger(MESSENGER).crossDomainMessageSender() != address(this)) {
        revert InvalidCrossDomainSender();
    }

    uint256 source = IL2ToL2CrossDomainMessenger(MESSENGER).crossDomainMessageSource();

    _mint(_to, _amount);

    emit RelayERC20(_from, _to, _amount, source);
}

sendERC20() はユーザーがトークンを別チェーンに送信したい時に実行する関数です。トークンをburnして、指定したチェーンのrelayERC20() を実行します。

relayERC20() は別のチェーンのトークンコントラクトからトークン送信依頼を受信する関数です。リクエストに応じて、トークンをmintします。

クロスチェーンにおけるブリッジ機能がERC20に付随しています。

ICrosschainERC20

ICrosschainERC20はクロスチェーンのためのERC20トークンのインターフェースです。__crosschainMint()、__crosschainBurn() の関数があります。__crosschainMint() は、クロスチェーンでトークンを受信してmintする際に呼び出す関数であり、__crosschainBurn() は、トークンを送信してburnする際に呼び出す関数です。

interface ICrosschainERC20 {
    event CrosschainMinted(address indexed to, uint256 amount);
    event CrosschainBurnt(address indexed from, uint256 amount);

    function __crosschainMint(address _to, uint256 _amount) external;
    function __crosschainBurn(address _from, uint256 _amount) external;
}

修正されたSuperchainERC20

修正されたSuperchainERC20では、sendERC20()relayERC20() がなくなり、__crosschainMint()、__crosschainBurn() が実装されています。sendERC20()relayERC20() はSuperchainERC20用のブリッジコントラクトからのみ呼び出すことができ、その中でmint、burnを実行しています。

abstract contract SuperchainERC20 is ERC20, ICrosschainERC20, ISemver {
    error OnlySuperchainERC20Bridge();

    modifier onlySuperchainERC20Bridge() {
        if (msg.sender != Predeploys.SUPERCHAIN_ERC20_BRIDGE) revert OnlySuperchainERC20Bridge();
        _;
    }

    function __crosschainMint(address _to, uint256 _amount) external virtual onlySuperchainERC20Bridge {
        _mint(_to, _amount);

        emit CrosschainMinted(_to, _amount);
    }

    function __crosschainBurn(address _from, uint256 _amount) external virtual onlySuperchainERC20Bridge {
        _burn(_from, _amount);

        emit CrosschainBurnt(_from, _amount);
    }
}

SuperchainERC20Bridge

SuperchainERC20BridgeはSuperchainERC20トークンをブリッジするコントラクトです。sendERC20()relayERC20() の二つの関数があります。既存のSuperchainERC20からクロスチェーンの機能を取り出し、ブリッジのコントラクトとして独立させています。独立しているため、中立的なクロスチェーンを実現しています。

function sendERC20(
    address _token,
    address _to,
    uint256 _amount,
    uint256 _chainId
)
    external
    returns (bytes32 msgHash_)
{
    if (_to == address(0)) revert ZeroAddress();

    ISuperchainERC20(_token).__crosschainBurn(msg.sender, _amount);

    bytes memory message = abi.encodeCall(this.relayERC20, (_token, msg.sender, _to, _amount));
    msgHash_ = IL2ToL2CrossDomainMessenger(MESSENGER).sendMessage(_chainId, address(this), message);

    emit SendERC20(_token, msg.sender, _to, _amount, _chainId);
}

function relayERC20(address _token, address _from, address _to, uint256 _amount) external {
    if (msg.sender != MESSENGER) revert CallerNotL2ToL2CrossDomainMessenger();

    if (IL2ToL2CrossDomainMessenger(MESSENGER).crossDomainMessageSender() != address(this)) {
        revert InvalidCrossDomainSender();
    }

    uint256 source = IL2ToL2CrossDomainMessenger(MESSENGER).crossDomainMessageSource();

    ISuperchainERC20(_token).__crosschainMint(_to, _amount);

    emit RelayERC20(_token, _from, _to, _amount, source);
}

まとめ

Optimismが提案したERC20の新しいインターフェースであるICrosschainERC20について紹介しました。また、その実装であるSuperchainERC20とそのトークンのためのブリッジコントラクトであるSuperchainERC20Bridgeを紹介しました。

ICrosschainERC20は統一化されたエコシステムの構築の一環であり、Vitalik氏は開発者たちに協力を呼びかけていましたが、実現するのか注目していきます。

 

次世代システム研究室では、グループ全体のインテグレーションを支援してくれるアーキテクトを募集しています。インフラ設計、構築経験者の方、次世代システム研究室にご興味を持って頂ける方がいらっしゃいましたら、ぜひ募集職種一覧からご応募をお願いします。

皆さんのご応募をお待ちしています。

 

参考

https://github.com/ethereum-optimism/optimism

https://x.com/VitalikButerin/status/1842441242799440287

  • Twitter
  • Facebook
  • はてなブックマークに追加

グループ研究開発本部の最新情報をTwitterで配信中です。ぜひフォローください。

 
  • AI研究開発室
  • 大阪研究開発グループ

関連記事