mirror of
https://github.com/par274/sharpemu.git
synced 2026-08-01 07:29:43 +08:00
Compare commits
10 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| c3019b78d6 | |||
| dd5e524879 | |||
| df9d0e6aaf | |||
| 253d0fae3f | |||
| 78d719ef9e | |||
| be3806cdf6 | |||
| dc47deee93 | |||
| 1c838cf8d6 | |||
| 2f269566a5 | |||
| 9d7afef6f6 |
Binary file not shown.
|
Before Width: | Height: | Size: 621 KiB |
Binary file not shown.
|
After Width: | Height: | Size: 225 KiB |
@@ -12,5 +12,6 @@ SPDX-License-Identifier: GPL-2.0-or-later
|
|||||||
<PackageVersion Include="Silk.NET.Vulkan" Version="2.23.0" />
|
<PackageVersion Include="Silk.NET.Vulkan" Version="2.23.0" />
|
||||||
<PackageVersion Include="Silk.NET.Vulkan.Extensions.KHR" Version="2.23.0" />
|
<PackageVersion Include="Silk.NET.Vulkan.Extensions.KHR" Version="2.23.0" />
|
||||||
<PackageVersion Include="Silk.NET.Windowing" Version="2.23.0" />
|
<PackageVersion Include="Silk.NET.Windowing" Version="2.23.0" />
|
||||||
|
<PackageVersion Include="Silk.NET.Shaderc" Version="2.23.0" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
</Project>
|
</Project>
|
||||||
|
|||||||
@@ -41,6 +41,11 @@
|
|||||||
"resolved": "2.23.0",
|
"resolved": "2.23.0",
|
||||||
"contentHash": "r8PdIVzME8EH0qAgbmRPO87I4GfgR2j8TofT7EMuRJDf1QluoQwnVypDoFJjQ2ZBSRsGYk5unYxxogI05Ogsmw=="
|
"contentHash": "r8PdIVzME8EH0qAgbmRPO87I4GfgR2j8TofT7EMuRJDf1QluoQwnVypDoFJjQ2ZBSRsGYk5unYxxogI05Ogsmw=="
|
||||||
},
|
},
|
||||||
|
"Silk.NET.Shaderc.Native": {
|
||||||
|
"type": "Transitive",
|
||||||
|
"resolved": "2.23.0",
|
||||||
|
"contentHash": "H6OMLIWdh2HITvkmj+ALs8LTIdQvQ2/JTtkDXinVbJ3xxrQIBXhVmc9jnuTQ67YDybGlENSMrgthzhLwK0rjnQ=="
|
||||||
|
},
|
||||||
"Silk.NET.Windowing.Common": {
|
"Silk.NET.Windowing.Common": {
|
||||||
"type": "Transitive",
|
"type": "Transitive",
|
||||||
"resolved": "2.23.0",
|
"resolved": "2.23.0",
|
||||||
@@ -80,6 +85,7 @@
|
|||||||
"type": "Project",
|
"type": "Project",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"SharpEmu.HLE": "[1.0.0, )",
|
"SharpEmu.HLE": "[1.0.0, )",
|
||||||
|
"Silk.NET.Shaderc": "[2.23.0, )",
|
||||||
"Silk.NET.Vulkan": "[2.23.0, )",
|
"Silk.NET.Vulkan": "[2.23.0, )",
|
||||||
"Silk.NET.Vulkan.Extensions.KHR": "[2.23.0, )",
|
"Silk.NET.Vulkan.Extensions.KHR": "[2.23.0, )",
|
||||||
"Silk.NET.Windowing": "[2.23.0, )"
|
"Silk.NET.Windowing": "[2.23.0, )"
|
||||||
@@ -94,6 +100,16 @@
|
|||||||
"resolved": "1.21.0",
|
"resolved": "1.21.0",
|
||||||
"contentHash": "dv5+81Q1TBQvVMSOOOmRcjJmvWcX3BZPZsIq31+RLc5cNft0IHAyNlkdb7ZarOWG913PyBoFDsDXoCIlKmLclg=="
|
"contentHash": "dv5+81Q1TBQvVMSOOOmRcjJmvWcX3BZPZsIq31+RLc5cNft0IHAyNlkdb7ZarOWG913PyBoFDsDXoCIlKmLclg=="
|
||||||
},
|
},
|
||||||
|
"Silk.NET.Shaderc": {
|
||||||
|
"type": "CentralTransitive",
|
||||||
|
"requested": "[2.23.0, )",
|
||||||
|
"resolved": "2.23.0",
|
||||||
|
"contentHash": "+pXfOhmSCeeMECOo9HMi3C63LVbQ7FBxPFgxPKOT6mXD8Gg/90Wt4fLX4LqUuVbGid5LW6BXAUu1g17XQoawdA==",
|
||||||
|
"dependencies": {
|
||||||
|
"Silk.NET.Core": "2.23.0",
|
||||||
|
"Silk.NET.Shaderc.Native": "2.23.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
"Silk.NET.Vulkan": {
|
"Silk.NET.Vulkan": {
|
||||||
"type": "CentralTransitive",
|
"type": "CentralTransitive",
|
||||||
"requested": "[2.23.0, )",
|
"requested": "[2.23.0, )",
|
||||||
@@ -125,6 +141,11 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"net10.0/linux-x64": {
|
"net10.0/linux-x64": {
|
||||||
|
"Silk.NET.Shaderc.Native": {
|
||||||
|
"type": "Transitive",
|
||||||
|
"resolved": "2.23.0",
|
||||||
|
"contentHash": "H6OMLIWdh2HITvkmj+ALs8LTIdQvQ2/JTtkDXinVbJ3xxrQIBXhVmc9jnuTQ67YDybGlENSMrgthzhLwK0rjnQ=="
|
||||||
|
},
|
||||||
"Ultz.Native.GLFW": {
|
"Ultz.Native.GLFW": {
|
||||||
"type": "Transitive",
|
"type": "Transitive",
|
||||||
"resolved": "3.4.0",
|
"resolved": "3.4.0",
|
||||||
@@ -132,6 +153,11 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"net10.0/osx-arm64": {
|
"net10.0/osx-arm64": {
|
||||||
|
"Silk.NET.Shaderc.Native": {
|
||||||
|
"type": "Transitive",
|
||||||
|
"resolved": "2.23.0",
|
||||||
|
"contentHash": "H6OMLIWdh2HITvkmj+ALs8LTIdQvQ2/JTtkDXinVbJ3xxrQIBXhVmc9jnuTQ67YDybGlENSMrgthzhLwK0rjnQ=="
|
||||||
|
},
|
||||||
"Ultz.Native.GLFW": {
|
"Ultz.Native.GLFW": {
|
||||||
"type": "Transitive",
|
"type": "Transitive",
|
||||||
"resolved": "3.4.0",
|
"resolved": "3.4.0",
|
||||||
@@ -139,6 +165,11 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"net10.0/win-x64": {
|
"net10.0/win-x64": {
|
||||||
|
"Silk.NET.Shaderc.Native": {
|
||||||
|
"type": "Transitive",
|
||||||
|
"resolved": "2.23.0",
|
||||||
|
"contentHash": "H6OMLIWdh2HITvkmj+ALs8LTIdQvQ2/JTtkDXinVbJ3xxrQIBXhVmc9jnuTQ67YDybGlENSMrgthzhLwK0rjnQ=="
|
||||||
|
},
|
||||||
"Ultz.Native.GLFW": {
|
"Ultz.Native.GLFW": {
|
||||||
"type": "Transitive",
|
"type": "Transitive",
|
||||||
"resolved": "3.4.0",
|
"resolved": "3.4.0",
|
||||||
|
|||||||
@@ -482,6 +482,8 @@ public sealed partial class DirectExecutionBackend
|
|||||||
catch (Exception ex)
|
catch (Exception ex)
|
||||||
{
|
{
|
||||||
LastError = $"HLE dispatch error for {importStubEntry.Nid}: {ex.GetType().Name}: {ex.Message}";
|
LastError = $"HLE dispatch error for {importStubEntry.Nid}: {ex.GetType().Name}: {ex.Message}";
|
||||||
|
Console.Error.WriteLine($"[LOADER][ERROR] {LastError}");
|
||||||
|
Console.Error.WriteLine($"[LOADER][ERROR] {ex.StackTrace}");
|
||||||
cpuContext[CpuRegister.Rax] = 18446744071562199298uL;
|
cpuContext[CpuRegister.Rax] = 18446744071562199298uL;
|
||||||
return 18446744071562199298uL;
|
return 18446744071562199298uL;
|
||||||
}
|
}
|
||||||
@@ -533,12 +535,8 @@ public sealed partial class DirectExecutionBackend
|
|||||||
$"ret=0x{returnRip:X16}");
|
$"ret=0x{returnRip:X16}");
|
||||||
}
|
}
|
||||||
|
|
||||||
var previousImportCallFrame = GuestThreadExecution.EnterImportCallFrame(
|
|
||||||
returnRip,
|
|
||||||
(ulong)argPackPtr + 104uL,
|
|
||||||
ActiveGuestReturnSlotAddress);
|
|
||||||
int returnValue;
|
int returnValue;
|
||||||
try
|
if (IsNoBlockLeafImport(importStubEntry.Nid))
|
||||||
{
|
{
|
||||||
cpuContext.ClearRaxWriteFlag();
|
cpuContext.ClearRaxWriteFlag();
|
||||||
returnValue = export.Function(cpuContext);
|
returnValue = export.Function(cpuContext);
|
||||||
@@ -547,9 +545,25 @@ public sealed partial class DirectExecutionBackend
|
|||||||
cpuContext[CpuRegister.Rax] = unchecked((ulong)returnValue);
|
cpuContext[CpuRegister.Rax] = unchecked((ulong)returnValue);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
finally
|
else
|
||||||
{
|
{
|
||||||
GuestThreadExecution.RestoreImportCallFrame(previousImportCallFrame);
|
var previousImportCallFrame = GuestThreadExecution.EnterImportCallFrame(
|
||||||
|
returnRip,
|
||||||
|
(ulong)argPackPtr + 104uL,
|
||||||
|
ActiveGuestReturnSlotAddress);
|
||||||
|
try
|
||||||
|
{
|
||||||
|
cpuContext.ClearRaxWriteFlag();
|
||||||
|
returnValue = export.Function(cpuContext);
|
||||||
|
if (!cpuContext.WasRaxWritten)
|
||||||
|
{
|
||||||
|
cpuContext[CpuRegister.Rax] = unchecked((ulong)returnValue);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
GuestThreadExecution.RestoreImportCallFrame(previousImportCallFrame);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (returnValue != (int)OrbisGen2Result.ORBIS_GEN2_OK)
|
if (returnValue != (int)OrbisGen2Result.ORBIS_GEN2_OK)
|
||||||
@@ -594,6 +608,28 @@ public sealed partial class DirectExecutionBackend
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static bool IsNoBlockLeafImport(string nid) =>
|
||||||
|
nid is
|
||||||
|
"8aI7R7WaOlc" or // sceAmprCommandBufferConstructor
|
||||||
|
"a8uLzYY--tM" or // sceAmprAprCommandBufferConstructor
|
||||||
|
"Qs1xtplKo0U" or // sceAmprAprCommandBufferDestructor
|
||||||
|
"GuchCTefuZw" or // sceAmprCommandBufferDestructor
|
||||||
|
"N-FSPA4S3nI" or // sceAmprCommandBufferSetBuffer
|
||||||
|
"baQO9ez2gL4" or // sceAmprCommandBufferReset
|
||||||
|
"ULvXMDz56po" or // sceAmprCommandBufferClearBuffer
|
||||||
|
"mQ16-QdKv7k" or // sceAmprAprCommandBufferReadFile
|
||||||
|
"vWU-odnS+fU" or // sceAmprMeasureCommandSizeReadFile
|
||||||
|
"sSAUCCU1dv4" or // sceAmprMeasureCommandSizeWriteKernelEventQueue_04_00
|
||||||
|
"C+IEj+BsAFM" or // sceAmprMeasureCommandSizeWriteAddressOnCompletion
|
||||||
|
"tZDDEo2tE5k" or // sceAmprCommandBufferGetSize
|
||||||
|
"GnxKOHEawhk" or // sceAmprCommandBufferGetCurrentOffset
|
||||||
|
"H896Pt-yB4I" or // sceAmprCommandBufferWriteKernelEventQueue_04_00
|
||||||
|
"sJXyWHjP-F8" or // sceAmprCommandBufferWriteAddressOnCompletion
|
||||||
|
"ASoW5WE-UPo" or // sceKernelAprSubmitCommandBufferAndGetResult
|
||||||
|
"rqwFKI4PAiM" or // sceKernelAprWaitCommandBuffer
|
||||||
|
"eE4Szl8sil8" or // sceKernelAprSubmitCommandBuffer
|
||||||
|
"qvMUCyyaCSI"; // sceKernelAprSubmitCommandBufferAndGetId
|
||||||
|
|
||||||
private bool ShouldLogImportResult(string nid, OrbisGen2Result result)
|
private bool ShouldLogImportResult(string nid, OrbisGen2Result result)
|
||||||
{
|
{
|
||||||
var expectedFileProbeMiss =
|
var expectedFileProbeMiss =
|
||||||
@@ -602,7 +638,10 @@ public sealed partial class DirectExecutionBackend
|
|||||||
var expectedTimedWaitTimeout =
|
var expectedTimedWaitTimeout =
|
||||||
string.Equals(nid, "27bAgiJmOh0", StringComparison.Ordinal) &&
|
string.Equals(nid, "27bAgiJmOh0", StringComparison.Ordinal) &&
|
||||||
unchecked((int)result) == 60;
|
unchecked((int)result) == 60;
|
||||||
if (!expectedFileProbeMiss && !expectedTimedWaitTimeout)
|
var expectedMutexTrylockBusy =
|
||||||
|
string.Equals(nid, "K-jXhbt2gn4", StringComparison.Ordinal) &&
|
||||||
|
result == OrbisGen2Result.ORBIS_GEN2_ERROR_BUSY;
|
||||||
|
if (!expectedFileProbeMiss && !expectedTimedWaitTimeout && !expectedMutexTrylockBusy)
|
||||||
{
|
{
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -639,6 +678,30 @@ public sealed partial class DirectExecutionBackend
|
|||||||
"2Z+PpY6CaJg" or
|
"2Z+PpY6CaJg" or
|
||||||
"8aI7R7WaOlc" or
|
"8aI7R7WaOlc" or
|
||||||
"zgXifHT9ErY" or // sceVideoOutIsFlipPending
|
"zgXifHT9ErY" or // sceVideoOutIsFlipPending
|
||||||
|
"V++UgBtQhn0" or // sceAgcGetDataPacketPayloadAddress
|
||||||
|
"qj7QZpgr9Uw" or // Gen5 graphics type-2 packet
|
||||||
|
"LtTouSCZjHM" or // sceAgcCbNop
|
||||||
|
"k3GhuSNmBLU" or // sceAgcCbDispatch
|
||||||
|
"UZbQjYAwwXM" or // sceAgcCbSetShRegistersDirect
|
||||||
|
"JrtiDtKeS38" or // sceAgcAcbResetQueue
|
||||||
|
"cFazmnXpJOE" or // sceAgcAcbEventWrite
|
||||||
|
"KT-hTp-Ch14" or // sceAgcAcbAcquireMem
|
||||||
|
"htn36gPnBk4" or // sceAgcAcbWaitRegMem
|
||||||
|
"eZ4+17OQz4Q" or // sceAgcAcbWriteData
|
||||||
|
"j3EtxFkSIhQ" or // sceAgcAcbDispatchIndirect
|
||||||
|
"gSRnr79F8tQ" or // sceAgcDriverSubmitAcb
|
||||||
|
"i1jyy49AjXU" or // sceAgcDcbWriteData
|
||||||
|
"VmW0Tdpy420" or // sceAgcDcbWaitRegMem
|
||||||
|
"WmAc2MEj6Io" or // sceAgcDcbDmaData
|
||||||
|
"rUuVjyR+Rd4" or // sceAgcDcbGetLodStatsGetSize
|
||||||
|
"vuSXe69VILM" or // sceAgcDcbGetLodStats
|
||||||
|
"RmaJwLtc8rY" or // sceAgcDcbSetBaseIndirectArgs
|
||||||
|
"CtB+A9-VxO0" or // sceAgcDcbDispatchIndirect
|
||||||
|
"+kSrjIVxKFE" or // sceAgcDcbPushMarker
|
||||||
|
"H7uZqCoNuWk" or // sceAgcDcbPopMarker
|
||||||
|
"IxYiarKlXxM" or // sceAgcDmaDataPatchSetDstAddressOrOffset
|
||||||
|
"3KDcnM3lrcU" or // sceAgcWaitRegMemPatchAddress
|
||||||
|
"0fWWK5uG9rQ" or // sceAgcQueueEndOfPipeActionPatchAddress
|
||||||
"a8uLzYY--tM" or
|
"a8uLzYY--tM" or
|
||||||
"Qs1xtplKo0U" or
|
"Qs1xtplKo0U" or
|
||||||
"GuchCTefuZw" or
|
"GuchCTefuZw" or
|
||||||
@@ -660,7 +723,11 @@ public sealed partial class DirectExecutionBackend
|
|||||||
"Vo5V8KAwCmk" or // sceSystemServiceHideSplashScreen
|
"Vo5V8KAwCmk" or // sceSystemServiceHideSplashScreen
|
||||||
"TywrFKCoLGY" or // sceSaveDataInitialize3
|
"TywrFKCoLGY" or // sceSaveDataInitialize3
|
||||||
"dyIhnXq-0SM" or // sceSaveDataDirNameSearch
|
"dyIhnXq-0SM" or // sceSaveDataDirNameSearch
|
||||||
|
"ERKzksauAJA" or // sceSaveDataDialogGetStatus
|
||||||
|
"KK3Bdg1RWK0" or // sceSaveDataDialogUpdateStatus
|
||||||
|
"en7gNVnh878" or // sceSaveDataDialogIsReadyToDisplay
|
||||||
"jO8DM8oyego" or // sceNpEntitlementAccessInitialize
|
"jO8DM8oyego" or // sceNpEntitlementAccessInitialize
|
||||||
|
"TFyU+KFBv54" or // sceNpEntitlementAccessGetAddcontEntitlementInfoList
|
||||||
"27bAgiJmOh0" or // pthread_cond_timedwait
|
"27bAgiJmOh0" or // pthread_cond_timedwait
|
||||||
"iQw3iQPhvUQ" or // sceNetCtlCheckCallback
|
"iQw3iQPhvUQ" or // sceNetCtlCheckCallback
|
||||||
"Q2V+iqvjgC0" or // vsnprintf
|
"Q2V+iqvjgC0" or // vsnprintf
|
||||||
|
|||||||
@@ -41,6 +41,11 @@
|
|||||||
"resolved": "2.23.0",
|
"resolved": "2.23.0",
|
||||||
"contentHash": "r8PdIVzME8EH0qAgbmRPO87I4GfgR2j8TofT7EMuRJDf1QluoQwnVypDoFJjQ2ZBSRsGYk5unYxxogI05Ogsmw=="
|
"contentHash": "r8PdIVzME8EH0qAgbmRPO87I4GfgR2j8TofT7EMuRJDf1QluoQwnVypDoFJjQ2ZBSRsGYk5unYxxogI05Ogsmw=="
|
||||||
},
|
},
|
||||||
|
"Silk.NET.Shaderc.Native": {
|
||||||
|
"type": "Transitive",
|
||||||
|
"resolved": "2.23.0",
|
||||||
|
"contentHash": "H6OMLIWdh2HITvkmj+ALs8LTIdQvQ2/JTtkDXinVbJ3xxrQIBXhVmc9jnuTQ67YDybGlENSMrgthzhLwK0rjnQ=="
|
||||||
|
},
|
||||||
"Silk.NET.Windowing.Common": {
|
"Silk.NET.Windowing.Common": {
|
||||||
"type": "Transitive",
|
"type": "Transitive",
|
||||||
"resolved": "2.23.0",
|
"resolved": "2.23.0",
|
||||||
@@ -71,6 +76,7 @@
|
|||||||
"type": "Project",
|
"type": "Project",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"SharpEmu.HLE": "[1.0.0, )",
|
"SharpEmu.HLE": "[1.0.0, )",
|
||||||
|
"Silk.NET.Shaderc": "[2.23.0, )",
|
||||||
"Silk.NET.Vulkan": "[2.23.0, )",
|
"Silk.NET.Vulkan": "[2.23.0, )",
|
||||||
"Silk.NET.Vulkan.Extensions.KHR": "[2.23.0, )",
|
"Silk.NET.Vulkan.Extensions.KHR": "[2.23.0, )",
|
||||||
"Silk.NET.Windowing": "[2.23.0, )"
|
"Silk.NET.Windowing": "[2.23.0, )"
|
||||||
@@ -79,6 +85,16 @@
|
|||||||
"sharpemu.logging": {
|
"sharpemu.logging": {
|
||||||
"type": "Project"
|
"type": "Project"
|
||||||
},
|
},
|
||||||
|
"Silk.NET.Shaderc": {
|
||||||
|
"type": "CentralTransitive",
|
||||||
|
"requested": "[2.23.0, )",
|
||||||
|
"resolved": "2.23.0",
|
||||||
|
"contentHash": "+pXfOhmSCeeMECOo9HMi3C63LVbQ7FBxPFgxPKOT6mXD8Gg/90Wt4fLX4LqUuVbGid5LW6BXAUu1g17XQoawdA==",
|
||||||
|
"dependencies": {
|
||||||
|
"Silk.NET.Core": "2.23.0",
|
||||||
|
"Silk.NET.Shaderc.Native": "2.23.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
"Silk.NET.Vulkan": {
|
"Silk.NET.Vulkan": {
|
||||||
"type": "CentralTransitive",
|
"type": "CentralTransitive",
|
||||||
"requested": "[2.23.0, )",
|
"requested": "[2.23.0, )",
|
||||||
|
|||||||
+1242
-42
File diff suppressed because it is too large
Load Diff
@@ -3,6 +3,7 @@
|
|||||||
|
|
||||||
using SharpEmu.HLE;
|
using SharpEmu.HLE;
|
||||||
using SharpEmu.Libs.Kernel;
|
using SharpEmu.Libs.Kernel;
|
||||||
|
using System.Buffers;
|
||||||
using System.Buffers.Binary;
|
using System.Buffers.Binary;
|
||||||
using System.Collections.Concurrent;
|
using System.Collections.Concurrent;
|
||||||
|
|
||||||
@@ -25,6 +26,9 @@ public static class AmprExports
|
|||||||
private static readonly ConcurrentDictionary<ulong, CommandBufferState> _commandBuffers = new();
|
private static readonly ConcurrentDictionary<ulong, CommandBufferState> _commandBuffers = new();
|
||||||
private static readonly bool _traceAmpr =
|
private static readonly bool _traceAmpr =
|
||||||
string.Equals(Environment.GetEnvironmentVariable("SHARPEMU_LOG_AMPR"), "1", StringComparison.Ordinal);
|
string.Equals(Environment.GetEnvironmentVariable("SHARPEMU_LOG_AMPR"), "1", StringComparison.Ordinal);
|
||||||
|
private static readonly bool _traceAmprReads =
|
||||||
|
_traceAmpr ||
|
||||||
|
string.Equals(Environment.GetEnvironmentVariable("SHARPEMU_LOG_AMPR_READS"), "1", StringComparison.Ordinal);
|
||||||
|
|
||||||
private sealed class CommandBufferState
|
private sealed class CommandBufferState
|
||||||
{
|
{
|
||||||
@@ -625,12 +629,18 @@ public static class AmprExports
|
|||||||
return (int)OrbisGen2Result.ORBIS_GEN2_ERROR_INVALID_ARGUMENT;
|
return (int)OrbisGen2Result.ORBIS_GEN2_ERROR_INVALID_ARGUMENT;
|
||||||
}
|
}
|
||||||
|
|
||||||
const int ChunkSize = 64 * 1024;
|
const int ChunkSize = 1024 * 1024;
|
||||||
var buffer = new byte[(int)Math.Min((ulong)ChunkSize, size)];
|
var buffer = ArrayPool<byte>.Shared.Rent((int)Math.Min((ulong)ChunkSize, size));
|
||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
using var stream = new FileStream(hostPath, FileMode.Open, FileAccess.Read, FileShare.ReadWrite | FileShare.Delete);
|
using var stream = new FileStream(
|
||||||
|
hostPath,
|
||||||
|
FileMode.Open,
|
||||||
|
FileAccess.Read,
|
||||||
|
FileShare.ReadWrite | FileShare.Delete,
|
||||||
|
ChunkSize,
|
||||||
|
FileOptions.SequentialScan);
|
||||||
if (fileOffset >= (ulong)stream.Length)
|
if (fileOffset >= (ulong)stream.Length)
|
||||||
{
|
{
|
||||||
return (int)OrbisGen2Result.ORBIS_GEN2_OK;
|
return (int)OrbisGen2Result.ORBIS_GEN2_OK;
|
||||||
@@ -663,6 +673,10 @@ public static class AmprExports
|
|||||||
{
|
{
|
||||||
return (int)OrbisGen2Result.ORBIS_GEN2_ERROR_NOT_FOUND;
|
return (int)OrbisGen2Result.ORBIS_GEN2_ERROR_NOT_FOUND;
|
||||||
}
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
ArrayPool<byte>.Shared.Return(buffer);
|
||||||
|
}
|
||||||
|
|
||||||
return (int)OrbisGen2Result.ORBIS_GEN2_OK;
|
return (int)OrbisGen2Result.ORBIS_GEN2_OK;
|
||||||
}
|
}
|
||||||
@@ -831,7 +845,7 @@ public static class AmprExports
|
|||||||
string? hostPath,
|
string? hostPath,
|
||||||
int result)
|
int result)
|
||||||
{
|
{
|
||||||
if (!_traceAmpr)
|
if (!_traceAmprReads)
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -11,7 +11,6 @@ namespace SharpEmu.Libs.Kernel;
|
|||||||
|
|
||||||
public static class KernelPthreadCompatExports
|
public static class KernelPthreadCompatExports
|
||||||
{
|
{
|
||||||
private const int MutexTypeDefault = 0;
|
|
||||||
private const int MutexTypeErrorCheck = 1;
|
private const int MutexTypeErrorCheck = 1;
|
||||||
private const int MutexTypeRecursive = 2;
|
private const int MutexTypeRecursive = 2;
|
||||||
private const int MutexTypeNormal = 3;
|
private const int MutexTypeNormal = 3;
|
||||||
@@ -44,7 +43,7 @@ public static class KernelPthreadCompatExports
|
|||||||
public SemaphoreSlim Semaphore { get; } = new(1, 1);
|
public SemaphoreSlim Semaphore { get; } = new(1, 1);
|
||||||
public ulong OwnerThreadId { get; set; }
|
public ulong OwnerThreadId { get; set; }
|
||||||
public int RecursionCount { get; set; }
|
public int RecursionCount { get; set; }
|
||||||
public int Type { get; set; } = MutexTypeDefault;
|
public int Type { get; set; } = MutexTypeErrorCheck;
|
||||||
public int Protocol { get; set; }
|
public int Protocol { get; set; }
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -541,7 +540,7 @@ public static class KernelPthreadCompatExports
|
|||||||
return (int)OrbisGen2Result.ORBIS_GEN2_OK;
|
return (int)OrbisGen2Result.ORBIS_GEN2_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (state.Type is MutexTypeDefault or MutexTypeNormal or MutexTypeAdaptiveNp)
|
if (state.Type is MutexTypeNormal or MutexTypeAdaptiveNp)
|
||||||
{
|
{
|
||||||
if (tryOnly)
|
if (tryOnly)
|
||||||
{
|
{
|
||||||
@@ -676,7 +675,7 @@ public static class KernelPthreadCompatExports
|
|||||||
return (int)OrbisGen2Result.ORBIS_GEN2_ERROR_MEMORY_FAULT;
|
return (int)OrbisGen2Result.ORBIS_GEN2_ERROR_MEMORY_FAULT;
|
||||||
}
|
}
|
||||||
|
|
||||||
var initialState = new PthreadMutexAttrState(MutexTypeDefault, 0);
|
var initialState = new PthreadMutexAttrState(MutexTypeErrorCheck, 0);
|
||||||
if (!WriteMutexAttrObject(ctx, handle, initialState))
|
if (!WriteMutexAttrObject(ctx, handle, initialState))
|
||||||
{
|
{
|
||||||
return (int)OrbisGen2Result.ORBIS_GEN2_ERROR_MEMORY_FAULT;
|
return (int)OrbisGen2Result.ORBIS_GEN2_ERROR_MEMORY_FAULT;
|
||||||
@@ -735,7 +734,7 @@ public static class KernelPthreadCompatExports
|
|||||||
{
|
{
|
||||||
if (!_mutexAttrStates.TryGetValue(resolvedAddress, out var state))
|
if (!_mutexAttrStates.TryGetValue(resolvedAddress, out var state))
|
||||||
{
|
{
|
||||||
state = new PthreadMutexAttrState(MutexTypeDefault, 0);
|
state = new PthreadMutexAttrState(MutexTypeErrorCheck, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
updatedState = state with { Type = NormalizeMutexType(type) };
|
updatedState = state with { Type = NormalizeMutexType(type) };
|
||||||
@@ -764,7 +763,7 @@ public static class KernelPthreadCompatExports
|
|||||||
{
|
{
|
||||||
if (!_mutexAttrStates.TryGetValue(resolvedAddress, out var state))
|
if (!_mutexAttrStates.TryGetValue(resolvedAddress, out var state))
|
||||||
{
|
{
|
||||||
state = new PthreadMutexAttrState(MutexTypeDefault, 0);
|
state = new PthreadMutexAttrState(MutexTypeErrorCheck, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
updatedState = state with { Protocol = protocol };
|
updatedState = state with { Protocol = protocol };
|
||||||
@@ -847,7 +846,7 @@ public static class KernelPthreadCompatExports
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
return CreateImplicitMutexState(ctx, mutexAddress, MutexTypeDefault, out resolvedAddress, out state);
|
return CreateImplicitMutexState(ctx, mutexAddress, MutexTypeErrorCheck, out resolvedAddress, out state);
|
||||||
}
|
}
|
||||||
|
|
||||||
private static ulong ResolveMutexAttrHandle(CpuContext ctx, ulong attrAddress)
|
private static ulong ResolveMutexAttrHandle(CpuContext ctx, ulong attrAddress)
|
||||||
@@ -891,7 +890,7 @@ public static class KernelPthreadCompatExports
|
|||||||
{
|
{
|
||||||
return _mutexAttrStates.TryGetValue(resolvedAddress, out var state)
|
return _mutexAttrStates.TryGetValue(resolvedAddress, out var state)
|
||||||
? state
|
? state
|
||||||
: new PthreadMutexAttrState(MutexTypeDefault, 0);
|
: new PthreadMutexAttrState(MutexTypeErrorCheck, 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1293,12 +1292,12 @@ public static class KernelPthreadCompatExports
|
|||||||
{
|
{
|
||||||
return type switch
|
return type switch
|
||||||
{
|
{
|
||||||
0 => MutexTypeDefault,
|
0 => MutexTypeErrorCheck,
|
||||||
1 => MutexTypeErrorCheck,
|
1 => MutexTypeErrorCheck,
|
||||||
2 => MutexTypeRecursive,
|
2 => MutexTypeRecursive,
|
||||||
3 => MutexTypeNormal,
|
3 => MutexTypeNormal,
|
||||||
4 => MutexTypeAdaptiveNp,
|
4 => MutexTypeAdaptiveNp,
|
||||||
_ => MutexTypeDefault,
|
_ => MutexTypeErrorCheck,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -8,6 +8,7 @@ namespace SharpEmu.Libs.Np;
|
|||||||
public static class NpEntitlementAccessExports
|
public static class NpEntitlementAccessExports
|
||||||
{
|
{
|
||||||
private const int BootParamClearSize = 0x20;
|
private const int BootParamClearSize = 0x20;
|
||||||
|
private const int EmptyAddcontInfoListSize = 0x10;
|
||||||
|
|
||||||
[SysAbiExport(
|
[SysAbiExport(
|
||||||
Nid = "jO8DM8oyego",
|
Nid = "jO8DM8oyego",
|
||||||
@@ -33,6 +34,30 @@ public static class NpEntitlementAccessExports
|
|||||||
return SetReturn(ctx, OrbisGen2Result.ORBIS_GEN2_OK);
|
return SetReturn(ctx, OrbisGen2Result.ORBIS_GEN2_OK);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
[SysAbiExport(
|
||||||
|
Nid = "TFyU+KFBv54",
|
||||||
|
ExportName = "sceNpEntitlementAccessGetAddcontEntitlementInfoList",
|
||||||
|
Target = Generation.Gen4 | Generation.Gen5,
|
||||||
|
LibraryName = "libSceNpEntitlementAccess")]
|
||||||
|
public static int NpEntitlementAccessGetAddcontEntitlementInfoList(CpuContext ctx)
|
||||||
|
{
|
||||||
|
var listAddress = ctx[CpuRegister.Rsi];
|
||||||
|
if (listAddress != 0)
|
||||||
|
{
|
||||||
|
Span<byte> emptyList = stackalloc byte[EmptyAddcontInfoListSize];
|
||||||
|
emptyList.Clear();
|
||||||
|
if (!ctx.Memory.TryWrite(listAddress, emptyList))
|
||||||
|
{
|
||||||
|
return SetReturn(ctx, OrbisGen2Result.ORBIS_GEN2_ERROR_MEMORY_FAULT);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
TraceNpEntitlementAccess(
|
||||||
|
$"get_addcont_info_list service=0x{ctx[CpuRegister.Rdi]:X16} list=0x{listAddress:X16} " +
|
||||||
|
$"max={ctx[CpuRegister.Rdx]} flags=0x{ctx[CpuRegister.Rcx]:X16} -> empty");
|
||||||
|
return SetReturn(ctx, OrbisGen2Result.ORBIS_GEN2_OK);
|
||||||
|
}
|
||||||
|
|
||||||
private static int SetReturn(CpuContext ctx, OrbisGen2Result result)
|
private static int SetReturn(CpuContext ctx, OrbisGen2Result result)
|
||||||
{
|
{
|
||||||
ctx[CpuRegister.Rax] = unchecked((ulong)(int)result);
|
ctx[CpuRegister.Rax] = unchecked((ulong)(int)result);
|
||||||
|
|||||||
@@ -0,0 +1,213 @@
|
|||||||
|
// Copyright (C) 2026 SharpEmu Emulator Project
|
||||||
|
// SPDX-License-Identifier: GPL-2.0-or-later
|
||||||
|
|
||||||
|
using SharpEmu.HLE;
|
||||||
|
using System.Buffers.Binary;
|
||||||
|
using System.Threading;
|
||||||
|
|
||||||
|
namespace SharpEmu.Libs.SaveData;
|
||||||
|
|
||||||
|
public static class SaveDataDialogExports
|
||||||
|
{
|
||||||
|
private const int StatusNone = 0;
|
||||||
|
private const int StatusInitialized = 1;
|
||||||
|
private const int StatusRunning = 2;
|
||||||
|
private const int StatusFinished = 3;
|
||||||
|
|
||||||
|
private const int ErrorOk = 0;
|
||||||
|
private const int ErrorNotInitialized = unchecked((int)0x80B80003);
|
||||||
|
private const int ErrorAlreadyInitialized = unchecked((int)0x80B80004);
|
||||||
|
private const int ErrorNotFinished = unchecked((int)0x80B80005);
|
||||||
|
private const int ErrorNotRunning = unchecked((int)0x80B8000B);
|
||||||
|
private const int ErrorArgNull = unchecked((int)0x80B8000D);
|
||||||
|
|
||||||
|
private const int ResultSize = 0x48;
|
||||||
|
private static int _status;
|
||||||
|
private static int _lastMode;
|
||||||
|
private static ulong _lastUserData;
|
||||||
|
|
||||||
|
[SysAbiExport(
|
||||||
|
Nid = "s9e3+YpRnzw",
|
||||||
|
ExportName = "sceSaveDataDialogInitialize",
|
||||||
|
Target = Generation.Gen4 | Generation.Gen5,
|
||||||
|
LibraryName = "libSceSaveDataDialog")]
|
||||||
|
public static int SaveDataDialogInitialize(CpuContext ctx)
|
||||||
|
{
|
||||||
|
if (Interlocked.CompareExchange(ref _status, StatusInitialized, StatusNone) != StatusNone)
|
||||||
|
{
|
||||||
|
return SetReturn(ctx, ErrorAlreadyInitialized);
|
||||||
|
}
|
||||||
|
|
||||||
|
return SetReturn(ctx, ErrorOk);
|
||||||
|
}
|
||||||
|
|
||||||
|
[SysAbiExport(
|
||||||
|
Nid = "4tPhsP6FpDI",
|
||||||
|
ExportName = "sceSaveDataDialogOpen",
|
||||||
|
Target = Generation.Gen4 | Generation.Gen5,
|
||||||
|
LibraryName = "libSceSaveDataDialog")]
|
||||||
|
public static int SaveDataDialogOpen(CpuContext ctx)
|
||||||
|
{
|
||||||
|
var paramAddress = ctx[CpuRegister.Rdi];
|
||||||
|
if (paramAddress == 0)
|
||||||
|
{
|
||||||
|
return SetReturn(ctx, ErrorArgNull);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (_status is not (StatusInitialized or StatusFinished))
|
||||||
|
{
|
||||||
|
return SetReturn(ctx, ErrorNotInitialized);
|
||||||
|
}
|
||||||
|
|
||||||
|
_lastMode = TryReadInt32(ctx, paramAddress, out var mode) ? mode : 0;
|
||||||
|
_lastUserData = TryReadUInt64(ctx, paramAddress + 0xC8, out var userData) ? userData : 0;
|
||||||
|
|
||||||
|
// There is no host save dialog yet. Complete immediately with OK so
|
||||||
|
// guest polling sees a finished dialog instead of spinning forever.
|
||||||
|
Interlocked.Exchange(ref _status, StatusFinished);
|
||||||
|
TraceSaveDataDialog($"open mode={_lastMode} userData=0x{_lastUserData:X16} -> finished");
|
||||||
|
return SetReturn(ctx, ErrorOk);
|
||||||
|
}
|
||||||
|
|
||||||
|
[SysAbiExport(
|
||||||
|
Nid = "ERKzksauAJA",
|
||||||
|
ExportName = "sceSaveDataDialogGetStatus",
|
||||||
|
Target = Generation.Gen4 | Generation.Gen5,
|
||||||
|
LibraryName = "libSceSaveDataDialog")]
|
||||||
|
public static int SaveDataDialogGetStatus(CpuContext ctx) => SetReturn(ctx, Volatile.Read(ref _status));
|
||||||
|
|
||||||
|
[SysAbiExport(
|
||||||
|
Nid = "KK3Bdg1RWK0",
|
||||||
|
ExportName = "sceSaveDataDialogUpdateStatus",
|
||||||
|
Target = Generation.Gen4 | Generation.Gen5,
|
||||||
|
LibraryName = "libSceSaveDataDialog")]
|
||||||
|
public static int SaveDataDialogUpdateStatus(CpuContext ctx) => SetReturn(ctx, Volatile.Read(ref _status));
|
||||||
|
|
||||||
|
[SysAbiExport(
|
||||||
|
Nid = "en7gNVnh878",
|
||||||
|
ExportName = "sceSaveDataDialogIsReadyToDisplay",
|
||||||
|
Target = Generation.Gen4 | Generation.Gen5,
|
||||||
|
LibraryName = "libSceSaveDataDialog")]
|
||||||
|
public static int SaveDataDialogIsReadyToDisplay(CpuContext ctx) => SetReturn(ctx, 1);
|
||||||
|
|
||||||
|
[SysAbiExport(
|
||||||
|
Nid = "yEiJ-qqr6Cg",
|
||||||
|
ExportName = "sceSaveDataDialogGetResult",
|
||||||
|
Target = Generation.Gen4 | Generation.Gen5,
|
||||||
|
LibraryName = "libSceSaveDataDialog")]
|
||||||
|
public static int SaveDataDialogGetResult(CpuContext ctx)
|
||||||
|
{
|
||||||
|
var resultAddress = ctx[CpuRegister.Rdi];
|
||||||
|
if (resultAddress == 0)
|
||||||
|
{
|
||||||
|
return SetReturn(ctx, ErrorArgNull);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Volatile.Read(ref _status) != StatusFinished)
|
||||||
|
{
|
||||||
|
return SetReturn(ctx, ErrorNotFinished);
|
||||||
|
}
|
||||||
|
|
||||||
|
Span<byte> result = stackalloc byte[ResultSize];
|
||||||
|
result.Clear();
|
||||||
|
BinaryPrimitives.WriteInt32LittleEndian(result[0x00..], _lastMode);
|
||||||
|
BinaryPrimitives.WriteInt32LittleEndian(result[0x04..], 0);
|
||||||
|
BinaryPrimitives.WriteInt32LittleEndian(result[0x08..], 0);
|
||||||
|
BinaryPrimitives.WriteUInt64LittleEndian(result[0x20..], _lastUserData);
|
||||||
|
|
||||||
|
if (!ctx.Memory.TryWrite(resultAddress, result))
|
||||||
|
{
|
||||||
|
return SetReturn(ctx, (int)OrbisGen2Result.ORBIS_GEN2_ERROR_MEMORY_FAULT);
|
||||||
|
}
|
||||||
|
|
||||||
|
return SetReturn(ctx, ErrorOk);
|
||||||
|
}
|
||||||
|
|
||||||
|
[SysAbiExport(
|
||||||
|
Nid = "fH46Lag88XY",
|
||||||
|
ExportName = "sceSaveDataDialogClose",
|
||||||
|
Target = Generation.Gen4 | Generation.Gen5,
|
||||||
|
LibraryName = "libSceSaveDataDialog")]
|
||||||
|
public static int SaveDataDialogClose(CpuContext ctx)
|
||||||
|
{
|
||||||
|
if (Interlocked.CompareExchange(ref _status, StatusFinished, StatusRunning) != StatusRunning)
|
||||||
|
{
|
||||||
|
return SetReturn(ctx, ErrorNotRunning);
|
||||||
|
}
|
||||||
|
|
||||||
|
return SetReturn(ctx, ErrorOk);
|
||||||
|
}
|
||||||
|
|
||||||
|
[SysAbiExport(
|
||||||
|
Nid = "YuH2FA7azqQ",
|
||||||
|
ExportName = "sceSaveDataDialogTerminate",
|
||||||
|
Target = Generation.Gen4 | Generation.Gen5,
|
||||||
|
LibraryName = "libSceSaveDataDialog")]
|
||||||
|
public static int SaveDataDialogTerminate(CpuContext ctx)
|
||||||
|
{
|
||||||
|
if (Interlocked.Exchange(ref _status, StatusNone) == StatusNone)
|
||||||
|
{
|
||||||
|
return SetReturn(ctx, ErrorNotInitialized);
|
||||||
|
}
|
||||||
|
|
||||||
|
_lastMode = 0;
|
||||||
|
_lastUserData = 0;
|
||||||
|
return SetReturn(ctx, ErrorOk);
|
||||||
|
}
|
||||||
|
|
||||||
|
[SysAbiExport(
|
||||||
|
Nid = "V-uEeFKARJU",
|
||||||
|
ExportName = "sceSaveDataDialogProgressBarInc",
|
||||||
|
Target = Generation.Gen4 | Generation.Gen5,
|
||||||
|
LibraryName = "libSceSaveDataDialog")]
|
||||||
|
public static int SaveDataDialogProgressBarInc(CpuContext ctx) => SetReturn(ctx, ErrorOk);
|
||||||
|
|
||||||
|
[SysAbiExport(
|
||||||
|
Nid = "hay1CfTmLyA",
|
||||||
|
ExportName = "sceSaveDataDialogProgressBarSetValue",
|
||||||
|
Target = Generation.Gen4 | Generation.Gen5,
|
||||||
|
LibraryName = "libSceSaveDataDialog")]
|
||||||
|
public static int SaveDataDialogProgressBarSetValue(CpuContext ctx) => SetReturn(ctx, ErrorOk);
|
||||||
|
|
||||||
|
private static bool TryReadInt32(CpuContext ctx, ulong address, out int value)
|
||||||
|
{
|
||||||
|
value = 0;
|
||||||
|
Span<byte> bytes = stackalloc byte[sizeof(int)];
|
||||||
|
if (!ctx.Memory.TryRead(address, bytes))
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
value = BinaryPrimitives.ReadInt32LittleEndian(bytes);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static bool TryReadUInt64(CpuContext ctx, ulong address, out ulong value)
|
||||||
|
{
|
||||||
|
value = 0;
|
||||||
|
Span<byte> bytes = stackalloc byte[sizeof(ulong)];
|
||||||
|
if (!ctx.Memory.TryRead(address, bytes))
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
value = BinaryPrimitives.ReadUInt64LittleEndian(bytes);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static int SetReturn(CpuContext ctx, int result)
|
||||||
|
{
|
||||||
|
ctx[CpuRegister.Rax] = unchecked((ulong)result);
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void TraceSaveDataDialog(string message)
|
||||||
|
{
|
||||||
|
if (!string.Equals(Environment.GetEnvironmentVariable("SHARPEMU_LOG_SAVEDATA"), "1", StringComparison.Ordinal))
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
Console.Error.WriteLine($"[LOADER][TRACE] save_data_dialog.{message}");
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -12,6 +12,7 @@ SPDX-License-Identifier: GPL-2.0-or-later
|
|||||||
<PackageReference Include="Silk.NET.Vulkan" />
|
<PackageReference Include="Silk.NET.Vulkan" />
|
||||||
<PackageReference Include="Silk.NET.Vulkan.Extensions.KHR" />
|
<PackageReference Include="Silk.NET.Vulkan.Extensions.KHR" />
|
||||||
<PackageReference Include="Silk.NET.Windowing" />
|
<PackageReference Include="Silk.NET.Windowing" />
|
||||||
|
<PackageReference Include="Silk.NET.Shaderc" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
|
|||||||
@@ -2,6 +2,16 @@
|
|||||||
"version": 2,
|
"version": 2,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"net10.0": {
|
"net10.0": {
|
||||||
|
"Silk.NET.Shaderc": {
|
||||||
|
"type": "Direct",
|
||||||
|
"requested": "[2.23.0, )",
|
||||||
|
"resolved": "2.23.0",
|
||||||
|
"contentHash": "+pXfOhmSCeeMECOo9HMi3C63LVbQ7FBxPFgxPKOT6mXD8Gg/90Wt4fLX4LqUuVbGid5LW6BXAUu1g17XQoawdA==",
|
||||||
|
"dependencies": {
|
||||||
|
"Silk.NET.Core": "2.23.0",
|
||||||
|
"Silk.NET.Shaderc.Native": "2.23.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
"Silk.NET.Vulkan": {
|
"Silk.NET.Vulkan": {
|
||||||
"type": "Direct",
|
"type": "Direct",
|
||||||
"requested": "[2.23.0, )",
|
"requested": "[2.23.0, )",
|
||||||
@@ -64,6 +74,11 @@
|
|||||||
"resolved": "2.23.0",
|
"resolved": "2.23.0",
|
||||||
"contentHash": "r8PdIVzME8EH0qAgbmRPO87I4GfgR2j8TofT7EMuRJDf1QluoQwnVypDoFJjQ2ZBSRsGYk5unYxxogI05Ogsmw=="
|
"contentHash": "r8PdIVzME8EH0qAgbmRPO87I4GfgR2j8TofT7EMuRJDf1QluoQwnVypDoFJjQ2ZBSRsGYk5unYxxogI05Ogsmw=="
|
||||||
},
|
},
|
||||||
|
"Silk.NET.Shaderc.Native": {
|
||||||
|
"type": "Transitive",
|
||||||
|
"resolved": "2.23.0",
|
||||||
|
"contentHash": "H6OMLIWdh2HITvkmj+ALs8LTIdQvQ2/JTtkDXinVbJ3xxrQIBXhVmc9jnuTQ67YDybGlENSMrgthzhLwK0rjnQ=="
|
||||||
|
},
|
||||||
"Silk.NET.Windowing.Common": {
|
"Silk.NET.Windowing.Common": {
|
||||||
"type": "Transitive",
|
"type": "Transitive",
|
||||||
"resolved": "2.23.0",
|
"resolved": "2.23.0",
|
||||||
|
|||||||
Reference in New Issue
Block a user