将TSA的响应添加到CryptSignMessage的CRYPT_SIGN_MESSAGE_PARA(c
发布时间:2020-12-16 07:05:40 所属栏目:百科 来源:网络整理
导读:我正在努力如何将TSA服务器的响应添加到我的CryptSignMessage? 使用PKCS#7.我目前有消息摘要,并且我使用来自crypto api的CryptSignMessage成功签名.像这样: // Initialize the signature structure.CRYPT_SIGN_MESSAGE_PARA SigParams;SigParams.cbSize =
我正在努力如何将TSA服务器的响应添加到我的CryptSignMessage?
使用PKCS#7.我目前有消息摘要,并且我使用来自crypto api的CryptSignMessage成功签名.像这样: // Initialize the signature structure. CRYPT_SIGN_MESSAGE_PARA SigParams; SigParams.cbSize = sizeof(CRYPT_SIGN_MESSAGE_PARA); SigParams.dwMsgEncodingType = MY_ENCODING_TYPE; SigParams.pSigningCert = hContext; SigParams.HashAlgorithm.pszObjId = szOID_RSA_SHA1RSA; SigParams.HashAlgorithm.Parameters.cbData = NULL; SigParams.cMsgCert = 1; SigParams.rgpMsgCert = &hContext; SigParams.dwInnerContentType = 0; SigParams.cMsgCrl = 0; SigParams.cUnauthAttr = 0; SigParams.dwFlags = 0; SigParams.pvHashAuxInfo = NULL; SigParams.cAuthAttr = 0; SigParams.rgAuthAttr = NULL; // First,get the size of the signed BLOB. if(CryptSignMessage( &SigParams,FALSE,1,MessageArray,MessageSizeArray,NULL,&cbSignedMessageBlob)) { printf("%d bytes needed for the encoded BLOB.",cbSignedMessageBlob); } else { MyHandleError(); fReturn = false; exit_SignMessage(); } // Allocate memory for the signed BLOB. if(!(pbSignedMessageBlob = (BYTE*)malloc(cbSignedMessageBlob))) { MyHandleError(); exit_SignMessage(); } // Get the signed message BLOB. if(CryptSignMessage( &SigParams,TRUE,pbSignedMessageBlob,&cbSignedMessageBlob)) { printf("The message was signed successfully. n"); // pbSignedMessageBlob now contains the signed BLOB. fReturn = true; } else { MyHandleError(); fReturn = false; exit_SignMessage(); } 现在我想使用TSA服务器为我的摘要加时间戳,但我不确定如何包含它.假设我有一个rfc3161 TimeStamp请求;我发送给我的TSA,我收到一个rfc3161 TimeStamp响应(可能使用libcurl).如何将响应纳入我的SigParams?我必须提取TimeStampToken,然后将其存储为未经身份验证的计数器签名吗?就像是: CRYPT_ATTR_BLOB cablob[1]; CRYPT_ATTRIBUTE ca[1]; cablob[0].cbData = tstResponseSize; cablob[0].pbData = tstResponse; // the response from TSA ca[0].pszObjId = "1.2.840.113549.9.6"; // object identifier for counter signature ca[0].cValue = 1; ca[0].rgValue = cablob; 然后设置SigParams: SigParams.cUnauthAtt = 1; SigParams.rgUnauthAttr = ca; 任何建议将不胜感激. 解决方法
我挣扎了几天.那里没有那么多例子,所以这是我的解决方案.希望能帮助到你 :)
HCRYPTMSG hMsg = ::CryptMsgOpenToDecode(X509_ASN_ENCODING | PKCS_7_ASN_ENCODING,CMSG_DETACHED_FLAG,NULL); if (NULL == hMsg) { throw std::exception("Failed to open messsage to decode"); } if (!::CryptMsgUpdate(hMsg,signedData.pbData,signedData.cbData,TRUE)) { throw std::exception("Failed to add signature block to message"); } //get the digest from the signature PCRYPT_TIMESTAMP_CONTEXT pTsContext = NULL; DWORD encDigestSize = 0; if (::CryptMsgGetParam(hMsg,CMSG_ENCRYPTED_DIGEST,&encDigestSize)) { std::unique_ptr<BYTE> pEncDigest(new BYTE[encDigestSize]); if (::CryptMsgGetParam(hMsg,pEncDigest.get(),&encDigestSize)) { //get timestamp if (::CryptRetrieveTimeStamp(L"http://sha256timestamp.ws.symantec.com/sha256/timestamp",TIMESTAMP_NO_AUTH_RETRIEVAL,//timeout????? szOID_NIST_sha256,encDigestSize,&pTsContext,NULL)) { CRYPT_ATTR_BLOB cryptBlob = {}; cryptBlob.cbData = pTsContext->cbEncoded; cryptBlob.pbData = pTsContext->pbEncoded; CRYPT_ATTRIBUTE cryptAttribute = {}; cryptAttribute.pszObjId = "1.2.840.113549.1.9.16.2.14"; //id-smime-aa-timeStampToken cryptAttribute.cValue = 1; cryptAttribute.rgValue = &cryptBlob; DWORD encodedAttributeSize = 0; std::unique_ptr<BYTE> encodedAttribute; if (::CryptEncodeObject(X509_ASN_ENCODING | PKCS_7_ASN_ENCODING,PKCS_ATTRIBUTE,&cryptAttribute,&encodedAttributeSize)) { encodedAttribute.reset(new BYTE[encodedAttributeSize]); if (::CryptEncodeObject(X509_ASN_ENCODING | PKCS_7_ASN_ENCODING,encodedAttribute.get(),&encodedAttributeSize)) { CMSG_CTRL_ADD_SIGNER_UNAUTH_ATTR_PARA unauthenticatedParam = { 0 }; unauthenticatedParam.cbSize = sizeof(unauthenticatedParam); unauthenticatedParam.dwSignerIndex = 0; //only have 1 cert unauthenticatedParam.blob.cbData = encodedAttributeSize; unauthenticatedParam.blob.pbData = encodedAttribute.get(); if (::CryptMsgControl(hMsg,CMSG_CTRL_ADD_SIGNER_UNAUTH_ATTR,&unauthenticatedParam)) { DWORD encodedMessageLength = 0; if (::CryptMsgGetParam(hMsg,CMSG_ENCODED_MESSAGE,&encodedMessageLength)) { std::unique_ptr<BYTE> pData(new BYTE[encodedMessageLength]); if (::CryptMsgGetParam(hMsg,pData.get(),&encodedMessageLength)) { //save pData/encodedMessageLength here to file } } } } } } } } if (NULL != pTsContext) { ::CryptMemFree(pTsContext); } if (NULL != hMsg) { ::CryptMsgClose(hMsg); } (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |