Contracts
14
5 contracts · 9 libraries · 3 outside
Flows
4
Swap · Add liquidity · Remove and collect · Create a pool
Source
5/14
Source for 5 of 14 · BUSL-1.1, GPL-2.0-or-later
Pinned
v1.0.0
2 repos · commit e3589b1
Automated market maker with concentrated liquidity: LPs provide liquidity inside a price range, traders swap against the pool of one token pair and fee tier.
The core is one Factory and one Pool per (token0, token1, fee). A Pool keeps the current price (sqrtPriceX96) and tick in slot0, liquidity per tick, positions per owner and range, and a price oracle. The core never pulls tokens: it sends first and then calls back msg.sender to be paid, checking its own balance afterwards. The periphery (SwapRouter, NonfungiblePositionManager) are the contracts users call; they implement those callbacks, check deadlines and slippage, and pay the pool.
DEXEthereum and EVM L2s
Periphery
Periphery libraries
Core
Pool libraries
Outside
SwapRoutercontract
Swap entry point. exactInput(Single) and exactOutput(Single), single and multi-hop. Finds the pool by computing its address, calls swap, and pays the pool from the user in the swap callback. Checks deadline and the minimum out / maximum in.
16 entry points23 functions1 storage0 eventsSwapRouter.sol:22
Inherits SelfPermit, ISelfPermit, Multicall, IMulticall, PeripheryPaymentsWithFee, IPeripheryPaymentsWithFee, PeripheryPayments, PeripheryValidation, PeripheryImmutableState, IPeripheryImmutableState, IPeripheryPayments, BlockTimestamp, ISwapRouter, IUniswapV3SwapCallback
Exact input, one pool: amountIn of tokenIn for at least amountOutMinimum of tokenOut.
Trader starts
Approves SwapRouter for tokenIn, then calls exactInputSingle(tokenIn, tokenOut, fee, recipient, deadline, amountIn, amountOutMinimum, sqrtPriceLimitX96).
SwapRouter.exactInputSingle
checkDeadline, then exactInputInternal with the caller recorded as payer in the callback data.
SwapRouter.sol:115 on GitHubPoolAddress.computeAddress
The pool's address comes from CREATE2 (factory, sorted tokens, fee), not from a storage lookup.
PoolAddress.sol:33 on GitHubUniswapV3Pool.swap
Takes the lock in slot0 and swaps step by step until the amount is used or the price limit is reached.
UniswapV3Pool.sol:596 on GitHubTickBitmap.nextInitializedTickWithinOneWord
Finds the next initialized tick in the swap direction, within one 256-tick word.
TickBitmap.sol:42 on GitHubSwapMath.computeSwapStep
Moves the price toward that tick: amount in, amount out and the LP fee for the step; the protocol's share is split off when the protocol fee is on.
SwapMath.sol:21 on GitHubTick.cross
When the price crosses an initialized tick, its net liquidity is added or removed and its fee growth outside flipped.
Tick.sol:166 on GitHubIERC20Minimal.transfer
The pool sends tokenOut to the recipient first.
SwapRouter.uniswapV3SwapCallback
The pool calls back msg.sender (the router) with the amounts owed.
SwapRouter.sol:57 on GitHubCallbackValidation.verifyCallback
The router checks msg.sender is the canonical pool for tokenIn, tokenOut and fee.
CallbackValidation.sol:15 on GitHubIERC20Minimal.transferFrom
The router pays tokenIn from the payer to the pool (wrapping ETH into WETH when the payer sent ETH).
UniswapV3Pool emit Swap
Back in the pool: requires its tokenIn balance grew by at least the amount owed, emits Swap, releases the lock.
IUniswapV3PoolEvents.sol:72 on GitHubSwapRouter back in exactInputSingle()
Requires amountOut ≥ amountOutMinimum, otherwise the whole swap reverts.
SwapRouter.sol:115 on GitHub0/18 checked
Mapped: core (factory, deployer, pool and its libraries) and the two main periphery contracts with their callback libraries. Not mapped: Quoter, position descriptor, multicall, migrator, Uniswap v4.
forge Version: 1.5.1-stable