mirror of
https://github.com/Ryujinx/Ryujinx.git
synced 2024-09-29 07:21:28 +00:00
Avoid useless buffer data modification checks
This commit is contained in:
parent
c8a19501ee
commit
70a6b7ea65
|
@ -176,6 +176,7 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
private int[] _cachedSamplerBuffer;
|
private int[] _cachedSamplerBuffer;
|
||||||
|
|
||||||
private int _lastBinding;
|
private int _lastBinding;
|
||||||
|
private int _lastSequenceNumber;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Creates a new array cache entry.
|
/// Creates a new array cache entry.
|
||||||
|
@ -192,6 +193,9 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
|
|
||||||
_texturePool = texturePool;
|
_texturePool = texturePool;
|
||||||
_samplerPool = samplerPool;
|
_samplerPool = samplerPool;
|
||||||
|
|
||||||
|
_lastBinding = -1;
|
||||||
|
_lastSequenceNumber = -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
@ -218,6 +222,23 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
ImageArray = array;
|
ImageArray = array;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Synchronizes memory for all textures in the array.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="isStore">Indicates if the texture may be modified by the access</param>
|
||||||
|
public void SynchronizeMemory(bool isStore)
|
||||||
|
{
|
||||||
|
foreach (Texture texture in Textures.Keys)
|
||||||
|
{
|
||||||
|
texture.SynchronizeMemory();
|
||||||
|
|
||||||
|
if (isStore)
|
||||||
|
{
|
||||||
|
texture.SignalModified();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Clears all cached texture instances.
|
/// Clears all cached texture instances.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
@ -336,6 +357,23 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Checks if the sequence number matches the one used on the last call to this method.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="currentSequenceNumber">Current sequence number</param>
|
||||||
|
/// <returns>True if the sequence numbers match, false otherwise</returns>
|
||||||
|
public bool MatchesSequenceNumber(int currentSequenceNumber)
|
||||||
|
{
|
||||||
|
if (_lastSequenceNumber == currentSequenceNumber)
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
_lastSequenceNumber = currentSequenceNumber;
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Checks if the buffer data matches the cached data.
|
/// Checks if the buffer data matches the cached data.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
@ -455,9 +493,6 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
SamplerIndex samplerIndex,
|
SamplerIndex samplerIndex,
|
||||||
TextureBindingInfo bindingInfo)
|
TextureBindingInfo bindingInfo)
|
||||||
{
|
{
|
||||||
ReadOnlySpan<int> cachedTextureBuffer;
|
|
||||||
ReadOnlySpan<int> cachedSamplerBuffer;
|
|
||||||
|
|
||||||
(textureBufferIndex, int samplerBufferIndex) = TextureHandle.UnpackSlots(bindingInfo.CbufSlot, textureBufferIndex);
|
(textureBufferIndex, int samplerBufferIndex) = TextureHandle.UnpackSlots(bindingInfo.CbufSlot, textureBufferIndex);
|
||||||
|
|
||||||
bool separateSamplerBuffer = textureBufferIndex != samplerBufferIndex;
|
bool separateSamplerBuffer = textureBufferIndex != samplerBufferIndex;
|
||||||
|
@ -465,6 +500,34 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
ref BufferBounds textureBufferBounds = ref _channel.BufferManager.GetUniformBufferBounds(_isCompute, stageIndex, textureBufferIndex);
|
ref BufferBounds textureBufferBounds = ref _channel.BufferManager.GetUniformBufferBounds(_isCompute, stageIndex, textureBufferIndex);
|
||||||
ref BufferBounds samplerBufferBounds = ref _channel.BufferManager.GetUniformBufferBounds(_isCompute, stageIndex, samplerBufferIndex);
|
ref BufferBounds samplerBufferBounds = ref _channel.BufferManager.GetUniformBufferBounds(_isCompute, stageIndex, samplerBufferIndex);
|
||||||
|
|
||||||
|
CacheEntry entry = GetOrAddEntry(
|
||||||
|
texturePool,
|
||||||
|
samplerPool,
|
||||||
|
bindingInfo,
|
||||||
|
isImage,
|
||||||
|
ref textureBufferBounds,
|
||||||
|
out bool isNewEnry);
|
||||||
|
|
||||||
|
bool poolsModified = entry.PoolsModified();
|
||||||
|
bool isStore = bindingInfo.Flags.HasFlag(TextureUsageFlags.ImageStore);
|
||||||
|
|
||||||
|
ReadOnlySpan<int> cachedTextureBuffer;
|
||||||
|
ReadOnlySpan<int> cachedSamplerBuffer;
|
||||||
|
|
||||||
|
if (!poolsModified && !isNewEnry && entry.ValidateTextures())
|
||||||
|
{
|
||||||
|
if (entry.MatchesSequenceNumber(_context.SequenceNumber))
|
||||||
|
{
|
||||||
|
entry.SynchronizeMemory(isStore);
|
||||||
|
|
||||||
|
if (entry.BindingChanged(this, bindingInfo.Binding))
|
||||||
|
{
|
||||||
|
_context.Renderer.Pipeline.SetTextureArray(stage, bindingInfo.Binding, entry.TextureArray);
|
||||||
|
}
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
cachedTextureBuffer = MemoryMarshal.Cast<byte, int>(_channel.MemoryManager.Physical.GetSpan(textureBufferBounds.Range));
|
cachedTextureBuffer = MemoryMarshal.Cast<byte, int>(_channel.MemoryManager.Physical.GetSpan(textureBufferBounds.Range));
|
||||||
|
|
||||||
if (separateSamplerBuffer)
|
if (separateSamplerBuffer)
|
||||||
|
@ -478,31 +541,9 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
|
|
||||||
(_, int samplerWordOffset, _) = TextureHandle.UnpackOffsets(bindingInfo.Handle);
|
(_, int samplerWordOffset, _) = TextureHandle.UnpackOffsets(bindingInfo.Handle);
|
||||||
|
|
||||||
CacheEntry entry = GetOrAddEntry(
|
if (entry.MatchesBufferData(cachedTextureBuffer, cachedSamplerBuffer, separateSamplerBuffer, samplerWordOffset))
|
||||||
texturePool,
|
|
||||||
samplerPool,
|
|
||||||
bindingInfo,
|
|
||||||
isImage,
|
|
||||||
ref textureBufferBounds,
|
|
||||||
out bool isNewEnry);
|
|
||||||
|
|
||||||
bool isStore = bindingInfo.Flags.HasFlag(TextureUsageFlags.ImageStore);
|
|
||||||
bool poolsModified = entry.PoolsModified();
|
|
||||||
|
|
||||||
if (!poolsModified &&
|
|
||||||
!isNewEnry &&
|
|
||||||
entry.MatchesBufferData(cachedTextureBuffer, cachedSamplerBuffer, separateSamplerBuffer, samplerWordOffset) &&
|
|
||||||
entry.ValidateTextures())
|
|
||||||
{
|
{
|
||||||
foreach (Texture texture in entry.Textures.Keys)
|
entry.SynchronizeMemory(isStore);
|
||||||
{
|
|
||||||
texture.SynchronizeMemory();
|
|
||||||
|
|
||||||
if (isStore)
|
|
||||||
{
|
|
||||||
texture.SignalModified();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (entry.BindingChanged(this, bindingInfo.Binding))
|
if (entry.BindingChanged(this, bindingInfo.Binding))
|
||||||
{
|
{
|
||||||
|
@ -511,6 +552,20 @@ namespace Ryujinx.Graphics.Gpu.Image
|
||||||
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
cachedTextureBuffer = MemoryMarshal.Cast<byte, int>(_channel.MemoryManager.Physical.GetSpan(textureBufferBounds.Range));
|
||||||
|
|
||||||
|
if (separateSamplerBuffer)
|
||||||
|
{
|
||||||
|
cachedSamplerBuffer = MemoryMarshal.Cast<byte, int>(_channel.MemoryManager.Physical.GetSpan(samplerBufferBounds.Range));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
cachedSamplerBuffer = cachedTextureBuffer;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (!isNewEnry)
|
if (!isNewEnry)
|
||||||
{
|
{
|
||||||
|
|
Loading…
Reference in a new issue