/** @brief This will sniff incoming packets for an ICMP ECHO reply libpcap version */ bool turbotrace::start_sniffer() { log("Sniffer initialising...\n"); char errbuf[1000]; //Open the device adapter = pcap_open(adapter_info.name , 65536 , PCAP_OPENFLAG_PROMISCUOUS , 20 , NULL ,errbuf); if (adapter == NULL) { log(_("pcap_open_live failed") + wxString(errbuf , wxConvUTF8)); return false; } log(_("pcap_open successful")); sniffer_ready = true; //Send the syn packets send_syn(); //Put the device in sniff loop pcap_loop(adapter , -1 , process_packet2 , (u_char*)this); return true; }
void send_keycode(struct input_event ev, int fdo, unsigned int keycode, int value) { ev.type = EV_KEY; ev.code = keycode; ev.value = value; write(fdo, &ev, sizeof(ev)); send_syn(ev,fdo); }
int32_t RUDPSocket::handle_timeout(const void *act, uint32_t timer_id) { if(timer_id_ != timer_id) return 0; timer_id_= 0; //解决状态定时的问题,尤其是报文发送 switch(state_) { case RUDP_CONNECTING: if(send_count_ < SYN_MAX_COUNT) { send_syn(); set_timer(CONNECT_DELAY); RUDP_DEBUG("resend syn, rudp socket id = " << rudp_id_); send_count_ ++; } else //连接超时 { RUDP_INFO("connecting timeout! state = RUDP_FIN2_STATE, rudp id = " << rudp_id_); set_state(RUDP_FIN2_STATE); if(event_handler_ != NULL) event_handler_->rudp_exception_event(rudp_id_); else { RUDP_INFO("state = RUDP_CLOSE, rudp id = " << rudp_id_); set_state(RUDP_CLOSE); } } break; case RUDP_FIN_STATE: if(send_count_ < FIN_MAX_COUNT) { RUDP_DEBUG("resend fin, rudp socket id = " << rudp_id_); send_fin(); set_timer(ccc_.get_rtt() + TIMER_MIN_DELAY); send_count_ ++; } else { RUDP_INFO("fin timeout, state = RUDP_CLOSE, rudp id = " << rudp_id_); set_state(RUDP_CLOSE); } break; } return 0; }
/** * [Client-only] * TCP handshake with server. This includes the SYN, SYN-ACK, and ACK segments. * * returns: A connection object if able to connect, NULL otherwise. This * object must be freed. */ conn_t *tcp_handshake(void) { ASSERT_CLIENT_ONLY; char buf[MAX_PACKET_SIZE]; /* Send a SYN segment to the server. */ if (send_syn(config->sconn)) exit(EXIT_FAILURE); /* Wait to receive SYN-ACK. */ int r = recv_filter(config->socket, buf, MAX_PACKET_SIZE, 0, NULL); if (r <= 0) return NULL; tcphdr_t *synack = (tcphdr_t *) (buf + IP_HDR_SIZE); /* Set window size for the other host. */ ctcp_cfg->send_window = ntohs(synack->window); /* If an ACK is received instead of a SYN-ACK, continue previous connection. Get sequence numbers from previous connection. */ if ((synack->th_flags & TH_SYN) == 0) { config->sconn->init_seqno = ntohl(synack->th_ack) - 1; config->sconn->their_init_seqno = ntohl(synack->th_seq) - 1; config->sconn->next_seqno = config->sconn->init_seqno + 1; config->sconn->ackno = ntohl(synack->th_seq); } /* Otherwise, set new acknowledgement number and send ACK response */ else { config->sconn->next_seqno++; config->sconn->their_init_seqno = ntohl(synack->th_seq); config->sconn->ackno = ntohl(synack->th_seq) + 1; send_ack(config->sconn); } return config->sconn; }
int32_t RUDPSocket::connect(const Inet_Addr& remote_addr) { if(rudp_id_ == INVALID_RUDP_HANDLE || state_ != RUDP_IDLE || local_index_ == 255 || remote_rudp_id_ != INVALID_RUDP_HANDLE) { RUDP_FATAL("rudp connect failed! rudp socket id = " << rudp_id_); error_code_ = RUDP_CONNECT_FAIL; return -1; } remote_addr_ = remote_addr; check_sum_ = rand() % 65536; //产生一个会话的CHECK SUM RUDP_INFO("state = RUDP_CONNECTING, rudp id = " << rudp_id_ << ", remote addr = " << remote_addr_); set_state(RUDP_CONNECTING); RUDP_DEBUG("send syn, rudp socket id = " << rudp_id_); send_syn(); ccc_.init(send_buffer_.get_buffer_seq() - 1); set_timer(CONNECT_DELAY); send_count_ ++; return 0; }
sint15 send_tcp ( register struct tcb *tcb, /* ptr to TCP Control Block */ dsm_item_type *new_item_ptr /* ptr to data item for TCP output */ ) { word cnt; /* holds count of new data bytes */ /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ #ifdef FEATURE_DSM_MEM_CHK /*--------------------------------------------------------- Set tracer to indicate where the item is being stored ---------------------------------------------------------*/ new_item_ptr->tracer = DSM_TCP_SNDQ; #endif if(tcb == NULL || new_item_ptr == NULL) { dsm_free_packet( &new_item_ptr); return -1; } cnt = 0; switch(tcb->state) { case TCP_CLOSED: dsm_free_packet( &new_item_ptr); return -1; case TCP_LISTEN: /* -------------------------------------------------------------- If any remote address is 0, then it is a passive connection (LtoM). We stay in LISTEN state till we receive TCP packets from the IWF. Earlier the remote address was set to 0 in psmgr.c, so we enter the if when we are in passive mode and don't have dest. port # yet ----------------------------------------------------------------*/ if(tcb->conn.remote.address == 0 || tcb->conn.remote.port == 0) { /* Save data for later */ cnt = append_to_sndq( tcb, new_item_ptr); break; } /* Change state from passive to active */ tcb->flags.active = 1; send_syn(tcb); setstate(tcb,TCP_SYN_SENT); /* Note fall-thru */ case TCP_SYN_SENT: case TCP_SYN_RECEIVED: case TCP_ESTABLISHED: case TCP_CLOSE_WAIT: cnt = append_to_sndq( tcb, new_item_ptr); tcp_output(tcb); break; case TCP_FINWAIT1: case TCP_FINWAIT2: case TCP_CLOSING: case TCP_LAST_ACK: case TCP_TIME_WAIT: dsm_free_packet( &new_item_ptr); return -1; } return cnt; }
struct tcb *open_tcp ( struct socket *lsocket, /* Local socket */ struct socket *fsocket, /* Remote socket */ int mode, /* Active/passive/server */ uint16 window, /* Receive window (and send buffer) sizes */ uint16 mss, /* TCP mss */ int tos, /* Type of service */ int user, /* User linkage area */ struct tcb *tcb_ptr ) { /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ #ifdef FEATURE_DS_PSTATS #error code not present #endif if(lsocket == NULL) { return NULL; } tcb_ptr->conn.local.address = lsocket->address; tcb_ptr->conn.local.port = lsocket->port; if(fsocket != NULL) { tcb_ptr->conn.remote.address = fsocket->address; tcb_ptr->conn.remote.port = fsocket->port; } else { tcb_ptr->conn.remote.address = 0; tcb_ptr->conn.remote.port = 0; } tcb_ptr->user = user; if( window != 0) { tcb_ptr->window = window; } else if( Tcp_window >= Tcp_mss ) { tcb_ptr->window = Tcp_window; } else { tcb_ptr->window = Tcp_window * Tcp_mss; } tcb_ptr->rcv.wnd = tcb_ptr->window; tcb_ptr->snd.wnd = 1; /* Allow space for sending a SYN */ tcb_ptr->tos = tos; tcb_ptr->mss = mss; tcb_ptr->cwind = mss; switch( mode) { case TCP_SERVER: tcb_ptr->flags.clone = 1; case TCP_PASSIVE: /* Note fall-thru */ setstate( tcb_ptr, TCP_LISTEN); break; case TCP_ACTIVE: /* Send SYN, go into TCP_SYN_SENT state */ tcb_ptr->flags.active = 1; send_syn( tcb_ptr); setstate( tcb_ptr, TCP_SYN_SENT); tcp_output( tcb_ptr); break; default: /* Error Trap, Path-whatever-logical */ ERR_FATAL( "Invalid TCP Open", 0, 0, 0); } return( tcb_ptr); }
int rudp_sendto(rudp_socket_t rsocket, void* data, int len, struct sockaddr_in* to) { if (len>RUDP_MAXPKTSIZE) { perror("rudp_sendto: packet too long"); return -1; } //Create an internal socket structure struct rudp_socket_int* sockint = (struct rudp_socket_int*)malloc(sizeof(struct rudp_socket_int)); memcpy(sockint,rsocket,sizeof(struct rudp_socket_int)); //Look up state of (socket,remote peer) pair int cstate = getsstate(sockint->socket_id,to); switch(cstate) { case INITIAL: { //Add a peer to the socket if (addpeer(sid,to)==-1) return -1; int pnum = getpeernum(sid,to); //Create a queue for this socket/peer pair and add the packet to this queue init_queue(sid,pnum); add_packet(data,len,sid,pnum); //Send a SYN packet send_syn(sockint->socket_desc,sid,pnum,to); break; } case SENT_SYN: { int pnum = getpeernum(sid,to); //Get the data and add it to the queue add_packet(data,len,sid,pnum); break; } case SENDING: { int pnum = getpeernum(sid,to); //Get the data and add it to the queue add_packet(data,len,sid,pnum); send_data(sockint->socket_desc,sid,pnum,to); break; } case SENT_FIN: { int pnum = getpeernum(sid,to); //Get the data and add it to the queue add_packet(data,len,sid,pnum); setsstate(sid,to,SENDING); break; } case CLOSED: { return -1; } } return 0; }
/** @brief This will sniff incoming packets and send them to processor */ bool turbotrace::start_sniffer() { int sock_raw; int saddr_size , data_size; struct sockaddr saddr; unsigned char *buffer = (unsigned char *)malloc(65536); //Its Big! tlog( _("Sniffer initialising...\n") ); //Create a raw socket that shall sniff all packets sock_raw = socket( AF_PACKET , SOCK_RAW , htons(ETH_P_ALL)) ; if(sock_raw < 0) { tlog( _("Socket Error\n") ); return false; } saddr_size = sizeof saddr; sniffer_ready = true; //set of socket descriptors fd_set readfds; int activity; int k = sock_raw > comm_sock ? sock_raw : comm_sock; /* It is important to send syn packets here to ensure , they are being send when sniffer is most ready Because if due to thread races , the syn packets are released before sniffer is ready then icmp replies would be lost , resulting into incorrect output. */ if( !send_syn() ) { return false; } while( ! GetThread()->TestDestroy() ) { //clear the socket set FD_ZERO(&readfds); //add master socket to set FD_SET(sock_raw , &readfds); FD_SET(comm_sock , &readfds); //wait for an activity on one of the sockets , timeout is NULL , so wait indefinitely activity = select( k + 1 , &readfds , NULL , NULL , NULL); if ((activity < 0) && (errno!=EINTR)) { tlog(_("select error\n")); break; } //If something happened on the master socket , then its an incoming connection if (FD_ISSET(sock_raw , &readfds)) { //Receive a packet data_size = recvfrom(sock_raw ,(char*) buffer , 65536 , 0 , &saddr , (socklen_t*)&saddr_size ); if(data_size < 0 ) { tlog(_("Recvfrom error , failed to get packets\n")); break; } //Now process the packet process_packet(buffer , data_size); } //Something happened on communication socket , a TERMINATE signal ? if (FD_ISSET(comm_sock , &readfds)) { if(read(comm_sock , buffer , 1024) > 0) { tlog(_("Terminate signal. \n") + wxString(buffer , wxConvUTF8)); break; } } } close(sock_raw); free(buffer); tlog(_("Sniffer finished. \n")); return true; }