tempo_contracts/precompiles/
tip_fee_manager.rs

1pub use IFeeManager::{IFeeManagerErrors as FeeManagerError, IFeeManagerEvents as FeeManagerEvent};
2pub use ITIPFeeAMM::{ITIPFeeAMMErrors as TIPFeeAMMError, ITIPFeeAMMEvents as TIPFeeAMMEvent};
3
4use alloy::sol;
5
6sol! {
7    /// FeeManager interface for managing gas fee collection and distribution.
8    ///
9    /// IMPORTANT: FeeManager inherits from TIPFeeAMM and shares the same storage layout.
10    /// This means:
11    /// - FeeManager has all the functionality of TIPFeeAMM (pool management, swaps, liquidity operations)
12    /// - Both contracts use the same storage slots for AMM data (pools, reserves, liquidity balances)
13    /// - FeeManager extends TIPFeeAMM with additional storage slots (4-15) for fee-specific data
14    /// - When deployed, FeeManager IS a TIPFeeAMM with additional fee management capabilities
15    ///
16    /// Storage layout:
17    /// - Slots 0-3: TIPFeeAMM storage (pools, pool exists, liquidity data)
18    /// - Slots 4+: FeeManager-specific storage (validator tokens, user tokens, collected fees, etc.)
19    #[derive(Debug, PartialEq, Eq)]
20    #[sol(rpc, abi)]
21    interface IFeeManager {
22        // Structs
23        struct FeeInfo {
24            uint128 amount;
25            bool hasBeenSet;
26        }
27
28        // User preferences
29        function userTokens(address user) external view returns (address);
30        function validatorTokens(address validator) external view returns (address);
31        function setUserToken(address token) external;
32        function setValidatorToken(address token) external;
33
34        // Fee functions
35        function getFeeTokenBalance(address sender, address validator) external view returns (address, uint256);
36        function executeBlock() external;
37        // NOTE: collectFeePreTx and collectFeePostTx are protocol-internal functions
38        // called directly by the execution handler, not exposed via the dispatch interface.
39
40        // Events
41        event UserTokenSet(address indexed user, address indexed token);
42        event ValidatorTokenSet(address indexed validator, address indexed token);
43
44        // Errors
45        error OnlyValidator();
46        error OnlySystemContract();
47        error InvalidToken();
48        error PoolDoesNotExist();
49        error InsufficientFeeTokenBalance();
50        error InternalError();
51        error CannotChangeWithinBlock();
52        error CannotChangeWithPendingFees();
53        error TokenPolicyForbids();
54    }
55
56    /// TIPFeeAMM interface defining the base AMM functionality for stablecoin pools.
57    /// This interface provides core liquidity pool management and swap operations.
58    ///
59    /// NOTE: The FeeManager contract inherits from TIPFeeAMM and shares the same storage layout.
60    /// When FeeManager is deployed, it effectively "is" a TIPFeeAMM with additional fee management
61    /// capabilities layered on top. Both contracts operate on the same storage slots.
62    #[derive(Debug, PartialEq, Eq)]
63    #[sol(rpc)]
64    #[allow(clippy::too_many_arguments)]
65    interface ITIPFeeAMM {
66        // Structs
67        struct Pool {
68            uint128 reserveUserToken;
69            uint128 reserveValidatorToken;
70        }
71
72        struct PoolKey {
73            address token0;
74            address token1;
75        }
76
77
78        // Constants
79        function M() external view returns (uint256);
80        function N() external view returns (uint256);
81        function SCALE() external view returns (uint256);
82        function MIN_LIQUIDITY() external view returns (uint256);
83
84        // Pool Management
85        function getPoolId(address userToken, address validatorToken) external pure returns (bytes32);
86        function getPool(address userToken, address validatorToken) external view returns (Pool memory);
87        function pools(bytes32 poolId) external view returns (Pool memory);
88
89        // Liquidity Operations
90        function mint(address userToken, address validatorToken, uint256 amountUserToken, uint256 amountValidatorToken, address to) external returns (uint256 liquidity);
91        function mintWithValidatorToken(address userToken, address validatorToken, uint256 amountValidatorToken, address to) external returns (uint256 liquidity);
92        function burn(address userToken, address validatorToken, uint256 liquidity, address to) external returns (uint256 amountUserToken, uint256 amountValidatorToken);
93
94        // Liquidity Balances
95        function totalSupply(bytes32 poolId) external view returns (uint256);
96        function liquidityBalances(bytes32 poolId, address user) external view returns (uint256);
97
98        // Swapping
99        function rebalanceSwap(address userToken, address validatorToken, uint256 amountOut, address to) external returns (uint256 amountIn);
100
101        // Events
102        event Mint(address indexed sender, address indexed userToken, address indexed validatorToken, uint256 amountUserToken, uint256 amountValidatorToken, uint256 liquidity);
103        event Burn(address indexed sender, address indexed userToken, address indexed validatorToken, uint256 amountUserToken, uint256 amountValidatorToken, uint256 liquidity, address to);
104        event RebalanceSwap(address indexed userToken, address indexed validatorToken, address indexed swapper, uint256 amountIn, uint256 amountOut);
105        event FeeSwap(
106            address indexed userToken,
107            address indexed validatorToken,
108            uint256 amountIn,
109            uint256 amountOut
110        );
111
112        // Errors
113        error IdenticalAddresses();
114        error ZeroAddress();
115        error PoolExists();
116        error PoolDoesNotExist();
117        error InvalidToken();
118        error InsufficientLiquidity();
119        error OnlyProtocol();
120        error InsufficientPoolBalance();
121        error InsufficientReserves();
122        error InsufficientLiquidityBalance();
123        error MustDepositLowerBalanceToken();
124        error InvalidAmount();
125        error InvalidRebalanceState();
126        error InvalidRebalanceDirection();
127        error InvalidNewReserves();
128        error CannotSupportPendingSwaps();
129        error DivisionByZero();
130        error InvalidSwapCalculation();
131        error InsufficientLiquidityForPending();
132        error TokenTransferFailed();
133        error InternalError();
134    }
135}
136
137impl FeeManagerError {
138    /// Creates an error for only validator access.
139    pub const fn only_validator() -> Self {
140        Self::OnlyValidator(IFeeManager::OnlyValidator {})
141    }
142
143    /// Creates an error for only system contract access.
144    pub const fn only_system_contract() -> Self {
145        Self::OnlySystemContract(IFeeManager::OnlySystemContract {})
146    }
147
148    /// Creates an error for invalid token.
149    pub const fn invalid_token() -> Self {
150        Self::InvalidToken(IFeeManager::InvalidToken {})
151    }
152
153    /// Creates an error when pool does not exist.
154    pub const fn pool_does_not_exist() -> Self {
155        Self::PoolDoesNotExist(IFeeManager::PoolDoesNotExist {})
156    }
157
158    /// Creates an error for insufficient fee token balance.
159    pub const fn insufficient_fee_token_balance() -> Self {
160        Self::InsufficientFeeTokenBalance(IFeeManager::InsufficientFeeTokenBalance {})
161    }
162
163    /// Creates an error for internal errors.
164    pub const fn internal_error() -> Self {
165        Self::InternalError(IFeeManager::InternalError {})
166    }
167
168    /// Creates an error for cannot change within block.
169    pub const fn cannot_change_within_block() -> Self {
170        Self::CannotChangeWithinBlock(IFeeManager::CannotChangeWithinBlock {})
171    }
172
173    /// Creates an error for cannot change with pending fees.
174    pub const fn cannot_change_with_pending_fees() -> Self {
175        Self::CannotChangeWithPendingFees(IFeeManager::CannotChangeWithPendingFees {})
176    }
177
178    /// Creates an error for token policy forbids.
179    pub const fn token_policy_forbids() -> Self {
180        Self::TokenPolicyForbids(IFeeManager::TokenPolicyForbids {})
181    }
182}
183
184impl TIPFeeAMMError {
185    /// Creates an error for identical token addresses.
186    pub const fn identical_addresses() -> Self {
187        Self::IdenticalAddresses(ITIPFeeAMM::IdenticalAddresses {})
188    }
189
190    /// Creates an error for zero address.
191    pub const fn zero_address() -> Self {
192        Self::ZeroAddress(ITIPFeeAMM::ZeroAddress {})
193    }
194
195    /// Creates an error when pool already exists.
196    pub const fn pool_exists() -> Self {
197        Self::PoolExists(ITIPFeeAMM::PoolExists {})
198    }
199
200    /// Creates an error when pool does not exist.
201    pub const fn pool_does_not_exist() -> Self {
202        Self::PoolDoesNotExist(ITIPFeeAMM::PoolDoesNotExist {})
203    }
204
205    /// Creates an error for invalid token.
206    pub const fn invalid_token() -> Self {
207        Self::InvalidToken(ITIPFeeAMM::InvalidToken {})
208    }
209
210    /// Creates an error for insufficient liquidity.
211    pub const fn insufficient_liquidity() -> Self {
212        Self::InsufficientLiquidity(ITIPFeeAMM::InsufficientLiquidity {})
213    }
214
215    /// Creates an error for insufficient pool balance.
216    pub const fn insufficient_pool_balance() -> Self {
217        Self::InsufficientPoolBalance(ITIPFeeAMM::InsufficientPoolBalance {})
218    }
219
220    /// Creates an error for insufficient reserves.
221    pub const fn insufficient_reserves() -> Self {
222        Self::InsufficientReserves(ITIPFeeAMM::InsufficientReserves {})
223    }
224
225    /// Creates an error for insufficient liquidity balance.
226    pub const fn insufficient_liquidity_balance() -> Self {
227        Self::InsufficientLiquidityBalance(ITIPFeeAMM::InsufficientLiquidityBalance {})
228    }
229
230    /// Creates an error when must deposit lower balance token.
231    pub const fn must_deposit_lower_balance_token() -> Self {
232        Self::MustDepositLowerBalanceToken(ITIPFeeAMM::MustDepositLowerBalanceToken {})
233    }
234
235    /// Creates an error for invalid amount.
236    pub const fn invalid_amount() -> Self {
237        Self::InvalidAmount(ITIPFeeAMM::InvalidAmount {})
238    }
239
240    /// Creates an error for token transfer failure.
241    pub const fn token_transfer_failed() -> Self {
242        Self::TokenTransferFailed(ITIPFeeAMM::TokenTransferFailed {})
243    }
244
245    /// Creates an error for invalid swap calculation.
246    pub const fn invalid_swap_calculation() -> Self {
247        Self::InvalidSwapCalculation(ITIPFeeAMM::InvalidSwapCalculation {})
248    }
249
250    /// Creates an error for insufficient liquidity for pending operations.
251    pub const fn insufficient_liquidity_for_pending() -> Self {
252        Self::InsufficientLiquidityForPending(ITIPFeeAMM::InsufficientLiquidityForPending {})
253    }
254
255    /// Creates an error for division by zero.
256    pub const fn division_by_zero() -> Self {
257        Self::DivisionByZero(ITIPFeeAMM::DivisionByZero {})
258    }
259
260    /// Creates an error for invalid new reserves.
261    pub const fn invalid_new_reserves() -> Self {
262        Self::InvalidNewReserves(ITIPFeeAMM::InvalidNewReserves {})
263    }
264
265    /// Creates an error for internal errors.
266    pub const fn internal_error() -> Self {
267        Self::InternalError(ITIPFeeAMM::InternalError {})
268    }
269}