create/create2
用于在合约内创建合约。
create
创建合约是通过new
构造合约实例,并传入构造参数
// value 表示可以payable的构造函数转入的eth数量
Contract con = new Contract{value: _value}(params);
address(con); // 合约的地址
create
合约地址是通过交易发起者sender
的地址以及交易序号nonce
来计算确定的。sender
和 nonce
进行 RLP
编码,然后用 Keccak-256
进行 hash
计算(伪码)
address = keccak256(rlp([sender, nonce]));
创建者地址不会变,但nonce
可能会随时间而改变,因此用create
创建的合约地址不好预测。
create2
创建合约也是通过new
构造合约实例,不同的是需要一个 salt
参数
Contract con = new Contract{salt: _salt, value: _value}(params)
用create2
创建的合约地址由 4 个部分决定:
0xFF
:常数- 交易发起者
sender
的地址 salt
:给定的数值- 待部署合约的字节码(
bytecode
)
address = keccak256(0xFF + sender + salt + bytecode)
因此可以事先计算出create2
合约地址
address(uint(keccak256(abi.encodePacked(
hex'ff',
address(this),
salt,
keccak256(type(Contract).creationCode)
))));