Перейти к основному содержимому

Отказоустойчивость и финальность

Гарантии BFT

Консенсус Savitri использует протокол голосования BFT (Byzantine Fault Tolerant) с кворумом 2f+1 (порог 67%).

Отказоустойчивость

Всего нод (n)Макс. Byzantine (f)Требуемый кворум
302
514
725
1037
15411

Формула: f = floor((n-1) / 3), кворум = 2f + 1

Безопасность

Блок финализируется только при получении Block Acceptance Certificate (BAC) с подписями от 2f+1 валидаторов. Это гарантирует:

  • Ни один конфликтующий блок не может быть финализирован на той же высоте
  • Нет откатов после выдачи BAC (детерминированная финальность, не вероятностная)
  • Byzantinе-ноды не могут подделать сертификаты без участия в кворуме

Живость

Сеть может производить блоки, пока n - f честных нод онлайн:

  • Ротация предложителя: после 50 блоков предложитель уступает место, предотвращая единую точку отказа
  • Сторожевой таймер выборов: повторно запускает выборы при отсутствии прогресса блоков в течение 60 секунд
  • Прогрессивное ослабление кворума: после 3+ последовательных неудач выборов минимальное число кандидатов снижается до 2

Структура DAG

BlockHeaders поддерживают многородительскую структуру DAG для параллельного производства блоков:

pub struct BlockHeader {
pub parent_hash: Vec<u8>, // основной родитель (обратно совместимо)
pub parent_hashes: Vec<Vec<u8>>, // дополнительные родители для DAG
// ...
}

Обнаружение конфликтов

ConflictDetector выявляет:

  • Конфликты двойных трат: одно UTXO, ссылаемое в нескольких ветвях
  • Конфликты состояния: конфликтующие переходы состояний
  • Обнаружение форков: несколько блоков на одной высоте от разных предложителей

Разрешение конфликтов

При обнаружении конфликтов:

  1. Выбирается ветвь с более высокой совокупной оценкой PoU
  2. Конфликтующие транзакции откатываются
  3. Неконфликтующие транзакции из проигравшей ветви повторно применяются

Групповой консенсус

Формирование групп

Masternodes организуют lightnodes в группы:

  1. Сортировка lightnodes по PoU-оценке
  2. Назначение в группы размером group_size (3 для разработки, 7 для продакшна)
  3. Публикация назначений групп через gossipsub
  4. Детерминированные идентификаторы групп на основе эпохи (не системного времени)

Выборы внутри группы

В каждой группе:

  1. Члены обмениваются PoU-оценками
  2. Наивысшая PoU-оценка становится предложителем (тайбрейкер по peer_id)
  3. Требуется минимум (total+1)/2 кандидатов
  4. После 3+ неудач: снижение до минимум 2 кандидатов

Принятие блоков

  1. Предложитель группы производит блок
  2. Члены группы верифицируют и подписывают
  3. BAC создаётся с 2f+1 подписями
  4. Masternodes верифицируют BAC и финализируют

Механизмы восстановления

Восстановление выборов

МеханизмТриггерДействие
Сторожевой таймерНет блока 60сПовторный запуск PoU + выборы
Прогрессивное ослабление3+ неудачиСнижение кворума до 2
Ротация предложителя50 блоковУступить место, переизбрать
Немедленные перевыборыРеинициализация группыЗапустить PoU + задачу выборов

Восстановление узлов

МеханизмТриггерДействие
Keepalive gossipsubИнтервал 60сПубликация PoU-оценки
Сторожевой таймер meshНет mesh 60сПереподключение к узлам группы
Отключение SlowPeerОчередь переполненаОтключить и переподключить
Сброс nonceЛокальный > storage + 200Сброс до storage nonce

Восстановление группы

При реинициализации группы:

  1. PoU-оценки сохраняются для продолжающих членов
  2. Новые члены начинают с оценок по умолчанию
  3. Флаг intra_group_started сбрасывается
  4. Немедленно запускаются PoU + выборы (без ожидания периодических таймеров)

Слэшинг (продакшн)

НарушениеШтрафПериод восстановления
Двойное голосование50% стейка
Простой10% стейкаПостепенно
Неверное предложение25% стейка

Слэшинг отключён на devnet, включён на mainnet (config/production.toml).

Конфигурация консенсуса

ПараметрРазработкаПродакшн
Тайм-аут15с10с
Макс. раундов510
Порог кворума0.670.67
BFT-оптимизацииОтключеныВключены
СлэшингОтключёнВключён
Время блока
Размер группы37