From 8a21cf0b787699544cbd710f722e25bbfe750838 Mon Sep 17 00:00:00 2001 From: ReinUsesLisp Date: Fri, 6 Jul 2018 00:02:04 -0300 Subject: [PATCH] Replace OGL buffer streaming from SubData to MapAndOprhan --- Ryujinx.Graphics/Gal/OpenGL/OGLShader.cs | 15 ++-- .../Gal/OpenGL/OGLStreamBuffer.cs | 78 ++++++++++--------- 2 files changed, 46 insertions(+), 47 deletions(-) diff --git a/Ryujinx.Graphics/Gal/OpenGL/OGLShader.cs b/Ryujinx.Graphics/Gal/OpenGL/OGLShader.cs index 3c5c874eaa..20d6ee57cc 100644 --- a/Ryujinx.Graphics/Gal/OpenGL/OGLShader.cs +++ b/Ryujinx.Graphics/Gal/OpenGL/OGLShader.cs @@ -4,6 +4,7 @@ using System; using System.Collections.Concurrent; using System.Collections.Generic; using System.Linq; +using System.Runtime.InteropServices; namespace Ryujinx.Graphics.Gal.OpenGL { @@ -156,9 +157,9 @@ namespace Ryujinx.Graphics.Gal.OpenGL int Size = Math.Min(Data.Length, Buffer.Size); - byte[] Destiny = Buffer.Map(Size); + IntPtr Map = Buffer.Map(Size); - Array.Copy(Data, Destiny, Size); + Marshal.Copy(Data, 0, Map, Size); Buffer.Unmap(Size); } @@ -251,7 +252,7 @@ namespace Ryujinx.Graphics.Gal.OpenGL { int FreeBinding = 0; - int BindUniformBlocksIfNotNull(ShaderStage Stage) + void BindUniformBlocksIfNotNull(ShaderStage Stage) { if (Stage != null) { @@ -270,8 +271,6 @@ namespace Ryujinx.Graphics.Gal.OpenGL FreeBinding++; } } - - return FreeBinding; } BindUniformBlocksIfNotNull(Current.Vertex); @@ -285,7 +284,7 @@ namespace Ryujinx.Graphics.Gal.OpenGL { int FreeBinding = 0; - int BindUniformBuffersIfNotNull(ShaderStage Stage) + void BindUniformBuffersIfNotNull(ShaderStage Stage) { if (Stage != null) { @@ -293,13 +292,11 @@ namespace Ryujinx.Graphics.Gal.OpenGL { OGLStreamBuffer Buffer = GetConstBuffer(Stage.Type, DeclInfo.Cbuf); - GL.BindBufferBase(BufferRangeTarget.UniformBuffer, FreeBinding, Buffer.Handle); + Buffer.Bind(FreeBinding); FreeBinding++; } } - - return FreeBinding; } BindUniformBuffersIfNotNull(Current.Vertex); diff --git a/Ryujinx.Graphics/Gal/OpenGL/OGLStreamBuffer.cs b/Ryujinx.Graphics/Gal/OpenGL/OGLStreamBuffer.cs index 329c5b5df7..439b23e383 100644 --- a/Ryujinx.Graphics/Gal/OpenGL/OGLStreamBuffer.cs +++ b/Ryujinx.Graphics/Gal/OpenGL/OGLStreamBuffer.cs @@ -1,5 +1,6 @@ -using System; using OpenTK.Graphics.OpenGL; +using System; +using System.Runtime.InteropServices; namespace Ryujinx.Graphics.Gal.OpenGL { @@ -11,7 +12,7 @@ namespace Ryujinx.Graphics.Gal.OpenGL protected BufferTarget Target { get; private set; } - private bool Mapped = false; + private bool Mapped; public OGLStreamBuffer(BufferTarget Target, int MaxSize) { @@ -24,18 +25,17 @@ namespace Ryujinx.Graphics.Gal.OpenGL public static OGLStreamBuffer Create(BufferTarget Target, int MaxSize) { - //TODO: Query here for ARB_buffer_storage and use when available - return new SubDataBuffer(Target, MaxSize); + return new MapAndOrphan(Target, MaxSize); } - public byte[] Map(int Size) + public IntPtr Map(int Size) { if (Handle == 0 || Mapped || Size > this.Size) { throw new InvalidOperationException(); } - byte[] Memory = InternMap(Size); + IntPtr Memory = InternMap(Size); Mapped = true; @@ -54,7 +54,9 @@ namespace Ryujinx.Graphics.Gal.OpenGL Mapped = false; } - protected abstract byte[] InternMap(int Size); + public abstract void Bind(int Index); + + protected abstract IntPtr InternMap(int Size); protected abstract void InternUnmap(int UsedSize); @@ -72,41 +74,41 @@ namespace Ryujinx.Graphics.Gal.OpenGL Handle = 0; } } - } - class SubDataBuffer : OGLStreamBuffer - { - private byte[] Memory; - - public SubDataBuffer(BufferTarget Target, int MaxSize) - : base(Target, MaxSize) + class MapAndOrphan : OGLStreamBuffer { - Memory = new byte[MaxSize]; + private const BufferAccessMask Access = + BufferAccessMask.MapInvalidateBufferBit | + BufferAccessMask.MapUnsynchronizedBit | + BufferAccessMask.MapWriteBit; - GL.GenBuffers(1, out int Handle); - - GL.BindBuffer(Target, Handle); - - GL.BufferData(Target, Size, IntPtr.Zero, BufferUsageHint.StreamDraw); - - this.Handle = Handle; - } - - protected override byte[] InternMap(int Size) - { - return Memory; - } - - protected override void InternUnmap(int UsedSize) - { - GL.BindBuffer(Target, Handle); - - unsafe + public MapAndOrphan(BufferTarget Target, int MaxSize) + : base(Target, MaxSize) { - fixed (byte* MemoryPtr = Memory) - { - GL.BufferSubData(Target, IntPtr.Zero, UsedSize, (IntPtr)MemoryPtr); - } + Handle = GL.GenBuffer(); + + GL.BindBuffer(Target, Handle); + + GL.BufferData(Target, Size, IntPtr.Zero, BufferUsageHint.StreamDraw); + } + + public override void Bind(int Index) + { + GL.BindBufferBase((BufferRangeTarget)Target, Index, Handle); + } + + protected override IntPtr InternMap(int Size) + { + GL.BindBuffer(Target, Handle); + + return GL.MapBufferRange(Target, IntPtr.Zero, Size, Access); + } + + protected override void InternUnmap(int UsedSize) + { + //It's not needed to bind handle to Target here, since Map was called previously + + GL.UnmapBuffer(Target); } } }