Skip to content

Commit

Permalink
Tasks: Optimize contract size (#110)
Browse files Browse the repository at this point in the history
  • Loading branch information
facuspagnuolo committed Oct 19, 2023
1 parent 2c92a19 commit 295870c
Show file tree
Hide file tree
Showing 17 changed files with 277 additions and 416 deletions.
12 changes: 10 additions & 2 deletions packages/tasks/contracts/base/BaseTask.sol
Original file line number Diff line number Diff line change
Expand Up @@ -31,10 +31,10 @@ abstract contract BaseTask is IBaseTask, Authorized {
address public override smartVault;

// Optional balance connector id for the previous task in the workflow
bytes32 public override previousBalanceConnectorId;
bytes32 internal previousBalanceConnectorId;

// Optional balance connector id for the next task in the workflow
bytes32 public override nextBalanceConnectorId;
bytes32 internal nextBalanceConnectorId;

/**
* @dev Base task config. Only used in the initializer.
Expand Down Expand Up @@ -85,6 +85,14 @@ abstract contract BaseTask is IBaseTask, Authorized {
return ISmartVault(smartVault).getBalanceConnector(previousBalanceConnectorId, token);
}

/**
* @dev Tells the previous and next balance connectors id of the previous task in the workflow
*/
function getBalanceConnectors() external view returns (bytes32 previous, bytes32 next) {
previous = previousBalanceConnectorId;
next = nextBalanceConnectorId;
}

/**
* @dev Sets the balance connectors
* @param previous Balance connector id of the previous task in the workflow
Expand Down
123 changes: 47 additions & 76 deletions packages/tasks/contracts/base/GasLimitedTask.sol
Original file line number Diff line number Diff line change
Expand Up @@ -30,20 +30,11 @@ abstract contract GasLimitedTask is IGasLimitedTask, Authorized {
// solhint-disable-next-line var-name-mixedcase
uint256 private __initialGas__;

// Gas price limit expressed in the native token
uint256 public override gasPriceLimit;

// Priority fee limit expressed in the native token
uint256 public override priorityFeeLimit;

// Total transaction cost limit expressed in the native token
uint256 public override txCostLimit;

// Transaction cost limit percentage
uint256 public override txCostLimitPct;
// Gas limits config
GasLimitConfig internal gasLimits;

/**
* @dev Gas limit config params. Only used in the initializer.
* @dev Gas limits config
* @param gasPriceLimit Gas price limit expressed in the native token
* @param priorityFeeLimit Priority fee limit expressed in the native token
* @param txCostLimit Transaction cost limit to be set
Expand All @@ -69,42 +60,34 @@ abstract contract GasLimitedTask is IGasLimitedTask, Authorized {
* @param config Gas limited task config
*/
function __GasLimitedTask_init_unchained(GasLimitConfig memory config) internal onlyInitializing {
_setGasPriceLimit(config.gasPriceLimit);
_setPriorityFeeLimit(config.priorityFeeLimit);
_setTxCostLimit(config.txCostLimit);
_setTxCostLimitPct(config.txCostLimitPct);
_setGasLimits(config.gasPriceLimit, config.priorityFeeLimit, config.txCostLimit, config.txCostLimitPct);
}

/**
* @dev Sets the gas price limit
* @param newGasPriceLimit New gas price limit to be set
* @dev Tells the gas limits config
*/
function setGasPriceLimit(uint256 newGasPriceLimit) external override authP(authParams(newGasPriceLimit)) {
_setGasPriceLimit(newGasPriceLimit);
function getGasLimits()
external
view
returns (uint256 gasPriceLimit, uint256 priorityFeeLimit, uint256 txCostLimit, uint256 txCostLimitPct)
{
return (gasLimits.gasPriceLimit, gasLimits.priorityFeeLimit, gasLimits.txCostLimit, gasLimits.txCostLimitPct);
}

/**
* @dev Sets the priority fee limit
* @dev Sets the gas limits config
* @param newGasPriceLimit New gas price limit to be set
* @param newPriorityFeeLimit New priority fee limit to be set
* @param newTxCostLimit New tx cost limit to be set
* @param newTxCostLimitPct New tx cost percentage limit to be set
*/
function setPriorityFeeLimit(uint256 newPriorityFeeLimit) external override authP(authParams(newPriorityFeeLimit)) {
_setPriorityFeeLimit(newPriorityFeeLimit);
}

/**
* @dev Sets the transaction cost limit
* @param newTxCostLimit New transaction cost limit to be set
*/
function setTxCostLimit(uint256 newTxCostLimit) external override authP(authParams(newTxCostLimit)) {
_setTxCostLimit(newTxCostLimit);
}

/**
* @dev Sets the transaction cost limit percentage
* @param newTxCostLimitPct New transaction cost limit percentage to be set
*/
function setTxCostLimitPct(uint256 newTxCostLimitPct) external override authP(authParams(newTxCostLimitPct)) {
_setTxCostLimitPct(newTxCostLimitPct);
function setGasLimits(
uint256 newGasPriceLimit,
uint256 newPriorityFeeLimit,
uint256 newTxCostLimit,
uint256 newTxCostLimitPct
) external override authP(authParams(newGasPriceLimit, newPriorityFeeLimit, newTxCostLimit, newTxCostLimitPct)) {
_setGasLimits(newGasPriceLimit, newPriorityFeeLimit, newTxCostLimit, newTxCostLimitPct);
}

/**
Expand All @@ -117,12 +100,13 @@ abstract contract GasLimitedTask is IGasLimitedTask, Authorized {
*/
function _beforeGasLimitedTask(address, uint256) internal virtual {
__initialGas__ = gasleft();
bool isGasPriceAllowed = gasPriceLimit == 0 || tx.gasprice <= gasPriceLimit;
if (!isGasPriceAllowed) revert TaskGasPriceLimitExceeded(tx.gasprice, gasPriceLimit);
GasLimitConfig memory config = gasLimits;
bool isGasPriceAllowed = config.gasPriceLimit == 0 || tx.gasprice <= config.gasPriceLimit;
if (!isGasPriceAllowed) revert TaskGasPriceLimitExceeded(tx.gasprice, config.gasPriceLimit);

uint256 priorityFee = tx.gasprice - block.basefee;
bool isPriorityFeeAllowed = priorityFeeLimit == 0 || priorityFee <= priorityFeeLimit;
if (!isPriorityFeeAllowed) revert TaskPriorityFeeLimitExceeded(priorityFee, priorityFeeLimit);
bool isPriorityFeeAllowed = config.priorityFeeLimit == 0 || priorityFee <= config.priorityFeeLimit;
if (!isPriorityFeeAllowed) revert TaskPriorityFeeLimitExceeded(priorityFee, config.priorityFeeLimit);
}

/**
Expand All @@ -131,53 +115,40 @@ abstract contract GasLimitedTask is IGasLimitedTask, Authorized {
function _afterGasLimitedTask(address token, uint256 amount) internal virtual {
if (__initialGas__ == 0) revert TaskGasNotInitialized();

GasLimitConfig memory config = gasLimits;
uint256 totalGas = __initialGas__ - gasleft();
uint256 totalCost = totalGas * tx.gasprice;
if (txCostLimit > 0 && totalCost > txCostLimit) revert TaskTxCostLimitExceeded(totalCost, txCostLimit);
bool isTxCostAllowed = config.txCostLimit == 0 || totalCost <= config.txCostLimit;
if (!isTxCostAllowed) revert TaskTxCostLimitExceeded(totalCost, config.txCostLimit);
delete __initialGas__;

if (txCostLimitPct > 0 && amount > 0) {
if (config.txCostLimitPct > 0 && amount > 0) {
uint256 price = _getPrice(ISmartVault(this.smartVault()).wrappedNativeToken(), token);
uint256 totalCostInToken = totalCost.mulUp(price);
uint256 txCostPct = totalCostInToken.divUp(amount);
if (txCostPct > txCostLimitPct) revert TaskTxCostLimitPctExceeded(txCostPct, txCostLimitPct);
if (txCostPct > config.txCostLimitPct) revert TaskTxCostLimitPctExceeded(txCostPct, config.txCostLimitPct);
}
}

/**
* @dev Sets the gas price limit
* @dev Sets the gas limits config
* @param newGasPriceLimit New gas price limit to be set
*/
function _setGasPriceLimit(uint256 newGasPriceLimit) internal {
gasPriceLimit = newGasPriceLimit;
emit GasPriceLimitSet(newGasPriceLimit);
}

/**
* @dev Sets the priority fee limit
* @param newPriorityFeeLimit New priority fee limit to be set
* @param newTxCostLimit New tx cost limit to be set
* @param newTxCostLimitPct New tx cost percentage limit to be set
*/
function _setPriorityFeeLimit(uint256 newPriorityFeeLimit) internal {
priorityFeeLimit = newPriorityFeeLimit;
emit PriorityFeeLimitSet(newPriorityFeeLimit);
}

/**
* @dev Sets the transaction cost limit
* @param newTxCostLimit New transaction cost limit to be set
*/
function _setTxCostLimit(uint256 newTxCostLimit) internal {
txCostLimit = newTxCostLimit;
emit TxCostLimitSet(newTxCostLimit);
}

/**
* @dev Sets the transaction cost limit percentage
* @param newTxCostLimitPct New transaction cost limit percentage to be set
*/
function _setTxCostLimitPct(uint256 newTxCostLimitPct) internal {
function _setGasLimits(
uint256 newGasPriceLimit,
uint256 newPriorityFeeLimit,
uint256 newTxCostLimit,
uint256 newTxCostLimitPct
) internal {
if (newTxCostLimitPct > FixedPoint.ONE) revert TaskTxCostLimitPctAboveOne();
txCostLimitPct = newTxCostLimitPct;
emit TxCostLimitPctSet(newTxCostLimitPct);

gasLimits.gasPriceLimit = newGasPriceLimit;
gasLimits.priorityFeeLimit = newPriorityFeeLimit;
gasLimits.txCostLimit = newTxCostLimit;
gasLimits.txCostLimitPct = newTxCostLimitPct;
emit GasLimitsSet(newGasPriceLimit, newPriorityFeeLimit, newTxCostLimit, newTxCostLimitPct);
}
}
89 changes: 59 additions & 30 deletions packages/tasks/contracts/base/TokenThresholdTask.sol
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,15 @@ abstract contract TokenThresholdTask is ITokenThresholdTask, Authorized {
// Custom thresholds per token
mapping (address => Threshold) internal _customThresholds;

/**
* @dev Threshold defined by a token address and min/max values
*/
struct Threshold {
address token;
uint256 min;
uint256 max;
}

/**
* @dev Custom token threshold config. Only used in the initializer.
*/
Expand Down Expand Up @@ -78,66 +87,88 @@ abstract contract TokenThresholdTask is ITokenThresholdTask, Authorized {
/**
* @dev Tells the default token threshold
*/
function defaultTokenThreshold() external view override returns (Threshold memory) {
return _defaultThreshold;
function defaultTokenThreshold() external view override returns (address thresholdToken, uint256 min, uint256 max) {
Threshold memory threshold = _defaultThreshold;
return (threshold.token, threshold.min, threshold.max);
}

/**
* @dev Tells the token threshold defined for a specific token
* @param token Address of the token being queried
*/
function customTokenThreshold(address token) public view override returns (Threshold memory) {
return _customThresholds[token];
function customTokenThreshold(address token)
external
view
override
returns (address thresholdToken, uint256 min, uint256 max)
{
Threshold memory threshold = _customThresholds[token];
return (threshold.token, threshold.min, threshold.max);
}

/**
* @dev Tells the threshold that should be used for a token, it prioritizes custom thresholds over the default one
* @param token Address of the token being queried
*/
function getTokenThreshold(address token) public view virtual override returns (Threshold memory) {
Threshold storage customThreshold = _customThresholds[token];
return customThreshold.token == address(0) ? _defaultThreshold : customThreshold;
function getTokenThreshold(address token)
external
view
virtual
override
returns (address thresholdToken, uint256 min, uint256 max)
{
Threshold memory threshold = _getTokenThreshold(token);
return (threshold.token, threshold.min, threshold.max);
}

/**
* @dev Sets a new default threshold config
* @param thresholdToken New threshold token to be set
* @param thresholdMin New threshold minimum to be set
* @param thresholdMax New threshold maximum to be set
* @param min New threshold minimum to be set
* @param max New threshold maximum to be set
*/
function setDefaultTokenThreshold(address thresholdToken, uint256 thresholdMin, uint256 thresholdMax)
function setDefaultTokenThreshold(address thresholdToken, uint256 min, uint256 max)
external
override
authP(authParams(thresholdToken, thresholdMin, thresholdMax))
authP(authParams(thresholdToken, min, max))
{
_setDefaultTokenThreshold(thresholdToken, thresholdMin, thresholdMax);
_setDefaultTokenThreshold(thresholdToken, min, max);
}

/**
* @dev Sets a custom token threshold
* @param token Address of the token to set a custom threshold for
* @param thresholdToken New custom threshold token to be set
* @param thresholdMin New custom threshold minimum to be set
* @param thresholdMax New custom threshold maximum to be set
* @param min New custom threshold minimum to be set
* @param max New custom threshold maximum to be set
*/
function setCustomTokenThreshold(address token, address thresholdToken, uint256 thresholdMin, uint256 thresholdMax)
function setCustomTokenThreshold(address token, address thresholdToken, uint256 min, uint256 max)
external
override
authP(authParams(token, thresholdToken, thresholdMin, thresholdMax))
authP(authParams(token, thresholdToken, min, max))
{
_setCustomTokenThreshold(token, thresholdToken, thresholdMin, thresholdMax);
_setCustomTokenThreshold(token, thresholdToken, min, max);
}

/**
* @dev Fetches a base/quote price
*/
function _getPrice(address base, address quote) internal view virtual returns (uint256);

/**
* @dev Tells the threshold that should be used for a token, it prioritizes custom thresholds over the default one
* @param token Address of the token being queried
*/
function _getTokenThreshold(address token) internal view returns (Threshold memory) {
Threshold storage customThreshold = _customThresholds[token];
return customThreshold.token == address(0) ? _defaultThreshold : customThreshold;
}

/**
* @dev Before token threshold task hook
*/
function _beforeTokenThresholdTask(address token, uint256 amount) internal virtual {
Threshold memory threshold = getTokenThreshold(token);
Threshold memory threshold = _getTokenThreshold(token);
if (threshold.token == address(0)) return;

uint256 convertedAmount = threshold.token == token ? amount : amount.mulDown(_getPrice(token, threshold.token));
Expand All @@ -155,27 +186,25 @@ abstract contract TokenThresholdTask is ITokenThresholdTask, Authorized {
/**
* @dev Sets a new default threshold config
* @param thresholdToken New threshold token to be set
* @param thresholdMin New threshold minimum to be set
* @param thresholdMax New threshold maximum to be set
* @param min New threshold minimum to be set
* @param max New threshold maximum to be set
*/
function _setDefaultTokenThreshold(address thresholdToken, uint256 thresholdMin, uint256 thresholdMax) internal {
_setTokenThreshold(_defaultThreshold, thresholdToken, thresholdMin, thresholdMax);
emit DefaultTokenThresholdSet(thresholdToken, thresholdMin, thresholdMax);
function _setDefaultTokenThreshold(address thresholdToken, uint256 min, uint256 max) internal {
_setTokenThreshold(_defaultThreshold, thresholdToken, min, max);
emit DefaultTokenThresholdSet(thresholdToken, min, max);
}

/**
* @dev Sets a custom of tokens thresholds
* @param token Address of the token to set a custom threshold for
* @param thresholdToken New custom threshold token to be set
* @param thresholdMin New custom threshold minimum to be set
* @param thresholdMax New custom threshold maximum to be set
* @param min New custom threshold minimum to be set
* @param max New custom threshold maximum to be set
*/
function _setCustomTokenThreshold(address token, address thresholdToken, uint256 thresholdMin, uint256 thresholdMax)
internal
{
function _setCustomTokenThreshold(address token, address thresholdToken, uint256 min, uint256 max) internal {
if (token == address(0)) revert TaskThresholdTokenZero();
_setTokenThreshold(_customThresholds[token], thresholdToken, thresholdMin, thresholdMax);
emit CustomTokenThresholdSet(token, thresholdToken, thresholdMin, thresholdMax);
_setTokenThreshold(_customThresholds[token], thresholdToken, min, max);
emit CustomTokenThresholdSet(token, thresholdToken, min, max);
}

/**
Expand Down
Loading

0 comments on commit 295870c

Please sign in to comment.