void RUDPSocket::process_syn2(BinStream& strm, const Inet_Addr& remote_addr) { RUDP_INFO("recv syn2 from " << remote_addr << ", rudp id = " << rudp_id_); PARSE_RUDP_MESSAGE(strm, RUDPSyn2Packet, syn2, "parse syn2 failed!"); if(state_ == RUDP_CONNECTING) { if(syn2.syn2_result_ != 0x00) //连接异常 { RUDP_INFO("syn failed! syn2.syn2_result_ = " << (uint16_t)syn2.syn2_result_); if(event_handler_ != NULL) { RUDP_INFO("state = RUDP_FIN2_STATE, rudp id = " << rudp_id_); set_state(RUDP_FIN2_STATE); event_handler_->rudp_exception_event(rudp_id_); } else { RUDP_INFO("state = RUDP_CLOSE, rudp id = " << rudp_id_); set_state(RUDP_CLOSE); } return ; } //设置接收BUFF的初始化 //ccc_.init(syn2.start_seq_ - 1); recv_buffer_.set_first_seq(syn2.start_seq_); //设置连接信息 remote_addr_ = remote_addr; remote_rudp_id_ = syn2.local_rudp_id_; //计算RTT uint64_t now_ts = CBaseTimeValue::get_time_value().msec(); uint32_t rtt = static_cast<uint32_t>(now_ts > syn2.remote_ts_ ? (now_ts - syn2.remote_ts_) : 5); recv_buffer_.set_send_last_ack_ts(now_ts); ccc_.set_rtt(rtt); RUDP_INFO("syn succ, sart seq = " << syn2.start_seq_ << ", remote_rudp_id = " << remote_rudp_id_ << ", rtt = " << rtt); RUDP_INFO("state = RUDP_CONNECTED, rudp id = " << rudp_id_); set_state(RUDP_CONNECTED); RUDP_DEBUG("send syn ack, rudp socket id = " << rudp_id_); send_syn_ack(0, syn2.local_ts_); //触发一个写事件 if(event_handler_ != NULL) event_handler_->rudp_output_event(rudp_id_); heart_ts_ = now_ts; } else if(state_ == RUDP_CONNECTED) { RUDP_DEBUG("send syn ack, rudp socket id = " << rudp_id_); send_syn_ack(0, syn2.local_ts_); } }
/* *************************************************** * Function: passive_init * *************************************************** * Passive node waits for a SYN packet to arrive, it then * sends an SYN_ACK using another helper function (below) */ static bool passive_init(mysocket_t sd, context_t *ctx) { ctx->connection_state = CSTATE_LISTEN; struct tcphdr* syn_packet = (struct tcphdr *)calloc(1, (TH_MAX_OFFSET*sizeof(uint32_t))+STCP_MSS); /* Listen for a connection request */ while (true){ stcp_wait_for_event(sd, NETWORK_DATA, NULL); network_recv(sd, syn_packet); if (syn_packet->th_flags == TH_SYN){ break; } } our_dprintf("PASSIVE - RCVD SYN with seq: %d\n", syn_packet->th_seq); /* Prepare SYN_ACK*/ syn_packet->th_ack = syn_packet->th_seq + 1; syn_packet->th_seq = ctx->initial_sequence_num; syn_packet->th_off = TH_MIN_OFFSET; syn_packet->th_flags = TH_SYN | TH_ACK; syn_packet->th_win = RWIN; /*Update connection state variables */ ctx->last_ack_sent = syn_packet->th_ack; ctx->nxt_seq_num = ctx->initial_sequence_num + 1; ctx->connection_state = CSTATE_SYN_RCVD; ctx->seq_base = ctx->nxt_seq_num; our_dprintf("PASSIVE - SEND SYN_ACK Packet with seq: %d and ack: %d \n", syn_packet->th_seq, syn_packet->th_ack); bool success = send_syn_ack(sd, ctx, syn_packet); free(syn_packet); return success; }
int main(int argc, char **argv) { init(); if(sock == -1) { return 0; } int fd = open_csman(NULL,0); if (fd < 0) { perror("Can't Open CSMAN"); close_csman(fd); close(sock); return 0; } struct in_addr local_ip; read_csman(fd, CSID_C_LOCAL_LANIP, &local_ip, sizeof(struct in_addr), CSM_R_ZERO); char router_ip[16]; snprintf(router_ip, 16, "%s\0", inet_ntoa(local_ip)); struct in_addr local_mask; read_csman(fd, CSID_C_LOCAL_LANNM, &local_mask, sizeof(struct in_addr), CSM_R_ZERO); char router_mask[16]; snprintf(router_mask, 16, "%s\0", inet_ntoa(local_mask)); char redirect_page[128]; snprintf(redirect_page, 128, "http://%s/%s\0", inet_ntoa(local_ip), REDIRECT_PAGE); int nrecv = 0; short req = UNKNOWN_REQUEST; short do_reply = 0; char target[16]; while (1) { /* * Check to see if the packet contains at least * complete Ethernet (14), IP (20) and TCP/UDP (8) headers. */ char pkt_buffer[PKT_BUF_LEN] = {0}; nrecv = recvfrom(sock, pkt_buffer, PKT_BUF_LEN, 0, NULL, NULL); if (nrecv < 34) { error("Incomplete packet (errno is %d)\n", errno); continue; } struct conn_info cinfo; req = get_conn_info(nrecv, pkt_buffer, &cinfo); if(req == UNKNOWN_REQUEST) { continue; } short is_wanpkt = wanpkt(&cinfo, router_ip, router_mask); short is_gw = (!strcmp(cinfo.dst_ip, router_ip)) ? 1 : 0; //ddebug("wan-pkt %d, gw %d !\n", is_wanpkt, is_gw); if(req == DNS_REQUEST) { error("Send DNS rebinding for LAN %s:%d\n", cinfo.src_ip, cinfo.src_port); send_dns_reply(pkt_buffer, nrecv, &cinfo, router_ip); snprintf(target, 16, "%s\0", cinfo.src_ip); do_reply = 1; } #if ENABLE_SYN_ACK_REPLY == 1 if(req == SYN_REQUEST && is_wanpkt) { error("Send SYN+ACK for LAN %s:%d\n", cinfo.src_ip, cinfo.src_port); send_syn_ack(&cinfo); snprintf(target, 16, "%s\0", cinfo.src_ip); do_reply = 1; } #endif #if ENABLE_ICMP_REPLY == 1 if(req == ICMP_REQUEST && is_wanpkt) { //error("ICMP packet !\n"); send_icmp_reply(pkt_buffer, nrecv, &cinfo); } #endif #if ENABLE_HTTP_REPLY == 1 if(req == HTTP_REQUEST && do_reply) { if(!strcmp(cinfo.src_ip, target)) { error("Send HTTP redirect for LAN %s:%d\n", cinfo.src_ip, cinfo.src_port); send_http_redirect(&cinfo, redirect_page); do_reply = 0; snprintf(target, 16, "\0"); } ddebug("\n"); } #endif } close(sock); }