int width, int height, int depth)
{
struct loader_dri3_buffer *buffer;
- __DRIimage *pixmap_buffer;
+ __DRIimage *pixmap_buffer = NULL, *linear_buffer_display_gpu = NULL;
xcb_pixmap_t pixmap;
xcb_sync_fence_t sync_fence;
struct xshmfence *shm_fence;
if (!buffer->image)
goto no_image;
- buffer->linear_buffer =
- draw->ext->image->createImage(draw->dri_screen,
- width, height,
- dri3_linear_format_for_format(draw, format),
- __DRI_IMAGE_USE_SHARE |
- __DRI_IMAGE_USE_LINEAR |
- __DRI_IMAGE_USE_BACKBUFFER,
- buffer);
- pixmap_buffer = buffer->linear_buffer;
+ /* if driver name is same only then dri_screen_display_gpu is set.
+ * This check is needed because for simplicity render gpu image extension
+ * is also used for display gpu.
+ */
+ if (draw->dri_screen_display_gpu) {
+ linear_buffer_display_gpu =
+ draw->ext->image->createImage(draw->dri_screen_display_gpu,
+ width, height,
+ dri3_linear_format_for_format(draw, format),
+ __DRI_IMAGE_USE_SHARE |
+ __DRI_IMAGE_USE_LINEAR |
+ __DRI_IMAGE_USE_BACKBUFFER,
+ buffer);
+ pixmap_buffer = linear_buffer_display_gpu;
+ }
- if (!buffer->linear_buffer)
- goto no_linear_buffer;
+ if (!pixmap_buffer) {
+ buffer->linear_buffer =
+ draw->ext->image->createImage(draw->dri_screen,
+ width, height,
+ dri3_linear_format_for_format(draw, format),
+ __DRI_IMAGE_USE_SHARE |
+ __DRI_IMAGE_USE_LINEAR |
+ __DRI_IMAGE_USE_BACKBUFFER,
+ buffer);
+
+ pixmap_buffer = buffer->linear_buffer;
+ if (!buffer->linear_buffer) {
+ goto no_linear_buffer;
+ }
+ }
}
/* X want some information about the planes, so ask the image for it
if (!ret)
buffer->modifier = DRM_FORMAT_MOD_INVALID;
+ if (draw->is_different_gpu && draw->dri_screen_display_gpu &&
+ linear_buffer_display_gpu) {
+ /* The linear buffer was created in the display GPU's vram, so we
+ * need to make it visible to render GPU
+ */
+ buffer->linear_buffer =
+ draw->ext->image->createImageFromFds(draw->dri_screen,
+ width,
+ height,
+ image_format_to_fourcc(format),
+ &buffer_fds[0], num_planes,
+ &buffer->strides[0],
+ &buffer->offsets[0],
+ buffer);
+ if (!buffer->linear_buffer)
+ goto no_buffer_attrib;
+
+ draw->ext->image->destroyImage(linear_buffer_display_gpu);
+ }
+
pixmap = xcb_generate_id(draw->conn);
#ifdef HAVE_DRI3_MODIFIERS
if (draw->multiplanes_available &&
struct loader_dri3_buffer {
__DRIimage *image;
- __DRIimage *linear_buffer;
uint32_t pixmap;
+ /* default case: linear buffer allocated in render gpu vram.
+ * p2p case: linear buffer allocated in display gpu vram and imported
+ * to render gpu. p2p case is enabled when driver name matches
+ * while creating screen in dri3_create_screen() function.
+ */
+ __DRIimage *linear_buffer;
+
/* Synchronization between the client and X server is done using an
* xshmfence that is mapped into an X server SyncFence. This lets the
* client check whether the X server is done using a buffer with a simple