private void ProcessreceivedMsg(Message msg) { if (msg.CommandCode == DiameterMessageCode.DEVICE_WATCHDOG) { Message DWA = new Answer(stackContext).CreateDWA(msg); byte[] toSend = DWA.GetBytes(); //networkStream.Write(toSend, 0, toSend.Length); tcpClient.Client.Send(toSend); } else { //Return message response if (msg.CommandCode == DiameterMessageCode.CAPABILITY_EXCHANGE) { if (ResponseWaiter.ContainsRequest("CEX")) { msg.SessionID = "CEX"; if (!ResponseWaiter.AddResponse(msg)) { Common.StackLog.Write2ErrorLog("ProcessreceivedMsg", "Unable to Add Response for CEA Session:" + msg.SessionID); } } else { Common.StackLog.Write2ErrorLog("ProcessreceivedMsg", "Unexpected CEA Received \r\n" + msg.ToString()); } } else if (msg.CommandCode == DiameterMessageCode.CREDIT_CONTROL) { if (ResponseWaiter.ContainsRequest(msg.SessionID)) { if (!ResponseWaiter.AddResponse(msg)) { Common.StackLog.Write2ErrorLog("ProcessreceivedMsg", "Unable to Add Response for CCA Session:" + msg.SessionID); } } else { Common.StackLog.Write2ErrorLog("ProcessreceivedMsg", "Unexpected CCA Received for Session " + msg.SessionID + "\r\n" + msg.ToString()); } } else { Common.StackLog.Write2ErrorLog("ProcessreceivedMsg", "Unexpected Messages Received:" + msg.ToString() + msg.ToString()); } } }
/// <summary> /// Send Message to the Diameter Peer /// </summary> /// <param name="MessageBytes"></param> /// <param name="TransportType"></param> /// <param name="remotePeer"></param> public Message SendMessage(Message diameterRequest, Peer destPeer) { try { byte[] mgsBytesToSend = diameterRequest.GetBytes(); //Connect if not connected if (stackContext.peers[0].PeerConnection == null || !stackContext.peers[0].PeerConnection.Connected) { if (diameterRequest.CommandCode != DiameterMessageCode.CAPABILITY_EXCHANGE) { Common.StackLog.Write2ErrorLog("Transport::SendMessage", "Connection Broken, calling Connect()"); } //Connect Diameter Socket Connect(); } Thread pWaiterThread; //Just Copy to localThreadWaiter Variable. pWaiterThread = Thread.CurrentThread; //CCRWaiter vRespWaiter = null; //if Message is a CCR message, we need to wait for a response, so add Session to CCRSession if (diameterRequest.CommandCode == DiameterMessageCode.CREDIT_CONTROL) { ResponseWaiter.AddRequest(diameterRequest.SessionID, pWaiterThread); } //CER Never Contains a Session ID else if (diameterRequest.CommandCode == DiameterMessageCode.CAPABILITY_EXCHANGE) { ResponseWaiter.AddRequest("CEX", pWaiterThread); diameterRequest.SessionID = "CEX"; } else { StackLog.Write2TraceLog("Transport.SendMessage() ", "UnHandled Message Type:" + diameterRequest.CommandCode); return(null); } //Record Time TimeSpan STime = new TimeSpan(DateTime.Now.Ticks); ///////////////////////////////Send Message to the Remote Peer //////////////////////////////// //StackLog.Write2TraceLog("\r\nSendMessage", diameterRequest.ToString()); msgLogger.Write2MessageLog(diameterRequest.ToString()); Common.StackLog.Write2TraceLog("Transport::SendMessage() ", " Sending Message " + DiameterMessageCode.GetMessageName(diameterRequest.CommandCode, true) + " (" + diameterRequest.SessionID + ") .."); destPeer.PeerConnection.GetStream().Write(mgsBytesToSend, 0, mgsBytesToSend.Length); //Wait for Response; Common.StackLog.Write2TraceLog("Transport::SendMessage() ", " Message Sent, Waiting For Diameter Message Response of Session: " + diameterRequest.SessionID); bool isInterrupted = false; try { //Sleep for 3 Seconds Maximum until interrupted. for (int i = 0; i <= stackContext.CCATimeout * 10; i++) { Thread.Sleep(100); } } catch (ThreadInterruptedException ex) { isInterrupted = true; //StackLog.Write2ErrorLog("SendMessage", "Thread Intrupted for for Response for the Session: " + diameterRequest.SessionID); } if (isInterrupted) { Common.StackLog.Write2TraceLog("Transport.SendMessage() ", " Waiter Thread Response Interrupted for Session: " + diameterRequest.SessionID); } else { Common.StackLog.Write2TraceLog("Transport.SendMessage() ", " Waiter Thread Response Timedout for Session: " + diameterRequest.SessionID); } //After Thread intrruption get the response here. //CEX Dont have any session ID so validate here. Message diameterResponse; if (ResponseWaiter.ContainsResponse(diameterRequest.SessionID)) { diameterResponse = ResponseWaiter.GetResponse(diameterRequest.SessionID); } else { Common.StackLog.Write2ErrorLog("Transport::SendMessage", "Response message not available for " + DiameterMessageCode.GetMessageName(diameterRequest.CommandCode, true) + " " + diameterRequest.SessionID); return(null); } //Check the Recieved Response if (diameterResponse != null) { Common.StackLog.Write2TraceLog("Transport.SendMessage() ", "Response Message " + DiameterMessageCode.GetMessageName(diameterResponse.CommandCode, false) + " of Request Session: " + diameterRequest.SessionID + " with Response of:" + diameterResponse.SessionID.ToString() + " Received..\r\n"); /*if (diameterResponse.avps.Count == 0) * { * StackLog.Write2ErrorLog("SendMessage", "Response Msg has no AVP's for Session:" + diameterResponse.SessionID); * StackLog.Write2ErrorLog("SendMessage", diameterResponse.ToString()); * }*/ ////Log Recieved Message //StackLog.Write2MessageLog(diameterResponse.ToString()); msgLogger.Write2MessageLog(diameterResponse.ToString()); TimeSpan ETime = new TimeSpan(DateTime.Now.Ticks); diameterResponse.ExecTime = ETime.Subtract(STime).Milliseconds; //diameterResponse.PrintMessage(); } else { Common.StackLog.Write2ErrorLog("Transport::SendMessage", "Unable to Receive Response message for " + DiameterMessageCode.GetMessageName(diameterRequest.CommandCode, true) + " " + diameterRequest.SessionID); //Common.StackLog.Write2ErrorLog("Transport::SendMessage", diameterRequest.ToString()); } return(diameterResponse); } catch (Exception exp) { StackLog.Write2ErrorLog("DiameterTransport:SendMessage()", "Error:" + exp.Message + " Stack:" + exp.StackTrace.ToString()); //throw exp; return(null); } }
private void ReceiveCallbackSeq(IAsyncResult result) { int bytesRead; StateObject state = (StateObject)result.AsyncState; Socket client = state.workSocket; //NetworkStream networkStream = tcpClient.GetStream(); //responseBuffer = result.AsyncState as byte[]; try { // Retrieve the state object and the client socket try { // read = networkStream.EndRead(result); bytesRead = client.EndReceive(result); } catch { //An error has occured when reading return; } if (bytesRead == 0) { //The connection has been closed. return; } client.BeginReceive(state.buffer, 0, StateObject.BufferSize, 0, new AsyncCallback(ReceiveCallbackSeq), state); /// Begin processing Diameter messages /// byte[] responselocBuffer = new byte[bytesRead]; Array.Copy(state.buffer, 0, responselocBuffer, 0, bytesRead); Message msg = new Message(stackContext, responselocBuffer); //msg = msg.ProcessMessage(stackContext, responselocBuffer); //Perform Additional Messag Processing if (msg.CommandCode == DiameterMessageCode.DEVICE_WATCHDOG) { Message DWA = new Answer(stackContext).CreateDWA(msg); byte[] toSend = DWA.GetBytes(); //networkStream.Write(toSend, 0, toSend.Length); client.Send(toSend); } else { //Return message response if (msg.CommandCode == DiameterMessageCode.CAPABILITY_EXCHANGE) { if (ResponseWaiter.ContainsRequest("CEX")) { msg.SessionID = "CEX"; if (!ResponseWaiter.AddResponse(msg)) { Common.StackLog.Write2ErrorLog("ReceiveCallBack", "Unable to Add Response for CEA Session:" + msg.SessionID); } } else { Common.StackLog.Write2ErrorLog("ReceiveCallBack", "Unexpected CEA Received \r\n" + msg.ToString()); } } else if (msg.CommandCode == DiameterMessageCode.CREDIT_CONTROL) { if (ResponseWaiter.ContainsRequest(msg.SessionID)) { if (!ResponseWaiter.AddResponse(msg)) { Common.StackLog.Write2ErrorLog("ReceiveCallBack", "Unable to Add Response for CCA Session:" + msg.SessionID); } } else { Common.StackLog.Write2ErrorLog("ReceiveCallBack", "Unexpected CCA Received for Session " + msg.SessionID + "\r\n" + msg.ToString()); } } else { Common.StackLog.Write2ErrorLog("ReceiveCallBack", "Unexpected Messages Received:" + msg.ToString()); } } //Then start reading from the network again after Parsing recieved Message. //networkStream.BeginRead(responseBuffer, 0, responseBuffer.Length, ReceiveCallback, buffer); } catch (Exception e) { //Then start reading from the network again. //networkStream.BeginRead(buffer, 0, buffer.Length, ReceiveCallback, buffer); //state.workSocket.Connect(state.workSocket.RemoteEndPoint); Common.StackLog.Write2ErrorLog("ReceiveCallBack", "Error:" + e.Message + " Stack:" + e.StackTrace); client.BeginReceive(state.buffer, 0, StateObject.BufferSize, 0, new AsyncCallback(ReceiveCallbackSeq), state); } }