Skip to content
On this page

NFT市場への潜入:「タダ乗り」を巡るスリリングな宝探し

想像してみてください: 価値あるNFTが並ぶ真新しいマーケットプレイスが誕生しました。6点の希少なデジタルアートは、それぞれ15 ETHの価値を持ち、購入者を待っています。しかし、驚くべきことに、これらすべてのNFTは簡単に「持ち去る」ことができる重大な脆弱性が発見されました。開発者たちは手詰まりとなり、こう宣言します——これらのNFTを「救出」して彼らの元へ届けた者には、45 ETHの報酬を与えると。

そしてあなたは、その任務を引き受けたブロックチェーン探検家。しかし、手元にあるのはわずか 0.1 ETH。この規模の取引には到底足りません。追加資金の要求も拒否されてしまいました。 「一瞬で無料のETHが手に入れば…!」

これこそが Damn Vulnerable DeFi v4 のチャレンジの一つ——Free Rider です。


脆弱性の核心:FreeRiderRecoveryManager.sol

コードの核心となるのは FreeRiderRecoveryManager.sol です。

■ コンストラクタ

  • デプロイ時に 45 ETH(報酬額と同額) の送金が必要 → 初期資金が少ないプレイヤーにとって大きな障壁

onERC721Received

NFT受領時に呼び出される関数で、以下のチェックを行います:

  • msg.sender != address(nft):呼び出し元がNFTコントラクトであること
  • tx.origin != beneficiary:トランザクション発行者が受益者であること
  • _tokenId > 5:対象はID 0〜5のみ
  • nft.ownerOf(_tokenId) == address(this):NFTが確実にこのコントラクトに属していること

🚨 脆弱性の本質

最大の問題はここです:

👉 received == 6 のとき、報酬が _data からデコードされたアドレスへ送金される

そして _data は:

👉 safeTransferFrom の引数として自由に指定可能

つまり:

👉 送金先を自分に書き換えられる!


攻撃の鍵:FreeRiderNFTMarketplace.sol

攻撃は以下の2つを組み合わせて成立します:

  • NFTマーケットのロジック
  • Uniswap V2 のフラッシュローン

攻撃の流れ

1. 下準備

  • 手持ちの 0.1 ETH を使い Uniswap V2 に流動性を作成
  • DamnValuableTokenWETH のペアを準備

2. フラッシュローン実行

  • UniswapV2Callee を使い大量のETHを一時借入
  • NFT購入+45 ETH支払い分をカバー

3. NFT購入とトリック

  • buyMany で6つのNFTを購入

  • safeTransferFrom に以下を仕込む:

    • recipientFreeRiderRecoveryManager
    • _dataabi.encode(address(this))

👉 ここが重要:

  • _data に「自分のコントラクトアドレス」を埋め込む

4. 脆弱性発動

  • NFTが RecoveryManager に送られる
  • received == 6 条件達成

すると:

👉 報酬 45 ETH が送金される

送金先は:

👉 abi.decode(_data)自分のコントラクト!


5. フラッシュローン返済

  • 得たETHでローン返済
  • 残りが利益

最終結果

  • NFT6枚を取得
  • 45 ETH 報酬を横取り
  • フラッシュローン返済
  • 利益確保

重要ポイントまとめ

  • _data パラメータの悪用
  • NFT転送時のコールバックロジック
  • フラッシュローンによる資金問題の解決
  • tx.origin チェックの不完全性

この「Free Rider」チャレンジは、単なるバグ利用ではありません。

  • コントラクト間の相互作用
  • コールバックの挙動
  • 任意データの危険性

これらを深く理解してこそ攻略できる、極めて洗練された問題です。

わずかな資金でも、ロジックを制すれば市場を制する——それがDeFiの本質です。

Built with AiAda