aboutsummaryrefslogtreecommitdiff
path: root/ChocolArm64/State/AThreadState.cs
diff options
context:
space:
mode:
Diffstat (limited to 'ChocolArm64/State/AThreadState.cs')
-rw-r--r--ChocolArm64/State/AThreadState.cs30
1 files changed, 23 insertions, 7 deletions
diff --git a/ChocolArm64/State/AThreadState.cs b/ChocolArm64/State/AThreadState.cs
index 783f5a12..22e3df14 100644
--- a/ChocolArm64/State/AThreadState.cs
+++ b/ChocolArm64/State/AThreadState.cs
@@ -2,6 +2,7 @@ using ChocolArm64.Events;
using System;
using System.Collections.Generic;
using System.Diagnostics;
+using System.Runtime.CompilerServices;
using System.Runtime.Intrinsics;
namespace ChocolArm64.State
@@ -14,6 +15,8 @@ namespace ChocolArm64.State
internal const int ErgSizeLog2 = 4;
internal const int DczSizeLog2 = 4;
+ private const int MinInstForCheck = 4000000;
+
internal AExecutionMode ExecutionMode;
//AArch32 state.
@@ -45,6 +48,8 @@ namespace ChocolArm64.State
private bool Interrupted;
+ private int SyncCount;
+
public long TpidrEl0 { get; set; }
public long Tpidr { get; set; }
@@ -101,13 +106,16 @@ namespace ChocolArm64.State
TickCounter.Start();
}
- internal bool Synchronize()
+ [MethodImpl(MethodImplOptions.AggressiveInlining)]
+ internal bool Synchronize(int BbWeight)
{
- if (Interrupted)
- {
- Interrupted = false;
+ //Firing a interrupt frequently is expensive, so we only
+ //do it after a given number of instructions has executed.
+ SyncCount += BbWeight;
- OnInterrupt();
+ if (SyncCount >= MinInstForCheck)
+ {
+ CheckInterrupt();
}
return Running;
@@ -118,9 +126,17 @@ namespace ChocolArm64.State
Interrupted = true;
}
- private void OnInterrupt()
+ [MethodImpl(MethodImplOptions.NoInlining)]
+ private void CheckInterrupt()
{
- Interrupt?.Invoke(this, EventArgs.Empty);
+ SyncCount = 0;
+
+ if (Interrupted)
+ {
+ Interrupted = false;
+
+ Interrupt?.Invoke(this, EventArgs.Empty);
+ }
}
internal void OnBreak(long Position, int Imm)