mirror of
https://github.com/X11Libre/xserver.git
synced 2026-10-26 01:59:57 +00:00
[PR #3877] glamor/glamor_egl: Add a fallback path to glamor_gbm_bo_from_pixmap_internal
nvidia's gbm backend has issues dealing with importing a gbm bo directly from an EGLImage This exports the image as dmabufs and imports a bo from dmabufs This is needed for DRI3 export on nvidia Fixes: https://gitlab.freedesktop.org/mesa/mesa/-/work_items/14047 v2: Don't pass usage flags Reviewed-by: James Jones <jajones@nvidia.com> Signed-off-by: stefan11111 <stefan11111github@gmail.com> Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2321> (cherry picked from commitb522485155) (cherry picked from commit9f36f7bd50) PR: https://github.com/X11Libre/xserver/pull/3877 (cherry picked from commit74b69ba1b3) (cherry picked from commit d5f91a42c49e0a251c91f0cbe214a964805d61aa)
This commit is contained in:
parent
c0e0e3568c
commit
3715cb527e
1 changed files with 139 additions and 195 deletions
|
|
@ -26,7 +26,8 @@
|
|||
* Zhigang Gong <zhigang.gong@linux.intel.com>
|
||||
*
|
||||
*/
|
||||
#include <dix-config.h>
|
||||
|
||||
#include "dix-config.h"
|
||||
|
||||
#define GLAMOR_FOR_XORG
|
||||
#include <unistd.h>
|
||||
|
|
@ -41,11 +42,10 @@
|
|||
#include <gbm.h>
|
||||
#include <drm_fourcc.h>
|
||||
|
||||
#include "dix/screen_hooks_priv.h"
|
||||
#include "glamor/glamor_priv.h"
|
||||
#include "os/bug_priv.h"
|
||||
|
||||
#include "glamor_egl.h"
|
||||
|
||||
#include "glamor.h"
|
||||
#include "glamor_priv.h"
|
||||
#include "glamor_glx_provider.h"
|
||||
#include "dri3.h"
|
||||
|
||||
|
|
@ -53,12 +53,19 @@ struct glamor_egl_screen_private {
|
|||
EGLDisplay display;
|
||||
EGLContext context;
|
||||
char *device_path;
|
||||
|
||||
CreateScreenResourcesProcPtr CreateScreenResources;
|
||||
CloseScreenProcPtr CloseScreen;
|
||||
#ifdef EGL_MESA_image_dma_buf_export
|
||||
int has_image_dma_buf_export;
|
||||
#endif
|
||||
int fd;
|
||||
struct gbm_device *gbm;
|
||||
int dmabuf_capable;
|
||||
char *glvnd_vendor; /* GLVND vendor if forced from options or NULL otherwise */
|
||||
|
||||
struct gbm_device *gbm;
|
||||
int fd;
|
||||
int dmabuf_capable;
|
||||
|
||||
CloseScreenProcPtr saved_close_screen;
|
||||
DestroyPixmapProcPtr saved_destroy_pixmap;
|
||||
xf86FreeScreenProc *saved_free_screen;
|
||||
};
|
||||
|
||||
|
|
@ -141,6 +148,22 @@ glamor_egl_get_gbm_device(ScreenPtr screen)
|
|||
return glamor_egl->gbm;
|
||||
}
|
||||
|
||||
Bool
|
||||
glamor_egl_create_textured_screen(ScreenPtr screen, int handle, int stride)
|
||||
{
|
||||
ScrnInfoPtr scrn = xf86ScreenToScrn(screen);
|
||||
PixmapPtr screen_pixmap;
|
||||
|
||||
screen_pixmap = screen->GetScreenPixmap(screen);
|
||||
|
||||
if (!glamor_egl_create_textured_pixmap(screen_pixmap, handle, stride)) {
|
||||
xf86DrvMsg(scrn->scrnIndex, X_ERROR,
|
||||
"Failed to create textured screen.");
|
||||
return FALSE;
|
||||
}
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static void
|
||||
glamor_egl_set_pixmap_image(PixmapPtr pixmap, EGLImageKHR image,
|
||||
Bool used_modifiers)
|
||||
|
|
@ -149,8 +172,6 @@ glamor_egl_set_pixmap_image(PixmapPtr pixmap, EGLImageKHR image,
|
|||
glamor_get_pixmap_private(pixmap);
|
||||
EGLImageKHR old;
|
||||
|
||||
BUG_RETURN(!pixmap_priv);
|
||||
|
||||
old = pixmap_priv->image;
|
||||
if (old) {
|
||||
ScreenPtr screen = pixmap->drawable.pScreen;
|
||||
|
|
@ -213,106 +234,12 @@ glamor_egl_create_textured_pixmap_from_gbm_bo(PixmapPtr pixmap,
|
|||
Bool ret = FALSE;
|
||||
|
||||
glamor_egl = glamor_egl_get_screen_private(scrn);
|
||||
#ifdef GBM_BO_FD_FOR_PLANE
|
||||
uint64_t modifier = gbm_bo_get_modifier(bo);
|
||||
const int num_planes = gbm_bo_get_plane_count(bo);
|
||||
int fds[GBM_MAX_PLANES];
|
||||
int plane;
|
||||
int attr_num = 0;
|
||||
EGLint img_attrs[64] = {0};
|
||||
enum PlaneAttrs {
|
||||
PLANE_FD,
|
||||
PLANE_OFFSET,
|
||||
PLANE_PITCH,
|
||||
PLANE_MODIFIER_LO,
|
||||
PLANE_MODIFIER_HI,
|
||||
NUM_PLANE_ATTRS
|
||||
};
|
||||
static const EGLint planeAttrs[][NUM_PLANE_ATTRS] = {
|
||||
{
|
||||
EGL_DMA_BUF_PLANE0_FD_EXT,
|
||||
EGL_DMA_BUF_PLANE0_OFFSET_EXT,
|
||||
EGL_DMA_BUF_PLANE0_PITCH_EXT,
|
||||
EGL_DMA_BUF_PLANE0_MODIFIER_LO_EXT,
|
||||
EGL_DMA_BUF_PLANE0_MODIFIER_HI_EXT,
|
||||
},
|
||||
{
|
||||
EGL_DMA_BUF_PLANE1_FD_EXT,
|
||||
EGL_DMA_BUF_PLANE1_OFFSET_EXT,
|
||||
EGL_DMA_BUF_PLANE1_PITCH_EXT,
|
||||
EGL_DMA_BUF_PLANE1_MODIFIER_LO_EXT,
|
||||
EGL_DMA_BUF_PLANE1_MODIFIER_HI_EXT,
|
||||
},
|
||||
{
|
||||
EGL_DMA_BUF_PLANE2_FD_EXT,
|
||||
EGL_DMA_BUF_PLANE2_OFFSET_EXT,
|
||||
EGL_DMA_BUF_PLANE2_PITCH_EXT,
|
||||
EGL_DMA_BUF_PLANE2_MODIFIER_LO_EXT,
|
||||
EGL_DMA_BUF_PLANE2_MODIFIER_HI_EXT,
|
||||
},
|
||||
{
|
||||
EGL_DMA_BUF_PLANE3_FD_EXT,
|
||||
EGL_DMA_BUF_PLANE3_OFFSET_EXT,
|
||||
EGL_DMA_BUF_PLANE3_PITCH_EXT,
|
||||
EGL_DMA_BUF_PLANE3_MODIFIER_LO_EXT,
|
||||
EGL_DMA_BUF_PLANE3_MODIFIER_HI_EXT,
|
||||
},
|
||||
};
|
||||
|
||||
for (plane = 0; plane < num_planes; plane++) fds[plane] = -1;
|
||||
#endif
|
||||
|
||||
glamor_make_current(glamor_priv);
|
||||
|
||||
#ifdef GBM_BO_FD_FOR_PLANE
|
||||
if (glamor_egl->dmabuf_capable) {
|
||||
#define ADD_ATTR(attrs, num, attr) \
|
||||
do { \
|
||||
assert(((num) + 1) < (sizeof(attrs) / sizeof((attrs)[0]))); \
|
||||
(attrs)[(num)++] = (attr); \
|
||||
} while (0)
|
||||
ADD_ATTR(img_attrs, attr_num, EGL_WIDTH);
|
||||
ADD_ATTR(img_attrs, attr_num, gbm_bo_get_width(bo));
|
||||
ADD_ATTR(img_attrs, attr_num, EGL_HEIGHT);
|
||||
ADD_ATTR(img_attrs, attr_num, gbm_bo_get_height(bo));
|
||||
ADD_ATTR(img_attrs, attr_num, EGL_LINUX_DRM_FOURCC_EXT);
|
||||
ADD_ATTR(img_attrs, attr_num, gbm_bo_get_format(bo));
|
||||
|
||||
for (plane = 0; plane < num_planes; plane++) {
|
||||
fds[plane] = gbm_bo_get_fd_for_plane(bo, plane);
|
||||
ADD_ATTR(img_attrs, attr_num, planeAttrs[plane][PLANE_FD]);
|
||||
ADD_ATTR(img_attrs, attr_num, fds[plane]);
|
||||
ADD_ATTR(img_attrs, attr_num, planeAttrs[plane][PLANE_OFFSET]);
|
||||
ADD_ATTR(img_attrs, attr_num, gbm_bo_get_offset(bo, plane));
|
||||
ADD_ATTR(img_attrs, attr_num, planeAttrs[plane][PLANE_PITCH]);
|
||||
ADD_ATTR(img_attrs, attr_num, gbm_bo_get_stride_for_plane(bo, plane));
|
||||
ADD_ATTR(img_attrs, attr_num, planeAttrs[plane][PLANE_MODIFIER_LO]);
|
||||
ADD_ATTR(img_attrs, attr_num, (uint32_t)(modifier & 0xFFFFFFFFULL));
|
||||
ADD_ATTR(img_attrs, attr_num, planeAttrs[plane][PLANE_MODIFIER_HI]);
|
||||
ADD_ATTR(img_attrs, attr_num, (uint32_t)(modifier >> 32ULL));
|
||||
}
|
||||
ADD_ATTR(img_attrs, attr_num, EGL_NONE);
|
||||
#undef ADD_ATTR
|
||||
|
||||
image = eglCreateImageKHR(glamor_egl->display,
|
||||
EGL_NO_CONTEXT,
|
||||
EGL_LINUX_DMA_BUF_EXT,
|
||||
NULL,
|
||||
img_attrs);
|
||||
|
||||
for (plane = 0; plane < num_planes; plane++) {
|
||||
close(fds[plane]);
|
||||
fds[plane] = -1;
|
||||
}
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
image = eglCreateImageKHR(glamor_egl->display,
|
||||
EGL_NO_CONTEXT,
|
||||
EGL_NATIVE_PIXMAP_KHR, bo, NULL);
|
||||
}
|
||||
|
||||
image = eglCreateImageKHR(glamor_egl->display,
|
||||
EGL_NO_CONTEXT,
|
||||
EGL_NATIVE_PIXMAP_KHR, bo, NULL);
|
||||
if (image == EGL_NO_IMAGE_KHR) {
|
||||
glamor_set_pixmap_type(pixmap, GLAMOR_DRM_ONLY);
|
||||
goto done;
|
||||
|
|
@ -354,8 +281,6 @@ glamor_make_pixmap_exportable(PixmapPtr pixmap, Bool modifiers_ok)
|
|||
PixmapPtr exported;
|
||||
GCPtr scratch_gc;
|
||||
|
||||
BUG_RETURN_VAL(!pixmap_priv, FALSE);
|
||||
|
||||
if (pixmap_priv->image &&
|
||||
(modifiers_ok || !pixmap_priv->used_modifiers))
|
||||
return TRUE;
|
||||
|
|
@ -391,30 +316,8 @@ glamor_make_pixmap_exportable(PixmapPtr pixmap, Bool modifiers_ok)
|
|||
|
||||
glamor_get_modifiers(screen, format, &num_modifiers, &modifiers);
|
||||
|
||||
if (num_modifiers > 0) {
|
||||
#ifdef GBM_BO_WITH_MODIFIERS2
|
||||
/* TODO: Is scanout ever used? If so, where? */
|
||||
bo = gbm_bo_create_with_modifiers2(glamor_egl->gbm, width, height,
|
||||
format, modifiers, num_modifiers,
|
||||
GBM_BO_USE_RENDERING | GBM_BO_USE_SCANOUT);
|
||||
if (!bo) {
|
||||
/* something failed, try again without GBM_BO_USE_SCANOUT */
|
||||
/* maybe scanout does work, but modifiers aren't supported */
|
||||
/* we handle this case on the fallback path */
|
||||
bo = gbm_bo_create_with_modifiers2(glamor_egl->gbm, width, height,
|
||||
format, modifiers, num_modifiers,
|
||||
GBM_BO_USE_RENDERING);
|
||||
#if 0
|
||||
if (bo) {
|
||||
/* TODO: scanout failed, but regular buffer succeeded, maybe log something? */
|
||||
}
|
||||
#endif
|
||||
}
|
||||
#else
|
||||
bo = gbm_bo_create_with_modifiers(glamor_egl->gbm, width, height,
|
||||
format, modifiers, num_modifiers);
|
||||
#endif
|
||||
}
|
||||
bo = gbm_bo_create_with_modifiers(glamor_egl->gbm, width, height,
|
||||
format, modifiers, num_modifiers);
|
||||
if (bo)
|
||||
used_modifiers = TRUE;
|
||||
free(modifiers);
|
||||
|
|
@ -423,27 +326,12 @@ glamor_make_pixmap_exportable(PixmapPtr pixmap, Bool modifiers_ok)
|
|||
|
||||
if (!bo)
|
||||
{
|
||||
/* TODO: Is scanout ever used? If so, where? */
|
||||
bo = gbm_bo_create(glamor_egl->gbm, width, height, format,
|
||||
#ifdef GLAMOR_HAS_GBM_LINEAR
|
||||
(pixmap->usage_hint == CREATE_PIXMAP_USAGE_SHARED ?
|
||||
GBM_BO_USE_LINEAR : 0) |
|
||||
#endif
|
||||
GBM_BO_USE_RENDERING | GBM_BO_USE_SCANOUT);
|
||||
if (!bo) {
|
||||
/* something failed, try again without GBM_BO_USE_SCANOUT */
|
||||
bo = gbm_bo_create(glamor_egl->gbm, width, height, format,
|
||||
#ifdef GLAMOR_HAS_GBM_LINEAR
|
||||
(pixmap->usage_hint == CREATE_PIXMAP_USAGE_SHARED ?
|
||||
GBM_BO_USE_LINEAR : 0) |
|
||||
GBM_BO_USE_RENDERING);
|
||||
#endif
|
||||
#if 0
|
||||
if (bo) {
|
||||
/* TODO: scanout failed, but regular buffer succeeded, maybe log something? */
|
||||
}
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
if (!bo) {
|
||||
|
|
@ -461,7 +349,7 @@ glamor_make_pixmap_exportable(PixmapPtr pixmap, Bool modifiers_ok)
|
|||
xf86DrvMsg(scrn->scrnIndex, X_ERROR,
|
||||
"Failed to make %dx%dx%dbpp pixmap from GBM bo\n",
|
||||
width, height, pixmap->drawable.bitsPerPixel);
|
||||
dixDestroyPixmap(exported, 0);
|
||||
screen->DestroyPixmap(exported);
|
||||
gbm_bo_destroy(bo);
|
||||
return FALSE;
|
||||
}
|
||||
|
|
@ -482,7 +370,7 @@ glamor_make_pixmap_exportable(PixmapPtr pixmap, Bool modifiers_ok)
|
|||
/* Swap the devKind into the original pixmap, reflecting the bo's stride */
|
||||
screen->ModifyPixmapHeader(pixmap, 0, 0, 0, 0, exported->devKind, NULL);
|
||||
|
||||
dixDestroyPixmap(exported, 0);
|
||||
screen->DestroyPixmap(exported);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
|
@ -494,14 +382,58 @@ glamor_gbm_bo_from_pixmap_internal(ScreenPtr screen, PixmapPtr pixmap)
|
|||
glamor_egl_get_screen_private(xf86ScreenToScrn(screen));
|
||||
struct glamor_pixmap_private *pixmap_priv =
|
||||
glamor_get_pixmap_private(pixmap);
|
||||
|
||||
BUG_RETURN_VAL(!pixmap_priv, NULL);
|
||||
struct gbm_bo* ret = NULL;
|
||||
#ifdef EGL_MESA_image_dma_buf_export
|
||||
int fourcc = 0;
|
||||
int num_planes = 0;
|
||||
struct gbm_import_fd_modifier_data fd_modifier_data;
|
||||
EGLuint64KHR modifiers[GBM_MAX_PLANES] = {0};
|
||||
#endif
|
||||
|
||||
if (!pixmap_priv->image)
|
||||
return NULL;
|
||||
|
||||
return gbm_bo_import(glamor_egl->gbm, GBM_BO_IMPORT_EGL_IMAGE,
|
||||
pixmap_priv->image, GBM_BO_USE_RENDERING);
|
||||
ret = gbm_bo_import(glamor_egl->gbm, GBM_BO_IMPORT_EGL_IMAGE,
|
||||
pixmap_priv->image, 0);
|
||||
|
||||
#ifdef EGL_MESA_image_dma_buf_export
|
||||
if (ret || !glamor_egl->has_image_dma_buf_export) {
|
||||
return ret;
|
||||
}
|
||||
|
||||
#ifndef GBM_MAX_PLANES
|
||||
#define GBM_MAX_PLANES 4
|
||||
#endif
|
||||
|
||||
if (!eglExportDMABUFImageQueryMESA(glamor_egl->display, pixmap_priv->image, &fourcc, &num_planes, modifiers) || (num_planes > GBM_MAX_PLANES)) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
fd_modifier_data = (struct gbm_import_fd_modifier_data) {
|
||||
.width = pixmap->drawable.width,
|
||||
.height = pixmap->drawable.height,
|
||||
.format = fourcc, /* GBM and DRM formats are the same */
|
||||
.num_fds = num_planes,
|
||||
.modifier = modifiers[0],
|
||||
.fds = {-1, -1, -1, -1},
|
||||
.strides = {0},
|
||||
.offsets = {0},
|
||||
};
|
||||
|
||||
if (eglExportDMABUFImageMESA(glamor_egl->display, pixmap_priv->image,
|
||||
fd_modifier_data.fds,
|
||||
fd_modifier_data.strides,
|
||||
fd_modifier_data.offsets)) {
|
||||
ret = gbm_bo_import(glamor_egl->gbm, GBM_BO_IMPORT_FD_MODIFIER,
|
||||
&fd_modifier_data, 0);
|
||||
}
|
||||
for (int i = 0; i < num_planes; i++) {
|
||||
if (fd_modifier_data.fds[i] >= 0) {
|
||||
close(fd_modifier_data.fds[i]);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
return ret;
|
||||
}
|
||||
|
||||
struct gbm_bo *
|
||||
|
|
@ -518,7 +450,7 @@ glamor_egl_fds_from_pixmap(ScreenPtr screen, PixmapPtr pixmap, int *fds,
|
|||
uint32_t *strides, uint32_t *offsets,
|
||||
uint64_t *modifier)
|
||||
{
|
||||
#ifdef GLAMOR_HAS_GBM
|
||||
#ifdef HAVE_GBM
|
||||
struct gbm_bo *bo;
|
||||
int num_fds;
|
||||
#ifdef GBM_BO_WITH_MODIFIERS
|
||||
|
|
@ -586,7 +518,7 @@ int
|
|||
glamor_egl_fd_from_pixmap(ScreenPtr screen, PixmapPtr pixmap,
|
||||
CARD16 *stride, CARD32 *size)
|
||||
{
|
||||
#ifdef GLAMOR_HAS_GBM
|
||||
#ifdef HAVE_GBM
|
||||
struct gbm_bo *bo;
|
||||
int fd;
|
||||
|
||||
|
|
@ -686,8 +618,7 @@ glamor_back_pixmap_from_fd(PixmapPtr pixmap,
|
|||
import_data.width = width;
|
||||
import_data.height = height;
|
||||
import_data.stride = stride;
|
||||
bo = gbm_bo_import(glamor_egl->gbm, GBM_BO_IMPORT_FD, &import_data,
|
||||
GBM_BO_USE_RENDERING);
|
||||
bo = gbm_bo_import(glamor_egl->gbm, GBM_BO_IMPORT_FD, &import_data, 0);
|
||||
if (!bo)
|
||||
return FALSE;
|
||||
|
||||
|
|
@ -733,8 +664,7 @@ glamor_pixmap_from_fds(ScreenPtr screen,
|
|||
import_data.strides[i] = strides[i];
|
||||
import_data.offsets[i] = offsets[i];
|
||||
}
|
||||
bo = gbm_bo_import(glamor_egl->gbm, GBM_BO_IMPORT_FD_MODIFIER, &import_data,
|
||||
GBM_BO_USE_RENDERING);
|
||||
bo = gbm_bo_import(glamor_egl->gbm, GBM_BO_IMPORT_FD_MODIFIER, &import_data, 0);
|
||||
if (bo) {
|
||||
screen->ModifyPixmapHeader(pixmap, width, height, 0, 0, strides[0], NULL);
|
||||
ret = glamor_egl_create_textured_pixmap_from_gbm_bo(pixmap, bo, TRUE);
|
||||
|
|
@ -751,7 +681,7 @@ glamor_pixmap_from_fds(ScreenPtr screen,
|
|||
|
||||
error:
|
||||
if (ret == FALSE) {
|
||||
dixDestroyPixmap(pixmap, 0);
|
||||
screen->DestroyPixmap(pixmap);
|
||||
return NULL;
|
||||
}
|
||||
return pixmap;
|
||||
|
|
@ -773,7 +703,7 @@ glamor_pixmap_from_fd(ScreenPtr screen,
|
|||
stride, depth, bpp);
|
||||
|
||||
if (ret == FALSE) {
|
||||
dixDestroyPixmap(pixmap, 0);
|
||||
screen->DestroyPixmap(pixmap);
|
||||
return NULL;
|
||||
}
|
||||
return pixmap;
|
||||
|
|
@ -786,12 +716,10 @@ glamor_get_formats(ScreenPtr screen,
|
|||
#ifdef GLAMOR_HAS_EGL_QUERY_DMABUF
|
||||
struct glamor_egl_screen_private *glamor_egl;
|
||||
EGLint num;
|
||||
#endif
|
||||
|
||||
/* Explicitly zero the count and formats as the caller may ignore the return value */
|
||||
/* Explicitly zero the count as the caller may ignore the return value */
|
||||
*num_formats = 0;
|
||||
*formats = NULL;
|
||||
#ifdef GLAMOR_HAS_EGL_QUERY_DMABUF
|
||||
|
||||
glamor_egl = glamor_egl_get_screen_private(xf86ScreenToScrn(screen));
|
||||
|
||||
if (!glamor_egl->dmabuf_capable)
|
||||
|
|
@ -810,13 +738,15 @@ glamor_get_formats(ScreenPtr screen,
|
|||
if (!eglQueryDmaBufFormatsEXT(glamor_egl->display, num,
|
||||
(EGLint *) *formats, &num)) {
|
||||
free(*formats);
|
||||
*formats = NULL;
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
*num_formats = num;
|
||||
#endif
|
||||
return TRUE;
|
||||
#else
|
||||
*num_formats = 0;
|
||||
return TRUE;
|
||||
#endif
|
||||
}
|
||||
|
||||
Bool
|
||||
|
|
@ -826,12 +756,10 @@ glamor_get_modifiers(ScreenPtr screen, uint32_t format,
|
|||
#ifdef GLAMOR_HAS_EGL_QUERY_DMABUF
|
||||
struct glamor_egl_screen_private *glamor_egl;
|
||||
EGLint num;
|
||||
#endif
|
||||
|
||||
/* Explicitly zero the count and modifiers as the caller may ignore the return value */
|
||||
/* Explicitly zero the count as the caller may ignore the return value */
|
||||
*num_modifiers = 0;
|
||||
*modifiers = NULL;
|
||||
#ifdef GLAMOR_HAS_EGL_QUERY_DMABUF
|
||||
|
||||
glamor_egl = glamor_egl_get_screen_private(xf86ScreenToScrn(screen));
|
||||
|
||||
if (!glamor_egl->dmabuf_capable)
|
||||
|
|
@ -856,8 +784,11 @@ glamor_get_modifiers(ScreenPtr screen, uint32_t format,
|
|||
}
|
||||
|
||||
*num_modifiers = num;
|
||||
#endif
|
||||
return TRUE;
|
||||
#else
|
||||
*num_modifiers = 0;
|
||||
return TRUE;
|
||||
#endif
|
||||
}
|
||||
|
||||
const char *
|
||||
|
|
@ -875,20 +806,30 @@ glamor_egl_get_driver_name(ScreenPtr screen)
|
|||
return NULL;
|
||||
}
|
||||
|
||||
static void glamor_egl_pixmap_destroy(CallbackListPtr *pcbl, ScreenPtr pScreen, PixmapPtr pixmap)
|
||||
|
||||
static Bool
|
||||
glamor_egl_destroy_pixmap(PixmapPtr pixmap)
|
||||
{
|
||||
ScreenPtr screen = pixmap->drawable.pScreen;
|
||||
ScrnInfoPtr scrn = xf86ScreenToScrn(screen);
|
||||
struct glamor_egl_screen_private *glamor_egl =
|
||||
glamor_egl_get_screen_private(scrn);
|
||||
Bool ret;
|
||||
|
||||
struct glamor_pixmap_private *pixmap_priv =
|
||||
glamor_get_pixmap_private(pixmap);
|
||||
if (pixmap->refcnt == 1) {
|
||||
struct glamor_pixmap_private *pixmap_priv =
|
||||
glamor_get_pixmap_private(pixmap);
|
||||
|
||||
BUG_RETURN(!pixmap_priv);
|
||||
if (pixmap_priv->image)
|
||||
eglDestroyImageKHR(glamor_egl->display, pixmap_priv->image);
|
||||
}
|
||||
|
||||
if (pixmap_priv->image)
|
||||
eglDestroyImageKHR(glamor_egl->display, pixmap_priv->image);
|
||||
screen->DestroyPixmap = glamor_egl->saved_destroy_pixmap;
|
||||
ret = screen->DestroyPixmap(pixmap);
|
||||
glamor_egl->saved_destroy_pixmap = screen->DestroyPixmap;
|
||||
screen->DestroyPixmap = glamor_egl_destroy_pixmap;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
void
|
||||
|
|
@ -905,10 +846,8 @@ glamor_egl_exchange_buffers(PixmapPtr front, PixmapPtr back)
|
|||
|
||||
temp_img = back_priv->image;
|
||||
temp_mod = back_priv->used_modifiers;
|
||||
BUG_RETURN(!back_priv);
|
||||
back_priv->image = front_priv->image;
|
||||
back_priv->used_modifiers = front_priv->used_modifiers;
|
||||
BUG_RETURN(!front_priv);
|
||||
front_priv->image = temp_img;
|
||||
front_priv->used_modifiers = temp_mod;
|
||||
|
||||
|
|
@ -916,7 +855,8 @@ glamor_egl_exchange_buffers(PixmapPtr front, PixmapPtr back)
|
|||
glamor_set_pixmap_type(back, GLAMOR_TEXTURE_DRM);
|
||||
}
|
||||
|
||||
static void glamor_egl_close_screen(CallbackListPtr *pcbl, ScreenPtr screen, void *unused)
|
||||
static Bool
|
||||
glamor_egl_close_screen(ScreenPtr screen)
|
||||
{
|
||||
ScrnInfoPtr scrn;
|
||||
struct glamor_egl_screen_private *glamor_egl;
|
||||
|
|
@ -926,15 +866,14 @@ static void glamor_egl_close_screen(CallbackListPtr *pcbl, ScreenPtr screen, voi
|
|||
scrn = xf86ScreenToScrn(screen);
|
||||
glamor_egl = glamor_egl_get_screen_private(scrn);
|
||||
screen_pixmap = screen->GetScreenPixmap(screen);
|
||||
|
||||
pixmap_priv = glamor_get_pixmap_private(screen_pixmap);
|
||||
BUG_RETURN(!pixmap_priv);
|
||||
|
||||
eglDestroyImageKHR(glamor_egl->display, pixmap_priv->image);
|
||||
pixmap_priv->image = NULL;
|
||||
|
||||
dixScreenUnhookClose(screen, glamor_egl_close_screen);
|
||||
dixScreenUnhookPixmapDestroy(screen, glamor_egl_pixmap_destroy);
|
||||
screen->CloseScreen = glamor_egl->saved_close_screen;
|
||||
|
||||
return screen->CloseScreen(screen);
|
||||
}
|
||||
|
||||
#ifdef DRI3
|
||||
|
|
@ -1014,8 +953,11 @@ glamor_egl_screen_init(ScreenPtr screen, struct glamor_context *glamor_ctx)
|
|||
#endif
|
||||
const char *gbm_backend_name;
|
||||
|
||||
dixScreenHookClose(screen, glamor_egl_close_screen);
|
||||
dixScreenHookPixmapDestroy(screen, glamor_egl_pixmap_destroy);
|
||||
glamor_egl->saved_close_screen = screen->CloseScreen;
|
||||
screen->CloseScreen = glamor_egl_close_screen;
|
||||
|
||||
glamor_egl->saved_destroy_pixmap = screen->DestroyPixmap;
|
||||
screen->DestroyPixmap = glamor_egl_destroy_pixmap;
|
||||
|
||||
glamor_ctx->ctx = glamor_egl->context;
|
||||
glamor_ctx->display = glamor_egl->display;
|
||||
|
|
@ -1059,6 +1001,7 @@ glamor_egl_screen_init(ScreenPtr screen, struct glamor_context *glamor_ctx)
|
|||
#ifdef GLXEXT
|
||||
if (!vendor_initialized) {
|
||||
GlxPushProvider(&glamor_provider);
|
||||
xorgGlxCreateVendor();
|
||||
vendor_initialized = TRUE;
|
||||
}
|
||||
#endif
|
||||
|
|
@ -1216,12 +1159,9 @@ glamor_egl_init(ScrnInfoPtr scrn, int fd)
|
|||
memcpy(options, GlamorEGLOptions, sizeof(GlamorEGLOptions));
|
||||
xf86ProcessOptions(scrn->scrnIndex, scrn->options, options);
|
||||
glvnd_vendor = xf86GetOptValString(options, GLAMOREGLOPT_VENDOR_LIBRARY);
|
||||
if (glvnd_vendor) {
|
||||
glamor_egl->glvnd_vendor = strdup(glvnd_vendor);
|
||||
if (!glamor_egl->glvnd_vendor) {
|
||||
xf86DrvMsg(scrn->scrnIndex, X_WARNING, "Couldn't set gl vendor to: %s\n", glvnd_vendor);
|
||||
}
|
||||
}
|
||||
if (glvnd_vendor)
|
||||
glamor_egl->glvnd_vendor = XNFstrdup(glvnd_vendor);
|
||||
|
||||
api = xf86GetOptValString(options, GLAMOREGLOPT_RENDERING_API);
|
||||
if (api && !strncasecmp(api, "es", 2))
|
||||
force_es = TRUE;
|
||||
|
|
@ -1250,6 +1190,10 @@ glamor_egl_init(ScrnInfoPtr scrn, int fd)
|
|||
goto error;
|
||||
}
|
||||
|
||||
#ifdef EGL_MESA_image_dma_buf_export
|
||||
glamor_egl->has_image_dma_buf_export = epoxy_has_egl_extension(glamor_egl->display, "EGL_MESA_image_dma_buf_export");
|
||||
#endif
|
||||
|
||||
#define GLAMOR_CHECK_EGL_EXTENSION(EXT) \
|
||||
if (!epoxy_has_egl_extension(glamor_egl->display, "EGL_" #EXT)) { \
|
||||
ErrorF("EGL_" #EXT " required.\n"); \
|
||||
|
|
@ -1331,7 +1275,7 @@ glamor_egl_init(ScrnInfoPtr scrn, int fd)
|
|||
glamor_egl->dmabuf_capable = TRUE;
|
||||
else if (strstr((const char *)renderer, "zink"))
|
||||
glamor_egl->dmabuf_capable = TRUE;
|
||||
else if (strstr((const char *)renderer, "NVIDIA"))
|
||||
else if (strstr((const char *)renderer, "radeonsi"))
|
||||
glamor_egl->dmabuf_capable = TRUE;
|
||||
else
|
||||
glamor_egl->dmabuf_capable = FALSE;
|
||||
|
|
|
|||
Loading…
Reference in a new issue