using System.Collections.Concurrent;
using System.Runtime.InteropServices;
using System.Security.Cryptography;
using System.Text;
using System.Text.Json.Nodes;
using XFEWarframe.Client;
using XFEWarframe.Client.Runtime;
namespace XFEWarframe.Bridge;
/// <summary>
/// Opt-in, loopback-only engine test adapter. Commands run on the game's profile update
/// thread, never on an HTTP worker. No keyboard, window messages or authentication UI.
/// </summary>
internal static unsafe class GameTestRuntime
{
private sealed record Request(string Operation, JsonObject Body, CancellationToken Cancellation, TaskCompletionSource<string> Completion);
private static readonly ConcurrentQueue<Request> Pending = new();
private static nint image, update, login, callbackTable;
private static Action<string> log = _ => { };
private static string loginResult = "not-requested";
private static int tickThread;
private static nint exclusiveInputSuit;
private static long exclusiveInputUntil;
private static readonly Queue<JsonObject> SoundEvents = [];
private static readonly object SoundGate = new();
private static long soundSequence;
private static long soundCalls;
[ThreadStatic] private static bool injectingAbilityInput;
public static bool Available { get; private set; }
internal static bool AcceptAbilityInput(nint suit) => !Available || injectingAbilityInput ||
suit != exclusiveInputSuit || Environment.TickCount64 >= exclusiveInputUntil;
public static void Prepare(nint module, ClientConfiguration config, List<NativeHook> hooks, Action<string> writeLog)
{
if (!config.EnableGameTestControl && !ExperimentalAbilityRuntime.Available) return;
if (config.EnableGameTestControl && (!new Uri(config.ServerUrl).IsLoopback || !new Uri(config.GameServerUrl).IsLoopback ||
!config.GameSha256.Equals(ExperimentalAbilityCompatibility.ExecutableSha256, StringComparison.OrdinalIgnoreCase))
)
throw new InvalidDataException("Game test control requires the audited build and a loopback server.");
Check(module + 0x8DFD50, "48895C2408574883EC20488B01488BD933FFFF90E8000000");
Check(module + 0xB1D570, "40555657415541564157488DAC2438FBFFFF4881ECC80500");
Check(module + 0x144CF80, "4053415541574883EC50450FB6E8448BFA488BD9E8A71F6C");
image = module; login = module + 0xB1D570; log = writeLog;
GameTestLua.Prepare(module);
var hook = new NativeHook(module + 0x8DFD50, (nint)(delegate* unmanaged<nint, void>)&Update);
update = hook.Trampoline; hooks.Add(hook);
if (!config.EnableGameTestControl) return;
Check(module + 0x1A2C7A0, "4C8BDC49895B0855565741544155415641574881EC80000000");
hooks.Add(NativeHook.Observe(module + 0x1A2C7A0, (nint)(delegate* unmanaged<nint, void>)&ObserveSound));
Check(module + 0x1568020, "48895C240848896C24104889742420574883EC60498B0041");
hooks.Add(NativeHook.Observe(module + 0x1568020, (nint)(delegate* unmanaged<nint, nint, nint, void>)&ObserveEntitySound));
Check(module + 0x10F77F0, "40534881ECA0000000488B05408479014833C44889842490");
hooks.Add(NativeHook.Observe(module + 0x10F77F0, (nint)(delegate* unmanaged<nint, nint, nint, nint, void>)&ObserveNativeSound));
callbackTable = (nint)NativeMemory.AllocZeroed(48);
var table = (nint*)callbackTable;
table[0] = (nint)(delegate* unmanaged<nint, void>)&CallbackDestroy;
table[1] = (nint)(delegate* unmanaged<nint, byte>)&CallbackValid;
table[2] = (nint)(delegate* unmanaged<nint, nint>)&CallbackTarget;
table[3] = (nint)(delegate* unmanaged<nint, nint>)&CallbackFunction;
table[4] = (nint)(delegate* unmanaged<nint, byte, Bootstrap.GameString*, void>)&LoginCompleted;
table[5] = (nint)(delegate* unmanaged<nint, nint, void>)&CallbackCopy;
Available = true;
log("Game test control: engine-thread adapter enabled for this launch.");
}
[UnmanagedCallersOnly] private static void ObserveSound(nint state)
{
try
{
Interlocked.Increment(ref soundCalls);
var arguments = *(nint*)(state + 0x10);
if (*(nint*)(state + 8) < arguments + 32 || *(int*)(arguments + 28) != 9) return;
var reference = *(nint*)(*(nint*)(arguments + 16) + 0x18);
var resource = reference == 0 ? 0 : *(nint*)reference;
if (resource == 0) return;
var type = ExperimentalAbilityRuntime.DescribeResource(*(nint*)(resource + 8));
if (type is null) return;
RecordSound(type, "lua");
}
catch { /* Observation never changes playback. */ }
}
[UnmanagedCallersOnly] private static void ObserveEntitySound(nint result, nint actor, nint reference)
{
try
{
var resource = reference == 0 || *(nint*)reference == 0 ? 0 : **(nint**)reference;
if (resource != 0 && ExperimentalAbilityRuntime.DescribeResource(*(nint*)(resource + 8)) is { } type)
RecordSound(type, "entity");
}
catch { /* Observation never changes playback. */ }
}
private static void RecordSound(string type, string source)
{
lock (SoundGate)
{
SoundEvents.Enqueue(new JsonObject { ["sequence"] = ++soundSequence, ["resource"] = type, ["source"] = source });
while (SoundEvents.Count > 256) SoundEvents.Dequeue();
}
}
[UnmanagedCallersOnly] private static void ObserveNativeSound(nint region, nint result, nint reference, nint actor)
{
try
{
var resource = reference == 0 || *(nint*)reference == 0 ? 0 : **(nint**)reference;
if (resource != 0 && ExperimentalAbilityRuntime.DescribeResource(*(nint*)(resource + 8)) is { } type)
RecordSound(type, "native");
}
catch { /* Observation never changes playback. */ }
}
internal static JsonObject SoundSnapshot()
{
lock (SoundGate) return new() { ["calls"] = Interlocked.Read(ref soundCalls),
["events"] = new JsonArray(SoundEvents.Select(e => (JsonNode)e.DeepClone()).ToArray()) };
}
private static void Check(nint address, string bytes)
{
var expected = Convert.FromHexString(bytes);
if (!new ReadOnlySpan<byte>((void*)address, expected.Length).SequenceEqual(expected))
throw new InvalidDataException("Game test ABI signature changed.");
}
public static Task<string> Dispatch(string operation, byte[] body, CancellationToken cancellation)
{
cancellation.ThrowIfCancellationRequested();
if (Pending.Count >= 16) throw new InvalidOperationException("Game command queue is full.");
var data = GameTestProtocol.Parse(operation, body);
var completion = new TaskCompletionSource<string>(TaskCreationOptions.RunContinuationsAsynchronously);
Pending.Enqueue(new(operation, data, cancellation, completion));
return completion.Task.WaitAsync(cancellation);
}
[UnmanagedCallersOnly] private static void Update(nint manager)
{
((delegate* unmanaged<nint, void>)update)(manager);
ExperimentalAbilityRuntime.UpdateHud();
ExperimentalAbilityRuntime.UpdateKing();
GameBranding.UpdateLoginUi(*(int*)(manager + 0x168) == 4);
if (Pending.IsEmpty) return;
if (tickThread == 0) tickThread = Environment.CurrentManagedThreadId;
if (tickThread != Environment.CurrentManagedThreadId) return;
if (!Pending.TryDequeue(out var request)) return;
try
{
request.Cancellation.ThrowIfCancellationRequested();
if (*(nint*)manager != image + 0x214BA70) throw new InvalidOperationException("Unexpected game profile manager.");
if (request.Operation == "POST lua")
{
request.Completion.TrySetResult(GameTestLua.Execute(request.Body).ToJsonString());
return;
}
if (request.Operation == "GET ability-state")
{
request.Completion.TrySetResult(GameTestLua.WithLocalSuit(ExperimentalAbilityRuntime.Snapshot).ToJsonString());
return;
}
if (request.Operation == "POST ability-input")
{
var slot = request.Body["slot"]!.GetValue<int>();
var pressed = request.Body["pressed"]!.GetValue<bool>();
var result = GameTestLua.WithLocalSuit(suit =>
{
if (request.Body["exclusive"] is { } exclusive)
{
exclusiveInputSuit = suit;
// A crashed test runner must never leave the user's controls disabled.
exclusiveInputUntil = exclusive.GetValue<bool>() ? Environment.TickCount64 + 10000 : 0;
}
injectingAbilityInput = true;
try
{
// Enter the normal game skill input handler, including passive/input scripts.
return new JsonObject { ["handled"] = ((delegate* unmanaged<nint, int, byte, byte>)(image + 0x144CF80))
(suit, 0x91 + slot, pressed ? (byte)1 : (byte)0) != 0 };
}
finally { injectingAbilityInput = false; }
});
request.Completion.TrySetResult(result.ToJsonString());
return;
}
if (request.Operation == "POST login") Login(manager, request.Body);
request.Completion.TrySetResult(new JsonObject
{
["profileState"] = *(int*)(manager + 0x168),
["profileCount"] = *(uint*)(manager + 0x238) / 8,
["loginResult"] = loginResult,
["thread"] = tickThread
}.ToJsonString());
}
catch (Exception ex) { request.Completion.TrySetException(ex); }
finally { request.Body.Clear(); }
}
private static void Login(nint manager, JsonObject body)
{
var state = *(int*)(manager + 0x168);
if (state is 1 or 4) throw new InvalidOperationException("The game is already logging in or logged in.");
var email = Bootstrap.GameString.Empty; var hash = Bootstrap.GameString.Empty;
var emailBytes = Encoding.UTF8.GetBytes(body["email"]!.GetValue<string>());
var hashBytes = Encoding.ASCII.GetBytes(body["passwordHash"]!.GetValue<string>());
Span<nint> callback = stackalloc nint[3]; callback.Clear(); callback[0] = callbackTable;
try
{
email.Assign(emailBytes);
hash.Assign(hashBytes);
loginResult = "pending";
fixed (nint* callbackPointer = callback)
((delegate* unmanaged<nint, Bootstrap.GameString*, Bootstrap.GameString*, nint*, byte, void>)login)
(manager, &email, &hash, callbackPointer, 1);
log("Game test control: native login requested.");
}
finally
{
email.ClearAndFree(); hash.ClearAndFree();
CryptographicOperations.ZeroMemory(emailBytes); CryptographicOperations.ZeroMemory(hashBytes);
}
}
[UnmanagedCallersOnly] private static void CallbackDestroy(nint self) => *(nint*)self = 0;
[UnmanagedCallersOnly] private static byte CallbackValid(nint self) => 1;
[UnmanagedCallersOnly] private static nint CallbackTarget(nint self) => 0;
[UnmanagedCallersOnly] private static nint CallbackFunction(nint self) => (nint)(delegate* unmanaged<nint, byte, Bootstrap.GameString*, void>)&LoginCompleted;
[UnmanagedCallersOnly] private static void CallbackCopy(nint source, nint destination) => new ReadOnlySpan<byte>((void*)source, 24).CopyTo(new Span<byte>((void*)destination, 24));
[UnmanagedCallersOnly] private static void LoginCompleted(nint self, byte success, Bootstrap.GameString* message)
{
loginResult = success != 0 ? "succeeded" : "failed";
// The game's message may contain account data; never include it in logs or status.
log("Game test control: native login " + loginResult + ".");
}
}
using System.Collections.Concurrent;
using System.Runtime.InteropServices;
using System.Security.Cryptography;
using System.Text;
using System.Text.Json.Nodes;
using XFEWarframe.Client;
using XFEWarframe.Client.Runtime;
namespace XFEWarframe.Bridge;
/// <summary>
/// Opt-in, loopback-only engine test adapter. Commands run on the game's profile update
/// thread, never on an HTTP worker. No keyboard, window messages or authentication UI.
/// </summary>
internal static unsafe class GameTestRuntime
{
private sealed record Request(string Operation, JsonObject Body, CancellationToken Cancellation, TaskCompletionSource<string> Completion);
private static readonly ConcurrentQueue<Request> Pending = new();
private static nint image, update, login, callbackTable;
private static Action<string> log = _ => { };
private static string loginResult = "not-requested";
private static int tickThread;
private static nint exclusiveInputSuit;
private static long exclusiveInputUntil;
private static readonly Queue<JsonObject> SoundEvents = [];
private static readonly object SoundGate = new();
private static long soundSequence;
private static long soundCalls;
[ThreadStatic] private static bool injectingAbilityInput;
public static bool Available { get; private set; }
internal static bool AcceptAbilityInput(nint suit) => !Available || injectingAbilityInput ||
suit != exclusiveInputSuit || Environment.TickCount64 >= exclusiveInputUntil;
public static void Prepare(nint module, ClientConfiguration config, List<NativeHook> hooks, Action<string> writeLog)
{
if (!config.EnableGameTestControl && !ExperimentalAbilityRuntime.Available) return;
if (config.EnableGameTestControl && (!new Uri(config.ServerUrl).IsLoopback || !new Uri(config.GameServerUrl).IsLoopback ||
!config.GameSha256.Equals(ExperimentalAbilityCompatibility.ExecutableSha256, StringComparison.OrdinalIgnoreCase))
)
throw new InvalidDataException("Game test control requires the audited build and a loopback server.");
Check(module + 0x8DFD50, "48895C2408574883EC20488B01488BD933FFFF90E8000000");
Check(module + 0xB1D570, "40555657415541564157488DAC2438FBFFFF4881ECC80500");
Check(module + 0x144CF80, "4053415541574883EC50450FB6E8448BFA488BD9E8A71F6C");
image = module; login = module + 0xB1D570; log = writeLog;
GameTestLua.Prepare(module);
var hook = new NativeHook(module + 0x8DFD50, (nint)(delegate* unmanaged<nint, void>)&Update);
update = hook.Trampoline; hooks.Add(hook);
if (!config.EnableGameTestControl) return;
Check(module + 0x1A2C7A0, "4C8BDC49895B0855565741544155415641574881EC80000000");
hooks.Add(NativeHook.Observe(module + 0x1A2C7A0, (nint)(delegate* unmanaged<nint, void>)&ObserveSound));
Check(module + 0x1568020, "48895C240848896C24104889742420574883EC60498B0041");
hooks.Add(NativeHook.Observe(module + 0x1568020, (nint)(delegate* unmanaged<nint, nint, nint, void>)&ObserveEntitySound));
Check(module + 0x10F77F0, "40534881ECA0000000488B05408479014833C44889842490");
hooks.Add(NativeHook.Observe(module + 0x10F77F0, (nint)(delegate* unmanaged<nint, nint, nint, nint, void>)&ObserveNativeSound));
callbackTable = (nint)NativeMemory.AllocZeroed(48);
var table = (nint*)callbackTable;
table[0] = (nint)(delegate* unmanaged<nint, void>)&CallbackDestroy;
table[1] = (nint)(delegate* unmanaged<nint, byte>)&CallbackValid;
table[2] = (nint)(delegate* unmanaged<nint, nint>)&CallbackTarget;
table[3] = (nint)(delegate* unmanaged<nint, nint>)&CallbackFunction;
table[4] = (nint)(delegate* unmanaged<nint, byte, Bootstrap.GameString*, void>)&LoginCompleted;
table[5] = (nint)(delegate* unmanaged<nint, nint, void>)&CallbackCopy;
Available = true;
log("Game test control: engine-thread adapter enabled for this launch.");
}
[UnmanagedCallersOnly] private static void ObserveSound(nint state)
{
try
{
Interlocked.Increment(ref soundCalls);
var arguments = *(nint*)(state + 0x10);
if (*(nint*)(state + 8) < arguments + 32 || *(int*)(arguments + 28) != 9) return;
var reference = *(nint*)(*(nint*)(arguments + 16) + 0x18);
var resource = reference == 0 ? 0 : *(nint*)reference;
if (resource == 0) return;
var type = ExperimentalAbilityRuntime.DescribeResource(*(nint*)(resource + 8));
if (type is null) return;
RecordSound(type, "lua");
}
catch { /* Observation never changes playback. */ }
}
[UnmanagedCallersOnly] private static void ObserveEntitySound(nint result, nint actor, nint reference)
{
try
{
var resource = reference == 0 || *(nint*)reference == 0 ? 0 : **(nint**)reference;
if (resource != 0 && ExperimentalAbilityRuntime.DescribeResource(*(nint*)(resource + 8)) is { } type)
RecordSound(type, "entity");
}
catch { /* Observation never changes playback. */ }
}
private static void RecordSound(string type, string source)
{
lock (SoundGate)
{
SoundEvents.Enqueue(new JsonObject { ["sequence"] = ++soundSequence, ["resource"] = type, ["source"] = source });
while (SoundEvents.Count > 256) SoundEvents.Dequeue();
}
}
[UnmanagedCallersOnly] private static void ObserveNativeSound(nint region, nint result, nint reference, nint actor)
{
try
{
var resource = reference == 0 || *(nint*)reference == 0 ? 0 : **(nint**)reference;
if (resource != 0 && ExperimentalAbilityRuntime.DescribeResource(*(nint*)(resource + 8)) is { } type)
RecordSound(type, "native");
}
catch { /* Observation never changes playback. */ }
}
internal static JsonObject SoundSnapshot()
{
lock (SoundGate) return new() { ["calls"] = Interlocked.Read(ref soundCalls),
["events"] = new JsonArray(SoundEvents.Select(e => (JsonNode)e.DeepClone()).ToArray()) };
}
private static void Check(nint address, string bytes)
{
var expected = Convert.FromHexString(bytes);
if (!new ReadOnlySpan<byte>((void*)address, expected.Length).SequenceEqual(expected))
throw new InvalidDataException("Game test ABI signature changed.");
}
public static Task<string> Dispatch(string operation, byte[] body, CancellationToken cancellation)
{
cancellation.ThrowIfCancellationRequested();
if (Pending.Count >= 16) throw new InvalidOperationException("Game command queue is full.");
var data = GameTestProtocol.Parse(operation, body);
var completion = new TaskCompletionSource<string>(TaskCreationOptions.RunContinuationsAsynchronously);
Pending.Enqueue(new(operation, data, cancellation, completion));
return completion.Task.WaitAsync(cancellation);
}
[UnmanagedCallersOnly] private static void Update(nint manager)
{
((delegate* unmanaged<nint, void>)update)(manager);
ExperimentalAbilityRuntime.UpdateHud();
ExperimentalAbilityRuntime.UpdateKing();
GameBranding.UpdateLoginUi(*(int*)(manager + 0x168) == 4);
if (Pending.IsEmpty) return;
if (tickThread == 0) tickThread = Environment.CurrentManagedThreadId;
if (tickThread != Environment.CurrentManagedThreadId) return;
if (!Pending.TryDequeue(out var request)) return;
try
{
request.Cancellation.ThrowIfCancellationRequested();
if (*(nint*)manager != image + 0x214BA70) throw new InvalidOperationException("Unexpected game profile manager.");
if (request.Operation == "POST lua")
{
request.Completion.TrySetResult(GameTestLua.Execute(request.Body).ToJsonString());
return;
}
if (request.Operation == "GET ability-state")
{
request.Completion.TrySetResult(GameTestLua.WithLocalSuit(ExperimentalAbilityRuntime.Snapshot).ToJsonString());
return;
}
if (request.Operation == "POST ability-input")
{
var slot = request.Body["slot"]!.GetValue<int>();
var pressed = request.Body["pressed"]!.GetValue<bool>();
var result = GameTestLua.WithLocalSuit(suit =>
{
if (request.Body["exclusive"] is { } exclusive)
{
exclusiveInputSuit = suit;
// A crashed test runner must never leave the user's controls disabled.
exclusiveInputUntil = exclusive.GetValue<bool>() ? Environment.TickCount64 + 10000 : 0;
}
injectingAbilityInput = true;
try
{
// Enter the normal game skill input handler, including passive/input scripts.
return new JsonObject { ["handled"] = ((delegate* unmanaged<nint, int, byte, byte>)(image + 0x144CF80))
(suit, 0x91 + slot, pressed ? (byte)1 : (byte)0) != 0 };
}
finally { injectingAbilityInput = false; }
});
request.Completion.TrySetResult(result.ToJsonString());
return;
}
if (request.Operation == "POST login") Login(manager, request.Body);
request.Completion.TrySetResult(new JsonObject
{
["profileState"] = *(int*)(manager + 0x168),
["profileCount"] = *(uint*)(manager + 0x238) / 8,
["loginResult"] = loginResult,
["thread"] = tickThread
}.ToJsonString());
}
catch (Exception ex) { request.Completion.TrySetException(ex); }
finally { request.Body.Clear(); }
}
private static void Login(nint manager, JsonObject body)
{
var state = *(int*)(manager + 0x168);
if (state is 1 or 4) throw new InvalidOperationException("The game is already logging in or logged in.");
var email = Bootstrap.GameString.Empty; var hash = Bootstrap.GameString.Empty;
var emailBytes = Encoding.UTF8.GetBytes(body["email"]!.GetValue<string>());
var hashBytes = Encoding.ASCII.GetBytes(body["passwordHash"]!.GetValue<string>());
Span<nint> callback = stackalloc nint[3]; callback.Clear(); callback[0] = callbackTable;
try
{
email.Assign(emailBytes);
hash.Assign(hashBytes);
loginResult = "pending";
fixed (nint* callbackPointer = callback)
((delegate* unmanaged<nint, Bootstrap.GameString*, Bootstrap.GameString*, nint*, byte, void>)login)
(manager, &email, &hash, callbackPointer, 1);
log("Game test control: native login requested.");
}
finally
{
email.ClearAndFree(); hash.ClearAndFree();
CryptographicOperations.ZeroMemory(emailBytes); CryptographicOperations.ZeroMemory(hashBytes);
}
}
[UnmanagedCallersOnly] private static void CallbackDestroy(nint self) => *(nint*)self = 0;
[UnmanagedCallersOnly] private static byte CallbackValid(nint self) => 1;
[UnmanagedCallersOnly] private static nint CallbackTarget(nint self) => 0;
[UnmanagedCallersOnly] private static nint CallbackFunction(nint self) => (nint)(delegate* unmanaged<nint, byte, Bootstrap.GameString*, void>)&LoginCompleted;
[UnmanagedCallersOnly] private static void CallbackCopy(nint source, nint destination) => new ReadOnlySpan<byte>((void*)source, 24).CopyTo(new Span<byte>((void*)destination, 24));
[UnmanagedCallersOnly] private static void LoginCompleted(nint self, byte success, Bootstrap.GameString* message)
{
loginResult = success != 0 ? "succeeded" : "failed";
// The game's message may contain account data; never include it in logs or status.
log("Game test control: native login " + loginResult + ".");
}
}