in c/src/ssl/schannel.cpp [1885:1975]
static HCERTSTORE open_cert_db(const char *store_name, const char *passwd, int *error) {
*error = 0;
DWORD sys_store_type = 0;
HCERTSTORE cert_store = 0;
if (store_name) {
if (strncmp(store_name, "ss:", 3) == 0) {
store_name += 3;
sys_store_type = CERT_SYSTEM_STORE_CURRENT_USER;
}
else if (strncmp(store_name, "lmss:", 5) == 0) {
store_name += 5;
sys_store_type = CERT_SYSTEM_STORE_LOCAL_MACHINE;
}
}
if (sys_store_type) {
// Opening a system store, names are not case sensitive.
// Map confusing GUI name to actual registry store name.
if (!pn_strcasecmp(store_name, "personal")) store_name= "my";
cert_store = CertOpenStore(CERT_STORE_PROV_SYSTEM_A, 0, NULL,
CERT_STORE_OPEN_EXISTING_FLAG | CERT_STORE_READONLY_FLAG |
sys_store_type, store_name);
if (!cert_store) {
ssl_log_error_status(GetLastError(), "Failed to open system certificate store %s", store_name);
*error = -3;
return NULL;
}
} else {
// PKCS#12 file
HANDLE cert_file = CreateFile(store_name, GENERIC_READ, 0, NULL, OPEN_EXISTING,
FILE_ATTRIBUTE_NORMAL, NULL);
if (INVALID_HANDLE_VALUE == cert_file) {
HRESULT status = GetLastError();
ssl_log_error_status(status, "Failed to open the file holding the private key: %s", store_name);
*error = -4;
return NULL;
}
DWORD nread = 0L;
const DWORD file_size = GetFileSize(cert_file, NULL);
char *buf = NULL;
if (INVALID_FILE_SIZE != file_size)
buf = (char *) malloc(file_size);
if (!buf || !ReadFile(cert_file, buf, file_size, &nread, NULL)
|| file_size != nread) {
HRESULT status = GetLastError();
CloseHandle(cert_file);
free(buf);
ssl_log_error_status(status, "Reading the private key from file failed %s", store_name);
*error = -5;
return NULL;
}
CloseHandle(cert_file);
CRYPT_DATA_BLOB blob;
blob.cbData = nread;
blob.pbData = (BYTE *) buf;
wchar_t *pwUCS2 = NULL;
int pwlen = 0;
if (passwd) {
// convert passwd to null terminated wchar_t (Windows UCS2)
pwlen = strlen(passwd);
pwUCS2 = (wchar_t *) calloc(pwlen + 1, sizeof(wchar_t));
int nwc = MultiByteToWideChar(CP_UTF8, MB_ERR_INVALID_CHARS, passwd, pwlen, &pwUCS2[0], pwlen);
if (!nwc) {
ssl_log_error_status(GetLastError(), "Error converting password from UTF8");
free(buf);
free(pwUCS2);
*error = -6;
return NULL;
}
}
cert_store = PFXImportCertStore(&blob, pwUCS2, 0);
if (pwUCS2) {
SecureZeroMemory(pwUCS2, pwlen * sizeof(wchar_t));
free(pwUCS2);
}
if (cert_store == NULL) {
ssl_log_error_status(GetLastError(), "Failed to import the file based certificate store");
free(buf);
*error = -7;
return NULL;
}
free(buf);
}
return cert_store;
}