示例#1
0
        void OnAcceptAsync(object _obj, SocketAsyncEventArgs _acceptArgs)
        {
            if (Protocol.DEBUG_SLEEP_ACCEPT)
            {
                System.Threading.Thread.Sleep(10);
            }
            identity++;
            Console.WriteLine("[{0}]OnAcceptAsync (callback) New Client connect", identity);

            //---------------------------------------
            //신규접속 유저 신규소켓 > Pool에서 하나 꺼내서 달아주기.
            //신규유저 받는 전용 소켓은 재등록 해주고...
            //---------------------------------------
            Socket _clientSocket = _acceptArgs.AcceptSocket;
            Socket _acceptSocket = acceptSocket;

            _acceptArgs.AcceptSocket = null;
            bool _bAcceptSocketAlive = _acceptSocket.AcceptAsync(_acceptArgs);

            if (Protocol.DEBUG)
            {
                Console.WriteLine((_acceptSocket == acceptSocket) + ":" + (acceptArgs == _acceptArgs));
            }

            if (_bAcceptSocketAlive == false)
            {
                //접속대기 등록하자마자 -> 신규유저 바로 접속은 없다
                //50  대기중 발생안함
                //100 대기중 발생안함
                //120 대기중 발생안함.
                //03-10 200회 테스트 했는데 안들어옴...
                //절대 안들어올듯...
                Console.WriteLine("OnAcceptAsync >> .AcceptAsync @@@@ {0} 신규유저접속받기 등록하자마사 > 바로접속", identity);
                OnAcceptAsync(_acceptSocket, _acceptArgs);
            }

            //---------------------------------------
            // pool -> client setting infomation
            //---------------------------------------
            CUserToken _token = listFreeUser.Dequeue();

            //if (_token.bProblemData)
            //{
            //	//_token 문제가 있는놈이다
            //	//       > 뎅글링 클래스로 나둬버림...
            //	//       > GC가 호출해감....
            //	//새것으로 다시 뺴오자..~~~
            //	_token = listFreeUser.Dequeue();
            //}

            _token.socket = _clientSocket;
            listConnectUser.Add(_token);
            _token.identityID = identity;

            //-------------------------------------------------------------------
            //	이중으로 ReceiveAsync 등록시 오류
            //_bReceive = _clientSocket.ReceiveAsync(_token.receiveArgs);
            //_bReceive = _clientSocket.ReceiveAsync(_token.receiveArgs); < -이놈이 발생...
            //System.InvalidOperationException: '"이 SocketAsyncEventArgs 인스턴스를 사용하여 비동기 소켓 작업이 이미 진행되고 있습니다.";'
            //
            // 서버가 오류발생....
            //
            // 클라에 오류가 발생 전달... 클라를 닫으면 아래의 메세지가 그제서야 들어옴...
            //System.InvalidOperationException: "이 SocketAsyncEventArgs인스턴스를 사용하여 비동기 소켓 작업이 이미 진행되고 있습니다.";
            //System.Net.Sockets.SocketAsyncEventArgs.StartOperationCommon(Socket socket)
            //System.Net.Sockets.Socket.ReceiveAsync(SocketAsyncEventArgs e)
            //TimeServer10.Program.OnAcceptAsync(Object _obj, SocketAsyncEventArgs _acceptArgs) 파일 D:\devtool\study\study\_Lesson_NetStep1\20_TcpAsyncSample\FreeNetTest2\TimeServer10\TimeServer10\Program.cs:줄 123
            //System.Net.Sockets.SocketAsyncEventArgs.OnCompleted(SocketAsyncEventArgs e)
            //System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)
            //System.Net.Sockets.SocketAsyncEventArgs.FinishOperationSuccess(SocketError socketError, Int32 bytesTransferred, SocketFlags flags)
            //System.Net.Sockets.SocketAsyncEventArgs.CompletionPortCallback(UInt32 errorCode, UInt32 numBytes, NativeOverlapped * nativeOverlapped)
            //System.Threading._IOCompletionCallback.PerformIOCompletionCallback(UInt32 errorCode, UInt32 numBytes, NativeOverlapped * pOVERLAP)
            //-------------------------------------------------------------------

            bool _bReciveSocketAlive = _clientSocket.ReceiveAsync(_token.receiveArgs);

            //_bReceive = _clientSocket.ReceiveAsync(_token.receiveArgs);
            if (_bReciveSocketAlive == false)
            {
                //50  대기중 발생안함
                //100 대기중 발생안함
                //120 대기중 발생안함.
                //등록하자마자 바로 데이타 받음...
                //
                //서버가 과부하 상태에서 신규 유저 접속하자 마자 바로 종료하는 경우...
                //100% 발생함...데이타 대량으로 오고 가는중에 발생....
                // > 접속 종료에 대한 메세지를 받은 것임.. ㅎㅎㅎ
                // 접속 -> 대기중... 음... 바로 -> 바로 종료.... 발생....(종료 메세지)
                Console.WriteLine("[{0}]OnAcceptAsync >> .ReceiveAsync @@@@ {0}/{1} 신규유저받고, 바로 메세지 받음",
                                  _token.identityID,
                                  _token.socket.Connected,
                                  _token.receiveArgs.BytesTransferred,
                                  _token.receiveArgs.LastOperation,
                                  _token.receiveArgs.SocketError);
                OnReceiveAsync(_clientSocket, _token.receiveArgs);
            }
            Console.WriteLine("[{0}]connect free:{1} use:{2}", _token.identityID, listFreeUser.Count, listConnectUser.Count);
        }
示例#2
0
        void OnReceiveAsync(object _obj, SocketAsyncEventArgs _receiveArgs)
        {
            CUserToken _token        = _receiveArgs.UserToken as CUserToken;
            int        _debugWorkNum = _token.GetWorkNum();

            if (Protocol.DEBUG)
            {
                Console.WriteLine("[{0}]OnReceiveAsync (callback) >> socket:{1} BytesTransferred:{2} LastOperation:{3} SocketError:{4}",
                                  _token.identityID + "/" + _debugWorkNum,
                                  _token.socket.Connected,
                                  _receiveArgs.BytesTransferred,
                                  _receiveArgs.LastOperation,
                                  _receiveArgs.SocketError);
            }

            if (_receiveArgs.LastOperation == SocketAsyncOperation.Receive &&
                _receiveArgs.SocketError == SocketError.Success &&
                _receiveArgs.BytesTransferred > 0)
            {
                SocketAsyncEventArgs _sendArgs = _token.sendArgs;
                Socket _clientSocket           = _token.socket;

                //---------------------------------------
                // Client -> Socket -> Receive
                //---------------------------------------
                int    _transferred = _receiveArgs.BytesTransferred;
                byte[] _buffer2     = new byte[_transferred];
                Array.Copy(_receiveArgs.Buffer, _receiveArgs.Offset, _buffer2, 0, _transferred);
                if (Protocol.DEBUG)
                {
                    Console.WriteLine(" [{0}] >> 등록전 _socket.Connected:{1} _transferred:{2}", _token.identityID, _clientSocket.Connected, _transferred);
                }

                bool _bDebugRececiveTrueAfter = false;
                if (Protocol.DEBUG_SLEEP_PACKET)
                {
                    System.Threading.Thread.Sleep(10);
                }
                if (_clientSocket.Connected == false)
                {
                    _bDebugRececiveTrueAfter = true;
                    Console.WriteLine("@@@@ 등록전 @@@@");
                    Console.WriteLine(" [{0}] >> 등록전 _socket.Connected:{1} _transferred:{2}", _token.identityID, _clientSocket.Connected, _transferred);
                }
                if (Protocol.DEBUG_SLEEP_PACKET)
                {
                    System.Threading.Thread.Sleep(10);
                }
                bool _bReceiveAsync = _clientSocket.ReceiveAsync(_receiveArgs);

                if (Protocol.DEBUG_SLEEP_PACKET)
                {
                    System.Threading.Thread.Sleep(10);
                }
                //_bReceive = _socket.ReceiveAsync(_receiveArgs);
                if (Protocol.DEBUG)
                {
                    Console.WriteLine(" [{0}] >> 등록후 _socket.Connected:{2} _bReceive:{1}", _token.identityID, _bReceiveAsync, _clientSocket.Connected);
                }
                if (_bDebugRececiveTrueAfter)
                {
                    Console.WriteLine("@@@@ 등록후 @@@@");
                    Console.WriteLine(" [{0}] >> 등록전 _socket.Connected:{1} _transferred:{2}", _token.identityID, _clientSocket.Connected, _transferred);
                }
                //--------------------------------------
                //중간에 끼워들어옴... 음...
                if (_clientSocket.Connected == false)
                {
                    //갑자기 종료하면 발생함....
                    //20개에서도 발생함...
                    Console.WriteLine(" [{0}]OnReceiveAsync .ReceiveAsync @@@@ 파싱중~~ 재등록후(소켓꺼짐) {1}/{2}/{3}/{4}",
                                      _token.identityID + "/" + _debugWorkNum,
                                      _token.socket.Connected,
                                      _receiveArgs.BytesTransferred,
                                      _receiveArgs.LastOperation,
                                      _receiveArgs.SocketError);
                    Disconnect(" @@@@@(" + _debugWorkNum + ") >> OnReceiveAsync 파싱후 재등록후(소켓꺼짐)", _token);
                    return;
                }

                if (_bReceiveAsync == false)
                {
                    //등록하자마사 바로 데이타 받음...
                    Console.WriteLine(" [{0}] #### OnReceiveAsync > _socket.ReceiveAsync 메세지 받기(2) 등록하자마사 바로 받음.{1}", _token.identityID, _clientSocket.Connected);
                    OnReceiveAsync(null, _receiveArgs);
                }

                //Data Parse and Send...
                string _text = Encoding.ASCII.GetString(_buffer2, 0, _transferred);
                if (Protocol.DEBUG_PACKET)
                {
                    Console.WriteLine("[{0}]:{1}", _token.identityID + ":" + _debugWorkNum, _text);
                }

                string _response = string.Empty;
                if (_text.ToLower().Equals("get time"))
                {
                    _response = "[C <- S] OK Time Server9";
                }
                else
                {
                    _response = "[C <- S] Fail";
                }
                byte[] _sendBuffer2 = Encoding.ASCII.GetBytes(_response);
                int    _sendSize    = _sendBuffer2.Length;
                Array.Copy(_sendBuffer2, 0, _sendArgs.Buffer, _sendArgs.Offset, _sendSize);
                _sendArgs.SetBuffer(_sendArgs.Offset, _sendSize);

                //이부분에서 130개를 넘어가면 오류가 메모리 오류...
                //그 근처에서 메모리 오류가 먼저 발생해준다. (메모리는 충분한데... win7내 컴에서 종종 나타난다...)
                //2G까지만 (Person win7)
                //bool _bSend = true;
                //try
                //{
                //	_bSend = _socket.SendAsync(_sendArgs);
                //}
                //catch (Exception _e)
                //{
                //	Console.WriteLine(" >>> OnReceiveAsync _socket.SendAsync _e:{0}", _e);
                //	Disconnect(" <<<< ***보낼려고 하는데 어 아직 안보낸것이 있네...***", _token, true);
                //	return;
                //}
                //if (Protocol.DEBUG) Console.WriteLine("[{0}] _bSend {1} {2}", _token.identityID, _bSend, _socket.Connected);
                //
                //
                //if (_socket.Connected == false)
                //{
                //	Disconnect(" <<<< 보낼때1", _token);
                //	return;
                //}
                //if (_bSend == false)
                //{
                //	Console.WriteLine("[{0}] #### OnReceiveAsync _socket.SendAsync -> 보내기(1) 등록하자마사 바로 받음.{1}", _token.identityID, _socket.Connected);
                //	OnSendAsync(_socket, _sendArgs);
                //}
            }
            else
            {
                Console.WriteLine("[{0}]OnReceiveAsync [정상종료] >>> :{1} :{2} :{3} :{4}",
                                  _token.identityID + "/" + _debugWorkNum,
                                  _token.socket.Connected,
                                  _receiveArgs.BytesTransferred,
                                  _receiveArgs.LastOperation,
                                  _receiveArgs.SocketError
                                  );
                //if (_token.socket != null)
                //{
                //	bool _bReceive = _token.socket.ReceiveAsync(_receiveArgs);
                //	Console.WriteLine(" _bReceive:" + _bReceive);
                //}
                Disconnect("[정상종료]", _token);
            }
        }