UniversalRouter
0x8876789976decbfcbbbe364623c63652db8c0904
Verification
Verified
v0.8.26+commit.8a97fa7a
Type
Contract
24,546 bytes
ABI entries
72
8 read · 5 write
License
none
Contract information
- Address
- 0x8876789976decbfcbbbe364623c63652db8c0904
- Chain
- Robinhood Chain (4663)
- Compiler
- v0.8.26+commit.8a97fa7a
- Optimization
- Enabled
- Creator
- 0x4e59b44847…26c0B4956C
- Creation tx
- 0x422569c99e…03009ed1fa
Token
Not a token
This contract does not expose ERC-20 metadata.
Read contract (8)
SPOKE_POOL() → address
V3_POSITION_MANAGER() → address
V4_POSITION_MANAGER() → address
eip712Domain() → bytes1, string, string, uint256, address, bytes32, uint256[]
msgSender() → address
noncesUsed(address, bytes32) → bool
poolManager() → address
signedRouteContext() → address, bytes32, bytes32
Events (1)
EIP712DomainChanged
ABI
[
{
"inputs": [
{
"components": [
{
"internalType": "address",
"name": "permit2",
"type": "address"
},
{
"internalType": "address",
"name": "weth9",
"type": "address"
},
{
"internalType": "address",
"name": "v2Factory",
"type": "address"
},
{
"internalType": "address",
"name": "v3Factory",
"type": "address"
},
{
"internalType": "bytes32",
"name": "pairInitCodeHash",
"type": "bytes32"
},
{
"internalType": "bytes32",
"name": "poolInitCodeHash",
"type": "bytes32"
},
{
"internalType": "address",
"name": "v4PoolManager",
"type": "address"
},
{
"internalType": "address",
"name": "v3NFTPositionManager",
"type": "address"
},
{
"internalType": "address",
"name": "v4PositionManager",
"type": "address"
},
{
"internalType": "address",
"name": "spokePool",
"type": "address"
}
],
"internalType": "struct RouterParameters",
"name": "params",
"type": "tuple"
}
],
"stateMutability": "nonpayable",
"type": "constructor"
},
{
"inputs": [
{
"internalType": "address",
"name": "target",
"type": "address"
}
],
"name": "AddressEmptyCode",
"type": "error"
},
{
"inputs": [
{
"internalType": "address",
"name": "account",
"type": "address"
}
],
"name": "AddressInsufficientBalance",
"type": "error"
},
{
"inputs": [],
"name": "BalanceTooLow",
"type": "error"
},
{
"inputs": [],
"name": "ContractLocked",
"type": "error"
},
{
"inputs": [
{
"internalType": "Currency",
"name": "currency",
"type": "address"
}
],
"name": "DeltaNotNegative",
"type": "error"
},
{
"inputs": [
{
"internalType": "Currency",
"name": "currency",
"type": "address"
}
],
"name": "DeltaNotPositive",
"type": "error"
},
{
"inputs": [],
"name": "ECDSAInvalidSignature",
"type": "error"
},
{
"inputs": [
{
"internalType": "uint256",
"name": "length",
"type": "uint256"
}
],
"name": "ECDSAInvalidSignatureLength",
"type": "error"
},
{
"inputs": [
{
"internalType": "bytes32",
"name": "s",
"type": "bytes32"
}
],
"name": "ECDSAInvalidSignatureS",
"type": "error"
},
{
"inputs": [],
"name": "ETHNotAccepted",
"type": "error"
},
{
"inputs": [
{
"internalType": "uint256",
"name": "commandIndex",
"type": "uint256"
},
{
"internalType": "bytes",
"name": "message",
"type": "bytes"
}
],
"name": "ExecutionFailed",
"type": "error"
},
{
"inputs": [],
"name": "FailedInnerCall",
"type": "error"
},
{
"inputs": [],
"name": "FromAddressIsNotOwner",
"type": "error"
},
{
"inputs": [],
"name": "InputLengthMismatch",
"type": "error"
},
{
"inputs": [],
"name": "InsufficientBalance",
"type": "error"
},
{
"inputs": [],
"name": "InsufficientETH",
"type": "error"
},
{
"inputs": [],
"name": "InsufficientToken",
"type": "error"
},
{
"inputs": [
{
"internalType": "bytes4",
"name": "action",
"type": "bytes4"
}
],
"name": "InvalidAction",
"type": "error"
},
{
"inputs": [],
"name": "InvalidBips",
"type": "error"
},
{
"inputs": [
{
"internalType": "uint256",
"name": "commandType",
"type": "uint256"
}
],
"name": "InvalidCommandType",
"type": "error"
},
{
"inputs": [],
"name": "InvalidEthSender",
"type": "error"
},
{
"inputs": [],
"name": "InvalidHopPriceLength",
"type": "error"
},
{
"inputs": [],
"name": "InvalidPath",
"type": "error"
},
{
"inputs": [],
"name": "InvalidPortion",
"type": "error"
},
{
"inputs": [],
"name": "InvalidReserves",
"type": "error"
},
{
"inputs": [],
"name": "InvalidShortString",
"type": "error"
},
{
"inputs": [],
"name": "LengthMismatch",
"type": "error"
},
{
"inputs": [],
"name": "NonceAlreadyUsed",
"type": "error"
},
{
"inputs": [
{
"internalType": "uint256",
"name": "tokenId",
"type": "uint256"
}
],
"name": "NotAuthorizedForToken",
"type": "error"
},
{
"inputs": [],
"name": "NotPoolManager",
"type": "error"
},
{
"inputs": [],
"name": "OnlyMintAllowed",
"type": "error"
},
{
"inputs": [
{
"internalType": "address",
"name": "token",
"type": "address"
}
],
"name": "SafeERC20FailedOperation",
"type": "error"
},
{
"inputs": [],
"name": "SliceOutOfBounds",
"type": "error"
},
{
"inputs": [
{
"internalType": "string",
"name": "str",
"type": "string"
}
],
"name": "StringTooLong",
"type": "error"
},
{
"inputs": [],
"name": "TransactionDeadlinePassed",
"type": "error"
},
{
"inputs": [],
"name": "UnsafeCast",
"type": "error"
},
{
"inputs": [
{
"internalType": "uint256",
"name": "action",
"type": "uint256"
}
],
"name": "UnsupportedAction",
"type": "error"
},
{
"inputs": [],
"name": "V2InvalidHopPriceLength",
"type": "error"
},
{
"inputs": [],
"name": "V2InvalidPath",
"type": "error"
},
{
"inputs": [],
"name": "V2TooLittleReceived",
"type": "error"
},
{
"inputs": [
{
"internalType": "uint256",
"name": "hopIndex",
"type": "uint256"
},
{
"internalType": "uint256",
"name": "minPrice",
"type": "uint256"
},
{
"internalType": "uint256",
"name": "price",
"type": "uint256"
}
],
"name": "V2TooLittleReceivedPerHop",
"type": "error"
},
{
"inputs": [],
"name": "V2TooMuchRequested",
"type": "error"
},
{
"inputs": [],
"name": "V3HopPriceAndPathLengthMismatch",
"type": "error"
},
{
"inputs": [],
"name": "V3InvalidAmountOut",
"type": "error"
},
{
"inputs": [],
"name": "V3InvalidCaller",
"type": "error"
},
{
"inputs": [],
"name": "V3InvalidSwap",
"type": "error"
},
{
"inputs": [],
"name": "V3TooLittleReceived",
"type": "error"
},
{
"inputs": [
{
"internalType": "uint256",
"name": "hopIndex",
"type": "uint256"
},
{
"internalType": "uint256",
"name": "minPrice",
"type": "uint256"
},
{
"internalType": "uint256",
"name": "price",
"type": "uint256"
}
],
"name": "V3TooLittleReceivedPerHop",
"type": "error"
},
{
"inputs": [],
"name": "V3TooMuchRequested",
"type": "error"
},
{
"inputs": [
{
"internalType": "uint256",
"name": "hopIndex",
"type": "uint256"
},
{
"internalType": "uint256",
"name": "minPrice",
"type": "uint256"
},
{
"internalType": "uint256",
"name": "price",
"type": "uint256"
}
],
"name": "V3TooMuchRequestedPerHop",
"type": "error"
},
{
"inputs": [
{
"internalType": "uint256",
"name": "minAmountOutReceived",
"type": "uint256"
},
{
"internalType": "uint256",
"name": "amountReceived",
"type": "uint256"
}
],
"name": "V4TooLittleReceived",
"type": "error"
},
{
"inputs": [
{
"internalType": "uint256",
"name": "hopIndex",
"type": "uint256"
},
{
"internalType": "uint256",
"name": "minPrice",
"type": "uint256"
},
{
"internalType": "uint256",
"name": "price",
"type": "uint256"
}
],
"name": "V4TooLittleReceivedPerHop",
"type": "error"
},
{
"inputs": [
{
"internalType": "uint256",
"name": "minPrice",
"type": "uint256"
},
{
"internalType": "uint256",
"name": "price",
"type": "uint256"
}
],
"name": "V4TooLittleReceivedPerHopSingle",
"type": "error"
},
{
"inputs": [
{
"internalType": "uint256",
"name": "maxAmountInRequested",
"type": "uint256"
},
{
"internalType": "uint256",
"name": "amountRequested",
"type": "uint256"
}
],
"name": "V4TooMuchRequested",
"type": "error"
},
{
"inputs": [
{
"internalType": "uint256",
"name": "hopIndex",
"type": "uint256"
},
{
"internalType": "uint256",
"name": "minPrice",
"type": "uint256"
},
{
"internalType": "uint256",
"name": "price",
"type": "uint256"
}
],
"name": "V4TooMuchRequestedPerHop",
"type": "error"
},
{
"inputs": [
{
"internalType": "uint256",
"name": "minPrice",
"type": "uint256"
},
{
"internalType": "uint256",
"name": "price",
"type": "uint256"
}
],
"name": "V4TooMuchRequestedPerHopSingle",
"type": "error"
},
{
"anonymous": false,
"inputs": [],
"name": "EIP712DomainChanged",
"type": "event"
},
{
"inputs": [],
"name": "SPOKE_POOL",
"outputs": [
{
"internalType": "contract IV3SpokePool",
"name": "",
"type": "address"
}
],
"stateMutability": "view",
"type": "function"
},
{
"inputs": [],
"name": "V3_POSITION_MANAGER",
"outputs": [
{
"internalType": "contract INonfungiblePositionManager",
"name": "",
"type": "address"
}
],
"stateMutability": "view",
"type": "function"
},
{
"inputs": [],
"name": "V4_POSITION_MANAGER",
"outputs": [
{
"internalType": "contract IPositionManager",
"name": "",
"type": "address"
}
],
"stateMutability": "view",
"type": "function"
},
{
"inputs": [],
"name": "eip712Domain",
"outputs": [
{
"internalType": "bytes1",
"name": "fields",
"type": "bytes1"
},
{
"internalType": "string",
"name": "name",
"type": "string"
},
{
"internalType": "string",
"name": "version",
"type": "string"
},
{
"internalType": "uint256",
"name": "chainId",
"type": "uint256"
},
{
"internalType": "address",
"name": "verifyingContract",
"type": "address"
},
{
"internalType": "bytes32",
"name": "salt",
"type": "bytes32"
},
{
"internalType": "uint256[]",
"name": "extensions",
"type": "uint256[]"
}
],
"stateMutability": "view",
"type": "function"
},
{
"inputs": [
{
"internalType": "bytes",
"name": "commands",
"type": "bytes"
},
{
"internalType": "bytes[]",
"name": "inputs",
"type": "bytes[]"
}
],
"name": "execute",
"outputs": [],
"stateMutability": "payable",
"type": "function"
},
{
"inputs": [
{
"internalType": "bytes",
"name": "commands",
"type": "bytes"
},
{
"internalType": "bytes[]",
"name": "inputs",
"type": "bytes[]"
},
{
"internalType": "uint256",
"name": "deadline",
"type": "uint256"
}
],
"name": "execute",
"outputs": [],
"stateMutability": "payable",
"type": "function"
},
{
"inputs": [
{
"internalType": "bytes",
"name": "commands",
"type": "bytes"
},
{
"internalType": "bytes[]",
"name": "inputs",
"type": "bytes[]"
},
{
"internalType": "bytes32",
"name": "intent",
"type": "bytes32"
},
{
"internalType": "bytes32",
"name": "data",
"type": "bytes32"
},
{
"internalType": "bool",
"name": "verifySender",
"type": "bool"
},
{
"internalType": "bytes32",
"name": "nonce",
"type": "bytes32"
},
{
"internalType": "bytes",
"name": "signature",
"type": "bytes"
},
{
"internalType": "uint256",
"name": "deadline",
"type": "uint256"
}
],
"name": "executeSigned",
"outputs": [],
"stateMutability": "payable",
"type": "function"
},
{
"inputs": [],
"name": "msgSender",
"outputs": [
{
"internalType": "address",
"name": "",
"type": "address"
}
],
"stateMutability": "view",
"type": "function"
},
{
"inputs": [
{
"internalType": "address",
"name": "user",
"type": "address"
},
{
"internalType": "bytes32",
"name": "nonce",
"type": "bytes32"
}
],
"name": "noncesUsed",
"outputs": [
{
"internalType": "bool",
"name": "used",
"type": "bool"
}
],
"stateMutability": "view",
"type": "function"
},
{
"inputs": [],
"name": "poolManager",
"outputs": [
{
"internalType": "contract IPoolManager",
"name": "",
"type": "address"
}
],
"stateMutability": "view",
"type": "function"
},
{
"inputs": [],
"name": "signedRouteContext",
"outputs": [
{
"internalType": "address",
"name": "signer",
"type": "address"
},
{
"internalType": "bytes32",
"name": "intent",
"type": "bytes32"
},
{
"internalType": "bytes32",
"name": "data",
"type": "bytes32"
}
],
"stateMutability": "view",
"type": "function"
},
{
"inputs": [
{
"internalType": "int256",
"name": "amount0Delta",
"type": "int256"
},
{
"internalType": "int256",
"name": "amount1Delta",
"type": "int256"
},
{
"internalType": "bytes",
"name": "data",
"type": "bytes"
}
],
"name": "uniswapV3SwapCallback",
"outputs": [],
"stateMutability": "nonpayable",
"type": "function"
},
{
"inputs": [
{
"internalType": "bytes",
"name": "data",
"type": "bytes"
}
],
"name": "unlockCallback",
"outputs": [
{
"internalType": "bytes",
"name": "",
"type": "bytes"
}
],
"stateMutability": "nonpayable",
"type": "function"
},
{
"stateMutability": "payable",
"type": "receive"
}
]Source code
// SPDX-License-Identifier: GPL-3.0-or-later
pragma solidity ^0.8.24;
// Command implementations
import {Dispatcher} from './base/Dispatcher.sol';
import {RouteSigner} from './base/RouteSigner.sol';
import {RouterParameters} from './types/RouterParameters.sol';
import {PaymentsImmutables, PaymentsParameters} from './modules/PaymentsImmutables.sol';
import {UniswapImmutables, UniswapParameters} from './modules/uniswap/UniswapImmutables.sol';
import {V4SwapRouter} from './modules/uniswap/v4/V4SwapRouter.sol';
import {Commands} from './libraries/Commands.sol';
import {IUniversalRouter} from './interfaces/IUniversalRouter.sol';
import {MigratorImmutables, MigratorParameters} from './modules/MigratorImmutables.sol';
import {EIP712} from '@openzeppelin/contracts/utils/cryptography/EIP712.sol';
import {ChainedActions} from './modules/ChainedActions.sol';
contract UniversalRouter is IUniversalRouter, ChainedActions, RouteSigner, Dispatcher {
constructor(RouterParameters memory params)
UniswapImmutables(UniswapParameters(
params.v2Factory, params.v3Factory, params.pairInitCodeHash, params.poolInitCodeHash
))
V4SwapRouter(params.v4PoolManager)
PaymentsImmutables(PaymentsParameters(params.permit2, params.weth9))
MigratorImmutables(MigratorParameters(params.v3NFTPositionManager, params.v4PositionManager))
ChainedActions(params.spokePool)
EIP712('UniversalRouter', '2')
{}
modifier checkDeadline(uint256 deadline) {
if (block.timestamp > deadline) revert TransactionDeadlinePassed();
_;
}
/// @notice To receive ETH from WETH
receive() external payable {
if (msg.sender != address(WETH9) && msg.sender != address(poolManager)) revert InvalidEthSender();
}
/// @inheritdoc IUniversalRouter
function execute(bytes calldata commands, bytes[] calldata inputs, uint256 deadline)
external
payable
checkDeadline(deadline)
{
execute(commands, inputs);
}
/// @inheritdoc IUniversalRouter
function executeSigned(
bytes calldata commands,
bytes[] calldata inputs,
bytes32 intent,
bytes32 data,
bool verifySender,
bytes32 nonce,
bytes calldata signature,
uint256 deadline
) external payable checkDeadline(deadline) {
// Set signature context and verify
_setSignatureContext(commands, inputs, intent, data, verifySender, nonce, signature, deadline);
// Execute commands
execute(commands, inputs);
// Clear signature context
_resetSignatureContext();
}
/// @inheritdoc Dispatcher
function execute(bytes calldata commands, bytes[] calldata inputs) public payable override isNotLocked {
bool success;
bytes memory output;
uint256 numCommands = commands.length;
if (inputs.length != numCommands) revert LengthMismatch();
// loop through all given commands, execute them and pass along outputs as defined
for (uint256 commandIndex = 0; commandIndex < numCommands; commandIndex++) {
bytes1 command = commands[commandIndex];
bytes calldata input = inputs[commandIndex];
(success, output) = dispatch(command, input);
if (!success && successRequired(command)) {
revert ExecutionFailed({commandIndex: commandIndex, message: output});
}
}
}
/// @inheritdoc IUniversalRouter
function signedRouteContext() external view returns (address signer, bytes32 intent, bytes32 data) {
return _signedRouteContext();
}
function successRequired(bytes1 command) internal pure returns (bool) {
return command & Commands.FLAG_ALLOW_REVERT == 0;
}
}
Chain explorer1726msChain node84ms