31.03.2006 11:15:36CryptSignMessage ошибка 2147942487 или AV Ответов: 7
Мария
При использовании функции CryptSignMessage возникает указанная ошибка.
Что я делаю не так ?
Пишу на дельфи
...
size : DWORD;
SignPara : CRYPT_SIGN_MESSAGE_PARA;
Signature, XMLData : PByte;
data : array [0..0] of PByte;
datasize : array [0..0] of DWORD;
...
ZeroMemory(@SignPara,sizeof(CRYPT_SIGN_MESSAGE_PARA));
SignPara.cbSize:=sizeof(SignPara);
SignPara.dwMsgEncodingType:=X509_ASN_ENCODING;
SignPara.pSigningCert:=FCertificate;
SignPara.HashAlgorithm.pszObjId:=szOID_RSA_MD5;
SignPara.HashAlgorithm.Parameters.cbData:=0;
SignPara.HashAlgorithm.Parameters.pbData:=nil;
SignPara.pvHashAuxInfo:=nil;
SignPara.cMsgCert:=0;
SignPara.rgpMsgCert:=nil;
SignPara.cAuthAttr:=0;
SignPara.dwInnerContentType:=0;
SignPara.cMsgCrl:=0;
SignPara.cUnauthAttr:=0;

GetMem(XMLData,Length(Content));
System.Move(Pointer(Content)^,XMLData^,Length(Content));
data[0]:=XMLData;
datasize[0]:=Length(Content);
size:=0;

if not CryptSignMessage(@SignPara,True,1,@data[0],@datasize[0],nil,@size) then begin
ShowMessage('Error: '+IntToStr(GetLastError));
CloseProvider;
Exit;
end;
...

Прототип функции
function CryptSignMessage(pSignPara :PCRYPT_SIGN_MESSAGE_PARA;
fDetachedSignature :BOOL;
cToBeSigned :DWORD;
const rgpbToBeSigned : Pointer;
rgcbToBeSigned : Pointer;
pbSignedBlob :PBYTE;
pcbSignedBlob :PDWORD):BOOL ; stdcall;

До этого возникал AV 0000000
поменяла прототип, как было посоветовано в одном из вопросов на форуме, теперь другая ошибка
 
Ответы:
31.03.2006 16:19:59Мария
Вопрос снят, был неправильно указан алгоритм

Сделала так и все заработало :
SignPara.HashAlgorithm.pszObjId:=FCertificate.pCertInfo.SignatureAlgorithm.pszObjId;
03.04.2006 10:11:45Kirill Sobolev
В общем случае этот подход неверный, т.к. алгоритм ОК ЦС может отличаться от ОК выдаваемых им сертификатов, т.е. алгоритмы подписи не будут совпадать.
05.04.2006 11:54:42Мария
Да действительно и в моем случае правильнее было указать жестко требуемый алгоритм, то есть

SignPara.HashAlgorithm.pszObjId:=CertAlgIdToOID(AlgorithmHash);

Вопрос такой у меня возник
У меня требуется чтобы ЭЦП была получена по ГОСТ 34.10-94 или по ГОСТ 34.10-2001, то есть FAlgorithmSign := CALG_GR3410;
Я не могу понять где мне надо указать чтоб для получения ЭЦП использовался именно этот алгоритм
Я думаю моя проблема именно в этом, потому что получаемая мной ЭЦП долна иметь размер 512, а она получается всего лишь 310
Подскажите пожалуйста, где я что делаю неправильно
05.04.2006 12:31:52Kirill Sobolev
CALG_GR3410 - это алгоритм ОК,
алгоритм хэширования - это CALG_GR3411 (1.2.643.2.2.9), его как раз и надо указывать в поле
SignPara.HashAlgorithm.pszObjId
А с чего Вы решили что у Вас ЭЦП будет именно 512 байт?
05.04.2006 12:37:47Мария
Смотрю у себя в нормативный документ, читаю :
"В соответсвии с ГОСТ Р 34.10-94 и ГОСТ Р 34.10-2001 значение ЭЦП представляется в виде двоичного вектора длиной 512..."
И в чужом подписанном документе, длина ЭЦП - 512
Может конечно я вообще все путаю..

А алгоритм хеширования я именно такой и указала
FAlgorithmHash := CALG_GR3411;
05.04.2006 13:39:04Kirill Sobolev
"двоичного вектора длиной 512..." бит все-таки. Это как раз длина ОК.
Дело в том, что CryptSignMessage возвращает сообщение формата PKCS7, где помимо собственно критопграфической подписи (которая 512 бит) содержится еще алгоритм подписи, информация о сертификате подписчика да еще много чего. Вот этот PKCS7 и занимает 310 байт.
05.04.2006 13:44:07Мария
Спасибо за разъяснение, вроде поняла )