Симметричное Шифрование
Разберемся, что такое симметричное шифрование; чем отличаются блочные шифры от потоковых; зачем нужен вектор иницилизации(IV); какие бывают режимы работы шифра; что делать с последним блоком.
Симметричное Шифрование
Симметричное шифрование применяется для шифрования данных ключом шифрования.
Симметричное шифрование называется симметричным, потому что для шифрования и расшифрования используется один и тот же ключ. Имеется также асимметричное шифрование, при котором ключи шифрования и расшифрования (открытый и закрытый) различны.
Полезные данные, подвергающиеся шифрованию, называются открытым текстом.
Чтобы зашифровать открытый текст, нужно выполнить следующие действия:
- Выбрать алгоритм шифрования (шифр);
- Сгенерировать ключ шифрования;
- Сгенерировать вектор инициализации (IV), или синхропосылку;
- Выбрать режим работы шифра;
- Выбрать тип дополнения;
- Зашифровать открытый текст, применив выбранный шифр с выбранным ключом и типом дополнения в выбранном режиме работы.
Для потоковых шифров и некоторых режимов работы блочных шифров дополнение не нужно.
Сравнение блочных и потоковых шифров
Блочные шифры работают с блоками данных. Например, в популярном шифре Advanced Encryption Standard (AES) размер блока составляет 128 бит, т.е. данные шифруются блоками по 128 бит. Если объем данных больше размера блока, то данные разбиваются на блоки нужного размера. Если длина открытого текста не кратна размеру блока, то последний блок обычно дополняется до размера блока с учетом выбранного типа дополнения. Таким образом, в большинстве режимов работы блочного шифра длина шифртекста кратна размеру блока.
На вход алгоритма шифрования подается блок открытого текста (например, 16 байт), ключ шифрования и, возможно, какие-то данные, зависящие от режима шифрования (например, предыдущий блок шифртекста или IV). Отдельные байты открытого текста помещаются в список или матрицу. Затем над этими байтами, байтами ключа шифрования и дополнительными, зависящими от режима байтами данных выполняются различные логические и арифметические операции: поразрядный циклический сдвиг, исключающее ИЛИ (XOR), сложение или вычитание, обмен полных или частичных байтов в списке или матрице. Результатом этих операций является блок шифртекста того же размера, что входной блок открытого текста.
Потоковые шифры оперируют не блоками, а отдельными байтами или даже битами данных. Это значит, что потоковые шифры не нуждаются в дополнении. У них также нет режима работы. Благодаря таким характеристикам потоковые шифры проще использовать, особенно для поступающих потоком данных, их проще реализовать, и работают они быстрее блочных. Однако криптографы полагают, что в общем случае стойкость существующих потоковых шифров ниже, чем блочных.
В процессе шифрования и расшифрования потоковый шифр генерирует так называемый поток псевдослучайных цифр шифра, или гамму, взяв за основу ключ шифрования и IV или одноразовое число (nonce, т. е. number used once). Шифр принимает байты ключа шифрования и IV и выполняет над ними логические и математические операции с целью породить бесконечный поток кажущихся случайными байтов. Это и есть гамма. При порождении гаммы потоковый шифр работает как генератор псевдослучайных чисел (ГПСЧ), который инициализируется ключом шифрования и IV.
На этапе шифрования поток шифртекста порождается путем объединения гаммы с потоком открытого текста. Обычно к байтам гаммы и открытого текста просто применяется операция XOR. На этапе расшифрования порождается та же гамма, которая объединяется с потоком шифртекста.
Стойкость симметричного шифра
Криптостойкость, или просто стойкость шифра, криптографы обычно измеряют в битах. Например, если противнику для вскрытия шифра нужно выполнить 2²⁵⁶ вычислительных операций, то стойкость шифра равна 256 бит.
Максимально возможная стойкость шифра равна длине используемого ключа шифрования. Например, если используется 256-битовый ключ, то стойкость шифра не может превышать 256 бит.
Если длина ключа равна 256 бит, то всего существует 2²⁵⁶ возможных ключей. Противник может произвести полный перебор, или исчерпывающий поиск, т.е. попробовать для расшифрования все возможные ключи.
Важно понимать, что вычислительная сложность экспоненциально возрастает с увеличением длины ключа, т.е. вскрытие шифра с 256-битовым ключом займет не в 2, а в 2¹²⁸ раз больше времени, чем вскрытие шифра с 128-битовым ключом.
Сколько битов стойкости достаточно?
По состоянию на 2021 год в профессиональной среде сложилось общее мнение, подтвержденное и Национальным институтом стандартов и технологий (NIST), о том, что:
- 112 бит должно быть достаточно до 2030 года;
- 128 бит должно быть достаточно до следующего революционного прорыва в технологии или в математике.
Ожидается, что квантовые вычисления способны вдвое уменьшить число битов стойкости для симметричных криптографических алгоритмов.
DES и 3DES
Первым стандартом шифрования был Data Encryption Standard (DES). Это блочный шифр с размером блока 64 бит и длиной ключа 56 бит. И размер блока, и длина ключа слишком малы и не обеспе чивают стойкости шифра. Криптоаналитики еще и снизили стойкость DES до 39–41 бит. На практике ключ DES можно восстановить на современном персональном компьютере потребительского класса за несколько дней или даже часов.
3DES, или Triple DES, — шифр основанный на обычном DES. 3DES сводится к троекратному применению DES с двумя или тремя разными ключами. Считается, что стойкость 3DES составляет 112 бит для варианта с тремя ключами и всего 80 бит для варианта с двумя ключами.
3DES в три раза медленнее обычного DES. Шифр DES и сам довольно медленный по сравнению с AES и другими конкурентами.
Не рекомендуется использовать шифры DES и 3DES в новых приложениях.
AES
AES — самый популярный из современных симметричных шифров. Он быстрый и стойкий. AES — блочный шифр с размером блока 128 бит. Существуют три варианта AES с длинами ключей 128, 192 и 256 бит. Они называются соответственно AES-128, AES-192 и AES-256.
Лучшим из известных атак удалось уменьшить стойкость AES всего на 2 бита: до 126, 190 и 254 бит.
Cовременных процессорах x86 и x86_64 имеются команды аппаратного ускорения AES, в совокупности называемые Advanced Encryption Standard New Instructions (AES-NI — расширение системы команд AES). Некоторые процессоры ARMv8 поддерживают криптографическое расширение, также ускоряющее работу AES.
В AES применяется алгоритм шифрования Rijndael, который до стандартизации поддерживал больше размеров блоков и длин ключа. Поэтому можно сказать, что AES является подмножеством Rijndael.
Алгоритм Rijndael разработан двумя бельгийскими криптографами, Винсентом Рэйманом (Vincent Rijmen) и Йоаном Дайменом (Joan Daemen). Название Rijndael образовано из частей их имен, Rij и Dae.
AES был стандартизирован в 2001 году институтом NIST в качестве стандартного алгоритма шифрования для секретной коммерческой и правительственной информации (в США). Он также является самым популярным общедоступным симметричным шифром в мире.
RC4
RC4 — старый потоковый шифр, допускающий использование ключей длиной от 40 до 2048 бит. В прошлом он был очень популярен благодаря своей скорости и простоте реализации, но с годами в алгоритме обнаружилось много дефектов, и теперь он считается нестойким. Например, одна из атак снижает стойкость RC4 с 128битовыми ключами всего до 26 бит.
ChaCha20
ChaCha20 — современный потоковый шифр, стойкий и быстрый. ChaCha20 можно применять с 128 или 256-битовым ключом.
Шифр ChaCha20 разработал Даниэль Дж. Бернштейн (Daniel J. Bernstein — DJB), знаменитый криптограф и криптоаналитик. DJB известен также другими проектами, в т.ч. qmail, djbdns, Poly1305 и Curve25519. ChaCha20 — вариант шифра Salsa20 того же автора, оптимизированный с целью повышения производительности.
ChaCha20 стал популярен, когда компания Google начала использовать его в своем браузере Chrome наряду с алгоритмом вычисления имитовставки (MAC) Poly1305. Затем поддержка ChaCha20 и Poly1305 была добавлена в OpenSSH.
ChaCha20 — быстрый шифр, его программная реализация быстрее, чем AES. Аппаратно ускоренная реализация AES на x86 или x86_64 и ARMv8 работает быстрее ChaCha20, но такое ускорение доступно не на всех процессорах.
Недостатком ChaCha20, хотя и не очень существенным, является то, что в нем используется счетчик блоков длиной всего 32 бит. Из-за этого шифр может считаться стойким только при работе с непрерывными открытыми текстами, не превышающими 256 ГиБ.
Другие симметричные шифры
Blowfish, CAST5, ГОСТ89, IDEA, RC2 и RC5, — блочные шифры с размером блока 64 бит или переменным размером блока. Эти шифры не рекомендуется использовать для очень длинных шифртекстов (длиннее 32 ГиБ) из-за коллизионных атак и парадокса дней рождения.
ARIA, Camellia, SEED и SM4, — блочные шифры со 128-битовыми блоками. При таком размере блока можно шифровать очень длинные открытые тексты (до 256 экзабайт), не опасаясь коллизионных атак.
Национальные шифры
Национальные шифры разрабатываются и стандартизируются в конкретной стране. Зачастую такие шифры хороши, но не очень популярны за пределами страны происхождения.
CAST5 или CAST-128 — долгое время был симметричным шифром по умолчанию в программе GNU Privacy Guard (GnuPG), пока его не заменили на AES. CAST5 — один из стандартных шифров, используемых канадским правительством.
ГОСТ89, или Магма, — старый государственный стандартный шифр, применявшийся в СССР, а затем в России. На смену ГОСТ89 пришел шифр ГОСТ2015, или Кузнечик, но ГОСТ89 при этом не был объявлен устаревшим.
SEED и ARIA — южнокорейские шифры.
Camellia — 128-битовый блочный шифр, разработанный в 2000 году в Японии компаниями NTT и Mitsubishi Electric.
SM4 — китайский национальный стандарт и используется в беспроводных локальных сетях (LAN) в Китае.
Режимы работы блочных шифров
Режим работы определяет, как блоки шифртекста зацепляются друг с другом.
Режим простой замены
Простейшим режимом работы является режим простой замены (Electronic Code Book — ECB). В этом режиме каждый блок открытого текста преобразуется в блок шифртекста с применением только ключа шифрования, без использования IV или предыдущих блоков открытого или шифртекста. Таким образом, порожденные блоки шифртекста конкатенируются.
В режиме ECB один и тот же открытый текст всегда порождает один и тот же шифртекст. С точки зрения безопасности, это проблема, потому что любые закономерности в открытом тексте сохраняются в шифртексте и видны наблюдателю.
Режима CTR
В режим счётчика (counter mode, CTR) сам открытый текст не обрабатывается алгоритмом шифрования, как в случае AES. Вместо этого последовательность блоков счетчика шифруется блочным шифром.
Например, каждый блок счетчика может состоять из результата конкатенации 64-битового случайного одноразового значения и фактического 64-битового целочисленного счетчика, который инкрементируется для каждого блока. Важно, что первый блок счетчика не используется повторно для шифрования другого открытого текста тем же ключом шифрования и что все блоки счетчиков различны.
Самый простой и популярный способ инкрементирования счетчика — прибавить к нему 1, но это необязательно. Вполне возможны и другие операции, например прибавление или вычитание числа, большего 1, или еще сложнее, например XOR и поразрядный сдвиг. Важно лишь, чтобы последовательность значений счетчика не начала повторяться.
Дальше мы должны взять зашифрованные блоки счетчиков и применить к ним и к блокам открытого текста операцию XOR. Результатом и будет шифртекст.
Можно сказать, что режим CTR преобразует блочный шифр в потоковый. Действительно, последовательность зашифрованных блоков счетчика — это и есть гамма! Мы объединяем гамму с открытым текстом с помощью XOR — точно так же, как при использовании потокового шифра!
Первый блок счетчика можно интерпретировать по аналогии с IV. Как и IV в режиме CBC, первый блок счетчика обычно сохраняется вместе с шифртекстом, потому что он нужен для расшифрования.
Метод инкрементирования блока счетчика обычно тоже не является секретом.
Поэтому все блоки счетчика известны наблюдателю или противнику. Но зашифрованные блоки счетчика наблюдателю неизвестны, если только он не знает ключа шифрования. Если наблюдатель не может получить зашифрованные блоки счетчика (гамму), то не сможет и восстановить открытый текст, применив XOR к гамме и шифртексту.
IV, используемый в режиме CTR, никогда не следует применять повторно для шифрования другого сообщения тем же ключом. Если это сделать, то одна и та же гамма будет сгенерирована для шифрования нескольких сообщений. К двум шифртекстам, зашифрованным одной гаммой, можно применить XOR, и результат будет таким же, как если бы мы применили XOR к соответствующим открытым текстам.
В то время как уникальность IV — очень важное требование в режиме CTR, его непредсказуемость в этом режиме не требуется, в отличие от режима CBC. Объясняется это тем, что устойчивость CTR к атаке на основе подобранного открытого текста базируется на непредскаазуемости следующего блока гаммы, а не на непредсказуемости IV.
Поскольку режим CTR преобразует блочный шифр в потоковый, он обладает всеми преимуществами потоковых шифров. В режиме CTR не требует дополнять открытый текст, а значит, невозможны атаки с оракулом дополнения. Гамму можно вычислять заранее, а не в момент шифрования. Наконец, операции шифрования и расшифрования сводятся к применению XOR к гамме и открытому тексту, а значит, разные блоки открытого текста можно зашифровывать и расшифровывать параллельно, пользуясь заранее вычисленной гаммой.
Режим GCM
Режим гаммирования с аутентификацией Галуа (Galois/Counter mode — GCM) порождает шифртекст так же, как в режиме CTR. Блоки счетчика шифруются блочным шифром, в результате чего порождается гамма. Затем к гамме и открытому тексту применяется операция XOR, и получается шифртекст.
Отличие от режима CTR заключается в том, что GCM не только шифрует открытый текст, но также аутентифицирует шифртекст. Это означает, что знание ключа шифрования позволяет проверить целостность шифртекста, иными словами, обнаружить несанкционированные изменения шифртекста, если проверка не проходит. Такое обнаружение полезно, потому что в основе многих атак лежит изменение шифртекста: измененный шифртекст подается оракулу, и анализируется его ответ.
В криптографии оракулом называется программа, устройство или сетевой узел, который располагает ключом шифрования и может зашифровывать и расшифровывать данные. Оракул выдает ответ, иногда в форме (правильно или неправильно) зашифрованных или расшифрованных данных, иногда в форме сообщения об ошибке, а иногда какойто другой информации, на пример времени, затраченного на расшифрование. Это время может различаться для успешного и безуспешного расшифрования. Ответ оракула позволяет противнику или криптоаналитику получить данные, которые могут помочь во вскрытии шифра.
Режимы шифрования с аутентификацией (authenticated encryption — AE), в частности GCM, дают возможность обнаружить несанкционированные изменения зашифрованных данных и отказаться от использования поврежденных данных.
Некоторые режимы шифрования с аутентификацией позволяют комбинировать зашифрованные и незашифрованные данные для аутентификации. Это необходимо для хранения или передачи данных, которые сами по себе не являются конфиденциальными, но связаны с зашифрованными конфиденциальными данными и нуждаются в защите от несанкционированного изменения. Такие режимы работы называются шифрованием с аутентификацией и присоединенными данными (authenticated encryption with associated data — AEAD).
GCM является AEAD-режимом — дополнительные данные будут только аутентифицироваться, без шифрования.
Как GCM аутентифицирует шифртекст? Каждый блок шифртекста преобразуется в число, и к нему, и к начальному блоку, который зависит от ключа шифрования, применяются арифметические операции над конечным полем Галуа. Именно поэтому в названии режима фигурирует имя Галуа. Операция аутентификации порождает аутентификационный жетон, который расшифровывающая сторона может использовать для проверки целостности шифртекста.
Таким образом, выход шифрования в режиме GCM содержит IV, шифртекст и аутентификационный жетон.
Режим GCM не вполне обычный. Он работает только для 128-битовых блоков и требует 96-битового IV. Поэтому его невозможно использовать со старыми 64-битовыми блочными шифрами.
Если расшифровывающая сторона хочет верифицировать целостность шифртекста, то она должна обработать весь шифртекст, чтобы проверить аутентификационный жетон. Обычно расшифрование и проверка производятся одновременно. Поэтому если проверка заканчивается неудачно, то расшифрованные данные следует отбросить.
Требование к IV в AES-GCM такое же, как в режиме CTR: IV должен быть уникален, т.е. один и тот же IV нельзя использовать повторно для шифрования другого сообщения тем же ключом. Если IV используется повторно, то против AES-GCM можно применить те же атаки, что против CTR. Кроме того, противник может восстановить ключ, использованный для аутентификации сообщений (не ключ шифрования). Зная ключ аутентификации, противник может сгенерировать поддельные аутентификационные жетоны и внедрить в поток шифртекста посторонние данные, кажущиеся подлинными.
В настоящее время GCM является самым популярным режимом блочного шифрования из используемых в протоколе TLS. GCM поддерживается начиная с версии TLS 1.2.
Протокол TLS всегда проверяет целостность зашифрованных данных, даже если используется режим шифрования без аутентификации. Для верификации применяются имитовставки.
Режим AES-GCM-SIV
Режим GCM уязвим для различных атак, если пара ключ–IV повторно используется для нескольких сообщений. Чтобы купировать эту слабость, был предложен AES в режиме гаммирования с аутентификацией Галуа с синтетическим вектором инициализации (Advanced Encryption Standard in Galois/Counter Mode with a Synthetic Initialization Vector — AES-GCM-SIV).
AES-GCM-SIV — вариант шифра AES в режиме GCM. Его отличительной особенностью и преимуществом является то, что алгоритм не допускает неправильного использования IV или одноразового значения, т.е. гарантирует, что один и тот же IV никогда не будет использован повторно для разных сообщений.
AES-GCM-SIV не принимает IV в составе входных данных, зато принимает второй секретный ключ для аутентификации. Алгоритм генерирует аутентификационный жетон на основе открытого текста, дополнительных аутентифицированных данных и ключа аутентификации. Сгенерированный жетон используется также в роли IV для шифрования открытого текста. Этот сгенерированный IV называется синтетическим вектором инициализации (Synthetic Initialization Vector — SIV). Поскольку IV зависит от открытого текста, он будет разным для различных открытых текстов.
Недостаток AES-GCM-SIV — необходимость двух проходов по открытому тексту: первый — для генерирования аутентификационного жетона и IV, второй — для шифрования.
Другие режимы работы блочных шифров
Существует много других режимов работы блочных шифров, например CBC с распространением (propagating CBC — PCBC), режим гаммирования с обратной связью по шифртексту (Cipher Feedback — CFB), режим гаммирования с обратной связью по выходу (output feedback — OFB), режим гаммирования с имитовставкой (Counter with CBCMAC — CCM), режим Картера–Вегмана + CTR (CarterWegman + CTR — CWC), режим гаммирования с аутентификацией Софи Жермен (Sophie Germain Counter Mode — SGCM) и т. д.
Выбор режима работы блочного шифра
Считается, что лучшим режимом работы из поддерживаемых OpenSSL является GCM. GCM поддерживает не только шифрование, но и аутентификацию, не требует дополнения, а следовательно, неуязвим для атак с оракулом. GCM также позволяет предварительно вычислить гамму и распараллелить шифрование и расшифрование. При использовании GCM обязательно нужно задавать разные IV для всех открытых текстов, шифруемых одним и тем же ключом. Это очень важно — в противном случае ни о какой стойкости шифрования говорить не приходится.
Дополнение для блочных шифров
В режиме CBC открытый текст шифруется поблочно, но что делать с последним блоком, который обычно короче всех остальных? Его нельзя зашифровать просто так, потому что блочный шифр требует полного блока данных на входе. Поэтому последний блок дополняется до требуемого размера блока.
Криптографы придумали различные типы дополнения. Для симметричного шифрования OpenSSL поддерживает только дополнение по стандарту криптографии с открытым ключом номер 7 (Public Key Cryptography Standard number 7 — PKCS #7), которое также называют дополнением PKCS7, или просто дополнением PKCS, или стандартным дополнением блока.
Дополнение PKCS #7 состоит из N байт, значение каждого из которых равно N. Например, если размер блока шифра равен 16 байт (128 бит), а последний блок открытого текста содержит только 10 байт данных, то длина дополнения будет равна 6 байт и каждый байт будет равен 0x06. Все дополнение выглядит так: 0x06 0x06 0x06 0x06 0x06 0x06.
Как видим, достоинство дополнения PKCS #7 в том, что кодируется длина дополнения, т.е. неявно кодируется длина полезных данных в последнем блоке открытого текста. Поэтому не нужно передавать вместе с данными длину всего открытого текста. Ну и заодно наблюдатель не видит длину по следнего блока, потому что дополняющие байты шифруются вместе с последними полезными байтами данных.
Что будет, если длина открытого текста кратна размеру блока, так что по следний блок целиком заполнен данными? В таком случае PKCS #7 все равно требует дополнять данные. Блок, содержащий только дополняющие байты, дописывается в конец открытого текста и подлежит шифрованию. В случае со временных шифров со 128-битовыми блоками дописывается 16 дополняющих байт, каждый из которых имеет значение 0x10. Если бы не это кажущееся лишним дополнение, то после расшифрования последнего блока невозможно было бы сказать, является ли последний байт дополнением или байтом данных.
OpenSSL автоматически добавляет дополняющие байты при шифровании, удаляет при расшифровании и проверяет, корректно ли применено дополнение. Дополнение некорректно, если расшифрованный открытый текст не заканчивается N байтами со значением N. В таком случае OpenSSL вернет ошибку на последнем шаге расшифрования.
Дополнение PKCS #7 иногда называют дополнением PKCS #5. В стандарте дополнения PKCS #5 используется тот же принцип (N байт со значением N), но он определен только для блоков длиной не более 64 бит.
Комментарии в Telegram-группе!