diff options
author | Luca Deri <deri@ntop.org> | 2019-09-17 00:11:17 +0200 |
---|---|---|
committer | Luca Deri <deri@ntop.org> | 2019-09-17 00:11:17 +0200 |
commit | 64ed0ac6b33744263e7a05010db366efa925eea1 (patch) | |
tree | 1f576617ebc2999991cb2ad09ca6f960b16883c4 /src/lib | |
parent | 8f4e8d8254d79404e9b9490f9ab9bb5296194d68 (diff) |
Various STUN improvements
Diffstat (limited to 'src/lib')
-rw-r--r-- | src/lib/protocols/stun.c | 100 | ||||
-rw-r--r-- | src/lib/protocols/tls.c | 12 |
2 files changed, 75 insertions, 37 deletions
diff --git a/src/lib/protocols/stun.c b/src/lib/protocols/stun.c index 0ab3ed805..76a75fb8d 100644 --- a/src/lib/protocols/stun.c +++ b/src/lib/protocols/stun.c @@ -30,10 +30,8 @@ #define MAX_NUM_STUN_PKTS 8 -#if 0 -#define DEBUG_STUN 1 -#define DEBUG_LRU 1 -#endif +// #define DEBUG_STUN 1 +// #define DEBUG_LRU 1 struct stun_packet_header { u_int16_t msg_type, msg_len; @@ -52,9 +50,9 @@ u_int32_t get_stun_lru_key(struct ndpi_flow_struct *flow, u_int8_t rev) { /* ************************************************************ */ -static void ndpi_int_stun_add_connection(struct ndpi_detection_module_struct *ndpi_struct, - struct ndpi_flow_struct *flow, - u_int app_proto, u_int proto) { +void ndpi_int_stun_add_connection(struct ndpi_detection_module_struct *ndpi_struct, + struct ndpi_flow_struct *flow, + u_int app_proto, u_int proto) { if(ndpi_struct->stun_cache == NULL) ndpi_struct->stun_cache = ndpi_lru_cache_init(1024); @@ -62,24 +60,40 @@ static void ndpi_int_stun_add_connection(struct ndpi_detection_module_struct *nd && flow->packet.iph && flow->packet.udp && (app_proto != NDPI_PROTOCOL_UNKNOWN) - ) /* Cache flow sender info */ { + ) /* Cache flow sender info */ { u_int32_t key = get_stun_lru_key(flow, 0); u_int16_t cached_proto; - - if(ndpi_lru_find_cache(ndpi_struct->stun_cache, key, &cached_proto, 0 /* Don't remove it as it can be used for other connections */)) { + + if(ndpi_lru_find_cache(ndpi_struct->stun_cache, key, + &cached_proto, 0 /* Don't remove it as it can be used for other connections */)) { #ifdef DEBUG_LRU printf("[LRU] FOUND %u / %u: no need to cache %u.%u\n", key, cached_proto, proto, app_proto); #endif - app_proto = cached_proto, proto = NDPI_PROTOCOL_STUN; - } else { + app_proto = cached_proto, proto = NDPI_PROTOCOL_STUN; + } else { + u_int32_t key1 = get_stun_lru_key(flow, 1); + + if(ndpi_lru_find_cache(ndpi_struct->stun_cache, key1, + &cached_proto, 0 /* Don't remove it as it can be used for other connections */)) { +#ifdef DEBUG_LRU + printf("[LRU] FOUND %u / %u: no need to cache %u.%u\n", key1, cached_proto, proto, app_proto); +#endif + app_proto = cached_proto, proto = NDPI_PROTOCOL_STUN; + } else { + if(app_proto != NDPI_PROTOCOL_STUN) { + /* No sense to ass STUN, but only subprotocols */ + #ifdef DEBUG_LRU - printf("[LRU] ADDING %u / %u.%u\n", key, proto, app_proto); + printf("[LRU] ADDING %u / %u.%u [%u -> %u]\n", key, proto, app_proto, + ntohs(flow->packet.udp->source), ntohs(flow->packet.udp->dest)); #endif - - ndpi_lru_add_to_cache(ndpi_struct->stun_cache, key, app_proto); + + ndpi_lru_add_to_cache(ndpi_struct->stun_cache, key, app_proto); + } + } } } - + ndpi_set_detected_protocol(ndpi_struct, flow, app_proto, proto); } @@ -174,7 +188,7 @@ static ndpi_int_stun_t ndpi_int_check_stun(struct ndpi_detection_module_struct * ) printf("[STUN] Here we go\n");; #endif - + if(ndpi_struct->stun_cache) { u_int16_t proto; u_int32_t key = get_stun_lru_key(flow, 0); @@ -186,18 +200,18 @@ static ndpi_int_stun_t ndpi_int_check_stun(struct ndpi_detection_module_struct * if(!rc) { key = get_stun_lru_key(flow, 1); - rc = ndpi_lru_find_cache(ndpi_struct->stun_cache, key, &proto, 0 /* Don't remove it as it can be used for other connections */); + rc = ndpi_lru_find_cache(ndpi_struct->stun_cache, key, &proto, 0 /* Don't remove it as it can be used for other connections */); #ifdef DEBUG_LRU printf("[LRU] Searching %u\n", key); #endif } - + if(rc) { #ifdef DEBUG_LRU printf("[LRU] Cache FOUND %u / %u\n", key, proto); #endif - + flow->guessed_host_protocol_id = proto, flow->guessed_protocol_id = NDPI_PROTOCOL_STUN; switch(proto) { @@ -214,19 +228,19 @@ static ndpi_int_stun_t ndpi_int_check_stun(struct ndpi_detection_module_struct * flow->protos.stun_ssl.stun.is_skype = 1; break; } - + return(NDPI_IS_STUN); } else { #ifdef DEBUG_LRU printf("[LRU] NOT FOUND %u\n", key); -#endif - } +#endif + } } else { #ifdef DEBUG_LRU printf("[LRU] NO/EMPTY CACHE\n"); #endif } - + if(msg_type == 0x01 /* Binding Request */) { flow->protos.stun_ssl.stun.num_binding_requests++; @@ -235,10 +249,10 @@ static ndpi_int_stun_t ndpi_int_check_stun(struct ndpi_detection_module_struct * else flow->guessed_host_protocol_id = NDPI_PROTOCOL_STUN; - flow->protos.stun_ssl.stun.num_udp_pkts++; - - if(msg_len == 0) + if(msg_len == 0) { + flow->protos.stun_ssl.stun.num_udp_pkts++; return(NDPI_IS_NOT_STUN); /* This to keep analyzing STUN instead of giving up */ + } } if((msg_len == 0) && (flow->guessed_host_protocol_id == NDPI_PROTOCOL_UNKNOWN)) { @@ -330,10 +344,17 @@ static ndpi_int_stun_t ndpi_int_check_stun(struct ndpi_detection_module_struct * for(j=0; j<i; j++) flow->host_server_name[j] = payload[k++]; +#ifdef DEBUG_STUN + printf("==> [%s]\n", flow->host_server_name); +#endif + if(strstr((char*)flow->host_server_name, "google.com") != NULL) { *is_duo = 1; flow->guessed_host_protocol_id = NDPI_PROTOCOL_HANGOUT_DUO, flow->guessed_protocol_id = NDPI_PROTOCOL_STUN; return(NDPI_IS_STUN); + } else if(strstr((char*)flow->host_server_name, "whispersystems.org") != NULL) { + flow->guessed_host_protocol_id = NDPI_PROTOCOL_SIGNAL, flow->guessed_protocol_id = NDPI_PROTOCOL_STUN; + return(NDPI_IS_STUN); } } } @@ -345,13 +366,15 @@ static ndpi_int_stun_t ndpi_int_check_stun(struct ndpi_detection_module_struct * *is_messenger = 1; return(NDPI_IS_STUN); } else if(msg_len == 76) { +#if 0 *is_duo = 1; - + if(1) { flow->guessed_host_protocol_id = NDPI_PROTOCOL_HANGOUT_DUO, flow->guessed_protocol_id = NDPI_PROTOCOL_STUN; return(NDPI_IS_NOT_STUN); /* This case is found also with signal traffic */ } else return(NDPI_IS_STUN); +#endif } } break; @@ -442,7 +465,8 @@ static ndpi_int_stun_t ndpi_int_check_stun(struct ndpi_detection_module_struct * udp_stun_found: if(can_this_be_whatsapp_voice) { struct ndpi_packet_struct *packet = &flow->packet; - + int rc; + flow->protos.stun_ssl.stun.num_processed_pkts++; #ifdef DEBUG_STUN printf("==>> NDPI_PROTOCOL_WHATSAPP_VOICE\n"); @@ -454,7 +478,13 @@ static ndpi_int_stun_t ndpi_int_check_stun(struct ndpi_detection_module_struct * } else flow->guessed_host_protocol_id = (is_google_ip_address(ntohl(packet->iph->saddr)) || is_google_ip_address(ntohl(packet->iph->daddr))) ? NDPI_PROTOCOL_HANGOUT_DUO : NDPI_PROTOCOL_WHATSAPP_VOICE; - return((flow->protos.stun_ssl.stun.num_udp_pkts < MAX_NUM_STUN_PKTS) ? NDPI_IS_NOT_STUN : NDPI_IS_STUN); + + rc = (flow->protos.stun_ssl.stun.num_udp_pkts < MAX_NUM_STUN_PKTS) ? NDPI_IS_NOT_STUN : NDPI_IS_STUN; + + if(rc == NDPI_IS_STUN) + ndpi_int_stun_add_connection(ndpi_struct, flow, flow->guessed_host_protocol_id, NDPI_IS_STUN); + + return(rc); } else { /* We cannot immediately say that this is STUN as there are other protocols @@ -497,11 +527,14 @@ void ndpi_search_stun(struct ndpi_detection_module_struct *ndpi_struct, struct n } else if(is_duo) { ndpi_int_stun_add_connection(ndpi_struct, flow, NDPI_PROTOCOL_HANGOUT_DUO, NDPI_PROTOCOL_STUN); return; + } else if(flow->guessed_host_protocol_id == NDPI_PROTOCOL_SIGNAL) { + ndpi_int_stun_add_connection(ndpi_struct, flow, NDPI_PROTOCOL_SIGNAL, NDPI_PROTOCOL_STUN); + return; } else if(flow->protos.stun_ssl.stun.is_skype || (flow->guessed_host_protocol_id = NDPI_PROTOCOL_SKYPE_CALL)) { NDPI_LOG_INFO(ndpi_struct, "found Skype\n"); // if((flow->protos.stun_ssl.stun.num_processed_pkts >= 8) || (flow->protos.stun_ssl.stun.num_binding_requests >= 4)) - ndpi_int_stun_add_connection(ndpi_struct, flow, NDPI_PROTOCOL_SKYPE_CALL, NDPI_PROTOCOL_SKYPE); + ndpi_int_stun_add_connection(ndpi_struct, flow, NDPI_PROTOCOL_SKYPE_CALL, NDPI_PROTOCOL_SKYPE); } else { NDPI_LOG_INFO(ndpi_struct, "found UDP stun\n"); /* Ummmmm we're in the TCP branch. This code looks bad */ ndpi_int_stun_add_connection(ndpi_struct, flow, @@ -519,13 +552,16 @@ void ndpi_search_stun(struct ndpi_detection_module_struct *ndpi_struct, struct n packet->payload_packet_len, &is_whatsapp, &is_messenger, &is_duo) == NDPI_IS_STUN) { if(flow->guessed_protocol_id == NDPI_PROTOCOL_UNKNOWN) flow->guessed_protocol_id = NDPI_PROTOCOL_STUN; - + if(is_messenger) { ndpi_int_stun_add_connection(ndpi_struct, flow, NDPI_PROTOCOL_MESSENGER, NDPI_PROTOCOL_STUN); return; } else if(is_duo) { ndpi_int_stun_add_connection(ndpi_struct, flow, NDPI_PROTOCOL_HANGOUT_DUO, NDPI_PROTOCOL_STUN); return; + } else if(flow->guessed_host_protocol_id == NDPI_PROTOCOL_SIGNAL) { + ndpi_int_stun_add_connection(ndpi_struct, flow, NDPI_PROTOCOL_SIGNAL, NDPI_PROTOCOL_STUN); + return; } else if(flow->protos.stun_ssl.stun.is_skype) { NDPI_LOG_INFO(ndpi_struct, "Found Skype\n"); diff --git a/src/lib/protocols/tls.c b/src/lib/protocols/tls.c index f468df8d8..0df5d52e0 100644 --- a/src/lib/protocols/tls.c +++ b/src/lib/protocols/tls.c @@ -1329,16 +1329,18 @@ void ndpi_search_tls_tcp_udp(struct ndpi_detection_module_struct *ndpi_struct, flow->guessed_protocol_id = NDPI_PROTOCOL_TLS; if(flow->protos.stun_ssl.stun.num_udp_pkts > 0) { - u_int32_t key = get_stun_lru_key(flow, 1); - if(ndpi_struct->stun_cache == NULL) ndpi_struct->stun_cache = ndpi_lru_cache_init(1024); - ndpi_lru_add_to_cache(ndpi_struct->stun_cache, key, NDPI_PROTOCOL_SIGNAL); + if(ndpi_struct->stun_cache) { #ifdef DEBUG_TLS - printf("[LRU] Adding Signal cached key %u\n", key); + printf("[LRU] Adding Signal cached keys\n"); #endif - + + ndpi_lru_add_to_cache(ndpi_struct->stun_cache, get_stun_lru_key(flow, 0), NDPI_PROTOCOL_SIGNAL); + ndpi_lru_add_to_cache(ndpi_struct->stun_cache, get_stun_lru_key(flow, 1), NDPI_PROTOCOL_SIGNAL); + } + /* In Signal protocol STUN turns into DTLS... */ ndpi_int_tls_add_connection(ndpi_struct, flow, NDPI_PROTOCOL_SIGNAL); } else if(flow->protos.stun_ssl.ssl.ja3_server[0] != '\0') { |