Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

IF THE UNDERLYING ASSET IS A FEE ON TRANSFER TOKEN IT COULD BREAK THE INTERNAL ACCOUNTING OF THE VAULT #470

Open
code423n4 opened this issue Jul 14, 2023 · 10 comments
Labels
2 (Med Risk) Assets not at direct risk, but function/availability of the protocol could be impacted or leak value bug Something isn't working M-01 primary issue Highest quality submission among a set of duplicates satisfactory satisfies C4 submission criteria; eligible for awards selected for report This submission will be included/highlighted in the audit report sponsor confirmed Sponsor agrees this is a problem and intends to fix it (OK to use w/ "disagree with severity")

Comments

@code423n4
Copy link
Contributor

Lines of code

https://github.com/GenerationSoftware/pt-v5-vault/blob/b1deb5d494c25f885c34c83f014c8a855c5e2749/src/Vault.sol#L951-L956
https://github.com/GenerationSoftware/pt-v5-vault/blob/b1deb5d494c25f885c34c83f014c8a855c5e2749/src/Vault.sol#L959
https://github.com/GenerationSoftware/pt-v5-vault/blob/b1deb5d494c25f885c34c83f014c8a855c5e2749/src/Vault.sol#L1026-L1027

Vulnerability details

Impact

The Vault._deposit function is used by the users to deposit _assets to the vault and mint vault shares to the recipient address. The amount of _assets are transferred to the Vault as follows:

  SafeERC20.safeTransferFrom(
    _asset,
    _caller,
    address(this),
    _assetsDeposit != 0 ? _assetsDeposit : _assets
  );

The Vault.deposit function uses this _assets amount to calculate the number of shares to be minted to the _recipient address.

The issue here is if the underlying _asset is a fee on transfer token then the actual received amount to the vault will be less than what is referred in the Vault.deposit function _assets input parameter. But the shares to mint is calculated using the entire _assets amount.

This issue could be further aggravated since the _asset is again deposited to the _yieldVault and when needing to be redeemed will be withdrawn from the _yieldVault as well. These operations will again charge a fee if the _asset is a fee on transfer token. Hence the actual left _asset amount for particular user will be less than the amount he initially transferred in.

Hence when the user redeems the minted shares back to the _assets, the contract will not have enough assets to transfer to the redeemer thus reverting the transaction.

Proof of Concept

      SafeERC20.safeTransferFrom(
        _asset,
        _caller,
        address(this),
        _assetsDeposit != 0 ? _assetsDeposit : _assets
      );

https://github.com/GenerationSoftware/pt-v5-vault/blob/b1deb5d494c25f885c34c83f014c8a855c5e2749/src/Vault.sol#L951-L956

    _yieldVault.deposit(_assets, address(this));

https://github.com/GenerationSoftware/pt-v5-vault/blob/b1deb5d494c25f885c34c83f014c8a855c5e2749/src/Vault.sol#L959

    _yieldVault.withdraw(_assets, address(this), address(this));
    SafeERC20.safeTransfer(IERC20(asset()), _receiver, _assets);

https://github.com/GenerationSoftware/pt-v5-vault/blob/b1deb5d494c25f885c34c83f014c8a855c5e2749/src/Vault.sol#L1026-L1027

Tools Used

Manual Review and VSCode

Recommended Mitigation Steps

Hence it is recommended to compute the _assets amount balance of the contract before and after the safeTransferFrom call and get the difference between the two as the actually transferred amount to the Vault. Then this actually transferred amount can be converted to shares and mint the correct amount of shares to the recipient.

  uint256 balanceBefore = _asset.balanceOf(address(this));

      SafeERC20.safeTransferFrom(
        _asset,
        _caller,
        address(this),
        _assetsDeposit != 0 ? _assetsDeposit : _assets
      );

  uint256 balanceAfter = _asset.balanceOf(address(this));  

  uint256 transferredAmount = balanceAfter - balanceBefore;

Assessed type

Other

@code423n4 code423n4 added 2 (Med Risk) Assets not at direct risk, but function/availability of the protocol could be impacted or leak value bug Something isn't working labels Jul 14, 2023
code423n4 added a commit that referenced this issue Jul 14, 2023
@c4-judge
Copy link
Contributor

Picodes marked the issue as primary issue

@c4-judge c4-judge added the primary issue Highest quality submission among a set of duplicates label Jul 16, 2023
@c4-sponsor c4-sponsor added the sponsor confirmed Sponsor agrees this is a problem and intends to fix it (OK to use w/ "disagree with severity") label Jul 20, 2023
@c4-sponsor
Copy link

asselstine marked the issue as sponsor confirmed

@c4-judge c4-judge added the satisfactory satisfies C4 submission criteria; eligible for awards label Aug 7, 2023
@c4-judge
Copy link
Contributor

c4-judge commented Aug 7, 2023

Picodes marked the issue as satisfactory

@c4-judge c4-judge added the selected for report This submission will be included/highlighted in the audit report label Aug 7, 2023
@c4-judge
Copy link
Contributor

c4-judge commented Aug 7, 2023

Picodes marked the issue as selected for report

@Picodes
Copy link

Picodes commented Aug 8, 2023

Out of scope per the automated report: https://gist.github.com/itsmetechjay/e7fd03943bbacff1984a33b9f89c4149 (MEDIUM-4)

@c4-judge c4-judge closed this as completed Aug 8, 2023
@c4-judge
Copy link
Contributor

c4-judge commented Aug 8, 2023

Picodes marked the issue as unsatisfactory:
Out of scope

@c4-judge c4-judge added unsatisfactory does not satisfy C4 submission criteria; not eligible for awards and removed satisfactory satisfies C4 submission criteria; eligible for awards selected for report This submission will be included/highlighted in the audit report labels Aug 8, 2023
@udsene
Copy link

udsene commented Aug 10, 2023

@Picodes, The fee on transfer token vulnerability described in this issue (#470) is related to the token transfers happening in the Vault.sol contract. How the fee charged on token transfers could effect the Vault._deposit , _yieldVault.deposit and _yieldVault.withdraw functions.

The MEDIUM-4 given in the automated report has found one instance of this vulnerability (fee on token transfer) and it is related to the PrizePool.sol contract and not the Vault.sol contract. It is not the same vulnerability present in the #470 issue.

@Picodes
Copy link

Picodes commented Aug 12, 2023

Indeed. The automated report didn't properly flag that Vault.sol won't work with FoT.

@c4-judge
Copy link
Contributor

Picodes marked the issue as selected for report

@c4-judge c4-judge reopened this Aug 12, 2023
@c4-judge c4-judge added selected for report This submission will be included/highlighted in the audit report and removed unsatisfactory does not satisfy C4 submission criteria; not eligible for awards labels Aug 12, 2023
@c4-judge
Copy link
Contributor

Picodes marked the issue as satisfactory

@c4-judge c4-judge added the satisfactory satisfies C4 submission criteria; eligible for awards label Aug 12, 2023
@C4-Staff C4-Staff added the M-01 label Aug 15, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
2 (Med Risk) Assets not at direct risk, but function/availability of the protocol could be impacted or leak value bug Something isn't working M-01 primary issue Highest quality submission among a set of duplicates satisfactory satisfies C4 submission criteria; eligible for awards selected for report This submission will be included/highlighted in the audit report sponsor confirmed Sponsor agrees this is a problem and intends to fix it (OK to use w/ "disagree with severity")
Projects
None yet
Development

No branches or pull requests

6 participants