diff options
-rw-r--r-- | src/gallium/winsys/drm/vmware/xorg/vmw_driver.h | 4 | ||||
-rw-r--r-- | src/gallium/winsys/drm/vmware/xorg/vmw_ioctl.c | 17 | ||||
-rw-r--r-- | src/gallium/winsys/drm/vmware/xorg/vmw_screen.c | 58 |
3 files changed, 75 insertions, 4 deletions
diff --git a/src/gallium/winsys/drm/vmware/xorg/vmw_driver.h b/src/gallium/winsys/drm/vmware/xorg/vmw_driver.h index 04d446a2df..db6b89b8bc 100644 --- a/src/gallium/winsys/drm/vmware/xorg/vmw_driver.h +++ b/src/gallium/winsys/drm/vmware/xorg/vmw_driver.h @@ -44,6 +44,8 @@ struct vmw_driver { int fd; + void *cursor_priv; + /* vmw_video.c */ void *video_priv; }; @@ -69,6 +71,8 @@ Bool vmw_video_close(ScrnInfoPtr pScrn, struct vmw_driver *vmw); * vmw_ioctl.c */ +int vmw_ioctl_cursor_bypass(struct vmw_driver *vmw, int xhot, int yhot); + struct vmw_dma_buffer * vmw_ioctl_buffer_create(struct vmw_driver *vmw, uint32_t size, unsigned *handle); diff --git a/src/gallium/winsys/drm/vmware/xorg/vmw_ioctl.c b/src/gallium/winsys/drm/vmware/xorg/vmw_ioctl.c index 3cac5b7760..7ec651db05 100644 --- a/src/gallium/winsys/drm/vmware/xorg/vmw_ioctl.c +++ b/src/gallium/winsys/drm/vmware/xorg/vmw_ioctl.c @@ -54,6 +54,23 @@ struct vmw_dma_buffer uint32_t size; }; +int +vmw_ioctl_cursor_bypass(struct vmw_driver *vmw, int xhot, int yhot) +{ + struct drm_vmw_cursor_bypass_arg arg; + int ret; + + memset(&arg, 0, sizeof(arg)); + arg.flags = DRM_VMW_CURSOR_BYPASS_ALL; + arg.xhot = xhot; + arg.yhot = yhot; + + ret = drmCommandWriteRead(vmw->fd, DRM_VMW_CURSOR_BYPASS, + &arg, sizeof(arg)); + + return ret; +} + struct vmw_dma_buffer * vmw_ioctl_buffer_create(struct vmw_driver *vmw, uint32_t size, unsigned *handle) { diff --git a/src/gallium/winsys/drm/vmware/xorg/vmw_screen.c b/src/gallium/winsys/drm/vmware/xorg/vmw_screen.c index 344ef0b315..421906da99 100644 --- a/src/gallium/winsys/drm/vmware/xorg/vmw_screen.c +++ b/src/gallium/winsys/drm/vmware/xorg/vmw_screen.c @@ -33,16 +33,58 @@ #include "vmw_hook.h" #include "vmw_driver.h" +/* modified version of crtc functions */ +xf86CrtcFuncsRec vmw_screen_crtc_funcs; + +static void +vmw_screen_cursor_load_argb(xf86CrtcPtr crtc, CARD32 *image) +{ + struct vmw_driver *vmw = modesettingPTR(crtc->scrn)->winsys_priv; + xf86CrtcConfigPtr config = XF86_CRTC_CONFIG_PTR(crtc->scrn); + xf86CrtcFuncsPtr funcs = vmw->cursor_priv; + CursorPtr c = config->cursor; + + /* Run the ioctl before uploading the image */ + vmw_ioctl_cursor_bypass(vmw, c->bits->xhot, c->bits->yhot); + + funcs->load_cursor_argb(crtc, image); +} + +static void +vmw_screen_cursor_init(ScrnInfoPtr pScrn, struct vmw_driver *vmw) +{ + xf86CrtcConfigPtr config = XF86_CRTC_CONFIG_PTR(pScrn); + int i; + + /* XXX assume that all crtc's have the same function struct */ + + /* Save old struct need to call the old functions as well */ + vmw->cursor_priv = (void*)(config->crtc[0]->funcs); + memcpy(&vmw_screen_crtc_funcs, vmw->cursor_priv, sizeof(xf86CrtcFuncsRec)); + vmw_screen_crtc_funcs.load_cursor_argb = vmw_screen_cursor_load_argb; + + for (i = 0; i < config->num_crtc; i++) + config->crtc[i]->funcs = &vmw_screen_crtc_funcs; +} + +static void +vmw_screen_cursor_close(ScrnInfoPtr pScrn, struct vmw_driver *vmw) +{ + xf86CrtcConfigPtr config = XF86_CRTC_CONFIG_PTR(pScrn); + int i; + + vmw_ioctl_cursor_bypass(vmw, 0, 0); + + for (i = 0; i < config->num_crtc; i++) + config->crtc[i]->funcs = vmw->cursor_priv; +} + static Bool vmw_screen_init(ScrnInfoPtr pScrn) { modesettingPtr ms = modesettingPTR(pScrn); struct vmw_driver *vmw; - /* if gallium is used then we don't need to do anything. */ - if (ms->screen) - return TRUE; - vmw = xnfcalloc(sizeof(*vmw), 1); if (!vmw) return FALSE; @@ -50,6 +92,12 @@ vmw_screen_init(ScrnInfoPtr pScrn) vmw->fd = ms->fd; ms->winsys_priv = vmw; + vmw_screen_cursor_init(pScrn, vmw); + + /* if gallium is used then we don't need to do anything more. */ + if (ms->screen) + return TRUE; + vmw_video_init(pScrn, vmw); return TRUE; @@ -64,6 +112,8 @@ vmw_screen_close(ScrnInfoPtr pScrn) if (!vmw) return TRUE; + vmw_screen_cursor_close(pScrn, vmw); + vmw_video_close(pScrn, vmw); ms->winsys_priv = NULL; |