morpho-org / morpho-blue-irm Goto Github PK
View Code? Open in Web Editor NEWMorpho Blue Interest Rate Models
Home Page: https://morpho.org
License: MIT License
Morpho Blue Interest Rate Models
Home Page: https://morpho.org
License: MIT License
I think that the min/max rate at target could be immutables actually (we already considered changing them in #64), but this can be done in another PR
Originally posted by @QGarchery in #66 (review)
The Irm has a storage per market; values are not logged when modified.
I suggest adding an event during the borrowRate
update.
I suggest adding a specific name for this IRM, such as PidIrm
.
morpho-blue-irm/src/AdaptiveCurveIrm.sol
Lines 135 to 136 in c2b1732
quantify and test this underestimation
avgBorrowRate
is calculated using the unbounded value of newBorrowRate
, so there may be a case where newBorrowRate > MAX_RATE
leading to avgBorrowRate
being over-evaluated with regard to the bounded value newBorrowRate
returned by _borrowRate
The same applies symmetrically to the minimum bound
We may want to clarify that the following equality is not correct when endRateAtTarget
has been bounded.
For reference: #73
Mutation testing report:
Number of mutations: 75
Killed: 50 / 75
Mutations:
Mutation:
File: /home/rubilmax/sites/morpho.xyz/morpho-blue-irm/src/AdaptiveCurveIrm.sol
Line nr: 75
Result: Lived
Original line:
require(curveSteepness <= ConstantsLib.MAX_CURVE_STEEPNESS, ErrorsLib.INPUT_TOO_LARGE);
Mutated line:
require(curveSteepness < ConstantsLib.MAX_CURVE_STEEPNESS, ErrorsLib.INPUT_TOO_LARGE);
Mutation:
File: /home/rubilmax/sites/morpho.xyz/morpho-blue-irm/src/AdaptiveCurveIrm.sol
Line nr: 77
Result: Lived
Original line:
require(adjustmentSpeed <= ConstantsLib.MAX_ADJUSTMENT_SPEED, ErrorsLib.INPUT_TOO_LARGE);
Mutated line:
require(adjustmentSpeed < ConstantsLib.MAX_ADJUSTMENT_SPEED, ErrorsLib.INPUT_TOO_LARGE);
Mutation:
File: /home/rubilmax/sites/morpho.xyz/morpho-blue-irm/src/AdaptiveCurveIrm.sol
Line nr: 78
Result: Lived
Original line:
require(targetUtilization < WAD, ErrorsLib.INPUT_TOO_LARGE);
Mutated line:
require(targetUtilization <= WAD, ErrorsLib.INPUT_TOO_LARGE);
Mutation:
File: /home/rubilmax/sites/morpho.xyz/morpho-blue-irm/src/AdaptiveCurveIrm.sol
Line nr: 79
Result: Lived
Original line:
require(targetUtilization > 0, ErrorsLib.ZERO_INPUT);
Mutated line:
require(targetUtilization >= 0, ErrorsLib.ZERO_INPUT);
Mutation:
File: /home/rubilmax/sites/morpho.xyz/morpho-blue-irm/src/AdaptiveCurveIrm.sol
Line nr: 81
Result: Lived
Original line:
require(initialRateAtTarget <= ConstantsLib.MAX_RATE_AT_TARGET, ErrorsLib.INPUT_TOO_LARGE);
Mutated line:
require(initialRateAtTarget < ConstantsLib.MAX_RATE_AT_TARGET, ErrorsLib.INPUT_TOO_LARGE);
Mutation:
File: /home/rubilmax/sites/morpho.xyz/morpho-blue-irm/src/AdaptiveCurveIrm.sol
Line nr: 121
Result: Lived
Original line:
int256 errNormFactor = utilization > TARGET_UTILIZATION ? WAD - TARGET_UTILIZATION : TARGET_UTILIZATION;
Mutated line:
int256 errNormFactor = utilization >= TARGET_UTILIZATION ? WAD - TARGET_UTILIZATION : TARGET_UTILIZATION;
Mutation:
File: /home/rubilmax/sites/morpho.xyz/morpho-blue-irm/src/libraries/adaptive-curve/ExpLib.sol
Line nr: 27
Result: Lived
Original line:
if (x < LN_WEI_INT) return 0;
Mutated line:
if (x <= LN_WEI_INT) return 0;
Mutation:
File: /home/rubilmax/sites/morpho.xyz/morpho-blue-irm/src/libraries/adaptive-curve/ExpLib.sol
Line nr: 33
Result: Lived
Original line:
int256 roundingAdjustment = (x < 0) ? -(LN_2_INT / 2) : (LN_2_INT / 2);
Mutated line:
int256 roundingAdjustment = (x <= 0) ? -(LN_2_INT / 2) : (LN_2_INT / 2);
Mutation:
File: /home/rubilmax/sites/morpho.xyz/morpho-blue-irm/lib/morpho-blue/src/libraries/MathLib.sol
Line nr: 32
Result: Lived
Original line:
return (x * y + (d - 1)) / d;
Mutated line:
return (x * y + (d - 1)) * d;
Mutation:
File: /home/rubilmax/sites/morpho.xyz/morpho-blue-irm/lib/morpho-blue/src/libraries/MathLib.sol
Line nr: 32
Result: Lived
Original line:
return (x * y + (d - 1)) / d;
Mutated line:
return (x * y - (d - 1)) / d;
Mutation:
File: /home/rubilmax/sites/morpho.xyz/morpho-blue-irm/lib/morpho-blue/src/libraries/MathLib.sol
Line nr: 32
Result: Lived
Original line:
return (x * y + (d - 1)) / d;
Mutated line:
return (x / y + (d - 1)) / d;
Mutation:
File: /home/rubilmax/sites/morpho.xyz/morpho-blue-irm/lib/morpho-blue/src/libraries/MathLib.sol
Line nr: 32
Result: Lived
Original line:
return (x * y + (d - 1)) / d;
Mutated line:
return (x * y + (d + 1)) / d;
Mutation:
File: /home/rubilmax/sites/morpho.xyz/morpho-blue-irm/lib/morpho-blue/src/libraries/MathLib.sol
Line nr: 42
Result: Lived
Original line:
return firstTerm + secondTerm + thirdTerm;
Mutated line:
return firstTerm + secondTerm - thirdTerm;
Mutation:
File: /home/rubilmax/sites/morpho.xyz/morpho-blue-irm/lib/morpho-blue/src/libraries/MathLib.sol
Line nr: 42
Result: Lived
Original line:
return firstTerm + secondTerm + thirdTerm;
Mutated line:
return firstTerm - secondTerm + thirdTerm;
Mutation:
File: /home/rubilmax/sites/morpho.xyz/morpho-blue-irm/src/libraries/adaptive-curve/ConstantsLib.sol
Line nr: 17
Result: Lived
Original line:
int256 internal constant MAX_ADJUSTMENT_SPEED = int256(1_000 ether) / 365 days;
Mutated line:
int256 internal constant MAX_ADJUSTMENT_SPEED = int256(1_000 ether) * 365 days;
Instead of being able to uint256(MathLib.LN2_INT)
, an integrator has to define again LN2_INT
(or its uint256
equivalent)
### Tasks
- [x] (MIN/MAX) value
And be stuck there forever ?
(consideration assuming #54)
even if there are some logical arguments in favor of keeping it, it is likely that it will make no change in practice so I'm in favor of removing it
discussion: https://morpholabs.slack.com/archives/C02N7CZ088N/p1698624167103969
Currently the minimum rate is 1e-18 per second, which is very low (~1e-11% APR). If a market is abandoned and then re-used, this very low rate might take a long time to come back to reasonable values. Maybe it could be capped to something higher.
These values could be used by integrators so we may consider exposing them as library constants
The SPEED_FACTOR can be used by seconds or by year. Maybe it's worth writing that in this code it is by second (while the one used by Matthieu was by year)
I seriously wonder if it is not a bit overkill. This computation cost a non-negligible amount of gas, and it is complex: it requires to ensure that there are no overflow in a computation up to a power of 12 (and it has also a limit when the linear variation is < -3).
Something simpler like
uint256 variationMultiplier = WAD_INT + linearVariation;
would not have those issues. I understand that we would lose the property that having multiple updates in an interval is the same as having one update at the end, but this is only a third order loss in the worst case:
It was already unclear for rates if it was worth the extra computation cost, it may be the case here that it's not worth at all
Originally posted by @QGarchery in #1 (comment)
with fixed rate irm
There is this idea by @QGarchery, and probably other ideas. I estimate the current two wExp to be responsible for a little bit more than half of the total gas cost of the borrowRate
function
A declarative, efficient, and flexible JavaScript library for building user interfaces.
๐ Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. ๐๐๐
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google โค๏ธ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.