·
We continued the Panoptic contest on Code4rena.
Lesson Summary:
- Master bit manipulation first — Prioritize learning shifts (<<, >>), masks (&, |, ~), packing/unpacking, and signed integer behavior before diving deep; once comfortable, most "complex" libraries become straightforward helpers.
- Treat bit-packing as storage optimization, not magic — Expect every value (ticks, liquidity, pointers, legs, flags) crammed into 256-bit words with manual getters/setters; always trace back to the packing layout comment or constants to verify offsets and ranges.
- Watch for negative number rounding traps — When averaging or dividing for medians/averages (e.g., (a + b) / 2), Solidity’s toward-zero division rounds negative numbers “up” (toward zero) — flag this for consistency checks in tick/price calculations.
- Be extra suspicious of unchecked blocks — They appear everywhere in extreme-optimization code; carefully verify arithmetic (especially +, - in clamps or deltas) can’t overflow/underflow in ways that break logic (e.g., int24 wrap-around making values unexpectedly small).Lean on fuzz testing for confidence — Once you understand the bit logic, write fuzz tests for encode/decode/update functions — deterministic packing is usually easy to prove correct (or find bugs) with good coverage, so don’t skip this step even if it initially looks clean.