Пошаговое руководство по аудиту смарт-контракта криптопроекта

Аудит смарт-контракта — это структурированная попытка выявить, как контракт может дать сбой, быть использован не по назначению или управляться способом, не ожидаемым пользователями. Это не то же самое, что запуск одного сканера, чтение аудиторского значка или подтверждение проверки исходного кода. Используйте описанный ниже рабочий процесс для проверки развернутого контракта EVM или кодовой базы, прежде чем доверить им значительные средства.

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

Краткий обзор контрольного списка аудита

ШагОсновной вопросПолезные доказательства
1. Область примененияПроверяю ли я именно тот договор, по которому звонят пользователи?Адрес, цепочка, байт-код, прокси и реализация
2. Точки входаЧто может сделать каждый звонивший?Общедоступные/внешние функции, изменения состояния, граф вызовов
3. АвтоматизацияКакие очевидные закономерности заслуживают внимания?Вывод компилятора, результаты Slither, анализ детекторов.
4. Ручная защитаМожет ли последовательность вызовов нарушить предположения?Внешние вызовы, повторный вход, обратные вызовы, обработка сбоев
5. ЛогикаСохраняется ли корректность бухгалтерского учета в исключительных случаях?Арифметика, округление, сборы, лимиты, переходы между состояниями.
6. ПривилегииКто может изменить или остановить эту систему?Роли, владелец, ключи администратора, прокси, инициализатор
7. ТестированиеСохраняется ли это поведение при неожиданных входных данных и последовательностях?модульные, нечеткие, инвариантные и форк-тесты
8. Составление отчетовМожет ли другой человек воспроизвести и повторно проверить результат?Результаты, последствия, доказательства, исправление и статус повторного тестирования

Шаг 1: Подтвердите область действия и развернутый артефакт.

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

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

Проверьте, воспроизводит ли проверенный исходный код обозревателя развернутый байт-код. Проверка полезна, поскольку позволяет изучить исходный код и ABI, но это лишь проверка подлинности: она не доказывает безопасность бизнес-логики. Если контракт подлежит обновлению, определите как прокси, так и его текущую реализацию. Прочитайте адрес реализации из документированного механизма прокси или информации обозревателя, а затем подтвердите, что это именно та реализация, которую вы собираетесь проверить. В официальном руководстве Etherscan по проверке Foundry описана проверка новых и существующих контрактов.

Также определите границы. Включите импортированные библиотеки, унаследованные контракты, связанные библиотеки, развернутые вспомогательные контракты, адаптеры оракулов, токены, полученные от пользователей, и привилегированные компоненты вне блокчейна. Запишите, что выходит за рамки обзора и почему. Это предотвратит ошибочное принятие узкого обзора за обзор всей системы.

Шаг 2: Создайте карту точек входа и активов.

Универсальное окно просмотра исходного кода, отображающее общедоступные и внешние функции Solidity рядом с реализацией контракта в стиле ERC-20.
Список функций, который разделяет общедоступные и внешние точки входа, прежде чем рецензент сможет отследить изменения их состояния.

Перечислите все публичные и внешние функции, включая унаследованные функции и обработчики резервных или приемных запросов. Для каждой из них укажите, может ли она:

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

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

Шаг 3: Выполните чистую компиляцию и статический анализ.

Типичный терминал, отображающий точку командной строки и результаты проверки на реентрантность, непроверенные низкоуровневые вызовы и проблему с интерфейсом ERC-20.
Статический анализ позволяет быстро выявить потенциальные проблемы, которые еще предстоит подтвердить на основе фактического кода и модели угроз.

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

Для проектов типа Hardhat, Foundry или аналогичных запустите Slither из корневой папки проекта. В официальной документации инструмент описывается как статический анализатор Solidity и Vyper и приводится распространенная команда:

slither .

Сохраните результаты и проанализируйте каждый из них по степени влияния и достоверности. Внимательно изучите результаты, касающиеся произвольной отправки токенов, незащищенных обновлений, повторного входа, непроверенных возвращаемых значений, опасных вызовов делегатов, tx.origin, слабой случайности и некорректных интерфейсов. Детектор может выдать ложноположительный результат, пропустить специфическую для проекта экономическую ошибку или отметить код, который намеренно ограничен в других местах. Статический анализ сужает область поиска; он не заменяет ручное рассуждение. В репозитории и документации Slither также указаны принтеры для точек входа, авторизации, графов вызовов и сводок контрактов, которые помогают организовать проверку.

Шаг 4: Вручную отследите внешние вызовы и повторное подключение.

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

Для каждого внешнего вызова остановите и отследите состояние до, во время и после вызова. Вызываемым объектом может быть вредоносный контракт, токен с перехватчиками, получатель обратного вызова или другой протокол, изменяющий общую зависимость. В документации Solidity объясняется, что взаимодействие с другим контрактом может передать управление этому контракту, и рекомендуется использовать шаблон «Проверки-Эффекты-Взаимодействия»: сначала проверка, затем обновление состояния этого контракта, и последнее взаимодействие с внешними объектами.

Не ограничивайте поиск очевидными переводами Ether. Проверьте хуки в стиле ERC-777, коллбэки ERC-1155, коллбэки для мгновенных займов, произвольные маршрутизаторы, вызовы оракулов и вызовы, выполняемые через унаследованные библиотеки. Проверьте реентрантность между функциями и контрактами: коллбэк может войти в другую функцию, которая считывает промежуточное состояние. Убедитесь, что каждый низкоуровневый вызов проверяет результат успешного выполнения и корректно обрабатывает возвращаемое значение. Спросите, может ли получатель, которому не удалось осуществить перевод, навсегда заблокировать вывод средств или замкнуть цикл.

Для каждой возможной ситуации запишите конкретную последовательность действий злоумышленника. Например: злоумышленник вносит депозит, начинает вывод средств, получает обратный вызов, повторно вводит данные для вывода средств и только после этого позволяет завершить первый вызов. Если последовательность не может быть реализована из-за какого-либо конкретного инварианта или условия, запишите эту причину. Это позволит проверить вывод, а не делать его предположительным.

Шаг 5: Проверка арифметических и бизнес-инвариантов

Общий контрольный список аудита, включающий проверки границ целых чисел, округления, математических операций с ценами акций и случаев нулевых значений.
Контрольный список, учитывающий арифметические вычисления и бизнес-логику, выделяет крайние случаи, которые часто упускаются из виду при обычных тестах "счастливого пути".

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

В Solidity 0.8 и более поздних версиях обычно обнаруживаются арифметические ошибки переполнения и недополнения, но код внутри uncheckedблока намеренно изменяет это поведение. Проверенные арифметические операции также могут привести к возврату протокола к исходному состоянию или сделать его непригодным для использования, если ограничения заданы неправильно. Проверьте оба исхода: кражу или некорректный учет, а также отказ в обслуживании, вызванный значением, которое никогда не может быть обработано.

Прежде чем превращать инварианты в тесты, напишите их простым языком. Примеры включают: «общее количество акций соответствует активам согласно указанному правилу округления», «пользователь не может вывести больше, чем указано в его требованиях», «общее количество токенов равно сумме балансов, к которым применяется данная модель», и «комиссия не может превышать установленный лимит». Сравнивайте балансы хранилища с фактическими балансами токенов, поскольку токены могут быть отправлены непосредственно в контракт или вести себя иначе, чем предполагаемая реализация ERC-20.

Шаг 6: Проверка прав доступа и возможности обновления.

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

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

Разграничьте утверждения «код позволяет администратору сделать это» и «это может сделать любой пользователь». Первое может представлять собой явный риск управления или хранения данных; второе — уязвимость авторизации. Убедитесь, что проверки ролей охватывают все конфиденциальные пути, включая внутренние вспомогательные функции, доступные из общедоступных функций. Проверьте, может ли администратор по умолчанию предоставлять себе или другим дополнительные полномочия, и может ли передача прав собственности быть случайно отправлена ​​на неиспользуемый адрес.

Для прокси-серверов следует изучить инициализатор, авторизацию реализации, задержку обновления, структуру хранилища и план отката или аварийного восстановления. В руководстве OpenZeppelin по обновляемым контрактам объясняется, почему конструкторы не инициализируют хранилище прокси-сервера, почему инициализаторы должны быть защищены, почему реализация не должна оставаться неинициализированной и почему изменение порядка или типов хранилища может привести к сбою обновления. Рассматривайте ключ администратора прокси-сервера как часть границы безопасности протокола, а не как деталь реализации.

Шаг 7: Протестируйте систему с помощью фаззинга, инвариантов и форков.

Универсальная панель мониторинга тестирования, отображающая пройденные фаззинг-тесты, пройденные инвариантные тесты и последовательность вызовов контрпримера.
Проходящие мимо кампании являются полезным доказательством, в то время как контрпример показывает, какая именно последовательность требует исследования.

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

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

По возможности используйте форк целевой сети для проверки развернутых адресов, текущей конфигурации, поведения токенов и маршрутизации через прокси. Тесты форка должны быть безопасными и доступными только для чтения, если вы не используете изолированный локальный форк. Минимизируйте количество ошибок и сохраняйте контрпример, адреса вызывающих сторон, контекст блока, балансы и соответствующие значения хранилища. Успешный тест свидетельствует о проверенных путях, а не о всех возможных путях.

Шаг 8: Опишите выявленные недостатки, которые можно исправить и повторно проверить.

Типовой отчет об аудите, содержащий информацию о выявленных проблемах по степени серьезности, а также статусы «открытый», «исправленный» и «принятый риск», плюс контрольный список для повторной проверки.
Полезный отчет связывает степень тяжести и статус с имеющимися данными, конкретным решением и условиями повторного тестирования.

Для каждого вопроса используйте одну запись. Практическое заключение должно содержать:

  • Название и местоположение: контракт, функция, файл и ссылка на строку или код.
  • Последствия: что может быть украдено, заморожено, завышено, обойдено или искажено.
  • Предварительное условие: необходимые разрешения, балансы, сроки или конфигурация.
  • Воспроизведение: короткая последовательность транзакций, проверка, отслеживание или подтверждение.
  • Рекомендация: внесение конкретных изменений в код или операционные процессы с учетом компромиссов.
  • Статус: открыто, исправлено, смягчено, риск принят или не воспроизводится.
  • Повторное тестирование: точное тестирование или наблюдение, подтверждающее разрешение проблемы.

Степень серьезности должна отражать реальное воздействие и возможность эксплуатации уязвимости, а не то, насколько тревожно выглядит шаблон кода. Объясните допущения. Низкоуровневый вызов может быть безопасным благодаря строгому инварианту; казалось бы, обычное изменение параметра может быть критическим, если оно управляет оракулом или обновлением. После исправления просмотрите различия, повторно запустите соответствующий тест, повторно запустите полный набор тестов и проверьте наличие регрессий. Если развернутый адрес уже был обновлен или изменен, повторно протестируйте фактическую реализацию и конфигурацию в блокчейне.

Распространенные ошибки при проведении аудита, которых следует избегать.

  • «Исходный код проверен, поэтому он безопасен». Проверка устанавливает соответствие между исходным кодом и байт-кодом; она не подтверждает корректность проекта.
  • «Сканер ничего не обнаружил, значит, ошибок нет». Инструменты наиболее эффективны при выявлении известных закономерностей, в то время как экономические и междоговорные недостатки часто требуют анализа человеком.
  • «Проект имеет аудиторский отчет, поэтому текущая версия развертывания охватывается». Сравните данные из отчета: коммит, область действия, адреса развертывания, исправления и историю обновлений.
  • «Фазз-тесты пройдены, поэтому инвариант верен». Сначала убедитесь, что инвариант выражает предполагаемое экономическое свойство и что обработчики достигают осмысленных состояний.
  • «Административный контроль не представляет угрозы безопасности». Возможно, это намеренное предположение о доверии, но пользователи должны иметь возможность видеть, кто может создавать новые файлы, приостанавливать их выпуск, изменять параметры или обновлять.

Перед тем как довериться результату, проведите последнюю самопроверку.

Вы должны быть в состоянии ответить утвердительно на следующие вопросы:

  • Записал ли я точную цепочку, адрес, байт-код, прокси, реализацию и параметры сборки?
  • Провел ли я инвентаризацию всех точек входа, изменяющих состояние системы, и активов, на которые они могут повлиять?
  • Проверил ли я компиляцию на отсутствие ошибок, просмотрел ли предупреждения и обработал ли автоматические результаты?
  • Проследил ли я каждый внешний вызов, обратный вызов, низкоуровневый вызов и путь сбоя?
  • Проверял ли я округление, пределы, нулевые значения, устаревшие данные и повторяющиеся действия?
  • Удалось ли мне настроить все привилегированные роли, ключи, задержки, инициализаторы и пути обновления?
  • Сохранил ли я осмысленные нечеткие представления и инвариантные контрпримеры?
  • Может ли независимый эксперт воспроизвести каждое обнаруженное нарушение и проверить каждое исправление?

Если какой-либо ответ отрицательный, пометьте аудит как неполный и укажите недостающие доказательства. Четкое ограничение полезнее, чем расплывчатый вывод о «безопасности». Безопасность смарт-контрактов — это непрерывный процесс: каждое обновление, изменение зависимостей, новая интеграция и изменение привилегий могут создавать новые границы проверки.

Оставить комментарий

Анализ распределения токенов: как выявить потенциальные кошельки инсайдеров.

Анализ распределения токенов: как выявить потенциальные кошельки инсайдеров.

Практическая методика выявления потенциально связанных с инсайдерами криптокошельков с использованием концентрации держателей, связей с разработчиками, моделей финансирования, меток и поведения в блокчейне.

Полное руководство по безопасной и прибыльной торговле мем-монетами

Полное руководство по безопасной и прибыльной торговле мем-монетами

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

A Beginner's Guide to Using KuCoin's Peer-to-Peer (P2P) Marketplace

A Beginner's Guide to Using KuCoin's Peer-to-Peer (P2P) Marketplace

Learn how to use KuCoin P2P to buy and sell crypto, verify payments, choose offers, avoid common scams, and handle disputes safely.

Что такое криптодробы и как получить право участвовать в крупнейших из них?

Что такое криптодробы и как получить право участвовать в крупнейших из них?

Узнайте, что такое криптоаирдропы, как работают правила участия, каких мифов следует избегать и как воспользоваться выгодными возможностями, не рискуя своими деньгами.

Исправление ошибок, связанных с неудачной проверкой KYC на Binance, Bybit и OKX.

Исправление ошибок, связанных с неудачной проверкой KYC на Binance, Bybit и OKX.

Узнайте, как исправить ошибки верификации KYC на Binance, Bybit и OKX, устранив несоответствия в документах, селфи, данных и учетной записи.

Спотовая торговля против маржинальной торговли: ключевые различия, риски и что следует знать новичкам.

Спотовая торговля против маржинальной торговли: ключевые различия, риски и что следует знать новичкам.

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

Honeypot Crypto Scams Explained: How to Check If You Can Sell a Token

Honeypot Crypto Scams Explained: How to Check If You Can Sell a Token

Learn how honeypot crypto scams block token sales, how to check sell simulations, taxes, liquidity, and contract controls before risking funds.

Опасности схем «накачки и сброса»: как защитить свой капитал

Опасности схем «накачки и сброса»: как защитить свой капитал

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

Как успешно разблокировать заблокированный аккаунт на криптовалютной бирже

Как успешно разблокировать заблокированный аккаунт на криптовалютной бирже

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

Инвестиции в Binance Dual: риски и выгоды.

Инвестиции в Binance Dual: риски и выгоды.

Узнайте, как работает Binance Dual Investment, включая покупку по низкой цене, продажу по высокой цене, расчеты, годовую процентную ставку, лимиты ликвидности, рыночный риск и автоматическое начисление процентов.