https://bugs.freedesktop.org/show_bug.cgi?id=87030
--- Comment #5 from Tor Lillqvist <[email protected]> --- For reference, here is a diff with various hacks that I have tried to get it to work, but no luck. It is interesting that if I don't use the certificate created directly by CertCreateCertificateContext() from the DER data, but look it up from the "MY" store using CertFindCertificateInStore(), then CertEnumCertificateContextProperties() finds various properties in the certificate. Also, it is interesting that the certificate provided to me (the "Collabora Dev Softtoken" one) is an AT_KEYEXCHANGE one!? That is what certutil -dump -v and CryptAcquireCertificatePrivateKey() tell me. I would have expected it to be an AT_SIGNATURE one. But probably I misunderstand something. diff --git a/vcl/source/gdi/pdfwriter_impl.cxx b/vcl/source/gdi/pdfwriter_impl.cxx index b459a8d..ab9e2cf --- a/vcl/source/gdi/pdfwriter_impl.cxx +++ b/vcl/source/gdi/pdfwriter_impl.cxx @@ -6215,13 +6215,31 @@ bool PDFWriterImpl::finalizeSignature() #else - PCCERT_CONTEXT pCertContext = CertCreateCertificateContext(X509_ASN_ENCODING | PKCS_7_ASN_ENCODING, reinterpret_cast<const BYTE*>(n_derArray), n_derLength); - if (pCertContext == NULL) + PCCERT_CONTEXT pCertContextFromDER = CertCreateCertificateContext(X509_ASN_ENCODING | PKCS_7_ASN_ENCODING, reinterpret_cast<const BYTE*>(n_derArray), n_derLength); + if (pCertContextFromDER == NULL) { SAL_WARN("vcl.pdfwriter", "CertCreateCertificateContext failed: " << WindowsError(GetLastError())); return false; } +#if 1 + HCERTSTORE hCertStore = CertOpenSystemStore(NULL, "MY"); + if (!hCertStore) + { + SAL_WARN("vcl.pdfwriter", "CertOpenSystemStore failed: " << WindowsError(GetLastError())); + return false; + } + + PCCERT_CONTEXT pCertContext = CertFindCertificateInStore(hCertStore, X509_ASN_ENCODING | PKCS_7_ASN_ENCODING, 0, CERT_FIND_EXISTING, (const void*) pCertContextFromDER, NULL); + if (pCertContext == NULL) + { + SAL_WARN("vcl.pdfwriter", "CertFindCertificateInStore failed: " << WindowsError(GetLastError())); + return false; + } +#else + PCCERT_CONTEXT pCertContext = pCertContextFromDER; +#endif + #if SAL_LOG_INFO DWORD nProperty(0); bool first(true); @@ -6234,8 +6252,7 @@ bool PDFWriterImpl::finalizeSignature() DWORD nSize(0); if (!CertGetCertificateContextProperty(pCertContext, nProperty, NULL, &nSize)) SAL_INFO("vcl.pdfwriter", " " << "(missing?) " << std::hex << nProperty); - else - { + else { boost::scoped_array<char> aData(new char[nSize]); if (!CertGetCertificateContextProperty(pCertContext, nProperty, aData.get(), &nSize)) SAL_INFO("vcl.pdfwriter", " " << "(missing?) " << std::hex:: << nProperty); @@ -6243,7 +6260,7 @@ bool PDFWriterImpl::finalizeSignature() SAL_INFO("vcl.pdfwriter", " " << CertificatePropertyNameAndData(nProperty, aData, nSize)); } #else - SAL_INFO("vcl.pdfwriter", " " << std::hex << nProperty); + SAL_INFO("vcl.pdfwriter", " " << nProperty); #endif } #endif @@ -6252,7 +6269,7 @@ bool PDFWriterImpl::finalizeSignature() CHECK_RETURN( (osl::File::E_None == m_aFile.setPos(osl_Pos_Absolut, 0)) ); HCRYPTPROV hCryptProvider; - if (!CryptAcquireContext(&hCryptProvider, NULL, MS_ENHANCED_PROV, PROV_RSA_FULL, CRYPT_VERIFYCONTEXT)) + if (!CryptAcquireContext(&hCryptProvider, NULL, MS_ENH_RSA_AES_PROV, PROV_RSA_AES, CRYPT_VERIFYCONTEXT)) { SAL_WARN("vcl.pdfwriter", "CryptAcquireContext failed: " << WindowsError(GetLastError())); CertFreeCertificateContext(pCertContext); @@ -6268,6 +6285,7 @@ bool PDFWriterImpl::finalizeSignature() return false; } +#if 0 DWORD nHashSize; DWORD nHashSizeLen(sizeof(DWORD)); if (!CryptGetHashParam(hHash, HP_HASHSIZE, reinterpret_cast<BYTE *>(&nHashSize), &nHashSizeLen, 0)) @@ -6281,6 +6299,7 @@ bool PDFWriterImpl::finalizeSignature() assert(nHashSizeLen == sizeof(DWORD)); assert(nHashSize == 20); +#endif boost::scoped_array<char> buffer(new char[m_nSignatureContentOffset + 1]); sal_uInt64 bytesRead; @@ -6337,8 +6356,26 @@ bool PDFWriterImpl::finalizeSignature() OString pass = OUStringToOString( m_aContext.SignPassword, RTL_TEXTENCODING_UTF8 ); + HCRYPTPROV_OR_NCRYPT_KEY_HANDLE hCryptProvOrNCryptKey; + DWORD nKeySpecType; + BOOL bMustFree; + if (!CryptAcquireCertificatePrivateKey(pCertContext, 0, NULL, &hCryptProvOrNCryptKey, &nKeySpecType, &bMustFree)) + { + SAL_WARN("vcl.pdfwriter", "CryptAcquireCertificatePrivateKey failed: " << WindowsError(GetLastError())); + CryptDestroyHash(hHash); + CryptReleaseContext(hCryptProvider, 0); + CertFreeCertificateContext(pCertContext); + return false; + } + + SAL_INFO("vcl.pdfwriter", "Certificate has private key that is " << + (nKeySpecType == AT_KEYEXCHANGE ? OUString("for key exchange") : + (nKeySpecType == AT_SIGNATURE ? OUString("for signatures") : + (nKeySpecType == CERT_NCRYPT_KEY_SPEC ? OUString("a CNG key, whatever that is") : + OUString("unknown type (") + OUString::number(nKeySpecType, 16) + ")")))); + DWORD nSigLen(0); - if (!CryptSignHash(hHash, AT_SIGNATURE, NULL, 0, NULL, &nSigLen)) + if (!CryptSignHash(hHash, nKeySpecType, NULL, CRYPT_NOHASHOID, NULL, &nSigLen)) { SAL_WARN("vcl.pdfwriter", "CryptSignHash failed: " << WindowsError(GetLastError())); CryptDestroyHash(hHash); @@ -6348,7 +6385,7 @@ bool PDFWriterImpl::finalizeSignature() } boost::scoped_array<BYTE> pSig(new BYTE[nSigLen]); - if (!CryptSignHash(hHash, AT_SIGNATURE, NULL, 0, pSig.get(), &nSigLen)) + if (!CryptSignHash(hHash, nKeySpecType, NULL, CRYPT_NOHASHOID, pSig.get(), &nSigLen)) { SAL_WARN("vcl.pdfwriter", "CryptSignHash failed: " << WindowsError(GetLastError())); CryptDestroyHash(hHash); -- You are receiving this mail because: You are the assignee for the bug.
_______________________________________________ Libreoffice-bugs mailing list [email protected] http://lists.freedesktop.org/mailman/listinfo/libreoffice-bugs
