| ||||
| ||||
Добрый день. Сразу оговорюсь, что абсолютный новичок по отношению к CryptoAPI, да и к криптографии вобщем-то(всего несколько дней разбираюсь с этим пока и впечатления достаточно противоречивые), так что сильно не пинайте. Есть следующая задачка: на серваке хранится "документ", который нужно "подписывать" нескольким "клиентам". Здесь и начинаются проблемы(моего понимания). Документ не пересылается клиентам, подписывается хеш, выданный сервером, а значит используются низкоуровневые функции(CryptSignHash,...). То есть нужно использовать заранее определённую схему кеширования(алгоритм), а это ведёт к несовместимости в условиях наличия нескольких CSP. Пока я ничего нигде не "проморгал"? Далее, сам процесс подписи - тут, как я понимаю, лучше(нужно) использовать сертификаты открытых ключей(из них уже вытягивать ключи), а не просто ключи(как потом выйти от ключей к "людям", и более "серьёзная" проверка самого сертификата на валидность, например)? Прав? И хранить подпись вместе с сертификатом опять же на сервере. Что обычно находится у клиента на защищённом носителе(дискета, флэщка), ключи вместе с сертификатом? Кстати, как создать пару ключей и сертификат с помощью КриптоПро(у меня имеется демо)? Выполняю следующее(пытаюсь создать пару ключей): csptest-2-0.exe -keyset -newkeyset -provtype 71 -keytype signature -container MyContainer в ответ: CryptAcquireContext succeeded.HCRYPTPROV: 1269048 CryptGetProvParam succeeded. Provider name: Crypto-Pro GOST R 34.10-94 KC2 CSP A crypto context has been acquired and The name on the key container is "MyContainer" No signature key is available. The signature key does not exist. Create a signature key pair. An error occurred in running the program. ctkey.c:1290:Error occurred creating a signature key. Error number 80090020 (-2146893792). An internal error occurred. Program terminating. Press Enter to exit. Заранее благодарен всем ответившим. | ||||
Ответы: | ||||
| ||||
Отвечаю по порядку: "Документ не пересылается клиентам, подписывается хеш, выданный сервером, а значит используются низкоуровневые функции(CryptSignHash,...)." - неудачная схема. "Получается, что клиент не видит что реально подписывает. заранее определённую схему кеширования(алгоритм), а это ведёт к несовместимости в условиях наличия нескольких CSP". Схему хеширования? Да, только если CSP, реализующие один и тот же алгоритм, несовместимы между собой. Это легко учесть и включить в требования на стадии проектирования - вообщем то достаточно требовать наличия какого-то определенного провайдера. "Прав?" Абсолютно. "Что обычно находится у клиента на защищённом носителе(дискета, флэщка), ключи вместе с сертификатом?" Да, именно это и находится. "Error number 80090020 (-2146893792)." У Вас, скорее всего, нету аппаратного генератора случайных чисел, в КС2 биологический не установлен. 2 варианта - либо поставьте КриптоПро CSP КС1, либо добавьте биологический датчик случайных чисел в KC2. | ||||
| ||||
Кирилл, спасибо за ответы. По поводу неудачной схемы - это да, но если нужно не перекачивать файлы с сервера клиенту, то какое решение может тут иметь своё место?... К слову, Множественная подпись - это просто подписание подписанного документа энное количество раз? Хотелось бы иметь подписи к исходному документу, а не к документу, "нагруженному" другими подписями - выход "detached signing" или есть некий стандарт? "Схему хеширования? Да, только если CSP, реализующие один и тот же алгоритм, несовместимы между собой. Это легко учесть и включить в требования на стадии проектирования - вообщем то достаточно требовать наличия какого-то определенного провайдера." Суть вопроса в том, что КриптоПро CSP не будет подписывать MD5-хэш, так же как, скажем, ' Microsoft Enhanced Cryptographic Provider v1.0' не будет это же делать с ГОСТовским хэшем ... :( А значит, требования - наличия единого провайдера. "У Вас, скорее всего, нету аппаратного генератора случайных чисел, в КС2 биологический не установлен. 2 варианта - либо поставьте КриптоПро CSP КС1, либо добавьте биологический датчик случайных чисел в KC2." Спасибо, заработало. Еще, если не против, вопрос. Как узнать ALGORITHM_ID(не прописывая его явно в коде) алгоритма, которым "следует" генерировать хэш, конкретного провайдера? C помощью CryptGetProvParam(...,PP_ENUMALGS_EX,...) можно их перечислить, причём некоторые провайдеры возвращают в dwProtocols что-то(0x20(CRYPT_FLAG_SIGNING) для подписи), а некоторые нет... | ||||
| ||||
Все зависит от клиентов. Если они согласны подписывать "кота в мешке", то такая схема пройдет. Однако возможна подмена данных на сервере перед или в момент подписания. Сами подписи друг другу не мешают. Зависит от того каким способом Вы будете подписывать - добавлять подпись к существующим, заверять уже существующие, удалять предыдущую и добавлять новую - в любом случае исходный документ без подписей можно получить без проблем. Detached нужно для того чтобы хранить подпись отдельно от документа. Допустим у Вас есть база документов и Вы хотите каждый подписать - создавать новое поле, которое будет содержать подпись + исходный документ плохой вариант, для этого и существует detached. Вопрос про хэш не совсем понятен. Если провайдер поддерживает несколько алгоритмов, то хешировать можно любым из них, а каким именно - должно определяться дополнительными требованиями. | ||||
| ||||
"Все зависит от клиентов. Если они согласны подписывать "кота в мешке", то такая схема пройдет. Однако возможна подмена данных на сервере перед или в момент подписания." Это конечно. А также интересен вопрос о "самописном" софте, не должен ли он быть каким либо образом "сертифицирован", ведь при желании, ничто не мешает отказаться от подписи ввиду отсутствия "сертифицированного инструмента". "Вопрос про хэш не совсем понятен." Тут вопрос о возможности узнать метод(даже не знаю..., рекомендованный что-ли) хэширования данного криптопровайдера(и не из документации :) ). Вот например, список поддерживаемых алгоритмов: ALG_ID(OID) | (key length(min,def,max)) | dwProtocols | Name --- 26142(1.2.643.2.2.21) | (256,256,256) | 0x0 | GOST 28147-89(ProCSP ГОСТ 28147-89) 32798(1.2.643.2.2.9) | (256,256,256) | 0x0 | GOST R 34.11-94(ProCSP ГОСТ Р 34.11-94) 32799(NULL) | (32,32,32) | 0x0 | HMAC GOST 28147-89(ProCSP Имитовставка ГОСТ 28147-89) 11806(1.2.643.2.2.20) | (1024,1024,1024) | 0x0 | GOST R 34.10-94(ProCSP ГОСТ Р 34.10-94) 43550(1.2.643.2.2.99) | (1024,1024,1024) | 0x0 | Diffie-Hellman(ProCSP Диффи-Хелман Крипто Про ГОСТ) 43551(NULL) | (1024,1024,1024) | 0x0 | Diffie-Hellman(ProCSP Диффи-Хелман Крипто Про ГОСТ) как тут узнать какой протокол используется для "signing", а про "рекомендуемый" и говорить не приходится(или я не прав - буду очень обрадован, если не прав :) )? То есть протокол необходимо "зашивать"... | ||||
| ||||
Про равнозначность подписи и сертифицированность лучше почитать в Законе об ЭЦП http://www.cryptopro.ru/cryptopro/documentation/pdf/podpis.pdf. Тип алгоритма содержится в его ALG_ID. Например #define CALG_GR3411 (ALG_CLASS_HASH | ALG_TYPE_ANY | ALG_SID_GR3411), #define CALG_GR3410EL (ALG_CLASS_SIGNATURE | ALG_TYPE_GR3410 | ALG_SID_GR3410EL). Эти константы прописаны в wincryptex.h. Рекомендуемый алгоритм, конечно, по ним определить нельзя. | ||||
| ||||
Кирилл, спасибо за подсказки. | ||||