Commit 6fc38604 authored by Michael Spang's avatar Michael Spang Committed by Commit Bot

ozone: drm: Move DrmFramebuffer from GbmBuffer to GbmPixmap

Framebuffers are a DRM-master specific object, so move them out out of
GbmBuffer. This makes GbmBuffer independent enough of the DRM modesetting
code that we can merge it with GbmBoWrapper.

Bug: 869206

Change-Id: I4ae6e1191ef115a4aa58b1c7ccb9f19e06de28aa
Reviewed-on: https://chromium-review.googlesource.com/1155918
Commit-Queue: Michael Spang <spang@chromium.org>
Reviewed-by: default avatarDaniel Nicoara <dnicoara@chromium.org>
Cr-Commit-Position: refs/heads/master@{#579656}
parent c9098ae3
......@@ -35,6 +35,35 @@ namespace ui {
namespace {
scoped_refptr<DrmFramebuffer> AddFramebuffersForBo(
const scoped_refptr<GbmDevice>& gbm,
gbm_bo* bo,
uint32_t format,
uint64_t format_modifier) {
DrmFramebuffer::AddFramebufferParams params;
params.format = format;
params.modifier = format_modifier;
params.width = gbm_bo_get_width(bo);
params.height = gbm_bo_get_height(bo);
params.num_planes = gbm_bo_get_num_planes(bo);
for (size_t i = 0; i < params.num_planes; ++i) {
params.handles[i] = gbm_bo_get_plane_handle(bo, i).u32;
params.strides[i] = gbm_bo_get_plane_stride(bo, i);
params.offsets[i] = gbm_bo_get_plane_offset(bo, i);
}
// AddFramebuffer2 only considers the modifiers if addfb_flags has
// DRM_MODE_FB_MODIFIERS set. We only set that when we've created
// a bo with modifiers, otherwise, we rely on the "no modifiers"
// behavior doing the right thing.
params.flags = 0;
if (gbm->allow_addfb2_modifiers() &&
params.modifier != DRM_FORMAT_MOD_INVALID)
params.flags |= DRM_MODE_FB_MODIFIERS;
return DrmFramebuffer::AddFramebuffer(gbm.get(), params);
}
uint32_t BufferUsageToGbmFlags(gfx::BufferUsage usage) {
switch (usage) {
case gfx::BufferUsage::GPU_READ:
......@@ -64,7 +93,8 @@ void CreateBufferWithGbmFlags(const scoped_refptr<GbmDevice>& gbm,
const gfx::Size& size,
uint32_t flags,
const std::vector<uint64_t>& modifiers,
std::unique_ptr<GbmBuffer>* out_buffer) {
std::unique_ptr<GbmBuffer>* out_buffer,
scoped_refptr<DrmFramebuffer>* out_framebuffer) {
std::unique_ptr<GbmBuffer> buffer;
if (modifiers.empty())
buffer = GbmBuffer::CreateBuffer(gbm, fourcc_format, size, flags);
......@@ -74,10 +104,17 @@ void CreateBufferWithGbmFlags(const scoped_refptr<GbmDevice>& gbm,
if (!buffer)
return;
if (flags & GBM_BO_USE_SCANOUT && !buffer->framebuffer())
return;
scoped_refptr<DrmFramebuffer> framebuffer;
if (flags & GBM_BO_USE_SCANOUT) {
framebuffer = AddFramebuffersForBo(gbm, buffer->gbm_bo()->bo(),
buffer->gbm_bo()->format(),
buffer->gbm_bo()->format_modifier());
if (!framebuffer)
return;
}
*out_buffer = std::move(buffer);
*out_framebuffer = std::move(framebuffer);
}
class GbmBufferGenerator : public DrmFramebufferGenerator {
......@@ -103,7 +140,9 @@ class GbmBufferGenerator : public DrmFramebufferGenerator {
if (!buffer)
return nullptr;
return buffer->framebuffer();
return AddFramebuffersForBo(gbm, buffer->gbm_bo()->bo(),
buffer->gbm_bo()->format(),
buffer->gbm_bo()->format_modifier());
}
protected:
......@@ -172,7 +211,8 @@ void DrmThread::CreateBuffer(gfx::AcceleratedWidget widget,
gfx::BufferFormat format,
gfx::BufferUsage usage,
uint32_t client_flags,
std::unique_ptr<GbmBuffer>* buffer) {
std::unique_ptr<GbmBuffer>* buffer,
scoped_refptr<DrmFramebuffer>* framebuffer) {
scoped_refptr<GbmDevice> gbm =
static_cast<GbmDevice*>(device_manager_->GetDrmDevice(widget).get());
DCHECK(gbm);
......@@ -189,7 +229,8 @@ void DrmThread::CreateBuffer(gfx::AcceleratedWidget widget,
modifiers = window->GetController()->GetFormatModifiers(fourcc_format);
}
CreateBufferWithGbmFlags(gbm, fourcc_format, size, flags, modifiers, buffer);
CreateBufferWithGbmFlags(gbm, fourcc_format, size, flags, modifiers, buffer,
framebuffer);
// NOTE: BufferUsage::SCANOUT is used to create buffers that will be
// explicitly set via kms on a CRTC (e.g: BufferQueue buffers), therefore
......@@ -197,8 +238,8 @@ void DrmThread::CreateBuffer(gfx::AcceleratedWidget widget,
// buffer in that case.
if (!*buffer && usage != gfx::BufferUsage::SCANOUT) {
flags &= ~GBM_BO_USE_SCANOUT;
CreateBufferWithGbmFlags(gbm, fourcc_format, size, flags, modifiers,
buffer);
CreateBufferWithGbmFlags(gbm, fourcc_format, size, flags, modifiers, buffer,
framebuffer);
}
}
......@@ -208,14 +249,29 @@ void DrmThread::CreateBufferFromFds(
gfx::BufferFormat format,
std::vector<base::ScopedFD> fds,
const std::vector<gfx::NativePixmapPlane>& planes,
std::unique_ptr<GbmBuffer>* buffer) {
std::unique_ptr<GbmBuffer>* out_buffer,
scoped_refptr<DrmFramebuffer>* out_framebuffer) {
scoped_refptr<GbmDevice> gbm =
static_cast<GbmDevice*>(device_manager_->GetDrmDevice(widget).get());
DCHECK(gbm);
*buffer = GbmBuffer::CreateBufferFromFds(
std::unique_ptr<GbmBuffer> buffer = GbmBuffer::CreateBufferFromFds(
gbm, ui::GetFourCCFormatFromBufferFormat(format), size, std::move(fds),
planes);
if (!buffer)
return;
scoped_refptr<DrmFramebuffer> framebuffer;
if (buffer->gbm_bo()->flags() & GBM_BO_USE_SCANOUT) {
framebuffer = AddFramebuffersForBo(gbm, buffer->gbm_bo()->bo(),
buffer->gbm_bo()->format(),
buffer->gbm_bo()->format_modifier());
if (!framebuffer)
return;
}
*out_buffer = std::move(buffer);
*out_framebuffer = std::move(framebuffer);
}
void DrmThread::GetScanoutFormats(
......
......@@ -41,6 +41,7 @@ class Rect;
namespace ui {
class DrmDeviceManager;
class DrmFramebuffer;
class DrmGpuDisplayManager;
class GbmBuffer;
class DrmFramebufferGenerator;
......@@ -71,13 +72,15 @@ class DrmThread : public base::Thread,
gfx::BufferFormat format,
gfx::BufferUsage usage,
uint32_t flags,
std::unique_ptr<GbmBuffer>* buffer);
std::unique_ptr<GbmBuffer>* buffer,
scoped_refptr<DrmFramebuffer>* framebuffer);
void CreateBufferFromFds(gfx::AcceleratedWidget widget,
const gfx::Size& size,
gfx::BufferFormat format,
std::vector<base::ScopedFD> fds,
const std::vector<gfx::NativePixmapPlane>& planes,
std::unique_ptr<GbmBuffer>* buffer);
std::unique_ptr<GbmBuffer>* buffer,
scoped_refptr<DrmFramebuffer>* framebuffer);
void GetScanoutFormats(gfx::AcceleratedWidget widget,
std::vector<gfx::BufferFormat>* scanout_formats);
void AddBindingCursorDevice(ozone::mojom::DeviceCursorRequest request);
......
......@@ -32,36 +32,34 @@ std::unique_ptr<DrmWindowProxy> DrmThreadProxy::CreateDrmWindowProxy(
return std::make_unique<DrmWindowProxy>(widget, &drm_thread_);
}
std::unique_ptr<GbmBuffer> DrmThreadProxy::CreateBuffer(
gfx::AcceleratedWidget widget,
const gfx::Size& size,
gfx::BufferFormat format,
gfx::BufferUsage usage,
uint32_t flags) {
void DrmThreadProxy::CreateBuffer(gfx::AcceleratedWidget widget,
const gfx::Size& size,
gfx::BufferFormat format,
gfx::BufferUsage usage,
uint32_t flags,
std::unique_ptr<GbmBuffer>* buffer,
scoped_refptr<DrmFramebuffer>* framebuffer) {
DCHECK(drm_thread_.task_runner())
<< "no task runner! in DrmThreadProxy::CreateBuffer";
std::unique_ptr<GbmBuffer> buffer;
PostSyncTask(
drm_thread_.task_runner(),
base::BindOnce(&DrmThread::CreateBuffer, base::Unretained(&drm_thread_),
widget, size, format, usage, flags, &buffer));
return buffer;
widget, size, format, usage, flags, buffer, framebuffer));
}
std::unique_ptr<GbmBuffer> DrmThreadProxy::CreateBufferFromFds(
void DrmThreadProxy::CreateBufferFromFds(
gfx::AcceleratedWidget widget,
const gfx::Size& size,
gfx::BufferFormat format,
std::vector<base::ScopedFD> fds,
const std::vector<gfx::NativePixmapPlane>& planes) {
std::unique_ptr<GbmBuffer> buffer;
PostSyncTask(
drm_thread_.task_runner(),
base::BindOnce(&DrmThread::CreateBufferFromFds,
base::Unretained(&drm_thread_), widget, size, format,
base::Passed(std::move(fds)), planes, &buffer));
return buffer;
const std::vector<gfx::NativePixmapPlane>& planes,
std::unique_ptr<GbmBuffer>* buffer,
scoped_refptr<DrmFramebuffer>* framebuffer) {
PostSyncTask(drm_thread_.task_runner(),
base::BindOnce(&DrmThread::CreateBufferFromFds,
base::Unretained(&drm_thread_), widget, size,
format, base::Passed(std::move(fds)), planes,
buffer, framebuffer));
}
void DrmThreadProxy::GetScanoutFormats(
......
......@@ -32,18 +32,21 @@ class DrmThreadProxy {
std::unique_ptr<DrmWindowProxy> CreateDrmWindowProxy(
gfx::AcceleratedWidget widget);
std::unique_ptr<GbmBuffer> CreateBuffer(gfx::AcceleratedWidget widget,
const gfx::Size& size,
gfx::BufferFormat format,
gfx::BufferUsage usage,
uint32_t flags);
std::unique_ptr<GbmBuffer> CreateBufferFromFds(
gfx::AcceleratedWidget widget,
const gfx::Size& size,
gfx::BufferFormat format,
std::vector<base::ScopedFD> fds,
const std::vector<gfx::NativePixmapPlane>& planes);
void CreateBuffer(gfx::AcceleratedWidget widget,
const gfx::Size& size,
gfx::BufferFormat format,
gfx::BufferUsage usage,
uint32_t flags,
std::unique_ptr<GbmBuffer>* buffer,
scoped_refptr<DrmFramebuffer>* framebuffer);
void CreateBufferFromFds(gfx::AcceleratedWidget widget,
const gfx::Size& size,
gfx::BufferFormat format,
std::vector<base::ScopedFD> fds,
const std::vector<gfx::NativePixmapPlane>& planes,
std::unique_ptr<GbmBuffer>* buffer,
scoped_refptr<DrmFramebuffer>* framebuffer);
void GetScanoutFormats(gfx::AcceleratedWidget widget,
std::vector<gfx::BufferFormat>* scanout_formats);
......
......@@ -31,39 +31,6 @@
namespace ui {
namespace {
scoped_refptr<DrmFramebuffer> AddFramebuffersForBo(
const scoped_refptr<GbmDevice>& gbm,
gbm_bo* bo,
uint32_t format,
uint64_t format_modifier) {
DrmFramebuffer::AddFramebufferParams params;
params.format = format;
params.modifier = format_modifier;
params.width = gbm_bo_get_width(bo);
params.height = gbm_bo_get_height(bo);
params.num_planes = gbm_bo_get_num_planes(bo);
for (size_t i = 0; i < params.num_planes; ++i) {
params.handles[i] = gbm_bo_get_plane_handle(bo, i).u32;
params.strides[i] = gbm_bo_get_plane_stride(bo, i);
params.offsets[i] = gbm_bo_get_plane_offset(bo, i);
}
// AddFramebuffer2 only considers the modifiers if addfb_flags has
// DRM_MODE_FB_MODIFIERS set. We only set that when we've created
// a bo with modifiers, otherwise, we rely on the "no modifiers"
// behavior doing the right thing.
params.flags = 0;
if (gbm->allow_addfb2_modifiers() &&
params.modifier != DRM_FORMAT_MOD_INVALID)
params.flags |= DRM_MODE_FB_MODIFIERS;
return DrmFramebuffer::AddFramebuffer(gbm.get(), params);
}
} // namespace
GbmBuffer::GbmBuffer(const scoped_refptr<GbmDevice>& gbm,
struct gbm_bo* bo,
uint32_t format,
......@@ -79,12 +46,7 @@ GbmBuffer::GbmBuffer(const scoped_refptr<GbmDevice>& gbm,
modifier,
std::move(fds),
size,
std::move(planes)) {
if (gbm_bo_.flags() & GBM_BO_USE_SCANOUT) {
framebuffer_ = AddFramebuffersForBo(
drm_.get(), gbm_bo_.bo(), gbm_bo_.format(), gbm_bo_.format_modifier());
}
}
std::move(planes)) {}
GbmBuffer::~GbmBuffer() {}
......@@ -207,8 +169,11 @@ std::unique_ptr<GbmBuffer> GbmBuffer::CreateBufferFromFds(
}
GbmPixmap::GbmPixmap(GbmSurfaceFactory* surface_manager,
std::unique_ptr<GbmBuffer> buffer)
: surface_manager_(surface_manager), buffer_(std::move(buffer)) {}
std::unique_ptr<GbmBuffer> buffer,
scoped_refptr<DrmFramebuffer> framebuffer)
: surface_manager_(surface_manager),
buffer_(std::move(buffer)),
framebuffer_(std::move(framebuffer)) {}
gfx::NativePixmapHandle GbmPixmap::ExportHandle() {
gfx::NativePixmapHandle handle;
......@@ -235,9 +200,6 @@ gfx::NativePixmapHandle GbmPixmap::ExportHandle() {
return handle;
}
GbmPixmap::~GbmPixmap() {
}
bool GbmPixmap::AreDmaBufFdsValid() const {
return buffer_->gbm_bo()->AreFdsValid();
}
......@@ -285,13 +247,15 @@ bool GbmPixmap::ScheduleOverlayPlane(gfx::AcceleratedWidget widget,
// |framebuffer_id| might be 0 if AddFramebuffer2 failed, in that case we
// already logged the error in GbmBuffer ctor. We avoid logging the error
// here since this method might be called every pageflip.
if (buffer_->framebuffer()) {
if (framebuffer_) {
surface_manager_->GetSurface(widget)->QueueOverlayPlane(DrmOverlayPlane(
buffer_->framebuffer(), plane_z_order, plane_transform, display_bounds,
crop_rect, enable_blend, std::move(gpu_fence)));
framebuffer_, plane_z_order, plane_transform, display_bounds, crop_rect,
enable_blend, std::move(gpu_fence)));
}
return true;
}
GbmPixmap::~GbmPixmap() {}
} // namespace ui
......@@ -51,9 +51,6 @@ class GbmBuffer {
~GbmBuffer();
const GbmBoWrapper* gbm_bo() const { return &gbm_bo_; }
const scoped_refptr<DrmFramebuffer>& framebuffer() const {
return framebuffer_;
}
private:
static std::unique_ptr<GbmBuffer> CreateBufferForBO(
......@@ -63,7 +60,6 @@ class GbmBuffer {
const gfx::Size& size,
uint32_t flags);
scoped_refptr<DrmFramebuffer> framebuffer_;
const scoped_refptr<GbmDevice> drm_;
// Owned gbm_bo wrapper.
......@@ -75,7 +71,8 @@ class GbmBuffer {
class GbmPixmap : public gfx::NativePixmap {
public:
GbmPixmap(GbmSurfaceFactory* surface_manager,
std::unique_ptr<GbmBuffer> buffer);
std::unique_ptr<GbmBuffer> buffer,
scoped_refptr<DrmFramebuffer> framebuffer);
// NativePixmap:
bool AreDmaBufFdsValid() const override;
......@@ -97,14 +94,16 @@ class GbmPixmap : public gfx::NativePixmap {
gfx::NativePixmapHandle ExportHandle() override;
GbmBuffer* buffer() { return buffer_.get(); }
const scoped_refptr<DrmFramebuffer>& framebuffer() const {
return framebuffer_;
}
private:
~GbmPixmap() override;
scoped_refptr<DrmFramebuffer> ProcessBuffer(const gfx::Size& size,
uint32_t format);
GbmSurfaceFactory* surface_manager_;
std::unique_ptr<GbmBuffer> buffer_;
scoped_refptr<DrmFramebuffer> framebuffer_;
DISALLOW_COPY_AND_ASSIGN(GbmPixmap);
};
......
......@@ -37,7 +37,7 @@ void GbmOverlaySurface::SubmitFrame(std::vector<OverlayPlane> overlay_planes,
unsubmitted_frame.overlay_planes.reserve(overlay_planes.size());
for (auto& plane : overlay_planes) {
unsubmitted_frame.overlay_planes.push_back(ui::DrmOverlayPlane(
static_cast<GbmPixmap*>(plane.pixmap.get())->buffer()->framebuffer(),
static_cast<GbmPixmap*>(plane.pixmap.get())->framebuffer(),
plane.z_order, plane.plane_transform, plane.display_bounds,
plane.crop_rect, plane.enable_blend, std::move(plane.gpu_fence)));
}
......
......@@ -164,9 +164,13 @@ scoped_refptr<gfx::NativePixmap> GbmSurfaceFactory::CreateNativePixmapForVulkan(
VkDeviceMemory* vk_device_memory,
VkImage* vk_image) {
#if defined(OS_CHROMEOS)
std::unique_ptr<GbmBuffer> buffer = drm_thread_proxy_->CreateBuffer(
widget, size, format, usage, GbmBuffer::kFlagNoModifiers);
if (!buffer.get())
std::unique_ptr<GbmBuffer> buffer;
scoped_refptr<DrmFramebuffer> framebuffer;
drm_thread_proxy_->CreateBuffer(widget, size, format, usage,
GbmBuffer::kFlagNoModifiers, &buffer,
&framebuffer);
if (!buffer)
return nullptr;
PFN_vkCreateDmaBufImageINTEL create_dma_buf_image_intel =
......@@ -201,7 +205,8 @@ scoped_refptr<gfx::NativePixmap> GbmSurfaceFactory::CreateNativePixmapForVulkan(
return nullptr;
}
return base::MakeRefCounted<GbmPixmap>(this, std::move(buffer));
return base::MakeRefCounted<GbmPixmap>(this, std::move(buffer),
std::move(framebuffer));
#else
return nullptr;
#endif
......@@ -233,12 +238,14 @@ scoped_refptr<gfx::NativePixmap> GbmSurfaceFactory::CreateNativePixmap(
gfx::Size size,
gfx::BufferFormat format,
gfx::BufferUsage usage) {
std::unique_ptr<GbmBuffer> buffer = drm_thread_proxy_->CreateBuffer(
widget, size, format, usage, 0 /* flags */);
if (!buffer.get())
std::unique_ptr<GbmBuffer> buffer;
scoped_refptr<DrmFramebuffer> framebuffer;
drm_thread_proxy_->CreateBuffer(widget, size, format, usage, 0 /* flags */,
&buffer, &framebuffer);
if (!buffer)
return nullptr;
return base::MakeRefCounted<GbmPixmap>(this, std::move(buffer));
return base::MakeRefCounted<GbmPixmap>(this, std::move(buffer),
std::move(framebuffer));
}
scoped_refptr<gfx::NativePixmap>
......@@ -262,12 +269,15 @@ GbmSurfaceFactory::CreateNativePixmapFromHandleInternal(
planes.push_back(plane);
}
std::unique_ptr<GbmBuffer> buffer = drm_thread_proxy_->CreateBufferFromFds(
widget, size, format, std::move(scoped_fds), planes);
std::unique_ptr<GbmBuffer> buffer;
scoped_refptr<DrmFramebuffer> framebuffer;
drm_thread_proxy_->CreateBufferFromFds(widget, size, format,
std::move(scoped_fds), planes, &buffer,
&framebuffer);
if (!buffer)
return nullptr;
return base::MakeRefCounted<GbmPixmap>(this, std::move(buffer));
return base::MakeRefCounted<GbmPixmap>(this, std::move(buffer),
std::move(framebuffer));
}
scoped_refptr<gfx::NativePixmap>
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment