From f459280f965b6e737466e2e250226aa809627c13 Mon Sep 17 00:00:00 2001 From: Simon Howard Date: Thu, 29 Dec 2005 21:29:55 +0000 Subject: Working client connect code Subversion-branch: /trunk/chocolate-doom Subversion-revision: 233 --- src/net_client.c | 165 ++++++++++++++++++++++++++++++++++++++++++++++++------- 1 file changed, 146 insertions(+), 19 deletions(-) (limited to 'src/net_client.c') diff --git a/src/net_client.c b/src/net_client.c index 2abc5acf..639f609d 100644 --- a/src/net_client.c +++ b/src/net_client.c @@ -1,7 +1,7 @@ // Emacs style mode select -*- C++ -*- //----------------------------------------------------------------------------- // -// $Id: net_client.c 232 2005-12-29 17:48:25Z fraggle $ +// $Id: net_client.c 233 2005-12-29 21:29:55Z fraggle $ // // Copyright(C) 2005 Simon Howard // @@ -21,6 +21,9 @@ // 02111-1307, USA. // // $Log$ +// Revision 1.2 2005/12/29 21:29:55 fraggle +// Working client connect code +// // Revision 1.1 2005/12/29 17:48:25 fraggle // Add initial client/server connect code. Reorganise sources list in // Makefile.am. @@ -38,15 +41,130 @@ #include "net_packet.h" #include "net_server.h" +typedef enum +{ + // sent a syn, not received an ack yet + + CLIENT_STATE_CONNECTING, + + // waiting for the game to start + + CLIENT_STATE_WAITING_START, + + // in game + + CLIENT_STATE_IN_GAME, +} net_clientstate_t; + +static net_clientstate_t client_state; static net_addr_t *server_addr; static net_context_t *client_context; +static int last_send_time; + +// parse a received packet + +static void ClientParsePacket(net_packet_t *packet) +{ + unsigned int packet_type; + + if (!NET_ReadInt16(packet, &packet_type)) + { + return; + } + + switch (packet_type) + { + case NET_PACKET_TYPE_ACK: + + // received an acknowledgement to the SYN we sent + + if (client_state == CLIENT_STATE_CONNECTING) + { + client_state = CLIENT_STATE_WAITING_START; + } + break; + + case NET_PACKET_TYPE_GAMESTART: + break; + + case NET_PACKET_TYPE_GAMEDATA: + break; + default: + break; + } +} + +// called when we are in the "connecting" state + +static void ClientConnecting(void) +{ + net_packet_t *packet; + + // send a SYN packet every second + + if (last_send_time < 0 || I_GetTimeMS() - last_send_time > 1000) + { + // construct a SYN packet + + packet = NET_NewPacket(10); + + // packet type + + NET_WriteInt16(packet, NET_PACKET_TYPE_SYN); + + // magic number + + NET_WriteInt32(packet, NET_MAGIC_NUMBER); + + // send to the server + + NET_SendPacket(server_addr, packet); + + NET_FreePacket(packet); + + last_send_time = I_GetTimeMS(); + } +} + +// "Run" the client code: check for new packets, send packets as +// needed + +void NET_ClientRun(void) +{ + net_addr_t *addr; + net_packet_t *packet; + + while (NET_RecvPacket(client_context, &addr, &packet)) + { + // only accept packets from the server + + if (addr == server_addr) + { + ClientParsePacket(packet); + } + + NET_FreePacket(packet); + } + + // send packets as needed + + switch (client_state) + { + case CLIENT_STATE_CONNECTING: + ClientConnecting(); + break; + case CLIENT_STATE_WAITING_START: + break; + case CLIENT_STATE_IN_GAME: + break; + } +} // connect to a server boolean NET_ClientConnect(net_addr_t *addr) { - net_packet_t *packet; - int last_send_time = -1; + int start_time; server_addr = addr; @@ -66,33 +184,42 @@ boolean NET_ClientConnect(net_addr_t *addr) // try to connect - // construct a SYN packet + client_state = CLIENT_STATE_CONNECTING; + last_send_time = -1; - packet = NET_NewPacket(10); - - // packet type - - NET_WriteInt16(packet, NET_PACKET_TYPE_SYN); + start_time = I_GetTimeMS(); - // magic number - - NET_WriteInt32(packet, NET_MAGIC_NUMBER); - - while (true) + while (client_state == CLIENT_STATE_CONNECTING) { - if (I_GetTime() - last_send_time > 35) - { - // resend packet + // time out after 5 seconds - NET_SendPacket(addr, packet); - last_send_time = I_GetTime(); + if (I_GetTime() - start_time > 5000) + { + break; } + // run client code + + NET_ClientRun(); + // run the server, just incase we are doing a loopback // connect NET_ServerRun(); } + + if (client_state != CLIENT_STATE_CONNECTING) + { + // connected ok! + + return true; + } + else + { + // failed to connect + + return false; + } } -- cgit v1.2.3