minigbm: flatten gralloc handle
Many GL drivers assume that first value in the native_handle data array is the fd associated with the graphics buffer, i.e, int prime_fd = handle->data[0]; This in our case until 4bfc7401. We added 64-bit modifiers in our import data, so all values in the drv_import_fd_data struct get 8-byte aligned. In our cros_gralloc_handle, 4 bytes of padding are added between native_handle_t and drv_import_fd_data to make the alignment work. To counter-act this, we can stop embedding drv_import_fd_data in cros_gralloc_handle. BUG=chromium:616275 TEST=Mali driver doesn't return an error when running cros_gralloc CQ-DEPEND=CL:414585 Change-Id: Ib6c165e98126468b96fa7119d5ca13eebee1655c Reviewed-on: https://chromium-review.googlesource.com/414536 Commit-Ready: Gurchetan Singh <gurchetansingh@chromium.org> Tested-by: Gurchetan Singh <gurchetansingh@chromium.org> Reviewed-by: Stéphane Marchesin <marcheu@chromium.org>
This commit is contained in:
parent
458976feb1
commit
c67f9e422c
4 changed files with 75 additions and 39 deletions
|
|
@ -37,6 +37,11 @@ static struct cros_gralloc_bo *cros_gralloc_bo_create(struct driver *drv,
|
|||
return NULL;
|
||||
}
|
||||
|
||||
/*
|
||||
* If there is a desire for more than one kernel buffer, this can be
|
||||
* removed once the ArcCodec and Wayland service have the ability to
|
||||
* send more than one fd. GL/Vulkan drivers may also have to modified.
|
||||
*/
|
||||
if (drv_num_buffers_per_bo(bo->bo) != 1) {
|
||||
drv_bo_destroy(bo->bo);
|
||||
delete bo;
|
||||
|
|
@ -51,31 +56,39 @@ static struct cros_gralloc_bo *cros_gralloc_bo_create(struct driver *drv,
|
|||
|
||||
static struct cros_gralloc_handle *cros_gralloc_handle_from_bo(struct bo *bo)
|
||||
{
|
||||
uint64_t mod;
|
||||
size_t num_planes;
|
||||
struct cros_gralloc_handle *hnd;
|
||||
|
||||
hnd = new cros_gralloc_handle();
|
||||
memset(hnd, 0, sizeof(*hnd));
|
||||
|
||||
hnd->base.version = sizeof(hnd->base);
|
||||
hnd->base.numFds = 1;
|
||||
hnd->base.numInts = num_ints();
|
||||
num_planes = drv_bo_get_num_planes(bo);
|
||||
|
||||
for (size_t p = 0; p < drv_bo_get_num_planes(bo); p++) {
|
||||
hnd->data.strides[p] = drv_bo_get_plane_stride(bo, p);
|
||||
hnd->data.offsets[p] = drv_bo_get_plane_offset(bo, p);
|
||||
hnd->data.sizes[p] = drv_bo_get_plane_size(bo, p);
|
||||
hnd->base.version = sizeof(hnd->base);
|
||||
hnd->base.numFds = num_planes;
|
||||
hnd->base.numInts = num_ints_handle() - num_planes;
|
||||
|
||||
for (size_t p = 0; p < num_planes; p++) {
|
||||
hnd->fds[p] = drv_bo_get_plane_fd(bo, p);
|
||||
hnd->strides[p] = drv_bo_get_plane_stride(bo, p);
|
||||
hnd->offsets[p] = drv_bo_get_plane_offset(bo, p);
|
||||
hnd->sizes[p] = drv_bo_get_plane_size(bo, p);
|
||||
|
||||
mod = drv_bo_get_plane_format_modifier(bo, p);
|
||||
hnd->format_modifiers[p] = static_cast<uint32_t>(mod >> 32);
|
||||
hnd->format_modifiers[p+1] = static_cast<uint32_t>(mod);
|
||||
}
|
||||
|
||||
hnd->data.fds[0] = drv_bo_get_plane_fd(bo, 0);
|
||||
hnd->data.width = drv_bo_get_width(bo);
|
||||
hnd->data.height = drv_bo_get_height(bo);
|
||||
hnd->data.format = drv_bo_get_format(bo);
|
||||
hnd->width = drv_bo_get_width(bo);
|
||||
hnd->height = drv_bo_get_height(bo);
|
||||
hnd->format = drv_bo_get_format(bo);
|
||||
|
||||
hnd->magic = cros_gralloc_magic();
|
||||
hnd->registrations = 0;
|
||||
|
||||
hnd->pixel_stride = hnd->data.strides[0];
|
||||
hnd->pixel_stride /= drv_stride_from_format(hnd->data.format, 1, 0);
|
||||
hnd->pixel_stride = hnd->strides[0];
|
||||
hnd->pixel_stride /= drv_stride_from_format(hnd->format, 1, 0);
|
||||
|
||||
return hnd;
|
||||
}
|
||||
|
|
@ -91,7 +104,7 @@ static int cros_gralloc_alloc(alloc_device_t *dev, int w, int h, int format,
|
|||
return CROS_GRALLOC_ERROR_NO_RESOURCES;
|
||||
|
||||
auto hnd = cros_gralloc_handle_from_bo(bo->bo);
|
||||
hnd->format = static_cast<int32_t>(format);
|
||||
hnd->droid_format = static_cast<int32_t>(format);
|
||||
hnd->usage = static_cast<int32_t>(usage);
|
||||
|
||||
hnd->bo = reinterpret_cast<uint64_t>(bo);
|
||||
|
|
|
|||
|
|
@ -10,19 +10,32 @@
|
|||
#include <cutils/native_handle.h>
|
||||
#include <cstdint>
|
||||
|
||||
#include "../drv.h"
|
||||
#define DRV_MAX_PLANES 4
|
||||
|
||||
/*
|
||||
* Only use 32-bit integers in the handle. This guarantees that the handle is
|
||||
* densely packed (i.e, the compiler does not insert any padding).
|
||||
*/
|
||||
|
||||
struct cros_gralloc_handle {
|
||||
native_handle_t base;
|
||||
drv_import_fd_data data;
|
||||
int32_t fds[DRV_MAX_PLANES];
|
||||
uint32_t strides[DRV_MAX_PLANES];
|
||||
uint32_t offsets[DRV_MAX_PLANES];
|
||||
uint32_t sizes[DRV_MAX_PLANES];
|
||||
uint32_t format_modifiers[2 * DRV_MAX_PLANES];
|
||||
uint32_t width;
|
||||
uint32_t height;
|
||||
uint32_t format; /* DRM format */
|
||||
uint32_t magic;
|
||||
uint32_t pixel_stride;
|
||||
int32_t format, usage; /* Android format and usage. */
|
||||
uint64_t bo; /* Pointer to cros_gralloc_bo. */
|
||||
int32_t registrations; /*
|
||||
* Number of times (*register)() has been
|
||||
* called on this handle.
|
||||
*/
|
||||
int32_t droid_format;
|
||||
int32_t usage; /* Android usage. */
|
||||
uint64_t bo; /* Pointer to cros_gralloc_bo. */
|
||||
int32_t registrations; /*
|
||||
* Number of times (*register)() has been
|
||||
* called on this handle.
|
||||
*/
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -7,6 +7,7 @@
|
|||
#ifndef CROS_GRALLOC_HELPERS_H
|
||||
#define CROS_GRALLOC_HELPERS_H
|
||||
|
||||
#include "../drv.h"
|
||||
#include "cros_gralloc_handle.h"
|
||||
|
||||
#include <hardware/gralloc.h>
|
||||
|
|
@ -44,14 +45,9 @@ constexpr uint32_t cros_gralloc_magic(void)
|
|||
return 0xABCDDCBA;
|
||||
}
|
||||
|
||||
constexpr uint32_t num_ints(void)
|
||||
constexpr uint32_t num_ints_handle()
|
||||
{
|
||||
/*
|
||||
* numFds in our case is one. Subtract that from our numInts
|
||||
* calculation.
|
||||
*/
|
||||
return ((sizeof(struct cros_gralloc_handle)
|
||||
- offsetof(cros_gralloc_handle, data)) / sizeof(int)) - 1;
|
||||
return ((sizeof(struct cros_gralloc_handle)) / sizeof(int));
|
||||
}
|
||||
|
||||
constexpr uint32_t sw_access(void)
|
||||
|
|
|
|||
|
|
@ -72,7 +72,7 @@ static int cros_gralloc_register_buffer(struct gralloc_module_t const* module,
|
|||
return CROS_GRALLOC_ERROR_NONE;
|
||||
}
|
||||
|
||||
if (drmPrimeFDToHandle(drv_get_fd(mod->drv), hnd->data.fds[0], &id)) {
|
||||
if (drmPrimeFDToHandle(drv_get_fd(mod->drv), hnd->fds[0], &id)) {
|
||||
cros_gralloc_error("drmPrimeFDToHandle failed.");
|
||||
return CROS_GRALLOC_ERROR_BAD_HANDLE;
|
||||
}
|
||||
|
|
@ -82,11 +82,25 @@ static int cros_gralloc_register_buffer(struct gralloc_module_t const* module,
|
|||
bo->refcount++;
|
||||
hnd->bo = reinterpret_cast<uint64_t>(bo);
|
||||
} else {
|
||||
hnd->data.fds[1] = hnd->data.fds[2] = hnd->data.fds[3]
|
||||
= hnd->data.fds[0];
|
||||
struct drv_import_fd_data data;
|
||||
size_t num_planes = drv_num_planes_from_format(hnd->format);
|
||||
|
||||
data.format = hnd->format;
|
||||
data.width = hnd->width;
|
||||
data.height = hnd->height;
|
||||
for (size_t p = 0; p < num_planes; p++) {
|
||||
data.fds[p] = hnd->fds[p];
|
||||
data.strides[p] = hnd->strides[p];
|
||||
data.offsets[p] = hnd->offsets[p];
|
||||
data.sizes[p] = hnd->sizes[p];
|
||||
data.format_modifiers[p] = static_cast<uint64_t>
|
||||
(hnd->format_modifiers[p]) << 32;
|
||||
data.format_modifiers[p] |= hnd->format_modifiers[p+1];
|
||||
}
|
||||
|
||||
bo = new cros_gralloc_bo();
|
||||
|
||||
bo->bo = drv_bo_import(mod->drv, &hnd->data);
|
||||
bo->bo = drv_bo_import(mod->drv, &data);
|
||||
if (!bo->bo) {
|
||||
delete bo;
|
||||
return CROS_GRALLOC_ERROR_NO_RESOURCES;
|
||||
|
|
@ -155,7 +169,7 @@ static int cros_gralloc_lock(struct gralloc_module_t const* module,
|
|||
return CROS_GRALLOC_ERROR_BAD_HANDLE;
|
||||
}
|
||||
|
||||
if (hnd->format == HAL_PIXEL_FORMAT_YCbCr_420_888) {
|
||||
if (hnd->droid_format == HAL_PIXEL_FORMAT_YCbCr_420_888) {
|
||||
cros_gralloc_error("YUV format not compatible.");
|
||||
return CROS_GRALLOC_ERROR_BAD_HANDLE;
|
||||
}
|
||||
|
|
@ -241,13 +255,13 @@ static int cros_gralloc_perform(struct gralloc_module_t const* module,
|
|||
break;
|
||||
case GRALLOC_DRM_GET_FORMAT:
|
||||
out_format = va_arg(args, int32_t *);
|
||||
*out_format = hnd->format;
|
||||
*out_format = hnd->droid_format;
|
||||
break;
|
||||
case GRALLOC_DRM_GET_DIMENSIONS:
|
||||
out_width = va_arg(args, uint32_t *);
|
||||
out_height = va_arg(args, uint32_t *);
|
||||
*out_width = hnd->data.width;
|
||||
*out_height = hnd->data.height;
|
||||
*out_width = hnd->width;
|
||||
*out_height = hnd->height;
|
||||
break;
|
||||
case GRALLOC_DRM_GET_BACKING_STORE:
|
||||
out_store = va_arg(args, uint64_t *);
|
||||
|
|
@ -284,7 +298,7 @@ static int cros_gralloc_lock_ycbcr(struct gralloc_module_t const* module,
|
|||
return CROS_GRALLOC_ERROR_BAD_HANDLE;
|
||||
}
|
||||
|
||||
if ((hnd->format != HAL_PIXEL_FORMAT_YCbCr_420_888)) {
|
||||
if ((hnd->droid_format != HAL_PIXEL_FORMAT_YCbCr_420_888)) {
|
||||
cros_gralloc_error("Non-YUV format not compatible.");
|
||||
return CROS_GRALLOC_ERROR_BAD_HANDLE;
|
||||
}
|
||||
|
|
@ -305,7 +319,7 @@ static int cros_gralloc_lock_ycbcr(struct gralloc_module_t const* module,
|
|||
for (size_t p = 0; p < drv_bo_get_num_planes(bo->bo); p++)
|
||||
offsets[p] = drv_bo_get_plane_offset(bo->bo, p);
|
||||
|
||||
switch (hnd->data.format) {
|
||||
switch (hnd->format) {
|
||||
case DRM_FORMAT_NV12:
|
||||
ycbcr->y = addr;
|
||||
ycbcr->cb = addr + offsets[1];
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue