//async method for connecting to clients public static void connect(IAsyncResult ar) { ComState state = null; try { //connection finished, allow others to connect connectionFound.Set(); Console.WriteLine("\nPlayer connected gen com"); //get socket for client Socket listener = (Socket)ar.AsyncState; Socket handler = listener.EndAccept(ar); byte[] id = new byte[16]; handler.Receive(id, 16, 0); Guid clientID = new Guid(id); ClientState addSocket; lock (ConnectedPlayers.DICTIONARY_LOCK) { if (ConnectedPlayers.playerDetails.TryGetValue(clientID, out addSocket)) { addSocket.GenComSocket = handler; } else { addSocket = new ClientState(handler, null, null, null); ConnectedPlayers.playerDetails.Add(clientID, addSocket); } } //link writelock with the playerdetails gencomwritelock for this client state = new ComState(addSocket.GENCOM_WRITE_LOCK); //initialize values state.ClientSocket = handler; state.Update = new byte[UPDATE_SIZE]; state.ClientID = clientID; //start receiving client updates handler.BeginReceive(state.Update, 0, UPDATE_SIZE, 0, new AsyncCallback(readUpdate), state); } //catch connection errors catch (Exception e) { if (state != null) { state.disposeTimer(); } Console.WriteLine(e.ToString()); Console.WriteLine("\nPlayer disconnected gen com connect"); } }
//read updates from clients public static void readUpdate(IAsyncResult ar) { //retreive the state object and socket ComState state = (ComState)ar.AsyncState; Socket handler = state.ClientSocket; try { ar.AsyncWaitHandle.WaitOne(); if (handler.EndReceive(ar) == 0) { state.disposeTimer(); Console.WriteLine("\nPlayer disconnected gen com readUpdate"); return; } byte type = state.Update[0]; //if (serverUpdateAvailable(state)) //{ // processSpCom(state); //} switch (type) { //player requesting battle with another player case 0: processBattleReq(state); break; //player interacting with colloseum case 1: processColloseumReq(state); break; //player interacting with landmark case 2: processLandmarkReq(state); break; case 3: processQuestComplete(state); break; case 4: processItemReq(state); break; case 5: processBattleResponse(state); break; //anything else we may want default: Console.WriteLine("Error: invalid update type received"); break; } handler.BeginReceive(state.Update, 0, UPDATE_SIZE, 0, new AsyncCallback(readUpdate), state); } //end communications gracefully if player disconnects catch (Exception) { state.disposeTimer(); Console.WriteLine("\nPlayer disconnected gen com readUpdate"); } }