Example #1
0
void
process_tcp(u_char * data, int skblen)
{
  struct ip *this_iphdr = (struct ip *)data;
  struct tcphdr *this_tcphdr = (struct tcphdr *)(data + 4 * this_iphdr->ip_hl);
  int datalen, iplen;
  int from_client = 1;
  unsigned int tmp_ts;
  struct tcp_stream *a_tcp;
  struct half_stream *snd, *rcv;

  ugly_iphdr = this_iphdr;
  iplen = ntohs(this_iphdr->ip_len);
  if ((unsigned)iplen < 4 * this_iphdr->ip_hl + sizeof(struct tcphdr)) {
    nids_params.syslog(NIDS_WARN_TCP, NIDS_WARN_TCP_HDR, this_iphdr,
		       this_tcphdr);
    return;
  } // ktos sie bawi
  
  datalen = iplen - 4 * this_iphdr->ip_hl - 4 * this_tcphdr->th_off;
  
  if (datalen < 0) {
    nids_params.syslog(NIDS_WARN_TCP, NIDS_WARN_TCP_HDR, this_iphdr,
		       this_tcphdr);
    return;
  } // ktos sie bawi

  if ((this_iphdr->ip_src.s_addr | this_iphdr->ip_dst.s_addr) == 0) {
    nids_params.syslog(NIDS_WARN_TCP, NIDS_WARN_TCP_HDR, this_iphdr,
		       this_tcphdr);
    return;
  }
  if (!(this_tcphdr->th_flags & TH_ACK))
    detect_scan(this_iphdr);
  if (!nids_params.n_tcp_streams) return;
  /*FIXME: remove the tcp header check function tempor..*/
#ifdef OSPLIT
#ifdef CHECK_TCPHDR_DISABLED
#if 0
  if (my_tcp_check(this_tcphdr, iplen - 4 * this_iphdr->ip_hl,
			  this_iphdr->ip_src.s_addr, this_iphdr->ip_dst.s_addr)) {
	  nids_params.syslog(NIDS_WARN_TCP, NIDS_WARN_TCP_HDR, this_iphdr,
			  this_tcphdr);
	  return;
  }
#endif
#else
  if (my_tcp_check(this_tcphdr, iplen - 4 * this_iphdr->ip_hl,
			  this_iphdr->ip_src.s_addr, this_iphdr->ip_dst.s_addr)) {
	  nids_params.syslog(NIDS_WARN_TCP, NIDS_WARN_TCP_HDR, this_iphdr,
			  this_tcphdr);
	  return;
  }
#endif
#endif
#if 0
  check_flags(this_iphdr, this_tcphdr);
//ECN
#endif
  if (!(a_tcp = find_stream(this_tcphdr, this_iphdr, &from_client))) {
    if ((this_tcphdr->th_flags & TH_SYN) &&
	!(this_tcphdr->th_flags & TH_ACK) &&
	!(this_tcphdr->th_flags & TH_RST))
      add_new_tcp(this_tcphdr, this_iphdr);
    return;
  }
 #ifdef OSPLIT
  struct ipfrag *frag_tag=this_fragments;
  struct ipfrag *ip_frag_next;
  if(this_fragments)
	  ip_frag_next=this_fragments->next;
  /*write all fragment(s) to fp trace file*/
  if(is_frag==0) {
	  write_pcap_hdr(a_tcp->fp,(char*)nids_last_pcap_header,sizeof(struct pcap_sf_pkthdr));
	  write_ip(a_tcp->fp,(char*)this_iphdr,ntohs(this_iphdr->ip_len),(char*)nids_last_pcap_header);
  }
  else {
	  /*fragments*/
	  while(frag_tag!=NULL) {
		  write_pcap_hdr(a_tcp->fp,(char*)(&(frag_tag->pcap_header)),sizeof(struct pcap_sf_pkthdr));
		  write_ip(a_tcp->fp,(char*)frag_tag->skb->data,frag_tag->wtrace_len,(char*)(&(frag_tag->pcap_header)));
		  free(frag_tag);
		  frag_tag=ip_frag_next;
		  if(ip_frag_next!=NULL)
			  ip_frag_next=ip_frag_next->next;
	  }
	  is_frag=0;
   }
	/*set statistic info*/
	store_flag=1;
 #endif
  if (from_client) {
    snd = &a_tcp->client;
    rcv = &a_tcp->server;
  }
  else {
    rcv = &a_tcp->client;
    snd = &a_tcp->server;
  }
  if ((this_tcphdr->th_flags & TH_SYN)) {
    if (from_client || a_tcp->client.state != TCP_SYN_SENT ||
      a_tcp->server.state != TCP_CLOSE || !(this_tcphdr->th_flags & TH_ACK))
      return;
    if (a_tcp->client.seq != ntohl(this_tcphdr->th_ack))
      return;
    a_tcp->server.state = TCP_SYN_RECV;
    a_tcp->server.seq = ntohl(this_tcphdr->th_seq) + 1;
    a_tcp->server.first_data_seq = a_tcp->server.seq;
    a_tcp->server.ack_seq = ntohl(this_tcphdr->th_ack);
    a_tcp->server.window = ntohs(this_tcphdr->th_win);
    if (a_tcp->client.ts_on) {
    	a_tcp->server.ts_on = get_ts(this_tcphdr, &a_tcp->server.curr_ts);
	if (!a_tcp->server.ts_on)
		a_tcp->client.ts_on = 0;
    } else a_tcp->server.ts_on = 0;	
    if (a_tcp->client.wscale_on) {
    	a_tcp->server.wscale_on = get_wscale(this_tcphdr, &a_tcp->server.wscale);
	if (!a_tcp->server.wscale_on) {
		a_tcp->client.wscale_on = 0;
		a_tcp->client.wscale  = 1;
		a_tcp->server.wscale = 1;
	}	
    } else {
    	a_tcp->server.wscale_on = 0;	
    	a_tcp->server.wscale = 1;
    }	
    return;
  }
  if (
  	! (  !datalen && ntohl(this_tcphdr->th_seq) == rcv->ack_seq  )
  	&&
  	( !before(ntohl(this_tcphdr->th_seq), rcv->ack_seq + rcv->window*rcv->wscale) ||
          before(ntohl(this_tcphdr->th_seq) + datalen, rcv->ack_seq)  
        )
     )     
     return;

  if ((this_tcphdr->th_flags & TH_RST)) {
    if (a_tcp->nids_state == NIDS_DATA) {
      struct lurker_node *i;

      a_tcp->nids_state = NIDS_RESET;
      for (i = a_tcp->listeners; i; i = i->next)
	(i->item) (a_tcp, &i->data);
    }
    nids_free_tcp_stream(a_tcp);
    return;
  }

  /* PAWS check */
  if (rcv->ts_on && get_ts(this_tcphdr, &tmp_ts) && 
  	before(tmp_ts, snd->curr_ts))
  return; 	
  
  if ((this_tcphdr->th_flags & TH_ACK)) {
    if (from_client && a_tcp->client.state == TCP_SYN_SENT &&
	a_tcp->server.state == TCP_SYN_RECV) {
      if (ntohl(this_tcphdr->th_ack) == a_tcp->server.seq) {
	a_tcp->client.state = TCP_ESTABLISHED;
	a_tcp->client.ack_seq = ntohl(this_tcphdr->th_ack);
	{
	  struct proc_node *i;
	  struct lurker_node *j;
	  void *data;
	  
	  a_tcp->server.state = TCP_ESTABLISHED;
	  a_tcp->nids_state = NIDS_JUST_EST;
	  for (i = tcp_procs; i; i = i->next) {
	    char whatto = 0;
	    char cc = a_tcp->client.collect;
	    char sc = a_tcp->server.collect;
	    char ccu = a_tcp->client.collect_urg;
	    char scu = a_tcp->server.collect_urg;
	    
	    (i->item) (a_tcp, &data);
	    if (cc < a_tcp->client.collect)
	      whatto |= COLLECT_cc;
	    if (ccu < a_tcp->client.collect_urg)
	      whatto |= COLLECT_ccu;
	    if (sc < a_tcp->server.collect)
	      whatto |= COLLECT_sc;
	    if (scu < a_tcp->server.collect_urg)
	      whatto |= COLLECT_scu;
	    if (nids_params.one_loop_less) {
	    		if (a_tcp->client.collect >=2) {
	    			a_tcp->client.collect=cc;
	    			whatto&=~COLLECT_cc;
	    		}
	    		if (a_tcp->server.collect >=2 ) {
	    			a_tcp->server.collect=sc;
	    			whatto&=~COLLECT_sc;
	    		}
	    }  
	    if (whatto) {
	      j = mknew(struct lurker_node);
	      j->item = i->item;
	      j->data = data;
	      j->whatto = whatto;
	      j->next = a_tcp->listeners;
	      a_tcp->listeners = j;
	    }
	  }
 #ifdef OSPLIT
 #if 0
	  if (!a_tcp->listeners) {
	    nids_free_tcp_stream(a_tcp);
	    return;
	  }
#endif
 #endif
	  a_tcp->nids_state = NIDS_DATA;
	}
      }
      // return;
    }
  }
Example #2
0
// ------------------------------------------------
// Function:        dhcp_send()
// ------------------------------------------------
// Input:           Message type
//                  TRUE to broadcast answer
// Output:          TRUE if succesful
// ------------------------------------------------
// Description:     Send a DHCP message
// ------------------------------------------------
BOOL dhcp_send(BYTE type, BOOL broadcast)
{
    PPBUF buf;

    buf = udp_new(SOCKET_DHCP);
    if(buf == NULL) return FALSE;

    DHCP(buf->data)->op = 1;                            // BOOTREQUEST
    DHCP(buf->data)->htype = 1;                         // ETH 10MBPS
    DHCP(buf->data)->hlen = 6;                          // 6 bytes ETH MAC
    DHCP(buf->data)->hops = 0;
    DHCP(buf->data)->xid = xid.d;
    DHCP(buf->data)->secs = 0;

    if(broadcast) {
        DHCP(buf->data)->flags = HTONS(0x8000);         // server must broadcast answer
        DHCP(buf->data)->ci.d = 0;
    } else {
        DHCP(buf->data)->flags = 0;                     // server must send unicast answer
        DHCP(buf->data)->ci.d = ip_local[INTERFACE_ETH].d;
    }

    DHCP(buf->data)->yi.d = 0;
    DHCP(buf->data)->gi.d = 0;
    DHCP(buf->data)->si.d = ip_dhcp.d;

    os_set((BYTE *)(&DHCP(buf->data)->chaddr), 0, 16+64+128);
    os_copy((BYTE *)&mac_local,
            (BYTE *)(&DHCP(buf->data)->chaddr),
            sizeof(MACADDR));

    // --------------
    // insert options
    // --------------
    skip(buf, BOOTP_HDR_SIZE);
    buf->size = BOOTP_HDR_SIZE;
    write_uint32(buf, 0x63825363);                      // magic cookie

    write_byte(buf, DHCP_OPT_TYPE);                     // DHCP message type
    write_byte(buf, 1);
    write_byte(buf, type);

    write_byte(buf, DHCP_OPT_ID);                       // DHCP source ID
    write_byte(buf, 7);
    write_byte(buf, 1);
    write_buf(buf, (BYTE *)&mac_local, sizeof(MACADDR));

    write_byte(buf, DHCP_OPT_IP);                       // Request IP address
    write_byte(buf, 4);
    write_ip(buf, ip_tmp);

#ifdef _DNS
    write_byte(buf, DHCP_OPT_REQ);                      // Request options
    write_byte(buf, 3);
    write_byte(buf, DHCP_OPT_MASK);
    write_byte(buf, DHCP_OPT_ROUTER);
    write_byte(buf, DHCP_OPT_DNS);
#else
    write_byte(buf, DHCP_OPT_REQ);                      // Request options
    write_byte(buf, 2);
    write_byte(buf, DHCP_OPT_MASK);
    write_byte(buf, DHCP_OPT_ROUTER);
#endif

    write_byte(buf, DHCP_OPT_END);                      // done with options

    udp_send(buf);
    release_buffer(buf);
    return TRUE;
}	
Example #3
0
static void
add_new_tcp(struct tcphdr * this_tcphdr, struct ip * this_iphdr)
{
  struct tcp_stream *tolink;
  struct tcp_stream *a_tcp;
  int hash_index;
  struct tuple4 addr;
  
  addr.source = ntohs(this_tcphdr->th_sport);
  addr.dest = ntohs(this_tcphdr->th_dport);
  addr.saddr = this_iphdr->ip_src.s_addr;
  addr.daddr = this_iphdr->ip_dst.s_addr;
  hash_index = mk_hash_index(addr);
  
  if (tcp_num > max_stream) {
    struct lurker_node *i;
    int orig_client_state=tcp_oldest->client.state;
    tcp_oldest->nids_state = NIDS_TIMED_OUT;
    for (i = tcp_oldest->listeners; i; i = i->next)
      (i->item) (tcp_oldest, &i->data);
    nids_free_tcp_stream(tcp_oldest);
    if (orig_client_state!=TCP_SYN_SENT)
      nids_params.syslog(NIDS_WARN_TCP, NIDS_WARN_TCP_TOOMUCH, ugly_iphdr, this_tcphdr);
  }
  a_tcp = free_streams;
  if (!a_tcp) {
    fprintf(stderr, "gdb me ...\n");
    pause();
  }
  free_streams = a_tcp->next_free;
  
  tcp_num++;
  tolink = tcp_stream_table[hash_index];
  memset(a_tcp, 0, sizeof(struct tcp_stream));
 #ifdef OSPLIT 
  struct ipfrag *frag_tag=this_fragments;
  struct ipfrag *ip_frag_next;
  if(this_fragments)
	  ip_frag_next=this_fragments->next;
  a_tcp->fp=split_file[(TCP_file_idx++)%SPLIT_FILE_NUM];
  /*write all fragment(s) to fp trace file*/
  if(is_frag==0) {
	  write_pcap_hdr(a_tcp->fp,(char*)nids_last_pcap_header,sizeof(struct pcap_sf_pkthdr));
	  write_ip(a_tcp->fp,(char*)this_iphdr,ntohs(this_iphdr->ip_len),(char*)nids_last_pcap_header);
  }
  else {
	  /*fragments*/
	  while(frag_tag!=NULL) {
		  write_pcap_hdr(a_tcp->fp,(char*)(&(frag_tag->pcap_header)),sizeof(struct pcap_sf_pkthdr));
		  write_ip(a_tcp->fp,(char*)frag_tag->skb->data,frag_tag->wtrace_len,(char*)(&(frag_tag->pcap_header)));
		  free(frag_tag);
		  frag_tag=ip_frag_next;
		  if(ip_frag_next!=NULL)
			  ip_frag_next=ip_frag_next->next;
	  }
	  is_frag=0;
   }
	/*set statistic info*/
	store_flag=1;
 #endif
  a_tcp->hash_index = hash_index;
  a_tcp->addr = addr;
  a_tcp->client.state = TCP_SYN_SENT;
  a_tcp->client.seq = ntohl(this_tcphdr->th_seq) + 1;
  a_tcp->client.first_data_seq = a_tcp->client.seq;
  a_tcp->client.window = ntohs(this_tcphdr->th_win);
  a_tcp->client.ts_on = get_ts(this_tcphdr, &a_tcp->client.curr_ts);
  a_tcp->client.wscale_on = get_wscale(this_tcphdr, &a_tcp->client.wscale);
  a_tcp->server.state = TCP_CLOSE;
  a_tcp->next_node = tolink;
  a_tcp->prev_node = 0;
  if (tolink)
    tolink->prev_node = a_tcp;
  tcp_stream_table[hash_index] = a_tcp;
  a_tcp->next_time = tcp_latest;
  a_tcp->prev_time = 0;
  if (!tcp_oldest)
    tcp_oldest = a_tcp;
  if (tcp_latest)
    tcp_latest->prev_time = a_tcp;
  tcp_latest = a_tcp;
}
Example #4
0
int main(int argc, char *argv[]){
	char bf_ip[SIZE] = "", bf_rfcomm[SIZE] = "", bf_seial[SIZE] = "";
	char buffer[20] = "";

	int port_no = atoi(argv[1]);
	uint32_t svc_uuid_int[] = {0x1101, 0x1000, 0x80000080 ,0x5f9b34fb};

	FD_ZERO(&readfds);

	printf("Program start up!\n");

	// setup_serial(BAUD, DEVICE_ARDUINO);
	// setup_rfcomm(svc_uuid_int);
	setup_ip(port_no);

	fflush(stdin);
	FD_SET(STDIN, &readfds);
	fd_set readfds_temp;
	while(1){
		readfds_temp = readfds;
		
		select(FD_SETSIZE, &readfds_temp, NULL, NULL, NULL);

		// just for jumping out of loop through command
		if (FD_ISSET(STDIN, &readfds_temp)){
			scanf("%s", buffer);
			if(strcmp(buffer, "end")==0){
				break;
			}
		}

		// if (FD_ISSET(fd_rfcomm_server, &readfds_temp)){
		// 	accept_rfcomm();
		// }

		if (FD_ISSET(fd_ip_server, &readfds_temp)){
			accept_ip();
		}

		//if all three connections are established, start reading
		//ip or rfcomm writing should be before serial.
		// if(fd_rfcomm > 0 && fd_serial > 0 && fd_ip > 0){
			// if (FD_ISSET(fd_rfcomm, &readfds_temp)){
			// 	read_rfcomm(bf_rfcomm);
			// 	if(strcmp(bf_rfcomm, EXPLORE)==0)
			// 		write_serial(bf_rfcomm);
			// 	else if(strcmp(bf_rfcomm, RUN)==0)
			// 		write_ip(bf_rfcomm);
			// 	bzero(bf_rfcomm,sizeof(bf_rfcomm));
			// }
			// if (FD_ISSET(fd_serial, &readfds_temp)){
			// 	read_serial(bf_seial);
			// 	write_ip(bf_seial);
			// 	bzero(bf_seial,sizeof(bf_seial));
			// }
			if (FD_ISSET(fd_ip, &readfds_temp)){
				read_ip(bf_ip);
				write_ip(bf_ip);
				// write_serial(bf_ip);
				bzero(bf_ip,sizeof(bf_ip));
			}
		}
	// }

	close_ip();
	// close_rfcomm();
	// close_serial();

	printf("Programm terminating...\n");
}