vaapi_picture_factory.cc 6.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178
  1. // Copyright 2017 The Chromium Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file.
  4. #include "media/gpu/vaapi/vaapi_picture_factory.h"
  5. #include "base/containers/contains.h"
  6. #include "media/gpu/vaapi/vaapi_wrapper.h"
  7. #include "media/video/picture.h"
  8. #include "ui/gl/gl_bindings.h"
  9. #if defined(USE_OZONE)
  10. #include "media/gpu/vaapi/vaapi_picture_native_pixmap_ozone.h"
  11. #endif // defined(USE_OZONE)
  12. #if BUILDFLAG(USE_VAAPI_X11)
  13. #include "media/gpu/vaapi/vaapi_picture_native_pixmap_angle.h"
  14. #include "media/gpu/vaapi/vaapi_picture_tfp.h"
  15. #endif // BUILDFLAG(USE_VAAPI_X11)
  16. #if defined(USE_EGL)
  17. #include "media/gpu/vaapi/vaapi_picture_native_pixmap_egl.h"
  18. #endif
  19. namespace media {
  20. namespace {
  21. template <typename PictureType>
  22. std::unique_ptr<VaapiPicture> CreateVaapiPictureNativeImpl(
  23. scoped_refptr<VaapiWrapper> vaapi_wrapper,
  24. const MakeGLContextCurrentCallback& make_context_current_cb,
  25. const BindGLImageCallback& bind_image_cb,
  26. const PictureBuffer& picture_buffer,
  27. const gfx::Size& visible_size,
  28. uint32_t client_texture_id,
  29. uint32_t service_texture_id) {
  30. return std::make_unique<PictureType>(
  31. std::move(vaapi_wrapper), make_context_current_cb, bind_image_cb,
  32. picture_buffer.id(), picture_buffer.size(), visible_size,
  33. service_texture_id, client_texture_id, picture_buffer.texture_target());
  34. }
  35. } // namespace
  36. VaapiPictureFactory::VaapiPictureFactory() {
  37. vaapi_impl_pairs_.insert(
  38. std::make_pair(gl::kGLImplementationEGLGLES2,
  39. VaapiPictureFactory::kVaapiImplementationDrm));
  40. #if BUILDFLAG(USE_VAAPI_X11)
  41. vaapi_impl_pairs_.insert(
  42. std::make_pair(gl::kGLImplementationEGLANGLE,
  43. VaapiPictureFactory::kVaapiImplementationAngle));
  44. vaapi_impl_pairs_.insert(
  45. std::make_pair(gl::kGLImplementationDesktopGL,
  46. VaapiPictureFactory::kVaapiImplementationX11));
  47. #elif defined(USE_OZONE)
  48. vaapi_impl_pairs_.insert(
  49. std::make_pair(gl::kGLImplementationEGLANGLE,
  50. VaapiPictureFactory::kVaapiImplementationDrm));
  51. #endif
  52. DeterminePictureCreationAndDownloadingMechanism();
  53. }
  54. VaapiPictureFactory::~VaapiPictureFactory() = default;
  55. std::unique_ptr<VaapiPicture> VaapiPictureFactory::Create(
  56. scoped_refptr<VaapiWrapper> vaapi_wrapper,
  57. const MakeGLContextCurrentCallback& make_context_current_cb,
  58. const BindGLImageCallback& bind_image_cb,
  59. const PictureBuffer& picture_buffer,
  60. const gfx::Size& visible_size) {
  61. // ARC++ sends |picture_buffer| with no texture_target().
  62. DCHECK(picture_buffer.texture_target() == GetGLTextureTarget() ||
  63. picture_buffer.texture_target() == 0u);
  64. // |client_texture_ids| and |service_texture_ids| are empty from ARC++.
  65. const uint32_t client_texture_id =
  66. !picture_buffer.client_texture_ids().empty()
  67. ? picture_buffer.client_texture_ids()[0]
  68. : 0;
  69. const uint32_t service_texture_id =
  70. !picture_buffer.service_texture_ids().empty()
  71. ? picture_buffer.service_texture_ids()[0]
  72. : 0;
  73. // Select DRM(egl) / TFP(glx) at runtime with --use-gl=egl / --use-gl=desktop
  74. return CreateVaapiPictureNative(vaapi_wrapper, make_context_current_cb,
  75. bind_image_cb, picture_buffer, visible_size,
  76. client_texture_id, service_texture_id);
  77. }
  78. VaapiPictureFactory::VaapiImplementation
  79. VaapiPictureFactory::GetVaapiImplementation(gl::GLImplementation gl_impl) {
  80. if (base::Contains(vaapi_impl_pairs_, gl_impl))
  81. return vaapi_impl_pairs_[gl_impl];
  82. return kVaapiImplementationNone;
  83. }
  84. uint32_t VaapiPictureFactory::GetGLTextureTarget() {
  85. #if BUILDFLAG(USE_VAAPI_X11)
  86. return GL_TEXTURE_2D;
  87. #else
  88. return GL_TEXTURE_EXTERNAL_OES;
  89. #endif
  90. }
  91. gfx::BufferFormat VaapiPictureFactory::GetBufferFormat() {
  92. #if BUILDFLAG(USE_VAAPI_X11)
  93. return gfx::BufferFormat::RGBX_8888;
  94. #else
  95. return gfx::BufferFormat::YUV_420_BIPLANAR;
  96. #endif
  97. }
  98. void VaapiPictureFactory::DeterminePictureCreationAndDownloadingMechanism() {
  99. switch (GetVaapiImplementation(gl::GetGLImplementation())) {
  100. #if defined(USE_OZONE)
  101. // We can be called without GL initialized, which is valid if we use Ozone.
  102. case kVaapiImplementationNone:
  103. create_picture_cb_ = base::BindRepeating(
  104. &CreateVaapiPictureNativeImpl<VaapiPictureNativePixmapOzone>);
  105. needs_vpp_for_downloading_ = true;
  106. break;
  107. #endif // defined(USE_OZONE)
  108. #if BUILDFLAG(USE_VAAPI_X11)
  109. case kVaapiImplementationX11:
  110. create_picture_cb_ =
  111. base::BindRepeating(&CreateVaapiPictureNativeImpl<VaapiTFPPicture>);
  112. // Neither VaapiTFPPicture or VaapiPictureNativePixmapAngle needs the VPP.
  113. needs_vpp_for_downloading_ = false;
  114. break;
  115. case kVaapiImplementationAngle:
  116. create_picture_cb_ = base::BindRepeating(
  117. &CreateVaapiPictureNativeImpl<VaapiPictureNativePixmapAngle>);
  118. // Neither VaapiTFPPicture or VaapiPictureNativePixmapAngle needs the VPP.
  119. needs_vpp_for_downloading_ = false;
  120. break;
  121. #endif // BUILDFLAG(USE_VAAPI_X11)
  122. case kVaapiImplementationDrm:
  123. #if defined(USE_OZONE)
  124. create_picture_cb_ = base::BindRepeating(
  125. &CreateVaapiPictureNativeImpl<VaapiPictureNativePixmapOzone>);
  126. needs_vpp_for_downloading_ = true;
  127. break;
  128. #elif defined(USE_EGL)
  129. create_picture_cb_ = base::BindRepeating(
  130. &CreateVaapiPictureNativeImpl<VaapiPictureNativePixmapEgl>);
  131. needs_vpp_for_downloading_ = true;
  132. break;
  133. #else
  134. // ozone or egl must be used to use the DRM implementation.
  135. [[fallthrough]];
  136. #endif
  137. default:
  138. NOTREACHED();
  139. break;
  140. }
  141. }
  142. bool VaapiPictureFactory::NeedsProcessingPipelineForDownloading() const {
  143. return needs_vpp_for_downloading_;
  144. }
  145. std::unique_ptr<VaapiPicture> VaapiPictureFactory::CreateVaapiPictureNative(
  146. scoped_refptr<VaapiWrapper> vaapi_wrapper,
  147. const MakeGLContextCurrentCallback& make_context_current_cb,
  148. const BindGLImageCallback& bind_image_cb,
  149. const PictureBuffer& picture_buffer,
  150. const gfx::Size& visible_size,
  151. uint32_t client_texture_id,
  152. uint32_t service_texture_id) {
  153. CHECK(create_picture_cb_);
  154. return create_picture_cb_.Run(
  155. std::move(vaapi_wrapper), make_context_current_cb, bind_image_cb,
  156. picture_buffer, visible_size, client_texture_id, service_texture_id);
  157. }
  158. } // namespace media