Em 18 de julho, nosso sistema DeFiRanger reportou algumas transações suspeitas. Após análise manual, confirmamos que essas transações são ataques à Array Finance. A seguir, usaremos uma transação de ataque para ilustrar o processo de ataque e a causa raiz da vulnerabilidade.
Transação de Ataque
A transação de ataque utilizada neste blog é: 0xa17bbc7c9ab17aa88fdb5de83b41de982845e9c9c072efff6709dd29febf0daa
Fluxo do Ataque

Conforme mostrado na Figura 1, descobrimos que o atacante obteve um lucro de 186,62 WETH (não distinguimos explicitamente entre WETH e ETH neste blog) após tomar emprestado o flash loan da AAVE.

O processo detalhado do ataque é mostrado na Figura 2.
- Primeiro, o atacante invocou a função
buyda Array Finance. O atacante obteve 430 tokens ARRAY cunhados pela Array Finance usando 45,91 WETH. - Em seguida, o atacante invocou a função
joinPoolde um contrato de código fechado (Array Collater - 0xa800cda5) cinco vezes. Ele/ela depositou 676.410,58 DAI + 679.080,46 USDC + 901,82 WETH + 20 WBTC + 20 renBTC e obteve 726,38 tokens aBPT cunhados pelo Array Collater. - O atacante invocou a função
sellpara queimar 430 tokens ARRAY e obteve 77,17 tokens aBPT. - Por fim, o atacante invocou a função
exitPooldo Array Collater. Ele/ela queimou 804,55 tokens aBPT obtidos nas duas etapas anteriores e obteve 748.271,55 DAI + 751.225,08 USDC + 997,62 WETH + 22,63 WBTC + 22,74 renBTC.
Pela Figura 2, podemos ver que o atacante obtém lucros na etapa 5 (Figura 2: Invocar a função sell). Isso ocorre porque os 77,17 tokens aBPT obtidos são mais valiosos do que os 49,9142 WETH depositados na etapa 3 (Figura 2: Invocar a função buy). A seguir, analisaremos o código para entender por que esse ataque pode acontecer.
Vulnerabilidade no Código
O código a seguir mostra a função sell da Array Finance. Nesta função, a Array Finance usa o saldo do token ARRAY de propriedade do atacante e invoca a função interna _sell para calcular o número de tokens aBPT que podem ser obtidos ao vender o token ARRAY.

A seguir está a implementação da função _sell. Ela invoca a calculateLPtokensGivenArrayTokens para obter o número de tokens aBPT que podem ser ganhos dado um certo número de tokens ARRAY. Em seguida, essa função queima o token ARRAY e retorna o token aBPT.

A seguir está a implementação da função calculateLPtokensGivenArrayTokens.

Observe que há quatro argumentos que podem afetar o cálculo de amountLPToken. Após ler o saleTargetAmount, inferimos que a fórmula é a seguinte:
arraySmartPool.totalSupply() * (1 - (1 - amount / ARRAY.totalSupply()) ^ (1000000 / reseveRatio))
O arraySmartPool é o endereço do contrato inteligente do Array Collater (0xa800cda5f3416a6fb64ef93d84d6298a685d190d). O valor de arraySmartPool.totalSupply() aumentará quando o atacante depositar fundos emprestados do flash loan no Array Collater (mostrado na tabela a seguir).
TxnIndex: 64 arraySmartPool.totalSupply(): 110162296218708026400
TxnIndex: 107 arraySmartPool.totalSupply(): 165243444328062039600
TxnIndex: 150 arraySmartPool.totalSupply(): 247865166492093059400
TxnIndex: 193 arraySmartPool.totalSupply(): 371797749738139589100
TxnIndex: 236 arraySmartPool.totalSupply(): 557696624607209383650
TxnIndex: 280 arraySmartPool.totalSupply(): 836544936910814075475
Podemos confirmar essa lógica após ler o código do arraySmartPool. A seguir está a função joinPool do arraySmartPool.

Essa função primeiro invoca a função SmartPoolManager.joinPool para calcular o número de tokens (actualAmountsIn) que precisam ser obtidos do msg.sender. Em seguida, para cada token, ela invoca a função _pullUnderlying para depositar o token no arraySmartPool. Por fim, ela invoca o _mintPoolShare e o _pushPoolShare para cunhar o token aBPT e transferir o token aBPT cunhado para o msg.sender.
Observe que o arraySmartPool herda do PCToken. A função _mintPoolShare invoca a função _mint, que é mostrada a seguir.
A função _mint aumentará a variável varTotalSupply, que é retornada diretamente pelo totalSupply(). Portanto, esse valor é incrementado a cada invocação do joinPool.
Estimativa de Lucro
| Endereço do atacante | Transação de ataque | Lucro (ETH) |
|---|---|---|
| 0x1337 | 0xa17bbc7c9ab17aa88fdb5de83b41de982845e9c9c072efff6709dd29febf0daa | 186.62073907323577 |
| 0x1b4fb735b51a25b280499710d02f50e4f772949664f9eb088e9d968b41ca2a1c | 59.338842936817095 | |
| 0x356ae8a278754551d9d2ae7dc0ea876b37c342ff2d010bee14aa253bb0b6030b | 18.827787420260467 | |
| 0x388fd59eab65b6034c96c01a21197eb2889d6507f84ff07e553749c541563962 | 5.880854505948256 | |
| 0xf4227ca3c8e8b5c8a0b10f034c6dee6556788c618e4cd289dc343b3247e85add | 0.4327422187881 | |
| Total | 271.1009661550497 | |
| 0x80d2 | 0xf061f8fc19c894ec37310ff59977ec97de55fd1494f1b1e66ae89188552d5c60 | 1.8414029470248867 |
| Total | 1.8414029470248867 | |
| Total | 272.9423691020746 |
Resumo
Em resumo, o atacante explora a vulnerabilidade de que o mecanismo de preço da Array Finance depende do totalSupply do token aBPT, que é manipulável. A vulnerabilidade foi discutida em nosso artigo de pesquisa DeFiRanger: Detecting Price Manipulation Attacks on DeFi Applications.
Créditos
Junjie Fei, Yufeng Hu, Ziling Lin, Siwei Wu, Lei Wu, Yajin Zhou @BlockSec
(Em ordem alfabética pelo sobrenome)
Sobre a BlockSec
A BlockSec é uma empresa pioneira em segurança blockchain estabelecida em 2021 por um grupo de especialistas em segurança de renome mundial. A empresa está comprometida em aprimorar a segurança e a usabilidade para o emergente mundo Web3, a fim de facilitar sua adoção em massa. Para isso, a BlockSec oferece serviços de auditoria de contratos inteligentes e segurança de redes EVM, a plataforma Phalcon para desenvolvimento seguro e bloqueio proativo de ameaças, a plataforma MetaSleuth para rastreamento e investigação de fundos, e a extensão MetaDock para construtores web3 navegando com eficiência no mundo cripto.
Até o momento, a empresa atendeu mais de 300 clientes renomados, como MetaMask, Uniswap Foundation, Compound, Forta e PancakeSwap, e recebeu dezenas de milhões de dólares americanos em duas rodadas de financiamento de investidores proeminentes, incluindo Matrix Partners, Vitalbridge Capital e Fenbushi Capital.
Site oficial: https://blocksec.com/
Conta oficial no Twitter: https://twitter.com/BlockSecTeam



