Примечание
Сетевое развертывание и тестирование в процессе. Возможны незначительные правки.
Обзор
Краткое содержание
ECIES уменьшает накладные расходы существующего сеансового (ES) сообщения примерно на 90 байт. Следовательно, мы можем увеличить MTU примерно на 90 байт для соединений ECIES. См. спецификацию ECIES , спецификацию Streaming и документацию по API Streaming .
Без увеличения MTU в большинстве случаев экономия на накладных расходах фактически не «сохраняется», так как сообщения всё равно будут дополняться до двух полных туннельных сообщений.
Данное предложение не требует изменений в спецификациях. Оно публикуется исключительно для обсуждения и формирования консенсуса по рекомендуемому значению и деталям реализации.
Цели
- Увеличить согласованный MTU
- Максимально эффективно использовать туннельные сообщения размером 1 КБ
- Не изменять протокол потоковой передачи (streaming)
Дизайн
Использовать существующую опцию MAX_PACKET_SIZE_INCLUDED и механизм согласования MTU. Streaming по-прежнему использует минимальное значение из отправленного и полученного MTU. Значение по умолчанию остаётся 1730 для всех соединений, независимо от используемых ключей.
Реализациям рекомендуется включать опцию MAX_PACKET_SIZE_INCLUDED во все пакеты SYN в обоих направлениях, хотя это и не является обязательным требованием.
Если целевой узел поддерживает только ECIES, следует использовать большее значение (как Алиса, так и Боб). Если целевой узел поддерживает оба типа ключей (dual-key), поведение может различаться:
Если клиент с двойным ключом находится вне маршрутизатора (во внешнем приложении), он может не «знать», какой ключ используется на удалённой стороне, и Алиса может запросить большее значение в пакете SYN, в то время как максимальные данные в SYN остаются 1730.
Если клиент с двойным ключом находится внутри маршрутизатора, информация о том, какой ключ используется, может быть доступна или недоступна клиенту. Leaseset может ещё не быть получен, или внутренние интерфейсы API могут не предоставлять эту информацию клиенту легко. Если информация доступна, Алиса может использовать большее значение; в противном случае Алиса должна использовать стандартное значение 1730 до согласования.
Клиент с двойным ключом в роли Боба может отправить большее значение в ответ, даже если от Алисы было получено значение 1730 или не было получено никакого значения; однако в протоколе потоковой передачи нет механизма повторного согласования в сторону увеличения, поэтому MTU должен оставаться на уровне 1730.
Как указано в документации по API Streaming , данные в пакетах SYN, отправленные от Алисы к Бобу, могут превышать MTU Боба. Это слабое место в протоколе потоковой передачи. Следовательно, клиенты с двойным ключом должны ограничивать данные в отправляемых пакетах SYN до 1730 байт, одновременно отправляя опцию с большим значением MTU. После получения большего MTU от Боба Алиса может увеличить фактический максимальный объём отправляемых данных.
Анализ
Как описано в спецификации ECIES , накладные расходы ElGamal для сообщений существующего сеанса составляют 151 байт, а накладные расходы Ratchet — 69 байт. Следовательно, мы можем увеличить MTU для соединений Ratchet на (151 - 69) = 82 байта, с 1730 до 1812.
Спецификация
Добавить следующие изменения и пояснения в раздел «Выбор и согласование MTU» документации по API Streaming . Изменения в спецификации Streaming не требуются.
Значение по умолчанию для опции i2p.streaming.maxMessageSize остаётся 1730 для всех соединений, независимо от используемых ключей. Клиенты должны использовать минимальное значение из отправленного и полученного MTU, как обычно.
Существует четыре связанных константы и переменные MTU:
- DEFAULT_MTU: 1730, без изменений, для всех соединений
- i2cp.streaming.maxMessageSize: по умолчанию 1730 или 1812, может быть изменено конфигурацией
- ALICE_SYN_MAX_DATA: Максимальные данные, которые Алиса может включить в пакет SYN
- negotiated_mtu: Минимум из MTU Алисы и Боба, используется как максимальный размер данных в пакете SYN ACK от Боба к Алисе и во всех последующих пакетах в обоих направлениях
Следует рассмотреть пять случаев:
1) Алиса только ElGamal
Без изменений, MTU 1730 во всех пакетах.
- ALICE_SYN_MAX_DATA = 1730
- i2cp.streaming.maxMessageSize по умолчанию: 1730
- Алиса может отправить MAX_PACKET_SIZE_INCLUDED в SYN, не обязательно, если значение не отличается от 1730
2) Алиса только ECIES
MTU 1812 во всех пакетах.
- ALICE_SYN_MAX_DATA = 1812
- i2cp.streaming.maxMessageSize по умолчанию: 1812
- Алиса обязана отправить MAX_PACKET_SIZE_INCLUDED в SYN
3) Алиса с двойным ключом и знает, что Боб использует ElGamal
MTU 1730 во всех пакетах.
- ALICE_SYN_MAX_DATA = 1730
- i2cp.streaming.maxMessageSize по умолчанию: 1812
- Алиса может отправить MAX_PACKET_SIZE_INCLUDED в SYN, не обязательно, если значение не отличается от 1730
4) Алиса с двойным ключом и знает, что Боб использует ECIES
MTU 1812 во всех пакетах.
- ALICE_SYN_MAX_DATA = 1812
- i2cp.streaming.maxMessageSize по умолчанию: 1812
- Алиса обязана отправить MAX_PACKET_SIZE_INCLUDED в SYN
5) Алиса с двойным ключом, тип ключа Боба неизвестен
Отправлять 1812 в опции MAX_PACKET_SIZE_INCLUDED в пакете SYN, но ограничивать данные в пакете SYN до 1730.
- ALICE_SYN_MAX_DATA = 1730
- i2cp.streaming.maxMessageSize по умолчанию: 1812
- Алиса обязана отправить MAX_PACKET_SIZE_INCLUDED в SYN
Для всех случаев
Алиса и Боб вычисляют negotiated_mtu — минимум из MTU Алисы и Боба, который будет использоваться как максимальный размер данных в пакете SYN ACK от Боба к Алисе и во всех последующих пакетах в обоих направлениях.
Обоснование
См. исходный код Java I2P , почему текущее значение равно 1730. См. спецификацию ECIES , почему накладные расходы ECIES на 82 байта меньше, чем у ElGamal.
Замечания по реализации
Если потоковая передача создаёт сообщения оптимального размера, крайне важно, чтобы уровень ECIES-Ratchet не добавлял дополнительное выравнивание за пределы этого размера.
Оптимальный размер сообщения Garlic для размещения в двух туннельных сообщениях, включая 16-байтный заголовок Garlic Message I2NP, 4-байтную длину Garlic Message, 8-байтный ES-тег и 16-байтный MAC, составляет 1956 байт.
Рекомендуемый алгоритм дополнения в ECIES следующий:
- Если общая длина сообщения Garlic будет 1954–1956 байт, не добавлять блок дополнения (нет места)
- Если общая длина сообщения Garlic будет 1938–1953 байт, добавить блок дополнения, чтобы выровнять ровно до 1956 байт.
- В остальных случаях дополнять как обычно, например, случайным количеством от 0 до 15 байт.
Аналогичные стратегии могут применяться для оптимального размера одного туннельного сообщения (964) и трёх туннельных сообщений (2952), хотя на практике такие размеры должны встречаться редко.
Проблемы
Значение 1812 является предварительным. Подлежит подтверждению и возможной корректировке.
Миграция
Проблем с обратной совместимостью нет. Это существующая опция, а согласование MTU уже является частью спецификации.
Старые ECIES-назначения будут поддерживать значение 1730. Любой клиент, получающий большее значение, ответит 1730, и удалённая сторона осуществит понижение согласования, как обычно.