[libs] Update AMPR and PlayGo exports

This commit is contained in:
ParantezTech
2026-06-28 23:46:55 +03:00
parent 418d46beb5
commit 46b3a207c1
2 changed files with 31 additions and 24 deletions
+17 -16
View File
@@ -23,6 +23,8 @@ public static class AmprExports
private const uint KernelEventQueueRecordType = 2; private const uint KernelEventQueueRecordType = 2;
private const uint WriteAddressRecordType = 3; private const uint WriteAddressRecordType = 3;
private static readonly ConcurrentDictionary<ulong, CommandBufferState> _commandBuffers = new(); private static readonly ConcurrentDictionary<ulong, CommandBufferState> _commandBuffers = new();
private static readonly bool _traceAmpr =
string.Equals(Environment.GetEnvironmentVariable("SHARPEMU_LOG_AMPR"), "1", StringComparison.Ordinal);
private sealed class CommandBufferState private sealed class CommandBufferState
{ {
@@ -355,24 +357,26 @@ public static class AmprExports
var commandBuffer = ctx[CpuRegister.Rdi]; var commandBuffer = ctx[CpuRegister.Rdi];
var equeue = ctx[CpuRegister.Rsi]; var equeue = ctx[CpuRegister.Rsi];
var ident = ctx[CpuRegister.Rdx]; var ident = ctx[CpuRegister.Rdx];
var filter = ctx[CpuRegister.Rcx]; var completionToken = ctx[CpuRegister.Rcx];
var userData = ctx[CpuRegister.R8]; var userData = ctx[CpuRegister.R8];
var data = ctx[CpuRegister.R9];
if (commandBuffer == 0) if (commandBuffer == 0)
{ {
return (int)OrbisGen2Result.ORBIS_GEN2_ERROR_INVALID_ARGUMENT; return (int)OrbisGen2Result.ORBIS_GEN2_ERROR_INVALID_ARGUMENT;
} }
var extra = 0UL; if (!AppendKernelEventQueueRecord(
_ = ctx.TryReadUInt64(ctx[CpuRegister.Rsp] + sizeof(ulong), out extra); ctx,
commandBuffer,
if (!AppendKernelEventQueueRecord(ctx, commandBuffer, equeue, ident, filter, userData, data, extra)) equeue,
ident,
completionToken,
userData))
{ {
return (int)OrbisGen2Result.ORBIS_GEN2_ERROR_MEMORY_FAULT; return (int)OrbisGen2Result.ORBIS_GEN2_ERROR_MEMORY_FAULT;
} }
TraceAmpr(ctx, "write_equeue", commandBuffer, equeue, ident); TraceAmpr(ctx, "write_equeue", commandBuffer, ident, completionToken);
ctx[CpuRegister.Rax] = 0; ctx[CpuRegister.Rax] = 0;
return (int)OrbisGen2Result.ORBIS_GEN2_OK; return (int)OrbisGen2Result.ORBIS_GEN2_OK;
} }
@@ -659,20 +663,17 @@ public static class AmprExports
ulong commandBuffer, ulong commandBuffer,
ulong equeue, ulong equeue,
ulong ident, ulong ident,
ulong filter, ulong completionToken,
ulong userData, ulong userData)
ulong data,
ulong extra)
{ {
Span<byte> record = stackalloc byte[(int)KernelEventQueueRecordSize]; Span<byte> record = stackalloc byte[(int)KernelEventQueueRecordSize];
record.Clear(); record.Clear();
BinaryPrimitives.WriteUInt32LittleEndian(record[0x00..], KernelEventQueueRecordType); BinaryPrimitives.WriteUInt32LittleEndian(record[0x00..], KernelEventQueueRecordType);
BinaryPrimitives.WriteUInt32LittleEndian(record[0x04..], unchecked((uint)filter)); BinaryPrimitives.WriteInt16LittleEndian(record[0x04..], KernelEventQueueCompatExports.KernelEventFilterAmpr);
BinaryPrimitives.WriteUInt64LittleEndian(record[0x08..], equeue); BinaryPrimitives.WriteUInt64LittleEndian(record[0x08..], equeue);
BinaryPrimitives.WriteUInt64LittleEndian(record[0x10..], ident); BinaryPrimitives.WriteUInt64LittleEndian(record[0x10..], ident);
BinaryPrimitives.WriteUInt64LittleEndian(record[0x18..], userData); BinaryPrimitives.WriteUInt64LittleEndian(record[0x18..], userData);
BinaryPrimitives.WriteUInt64LittleEndian(record[0x20..], data); BinaryPrimitives.WriteUInt64LittleEndian(record[0x20..], completionToken);
BinaryPrimitives.WriteUInt64LittleEndian(record[0x28..], extra);
return AppendCommandBufferRecord(ctx, commandBuffer, record); return AppendCommandBufferRecord(ctx, commandBuffer, record);
} }
@@ -778,7 +779,7 @@ public static class AmprExports
private static void TraceAmpr(CpuContext ctx, string operation, ulong commandBuffer, ulong arg0, ulong arg1) private static void TraceAmpr(CpuContext ctx, string operation, ulong commandBuffer, ulong arg0, ulong arg1)
{ {
if (!string.Equals(Environment.GetEnvironmentVariable("SHARPEMU_LOG_AMPR"), "1", StringComparison.Ordinal)) if (!_traceAmpr)
{ {
return; return;
} }
@@ -800,7 +801,7 @@ public static class AmprExports
string? hostPath, string? hostPath,
int result) int result)
{ {
if (!string.Equals(Environment.GetEnvironmentVariable("SHARPEMU_LOG_AMPR"), "1", StringComparison.Ordinal)) if (!_traceAmpr)
{ {
return; return;
} }
+14 -8
View File
@@ -44,6 +44,7 @@ public static class PlayGoExports
private static PlayGoMetadata _metadata = PlayGoMetadata.Empty; private static PlayGoMetadata _metadata = PlayGoMetadata.Empty;
private static int _installSpeed = PlayGoInstallSpeedTrickle; private static int _installSpeed = PlayGoInstallSpeedTrickle;
private static ulong _languageMask = ulong.MaxValue; private static ulong _languageMask = ulong.MaxValue;
private static int _unknownChunkDiagnostics;
[SysAbiExport( [SysAbiExport(
Nid = "ts6GlZOKRrE", Nid = "ts6GlZOKRrE",
@@ -390,10 +391,18 @@ public static class PlayGoExports
if (!IsKnownChunkId(chunkId)) if (!IsKnownChunkId(chunkId))
{ {
loci[i] = PlayGoLocusNotDownloaded; if (Interlocked.Increment(ref _unknownChunkDiagnostics) <= 8)
return ctx.Memory.TryWrite(outLoci, loci) {
? OrbisPlayGoErrorBadChunkId ushort[] knownChunkIds;
: (int)OrbisGen2Result.ORBIS_GEN2_ERROR_MEMORY_FAULT; lock (_stateGate)
{
knownChunkIds = _metadata.ChunkIds;
}
Console.Error.WriteLine(
$"[LOADER][TRACE] playgo.unknown_chunk_id id={chunkId} entries={numberOfEntries} " +
$"known=[{string.Join(',', knownChunkIds)}]");
}
} }
loci[i] = PlayGoLocusLocalFast; loci[i] = PlayGoLocusLocalFast;
@@ -624,10 +633,7 @@ public static class PlayGoExports
return (int)OrbisGen2Result.ORBIS_GEN2_ERROR_MEMORY_FAULT; return (int)OrbisGen2Result.ORBIS_GEN2_ERROR_MEMORY_FAULT;
} }
if (!IsKnownChunkId(chunkId)) _ = chunkId;
{
return OrbisPlayGoErrorBadChunkId;
}
} }
return (int)OrbisGen2Result.ORBIS_GEN2_OK; return (int)OrbisGen2Result.ORBIS_GEN2_OK;