forked from ethereum-optimism/optimism
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathRLP.t.sol
46 lines (41 loc) · 2.3 KB
/
RLP.t.sol
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
// SPDX-License-Identifier: Unlicense
pragma solidity ^0.8.0;
import { Bytes32AddressLib } from "@rari-capital/solmate/src/utils/Bytes32AddressLib.sol";
/// @title LibRLP
/// @notice Via https://github.com/Rari-Capital/solmate/issues/207.
library LibRLP {
using Bytes32AddressLib for bytes32;
function computeAddress(address deployer, uint256 nonce) internal pure returns (address) {
// The integer zero is treated as an empty byte string, and as a result it only has a length prefix, 0x80,
// computed via 0x80 + 0.
// A one byte integer uses its own value as its length prefix, there is no additional "0x80 + length" prefix
// that comes before it.
if (nonce == 0x00) {
return keccak256(abi.encodePacked(bytes1(0xd6), bytes1(0x94), deployer, bytes1(0x80))).fromLast20Bytes();
}
if (nonce <= 0x7f) {
return keccak256(abi.encodePacked(bytes1(0xd6), bytes1(0x94), deployer, uint8(nonce))).fromLast20Bytes();
}
// Nonces greater than 1 byte all follow a consistent encoding scheme, where each value is preceded by a prefix
// of 0x80 + length.
if (nonce <= type(uint8).max) {
return keccak256(abi.encodePacked(bytes1(0xd7), bytes1(0x94), deployer, bytes1(0x81), uint8(nonce)))
.fromLast20Bytes();
}
if (nonce <= type(uint16).max) {
return keccak256(abi.encodePacked(bytes1(0xd8), bytes1(0x94), deployer, bytes1(0x82), uint16(nonce)))
.fromLast20Bytes();
}
if (nonce <= type(uint24).max) {
return keccak256(abi.encodePacked(bytes1(0xd9), bytes1(0x94), deployer, bytes1(0x83), uint24(nonce)))
.fromLast20Bytes();
}
// More details about RLP encoding can be found here: https://eth.wiki/fundamentals/rlp
// 0xda = 0xc0 (short RLP prefix) + 0x16 (length of: 0x94 ++ proxy ++ 0x84 ++ nonce)
// 0x94 = 0x80 + 0x14 (0x14 = the length of an address, 20 bytes, in hex)
// 0x84 = 0x80 + 0x04 (0x04 = the bytes length of the nonce, 4 bytes, in hex)
// We assume nobody can have a nonce large enough to require more than 32 bytes.
return keccak256(abi.encodePacked(bytes1(0xda), bytes1(0x94), deployer, bytes1(0x84), uint32(nonce)))
.fromLast20Bytes();
}
}