58396 sc high total locked is not cleared proportionally to the total debt this forces the collateral weight to become incorrect and new users transmuter redeem repayment will repay more debt fo
Description
Brief/Intro
Vulnerability Details
/// @inheritdoc IAlchemistV3Actions
function redeem(uint256 amount) external onlyTransmuter {
_earmark();
emit cumulativeguy(cumulativeEarmarked);
uint256 liveEarmarked = cumulativeEarmarked;
if (amount > liveEarmarked) amount = liveEarmarked;
// observed transmuter pre-balance -> potential cover
uint256 transmuterBal = TokenUtils.safeBalanceOf(myt, address(transmuter));
uint256 deltaYield = transmuterBal > lastTransmuterTokenBalance ? transmuterBal - lastTransmuterTokenBalance : 0;
uint256 coverDebt = convertYieldTokensToDebt(deltaYield);
// cap cover so we never consume beyond remaining earmarked
uint256 coverToApplyDebt = amount + coverDebt > liveEarmarked ? (liveEarmarked - amount) : coverDebt;
uint256 redeemedDebtTotal = amount + coverToApplyDebt;
// Apply redemption weights/decay to the full amount that left the earmarked bucket
if (liveEarmarked != 0 && redeemedDebtTotal != 0) {
uint256 survival = ((liveEarmarked - redeemedDebtTotal) << 128) / liveEarmarked;
_survivalAccumulator = _mulQ128(_survivalAccumulator, survival);
_redemptionWeight += PositionDecay.WeightIncrement(redeemedDebtTotal, cumulativeEarmarked);
}
// earmarks are reduced by the full redeemed amount (net + cover)
cumulativeEarmarked -= redeemedDebtTotal;
// global borrower debt falls by the full redeemed amount
totalDebt -= redeemedDebtTotal;
lastRedemptionBlock = block.number;
// consume the observed cover so it can't be reused
if (deltaYield != 0) {
uint256 usedYield = convertDebtTokensToYield(coverToApplyDebt);
lastTransmuterTokenBalance = transmuterBal > usedYield ? transmuterBal - usedYield : transmuterBal;
}
// move only the net collateral + fee
uint256 collRedeemed = convertDebtTokensToYield(amount); // total out is updated
uint256 feeCollateral = collRedeemed * protocolFee / BPS;
uint256 totalOut = collRedeemed + feeCollateral;
// uint256 newtotalLocked = (convertDebtTokensToYield(totalDebt) * minimumCollateralization) / FIXED_POINT_SCALAR;
// update locked collateral + collateral weight
uint256 old = _totalLocked;
@audit>>> _totalLocked = totalOut > old ? 0 : old - totalOut; // reduce this with th debt to amount ratio. that is debt in transmuter covered/
@audit>>> _collateralWeight += PositionDecay.WeightIncrement(totalOut > old ? old : totalOut, old); // test this well
TokenUtils.safeTransfer(myt, transmuter, collRedeemed);
TokenUtils.safeTransfer(myt, protocolFeeReceiver, feeCollateral);
_mytSharesDeposited -= collRedeemed + feeCollateral;
emit Redemption(redeemedDebtTotal);
}Impact Details
References
Proof of Concept
Proof of Concept
Previous56529 sc low incorrect token balance calculation in morphoyearnogwethstrategy sol deallocate leads to wrong event emitted every timeNext58428 sc low toke reward loss when calling deallocate
Was this helpful?