void HeartbeatRoutine(object a_worker) { Worker worker = (Worker)a_worker; ProtocolType protocol = worker.m_socket.ProtocolType; IPEndPoint dest; if (protocol == ProtocolType.Udp) { dest = m_subServerAddr_udp; worker.m_poller.Start(worker.m_socket); } else { Debug.Assert(protocol == ProtocolType.Tcp); dest = m_subServerAddr_tcp; } Heartbeat heartbeat = new Heartbeat(GetName(worker.m_socket)); Message ping = new Message(); int pingPongCtx = 0; ping.m_contextSeq = 1; ping.m_contextID = pingPongCtx; string errComment = ""; while (m_run) { heartbeat.WaitForInterval(errComment); ping.m_pingTime = System.Environment.TickCount; bool succeedPing = false; switch (protocol) { case ProtocolType.Tcp: if (worker.m_poller.IsRegstered(worker.m_socket)) succeedPing = worker.m_poller.Send(worker.m_socket, ping, true); else { if (ping.m_contextSeq > 1) { ping.m_contextSeq = 1; worker.m_socket.Close(); worker.m_socket = Function.CreateSocket(ProtocolType.Tcp, null, false); } succeedPing = worker.m_poller.ConnectAndSend(worker.m_socket, dest, ping); } break; case ProtocolType.Udp: succeedPing = worker.m_poller.SendTo(worker.m_socket, dest, ping, true); break; default: Debug.Assert(false); break; } if (succeedPing == false) { errComment = "failed request."; heartbeat.Timeout(); continue; } Message pong; Socket sock; IPEndPoint sender; bool isTimeout = ! worker.m_poller.WaitForMessage(Config.Response_Timeout_Ms, out pong, out sock, out sender); if (isTimeout) { errComment = "response timeout."; heartbeat.Timeout(); continue; } if (pong.m_contextID != pingPongCtx) { heartbeat.Timeout(); errComment = "wrong message."; Config.OnErrorDelegate("잘못된 메시지를 수신 : " + pong.ToString()); continue; } heartbeat.Reset(); if (ping.AddressIsEmpty()) { ping.m_address = pong.m_address; ping.m_port = pong.m_port; } ++ping.m_contextSeq; } }