Skip to content

Instantly share code, notes, and snippets.

@PanicWoo
Created December 18, 2020 13:44
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save PanicWoo/87f83b41d7affef7cbc8b30c055a21a0 to your computer and use it in GitHub Desktop.
Save PanicWoo/87f83b41d7affef7cbc8b30c055a21a0 to your computer and use it in GitHub Desktop.

Flash Loan Attack on Plouto Vault

The BlockSec Team, Zhejiang University, China

On 16th Dec 2020, our monitoring system ThunderForecast reported a series of suspicious transactions. Then, we used the EthScope system developed by our research team to analyze these transactions and confirmed that all reported transactions are malicious. In this blog, we illustrate the attack with rich details to help understand the intention of each behaviour of the attacker.

What is Plouto Vault?

Plouto is an open decentralized asset management protocol. Plouto protocol comes up with a key idea called "Open Vault". With this idea, except standard investing strategies, asset managers can also deploy their protocol with other third parties or even design their own strategies with Plouto Vault. In this attack, the attacker leveraged Plouto Vault's vulnerability that the minting token amount depends on the corresponding token amount at the YPool. Finally, the attacker arb out a total of 698,775.32 USD.

	function deposit(uint _amount) public {
    	uint _pool = balance();
    	uint _before = token.balanceOf(address(this));
    	token.safeTransferFrom(msg.sender, address(this), _amount);
    	uint _after = token.balanceOf(address(this));
    	_amount = _after.sub(_before);
    	uint shares = 0;
    	if (totalSupply() == 0) {
        	shares = _amount;
    	} else {
        	// Plouto mints LPs based on YPool's existing liquidity 
        	shares = (_amount.mul(totalSupply())).div(_pool);
 	   }
    	_mint(msg.sender, shares);
	}
 

Details

We now start revealing more details of this attack with one attack transaction0x49112d...

There are ten steps involved:

  • Step1: Take a flash loan of 9,000,000 USDC from AAVE.
  • Step2: Swap 9,000,000 USDC to 8,212,076.282 USDT at the YPool. The rate of this trade is: 1 USDT = 1.0959 USDC. In this step, the attacker manipulates the liquidity of USDC/USDT token pair at the YPool. All 9,000,000 borrowed USDC are used to drain YPool's USDT.
  • Step3: Take a flash loan of 2,000,000 USDT from UniswapV2.
  • Step4: Deposit 2,000,000 USDT into Plouto Vault and mint 4,221,996.36 pUSDT. The rate of this mint process is: 1 USDT = 2.1109 pUSDT. In this step, the attacker leverages the fact that the amount of offered pUSDT is depending on the existing amount of USDT at the YPool, to gain more pUSDT based on the manipulation in step 2.
  • Step 5: Swap 8,212,076.282 USDT to 8,990,779.02 USDC at the YPool. The rate of this trade is: 1 USDT = 1.0948 USDC. To maximize the profit of this manipulation, the attacker trades 8,212,076.282 USDT(which is gained in step 2) at the YPool. This step increases the volume of USDT at the YPool. Simultaneously, it increases the value of pUSDT at the Plouto Vault.
  • Step 6: Burn 4,221,996.36 pUSDT and withdraw 2,201,031.728 USDT. The rate of this burn process is: 1 USDT = 1.9181 pUSDT. Based on the manipulation in step 5, the attacker withdraws extra 201,0317.28 USDT in this step. As you can see, the rate of USDT/pUSDT token pair has an obvious difference.
  • Step 7: Return 2,006,200 USDT flash loan lent on UniswapV2.
  • Step 8: Swap 17,298 USDT to 17,320 USDC at the UniswapV2-USDT pool. The exchanged USDC is used to pay back the first flash loan lent on AAVE.
  • Step 9: Return 9,008,100 USDC flash loan lent on AAVE.
  • Step 10: Swap 177,533 USDC to 175,669 DAI and send the profit to the attacker's EOA.

Gain&Loss

In the transaction mentioned above, the attacker manipulates the liquidity of USDT at the YPool and arb out 175,669 DAI from Plouto Vault.

The scale of the attack

Based on the feature of the attack, we detect 1 malicious contract0x2421ce... and 8 transactions(The largest profit gained in transaction0x49112d... event reaches 175,669.88 USD) launched by the attacker0x43c162.... According to the data on Ehterscan, The attacker arb out a total of 698,775.32 USD.

The End

With the development of the DeFi ecosystem on Ethereum and the continuous updating of DeFi services (Flash Loan), security issues have gradually become prominent. Behind this attack, Flash Loan provided a lot of "convenience" for the attacker to implement liquidity manipulation. Recently, Harvest platform suffered from an attack which leverages a strong dependency built in between contracts.

Timeline

  • 2020/12/16: Found suspicious transactions
  • 2020/12/17: Finished the analysis
  • 2020/12/18: Details were released
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment