Beispiel #1
0
 /// <summary>
 /// Internal function to reset the SetupStep objects of all channels.
 /// </summary>
 private void ResetSteps()
 {
     for (int i = 0; i < this.sessions.Length; i++)
     {
         SetupStep currStep = this.hostRoot.GetStep(i);
         if (currStep.State == SetupStepState.READY || currStep.State == SetupStepState.ERROR)
         {
             currStep.Reset();
         }
     }
 }
Beispiel #2
0
        /// <summary>
        /// Sends the setup step answer to the host.
        /// </summary>
        private void ContinueSetup()
        {
            /// Send the answer packages.
            SetupStep currStep = this.guestRoot.Step;

            RCPackage[] packagesToSend = currStep.CreateAnswer(this.channelProxy.OutgoingPackages != null ?
                                                               this.channelProxy.OutgoingPackages :
                                                               new RCPackage[0] {
            });
            currStep.Reset();
            foreach (RCPackage pckg in packagesToSend)
            {
                this.guestRoot.Lobby.SendControlPackage(pckg);
            }

            /// Trigger the session state machine.
            this.SendingSetupStepAW_WaitingSetupStepRQ.Fire();
        }
Beispiel #3
0
        /// <summary>
        /// This function is called when a control package arrives at setup stage.
        /// </summary>
        /// <param name="package">The arrived control package.</param>
        public void SetupStageCtrlPackage(RCPackage package)
        {
            bool error = false;

            if (this.sm.CurrentState == this.WaitingConnectionRQ)
            {
                if (package.PackageFormat.ID == DssRoot.DSS_CTRL_CONN_REQUEST)
                {
                    RCPackage rejPackage    = null;
                    int       otherMajor    = package.ReadInt(0);
                    int       otherMinor    = package.ReadInt(1);
                    int       otherBuild    = package.ReadInt(2);
                    int       otherRevision = package.ReadInt(3);
                    if (otherMajor >= 0 && otherMinor >= 0 && otherBuild >= 0 && otherRevision >= 0)
                    {
                        Version otherVer = new Version(otherMajor, otherMinor, otherBuild, otherRevision);
                        if (DssRoot.IsCompatibleVersion(otherVer))
                        {
                            /// We send back a DSS_CTRL_CONN_ACK package.
                            RCPackage ackPackage = RCPackage.CreateNetworkControlPackage(DssRoot.DSS_CTRL_CONN_ACK);
                            ackPackage.WriteInt(0, DssRoot.APPLICATION_VERSION.Major);
                            ackPackage.WriteInt(1, DssRoot.APPLICATION_VERSION.Minor);
                            ackPackage.WriteInt(2, DssRoot.APPLICATION_VERSION.Build);
                            ackPackage.WriteInt(3, DssRoot.APPLICATION_VERSION.Revision);

                            this.manager.HostRoot.Lobby.SendControlPackage(ackPackage, this.channel.Index + 1);
                            this.WaitingConnectionRQ_SendingSetupStepRQ.Fire();
                        }
                        else
                        {
                            /// We send back a DSS_CTRL_CONN_REJECT package
                            rejPackage = RCPackage.CreateNetworkControlPackage(DssRoot.DSS_CTRL_CONN_REJECT);
                            string reason = string.Format("Incompatible with host version: {0} (RC.DssServices)",
                                                          DssRoot.APPLICATION_VERSION.ToString());
                            rejPackage.WriteString(0, reason);
                            rejPackage.WriteByteArray(1, new byte[0]);
                        }
                    }
                    else
                    {
                        /// We create a DSS_CTRL_CONN_REJECT package
                        rejPackage = RCPackage.CreateNetworkControlPackage(DssRoot.DSS_CTRL_CONN_REJECT);
                        rejPackage.WriteString(0, "Unable to parse version information!");
                        rejPackage.WriteByteArray(1, new byte[0]);
                    }


                    /// We send back a DSS_CTRL_CONN_REJECT package if necessary.
                    if (rejPackage != null && rejPackage.IsCommitted)
                    {
                        this.manager.HostRoot.Lobby.SendControlPackage(rejPackage, this.channel.Index + 1);

                        error = true;
                    }
                } /// end-if (package.PackageFormat.ID == DssRoot.DSS_CTRL_CONN_REQUEST)
            }     /// end-if (this.sm.CurrentState == this.WaitingConnectionRQ)
            else if (this.sm.CurrentState == this.WaitingSetupStepAW)
            {
                if (package.PackageFormat.ID == DssRoot.DSS_LEAVE)
                {
                    string leaveReason = package.ReadString(0);
                    string trcMsg      = string.Format("Guest-{0} has left the DSS. Reason: {1}",
                                                       this.channel.Index,
                                                       leaveReason.Length != 0 ? leaveReason : "-");
                    TraceManager.WriteAllTrace(trcMsg, DssTraceFilters.SETUP_STAGE_INFO);
                    this.WaitingSetupStepAW_Inactive.Fire();
                    this.channel.GuestLeaveSetupStage();
                } /// end-if (package.PackageFormat.ID == DssRoot.DSS_LEAVE)
                else
                {
                    SetupStep currentStep = this.manager.HostRoot.GetStep(this.channel.Index);
                    currentStep.IncomingPackage(package);
                    if (currentStep.State == SetupStepState.READY)
                    {
                        /// Setup step answer arrived.
                        this.WaitingSetupStepAW_SendingSetupStepRQ.Fire();
                    }
                    else if (currentStep.State == SetupStepState.ERROR)
                    {
                        /// Setup step answer error.
                        error = true;
                    }
                    else
                    {
                        /// Setup step answer not finished yet, more packages to wait.
                    }
                }
            } /// end-if (this.sm.CurrentState == this.WaitingSetupStepAW)

            if (error)
            {
                /// Go to error state if the package cannot be handled until now.
                SetupStageError();
                this.channel.SetupStageError();
                return;
            }
        }
Beispiel #4
0
        /// <summary>
        /// Sends the setup step requests to the guests, perform the tasks initiated by the client module and
        /// send the SMC to waiting state.
        /// </summary>
        private void ContinueSetup()
        {
            this.SetupStepTimerInactive_Running.Fire();
            this.SendingSetupStepRQs_WaitingSetupStepAWs.Fire();

            /// First handle the channels where drop happened.
            for (int i = 0; i < this.channelProxies.Length; i++)
            {
                if (this.channelProxies[i].TaskToPerform == DssChannelTask.DROP_AND_OPEN ||
                    this.channelProxies[i].TaskToPerform == DssChannelTask.DROP_AND_CLOSE)
                {
                    /// Drop guest and close channel if necessary.
                    this.channels[i].DropGuest(this.channelProxies[i].TaskToPerform == DssChannelTask.DROP_AND_OPEN);
                    this.hostRoot.GuestLeftDss(i);
                }
            }

            /// Then handle any other channels.
            for (int i = 0; i < this.sessions.Length; i++)
            {
                if (this.channelProxies[i].TaskToPerform == DssChannelTask.CLOSE)
                {
                    /// Close the channel.
                    this.channels[i].CloseChannel();
                }
                else if (this.channelProxies[i].TaskToPerform == DssChannelTask.OPEN)
                {
                    /// Open the channel.
                    this.channels[i].OpenChannel();
                }
                else if (this.channelProxies[i].TaskToPerform != DssChannelTask.DROP_AND_OPEN &&
                         this.channelProxies[i].TaskToPerform != DssChannelTask.DROP_AND_CLOSE)
                {
                    /// No task to perform on the channel just send the setup step request.
                    if (this.channels[i].CurrentState == this.channels[i].Engaged)
                    {
                        SetupStep currStep = this.hostRoot.GetStep(i);
                        if (currStep.State == SetupStepState.READY || currStep.State == SetupStepState.ERROR)
                        {
                            currStep.Reset();
                        }
                        DssChannelState[] chStates = new DssChannelState[this.channels.Length];
                        for (int j = 0; j < channels.Length; j++)
                        {
                            if (this.channelProxies[j].TaskToPerform == DssChannelTask.OPEN ||
                                this.channelProxies[j].TaskToPerform == DssChannelTask.DROP_AND_OPEN)
                            {
                                chStates[j] = DssChannelState.CHANNEL_OPENED;
                            }
                            else if (this.channelProxies[j].TaskToPerform == DssChannelTask.CLOSE ||
                                     this.channelProxies[j].TaskToPerform == DssChannelTask.DROP_AND_CLOSE)
                            {
                                chStates[j] = DssChannelState.CHANNEL_CLOSED;
                            }
                            else
                            {
                                if (this.channels[j].CurrentState == this.channels[j].Opened)
                                {
                                    chStates[j] = DssChannelState.CHANNEL_OPENED;
                                }
                                else if (this.channels[j].CurrentState == this.channels[j].Closed)
                                {
                                    chStates[j] = DssChannelState.CHANNEL_CLOSED;
                                }
                                else if (this.channels[j].CurrentState == this.channels[j].Engaged)
                                {
                                    chStates[j] = DssChannelState.GUEST_CONNECTED;
                                }
                                else
                                {
                                    throw new DssException("Unexpected channel state!");
                                }
                            }
                        }

                        int[] leftList = null;
                        int[] lostList = null;
                        this.hostRoot.GetGuestEvents(out leftList, out lostList);
                        RCPackage[] packagesToSend = currStep.CreateRequest(this.channelProxies[i].OutgoingPackages != null ?
                                                                            this.channelProxies[i].OutgoingPackages :
                                                                            new RCPackage[0] {
                        },
                                                                            leftList,
                                                                            lostList,
                                                                            chStates);
                        foreach (RCPackage pckg in packagesToSend)
                        {
                            this.hostRoot.Lobby.SendControlPackage(pckg, i + 1);
                        }
                        this.sessions[i].SetupStepRequestSent();
                    }
                }
            } /// end-for (int i = 0; i < this.channelProxies.Length; i++)
        }
Beispiel #5
0
        /// <summary>
        /// This function is called by the SMC framework when the DSS-manager has to call the setup interface
        /// of the client module.
        /// </summary>
        /// <param name="state"></param>
        private void CallClientModuleSetupIface(ISMState state)
        {
            if (state == this.SendingSetupStepRQs)
            {
                TraceManager.WriteAllTrace("Calling IDssHostSetup.ExecuteNextStep on client module.", DssTraceFilters.SETUP_STAGE_INFO);

                /// Unlock the channel interfaces for the client module.
                IDssGuestChannel[] channelIfaces = this.DssChannelIfaces;
                for (int i = 0; i < this.channels.Length; i++)
                {
                    if (this.channels[i].CurrentState == this.channels[i].Opened)
                    {
                        this.channelProxies[i].UnlockForClient(null, DssChannelState.CHANNEL_OPENED);
                    }
                    else if (this.channels[i].CurrentState == this.channels[i].Closed)
                    {
                        this.channelProxies[i].UnlockForClient(null, DssChannelState.CHANNEL_CLOSED);
                    }
                    else if (this.channels[i].CurrentState == this.channels[i].Engaged)
                    {
                        SetupStep currStep = this.hostRoot.GetStep(i);
                        this.channelProxies[i].UnlockForClient(currStep.StepPackageList, DssChannelState.GUEST_CONNECTED);
                    }
                    else
                    {
                        throw new DssException("Unexpected channel state!");
                    }
                }

                /// Calling the client module for setup step execution.
                DssSetupResult result = this.hostRoot.SetupIface.ExecuteNextStep(channelIfaces);

                /// Lock the channel interfaces.
                for (int i = 0; i < this.channels.Length; i++)
                {
                    this.channelProxies[i].Lock();
                }

                /// Evaluate the result of the setup step execution.
                if (result == DssSetupResult.CONTINUE_SETUP)
                {
                    ContinueSetup();
                }
                else if (result == DssSetupResult.LEAVE_DSS)
                {
                    LeaveDss();
                }
                else if (result == DssSetupResult.START_SIMULATION)
                {
                    StartSimulation();
                }
                else
                {
                    throw new DssException("Unexpected answer from client module!");
                }
            }
            else
            {
                throw new DssException("Unexpected state!");
            }
        }