Проверка криптографической подписи хеша

Обновлено: 03.07.2024

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

В этом разделе объясняется, как создавать и проверять цифровые подписи с помощью классов в пространстве имен System.Security.Cryptography.

Создание подписей

Цифровые подписи обычно применяются к хеш-значениям, представляющим большие данные. В следующем примере цифровая подпись применяется к хэш-значению. Во-первых, создается новый экземпляр класса RSA для создания пары открытый/закрытый ключ. Затем RSA передается новому экземпляру класса RSAPKCS1SignatureFormatter. Это передает закрытый ключ в RSAPKCS1SignatureFormatter, который фактически выполняет цифровую подпись. Прежде чем вы сможете подписать хэш-код, вы должны указать алгоритм хеширования, который будет использоваться. В этом примере используется алгоритм SHA1. Наконец, для подписания вызывается метод CreateSignature.

Из-за проблем с конфликтами с SHA1 мы рекомендуем SHA256 или лучше.

Проверка подписей

Чтобы убедиться, что данные были подписаны определенной стороной, у вас должна быть следующая информация:

Открытый ключ стороны, подписавшей данные.

Цифровая подпись.

Данные, которые были подписаны.

Алгоритм хеширования, используемый подписывающей стороной.

Чтобы проверить подпись, подписанную классом RSAPKCS1SignatureFormatter, используйте класс RSAPKCS1SignatureDeformatter. Классу RSAPKCS1SignatureDeformatter должен быть предоставлен открытый ключ подписывающей стороны. Для RSA вам понадобятся значения модуля и показателя степени, чтобы указать открытый ключ. (Эти значения должна предоставить сторона, сгенерировавшая пару открытый/закрытый ключ.) Сначала создайте объект RSA для хранения открытого ключа, который будет проверять подпись, а затем инициализируйте структуру RSAParameters со значениями модуля и экспоненты, которые определяют открытый ключ. .

В следующем коде показано создание структуры RSAParameters. Свойству Modulus присваивается значение массива байтов с именем modulusData, а свойству Exponent присваивается значение массива байтов с именем exponentData .

После того как вы создали объект RSAParameters, вы можете инициализировать новый экземпляр класса реализации RSA значениями, указанными в RSAParameters. Экземпляр RSA, в свою очередь, передается конструктору RSAPKCS1SignatureDeformatter для передачи ключа.

Следующий пример иллюстрирует этот процесс. В этом примере hashValue и signedHashValue представляют собой массивы байтов, предоставленные удаленной стороной. Удаленная сторона подписала hashValue с помощью алгоритма SHA1, создав цифровую подпись signedHashValue. Метод RSAPKCS1SignatureDeformatter.VerifySignature проверяет, действительна ли цифровая подпись и использовалась ли она для подписи hashValue .

Из-за проблем с конфликтами с SHA1 мы рекомендуем SHA256 или лучше. Однако, если для создания подписи использовался SHA1, вам придется использовать SHA1 для проверки подписи.

В этом фрагменте кода будет отображаться "Подпись действительна", если подпись действительна, и "Подпись недействительна", если нет.

Термины "цифровая подпись" и "электронная подпись" иногда путают или используют как синонимы. Хотя цифровые подписи являются формой электронной подписи, не все электронные подписи являются цифровыми подписями. Электронные подписи, также называемые электронными подписями, — это любой звук, символ или процесс, которые показывают намерение что-то подписать. Это может быть скан вашей собственноручной подписи, печати или записанное устное подтверждение. Электронной подписью может быть даже ваше имя, напечатанное в строке подписи документа.

Что такое цифровая подпись?

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

Зачем использовать цифровую подпись?

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

Как работают цифровые подписи?

Ознакомьтесь со следующими терминами, чтобы лучше понять, как работают цифровые подписи:

  • Хеш-функция. Хеш-функция (также называемая «хеш») представляет собой строку фиксированной длины из цифр и букв, сгенерированную с помощью математического алгоритма, и файл произвольного размера, такой как электронное письмо, документ, изображение или другой тип файла. данные. Эта сгенерированная строка уникальна для хешируемого файла и представляет собой одностороннюю функцию — вычисленный хэш нельзя обратить вспять, чтобы найти другие файлы, которые могут генерировать такое же значение хеш-функции. Некоторые из наиболее популярных алгоритмов хэширования, используемых сегодня, — это алгоритм безопасного хеширования-1 (SHA-1), семейство алгоритмов безопасного хеширования-2 (SHA-2 и SHA-256) и дайджест сообщения 5 (MD5).
  • Криптография с открытым ключом. Криптография с открытым ключом (также известная как асимметричное шифрование) — это криптографический метод, использующий систему пар ключей. Один ключ, называемый открытым ключом, шифрует данные. Другой ключ, называемый закрытым ключом, расшифровывает данные. Криптография с открытым ключом может использоваться несколькими способами для обеспечения конфиденциальности, целостности и подлинности. Криптография с открытым ключом может
    • Обеспечьте целостность, создав цифровую подпись сообщения с помощью закрытого ключа отправителя. Это делается путем хэширования сообщения и шифрования хэш-значения с помощью их закрытого ключа. При этом любые изменения в сообщении приведут к другому значению хеш-функции.
    • Обеспечьте конфиденциальность, зашифровав все сообщение с помощью открытого ключа получателя. Это означает, что только получатель, у которого есть соответствующий закрытый ключ, может прочитать сообщение.
    • Подтвердить личность пользователя с помощью открытого ключа и сверить его с центром сертификации.

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

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

    Почему следует использовать PKI или PGP с цифровыми подписями?

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

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

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

    Авторы

    Этот продукт предоставляется в соответствии с настоящим Уведомлением и настоящей Политикой конфиденциальности и использования.

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

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

    Цифровая подпись — это криптографическое значение, вычисляемое на основе данных и секретного ключа, известного только подписывающему.

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

    Модель цифровой подписи

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

    Модель цифровой подписи

    Следующие пункты подробно объясняют весь процесс —

    Каждый человек, использующий эту схему, имеет пару открытого и закрытого ключей.

    Как правило, пары ключей, используемые для шифрования/дешифрования и подписи/проверки, различаются. Закрытый ключ, используемый для подписи, называется ключом подписи, а открытый ключ — ключом проверки.

    Подписывающая сторона передает данные хэш-функции и создает хэш данных.

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

    Verifier передает цифровую подпись и ключ проверки в алгоритм проверки. Алгоритм проверки выдает некоторое значение на выходе.

    Verifier также запускает ту же хеш-функцию для полученных данных для создания хэш-значения.

    Для проверки это хеш-значение сравнивается с выходными данными алгоритма проверки. На основе результата сравнения верификатор решает, действительна ли цифровая подпись.

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

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

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

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

    Важность цифровой подписи

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

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

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

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

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

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

    Шифрование с цифровой подписью

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

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

    Это можно заархивировать, объединив цифровые подписи со схемой шифрования. Кратко обсудим, как выполнить это требование. Есть две возможности: подписать, затем зашифровать и зашифровать, затем подписать.

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

    Шифрование с цифровой подписью

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

    Ученая степень поможет вам получить работу с открытым исходным кодом

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

    Криптографические хэши

    Хеши используются во многих областях вычислительной техники. Например, блокчейн Биткойн использует хеш-значения SHA256 в качестве идентификаторов блоков. Чтобы добыть биткойн, нужно сгенерировать хеш-значение SHA256, которое падает ниже указанного порога, что означает хеш-значение, по крайней мере, с N ведущими нулями. (Значение N может увеличиваться или уменьшаться в зависимости от того, насколько продуктивным является майнинг в конкретный момент времени.) Интересно отметить, что современные майнеры представляют собой аппаратные кластеры, предназначенные для параллельной генерации хэшей SHA256. В пиковый период 2018 года майнеры биткойнов по всему миру генерировали около 75 млн терахэшей в секунду — еще одно непонятное число.

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

    Что должно храниться в этой таблице поиска? Хранение самих паролей рискованно. Гораздо менее рискованно хранить хэш, сгенерированный из пароля, возможно, с некоторой солью (дополнительными битами), добавленной по вкусу перед вычислением хеш-значения. Ваш пароль может быть отправлен на веб-сервер, но сайт может заверить вас, что пароль там не хранится.

    Хэш-значения также используются в различных областях безопасности. Например, код проверки подлинности сообщения на основе хэша (HMAC) использует хеш-значение и секретный криптографический ключ для проверки подлинности сообщения, отправляемого по сети. Коды HMAC, легкие и простые в использовании в программах, популярны в веб-сервисах. Цифровой сертификат X509 включает хеш-значение, известное как отпечаток пальца, которое может упростить проверку сертификата. Хранилище доверенных сертификатов в памяти может быть реализовано в виде таблицы поиска с ключами для таких отпечатков пальцев — в виде хэш-карты, которая поддерживает поиск в постоянном времени. Отпечаток входящего сертификата можно сравнить с ключами хранилища доверенных сертификатов для совпадения.

    Каким особым свойством должна обладать криптографическая хеш-функция? Он должен быть односторонним, что означает, что его очень трудно инвертировать. Криптографическая хэш-функция должна быть относительно простой для вычисления, но вычисление ее обратной функции, которая отображает хэш-значение обратно во входную битовую строку, должно быть трудновыполнимым с вычислительной точки зрения. Вот изображение с chf в качестве криптографической хэш-функции и моим паролем foobar в качестве примера ввода:

    Наоборот, обратная операция невозможна:

    Вспомните, например, хеш-функцию SHA256. Для входной битовой строки любой длины N > 0 эта функция генерирует хеш-значение фиксированной длины, равное 256 битам; следовательно, это хэш-значение не показывает даже длину входной битовой строки N, не говоря уже о значении каждого бита в строке. Кстати, SHA256 не подвержен атаке с расширением длины. Единственный эффективный способ реконструировать вычисленное хэш-значение SHA256 обратно во входную битовую строку — это поиск методом грубой силы, что означает перебор всех возможных входных битовых строк до тех пор, пока не будет найдено совпадение с целевым хеш-значением. Такой поиск невозможен для надежной криптографической хэш-функции, такой как SHA256.

    Хорошей оценки разбивки по устойчивости к коллизиям для SHA256 пока нет. Этот факт не удивителен. SHA256 имеет диапазон из 2 256 различных хэш-значений, число, десятичное представление которого состоит из целых 78 цифр! Итак, могут ли возникнуть коллизии при хешировании SHA256? Конечно, но крайне маловероятно.

    В приведенных ниже примерах командной строки в качестве источников битовой строки используются два входных файла: hashIn1.txt и hashIn2.txt. Первый файл содержит abc, а второй — 1a2b3c.

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

    Использование утилиты Linux sha256sum для этих двух файлов в командной строке (со знаком процента (%) в качестве подсказки) дает следующие хэш-значения (в шестнадцатеричном формате):

    Аналоги хеширования OpenSSL дают такие же результаты, как и ожидалось:

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

    Цифровые подписи

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

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

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

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

    Затем закрытый ключ пары используется для обработки хеш-значения целевого артефакта (например, электронного письма), тем самым создавая подпись. С другой стороны, система получателя использует открытый ключ пары для проверки подписи, прикрепленной к артефакту.

    openssl genpkey -out privkey.pem -algorithm rsa 2048

    В этом примере мы можем опустить флаг -algorithm rsa, потому что genpkey по умолчанию имеет тип RSA. Имя файла (privkey.pem) произвольное, но расширение PEM для почты с расширенной конфиденциальностью (PEM) является обычным для формата PEM по умолчанию. (В OpenSSL есть команды для преобразования между форматами, если это необходимо.) Если требуется больший размер ключа (например, 4096), то последний аргумент 2048 можно изменить на 4096. Эти размеры всегда являются степенями двойки.

    Вот фрагмент получившегося файла privkey.pem в формате base64:

    Следующая команда затем извлекает открытый ключ пары из закрытого:

    openssl rsa -in privkey.pem -outform PEM -pubout -out pubkey.pem

    Полученный файл pubkey.pem достаточно мал, чтобы показать его здесь полностью:

    Теперь, имея под рукой пару ключей, цифровая подпись упрощается — в данном случае с исходным файлом client.c в качестве артефакта, который нужно подписать:

    openssl dgst -sha256 -sign privkey.pem -out sign.sha256 client.c

    Дайджест исходного файла client.c — SHA256, а закрытый ключ находится в ранее созданном файле privkey.pem. Полученный файл бинарной подписи имеет произвольное имя sign.sha256. Чтобы получить удобочитаемую (в формате base64) версию этого файла, выполните следующую команду:

    openssl enc -base64 -in sign.sha256 -out sign.sha256.base64

    Файл sign.sha256.base64 теперь содержит:

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

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

    openssl enc -base64 -d -in sign.sha256.base64 -out sign.sha256

    openssl dgst -sha256 -verify pubkey.pem -signature sign.sha256 client

    Вывод этой второй команды, как и должно быть:

    Чтобы понять, что происходит в случае сбоя проверки, выполните короткое, но полезное упражнение: замените исполняемый файл клиента в последней команде OpenSSL исходным файлом client.c, а затем попробуйте выполнить проверку. Другое упражнение состоит в том, чтобы немного изменить программу клиента и повторить попытку.

    Цифровые сертификаты

    Цифровой сертификат объединяет проанализированные до сих пор элементы: хэш-значения, пары ключей, цифровые подписи и шифрование/дешифрование. Первым шагом к сертификату производственного уровня является создание запроса на подпись сертификата (CSR), который затем отправляется в центр сертификации (CA). Чтобы сделать это для примера с OpenSSL, запустите:

    openssl req -out myserver.csr -new -newkey rsa:4096 -nodes -keyout myserverkey.pem

    В этом примере создается документ CSR, который сохраняется в файле myserver.csr (текст base64). Цель здесь такова: документ CSR запрашивает, чтобы CA поручился за удостоверение, связанное с указанным доменным именем — общее имя (CN) на языке CA.

    Однако одна и та же команда создает CSR независимо от того, как может использоваться цифровой сертификат. Он также запускает интерактивный сеанс вопросов и ответов, который запрашивает соответствующую информацию о доменном имени для связи с цифровым сертификатом запрашивающей стороны. Этот интерактивный сеанс можно сократить, предоставив основную информацию как часть команды, с обратной косой чертой в качестве продолжения разрыва строки. Флаг -subj вводит необходимую информацию:

    Результирующий документ CSR можно проверить и проверить перед отправкой в ​​ЦС. В ходе этого процесса создается цифровой сертификат нужного формата (например, X509), подписи, даты действия и т. д.:

    openssl req -text -in myserver.csr -noout -verify

    Вот фрагмент вывода:

    Самоподписанный сертификат

    openssl req -x509 -sha256 -nodes -days 365 -newkey rsa:4096 -keyout myserver.pem -out myserver.crt

    Приведенная ниже команда OpenSSL представляет удобочитаемую версию сгенерированного сертификата:

    openssl x509 -in myserver.crt -text -noout

    Вот часть вывода для самозаверяющего сертификата:

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

    • Цифровой сертификат содержит значения показателя и модуля, составляющие открытый ключ. Эти значения являются частью пары ключей в исходном PEM-файле, в данном случае в файле myserver.pem.
    • Показатель степени почти всегда равен 65 537 (как в данном случае), поэтому его можно игнорировать.
    • Модуль пары ключей должен совпадать с модулем цифрового сертификата.

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

    Результирующие хеш-значения совпадают, что подтверждает, что цифровой сертификат основан на указанной паре ключей.

    Вернемся к проблеме распределения ключей

    Вернемся к проблеме, затронутой в конце первой части: рукопожатию TLS между клиентской программой и веб-сервером Google. Существуют различные протоколы рукопожатия, и даже работающая версия Диффи-Хеллмана в примере с клиентом предлагает пространство для маневра. Тем не менее, пример клиента следует общему шаблону.

    Двумя элементами, представляющими интерес, являются алгоритм пары ключей RSA и блочный шифр AES128, используемый для шифрования и дешифрования сообщений в случае успешного рукопожатия. Что касается шифрования/дешифрования, этот процесс бывает двух видов: симметричный и асимметричный. В симметричном варианте для шифрования и дешифрования используется один и тот же ключ, что в первую очередь поднимает проблему распределения ключей: как безопасно передать ключ обоим стороны? В асимметричном варианте для шифрования используется один ключ (в данном случае открытый ключ RSA), а для расшифровки используется другой ключ (в данном случае закрытый ключ RSA из той же пары).

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

    В ситуации с TLS симметричный подход имеет два существенных преимущества:

    • При взаимодействии между клиентской программой и веб-сервером Google аутентификация является односторонней. Веб-сервер Google отправляет клиентской программе три сертификата, но клиентская программа не отправляет сертификат веб-серверу; следовательно, веб-сервер не имеет открытого ключа от клиента и не может шифровать сообщения клиенту.
    • Симметричное шифрование/дешифрование с помощью AES128 почти в тысячу раз быстрее, чем асимметричная альтернатива с использованием ключей RSA.

    Квитирование TLS умело сочетает в себе два варианта шифрования/дешифрования. Во время рукопожатия клиентская программа генерирует случайные биты, известные как предварительный секрет (PMS). Затем клиентская программа шифрует PMS с помощью открытого ключа сервера и отправляет зашифрованную PMS на сервер, который, в свою очередь, расшифровывает сообщение PMS с помощью своего закрытого ключа из пары RSA:

    В конце этого процесса клиентская программа и веб-сервер Google теперь имеют одинаковые биты PMS. Каждая сторона использует эти биты для создания главного секрета и, вкратце, симметричного ключа шифрования/дешифрования, известного как сеансовый ключ.Теперь есть два разных, но идентичных сеансовых ключа, по одному на каждой стороне соединения. В примере с клиентом используется ключ сеанса AES128. После создания как на стороне клиентской программы, так и на стороне веб-сервера Google ключ сеанса на каждой стороне обеспечивает конфиденциальность разговора между двумя сторонами. Протокол рукопожатия, такой как Диффи-Хеллман, позволяет повторить весь процесс PMS, если одна из сторон (например, клиентская программа) или другая сторона (в данном случае веб-сервер Google) требуют перезапуска рукопожатия.

    Подведение итогов

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

    Читайте также: