Separate GPU engines and make state follow official docs (part 1/2) (#2422)

* Use DeviceState for compute and i2m

* Migrate 2D class, more comments

* Migrate DMA copy engine

* Remove now unused code

* Replace GpuState by GpuAccessorState on GpuAcessor, since compute no longer has a GpuState

* More comments

* Add logging (disabled)

* Add back i2m on 3D engine
This commit is contained in:
gdkchan 2021-07-07 20:56:06 -03:00 committed by GitHub
parent 31cbd09a75
commit 8b44eb1c98
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
30 changed files with 2599 additions and 460 deletions

View file

@ -425,22 +425,28 @@ namespace Ryujinx.Graphics.Gpu.Image
/// <summary>
/// Gets the texture descriptor for a given texture handle.
/// </summary>
/// <param name="state">The current GPU state</param>
/// <param name="poolGpuVa">GPU virtual address of the texture pool</param>
/// <param name="bufferIndex">Index of the constant buffer with texture handles</param>
/// <param name="maximumId">Maximum ID of the texture pool</param>
/// <param name="stageIndex">The stage number where the texture is bound</param>
/// <param name="handle">The texture handle</param>
/// <param name="cbufSlot">The texture handle's constant buffer slot</param>
/// <returns>The texture descriptor for the specified texture</returns>
public TextureDescriptor GetTextureDescriptor(GpuState state, int stageIndex, int handle, int cbufSlot)
public TextureDescriptor GetTextureDescriptor(
ulong poolGpuVa,
int bufferIndex,
int maximumId,
int stageIndex,
int handle,
int cbufSlot)
{
int textureBufferIndex = cbufSlot < 0 ? state.Get<int>(MethodOffset.TextureBufferIndex) : cbufSlot & SlotMask;
int textureBufferIndex = cbufSlot < 0 ? bufferIndex : cbufSlot & SlotMask;
int packedId = ReadPackedId(stageIndex, handle, textureBufferIndex, textureBufferIndex);
int textureId = UnpackTextureId(packedId);
var poolState = state.Get<PoolState>(MethodOffset.TexturePoolState);
ulong poolAddress = _channel.MemoryManager.Translate(poolGpuVa);
ulong poolAddress = _channel.MemoryManager.Translate(poolState.Address.Pack());
TexturePool texturePool = _texturePoolCache.FindOrCreate(_channel, poolAddress, poolState.MaximumId);
TexturePool texturePool = _texturePoolCache.FindOrCreate(_channel, poolAddress, maximumId);
return texturePool.GetDescriptor(textureId);
}

View file

@ -753,21 +753,30 @@ namespace Ryujinx.Graphics.Gpu.Image
/// </summary>
/// <param name="memoryManager">GPU memory manager where the texture is mapped</param>
/// <param name="tex">The texture information</param>
/// <param name="cbp">The copy buffer parameters</param>
/// <param name="swizzle">The copy buffer swizzle</param>
/// <param name="gpuVa">GPU virtual address of the texture</param>
/// <param name="bpp">Bytes per pixel</param>
/// <param name="stride">If <paramref name="linear"/> is true, should have the texture stride, otherwise ignored</param>
/// <param name="xCount">Number of pixels to be copied per line</param>
/// <param name="yCount">Number of lines to be copied</param>
/// <param name="linear">True if the texture has a linear layout, false otherwise</param>
/// <returns>A matching texture, or null if there is no match</returns>
public Texture FindTexture(MemoryManager memoryManager, CopyBufferTexture tex, CopyBufferParams cbp, CopyBufferSwizzle swizzle, bool linear)
public Texture FindTexture(
MemoryManager memoryManager,
CopyBufferTexture tex,
ulong gpuVa,
int bpp,
int stride,
int xCount,
int yCount,
bool linear)
{
ulong address = memoryManager.Translate(cbp.DstAddress.Pack());
ulong address = memoryManager.Translate(gpuVa);
if (address == MemoryManager.PteUnmapped)
{
return null;
}
int bpp = swizzle.UnpackDstComponentsCount() * swizzle.UnpackComponentSize();
int addressMatches = _textures.FindOverlaps(address, ref _textureOverlaps);
for (int i = 0; i < addressMatches; i++)
@ -786,7 +795,7 @@ namespace Ryujinx.Graphics.Gpu.Image
{
// Size is not available for linear textures. Use the stride and end of the copy region instead.
match = texture.Info.IsLinear && texture.Info.Stride == cbp.DstStride && tex.RegionY + cbp.YCount <= texture.Info.Height;
match = texture.Info.IsLinear && texture.Info.Stride == stride && tex.RegionY + yCount <= texture.Info.Height;
}
else
{
@ -794,7 +803,7 @@ namespace Ryujinx.Graphics.Gpu.Image
// Due to the way linear strided and block layouts work, widths can be multiplied by Bpp for comparison.
// Note: tex.Width is the aligned texture size. Prefer param.XCount, as the destination should be a texture with that exact size.
bool sizeMatch = cbp.XCount * bpp == texture.Info.Width * format.BytesPerPixel && tex.Height == texture.Info.Height;
bool sizeMatch = xCount * bpp == texture.Info.Width * format.BytesPerPixel && tex.Height == texture.Info.Height;
bool formatMatch = !texture.Info.IsLinear &&
texture.Info.GobBlocksInY == tex.MemoryLayout.UnpackGobBlocksInY() &&
texture.Info.GobBlocksInZ == tex.MemoryLayout.UnpackGobBlocksInZ();

View file

@ -313,26 +313,36 @@ namespace Ryujinx.Graphics.Gpu.Image
/// <summary>
/// Gets a texture descriptor used on the compute pipeline.
/// </summary>
/// <param name="state">Current GPU state</param>
/// <param name="poolGpuVa">GPU virtual address of the texture pool</param>
/// <param name="bufferIndex">Index of the constant buffer with texture handles</param>
/// <param name="maximumId">Maximum ID of the texture pool</param>
/// <param name="handle">Shader "fake" handle of the texture</param>
/// <param name="cbufSlot">Shader constant buffer slot of the texture</param>
/// <returns>The texture descriptor</returns>
public TextureDescriptor GetComputeTextureDescriptor(GpuState state, int handle, int cbufSlot)
public TextureDescriptor GetComputeTextureDescriptor(ulong poolGpuVa, int bufferIndex, int maximumId, int handle, int cbufSlot)
{
return _cpBindingsManager.GetTextureDescriptor(state, 0, handle, cbufSlot);
return _cpBindingsManager.GetTextureDescriptor(poolGpuVa, bufferIndex, maximumId, 0, handle, cbufSlot);
}
/// <summary>
/// Gets a texture descriptor used on the graphics pipeline.
/// </summary>
/// <param name="state">Current GPU state</param>
/// <param name="poolGpuVa">GPU virtual address of the texture pool</param>
/// <param name="bufferIndex">Index of the constant buffer with texture handles</param>
/// <param name="maximumId">Maximum ID of the texture pool</param>
/// <param name="stageIndex">Index of the shader stage where the texture is bound</param>
/// <param name="handle">Shader "fake" handle of the texture</param>
/// <param name="cbufSlot">Shader constant buffer slot of the texture</param>
/// <returns>The texture descriptor</returns>
public TextureDescriptor GetGraphicsTextureDescriptor(GpuState state, int stageIndex, int handle, int cbufSlot)
public TextureDescriptor GetGraphicsTextureDescriptor(
ulong poolGpuVa,
int bufferIndex,
int maximumId,
int stageIndex,
int handle,
int cbufSlot)
{
return _gpBindingsManager.GetTextureDescriptor(state, stageIndex, handle, cbufSlot);
return _gpBindingsManager.GetTextureDescriptor(poolGpuVa, bufferIndex, maximumId, stageIndex, handle, cbufSlot);
}
/// <summary>