# Рукопожатие На рукопожатие возложена задача создать между клиентом и сервером новый поток или восстановить существующий (из десинхронизированного состояния в рабочее), на взаимно согласованных условиях. Это включает в себя определение готовности коммуникации по протоколу, согласование версии протокола в пределах сессии (если создаётся новая), а также согласование различных параметров потока. Рукопожатие может быть "открытое", то есть в котором тело пакета представлено в нешифрованном виде и которое ведёт к созданию нешифрованного потока, и "шифрованное", в котором тело пакета зашифровано, подписано, и которое ведёт к созданию шифрованного потока. При выполнении этой процедуры используются данные в уникальном формате, несоответствующие формальному определению пакета. Формат данных использующийся в рукопожатии представлен ниже. Существуют следующие типы рукопожатия: - Первый тип: создаёт новую сессию - Второй тип: создаёт новый поток в рамках существующей сессии - Третий тип: восстанавливает существующий поток из десинхронизированного состояния в рабочее Рукопожатие любого типа выполняется ровно в два действия: 1. Клиент запрашивает рукопожатие с избранными параметрами 2. Сервер отвечает клиенту либо своей частью параметров, либо ошибкой Пакет рукопожатия состоит из заголовка и тела. В заголовок входят магическое число протокола и флаг шифрования. Тело представляет из себя данные сериализованные в формат KLV. Флаг шифрования является восьмибитным целым числом и может принимать одно из двух значений: 1. `0x00` - шифрования нет. 2. `0x80` - шифрование включено. Формат пакета рукопожатия следующий: ```text B: byte(s) |----------------------| | Magic number: 8B | |----------------------| | Encryption flag: 1B | |----------------------| | Handshake body: >=1B | |----------------------| ``` ## Базовые параметры Базовые параметры, использующиеся в рукопожатии: - Параметры шума в потоке - Версия протокола - Секрет потока - Максимальный размер полезной нагрузки пакета - Код ошибки сервера - Детальное описание ошибки ## Криптографические параметры Тоже самое, что и базовые параметры, только связанные с криптографией. - Алгоритм хэширования пакета - Алгоритм шифрования события - KDF для генерации ключей шифрования для пакетов - Значение для инициализации KDF ключей пакетов - Константа для использования KDF ключей пакетов - Алгоритм подписи сервера - Публичный ключ подписи сервера - Алгоритм подписи клиента - Публичный ключ подписи клиента - KDF для генерации Server StreamId - Значение для инициализации KDF SSId - Константа для KDF SSId - KDF для генерации Client StreamId - Значение для инициализации KDF CSId - Константа для KDF CSId