AalHardwareDevice.cs 2.5 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798
  1. using Ryujinx.Audio;
  2. using Ryujinx.Audio.Renderer;
  3. using Ryujinx.Audio.Renderer.Integration;
  4. using System;
  5. using System.Collections.Generic;
  6. using System.Threading;
  7. namespace Ryujinx.HLE.HOS.Services.Audio.AudioRenderer
  8. {
  9. public class AalHardwareDevice : HardwareDevice
  10. {
  11. private IAalOutput _output;
  12. private int _trackId;
  13. private int _bufferTag;
  14. private int _nextTag;
  15. private AutoResetEvent _releaseEvent;
  16. private uint _channelCount;
  17. private uint _sampleRate;
  18. private short[] _buffer;
  19. private Queue<long> _releasedTags;
  20. public AalHardwareDevice(int bufferTag, IAalOutput output, uint channelCount, uint sampleRate)
  21. {
  22. _bufferTag = bufferTag;
  23. _channelCount = channelCount;
  24. _sampleRate = sampleRate;
  25. _output = output;
  26. _releaseEvent = new AutoResetEvent(true);
  27. _trackId = _output.OpenTrack((int)sampleRate, (int)channelCount, AudioCallback);
  28. _releasedTags = new Queue<long>();
  29. _buffer = new short[RendererConstants.TargetSampleCount * channelCount];
  30. _output.Start(_trackId);
  31. }
  32. private void AudioCallback()
  33. {
  34. long[] released = _output.GetReleasedBuffers(_trackId, int.MaxValue);
  35. lock (_releasedTags)
  36. {
  37. foreach (long tag in released)
  38. {
  39. _releasedTags.Enqueue(tag);
  40. }
  41. }
  42. }
  43. private long GetReleasedTag()
  44. {
  45. lock (_releasedTags)
  46. {
  47. if (_releasedTags.Count > 0)
  48. {
  49. return _releasedTags.Dequeue();
  50. }
  51. return (_bufferTag << 16) | (_nextTag++);
  52. }
  53. }
  54. public void AppendBuffer(ReadOnlySpan<short> data, uint channelCount)
  55. {
  56. data.CopyTo(_buffer.AsSpan());
  57. _output.AppendBuffer(_trackId, GetReleasedTag(), _buffer);
  58. }
  59. public uint GetChannelCount()
  60. {
  61. return _channelCount;
  62. }
  63. public uint GetSampleRate()
  64. {
  65. return _sampleRate;
  66. }
  67. public void Dispose()
  68. {
  69. Dispose(true);
  70. }
  71. protected virtual void Dispose(bool disposing)
  72. {
  73. if (disposing)
  74. {
  75. _output.Stop(_trackId);
  76. _output.CloseTrack(_trackId);
  77. _releaseEvent.Dispose();
  78. }
  79. }
  80. }
  81. }