The checks
Three ways to read a hook that never published its code.
- 01
The address
A v4 hook cannot choose what it is called for after it is deployed. Its address is mined so the last fourteen bits say which callbacks the PoolManager will make, and the PoolManager refuses a pool whose hook disagrees. Reading those bits costs nothing and lies to no one.
- 02
The bytecode
No source needed. The opcodes are walked once: the selectors the dispatcher answers to, DELEGATECALL and SELFDESTRUCT, outside calls, constant addresses, the proxy slots. Selectors are named from the public signature database, so a hook nobody published still reads in words.
- 03
The probe
A small contract is lent to an empty address for one eth_call. It opens the PoolManager, swaps a little each way through the real pool and its hook, adds liquidity and takes it back, then reverts with what it was given. Nothing settles and no tokens are needed. The pool fee is expected; the rest of the difference is the hook.
Eight checks, the same for every hook.
Each check passes, needs caution, fails, or does not apply. A pass earns its weight, a caution half of it, a fail nothing; what does not apply leaves the total. The verdict is separate from the score: any fail makes it danger, and any caution outside the track record makes it caution. Safe means safe by construction.
- 01Permissions that touch your moneyRead from the address
Whether the hook may take from swaps or from LPs at all. Four of the fourteen permission bits allow it.
10 pts - 02What it takes from a swapMeasured
A swap each way through the pool. Anything missing beyond the pool fee is what the hook took. A refused sell is a fail.
25 pts - 03LPs can get outMeasured
Liquidity is added and taken straight back out. It should come back whole.
15 pts - 04The fee is the feeRead from the pool
A fixed fee is written in the pool key. A dynamic one is whatever the hook last set; above ten percent it fails.
5 pts - 05No one holds the switchRead from the bytecode
An owner, and the functions an owner usually has: setters, pause, withdraw, blacklist.
15 pts - 06The code cannot changeRead from the bytecode
Not a proxy, no DELEGATECALL, no SELFDESTRUCT. What you scanned is what will run.
15 pts - 07Only the PoolManager can call itCalled from a stranger
Each callback is called directly by an outside address. It should refuse.
10 pts - 08Track recordRead from the chain
How many pools use it and for how long. Age is not safety, but a hook from this morning has proven nothing.
5 pts
The fourteen bits.
Read from the end of the address. Red ones let a hook move someone else's money or keep it.
- 13Before initialize
Runs once, when a pool is created.
- 12After initialize
Runs once, right after a pool is created.
- 11Before add liquidity
Can refuse a deposit, or only let some addresses provide liquidity.
- 10After add liquidity
Runs after each deposit.
- 9Before remove liquidity
Can refuse a withdrawal. LPs may not get out.
- 8After remove liquidity
Runs after each withdrawal.
- 7Before swap
Runs before every swap. On a dynamic-fee pool it can set the fee each time.
- 6After swap
Runs after every swap.
- 5Before donate
Runs before a donation to LPs.
- 4After donate
Runs after a donation to LPs.
- 3Before swap returns delta
Can take part of what you put into a swap, or change how much is swapped.
- 2After swap returns delta
Can take part of what you get out of every swap.
- 1After add returns delta
Can charge LPs on the way in.
- 0After remove returns delta
Can take part of what LPs withdraw.
What a report cannot tell you.
- A scan is a measurement at one block. A hook with an owner or a dynamic fee can do something else tomorrow, and the page says when it was taken.
- The probe swaps a small amount, from a fresh address, with no hook data. A hook can treat a large order, a known router or a sniper differently, and many launch hooks lower their tax with time.
- Reading bytecode is reading, not decompiling. An unusual dispatcher can hide a selector, and names from the signature database can be wrong or missing.
- A clean report means none of these eight things went wrong. It does not mean the hook has no bug. It is not an audit.