Sign Up
Log In
Log In
or
Sign Up
Places
All Projects
Status Monitor
Collapse sidebar
SUSE:SLE-12-SP5:Update
freerdp.6948
freerdp-Fix-TALOS-issues.patch
Overview
Repositories
Revisions
Requests
Users
Attributes
Meta
File freerdp-Fix-TALOS-issues.patch of Package freerdp.6948
diff --git a/libfreerdp/core/capabilities.c b/libfreerdp/core/capabilities.c index d6e46e8..1a16b03 100644 --- a/libfreerdp/core/capabilities.c +++ b/libfreerdp/core/capabilities.c @@ -3657,12 +3657,12 @@ BOOL rdp_recv_get_active_header(rdpRdp* rdp, wStream* s, UINT16* pChannelId) if (rdp->settings->UseRdpSecurityLayer) { - if (!rdp_read_security_header(s, &securityFlags)) + if (!rdp_read_security_header(s, &securityFlags, &length)) return FALSE; if (securityFlags & SEC_ENCRYPT) { - if (!rdp_decrypt(rdp, s, length - 4, securityFlags)) + if (!rdp_decrypt(rdp, s, length, securityFlags)) { WLog_ERR(TAG, "rdp_decrypt failed"); return FALSE; diff --git a/libfreerdp/core/certificate.c b/libfreerdp/core/certificate.c index 9ce68f3..d750685 100644 --- a/libfreerdp/core/certificate.c +++ b/libfreerdp/core/certificate.c @@ -361,7 +361,6 @@ static BOOL certificate_process_server_public_key(rdpCertificate* certificate, w UINT32 keylen; UINT32 bitlen; UINT32 datalen; - UINT32 modlen; if (Stream_GetRemainingLength(s) < 20) return FALSE; @@ -378,12 +377,11 @@ static BOOL certificate_process_server_public_key(rdpCertificate* certificate, w Stream_Read_UINT32(s, bitlen); Stream_Read_UINT32(s, datalen); Stream_Read(s, certificate->cert_info.exponent, 4); - modlen = keylen - 8; - if (Stream_GetRemainingLength(s) < modlen + 8) // count padding + if ((keylen <= 8) || (Stream_GetRemainingLength(s) < keylen)) return FALSE; - certificate->cert_info.ModulusLength = modlen; + certificate->cert_info.ModulusLength = keylen - 8; certificate->cert_info.Modulus = malloc(certificate->cert_info.ModulusLength); if (!certificate->cert_info.Modulus) @@ -547,7 +545,7 @@ BOOL certificate_read_server_proprietary_certificate(rdpCertificate* certificate BOOL certificate_read_server_x509_certificate_chain(rdpCertificate* certificate, wStream* s) { - int i; + UINT32 i; BOOL ret; UINT32 certLength; UINT32 numCertBlobs; @@ -563,7 +561,7 @@ BOOL certificate_read_server_x509_certificate_chain(rdpCertificate* certificate, if (!certificate->x509_cert_chain) return FALSE; - for (i = 0; i < (int) numCertBlobs; i++) + for (i = 0; i < numCertBlobs; i++) { if (Stream_GetRemainingLength(s) < 4) return FALSE; @@ -622,7 +620,7 @@ BOOL certificate_read_server_x509_certificate_chain(rdpCertificate* certificate, * @param length certificate length */ -BOOL certificate_read_server_certificate(rdpCertificate* certificate, BYTE* server_cert, int length) +BOOL certificate_read_server_certificate(rdpCertificate* certificate, BYTE* server_cert, size_t length) { BOOL ret; wStream* s; diff --git a/libfreerdp/core/certificate.h b/libfreerdp/core/certificate.h index a48701b..3b0b4a2 100644 --- a/libfreerdp/core/certificate.h +++ b/libfreerdp/core/certificate.h @@ -51,7 +51,7 @@ void certificate_free_x509_certificate_chain(rdpX509CertChain* x509_cert_chain); BOOL certificate_read_server_proprietary_certificate(rdpCertificate* certificate, wStream* s); BOOL certificate_read_server_x509_certificate_chain(rdpCertificate* certificate, wStream* s); -BOOL certificate_read_server_certificate(rdpCertificate* certificate, BYTE* server_cert, int length); +BOOL certificate_read_server_certificate(rdpCertificate* certificate, BYTE* server_cert, size_t length); rdpCertificate* certificate_clone(rdpCertificate* certificate); diff --git a/libfreerdp/core/connection.c b/libfreerdp/core/connection.c index f66e181..e03ffb9 100644 --- a/libfreerdp/core/connection.c +++ b/libfreerdp/core/connection.c @@ -565,7 +565,7 @@ BOOL rdp_server_establish_keys(rdpRdp* rdp, wStream* s) return FALSE; } - if (!rdp_read_security_header(s, &sec_flags)) + if (!rdp_read_security_header(s, &sec_flags, NULL)) { WLog_ERR(TAG, "invalid security header"); return FALSE; @@ -787,7 +787,7 @@ BOOL rdp_client_connect_auto_detect(rdpRdp* rdp, wStream* s) { UINT16 securityFlags; - if (!rdp_read_security_header(s, &securityFlags)) + if (!rdp_read_security_header(s, &securityFlags, &length)) return FALSE; if (rdp_recv_message_channel_pdu(rdp, s, securityFlags) == 0) diff --git a/libfreerdp/core/gcc.c b/libfreerdp/core/gcc.c index e19e019..019b48b 100644 --- a/libfreerdp/core/gcc.c +++ b/libfreerdp/core/gcc.c @@ -33,6 +33,7 @@ #define TAG FREERDP_TAG("core.gcc") + /** * T.124 GCC is defined in: * @@ -1113,34 +1114,49 @@ BOOL gcc_read_server_security_data(wStream* s, rdpMcs* mcs) Stream_Read_UINT32(s, settings->ServerRandomLength); /* serverRandomLen */ Stream_Read_UINT32(s, settings->ServerCertificateLength); /* serverCertLen */ - if (Stream_GetRemainingLength(s) < settings->ServerRandomLength + settings->ServerCertificateLength) + if ((settings->ServerRandomLength == 0) || (settings->ServerCertificateLength == 0)) return FALSE; - if ((settings->ServerRandomLength <= 0) || (settings->ServerCertificateLength <= 0)) + if (Stream_GetRemainingLength(s) < settings->ServerRandomLength) return FALSE; /* serverRandom */ settings->ServerRandom = (BYTE*) malloc(settings->ServerRandomLength); if (!settings->ServerRandom) - return FALSE; + goto fail; Stream_Read(s, settings->ServerRandom, settings->ServerRandomLength); + + if (Stream_GetRemainingLength(s) < settings->ServerCertificateLength) + goto fail; + /* serverCertificate */ settings->ServerCertificate = (BYTE*) malloc(settings->ServerCertificateLength); if (!settings->ServerCertificate) - return FALSE; + goto fail; Stream_Read(s, settings->ServerCertificate, settings->ServerCertificateLength); certificate_free(settings->RdpServerCertificate); settings->RdpServerCertificate = certificate_new(); if (!settings->RdpServerCertificate) - return FALSE; + goto fail; data = settings->ServerCertificate; length = settings->ServerCertificateLength; - return certificate_read_server_certificate(settings->RdpServerCertificate, data, length); + if (!certificate_read_server_certificate(settings->RdpServerCertificate, data, + length)) + goto fail; + + return TRUE; + + fail: + free (settings->ServerRandom); + free (settings->ServerCertificate); + settings->ServerRandom = NULL; + settings->ServerCertificate = NULL; + return FALSE; } static const BYTE initial_signature[] = diff --git a/libfreerdp/core/info.c b/libfreerdp/core/info.c index 4f6c703..ab1161a 100644 --- a/libfreerdp/core/info.c +++ b/libfreerdp/core/info.c @@ -759,7 +759,7 @@ BOOL rdp_recv_client_info(rdpRdp* rdp, wStream* s) if (!rdp_read_header(rdp, s, &length, &channelId)) return FALSE; - if (!rdp_read_security_header(s, &securityFlags)) + if (!rdp_read_security_header(s, &securityFlags, &length)) return FALSE; if ((securityFlags & SEC_INFO_PKT) == 0) @@ -775,7 +775,7 @@ BOOL rdp_recv_client_info(rdpRdp* rdp, wStream* s) if (securityFlags & SEC_ENCRYPT) { - if (!rdp_decrypt(rdp, s, length - 4, securityFlags)) + if (!rdp_decrypt(rdp, s, length, securityFlags)) { WLog_ERR(TAG, "rdp_decrypt failed"); return FALSE; diff --git a/libfreerdp/core/license.c b/libfreerdp/core/license.c index 055a2dc..83328c1 100644 --- a/libfreerdp/core/license.c +++ b/libfreerdp/core/license.c @@ -36,6 +36,40 @@ /* #define LICENSE_NULL_CLIENT_RANDOM 1 */ /* #define LICENSE_NULL_PREMASTER_SECRET 1 */ +static wStream* license_send_stream_init(rdpLicense* license); + +static void license_generate_randoms(rdpLicense* license); +static BOOL license_generate_keys(rdpLicense* license); +static BOOL license_generate_hwid(rdpLicense* license); +static BOOL license_encrypt_premaster_secret(rdpLicense* license); +static BOOL license_decrypt_platform_challenge(rdpLicense* license); + +static LICENSE_PRODUCT_INFO* license_new_product_info(void); +static void license_free_product_info(LICENSE_PRODUCT_INFO* productInfo); +static BOOL license_read_product_info(wStream* s, LICENSE_PRODUCT_INFO* productInfo); + +static LICENSE_BLOB* license_new_binary_blob(UINT16 type); +static void license_free_binary_blob(LICENSE_BLOB* blob); +static BOOL license_read_binary_blob(wStream* s, LICENSE_BLOB* blob); +static BOOL license_write_binary_blob(wStream* s, LICENSE_BLOB* blob); + +static SCOPE_LIST* license_new_scope_list(void); +static void license_free_scope_list(SCOPE_LIST* scopeList); +static BOOL license_read_scope_list(wStream* s, SCOPE_LIST* scopeList); + +static BOOL license_read_license_request_packet(rdpLicense* license, wStream* s); +static BOOL license_read_platform_challenge_packet(rdpLicense* license, wStream* s); +static void license_read_new_license_packet(rdpLicense* license, wStream* s); +static void license_read_upgrade_license_packet(rdpLicense* license, wStream* s); +static BOOL license_read_error_alert_packet(rdpLicense* license, wStream* s); + +static BOOL license_write_new_license_request_packet(rdpLicense* license, wStream* s); +static BOOL license_send_new_license_request_packet(rdpLicense* license); + +static BOOL license_write_platform_challenge_response_packet( + rdpLicense* license, wStream* s, BYTE* mac_data); +static BOOL license_send_platform_challenge_response_packet(rdpLicense* license); + #ifdef WITH_DEBUG_LICENSE static const char* const LICENSE_MESSAGE_STRINGS[] = @@ -82,7 +116,7 @@ static const char* const state_transitions[] = "ST_RESEND_LAST_MESSAGE" }; -void license_print_product_info(LICENSE_PRODUCT_INFO* productInfo) +static void license_print_product_info(LICENSE_PRODUCT_INFO* productInfo) { char* CompanyName = NULL; char* ProductId = NULL; @@ -98,7 +132,7 @@ void license_print_product_info(LICENSE_PRODUCT_INFO* productInfo) free(ProductId); } -void license_print_scope_list(SCOPE_LIST* scopeList) +static void license_print_scope_list(SCOPE_LIST* scopeList) { int index; LICENSE_BLOB* scope; @@ -251,12 +285,12 @@ int license_recv(rdpLicense* license, wStream* s) return -1; } - if (!rdp_read_security_header(s, &securityFlags)) + if (!rdp_read_security_header(s, &securityFlags, &length)) return -1; if (securityFlags & SEC_ENCRYPT) { - if (!rdp_decrypt(license->rdp, s, length - 4, securityFlags)) + if (!rdp_decrypt(license->rdp, s, length, securityFlags)) { WLog_ERR(TAG, "rdp_decrypt failed"); return -1; @@ -468,7 +502,12 @@ BOOL license_decrypt_platform_challenge(rdpLicense* license) if ((rc4 = winpr_RC4_New(license->LicensingEncryptionKey, LICENSING_ENCRYPTION_KEY_LENGTH)) == NULL) + { + free(license->PlatformChallenge->data); + license->PlatformChallenge->data = NULL; + license->PlatformChallenge->length = 0; return FALSE; + } rc = winpr_RC4_Update(rc4, license->EncryptedPlatformChallenge->length, license->EncryptedPlatformChallenge->data, license->PlatformChallenge->data); @@ -492,15 +531,27 @@ BOOL license_read_product_info(wStream* s, LICENSE_PRODUCT_INFO* productInfo) Stream_Read_UINT32(s, productInfo->dwVersion); /* dwVersion (4 bytes) */ Stream_Read_UINT32(s, productInfo->cbCompanyName); /* cbCompanyName (4 bytes) */ - if (Stream_GetRemainingLength(s) < productInfo->cbCompanyName + 4) + /* Name must be >0, but there is no upper limit defined, use UINT32_MAX */ + if ((productInfo->cbCompanyName < 2) || (productInfo->cbCompanyName % 2 != 0)) + return FALSE; + + if (Stream_GetRemainingLength(s) < productInfo->cbCompanyName) return FALSE; + productInfo->pbProductId = NULL; productInfo->pbCompanyName = (BYTE*) malloc(productInfo->cbCompanyName); if (!productInfo->pbCompanyName) return FALSE; Stream_Read(s, productInfo->pbCompanyName, productInfo->cbCompanyName); + + if (Stream_GetRemainingLength(s) < 4) + goto out_fail; + Stream_Read_UINT32(s, productInfo->cbProductId); /* cbProductId (4 bytes) */ + if ((productInfo->cbProductId < 2) || (productInfo->cbProductId % 2 != 0)) + goto out_fail; + if (Stream_GetRemainingLength(s) < productInfo->cbProductId) goto out_fail; @@ -512,7 +563,9 @@ BOOL license_read_product_info(wStream* s, LICENSE_PRODUCT_INFO* productInfo) out_fail: free(productInfo->pbCompanyName); + free(productInfo->pbProductId); productInfo->pbCompanyName = NULL; + productInfo->pbProductId = NULL; return FALSE; } @@ -811,7 +864,9 @@ BOOL license_read_platform_challenge_packet(rdpLicense* license, wStream* s) Stream_Read_UINT32(s, ConnectFlags); /* ConnectFlags, Reserved (4 bytes) */ /* EncryptedPlatformChallenge */ license->EncryptedPlatformChallenge->type = BB_ANY_BLOB; - license_read_binary_blob(s, license->EncryptedPlatformChallenge); + if (!license_read_binary_blob(s, license->EncryptedPlatformChallenge)) + return FALSE; + license->EncryptedPlatformChallenge->type = BB_ENCRYPTED_DATA_BLOB; if (Stream_GetRemainingLength(s) < 16) diff --git a/libfreerdp/core/license.h b/libfreerdp/core/license.h index aba0a02..ef128ea 100644 --- a/libfreerdp/core/license.h +++ b/libfreerdp/core/license.h @@ -17,8 +17,8 @@ * limitations under the License. */ -#ifndef __LICENSE_H -#define __LICENSE_H +#ifndef FREERDP_LICENSE_H +#define FREERDP_LICENSE_H typedef struct rdp_license rdpLicense; @@ -202,38 +202,6 @@ struct rdp_license int license_recv(rdpLicense* license, wStream* s); BOOL license_send(rdpLicense* license, wStream* s, BYTE type); -wStream* license_send_stream_init(rdpLicense* license); - -void license_generate_randoms(rdpLicense* license); -BOOL license_generate_keys(rdpLicense* license); -BOOL license_generate_hwid(rdpLicense* license); -BOOL license_encrypt_premaster_secret(rdpLicense* license); -BOOL license_decrypt_platform_challenge(rdpLicense* license); - -LICENSE_PRODUCT_INFO* license_new_product_info(void); -void license_free_product_info(LICENSE_PRODUCT_INFO* productInfo); -BOOL license_read_product_info(wStream* s, LICENSE_PRODUCT_INFO* productInfo); - -LICENSE_BLOB* license_new_binary_blob(UINT16 type); -void license_free_binary_blob(LICENSE_BLOB* blob); -BOOL license_read_binary_blob(wStream* s, LICENSE_BLOB* blob); -BOOL license_write_binary_blob(wStream* s, LICENSE_BLOB* blob); - -SCOPE_LIST* license_new_scope_list(void); -void license_free_scope_list(SCOPE_LIST* scopeList); -BOOL license_read_scope_list(wStream* s, SCOPE_LIST* scopeList); - -BOOL license_read_license_request_packet(rdpLicense* license, wStream* s); -BOOL license_read_platform_challenge_packet(rdpLicense* license, wStream* s); -void license_read_new_license_packet(rdpLicense* license, wStream* s); -void license_read_upgrade_license_packet(rdpLicense* license, wStream* s); -BOOL license_read_error_alert_packet(rdpLicense* license, wStream* s); - -BOOL license_write_new_license_request_packet(rdpLicense* license, wStream* s); -BOOL license_send_new_license_request_packet(rdpLicense* license); - -BOOL license_write_platform_challenge_response_packet(rdpLicense* license, wStream* s, BYTE* mac_data); -BOOL license_send_platform_challenge_response_packet(rdpLicense* license); BOOL license_send_valid_client_error_packet(rdpLicense* license); diff --git a/libfreerdp/core/mcs.c b/libfreerdp/core/mcs.c index 27c9126..e3f2a71 100644 --- a/libfreerdp/core/mcs.c +++ b/libfreerdp/core/mcs.c @@ -223,7 +223,8 @@ BOOL mcs_read_domain_mcspdu_header(wStream* s, enum DomainMCSPDU* domainMCSPDU, BYTE choice; enum DomainMCSPDU MCSPDU; - *length = tpkt_read_header(s); + if (!tpkt_read_header(s, length)) + return FALSE; if (!tpdu_read_data(s, &li)) return FALSE; @@ -480,8 +481,10 @@ BOOL mcs_recv_connect_initial(rdpMcs* mcs, wStream* s) UINT16 li; int length; BOOL upwardFlag; + UINT16 tlength; - tpkt_read_header(s); + if (!tpkt_read_header(s, &tlength)) + return FALSE; if (!tpdu_read_data(s, &li)) return FALSE; @@ -697,11 +700,13 @@ out: BOOL mcs_recv_connect_response(rdpMcs* mcs, wStream* s) { int length; + UINT16 tlength; BYTE result; UINT16 li; UINT32 calledConnectId; - tpkt_read_header(s); + if (!tpkt_read_header(s, &tlength)) + return FALSE; if (!tpdu_read_data(s, &li)) return FALSE; diff --git a/libfreerdp/core/nego.c b/libfreerdp/core/nego.c index 136b305..3cbad6a 100644 --- a/libfreerdp/core/nego.c +++ b/libfreerdp/core/nego.c @@ -575,7 +575,8 @@ int nego_recv(rdpTransport* transport, wStream* s, void* extra) UINT16 length; rdpNego* nego = (rdpNego*) extra; - length = tpkt_read_header(s); + if (!tpkt_read_header(s, &length)) + return -1; if (length == 0) return -1; @@ -739,8 +740,10 @@ BOOL nego_read_request(rdpNego* nego, wStream* s) { BYTE li; BYTE type; + UINT16 length; - tpkt_read_header(s); + if (!tpkt_read_header(s, &length)) + return FALSE; if (!tpdu_read_connection_request(s, &li)) return FALSE; diff --git a/libfreerdp/core/peer.c b/libfreerdp/core/peer.c index 8318c4d..7263feb 100644 --- a/libfreerdp/core/peer.c +++ b/libfreerdp/core/peer.c @@ -369,12 +369,12 @@ static int peer_recv_tpkt_pdu(freerdp_peer* client, wStream* s) if (rdp->settings->UseRdpSecurityLayer) { - if (!rdp_read_security_header(s, &securityFlags)) + if (!rdp_read_security_header(s, &securityFlags, &length)) return -1; if (securityFlags & SEC_ENCRYPT) { - if (!rdp_decrypt(rdp, s, length - 4, securityFlags)) + if (!rdp_decrypt(rdp, s, length, securityFlags)) { WLog_ERR(TAG, "rdp_decrypt failed"); return -1; @@ -414,7 +414,7 @@ static int peer_recv_tpkt_pdu(freerdp_peer* client, wStream* s) else if (rdp->mcs->messageChannelId && channelId == rdp->mcs->messageChannelId) { if (!rdp->settings->UseRdpSecurityLayer) - if (!rdp_read_security_header(s, &securityFlags)) + if (!rdp_read_security_header(s, &securityFlags, NULL)) return -1; return rdp_recv_message_channel_pdu(rdp, s, securityFlags); diff --git a/libfreerdp/core/rdp.c b/libfreerdp/core/rdp.c index e7c5bd2..2d34a34 100644 --- a/libfreerdp/core/rdp.c +++ b/libfreerdp/core/rdp.c @@ -79,13 +79,17 @@ const char* DATA_PDU_TYPE_STRINGS[80] = * @param flags security flags */ -BOOL rdp_read_security_header(wStream* s, UINT16* flags) +BOOL rdp_read_security_header(wStream* s, UINT16* flags, UINT16* length) { /* Basic Security Header */ - if (Stream_GetRemainingLength(s) < 4) + if ((Stream_GetRemainingLength(s) < 4) || (length && (*length < 4))) return FALSE; Stream_Read_UINT16(s, *flags); /* flags */ Stream_Seek(s, 2); /* flagsHi (unused) */ + + if (length) + *length -= 4; + return TRUE; } @@ -301,7 +305,8 @@ BOOL rdp_read_header(rdpRdp* rdp, wStream* s, UINT16* length, UINT16* channelId) MCSPDU = (rdp->settings->ServerMode) ? DomainMCSPDU_SendDataRequest : DomainMCSPDU_SendDataIndication; - *length = tpkt_read_header(s); + if (!tpkt_read_header(s, length)) + return FALSE; if (!tpdu_read_header(s, &code, &li)) return FALSE; @@ -330,7 +335,10 @@ BOOL rdp_read_header(rdpRdp* rdp, wStream* s, UINT16* length, UINT16* channelId) MCSPDU = domainMCSPDU; - if ((size_t) (*length - 8) > Stream_GetRemainingLength(s)) + if (*length < 8) + return FALSE; + + if ((*length - 8) > Stream_GetRemainingLength(s)) return FALSE; if (MCSPDU == DomainMCSPDU_DisconnectProviderUltimatum) @@ -376,8 +384,12 @@ BOOL rdp_read_header(rdpRdp* rdp, wStream* s, UINT16* length, UINT16* channelId) if (Stream_GetRemainingLength(s) < 5) return FALSE; - per_read_integer16(s, &initiator, MCS_BASE_CHANNEL_ID); /* initiator (UserId) */ - per_read_integer16(s, channelId, 0); /* channelId */ + if (!per_read_integer16(s, &initiator, MCS_BASE_CHANNEL_ID)) /* initiator (UserId) */ + return FALSE; + + if (!per_read_integer16(s, channelId, 0)) /* channelId */ + return FALSE; + Stream_Read_UINT8(s, byte); /* dataPriority + Segmentation (0x70) */ if (!per_read_length(s, length)) /* userData (OCTET_STRING) */ @@ -1024,17 +1036,21 @@ void rdp_read_flow_control_pdu(wStream* s, UINT16* type) * @param length int */ -BOOL rdp_decrypt(rdpRdp* rdp, wStream* s, int length, UINT16 securityFlags) +BOOL rdp_decrypt(rdpRdp* rdp, wStream* s, INT32 length, UINT16 securityFlags) { BYTE cmac[8]; BYTE wmac[8]; BOOL status; + if (!rdp || !s || (length < 0)) + return FALSE; + if (rdp->settings->EncryptionMethods == ENCRYPTION_METHOD_FIPS) { UINT16 len; BYTE version, pad; BYTE* sig; + INT64 padLength; if (Stream_GetRemainingLength(s) < 12) return FALSE; @@ -1047,6 +1063,9 @@ BOOL rdp_decrypt(rdpRdp* rdp, wStream* s, int length, UINT16 securityFlags) Stream_Seek(s, 8); /* signature */ length -= 12; + padLength = length - pad; + if ((length <= 0) || (padLength <= 0)) + return FALSE; if (!security_fips_decrypt(Stream_Pointer(s), length, rdp)) { @@ -1064,11 +1083,13 @@ BOOL rdp_decrypt(rdpRdp* rdp, wStream* s, int length, UINT16 securityFlags) return TRUE; } - if (Stream_GetRemainingLength(s) < 8) + if (Stream_GetRemainingLength(s) < sizeof(wmac)) return FALSE; Stream_Read(s, wmac, sizeof(wmac)); length -= sizeof(wmac); + if (length <= 0) + return FALSE; if (!security_decrypt(Stream_Pointer(s), length, rdp)) return FALSE; @@ -1129,7 +1150,7 @@ static int rdp_recv_tpkt_pdu(rdpRdp* rdp, wStream* s) if (rdp->settings->UseRdpSecurityLayer) { - if (!rdp_read_security_header(s, &securityFlags)) + if (!rdp_read_security_header(s, &securityFlags, &length)) { WLog_ERR(TAG, "rdp_recv_tpkt_pdu: rdp_read_security_header() fail"); return -1; @@ -1137,7 +1158,7 @@ static int rdp_recv_tpkt_pdu(rdpRdp* rdp, wStream* s) if (securityFlags & (SEC_ENCRYPT | SEC_REDIRECTION_PKT)) { - if (!rdp_decrypt(rdp, s, length - 4, securityFlags)) + if (!rdp_decrypt(rdp, s, length, securityFlags)) { WLog_ERR(TAG, "rdp_decrypt failed"); return -1; @@ -1210,7 +1231,7 @@ static int rdp_recv_tpkt_pdu(rdpRdp* rdp, wStream* s) else if (rdp->mcs->messageChannelId && channelId == rdp->mcs->messageChannelId) { if (!rdp->settings->UseRdpSecurityLayer) - if (!rdp_read_security_header(s, &securityFlags)) + if (!rdp_read_security_header(s, &securityFlags, NULL)) return -1; return rdp_recv_message_channel_pdu(rdp, s, securityFlags); diff --git a/libfreerdp/core/rdp.h b/libfreerdp/core/rdp.h index ef8e0dc..5c6ce35 100644 --- a/libfreerdp/core/rdp.h +++ b/libfreerdp/core/rdp.h @@ -178,7 +178,7 @@ struct rdp_rdp rdpSettings* settingsCopy; }; -BOOL rdp_read_security_header(wStream* s, UINT16* flags); +BOOL rdp_read_security_header(wStream* s, UINT16* flags, UINT16* length); void rdp_write_security_header(wStream* s, UINT16 flags); BOOL rdp_read_share_control_header(wStream* s, UINT16* length, UINT16* type, UINT16* channel_id); @@ -232,7 +232,7 @@ void rdp_free(rdpRdp* rdp); #define DEBUG_RDP(fmt, ...) do { } while (0) #endif -BOOL rdp_decrypt(rdpRdp* rdp, wStream* s, int length, UINT16 securityFlags); +BOOL rdp_decrypt(rdpRdp* rdp, wStream* s, INT32 length, UINT16 securityFlags); BOOL rdp_set_error_info(rdpRdp* rdp, UINT32 errorInfo); BOOL rdp_send_error_info(rdpRdp* rdp); diff --git a/libfreerdp/core/security.c b/libfreerdp/core/security.c index e415786..e6121d4 100644 --- a/libfreerdp/core/security.c +++ b/libfreerdp/core/security.c @@ -580,7 +580,7 @@ BOOL security_key_update(BYTE* key, BYTE* update_key, int key_len, rdpRdp* rdp) return TRUE; } -BOOL security_encrypt(BYTE* data, int length, rdpRdp* rdp) +BOOL security_encrypt(BYTE* data, size_t length, rdpRdp* rdp) { if (rdp->encrypt_use_count >= 4096) { @@ -602,7 +602,7 @@ BOOL security_encrypt(BYTE* data, int length, rdpRdp* rdp) return TRUE; } -BOOL security_decrypt(BYTE* data, int length, rdpRdp* rdp) +BOOL security_decrypt(BYTE* data, size_t length, rdpRdp* rdp) { if (rdp->rc4_decrypt_key == NULL) return FALSE; @@ -626,7 +626,7 @@ BOOL security_decrypt(BYTE* data, int length, rdpRdp* rdp) return TRUE; } -BOOL security_hmac_signature(const BYTE* data, int length, BYTE* output, rdpRdp* rdp) +BOOL security_hmac_signature(const BYTE* data, size_t length, BYTE* output, rdpRdp* rdp) { BYTE buf[WINPR_SHA1_DIGEST_LENGTH]; BYTE use_count_le[4]; @@ -647,7 +647,7 @@ BOOL security_hmac_signature(const BYTE* data, int length, BYTE* output, rdpRdp* return TRUE; } -BOOL security_fips_encrypt(BYTE* data, int length, rdpRdp* rdp) +BOOL security_fips_encrypt(BYTE* data, size_t length, rdpRdp* rdp) { size_t olen; @@ -657,7 +657,7 @@ BOOL security_fips_encrypt(BYTE* data, int length, rdpRdp* rdp) return TRUE; } -BOOL security_fips_decrypt(BYTE* data, int length, rdpRdp* rdp) +BOOL security_fips_decrypt(BYTE* data, size_t length, rdpRdp* rdp) { size_t olen; @@ -666,7 +666,7 @@ BOOL security_fips_decrypt(BYTE* data, int length, rdpRdp* rdp) return TRUE; } -BOOL security_fips_check_signature(const BYTE* data, int length, const BYTE* sig, rdpRdp* rdp) +BOOL security_fips_check_signature(const BYTE* data, size_t length, const BYTE* sig, rdpRdp* rdp) { BYTE buf[WINPR_SHA1_DIGEST_LENGTH]; BYTE use_count_le[4]; diff --git a/libfreerdp/core/security.h b/libfreerdp/core/security.h index fc03a3e..14f4664 100644 --- a/libfreerdp/core/security.h +++ b/libfreerdp/core/security.h @@ -17,8 +17,8 @@ * limitations under the License. */ -#ifndef __SECURITY_H -#define __SECURITY_H +#ifndef FREERDP_SECURITY_H +#define FREERDP_SECURITY_H #include "rdp.h" #include <freerdp/crypto/crypto.h> @@ -37,12 +37,12 @@ BOOL security_mac_signature(rdpRdp *rdp, const BYTE* data, UINT32 length, BYTE* BOOL security_salted_mac_signature(rdpRdp *rdp, const BYTE* data, UINT32 length, BOOL encryption, BYTE* output); BOOL security_establish_keys(const BYTE* client_random, rdpRdp* rdp); -BOOL security_encrypt(BYTE* data, int length, rdpRdp* rdp); -BOOL security_decrypt(BYTE* data, int length, rdpRdp* rdp); +BOOL security_encrypt(BYTE* data, size_t length, rdpRdp* rdp); +BOOL security_decrypt(BYTE* data, size_t length, rdpRdp* rdp); -BOOL security_hmac_signature(const BYTE* data, int length, BYTE* output, rdpRdp* rdp); -BOOL security_fips_encrypt(BYTE* data, int length, rdpRdp* rdp); -BOOL security_fips_decrypt(BYTE* data, int length, rdpRdp* rdp); -BOOL security_fips_check_signature(const BYTE* data, int length, const BYTE* sig, rdpRdp* rdp); +BOOL security_hmac_signature(const BYTE* data, size_t length, BYTE* output, rdpRdp* rdp); +BOOL security_fips_encrypt(BYTE* data, size_t length, rdpRdp* rdp); +BOOL security_fips_decrypt(BYTE* data, size_t length, rdpRdp* rdp); +BOOL security_fips_check_signature(const BYTE* data, size_t length, const BYTE* sig, rdpRdp* rdp); #endif /* __SECURITY_H */ diff --git a/libfreerdp/core/tpkt.c b/libfreerdp/core/tpkt.c index 5689d62..eed79d7 100644 --- a/libfreerdp/core/tpkt.c +++ b/libfreerdp/core/tpkt.c @@ -78,28 +78,39 @@ BOOL tpkt_verify_header(wStream* s) /** * Read a TPKT header.\n * @param s - * @return length + * @param length + * @return success */ -UINT16 tpkt_read_header(wStream* s) +BOOL tpkt_read_header(wStream* s, UINT16* length) { BYTE version; - UINT16 length; + + if (Stream_GetRemainingLength(s) < 1) + return FALSE; Stream_Peek_UINT8(s, version); if (version == 3) { + UINT16 len; + if (Stream_GetRemainingLength(s) < 4) + return FALSE; + Stream_Seek(s, 2); - Stream_Read_UINT16_BE(s, length); + Stream_Read_UINT16_BE(s, len); + if (len < 4) + return FALSE; + + *length = len; } else { /* not a TPKT header */ - length = 0; + *length = 0; } - return length; + return TRUE; } /** diff --git a/libfreerdp/core/tpkt.h b/libfreerdp/core/tpkt.h index af984c1..9b51749 100644 --- a/libfreerdp/core/tpkt.h +++ b/libfreerdp/core/tpkt.h @@ -28,7 +28,7 @@ #define TPKT_HEADER_LENGTH 4 BOOL tpkt_verify_header(wStream* s); -UINT16 tpkt_read_header(wStream* s); +BOOL tpkt_read_header(wStream* s, UINT16* length); void tpkt_write_header(wStream* s, UINT16 length); #endif /* __TPKT_H */
Locations
Projects
Search
Status Monitor
Help
OpenBuildService.org
Documentation
API Documentation
Code of Conduct
Contact
Support
@OBShq
Terms
openSUSE Build Service is sponsored by
The Open Build Service is an
openSUSE project
.
Sign Up
Log In
Places
Places
All Projects
Status Monitor