ReactOS 0.4.17-dev-381-g2ec7c03
pfx.c
Go to the documentation of this file.
1/*
2 * Copyright 2019 Hans Leidekker for CodeWeavers
3 *
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2.1 of the License, or (at your option) any later version.
8 *
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
13 *
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
17 */
18
19#include <stdarg.h>
20
21#include "ntstatus.h"
22#define WIN32_NO_STATUS
23#include "windef.h"
24#include "winbase.h"
25#include "wincrypt.h"
26#ifdef __REACTOS__
27#include <winnls.h>
28#endif
29#include "snmp.h"
30#include "crypt32_private.h"
31
32#include "wine/debug.h"
33
35
37{
38 HCRYPTPROV prov = 0;
39 HCRYPTKEY cryptkey;
40 DWORD size, acquire_flags;
41 void *key;
43
45
46 acquire_flags = (flags & CRYPT_MACHINE_KEYSET) | CRYPT_NEWKEYSET;
47 if (!CryptAcquireContextW( &prov, NULL, MS_ENHANCED_PROV_W, PROV_RSA_FULL, acquire_flags ))
48 {
49 if (GetLastError() != NTE_EXISTS) return 0;
50
51 acquire_flags &= ~CRYPT_NEWKEYSET;
52 if (!CryptAcquireContextW( &prov, NULL, MS_ENHANCED_PROV_W, PROV_RSA_FULL, acquire_flags ))
53 {
54 WARN( "CryptAcquireContextW failed %08lx\n", GetLastError() );
55 return 0;
56 }
57 }
58
59 params.buf = key = CryptMemAlloc( size );
61 !CryptImportKey( prov, key, size, 0, flags & CRYPT_EXPORTABLE, &cryptkey ))
62 {
63 WARN( "CryptImportKey failed %08lx\n", GetLastError() );
64 CryptReleaseContext( prov, 0 );
66 return 0;
67 }
68 CryptDestroyKey( cryptkey );
70 return prov;
71}
72
73static BOOL set_key_context( const void *ctx, HCRYPTPROV prov )
74{
75 CERT_KEY_CONTEXT key_ctx;
76 key_ctx.cbSize = sizeof(key_ctx);
77 key_ctx.hCryptProv = prov;
78 key_ctx.dwKeySpec = AT_KEYEXCHANGE;
80}
81
83{
84 DWORD size = 0;
85 WCHAR *ret;
86 char *str;
87
88 CryptGetProvParam( prov, prop_id, NULL, &size, 0 );
89 if (!size) return NULL;
90 if (!(str = CryptMemAlloc( size ))) return NULL;
91 CryptGetProvParam( prov, prop_id, (BYTE *)str, &size, 0 );
92
93 *len = MultiByteToWideChar( CP_ACP, 0, str, -1, NULL, 0 );
94 if ((ret = CryptMemAlloc( *len * sizeof(WCHAR) ))) MultiByteToWideChar( CP_ACP, 0, str, -1, ret, *len );
96 return ret;
97}
98
99static BOOL set_key_prov_info( const void *ctx, HCRYPTPROV prov )
100{
101 CRYPT_KEY_PROV_INFO *prov_info;
102 DWORD size, len_container, len_name;
103 WCHAR *ptr, *container, *name;
104 BOOL ret;
105
106 if (!(container = get_provider_property( prov, PP_CONTAINER, &len_container ))) return FALSE;
107 if (!(name = get_provider_property( prov, PP_NAME, &len_name )))
108 {
110 return FALSE;
111 }
112 if (!(prov_info = CryptMemAlloc( sizeof(*prov_info) + (len_container + len_name) * sizeof(WCHAR) )))
113 {
116 return FALSE;
117 }
118
119 ptr = (WCHAR *)(prov_info + 1);
120 prov_info->pwszContainerName = ptr;
121 lstrcpyW( prov_info->pwszContainerName, container );
122
123 ptr += len_container;
124 prov_info->pwszProvName = ptr;
125 lstrcpyW( prov_info->pwszProvName, name );
126
127 size = sizeof(prov_info->dwProvType);
128 CryptGetProvParam( prov, PP_PROVTYPE, (BYTE *)&prov_info->dwProvType, &size, 0 );
129
130 prov_info->dwFlags = 0;
131 prov_info->cProvParam = 0;
132 prov_info->rgProvParam = NULL;
133 size = sizeof(prov_info->dwKeySpec);
134 CryptGetProvParam( prov, PP_KEYSPEC, (BYTE *)&prov_info->dwKeySpec, &size, 0 );
135
137
138 CryptMemFree( prov_info );
141 return ret;
142}
143
145{
146 DWORD i = 0, size;
147 HCERTSTORE store = NULL;
148 HCRYPTPROV prov = 0;
150 struct open_cert_store_params open_params = { pfx, password, &data };
151 struct close_cert_store_params close_params;
152
153 if (!pfx)
154 {
156 return NULL;
157 }
159 {
160 FIXME( "flags %08lx not supported\n", flags );
161 return NULL;
162 }
163 if (CRYPT32_CALL( open_cert_store, &open_params )) return NULL;
164
165 prov = import_key( data, flags );
166 if (!prov) goto error;
167
168 if (!(store = CertOpenStore( CERT_STORE_PROV_MEMORY, 0, 0, 0, NULL )))
169 {
170 WARN( "CertOpenStore failed %08lx\n", GetLastError() );
171 goto error;
172 }
173
174 for (;;)
175 {
176 const void *ctx = NULL;
177 void *cert;
178 struct import_store_cert_params import_params = { data, i, NULL, &size };
179
180 if (CRYPT32_CALL( import_store_cert, &import_params ) != STATUS_BUFFER_TOO_SMALL) break;
181 import_params.buf = cert = CryptMemAlloc( size );
182 if (!CRYPT32_CALL( import_store_cert, &import_params ))
185 if (!ctx)
186 {
187 WARN( "CertCreateContext failed %08lx\n", GetLastError() );
188 goto error;
189 }
191 {
192 if (!set_key_context( ctx, prov ))
193 {
194 WARN( "failed to set context property %08lx\n", GetLastError() );
196 goto error;
197 }
198 }
199 else if (!set_key_prov_info( ctx, prov ))
200 {
201 WARN( "failed to set provider info property %08lx\n", GetLastError() );
203 goto error;
204 }
206 {
207 WARN( "CertAddCertificateContextToStore failed %08lx\n", GetLastError() );
209 goto error;
210 }
212 i++;
213 }
214 close_params.data = data;
215 CRYPT32_CALL( close_cert_store, &close_params );
216 return store;
217
218error:
219 CryptReleaseContext( prov, 0 );
220 CertCloseStore( store, 0 );
221 close_params.data = data;
222 CRYPT32_CALL( close_cert_store, &close_params );
223 return NULL;
224}
225
227{
228 FIXME( "(%p, %p, %08lx): stub\n", pfx, password, flags );
229 return FALSE;
230}
231
233{
234 return PFXExportCertStoreEx( store, pfx, password, NULL, flags );
235}
236
238 DWORD flags )
239{
240 FIXME( "(%p, %p, %p, %p, %08lx): stub\n", store, pfx, password, reserved, flags );
241 return FALSE;
242}
#define WINE_DEFAULT_DEBUG_CHANNEL(t)
Definition: precomp.h:23
#define FIXME(fmt,...)
Definition: precomp.h:53
#define WARN(fmt,...)
Definition: precomp.h:61
UINT64 cert_store_data_t
#define CRYPT32_CALL(func, params)
#define NULL
Definition: types.h:112
#define FALSE
Definition: types.h:117
BOOL WINAPI CryptDestroyKey(HCRYPTKEY hKey)
Definition: crypt.c:911
BOOL WINAPI CryptReleaseContext(HCRYPTPROV hProv, DWORD dwFlags)
Definition: crypt.c:641
BOOL WINAPI CryptAcquireContextW(HCRYPTPROV *phProv, LPCWSTR pszContainer, LPCWSTR pszProvider, DWORD dwProvType, DWORD dwFlags)
Definition: crypt.c:362
BOOL WINAPI CryptGetProvParam(HCRYPTPROV hProv, DWORD dwParam, BYTE *pbData, DWORD *pdwDataLen, DWORD dwFlags)
Definition: crypt.c:1667
BOOL WINAPI CryptImportKey(HCRYPTPROV hProv, const BYTE *pbData, DWORD dwDataLen, HCRYPTKEY hPubKey, DWORD dwFlags, HCRYPTKEY *phKey)
Definition: crypt.c:1820
BOOL WINAPI CertAddCertificateContextToStore(HCERTSTORE hCertStore, PCCERT_CONTEXT pCertContext, DWORD dwAddDisposition, PCCERT_CONTEXT *ppStoreContext)
Definition: cert.c:284
BOOL WINAPI CertFreeCertificateContext(PCCERT_CONTEXT pCertContext)
Definition: cert.c:369
BOOL WINAPI CertSetCertificateContextProperty(PCCERT_CONTEXT pCertContext, DWORD dwPropId, DWORD dwFlags, const void *pvData)
Definition: cert.c:838
const void *WINAPI CertCreateContext(DWORD dwContextType, DWORD dwEncodingType, const BYTE *pbEncoded, DWORD cbEncoded, DWORD dwFlags, PCERT_CREATE_CONTEXT_PARA pCreatePara)
Definition: cert.c:3876
LPVOID WINAPI CryptMemAlloc(ULONG cbSize)
Definition: main.c:136
VOID WINAPI CryptMemFree(LPVOID pv)
Definition: main.c:146
HCERTSTORE WINAPI CertOpenStore(LPCSTR lpszStoreProvider, DWORD dwMsgAndCertEncodingType, HCRYPTPROV_LEGACY hCryptProv, DWORD dwFlags, const void *pvPara)
Definition: store.c:809
BOOL WINAPI CertCloseStore(HCERTSTORE hCertStore, DWORD dwFlags)
Definition: store.c:1121
#define ERROR_INVALID_PARAMETER
Definition: compat.h:101
#define CP_ACP
Definition: compat.h:109
#define SetLastError(x)
Definition: compat.h:752
#define lstrcpyW
Definition: compat.h:749
#define MultiByteToWideChar
Definition: compat.h:110
return ret
Definition: mutex.c:146
r reserved
Definition: btrfs.c:3006
unsigned int BOOL
Definition: ntddk_ex.h:94
unsigned long DWORD
Definition: ntddk_ex.h:95
GLint GLenum GLsizei GLsizei GLsizei GLint GLsizei const GLvoid * data
Definition: gl.h:1950
GLsizeiptr size
Definition: glext.h:5919
GLenum const GLfloat * params
Definition: glext.h:5645
GLbitfield flags
Definition: glext.h:7161
GLenum GLsizei len
Definition: glext.h:6722
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
#define error(str)
Definition: mkdosfs.c:1605
static PVOID ptr
Definition: dispmode.c:27
static BYTE cert[]
Definition: msg.c:1374
static WCHAR password[]
Definition: url.c:33
short WCHAR
Definition: pedump.c:58
static BOOL set_key_context(const void *ctx, HCRYPTPROV prov)
Definition: pfx.c:73
BOOL WINAPI PFXVerifyPassword(CRYPT_DATA_BLOB *pfx, const WCHAR *password, DWORD flags)
Definition: pfx.c:226
BOOL WINAPI PFXExportCertStoreEx(HCERTSTORE store, CRYPT_DATA_BLOB *pfx, const WCHAR *password, void *reserved, DWORD flags)
Definition: pfx.c:237
BOOL WINAPI PFXExportCertStore(HCERTSTORE store, CRYPT_DATA_BLOB *pfx, const WCHAR *password, DWORD flags)
Definition: pfx.c:232
HCERTSTORE WINAPI PFXImportCertStore(CRYPT_DATA_BLOB *pfx, const WCHAR *password, DWORD flags)
Definition: pfx.c:144
static HCRYPTPROV import_key(cert_store_data_t data, DWORD flags)
Definition: pfx.c:36
static BOOL set_key_prov_info(const void *ctx, HCRYPTPROV prov)
Definition: pfx.c:99
static WCHAR * get_provider_property(HCRYPTPROV prov, DWORD prop_id, DWORD *len)
Definition: pfx.c:82
const WCHAR * str
#define STATUS_BUFFER_TOO_SMALL
Definition: shellext.h:69
HCRYPTPROV hCryptProv
Definition: wincrypt.h:229
LPWSTR pwszContainerName
Definition: wincrypt.h:218
PCRYPT_KEY_PROV_PARAM rgProvParam
Definition: wincrypt.h:223
cert_store_data_t data
Definition: copy.c:22
Definition: name.c:39
CRYPT_DATA_BLOB * pfx
static NTSTATUS import_store_key(void *args)
Definition: unixlib.c:364
static NTSTATUS close_cert_store(void *args)
Definition: unixlib.c:366
static NTSTATUS import_store_cert(void *args)
Definition: unixlib.c:365
static NTSTATUS open_cert_store(void *args)
Definition: unixlib.c:363
DWORD WINAPI GetLastError(void)
Definition: except.c:1042
#define CRYPT_NEWKEYSET
Definition: wincrypt.h:2274
#define PROV_RSA_FULL
Definition: wincrypt.h:2243
#define CERT_KEY_CONTEXT_PROP_ID
Definition: wincrypt.h:2837
ULONG_PTR HCRYPTPROV
Definition: wincrypt.h:55
#define CRYPT_USER_KEYSET
Definition: wincrypt.h:4320
#define CERT_KEY_PROV_INFO_PROP_ID
Definition: wincrypt.h:2833
#define PP_KEYSPEC
Definition: wincrypt.h:2318
#define AT_KEYEXCHANGE
Definition: wincrypt.h:2239
#define X509_ASN_ENCODING
Definition: wincrypt.h:2501
#define CERT_STORE_PROV_MEMORY
Definition: wincrypt.h:2455
#define PKCS12_NO_PERSIST_KEY
Definition: wincrypt.h:4327
#define CERT_STORE_CERTIFICATE_CONTEXT
Definition: wincrypt.h:3121
#define PP_NAME
Definition: wincrypt.h:2289
ULONG_PTR HCRYPTKEY
Definition: wincrypt.h:58
#define CERT_STORE_ADD_ALWAYS
Definition: wincrypt.h:2654
#define PP_CONTAINER
Definition: wincrypt.h:2291
#define PP_PROVTYPE
Definition: wincrypt.h:2300
static const WCHAR MS_ENHANCED_PROV_W[]
Definition: wincrypt.h:2129
#define CRYPT_EXPORTABLE
Definition: wincrypt.h:2410
#define CRYPT_MACHINE_KEYSET
Definition: wincrypt.h:2276
#define WINAPI
Definition: msvc.h:6
#define NTE_EXISTS
Definition: winerror.h:4262
unsigned char BYTE
Definition: xxhash.c:193