Improved fingerprint hash comparison
* Allow new hash format 11bbccdd along already supported 11:22:aa:BB
This commit is contained in:
parent
06c883a709
commit
13f54fc0dd
@ -56,6 +56,8 @@ extern "C"
|
||||
FREERDP_API CryptoCert crypto_cert_read(BYTE* data, UINT32 length);
|
||||
FREERDP_API BYTE* crypto_cert_hash(X509* xcert, const char* hash, UINT32* length);
|
||||
FREERDP_API char* crypto_cert_fingerprint_by_hash(X509* xcert, const char* hash);
|
||||
FREERDP_API char* crypto_cert_fingerprint_by_hash_ex(X509* xcert, const char* hash,
|
||||
BOOL separator);
|
||||
FREERDP_API char* crypto_cert_fingerprint(X509* xcert);
|
||||
FREERDP_API BYTE* crypto_cert_pem(X509* xcert, STACK_OF(X509) * chain, size_t* length);
|
||||
FREERDP_API X509* crypto_cert_from_pem(const char* data, size_t length, BOOL fromFile);
|
||||
|
@ -275,11 +275,16 @@ BYTE* crypto_cert_hash(X509* xcert, const char* hash, UINT32* length)
|
||||
}
|
||||
|
||||
char* crypto_cert_fingerprint_by_hash(X509* xcert, const char* hash)
|
||||
{
|
||||
return crypto_cert_fingerprint_by_hash_ex(xcert, hash, 0);
|
||||
}
|
||||
|
||||
char* crypto_cert_fingerprint_by_hash_ex(X509* xcert, const char* hash, BOOL separator)
|
||||
{
|
||||
UINT32 fp_len, i;
|
||||
size_t pos, size;
|
||||
BYTE* fp;
|
||||
char* p;
|
||||
char* fp_buffer;
|
||||
char* fp_buffer = NULL;
|
||||
if (!xcert)
|
||||
{
|
||||
WLog_ERR(TAG, "Invalid certificate %p", xcert);
|
||||
@ -294,23 +299,35 @@ char* crypto_cert_fingerprint_by_hash(X509* xcert, const char* hash)
|
||||
if (!fp)
|
||||
return NULL;
|
||||
|
||||
fp_buffer = calloc(fp_len * 3 + 1, sizeof(char));
|
||||
size = fp_len * 3 + 1;
|
||||
fp_buffer = calloc(size, sizeof(char));
|
||||
if (!fp_buffer)
|
||||
goto fail;
|
||||
|
||||
p = fp_buffer;
|
||||
pos = 0;
|
||||
|
||||
for (i = 0; i < (fp_len - 1); i++)
|
||||
{
|
||||
sprintf_s(p, (fp_len - i) * 3, "%02" PRIx8 ":", fp[i]);
|
||||
p = &fp_buffer[(i + 1) * 3];
|
||||
int rc;
|
||||
char* p = &fp_buffer[pos];
|
||||
if (separator)
|
||||
rc = sprintf_s(p, size - pos, "%02" PRIx8 ":", fp[i]);
|
||||
else
|
||||
rc = sprintf_s(p, size - pos, "%02" PRIx8, fp[i]);
|
||||
if (rc <= 0)
|
||||
goto fail;
|
||||
pos += (size_t)rc;
|
||||
}
|
||||
|
||||
sprintf_s(p, (fp_len - i) * 3, "%02" PRIx8 "", fp[i]);
|
||||
fail:
|
||||
sprintf_s(&fp_buffer[pos], size - pos, "%02" PRIx8 "", fp[i]);
|
||||
|
||||
free(fp);
|
||||
|
||||
return fp_buffer;
|
||||
fail:
|
||||
free(fp);
|
||||
free(fp_buffer);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static char* crypto_print_name(X509_NAME* name)
|
||||
|
@ -1176,6 +1176,33 @@ static BOOL is_accepted(rdpTls* tls, const BYTE* pem, size_t length)
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
static BOOL compare_fingerprint(const char* fp, const char* hash, CryptoCert cert, BOOL separator)
|
||||
{
|
||||
BOOL equal;
|
||||
char* strhash;
|
||||
|
||||
WINPR_ASSERT(fp);
|
||||
WINPR_ASSERT(hash);
|
||||
WINPR_ASSERT(cert);
|
||||
|
||||
strhash = crypto_cert_fingerprint_by_hash_ex(cert->px509, hash, separator);
|
||||
if (!strhash)
|
||||
return FALSE;
|
||||
|
||||
equal = (_stricmp(strhash, fp) == 0);
|
||||
free(strhash);
|
||||
return equal;
|
||||
}
|
||||
|
||||
static BOOL compare_fingerprint_all(const char* fp, const char* hash, CryptoCert cert)
|
||||
{
|
||||
if (compare_fingerprint(fp, hash, cert, FALSE))
|
||||
return TRUE;
|
||||
if (compare_fingerprint(fp, hash, cert, TRUE))
|
||||
return TRUE;
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
static BOOL is_accepted_fingerprint(CryptoCert cert, const char* CertificateAcceptedFingerprints)
|
||||
{
|
||||
BOOL rc = FALSE;
|
||||
@ -1187,30 +1214,22 @@ static BOOL is_accepted_fingerprint(CryptoCert cert, const char* CertificateAcce
|
||||
while (cur)
|
||||
{
|
||||
char* subcontext = NULL;
|
||||
BOOL equal;
|
||||
char* strhash;
|
||||
const char* h = strtok_s(cur, ":", &subcontext);
|
||||
const char* fp;
|
||||
|
||||
if (!h)
|
||||
continue;
|
||||
goto next;
|
||||
|
||||
fp = h + strlen(h) + 1;
|
||||
if (!fp)
|
||||
continue;
|
||||
goto next;
|
||||
|
||||
strhash = crypto_cert_fingerprint_by_hash(cert->px509, h);
|
||||
if (!strhash)
|
||||
continue;
|
||||
|
||||
equal = (_stricmp(strhash, fp) == 0);
|
||||
free(strhash);
|
||||
if (equal)
|
||||
if (compare_fingerprint_all(fp, h, cert))
|
||||
{
|
||||
rc = TRUE;
|
||||
break;
|
||||
}
|
||||
|
||||
next:
|
||||
cur = strtok_s(NULL, ",", &context);
|
||||
}
|
||||
free(copy);
|
||||
|
Loading…
Reference in New Issue
Block a user