mirror of
https://github.com/ethereum/solidity
synced 2023-10-03 13:03:40 +00:00
EVMHost: Calculate address for CREATE properly
This commit is contained in:
parent
5f8b48793c
commit
9aa304d43a
@ -250,23 +250,48 @@ evmc::result EVMHost::call(evmc_message const& _message) noexcept
|
||||
|
||||
if (message.kind == EVMC_CREATE)
|
||||
{
|
||||
// TODO this is not the right formula
|
||||
// TODO is the nonce incremented on failure, too?
|
||||
// NOTE: nonce for creation from contracts starts at 1
|
||||
// TODO: check if sender is an EOA and do not pre-increment
|
||||
sender.nonce++;
|
||||
|
||||
auto encodeRlpInteger = [](int value) -> bytes {
|
||||
if (value == 0) {
|
||||
return bytes{128};
|
||||
} else if (value <= 127) {
|
||||
return bytes{static_cast<uint8_t>(value)};
|
||||
} else if (value <= 0xff) {
|
||||
return bytes{128 + 1, static_cast<uint8_t>(value)};
|
||||
} else if (value <= 0xffff) {
|
||||
return bytes{128 + 55 + 2, static_cast<uint8_t>(value >> 8), static_cast<uint8_t>(value)};
|
||||
} else {
|
||||
assertThrow(false, Exception, "Can only encode RLP numbers <= 0xffff");
|
||||
}
|
||||
};
|
||||
|
||||
bytes encodedNonce = encodeRlpInteger(sender.nonce);
|
||||
|
||||
h160 createAddress(keccak256(
|
||||
bytes{static_cast<uint8_t>(0xc0 + 21 + encodedNonce.size())} +
|
||||
bytes{0x94} +
|
||||
bytes(begin(message.sender.bytes), end(message.sender.bytes)) +
|
||||
asBytes(to_string(sender.nonce++))
|
||||
), h160::AlignLeft);
|
||||
encodedNonce
|
||||
), h160::AlignRight);
|
||||
|
||||
message.destination = convertToEVMC(createAddress);
|
||||
assertThrow(accounts.count(message.destination) == 0, Exception, "Account cannot exist");
|
||||
|
||||
code = evmc::bytes(message.input_data, message.input_data + message.input_size);
|
||||
}
|
||||
else if (message.kind == EVMC_CREATE2)
|
||||
{
|
||||
h160 createAddress(keccak256(
|
||||
bytes(1, 0xff) +
|
||||
bytes{0xff} +
|
||||
bytes(begin(message.sender.bytes), end(message.sender.bytes)) +
|
||||
bytes(begin(message.create2_salt.bytes), end(message.create2_salt.bytes)) +
|
||||
keccak256(bytes(message.input_data, message.input_data + message.input_size)).asBytes()
|
||||
), h160::AlignLeft);
|
||||
), h160::AlignRight);
|
||||
|
||||
message.destination = convertToEVMC(createAddress);
|
||||
if (accounts.count(message.destination) && (
|
||||
accounts[message.destination].nonce > 0 ||
|
||||
|
Loading…
Reference in New Issue
Block a user