メインコンテンツへスキップ
ブロックチェーンMar 28, 2026

Deep EVM #2:メモリモデル — スタック、メモリ、ストレージ、Calldata

OS
Open Soft Team

Engineering Team

データが存在できる4つの場所

EVMは4つの異なるデータロケーションを提供し、それぞれコスト、ライフタイム、アクセスパターンが根本的に異なります。間違ったものを選ぶことが、スマートコントラクトで過剰なガス消費の最も一般的な原因です。

ロケーションライフタイム読み取りコスト書き込みコストサイズ
スタック現在のオペコード0(DUP: 3)0(PUSH: 3)1024ワード
メモリ現在のコールコンテキストMLOAD: 3*MSTORE: 3*拡張可能
ストレージ永続(ブロックチェーン)SLOAD: 2100/100SSTORE: 20000/2900/1002^256スロット
Calldata現在のコールコンテキストCALLDATALOAD: 3読み取り専用トランザクション入力

*メモリコストは操作あたり3ガス+二次拡張コスト。

スタック:高速だが小さい

スタックはEVMのワーキングメモリです。すべての算術、比較、論理演算がスタックから読み書きします。最大1024要素、各32バイト幅です。

実際には、DUPとSWAPオペコードが16要素までしか到達できないため、16スロット以上を使用することはまれです。スタックアクセスは基本的に無料(PUSH/DUP/SWAP操作に3ガス)です。

メモリ:安価だが一時的

メモリはバイトアドレス可能な配列で、空から始まり必要に応じて拡張されます。現在のコールコンテキストの間のみ持続します。

フリーメモリポインタ

Solidityはメモリの最初の128バイトを特別な目的に予約します:

オフセット目的
0x00-0x3fスクラッチスペース(ハッシュに使用)
0x40-0x5fフリーメモリポインタ
0x60-0x7fゼロスロット
0x80+フリーメモリ(割り当てはここから開始)

メモリ拡張コスト

メモリが高価になるポイントがここです。ガスコストはMSTORE/MLOADあたり3ガスだけでなく、現在の最高水準を超えてメモリにアクセスすると、二次拡張コストが課されます。

公式(イエローペーパーより):

memory_cost = (memory_size_words^2 / 512) + (3 * memory_size_words)
使用メモリコスト
32バイト(1ワード)3ガス
1 KB(32ワード)98ガス
10 KB(320ワード)1160ガス
100 KB(3200ワード)29600ガス
1 MB(32000ワード)2,001,000ガス

ストレージ:永続だが高価

ストレージはEVMの永続キーバリューストアです。各コントラクトは2^256個の32バイトスロットを持つ独立したストレージスペースを持ちます。

Solidityのストレージレイアウト

contract StorageLayout {
    uint256 public x;       // スロット0
    uint256 public y;       // スロット1
    address public owner;   // スロット2(パック:20バイト)
    bool public paused;     // スロット2(パック:1バイト、同スロット!)
    mapping(address => uint256) public balances;  // スロット3(ベース)
}

ストレージパッキング

Solidityは可能な場合、複数の小さな変数を1つの32バイトスロットにパックします。これは重要な最適化です。

Calldata:読み取り専用で安価

Calldataはトランザクションまたはコールと共に送信される入力データです。読み取り専用で、アクセスは安価(CALLDATALOADに3ガス)です。

一時ストレージ(EIP-1153)

EIP-1153(Cancunアップグレード、2024年3月)は、TSTORETLOADの2つの新しいオペコードを導入しました。一時ストレージは通常のストレージと似ていますが、トランザクション終了時に自動的にクリアされます。

  • TLOADとTSTOREの両方に100ガス
  • トランザクション完了後にクリア
  • 同一トランザクション内のコールフレーム間でアクセス可能

リエントランシーロックに最適 — TSTOREでフラグを設定、TLOADでチェック。20000ガスのSSTOREコストが不要。

実践的最適化:適切なロケーションの選択

  1. スタックに置けるか? スタックを使用。マージナルコストゼロ。
  2. 16以上の値が必要? メモリを使用。
  3. 読み取り専用の入力データ? Calldataを使用。32バイトの読み取りあたり3ガス。
  4. トランザクション間で永続化が必要? ストレージを使用。新規エントリに20000+ガスを予算。
  5. コールフレーム間で永続化が必要だがトランザクション間では不要? 一時ストレージを使用。100ガス。

まとめ

EVMのメモリモデルは見かけ上シンプルです — 4つのロケーションに明確なトレードオフ。しかし、コストの差は膨大です:スタックのADDは3ガス、SSTOREは20000ガス。これらのコストを直感的レベルで理解することが、ガス効率の良いコントラクトとガスを浪費するコントラクトの違いです。