@@ -54,7 +54,11 @@ contract VaultManager is VaultManagerPermit, IVaultManagerFunctions {
5454 /// in a vault during a liquidation where the health factor function is decreasing
5555 uint256 internal _dustCollateral;
5656
57- uint256 [48 ] private __gapVaultManager;
57+ /// @notice If the amount of debt of a vault that gets liquidated is below this amount, then the liquidator
58+ /// can liquidate all the debt of the vault (and not just what's needed to get to the target health factor)
59+ uint256 public dustLiquidation;
60+
61+ uint256 [47 ] private __gapVaultManager;
5862
5963 /// @inheritdoc IVaultManagerFunctions
6064 function initialize (
@@ -719,6 +723,7 @@ contract VaultManager is VaultManagerPermit, IVaultManagerFunctions {
719723 // Because we're rounding up in some divisions, `collateralReleased` can be greater than the `collateralAmount` of the vault
720724 // In this case, `stablecoinAmountToReceive` is still rounded up
721725 if (vault.collateralAmount <= collateralReleased) {
726+ // Liquidators should never get more collateral than what's in the vault
722727 collateralReleased = vault.collateralAmount;
723728 // Remove all the vault's debt (debt repayed + bad debt) from VaultManager totalDebt
724729 totalNormalizedDebt -= vault.normalizedDebt;
@@ -778,12 +783,11 @@ contract VaultManager is VaultManagerPermit, IVaultManagerFunctions {
778783 : BASE_PARAMS - liquidationDiscount;
779784 // Same for the surcharge here: it's in fact 1 - the fee taken by the protocol
780785 uint256 surcharge = liquidationSurcharge;
781- // Checking if we're in a situation where the health factor is an increasing or a decreasing function of the
782- // amount repaid
783786 uint256 maxAmountToRepay;
784787 uint256 thresholdRepayAmount;
785- // In the first case, the health factor is an increasing function of the stablecoin amount to repay,
786- // this means that the liquidator can bring the vault to the target health ratio
788+ // Checking if we're in a situation where the health factor is an increasing or a decreasing function of the
789+ // amount repaid. In the first case, the health factor is an increasing function which means that the liquidator
790+ // can bring the vault to the target health ratio
787791 if (healthFactor * liquidationDiscount * surcharge >= collateralFactor * BASE_PARAMS** 2 ) {
788792 // This is the max amount to repay that will bring the person to the target health factor
789793 // Denom is always positive when a vault gets liquidated in this case and when the health factor
@@ -794,32 +798,27 @@ contract VaultManager is VaultManagerPermit, IVaultManagerFunctions {
794798 BASE_PARAMS *
795799 liquidationDiscount) /
796800 (surcharge * targetHealthFactor * liquidationDiscount - (BASE_PARAMS** 2 ) * collateralFactor);
797- // The quantity below tends to be rounded in the above direction, which means that governance or guardians should
798- // set the `targetHealthFactor` accordingly
799- // Need to check for the dust: liquidating should not leave a dusty amount in the vault
800- if (currentDebt * BASE_PARAMS <= maxAmountToRepay * surcharge + dust * BASE_PARAMS) {
801- // If liquidating to the target threshold would leave a dusty amount: the liquidator can repay all
802- // We're rounding up the max amount to repay to make sure all the debt ends up being paid
803- // and we're computing again the real value of the debt to avoid propagation of rounding errors
801+ // Need to check for the dustas liquidating should not leave a dusty amount in the vault
802+ uint256 dustParameter = dustLiquidation;
803+ if (currentDebt * BASE_PARAMS <= maxAmountToRepay * surcharge + dustParameter * BASE_PARAMS) {
804+ // If liquidating to the target threshold would leave a dusty amount: the liquidator can repay all.
805+ // We're avoiding here propagation of rounding errors and rounding up the max amount to repay to make
806+ // sure all the debt ends up being paid
804807 maxAmountToRepay =
805808 (vault.normalizedDebt * newInterestAccumulator * BASE_PARAMS) /
806809 (surcharge * BASE_INTEREST) +
807810 1 ;
808811 // In this case the threshold amount is such that it leaves just enough dust: amount is rounded
809- // down such that if a liquidator repays this amount then there would be more than `dust ` left in
812+ // down such that if a liquidator repays this amount then there is more than `dustLiquidation ` left in
810813 // the liquidated vault
811- if (currentDebt > dust)
812- thresholdRepayAmount = ((currentDebt - dust) * BASE_PARAMS) / surcharge;
813- // If there is from the beginning a dusty debt (because of an implementation upgrade), then
814- // liquidator should repay everything that's left
814+ if (currentDebt > dustParameter)
815+ thresholdRepayAmount = ((currentDebt - dustParameter) * BASE_PARAMS) / surcharge;
816+ // If there is from the beginning a dusty debt, then liquidator should repay everything that's left
815817 else thresholdRepayAmount = 1 ;
816818 }
817819 } else {
818- // In all cases the liquidator can repay stablecoins such that they'll end up getting exactly the collateral
820+ // In this case, the liquidator can repay stablecoins such that they'll end up getting exactly the collateral
819821 // in the liquidated vault
820- // Rounding up to make sure all gets liquidated in this case: the liquidator will never get more than the collateral
821- // amount in the vault however: we're performing the computation of the `collateralAmountInStable` again to avoid
822- // propagation of rounding errors
823822 maxAmountToRepay =
824823 (vault.collateralAmount * liquidationDiscount * oracleValue) /
825824 (BASE_PARAMS * _collatBase) +
@@ -864,7 +863,7 @@ contract VaultManager is VaultManagerPermit, IVaultManagerFunctions {
864863 borrowFee = param;
865864 } else if (what == "RF " ) {
866865 // As liquidation surcharge is stored as `1-fee` and as we need `repayFee` to be smaller
867- // then the liquidation surcharge, then we need to have:
866+ // than the liquidation surcharge, we need to have:
868867 // `liquidationSurcharge <= BASE_PARAMS - repayFee` and as such `liquidationSurcharge + repayFee <= BASE_PARAMS`
869868 if (param + liquidationSurcharge > BASE_PARAMS) revert TooHighParameterValue ();
870869 repayFee = param;
@@ -933,10 +932,17 @@ contract VaultManager is VaultManagerPermit, IVaultManagerFunctions {
933932
934933 /// @notice Sets the dust variables
935934 /// @param _dust New minimum debt allowed
935+ /// @param _dustLiquidation New `dustLiquidation` value
936936 /// @param dustCollateral_ New minimum collateral allowed in a vault after a liquidation
937937 /// @dev dustCollateral_ is in stable value
938- function setDusts (uint256 _dust , uint256 dustCollateral_ ) external onlyGovernor {
938+ function setDusts (
939+ uint256 _dust ,
940+ uint256 _dustLiquidation ,
941+ uint256 dustCollateral_
942+ ) external onlyGovernor {
943+ if (_dust > _dustLiquidation) revert InvalidParameterValue ();
939944 dust = _dust;
945+ dustLiquidation = _dustLiquidation;
940946 _dustCollateral = dustCollateral_;
941947 }
942948
0 commit comments