Level 12 - Privacy ⏺⏺⏺
Level Setup
Level Contract
Exploit
The data is a private
state variable, which means it's not accessible to other contracts, but can be read externally by a script.
Storage slots explained:
bool public locked
: This occupies slot 0. Each state variable takes up a single slot unless it is part of a struct or an array.bool
takes 1 byte, but an entire 32-byte slot is allocated for it.uint256 public ID
: This occupies slot 1.uint256
requires 32 bytes (1 full slot).uint8 private flattening
: This will start in slot 2.uint8
only takes 1 byte.uint8 private denomination
: Sinceuint8
also takes only 1 byte, it is packed into slot 2 along withflattening
.uint16 private awkwardness
:uint16
takes 2 bytes. Solidity packs this into slot 2 along with the otheruint8
values because they collectively fit within 32 bytes.Slot 2 looks like this (in bytes):
flattening (1) + denomination (1) + awkwardness (2) + 28 bytes padding = 32 bytes
bytes32[3] private data
: Arrays and structs are always stored in separate slots. The arraydata
has 3 elements of typebytes32
, and eachbytes32
takes 32 bytes (1 full slot).data[0]
is stored in slot 3.data[1]
is stored in slot 4.data[2]
is stored in slot 5.
Therefore, data[2]
is in slot 5 because it is the third element of the bytes32[3]
array, and each element of this array occupies its own 32-byte storage slot. The preceding variables occupy slots 0 through 2, with the array data
starting at slot 3 and extending to slots 4 and 5 for its elements.
Once found, cast it as bytes16
to truncate the packed zeros.
Submit instance... 🥳
Completion Message
Notes
Last updated