Appearance
S2C2: Show Me Your Key
1. Problem
You need to call mintFlag(bytes32 yourKey), where yourKey must equal keccak256(abi.encodePacked(msg.sender, address(this))).
2. Cause
The key is generated from the hash of the compact concatenation of the caller's address and the contract address. Since both are deterministic (the caller knows their own address, and the contract address is fixed), the key can be easily computed.
3. Solution
Compute the key using the correct method:
bash
# Key point: abi.encodePacked is compact concatenation, NOT standard ABI encoding!
ADDR1=$(echo $YOUR_ADDRESS | tr '[:upper:]' '[:lower:]' | sed 's/0x//')
ADDR2=$(echo $CHALLENGE | tr '[:upper:]' '[:lower:]' | sed 's/0x//')
KEY=$(cast keccak "0x${ADDR1}${ADDR2}")
cast send $CHALLENGE "mintFlag(bytes32)" "$KEY" --private-key $PK --rpc-url $RPC
4. Pitfalls Encountered
Incorrect ABI Encoding: Using cast abi-encode "f(address,address)" produces standard ABI encoding (each parameter 32 bytes) rather than the compact encoding of abi.encodePacked.
5. Why the Pitfall Occurred
Solidity's abi.encodePacked and abi.encode produce different byte sequences:
abi.encodePacked(addr1, addr2)-> 40 bytes (two 20-byte addresses concatenated)abi.encode(addr1, addr2)-> 64 bytes (each 32-byte aligned)- The
keccak256results are completely different!
6. How to Resolve
Strip the 0x prefix, manually concatenate the two addresses, then compute keccak256.
7. Technical Takeaways
| Point | Explanation |
|---|---|
abi.encodePacked vs abi.encode | The former uses compact concatenation, the latter uses 32-byte alignment |
| S2 Registration Dependency | New wallets must complete S1C1 registration before S2C2 |
| keccak256 as Identity Verification | Leverages hash determinism and collision resistance |