Warning! Contract bytecode has been changed and doesn't match the verified one. Therefore, interaction with this smart contract may be risky.
- Contract name:
- KinkMultiplierModel
- Optimization enabled
- true
- Compiler version
- v0.8.17+commit.8df45f5f
- Optimization runs
- 200
- EVM Version
- default
- Verified at
- 2024-06-02T13:25:29.651587Z
Constructor Arguments
0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000095626ee78400000000000000000000000000000000000000000000000000005b2d5430ce5100000000000000000000000000000000000000000000000000000853a0d2313c0000
Arg [0] (uint256) : 0
Arg [1] (uint256) : 42048000000000000
Arg [2] (uint256) : 6570000000000000000
Arg [3] (uint256) : 600000000000000000
contracts/KinkMultiplierModel.sol
// SPDX-License-Identifier: BSD-3-Clause pragma solidity 0.8.17; import "./interfaces/IKinkMultiplierModel.sol"; import "./interfaces/IInterestRateModel.sol"; contract KinkMultiplierModel is IKinkMultiplierModel, IInterestRateModel { uint256 public constant blocksPerYear = 2628000; // 12 second block interval uint256 public immutable interestRateMultiplierPerBlock; uint256 public immutable initialRatePerBlock; uint256 public immutable kinkCurveMultiplierPerBlock; uint256 public immutable kinkPoint; /// @param initialRatePerYear The approximate target initial APR, as a mantissa (scaled by 1e18) /// @param interestRateMultiplierPerYear Interest rate to utilisation rate increase ratio (scaled by 1e18) /// @param kinkCurveMultiplierPerYear The multiplier per year after hitting a kink point /// @param kinkPoint_ The utilisation point at which the kink curve multiplier is applied constructor( uint256 initialRatePerYear, uint256 interestRateMultiplierPerYear, uint256 kinkCurveMultiplierPerYear, uint256 kinkPoint_ ) { require(kinkPoint_ > 0); initialRatePerBlock = initialRatePerYear / blocksPerYear; interestRateMultiplierPerBlock = interestRateMultiplierPerYear / blocksPerYear; kinkCurveMultiplierPerBlock = kinkCurveMultiplierPerYear / blocksPerYear; kinkPoint = kinkPoint_; } /// @inheritdoc IInterestRateModel function getBorrowRate( uint256 cash, uint256 borrows, uint256 protocolInterest ) public view returns (uint256) { uint256 util = utilisationRate(cash, borrows, protocolInterest); if (util <= kinkPoint) { return (util * interestRateMultiplierPerBlock) / 1e18 + initialRatePerBlock; } else { uint256 normalRate = (kinkPoint * interestRateMultiplierPerBlock) / 1e18 + initialRatePerBlock; uint256 excessUtil = util - kinkPoint; return (excessUtil * kinkCurveMultiplierPerBlock) / 1e18 + normalRate; } } /// @inheritdoc IInterestRateModel function getSupplyRate( uint256 cash, uint256 borrows, uint256 protocolInterest, uint256 protocolInterestFactorMantissa ) external view returns (uint256) { uint256 oneMinusProtocolInterestFactor = 1e18 - protocolInterestFactorMantissa; uint256 borrowRate = getBorrowRate(cash, borrows, protocolInterest); uint256 rateToPool = (borrowRate * oneMinusProtocolInterestFactor) / 1e18; return (utilisationRate(cash, borrows, protocolInterest) * rateToPool) / 1e18; } /// @inheritdoc IKinkMultiplierModel function utilisationRate( uint256 cash, uint256 borrows, uint256 protocolInterest ) public pure returns (uint256) { // Utilisation rate is 0 when there are no borrows if (borrows == 0) return 0; return (borrows * 1e18) / (cash + borrows - protocolInterest); } }
@openzeppelin/contracts/utils/introspection/IERC165.sol
// SPDX-License-Identifier: MIT // OpenZeppelin Contracts v4.4.1 (utils/introspection/IERC165.sol) pragma solidity ^0.8.0; /** * @dev Interface of the ERC165 standard, as defined in the * https://eips.ethereum.org/EIPS/eip-165[EIP]. * * Implementers can declare support of contract interfaces, which can then be * queried by others ({ERC165Checker}). * * For an implementation, see {ERC165}. */ interface IERC165 { /** * @dev Returns true if this contract implements the interface defined by * `interfaceId`. See the corresponding * https://eips.ethereum.org/EIPS/eip-165#how-interfaces-are-identified[EIP section] * to learn more about how these ids are created. * * This function call must use less than 30 000 gas. */ function supportsInterface(bytes4 interfaceId) external view returns (bool); }
contracts/interfaces/IInterestRateModel.sol
// SPDX-License-Identifier: BSD-3-Clause pragma solidity 0.8.17; import "@openzeppelin/contracts/utils/introspection/IERC165.sol"; /** * @title Minterest InterestRateModel Interface * @author Minterest */ interface IInterestRateModel { /** * @notice Calculates the current borrow interest rate per block * @param cash The total amount of cash the market has * @param borrows The total amount of borrows the market has outstanding * @param protocolInterest The total amount of protocol interest the market has * @return The borrow rate per block (as a percentage, and scaled by 1e18) */ function getBorrowRate( uint256 cash, uint256 borrows, uint256 protocolInterest ) external view returns (uint256); /** * @notice Calculates the current supply interest rate per block * @param cash The total amount of cash the market has * @param borrows The total amount of borrows the market has outstanding * @param protocolInterest The total amount of protocol interest the market has * @param protocolInterestFactorMantissa The current protocol interest factor the market has * @return The supply rate per block (as a percentage, and scaled by 1e18) */ function getSupplyRate( uint256 cash, uint256 borrows, uint256 protocolInterest, uint256 protocolInterestFactorMantissa ) external view returns (uint256); }
contracts/interfaces/IKinkMultiplierModel.sol
// SPDX-License-Identifier: BSD-3-Clause pragma solidity 0.8.17; interface IKinkMultiplierModel { /** * @notice Gets the approximate number of blocks per year that is assumed by the interest rate model */ function blocksPerYear() external view returns (uint256); /** * @notice Gets the multiplier of utilisation rate that gives the slope of the interest rate */ function interestRateMultiplierPerBlock() external view returns (uint256); /** * @notice Gets the initial interest rate which is the y-intercept when utilisation rate is 0 */ function initialRatePerBlock() external view returns (uint256); /** * @notice Gets the interestRateMultiplierPerBlock after hitting a specified utilisation point */ function kinkCurveMultiplierPerBlock() external view returns (uint256); /** * @notice Gets the utilisation point at which the kink curve multiplier is applied */ function kinkPoint() external view returns (uint256); /** * @notice Calculates the utilisation rate of the market: `borrows / (cash + borrows - protocol interest)` * @param cash The amount of cash in the market * @param borrows The amount of borrows in the market * @param protocolInterest The amount of protocol interest in the market * @return The utilisation rate as a mantissa between [0, 1e18] */ function utilisationRate( uint256 cash, uint256 borrows, uint256 protocolInterest ) external pure returns (uint256); }
Compiler Settings
{"outputSelection":{"*":{"*":["*"],"":["*"]}},"optimizer":{"runs":200,"enabled":true},"metadata":{"useLiteralContent":true},"libraries":{}}
Contract ABI
[{"type":"constructor","stateMutability":"nonpayable","inputs":[{"type":"uint256","name":"initialRatePerYear","internalType":"uint256"},{"type":"uint256","name":"interestRateMultiplierPerYear","internalType":"uint256"},{"type":"uint256","name":"kinkCurveMultiplierPerYear","internalType":"uint256"},{"type":"uint256","name":"kinkPoint_","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"blocksPerYear","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"getBorrowRate","inputs":[{"type":"uint256","name":"cash","internalType":"uint256"},{"type":"uint256","name":"borrows","internalType":"uint256"},{"type":"uint256","name":"protocolInterest","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"getSupplyRate","inputs":[{"type":"uint256","name":"cash","internalType":"uint256"},{"type":"uint256","name":"borrows","internalType":"uint256"},{"type":"uint256","name":"protocolInterest","internalType":"uint256"},{"type":"uint256","name":"protocolInterestFactorMantissa","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"initialRatePerBlock","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"interestRateMultiplierPerBlock","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"kinkCurveMultiplierPerBlock","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"kinkPoint","inputs":[]},{"type":"function","stateMutability":"pure","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"utilisationRate","inputs":[{"type":"uint256","name":"cash","internalType":"uint256"},{"type":"uint256","name":"borrows","internalType":"uint256"},{"type":"uint256","name":"protocolInterest","internalType":"uint256"}]}]
Contract Creation Code
0x61010060405234801561001157600080fd5b5060405161064a38038061064a83398101604081905261003091610079565b6000811161003d57600080fd5b61004a622819a0856100af565b60a05261005a622819a0846100af565b60805261006a622819a0836100af565b60c05260e052506100d1915050565b6000806000806080858703121561008f57600080fd5b505082516020840151604085015160609095015191969095509092509050565b6000826100cc57634e487b7160e01b600052601260045260246000fd5b500490565b60805160a05160c05160e05161050a61014060003960008181610105015281816101900152818161027701526102b801526000818161012c01526102ee0152600081816092015281816101b7015261022901526000818160de015281816101e40152610256015261050a6000f3fe608060405234801561001057600080fd5b50600436106100885760003560e01c806372c2cfd01161005b57806372c2cfd014610127578063a385fb961461014e578063b816881614610158578063ca6c72001461016b57600080fd5b80630a9ea29f1461008d57806315f24053146100c65780634c041acc146100d9578063662db9ab14610100575b600080fd5b6100b47f000000000000000000000000000000000000000000000000000000000000000081565b60405190815260200160405180910390f35b6100b46100d43660046103fb565b61017e565b6100b47f000000000000000000000000000000000000000000000000000000000000000081565b6100b47f000000000000000000000000000000000000000000000000000000000000000081565b6100b47f000000000000000000000000000000000000000000000000000000000000000081565b6100b4622819a081565b6100b4610166366004610427565b610334565b6100b46101793660046103fb565b6103b0565b60008061018c8585856103b0565b90507f00000000000000000000000000000000000000000000000000000000000000008111610225577f0000000000000000000000000000000000000000000000000000000000000000670de0b6b3a76400006102097f00000000000000000000000000000000000000000000000000000000000000008461046f565b610213919061048c565b61021d91906104ae565b91505061032d565b60007f0000000000000000000000000000000000000000000000000000000000000000670de0b6b3a764000061029b7f00000000000000000000000000000000000000000000000000000000000000007f000000000000000000000000000000000000000000000000000000000000000061046f565b6102a5919061048c565b6102af91906104ae565b905060006102dd7f0000000000000000000000000000000000000000000000000000000000000000846104c1565b905081670de0b6b3a76400006103137f00000000000000000000000000000000000000000000000000000000000000008461046f565b61031d919061048c565b61032791906104ae565b93505050505b9392505050565b60008061034983670de0b6b3a76400006104c1565b9050600061035887878761017e565b90506000670de0b6b3a764000061036f848461046f565b610379919061048c565b9050670de0b6b3a7640000816103908a8a8a6103b0565b61039a919061046f565b6103a4919061048c565b98975050505050505050565b6000826000036103c25750600061032d565b816103cd84866104ae565b6103d791906104c1565b6103e984670de0b6b3a764000061046f565b6103f3919061048c565b949350505050565b60008060006060848603121561041057600080fd5b505081359360208301359350604090920135919050565b6000806000806080858703121561043d57600080fd5b5050823594602084013594506040840135936060013592509050565b634e487b7160e01b600052601160045260246000fd5b808202811582820484141761048657610486610459565b92915050565b6000826104a957634e487b7160e01b600052601260045260246000fd5b500490565b8082018082111561048657610486610459565b818103818111156104865761048661045956fea2646970667358221220cd1f02eb22df8738ed95308675433e68b4d5e8274162f4bea5ea8dcffc1f825964736f6c6343000811003300000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000095626ee78400000000000000000000000000000000000000000000000000005b2d5430ce5100000000000000000000000000000000000000000000000000000853a0d2313c0000
Deployed ByteCode
0x608060405234801561001057600080fd5b50600436106100885760003560e01c806372c2cfd01161005b57806372c2cfd014610127578063a385fb961461014e578063b816881614610158578063ca6c72001461016b57600080fd5b80630a9ea29f1461008d57806315f24053146100c65780634c041acc146100d9578063662db9ab14610100575b600080fd5b6100b47f000000000000000000000000000000000000000000000000000000000000000081565b60405190815260200160405180910390f35b6100b46100d43660046103fb565b61017e565b6100b47f00000000000000000000000000000000000000000000000000000003b9aca00081565b6100b47f0000000000000000000000000000000000000000000000000853a0d2313c000081565b6100b47f00000000000000000000000000000000000000000000000000000246139ca80081565b6100b4622819a081565b6100b4610166366004610427565b610334565b6100b46101793660046103fb565b6103b0565b60008061018c8585856103b0565b90507f0000000000000000000000000000000000000000000000000853a0d2313c00008111610225577f0000000000000000000000000000000000000000000000000000000000000000670de0b6b3a76400006102097f00000000000000000000000000000000000000000000000000000003b9aca0008461046f565b610213919061048c565b61021d91906104ae565b91505061032d565b60007f0000000000000000000000000000000000000000000000000000000000000000670de0b6b3a764000061029b7f00000000000000000000000000000000000000000000000000000003b9aca0007f0000000000000000000000000000000000000000000000000853a0d2313c000061046f565b6102a5919061048c565b6102af91906104ae565b905060006102dd7f0000000000000000000000000000000000000000000000000853a0d2313c0000846104c1565b905081670de0b6b3a76400006103137f00000000000000000000000000000000000000000000000000000246139ca8008461046f565b61031d919061048c565b61032791906104ae565b93505050505b9392505050565b60008061034983670de0b6b3a76400006104c1565b9050600061035887878761017e565b90506000670de0b6b3a764000061036f848461046f565b610379919061048c565b9050670de0b6b3a7640000816103908a8a8a6103b0565b61039a919061046f565b6103a4919061048c565b98975050505050505050565b6000826000036103c25750600061032d565b816103cd84866104ae565b6103d791906104c1565b6103e984670de0b6b3a764000061046f565b6103f3919061048c565b949350505050565b60008060006060848603121561041057600080fd5b505081359360208301359350604090920135919050565b6000806000806080858703121561043d57600080fd5b5050823594602084013594506040840135936060013592509050565b634e487b7160e01b600052601160045260246000fd5b808202811582820484141761048657610486610459565b92915050565b6000826104a957634e487b7160e01b600052601260045260246000fd5b500490565b8082018082111561048657610486610459565b818103818111156104865761048661045956fea2646970667358221220cd1f02eb22df8738ed95308675433e68b4d5e8274162f4bea5ea8dcffc1f825964736f6c63430008110033