private void StartReadNextMessage() { // read next message m_msgReceiveTask.StartReceiveMessage(); // don't perform anything after StartReceiveMessage, because a received message may // already be in ProcessRequestMessage now }
/// <summary> /// begins receiving messages asynchronously /// </summary> internal void StartMessageReception() { lock (this) { if (m_messageReceiveTask == null) { m_messageReceiveTask = new MessageReceiveTask(m_transport, this); m_messageReceiveTask.StartReceiveMessage(); } // else ignore, already started } }
internal void ProcessLocateRequestMessage(Stream requestStream, MessageReceiveTask receiveTask) { // this called is completely handled by IIOP.NET // -> no servant will be called and therefore whole request is processed before reading next message try { m_receiver.ProcessLocateRequest(requestStream, m_serverCon); receiveTask.StartReceiveMessage(); } catch (Exception ex) { HandleUnexpectedProcessingException(); Trace.WriteLine("stopped processing on server connection after unexpected exception: " + ex); } }
internal void MsgReceivedCallback(MessageReceiveTask messageReceived) { Stream messageStream = messageReceived.MessageStream; GiopHeader header = messageReceived.Header; if (FragmentedMessageAssembler.IsFragmentedMessage(header)) { // defragment if (FragmentedMessageAssembler.IsStartFragment(header)) { m_fragmentAssembler.StartFragment(messageStream); messageReceived.StartReceiveMessage(); // receive next message return; // wait for next callback } else if (!FragmentedMessageAssembler.IsLastFragment(header)) { m_fragmentAssembler.AddFragment(messageStream); messageReceived.StartReceiveMessage(); // receive next message return; // wait for next callback } else { messageStream = m_fragmentAssembler.FinishFragmentedMsg(messageStream, out header); } } // here, the message is no longer fragmented, don't check for fragment here switch (header.GiopType) { case GiopMsgTypes.Request: ProcessRequestMessage(messageStream, messageReceived); // process this message // don't receive next message here, new message reception is started by dispatcher at appropriate time break; case GiopMsgTypes.LocateRequest: ProcessLocateRequestMessage(messageStream, messageReceived); // process this message // don't receive next message here, new message reception is started by dispatcher at appropriate time break; case GiopMsgTypes.Reply: // see, if somebody is interested in the response lock (m_waitingForResponse.SyncRoot) { uint replyForRequestId = ExtractRequestIdFromReplyMessage(messageStream); IResponseWaiter waiter = (IResponseWaiter)m_waitingForResponse[replyForRequestId]; if (waiter != null) { m_waitingForResponse.Remove(replyForRequestId); waiter.Response = messageStream; waiter.Notify(); } else { Debug.WriteLine("received not expected reply for request with id " + replyForRequestId); } } messageReceived.StartReceiveMessage(); // receive next message break; case GiopMsgTypes.LocateReply: // ignore, not interesting messageReceived.StartReceiveMessage(); // receive next message break; case GiopMsgTypes.CloseConnection: CloseConnection(); AbortAllPendingRequestsWaiting(); // if requests are waiting for a reply, abort them RaiseConnectionClosedEvent(); // inform about connection closure break; case GiopMsgTypes.CancelRequest: CdrInputStreamImpl input = new CdrInputStreamImpl(messageStream); GiopHeader cancelHeader = new GiopHeader(input); uint requestIdToCancel = input.ReadULong(); m_fragmentAssembler.CancelFragmentsIfInProgress(requestIdToCancel); messageReceived.StartReceiveMessage(); // receive next message break; case GiopMsgTypes.MessageError: CloseConnectionAfterUnexpectedException(new MARSHAL(16, CompletionStatus.Completed_MayBe)); AbortAllPendingRequestsWaiting(); // if requests are waiting for a reply, abort them RaiseConnectionClosedEvent(); // inform about connection closure break; default: // should not occur; // hint: fragment is also considered as error here, // because fragment should be handled before this loop // send message error SendErrorResponseMessage(); messageReceived.StartReceiveMessage(); // receive next message break; } }
internal void MsgReceivedCallback(MessageReceiveTask messageReceived) { Stream messageStream = messageReceived.MessageStream; GiopHeader header = messageReceived.Header; if (FragmentedMessageAssembler.IsFragmentedMessage(header)) { // defragment if (FragmentedMessageAssembler.IsStartFragment(header)) { m_fragmentAssembler.StartFragment(messageStream); messageReceived.StartReceiveMessage(); // receive next message return; // wait for next callback } else if (!FragmentedMessageAssembler.IsLastFragment(header)) { m_fragmentAssembler.AddFragment(messageStream); messageReceived.StartReceiveMessage(); // receive next message return; // wait for next callback } else { messageStream = m_fragmentAssembler.FinishFragmentedMsg(messageStream, out header); } } // here, the message is no longer fragmented, don't check for fragment here switch (header.GiopType) { case GiopMsgTypes.Request: ProcessRequestMessage(messageStream, messageReceived); // process this message // don't receive next message here, new message reception is started by dispatcher at appropriate time break; case GiopMsgTypes.LocateRequest: ProcessLocateRequestMessage(messageStream, messageReceived); // process this message // don't receive next message here, new message reception is started by dispatcher at appropriate time break; case GiopMsgTypes.Reply: // see, if somebody is interested in the response lock (m_waitingForResponse.SyncRoot) { uint replyForRequestId = ExtractRequestIdFromReplyMessage(messageStream); IResponseWaiter waiter = (IResponseWaiter)m_waitingForResponse[replyForRequestId]; if (waiter != null) { m_waitingForResponse.Remove(replyForRequestId); waiter.Response = messageStream; waiter.Notify(); } else { Debug.WriteLine("received not expected reply for request with id " + replyForRequestId); } } messageReceived.StartReceiveMessage(); // receive next message break; case GiopMsgTypes.LocateReply: // ignore, not interesting messageReceived.StartReceiveMessage(); // receive next message break; case GiopMsgTypes.CloseConnection: CloseConnection(); AbortAllPendingRequestsWaiting(); // if requests are waiting for a reply, abort them RaiseConnectionClosedEvent(); // inform about connection closure break; case GiopMsgTypes.CancelRequest: CdrInputStreamImpl input = new CdrInputStreamImpl(messageStream); GiopHeader cancelHeader = new GiopHeader(input); uint requestIdToCancel = input.ReadULong(); m_fragmentAssembler.CancelFragmentsIfInProgress(requestIdToCancel); messageReceived.StartReceiveMessage(); // receive next message break; case GiopMsgTypes.MessageError: CloseConnectionAfterUnexpectedException(new MARSHAL(16, CompletionStatus.Completed_MayBe)); AbortAllPendingRequestsWaiting(); // if requests are waiting for a reply, abort them RaiseConnectionClosedEvent(); // inform about connection closure break; default: // should not occur; // hint: fragment is also considered as error here, // because fragment should be handled before this loop // send message error SendErrorResponseMessage(); messageReceived.StartReceiveMessage(); // receive next message break; } }
/// <summary> /// begins receiving messages asynchronously /// </summary> internal void StartMessageReception() { lock(this) { if (m_messageReceiveTask == null) { m_messageReceiveTask = new MessageReceiveTask(m_transport, this); m_messageReceiveTask.StartReceiveMessage(); } // else ignore, already started } }
internal void ProcessLocateRequestMessage(Stream requestStream, MessageReceiveTask receiveTask) { // this called is completely handled by IIOP.NET // -> no servant will be called and therefore whole request is processed before reading next message try { m_receiver.ProcessLocateRequest(requestStream, m_serverCon); receiveTask.StartReceiveMessage(); } catch (Exception ex) { HandleUnexpectedProcessingException(); Trace.WriteLine("stopped processing on server connection after unexpected exception: " + ex); } }