diff options
author | theirix <theirix@gmail.com> | 2016-04-12 22:14:13 +0300 |
---|---|---|
committer | theirix <theirix@gmail.com> | 2016-04-12 22:14:13 +0300 |
commit | c22d3d3cae8fc6d5fcf1b7320a7602426a9b9ca2 (patch) | |
tree | adebbf469efc03bba8a8d955b5116b35ae50ef3e /src/lib/protocols/ssl.c | |
parent | fb3fc0c6de201a2ab34b6f7ce4d5dfc2c54c3b5e (diff) |
Fixed more buffer overflows with small packets
Diffstat (limited to 'src/lib/protocols/ssl.c')
-rw-r--r-- | src/lib/protocols/ssl.c | 87 |
1 files changed, 45 insertions, 42 deletions
diff --git a/src/lib/protocols/ssl.c b/src/lib/protocols/ssl.c index 2269ae782..14deff7f9 100644 --- a/src/lib/protocols/ssl.c +++ b/src/lib/protocols/ssl.c @@ -223,64 +223,67 @@ int getSSLcertificate(struct ndpi_detection_module_struct *ndpi_struct, } } else if(handshake_protocol == 0x01 /* Client Hello */) { u_int offset, base_offset = 43; - u_int16_t session_id_len = packet->payload[base_offset]; + if (base_offset + 2 <= packet->payload_packet_len) + { + u_int16_t session_id_len = packet->payload[base_offset]; - if((session_id_len+base_offset+2) <= total_len) { - u_int16_t cypher_len = packet->payload[session_id_len+base_offset+2] + (packet->payload[session_id_len+base_offset+1] << 8); - offset = base_offset + session_id_len + cypher_len + 2; + if((session_id_len+base_offset+2) <= total_len) { + u_int16_t cypher_len = packet->payload[session_id_len+base_offset+2] + (packet->payload[session_id_len+base_offset+1] << 8); + offset = base_offset + session_id_len + cypher_len + 2; - flow->l4.tcp.ssl_seen_client_cert = 1; + flow->l4.tcp.ssl_seen_client_cert = 1; - if(offset < total_len) { - u_int16_t compression_len; - u_int16_t extensions_len; + if(offset < total_len) { + u_int16_t compression_len; + u_int16_t extensions_len; - compression_len = packet->payload[offset+1]; - offset += compression_len + 3; + compression_len = packet->payload[offset+1]; + offset += compression_len + 3; - if(offset < total_len) { - extensions_len = packet->payload[offset]; + if(offset < total_len) { + extensions_len = packet->payload[offset]; - if((extensions_len+offset) < total_len) { - u_int16_t extension_offset = 1; /* Move to the first extension */ + if((extensions_len+offset) < total_len) { + u_int16_t extension_offset = 1; /* Move to the first extension */ - while(extension_offset < extensions_len) { - u_int16_t extension_id, extension_len; + while(extension_offset < extensions_len) { + u_int16_t extension_id, extension_len; - memcpy(&extension_id, &packet->payload[offset+extension_offset], 2); - extension_offset += 2; + memcpy(&extension_id, &packet->payload[offset+extension_offset], 2); + extension_offset += 2; - memcpy(&extension_len, &packet->payload[offset+extension_offset], 2); - extension_offset += 2; + memcpy(&extension_len, &packet->payload[offset+extension_offset], 2); + extension_offset += 2; - extension_id = ntohs(extension_id), extension_len = ntohs(extension_len); + extension_id = ntohs(extension_id), extension_len = ntohs(extension_len); - if(extension_id == 0) { - u_int begin = 0,len; - char *server_name = (char*)&packet->payload[offset+extension_offset]; + if(extension_id == 0) { + u_int begin = 0,len; + char *server_name = (char*)&packet->payload[offset+extension_offset]; - while(begin < extension_len) { - if((!ndpi_isprint(server_name[begin])) - || ndpi_ispunct(server_name[begin]) - || ndpi_isspace(server_name[begin])) - begin++; - else - break; - } + while(begin < extension_len) { + if((!ndpi_isprint(server_name[begin])) + || ndpi_ispunct(server_name[begin]) + || ndpi_isspace(server_name[begin])) + begin++; + else + break; + } - len = (u_int)ndpi_min(extension_len-begin, buffer_len-1); - strncpy(buffer, &server_name[begin], len); - buffer[len] = '\0'; - stripCertificateTrailer(buffer, buffer_len); + len = (u_int)ndpi_min(extension_len-begin, buffer_len-1); + strncpy(buffer, &server_name[begin], len); + buffer[len] = '\0'; + stripCertificateTrailer(buffer, buffer_len); - snprintf(flow->protos.ssl.client_certificate, - sizeof(flow->protos.ssl.client_certificate), "%s", buffer); + snprintf(flow->protos.ssl.client_certificate, + sizeof(flow->protos.ssl.client_certificate), "%s", buffer); - /* We're happy now */ - return(2 /* Client Certificate */); - } + /* We're happy now */ + return(2 /* Client Certificate */); + } - extension_offset += extension_len; + extension_offset += extension_len; + } } } } |