aboutsummaryrefslogtreecommitdiff
path: root/src/lib/protocols
diff options
context:
space:
mode:
Diffstat (limited to 'src/lib/protocols')
-rw-r--r--src/lib/protocols/bittorrent.c243
-rw-r--r--src/lib/protocols/dhcp.c30
-rw-r--r--src/lib/protocols/dns.c61
-rw-r--r--src/lib/protocols/http.c29
-rw-r--r--src/lib/protocols/sip.c10
-rw-r--r--src/lib/protocols/socks4.c96
-rw-r--r--src/lib/protocols/socks45.c155
-rw-r--r--src/lib/protocols/socks5.c92
-rw-r--r--src/lib/protocols/ssl.c42
-rw-r--r--src/lib/protocols/stun.c16
-rw-r--r--src/lib/protocols/tcp_udp.c10
-rw-r--r--src/lib/protocols/tor.c2
-rw-r--r--src/lib/protocols/veohtv.c130
13 files changed, 395 insertions, 521 deletions
diff --git a/src/lib/protocols/bittorrent.c b/src/lib/protocols/bittorrent.c
index 99420b85e..8213d3b45 100644
--- a/src/lib/protocols/bittorrent.c
+++ b/src/lib/protocols/bittorrent.c
@@ -25,15 +25,53 @@
#include "ndpi_protocols.h"
#ifdef NDPI_PROTOCOL_BITTORRENT
-#define NDPI_PROTOCOL_UNSAFE_DETECTION 0
-#define NDPI_PROTOCOL_SAFE_DETECTION 1
+#define NDPI_PROTOCOL_UNSAFE_DETECTION 0
+#define NDPI_PROTOCOL_SAFE_DETECTION 1
+
+#define NDPI_PROTOCOL_PLAIN_DETECTION 0
+#define NDPI_PROTOCOL_WEBSEED_DETECTION 2
+
+
+struct ndpi_utp_hdr {
+ u_int8_t h_version:4, h_type:4, next_extension;
+ u_int16_t connection_id;
+ u_int32_t ts_usec, tdiff_usec, window_size;
+ u_int16_t sequence_nr, ack_nr;
+};
+
+static u_int8_t is_utp_pkt(const u_int8_t *payload, u_int payload_len) {
+ struct ndpi_utp_hdr *h = (struct ndpi_utp_hdr*)payload;
+
+ if(payload_len < sizeof(struct ndpi_utp_hdr)) return(0);
+ if(h->h_version != 1) return(0);
+ if(h->h_type > 4) return(0);
+ if(h->next_extension > 2) return(0);
+ if(ntohl(h->window_size) > 65565) return(0);
+
+ return(1);
+}
-#define NDPI_PROTOCOL_PLAIN_DETECTION 0
-#define NDPI_PROTOCOL_WEBSEED_DETECTION 2
static void ndpi_add_connection_as_bittorrent(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow,
+ int bt_offset, int check_hash,
const u_int8_t save_detection, const u_int8_t encrypted_connection/* , */
/* ndpi_protocol_type_t protocol_type */)
{
+ if(check_hash) {
+ const char *bt_hash = NULL; /* 20 bytes long */
+ const char *peer_id = NULL; /* 20 bytes long */
+
+ if(bt_offset == -1) {
+ const char *bt_magic = ndpi_strnstr((const char *)flow->packet.payload,
+ "BitTorrent protocol", flow->packet.payload_packet_len);
+
+ if(bt_magic)
+ bt_hash = &bt_magic[19], peer_id = &bt_magic[39];
+ } else
+ bt_hash = (const char*)&flow->packet.payload[28], peer_id = (const char*)&flow->packet.payload[48];
+
+ if(bt_hash) memcpy(flow->bittorent_hash, bt_hash, 20);
+ }
+
ndpi_int_change_protocol(ndpi_struct, flow, NDPI_PROTOCOL_BITTORRENT, NDPI_PROTOCOL_UNKNOWN);
}
@@ -43,61 +81,57 @@ static u_int8_t ndpi_int_search_bittorrent_tcp_zero(struct ndpi_detection_module
struct ndpi_packet_struct *packet = &flow->packet;
u_int16_t a = 0;
- if (packet->payload_packet_len == 1 && packet->payload[0] == 0x13) {
+ if(packet->payload_packet_len == 1 && packet->payload[0] == 0x13) {
/* reset stage back to 0 so we will see the next packet here too */
flow->bittorrent_stage = 0;
return 0;
}
- if (flow->packet_counter == 2 && packet->payload_packet_len > 20) {
- if (memcmp(&packet->payload[0], "BitTorrent protocol", 19) == 0) {
+ if(flow->packet_counter == 2 && packet->payload_packet_len > 20) {
+ if(memcmp(&packet->payload[0], "BitTorrent protocol", 19) == 0) {
NDPI_LOG(NDPI_PROTOCOL_BITTORRENT,
ndpi_struct, NDPI_LOG_TRACE, "BT: plain BitTorrent protocol detected\n");
- ndpi_add_connection_as_bittorrent(ndpi_struct, flow,
+ ndpi_add_connection_as_bittorrent(ndpi_struct, flow, 19, 1,
NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_PLAIN_DETECTION/* , */
/* NDPI_REAL_PROTOCOL */);
return 1;
}
}
-
- if (packet->payload_packet_len > 20) {
+ if(packet->payload_packet_len > 20) {
/* test for match 0x13+"BitTorrent protocol" */
- if (packet->payload[0] == 0x13) {
- if (memcmp(&packet->payload[1], "BitTorrent protocol", 19) == 0) {
- NDPI_LOG(NDPI_PROTOCOL_BITTORRENT,
- ndpi_struct, NDPI_LOG_TRACE, "BT: plain BitTorrent protocol detected\n");
- ndpi_add_connection_as_bittorrent(ndpi_struct, flow,
- NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_PLAIN_DETECTION/* , */
- /* NDPI_REAL_PROTOCOL */);
+ if(packet->payload[0] == 0x13) {
+ if(memcmp(&packet->payload[1], "BitTorrent protocol", 19) == 0) {
+ NDPI_LOG(NDPI_PROTOCOL_BITTORRENT, ndpi_struct, NDPI_LOG_TRACE, "BT: plain BitTorrent protocol detected\n");
+ ndpi_add_connection_as_bittorrent(ndpi_struct, flow, 20, 1,
+ NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_PLAIN_DETECTION);
return 1;
}
}
}
- if (packet->payload_packet_len > 23 && memcmp(packet->payload, "GET /webseed?info_hash=", 23) == 0) {
+ if(packet->payload_packet_len > 23 && memcmp(packet->payload, "GET /webseed?info_hash=", 23) == 0) {
NDPI_LOG(NDPI_PROTOCOL_BITTORRENT, ndpi_struct,
NDPI_LOG_TRACE, "BT: plain webseed BitTorrent protocol detected\n");
- ndpi_add_connection_as_bittorrent(ndpi_struct, flow,
- NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_WEBSEED_DETECTION/* , */
- /* NDPI_CORRELATED_PROTOCOL */);
+ ndpi_add_connection_as_bittorrent(ndpi_struct, flow, -1, 1,
+ NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_WEBSEED_DETECTION);
return 1;
}
/* seen Azureus as server for webseed, possibly other servers existing, to implement */
/* is Server: hypertracker Bittorrent? */
/* no asymmetric detection possible for answer of pattern "GET /data?fid=". */
- if (packet->payload_packet_len > 60
+ if(packet->payload_packet_len > 60
&& memcmp(packet->payload, "GET /data?fid=", 14) == 0 && memcmp(&packet->payload[54], "&size=", 6) == 0) {
NDPI_LOG(NDPI_PROTOCOL_BITTORRENT, ndpi_struct,
NDPI_LOG_TRACE, "BT: plain Bitcomet persistent seed protocol detected\n");
- ndpi_add_connection_as_bittorrent(ndpi_struct, flow,
+ ndpi_add_connection_as_bittorrent(ndpi_struct, flow, -1, 1,
NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_WEBSEED_DETECTION/* , */
/* NDPI_CORRELATED_PROTOCOL */);
return 1;
}
- if (packet->payload_packet_len > 90 && (memcmp(packet->payload, "GET ", 4) == 0
+ if(packet->payload_packet_len > 90 && (memcmp(packet->payload, "GET ", 4) == 0
|| memcmp(packet->payload, "POST ", 5) == 0)) {
const u_int8_t *ptr = &packet->payload[4];
u_int16_t len = packet->payload_packet_len - 4;
@@ -107,32 +141,30 @@ static u_int8_t ndpi_int_search_bittorrent_tcp_zero(struct ndpi_detection_module
/* parse complete get packet here into line structure elements */
ndpi_parse_packet_line_info(ndpi_struct, flow);
/* answer to this pattern is HTTP....Server: hypertracker */
- if (packet->user_agent_line.ptr != NULL
+ if(packet->user_agent_line.ptr != NULL
&& ((packet->user_agent_line.len > 8 && memcmp(packet->user_agent_line.ptr, "Azureus ", 8) == 0)
|| (packet->user_agent_line.len >= 10 && memcmp(packet->user_agent_line.ptr, "BitTorrent", 10) == 0)
|| (packet->user_agent_line.len >= 11 && memcmp(packet->user_agent_line.ptr, "BTWebClient", 11) == 0))) {
NDPI_LOG(NDPI_PROTOCOL_BITTORRENT, ndpi_struct,
NDPI_LOG_TRACE, "Azureus /Bittorrent user agent line detected\n");
- ndpi_add_connection_as_bittorrent(ndpi_struct, flow,
- NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_WEBSEED_DETECTION/* , */
- /* NDPI_CORRELATED_PROTOCOL */);
+ ndpi_add_connection_as_bittorrent(ndpi_struct, flow, -1, 1,
+ NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_WEBSEED_DETECTION);
return 1;
}
- if (packet->user_agent_line.ptr != NULL
- && (packet->user_agent_line.len >= 9 && memcmp(packet->user_agent_line.ptr, "Shareaza ", 9) == 0)
- && (packet->parsed_lines > 8 && packet->line[8].ptr != 0
- && packet->line[8].len >= 9 && memcmp(packet->line[8].ptr, "X-Queue: ", 9) == 0)) {
+ if(packet->user_agent_line.ptr != NULL
+ && (packet->user_agent_line.len >= 9 && memcmp(packet->user_agent_line.ptr, "Shareaza ", 9) == 0)
+ && (packet->parsed_lines > 8 && packet->line[8].ptr != 0
+ && packet->line[8].len >= 9 && memcmp(packet->line[8].ptr, "X-Queue: ", 9) == 0)) {
NDPI_LOG(NDPI_PROTOCOL_BITTORRENT, ndpi_struct,
NDPI_LOG_TRACE, "Bittorrent Shareaza detected.\n");
- ndpi_add_connection_as_bittorrent(ndpi_struct, flow,
- NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_WEBSEED_DETECTION/* , */
- /* NDPI_CORRELATED_PROTOCOL */);
+ ndpi_add_connection_as_bittorrent(ndpi_struct, flow, -1, 1,
+ NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_WEBSEED_DETECTION);
return 1;
}
/* this is a self built client, not possible to catch asymmetrically */
- if ((packet->parsed_lines == 10 || (packet->parsed_lines == 11 && packet->line[11].len == 0))
+ if((packet->parsed_lines == 10 || (packet->parsed_lines == 11 && packet->line[11].len == 0))
&& packet->user_agent_line.ptr != NULL
&& packet->user_agent_line.len > 12
&& memcmp(packet->user_agent_line.ptr, "Mozilla/4.0 ",
@@ -160,15 +192,13 @@ static u_int8_t ndpi_int_search_bittorrent_tcp_zero(struct ndpi_detection_module
&& packet->line[8].len > 22 && memcmp(packet->line[8].ptr, "Cache-Control: no-cache", 23) == 0) {
NDPI_LOG(NDPI_PROTOCOL_BITTORRENT, ndpi_struct, NDPI_LOG_TRACE, "Bitcomet LTS detected\n");
- ndpi_add_connection_as_bittorrent(ndpi_struct, flow,
- NDPI_PROTOCOL_UNSAFE_DETECTION, NDPI_PROTOCOL_PLAIN_DETECTION/* , */
- /* NDPI_CORRELATED_PROTOCOL */);
+ ndpi_add_connection_as_bittorrent(ndpi_struct, flow, -1, 1,
+ NDPI_PROTOCOL_UNSAFE_DETECTION, NDPI_PROTOCOL_PLAIN_DETECTION);
return 1;
-
}
/* FlashGet pattern */
- if (packet->parsed_lines == 8
+ if(packet->parsed_lines == 8
&& packet->user_agent_line.ptr != NULL
&& packet->user_agent_line.len > (sizeof("Mozilla/4.0 (compatible; MSIE 6.0;") - 1)
&& memcmp(packet->user_agent_line.ptr, "Mozilla/4.0 (compatible; MSIE 6.0;",
@@ -187,13 +217,12 @@ static u_int8_t ndpi_int_search_bittorrent_tcp_zero(struct ndpi_detection_module
&& packet->line[6].len > 21 && memcmp(packet->line[6].ptr, "Connection: Keep-Alive", 22) == 0) {
NDPI_LOG(NDPI_PROTOCOL_BITTORRENT, ndpi_struct, NDPI_LOG_TRACE, "FlashGet detected\n");
- ndpi_add_connection_as_bittorrent(ndpi_struct, flow,
- NDPI_PROTOCOL_UNSAFE_DETECTION, NDPI_PROTOCOL_PLAIN_DETECTION/* , */
- /* NDPI_CORRELATED_PROTOCOL */);
+ ndpi_add_connection_as_bittorrent(ndpi_struct, flow, -1, 1,
+ NDPI_PROTOCOL_UNSAFE_DETECTION, NDPI_PROTOCOL_PLAIN_DETECTION);
return 1;
-
}
- if (packet->parsed_lines == 7
+
+ if(packet->parsed_lines == 7
&& packet->user_agent_line.ptr != NULL
&& packet->user_agent_line.len > (sizeof("Mozilla/4.0 (compatible; MSIE 6.0;") - 1)
&& memcmp(packet->user_agent_line.ptr, "Mozilla/4.0 (compatible; MSIE 6.0;",
@@ -209,19 +238,17 @@ static u_int8_t ndpi_int_search_bittorrent_tcp_zero(struct ndpi_detection_module
&& packet->line[5].len > 21 && memcmp(packet->line[5].ptr, "Connection: Keep-Alive", 22) == 0) {
NDPI_LOG(NDPI_PROTOCOL_BITTORRENT, ndpi_struct, NDPI_LOG_TRACE, "FlashGet detected\n");
- ndpi_add_connection_as_bittorrent(ndpi_struct, flow,
- NDPI_PROTOCOL_UNSAFE_DETECTION, NDPI_PROTOCOL_PLAIN_DETECTION/* , */
- /* NDPI_CORRELATED_PROTOCOL */);
+ ndpi_add_connection_as_bittorrent(ndpi_struct, flow, -1, 1,
+ NDPI_PROTOCOL_UNSAFE_DETECTION, NDPI_PROTOCOL_PLAIN_DETECTION);
return 1;
-
}
/* answer to this pattern is not possible to implement asymmetrically */
while (1) {
- if (len < 50 || ptr[0] == 0x0d) {
+ if(len < 50 || ptr[0] == 0x0d) {
goto ndpi_end_bt_tracker_check;
}
- if (memcmp(ptr, "info_hash=", 10) == 0) {
+ if(memcmp(ptr, "info_hash=", 10) == 0) {
break;
}
len--;
@@ -237,40 +264,40 @@ static u_int8_t ndpi_int_search_bittorrent_tcp_zero(struct ndpi_detection_module
/* parse bt hash */
for (a = 0; a < 20; a++) {
- if (len < 3) {
+ if(len < 3) {
goto ndpi_end_bt_tracker_check;
}
- if (*ptr == '%') {
+ if(*ptr == '%') {
u_int8_t x1 = 0xFF;
u_int8_t x2 = 0xFF;
- if (ptr[1] >= '0' && ptr[1] <= '9') {
+ if(ptr[1] >= '0' && ptr[1] <= '9') {
x1 = ptr[1] - '0';
}
- if (ptr[1] >= 'a' && ptr[1] <= 'f') {
+ if(ptr[1] >= 'a' && ptr[1] <= 'f') {
x1 = 10 + ptr[1] - 'a';
}
- if (ptr[1] >= 'A' && ptr[1] <= 'F') {
+ if(ptr[1] >= 'A' && ptr[1] <= 'F') {
x1 = 10 + ptr[1] - 'A';
}
- if (ptr[2] >= '0' && ptr[2] <= '9') {
+ if(ptr[2] >= '0' && ptr[2] <= '9') {
x2 = ptr[2] - '0';
}
- if (ptr[2] >= 'a' && ptr[2] <= 'f') {
+ if(ptr[2] >= 'a' && ptr[2] <= 'f') {
x2 = 10 + ptr[2] - 'a';
}
- if (ptr[2] >= 'A' && ptr[2] <= 'F') {
+ if(ptr[2] >= 'A' && ptr[2] <= 'F') {
x2 = 10 + ptr[2] - 'A';
}
- if (x1 == 0xFF || x2 == 0xFF) {
+ if(x1 == 0xFF || x2 == 0xFF) {
goto ndpi_end_bt_tracker_check;
}
ptr += 3;
len -= 3;
- } else if (*ptr >= 32 && *ptr < 127) {
+ } else if(*ptr >= 32 && *ptr < 127) {
ptr++;
len--;
} else {
@@ -280,15 +307,14 @@ static u_int8_t ndpi_int_search_bittorrent_tcp_zero(struct ndpi_detection_module
NDPI_LOG(NDPI_PROTOCOL_BITTORRENT, ndpi_struct,
NDPI_LOG_TRACE, " BT stat: tracker info hash parsed\n");
- ndpi_add_connection_as_bittorrent(ndpi_struct, flow,
- NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_PLAIN_DETECTION/* , */
- /* NDPI_CORRELATED_PROTOCOL */);
+ ndpi_add_connection_as_bittorrent(ndpi_struct, flow, -1, 1,
+ NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_PLAIN_DETECTION);
return 1;
}
ndpi_end_bt_tracker_check:
- if (packet->payload_packet_len == 80) {
+ if(packet->payload_packet_len == 80) {
/* Warez 80 Bytes Packet
* +----------------+---------------+-----------------+-----------------+
* |20 BytesPattern | 32 Bytes Value| 12 BytesPattern | 16 Bytes Data |
@@ -306,30 +332,28 @@ static u_int8_t ndpi_int_search_bittorrent_tcp_zero(struct ndpi_detection_module
};
/* did not see this pattern anywhere */
- if ((memcmp(&packet->payload[0], pattern_20_bytes, 20) == 0)
+ if((memcmp(&packet->payload[0], pattern_20_bytes, 20) == 0)
&& (memcmp(&packet->payload[52], pattern_12_bytes, 12) == 0)) {
NDPI_LOG(NDPI_PROTOCOL_BITTORRENT, ndpi_struct,
NDPI_LOG_TRACE, "BT: Warez - Plain BitTorrent protocol detected\n");
- ndpi_add_connection_as_bittorrent(ndpi_struct, flow,
- NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_PLAIN_DETECTION/* , */
- /* NDPI_REAL_PROTOCOL */);
+ ndpi_add_connection_as_bittorrent(ndpi_struct, flow, -1, 1,
+ NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_PLAIN_DETECTION);
return 1;
}
}
- else if (packet->payload_packet_len > 50) {
- if (memcmp(packet->payload, "GET", 3) == 0) {
+ else if(packet->payload_packet_len > 50) {
+ if(memcmp(packet->payload, "GET", 3) == 0) {
ndpi_parse_packet_line_info(ndpi_struct, flow);
/* haven't fount this pattern anywhere */
- if (packet->host_line.ptr != NULL
+ if(packet->host_line.ptr != NULL
&& packet->host_line.len >= 9 && memcmp(packet->host_line.ptr, "ip2p.com:", 9) == 0) {
NDPI_LOG(NDPI_PROTOCOL_BITTORRENT,
ndpi_struct, NDPI_LOG_TRACE,
"BT: Warez - Plain BitTorrent protocol detected due to Host: ip2p.com: pattern\n");
- ndpi_add_connection_as_bittorrent(ndpi_struct, flow,
- NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_WEBSEED_DETECTION/* , */
- /* NDPI_CORRELATED_PROTOCOL */);
+ ndpi_add_connection_as_bittorrent(ndpi_struct, flow, -1, 1,
+ NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_WEBSEED_DETECTION);
return 1;
}
}
@@ -341,17 +365,16 @@ static u_int8_t ndpi_int_search_bittorrent_tcp_zero(struct ndpi_detection_module
/*Search for BitTorrent commands*/
static void ndpi_int_search_bittorrent_tcp(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow)
{
-
struct ndpi_packet_struct *packet = &flow->packet;
- if (packet->payload_packet_len == 0) {
+ if(packet->payload_packet_len == 0) {
return;
}
- if (flow->bittorrent_stage == 0 && packet->payload_packet_len != 0) {
+ if(flow->bittorrent_stage == 0 && packet->payload_packet_len != 0) {
/* exclude stage 0 detection from next run */
flow->bittorrent_stage = 1;
- if (ndpi_int_search_bittorrent_tcp_zero(ndpi_struct, flow) != 0) {
+ if(ndpi_int_search_bittorrent_tcp_zero(ndpi_struct, flow) != 0) {
NDPI_LOG(NDPI_PROTOCOL_BITTORRENT, ndpi_struct, NDPI_LOG_DEBUG,
"stage 0 has detected something, returning\n");
return;
@@ -367,6 +390,7 @@ void ndpi_search_bittorrent(struct ndpi_detection_module_struct *ndpi_struct, st
{
struct ndpi_packet_struct *packet = &flow->packet;
int no_bittorrent = 0;
+ char *bt_proto = NULL;
/* This is broadcast */
if(packet->iph
@@ -378,10 +402,10 @@ void ndpi_search_bittorrent(struct ndpi_detection_module_struct *ndpi_struct, st
return;
}
- if (packet->detected_protocol_stack[0] != NDPI_PROTOCOL_BITTORRENT) {
+ if(packet->detected_protocol_stack[0] != NDPI_PROTOCOL_BITTORRENT) {
/* check for tcp retransmission here */
- if ((packet->tcp != NULL)
+ if((packet->tcp != NULL)
&& (packet->tcp_retransmission == 0 || packet->num_retried_bytes)) {
ndpi_int_search_bittorrent_tcp(ndpi_struct, flow);
}
@@ -400,9 +424,8 @@ void ndpi_search_bittorrent(struct ndpi_detection_module_struct *ndpi_struct, st
if(packet->payload_packet_len >= 23 /* min header size */) {
if(strncmp((const char*)packet->payload, bt_search, strlen(bt_search)) == 0) {
- ndpi_add_connection_as_bittorrent(ndpi_struct, flow,
- NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_PLAIN_DETECTION/* , */
- /* NDPI_REAL_PROTOCOL */);
+ ndpi_add_connection_as_bittorrent(ndpi_struct, flow, -1, 1,
+ NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_PLAIN_DETECTION);
return;
} else {
/* Check if this is protocol v0 */
@@ -414,27 +437,31 @@ void ndpi_search_bittorrent(struct ndpi_detection_module_struct *ndpi_struct, st
u_int8_t v1_extension = packet->payload[1];
u_int32_t v1_window_size = *((u_int32_t*)&packet->payload[12]);
- if((packet->payload[0]== 0x60)
+ if(is_utp_pkt(packet->payload, packet->payload_packet_len))
+ goto bittorrent_found;
+ else if((packet->payload[0]== 0x60)
&& (packet->payload[1]== 0x0)
&& (packet->payload[2]== 0x0)
&& (packet->payload[3]== 0x0)
&& (packet->payload[4]== 0x0)) {
/* Heuristic */
+ bt_proto = ndpi_strnstr((const char *)&packet->payload[20], "BitTorrent protocol", packet->payload_packet_len-20);
goto bittorrent_found;
} else if(((v1_version & 0x0f) == 1)
&& ((v1_version >> 4) < 5 /* ST_NUM_STATES */)
&& (v1_extension < 3 /* EXT_NUM_EXT */)
&& (v1_window_size < 32768 /* 32k */)
) {
+ bt_proto = ndpi_strnstr((const char *)&packet->payload[20], "BitTorrent protocol", packet->payload_packet_len-20);
goto bittorrent_found;
- } else if((v0_flags < 6 /* ST_NUM_STATES */)
- && (v0_extension < 3 /* EXT_NUM_EXT */)) {
+ } else if((v0_flags < 6 /* ST_NUM_STATES */) && (v0_extension < 3 /* EXT_NUM_EXT */)) {
u_int32_t ts = ntohl(*((u_int32_t*)&(packet->payload[4])));
u_int32_t now;
now = (u_int32_t)time(NULL);
if((ts < (now+86400)) && (ts > (now-86400))) {
+ bt_proto = ndpi_strnstr((const char *)&packet->payload[20], "BitTorrent protocol", packet->payload_packet_len-20);
goto bittorrent_found;
}
}
@@ -444,24 +471,28 @@ void ndpi_search_bittorrent(struct ndpi_detection_module_struct *ndpi_struct, st
flow->bittorrent_stage++;
if(flow->bittorrent_stage < 10) {
- if(packet->payload_packet_len > 19 /* min size */) {
- if(ndpi_strnstr((const char *)packet->payload, ":target20:", packet->payload_packet_len)
- || ndpi_strnstr((const char *)packet->payload, ":find_node1:", packet->payload_packet_len)
- || ndpi_strnstr((const char *)packet->payload, "d1:ad2:id20:", packet->payload_packet_len)
- || ndpi_strnstr((const char *)packet->payload, ":info_hash20:", packet->payload_packet_len)
- || ndpi_strnstr((const char *)packet->payload, ":filter64", packet->payload_packet_len)
- || ndpi_strnstr((const char *)packet->payload, "d1:rd2:id20:", packet->payload_packet_len)
- || ndpi_strnstr((const char *)packet->payload, "BitTorrent protocol", packet->payload_packet_len)
- ) {
- bittorrent_found:
- NDPI_LOG(NDPI_PROTOCOL_BITTORRENT,
- ndpi_struct, NDPI_LOG_TRACE, "BT: plain BitTorrent protocol detected\n");
- ndpi_add_connection_as_bittorrent(ndpi_struct, flow,
- NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_PLAIN_DETECTION/* , */
- /* NDPI_REAL_PROTOCOL */);
- return;
- }
- }
+ /* We have detected bittorrent but we need to wait until we get a hash */
+
+ if(packet->payload_packet_len > 19 /* min size */) {
+ if(ndpi_strnstr((const char *)packet->payload, ":target20:", packet->payload_packet_len)
+ || ndpi_strnstr((const char *)packet->payload, ":find_node1:", packet->payload_packet_len)
+ || ndpi_strnstr((const char *)packet->payload, "d1:ad2:id20:", packet->payload_packet_len)
+ || ndpi_strnstr((const char *)packet->payload, ":info_hash20:", packet->payload_packet_len)
+ || ndpi_strnstr((const char *)packet->payload, ":filter64", packet->payload_packet_len)
+ || ndpi_strnstr((const char *)packet->payload, "d1:rd2:id20:", packet->payload_packet_len)
+ || (bt_proto = ndpi_strnstr((const char *)packet->payload, "BitTorrent protocol", packet->payload_packet_len))
+ ) {
+ bittorrent_found:
+ if(bt_proto && (packet->payload_packet_len > 47))
+ memcpy(flow->bittorent_hash, &bt_proto[27], 20);
+
+ NDPI_LOG(NDPI_PROTOCOL_BITTORRENT,
+ ndpi_struct, NDPI_LOG_TRACE, "BT: plain BitTorrent protocol detected\n");
+ ndpi_add_connection_as_bittorrent(ndpi_struct, flow, -1, 0,
+ NDPI_PROTOCOL_SAFE_DETECTION, NDPI_PROTOCOL_PLAIN_DETECTION);
+ return;
+ }
+ }
return;
}
diff --git a/src/lib/protocols/dhcp.c b/src/lib/protocols/dhcp.c
index cb78c9429..8ffc04d51 100644
--- a/src/lib/protocols/dhcp.c
+++ b/src/lib/protocols/dhcp.c
@@ -35,27 +35,27 @@ static void ndpi_int_dhcp_add_connection(struct ndpi_detection_module_struct *nd
void ndpi_search_dhcp_udp(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow)
{
- struct ndpi_packet_struct *packet = &flow->packet;
+ struct ndpi_packet_struct *packet = &flow->packet;
-// struct ndpi_id_struct *src=ndpi_struct->src;
-// struct ndpi_id_struct *dst=ndpi_struct->dst;
+ // struct ndpi_id_struct *src=ndpi_struct->src;
+ // struct ndpi_id_struct *dst=ndpi_struct->dst;
- /* this detection also works for asymmetric dhcp traffic */
+ /* this detection also works for asymmetric dhcp traffic */
- /*check standard DHCP 0.0.0.0:68 -> 255.255.255.255:67 */
- if (packet->payload_packet_len >= 244 && (packet->udp->source == htons(67)
- || packet->udp->source == htons(68))
- && (packet->udp->dest == htons(67) || packet->udp->dest == htons(68))
- && get_u_int32_t(packet->payload, 236) == htonl(0x63825363)
- && get_u_int16_t(packet->payload, 240) == htons(0x3501)) {
+ /*check standard DHCP 0.0.0.0:68 -> 255.255.255.255:67 */
+ if (packet->payload_packet_len >= 244 && (packet->udp->source == htons(67)
+ || packet->udp->source == htons(68))
+ && (packet->udp->dest == htons(67) || packet->udp->dest == htons(68))
+ && get_u_int32_t(packet->payload, 236) == htonl(0x63825363)
+ && get_u_int16_t(packet->payload, 240) == htons(0x3501)) {
- NDPI_LOG(NDPI_PROTOCOL_DHCP, ndpi_struct, NDPI_LOG_DEBUG, "DHCP request\n");
+ NDPI_LOG(NDPI_PROTOCOL_DHCP, ndpi_struct, NDPI_LOG_DEBUG, "DHCP request\n");
- ndpi_int_dhcp_add_connection(ndpi_struct, flow);
- return;
- }
+ ndpi_int_dhcp_add_connection(ndpi_struct, flow);
+ return;
+ }
- NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask, NDPI_PROTOCOL_DHCP);
+ NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask, NDPI_PROTOCOL_DHCP);
}
diff --git a/src/lib/protocols/dns.c b/src/lib/protocols/dns.c
index 8749f4d5e..c975465ea 100644
--- a/src/lib/protocols/dns.c
+++ b/src/lib/protocols/dns.c
@@ -60,43 +60,46 @@ void ndpi_search_dns(struct ndpi_detection_module_struct *ndpi_struct, struct nd
if((s_port == 53 || d_port == 53 || d_port == 5355)
&& (flow->packet.payload_packet_len > sizeof(struct ndpi_dns_packet_header)))
{
- struct ndpi_dns_packet_header *dns_header = (struct ndpi_dns_packet_header*) &flow->packet.payload[x];
+ struct ndpi_dns_packet_header dns_header;
int invalid = 0;
- dns_header->tr_id = ntohs(dns_header->tr_id);
- dns_header->flags = ntohs(dns_header->flags);
- dns_header->num_queries = ntohs(dns_header->num_queries);
- dns_header->num_answers = ntohs(dns_header->num_answers);
- dns_header->authority_rrs = ntohs(dns_header->authority_rrs);
- dns_header->additional_rrs = ntohs(dns_header->additional_rrs);
+ memcpy(&dns_header, (struct ndpi_dns_packet_header*) &flow->packet.payload[x], sizeof(struct ndpi_dns_packet_header));
+ dns_header.tr_id = ntohs(dns_header.tr_id);
+ dns_header.flags = ntohs(dns_header.flags);
+ dns_header.num_queries = ntohs(dns_header.num_queries);
+ dns_header.num_answers = ntohs(dns_header.num_answers);
+ dns_header.authority_rrs = ntohs(dns_header.authority_rrs);
+ dns_header.additional_rrs = ntohs(dns_header.additional_rrs);
/* 0x0000 QUERY */
- if((dns_header->flags & FLAGS_MASK) == 0x0000)
+ if((dns_header.flags & FLAGS_MASK) == 0x0000)
is_query = 1;
/* 0x8000 RESPONSE */
- else if((dns_header->flags & FLAGS_MASK) != 0x8000)
+ else if((dns_header.flags & FLAGS_MASK) != 0x8000)
is_query = 0;
else
invalid = 1;
- if(is_query) {
- /* DNS Request */
- if((dns_header->num_queries > 0) && (dns_header->num_queries <= NDPI_MAX_DNS_REQUESTS)
- && (((dns_header->flags & 0x2800) == 0x2800 /* Dynamic DNS Update */)
- || ((dns_header->num_answers == 0) && (dns_header->authority_rrs == 0)))) {
- /* This is a good query */
- } else
- invalid = 1;
- } else {
- /* DNS Reply */
- if((dns_header->num_queries > 0) && (dns_header->num_queries <= NDPI_MAX_DNS_REQUESTS) /* Don't assume that num_queries must be zero */
- && (((dns_header->num_answers > 0) && (dns_header->num_answers <= NDPI_MAX_DNS_REQUESTS))
- || ((dns_header->authority_rrs > 0) && (dns_header->authority_rrs <= NDPI_MAX_DNS_REQUESTS))
- || ((dns_header->additional_rrs > 0) && (dns_header->additional_rrs <= NDPI_MAX_DNS_REQUESTS)))
- ) {
- /* This is a good reply */
- } else
- invalid = 1;
+ if(!invalid) {
+ if(is_query) {
+ /* DNS Request */
+ if((dns_header.num_queries > 0) && (dns_header.num_queries <= NDPI_MAX_DNS_REQUESTS)
+ && (((dns_header.flags & 0x2800) == 0x2800 /* Dynamic DNS Update */)
+ || ((dns_header.num_answers == 0) && (dns_header.authority_rrs == 0)))) {
+ /* This is a good query */
+ } else
+ invalid = 1;
+ } else {
+ /* DNS Reply */
+ if((dns_header.num_queries > 0) && (dns_header.num_queries <= NDPI_MAX_DNS_REQUESTS) /* Don't assume that num_queries must be zero */
+ && (((dns_header.num_answers > 0) && (dns_header.num_answers <= NDPI_MAX_DNS_REQUESTS))
+ || ((dns_header.authority_rrs > 0) && (dns_header.authority_rrs <= NDPI_MAX_DNS_REQUESTS))
+ || ((dns_header.additional_rrs > 0) && (dns_header.additional_rrs <= NDPI_MAX_DNS_REQUESTS)))
+ ) {
+ /* This is a good reply */
+ } else
+ invalid = 1;
+ }
}
if(invalid) {
@@ -106,7 +109,7 @@ void ndpi_search_dns(struct ndpi_detection_module_struct *ndpi_struct, struct nd
}
/* extract host name server */
- ret_code = (is_query == 0) ? 0 : (dns_header->flags & 0x0F);
+ ret_code = (is_query == 0) ? 0 : (dns_header.flags & 0x0F);
int j = 0;
int off = sizeof(struct ndpi_dns_packet_header) + 1;
while((flow->packet.payload[off] != '\0'))
@@ -119,7 +122,7 @@ void ndpi_search_dns(struct ndpi_detection_module_struct *ndpi_struct, struct nd
}
flow->host_server_name[j] = '\0';
- flow->protos.dns.num_answers = (u_int8_t) (dns_header->num_answers + dns_header->authority_rrs + dns_header->additional_rrs);
+ flow->protos.dns.num_answers = (u_int8_t) (dns_header.num_answers + dns_header.authority_rrs + dns_header.additional_rrs);
flow->protos.dns.ret_code = ret_code;
if(j > 0)
diff --git a/src/lib/protocols/http.c b/src/lib/protocols/http.c
index ced34c099..caac7390b 100644
--- a/src/lib/protocols/http.c
+++ b/src/lib/protocols/http.c
@@ -37,18 +37,14 @@ static void ndpi_int_http_add_connection(struct ndpi_detection_module_struct *nd
/* If no custom protocol has been detected */
if(flow->detected_protocol_stack[0] == NDPI_PROTOCOL_UNKNOWN) {
- if(protocol != NDPI_PROTOCOL_HTTP) {
- ndpi_search_tcp_or_udp(ndpi_struct, flow);
- ndpi_set_detected_protocol(ndpi_struct, flow, protocol, NDPI_PROTOCOL_UNKNOWN);
- } else {
+ if(protocol == NDPI_PROTOCOL_HTTP)
ndpi_int_reset_protocol(flow);
- ndpi_set_detected_protocol(ndpi_struct, flow, protocol, NDPI_PROTOCOL_UNKNOWN);
- }
+
+ ndpi_set_detected_protocol(ndpi_struct, flow, protocol, NDPI_PROTOCOL_UNKNOWN);
}
flow->http_detected = 1;
}
-
}
#ifdef NDPI_CONTENT_FLASH
@@ -202,21 +198,14 @@ static void parseHttpSubprotocol(struct ndpi_detection_module_struct *ndpi_struc
/*
NOTE
-
+
If http_dont_dissect_response = 1 dissection of HTTP response
mime types won't happen
- */
-
- if(!ndpi_struct->http_dont_dissect_response) {
- if(flow->http.url && flow->http_detected)
- ndpi_match_host_subprotocol(ndpi_struct, flow, (char *)&flow->http.url[7],
- strlen((const char *)&flow->http.url[7]),
- NDPI_PROTOCOL_HTTP);
- } else
- ndpi_match_host_subprotocol(ndpi_struct, flow, (char *)flow->host_server_name,
- strlen((const char *)flow->host_server_name),
- NDPI_PROTOCOL_HTTP);
- }
+ */
+ ndpi_match_host_subprotocol(ndpi_struct, flow, (char *)flow->host_server_name,
+ strlen((const char *)flow->host_server_name),
+ NDPI_PROTOCOL_HTTP);
+ }
}
/*
diff --git a/src/lib/protocols/sip.c b/src/lib/protocols/sip.c
index 3d79561ac..94386d61e 100644
--- a/src/lib/protocols/sip.c
+++ b/src/lib/protocols/sip.c
@@ -19,7 +19,7 @@
*
* You should have received a copy of the GNU Lesser General Public License
* along with nDPI. If not, see <http://www.gnu.org/licenses/>.
- *
+ *
*/
@@ -31,7 +31,7 @@ static void ndpi_int_sip_add_connection(struct ndpi_detection_module_struct *ndp
u_int8_t due_to_correlation) {
ndpi_set_detected_protocol(ndpi_struct, flow, NDPI_PROTOCOL_SIP, NDPI_PROTOCOL_UNKNOWN);
}
-
+
#if !defined(WIN32)
static inline
#else
@@ -41,7 +41,7 @@ void ndpi_search_sip_handshake(struct ndpi_detection_module_struct
*ndpi_struct, struct ndpi_flow_struct *flow)
{
struct ndpi_packet_struct *packet = &flow->packet;
-
+
// struct ndpi_id_struct *src=ndpi_struct->src;
// struct ndpi_id_struct *dst=ndpi_struct->dst;
const u_int8_t *packet_payload = packet->payload;
@@ -92,7 +92,7 @@ void ndpi_search_sip_handshake(struct ndpi_detection_module_struct
* maybe it could be deleted, if somebody sees it in the first direction,
* please delete this comment.
*/
-
+
/*
if (memcmp(packet_payload, "SIP/2.0 200 OK", 14) == 0 || memcmp(packet_payload, "sip/2.0 200 OK", 14) == 0) {
NDPI_LOG(NDPI_PROTOCOL_SIP, ndpi_struct, NDPI_LOG_DEBUG, "found sip SIP/2.0 0K.\n");
@@ -121,7 +121,7 @@ void ndpi_search_sip_handshake(struct ndpi_detection_module_struct
}
if ((memcmp(packet_payload, "CANCEL ", 7) == 0 || memcmp(packet_payload, "cancel ", 7) == 0)
- && (memcmp(&packet_payload[4], "SIP:", 7) == 0 || memcmp(&packet_payload[4], "sip:", 7) == 0)) {
+ && (memcmp(&packet_payload[4], "SIP:", 4) == 0 || memcmp(&packet_payload[4], "sip:", 4) == 0)) {
NDPI_LOG(NDPI_PROTOCOL_SIP, ndpi_struct, NDPI_LOG_DEBUG, "found sip CANCEL.\n");
ndpi_int_sip_add_connection(ndpi_struct, flow, 0);
return;
diff --git a/src/lib/protocols/socks4.c b/src/lib/protocols/socks4.c
deleted file mode 100644
index 87bc3a634..000000000
--- a/src/lib/protocols/socks4.c
+++ /dev/null
@@ -1,96 +0,0 @@
-/*
- * socks4.c
- *
- * Copyright (C) 2014 Tomasz Bujlow <tomasz@skatnet.dk>
- *
- * The signature is based on the Libprotoident library.
- *
- * This file is part of nDPI, an open source deep packet inspection
- * library based on the OpenDPI and PACE technology by ipoque GmbH
- *
- * nDPI is free software: you can redistribute it and/or modify
- * it under the terms of the GNU Lesser General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * nDPI is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with nDPI. If not, see <http://www.gnu.org/licenses/>.
- *
- */
-
-
-#include "ndpi_api.h"
-
-#ifdef NDPI_PROTOCOL_SOCKS4
-static void ndpi_int_socks4_add_connection(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow)
-{
- ndpi_set_detected_protocol(ndpi_struct, flow, NDPI_PROTOCOL_SOCKS4, NDPI_PROTOCOL_UNKNOWN);
-}
-
-static void ndpi_check_socks4(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow)
-{
- struct ndpi_packet_struct *packet = &flow->packet;
- u_int32_t payload_len = packet->payload_packet_len;
-
- /* Break after 20 packets. */
- if (flow->packet_counter > 20) {
- NDPI_LOG(NDPI_PROTOCOL_SOCKS4, ndpi_struct, NDPI_LOG_DEBUG, "Exclude SOCKS4.\n");
- NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask, NDPI_PROTOCOL_SOCKS4);
- return;
- }
-
- /* Check if we so far detected the protocol in the request or not. */
- if (flow->socks4_stage == 0) {
- NDPI_LOG(NDPI_PROTOCOL_SOCKS4, ndpi_struct, NDPI_LOG_DEBUG, "SOCKS4 stage 0: \n");
-
- /*Octets 3 and 4 contain the port number, port 80 and 25 for now. */
- if ((payload_len == 9) &&
- (((packet->payload[0] == 0x04) && (packet->payload[1] == 0x01) && (packet->payload[2] == 0x00) && (packet->payload[3] == 0x50))
- ||
- ((packet->payload[0] == 0x04) && (packet->payload[1] == 0x01) && (packet->payload[2] == 0x00) && (packet->payload[3] == 0x19)))) {
- NDPI_LOG(NDPI_PROTOCOL_SOCKS4, ndpi_struct, NDPI_LOG_DEBUG, "Possible SOCKS4 request detected, we will look further for the response...\n");
-
- /* Encode the direction of the packet in the stage, so we will know when we need to look for the response packet. */
- flow->socks4_stage = packet->packet_direction + 1;
- }
-
- } else {
- NDPI_LOG(NDPI_PROTOCOL_SOCKS4, ndpi_struct, NDPI_LOG_DEBUG, "SOCKS4 stage %u: \n", flow->socks4_stage);
-
- /* At first check, if this is for sure a response packet (in another direction. If not, do nothing now and return. */
- if ((flow->socks4_stage - packet->packet_direction) == 1) {
- return;
- }
-
- /* This is a packet in another direction. Check if we find the proper response. */
- if (payload_len == 0) {
- NDPI_LOG(NDPI_PROTOCOL_SOCKS4, ndpi_struct, NDPI_LOG_DEBUG, "Found SOCKS4.\n");
- ndpi_int_socks4_add_connection(ndpi_struct, flow);
- } else {
- NDPI_LOG(NDPI_PROTOCOL_SOCKS4, ndpi_struct, NDPI_LOG_DEBUG, "The reply did not seem to belong to SOCKS4, resetting the stage to 0...\n");
- flow->socks4_stage = 0;
- }
-
- }
-}
-
-void ndpi_search_socks4(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow)
-{
- struct ndpi_packet_struct *packet = &flow->packet;
-
- NDPI_LOG(NDPI_PROTOCOL_SOCKS4, ndpi_struct, NDPI_LOG_DEBUG, "SOCKS4 detection...\n");
-
- /* skip marked packets */
- if (packet->detected_protocol_stack[0] != NDPI_PROTOCOL_SOCKS4) {
- if (packet->tcp_retransmission == 0) {
- ndpi_check_socks4(ndpi_struct, flow);
- }
- }
-}
-
-#endif
diff --git a/src/lib/protocols/socks45.c b/src/lib/protocols/socks45.c
new file mode 100644
index 000000000..7ad0868d2
--- /dev/null
+++ b/src/lib/protocols/socks45.c
@@ -0,0 +1,155 @@
+/*
+ * socks4.c
+ *
+ * Copyright (C) 2016 - ntop.org
+ * Copyright (C) 2014 Tomasz Bujlow <tomasz@skatnet.dk>
+ *
+ * The signature is based on the Libprotoident library.
+ *
+ * This file is part of nDPI, an open source deep packet inspection
+ * library based on the OpenDPI and PACE technology by ipoque GmbH
+ *
+ * nDPI is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * nDPI is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with nDPI. If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+
+
+#include "ndpi_api.h"
+
+#ifdef NDPI_PROTOCOL_SOCKS
+static void ndpi_int_socks_add_connection(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow)
+{
+ ndpi_set_detected_protocol(ndpi_struct, flow, NDPI_PROTOCOL_SOCKS, NDPI_PROTOCOL_UNKNOWN);
+}
+
+static void ndpi_check_socks4(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow)
+{
+ struct ndpi_packet_struct *packet = &flow->packet;
+ u_int32_t payload_len = packet->payload_packet_len;
+
+ /* Break after 20 packets. */
+ if(flow->packet_counter > 20) {
+ NDPI_LOG(NDPI_PROTOCOL_SOCKS, ndpi_struct, NDPI_LOG_DEBUG, "Exclude SOCKS4.\n");
+ NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask, NDPI_PROTOCOL_SOCKS);
+ return;
+ }
+
+ /* Check if we so far detected the protocol in the request or not. */
+ if(flow->socks4_stage == 0) {
+ NDPI_LOG(NDPI_PROTOCOL_SOCKS, ndpi_struct, NDPI_LOG_DEBUG, "SOCKS4 stage 0: \n");
+
+ /*Octets 3 and 4 contain the port number, port 80 and 25 for now. */
+ if((payload_len == 9) &&
+ (((packet->payload[0] == 0x04) && (packet->payload[1] == 0x01) && (packet->payload[2] == 0x00) && (packet->payload[3] == 0x50))
+ ||
+ ((packet->payload[0] == 0x04) && (packet->payload[1] == 0x01) && (packet->payload[2] == 0x00) && (packet->payload[3] == 0x19)))) {
+ NDPI_LOG(NDPI_PROTOCOL_SOCKS, ndpi_struct, NDPI_LOG_DEBUG, "Possible SOCKS4 request detected, we will look further for the response...\n");
+
+ /* Encode the direction of the packet in the stage, so we will know when we need to look for the response packet. */
+ flow->socks4_stage = packet->packet_direction + 1;
+ }
+
+ } else {
+ NDPI_LOG(NDPI_PROTOCOL_SOCKS, ndpi_struct, NDPI_LOG_DEBUG, "SOCKS4 stage %u: \n", flow->socks4_stage);
+
+ /* At first check, if this is for sure a response packet (in another direction. If not, do nothing now and return. */
+ if((flow->socks4_stage - packet->packet_direction) == 1) {
+ return;
+ }
+
+ /* This is a packet in another direction. Check if we find the proper response. */
+ if(payload_len == 0) {
+ NDPI_LOG(NDPI_PROTOCOL_SOCKS, ndpi_struct, NDPI_LOG_DEBUG, "Found SOCKS4.\n");
+ ndpi_int_socks_add_connection(ndpi_struct, flow);
+ } else {
+ NDPI_LOG(NDPI_PROTOCOL_SOCKS, ndpi_struct, NDPI_LOG_DEBUG, "The reply did not seem to belong to SOCKS4, resetting the stage to 0...\n");
+ flow->socks4_stage = 0;
+ }
+
+ }
+}
+
+static void ndpi_check_socks5(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow)
+{
+ struct ndpi_packet_struct *packet = &flow->packet;
+ u_int32_t payload_len = packet->payload_packet_len;
+
+ /* Break after 20 packets. */
+ if(flow->packet_counter > 20) {
+ NDPI_LOG(NDPI_PROTOCOL_SOCKS, ndpi_struct, NDPI_LOG_DEBUG, "Exclude SOCKS5.\n");
+ NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask, NDPI_PROTOCOL_SOCKS);
+ return;
+ }
+
+ /* Check if we so far detected the protocol in the request or not. */
+ if(flow->socks5_stage == 0) {
+ NDPI_LOG(NDPI_PROTOCOL_SOCKS, ndpi_struct, NDPI_LOG_DEBUG, "SOCKS5 stage 0: \n");
+
+ if((payload_len == 3) && (packet->payload[0] == 0x05) && (packet->payload[1] == 0x01) && (packet->payload[2] == 0x00)) {
+ NDPI_LOG(NDPI_PROTOCOL_SOCKS, ndpi_struct, NDPI_LOG_DEBUG, "Possible SOCKS5 request detected, we will look further for the response...\n");
+
+ /* Encode the direction of the packet in the stage, so we will know when we need to look for the response packet. */
+ flow->socks5_stage = packet->packet_direction + 1;
+ }
+
+ } else {
+ NDPI_LOG(NDPI_PROTOCOL_SOCKS, ndpi_struct, NDPI_LOG_DEBUG, "SOCKS5 stage %u: \n", flow->socks5_stage);
+
+ /* At first check, if this is for sure a response packet (in another direction. If not, do nothing now and return. */
+ if((flow->socks5_stage - packet->packet_direction) == 1) {
+ return;
+ }
+
+ /* This is a packet in another direction. Check if we find the proper response. */
+ if((payload_len == 0) || ((payload_len == 2) && (packet->payload[0] == 0x05) && (packet->payload[1] == 0x00))) {
+ NDPI_LOG(NDPI_PROTOCOL_SOCKS, ndpi_struct, NDPI_LOG_DEBUG, "Found SOCKS5.\n");
+ ndpi_int_socks_add_connection(ndpi_struct, flow);
+ } else {
+ NDPI_LOG(NDPI_PROTOCOL_SOCKS, ndpi_struct, NDPI_LOG_DEBUG, "The reply did not seem to belong to SOCKS5, resetting the stage to 0...\n");
+ flow->socks5_stage = 0;
+ }
+
+ }
+}
+
+void ndpi_search_socks(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow)
+{
+ struct ndpi_packet_struct *packet = &flow->packet;
+
+ NDPI_LOG(NDPI_PROTOCOL_SOCKS, ndpi_struct, NDPI_LOG_DEBUG, "SOCKS detection...\n");
+
+ /* skip marked packets */
+ if(packet->detected_protocol_stack[0] != NDPI_PROTOCOL_SOCKS) {
+ if(packet->tcp_retransmission == 0) {
+ ndpi_check_socks4(ndpi_struct, flow);
+
+ if(packet->detected_protocol_stack[0] != NDPI_PROTOCOL_SOCKS)
+ ndpi_check_socks5(ndpi_struct, flow);
+ }
+ }
+}
+
+void init_socks_dissector(struct ndpi_detection_module_struct *ndpi_struct, u_int32_t *id, NDPI_PROTOCOL_BITMASK *detection_bitmask)
+{
+ ndpi_set_bitmask_protocol_detection("SOCKS", ndpi_struct, detection_bitmask, *id,
+ NDPI_PROTOCOL_SOCKS,
+ ndpi_search_socks,
+ NDPI_SELECTION_BITMASK_PROTOCOL_V4_V6_TCP_WITH_PAYLOAD_WITHOUT_RETRANSMISSION,
+ SAVE_DETECTION_BITMASK_AS_UNKNOWN,
+ ADD_TO_DETECTION_BITMASK);
+
+ *id += 1;
+}
+
+#endif
diff --git a/src/lib/protocols/socks5.c b/src/lib/protocols/socks5.c
deleted file mode 100644
index f7cf89dfc..000000000
--- a/src/lib/protocols/socks5.c
+++ /dev/null
@@ -1,92 +0,0 @@
-/*
- * socks5.c
- *
- * Copyright (C) 2014 Tomasz Bujlow <tomasz@skatnet.dk>
- *
- * The signature is based on the Libprotoident library.
- *
- * This file is part of nDPI, an open source deep packet inspection
- * library based on the OpenDPI and PACE technology by ipoque GmbH
- *
- * nDPI is free software: you can redistribute it and/or modify
- * it under the terms of the GNU Lesser General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * nDPI is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with nDPI. If not, see <http://www.gnu.org/licenses/>.
- *
- */
-
-
-#include "ndpi_api.h"
-
-#ifdef NDPI_PROTOCOL_SOCKS5
-static void ndpi_int_socks5_add_connection(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow)
-{
- ndpi_set_detected_protocol(ndpi_struct, flow, NDPI_PROTOCOL_SOCKS5, NDPI_PROTOCOL_UNKNOWN);
-}
-
-static void ndpi_check_socks5(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow)
-{
- struct ndpi_packet_struct *packet = &flow->packet;
- u_int32_t payload_len = packet->payload_packet_len;
-
- /* Break after 20 packets. */
- if (flow->packet_counter > 20) {
- NDPI_LOG(NDPI_PROTOCOL_SOCKS5, ndpi_struct, NDPI_LOG_DEBUG, "Exclude SOCKS5.\n");
- NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask, NDPI_PROTOCOL_SOCKS5);
- return;
- }
-
- /* Check if we so far detected the protocol in the request or not. */
- if (flow->socks5_stage == 0) {
- NDPI_LOG(NDPI_PROTOCOL_SOCKS5, ndpi_struct, NDPI_LOG_DEBUG, "SOCKS5 stage 0: \n");
-
- if ((payload_len == 3) && (packet->payload[0] == 0x05) && (packet->payload[1] == 0x01) && (packet->payload[2] == 0x00)) {
- NDPI_LOG(NDPI_PROTOCOL_SOCKS5, ndpi_struct, NDPI_LOG_DEBUG, "Possible SOCKS5 request detected, we will look further for the response...\n");
-
- /* Encode the direction of the packet in the stage, so we will know when we need to look for the response packet. */
- flow->socks5_stage = packet->packet_direction + 1;
- }
-
- } else {
- NDPI_LOG(NDPI_PROTOCOL_SOCKS5, ndpi_struct, NDPI_LOG_DEBUG, "SOCKS5 stage %u: \n", flow->socks5_stage);
-
- /* At first check, if this is for sure a response packet (in another direction. If not, do nothing now and return. */
- if ((flow->socks5_stage - packet->packet_direction) == 1) {
- return;
- }
-
- /* This is a packet in another direction. Check if we find the proper response. */
- if ((payload_len == 0) || ((payload_len == 2) && (packet->payload[0] == 0x05) && (packet->payload[1] == 0x00))) {
- NDPI_LOG(NDPI_PROTOCOL_SOCKS5, ndpi_struct, NDPI_LOG_DEBUG, "Found SOCKS5.\n");
- ndpi_int_socks5_add_connection(ndpi_struct, flow);
- } else {
- NDPI_LOG(NDPI_PROTOCOL_SOCKS5, ndpi_struct, NDPI_LOG_DEBUG, "The reply did not seem to belong to SOCKS5, resetting the stage to 0...\n");
- flow->socks5_stage = 0;
- }
-
- }
-}
-
-void ndpi_search_socks5(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow)
-{
- struct ndpi_packet_struct *packet = &flow->packet;
-
- NDPI_LOG(NDPI_PROTOCOL_SOCKS5, ndpi_struct, NDPI_LOG_DEBUG, "SOCKS5 detection...\n");
-
- /* skip marked packets */
- if (packet->detected_protocol_stack[0] != NDPI_PROTOCOL_SOCKS5) {
- if (packet->tcp_retransmission == 0) {
- ndpi_check_socks5(ndpi_struct, flow);
- }
- }
-}
-
-#endif
diff --git a/src/lib/protocols/ssl.c b/src/lib/protocols/ssl.c
index bc0aa4f3c..2269ae782 100644
--- a/src/lib/protocols/ssl.c
+++ b/src/lib/protocols/ssl.c
@@ -92,11 +92,12 @@ static void ndpi_int_ssl_add_connection(struct ndpi_detection_module_struct *ndp
((ch) >= '{' && (ch) <= '~'))
static void stripCertificateTrailer(char *buffer, int buffer_len) {
- int i;
+
+ int i, is_puny;
// printf("->%s<-\n", buffer);
- for(i=0; i<buffer_len; i++) {
+ for(i = 0; i < buffer_len; i++) {
// printf("%c [%d]\n", buffer[i], buffer[i]);
if((buffer[i] != '.')
@@ -110,21 +111,28 @@ static void stripCertificateTrailer(char *buffer, int buffer_len) {
}
}
- if(i > 0) i--;
-
- while(i > 0) {
- if(!ndpi_isalpha(buffer[i])) {
- buffer[i] = '\0';
- buffer_len = i;
- i--;
- } else
- break;
- }
-
- for(i=buffer_len; i>0; i--) {
- if(buffer[i] == '.') break;
- else if(ndpi_isdigit(buffer[i]))
- buffer[i] = '\0', buffer_len = i;
+ /* check for punycode encoding */
+ is_puny = check_punycode_string(buffer, buffer_len);
+
+ // not a punycode string - need more checks
+ if(is_puny == 0) {
+
+ if(i > 0) i--;
+
+ while(i > 0) {
+ if(!ndpi_isalpha(buffer[i])) {
+ buffer[i] = '\0';
+ buffer_len = i;
+ i--;
+ } else
+ break;
+ }
+
+ for(i = buffer_len; i > 0; i--) {
+ if(buffer[i] == '.') break;
+ else if(ndpi_isdigit(buffer[i]))
+ buffer[i] = '\0', buffer_len = i;
+ }
}
}
diff --git a/src/lib/protocols/stun.c b/src/lib/protocols/stun.c
index 69e1cad52..e21f9331b 100644
--- a/src/lib/protocols/stun.c
+++ b/src/lib/protocols/stun.c
@@ -27,7 +27,7 @@
#ifdef NDPI_PROTOCOL_STUN
-#define MAX_NUM_STUN_PKTS 6
+#define MAX_NUM_STUN_PKTS 10
struct stun_packet_header {
@@ -55,8 +55,13 @@ static ndpi_int_stun_t ndpi_int_check_stun(struct ndpi_detection_module_struct *
u_int16_t msg_type, msg_len;
struct stun_packet_header *h = (struct stun_packet_header*)payload;
- if(payload_length < sizeof(struct stun_packet_header))
- return(NDPI_IS_NOT_STUN);
+ if(payload_length < sizeof(struct stun_packet_header)) {
+ if(flow->num_stun_udp_pkts > 0) {
+ *is_whatsapp = 1;
+ return NDPI_IS_STUN; /* This is WhatsApp Voice */
+ } else
+ return(NDPI_IS_NOT_STUN);
+ }
if((strncmp((const char*)payload, (const char*)"RSP/", 4) == 0)
&& (strncmp((const char*)&payload[7], (const char*)" STUN_", 6) == 0)) {
@@ -215,10 +220,7 @@ static ndpi_int_stun_t ndpi_int_check_stun(struct ndpi_detection_module_struct *
#endif
- if(
- ((flow->num_stun_udp_pkts > 0) && (msg_type == 0x0800))
- || ((msg_type == 0x0800) && (msg_len == 106))
- ) {
+ if((flow->num_stun_udp_pkts > 0) && (msg_type <= 0x00FF)) {
*is_whatsapp = 1;
return NDPI_IS_STUN; /* This is WhatsApp Voice */
} else
diff --git a/src/lib/protocols/tcp_udp.c b/src/lib/protocols/tcp_udp.c
index 9f9febfeb..2c6792551 100644
--- a/src/lib/protocols/tcp_udp.c
+++ b/src/lib/protocols/tcp_udp.c
@@ -30,6 +30,7 @@ u_int ndpi_search_tcp_or_udp_raw(struct ndpi_detection_module_struct *ndpi_struc
u_int16_t sport, u_int16_t dport) /* host endianess */
{
u_int16_t rc;
+ struct in_addr host;
if(protocol == IPPROTO_UDP) {
if((sport == dport) && (sport == 17500)) {
@@ -37,9 +38,12 @@ u_int ndpi_search_tcp_or_udp_raw(struct ndpi_detection_module_struct *ndpi_struc
}
}
- if((rc = ndpi_host_ptree_match(ndpi_struct, htonl(saddr))) != NDPI_PROTOCOL_UNKNOWN) return(rc);
-
- return(ndpi_host_ptree_match(ndpi_struct, htonl(daddr)));
+ host.s_addr = htonl(saddr);
+ if((rc = ndpi_network_ptree_match(ndpi_struct, &host)) != NDPI_PROTOCOL_UNKNOWN)
+ return (rc);
+
+ host.s_addr = htonl(daddr);
+ return (ndpi_network_ptree_match(ndpi_struct, &host));
}
void ndpi_search_tcp_or_udp(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow)
diff --git a/src/lib/protocols/tor.c b/src/lib/protocols/tor.c
index f2c2eae4c..f53e5da66 100644
--- a/src/lib/protocols/tor.c
+++ b/src/lib/protocols/tor.c
@@ -24,7 +24,7 @@ int ndpi_is_ssl_tor(struct ndpi_detection_module_struct *ndpi_struct,
if((certificate == NULL)
|| (strlen(certificate) < 6)
- || strncmp(certificate, "www.", 4))
+ || !(strncmp(certificate, "www.", 4)))
return(0);
// printf("***** [SSL] %s(): %s\n", __FUNCTION__, certificate);
diff --git a/src/lib/protocols/veohtv.c b/src/lib/protocols/veohtv.c
deleted file mode 100644
index a3ab267b9..000000000
--- a/src/lib/protocols/veohtv.c
+++ /dev/null
@@ -1,130 +0,0 @@
-/*
- * veohtv.c
- *
- * Copyright (C) 2009-2011 by ipoque GmbH
- * Copyright (C) 2011-15 - ntop.org
- *
- * This file is part of nDPI, an open source deep packet inspection
- * library based on the OpenDPI and PACE technology by ipoque GmbH
- *
- * nDPI is free software: you can redistribute it and/or modify
- * it under the terms of the GNU Lesser General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * nDPI is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with nDPI. If not, see <http://www.gnu.org/licenses/>.
- *
- */
-
-
-#include "ndpi_api.h"
-
-
-#ifdef NDPI_PROTOCOL_HTTP_APPLICATION_VEOHTV
-
-static void ndpi_int_veohtv_add_connection(struct ndpi_detection_module_struct *ndpi_struct,
- struct ndpi_flow_struct *flow/* , ndpi_protocol_type_t protocol_type */)
-{
- ndpi_set_detected_protocol(ndpi_struct, flow, NDPI_PROTOCOL_HTTP_APPLICATION_VEOHTV, NDPI_PROTOCOL_UNKNOWN);
-}
-
-void ndpi_search_veohtv_tcp(struct ndpi_detection_module_struct *ndpi_struct, struct ndpi_flow_struct *flow)
-{
- struct ndpi_packet_struct *packet = &flow->packet;
-
-// struct ndpi_id_struct *src=ndpi_struct->src;
-// struct ndpi_id_struct *dst=ndpi_struct->dst;
-
- if (packet->detected_protocol_stack[0] == NDPI_PROTOCOL_HTTP_APPLICATION_VEOHTV)
- return;
-
- if (flow->l4.tcp.veoh_tv_stage == 1 || flow->l4.tcp.veoh_tv_stage == 2) {
- if (packet->packet_direction != flow->setup_packet_direction &&
- packet->payload_packet_len > NDPI_STATICSTRING_LEN("HTTP/1.1 20")
- && memcmp(packet->payload, "HTTP/1.1 ", NDPI_STATICSTRING_LEN("HTTP/1.1 ")) == 0 &&
- (packet->payload[NDPI_STATICSTRING_LEN("HTTP/1.1 ")] == '2' ||
- packet->payload[NDPI_STATICSTRING_LEN("HTTP/1.1 ")] == '3' ||
- packet->payload[NDPI_STATICSTRING_LEN("HTTP/1.1 ")] == '4' ||
- packet->payload[NDPI_STATICSTRING_LEN("HTTP/1.1 ")] == '5')) {
-#ifdef NDPI_CONTENT_FLASH
- ndpi_parse_packet_line_info(ndpi_struct, flow);
- if (packet->detected_protocol_stack[0] == NDPI_CONTENT_FLASH &&
- packet->server_line.ptr != NULL &&
- packet->server_line.len > NDPI_STATICSTRING_LEN("Veoh-") &&
- memcmp(packet->server_line.ptr, "Veoh-", NDPI_STATICSTRING_LEN("Veoh-")) == 0) {
- NDPI_LOG(NDPI_PROTOCOL_HTTP_APPLICATION_VEOHTV, ndpi_struct, NDPI_LOG_DEBUG, "VeohTV detected.\n");
- ndpi_int_veohtv_add_connection(ndpi_struct, flow);
- return;
- }
-#endif
- if (flow->l4.tcp.veoh_tv_stage == 2) {
- NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask,
- NDPI_PROTOCOL_HTTP_APPLICATION_VEOHTV);
- return;
- }
- NDPI_LOG(NDPI_PROTOCOL_HTTP_APPLICATION_VEOHTV, ndpi_struct, NDPI_LOG_DEBUG, "VeohTV detected.\n");
- ndpi_int_veohtv_add_connection(ndpi_struct, flow);
- return;
- } else if (flow->packet_direction_counter[(flow->setup_packet_direction == 1) ? 0 : 1] > 3) {
- if (flow->l4.tcp.veoh_tv_stage == 2) {
- NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask,
- NDPI_PROTOCOL_HTTP_APPLICATION_VEOHTV);
- return;
- }
- NDPI_LOG(NDPI_PROTOCOL_HTTP_APPLICATION_VEOHTV, ndpi_struct, NDPI_LOG_DEBUG, "VeohTV detected.\n");
- ndpi_int_veohtv_add_connection(ndpi_struct, flow);
- return;
- } else {
- if (flow->packet_counter > 10) {
- if (flow->l4.tcp.veoh_tv_stage == 2) {
- NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask,
- NDPI_PROTOCOL_HTTP_APPLICATION_VEOHTV);
- return;
- }
- NDPI_LOG(NDPI_PROTOCOL_HTTP_APPLICATION_VEOHTV, ndpi_struct, NDPI_LOG_DEBUG, "VeohTV detected.\n");
- ndpi_int_veohtv_add_connection(ndpi_struct, flow);
- return;
- }
- return;
- }
- } else if (packet->udp) {
- /* UDP packets from Veoh Client Player
- *
- * packet starts with 16 byte random? value
- * then a 4 byte mode value
- * values between 21 and 26 has been seen
- * then a 4 byte counter */
-
- if (packet->payload_packet_len == 28 &&
- get_u_int32_t(packet->payload, 16) == htonl(0x00000021) &&
- get_u_int32_t(packet->payload, 20) == htonl(0x00000000) && get_u_int32_t(packet->payload, 24) == htonl(0x01040000)) {
- NDPI_LOG(NDPI_PROTOCOL_HTTP_APPLICATION_VEOHTV, ndpi_struct, NDPI_LOG_DEBUG, "UDP VeohTV found.\n");
- ndpi_int_veohtv_add_connection(ndpi_struct, flow);
- return;
- }
- }
-
-
- NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask, NDPI_PROTOCOL_HTTP_APPLICATION_VEOHTV);
-}
-
-
-void init_veohtv_dissector(struct ndpi_detection_module_struct *ndpi_struct, u_int32_t *id, NDPI_PROTOCOL_BITMASK *detection_bitmask)
-{
- ndpi_set_bitmask_protocol_detection("HTTP_APPLICATION_VEOHTV", ndpi_struct, detection_bitmask, *id,
- NDPI_PROTOCOL_HTTP_APPLICATION_VEOHTV,
- ndpi_search_veohtv_tcp,
- NDPI_SELECTION_BITMASK_PROTOCOL_V4_V6_TCP_OR_UDP_WITH_PAYLOAD_WITHOUT_RETRANSMISSION,
- SAVE_DETECTION_BITMASK_AS_UNKNOWN,
- ADD_TO_DETECTION_BITMASK);
-
- *id += 1;
-}
-
-#endif