Więc odkryłem, że to jest jeszcze bardziej wyrafinowane. Zauważyłem, że transakcja frontrunningowa (przez atakujących) wywołuje `initialize`, a protokoły również wywołują _pomyślnie_ `initialize` później (więc myślą, że wszystko jest w porządku). Ale chwila, jak to w ogóle możliwe? Musiałem bardzo dokładnie przyjrzeć się zmianom w slotach pamięci i zgadnij, co znalazłem: _zresetowali_ wartość slotu pamięci `_initialized` na końcu transakcji frontrunningowej (po tym, jak przeszli do złośliwej umowy implementacyjnej). To oznacza, że pamięć proxy wygląda teraz tak, jakby nigdy nie była inicjowana. Odpowiedni slot pamięci, na który należy zwrócić uwagę, to `keccak256(abi.encode(uint256(keccak256(" - 1)) & ~bytes32(uint256(0xff))` = `0xf0c57e16840df040f15088dc2f81fe391c3923bec73e23a9662efc9c229c6a00` To jest poziom zła.
sudo rm -rf --no-preserve-root /
sudo rm -rf --no-preserve-root /10 lip, 22:13
To staje się jeszcze bardziej wyszukane: sposób, w jaki Etherscan został oszukany, aby pokazać niewłaściwy kontrakt implementacji, opiera się na ustawieniu 2 różnych slotów proxy w tej samej transakcji frontrunning. Etherscan używa pewnej heurystyki, która uwzględnia różne sloty pamięci, aby pobrać kontrakt implementacji. Istnieje stary proxy od OpenZeppelin, który używał następującego slotu: `keccak256("org.zeppelinos.proxy.implementation")` = `0x7050c9e0f4ca769c69bd3a8ef740bc37934f8e2c036e5a723fd8ee048ed3f8c3` Mamy teraz również standardowy slot EIP-1967 `bytes32(uint256(keccak256('eip1967.proxy.implementation')) - 1)` = `0x360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc` Co się stało, to to, że stary slot proxy OpenZeppelin został zapisany z benignym adresem implementacji _i_ standardowy slot EIP-1967 również został zapisany z złośliwym adresem implementacji. Ponieważ Etherscan najpierw zapytuje o stary slot proxy, najpierw pobrał ten wyglądający na nieszkodliwy i w ten sposób go wyświetlił.
21,53K