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

Подписание через HSM

Spec: ISO 32000-2, §12.8 Spec: FIPS 140-3 Evidence: Standard-backed

Аппаратный модуль безопасности (HSM) выносит ключ подписания за пределы вашего процесса: устройство подписывает по запросу, но никогда не возвращает ключ. На этой странице объясняется стык PKCS#11, через который подписывает NextPDF, где именно проходит граница ключа и за какие части результата отвечает движок, а не устройство или вы.

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

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

  • Стандарт PKCS#11 определяет объект ключа, помеченный как чувствительный и неизвлекаемый. Его закрытое значение не может быть раскрыто в открытом виде за пределами токена. Spec: PKCS#11, v3.1 §10.9
  • NextPDF строит структуру подписи PDF и контейнер CMS. Он передаёт байты, подлежащие подписанию, через стык PKCS#11 и получает подпись обратно. Ключ никогда не пересекает этот стык.
  • Стык — это стабильный контракт. Один и тот же контракт удовлетворяют смарт-карта-токен, USB HSM, сетевой HSM и облачный KMS. Код движка между ними не меняется.
  • NextPDF — это программный движок подписания. Аппаратные гарантии устройства, его статус валидации, политика PIN-кода и развёртывание не входят в область сертификации движка. Он использует устройство, но не ручается за него.

NextPDF разделяет сборку подписи и вычисление значения подписи. Сборка — задача движка: разместить поле подписи, зарезервировать место в файле, вычислить диапазон байтов и построить CMS SignedData с его подписанными атрибутами. Spec: ISO 32000-2, §12.8

Вычисление значения подписи делегируется. Движок задаёт небольшой контракт поставщика подписи: тот получает непрозрачную последовательность байтов (на практике — подписанные атрибуты в кодировке DER) и возвращает «сырые» октеты подписи. Этот контракт и есть стык. Знание PDF и CMS остаётся на одной стороне, ключ — на другой. Поставщик может держать этот ключ в процессе для локального программного ключа, в облачном KMS или на аппаратном токене через PKCS#11. Код движка над стыком во всех случаях одинаков. Меняется только поставщик за ним.

PKCS#11 — интерфейс криптографического токена OASIS, исторически «Cryptoki», — это стандартный интерфейс на языке C для аппаратных токенов. Аппаратный путь NextPDF общается по PKCS#11 (напрямую или через мост командной строки OpenSSL для развёртываний типа engine или provider, где встроенная в процесс привязка не может загрузить токен).

Объект ключа на токене создаётся с двумя атрибутами, которые задают границу. Когда ключ помечен как чувствительный или неизвлекаемый, определённые закрытые атрибуты не могут быть раскрыты в открытом виде за пределами токена. Spec: PKCS#11, v3.1 §10.9 Сама операция подписания — это вызов токена: C_SignInit, затем C_Sign; выполняет её устройство. Spec: PKCS#11, v3.1 §5.10 Открытые данные, с которыми NextPDF работает во время подписания, — это байты, подлежащие подписанию. Назад возвращаются подпись и сертификат. Закрытого ключа нет ни на одном пути. Это и есть граница, и обеспечивает её токен, а не библиотека.

  1. Step 1 of 4: ISO 32000-2 §12.8 — signature dictionary, ByteRange, Contents
  2. Step 2 of 4: RFC 5652 CMS SignedData — the signature container
  3. Step 4 of 4: FIPS 140-3 / ISO/IEC 19790 cryptographic module assurance (device-level, deployment-dependent)
Где закреплена PDF-подпись с аппаратной поддержкой, по порядку: носитель PDF (ISO 32000-2 §12.8), содержащийся в нём контейнер CMS, интерфейс токена, через который подписывает NextPDF (PKCS#11), и стандарты гарантий модуля, которые описывают — но сами по себе не гарантируют — стоящее за ним устройство.

Один PIN-код, одна повторная аутентификация

Заголовок раздела «Один PIN-код, одна повторная аутентификация»

PKCS#11 позволяет требовать повторную аутентификацию ключа при каждом использовании: если атрибут CKA_ALWAYS_AUTHENTICATE установлен, пользователь должен предъявить PIN-код заново для каждой криптографической операции, а не один раз за сеанс. Spec: PKCS#11, v3.1 §10.9 Путь PKCS#11 в NextPDF рассчитан на это. PIN-код — чувствительный параметр. Он не журналируется и не сериализуется. Когда сеанс сообщает о существующем входе, NextPDF возвращает его в чистое состояние, чтобы следующая подпись прошла новую проверку PIN-кода. Это важно для токенов в стиле PIV, политика которых требует PIN-код для каждой подписи. Так движок уважает политику устройства и не ослабляет её.

Evidence: Standard-backed Свойство неизвлекаемости ключа — не утверждение NextPDF. Это модель PKCS#11: объект ключа, у которого CKA_SENSITIVE истинно или CKA_EXTRACTABLE ложно, не раскрывает своё закрытое значение в открытом виде за пределами токена. Spec: PKCS#11, v3.1 §10.9 Роль NextPDF в том, чтобы никогда не нуждаться в этом значении: он подписывает через операцию C_Sign токена, а не запрашивает материал ключа.

Evidence: Standard-backed PDF-сторона закреплена в Spec: ISO 32000-2, §12.8 . Дайджест диапазона байтов вычисляется по файлу, исключая значение подписи. Значение подписи, помещаемое в запись Contents, — это объект CMS SignedData в кодировке DER для подписей с открытым ключом. HSM создаёт только самые внутренние октеты подписи. NextPDF строит всё вокруг них и записывает их в структуру, которую определяет стандарт.

Evidence: Standard-backed Гарантии устройства описываются Spec: FIPS 140-3 и его базовым стандартом ISO/IEC 19790, которые определяют четыре возрастающих качественных уровня безопасности по одиннадцати группам требований — от спецификации алгоритма до признаков физического вскрытия. Эти стандарты описывают, чему должен удовлетворять модуль, чтобы заявлять уровень. Это свойство устройства и его валидации, а не NextPDF; и — по словам самого ISO/IEC 19790 — соответствия самого по себе недостаточно, чтобы гарантировать безопасность модуля в конкретном развёртывании.

Форма ниже носит иллюстративный характер. Она показывает стык, а не готовое к копированию развёртывание. Суть в том, что движку передают подписанта, а он никогда не видит ключ: sign() у подписанта — это вызов в устройство.

<?php
declare(strict_types=1);
use NextPDF\Contracts\HsmSignerInterface;
/**
* Sign a PDF where the private key lives on a PKCS#11 token.
*
* `$hsm` is a hardware-backed signer. Its sign() delegates to the token;
* the key never enters this process. Everything that makes the bytes a
* valid PDF signature — field, byte range, CMS SignedData — is built by
* the engine around the value the device returns.
*
* Token wiring (library path, slot, PIN, key label) is deployment
* configuration and is intentionally out of scope here: those values are
* operator-owned secrets, not library inputs to hardcode.
*/
function signWithToken(
string $pdfPath,
HsmSignerInterface $hsm,
): string {
// The engine asks the signer only for: the certificate (to embed in
// the CMS) and a signature over the bytes it computes. It never asks
// for, and the contract never exposes, the private key.
$certificateDer = $hsm->getCertificateDer();
$chainDer = $hsm->getCertificateChainDer();
// Pseudocode for the engine's own assembly step: build the signature
// dictionary + CMS SignedData, then hand the signed-attributes bytes
// to $hsm->sign(...) and place the returned octets in /Contents.
return nextpdf_sign_pdf(
pdfPath: $pdfPath,
signer: $hsm,
certificateDer: $certificateDer,
chainDer: $chainDer,
);
}

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

«Использование HSM означает, что подписание прошло валидацию FIPS.»

Нет. Путать эти две вещи — и есть ловушка. HSM — это место, где живёт ключ и выполняется операция. Валидация FIPS 140-3 / ISO/IEC 19790 — это свойство, которым может обладать устройство (или конкретная конфигурация модуля), установленное программой валидации, а не то, что присваивает вызывающая библиотека, и не то, что NextPDF утверждает от имени устройства. NextPDF совместим с подписанием через устройство PKCS#11, а его путь подписания протестирован с токенами, репрезентативными для категории. Прошло ли конкретное развёртывание валидацию на уровне FIPS-модуля, полностью зависит от оборудования, его сертификата, настройки и эксплуатации. Используйте точное слово для того, что у вас есть на самом деле.

Эта страница описывает стык и стандарты, на которых он основан. Это не гарантия развёртывания, и эту границу стоит обозначить прямо:

  • Ответственность движка. Построить поле подписи, зарезервировать место, вычислить диапазон байтов, собрать CMS SignedData, вызвать поставщика подписи и записать структурно корректную подпись согласно Spec: ISO 32000-2, §12.8 . Аппаратный путь NextPDF соответствует интерфейсу подписания PKCS#11 для этой цели.
  • Ответственность устройства и оператора. Устойчивость оборудования к вскрытию, его статус валидации FIPS 140-3 / ISO/IEC 19790, генерация и хранение ключей, политика PIN-кода, конфигурация слотов, прошивка и физическая безопасность. Ничего из этого движок не сертифицирует.
  • “Протестировано с” — не “сертифицировано”. То, что у NextPDF есть проверенный путь для репрезентативных категорий токенов — форм смарт-карты, USB, сетевых и облачных KMS, доступных через один и тот же контракт PKCS#11, — это заявление о совместимости. Это не сертификация, не подсчёт валидированных модулей и не утверждение о вашем конкретном устройстве. Категории оборудования ниже — это интеграционные формы через один стандартный интерфейс. Воспринимайте их как “где стык был опробован”, но никогда как гарантию для модели, которую вы сами не тестировали.
  • Постквантовое подписание носит экспериментальный характер. Там, где движок предоставляет постквантовое подписание через токен, оно включается явно, ограничено и проверено на заглушках, а не на постквантовой прошивке HSM. Каталоги криптографических наборов PAdES и AdES пока не признают эти наборы для долгосрочного архивирования. Не считайте его готовым к продакшену.
HSM-backed signing via PKCS#11 — edition availability
Edition Availability
Core

Не в этой редакции. Core предоставляет движок подписания и стык поставщика подписи с локальным поставщиком программного ключа.

Pro

Облачное управление ключами — подписание через управляемые ключи KMS — это возможность Pro, описанная только на уровне поведения.

Enterprise

Доступно. Подписание аппаратным токеном через интерфейс PKCS#11 (и мост командной строки OpenSSL для развёртываний типа engine/provider) — это возможность Enterprise. Доступность — это заявление о функции, а не сертификация какого-либо устройства или развёртывания.

Интеграционные формы через один интерфейс

Заголовок раздела «Интеграционные формы через один интерфейс»

Это формы, на которых был опробован стык PKCS#11. Столбец — это “как выглядит интеграция”, а не “список валидированных, сертифицированных или подсчитанных устройств”.

Интеграционная формаКак достигаетсяГраница ключаГарантии — свойство
Смарт-карта / PIV-токенPKCS#11-модуль; часто требуется PIN-код при каждом использованииНа карте; неизвлекаемыйКарта и её оператор
USB HSMPKCS#11-модульНа устройстве; неизвлекаемыйУстройство и его оператор
Сетевой / аппаратный HSMPKCS#11-модуль к сетевому устройствуНа устройстве; неизвлекаемыйУстройство, его конфигурация, оператор
Облачный KMSПоставщик управляемых ключей (Pro)В облачном сервисе; никогда не возвращаетсяОблачный провайдер и его аттестации
Мост-поставщик OpenSSLPKCS#11 через мост OpenSSLНа токене; неизвлекаемыйТокен и его оператор
Мини-FAQ

Попадает ли ключ когда-либо в процесс PHP? Нет. Для неизвлекаемого ключа PKCS#11 закрытое значение не может быть раскрыто в открытом виде за пределами токена. NextPDF подписывает через операцию токена и видит только байты для подписания и возвращённую подпись.

Отличается ли подпись через HSM внутри PDF? Нет. Структура подписи — тот же CMS SignedData в той же записи Contents по тому же диапазону байтов. HSM меняет то, где происходит подписание, а не вид на диске.

Могу ли я заявить о соответствии FIPS, потому что использовал HSM через NextPDF? Только с осторожностью. NextPDF ничего не утверждает о статусе FIPS устройства. Любое такое заявление должно опираться на собственную валидацию устройства и на то, как оно развёрнуто, а не на сам факт вызова из NextPDF.

Что, если встроенная в процесс привязка PKCS#11 недоступна? Движок сообщает, что аппаратное подписание недоступно, вместо того чтобы незаметно переключиться на программный ключ. Для развёртываний, где встроенная в процесс привязка не может загрузить токен, есть путь через мост командной строки OpenSSL.

  • HSM (аппаратный модуль безопасности) — защищённое устройство, которое хранит ключи и выполняет криптографические операции так, что материал ключа никогда его не покидает.
  • PKCS#11 — стандарт интерфейса криптографического токена OASIS (исторически «Cryptoki»); интерфейс на языке C, который NextPDF использует для общения с аппаратными токенами.
  • Неизвлекаемый ключ — объект ключа PKCS#11, чьё закрытое значение не может быть раскрыто в открытом виде за пределами токена (CKA_SENSITIVE истинно или CKA_EXTRACTABLE ложно).
  • Стык — граница поставщика подписи в NextPDF: непрозрачные байты на входе, октеты подписи на выходе. Знание PDF и CMS находится над ним, ключ — за ним.
  • CMS SignedData — структура Cryptographic Message Syntax (RFC 5652), которая несёт подпись и сертификаты внутри PDF.
  • FIPS 140-3 / ISO/IEC 19790 — стандарты безопасности криптографических модулей, определяющие четыре качественных уровня; это свойство устройства и его валидации, а не вызывающей библиотеки.