backend/native: Share drmModeAddFB code

With all the three paths this is quite a handful of code, and it was mostly
duplicated in two places. A follow-up patch would need to introduce a third
copy of it. Therefore move the code into a helper function.

There are two behavioral changes:

- The format error now prints the string code as well, because it is easy to
  read.

- The g_debug() in init_dumb_fb() is removed. Did not seem useful.

https://gitlab.gnome.org/GNOME/mutter/merge_requests/810
This commit is contained in:
Pekka Paalanen 2019-09-25 17:03:59 +03:00 committed by Jonas Ådahl
parent f409dddb54
commit 03ac7b1821
4 changed files with 119 additions and 116 deletions

View File

@ -57,16 +57,8 @@ acquire_swapped_buffer (MetaDrmBufferGbm *buffer_gbm,
gboolean use_modifiers,
GError **error)
{
uint32_t handles[4] = {0, 0, 0, 0};
uint32_t strides[4] = {0, 0, 0, 0};
uint32_t offsets[4] = {0, 0, 0, 0};
uint64_t modifiers[4] = {0, 0, 0, 0};
uint32_t width, height;
uint32_t format;
MetaGpuKmsFBArgs fb_args = { 0, };
struct gbm_bo *bo;
int kms_fd;
kms_fd = meta_gpu_kms_get_fd (buffer_gbm->gpu_kms);
bo = gbm_surface_lock_front_buffer (buffer_gbm->surface);
if (!bo)
@ -81,10 +73,10 @@ acquire_swapped_buffer (MetaDrmBufferGbm *buffer_gbm,
if (gbm_bo_get_handle_for_plane (bo, 0).s32 == -1)
{
/* Failed to fetch handle to plane, falling back to old method */
strides[0] = gbm_bo_get_stride (bo);
handles[0] = gbm_bo_get_handle (bo).u32;
offsets[0] = 0;
modifiers[0] = DRM_FORMAT_MOD_INVALID;
fb_args.strides[0] = gbm_bo_get_stride (bo);
fb_args.handles[0] = gbm_bo_get_handle (bo).u32;
fb_args.offsets[0] = 0;
fb_args.modifiers[0] = DRM_FORMAT_MOD_INVALID;
}
else
{
@ -92,77 +84,25 @@ acquire_swapped_buffer (MetaDrmBufferGbm *buffer_gbm,
for (i = 0; i < gbm_bo_get_plane_count (bo); i++)
{
strides[i] = gbm_bo_get_stride_for_plane (bo, i);
handles[i] = gbm_bo_get_handle_for_plane (bo, i).u32;
offsets[i] = gbm_bo_get_offset (bo, i);
modifiers[i] = gbm_bo_get_modifier (bo);
fb_args.strides[i] = gbm_bo_get_stride_for_plane (bo, i);
fb_args.handles[i] = gbm_bo_get_handle_for_plane (bo, i).u32;
fb_args.offsets[i] = gbm_bo_get_offset (bo, i);
fb_args.modifiers[i] = gbm_bo_get_modifier (bo);
}
}
width = gbm_bo_get_width (bo);
height = gbm_bo_get_height (bo);
format = gbm_bo_get_format (bo);
fb_args.width = gbm_bo_get_width (bo);
fb_args.height = gbm_bo_get_height (bo);
fb_args.format = gbm_bo_get_format (bo);
if (use_modifiers && modifiers[0] != DRM_FORMAT_MOD_INVALID)
if (!meta_gpu_kms_add_fb (buffer_gbm->gpu_kms,
use_modifiers,
&fb_args,
&buffer_gbm->fb_id, error))
{
if (drmModeAddFB2WithModifiers (kms_fd,
width, height,
format,
handles,
strides,
offsets,
modifiers,
&buffer_gbm->fb_id,
DRM_MODE_FB_MODIFIERS))
{
g_set_error (error,
G_IO_ERROR,
g_io_error_from_errno (errno),
"drmModeAddFB2WithModifiers failed: %s",
g_strerror (errno));
gbm_surface_release_buffer (buffer_gbm->surface, bo);
return FALSE;
}
}
else if (drmModeAddFB2 (kms_fd,
width,
height,
format,
handles,
strides,
offsets,
&buffer_gbm->fb_id,
0))
{
if (format != DRM_FORMAT_XRGB8888)
{
g_set_error (error,
G_IO_ERROR,
G_IO_ERROR_FAILED,
"drmModeAddFB does not support format 0x%x",
format);
gbm_surface_release_buffer (buffer_gbm->surface, bo);
return FALSE;
}
if (drmModeAddFB (kms_fd,
width,
height,
24,
32,
strides[0],
handles[0],
&buffer_gbm->fb_id))
{
g_set_error (error,
G_IO_ERROR,
g_io_error_from_errno (errno),
"drmModeAddFB failed: %s",
g_strerror (errno));
gbm_surface_release_buffer (buffer_gbm->surface, bo);
return FALSE;
}
}
buffer_gbm->bo = bo;

View File

@ -25,6 +25,7 @@
#include "backends/native/meta-gpu-kms.h"
#include <drm.h>
#include <drm_fourcc.h>
#include <errno.h>
#include <poll.h>
#include <string.h>
@ -63,6 +64,80 @@ struct _MetaGpuKms
G_DEFINE_TYPE (MetaGpuKms, meta_gpu_kms, META_TYPE_GPU)
gboolean
meta_gpu_kms_add_fb (MetaGpuKms *gpu_kms,
gboolean use_modifiers,
const MetaGpuKmsFBArgs *args,
uint32_t *fb_id_out,
GError **error)
{
MetaDrmFormatBuf tmp;
uint32_t fb_id;
if (use_modifiers && args->modifiers[0] != DRM_FORMAT_MOD_INVALID)
{
if (drmModeAddFB2WithModifiers (gpu_kms->fd,
args->width,
args->height,
args->format,
args->handles,
args->strides,
args->offsets,
args->modifiers,
&fb_id,
DRM_MODE_FB_MODIFIERS))
{
g_set_error (error,
G_IO_ERROR,
g_io_error_from_errno (errno),
"drmModeAddFB2WithModifiers failed: %s",
g_strerror (errno));
return FALSE;
}
}
else if (drmModeAddFB2 (gpu_kms->fd,
args->width,
args->height,
args->format,
args->handles,
args->strides,
args->offsets,
&fb_id,
0))
{
if (args->format != DRM_FORMAT_XRGB8888)
{
g_set_error (error,
G_IO_ERROR,
G_IO_ERROR_FAILED,
"drmModeAddFB does not support format '%s' (0x%x)",
meta_drm_format_to_string (&tmp, args->format),
args->format);
return FALSE;
}
if (drmModeAddFB (gpu_kms->fd,
args->width,
args->height,
24,
32,
args->strides[0],
args->handles[0],
&fb_id))
{
g_set_error (error,
G_IO_ERROR,
g_io_error_from_errno (errno),
"drmModeAddFB failed: %s",
g_strerror (errno));
return FALSE;
}
}
*fb_id_out = fb_id;
return TRUE;
}
gboolean
meta_gpu_kms_is_crtc_active (MetaGpuKms *gpu_kms,
MetaCrtc *crtc)

View File

@ -77,4 +77,21 @@ MetaGpuKmsFlipClosureContainer * meta_gpu_kms_wrap_flip_closure (MetaGpuKms *gpu
void meta_gpu_kms_flip_closure_container_free (MetaGpuKmsFlipClosureContainer *closure_container);
typedef struct _MetaGpuKmsFBArgs
{
uint32_t width;
uint32_t height;
uint32_t format;
uint32_t handles[4];
uint32_t offsets[4];
uint32_t strides[4];
uint64_t modifiers[4];
} MetaGpuKmsFBArgs;
gboolean meta_gpu_kms_add_fb (MetaGpuKms *gpu_kms,
gboolean use_modifiers,
const MetaGpuKmsFBArgs *args,
uint32_t *fb_id_out,
GError **error);
#endif /* META_GPU_KMS_H */

View File

@ -2534,9 +2534,11 @@ init_dumb_fb (MetaDumbBuffer *dumb_fb,
uint32_t fb_id = 0;
void *map;
int kms_fd;
uint32_t handles[4] = { 0, };
uint32_t pitches[4] = { 0, };
uint32_t offsets[4] = { 0, };
MetaGpuKmsFBArgs fb_args = {
.width = width,
.height = height,
.format = format,
};
kms_fd = meta_gpu_kms_get_fd (gpu_kms);
@ -2554,42 +2556,11 @@ init_dumb_fb (MetaDumbBuffer *dumb_fb,
goto err_ioctl;
}
handles[0] = create_arg.handle;
pitches[0] = create_arg.pitch;
fb_args.handles[0] = create_arg.handle;
fb_args.strides[0] = create_arg.pitch;
if (drmModeAddFB2 (kms_fd, width, height, format,
handles, pitches, offsets,
&fb_id, 0) != 0)
{
g_debug ("drmModeAddFB2 failed (%s), falling back to drmModeAddFB",
g_strerror (errno));
}
if (fb_id == 0)
{
if (format != DRM_FORMAT_XRGB8888)
{
g_set_error (error, G_IO_ERROR,
G_IO_ERROR_FAILED,
"drmModeAddFB does not support format 0x%x",
format);
if (!meta_gpu_kms_add_fb (gpu_kms, FALSE, &fb_args, &fb_id, error))
goto err_add_fb;
}
if (drmModeAddFB (kms_fd, width, height,
24 /* depth of RGBX8888 */,
32 /* bpp of RGBX8888 */,
create_arg.pitch,
create_arg.handle,
&fb_id) != 0)
{
g_set_error (error, G_IO_ERROR,
G_IO_ERROR_FAILED,
"drmModeAddFB failed: %s",
g_strerror (errno));
goto err_add_fb;
}
}
map_arg = (struct drm_mode_map_dumb) {
.handle = create_arg.handle