ComputePipeline.cs 2.3 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495
  1. using OpenTK.Graphics.OpenGL;
  2. using Ryujinx.Graphics.GAL;
  3. using Ryujinx.Graphics.Shader;
  4. using System;
  5. namespace Ryujinx.Graphics.OpenGL
  6. {
  7. class ComputePipeline : IComputePipeline
  8. {
  9. private Renderer _renderer;
  10. private Program _program;
  11. public ComputePipeline(Renderer renderer)
  12. {
  13. _renderer = renderer;
  14. }
  15. public void Dispatch(int groupsX, int groupsY, int groupsZ)
  16. {
  17. BindProgram();
  18. GL.DispatchCompute(groupsX, groupsY, groupsZ);
  19. UnbindProgram();
  20. }
  21. public void SetProgram(IProgram program)
  22. {
  23. _program = (Program)program;
  24. }
  25. public void SetStorageBuffer(int index, BufferRange buffer)
  26. {
  27. BindProgram();
  28. BindBuffer(index, buffer, isStorage: true);
  29. UnbindProgram();
  30. }
  31. public void SetUniformBuffer(int index, BufferRange buffer)
  32. {
  33. BindProgram();
  34. BindBuffer(index, buffer, isStorage: false);
  35. UnbindProgram();
  36. }
  37. private void BindBuffer(int index, BufferRange buffer, bool isStorage)
  38. {
  39. int bindingPoint = isStorage
  40. ? _program.GetStorageBufferBindingPoint(ShaderStage.Compute, index)
  41. : _program.GetUniformBufferBindingPoint(ShaderStage.Compute, index);
  42. if (bindingPoint == -1)
  43. {
  44. return;
  45. }
  46. BufferRangeTarget target = isStorage
  47. ? BufferRangeTarget.ShaderStorageBuffer
  48. : BufferRangeTarget.UniformBuffer;
  49. if (buffer.Buffer == null)
  50. {
  51. GL.BindBufferRange(target, bindingPoint, 0, IntPtr.Zero, 0);
  52. return;
  53. }
  54. int bufferHandle = ((Buffer)buffer.Buffer).Handle;
  55. IntPtr bufferOffset = (IntPtr)buffer.Offset;
  56. GL.BindBufferRange(
  57. target,
  58. bindingPoint,
  59. bufferHandle,
  60. bufferOffset,
  61. buffer.Size);
  62. }
  63. private void BindProgram()
  64. {
  65. _program.Bind();
  66. }
  67. private void UnbindProgram()
  68. {
  69. ((GraphicsPipeline)_renderer.GraphicsPipeline).RebindProgram();
  70. }
  71. }
  72. }