| ||||
| ||||
Можно ли средствами Крипто АПИ подписать данные используя закрытый ключ любого сертификата без предварительного хэширования данных. О маленькой скорости и нецелесообразности прошу не высказываться - я использую свой алгоритм хэширования. Так можно? и Как? | ||||
Ответы: | ||||
| ||||
Подпись - это шифрование хеша данных. То есть ты можешь просто с помощью стандартных средств CryptoAPI зашифровать подписываемые данные с помощью алгоритма, применяемого для подписи (обычно такие алгоритмы позволяют и шифровать на их основе). То есть ты будешь шифровать не просто данные, а какой-то хеш, сделанный самим тобой, то это будет нечто похожее на подпись. | ||||
| ||||
Ну, елки палки. Подпись - это не шифрование хэша данных. Подпись - это некоторое обратимое преобразование данных, обеспечивающее неотрекаемость и т.д и т.п. Так вот, если шифровать хэш данных закрытым ключом - это и будет подпись в вашем понимании. Почему используется хэш - да только потому, что ассиметричное шифрование очень медленное. А я за скоростью не гонюсь. Размер моих данных маленький. Так вот. Я повторяю свой вопрос - можно ли зашифровать произвольный набор данных на закрытом ключе сертификата и как это сделать? | ||||
| ||||
Евгений, сообщите народу, на каком алгоритме и на каком CSP Вы хотите делать подпись, не вычисляя хеша - и сразу ответим, можно ли это сделать через CryptoAPI. | ||||
| ||||
Василий. Еще раз - есть сертификат и ключевой контейнер, то есть имеются два ключа - закрытый и открытый. Ведь в ключе есть идентификатор, для чего он предназначен, для какого алгоритма. Хочу зашифровать данные с помощью закрытого ключа, то есть фактически их подписать. Так вот, можно ли это сделать средствами Крипто АПИ для любого криптопровайдера и любого алгоритма? | ||||
| ||||
Полная путаница в понятиях. Шифрование предназначено для того, чтобы никто, кроме конкретного получателя (имеющего закрытый ключ для расшифрования) не смог бы прочитать сообщение. Может быть несколько получателей. При этом тот, кто зашифровывает, заранее определяет тех (обладателей закрытых ключей), кто сможет расшифровать. Подпись предназначена для другого - чтобы любой человек мог бы проверить ЭЦП с помощью открытого ключа (из сертификата того, кто подписывает) и убедиться в двух фактах: 1) данные действительно подписаны обладателем закрытого ключа, соответствующего сертификату подписи 2) сообщение с подписью не модифицировано. | ||||
| ||||
Василий. Извините меня, но я не путаюсь в понятиях криптографии. Это Вы, вероятно, хороший программист, отлично знающий и ориентирующийся в Крипто АПИ и имеющий большой опыт в написании кодов, но, как у меня складывается впечатление, изучавший криптографию именно по этому Крипто АПИ. Почитайте хотя бы Брюса Шнайера для общего развития и более глубокого понимания корней крипторафии. То, что Вы мне написали в последнем сообщении - это всего лишь основные аспекты ассиметричной криптографии, я их прекрасно понимаю. Шифрование - это применение обратимых преобразований к исходным данным с целью их, данных, защиты. А защита может быть разная - как обеспечение конфиденциальности, так и целостности, подлинности и т.д. Если говорить простым языком, то шифрование с помощью открытого ключа ассиметричным шифром - это и есть обеспечение секретности, а шифрование с помощью закрытого ключа - это обеспечение подлинности, что называется электронно цифровой подписью. А смысл ведь один и тот же. Я задал вопрос - имеются ли средства в Крипто АПИ для шифрования данных с помощью закрытого ключа, и как это сделать. И моей ошибкой было то, что я упомянул ЭЦП. А Вы все здесь начали умничать, пытаясь задавить интеллектом и знанием терминологии, хотя сами, по-видимому, не особо разбираетесь в истоках криптографии. И я все еще гадаю, получу ли я ответ на свой вопрос... Изначальный... | ||||
| ||||
Ок, цитата из книги Брюса Шнайдера "Прикладная криптография": "Изменение вида сообщения так, чтобы спрятать его суть называется шифрованием". И ничего про целостность, авторство и т.п. Т.к. Вы не сообщили, на каком алгоритме Вы хотите делать описанное Вами криптографическое преобразование данных (как бы оно ни называлось), то я делаю вывод, что Вы хотите брать его из сертификата, т.е. сделать универсальный механизм. Если так, сообщите, с помощью какого(каких) CSP Вы хотите это делать - раз уж речь о CryptoAPI? В СКЗИ "КриптоПро CSP" нет реализации асимметричного шифрования данных. | ||||
| ||||
Василий, я понимаю, что Вы, конечно, практик. И поэтому Вам так необходимо знать алгоритм и криптопровайдер. Но, сертификат - это элемент PKI. Не суть как важно, какой криптопровайдер используется. У меня есть сертификат и связка с закрытым ключом. Вызываю CryptAcquireCertificatePrivateKey и получаю указатель на криптопровайдера. Я хочу с помощью секретного ключа (опять же как его получить) зашифровать какие-нибудь данные. Так вот - я пока не нашел инструментария, чтобы сделать этот универсал. И хочу узнать, возможно ли это вообще - для любого криптопровайдера, если нет, то интересно почему. Если да, то хотелось бы узнать направление движения. | ||||
| ||||
И еще... Как же так? Крипто ПРО реализует алгоритмы ГОСТ 94 и 2001, но при этом Вы утверждаете, что нет поддержки ассиметричного шифрования данных. Вы так сказали, чтобы от меня отделаться? Поясняю еще, тот же CryptSignMessage хэширует входные данные и фактически шифрует их закрытым ключом сертификата, и в зависимости от параметров включает в выходные данные входные и сам сертификат. В самом МСДН написано, что функция CryptSignMessage внутри использует CryptCreateHash, CryptHashData и CryptSignHash. Так вот. Возникает идея использовать CryptEncrypt (или что-нибудь другое, вот только что) и указатель на закрытый ключ, чтобы опять же фактически подписать данные. Зачем это делать - чтобы использовать свой алгоритм хэширования данных, опять же для универсальности. Не могу найти соответствующих средств Крипто АПИ. В таком подробном описании понятна суть вопроса? Надеюсь, что да. | ||||
| ||||
Я от своих слов не отказываюсь - средств асимметричного шифрования данных в нашем CSP нет. Есть только функция подписи хеша, т.е. криптографическое преобразование хеш-значения (фиксированной длины) с использованием закрытого ключа. Шифрование данных (CryptEncrypt) возможно в нашем CSP только на симметричном ключе (ГОСТ 28147-89). Если Вы допускаете использование разных CSP (в зависимости от сертификата) - то есть готовые средства (в CryptoAPI) для подписи, для шифрования, и для того и другого сразу. Проверка подписи и расшифрование будут выполняться на том же CSP (или совместимом). Универсальности тут нет, и, по-видимому, долго-долго не будет. Да и зачем - вот в чём вопрос? | ||||
| ||||
Мне все ясно. Спасибо за оказанное внимание. Жалко, конечно, что возникает необходимость каждый раз передавать в функции подписи OID алгоритмов хэширования, и это нельзя обойти. И последнее - Microsoft Base Cryptographic Provider поддерживает несколько алгоритмов хэширования, например sha и md5. Так вот, если перебирать поддерживаемые алгоритмы криптопровайдера, то в каком порядке они будут появляться - неизвестно? | ||||
| ||||
Порядок получения перечисляемых данных не фиксирован. | ||||
| ||||
(поднимем хорошую тему наверх) У меня вот какая задача. Дано 1) тонкий клиент - редактирует и смотрит док частями 2) выкачать документ полностью на клиента нереально 3) сервер умеет вычислять гостовый хэш от всего документа (32 байта) Требуется 1) подписать хэш на клиенте, на выходе имея pkcs7 signed message (detached) средствами cpcsp. Т.е. надо из 32-х байтов сделать структуру hash object Потом всё это подписать (контекст сертификата считаем что есть, закрытый ключ есть, всё связано, всё ok). Сошлите пожалуйста на тестовый пример, а то я от этого запутанного api сейчас помру. | ||||
| ||||
В общех чертах так: Сервер: CryptHashData CryptGetHashParam(HP_HASHVAL) Клиент CryptSetHashParam(HP_HASHVAL) CryptSignHash Ну и закодировать pkcs7. | ||||
| ||||
Мах, еще вопрос - откуду CryptSignHash берёт закрытый ключ? BOOL WINAPI CryptSignHash( HCRYPTHASH hHash, DWORD dwKeySpec, LPCTSTR sDescription, DWORD dwFlags, BYTE* pbSignature, DWORD* pdwSigLen ); dwKeySpec - Identifies the private key. It can be AT_KEYEXCHANGE or AT_SIGNATURE. Замечательно, только у меня этих закрытых ключей в хранилище - 2 :) Иванов1 и Иванов2. Как она выберет? | ||||
| ||||
hHash берется их CryptCreateHash, который в свою очередь использует hProv из CryptAcquireContext - там секретный ключ и цепляется. | ||||
| ||||
Спасибо :beer: | ||||