Dynamic fee hook on Ethereum

Uniswap v4 Hook Contract 0x7fc5ae7b2fd9e67ce0d8d90908770ffe4c4b0088 on Ethereum · Dynamic fee

Volume (24h)
$0
Value locked (TVL)
$0
All-time volume
$0
Pools using this hook
76
Swaps (24h)
0 (0 traders)
Total swaps
6

What it does

A custom Uniswap v4 hook on Arbitrum that gates swaps in registered pools through an owner-controlled pause switch and per-pool fee settings, with a before-swap return delta that lets it adjust swap amounts.

This read was written for the hook 0x65a0…0088 on Arbitrum and reused here: the two share a code shape, so constants such as fees, owners and addresses can differ.

How it works step by step

  • Keeps an owner-managed registry of pools (pool count, allPools array, pools mapping) that it works with
  • Exposes setPoolFee(bytes32,uint24) so the owner can set a fee per pool, which suggests the hook sets or overrides fees for swaps
  • Has a global pause flag (setPaused / paused) that the swap path reads, so the owner can halt swaps
  • beforeSwap reads the pool registry and pause flag and returns a delta, which means it can alter the amounts a swap settles for
  • Includes an execute(address,uint256,bytes) function and an unlockCallback handler, indicating it can perform arbitrary calls or pool manager interactions on behalf of the owner
Swap behaviour
beforeSwap is nonpayable and reads the paused flag and the pool registry, then returns a before-swap delta. It is the only swap callback enabled, and the return-delta permission means it can change how much the swap takes or gives. Whether it blocks swaps while paused cannot be confirmed without source, but the pause flag is read on the swap path.
Liquidity behaviour
beforeAddLiquidity, afterAddLiquidity, beforeRemoveLiquidity and afterRemoveLiquidity are present as selectors, but the hook permissions enabled are only beforeSwap and beforeSwapReturnDelta, so these are likely not invoked by the pool manager and appear to be inherited or unused.
Fee behaviour
setPoolFee(bytes32,uint24) lets the owner set a fee per pool id. The fee is stored and read on the swap path, so the hook appears to control pool fees dynamically. The exact fee application (override or additive) cannot be confirmed from bytecode.
Owner & admin controls
An owner address (storage slot 0) controls setOwner, setPaused, setPoolFee and execute. The owner can pause swaps, change fees for any registered pool, transfer ownership, and make arbitrary external calls via execute.

Enabled Uniswap v4 callbacks

beforeSwap, beforeSwapReturnDelta

beforeSwap: reads pause state and pool configuration and returns a delta during swaps. beforeSwapReturnDelta: allows the hook to modify the swap's specified or unspecified amount, which is how it can take or subsidise value from swaps.

Security & trust assessment

Risk level: high, estimated (decoded bytecode, medium confidence).

Who controls it: A single owner key controls pause, pool fees, ownership and arbitrary external calls. Compromise of that key could drain funds, freeze trading or extract value from swaps.

Risk to user funds: The hook can hold or move funds through return deltas on swaps and through the owner's execute function. Users' swap outputs can be altered and swaps can be blocked while the pause flag is set.

Security findings

  • [medium] Owner can pause swaps: setPaused(bool) writes a flag that is read by the swap callback path, so a privileged key can halt trading in pools using this hook.
  • [medium] Owner can set pool fees: setPoolFee(bytes32,uint24) lets the owner change the fee for a pool, so a high value could extract most of each swap's value from traders.
  • [high] Arbitrary execution by owner: execute(address,uint256,bytes) lets the owner call any contract with any calldata, which can move any tokens the hook or its approvals control.
  • [medium] Return delta can alter swap settlement: The beforeSwapReturnDelta permission lets the hook take or give tokens on swaps, so its logic directly affects user amounts.
  • [info] Single-key ownership with no visible timelock: Ownership is held in storage slot 0 and transferable via setOwner with no time delay visible in the selectors.

Contract details

Verified source
No
Bytecode size
16,885 bytes
Upgradeable proxy
No
Detected patterns
pausable, return-delta

Pools using Dynamic fee hook