X Tutup
Skip to content

Commit 384c678

Browse files
authored
[eval] Fix ssl cert verification failures on clean windows environments (#11838)
* Use windows api to verify ssl certs Taken from: Apprentice-Alchemist/hashlink@4d59012 * Handle error if cert store fails to open * Fix mscv warnings about invalid arguments Warning C6387 'parameters' could be '0': this does not adhere to the specification for the function 'CertGetCertificateChain'. Warning C6387 'policy_parameters' could be '0': this does not adhere to the specification for the function 'CertVerifyCertificateChainPolicy'. This also fixes an "incorrect parameter" runtime error. * Clear errors if certificate loading succeeded * Perform checks for all calls of verify_callback We need to do this every time, because if any callback call returns a non zero flags then the entire verification fails, see: https://github.com/Mbed-TLS/mbedtls/blob/3aefa5b705846c5d4466ae8747160ae9e5054ea8/library/x509_crt.c#L3031 We don't need to loop through the chain, since mbedtls already loops through and calls the callback on every certificate in the chain. * Free handles on certificate verification errors * Replace existing certificates if they exist This avoids duplicate certificates in the store * Propagate CN_MISMATCH ssl cert error The windows api functions won't check this automatically for us without further modifications, so it's easiest to just respect mbedtls' judgement and propagate this error. * Clarify comment regarding error mapping * Skip verification callback if no errors were found
1 parent 13ebeff commit 384c678

File tree

1 file changed

+47
-0
lines changed

1 file changed

+47
-0
lines changed

libs/mbedtls/mbedtls_stubs.c

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -302,12 +302,59 @@ static struct custom_operations ssl_config_ops = {
302302
.deserialize = custom_deserialize_default,
303303
};
304304

305+
#ifdef _WIN32
306+
static int verify_callback(void* param, mbedtls_x509_crt *crt, int depth, uint32_t *flags) {
307+
if (*flags == 0 || *flags & MBEDTLS_X509_BADCERT_CN_MISMATCH) {
308+
return 0;
309+
}
310+
311+
HCERTSTORE store = CertOpenStore(CERT_STORE_PROV_MEMORY, 0, 0, CERT_STORE_DEFER_CLOSE_UNTIL_LAST_FREE_FLAG, NULL);
312+
if(store == NULL) {
313+
return MBEDTLS_ERR_X509_FATAL_ERROR;
314+
}
315+
PCCERT_CONTEXT primary_context = {0};
316+
if(!CertAddEncodedCertificateToStore(store, X509_ASN_ENCODING, crt->raw.p, crt->raw.len, CERT_STORE_ADD_REPLACE_EXISTING, &primary_context)) {
317+
CertCloseStore(store, 0);
318+
return MBEDTLS_ERR_X509_FATAL_ERROR;
319+
}
320+
PCCERT_CHAIN_CONTEXT chain_context = {0};
321+
CERT_CHAIN_PARA parameters = {0};
322+
if(!CertGetCertificateChain(NULL, primary_context, NULL, store, &parameters, 0, NULL, &chain_context)) {
323+
CertFreeCertificateContext(primary_context);
324+
CertCloseStore(store, 0);
325+
return MBEDTLS_ERR_X509_FATAL_ERROR;
326+
}
327+
CERT_CHAIN_POLICY_PARA policy_parameters = {0};
328+
CERT_CHAIN_POLICY_STATUS policy_status = {0};
329+
if(!CertVerifyCertificateChainPolicy(CERT_CHAIN_POLICY_SSL, chain_context, &policy_parameters, &policy_status)) {
330+
CertFreeCertificateChain(chain_context);
331+
CertFreeCertificateContext(primary_context);
332+
CertCloseStore(store, 0);
333+
return MBEDTLS_ERR_X509_FATAL_ERROR;
334+
}
335+
if(policy_status.dwError == 0) {
336+
*flags = 0;
337+
} else {
338+
// if we ever want to read the verification result,
339+
// we need to properly map dwError to flags
340+
*flags |= MBEDTLS_X509_BADCERT_OTHER;
341+
}
342+
CertFreeCertificateChain(chain_context);
343+
CertFreeCertificateContext(primary_context);
344+
CertCloseStore(store, 0);
345+
return 0;
346+
}
347+
#endif
348+
305349
CAMLprim value ml_mbedtls_ssl_config_init(void) {
306350
CAMLparam0();
307351
CAMLlocal1(obj);
308352
obj = caml_alloc_custom(&ssl_config_ops, sizeof(mbedtls_ssl_config*), 0, 1);
309353
mbedtls_ssl_config* ssl_config = malloc(sizeof(mbedtls_ssl_config));
310354
mbedtls_ssl_config_init(ssl_config);
355+
#ifdef _WIN32
356+
mbedtls_ssl_conf_verify(ssl_config, verify_callback, NULL);
357+
#endif
311358
Config_val(obj) = ssl_config;
312359
CAMLreturn(obj);
313360
}

0 commit comments

Comments
 (0)
X Tutup