hw/xfree86: Avoid cursor use after free

Merged Martin Weber requested to merge webi123/xserver:cursor-fix-use-after-free into master

Storing a raw pointer to current cursor object with refcount=1 and then call xf86CursorSetCursor with pCurs = NullCursor which decrements and then frees the object leads to a dangling pointer in SavedCursor and a potential use after free.

    if (!enable && ScreenPriv->CurrentCursor != NullCursor) {
        CursorPtr currentCursor = ScreenPriv->CurrentCursor; <--- 1. assumed refcount=1

        xf86CursorSetCursor(pDev, pScreen, NullCursor, ScreenPriv->x,
        ScreenPriv->isUp = FALSE;
        ScreenPriv->SWCursor = TRUE;
        ScreenPriv->SavedCursor = currentCursor; <--- 3. dangling pointer, restored on VTEnter

    if (pCurs == NullCursor) {  /* means we're supposed to remove the cursor */
        if (ScreenPriv->SWCursor ||
            !(GetMaster(pDev, MASTER_POINTER) == inputInfo.pointer))
            (*ScreenPriv->spriteFuncs->SetCursor) (pDev, pScreen, NullCursor, x,
        else if (ScreenPriv->isUp) {
            xf86SetCursor(pScreen, NullCursor, x, y);
            ScreenPriv->isUp = FALSE;
        if (ScreenPriv->CurrentCursor)
            FreeCursor(ScreenPriv->CurrentCursor, None); <--- 2. UnrefCursor and free
        ScreenPriv->CurrentCursor = NullCursor;
Edited by Martin Weber

Merge request reports