Ethereum это Тёмный Лес

Перевод статьи Ethereum is a Dark Forest

Авторы: Dan Robinson, Georgios Konstantopoulos

Это жуткая история.

Вызов

Как любой нормальный человек, я провожу много времени, таясь на канале #support в Дискорде Uniswap.

В среду днём кто-то спросил, можно ли вернуть токены ликвидности Uniswap, по ошибке отправленные на контракт торговой пары.

Изначально я думал, что эти токены будут заблокированы навсегда. Но позже ночью я вдруг понял, что их способен вытащить кто угодно.

Когда кто-либо вызывает функцию burn в основном контракте Uniswap, контракт измеряет свой собственный баланс токенов ликвидности и сжигает его, передавая отозванные токены по адресу, указанному при вызове функции. Это основная часть предполагаемого поведения Uniswap v2 (основной механизм описан в разделе 3.2 вайтпейпера Uniswap v2).

Я нашёл контракт. Токены ликвидности все еще были на месте и стоили около 12,000 долларов.

Это означало три вещи:

  • Часы тикали. Даже если никто другой не заметил халявных денег, любой мог в любой момент вытащить свою ликвидность из контракта пары, случайно заполучив в придачу эти токены.
  • Я мог бы надеть белую шляпу и попытаться вернуть токены человеку, который случайно отправил их. Для этого достаточно просто вызвать функцию burn в пуле, передав ей мой адрес.
  • Вот только… Я знал, что это будет непросто.

Тёмный Лес

Не секрет, что блокчейн Ethereum — крайне враждебная среда. Если смарт-контракт можно проэксплуатировать ради профита, то это произойдет. Частота новых взломов указывает на то, что некоторые очень умные люди тратят много времени на изучение контрактов на наличие уязвимостей.

Но эта не прощающая ошибок среда блекнет по сравнению с мемпулом (набор ожидающих подтверждение транзакций). Если блокчейн сам по себе является полем битвы, то мемпул — это нечто худшее: темный лес.

«Тёмный лес» — моя любимая научно-фантастическая книга. Она вводит понятие «тёмного леса» — места, в котором обнаружение означает верную смерть от рук продвинутых хищников. В этой среде открытое определение чьего-то местоположения равносильно его прямому уничтожению. (Эта концепция также послужила источником вдохновения для игры Dark Forest в тестнете Ethereum.)

В мемпуле Ethereum эти высшие хищники принимают форму «арбитражных ботов». Арбитражные боты отслеживают ожидающие транзакции и пытаются использовать создаваемые ими выгодные возможности. Ни один вайтхет не знает об этих ботах больше, чем Фил Дайан, исследователь смарт-контрактов, который вместе со своими коллегами написал бумагу Flash Boys 2.0 и ввел термин «ценность извлекаемая майнером» (MEV).

Фил однажды рассказал мне о космическом ужасе, который он назвал «универсальным фронтраннером». Арбитражные боты обычно ищут в мемпуле определенные типы транзакций (такие как торговая сделка на DEX или обновление оракула) и пытаются опередить их в соответствии с заранее заданным алгоритмом.  Универсальные фронтраннеры ищут любую транзакцию, которую они могли бы выгодно опередить, скопировав ее и подменив адреса своими собственными. Они даже могут выполнить транзакцию и скопировать прибыльные внутренние транзакции, сгенерированные в ходе ее выполнения.

Вот почему спасение средств не будет простым. Функцию burn может вызвать кто угодно. Если бы я отправил транзакцию вызывающую burn, она выглядела бы как мигающий знак «халявные деньги», указывающий прямо на эту выгодную возможность. Если монстры живут в мемпуле, они увидят, скопируют, изменят и опередят мою транзакцию, забрав деньги до того, как моя транзакция будет смайнена.

Заметьте, насколько эта среда более жестокая, чем даже само состояние блокчейна Ethereum. Эти халявные деньги валялись незамеченными ончейн около восьми часов, ожидая пока кто-то их заберет вызовом burn. Но любая попытка поднять их была бы моментально перехвачена.

Спасение

Чтобы вытащить деньги, не привлекая внимания ботов, мне нужно было обфусцировать транзакцию, чтобы обращение к паре Uniswap было незаметным. Для этого нужно писать и деплоить кастомные контракты. Поскольку я профессиональный идейный лидер DeFi, я никогда раньше не деплоил контракт в Ethereum.

Мне нужна была помощь, а было уже за полночь. К счастью, некоторые из лучших инженеров по смарт-контрактам, которых я знаю, живут в европейском часовом поясе. Мой коллега по Paradigm Георгиос Константопулос согласился помочь с деплойментом контракта и отправкой транзакций. Альберто Куэста Каньяда, ведущий инженер другой из наших портфельных компаний, Yield, вызвался заимплементить контракты.

Несколько отличных инженеров по безопасности Ethereum помогли нам разработать план обфускации. В дополнение к тому, чтобы осуществить вызов burn в виде внутренней транзакции, мы задумали разделить транзакцию на две части: set-транзакцию, которая активирует наш контракт, и get-транзакцию, которая спасает средства, если контракт был активирован. Это должно сработать так:

  1. Контракт Getter, который при вызове овнером будет делать вызов burn ТОЛЬКО если активирован, иначе реверт.
  2. Контракт Setter, который при вызове овнером активирует контракт Getter.
  3. Разместить set и get транзакции в одном и том же блоке.
Код наших смарт-контрактов

Если атакующий попытается выполнить только get-транзакцию, она ревертнется без вызова функции burn. Мы надеялись, что к тому времени, когда атакующий выполнит обе транзакции set и get последовательно, обнаружит внутренний вызов pool.burn и зафронтранит нас, наши транзакции уже будут смайнены.

К нашему удивлению, Infura отвергла get-транзакцию, даже когда мы вручную увеличили оценку газа. После нескольких неудачных попыток и перезагрузок стало поджимать время, и мы стали небрежными и допустили, что вторая транзакция попала в более поздний блок.

Это была фатальная ошибка.

Наша get-транзакци была включена в блок, но с ошибкой UniswapV2: INSUFFICIENT_LIQUIDITY_BURNED, означающей, что ликвидность исчезла. Оказалось, что через несколько секунд после того, как наша get-транзакция попала в мемпул, кто-то выполнил вызов и захватил средства.

Нас сожрали монстры.

Урок

Монстры — реальны

Мы знали, что универсальные фронтраннеры существуют. Но пока не увидишь их в действии, ты их недооцениваешь.

Мы надеялись, что внутренний вызов через авторизованный контракт с передачей переменной из хранилища в качестве адреса to сможет нас защитить. Это оказалось не так.

Если вы оказались в подобной ситуации, советуем обратиться к Скотту Бигелоу, это исследователь безопасности, который изучал эту тему, у него есть прототипная реализация лучшего обфускатора.

Не будьте небрежными

Даже в условиях нехватки времени нам следовало придерживаться плана. Если бы мы потратили больше времени на скрипты, улучшили контракты (возможно, изменили бы контракт Getter, чтобы без активации он ничего не делал, а не ревертил), или даже синхронизировали бы нашу собственную ноду вместо использования Infura, вероятно мы бы смогли всунуть наши транзакции в один блок.

Не полагайтесь на нормальную инфраструктуру

Чем страннее вещи вы делаете, тем сложнее будет протолкнуть их через существующую инфраструктуру вроде Infura. В нашем случае мы пытались отправить транзакцию, которая выглядела так, будто при текущем состоянии блокчейна она завершилась ошибкой, от чего Infura имеет разумную защиту. Использование нашей собственной ноды могло бы помочь обойти эту проблему.

Еще лучше, если у вас есть знакомый майнер (у нас не было), вы можете попросить его включить транзакцию непосредственно в блок, полностью минуя мемпул и монстров.

Будущее будет только страшнее

Это был всего лишь один пример инцидента фронтраннинга. Подобные вещи происходят каждый день множество раз. Сегодня фронтраннеры — это просто боты. Завтра это будут майнеры.

Сегодня майнеры оставляют деньги на столе, не используя эти возможности. В будущем они будут переупорядочивать транзакции в своих мемпулах с выгодой для себя. Хуже того, они могут реорганизовывать блоки, добытые другими майнерами, в попытках украсть MEV, недополученную ими, что приведет к нестабильности блокчейна.

Мы считаем, что это будущее можно предотвратить, и рады нескольким амбициозным попыткам это сделать. В решении layer-2 масштабирования Optimism есть видение того, как можно перенаправить MEV на благо экосистемы. StarkWare в дополнение к собственным системам layer-2 масштабирования построили службу «функции верифицируемой задержки» (verifiable delay function) под названием VeeDo, которая может сделать приложения Ethereum невосприимчивыми к такого рода фронтраннерским атакам. (Paradigm инвестировала и в Optimism, и в StarkWare)

Если вы размышляете о MEV или о создании чего-нибудь в этой области, свяжитесь с нами!

0 Comments on “Ethereum это Тёмный Лес