Emul8.Peripherals.CPU.TranslationCPU.CpuLoop C# (CSharp) Method

CpuLoop() private method

private CpuLoop ( ) : void
return void
        private void CpuLoop()
        {
            var tlibResult = 0;
            if(ClockSource.HasEntries && advanceShouldBeRestarted)
            {
                try
                {
                    ClockSource.Advance(0, true);
                    advanceShouldBeRestarted = false;
                }
                catch(OperationCanceledException)
                {
                    return;
                }
            }

            while(true)
            {
                if(!(DisableInterruptsWhileStepping && executionMode == ExecutionMode.SingleStep) && TlibIsIrqSet() == 0 && interruptEvents.Any(x => x.WaitOne(0)))
                {
                    for(var i = 0; i < interruptEvents.Length; i++)
                    {
                        var decodedInterrupt = DecodeInterrupt(i);
                        TlibSetIrq((int)decodedInterrupt, interruptEvents[i].WaitOne(0) ? 1 : 0);
                    }
                    //this.NoisyLog("IRQ not active while event set, added.");
                }
                try
                {
                    bool doIteration;
                    lock(haltedFinishedEvent)
                    {
                        doIteration = !isHalted;
                    }
                    if(doIteration)
                    {
                        Action queuedAction;
                        while(actionsToExecuteInCpuThread.TryDequeue(out queuedAction))
                        {
                            queuedAction();
                        }

                        HandleStepping(true);

                        pauseGuard.Enter();
                        skipNextStepping = true;
                        tlibResult = TlibExecute();
                        pauseGuard.Leave();
                    }
                }
                catch(CpuAbortException)
                {
                    this.NoisyLog("CPU abort detected, halting.");
                    isAborted = true;
                    InvokeHalted(new HaltArguments(HaltReason.Abort));
                    break;
                }
                catch(OperationCanceledException)
                {
                    advanceShouldBeRestarted = true;
                    break;
                }

                if(tlibResult == BreakpointResult)
                {
                    ExecuteHooks(PC);
                    // it is necessary to deactivate hooks installed on this PC before
                    // calling `tlib_execute` again to avoid a loop;
                    // we need to do this because creating a breakpoint has caused special
                    // exeption-rising, block-breaking `trap` instruction to be 
                    // generated by the tcg;
                    // in order to execute code after the breakpoint we must first remove
                    // this `trap` and retranslate the code right after it;
                    // this is achieved by deactivating the breakpoint (i.e., unregistering
                    // from tlib, but keeping it in C#), executing the beginning of the next
                    // block and registering the breakpoint again in the OnBlockBegin hook
                    DeactivateHooks(PC);
                }

                if(PauseEvent.WaitOne(0))
                {
                    break;
                }

                if(CheckHalted())
                {
                    if(ClockSource.HasEntries)
                    {
                        try
                        {
                            var timeToSleep = new TimeSpan(Time.Consts.TimeQuantum.Ticks * ClockSource.NearestLimitIn);
                            var timeToSleepInMs = Math.Min(int.MaxValue, (int)timeToSleep.TotalMilliseconds);
                            if(timeToSleepInMs > 0)
                            {
                                if(!AdvanceImmediately)
                                {
                                    WaitHandle.WaitAny(waitHandles, timeToSleepInMs);
                                }
                                ClockSource.Advance(Time.Utilities.SecondsToTicks(timeToSleepInMs / 1000.0));
                            }
                            else
                            {
                                ClockSource.Advance(ClockSource.NearestLimitIn);
                            }
                        }
                        catch(OperationCanceledException)
                        {
                            advanceShouldBeRestarted = true;
                            break;
                        }
                    }
                    else
                    {
                        WaitHandle.WaitAny(waitHandles);
                    }
                }
            }
        }
TranslationCPU