GpuMemoryBuffer.cpp 3.1 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192
  1. #include "pch.h"
  2. #include "GpuMemoryBuffer.h"
  3. #include "GraphicsDevice/ITexture2D.h"
  4. namespace unity
  5. {
  6. namespace webrtc
  7. {
  8. GpuMemoryBufferHandle::GpuMemoryBufferHandle() { }
  9. GpuMemoryBufferHandle::GpuMemoryBufferHandle(GpuMemoryBufferHandle&& other) = default;
  10. GpuMemoryBufferHandle& GpuMemoryBufferHandle::operator=(GpuMemoryBufferHandle&& other) = default;
  11. GpuMemoryBufferHandle::~GpuMemoryBufferHandle() { }
  12. GpuMemoryBufferFromUnity::GpuMemoryBufferFromUnity(
  13. IGraphicsDevice* device, NativeTexPtr ptr, const Size& size, UnityRenderingExtTextureFormat format)
  14. : device_(device)
  15. , format_(format)
  16. , size_(size)
  17. , texture_(nullptr)
  18. , textureCpuRead_(nullptr)
  19. , handle_(nullptr)
  20. {
  21. uint32_t width = static_cast<uint32_t>(size.width());
  22. uint32_t height = static_cast<uint32_t>(size.height());
  23. texture_.reset(device_->CreateDefaultTextureV(width, height, format));
  24. textureCpuRead_.reset(device_->CreateCPUReadTextureV(width, height, format));
  25. // todo(kazuki): need to refactor
  26. #if CUDA_PLATFORM
  27. if (device_->IsCudaSupport())
  28. {
  29. // IGraphicsDevice::Map method is too heavy and stop the graphics process,
  30. // so must not call this method on the worker thread instead of the render thread.
  31. handle_ = device_->Map(texture_.get());
  32. }
  33. #endif
  34. CopyBuffer(ptr);
  35. }
  36. GpuMemoryBufferFromUnity::~GpuMemoryBufferFromUnity() { }
  37. void GpuMemoryBufferFromUnity::ResetSync()
  38. {
  39. if (!device_->ResetSync(texture_.get()))
  40. {
  41. RTC_LOG(LS_INFO) << "ResetSync failed.";
  42. }
  43. if (!device_->ResetSync(textureCpuRead_.get()))
  44. {
  45. RTC_LOG(LS_INFO) << "ResetSync failed.";
  46. }
  47. }
  48. void GpuMemoryBufferFromUnity::CopyBuffer(NativeTexPtr ptr)
  49. {
  50. // One texture cannot map CUDA memory and CPU memory simultaneously.
  51. // Believe there is still room for improvement.
  52. device_->CopyResourceFromNativeV(texture_.get(), ptr);
  53. device_->CopyResourceFromNativeV(textureCpuRead_.get(), ptr);
  54. }
  55. UnityRenderingExtTextureFormat GpuMemoryBufferFromUnity::GetFormat() const { return format_; }
  56. Size GpuMemoryBufferFromUnity::GetSize() const { return size_; }
  57. rtc::scoped_refptr<I420BufferInterface> GpuMemoryBufferFromUnity::ToI420()
  58. {
  59. using namespace std::chrono_literals;
  60. const std::chrono::nanoseconds timeout(30ms); // 30ms
  61. if (!device_->WaitSync(textureCpuRead_.get(), timeout.count()))
  62. {
  63. RTC_LOG(LS_INFO) << "WaitSync failed.";
  64. return nullptr;
  65. }
  66. return device_->ConvertRGBToI420(textureCpuRead_.get());
  67. }
  68. const GpuMemoryBufferHandle* GpuMemoryBufferFromUnity::handle() const
  69. {
  70. using namespace std::chrono_literals;
  71. const std::chrono::nanoseconds timeout(30ms); // 30ms
  72. if (!device_->WaitSync(texture_.get(), timeout.count()))
  73. {
  74. RTC_LOG(LS_INFO) << "WaitSync failed.";
  75. return nullptr;
  76. }
  77. return handle_.get();
  78. }
  79. }
  80. }