diff options
-rw-r--r-- | src/drmmode_display.c | 51 | ||||
-rw-r--r-- | src/drmmode_display.h | 4 | ||||
-rw-r--r-- | src/radeon.h | 13 | ||||
-rw-r--r-- | src/radeon_dri2.c | 2 | ||||
-rw-r--r-- | src/radeon_kms.c | 28 | ||||
-rw-r--r-- | src/radeon_present.c | 2 |
6 files changed, 98 insertions, 2 deletions
diff --git a/src/drmmode_display.c b/src/drmmode_display.c index 7ad3235a..f55677f6 100644 --- a/src/drmmode_display.c +++ b/src/drmmode_display.c @@ -34,6 +34,7 @@ #include <time.h> #include "cursorstr.h" #include "damagestr.h" +#include "inputstr.h" #include "list.h" #include "micmap.h" #include "xf86cmap.h" @@ -2628,6 +2629,56 @@ Bool drmmode_set_bufmgr(ScrnInfoPtr pScrn, drmmode_ptr drmmode, struct radeon_bo } +static void drmmode_sprite_do_set_cursor(struct radeon_device_priv *device_priv, + ScrnInfoPtr scrn, int x, int y) +{ + RADEONInfoPtr info = RADEONPTR(scrn); + CursorPtr cursor = device_priv->cursor; + Bool sprite_visible = device_priv->sprite_visible; + + if (cursor) { + x -= cursor->bits->xhot; + y -= cursor->bits->yhot; + + device_priv->sprite_visible = + x < scrn->virtualX && y < scrn->virtualY && + (x + cursor->bits->width > 0) && + (y + cursor->bits->height > 0); + } else { + device_priv->sprite_visible = FALSE; + } + + info->sprites_visible += device_priv->sprite_visible - sprite_visible; +} + +void drmmode_sprite_set_cursor(DeviceIntPtr pDev, ScreenPtr pScreen, + CursorPtr pCursor, int x, int y) +{ + ScrnInfoPtr scrn = xf86ScreenToScrn(pScreen); + RADEONInfoPtr info = RADEONPTR(scrn); + struct radeon_device_priv *device_priv = + dixLookupScreenPrivate(&pDev->devPrivates, + &radeon_device_private_key, pScreen); + + device_priv->cursor = pCursor; + drmmode_sprite_do_set_cursor(device_priv, scrn, x, y); + + info->SetCursor(pDev, pScreen, pCursor, x, y); +} + +void drmmode_sprite_move_cursor(DeviceIntPtr pDev, ScreenPtr pScreen, int x, + int y) +{ + ScrnInfoPtr scrn = xf86ScreenToScrn(pScreen); + RADEONInfoPtr info = RADEONPTR(scrn); + struct radeon_device_priv *device_priv = + dixLookupScreenPrivate(&pDev->devPrivates, + &radeon_device_private_key, pScreen); + + drmmode_sprite_do_set_cursor(device_priv, scrn, x, y); + + info->MoveCursor(pDev, pScreen, x, y); +} void drmmode_set_cursor(ScrnInfoPtr scrn, drmmode_ptr drmmode, int id, struct radeon_bo *bo) { diff --git a/src/drmmode_display.h b/src/drmmode_display.h index 8387279f..39d2d94a 100644 --- a/src/drmmode_display.h +++ b/src/drmmode_display.h @@ -206,6 +206,10 @@ extern Bool drmmode_pre_init(ScrnInfoPtr pScrn, drmmode_ptr drmmode, int cpp); extern void drmmode_init(ScrnInfoPtr pScrn, drmmode_ptr drmmode); extern void drmmode_fini(ScrnInfoPtr pScrn, drmmode_ptr drmmode); extern Bool drmmode_set_bufmgr(ScrnInfoPtr pScrn, drmmode_ptr drmmode, struct radeon_bo_manager *bufmgr); +extern void drmmode_sprite_set_cursor(DeviceIntPtr pDev, ScreenPtr pScreen, + CursorPtr pCursor, int x, int y); +extern void drmmode_sprite_move_cursor(DeviceIntPtr pDev, ScreenPtr pScreen, int x, + int y); extern void drmmode_set_cursor(ScrnInfoPtr scrn, drmmode_ptr drmmode, int id, struct radeon_bo *bo); void drmmode_adjust_frame(ScrnInfoPtr pScrn, drmmode_ptr drmmode, int x, int y); extern Bool drmmode_set_desired_modes(ScrnInfoPtr pScrn, drmmode_ptr drmmode, diff --git a/src/radeon.h b/src/radeon.h index cc5dc09f..9658e029 100644 --- a/src/radeon.h +++ b/src/radeon.h @@ -500,6 +500,13 @@ struct radeon_client_priv { uint_fast32_t needs_flush; }; +struct radeon_device_priv { + CursorPtr cursor; + Bool sprite_visible; +}; + +extern DevScreenPrivateKeyRec radeon_device_private_key; + typedef struct { EntityInfoPtr pEnt; pciVideoPtr PciInfo; @@ -550,6 +557,12 @@ typedef struct { CreateScreenResourcesProcPtr CreateScreenResources; CreateWindowProcPtr CreateWindow; WindowExposuresProcPtr WindowExposures; + void (*SetCursor) (DeviceIntPtr pDev, ScreenPtr pScreen, + CursorPtr pCursor, int x, int y); + void (*MoveCursor) (DeviceIntPtr pDev, ScreenPtr pScreen, int x, int y); + + /* Number of SW cursors currently visible on this screen */ + int sprites_visible; Bool IsSecondary; diff --git a/src/radeon_dri2.c b/src/radeon_dri2.c index b569bb4f..8376848c 100644 --- a/src/radeon_dri2.c +++ b/src/radeon_dri2.c @@ -723,7 +723,7 @@ can_flip(xf86CrtcPtr crtc, DrawablePtr draw, if (draw->type != DRAWABLE_WINDOW || !info->allowPageFlip || - info->hwcursor_disabled || + info->sprites_visible > 0 || info->drmmode.present_flipping || !pScrn->vtSema || !DRI2CanFlip(draw)) diff --git a/src/radeon_kms.c b/src/radeon_kms.c index 602a8fb7..c1f885eb 100644 --- a/src/radeon_kms.c +++ b/src/radeon_kms.c @@ -38,6 +38,7 @@ #include "radeon_reg.h" #include "radeon_probe.h" #include "micmap.h" +#include "mipointrst.h" #include "radeon_version.h" #include "shadow.h" @@ -66,6 +67,7 @@ #include "radeon_vbo.h" static DevScreenPrivateKeyRec radeon_client_private_key; +DevScreenPrivateKeyRec radeon_device_private_key; extern SymTabRec RADEONChipsets[]; static Bool radeon_setup_kernel_mem(ScreenPtr pScreen); @@ -1991,6 +1993,23 @@ static Bool RADEONCursorInit_KMS(ScreenPtr pScreen) /* Cursor setup */ miDCInitialize(pScreen, xf86GetPointerScreenFuncs()); + if (info->allowPageFlip) { + miPointerScreenPtr PointPriv = + dixLookupPrivate(&pScreen->devPrivates, miPointerScreenKey); + + if (!dixRegisterScreenPrivateKey(&radeon_device_private_key, pScreen, + PRIVATE_DEVICE, + sizeof(struct radeon_device_priv))) { + xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "dixRegisterScreenPrivateKey failed\n"); + return FALSE; + } + + info->SetCursor = PointPriv->spriteFuncs->SetCursor; + info->MoveCursor = PointPriv->spriteFuncs->MoveCursor; + PointPriv->spriteFuncs->SetCursor = drmmode_sprite_set_cursor; + PointPriv->spriteFuncs->MoveCursor = drmmode_sprite_move_cursor; + } + if (xf86ReturnOptValBool(info->Options, OPTION_SW_CURSOR, FALSE)) return TRUE; @@ -2147,6 +2166,15 @@ static Bool RADEONCloseScreen_KMS(ScreenPtr pScreen) pScrn->vtSema = FALSE; xf86ClearPrimInitDone(info->pEnt->index); + + if (info->allowPageFlip) { + miPointerScreenPtr PointPriv = + dixLookupPrivate(&pScreen->devPrivates, miPointerScreenKey); + + PointPriv->spriteFuncs->SetCursor = info->SetCursor; + PointPriv->spriteFuncs->MoveCursor = info->MoveCursor; + } + pScreen->BlockHandler = info->BlockHandler; pScreen->CloseScreen = info->CloseScreen; return pScreen->CloseScreen(pScreen); diff --git a/src/radeon_present.c b/src/radeon_present.c index 176853d9..d734b9d4 100644 --- a/src/radeon_present.c +++ b/src/radeon_present.c @@ -289,7 +289,7 @@ radeon_present_check_flip(RRCrtcPtr crtc, WindowPtr window, PixmapPtr pixmap, if (!info->allowPageFlip) return FALSE; - if (info->hwcursor_disabled) + if (info->sprites_visible > 0) return FALSE; if (info->drmmode.dri2_flipping) |