Function ethers::utils::get_create2_address_from_hash[][src]

pub fn get_create2_address_from_hash(
    from: impl Into<H160>,
    salt: impl Into<Bytes>,
    init_code_hash: impl Into<Bytes>
) -> H160
Expand description

Returns the CREATE2 address of a smart contract as specified in EIP1014, taking the pre-computed hash of the init code as input.

keccak256( 0xff ++ senderAddress ++ salt ++ keccak256(init_code))[12..]

Example

Calculate the address of a UniswapV3 pool.

use ethers_core::{
    abi,
    abi::Token,
    types::{Address, Bytes, U256},
    utils::{get_create2_address_from_hash, keccak256},
};

let UNISWAP_V3_POOL_INIT_CODE_HASH = Bytes::from(
    hex::decode("e34f199b19b2b4f47f68442619d555527d244f78a3297ea89325f843f87b8b54").unwrap(),
);
let factory: Address = "0x1F98431c8aD98523631AE4a59f267346ea31F984"
    .parse()
    .unwrap();
let token0: Address = "0xa0b86991c6218b36c1d19d4a2e9eb0ce3606eb48"
    .parse()
    .unwrap();
let token1: Address = "0xc02aaa39b223fe8d0a0e5c4f27ead9083c756cc2"
    .parse()
    .unwrap();
let fee = 500;

// abi.encode(token0 as address, token1 as address, fee as uint256)
let input = abi::encode(&vec![
    Token::Address(token0),
    Token::Address(token1),
    Token::Uint(U256::from(fee)),
]);

// keccak256(abi.encode(token0, token1, fee))
let salt = keccak256(&input);
let pool_address =
    get_create2_address_from_hash(factory, salt.to_vec(), UNISWAP_V3_POOL_INIT_CODE_HASH);

assert_eq!(
    pool_address,
    "0x88e6A0c2dDD26FEEb64F039a2c41296FcB3f5640" // USDC/ETH pool address
        .parse()
        .unwrap()
);