23template<
class _Traits,
class _Ax>
24static DWORD CertGetNameStringA(_In_ PCCERT_CONTEXT pCertContext, _In_ DWORD dwType, _In_ DWORD dwFlags, _In_opt_
void *pvTypePara, _Out_ std::basic_string<char, _Traits, _Ax> &sNameString)
27 DWORD dwSize = ::CertGetNameStringA(pCertContext, dwType, dwFlags, pvTypePara, NULL, 0);
30 std::unique_ptr<char[]> szBuffer(
new char[dwSize]);
31 dwSize = ::CertGetNameStringA(pCertContext, dwType, dwFlags, pvTypePara, szBuffer.get(), dwSize);
32 sNameString.assign(szBuffer.get(), dwSize - 1);
41template<
class _Traits,
class _Ax>
42static DWORD CertGetNameStringW(_In_ PCCERT_CONTEXT pCertContext, _In_ DWORD dwType, _In_ DWORD dwFlags, _In_opt_
void *pvTypePara, _Out_ std::basic_string<wchar_t, _Traits, _Ax> &sNameString)
45 DWORD dwSize = ::CertGetNameStringW(pCertContext, dwType, dwFlags, pvTypePara, NULL, 0);
48 std::unique_ptr<wchar_t[]> szBuffer(
new wchar_t[dwSize]);
49 dwSize = ::CertGetNameStringW(pCertContext, dwType, dwFlags, pvTypePara, szBuffer.get(), dwSize);
50 sNameString.assign(szBuffer.get(), dwSize - 1);
59template<
class _Ty,
class _Ax>
60static _Success_(
return != 0) BOOL WINAPI CertGetCertificateContextProperty(_In_ PCCERT_CONTEXT pCertContext, _In_ DWORD dwPropId, _Out_ std::vector<_Ty, _Ax> &aData)
66 if (CertGetCertificateContextProperty(pCertContext, dwPropId, buf, &dwSize)) {
68 aData.assign((
const _Ty*)buf, (
const _Ty*)buf + (dwSize +
sizeof(_Ty) - 1) /
sizeof(_Ty));
70 }
else if (GetLastError() == ERROR_MORE_DATA) {
71 aData.resize((dwSize +
sizeof(_Ty) - 1) /
sizeof(_Ty));
72 if (CertGetCertificateContextProperty(pCertContext, dwPropId, (BYTE*)aData.data(), &dwSize))
84template<
class _Ty,
class _Ax>
85static _Success_(
return != 0) BOOL CryptGetHashParam(_In_ HCRYPTHASH hHash, _In_ DWORD dwParam, _Out_ std::vector<_Ty, _Ax> &aData, _In_ DWORD dwFlags)
91 if (CryptGetHashParam(hHash, dwParam, buf, &dwSize, dwFlags)) {
93 aData.assign((
const _Ty*)buf, (
const _Ty*)buf + (dwSize +
sizeof(_Ty) - 1) /
sizeof(_Ty));
95 }
else if (GetLastError() == ERROR_MORE_DATA) {
96 aData.resize((dwSize +
sizeof(_Ty) - 1) /
sizeof(_Ty));
97 if (CryptGetHashParam(hHash, dwParam, (BYTE*)aData.data(), &dwSize, dwFlags))
110static _Success_(
return != 0) BOOL CryptGetHashParam(_In_ HCRYPTHASH hHash, _In_ DWORD dwParam, _Out_ T &data, _In_ DWORD dwFlags)
112 DWORD dwSize =
sizeof(T);
113 return CryptGetHashParam(hHash, dwParam, (BYTE*)&data, &dwSize, dwFlags);
121template<
class _Ty,
class _Ax>
122static _Success_(
return != 0) BOOL CryptGetKeyParam(_In_ HCRYPTKEY hKey, _In_ DWORD dwParam, _Out_ std::vector<_Ty, _Ax> &aData, _In_ DWORD dwFlags)
128 if (CryptGetKeyParam(hKey, dwParam, buf, &dwSize, dwFlags)) {
130 aData.assign((
const _Ty*)buf, (
const _Ty*)buf + (dwSize +
sizeof(_Ty) - 1) /
sizeof(_Ty));
132 }
else if (GetLastError() == ERROR_MORE_DATA) {
133 aData.resize((dwSize +
sizeof(_Ty) - 1) /
sizeof(_Ty));
134 if (CryptGetKeyParam(hKey, dwParam, (BYTE*)aData.data(), &dwSize, dwFlags))
147static BOOL CryptGetKeyParam(_In_ HCRYPTKEY hKey, _In_ DWORD dwParam, _Out_ T &data, _In_ DWORD dwFlags)
149 DWORD dwSize =
sizeof(T);
150 return CryptGetKeyParam(hKey, dwParam, (BYTE*)&data, &dwSize, dwFlags);
158template<
class _Ty,
class _Ax>
159static _Success_(
return != 0) BOOL CryptExportKey(_In_ HCRYPTKEY hKey, _In_ HCRYPTKEY hExpKey, _In_ DWORD dwBlobType, _In_ DWORD dwFlags, _Out_ std::vector<_Ty, _Ax> &aData)
161 DWORD dwKeyBLOBSize = 0;
163 if (CryptExportKey(hKey, hExpKey, dwBlobType, dwFlags, NULL, &dwKeyBLOBSize)) {
164 aData.resize((dwKeyBLOBSize +
sizeof(_Ty) - 1) /
sizeof(_Ty));
165 if (CryptExportKey(hKey, hExpKey, dwBlobType, dwFlags, aData.data(), &dwKeyBLOBSize))
177template<
class _Ty,
class _Ax>
178static _Success_(
return != 0) BOOL CryptEncrypt(_In_ HCRYPTKEY hKey, _In_opt_ HCRYPTHASH hHash, _In_ BOOL Final, _In_ DWORD dwFlags, _Inout_ std::vector<_Ty, _Ax> &aData)
181 dwDataLen = (DWORD)(aData.size() *
sizeof(_Ty)),
182 dwBufLen = (DWORD)(aData.capacity() *
sizeof(_Ty)),
183 dwEncLen = dwDataLen,
187 aData.resize(dwBufLen);
188 if (CryptEncrypt(hKey, hHash, Final, dwFlags, (BYTE*)aData.data(), &dwEncLen, dwBufLen)) {
190 assert(dwEncLen <= dwBufLen);
191 if (dwEncLen < dwBufLen)
192 aData.resize((dwEncLen +
sizeof(_Ty) - 1) /
sizeof(_Ty));
195 dwResult = GetLastError();
196 }
else if (CryptEncrypt(hKey, NULL, Final, dwFlags, NULL, &dwEncLen, 0)) {
199 dwResult = ERROR_MORE_DATA;
201 dwResult = GetLastError();
203 if (dwResult == ERROR_MORE_DATA) {
205 aData.resize(((dwBufLen = dwEncLen) +
sizeof(_Ty) - 1) /
sizeof(_Ty));
206 dwEncLen = dwDataLen;
207 if (CryptEncrypt(hKey, hHash, Final, dwFlags, (BYTE*)aData.data(), &dwEncLen, dwBufLen)) {
209 assert(dwEncLen <= dwBufLen);
210 if (dwEncLen < dwBufLen)
211 aData.resize((dwEncLen +
sizeof(_Ty) - 1) /
sizeof(_Ty));
216 aData.resize((dwDataLen +
sizeof(_Ty) - 1) /
sizeof(_Ty));
227template<
class _Ty,
class _Ax>
228static _Success_(
return != 0) BOOL CryptDecrypt(_In_ HCRYPTKEY hKey, _In_opt_ HCRYPTHASH hHash, _In_ BOOL Final, _In_ DWORD dwFlags, _Inout_ std::vector<_Ty, _Ax> &aData)
230 DWORD dwDataLen = (DWORD)(aData.size() *
sizeof(_Ty));
232 if (CryptDecrypt(hKey, hHash, Final, dwFlags, (BYTE*)aData.data(), &dwDataLen)) {
234 aData.resize((dwDataLen +
sizeof(_Ty) - 1) /
sizeof(_Ty));
277 bool create(_In_ DWORD dwCertEncodingType, _In_ LPCBYTE pbCertEncoded, _In_ DWORD cbCertEncoded) noexcept
279 handle_type h = CertCreateCertificateContext(dwCertEncodingType, pbCertEncoded, cbCertEncoded);
300 m_h->cbCertEncoded == other->cbCertEncoded && memcmp(
m_h->pbCertEncoded, other->pbCertEncoded,
m_h->cbCertEncoded) == 0;
327 const int r = memcmp(
m_h->pbCertEncoded, other->pbCertEncoded, std::min<DWORD>(
m_h->cbCertEncoded, other->cbCertEncoded));
328 return r < 0 || r == 0 &&
m_h->cbCertEncoded < other->cbCertEncoded;
342 const int r = memcmp(
m_h->pbCertEncoded, other->pbCertEncoded, std::min<DWORD>(
m_h->cbCertEncoded, other->cbCertEncoded));
343 return r > 0 || r == 0 &&
m_h->cbCertEncoded > other->cbCertEncoded;
380 CertFreeCertificateContext(
m_h);
394 return CertDuplicateCertificateContext(h);
427 bool create(_In_opt_ HCERTCHAINENGINE hChainEngine, _In_ PCCERT_CONTEXT pCertContext, _In_opt_ LPFILETIME pTime, _In_opt_ HCERTSTORE hAdditionalStore, _In_ PCERT_CHAIN_PARA pChainPara, _In_ DWORD dwFlags, __reserved LPVOID pvReserved = NULL) noexcept
430 if (CertGetCertificateChain(hChainEngine, pCertContext, pTime, hAdditionalStore, pChainPara, dwFlags, pvReserved, &h)) {
445 CertFreeCertificateChain(
m_h);
459 return CertDuplicateCertificateChain(h);
492 bool create(_In_ LPCSTR lpszStoreProvider, _In_ DWORD dwEncodingType, _In_opt_ HCRYPTPROV_LEGACY hCryptProv, _In_ DWORD dwFlags, _In_opt_ const
void *pvPara) noexcept
494 handle_type h = CertOpenStore(lpszStoreProvider, dwEncodingType, hCryptProv, dwFlags, pvPara);
512 bool create(_In_opt_ HCRYPTPROV_LEGACY hCryptProv, _In_z_ LPCTSTR szSubsystemProtocol) noexcept
514 handle_type h = CertOpenSystemStore(hCryptProv, szSubsystemProtocol);
530 CertCloseStore(
m_h, 0);
563 bool create(_In_opt_z_ LPCTSTR szContainer, _In_opt_z_ LPCTSTR szProvider, _In_ DWORD dwProvType, _In_ DWORD dwFlags = 0) noexcept
566 if (CryptAcquireContext(&h, szContainer, szProvider, dwProvType, dwFlags)) {
581 CryptReleaseContext(
m_h, 0);
614 bool create(_In_ HCRYPTPROV hProv, _In_ ALG_ID Algid, _In_opt_ HCRYPTKEY hKey = NULL, _In_opt_ DWORD dwFlags = 0) noexcept
617 if (CryptCreateHash(hProv, Algid, hKey, dwFlags, &h)) {
632 CryptDestroyHash(
m_h);
647 return CryptDuplicateHash(h, NULL, 0, &hNew) ? hNew :
invalid;
676 bool generate(_In_ HCRYPTPROV hProv, _In_ ALG_ID Algid, _In_ DWORD dwFlags) noexcept
679 if (CryptGenKey(hProv, Algid, dwFlags, &h)) {
692 bool import(_In_ HCRYPTPROV hProv, __in_bcount(dwDataLen) LPCBYTE pbData, _In_ DWORD dwDataLen, _In_ HCRYPTKEY hPubKey, _In_ DWORD dwFlags) noexcept
695 if (CryptImportKey(hProv, pbData, dwDataLen, hPubKey, dwFlags, &h)) {
708 bool import_public(_In_ HCRYPTPROV hCryptProv, _In_ DWORD dwCertEncodingType, _In_ PCERT_PUBLIC_KEY_INFO pInfo) noexcept
711 if (CryptImportPublicKeyInfo(hCryptProv, dwCertEncodingType, pInfo, &h)) {
724 bool derive(_In_ HCRYPTPROV hProv, _In_ ALG_ID Algid, _In_ HCRYPTHASH hBaseData, _In_ DWORD dwFlags) noexcept
727 if (CryptDeriveKey(hProv, Algid, hBaseData, dwFlags, &h)) {
744 if (dwKeySpec != AT_KEYEXCHANGE && dwKeySpec != AT_SIGNATURE) {
745 SetLastError(ERROR_INVALID_PARAMETER);
751 if (CryptGenKey(hProv, dwKeySpec, CRYPT_EXPORTABLE, &h)) {
753 std::vector<BYTE, sanitizing_allocator<BYTE>> key_blob;
754 if (CryptExportKey(h, 0, PRIVATEKEYBLOB, 0, key_blob)) {
759 size_key = *
reinterpret_cast<DWORD*
>(&key_blob[12])/8,
760 size_prime = size_key/2;
766 LPBYTE ptr = &key_blob[16];
767 *
reinterpret_cast<DWORD*
>(ptr) = 1;
768 ptr +=
sizeof(DWORD);
777 memset(ptr + 1, 0, size_prime - 1);
782 memset(ptr + 1, 0, size_prime - 1);
790 memset(ptr + 1, 0, size_key - 1);
793 if (CryptImportKey(hProv, key_blob.data(),
static_cast<DWORD
>(key_blob.size()), 0, 0, &h)) {
812 CryptDestroyKey(
m_h);
827 return CryptDuplicateKey(h, NULL, 0, &hNew) ? hNew :
invalid;
834 #pragma warning(push)
835 #pragma warning(disable: 26432)
862 cbData = other.cbData;
864 pbData =
static_cast<BYTE*
>(LocalAlloc(LMEM_FIXED, other.cbData));
866 memcpy(pbData, other.pbData, other.cbData);
876 cbData = other.cbData;
877 pbData = other.pbData;
896 if (
this != &other) {
897 cbData = other.cbData;
901 pbData =
static_cast<BYTE*
>(LocalAlloc(LMEM_FIXED, other.cbData));
903 memcpy(pbData, other.pbData, other.cbData);
916 if (
this != &other) {
917 cbData = other.cbData;
920 pbData = other.pbData;
939 const BYTE*
data() const noexcept
961#pragma warning(disable: 4505)
968static BOOL CertGetCertificateChain(_In_opt_ HCERTCHAINENGINE hChainEngine, _In_ PCCERT_CONTEXT pCertContext, _In_opt_ LPFILETIME pTime, _In_opt_ HCERTSTORE hAdditionalStore, _In_ PCERT_CHAIN_PARA pChainPara, _In_ DWORD dwFlags, _Reserved_ LPVOID pvReserved, _Inout_
winstd::cert_chain_context &ctx)
970 PCCERT_CHAIN_CONTEXT pChainContext;
971 BOOL bResult = CertGetCertificateChain(hChainEngine, pCertContext, pTime, hAdditionalStore, pChainPara, dwFlags, pvReserved, &pChainContext);
973 ctx.attach(pChainContext);
978static BOOL CryptAcquireContextA(_Inout_
winstd::crypt_prov &prov, _In_opt_ LPCSTR szContainer, _In_opt_ LPCSTR szProvider, _In_ DWORD dwProvType, _In_ DWORD dwFlags)
981 BOOL bResult = CryptAcquireContextA(&h, szContainer, szProvider, dwProvType, dwFlags);
992static BOOL CryptAcquireContextW(_Inout_
winstd::crypt_prov &prov, _In_opt_ LPCWSTR szContainer, _In_opt_ LPCWSTR szProvider, _In_ DWORD dwProvType, _In_ DWORD dwFlags)
995 BOOL bResult = CryptAcquireContextW(&h, szContainer, szProvider, dwProvType, dwFlags);
1006static BOOL CryptCreateHash(_In_ HCRYPTPROV hProv, _In_ ALG_ID Algid, _In_ HCRYPTKEY hKey, _In_ DWORD dwFlags, _Inout_
winstd::crypt_hash &hash)
1009 BOOL bResult = CryptCreateHash(hProv, Algid, hKey, dwFlags, &h);
1020static BOOL CryptGenKey(_In_ HCRYPTPROV hProv, _In_ ALG_ID Algid, _In_ DWORD dwFlags, _Inout_
winstd::crypt_key &key)
1023 BOOL bResult = CryptGenKey(hProv, Algid, dwFlags, &h);
1034static bool CryptImportKey(_In_ HCRYPTPROV hProv, __in_bcount(dwDataLen) LPCBYTE pbData, _In_ DWORD dwDataLen, _In_ HCRYPTKEY hPubKey, _In_ DWORD dwFlags, _Inout_
winstd::crypt_key &key)
1037 BOOL bResult = CryptImportKey(hProv, pbData, dwDataLen, hPubKey, dwFlags, &h);
1048static bool CryptImportPublicKeyInfo(_In_ HCRYPTPROV hCryptProv, _In_ DWORD dwCertEncodingType, _In_ PCERT_PUBLIC_KEY_INFO pInfo, _Inout_
winstd::crypt_key &key)
1051 BOOL bResult = CryptImportPublicKeyInfo(hCryptProv, dwCertEncodingType, pInfo, &h);
1062static bool CryptDeriveKey(_In_ HCRYPTPROV hProv, _In_ ALG_ID Algid, _In_ HCRYPTHASH hBaseData, _In_ DWORD dwFlags, _Inout_
winstd::crypt_key &key)
1065 BOOL bResult = CryptDeriveKey(hProv, Algid, hBaseData, dwFlags, &h);
PCCERT_CHAIN_CONTEXT wrapper class.
Definition: Crypt.h:402
virtual ~cert_chain_context()
Destroys the certificate chain context.
Definition: Crypt.h:411
__declspec(deprecated("Use CertGetCertificateChain")) bool create(HCERTCHAINENGINE hChainEngine
Creates the certificate chain context.
PCCERT_CONTEXT wrapper class.
Definition: Crypt.h:252
bool operator<=(const handle_type &other) const noexcept
Is certificate less than or equal?
Definition: Crypt.h:354
void free_internal() noexcept override
Destroys the certificate context.
Definition: Crypt.h:378
bool operator==(const handle_type &other) const noexcept
Is certificate equal to?
Definition: Crypt.h:295
handle_type duplicate_internal(handle_type h) const noexcept override
Duplicates the certificate context.
Definition: Crypt.h:392
bool operator>=(const handle_type &other) const noexcept
Is certificate greater than or equal?
Definition: Crypt.h:367
bool operator>(const handle_type &other) const noexcept
Is certificate greater than?
Definition: Crypt.h:339
bool operator<(const handle_type &other) const noexcept
Is certificate less than?
Definition: Crypt.h:324
__declspec(deprecated("Use CertCreateCertificateContext")) bool create(DWORD dwCertEncodingType
Creates the certificate context.
bool operator!=(const handle_type &other) const noexcept
Is certificate not equal to?
Definition: Crypt.h:311
virtual ~cert_context()
Destroys the certificate context.
Definition: Crypt.h:261
HCERTSTORE wrapper class.
Definition: Crypt.h:467
__declspec(deprecated("Use CertOpenStore")) bool create(LPCSTR lpszStoreProvider
Opens the certificate store.
virtual ~cert_store()
Closes the certificate store.
Definition: Crypt.h:476
__declspec(deprecated("Use CertOpenSystemStore")) bool create(HCRYPTPROV_LEGACY hCryptProv
Opens the most common system certificate store. To open certificate stores with more complex requirem...
void free_internal() noexcept override
Closes the certificate store.
Definition: Crypt.h:528
HCRYPTHASH wrapper class.
Definition: Crypt.h:589
__declspec(deprecated("Use CryptCreateHash")) bool create(HCRYPTPROV hProv
Creates the hash context.
virtual ~crypt_hash()
Destroys the hash context.
Definition: Crypt.h:598
HCRYPTKEY wrapper class.
Definition: Crypt.h:655
virtual ~crypt_key()
Destroys the key.
Definition: Crypt.h:664
__declspec(deprecated("Use CryptGenKey")) bool generate(HCRYPTPROV hProv
Generates the key.
bool create_exp1(HCRYPTPROV hProv, DWORD dwKeySpec)
Creates Exponent-of-one key.
Definition: Crypt.h:742
handle_type duplicate_internal(handle_type h) const noexcept override
Duplicates the key.
Definition: Crypt.h:824
void free_internal() noexcept override
Destroys the key.
Definition: Crypt.h:810
__declspec(deprecated("Use CryptImportPublicKeyInfo")) bool import_public(HCRYPTPROV hCryptProv
Imports the public key.
__declspec(deprecated("Use CryptImportKey")) bool import(HCRYPTPROV hProv
Imports the key.
__declspec(deprecated("Use CryptDeriveKey")) bool derive(HCRYPTPROV hProv
Generates cryptographic session keys derived from a base data value.
HCRYPTPROV wrapper class.
Definition: Crypt.h:538
__declspec(deprecated("Use CryptAcquireContext")) bool create(LPCTSTR szContainer
Acquires the cryptographic context.
virtual ~crypt_prov()
Releases the cryptographic context.
Definition: Crypt.h:547
DATA_BLOB wrapper class.
Definition: Crypt.h:837
data_blob(const DATA_BLOB &other)
Duplicate an existing BLOB.
Definition: Crypt.h:860
virtual ~data_blob()
Destroys the BLOB.
Definition: Crypt.h:885
BYTE * data() noexcept
Get BLOB buffer.
Definition: Crypt.h:947
const BYTE * data() const noexcept
Get BLOB buffer.
Definition: Crypt.h:939
data_blob() noexcept
Initializes an empty BLOB.
Definition: Crypt.h:842
data_blob(data_blob &&other) noexcept
Move an existing BLOB.
Definition: Crypt.h:874
data_blob & operator=(data_blob &&other) noexcept
Move an existing BLOB.
Definition: Crypt.h:914
data_blob(BYTE *data, DWORD size) noexcept
Initializes a BLOB from existing data.
Definition: Crypt.h:851
DWORD size() const noexcept
Get BLOB size.
Definition: Crypt.h:931
data_blob & operator=(const DATA_BLOB &other)
Copy an existing BLOB.
Definition: Crypt.h:894
Base abstract template class to support object handle keeping for objects that support trivial handle...
Definition: Common.h:865
virtual handle_type duplicate_internal(handle_type h) const noexcept=0
Abstract member function that must be implemented by child classes to do the actual object handle dup...
Base abstract template class to support generic object handle keeping.
Definition: Common.h:603
virtual void free_internal() noexcept=0
Abstract member function that must be implemented by child classes to do the actual object destructio...
PCCERT_CONTEXT handle_type
Datatype of the object handle this template class handles.
Definition: Common.h:608
handle_type m_h
Object handle.
Definition: Common.h:854
void attach(handle_type h) noexcept
Sets a new object handle for the class.
Definition: Common.h:817
Windows runtime error.
Definition: Common.h:1047
#define WINSTD_STACK_BUFFER_BYTES
Size of the stack buffer in bytes used for initial system function call.
Definition: Common.h:79
#define WINSTD_DPLHANDLE_IMPL(C, INVAL)
Implements default constructors and operators to prevent their auto-generation by compiler.
Definition: Common.h:173
#define WINSTD_HANDLE_IMPL(C, INVAL)
Implements default constructors and operators to prevent their auto-generation by compiler.
Definition: Common.h:161
static const PCCERT_CONTEXT invalid
Invalid handle value.
Definition: Common.h:613