mirror of
https://github.com/par274/sharpemu.git
synced 2026-07-25 20:28:48 +08:00
[Gpu] Stop retrying array uploads that overrun their allocation (#476)
A 2D-array texture whose Depth times the per-slice stride runs past its real allocation fails a slice read partway through the upload loop, and falls through to the single-slice path after already detiling the layers it did read. That fall-through builds the texture with ArrayLayers defaulting to 1, so the presenter caches it under a one-layer key while the next draw looks it up with ArrayLayers = Depth. The two never match, so the texture misses the cache and repeats the whole read-and-detile on every draw, throwing the result away each time. Detiling is per-texel swizzle math, so one such texture retried a few times per frame is expensive: it measured 568-879 ms of every second in Demon's Souls, against a 1.4 second frame. An allocation that is too short stays too short, so remembering the address and not retrying it costs nothing and repairs the cache key as a side effect: with the array upload skipped, arrayUploadLayers is 1, which is exactly what the fall-through texture reports. Tested on Demon's Souls (PPSA01342): 0.7 fps to 3.6-4.1 fps, CPU detile time per second from ~700 ms to 0, and arrayed textures go from missing the cache on every draw to hitting it every time. 28 of the 29 array uploads in that run already succeeded and are unaffected; only the one overrunning texture now falls back to its base slice. 495 tests pass.
This commit is contained in:
@@ -221,6 +221,7 @@ public static partial class AgcExports
|
||||
(ulong Es, ulong State, ulong AliasAlignment),
|
||||
IGuestCompiledShader> _depthOnlyVertexShaderCache = new();
|
||||
private static readonly Dictionary<ulong, ulong> _shaderHeadersByCode = new();
|
||||
private static readonly ConcurrentDictionary<ulong, byte> _arrayUploadUnsupported = new();
|
||||
private static readonly bool _traceAgc = string.Equals(
|
||||
Environment.GetEnvironmentVariable("SHARPEMU_LOG_AGC"),
|
||||
"1",
|
||||
@@ -7984,7 +7985,8 @@ public static partial class AgcExports
|
||||
descriptor.Address != 0 &&
|
||||
(descriptor.Type == Gen5TextureType2DArray ||
|
||||
descriptor.Type == Gen5TextureType1DArray) &&
|
||||
descriptor.Depth > 1;
|
||||
descriptor.Depth > 1 &&
|
||||
!_arrayUploadUnsupported.ContainsKey(descriptor.Address);
|
||||
var arrayUploadLayers = wantsArrayUpload ? descriptor.Depth : 1u;
|
||||
|
||||
// Upload-known (not plain availability): the presenter's answer goes
|
||||
@@ -8213,6 +8215,8 @@ public static partial class AgcExports
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
_arrayUploadUnsupported.TryAdd(descriptor.Address, 0);
|
||||
}
|
||||
|
||||
var source = new byte[(int)physicalSourceByteCount];
|
||||
|
||||
Reference in New Issue
Block a user