
GavinのWeb3理想郷:Polkadotスマートコントラクトと仮想マシンの進化史
TechFlow厳選深潮セレクト

GavinのWeb3理想郷:Polkadotスマートコントラクトと仮想マシンの進化史
Gavinのビジョンは、全く新しい分散型のインターネット世界を構築することである。
著者:クオズ
Polkadotは、古くから存在するブロックチェーンプロジェクトであり、Web3業界に携わる人々であれば、その製品を使ったことがなくても、少なくともこのプロジェクトの名前くらいは知っているだろう。

最近、Polkadotに関するニュースが相次いでおり、新しいJAMアーキテクチャには目を見張るものがあり、創業者がDOOMゲームをデモしたことで、Polkadotの新たな展開が見えてきた。これにより、私はPolkadotに対して強い研究意欲を持つようになった。しかしPolkadotプロジェクトは非常に大規模であり、Polkadotチェーン、Substrate開発フレームワーク、リレー/パラチェーンなど大きな構成要素がある。限られたページ数と注意力の中、今回は私が最も関心のある実行層、すなわち仮想機械(VM)という視点から、その歴史、現状および関連情報を紹介したい。
前夜
かつてイーサリアムが設立された当初、Gavin Woodはイーサリアムに興味を持ち、プロジェクトの開発に参加した。当時のイーサリアムはまだ初期の枠組みにすぎなかったが、Gavinの参加により技術的な面で具体化が進んだ。彼の貢献を見てみよう:
(1)イーサリアムのPoC-1(コンセプト実証-1)を完成;(2)ほぼ一人でイーサリアム最初のC++版クライアントを開発;(3)イーサリアム技術仕様である「イエローペーパー」を執筆;(4)スマートコントラクト開発用の高級言語Solidityを発明した。
この歴史については『万物への接続:イーサリアムと未来のデジタル金融』を読むとよい。また、Gavin Woodの伝説的な物語はネットでも簡単に検索できるため、ここでは省略する。
ここでSolidityとEVMに注目しよう。まず、簡単なSolidityのカウンターコード例を見てみる:
pragma solidity ^0.8.3; contract Counter { uint public count; function get() public view returns (uint) { return count; } function inc() public { count += 1; } function dec() public { count -= 1; } }
この例では、countという状態変数を宣言している。これはデータベース内の単一スロットと考えることができ、データベース管理コードを使って照会・変更可能だ。本例では、変数値を変更または取得する関数inc、dec、getをコントラクトが定義している。
Solidityコンパイラsolcでコンパイルすると、以下のようなバイトコードが得られる。これをJSON-RPCでノードにデプロイすると、実行層はまず合意形成を行い、その後EVMによって実行される。
6080604052348015600e575f80fd5b506101d98061001c5f395ff3fe608060405234801561000f575f80fd5 b506004361061004a575f3560e01c806306661abd1461004e578063371303c01461006c5780636d4ce63c14 610076578063b3bcfa8214610094575b5f80fd5b61005661009e565b60405161006391906100f7565b60405 180910390f35b6100746100a3565b005b61007e6100bd565b60405161008b91906100f7565b604051809103 90f35b61009c6100c5565b005b5f5481565b60015f808282546100b4919061013d565b92505081905550565 b5f8054905090565b60015f808282546100d69190610170565b92505081905550565b5f819050919050565b 6100f1816100df565b82525050565b5f60208201905061010a5f8301846100e8565b92915050565b7f4e487 b71000000000000000000000000000000000000000000000000000000005f52601160045260245ffd5b5f61 0147826100df565b9150610152836100df565b925082820190508082111561016a57610169610110565b5b9 2915050565b5f61017a826100df565b9150610185836100df565b925082820390508181111561019d576101 9c610110565b5b9291505056fea26469706673582212207b7edaa91dc37b9d0c1ea9627c0d65eb34996a5e3 791fb8c6a42ddf0571ca98164736f6c634300081a0033
これをアセンブリ命令形式に変換してみると、次のようになる:
PUSH1 0x80 PUSH1 0x40 MSTORE CALLVALUE DUP1 ISZERO PUSH1 0xE JUMPI PUSH0 DUP1 REVERT JUMPDEST POP PUSH2 0x1D9 DUP1 PUSH2 0x1C PUSH0 CODECOPY PUSH0 RETURN INVALID PUSH1 0x80 PUSH1 0x40 MSTORE CALLVALUE DUP1 ISZERO PUSH2 0xF JUMPI PUSH0 DUP1 REVERT JUMPDEST POP PUSH1 0x4 CALLDATASIZE LT PUSH2 0x4A JUMPI PUSH0 CALLDATALOAD PUSH1 0xE0 SHR DUP1 PUSH4 0x6661ABD EQ PUSH2 0x4E JUMPI DUP1 PUSH4 0x371303C0 EQ PUSH2 0x6C JUMPI DUP1 PUSH4 0x6D4CE63C EQ PUSH2 0x76 JUMPI DUP1 PUSH4 0xB3BCFA82 EQ PUSH2 0x94 JUMPI JUMPDEST PUSH0 DUP1 REVERT JUMPDEST PUSH2 0x56 PUSH2 0x9E JUMP JUMPDEST PUSH1 0x40 MLOAD PUSH2 0x63 SWAP2 SWAP1 PUSH2 0xF7 JUMP JUMPDEST PUSH1 0x40 MLOAD DUP1 SWAP2 SUB SWAP1 RETURN JUMPDEST PUSH2 0x74 PUSH2 0xA3 JUMP JUMPDEST STOP JUMPDEST PUSH2 0x7E PUSH2 0xBD JUMP JUMPDEST PUSH1 0x40 MLOAD PUSH2 0x8B SWAP2 SWAP1 PUSH2 0xF7 JUMP JUMPDEST PUSH1 0x40 MLOAD DUP1 SWAP2 SUB SWAP1 RETURN JUMPDEST PUSH2 0x9C PUSH2 0xC5 JUMP JUMPDEST STOP JUMPDEST PUSH0 SLOAD DUP2 JUMP JUMPDEST PUSH1 0x1 PUSH0 DUP1 DUP3 DUP3 SLOAD PUSH2 0xB4 SWAP2 SWAP1 PUSH2 0x13D JUMP JUMPDEST SWAP3 POP POP DUP2 SWAP1 SSTORE POP JUMP JUMPDEST PUSH0 DUP1 SLOAD SWAP1 POP SWAP1 JUMP JUMPDEST PUSH1 0x1 PUSH0 DUP1 DUP3 DUP3 SLOAD PUSH2 0xD6 SWAP2 SWAP1 PUSH2 0x170 JUMP JUMPDEST SWAP3 POP POP DUP2 SWAP1 SSTORE POP JUMP JUMPDEST PUSH0 DUP2 SWAP1 POP SWAP2 SWAP1 POP JUMP JUMPDEST PUSH2 0xF1 DUP2 PUSH2 0xDF JUMP JUMPDEST DUP3 MSTORE POP POP JUMP JUMPDEST PUSH0 PUSH1 0x20 DUP3 ADD SWAP1 POP PUSH2 0x10A PUSH0 DUP4 ADD DUP5 PUSH2 0xE8 JUMP JUMPDEST SWAP3 SWAP2 POP POP JUMP JUMPDEST PUSH32 0x4E487B7100000000000000000000000000000000000000000000000000000000 PUSH0 MSTORE PUSH1 0x11 PUSH1 0x4 MSTORE PUSH1 0x24 PUSH0 REVERT JUMPDEST PUSH0 PUSH2 0x147 DUP3 PUSH2 0xDF JUMP JUMPDEST SWAP2 POP PUSH2 0x152 DUP4 PUSH2 0xDF JUMP JUMPDEST SWAP3 POP DUP3 DUP3 ADD SWAP1 POP DUP1 DUP3 GT ISZERO PUSH2 0x16A JUMPI PUSH2 0x169 PUSH2 0x110 JUMP JUMPDEST JUMPDEST SWAP3 SWAP2 POP POP JUMP JUMPDEST PUSH0 PUSH2 0x17A DUP3 PUSH2 0xDF JUMP JUMPDEST SWAP2 POP PUSH2 0x185 DUP4 PUSH2 0xDF JUMP JUMPDEST SWAP3 POP DUP3 DUP3 SUB SWAP1 POP DUP2 DUP2 GT ISZERO PUSH2 0x19D JUMPI PUSH2 0x19C PUSH2 0x110 JUMP JUMPDEST JUMPDEST SWAP3 SWAP2 POP POP JUMP INVALID LOG2 PUSH5 0x6970667358 0x22 SLT KECCAK256 PUSH28 0x7EDAA91DC37B9D0C1EA9627C0D65EB34996A5E3791FB8C6A42DDF057 SHR 0xA9 DUP2 PUSH5 0x736F6C6343 STOP ADDMOD BYTE STOP CALLER
コンパイル原理の観点から実行フローを確認する:Solidityソースコード → 字句解析器 → 構文解析器 → コンパイル → バイトコード → 仮想マシン → 解釈実行
そう、IT業界においてこれはただの新しいプログラミング言語にすぎないが、当時としては非常に画期的な出来事だった。Gavinがイーサリアム開発に参加してから2年後、イーサリアムは予定通りローンチされた。もしここでV神がイーサリアムの体を作ったなら、Gavinはその魂を与えたと言える。ビットコインが電子決済システムであるのに対し、イーサリアムはブロックチェーンをプログラム可能にした。「ワールドコンピュータ」というスローガンを掲げたことで、すべてが変わった。
Web 3.0
Gavinがイーサリアムの共同創設者兼CTOを務めていた期間中、2014年4月17日、「Insights into a Modern World」というブログで「DApps: What Web 3.0 Looks Like[1]」という記事を公開し、彼自身が考えるWeb3.0の姿とその四つの構成要素について詳細に説明した。Web3.0という概念の影響力の大きさは周知の通りであり、Gavinは優れた技術力だけでなく、先見性も持ち合わせていた。Web3.0の歴史や議論についてはウィキペディアのWeb3項目[2]を参照されたい。アメリカの起業家兼ベンチャーキャピタリストであるノヴァ・スピーバック[3]は、Web3.0の定義を現在の主要な技術トレンドが新たな成熟段階に入った具体例として拡張することを提案しており、以下のように記述している:
• どこでもインターネット:高速ネットワークの普及と発展、モバイル端末のインターネット接続(例:タブレット)
• ネットワークコンピューティング:「SaaSサービス」のビジネスモデル、Webサービス相互運用性、分散処理、グリッドコンピューティング、ユーティリティコンピューティング(いわゆる「クラウドコンピューティング」)
• オープン技術:オープンAPIおよびプロトコル、オープンデータフォーマット、オープンソースソフトウェアプラットフォーム、オープンデータ(例:クリエイティブコモンズ、オープンデータライセンス)
• オープンアイデンティティ:OpenID、オープン評判、クロスドメインアイデンティティおよびプロファイル
• スマートネットワーク:RDFなどのセマンティックウェブ技術、OWL、SWRL、SPARQL、宣言型データストレージに基づくセマンティックアプリケーションプラットフォーム
• 分散型データベース:セマンティックウェブ技術で実現される「ワールドワイドデータベース」
• スマートアプリケーション:自然言語処理、機械学習、機械推論、自律エージェント

2015年末、Gavinはイーサリアムを離れた。
その後、彼はParity Technologiesを設立し、Rust言語で書かれたイーサリアムクライアントを開発し、一時期イーサ系ウォレット市場を独占した。Gavinがイーサリアムを去った理由は不明だが、わかっているのはGavinのビジョンは、まったく新しい非中央集権型インターネット世界を構築することにあるということだ。
「イーサリアムは私にとって技術的実現可能性を検証する実験であり、プロトタイプでした。イーサリアムは私の学校であり、そこを卒業した今、もっと多くのことに挑戦したいのです。」
「実は、イーサリアムから学んだ最大のものは技術ではなく(当時は専門の技術チームがいた)、社会経験です。その一つがガバナンスです。ブロックチェーンシステムにおいて、ガバナンスを通じてシステム能力を向上させることは極めて重要であり、革命的な新機能となるでしょう。それがまさにイーサリアムがやっていないことなのです。」
イーサリアム在籍中、Gavinは一貫して実践者であったが、設計者ではなかった。常に新たなイノベーションを温めていたのだ。
Polkadotの誕生
一年後、Gavinは長年頭を悩ませてきた課題を解決し、2016年にPolkadotホワイトペーパーを発表した。多くの人が知っているように、Polkadotはスケーラビリティ問題を解決するだけでなく、それぞれ独立したブロックチェーン間での通信(クロスチェーン)も実現しようとしている。しかしPolkadotについて最も理解すべきことは「シャーディング」である。極限までシャーディングを進めると、それこそがPolkadotそのものだからだ。
Polkadot創設者Gavin自身の言葉がそれをよく示している:
「Polkadotの設計理念は、直接的にインターオペラビリティを念頭に置いたものではない。我々はイーサリアムのシャーディング技術の登場を待っていたが、それは実現せず、今も出ていない。そこで、よりスケーラブルな『イーサリアム』を自ら作ろうと考えた。設計過程でシャーディングの概念を極限まで推し進め、ついにはシャードを完全に廃止し、代わりに独立したチェーンを設計した。こうすることで、異なるチェーン間で情報をやり取りできるようになり、最終的には共有のコンセンサス層を通じて通信が可能になった。」
では、どのようにしてシャーディングを理解すべきだろうか?まず、イーサリアムが直面する課題について考えてみよう。長年、イーサリアムの性能問題は致命的な弱点であり続けた。2018年、CryptoKittiesの人気に伴って深刻なネットワーク混雑が発生し、トランザクション時間が延び、手数料も高騰した。銀行の窓口が一つしかなく、処理速度も遅い場合、利用者が増えれば列が長くなるのと同じだ。
しかし、銀行に複数の窓口があれば、同時並行で業務を処理できるため、行列ができなくなるかもしれない。これがシャーディングの基本的な考えであり、ネットワーク全体のノードを「シャード」と呼ばれる複数の領域に分割し、多数の取引を異なるシャードで処理することで、効率を大幅に向上させるというものだ。
そのため、Polkadotでは各シャードが中心的なロジックを担い、並列取引やデータ交換を可能にし、最終的に複数のブロックチェーンを一つのネットワークに接続できる。
Polkadotの登場は、イーサリアム2.0の構想に匹敵するどころか、それを超える創造性を持っている。Polkadotの中には、複数のイーサリアムが存在できるのだ。もはや単なるブロックチェーンではなく、「Polkadotはあらゆる社会的革新に真に開放的で自由なプラットフォームを提供しようとしている」。
これはWeb3の理想であり、Polkadotの理想であり、Gavinの理想でもある。
Polkadot 1.0
Polkadotの中継チェーン自体はスマートコントラクトをサポートしていないが、接続されるパラチェーン[4]は独自の状態遷移ルールを定義でき、スマートコントラクト機能を提供できる。他のエコシステムとの違いは、Polkadotの文脈ではパラチェーンとスマートコントラクトがスタックの異なるレイヤーに存在することにある:スマートコントラクトはパラチェーンの上位に位置する。パラチェーンは通常第1層ブロックチェーンとみなされるが、独自のセキュリティを構築する必要がなく、アップグレード可能で相互運用可能という点で異なる。
Polkadotは、開発者がスマートコントラクトを構築する柔軟性を提供しており、EVM(イーサリアム仮想マシン)で実行されるSolidityコントラクトと、ink!を使用したWasmベースのコントラクトの両方をサポートしている:
EVM互換コントラクト
PolkadotエコシステムはFrontier[5]というツールセットのおかげで、イーサリアム仮想マシン(EVM)をサポートしている。Frontierにより、Substrateベースのブロックチェーンはネイティブにイーサリアムスマートコントラクトを実行でき、イーサリアム互換のAPI/RPCインターフェースを通じてイーサリアムエコシステムとシームレスに連携できる。SolidityやVyperなどの言語でコントラクトを記述でき、EVMはAstar、Moonbeam、AcalaなどのPolkadotパラチェーンを含め、広く標準化されている。この互換性により、最小限の修正で複数のネットワークにコントラクトをデプロイでき、成熟した広範な開発エコシステムの恩恵を受けられる。
例として、Astar[6]はPolkadot上の中核的なスマートコントラクトプラットフォームであり、EVMとWebAssembly(Wasm)の両方のスマートコントラクトを同時にサポートするユニークなマルチVMアプローチを持っている。この二重VMサポートにより、開発者は好みのプログラミング環境を選べつつ、イーサリアムとの完全な互換性を維持できる。このプラットフォームのランタイム[7]は、Substrate上のFRAMEで構築されており、Polkadot-SDKの主要コンポーネントと独自機能を処理するカスタムモジュールを統合している。

これらのチェーンは通常、既存のコントラクトモジュールを採用し、それに独自の革新を加えている。例えば:Phala[8]:信頼できる実行環境(TEE)内でコントラクトモジュールを使用し、秘匿性のあるスマートコントラクト実行と相互運用性を実現。Aleph Zero[9]:ゼロ知識環境でコントラクトトレイを使用。t3rn[10]:コントラクトモジュールを構成要素として使用し、スマートコントラクトのマルチチェーン実行を実現。EVM互換の他のパラチェーン(Aster、Moonbeam、Acalaなど)の技術詳細については公式ドキュメント「パラチェーンコントラクト[11]」を参照。
Wasm (ink!) コントラクト:
Polkadotは、FRAMEフレームワークを通じてContractsモジュール[12]を提供しており、このモジュールはWebAssemblyをコントラクトの実行環境として採用している。理論的には、Wasmにコンパイル可能なあらゆる言語でスマートコントラクトを開発できるが、最適化と利便性を考慮してParityは専用のink![13]をリリースした。
ink!について話す前に、まずSubstrate[14]とは何か、およびそのコントラクトモジュール(pallet-contracts)について明確にする必要がある。Substrateはブロックチェーンを構築するためのフレームワークであり、独立したブロックチェーンでも、Kusama[15]やPolkadot[16]に接続されるいわゆるパラチェーンでもよい。
Substrateには多くのモジュールが含まれており、Substrate用語では「トレイ(pallet)」と呼ばれる。Substrateには、ステーキング、同質性トークン、非同質性トークン、ガバナンスなど、現代的なブロックチェーンが通常必要とする多くの要件を満たす一連のトレイが付属している。
Substrateにはスマートコントラクト用のモジュールも付属しており、「Contracts pallet」と呼ばれる。Substrateでパラチェーンを開発する場合、このトレイを含めることで簡単にスマートコントラクト機能を追加できる。このモジュールは単なる実行環境であり、入力としてWebAssemblyファイルを受け取る。このモジュールのスマートコントラクトは、WebAssembly (Wasm) ターゲットアーキテクチャにコンパイルされる必要がある。
ここでink!はどのような役割を果たすのか?ink!はプログラミング言語であり、具体的には人気のあるRustプログラミング言語の埋め込みドメイン固有言語(eDSL)である。つまり、通常のRust構文に加え、いくつかの新しい要素を追加することで、スマートコントラクトの世界に適した言語となっている。コントラクトモジュールはこれらのink!コントラクトを受け取り、安全に実行する。簡単に言えば:
ink!を使えば、Substrateで構築されContractsトレイを含むブロックチェーン向けにRustでスマートコントラクトを書ける。
ink!は新しい言語を作ったわけではなく、明確な「コントラクトフォーマット」を持つ標準的なRustに、専用の#[ink(…)]属性マクロを加えたものだ。これらの属性マクロは、ink! Rustスマートコントラクトの各部分が何を意味するかを示し、最終的にPolkadot SDKと互換性のあるWasmバイトコード生成に必要なすべての処理を可能にする。ink!スマートコントラクトはWasmにコンパイルされるため、サンドボックス内で実行されることで、高い実行速度、プラットフォーム独立性、強化された安全性を提供する。
簡単なink!コントラクトを見てみよう。このコントラクトはストレージ内にブール値を保持する。コントラクト作成後、ブール値はtrueに設定される。コントラクトは2つの関数を公開する:ブール値の現在値を読み取る(fn get())、値を反転させる(fn flip())。
#[ink::contract] mod flipper { #[ink(storage)] pub struct Flipper { value: bool, } impl Flipper { #[ink(constructor)] pub fn new(init_value: bool) -> Self { Self { value: init_value } } #[ink(message)] pub fn flip(&mut self) { self.value = !self.value; } #[ink(message)] pub fn get(&self) -> bool { self.value } }}
Solidityと似た機能がある:Storage(ストレージ)、Message(メッセージ)、Errors(エラー)、Event(イベント)など。コントラクト開発者にとっては、ink!でスマートコントラクトを書けるだけでなく、他の言語を使う選択肢もある:SolidityのSolangコンパイラ[17]、AssemblyScriptのask
import { env, Pack } from "ask-lang";import { FlipEvent, Flipper } from "./storage";@contractexport class Contract { _data: Pack<Flipper>; constructor() { this._data = instantiate<Pack<Flipper>>(new Flipper(false)); } get data(): Flipper { return this._data.unwrap(); } set data(data: Flipper) { this._data = new Pack(data); } @constructor() default(flag: bool): void { this.data.flag = flag; } @message({ mutates: true }) flip(): void { this.data.flag = !this.data.flag; let event = new FlipEvent(this.data.flag); // @ts-ignore env().emitEvent(event); } @message() get(): bool { return this.data.flag; }}
新しい言語を追加するのは難しくない。WebAssembly対応の言語コンパイラがあれば、Contracts pallet APIを実装できる。
現在、このAPIには約15〜20の関数があり、ストレージアクセス、暗号化機能、環境情報(ブロック番号など)、乱数取得やコントラクト自己終了のための関数など、スマートコントラクトが必要とするあらゆる機能に使える。これらすべてを言語側で実装する必要はなく、ink!の「Hello,World!」はたった6つのAPI関数だけで動作する。以下の図式がこの関係を示している:

EVMと比較して、ink!とContracts palletを選ぶメリットは多い。本稿で詳しく紹介した主な利点をまとめると:
• ink!は単なるRust — 通常のRustツール(clippy、crates.io[19]、IDEなど)をそのまま使える。
• Rustは長年の言語研究を集約した言語であり、安全かつ高速。さらに、Solidityのような古いスマートコントラクト言語からの教訓を吸収し、ink!の言語設計に反映している。例えば、整数オーバーフローをデフォルトで無効にしたり、関数をデフォルトでプライベートにしたりといった合理的なデフォルトが採用されている。
• Rustは素晴らしい言語であり、StackOverflow上で7年連続で最も好まれるプログラミング言語に選ばれている(出典[20])。
• 企業がスマートコントラクト開発者を雇う場合、Solidity開発者よりもはるかに大きなRustエコシステムから人材を調達できる。
• ink!はSubstrateネイティブであり、同じプリミティブ、同じ型システムなどを使用している。
• コントラクトからパラチェーンへの移行パスが非常に明確。ink!とSubstrateはどちらもRustなので、大部分のコード、テスト、フロントエンドおよびクライアントコードを再利用できる。
• WebAssemblyは業界標準であり、ブロックチェーンの世界に限らず、Google、Apple、Microsoft、Mozilla、Facebookなどの大手企業が継続的に改善している。
• WebAssemblyはRust、C/C++、C#、TypeScript、Haxe、Kotlinなど、スマートコントラクト開発者が使える言語の幅を広げる。つまり、自分が得意な言語でスマートコントラクトを書ける。このような設計は、言語と実行アーキテクチャの密結合よりも将来を見据えたものだ。
本節の内容については、What is Parity's ink!?[21]を参照してさらに詳しい情報を得られたい。
Polkadot 2.0 / JAM
2月28日、Gavin Woodは上海でのJAMツアーで、JAM上でDOOMゲームを実行するデモを初公開した!これはブロックチェーン業界の歴史的瞬間であり、JAMによりブロックチェーンは単なるネットワークではなく、DOOMのような一般的なソフトウェアを実行できる強力なスーパーコンピュータプラットフォームとなり、強力な計算能力と低遅延を提供するようになった。

他の要素はひとまず置いておき、仮想マシンに焦点を当てる。過去数日間、PolkaVMの関連ソースコードを読んだ結果、実際に起こっていることが確かめられた。鍵は、PolkaVMがHost上でVMを実行し、エクスポートインターフェースを上位に提供し、そのVM上でRISC-V版のゲスト版Doomコードを実行している点にある。
ソースコードはこちら:
https://github.com/paritytech/polkavm/tree/master/examples/doom
ここで、今回の最も重要な新スマートコントラクトソリューションの構成要素を確認しよう:
Revive Pallet
Revive Pallet[22]は、ランタイムにPolkaVMスマートコントラクトのデプロイと実行機能を提供する。これは大幅に改変されたpallet_contractsの分岐である。これらのコントラクトは、RISC-Vにコンパイル可能な任意の言語で記述できる。現時点では、正式にサポートされている言語はSolidity(revive[23]経由)とRust(fixturesディレクトリ内のRustサンプルを参照)のみである。
コントラクト言語レベルでイーサリアムと互換性:Solidityでコントラクトを記述し、イーサリアムJSON RPCやMetaMaskなどのイーサリアムウォレットでノードとやり取りできる。裏側では、YULからRISC-Vへ再コンパイルされ、EVMではなくPolkaVMで実行される。操作を簡素化するため、カスタム版REMIX[24]Webフロントエンドを使って、コントラクトをRISC-Vにコンパイルし、Westend Asset Hub Parachain[25]にデプロイできる。
Revive
Revive[26]は「Solidity to PolkaVM」コンパイラプロジェクトの総称であり、複数のコンポーネント(YULフロントエンドやresolc実行ファイル自体など)を含む。resolcは、すべてのreviveコンポーネントを透過的に使ってコンパイル済みコントラクト成果物を生成する、単一エントリーポイントのフロントエンド実行可能ファイルの名称である。SolidityコントラクトをPolkaVMが実行可能なRISC-Vコードにコンパイルすることで、Polkadot上でSolidityコントラクトを実行できるようになる。
そのためにはコンパイラが必要。その仕組みは、オリジナルのsolcコンパイラを使い、その中間表現(YUL)出力をRISC-Vに再コンパイルすることにある。LLVM[27]は人気があり強力なコンパイラフレームワークで、バックエンドとして使われ、最適化とRISC-Vコード生成の重い仕事を担う。reviveは主に、生成されたYUL中間表現(IR)をsolcからLLVM IRに落とし込む責任を負っている。

この方法は、高いレベルのイーサリアム互換性、良好なコントラクトパフォーマンス、実現可能な工数の間に良いバランスを提供している。完全なSolidityコンパイラを実装するよりも、このアプローチの利点は、タスクがはるかに小さいことにある。この方法を選択することで、Solidityおよびそのすべてのバージョンの癖や奇抜な挙動をすべてサポートできる。
PolkaVM
PolkaVM[28]は、RISC-Vベースの汎用ユーザーレベル仮想マシンである。競合技術との最も顕著な違いである。EVMではなく、新しいカスタム仮想マシンを使ってコントラクトを実行する。現在、ランタイム自体にPolkaVMインタプリタが含まれている。将来的なアップデートでは、クライアント内で動作する完全なPolkaVM JITが提供される予定。

• デフォルトで安全かつサンドボックス化されている。VM内で実行されるコードは、別個のプロセスで実行され、ホストシステムにアクセスできないべきである。仮想マシン内部に完全なリモートコード実行権限を持つ攻撃者が存在しても同様である。
• 実行速度が速い。VMで実行されるコードのランタイムパフォーマンスは、最先端のWebAssembly VMに匹敵し、少なくとも同程度の数量級であるべき。
• コンパイル速度が速く、単回コンパイルO(n)を保証。新しいコードをVMにロードすることはほぼ即時であるべき。
• メモリ使用量が少ない。VMの各並列インスタンスのメモリオーバーヘッドは128KBを超えないべき。
• 小さいバイナリファイル。このVM向けにコンパイルされたプログラムは、可能な限り少ないスペースを占有すべき。
• 仮想アドレス空間を無駄にしない。VMはサンドボックス目的でGB単位の仮想アドレス空間を事前確保すべきではない。
• 完全に決定的。同じ入力と同じコードを与えれば、実行結果は常に完全に同一の出力を返すべき。
• 高性能な非同期gas計測をサポート。gas計測は安価で、決定的かつ妥当に正確であるべき。
• 単純であること。プログラマーが1週間以内に、この仮想マシンと完全に互換性のあるインタプリタを書けるべき。
• 操作意味のバージョン管理。将来、クライアントプログラムが観測可能な意味に変更がある場合は、すべてバージョン管理され、明示的にオプトインされるべき。
• 標準化。この仮想マシンのクライアントが観測可能な操作意味を完全に記述する仕様が存在すべき。
• クロスプラットフォーム。未サポートのOSやプラットフォームでは、VMはインタプリタモードで動作。
• 最小限の外部依存。VMは基本的に独立しており、コンパイルが速く、サプライチェーン攻撃に耐性があるべき。
• デバッグおよびパフォーマンス分析用の組み込みツール。
EVMとの根本的な2つの違い:
• レジスタマシン - EVMはスタックマシン。関数の引数は無限スタックを介して渡される。PolkaVMはRISC-Vベースであり、レジスタマシンである。つまり、有限のレジスタ群を使って引数を渡す。主な利点は、ハードウェアとの変換ステップがより効率的になる点にある。有名なレジスタ不足のx86-64命令セットより少ないレジスタ数が選ばれ、NP困難なレジスタ割り当て問題を単純な1対1マッピングに簡略化することが、PolkaVMの高速コンパイル時間の秘密である。
• ワードサイズの縮小 - EVMは256ビットのワードサイズを使用。つまり、すべての算術演算が巨大な数字に対して行われる。これにより、実際の数値演算が非常に遅くなり、多数のネイティブ命令に変換される必要がある。PolkaVMは64ビットのワードサイズを使用し、下位ハードウェアがネイティブにサポートしている。ただし、YUL(#Revive)経由でSolidityコントラクトを変換する際は、YULが低レベルすぎて整数型を自動変換できないため、依然として256ビット算術が使われる。しかし、異なる言語でコントラクトを書いてSolidityからシームレスに呼び出すことは可能。例えば、ビジネスロジックはSolidityで書き、基盤アーキテクチャはより高速な言語で書くようなシステムを想像してほしい。Pythonで、重い処理の多くがCモジュールで行われるのと似ている。
まとめ
スマートコントラクトプログラミング言語
スマートコントラクト言語の数は年々増加している。特に初心者にとっては、最初の言語を選ぶのは難しいかもしれない。選択は主に興味のあるエコシステムによるが、一部の言語は複数のプラットフォームに対応している。各言語には長所と短所があり、本稿では逐一紹介しない。
なぜこれほど多くのコントラクト言語があるのか?私なりに可能性をまとめると:1)既存言語ではチェーン特有の特性を満たせない;2)より良いパフォーマンス、安全性、コスト;3)好み :)
私はコントラクト言語に偏見を持っていない。以下にいくつかの異なる意見を引用する。利用者の視点、あるいは言語やVM設計の視点からも、さまざまな気づきを得られるだろう。
• なぜSolidityを使わないのか?Solidityは称賛される先駆者だが、EVMの多くの歴史的癖に制約されている。プログラマーが期待する一般的な機能が欠け、型システムは比較的表現力に乏しく、統一されたツールエコシステムもない。Swayでは、現代的なツール群を使ってスマートコントラクトを設計できる。ジェネリクス、代数的データ型、トレイトに基づく多態性を備えた充実した言語が得られる。また、コード補完LSPサーバー、フォーマッター、ドキュメント生成、コントラクトの実行・デプロイに必要なすべてが統合され、使いやすいツールチェーンも提供される。表現力豊かな型システムにより意味的エラーを捕捉でき、良いデフォルトを提供し、包括的な静的解析チェック(チェック強制、効果、相互作用など)を行うことで、コンパイル時に安全で正しいコードを書けるよう支援する。
via https://docs.fuel.network/docs/sway/
• なぜRustを使わないのか?Rustは優れたシステムプログラミング言語である(Sway自体もRustで書かれている)。しかし、スマートコントラクト開発には適していない。Rustの強みは、ゼロコスト抽象と複雑な借用チェッカーのメモリモデルにより、ガベージコレクションなしで印象的なランタイムパフォーマンスを実現することにある。しかしブロックチェーン上では、実行とデプロイのコストが希少資源である。メモリ使用量が少なく、実行時間が短いことが求められる。そのため、複雑なメモリ管理はしばしば高コストすぎて不採算となり、Rustの借用チェッカーは利益なしの負担となる。汎用プログラミング言語は通常、汎用計算環境での実行を前提に設計されているため、このような環境には適さない。Swayは、馴染みやすい構文とブロックチェーン環境特有のニーズに合った機能を提供することで、Rustの他のすべての利点(現代的な型システム、安全な手法、良いデフォルト)をスマートコントラクト開発者にもたらそうとしている。
via https://docs.fuel.network/docs/sway/
• Clarityコードは、書かれた通りに解釈され、実行される。Solidityなどの他の言語は、チェーンに提出される前にバイトコードにコンパイルされる。スマートコントラクト言語をコンパイルする危険性は二つある:第一に、コンパイラが複雑性の層を追加する。コンパイラのバグにより、バイトコードが期待とは異なってしまうリスクがあり、脆弱性が導入される可能性がある。第二に、バイトコードは人間が読める形ではないため、スマートコントラクトが実際に何をしているかを検証するのが難しくなる。自分自身に問いかけてみてほしい。読めない契約に署名しますか?答えが「いいえ」なら、スマートコントラクトはどう違うのか?Clarityなら、「見たままが手に入るもの」だ。
via https://docs.stacks.co/concepts/clarity\#clarity-is-interpreted-not-compiled
仮想マシンおよび命令セット
私たちがよく知るJVMから、EVMまで、ブロックチェーン分野ではヒューリスティックな台頭があった。私が知る限り、数十種類の仮想マシンがあり、実装方法はさまざまである。その中核である解釈器
TechFlow公式コミュニティへようこそ
Telegram購読グループ:https://t.me/TechFlowDaily
Twitter公式アカウント:https://x.com/TechFlowPost
Twitter英語アカウント:https://x.com/BlockFlow_News












