Delegatecall

從它的選擇器中找到合約中函式的最快方法?

  • July 13, 2022

假設我有一個函式選擇器:

0xa9059cbb

我有這樣的契約:

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.7;
contract CallAnything {
 function balanceOf(address someAddress) external view {...}
 function transfer(address someAddress, uint256 amount) external {...}
 function approve(address someAddress, uint256 amount) external {...}
}

我找到選擇器涉及的功能的最快方法是什麼?

更多上下文

許多代理使用delegatecall目標地址和數據對象呼叫一些合約。如果我是從 UI/前端與代理進行互動的使用者,那麼要準確查看代理正在呼叫的函式和數據可能非常棘手。

一種快速找到的方法:

  1. 被呼叫的函式
  2. (不在這個問題的範圍內)解碼正在發送的參數。

會很可愛。

提示,在上面的合約中,函式選擇器0xa9059cbb是針對transfer函式的。它有一個函式簽名"transfer(address,uint256)"

您可以使用乙太坊簽名數據庫(https://www.4byte.directory/)註冊功能的簽名超過 956,355 個。

  1. 使用現有的選擇器數據庫 ==============

並在搜尋欄中輸入您的選擇器。您將獲得數據庫已找到的已知選擇器列表。這裡的優點是它很快,缺點是它們可能在數據庫中沒有您的特定選擇器。

  1. 使用 Brownie、Foundry、Hardhat 等工具 =================================

鑄造廠

如果您的代工項目中有契約或介面,您可以執行以下操作:

forge inspect CallAnything methods

並獲得如下輸出:

{
 "approve(address,uint256)": "095ea7b3",
 "balanceOf(address)": "70a08231",
 "transfer(address,uint256)": "a9059cbb"
}

並簡單地匹配選擇器(更容易forge inspect CallAnything methods | grep a9059cbb

布朗尼

您可以編寫如下腳本:

# call_me.py
from brownie import Contract


def main():
   calldata = "some_calldata_here"
   result = Contract.from_explorer(
       "0x2a49Eae5CCa3f050eBEC729Cf90CC910fADAf7A2"
   ).decode_input(calldata)
   print(result)

然後執行它:

brownie run scripts/call_me.py --network mainnet

並獲得如下輸出:

Fetching source of 0x2a49Eae5CCa3f050eBEC729Cf90CC910fADAf7A2 from api.etherscan.io...
('openMultiplyVault((address,address,uint256,uint256,uint256,address,bytes),(address,address,uint256,bytes32,uint256,uint256,uint256,uint256,uint256,uint256,bool,string),(address,address,address,address,address))', [['0x6B175474E89094C44Da98b954EedeAC495271d0F', .........

這還有一個額外的好處,即通過代理的 calldata 為您提供您想要的東西,並告訴您它在其他合約上呼叫了哪些函式。

  1. 將其放入 Tenderly ================

如果交易存在,你可以去Tenderly輸入交易,它會給你所有的函式呼叫 tx 對其他合約的呼叫。

或者,如果您還沒有進行交易,您可以使用交易模擬器

4.自己編寫一個腳本,將所有函式轉換為函式選擇器

但是誰在這樣做呢?

引用自:https://ethereum.stackexchange.com/questions/131693