1

Тема: COM интерфейсы для работы с криптографическими алгоритмами. Signal-COM

Для работы с криптографическими алгоритмами  можно использовать стандартные COM интерфейсы, разработанные Microsoft на базе интерфейса CryptoAPI:
Certificate Enrollment Control
CAPICOM.

Поделиться

2

Re: COM интерфейсы для работы с криптографическими алгоритмами. Signal-COM

Поделиться

3

Re: COM интерфейсы для работы с криптографическими алгоритмами. Signal-COM

Поделиться

4

Re: COM интерфейсы для работы с криптографическими алгоритмами. Signal-COM

Поделиться

5

Re: COM интерфейсы для работы с криптографическими алгоритмами. Signal-COM

Поделиться

6

Re: COM интерфейсы для работы с криптографическими алгоритмами. Signal-COM

Базовые криптографические функции
Базовые криптографические функции - это самый низкий уровень интерфейса CryptoAPI.

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

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

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

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

Поделиться

7

Re: COM интерфейсы для работы с криптографическими алгоритмами. Signal-COM

Создание криптографического контекста
Многие функции CryptoAPI используют в качестве параметра криптографический контекст, получаемый с помощью функции CryptAcquireContext (см. MSDN). Наряду с другими параметрами в ней задаются имя и тип криптопровайдера. СКЗИ "Signal-COM CSP" включает в себя следующие криптопровайдеры (см. заголовочный файл SCCSP.H):

Имя Тип Описание
SC_ECGOST_PROV PROV_SC_ECGOST Криптопровайдер для алгоритма ГОСТ Р 34.10-2001. 
SC_CPGOST_PROV PROV_SC_CPGOST Криптопровайдер для алгоритма ГОСТ Р 34.10-2001 с параметрами, описанными в RFC 4491. 

Примечание. Для работы с устройством MS_Key в функции CryptAcquireContext необходимо задать тип провайдера PROV_SC_CPGOST и имя провайдера SC_CPGOST_PROV.

Поделиться

8

Re: COM интерфейсы для работы с криптографическими алгоритмами. Signal-COM

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

Вызовите функцию CryptAcquireContext с флагом CRYPT_NEWKEYSET (можно задать дополнительные флаги CRYPT_SILENT и CRYPT_MACHINE_KEYSET, см. MSDN), задав параметры Signal-COM CSP, как указано в  Создание криптографического контекста.
Если имя ключевого контейнера в функции CryptAcquireContext не задано, СКЗИ "Signal-COM CSP" будет создавать ключевой контейнер с именем текущего пользователя.
Если на локальном компьютере уже используется ключевой контейнер с заданным именем, и флаг CRYPT_SILENT не задан, на экран будет выдано соответствующее предупреждение, с предложением продолжить или прервать операцию.
Если флаг CRYPT_SILENT не задан, на экран будет выдано окно, в котором необходимо выбрать ключевой носитель. Если флаг CRYPT_SILENT задан, СКЗИ "Signal-COM CSP" будет создавать ключевой контейнер на первом обнаруженном ключевом носителе. Если ключевые носители отсутствуют, функция CryptAcquireContext завершится, установив код ошибки NTE_FAIL.
Если ключевой контейнер с заданным именем уже существует на выбранном ключевом носителе, и флаг CRYPT_SILENT не задан, на экран будет выдано соответствующее предупреждение, с предложением переписать существующий контейнер или выбрать другой ключевой носитель. Если флаг CRYPT_SILENT задан, функция CryptAcquireContext завершится, установив код ошибки NTE_EXISTS.
При создании ключевого носителя используются случайные числа, поэтому может потребоваться инициализация генератора случайных чисел.
Тип ключевого носителя можно задать в функции CryptAcquireContext явно, указав его перед именем ключевого контейнера, например:

\\.\Floppy\My Key Container

Следующие типы ключевых носителей СКЗИ "Signal-COM CSP" можно задать в функции CryptAcquireContext:

Тип Описание
"Floppy" Дискета или flash-диск. 
"eToken" Устройство eToken. 
"ruToken" Устройство ruToken. 
"iButton" Устройство iButton.

Поделиться

9

Re: COM интерфейсы для работы с криптографическими алгоритмами. Signal-COM

Открытие ключевого контейнера
Для открытия ключевого контейнера выполните следующие действия:

Вызовите функцию CryptAcquireContext с флагом равным нулю (можно задать дополнительные флаги CRYPT_SILENT и CRYPT_MACHINE_KEYSET, см. MSDN), задав параметры Signal-COM CSP, как указано в  Создание криптографического контекста.
Если имя ключевого контейнера в функции CryptAcquireContext не задано, СКЗИ "Signal-COM CSP" будет искать ключевой контейнер с именем текущего пользователя.
Если контейнер не найден, и флаг CRYPT_SILENT не задан, на экран будет выдано окно, с предложением вставить в считывающее устройство ключевой носитель с указанным ключевым контейнером. Если флаг CRYPT_SILENT задан, функция CryptAcquireContext завершится, установив код ошибки NTE_KEYSET_NOT_DEF.
Если датчик случайных чисел еще не был инициализирован, он будет инициализирован от данного ключевого контейнера.
Тип ключевого носителя можно задать в функции CryptAcquireContext явно (см. Создание ключевого контейнера).

Поделиться

10

Re: COM интерфейсы для работы с криптографическими алгоритмами. Signal-COM

Зашифрование и расшифрование данных
Для зашифрования данных с использованием базовых функций CryptoAPI и Signal-COM CSP необходимо сгенерировать сеансовый ключ шифрования. Для этого выполните следующие действия:

Создайте криптографический контекст Signal-COM CSP.
Вызовите функцию CryptGenKey для генерации сеансового ключа, задав полученный криптографический контекст, идентификатор алгоритма шифрования CALG_CP_GOST_28147 и другие параметры как описано в MSDN.
Для генерации сеансового ключа используются случайные числа, поэтому может потребоваться инициализация генератора случайных чисел.
Полученный ключ можно затем использовать для зашифрования (CryptEncrypt) или расшифрования (CryptDecrypt) данных (см. MSDN).

Пример программы на C++, демонстрирующей генерацию сеансового ключа, зашифрование и расшифрование данных с использованием СКЗИ "Signal-COM CSP", приводится в файле enc_data.cpp (каталог samples\enc_data).

Поделиться

11

Re: COM интерфейсы для работы с криптографическими алгоритмами. Signal-COM

Экспорт и импорт сеансового ключа
Алгоритм экспорта/импорта сеансового ключа для криптопровайдера типа SC_CPGOST_PROV (с параметрами, описанными в RFC 4491) отличается от алгоритма для криптопровайдера типа SC_ECGOST_PROV. Ниже приводится описание алгоритмов и примеры программ для каждого из криптопровайдеров.

Алгоритм экспорта/импорта сеансового ключа для криптопровайдера типа SC_CPGOST_PROV.

Для экспорта сеансового ключа выполните следующие действия:

Получите дескриптор секретного ключа отправителя с помощью функции CryptGetUserKey, передавая AT_KEYEXCHANGE в параметре dwKeySpec.
Импортируйте открытый ключ получателя с помощью функции CryptImportKey, передавая в параметре pbData указатель на BLOB открытого ключа получателя, в параметре dwDataLen длину этого BLOB и дескриптор секретного ключа отправителя в параметре hPubKey. В результате данной операции по алгоритму Diffie-Hellman будет сформирован Agreed Key (секретный ключ, общий для отправителя и получателя).
Задайте (опционально) алгоритм экспорта сеансового ключа с помощью функции CryptSetKeyParam, передавая в параметре hKey дескриптор AK, KP_ALGID в параметре dwParam и указатель на переменную со значением CALG_CP_SIMPLE_WRAP (RFC 4357, раздел 6.1) или CALG_CP_PRO_WRAP (RFC 4357, раздел 6.3) в параметре pbData. Алгоритмы экспорта (отправитель) и импорта (получатель) сеансового ключа должны совпадать! По умолчанию для экспорта сеансового ключа используется алгоритм CALG_CP_PRO_WRAP.
Для экспорта сеансового ключа вызовите функцию CryptExportKey, передавая в параметре hKey дескриптор сеансового ключа, в параметре hExpKey дескриптор ключа обмена, SIMPLEBLOB в параметре dwBlobType, нулевое значение в параметре dwFlags, в параметре pbData указатель на буфер для размещения BLOB сеансового ключа и в параметре pdwDataLen указатель на длину этого буфера.
Экспортированный таким образом сеансовый ключ должен передаваться получателю зашифрованных данных вместе с самими данными.

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

Получите дескриптор секретного ключа получателя с помощью функции CryptGetUserKey, передавая AT_KEYEXCHANGE в параметре dwKeySpec.
Импортируйте открытый ключ отправителя с помощью функции CryptImportKey, передавая в параметре pbData указатель на BLOB открытого ключа отправителя, в параметре dwDataLen  длину этого BLOB и дескриптор секретного ключа получателя в параметре hPubKey. В результате данной операции по алгоритму Diffie-Hellman будет сформирован Agreed Key.
Задайте (опционально) алгоритм импорта сеансового ключа с помощью функции CryptSetKeyParam, передавая в параметре hKey дескриптор AK, KP_ALGID в параметре dwParam и указатель на переменную со значением CALG_CP_SIMPLE_WRAP (RFC 4357, раздел 6.1) или CALG_CP_PRO_WRAP (RFC 4357, раздел 6.3) в параметре pbData. Алгоритмы экспорта (отправитель) и импорта (получатель) сеансового ключа должны совпадать! По умолчанию для импорта сеансового ключа используется алгоритм CALG_CP_PRO_WRAP.
Для импорта сеансового ключа вызовите функцию CryptImportKey, передавая в параметре pbData указатель на BLOB сеансового ключа, в параметре dwDataLen длину этого BLOB и дескриптор ключа обмена в параметре hPubKey.
Импортированный сеансовый ключ можно затем использовать для расшифрования (CryptDecrypt) данных (см. MSDN).

Алгоритм экспорта/импорта сеансового ключа для криптопровайдера типа SC_ECGOST_PROV.

Для экспорта сеансового ключа выполните следующие действия:

Получите дескриптор секретного ключа отправителя с помощью функции CryptGetUserKey, передавая AT_KEYEXCHANGE в параметре dwKeySpec.
Импортируйте открытый ключ получателя с помощью функции CryptImportKey, передавая в параметре pbData указатель на BLOB открытого ключа получателя, в параметре dwDataLen длину этого BLOB и дескриптор секретного ключа отправителя в параметре hPubKey. В результате данной операции по алгоритму Diffie-Hellman будет сформирован Agreed Key (секретный ключ, общий для отправителя и получателя).
Если для формирования Agreed Key (AK) использовался долговременный ключ отправителя (хранится в ключевом контейнере), с помощью функции CryptGenRandom сгенерируйте User Keying Material (ключевой материал пользователя). При использовании долговременных ключей, AK для определенной пары пользователей будет фиксированным, поэтому уникальный общий ключ обмена необходимо создавать на основе фиксированного AK и случайного User Keying Material (64 байта). User Keying Material (UKM) должен передаваться получателю зашифрованных данных вместе с самими данными.
С помощью функции CryptSetKeyParam установите значение UKM для AK, передавая в параметре hKey дескриптор AK, KP_IV в параметре dwParam и UKM в параметре pbData.
Для формирования ключа обмена на основе AK и UKM вызовите функцию CryptSetKeyParam, передавая в параметре hKey дескриптор AK, KP_ALGID в параметре dwParam и указатель на переменную со значением CALG_RUS_CMS_WRAP в параметре pbData.
Для экспорта сеансового ключа вызовите функцию CryptExportKey, передавая в параметре hKey дескриптор сеансового ключа, в параметре hExpKey дескриптор ключа обмена, SYMMETRICWRAPKEYBLOB в параметре dwBlobType, нулевое значение в параметре dwFlags, в параметре pbData указатель на буфер для размещения BLOB сеансового ключа и в параметре pdwDataLen указатель на длину этого буфера.
Экспортированный таким образом сеансовый ключ должен передаваться получателю зашифрованных данных вместе с самими данными.

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

Получите дескриптор секретного ключа получателя с помощью функции CryptGetUserKey, передавая AT_KEYEXCHANGE в параметре dwKeySpec.
Импортируйте открытый ключ отправителя с помощью функции CryptImportKey, передавая в параметре pbData указатель на BLOB открытого ключа отправителя, в параметре dwDataLen  длину этого BLOB и дескриптор секретного ключа получателя в параметре hPubKey. В результате данной операции по алгоритму Diffie-Hellman будет сформирован Agreed Key.
С помощью функции CryptSetKeyParam установите значение User Keying Material для Agreed Key, передавая в параметре hKey дескриптор AK , KP_IV в параметре dwParam и UKM в параметре pbData.
Для формирования ключа обмена на основе AK и UKM вызовите функцию CryptSetKeyParam, передавая в параметре hKey дескриптор AK, KP_ALGID в параметре dwParam и указатель на переменную со значением CALG_RUS_CMS_WRAP в параметре pbData.
Для импорта сеансового ключа вызовите функцию CryptImportKey, передавая в параметре pbData указатель на BLOB сеансового ключа, в параметре dwDataLen длину этого BLOB и дескриптор ключа обмена в параметре hPubKey.
Импортированный сеансовый ключ можно затем использовать для расшифрования (CryptDecrypt) данных (см. MSDN).

Пример программы на C++, демонстрирующей формирование секретного ключа обмена для пары пользователей, генерацию сеансового ключа, зашифрование данных, экспорт сеансового ключа, импорт сеансового ключа и расшифрование данных для криптопровайдеров типа SC_CPGOST_PROV (функция RFC4491ProviderSample) и SC_ECGOST_PROV (функция SignalCOMProviderSample), приводится в файле exp_sess.cpp (каталог samples\exp_sess).

Поделиться

12

Re: COM интерфейсы для работы с криптографическими алгоритмами. Signal-COM

Хэширование, формирование и проверка цифровой подписи данных
Для хэширования, формирования или проверки подписи данных с использованием базовых функций CryptoAPI и СКЗИ "Signal-COM CSP" необходимо создать дескриптор хэш-объекта. Для этого выполните следующие действия:

Создайте криптографический контекст Signal-COM CSP.
Вызовите функцию CryptCreateHash для создания дескриптора хэш-объекта, задав полученный криптографический контекст, идентификатор хэш-алгоритма ( CALG_R3411 или CALG_CP_R3411) и другие параметры как описано в MSDN.
Полученный дескриптор можно затем использовать для хэширования данных (CryptHashData), для задания значения хэш-функции извне (CryptSetHashParam), для формирования (CryptSignHash) или проверки (CryptVerifySignature) подписи данных (см. MSDN).

Пример программы на C++, демонстрирующей операции хэширования, формирования и проверки подписи данных с использованием СКЗИ "Signal-COM CSP", приводится в файле sign_data.cpp (каталог samples\sign_data).

Поделиться

13

Re: COM интерфейсы для работы с криптографическими алгоритмами. Signal-COM

Формирование сеансовых ключей на основе мастер-ключа
В СКЗИ "Signal-COM CSP" реализована возможность формирования сеансовых ключей на основе мастер-ключа с использованием PRF (Pseudo-Random Function). Мастер-ключом может быть только сеансовый ключ, созданный с помощью функции CryptGenKey (см. Зашифрование и расшифрование данных) или выработанный с помощью алгоритма Diffie-Hellman (см. Экспорт и импорт сеансового ключа). Для формирования нового сеансового ключа на основе существующего мастер-ключа выполните следующие действия:

Вызовите функцию CryptCreateHash для создания хэш-объекта, задав криптографический контекст Signal-COM CSP, идентификатор хэш-алгоритма CALG_TLS1PRF и дескриптор мастер-ключа.
С помощью функции CryptSetHashParam можно (необязательно) задать для созданного хэш-объекта значение метки - произвольную текстовую строку, передавая в качестве типа параметра HP_TLS1PRF_LABEL, а саму метку в структуре CRYPT_DATA_BLOB.
Задайте для данного хэш-объекта заранее выбранные данные (seed), не являющиеся секретными и однозначно соответствующие сеансу шифрования, для которого вырабатывается ключ (например, уникальный идентификатор сеанса связи или пакета данных). Для этого вызовите функцию CryptSetHashParam, передавая в качестве типа параметра HP_TLS1PRF_SEED, а сами данные в структуре CRYPT_DATA_BLOB.
Вызовите функцию CryptDeriveKey, задав требуемый для сеансового ключа идентификатор алгоритма шифрования и дескриптор данного хэш-объекта (вектор инициализации создается автоматически и сохраняется в контексте созданного сеансового ключа).
Пример программы на C++, демонстрирующей формирование сеансового ключа на основе мастер-ключа, приводится в файле prf_sess.cpp (каталог samples\prf_sess).

Поделиться

14

Re: COM интерфейсы для работы с криптографическими алгоритмами. Signal-COM

Функции для работы с сообщениями
Данная группа функций предназначена для работы с сообщениями в формате CMS (PKCS#7): формирования и проверки цифровой подписи, зашифрования и расшифрования сообщений.

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

Поделиться

15

Re: COM интерфейсы для работы с криптографическими алгоритмами. Signal-COM

Формирование и проверка цифровой подписи сообщения
Для формирования подписи сообщения с использованием Signal-COM CSP выполните следующие действия:

Инициализируйте структуру CRYPT_SIGN_MESSAGE_PARA.
В поле pSigningCert задайте сертификат автора подписи, соответствующий формату сертификатов СКЗИ "Signal-COM CSP".
В поле HashAlgorithm.pszObjId для сертификата с параметрами Сигнал-КОМ задайте szOID_R3411, для сертификата с параметрами, описанными в RFC 4491 - szOID_CP_R3411 (см. заголовочный файл SCCSP.H).
Вызовите функцию CryptSignMessage для формирования подписи сообщения, задав структуру CRYPT_SIGN_MESSAGE_PARA и другие параметры как описано в MSDN.
Для проверки подписи сообщения используйте функцию CryptVerifyMessageSignature.

Пример программы на C++, демонстрирующей формирование и проверку подписи сообщения с использованием  СКЗИ "Signal-COM CSP", приводится в файле sign_msg.cpp (каталог samples\sign_msg).

Поделиться

16

Re: COM интерфейсы для работы с криптографическими алгоритмами. Signal-COM

Зашифрование и расшифрование сообщения
Для зашифрования сообщения с использованием СКЗИ "Signal-COM CSP" выполните следующие действия:

Создайте массив сертификатов получателей зашифрованного сообщения. Эти сертификаты должны соответствовать формату сертификатов СКЗИ "Signal-COM CSP".
Инициализируйте структуру CRYPT_ENCRYPT_MESSAGE_PARA .
Вызовите функцию CryptEncryptMessage для зашифрования сообщения, задав структуру CRYPT_ENCRYPT_MESSAGE_PARA, массив сертификатов и другие параметры как описано в MSDN.
Для зашифрования сообщения используются случайные числа, поэтому может потребоваться инициализация генератора случайных чисел.
Для расшифрования сообщения используйте функцию CryptDecryptMessage.

Пример программы на C++, демонстрирующей зашифрование и расшифрование сообщения с использованием СКЗИ "Signal-COM CSP", приводится в файле enc_msg.cpp (каталог samples\enc_msg).

Поделиться

17

Re: COM интерфейсы для работы с криптографическими алгоритмами. Signal-COM

Информация с сайта: signal-com.ru/ru/demo/csp/index.php

Поделиться