From e234e3518b81fc98bd1cc907929c2442caa7a30f Mon Sep 17 00:00:00 2001 From: Nardi Ivan Date: Sun, 8 Jan 2023 15:54:39 +0100 Subject: [PATCH] Ookla: rework detection The logic of the LRU cache has been changed: once we know an ip has connected to an Ookla server, all the following (unknown) flows (for a short time interval) from the same ip to the port 8080 are treated as Ookla ones. Most of the changes in this commit are about introducing the concept of "aggressive detection". In some cases, to properly detect a protocol we might use some statistical/behavior logic that, from one side, let us to identify the protocol more often but, from the other side, might lead to some false positives. To allow the user/application to easily detect when such logic has been triggered, the new confidence value `NDPI_CONFIDENCE_DPI_AGGRESSIVE` has been added. It is always possible to disable/configure this kind of logic via the API. Detection of Ookla flows using plain TLS over port 8080 is the first example of aggressive detection in nDPI. Tested with: * Android 9.0 with app 4.8.3 * Ubuntu 20.04 with Firefox 110 * Win 10 with app 1.15 and 1.16 * Win 10 with Chrome 108, Edge 108 and Firefox 106 --- example/ndpiReader.c | 45 ++++++- fuzz/fuzz_config.cpp | 5 + src/include/ndpi_api.h | 5 + src/include/ndpi_typedefs.h | 17 ++- src/lib/ndpi_main.c | 56 ++++++++- src/lib/protocols/http.c | 60 +-------- src/lib/protocols/ookla.c | 167 +++++++++++-------------- src/lib/protocols/tls.c | 25 +++- tests/pcap/ookla.pcap | Bin 7485 -> 42424 bytes tests/result/alexa-app.pcapng.out | 2 +- tests/result/ookla.pcap.out | 46 ++++--- tests/result/skype.pcap.out | 2 +- tests/result/skype_no_unknown.pcap.out | 2 +- tests/result/synscan.pcap.out | 2 +- 14 files changed, 258 insertions(+), 176 deletions(-) diff --git a/example/ndpiReader.c b/example/ndpiReader.c index 02cb7364bcd..452c0f5ae15 100644 --- a/example/ndpiReader.c +++ b/example/ndpiReader.c @@ -96,6 +96,7 @@ u_int8_t verbose = 0, enable_flow_stats = 0; int nDPI_LogLevel = 0; char *_debug_protocols = NULL; char *_disabled_protocols = NULL; +int aggressiveness[NDPI_MAX_SUPPORTED_PROTOCOLS]; static u_int8_t stats_flag = 0; ndpi_init_prefs init_prefs = ndpi_no_prefs; u_int8_t human_readeable_string_len = 5; @@ -515,6 +516,7 @@ static void help(u_int long_help) { " -z | Enable JA3+\n" " -A | Dump internal statistics (LRU caches / Patricia trees / Ahocarasick automas / ...\n" " -M | Memory allocation stats on data-path (only by the library). It works only on single-thread configuration\n" + " -Z proto:value | Set this value of aggressiveness for this protocol (0 to disable it). This flag can be used multiple times\n" , human_readeable_string_len, min_pattern_len, max_pattern_len, max_num_packets_per_flow, max_packet_payload_dissection, @@ -797,7 +799,7 @@ void printCSVHeader() { */ static void parseOptions(int argc, char **argv) { int option_idx = 0; - int opt; + int opt, i; #ifndef USE_DPDK char *__pcap_file = NULL; int thread_id, do_capture = 0; @@ -818,7 +820,10 @@ static void parseOptions(int argc, char **argv) { } #endif - while((opt = getopt_long(argc, argv, "a:Ab:B:e:Ec:C:dDf:g:i:Ij:k:K:S:hHp:pP:l:r:s:tu:v:V:n:rp:x:w:zq0123:456:7:89:m:MT:U:", + for(i = 0; i < NDPI_MAX_SUPPORTED_PROTOCOLS; i++) + aggressiveness[i] = -1; /* Use the default value */ + + while((opt = getopt_long(argc, argv, "a:Ab:B:e:Ec:C:dDf:g:i:Ij:k:K:S:hHp:pP:l:r:s:tu:v:V:n:rp:x:w:zZ:q0123:456:7:89:m:MT:U:", longopts, &option_idx)) != EOF) { #ifdef DEBUG_TRACE if(trace) fprintf(trace, " #### Handling option -%c [%s] #### \n", opt, optarg ? optarg : ""); @@ -950,6 +955,35 @@ static void parseOptions(int argc, char **argv) { _disabled_protocols = ndpi_strdup(optarg); break; + case 'Z': /* proto_name:aggr_value */ + { + struct ndpi_detection_module_struct *module_tmp; + NDPI_PROTOCOL_BITMASK all; + char *saveptr, *tmp_str, *proto_str, *aggr_str; + + /* Use a temporary module with all protocols enabled */ + module_tmp = ndpi_init_detection_module(0); + if(!module_tmp) + break; + NDPI_BITMASK_SET_ALL(all); + ndpi_set_protocol_detection_bitmask2(module_tmp, &all); + ndpi_finalize_initialization(module_tmp); + + tmp_str = ndpi_strdup(optarg); + if(tmp_str) { + proto_str = strtok_r(tmp_str, ":", &saveptr); + if(proto_str) { + aggr_str = strtok_r(NULL, ":", &saveptr); + if(aggr_str) { + aggressiveness[ndpi_get_protocol_id(module_tmp, proto_str)] = atoi(aggr_str); + } + } + } + ndpi_free(tmp_str); + ndpi_exit_detection_module(module_tmp); + break; + } + case 'h': help(0); break; @@ -2413,6 +2447,7 @@ static void debug_printf(u_int32_t protocol, void *id_struct, static void setupDetection(u_int16_t thread_id, pcap_t * pcap_handle) { NDPI_PROTOCOL_BITMASK enabled_bitmask; struct ndpi_workflow_prefs prefs; + int i; memset(&prefs, 0, sizeof(prefs)); prefs.decode_tunnels = decode_tunnels; @@ -2472,6 +2507,12 @@ static void setupDetection(u_int16_t thread_id, pcap_t * pcap_handle) { NDPI_LRUCACHE_BITTORRENT, 32768); /* Enable/disable LRU caches TTL here */ + /* Set aggressiviness here */ + for(i = 0; i < NDPI_MAX_SUPPORTED_PROTOCOLS; i++) { + if(aggressiveness[i] != -1) + ndpi_set_protocol_aggressiveness(ndpi_thread_info[thread_id].workflow->ndpi_struct, i, aggressiveness[i]); + } + ndpi_finalize_initialization(ndpi_thread_info[thread_id].workflow->ndpi_struct); if(enable_doh_dot_detection) diff --git a/fuzz/fuzz_config.cpp b/fuzz/fuzz_config.cpp index de1bdd3e85d..2e0a27ff4c0 100644 --- a/fuzz/fuzz_config.cpp +++ b/fuzz/fuzz_config.cpp @@ -108,6 +108,11 @@ extern "C" int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) { ndpi_set_opportunistic_tls(ndpi_info_mod, random_proto, random_value); ndpi_get_opportunistic_tls(ndpi_info_mod, random_proto); + for(i = 0; i < NDPI_MAX_SUPPORTED_PROTOCOLS; i++) { + ndpi_set_protocol_aggressiveness(ndpi_info_mod, i, random_value); + ndpi_get_protocol_aggressiveness(ndpi_info_mod, i); + } + ndpi_finalize_initialization(ndpi_info_mod); /* Random protocol configuration */ diff --git a/src/include/ndpi_api.h b/src/include/ndpi_api.h index d1875b5d818..d3b02a4d57a 100644 --- a/src/include/ndpi_api.h +++ b/src/include/ndpi_api.h @@ -1031,6 +1031,11 @@ extern "C" { int ndpi_get_opportunistic_tls(struct ndpi_detection_module_struct *ndpi_struct, u_int16_t proto); + int ndpi_set_protocol_aggressiveness(struct ndpi_detection_module_struct *ndpi_struct, + u_int16_t proto, u_int32_t value); + u_int32_t ndpi_get_protocol_aggressiveness(struct ndpi_detection_module_struct *ndpi_struct, + u_int16_t proto); + /** * Find a protocol id associated with a string automata * diff --git a/src/include/ndpi_typedefs.h b/src/include/ndpi_typedefs.h index 6d560ef36fd..a5b1175bc4f 100644 --- a/src/include/ndpi_typedefs.h +++ b/src/include/ndpi_typedefs.h @@ -659,6 +659,14 @@ struct ndpi_lru_cache { struct ndpi_lru_cache_entry *entries; }; + +/* Aggressiveness values */ + +#define NDPI_AGGRESSIVENESS_DISABLED 0x00 /* For all protocols */ + +/* Ookla */ +#define NDPI_AGGRESSIVENESS_OOKLA_TLS 0x01 /* Enable detection over TLS (using ookla cache) */ + /* ************************************************** */ struct ndpi_flow_tcp_struct { @@ -920,7 +928,8 @@ typedef enum { NDPI_CONFIDENCE_DPI_CACHE, /* Classification results based on some LRU cache (i.e. correlation among sessions) */ NDPI_CONFIDENCE_DPI, /* Deep packet inspection */ NDPI_CONFIDENCE_MATCH_BY_IP, /* Classification obtained looking only at the IP addresses */ - + NDPI_CONFIDENCE_DPI_AGGRESSIVE, /* Aggressive DPI: it might be a false positive */ + /* IMPORTANT @@ -1229,6 +1238,8 @@ struct ndpi_detection_module_struct { int opportunistic_tls_pop_enabled; int opportunistic_tls_ftp_enabled; + u_int32_t aggressiveness_ookla; + u_int16_t ndpi_to_user_proto_id[NDPI_MAX_NUM_CUSTOM_PROTOCOLS]; /* custom protocolId mapping */ ndpi_proto_defaults_t proto_defaults[NDPI_MAX_SUPPORTED_PROTOCOLS+NDPI_MAX_NUM_CUSTOM_PROTOCOLS]; @@ -1563,6 +1574,10 @@ struct ndpi_flow_struct { /* NDPI_PROTOCOL_Z3950 */ u_int8_t z3950_stage : 2; // 0-3 + /* NDPI_PROTOCOL_OOKLA */ + u_int8_t ookla_stage : 1; + + /* NDPI_PROTOCOL_OPENVPN */ u_int8_t ovpn_session_id[8]; u_int8_t ovpn_counter; diff --git a/src/lib/ndpi_main.c b/src/lib/ndpi_main.c index f4266d87d03..dc5834549bc 100644 --- a/src/lib/ndpi_main.c +++ b/src/lib/ndpi_main.c @@ -198,6 +198,10 @@ extern void ndpi_unset_risk(struct ndpi_detection_module_struct *ndpi_str, struct ndpi_flow_struct *flow, ndpi_risk_enum r); extern u_int32_t make_mining_key(struct ndpi_flow_struct *flow); extern int stun_search_into_zoom_cache(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow); +extern void ookla_add_to_cache(struct ndpi_detection_module_struct *ndpi_struct, + struct ndpi_flow_struct *flow); +extern int ookla_search_into_cache(struct ndpi_detection_module_struct *ndpi_struct, + struct ndpi_flow_struct *flow); /* Forward */ static int addDefaultPort(struct ndpi_detection_module_struct *ndpi_str, @@ -2932,7 +2936,7 @@ struct ndpi_detection_module_struct *ndpi_init_detection_module(ndpi_init_prefs ndpi_str->msteams_cache_num_entries = 1024; ndpi_str->stun_zoom_cache_num_entries = 1024; - ndpi_str->ookla_cache_ttl = 0; + ndpi_str->ookla_cache_ttl = 120; /* sec */ ndpi_str->bittorrent_cache_ttl = 0; ndpi_str->zoom_cache_ttl = 0; ndpi_str->stun_cache_ttl = 0; @@ -2946,6 +2950,8 @@ struct ndpi_detection_module_struct *ndpi_init_detection_module(ndpi_init_prefs ndpi_str->opportunistic_tls_pop_enabled = 1; ndpi_str->opportunistic_tls_ftp_enabled = 1; + ndpi_str->aggressiveness_ookla = NDPI_AGGRESSIVENESS_OOKLA_TLS; + for(i = 0; i < NUM_CUSTOM_CATEGORIES; i++) ndpi_snprintf(ndpi_str->custom_category_labels[i], CUSTOM_CATEGORY_LABEL_LEN, "User custom category %u", (unsigned int) (i + 1)); @@ -6254,6 +6260,13 @@ ndpi_protocol ndpi_detection_giveup(struct ndpi_detection_module_struct *ndpi_st ret.app_protocol = flow->detected_protocol_stack[0]; } + /* Does it looks like Ookla? */ + if(ret.app_protocol == NDPI_PROTOCOL_UNKNOWN && + ntohs(flow->s_port) == 8080 && ookla_search_into_cache(ndpi_str, flow)) { + ndpi_set_detected_protocol(ndpi_str, flow, NDPI_PROTOCOL_OOKLA, NDPI_PROTOCOL_UNKNOWN, NDPI_CONFIDENCE_DPI_PARTIAL_CACHE); + ret.app_protocol = flow->detected_protocol_stack[0]; + } + /* Classification by-port is the last resort */ if(enable_guess && ret.app_protocol == NDPI_PROTOCOL_UNKNOWN) { @@ -8052,6 +8065,9 @@ const char *ndpi_confidence_get_name(ndpi_confidence_t confidence) case NDPI_CONFIDENCE_MATCH_BY_IP: return "Match by IP"; + case NDPI_CONFIDENCE_DPI_AGGRESSIVE: + return "DPI (aggressive)"; + default: return NULL; } @@ -8572,6 +8588,11 @@ int ndpi_match_hostname_protocol(struct ndpi_detection_module_struct *ndpi_struc ndpi_set_detected_protocol(ndpi_struct, flow, subproto, master_protocol, NDPI_CONFIDENCE_DPI); if(!category_depends_on_master(master_protocol)) ndpi_int_change_category(ndpi_struct, flow, ret_match.protocol_category); + + if(subproto == NDPI_PROTOCOL_OOKLA) { + ookla_add_to_cache(ndpi_struct, flow); + } + return(1); } else return(0); @@ -9643,3 +9664,36 @@ int ndpi_get_opportunistic_tls(struct ndpi_detection_module_struct *ndpi_struct, return -1; } } + +/* ******************************************************************** */ + +int ndpi_set_protocol_aggressiveness(struct ndpi_detection_module_struct *ndpi_struct, + u_int16_t proto, u_int32_t value) +{ + if(!ndpi_struct) + return -1; + + switch(proto) { + case NDPI_PROTOCOL_OOKLA: + ndpi_struct->aggressiveness_ookla = value; + return 0; + default: + return -1; + } +} + +/* ******************************************************************** */ + +u_int32_t ndpi_get_protocol_aggressiveness(struct ndpi_detection_module_struct *ndpi_struct, + u_int16_t proto) +{ + if(!ndpi_struct) + return -1; + + switch(proto) { + case NDPI_PROTOCOL_OOKLA: + return ndpi_struct->aggressiveness_ookla; + default: + return -1; + } +} diff --git a/src/lib/protocols/http.c b/src/lib/protocols/http.c index e0f56c4e804..4f139b8d318 100644 --- a/src/lib/protocols/http.c +++ b/src/lib/protocols/http.c @@ -46,6 +46,9 @@ static const char* binary_file_ext[] = { NULL }; +extern void ookla_add_to_cache(struct ndpi_detection_module_struct *ndpi_struct, + struct ndpi_flow_struct *flow); + static void ndpi_search_http_tcp(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow); @@ -436,6 +439,7 @@ static void ndpi_http_parse_subprotocol(struct ndpi_detection_module_struct *ndp || (strstr(flow->http.url, ":8080/upload?n=0.") != NULL))) { /* This looks like Ookla speedtest */ ndpi_set_detected_protocol(ndpi_struct, flow, NDPI_PROTOCOL_OOKLA, master_protocol, NDPI_CONFIDENCE_DPI); + ookla_add_to_cache(ndpi_struct, flow); } } @@ -1217,30 +1221,6 @@ static void ndpi_check_http_tcp(struct ndpi_detection_module_struct *ndpi_struct return; } - if((packet->payload_packet_len == 3) && memcmp(packet->payload, "HI\n", 3) == 0) { - /* This looks like Ookla: we don't give up with HTTP yet */ - flow->l4.tcp.http_stage = 1; - return; - } - - if((packet->payload_packet_len == 40) && (flow->l4.tcp.http_stage == 0)) { - /* - -> QR O06L0072-6L91-4O43-857J-K8OO172L6L51 - <- QNUUX 2.5 2017-08-15.1314.4jn12m5 - -> MXFWUXJM 31625365 - */ - - if((packet->payload[2] == ' ') - && (packet->payload[11] == '-') - && (packet->payload[16] == '-') - && (packet->payload[21] == '-') - && (packet->payload[26] == '-') - && (packet->payload[39] == 0x0A) - ) - flow->l4.tcp.http_stage = 1; - return; - } - if((packet->payload_packet_len == 23) && (memcmp(packet->payload, "", 23) == 0)) { /* @@ -1251,25 +1231,7 @@ static void ndpi_check_http_tcp(struct ndpi_detection_module_struct *ndpi_struct */ ookla_found: ndpi_int_http_add_connection(ndpi_struct, flow, NDPI_PROTOCOL_OOKLA, NDPI_PROTOCOL_CATEGORY_WEB); - - if(ndpi_struct->ookla_cache != NULL) { - if(packet->iph != NULL) { - if(packet->tcp->source == htons(8080)) - ndpi_lru_add_to_cache(ndpi_struct->ookla_cache, packet->iph->saddr, 1 /* dummy */, ndpi_get_current_time(flow)); - else - ndpi_lru_add_to_cache(ndpi_struct->ookla_cache, packet->iph->daddr, 1 /* dummy */, ndpi_get_current_time(flow)); - } else if(packet->iphv6 != NULL) { - u_int32_t h; - - if(packet->tcp->source == htons(8080)) - h = ndpi_quick_hash((unsigned char *)&packet->iphv6->ip6_src, sizeof(packet->iphv6->ip6_src)); - else - h = ndpi_quick_hash((unsigned char *)&packet->iphv6->ip6_dst, sizeof(packet->iphv6->ip6_dst)); - - ndpi_lru_add_to_cache(ndpi_struct->ookla_cache, h, 1 /* dummy */, ndpi_get_current_time(flow)); - } - } - + ookla_add_to_cache(ndpi_struct, flow); return; } @@ -1389,18 +1351,6 @@ static void ndpi_check_http_tcp(struct ndpi_detection_module_struct *ndpi_struct } else if((flow->l4.tcp.http_stage == 1) || (flow->l4.tcp.http_stage == 2)) { NDPI_LOG_DBG2(ndpi_struct, "HTTP stage %u: \n", flow->l4.tcp.http_stage); - if((packet->payload_packet_len == 34) && (flow->l4.tcp.http_stage == 1)) { - if((packet->payload[5] == ' ') && (packet->payload[9] == ' ')) { - goto ookla_found; - } - } - - if((packet->payload_packet_len > 6) && memcmp(packet->payload, "HELLO ", 6) == 0) { - /* This looks like Ookla */ - goto ookla_found; - } else - NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask, NDPI_PROTOCOL_OOKLA); - /** At first check, if this is for sure a response packet (in another direction. If not, if HTTP is detected do nothing now and return, diff --git a/src/lib/protocols/ookla.c b/src/lib/protocols/ookla.c index 0da42212cca..d7764e630fa 100644 --- a/src/lib/protocols/ookla.c +++ b/src/lib/protocols/ookla.c @@ -23,111 +23,92 @@ #include "ndpi_api.h" +/* #define DEBUG_OOKLA_LRU */ + const u_int16_t ookla_port = 8080; /* ************************************************************* */ -static void ndpi_search_ookla(struct ndpi_detection_module_struct* ndpi_struct, struct ndpi_flow_struct* flow) { - struct ndpi_packet_struct* packet = &ndpi_struct->packet; - u_int32_t addr = 0; - u_int16_t sport, dport; - - NDPI_LOG_DBG(ndpi_struct, "Ookla detection\n"); - - if(packet->tcp) - sport = ntohs(packet->tcp->source), dport = htons(packet->tcp->dest); +static u_int32_t get_ookla_key(struct ndpi_flow_struct *flow) +{ + if(flow->is_ipv6) + return ndpi_quick_hash(flow->c_address.v6, 16); else - sport = ntohs(packet->udp->source), dport = htons(packet->udp->dest); + return ntohl(flow->c_address.v4); +} - if((sport != ookla_port) && (dport != ookla_port)) { -#ifdef OOKLA_DEBUG - printf("=>>>>>>>> [OOKLA IPv6] Skipping flow [%u -> %u]\n", sport, dport); -#endif - goto ookla_exclude; - } - - if(packet->iphv6 != NULL) { - if((dport == ookla_port) && (packet->payload_packet_len >= 3)) { - u_int32_t h; - - if((packet->payload_packet_len == 3) - && (packet->payload[0] == 0x48) /* HI\n */ - && (packet->payload[1] == 0x49) - && (packet->payload[2] == 0x0A)) { - ndpi_set_detected_protocol(ndpi_struct, flow, NDPI_PROTOCOL_OOKLA, NDPI_PROTOCOL_UNKNOWN, NDPI_CONFIDENCE_DPI); - - if(ndpi_struct->ookla_cache != NULL) { - /* In order to avoid creating an IPv6 LRU we hash the IPv6 address */ - h = ndpi_quick_hash((unsigned char *)&packet->iphv6->ip6_dst, sizeof(packet->iphv6->ip6_dst)); - -#ifdef OOKLA_DEBUG - printf("=>>>>>>>> [OOKLA IPv6] Adding %u\n", h); -#endif - ndpi_lru_add_to_cache(ndpi_struct->ookla_cache, h, 1 /* dummy */, ndpi_get_current_time(flow)); - } - return; - } else { - if(sport == ookla_port) - h = ndpi_quick_hash((unsigned char *)&packet->iphv6->ip6_src, sizeof(packet->iphv6->ip6_src)); - else - h = ndpi_quick_hash((unsigned char *)&packet->iphv6->ip6_dst, sizeof(packet->iphv6->ip6_dst)); - - if(ndpi_struct->ookla_cache != NULL) { - u_int16_t dummy; - -#ifdef OOKLA_DEBUG - printf("=>>>>>>>> [OOKLA IPv6] Searching %u\n", h); -#endif - - if(ndpi_lru_find_cache(ndpi_struct->ookla_cache, h, &dummy, 0 /* Don't remove it as it can be used for other connections */, - ndpi_get_current_time(flow))) { - NDPI_LOG_INFO(ndpi_struct, "found ookla tcp connection\n"); - ndpi_set_detected_protocol(ndpi_struct, flow, NDPI_PROTOCOL_OOKLA, NDPI_PROTOCOL_UNKNOWN, NDPI_CONFIDENCE_DPI_CACHE); -#ifdef OOKLA_DEBUG - printf("=>>>>> Found %u\n", h); -#endif - return; - } else { -#ifdef OOKLA_DEBUG - printf("=>>>>> NOT Found %u\n", h); -#endif - } - } - } - } else { +/* ************************************************************* */ - goto ookla_exclude; - } - } else { - if(sport == ookla_port) - addr = packet->iph->saddr; - else - addr = packet->iph->daddr; - -#ifdef OOKLA_DEBUG - printf("=>>>>>>>> [OOKLA IPv4] Searching %u\n", addr); -#endif - - if(ndpi_struct->ookla_cache != NULL) { - u_int16_t dummy; - - if(ndpi_lru_find_cache(ndpi_struct->ookla_cache, addr, &dummy, 0 /* Don't remove it as it can be used for other connections */, - ndpi_get_current_time(flow))) { - NDPI_LOG_INFO(ndpi_struct, "found ookla tcp connection\n"); - ndpi_set_detected_protocol(ndpi_struct, flow, NDPI_PROTOCOL_OOKLA, NDPI_PROTOCOL_UNKNOWN, NDPI_CONFIDENCE_DPI_CACHE); -#ifdef OOKLA_DEBUG - printf("=>>>>> Found %u\n", addr); +int ookla_search_into_cache(struct ndpi_detection_module_struct *ndpi_struct, + struct ndpi_flow_struct *flow) +{ + u_int32_t key; + u_int16_t dummy; + + if(ndpi_struct->ookla_cache) { + key = get_ookla_key(flow); +#ifdef DEBUG_OOKLA_LRU + printf("[LRU OOKLA] Search %u\n", key); #endif - return; - } else { -#ifdef OOKLA_DEBUG - printf("=>>>>> NOT Found %u\n", addr); + + if(ndpi_lru_find_cache(ndpi_struct->ookla_cache, key, + &dummy, 0 /* Don't remove it as it can be used for other connections */, + ndpi_get_current_time(flow))) { +#ifdef DEBUG_OOKLA_LRU + printf("[LRU OOKLA] Found\n"); #endif - } + return 1; } } + return 0; +} + +/* ************************************************************* */ + +void ookla_add_to_cache(struct ndpi_detection_module_struct *ndpi_struct, + struct ndpi_flow_struct *flow) +{ + u_int32_t key; + + if(ndpi_struct->ookla_cache) { + key = get_ookla_key(flow); +#ifdef DEBUG_OOKLA_LRU + printf("[LRU OOKLA] ADDING %u\n", key); +#endif + ndpi_lru_add_to_cache(ndpi_struct->ookla_cache, key, 1 /* dummy */, + ndpi_get_current_time(flow)); + } + +} + +/* ************************************************************* */ + +void ndpi_search_ookla(struct ndpi_detection_module_struct* ndpi_struct, struct ndpi_flow_struct* flow) { + struct ndpi_packet_struct *packet = &ndpi_struct->packet; + + NDPI_LOG_DBG(ndpi_struct, "Ookla detection\n"); + + if(ntohs(flow->s_port) != ookla_port && ntohs(flow->c_port) != ookla_port) { + NDPI_EXCLUDE_PROTO(ndpi_struct, flow); + return; + } + + if(flow->packet_counter == 1 && + packet->payload_packet_len >= NDPI_STATICSTRING_LEN("HI") && + memcmp(packet->payload, "HI", NDPI_STATICSTRING_LEN("HI")) == 0) { + flow->ookla_stage = 1; + return; + } + if(flow->packet_counter == 2 && + flow->ookla_stage == 1 && + packet->payload_packet_len >= NDPI_STATICSTRING_LEN("HELLO") && + memcmp(packet->payload, "HELLO", NDPI_STATICSTRING_LEN("HELLO")) == 0) { + NDPI_LOG_INFO(ndpi_struct, "found ookla (Hi + Hello)\n"); + ndpi_set_detected_protocol(ndpi_struct, flow, NDPI_PROTOCOL_OOKLA, NDPI_PROTOCOL_UNKNOWN, NDPI_CONFIDENCE_DPI); + ookla_add_to_cache(ndpi_struct, flow); + return; + } - ookla_exclude: NDPI_EXCLUDE_PROTO(ndpi_struct, flow); } diff --git a/src/lib/protocols/tls.c b/src/lib/protocols/tls.c index 8e3fbedb823..58b19d0d5f2 100644 --- a/src/lib/protocols/tls.c +++ b/src/lib/protocols/tls.c @@ -33,6 +33,8 @@ extern int processClientServerHello(struct ndpi_detection_module_struct *ndpi_st extern int http_process_user_agent(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow, const u_int8_t *ua_ptr, u_int16_t ua_ptr_len); +extern int ookla_search_into_cache(struct ndpi_detection_module_struct* ndpi_struct, + struct ndpi_flow_struct* flow); /* QUIC/GQUIC stuff */ extern int quic_len(const uint8_t *buf, uint64_t *value); extern int quic_len_buffer_still_required(uint8_t value); @@ -1153,8 +1155,27 @@ static int ndpi_search_tls_tcp(struct ndpi_detection_module_struct *ndpi_struct, #ifdef DEBUG_TLS_BLOCKS printf("*** [TLS Block] No more blocks\n"); #endif - flow->extra_packets_func = NULL; - return(0); /* That's all */ + /* An ookla flow? */ + if((ndpi_struct->aggressiveness_ookla & NDPI_AGGRESSIVENESS_OOKLA_TLS) && /* Feature enabled */ + (!something_went_wrong && + flow->tls_quic.certificate_processed == 1 && + flow->protos.tls_quic.hello_processed == 1) && /* TLS handshake found without errors */ + flow->detected_protocol_stack[0] == NDPI_PROTOCOL_TLS && /* No IMAPS/FTPS/... */ + flow->detected_protocol_stack[1] == NDPI_PROTOCOL_UNKNOWN && /* No sub-classification */ + ntohs(flow->s_port) == 8080 && /* Ookla port */ + ookla_search_into_cache(ndpi_struct, flow)) { + NDPI_LOG_INFO(ndpi_struct, "found ookla (cache over TLS)\n"); + /* Even if a LRU cache is involved, NDPI_CONFIDENCE_DPI_AGGRESSIVE seems more + suited than NDPI_CONFIDENCE_DPI_CACHE */ + ndpi_set_detected_protocol(ndpi_struct, flow, NDPI_PROTOCOL_OOKLA, NDPI_PROTOCOL_TLS, NDPI_CONFIDENCE_DPI_AGGRESSIVE); + /* TLS over port 8080 usually triggers that risk; clear it */ + ndpi_unset_risk(ndpi_struct, flow, NDPI_KNOWN_PROTOCOL_ON_NON_STANDARD_PORT); + flow->extra_packets_func = NULL; + return(0); /* That's all */ + } else { + flow->extra_packets_func = NULL; + return(0); /* That's all */ + } } else return(1); } diff --git a/tests/pcap/ookla.pcap b/tests/pcap/ookla.pcap index 80123e85605ede23f4c8ca124685560a14d7e106..ac57c6d17656676169d23216f858b1d773ec80a3 100644 GIT binary patch literal 42424 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 delta 837 zcmYL{T}V@59LC?RRj1k)O{<-gXxni+`#NWo1!+WRn{)!j2^PVqNbq(y-gJ{!3K4|8 zu!~5T2z4VgI?g^si?*(Wj0lQAi!=-`%ImKBe+=^O`JLbMyzh?Z#j1O`yW>;+*{oZ5 z#Q#5!a6wr3_3diu?ja$ofe{76y5<$KBUqqt=QxB5ZK`}6%o0%By~5cIR$P?qF`tm% zbxqa}TLkpmKH+#nAvdLakf>c~<@Wd#fJ#_(7F!?jLM`eSvZQIw)X|4b26P~Jm@Q_uRa(gXj99K8CRoDR0gX}ycI$;=*Hwn=#pVHA{6Ih1IT#m-?;j+mg}(vQw8 z0e=I)L|m2mSRa8Wmpt$alA3%S>t(|RfR!_Gu6P#!OvH=ybf9N1>mh^ncL+*`O;7VL z_wo8~gV*Q!_Om{gVEx!d0Jy%9;PreJ0A8p!$(6rn6|6Lm>xO{($rS6WxdW`1Q>>@f z0O0)tX+EKh04tMeuB1;N6!Jrw2e+0XpnfaE`rrzHHyOTvc?dpUyv%u%*LOYxK>fMN c`i(Em&)c+kef 46.44.253.187:80 [proto: 7.191/HTTP.Ookla][IP: 0/Unknown][ClearText][Confidence: DPI][DPI packets: 12][cat: Network/14][12 pkts/2238 bytes <-> 8 pkts/2082 bytes][Goodput ratio: 64/74][5.33 sec][bytes ratio: 0.036 (Mixed)][IAT c2s/s2c min/avg/max/stddev: 0/4 528/47 5005/84 1493/28][Pkt Len c2s/s2c min/avg/max/stddev: 66/66 186/260 430/523 168/194][Risk: ** HTTP Susp User-Agent **** HTTP Obsolete Server **][Risk Score: 150][Risk Info: Obsolete Apache server 2.2.22 / Empty or missing User-Agent][PLAIN TEXT (GET /crossdomain.xml HTTP/1.1)][Plen Bins: 0,0,0,0,0,0,0,0,0,0,12,75,0,0,12,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0] - 2 TCP 192.168.1.7:51215 <-> 46.44.253.187:8080 [proto: 191/Ookla][IP: 0/Unknown][ClearText][Confidence: DPI (cache)][DPI packets: 4][cat: Network/14][19 pkts/1421 bytes <-> 11 pkts/920 bytes][Goodput ratio: 11/20][0.80 sec][bytes ratio: 0.214 (Upload)][IAT c2s/s2c min/avg/max/stddev: 26/0 44/75 103/137 23/41][Pkt Len c2s/s2c min/avg/max/stddev: 66/66 75/84 85/100 9/8][PLAIN TEXT ( 6HELLO 2.4 2016)][Plen Bins: 94,5,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0] +JA3 Host Stats: + IP Address # JA3C + 1 192.168.1.128 2 + + + 1 TCP 192.168.1.128:35830 <-> 89.96.108.170:8080 [proto: 91.191/TLS.Ookla][IP: 0/Unknown][Encrypted][Confidence: DPI (aggressive)][DPI packets: 6][cat: Web/5][21 pkts/21216 bytes <-> 8 pkts/1950 bytes][Goodput ratio: 93/72][0.32 sec][Hostname/SNI: spd-pub-mi-01-01.fastwebnet.it][(Advertised) ALPNs: h2;http/1.1][TLS Supported Versions: TLSv1.3;TLSv1.2][bytes ratio: 0.832 (Upload)][IAT c2s/s2c min/avg/max/stddev: 0/0 17/61 274/280 62/109][Pkt Len c2s/s2c min/avg/max/stddev: 66/66 1010/244 1514/387 612/138][TLSv1.3][JA3C: c279b0189edb9269da7bc43dea5e0c36][JA3S: fcb2d4d0991292272fcb1e464eedfd43][Firefox][Cipher: TLS_AES_128_GCM_SHA256][Plen Bins: 0,0,4,0,0,0,0,4,9,0,9,0,0,0,0,0,4,0,0,13,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,55,0,0] + 2 TCP 192.168.1.128:48854 <-> 104.16.209.12:443 [proto: 91.191/TLS.Ookla][IP: 220/Cloudflare][Encrypted][Confidence: DPI][DPI packets: 6][cat: Network/14][8 pkts/1620 bytes <-> 6 pkts/3818 bytes][Goodput ratio: 67/89][0.06 sec][Hostname/SNI: www.speedtest.net][(Advertised) ALPNs: h2;http/1.1][TLS Supported Versions: TLSv1.3;TLSv1.2][bytes ratio: -0.404 (Download)][IAT c2s/s2c min/avg/max/stddev: 0/0 7/5 18/15 7/6][Pkt Len c2s/s2c min/avg/max/stddev: 66/66 202/636 583/1514 181/646][TLSv1.3][JA3C: 579ccef312d18482fc42e2b822ca2430][JA3S: eb1d94daa7e0344597e756a1fb6e7054][Firefox][Cipher: TLS_AES_128_GCM_SHA256][PLAIN TEXT (@oTAgOeedtest.net)][Plen Bins: 0,0,14,0,0,14,0,0,0,0,14,0,0,0,0,0,28,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,28,0,0] + 3 TCP 192.168.1.7:51207 <-> 46.44.253.187:80 [proto: 7.191/HTTP.Ookla][IP: 0/Unknown][ClearText][Confidence: DPI][DPI packets: 12][cat: Network/14][12 pkts/2238 bytes <-> 8 pkts/2082 bytes][Goodput ratio: 64/74][5.33 sec][bytes ratio: 0.036 (Mixed)][IAT c2s/s2c min/avg/max/stddev: 0/4 528/47 5005/84 1493/28][Pkt Len c2s/s2c min/avg/max/stddev: 66/66 186/260 430/523 168/194][Risk: ** HTTP Susp User-Agent **** HTTP Obsolete Server **][Risk Score: 150][Risk Info: Obsolete Apache server 2.2.22 / Empty or missing User-Agent][PLAIN TEXT (GET /crossdomain.xml HTTP/1.1)][Plen Bins: 0,0,0,0,0,0,0,0,0,0,12,75,0,0,12,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0] + 4 TCP 192.168.1.192:51156 <-> 89.96.108.170:8080 [proto: 191/Ookla][IP: 0/Unknown][ClearText][Confidence: DPI (partial cache)][DPI packets: 10][cat: Network/14][6 pkts/591 bytes <-> 4 pkts/1784 bytes][Goodput ratio: 32/85][0.05 sec][bytes ratio: -0.502 (Download)][IAT c2s/s2c min/avg/max/stddev: 0/0 9/10 15/20 6/8][Pkt Len c2s/s2c min/avg/max/stddev: 66/66 98/446 143/1514 31/617][PLAIN TEXT (gKRZvA)][Plen Bins: 0,40,40,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,20,0,0] + 5 TCP 192.168.1.7:51215 <-> 46.44.253.187:8080 [proto: 191/Ookla][IP: 0/Unknown][ClearText][Confidence: DPI][DPI packets: 6][cat: Network/14][19 pkts/1421 bytes <-> 11 pkts/920 bytes][Goodput ratio: 11/20][0.80 sec][bytes ratio: 0.214 (Upload)][IAT c2s/s2c min/avg/max/stddev: 26/0 44/75 103/137 23/41][Pkt Len c2s/s2c min/avg/max/stddev: 66/66 75/84 85/100 9/8][PLAIN TEXT ( 6HELLO 2.4 2016)][Plen Bins: 94,5,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0] + 6 TCP 192.168.1.192:37790 <-> 185.157.229.246:8080 [proto: 191/Ookla][IP: 0/Unknown][ClearText][Confidence: DPI][DPI packets: 6][cat: Network/14][6 pkts/454 bytes <-> 4 pkts/317 bytes][Goodput ratio: 11/14][0.06 sec][bytes ratio: 0.178 (Mixed)][IAT c2s/s2c min/avg/max/stddev: 0/0 12/5 46/9 17/4][Pkt Len c2s/s2c min/avg/max/stddev: 66/66 76/79 106/108 14/17][PLAIN TEXT (HELLO 2.9 )][Plen Bins: 50,50,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0] diff --git a/tests/result/skype.pcap.out b/tests/result/skype.pcap.out index 5091e3a4e5f..d26ba706f76 100644 --- a/tests/result/skype.pcap.out +++ b/tests/result/skype.pcap.out @@ -7,7 +7,7 @@ Confidence Unknown : 59 (flows) Confidence Match by port : 27 (flows) Confidence DPI (partial) : 1 (flows) Confidence DPI : 206 (flows) -Num dissector calls: 26899 (91.81 diss/flow) +Num dissector calls: 26897 (91.80 diss/flow) LRU cache ookla: 0/0/0 (insert/search/found) LRU cache bittorrent: 0/261/0 (insert/search/found) LRU cache zoom: 0/0/0 (insert/search/found) diff --git a/tests/result/skype_no_unknown.pcap.out b/tests/result/skype_no_unknown.pcap.out index be90096f61e..328c50280ed 100644 --- a/tests/result/skype_no_unknown.pcap.out +++ b/tests/result/skype_no_unknown.pcap.out @@ -6,7 +6,7 @@ DPI Packets (other): 5 (1.00 pkts/flow) Confidence Unknown : 44 (flows) Confidence Match by port : 22 (flows) Confidence DPI : 201 (flows) -Num dissector calls: 22405 (83.91 diss/flow) +Num dissector calls: 22404 (83.91 diss/flow) LRU cache ookla: 0/0/0 (insert/search/found) LRU cache bittorrent: 0/198/0 (insert/search/found) LRU cache zoom: 0/0/0 (insert/search/found) diff --git a/tests/result/synscan.pcap.out b/tests/result/synscan.pcap.out index 9932b97b2e1..3bdf713b463 100644 --- a/tests/result/synscan.pcap.out +++ b/tests/result/synscan.pcap.out @@ -4,7 +4,7 @@ DPI Packets (TCP): 2011 (1.01 pkts/flow) Confidence Unknown : 1862 (flows) Confidence Match by port : 132 (flows) Num dissector calls: 0 (0.00 diss/flow) -LRU cache ookla: 0/0/0 (insert/search/found) +LRU cache ookla: 0/2/0 (insert/search/found) LRU cache bittorrent: 0/5976/0 (insert/search/found) LRU cache zoom: 0/0/0 (insert/search/found) LRU cache stun: 0/0/0 (insert/search/found)