Пример #1
0
static void ndpi_search_mysql_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->payload_packet_len > 37	//min length
		&& get_u_int16_t(packet->payload, 0) == packet->payload_packet_len - 4	//first 3 bytes are length
		&& get_u_int8_t(packet->payload, 2) == 0x00	//3rd byte of packet length
		&& get_u_int8_t(packet->payload, 3) == 0x00	//packet sequence number is 0 for startup packet
		&& get_u_int8_t(packet->payload, 5) > 0x30	//server version > 0
		&& get_u_int8_t(packet->payload, 5) < 0x37	//server version < 7
		&& get_u_int8_t(packet->payload, 6) == 0x2e	//dot
		) {
		u_int32_t a;
		for (a = 7; a + 31 < packet->payload_packet_len; a++) {
			if (packet->payload[a] == 0x00) {
				if (get_u_int8_t(packet->payload, a + 13) == 0x00	//filler byte
					&& get_u_int64_t(packet->payload, a + 19) == 0x0ULL	//13 more
					&& get_u_int32_t(packet->payload, a + 27) == 0x0	//filler bytes
					&& get_u_int8_t(packet->payload, a + 31) == 0x0) {
					NDPI_LOG(NDPI_PROTOCOL_MYSQL, ndpi_struct, NDPI_LOG_DEBUG, "MySQL detected.\n");
					ndpi_int_mysql_add_connection(ndpi_struct, flow);
					return;
				}
				break;
			}
		}
	}

	NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask, NDPI_PROTOCOL_MYSQL);

}
Пример #2
0
static void ndpi_search_rdp(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->payload_packet_len > 10
            && get_u_int8_t(packet->payload, 0) > 0
            && get_u_int8_t(packet->payload, 0) < 4 && get_u_int16_t(packet->payload, 2) == ntohs(packet->payload_packet_len)
            && get_u_int8_t(packet->payload, 4) == packet->payload_packet_len - 5
            && get_u_int8_t(packet->payload, 5) == 0xe0
            && get_u_int16_t(packet->payload, 6) == 0 && get_u_int16_t(packet->payload, 8) == 0 && get_u_int8_t(packet->payload, 10) == 0) {
        NDPI_LOG(NDPI_PROTOCOL_RDP, ndpi_struct, NDPI_LOG_DEBUG, "RDP detected.\n");
        ndpi_int_rdp_add_connection(ndpi_struct, flow);
        return;
    }

    NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask, NDPI_PROTOCOL_RDP);
}
Пример #3
0
static void ndpi_search_oscar_tcp_connect(struct ndpi_detection_module_struct
					  *ndpi_struct, struct ndpi_flow_struct *flow)
{
  struct ndpi_packet_struct *packet = &flow->packet;
	
  struct ndpi_id_struct *src = flow->src;
  struct ndpi_id_struct *dst = flow->dst;
  if (packet->payload_packet_len >= 10 && packet->payload[0] == 0x2a) {

    /* if is a oscar connection, 10 bytes long */

    /* OSCAR Connection :: Connection detected at initial packets only
     * +----+----+------+------+---------------+
     * |0x2a|Code|SeqNum|PktLen|ProtcolVersion |
     * +----+----+------+------+---------------+
     * Code 1 Byte : 0x01 Oscar Connection
     * SeqNum and PktLen are 2 Bytes each and ProtcolVersion: 0x00000001
     * */
    if (get_u_int8_t(packet->payload, 1) == 0x01 && get_u_int16_t(packet->payload, 4) == htons(packet->payload_packet_len - 6)
	&& get_u_int32_t(packet->payload, 6) == htonl(0x0000000001)) {
      NDPI_LOG(NDPI_PROTOCOL_OSCAR, ndpi_struct, NDPI_LOG_DEBUG, "OSCAR Connection FOUND \n");
      ndpi_int_oscar_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);
      return;
    }

    /* OSCAR IM
     * +----+----+------+------+----------+-----------+
     * |0x2a|Code|SeqNum|PktLen|FNACfamily|FNACsubtype|
     * +----+----+------+------+----------+-----------+
     * Code 1 Byte : 0x02 SNAC Header Code;
     * SeqNum and PktLen are 2 Bytes each
     * FNACfamily   2 Byte : 0x0004 IM Messaging
     * FNACEsubtype 2 Byte : 0x0006 IM Outgoing Message, 0x000c IM Message Acknowledgment
     * */
    if (packet->payload[1] == 0x02
	&& ntohs(get_u_int16_t(packet->payload, 4)) >=
	packet->payload_packet_len - 6 && get_u_int16_t(packet->payload, 6) == htons(0x0004)
	&& (get_u_int16_t(packet->payload, 8) == htons(0x0006)
	    || get_u_int16_t(packet->payload, 8) == htons(0x000c))) {
      NDPI_LOG(NDPI_PROTOCOL_OSCAR, ndpi_struct, NDPI_LOG_DEBUG, "OSCAR IM Detected \n");
      ndpi_int_oscar_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);
      return;
    }
  }


  /* detect http connections */
  if (packet->payload_packet_len >= 18) {
    if ((packet->payload[0] == 'P') && (memcmp(packet->payload, "POST /photo/upload", 18) == 0)) {
      NDPI_PARSE_PACKET_LINE_INFO(ndpi_struct, flow, packet);
      if (packet->host_line.len >= 18 && packet->host_line.ptr != NULL) {
	if (memcmp(packet->host_line.ptr, "lifestream.aol.com", 18) == 0) {
	  NDPI_LOG(NDPI_PROTOCOL_OSCAR, ndpi_struct, NDPI_LOG_DEBUG,
		   "OSCAR over HTTP found, POST method\n");
	  ndpi_int_oscar_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
	  return;
	}
      }
    }
  }
  if (packet->payload_packet_len > 40) {
    if ((packet->payload[0] == 'G') && (memcmp(packet->payload, "GET /", 5) == 0)) {
      if ((memcmp(&packet->payload[5], "aim/fetchEvents?aimsid=", 23) == 0) ||
	  (memcmp(&packet->payload[5], "aim/startSession?", 17) == 0) ||
	  (memcmp(&packet->payload[5], "aim/gromit/aim_express", 22) == 0) ||
	  (memcmp(&packet->payload[5], "b/ss/aolwpaim", 13) == 0) ||
	  (memcmp(&packet->payload[5], "hss/storage/aimtmpshare", 23) == 0)) {
	NDPI_LOG(NDPI_PROTOCOL_OSCAR, ndpi_struct, NDPI_LOG_DEBUG, "OSCAR over HTTP found, GET /aim/\n");
	ndpi_int_oscar_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
	return;
      }

      if ((memcmp(&packet->payload[5], "aim", 3) == 0) || (memcmp(&packet->payload[5], "im", 2) == 0)) {
	NDPI_PARSE_PACKET_LINE_INFO(ndpi_struct, flow, packet);
	if (packet->user_agent_line.len > 15 && packet->user_agent_line.ptr != NULL &&
	    ((memcmp(packet->user_agent_line.ptr, "mobileAIM/", 10) == 0) ||
	     (memcmp(packet->user_agent_line.ptr, "ICQ/", 4) == 0) ||
	     (memcmp(packet->user_agent_line.ptr, "mobileICQ/", 10) == 0) ||
	     (memcmp(packet->user_agent_line.ptr, "AIM%20Free/", NDPI_STATICSTRING_LEN("AIM%20Free/")) == 0) ||
	     (memcmp(packet->user_agent_line.ptr, "AIM/", 4) == 0))) {
	  NDPI_LOG(NDPI_PROTOCOL_OSCAR, ndpi_struct, NDPI_LOG_DEBUG, "OSCAR over HTTP found\n");
	  ndpi_int_oscar_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
	  return;
	}
      }
      NDPI_PARSE_PACKET_LINE_INFO(ndpi_struct, flow, packet);
      if (packet->referer_line.ptr != NULL && packet->referer_line.len >= 22) {

	if (memcmp(&packet->referer_line.ptr[packet->referer_line.len - NDPI_STATICSTRING_LEN("WidgetMain.swf")],
		   "WidgetMain.swf", NDPI_STATICSTRING_LEN("WidgetMain.swf")) == 0) {
	  u_int16_t i;
	  for (i = 0; i < (packet->referer_line.len - 22); i++) {
	    if (packet->referer_line.ptr[i] == 'a') {
	      if (memcmp(&packet->referer_line.ptr[i + 1], "im/gromit/aim_express", 21) == 0) {
		NDPI_LOG(NDPI_PROTOCOL_OSCAR, ndpi_struct, NDPI_LOG_DEBUG,
			 "OSCAR over HTTP found : aim/gromit/aim_express\n");
		ndpi_int_oscar_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
		return;
	      }
	    }
	  }
	}
      }
    }
    if (memcmp(packet->payload, "CONNECT ", 8) == 0) {
      if (memcmp(packet->payload, "CONNECT login.icq.com:443 HTTP/1.", 33) == 0) {
	NDPI_LOG(NDPI_PROTOCOL_OSCAR, ndpi_struct, NDPI_LOG_DEBUG, "OSCAR ICQ-HTTP FOUND\n");
	ndpi_int_oscar_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
	return;
      }
      if (memcmp(packet->payload, "CONNECT login.oscar.aol.com:5190 HTTP/1.", 40) == 0) {
	NDPI_LOG(NDPI_PROTOCOL_OSCAR, ndpi_struct, NDPI_LOG_DEBUG, "OSCAR AIM-HTTP FOUND\n");
	ndpi_int_oscar_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
	return;
      }

    }
  }

  if (packet->payload_packet_len > 43
      && memcmp(packet->payload, "GET http://http.proxy.icq.com/hello HTTP/1.", 43) == 0) {
    NDPI_LOG(NDPI_PROTOCOL_OSCAR, ndpi_struct, NDPI_LOG_DEBUG, "OSCAR ICQ-HTTP PROXY FOUND\n");
    ndpi_int_oscar_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
    return;
  }

  if (packet->payload_packet_len > 46
      && memcmp(packet->payload, "GET http://aimhttp.oscar.aol.com/hello HTTP/1.", 46) == 0) {
    NDPI_LOG(NDPI_PROTOCOL_OSCAR, ndpi_struct, NDPI_LOG_DEBUG, "OSCAR AIM-HTTP PROXY FOUND\n");
    ndpi_int_oscar_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
    return;
  }

  if (packet->payload_packet_len > 5 && get_u_int32_t(packet->payload, 0) == htonl(0x05010003)) {
    NDPI_LOG(NDPI_PROTOCOL_OSCAR, ndpi_struct, NDPI_LOG_DEBUG, "Maybe OSCAR Picturetransfer\n");
    return;
  }

  if (packet->payload_packet_len == 10 && get_u_int32_t(packet->payload, 0) == htonl(0x05000001) &&
      get_u_int32_t(packet->payload, 4) == 0) {
    NDPI_LOG(NDPI_PROTOCOL_OSCAR, ndpi_struct, NDPI_LOG_DEBUG, "Maybe OSCAR Picturetransfer\n");
    return;
  }

  if (packet->payload_packet_len >= 70 &&
      memcmp(&packet->payload[packet->payload_packet_len - 26],
	     "\x67\x00\x65\x00\x74\x00\x43\x00\x61\x00\x74\x00\x61\x00\x6c\x00\x6f\x00\x67", 19) == 0) {
    NDPI_LOG(NDPI_PROTOCOL_OSCAR, ndpi_struct, NDPI_LOG_DEBUG, "OSCAR PICTURE TRANSFER\n");
    ndpi_int_oscar_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);
    return;
  }

  if (NDPI_SRC_OR_DST_HAS_PROTOCOL(src, dst, NDPI_PROTOCOL_OSCAR) != 0) {

    if (flow->packet_counter == 1
	&&
	((packet->payload_packet_len == 9
	  && memcmp(packet->payload, "\x00\x09\x00\x00\x83\x01\xc0\x00\x00", 9) == 0)
	 || (packet->payload_packet_len == 13
	     && (memcmp(packet->payload, "\x00\x0d\x00\x87\x01\xc0", 6) == 0
		 || memcmp(packet->payload, "\x00\x0d\x00\x87\x01\xc1", 6) == 0)))) {
      flow->oscar_video_voice = 1;
    }
    if (flow->oscar_video_voice && ntohs(get_u_int16_t(packet->payload, 0)) == packet->payload_packet_len
	&& packet->payload[2] == 0x00 && packet->payload[3] == 0x00) {
    }

    if (packet->payload_packet_len >= 70 && ntohs(get_u_int16_t(packet->payload, 4)) == packet->payload_packet_len) {
      if (memcmp(packet->payload, "OFT", 3) == 0 &&
	  ((packet->payload[3] == '3' && ((memcmp(&packet->payload[4], "\x01\x00\x01\x01", 4) == 0)
					  || (memcmp(&packet->payload[6], "\x01\x01\x00", 3) == 0)))
	   || (packet->payload[3] == '2' && ((memcmp(&packet->payload[6], "\x01\x01", 2)
					      == 0)
					     )))) {
	// FILE TRANSFER PATTERN:: OFT3 or OFT2
	NDPI_LOG(NDPI_PROTOCOL_OSCAR, ndpi_struct, NDPI_LOG_DEBUG, "OSCAR FILE TRANSFER\n");
	ndpi_int_oscar_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);
	return;
      }

      if (memcmp(packet->payload, "ODC2", 4) == 0 && memcmp(&packet->payload[6], "\x00\x01\x00\x06", 4) == 0) {
	//PICTURE TRANSFER PATTERN EXMAPLE::
	//4f 44 43 32 00 4c 00 01 00 06 00 00 00 00 00 00  ODC2.L..........
	NDPI_LOG(NDPI_PROTOCOL_OSCAR, ndpi_struct, NDPI_LOG_DEBUG, "OSCAR PICTURE TRANSFER\n");
	ndpi_int_oscar_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);
	return;
      }
    }
    if (packet->payload_packet_len > 40 && (memcmp(&packet->payload[2], "\x04\x4a\x00", 3) == 0)
	&& (memcmp(&packet->payload[6], "\x00\x00", 2) == 0)
	&& packet->payload[packet->payload_packet_len - 15] == 'F'
	&& packet->payload[packet->payload_packet_len - 12] == 'L'
	&& (memcmp(&packet->payload[packet->payload_packet_len - 6], "DEST", 4) == 0)
	&& (memcmp(&packet->payload[packet->payload_packet_len - 2], "\x00\x00", 2) == 0)) {
      NDPI_LOG(NDPI_PROTOCOL_OSCAR, ndpi_struct, NDPI_LOG_DEBUG, "OSCAR PICTURE TRANSFER\n");
      ndpi_int_oscar_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);
      if (ntohs(packet->tcp->dest) == 443 || ntohs(packet->tcp->source) == 443) {
	flow->oscar_ssl_voice_stage = 1;
      }
      return;

    }
  }
  if (flow->packet_counter < 3 && packet->payload_packet_len > 11 && (memcmp(packet->payload, "\x00\x37\x04\x4a", 4)
								      || memcmp(packet->payload, "\x00\x0a\x04\x4a",
										4))) {
    return;
  }


  if (packet->detected_protocol_stack[0] != NDPI_PROTOCOL_OSCAR) {
    NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask, NDPI_PROTOCOL_OSCAR);
    return;
  }
}
Пример #4
0
static void ndpi_search_msn_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 = flow->src;
  struct ndpi_id_struct *dst = flow->dst;

  u_int16_t plen;
  u_int16_t status = 0;

  NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE, "search msn tcp.\n");
#ifdef NDPI_PROTOCOL_SSL
  if (packet->detected_protocol_stack[0] == NDPI_PROTOCOL_SSL) {
    NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE, "msn ssl ft test\n");
    if (flow->packet_counter < 10) {
    }

    if (flow->packet_counter == 7 && packet->payload_packet_len > 300) {
      if (memcmp(packet->payload + 24, "MSNSLP", 6) == 0
	  || (get_u_int32_t(packet->payload, 0) == htonl(0x30000000) && get_u_int32_t(packet->payload, 4) == 0x00000000)) {
	NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE, "detected MSN File Transfer, ifdef ssl.\n");
	ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);
	return;
      }
    }
    if (flow->packet_counter >= 5 && flow->packet_counter <= 10 && (get_u_int32_t(packet->payload, 0) == htonl(0x18000000)
								    && get_u_int32_t(packet->payload, 4) == 0x00000000)) {
      flow->l4.tcp.msn_ssl_ft++;
      NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE,
	       "increased msn ft ssl stage to: %u at packet nr: %u\n", flow->l4.tcp.msn_ssl_ft,
	       flow->packet_counter);
      if (flow->l4.tcp.msn_ssl_ft == 2) {
	NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE,
		 "detected MSN File Transfer, ifdef ssl 2.\n");
	ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);
      }
      return;
    }
  }
#endif



  /* we detect the initial connection only ! */
  /* match: "VER " ..... "CVR" x 0x0d 0x0a
   * len should be small, lets say less than 100 bytes
   * x is now "0", but can be increased
   */
  /* now we have a look at the first packet only. */
  if (flow->packet_counter == 1
#ifdef NDPI_PROTOCOL_SSL
      || ((packet->detected_protocol_stack[0] == NDPI_PROTOCOL_SSL) && flow->packet_counter <= 3)
#endif
      ) {

    /* this part is working asymmetrically */
    if (packet->payload_packet_len > 32 && (packet->payload[0] == 0x02 || packet->payload[0] == 0x00)
	&& (ntohl(get_u_int32_t(packet->payload, 8)) == 0x2112a442 || ntohl(get_u_int32_t(packet->payload, 4)) == 0x2112a442)
	&& ((ntohl(get_u_int32_t(packet->payload, 24)) == 0x000f0004 && ntohl(get_u_int32_t(packet->payload, 28)) == 0x72c64bc6)
	    || (ntohl(get_u_int32_t(packet->payload, 20)) == 0x000f0004
		&& ntohl(get_u_int32_t(packet->payload, 24)) == 0x72c64bc6))) {
      NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE,
	       "found MSN in packets that also contain voice.messenger.live.com.\n");

      /* TODO this is an alternative pattern for video detection */
      /*          if (packet->payload_packet_len > 100 &&
		  get_u_int16_t(packet->payload, 86) == htons(0x05dc)) { */
      if (packet->payload_packet_len > 101 && packet->payload[101] == 0x02) {
	ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
      } else {
	ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
      }

      return;
    }

    /* this case works asymmetrically */
    if (packet->payload_packet_len > 10 && packet->payload_packet_len < 100) {
      if (get_u_int8_t(packet->payload, packet->payload_packet_len - 2) == 0x0d
	  && get_u_int8_t(packet->payload, packet->payload_packet_len - 1) == 0x0a) {
	/* The MSNP string is used in XBOX clients. */
	if (memcmp(packet->payload, "VER ", 4) == 0) {

	  if (memcmp(&packet->payload[packet->payload_packet_len - 6], "CVR",
		     3) == 0 || memcmp(&packet->payload[packet->payload_packet_len - 8], "MSNP", 4) == 0) {
	    NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE,
		     "found MSN by pattern VER...CVR/MSNP ODOA.\n");
	    ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);
	    return;
	  }
	  if (memcmp(&packet->payload[4], "MSNFT", 5) == 0) {
	    NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE,
		     "found MSN FT by pattern VER MSNFT...0d0a.\n");
	    ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);
	    return;
	  }
	}
      }
    }

    if (
#ifdef NDPI_PROTOCOL_HTTP
	packet->detected_protocol_stack[0] == NDPI_PROTOCOL_HTTP ||
#endif
	memcmp(packet->payload, "GET ", NDPI_STATICSTRING_LEN("GET ")) == 0 ||
	memcmp(packet->payload, "POST ", NDPI_STATICSTRING_LEN("POST ")) == 0) {
      ndpi_parse_packet_line_info(ndpi_struct, flow);
      if (packet->user_agent_line.ptr != NULL &&
	  packet->user_agent_line.len > NDPI_STATICSTRING_LEN("Messenger/") &&
	  memcmp(packet->user_agent_line.ptr, "Messenger/", NDPI_STATICSTRING_LEN("Messenger/")) == 0) {
	ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
	return;
      }
    }
#ifdef NDPI_PROTOCOL_HTTP
    /* we have to examine two http packets */
    if (packet->detected_protocol_stack[0] == NDPI_PROTOCOL_HTTP) {
    }
#endif
    /* not seen this pattern in any trace */
    /* now test for http login, at least 100 a bytes packet */
    if (packet->payload_packet_len > 100) {
      if (
#ifdef NDPI_PROTOCOL_HTTP
	  packet->detected_protocol_stack[0] == NDPI_PROTOCOL_HTTP ||
#endif
	  memcmp(packet->payload, "POST http://", 12) == 0) {
	/* scan packet if not already done... */
	ndpi_parse_packet_line_info(ndpi_struct, flow);

	if (packet->content_line.ptr != NULL &&
	    ((packet->content_line.len == NDPI_STATICSTRING_LEN("application/x-msn-messenger") &&
	      memcmp(packet->content_line.ptr, "application/x-msn-messenger",
		     NDPI_STATICSTRING_LEN("application/x-msn-messenger")) == 0) ||
	     (packet->content_line.len >= NDPI_STATICSTRING_LEN("text/x-msnmsgr") &&
	      memcmp(packet->content_line.ptr, "text/x-msnmsgr",
		     NDPI_STATICSTRING_LEN("text/x-msnmsgr")) == 0))) {
	  NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE,
		   "found MSN by pattern POST http:// .... application/x-msn-messenger.\n");
	  ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
	  return;
	}
      }
    }

    /* now test for http login that uses a gateway, at least 400 a bytes packet */
    /* for this case the asymmetric detection is asym (1) */
    if (packet->payload_packet_len > 400) {
      if ((
#ifdef NDPI_PROTOCOL_HTTP
	   packet->detected_protocol_stack[0] == NDPI_PROTOCOL_HTTP ||
#endif
	   (memcmp(packet->payload, "POST ", 5) == 0))) {
	u_int16_t c;
	if (memcmp(&packet->payload[5], "http://", 7) == 0) {
	  /*
	   * We are searching for a paten "POST http://gateway.messenger.hotmail.com/gateway/gateway.dll" or
	   * "POST http://<some ip addres here like 172.0.0.0>/gateway/gateway.dll"
	   * POST http:// is 12 byte so we are searching for 13 to 70 byte for this paten.
	   */
	  for (c = 13; c < 50; c++) {
	    if (memcmp(&packet->payload[c], "/", 1) == 0) {
	      if (memcmp(&packet->payload[c], "/gateway/gateway.dll", 20) == 0) {
		NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE,
			 "found  pattern http://.../gateway/gateway.ddl.\n");
		status = 1;
		break;
	      }
	    }
	  }
	} else if ((memcmp(&packet->payload[5], "/gateway/gateway.dll", 20) == 0)) {
	  NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE,
		   "found  pattern http://.../gateway/gateway.ddl.\n");
	  status = 1;
	}
      }
      if (status) {
	u_int16_t a;

	ndpi_parse_packet_line_info(ndpi_struct, flow);

	if (packet->content_line.ptr != NULL
	    &&
	    ((packet->content_line.len == 23
	      && memcmp(packet->content_line.ptr, "text/xml; charset=utf-8", 23) == 0)
	     ||
	     (packet->content_line.len == 24
	      && memcmp(packet->content_line.ptr, "text/html; charset=utf-8", 24) == 0)
	     ||
	     (packet->content_line.len == 33
	      && memcmp(packet->content_line.ptr, "application/x-www-form-urlencoded", 33) == 0)
	     )) {
	  if ((src != NULL
	       && NDPI_COMPARE_PROTOCOL_TO_BITMASK(src->detected_protocol_bitmask, NDPI_PROTOCOL_MSN)
	       != 0) || (dst != NULL
			 && NDPI_COMPARE_PROTOCOL_TO_BITMASK(dst->detected_protocol_bitmask,
							     NDPI_PROTOCOL_MSN)
			 != 0)) {
	    NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE,
		     "found MSN with pattern text/xml; charset=utf-8.\n");
	    ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
	    return;
	  }
	  for (a = 0; a < packet->parsed_lines; a++) {
	    if (packet->line[a].len >= 4 &&
		(memcmp(packet->line[a].ptr, "CVR ", 4) == 0
		 || memcmp(packet->line[a].ptr, "VER ",
			   4) == 0 || memcmp(packet->line[a].ptr, "ANS ", 4) == 0)) {
	      NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE,
		       "found MSN with pattern text/sml; charset0utf-8.\n");
	      NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct,
		       NDPI_LOG_TRACE, "MSN xml CVS / VER / ANS found\n");
	      ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
	      return;
	    }
	  }
	}
      }
    }
    /* asym (1) ; possibly occurs in symmetric cases also. */
    if (flow->packet_counter <= 10 &&
	(flow->packet_direction_counter[0] <= 2 || flow->packet_direction_counter[1] <= 2)
	&& packet->payload_packet_len > 100) {
      /* not necessary to check the length, because this has been done : >400. */
      if (
#ifdef NDPI_PROTOCOL_HTTP
	  packet->detected_protocol_stack[0] == NDPI_PROTOCOL_HTTP ||
#endif
	  (memcmp(packet->payload, "HTTP/1.0 200 OK", 15) == 0) ||
	  (memcmp(packet->payload, "HTTP/1.1 200 OK", 15) == 0)
	  ) {

	ndpi_parse_packet_line_info(ndpi_struct, flow);

	if (packet->content_line.ptr != NULL &&
	    ((packet->content_line.len == NDPI_STATICSTRING_LEN("application/x-msn-messenger") &&
	      memcmp(packet->content_line.ptr, "application/x-msn-messenger",
		     NDPI_STATICSTRING_LEN("application/x-msn-messenger")) == 0) ||
	     (packet->content_line.len >= NDPI_STATICSTRING_LEN("text/x-msnmsgr") &&
	      memcmp(packet->content_line.ptr, "text/x-msnmsgr",
		     NDPI_STATICSTRING_LEN("text/x-msnmsgr")) == 0))) {
	  NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE,
		   "HTTP/1.0 200 OK .... application/x-msn-messenger.\n");
	  ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
	  return;
	}
	if (ndpi_int_find_xmsn(ndpi_struct, flow) == 1) {
	  NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE, "HTTP/1.0 200 OK .... X-MSN.\n");
	  ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
	  return;
	}
      }
    }


    /* did not find any trace with this pattern !!!!! */
    /* now block proxy connection */
    if (packet->payload_packet_len >= 42) {
      if (memcmp(packet->payload, "CONNECT messenger.hotmail.com:1863 HTTP/1.", 42) == 0) {
	NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE,
		 "found MSN  with pattern CONNECT messenger.hotmail.com:1863 HTTP/1..\n");
	ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
	return;
      }
    }

    if (packet->payload_packet_len >= 18) {

      if (memcmp(packet->payload, "USR ", 4) == 0 || memcmp(packet->payload, "ANS ", 4) == 0) {
	/* now we must see a number */
	const u_int16_t endlen = packet->payload_packet_len - 12;
	plen = 4;
	while (1) {
	  if (packet->payload[plen] == ' ') {
	    break;
	  }
	  if (packet->payload[plen] < '0' || packet->payload[plen] > '9') {
	    goto ndpi_msn_exclude;
	  }
	  plen++;
	  if (plen >= endlen) {
	    goto ndpi_msn_exclude;
	  }
	}

	while (plen < endlen) {
	  if (ndpi_check_for_email_address(ndpi_struct, flow, plen) != 0) {
	    NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE, "found mail address\n");
	    break;
	  }
	  if (packet->payload_packet_len > plen + 1
	      && (packet->payload[plen] < 20 || packet->payload[plen] > 128)) {
	    goto ndpi_msn_exclude;
	  }
	  plen++;
	  if (plen >= endlen) {
	    goto ndpi_msn_exclude;
	  }

	}
	NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE,
		 "found MSN  with pattern USR/ANS ...mail_address.\n");
	ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);
	return;
      }
    }
  }

  /* finished examining the first packet only. */


  /* asym (1) ; possibly occurs in symmetric cases also. */
  if (flow->packet_counter <= 10 &&
      (flow->packet_direction_counter[0] <= 2 || flow->packet_direction_counter[1] <= 2) &&
      packet->payload_packet_len > 100) {
    /* not necessary to check the length, because this has been done : >400. */
    if (
#ifdef NDPI_PROTOCOL_HTTP
	packet->detected_protocol_stack[0] == NDPI_PROTOCOL_HTTP ||
#endif
	(memcmp(packet->payload, "HTTP/1.0 200 OK", 15) == 0) ||
	(memcmp(packet->payload, "HTTP/1.1 200 OK", 15) == 0)
	) {

      ndpi_parse_packet_line_info(ndpi_struct, flow);

      if (packet->content_line.ptr != NULL &&
	  ((packet->content_line.len == NDPI_STATICSTRING_LEN("application/x-msn-messenger") &&
	    memcmp(packet->content_line.ptr, "application/x-msn-messenger",
		   NDPI_STATICSTRING_LEN("application/x-msn-messenger")) == 0) ||
	   (packet->content_line.len >= NDPI_STATICSTRING_LEN("text/x-msnmsgr") &&
	    memcmp(packet->content_line.ptr, "text/x-msnmsgr", NDPI_STATICSTRING_LEN("text/x-msnmsgr")) == 0))) {
	NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE,
		 "HTTP/1.0 200 OK .... application/x-msn-messenger.\n");
	ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
	return;
      }
      if (ndpi_int_find_xmsn(ndpi_struct, flow) == 1) {
	NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE, "HTTP/1.0 200 OK .... X-MSN.\n");
	ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_CORRELATED_PROTOCOL);
	return;
      }
    }
  }




  /* finished examining the secone packet only */
  /* direct user connection (file transfer,...) */

  if ((src != NULL && NDPI_COMPARE_PROTOCOL_TO_BITMASK(src->detected_protocol_bitmask, NDPI_PROTOCOL_MSN) != 0)
      || (dst != NULL
	  && NDPI_COMPARE_PROTOCOL_TO_BITMASK(dst->detected_protocol_bitmask, NDPI_PROTOCOL_MSN) != 0)) {
    if (flow->packet_counter == 1 &&
	packet->payload_packet_len > 12 && memcmp(packet->payload, "recipientid=", 12) == 0) {
      NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_DEBUG, "detected file transfer.\n");
      ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);
      return;
    }
  }

  /* MSN File Transfer of MSN 8.1 and 8.5
   * first packet with length 4 and pattern 0x04000000
   * second packet (in the same direction), with length 56 and pattern 0x00000000 from payload[16]
   * third packet (in the opposite direction to 1 & 2), with length 4 and pattern 0x30000000
   */
  if (flow->l4.tcp.msn_stage == 0) {
    /* asymmetric detection to this pattern is asym (2) */
    if ((packet->payload_packet_len == 4 || packet->payload_packet_len == 8)
	&& get_u_int32_t(packet->payload, 0) == htonl(0x04000000)) {
      NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_DEBUG, "maybe first TCP MSN detected\n");

      if (packet->payload_packet_len == 8 && get_u_int32_t(packet->payload, 4) == htonl(0x666f6f00)) {
	flow->l4.tcp.msn_stage = 5 + packet->packet_direction;
	return;
      }

      flow->l4.tcp.msn_stage = 1 + packet->packet_direction;
      return;
    }
    /* asymmetric detection to this pattern is asym (2) */
  } else if (flow->l4.tcp.msn_stage == 1 + packet->packet_direction) {
    if (packet->payload_packet_len > 10 && get_u_int32_t(packet->payload, 0) == htonl(0x666f6f00)) {
      ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);
      NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE, "MSN File Transfer detected 1\n");
      return;
    }
    /* did not see this pattern in any trace */
    if (packet->payload_packet_len == 56 && get_u_int32_t(packet->payload, 16) == 0) {
      NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_DEBUG, "maybe Second TCP MSN detected\n");
      flow->l4.tcp.msn_stage = 3 + packet->packet_direction;
      return;
    }


  } else if (flow->l4.tcp.msn_stage == 2 - packet->packet_direction
	     && packet->payload_packet_len == 4 && get_u_int32_t(packet->payload, 0) == htonl(0x30000000)) {
    ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);
    NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE, "MSN File Transfer detected 2\n");
    return;
  } else if ((flow->l4.tcp.msn_stage == 3 + packet->packet_direction)
	     || (flow->l4.tcp.msn_stage == 4 - packet->packet_direction)) {
    if (packet->payload_packet_len == 4 && get_u_int32_t(packet->payload, 0) == htonl(0x30000000)) {
      ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);
      NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE, "MSN File Transfer detected 2\n");
      return;
    }
  } else if (flow->l4.tcp.msn_stage == 6 - packet->packet_direction) {
    if ((packet->payload_packet_len == 4) &&
	(get_u_int32_t(packet->payload, 0) == htonl(0x10000000) || get_u_int32_t(packet->payload, 0) == htonl(0x30000000))) {
      ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);
      NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE, "MSN File Transfer detected 3\n");
      return;
    }
  } else if (flow->l4.tcp.msn_stage == 5 + packet->packet_direction) {
    if ((packet->payload_packet_len == 20) && get_u_int32_t(packet->payload, 0) == htonl(0x10000000)) {
      ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);
      NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE, "MSN File Transfer detected 3\n");
      return;
    }
  }
  NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE, "msn 7.\n");
  if (flow->packet_counter <= MAX_PACKETS_FOR_MSN) {
    if (packet->tcp->source == htons(443)
	|| packet->tcp->dest == htons(443)) {
      if (packet->payload_packet_len > 300) {
	if (memcmp(&packet->payload[40], "INVITE MSNMSGR", 14) == 0
	    || memcmp(&packet->payload[56], "INVITE MSNMSGR", 14) == 0
	    || memcmp(&packet->payload[172], "INVITE MSNMSGR", 14) == 0) {
	  ndpi_int_msn_add_connection(ndpi_struct, flow, NDPI_REAL_PROTOCOL);

	  NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE, "MSN File Transfer detected 3\n");
	  return;
	}
      }
      return;
    }
    /* For no
       n port 443 flows exclude flow bitmask after first packet itself */
  }
  NDPI_LOG(NDPI_PROTOCOL_MSN, ndpi_struct, NDPI_LOG_TRACE, "exclude msn.\n");
 ndpi_msn_exclude:
  NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask, NDPI_PROTOCOL_MSN);
}
Пример #5
0
void ndpi_search_snmp(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->payload_packet_len > 32 && packet->payload[0] == 0x30) {
    int offset;
    switch (packet->payload[1]) {
    case 0x81:
      offset = 3;
      break;
    case 0x82:
      offset = 4;
      break;
    default:
      if (packet->payload[1] > 0x82) {
	NDPI_LOG(NDPI_PROTOCOL_SNMP, ndpi_struct, NDPI_LOG_DEBUG, "SNMP excluded, second byte is > 0x82\n");
	goto excl;
      }
      offset = 2;
    }

    if (get_u_int16_t(packet->payload, offset) != htons(0x0201)) {
      NDPI_LOG(NDPI_PROTOCOL_SNMP, ndpi_struct, NDPI_LOG_DEBUG, "SNMP excluded, 0x0201 pattern not found\n");
      goto excl;
    }

    if (packet->payload[offset + 2] >= 0x04) {
      NDPI_LOG(NDPI_PROTOCOL_SNMP, ndpi_struct, NDPI_LOG_DEBUG, "SNMP excluded, version > 3\n");
      goto excl;
    }

    if (flow->l4.udp.snmp_stage == 0) {
      if (packet->udp->dest == htons(161) || packet->udp->dest == htons(162)) {
	NDPI_LOG(NDPI_PROTOCOL_SNMP, ndpi_struct, NDPI_LOG_DEBUG, "SNMP detected due to port.\n");
	ndpi_int_snmp_add_connection(ndpi_struct, flow);
	return;
      }
      NDPI_LOG(NDPI_PROTOCOL_SNMP, ndpi_struct, NDPI_LOG_DEBUG, "SNMP stage 0.\n");
      if (packet->payload[offset + 2] == 3) {
	flow->l4.udp.snmp_msg_id = ntohs(get_u_int32_t(packet->payload, offset + 8));
      } else if (packet->payload[offset + 2] == 0) {
	flow->l4.udp.snmp_msg_id = get_u_int8_t(packet->payload, offset + 15);
      } else {
	flow->l4.udp.snmp_msg_id = ntohs(get_u_int16_t(packet->payload, offset + 15));
      }
      flow->l4.udp.snmp_stage = 1 + packet->packet_direction;
      return;
    } else if (flow->l4.udp.snmp_stage == 1 + packet->packet_direction) {
      if (packet->payload[offset + 2] == 0) {
	if (flow->l4.udp.snmp_msg_id != get_u_int8_t(packet->payload, offset + 15) - 1) {
	  NDPI_LOG(NDPI_PROTOCOL_SNMP, ndpi_struct, NDPI_LOG_DEBUG,
		   "SNMP v1 excluded, message ID doesn't match\n");
	  goto excl;
	}
      }
    } else if (flow->l4.udp.snmp_stage == 2 - packet->packet_direction) {
      NDPI_LOG(NDPI_PROTOCOL_SNMP, ndpi_struct, NDPI_LOG_DEBUG, "SNMP stage 1-2.\n");
      if (packet->payload[offset + 2] == 3) {
	if (flow->l4.udp.snmp_msg_id != ntohs(get_u_int32_t(packet->payload, offset + 8))) {
	  NDPI_LOG(NDPI_PROTOCOL_SNMP, ndpi_struct, NDPI_LOG_DEBUG,
		   "SNMP v3 excluded, message ID doesn't match\n");
	  goto excl;
	}
      } else if (packet->payload[offset + 2] == 0) {
	if (flow->l4.udp.snmp_msg_id != get_u_int8_t(packet->payload, offset + 15)) {
	  NDPI_LOG(NDPI_PROTOCOL_SNMP, ndpi_struct, NDPI_LOG_DEBUG,
		   "SNMP v1 excluded, message ID doesn't match\n");
	  goto excl;
	}
      } else {
	if (flow->l4.udp.snmp_msg_id != ntohs(get_u_int16_t(packet->payload, offset + 15))) {
	  NDPI_LOG(NDPI_PROTOCOL_SNMP, ndpi_struct, NDPI_LOG_DEBUG,
		   "SNMP v2 excluded, message ID doesn't match\n");
	  goto excl;
	}
      }
      NDPI_LOG(NDPI_PROTOCOL_SNMP, ndpi_struct, NDPI_LOG_DEBUG, "SNMP detected.\n");
      ndpi_int_snmp_add_connection(ndpi_struct, flow);
      return;
    }
  } else {
    NDPI_LOG(NDPI_PROTOCOL_SNMP, ndpi_struct, NDPI_LOG_DEBUG, "SNMP excluded.\n");
  }
 excl:
  NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask, NDPI_PROTOCOL_SNMP);

}
Пример #6
0
static void ndpi_search_irc_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 = flow->src;
  struct ndpi_id_struct *dst = flow->dst;
  int less;
  u_int16_t c = 0;
  u_int16_t c1 = 0;
  u_int16_t port = 0;
  u_int16_t sport = 0;
  u_int16_t dport = 0;
  u_int16_t counter = 0;
  u_int16_t i = 0;
  u_int16_t j = 0;
  u_int16_t k = 0;
  u_int16_t h;
  u_int16_t http_content_ptr_len = 0;
  u_int8_t space = 0;

  NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_DEBUG, "irc : search irc\n");
  if (flow->detected_protocol_stack[0] != NDPI_PROTOCOL_IRC && flow->packet_counter > 70) {
    NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_DEBUG, "exclude irc, packet_counter > 70\n");
    NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask, NDPI_PROTOCOL_IRC);
    return;
  }
  if (flow->detected_protocol_stack[0] != NDPI_PROTOCOL_IRC && flow->packet_counter > 30 &&
      flow->l4.tcp.irc_stage2 == 0) {
    NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_DEBUG, "packet_counter > 30, exclude irc.\n");
    NDPI_ADD_PROTOCOL_TO_BITMASK(flow->excluded_protocol_bitmask, NDPI_PROTOCOL_IRC);
    return;
  }
  if (packet->detected_protocol_stack[0] == NDPI_PROTOCOL_IRC) {
    if (src != NULL && ((u_int32_t)
			(packet->tick_timestamp - src->irc_ts) < ndpi_struct->irc_timeout)) {
      NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_DEBUG, "irc : save src connection packet detected\n");
      src->irc_ts = packet->tick_timestamp;
    } else if (dst != NULL && ((u_int32_t)
			       (packet->tick_timestamp - dst->irc_ts) < ndpi_struct->irc_timeout)) {
      NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_DEBUG, "irc : save dst connection packet detected\n");
      dst->irc_ts = packet->tick_timestamp;
    }
  }

  if (((dst != NULL && NDPI_COMPARE_PROTOCOL_TO_BITMASK(dst->detected_protocol_bitmask, NDPI_PROTOCOL_IRC)
	&& ((u_int32_t)
	    (packet->tick_timestamp - dst->irc_ts)) <
	ndpi_struct->irc_timeout)) || (src != NULL
				       &&
				       NDPI_COMPARE_PROTOCOL_TO_BITMASK
				       (src->detected_protocol_bitmask, NDPI_PROTOCOL_IRC)
				       && ((u_int32_t)
					   (packet->tick_timestamp - src->irc_ts)) < ndpi_struct->irc_timeout)) {
    if (packet->tcp != NULL) {
      sport = packet->tcp->source;
      dport = packet->tcp->dest;
    }
    if (dst != NULL) {
      for (counter = 0; counter < dst->irc_number_of_port; counter++) {
	if (dst->irc_port[counter] == sport || dst->irc_port[counter] == dport) {
	  dst->last_time_port_used[counter] = packet->tick_timestamp;
	  NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE,
		   "dest port matched with the DCC port and the flow is marked as IRC");
	  ndpi_int_irc_add_connection(ndpi_struct, flow);
	  return;
	}
      }
    }
    if (src != NULL) {
      for (counter = 0; counter < src->irc_number_of_port; counter++) {
	if (src->irc_port[counter] == sport || src->irc_port[counter] == dport) {
	  src->last_time_port_used[counter] = packet->tick_timestamp;
	  ndpi_int_irc_add_connection(ndpi_struct, flow);
	  NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE,
		   "Source port matched with the DCC port and the flow is marked as IRC");
	  return;
	}
      }
    }
  }



  if (flow->detected_protocol_stack[0] != NDPI_PROTOCOL_IRC
      && flow->packet_counter == 2 && (packet->payload_packet_len > 400 && packet->payload_packet_len < 1381)) {
    for (c1 = 50; c1 < packet->payload_packet_len - 23; c1++) {
      if (packet->payload[c1] == 'i' || packet->payload[c1] == 'd') {
	if ((memcmp(&packet->payload[c1], "irc.hackthissite.org0", 21)
	     == 0)
	    || (memcmp(&packet->payload[c1], "irc.gamepad.ca1", 15) == 0)
	    || (memcmp(&packet->payload[c1], "dungeon.axenet.org0", 19)
		== 0)
	    || (memcmp(&packet->payload[c1], "dazed.nuggethaus.net", 20)
		== 0)
	    || (memcmp(&packet->payload[c1], "irc.indymedia.org", 17)
		== 0)
	    || (memcmp(&packet->payload[c1], "irc.cccp-project.net", 20)
		== 0)
	    || (memcmp(&packet->payload[c1], "dirc.followell.net0", 19)
		== 0)
	    || (memcmp(&packet->payload[c1], "irc.discostars.de1", 18)
		== 0)
	    || (memcmp(&packet->payload[c1], "irc.rizon.net", 13) == 0)) {
	  NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE,
		   "IRC SSL detected with :- irc.hackthissite.org0 | irc.gamepad.ca1 | dungeon.axenet.org0 "
		   "| dazed.nuggethaus.net | irc.indymedia.org | irc.discostars.de1 ");
	  ndpi_int_irc_add_connection(ndpi_struct, flow);
	  break;
	}
      }
    }
  }
  if (flow->detected_protocol_stack[0] != NDPI_PROTOCOL_IRC &&
      ndpi_search_irc_ssl_detect_ninty_percent_but_very_fast(ndpi_struct, flow) != 0) {
    return;
  }

  if (flow->detected_protocol_stack[0] != NDPI_PROTOCOL_IRC && flow->packet_counter < 20
      && packet->payload_packet_len >= 8) {
    if (get_u_int8_t(packet->payload, packet->payload_packet_len - 1) == 0x0a
	|| (ntohs(get_u_int16_t(packet->payload, packet->payload_packet_len - 2)) == 0x0a00)) {
      if (memcmp(packet->payload, ":", 1) == 0) {
	if (packet->payload[packet->payload_packet_len - 2] != 0x0d
	    && packet->payload[packet->payload_packet_len - 1] == 0x0a) {
	  ndpi_parse_packet_line_info_unix(ndpi_struct, flow);
	  packet->parsed_lines = packet->parsed_unix_lines;
	  for (i = 0; i < packet->parsed_lines; i++) {
	    packet->line[i] = packet->unix_line[i];
	    packet->line[i].ptr = packet->unix_line[i].ptr;
	    packet->line[i].len = packet->unix_line[i].len;
	  }
	} else if (packet->payload[packet->payload_packet_len - 2] == 0x0d) {
	  ndpi_parse_packet_line_info(ndpi_struct, flow);
	} else {
	  flow->l4.tcp.irc_3a_counter++;
	}
	for (i = 0; i < packet->parsed_lines; i++) {
	  if (packet->line[i].ptr[0] == ':') {
	    flow->l4.tcp.irc_3a_counter++;
	    if (flow->l4.tcp.irc_3a_counter == 7) {	/* ':' == 0x3a */
	      NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE, "0x3a. seven times. found irc.");
	      ndpi_int_irc_add_connection(ndpi_struct, flow);
	      goto detected_irc;
	    }
	  }
	}
	if (flow->l4.tcp.irc_3a_counter == 7) {	/* ':' == 0x3a */
	  NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE, "0x3a. seven times. found irc.");
	  ndpi_int_irc_add_connection(ndpi_struct, flow);
	  goto detected_irc;
	}
      }
      if ((memcmp(packet->payload, "USER ", 5) == 0)
	  || (memcmp(packet->payload, "NICK ", 5) == 0)
	  || (memcmp(packet->payload, "PASS ", 5) == 0)
	  || (memcmp(packet->payload, ":", 1) == 0 && ndpi_check_for_NOTICE_or_PRIVMSG(ndpi_struct, flow) != 0)
	  || (memcmp(packet->payload, "PONG ", 5) == 0)
	  || (memcmp(packet->payload, "PING ", 5) == 0)
	  || (memcmp(packet->payload, "JOIN ", 5) == 0)
	  || (memcmp(packet->payload, "NOTICE ", 7) == 0)
	  || (memcmp(packet->payload, "PRIVMSG ", 8) == 0)
	  || (memcmp(packet->payload, "VERSION ", 8) == 0)) {
	NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE,
		 "USER, NICK, PASS, NOTICE, PRIVMSG one time");
	if (flow->l4.tcp.irc_stage == 2) {
	  NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE, "found irc");
	  ndpi_int_irc_add_connection(ndpi_struct, flow);
	  flow->l4.tcp.irc_stage = 3;
	}
	if (flow->l4.tcp.irc_stage == 1) {
	  NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE, "second time, stage=2");
	  flow->l4.tcp.irc_stage = 2;
	}
	if (flow->l4.tcp.irc_stage == 0) {
	  NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE, "first time, stage=1");
	  flow->l4.tcp.irc_stage = 1;
	}
	/* irc packets can have either windows line breaks (0d0a) or unix line breaks (0a) */
	if (packet->payload[packet->payload_packet_len - 2] == 0x0d
	    && packet->payload[packet->payload_packet_len - 1] == 0x0a) {
	  ndpi_parse_packet_line_info(ndpi_struct, flow);
	  if (packet->parsed_lines > 1) {
	    NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE,
		     "packet contains more than one line");
	    for (c = 1; c < packet->parsed_lines; c++) {
	      if (packet->line[c].len > 4 && (memcmp(packet->line[c].ptr, "NICK ", 5) == 0
					      || memcmp(packet->line[c].ptr, "USER ", 5) == 0)) {
		NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct,
			 NDPI_LOG_TRACE, "two icq signal words in the same packet");
		ndpi_int_irc_add_connection(ndpi_struct, flow);
		flow->l4.tcp.irc_stage = 3;
		return;
	      }
	    }
	  }

	} else if (packet->payload[packet->payload_packet_len - 1] == 0x0a) {
	  ndpi_parse_packet_line_info_unix(ndpi_struct, flow);
	  if (packet->parsed_unix_lines > 1) {
	    NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE,
		     "packet contains more than one line");
	    for (c = 1; c < packet->parsed_unix_lines; c++) {
	      if (packet->unix_line[c].len > 4 && (memcmp(packet->unix_line[c].ptr, "NICK ", 5) == 0
						   || memcmp(packet->unix_line[c].ptr, "USER ",
							     5) == 0)) {
		NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE,
			 "two icq signal words in the same packet");
		ndpi_int_irc_add_connection(ndpi_struct, flow);
		flow->l4.tcp.irc_stage = 3;
		return;
	      }
	    }
	  }
	}
      }
    }
  }

  /**
   * Trying to primarily detect the HTTP Web based IRC chat patterns based on the HTTP headers
   * during the User login time.When the HTTP data gets posted using the POST method ,patterns
   * will be searched in the HTTP content.
   */
  if ((flow->detected_protocol_stack[0] != NDPI_PROTOCOL_IRC) && (flow->l4.tcp.irc_stage == 0)
      && (packet->payload_packet_len > 5)) {
    //HTTP POST Method being employed
    if (memcmp(packet->payload, "POST ", 5) == 0) {
      ndpi_parse_packet_line_info(ndpi_struct, flow);
      if (packet->parsed_lines) {
	u_int16_t http_header_len = (packet->line[packet->parsed_lines - 1].ptr - packet->payload) + 2;
	if (packet->payload_packet_len > http_header_len) {
	  http_content_ptr_len = packet->payload_packet_len - http_header_len;
	}
	if ((ndpi_check_for_IRC_traces(packet->line[0].ptr, packet->line[0].len))
	    || ((packet->http_url_name.ptr)
		&& (ndpi_check_for_IRC_traces(packet->http_url_name.ptr, packet->http_url_name.len)))
	    || ((packet->referer_line.ptr)
		&& (ndpi_check_for_IRC_traces(packet->referer_line.ptr, packet->referer_line.len)))) {
	  NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE,
		   "IRC detected from the Http URL/ Referer header ");
	  flow->l4.tcp.irc_stage = 1;
	  // HTTP POST Request body is not in the same packet.
	  if (!http_content_ptr_len) {
	    return;
	  }
	}
      }
    }
  }

  if ((flow->detected_protocol_stack[0] != NDPI_PROTOCOL_IRC) && (flow->l4.tcp.irc_stage == 1)) {
    if ((((packet->payload_packet_len - http_content_ptr_len) > 10)
	 && (memcmp(packet->payload + http_content_ptr_len, "interface=", 10) == 0)
	 && (ndpi_check_for_Nickname(ndpi_struct, flow) != 0))
	|| (((packet->payload_packet_len - http_content_ptr_len) > 5)
	    && (memcmp(packet->payload + http_content_ptr_len, "item=", 5) == 0)
	    && (ndpi_check_for_cmd(ndpi_struct, flow) != 0))) {
      NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE, "IRC Nickname, cmd,  one time");
      ndpi_int_irc_add_connection(ndpi_struct, flow);
      return;
    }
  }

 detected_irc:
  NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_DEBUG, "detected_irc:");

  if (flow->detected_protocol_stack[0] == NDPI_PROTOCOL_IRC) {
    /* maybe this can be deleted at the end */

    if (packet->payload[packet->payload_packet_len - 2] != 0x0d
	&& packet->payload[packet->payload_packet_len - 1] == 0x0a) {
      NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_DEBUG,
	       "ndpi_parse_packet_line_info_unix(ndpi_struct, flow);");
      ndpi_parse_packet_line_info_unix(ndpi_struct, flow);
      packet->parsed_lines = packet->parsed_unix_lines;
      for (i = 0; i < packet->parsed_lines; i++) {
	packet->line[i] = packet->unix_line[i];
	packet->line[i].ptr = packet->unix_line[i].ptr;
	packet->line[i].len = packet->unix_line[i].len;
      }
    } else if (packet->payload[packet->payload_packet_len - 2] == 0x0d) {
      ndpi_parse_packet_line_info(ndpi_struct, flow);
    } else {
      return;
    }
    for (i = 0; i < packet->parsed_lines; i++) {
      if (packet->line[i].len > 6 && memcmp(packet->line[i].ptr, "NOTICE ", 7) == 0) {
	NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_DEBUG, "NOTICE");
	for (j = 7; j < packet->line[i].len - 8; j++) {
	  if (packet->line[i].ptr[j] == ':') {
	    if (memcmp(&packet->line[i].ptr[j + 1], "DCC SEND ", 9) == 0
		|| memcmp(&packet->line[i].ptr[j + 1], "DCC CHAT ", 9) == 0) {
	      NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE,
		       "found NOTICE and DCC CHAT or DCC SEND.");
	    }
	  }
	}
      }
      if (packet->payload_packet_len > 0 && packet->payload[0] == 0x3a /* 0x3a = ':' */ ) {
	NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_DEBUG, "3a");
	for (j = 1; j < packet->line[i].len - 9; j++) {
	  if (packet->line[i].ptr[j] == ' ') {
	    j++;
	    if (packet->line[i].ptr[j] == 'P') {
	      NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_DEBUG, "P");
	      j++;
	      if (memcmp(&packet->line[i].ptr[j], "RIVMSG ", 7) == 0)
		NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_DEBUG, "RIVMSG");
	      h = j + 7;
	      goto read_privmsg;
	    }
	  }
	}
      }
      if (packet->line[i].len > 7 && (memcmp(packet->line[i].ptr, "PRIVMSG ", 8) == 0)) {
	NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_DEBUG, "PRIVMSG	");
	h = 7;
      read_privmsg:
	for (j = h; j < packet->line[i].len - 9; j++) {
	  if (packet->line[i].ptr[j] == ':') {
	    if (memcmp(&packet->line[i].ptr[j + 1], "xdcc ", 5) == 0) {
	      NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE, "xdcc should match.");
	    }
	    j += 2;
	    if (memcmp(&packet->line[i].ptr[j], "DCC ", 4) == 0) {
	      j += 4;
	      NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE, "found DCC.");
	      if (memcmp(&packet->line[i].ptr[j], "SEND ", 5) == 0
		  || (memcmp(&packet->line[i].ptr[j], "CHAT", 4) == 0)
		  || (memcmp(&packet->line[i].ptr[j], "chat", 4) == 0)
		  || (memcmp(&packet->line[i].ptr[j], "sslchat", 7) == 0)
		  || (memcmp(&packet->line[i].ptr[j], "TSEND", 5) == 0)) {
		NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE,
			 "found CHAT,chat,sslchat,TSEND.");
		j += 4;

		while (packet->line[i].len > j &&
		       ((packet->line[i].ptr[j] >= 'a' && packet->line[i].ptr[j] <= 'z')
			|| (packet->line[i].ptr[j] >= 'A' && packet->line[i].ptr[j] <= 'Z')
			|| (packet->line[i].ptr[j] >= '0' && packet->line[i].ptr[j] <= '9')
			|| (packet->line[i].ptr[j] >= ' ')
			|| (packet->line[i].ptr[j] >= '.')
			|| (packet->line[i].ptr[j] >= '-'))) {

		  if (packet->line[i].ptr[j] == ' ') {
		    space++;
		    NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE, "space %u.", space);
		  }
		  if (space == 3) {
		    j++;
		    NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE, "read port.");
		    if (src != NULL) {
		      k = j;
		      port =
			ntohs_ndpi_bytestream_to_number
			(&packet->line[i].ptr[j], packet->payload_packet_len - j, &j);
		      NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE, "port %u.",
			       port);
		      j = k;
		      // hier jetzt überlegen, wie die ports abgespeichert werden sollen
		      if (src->irc_number_of_port < 16)
			NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE,
				 "src->irc_number_of_port < 16.");
		      if (src->irc_number_of_port < 16 && port != 0) {
			if (!ndpi_is_duplicate(src, port)) {
			  src->irc_port[src->irc_number_of_port]
			    = port;
			  src->irc_number_of_port++;
			  NDPI_LOG
			    (NDPI_PROTOCOL_IRC,
			     ndpi_struct,
			     NDPI_LOG_DEBUG, "found port=%d",
			     ntohs(get_u_int16_t(src->irc_port, 0)));
			  NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_DEBUG,
				   "jjeeeeeeeeeeeeeeeeeeeeeeeee");
			}
			src->irc_ts = packet->tick_timestamp;
		      } else if (port != 0 && src->irc_number_of_port == 16) {
			if (!ndpi_is_duplicate(src, port)) {
			  less = 0;
			  NDPI_IRC_FIND_LESS(src->last_time_port_used, less);
			  src->irc_port[less] = port;
			  NDPI_LOG
			    (NDPI_PROTOCOL_IRC,
			     ndpi_struct,
			     NDPI_LOG_DEBUG, "found port=%d",
			     ntohs(get_u_int16_t(src->irc_port, 0)));
			}
			src->irc_ts = packet->tick_timestamp;
		      }
		      if (dst == NULL) {
			break;
		      }
		    }
		    if (dst != NULL) {
		      port = ntohs_ndpi_bytestream_to_number
			(&packet->line[i].ptr[j], packet->payload_packet_len - j, &j);
		      NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_TRACE, "port %u.",
			       port);
		      // hier das gleiche wie oben.
		      /* hier werden 16 ports pro irc flows mitgespeichert. könnte man denn nicht ein-
		       * fach an die dst oder src einen flag setzten, dass dieser port für eine bestimmte
		       * zeit ein irc-port bleibt?
		       */
		      if (dst->irc_number_of_port < 16 && port != 0) {
			if (!ndpi_is_duplicate(dst, port)) {
			  dst->irc_port[dst->irc_number_of_port]
			    = port;
			  dst->irc_number_of_port++;
			  NDPI_LOG
			    (NDPI_PROTOCOL_IRC,
			     ndpi_struct,
			     NDPI_LOG_DEBUG, "found port=%d",
			     ntohs(get_u_int16_t(dst->irc_port, 0)));
			  NDPI_LOG(NDPI_PROTOCOL_IRC, ndpi_struct, NDPI_LOG_DEBUG,
				   "juuuuuuuuuuuuuuuu");
			}
			dst->irc_ts = packet->tick_timestamp;
		      } else if (port != 0 && dst->irc_number_of_port == 16) {
			if (!ndpi_is_duplicate(dst, port)) {
			  less = 0;
			  NDPI_IRC_FIND_LESS(dst->last_time_port_used, less);
			  dst->irc_port[less] = port;

			  NDPI_LOG
			    (NDPI_PROTOCOL_IRC,
			     ndpi_struct,
			     NDPI_LOG_DEBUG, "found port=%d",
			     ntohs(get_u_int16_t(dst->irc_port, 0)));
			}
			dst->irc_ts = packet->tick_timestamp;
		      }

		      break;
		    }
		  }


		  j++;
		}

	      }
	    }
	  }
	}

      }
    }
  }
}