code-423n4 / 2022-01-timeswap-findings

2 stars 0 forks source link

`TimeswapPair.sol#mint()` Lack of input validation allows attacker to set `pool.state.y` to an arbitrary target value #167

Closed code423n4 closed 2 years ago

code423n4 commented 2 years ago

Handle

WatchPug

Vulnerability details

https://github.com/code-423n4/2022-01-timeswap/blob/bf50d2a8bb93a5571f35f96bd74af54d9c92a210/Timeswap/Timeswap-V1-Core/contracts/TimeswapPair.sol#L186-L186

pool.state.y += yIncrease;

TimeswapPair.sol#mint() takes a user input value of yIncrease without proper validation, which means that it allows the state of pool.state.y to increase by the arbitrary value set by the caller.

Impact

LendMath.check(): https://github.com/code-423n4/2022-01-timeswap/blob/bf50d2a8bb93a5571f35f96bd74af54d9c92a210/Timeswap/Timeswap-V1-Core/contracts/libraries/LendMath.sol#L28-L28

BorrowMath.check(): https://github.com/code-423n4/2022-01-timeswap/blob/bf50d2a8bb93a5571f35f96bd74af54d9c92a210/Timeswap/Timeswap-V1-Core/contracts/libraries/BorrowMath.sol#L31-L31

  1. An attacker can set state.y to a near overflow value, then lend() to get a large amount of extra interest (as Bond tokens) with a small amount of asset tokens. This way, the attacker can steal funds from other lenders and liquidity providers.

PoC

Near the maturity time, the attacker can do the following:

  1. mint() with a dust amount of assets (xIncrease = 1 wei) and increase pool.state.y to an extremely large value;
  2. lend() a regular amount of assets, get a large amount of bond token;
  3. burn() the bond token and get a large portion of the assets.

Recommendation

Consider making pair.mint() to be onlyConvenience, so that yIncrease will be a computed value (based on xIncrease and current state) rather than a user input value.

Mathepreneur commented 2 years ago

Duplicate of #187