BOOK THIS SPACE FOR AD
ARTICLE ADOfficial report available here
The mStable Bug Bounty program has been active since just after launch, on 05th June. mStable began by offering rewards of up to 10k mUSD for finding bugs in the mStable Smart Contracts. This upper-end reward has since been increased to up to 25k mUSD as mStable has grown.
Reporter — Devan Purhar | Twitter | Staked
Full submission available here 🔗
This was not so much a bug, but a circumvention of our intended save mechanism and hits on one of our core areas of interest:
Unfair payouts through SAVE functionalities (related: contracts/savings/*)
We thank Devan for providing such a comprehensive and analytical report for us, and his continued professionalism as we dealt with the resolution to the addressed issue.
Official response and report from mStable available HERE 🔗
Fix implemented on mStable-contracts#98
Severity: Low-Moderate
Likelihood: Likely-Almost certain
Bounty: $1,000
The SAVE feature reflects value accrual through an exchange rate, which is updated by default every time a deposit to the SavingsContract.sol occurs if more than 30 minutes has passed since it was last updated. By natural flow, upon withdrawals, the exchange rate is never updated, however the function responsible for updating the exchange rate is unprotected, and can be called at any time and will update the exchange rate as long as the contract isn’t “paused” and it’s been greater than 30 minutes since the last update. Any party can see and get the “last collection” timestamp.
Vulnerability
Any party can exploit the stale exchange rate mechanism by depositing at an artificially lower value, manually updating it, then withdrawing at the updated value. I focus on the scenario where the attacking parties already hold an mAsset. They do as they wish with their mAsset for 97% (29/30 minutes) of the time, and the other 3% carry out this attack. However, it’s also possible they’re not in the mStable system at all for 97% of the time, but in other external assets such as Dai, USDC, etc. The only change that makes is increasing the cost of the attack, as we need to include the cost for mint and burn transactions of the mAsset.
Resolution
Removes the blocker on collecting interest more than once in 30 minute period.
Retains existing ‘extrapolatedAPY’ calculations when it has been longer than 30 minutes since the last interest collection.
If it has been less than 30 minutes, it simply checks that the supply has not inflated by more than 0.1% (or 1e15) during that PERIOD (30 mins). At a 0.1% ‘SWAP’ fee, this would mean that the total supply of the mAsset would need to be swapped between the two collections, if this were to be hit.