aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/include/ndpi_typedefs.h4
-rw-r--r--src/lib/ndpi_main.c96
-rw-r--r--src/lib/ndpi_utils.c6
3 files changed, 95 insertions, 11 deletions
diff --git a/src/include/ndpi_typedefs.h b/src/include/ndpi_typedefs.h
index 82eaabcc3..2074181bf 100644
--- a/src/include/ndpi_typedefs.h
+++ b/src/include/ndpi_typedefs.h
@@ -1312,6 +1312,10 @@ struct ndpi_flow_struct {
ndpi_risk risk, risk_shadow; /* Issues found with this flow [bitmask of ndpi_risk] */
struct ndpi_risk_information risk_infos[MAX_NUM_RISK_INFOS]; /* String that contains information about the risks found */
u_int8_t num_risk_infos;
+
+ struct {
+ char *fingerprint;
+ } tcp;
/*
This structure below will not not stay inside the protos
diff --git a/src/lib/ndpi_main.c b/src/lib/ndpi_main.c
index bcd3520fb..3265ef80f 100644
--- a/src/lib/ndpi_main.c
+++ b/src/lib/ndpi_main.c
@@ -60,6 +60,8 @@
#define TH_PUSH 0x08
#define TH_ACK 0x10
#define TH_URG 0x20
+#define TH_ECE 0x40
+#define TH_CWR 0x80
#endif
#if defined __FreeBSD__ || defined __NetBSD__ || defined __OpenBSD__
@@ -4400,7 +4402,7 @@ void ndpi_exit_detection_module(struct ndpi_detection_module_struct *ndpi_str) {
if(ndpi_str->address_cache)
ndpi_term_address_cache(ndpi_str->address_cache);
-
+
ndpi_free(ndpi_str);
}
@@ -4794,7 +4796,7 @@ static int ndpi_handle_rule(struct ndpi_detection_module_struct *ndpi_str,
def = NULL;
else
def = &ndpi_str->proto_defaults[subprotocol_id];
-
+
if(def == NULL) {
ndpi_port_range ports_a[MAX_DEFAULT_PORTS], ports_b[MAX_DEFAULT_PORTS];
char *equal = strchr(proto, '=');
@@ -6724,6 +6726,9 @@ void ndpi_free_flow_data(struct ndpi_flow_struct* flow) {
ndpi_free(flow->risk_infos[i].info);
}
+ if(flow->tcp.fingerprint)
+ ndpi_free(flow->tcp.fingerprint);
+
if(flow->http.url)
ndpi_free(flow->http.url);
@@ -6904,14 +6909,86 @@ static int ndpi_init_packet(struct ndpi_detection_module_struct *ndpi_str,
/* TCP / UDP detection */
if(l4protocol == IPPROTO_TCP) {
+ u_int16_t header_len;
+
if(l4_packet_len < 20 /* min size of tcp */)
return(1);
/* tcp */
packet->tcp = (struct ndpi_tcphdr *) l4ptr;
- if(l4_packet_len >= packet->tcp->doff * 4) {
- packet->payload_packet_len = l4_packet_len - packet->tcp->doff * 4;
- packet->payload = ((u_int8_t *) packet->tcp) + (packet->tcp->doff * 4);
+ header_len = packet->tcp->doff * 4;
+
+ if(l4_packet_len >= header_len) {
+ if(flow->tcp.fingerprint == NULL) {
+ u_int8_t *t = (u_int8_t*)packet->tcp;
+ u_int16_t flags = ntohs(*((u_int16_t*)&t[12]));
+
+ if((flags & (TH_SYN | TH_ECE | TH_CWR)) == TH_SYN) {
+ u_int8_t *options = (u_int8_t*)(&t[sizeof(struct ndpi_tcphdr)]);
+ char fingerprint[128], options_fp[128];
+ u_int8_t i, fp_idx = 0, options_fp_idx = 0;
+ u_int8_t options_len = header_len - sizeof(struct ndpi_tcphdr);
+ u_int16_t tcp_win = ntohs(packet->tcp->window);
+ u_int8_t ip_ttl;
+ u_int8_t sha_hash[NDPI_SHA256_BLOCK_SIZE];
+
+ if(packet->iph)
+ ip_ttl = packet->iph->ttl;
+ else
+ ip_ttl = packet->iphv6->ip6_hdr.ip6_un1_hlim;
+
+ if(ip_ttl <= 32) ip_ttl = 32;
+ else if(ip_ttl <= 64) ip_ttl = 64;
+ else if(ip_ttl <= 128) ip_ttl = 128;
+ else if(ip_ttl <= 192) ip_ttl = 192;
+ else ip_ttl = 255;
+
+ fp_idx = snprintf(fingerprint, sizeof(fingerprint), "%u_%u_", ip_ttl, tcp_win);
+
+ for(i=0; i<options_len; ) {
+ u_int8_t kind = options[i];
+ int rc;
+
+ rc = snprintf(&options_fp[options_fp_idx], sizeof(options_fp)-options_fp_idx, "%02x", kind);
+ options_fp_idx += rc;
+
+ if(kind == 0) /* EOF */
+ break;
+ else if(kind == 1) /* NOP */
+ i++;
+ else {
+ u_int8_t len = options[i+1];
+
+ if(len == 0)
+ break;
+ else if(kind == 8) {
+ /* Timestamp: ignore it */
+ } else {
+ int j = i+2;
+ u_int8_t opt_len = len - 2;
+
+ while(opt_len > 0) {
+ rc = snprintf(&options_fp[options_fp_idx], sizeof(options_fp)-options_fp_idx, "%02x", options[j]);
+ options_fp_idx += rc;
+ j++, opt_len--;
+ }
+ }
+
+ i += len;
+ }
+ } /* for */
+
+ ndpi_sha256((const u_char*)options_fp, options_fp_idx, sha_hash);
+ snprintf(&fingerprint[fp_idx], sizeof(fingerprint)-fp_idx, "%02x%02x%02x%02x%02x%02x",
+ sha_hash[0], sha_hash[1], sha_hash[2],
+ sha_hash[3], sha_hash[4], sha_hash[5]);
+
+ flow->tcp.fingerprint = ndpi_strdup(fingerprint);
+ }
+ }
+
+ packet->payload_packet_len = l4_packet_len - header_len;
+ packet->payload = ((u_int8_t *) packet->tcp) + header_len;
} else {
/* tcp header not complete */
return(1);
@@ -7546,7 +7623,7 @@ static void ndpi_reconcile_msteams_udp(struct ndpi_detection_module_struct *ndpi
struct ndpi_flow_struct *flow,
u_int16_t master) {
/* This function can NOT access &ndpi_str->packet since it is called also from ndpi_detection_giveup(), via ndpi_reconcile_protocols() */
-
+
if(flow->l4_proto == IPPROTO_UDP) {
u_int16_t sport = ntohs(flow->c_port);
u_int16_t dport = ntohs(flow->s_port);
@@ -7694,7 +7771,7 @@ static void ndpi_reconcile_protocols(struct ndpi_detection_module_struct *ndpi_s
NDPI_CONFIDENCE_DPI_PARTIAL);
}
break;
-
+
case NDPI_PROTOCOL_SKYPE_TEAMS:
case NDPI_PROTOCOL_SKYPE_TEAMS_CALL:
if(flow->l4_proto == IPPROTO_UDP && ndpi_str->msteams_cache) {
@@ -9066,8 +9143,7 @@ struct header_line {
struct ndpi_int_one_line_struct *line;
};
-static void parse_single_packet_line(struct ndpi_detection_module_struct *ndpi_str)
-{
+static void parse_single_packet_line(struct ndpi_detection_module_struct *ndpi_str) {
struct ndpi_packet_struct *packet = &ndpi_str->packet;
struct ndpi_int_one_line_struct *line;
size_t length;
@@ -11366,7 +11442,7 @@ static const struct cfg_param {
{ "tls", "subclassification", "enable", NULL, NULL, CFG_PARAM_ENABLE_DISABLE, __OFF(tls_subclassification_enabled), NULL },
{ "quic", "subclassification", "enable", NULL, NULL, CFG_PARAM_ENABLE_DISABLE, __OFF(quic_subclassification_enabled), NULL },
-
+
{ "smtp", "tls_dissection", "enable", NULL, NULL, CFG_PARAM_ENABLE_DISABLE, __OFF(smtp_opportunistic_tls_enabled), NULL },
{ "imap", "tls_dissection", "enable", NULL, NULL, CFG_PARAM_ENABLE_DISABLE, __OFF(imap_opportunistic_tls_enabled), NULL },
diff --git a/src/lib/ndpi_utils.c b/src/lib/ndpi_utils.c
index 9b7cc387e..26efd20a2 100644
--- a/src/lib/ndpi_utils.c
+++ b/src/lib/ndpi_utils.c
@@ -1651,7 +1651,11 @@ int ndpi_flow2json(struct ndpi_detection_module_struct *ndpi_struct,
ndpi_serialize_string_uint32(serializer, "ip", ip_version);
- ndpi_serialize_string_string(serializer, "proto", ndpi_get_ip_proto_name(l4_protocol, l4_proto_name, sizeof(l4_proto_name)));
+ if(flow->tcp.fingerprint)
+ ndpi_serialize_string_string(serializer, "tcp_fingerprint", flow->tcp.fingerprint);
+
+ ndpi_serialize_string_string(serializer, "proto",
+ ndpi_get_ip_proto_name(l4_protocol, l4_proto_name, sizeof(l4_proto_name)));
return(ndpi_dpi2json(ndpi_struct, flow, l7_protocol, serializer));
}