Nomad только что потерял более 150 миллионов долларов в результате одного из самых хаотичных взломов, которые когда-либо видел Web3. Как именно это произошло и в чем была основная причина? Позвольте мне провести вас за кулисы.
Все началось, c того что мне запостили твит в Telegram-канале ETHSecurity. Хотя я понятия не имел, что происходит в то время, но быстро покидающие активы мост, были явно плохим признаком.
Моя первая мысль заключалась в том, что была некоторая неправильная конфигурация десятичных знаков токена. Все выглядело так, будто мост проводит акцию «Отправь 0,01 WBTC, получи 100 WBTC».
Однако после некоторых мучительных исследований в сети Moonbeam я обнаружил, что хотя в транзакции Moonbeam действительно отправились 0,01 WBTC, транзакция Ethereum каким-то образом прошла на 100 WBTC.
Кроме того, транзакция по мосту в WBTC на самом деле ничего не доказывает. Он просто называется
процесс напрямую. Достаточно сказать, что возможность обработать сообщение, не доказав его сначала, крайне плохо для сети.Здесь было возможно два варианта. Либо доказательство было отправлено отдельно в более раннем блоке, либо что-то сильно не так с контрактом реплики. Однако не было абсолютно никаких указаний на то, что что-либо было доказано в последнее время.
Оставался один вариант - в контракте реплики была фатальная ошибка. Но как? Беглый взгляд показал, что отправленное сообщение должно принадлежать приемлемому корню. В противном случае проверка в строке 185 завершится ошибкой.
К счастью, есть простой способ проверить это предположение на работоспособность. Я знал, что корень сообщения, которое не было проверено, будет 0x00, потому что messages[_messageHash] не будут инициализированы. Все, что мне нужно было сделать, это проверить, примет ли контракт это в качестве корня.
Упс. Оказывается, во время рутинного обновления команда Nomad инициализировала доверенный корень как 0x00. Чтобы было ясно, использование нулевых значений в качестве значений инициализации является обычной практикой. К сожалению, в данном случае это имело крошечный побочный эффект автоматического подтверждения каждого сообщения.
Вот почему взлом был таким хаотичным — вам не нужно было знать ни о Solidity, ни о Merkle Trees, ни о чем-то подобном. Все, что вам нужно было сделать, это найти транзакцию, которая сработала, найти/заменить адрес другого человека своим, а затем ретранслировать его.
tl; dr обычное обновление пометило нулевой хеш как действительный корень, что позволило подделать сообщения на Nomad. Злоумышленники воспользовались этим для копирования/вставки транзакций и быстро опустошили мост в бешеном свободном доступе.
Источник с картинками, но на английском.
$MART | Chat | Youtube