mirror of
https://github.com/par274/sharpemu.git
synced 2026-07-20 01:46:22 +08:00
[cpu] Add guest thread continuation
This commit is contained in:
@@ -15,8 +15,49 @@ public interface IGuestThreadScheduler
|
||||
bool TryStartThread(CpuContext creatorContext, GuestThreadStartRequest request, out string? error);
|
||||
|
||||
void Pump(CpuContext callerContext, string reason);
|
||||
|
||||
bool TryCallGuestFunction(
|
||||
CpuContext callerContext,
|
||||
ulong entryPoint,
|
||||
ulong arg0,
|
||||
ulong arg1,
|
||||
ulong stackAddress,
|
||||
ulong stackSize,
|
||||
string reason,
|
||||
out string? error);
|
||||
|
||||
bool TryCallGuestContinuation(
|
||||
CpuContext callerContext,
|
||||
GuestCpuContinuation continuation,
|
||||
string reason,
|
||||
out string? error);
|
||||
}
|
||||
|
||||
public readonly record struct GuestImportCallFrame(
|
||||
bool IsValid,
|
||||
ulong ReturnRip,
|
||||
ulong ResumeRsp);
|
||||
|
||||
public readonly record struct GuestCpuContinuation(
|
||||
ulong Rip,
|
||||
ulong Rsp,
|
||||
ulong Rflags,
|
||||
ulong FsBase,
|
||||
ulong GsBase,
|
||||
ulong Rax,
|
||||
ulong Rcx,
|
||||
ulong Rdx,
|
||||
ulong Rbx,
|
||||
ulong Rbp,
|
||||
ulong Rsi,
|
||||
ulong Rdi,
|
||||
ulong R8,
|
||||
ulong R9,
|
||||
ulong R12,
|
||||
ulong R13,
|
||||
ulong R14,
|
||||
ulong R15);
|
||||
|
||||
public static class GuestThreadExecution
|
||||
{
|
||||
[ThreadStatic]
|
||||
@@ -34,6 +75,15 @@ public static class GuestThreadExecution
|
||||
[ThreadStatic]
|
||||
private static string? _pendingEntryExitReason;
|
||||
|
||||
[ThreadStatic]
|
||||
private static bool _hasCurrentImportCallFrame;
|
||||
|
||||
[ThreadStatic]
|
||||
private static ulong _currentImportReturnRip;
|
||||
|
||||
[ThreadStatic]
|
||||
private static ulong _currentImportResumeRsp;
|
||||
|
||||
public static IGuestThreadScheduler? Scheduler { get; set; }
|
||||
|
||||
public static bool IsGuestThread => _currentGuestThreadHandle != 0;
|
||||
@@ -48,6 +98,9 @@ public static class GuestThreadExecution
|
||||
_pendingEntryExit = false;
|
||||
_pendingEntryExitStatus = 0;
|
||||
_pendingEntryExitReason = null;
|
||||
_hasCurrentImportCallFrame = false;
|
||||
_currentImportReturnRip = 0;
|
||||
_currentImportResumeRsp = 0;
|
||||
return previous;
|
||||
}
|
||||
|
||||
@@ -58,6 +111,9 @@ public static class GuestThreadExecution
|
||||
_pendingEntryExit = false;
|
||||
_pendingEntryExitStatus = 0;
|
||||
_pendingEntryExitReason = null;
|
||||
_hasCurrentImportCallFrame = false;
|
||||
_currentImportReturnRip = 0;
|
||||
_currentImportResumeRsp = 0;
|
||||
}
|
||||
|
||||
public static bool RequestCurrentThreadBlock(string reason)
|
||||
@@ -104,4 +160,35 @@ public static class GuestThreadExecution
|
||||
_pendingEntryExitReason = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public static GuestImportCallFrame EnterImportCallFrame(ulong returnRip, ulong resumeRsp)
|
||||
{
|
||||
var previous = new GuestImportCallFrame(
|
||||
_hasCurrentImportCallFrame,
|
||||
_currentImportReturnRip,
|
||||
_currentImportResumeRsp);
|
||||
_hasCurrentImportCallFrame = true;
|
||||
_currentImportReturnRip = returnRip;
|
||||
_currentImportResumeRsp = resumeRsp;
|
||||
return previous;
|
||||
}
|
||||
|
||||
public static void RestoreImportCallFrame(GuestImportCallFrame previous)
|
||||
{
|
||||
_hasCurrentImportCallFrame = previous.IsValid;
|
||||
_currentImportReturnRip = previous.ReturnRip;
|
||||
_currentImportResumeRsp = previous.ResumeRsp;
|
||||
}
|
||||
|
||||
public static bool TryGetCurrentImportCallFrame(out GuestImportCallFrame frame)
|
||||
{
|
||||
if (!_hasCurrentImportCallFrame)
|
||||
{
|
||||
frame = default;
|
||||
return false;
|
||||
}
|
||||
|
||||
frame = new GuestImportCallFrame(true, _currentImportReturnRip, _currentImportResumeRsp);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user