From a792d5500fa9cc0a9b917425e042121bf60f5851 Mon Sep 17 00:00:00 2001 From: Hadrien Charlanes Date: Tue, 15 Jun 2021 16:14:58 +0200 Subject: [PATCH] feat: Added validate Repay check to revert if borrow/repay in same tx --- .../protocol/libraries/helpers/Errors.sol | 2 ++ .../libraries/logic/ValidationLogic.sol | 33 ++++++++++++++----- 2 files changed, 26 insertions(+), 9 deletions(-) diff --git a/contracts/protocol/libraries/helpers/Errors.sol b/contracts/protocol/libraries/helpers/Errors.sol index 4b0644f5..1da6c2ad 100644 --- a/contracts/protocol/libraries/helpers/Errors.sol +++ b/contracts/protocol/libraries/helpers/Errors.sol @@ -112,6 +112,8 @@ library Errors { string public constant RL_ATOKEN_SUPPLY_NOT_ZERO = '88'; string public constant RL_STABLE_DEBT_NOT_ZERO = '89'; string public constant RL_VARIABLE_DEBT_SUPPLY_NOT_ZERO = '90'; + string public constant VL_SAME_BLOCK_REPAY_AS_LAST_ACTION = '91'; + string public constant VL_NO_DEBT_ACCRUED_BY_CONTRACT = '92'; enum CollateralManagerErrors { NO_ERROR, diff --git a/contracts/protocol/libraries/logic/ValidationLogic.sol b/contracts/protocol/libraries/logic/ValidationLogic.sol index 26388f46..6890a278 100644 --- a/contracts/protocol/libraries/logic/ValidationLogic.sol +++ b/contracts/protocol/libraries/logic/ValidationLogic.sol @@ -9,6 +9,7 @@ import {GenericLogic} from './GenericLogic.sol'; import {WadRayMath} from '../math/WadRayMath.sol'; import {PercentageMath} from '../math/PercentageMath.sol'; import {SafeERC20} from '../../../dependencies/openzeppelin/contracts/SafeERC20.sol'; +import {Address} from '../../../dependencies/openzeppelin/contracts/Address.sol'; import {ReserveConfiguration} from '../configuration/ReserveConfiguration.sol'; import {UserConfiguration} from '../configuration/UserConfiguration.sol'; import {Errors} from '../helpers/Errors.sol'; @@ -32,6 +33,7 @@ library ValidationLogic { using WadRayMath for uint256; using PercentageMath for uint256; using SafeERC20 for IERC20; + using Address for address; using ReserveConfiguration for DataTypes.ReserveConfigurationMap; using UserConfiguration for DataTypes.UserConfigurationMap; @@ -259,20 +261,33 @@ library ValidationLogic { address onBehalfOf, uint256 stableDebt, uint256 variableDebt - ) internal view { + ) external view { (bool isActive, , , , bool isPaused) = reserveCache.reserveConfiguration.getFlagsMemory(); + require(isActive, Errors.VL_NO_ACTIVE_RESERVE); require(!isPaused, Errors.VL_RESERVE_PAUSED); require(amountSent > 0, Errors.VL_INVALID_AMOUNT); - require( - (stableDebt > 0 && - DataTypes.InterestRateMode(rateMode) == DataTypes.InterestRateMode.STABLE) || - (variableDebt > 0 && - DataTypes.InterestRateMode(rateMode) == DataTypes.InterestRateMode.VARIABLE), - Errors.VL_NO_DEBT_OF_SELECTED_TYPE - ); + if (DataTypes.InterestRateMode(rateMode) == DataTypes.InterestRateMode.STABLE) { + require(stableDebt > 0, Errors.VL_NO_DEBT_OF_SELECTED_TYPE); + + require( + IStableDebtToken(reserveCache.stableDebtTokenAddress).getUserLastUpdated(onBehalfOf) < + uint40(block.timestamp), + Errors.VL_SAME_BLOCK_REPAY_AS_LAST_ACTION + ); + } else if (DataTypes.InterestRateMode(rateMode) == DataTypes.InterestRateMode.VARIABLE) { + require(variableDebt > 0, Errors.VL_NO_DEBT_OF_SELECTED_TYPE); + require( + !onBehalfOf.isContract() || + IERC20(reserveCache.variableDebtTokenAddress).balanceOf(onBehalfOf) > + IVariableDebtToken(reserveCache.variableDebtTokenAddress) + .scaledBalanceOf(onBehalfOf) + .rayMul(reserveCache.currVariableBorrowIndex), + Errors.VL_NO_DEBT_ACCRUED_BY_CONTRACT + ); + } require( amountSent != uint256(-1) || msg.sender == onBehalfOf, @@ -283,7 +298,7 @@ library ValidationLogic { /** * @dev Validates a swap of borrow rate mode. * @param reserve The reserve state on which the user is swapping the rate - * @param reserveCache The cached data of the reserve + * @param reserveCache The cached data of the reserve * @param userConfig The user reserves configuration * @param stableDebt The stable debt of the user * @param variableDebt The variable debt of the user