Index: /trunk/include/VBox/pdmifs.h
===================================================================
--- /trunk/include/VBox/pdmifs.h	(revision 26649)
+++ /trunk/include/VBox/pdmifs.h	(revision 26650)
@@ -279,6 +279,4 @@
 
 
-/** PDMIMOUSEPORT interface ID. */
-#define PDMIMOUSEPORT_IID "f8d45ecc-bd6f-4a8d-b262-b85498e7f143"
 /** Pointer to a mouse port interface. */
 typedef struct PDMIMOUSEPORT *PPDMIMOUSEPORT;
@@ -291,33 +289,39 @@
     /**
      * Puts a mouse event.
-     * This is called by the source of mouse events. The event will be passed up until the
-     * topmost driver, which then calls the registered event handler.
-     *
-     * @returns VBox status code.
+     *
+     * This is called by the source of mouse events.  The event will be passed up
+     * until the topmost driver, which then calls the registered event handler.
+     *
+     * @returns VBox status code.  Return VERR_TRY_AGAIN if you cannot process the
+     *          event now and want it to be repeated at a later point.
+     *
      * @param   pInterface          Pointer to this interface structure.
-     * @param   i32DeltaX       The X delta.
-     * @param   i32DeltaY       The Y delta.
-     * @param   i32DeltaZ       The Z delta.
-     * @param   i32DeltaW       The W (horizontal scroll button) delta.
-     * @param   fButtonStates   The button states, see the PDMIMOUSEPORT_BUTTON_* \#defines.
-     * @thread  The emulation thread.
-     */
-    DECLR3CALLBACKMEMBER(int, pfnPutEvent,(PPDMIMOUSEPORT pInterface, int32_t i32DeltaX, int32_t i32DeltaY, int32_t i32DeltaZ, int32_t i32DeltaW, uint32_t fButtonStates));
+     * @param   iDeltaX             The X delta.
+     * @param   iDeltaY             The Y delta.
+     * @param   iDeltaZ             The Z delta.
+     * @param   iDeltaW             The W (horizontal scroll button) delta.
+     * @param   fButtonStates       The button states, see the PDMIMOUSEPORT_BUTTON_* \#defines.
+     */
+    DECLR3CALLBACKMEMBER(int, pfnPutEvent,(PPDMIMOUSEPORT pInterface, int32_t iDeltaX, int32_t iDeltaY, int32_t iDeltaZ, int32_t iDeltaW, uint32_t fButtonStates));
     /**
      * Puts an absolute mouse event.
-     * This is called by the source of mouse events. The event will be passed up until the
-     * topmost driver, which then calls the registered event handler.
-     *
-     * @returns VBox status code.
+     *
+     * This is called by the source of mouse events.  The event will be passed up
+     * until the topmost driver, which then calls the registered event handler.
+     *
+     * @returns VBox status code.  Return VERR_TRY_AGAIN if you cannot process the
+     *          event now and want it to be repeated at a later point.
+     *
      * @param   pInterface          Pointer to this interface structure.
-     * @param   i32cX               The X value, in the range 0 to 0xffff.
-     * @param   i32cY               The Y value, in the range 0 to 0xffff.
-     * @param   i32DeltaZ           The Z delta.
-     * @param   i32DeltaW           The W (horizontal scroll button) delta.
+     * @param   uX                  The X value, in the range 0 to 0xffff.
+     * @param   uY                  The Y value, in the range 0 to 0xffff.
+     * @param   iDeltaZ             The Z delta.
+     * @param   iDeltaW             The W (horizontal scroll button) delta.
      * @param   fButtonStates       The button states, see the PDMIMOUSEPORT_BUTTON_* \#defines.
-     * @thread  The emulation thread.
-     */
-    DECLR3CALLBACKMEMBER(int, pfnPutEventAbs,(PPDMIMOUSEPORT pInterface, uint32_t i32cX, uint32_t i32cY, int32_t i32DeltaZ, int32_t i32DeltaW, uint32_t fButtonStates));
+     */
+    DECLR3CALLBACKMEMBER(int, pfnPutEventAbs,(PPDMIMOUSEPORT pInterface, uint32_t uX, uint32_t uY, int32_t iDeltaZ, int32_t iDeltaW, uint32_t fButtonStates));
 } PDMIMOUSEPORT;
+/** PDMIMOUSEPORT interface ID. */
+#define PDMIMOUSEPORT_IID                       "442136fe-6f3c-49ec-9964-259b378ffa64"
 
 /** Mouse button defines for PDMIMOUSEPORT::pfnPutEvent.
@@ -340,15 +344,15 @@
 {
     /**
-     * Notifies the the downstream driver when the guest switches the device into or out of absolute mode.
+     * Notifies the the downstream driver when the guest switches the device into or
+     * out of absolute mode.
      *
      * @param   pInterface      Pointer to the this interface.
-     * @param   fAbs            Whether absolute mode is currently enabled
-     */
-    DECLR3CALLBACKMEMBER(void, pfnAbsModeChange,(PPDMIMOUSECONNECTOR pInterface, bool fAbs));
+     * @param   fEnabled        Whether absolute mode is currently enabled.
+     */
+    DECLR3CALLBACKMEMBER(void, pfnAbsModeChange,(PPDMIMOUSECONNECTOR pInterface, bool fEnabled));
 
 } PDMIMOUSECONNECTOR;
-
 /** PDMIMOUSECONNECTOR interface ID.  */
-#define PDMIMOUSECONNECTOR_IID                  "39e48c1c-1514-4ac6-8a9c-88034d36ae98"
+#define PDMIMOUSECONNECTOR_IID                  "6b7be703-c1de-40a2-a977-0ef68d8760ca"
 
 
@@ -372,5 +376,4 @@
      * @param   pInterface          Pointer to this interface structure.
      * @param   u8KeyCode           The keycode to queue.
-     * @thread  The emulation thread.
      */
     DECLR3CALLBACKMEMBER(int, pfnPutEvent,(PPDMIKEYBOARDPORT pInterface, uint8_t u8KeyCode));
Index: /trunk/src/VBox/Devices/Input/DevPS2.cpp
===================================================================
--- /trunk/src/VBox/Devices/Input/DevPS2.cpp	(revision 26649)
+++ /trunk/src/VBox/Devices/Input/DevPS2.cpp	(revision 26650)
@@ -162,5 +162,5 @@
 #define KBD_QUEUE_SIZE 256
 
-/* Supported mouse protocols */
+/** Supported mouse protocols */
 enum
 {
@@ -171,8 +171,9 @@
 };
 
-/* Mouse flags */
+/** Mouse flags */
 # define MOUSE_REPORT_HORIZONTAL  0x01
 
-/** Extended mouse button values for Lifebook mode */
+/** @name Extended mouse button values for Lifebook mode
+ * @{ */
 /** Downwards scrollwheel movement of one step.  Doesn't affect the mouse
  * buttons */
@@ -184,4 +185,5 @@
 /** Rightwards scrollwheel movement of one step. */
 # define MOUSE_EXT_HSCROLL_FW   7
+/** @} */
 
 typedef struct {
@@ -230,5 +232,5 @@
     int32_t mouse_dw;
     int32_t mouse_flags;
-    uint32_t mouse_cx;
+    uint32_t mouse_cx; /** @todo r=bird: cx/cy? aren't these absolute coordinates? 'c' usually means 'count of'. mouse_abs_x or just mouse_x would probably be clearer. */
     uint32_t mouse_cy;
     uint8_t mouse_buttons;
@@ -707,5 +709,5 @@
 
 /**
- * Send a single relative packet in 3-byte PS/2 format, optionally with our 
+ * Send a single relative packet in 3-byte PS/2 format, optionally with our
  * packed button protocol extension, to the PS/2 controller.
  * @param  s               keyboard state object
@@ -839,8 +841,6 @@
  * Send a single absolute packet in 6-byte lifebook format to the PS/2
  * controller.
- * @param  s         keyboard state object
- * @param  cx        absolute X value
- * @param  cy        absolute y value
- * @param  fButtons  the state of the two first mouse buttons
+ * @param  s            keyboard state object
+ * @param  fToCmdQueue  Which queue.
  */
 static void kbd_mouse_send_abs_packet(KBDState *s, bool fToCmdQueue)
@@ -1228,5 +1228,6 @@
     s->mouse_wrap = 0;
     s->mouse_type = MOUSE_PROT_PS2;
-    s->Mouse.pDrv->pfnAbsModeChange(s->Mouse.pDrv, false);
+    if (s->Mouse.pDrv)
+        s->Mouse.pDrv->pfnAbsModeChange(s->Mouse.pDrv, false);
     s->mouse_detect_state = 0;
     s->mouse_dx = 0;
@@ -1331,5 +1332,5 @@
     qemu_get_8s(f, &s->mouse_wrap);
     qemu_get_8s(f, &s->mouse_type);
-    if (s->mouse_type == MOUSE_PROT_LIFEBOOK)
+    if (s->mouse_type == MOUSE_PROT_LIFEBOOK && s->Mouse.pDrv)
         s->Mouse.pDrv->pfnAbsModeChange(s->Mouse.pDrv, true);
     qemu_get_8s(f, &s->mouse_detect_state);
@@ -1657,15 +1658,8 @@
 
 /**
- * Mouse event handler.
- *
- * @returns VBox status code.
- * @param   pInterface      Pointer to the mouse port interface (KBDState::Mouse.IPort).
- * @param   i32DeltaX       The X delta.
- * @param   i32DeltaY       The Y delta.
- * @param   i32DeltaZ       The Z delta.
- * @param   fButtonStates   The button states.
- */
-static DECLCALLBACK(int) kbdMousePutEvent(PPDMIMOUSEPORT pInterface, int32_t i32DeltaX, int32_t i32DeltaY,
-                                          int32_t i32DeltaZ, int32_t i32DeltaW, uint32_t fButtonStates)
+ * @interface_method_impl{PDMIMOUSEPORT, pfnPutEvent}
+ */
+static DECLCALLBACK(int) kbdMousePutEvent(PPDMIMOUSEPORT pInterface, int32_t iDeltaX, int32_t iDeltaY,
+                                          int32_t iDeltaZ, int32_t iDeltaW, uint32_t fButtonStates)
 {
     KBDState *pThis = RT_FROM_MEMBER(pInterface, KBDState, Mouse.IPort);
@@ -1673,5 +1667,5 @@
     AssertReleaseRC(rc);
 
-    pc_kbd_mouse_event(pThis, i32DeltaX, i32DeltaY, i32DeltaZ, i32DeltaW, fButtonStates);
+    pc_kbd_mouse_event(pThis, iDeltaX, iDeltaY, iDeltaZ, iDeltaW, fButtonStates);
 
     PDMCritSectLeave(&pThis->CritSect);
@@ -1680,12 +1674,7 @@
 
 /**
- * Mouse event handler.
- *
- * @returns VBox status code.
- * @param   pInterface      Pointer to the mouse port interface (KBDState::Mouse.IPort).
- * @param   i32cX           The X value.
- * @param   i32cY           The Y value.
- */
-static DECLCALLBACK(int) kbdMousePutEventAbs(PPDMIMOUSEPORT pInterface, uint32_t u32cX, uint32_t u32cY, int32_t dz, int32_t dw, uint32_t fButtons)
+ * @interface_method_impl{PDMIMOUSEPORT, pfnPutEventAbs}
+ */
+static DECLCALLBACK(int) kbdMousePutEventAbs(PPDMIMOUSEPORT pInterface, uint32_t uX, uint32_t uY, int32_t iDeltaZ, int32_t iDeltaW, uint32_t fButtons)
 {
     KBDState *pThis = RT_FROM_MEMBER(pInterface, KBDState, Mouse.IPort);
@@ -1693,8 +1682,8 @@
     AssertReleaseRC(rc);
 
-    if (u32cX != pThis->mouse_cx || u32cY != pThis->mouse_cy)
-        pc_kbd_mouse_event_abs(pThis, u32cX, u32cY);
-    if (dz || dw || fButtons != pThis->mouse_buttons)
-        pc_kbd_mouse_event(pThis, 0, 0, dz, dw, fButtons);
+    if (uX != pThis->mouse_cx || uY != pThis->mouse_cy)
+        pc_kbd_mouse_event_abs(pThis, uX, uY);
+    if (iDeltaZ || iDeltaW || fButtons != pThis->mouse_buttons)
+        pc_kbd_mouse_event(pThis, 0, 0, iDeltaZ, iDeltaW, fButtons);
 
     PDMCritSectLeave(&pThis->CritSect);
Index: /trunk/src/VBox/Devices/Input/DrvMouseQueue.cpp
===================================================================
--- /trunk/src/VBox/Devices/Input/DrvMouseQueue.cpp	(revision 26649)
+++ /trunk/src/VBox/Devices/Input/DrvMouseQueue.cpp	(revision 26650)
@@ -70,11 +70,11 @@
     PDMQUEUEITEMCORE    Core;
     uint32_t            fAbs;
-    int32_t             i32DeltaX;
-    int32_t             i32DeltaY;
-    int32_t             i32DeltaZ;
-    int32_t             i32DeltaW;
+    int32_t             iDeltaX;
+    int32_t             iDeltaY;
+    int32_t             iDeltaZ;
+    int32_t             iDeltaW;
     uint32_t            fButtonStates;
-    uint32_t            u32cX;
-    uint32_t            u32cY;
+    uint32_t            uX;
+    uint32_t            uY;
 } DRVMOUSEQUEUEITEM, *PDRVMOUSEQUEUEITEM;
 
@@ -104,17 +104,7 @@
 
 /**
- * Queues a mouse event.
- * Because of the event queueing the EMT context requirement is lifted.
- *
- * @returns VBox status code.
- * @param   pInterface      Pointer to interface structure.
- * @param   i32DeltaX       The X delta.
- * @param   i32DeltaY       The Y delta.
- * @param   i32DeltaZ       The Z delta.
- * @param   i32DeltaW       The W delta.
- * @param   fButtonStates   The button states.
- * @thread  Any thread.
- */
-static DECLCALLBACK(int) drvMouseQueuePutEvent(PPDMIMOUSEPORT pInterface, int32_t i32DeltaX, int32_t i32DeltaY, int32_t i32DeltaZ, int32_t i32DeltaW, uint32_t fButtonStates)
+ * @interface_method_impl{PDMIMOUSEPORT,pfnPutEvent}
+ */
+static DECLCALLBACK(int) drvMouseQueuePutEvent(PPDMIMOUSEPORT pInterface, int32_t iDeltaX, int32_t iDeltaY, int32_t iDeltaZ, int32_t iDeltaW, uint32_t fButtonStates)
 {
     PDRVMOUSEQUEUE pDrv = IMOUSEPORT_2_DRVMOUSEQUEUE(pInterface);
@@ -126,9 +116,11 @@
     {
         pItem->fAbs = 0;
-        pItem->i32DeltaX = i32DeltaX;
-        pItem->i32DeltaY = i32DeltaY;
-        pItem->i32DeltaZ = i32DeltaZ;
-        pItem->i32DeltaW = i32DeltaW;
+        pItem->iDeltaX = iDeltaX;
+        pItem->iDeltaY = iDeltaY;
+        pItem->iDeltaZ = iDeltaZ;
+        pItem->iDeltaW = iDeltaW;
         pItem->fButtonStates = fButtonStates;
+        pItem->uX = 0;
+        pItem->uY = 0;
         PDMQueueInsert(pDrv->pQueue, &pItem->Core);
         return VINF_SUCCESS;
@@ -138,17 +130,7 @@
 
 /**
- * Queues an absolute mouse event.
- * Because of the event queueing the EMT context requirement is lifted.
- *
- * @returns VBox status code.
- * @param   pInterface      Pointer to interface structure.
- * @param   u32cX           The X value.
- * @param   u32cY           The Y value.
- * @param   i32DeltaZ       The Z delta.
- * @param   i32DeltaW       The W delta.
- * @param   fButtonStates   The button states.
- * @thread  Any thread.
- */
-static DECLCALLBACK(int) drvMouseQueuePutEventAbs(PPDMIMOUSEPORT pInterface, uint32_t u32cX, uint32_t u32cY, int32_t i32DeltaZ, int32_t i32DeltaW, uint32_t fButtonStates)
+ * @interface_method_impl{PDMIMOUSEPORT,pfnPutEventAbs}
+ */
+static DECLCALLBACK(int) drvMouseQueuePutEventAbs(PPDMIMOUSEPORT pInterface, uint32_t uX, uint32_t uY, int32_t iDeltaZ, int32_t iDeltaW, uint32_t fButtonStates)
 {
     PDRVMOUSEQUEUE pDrv = IMOUSEPORT_2_DRVMOUSEQUEUE(pInterface);
@@ -160,9 +142,11 @@
     {
         pItem->fAbs = 1;
-        pItem->u32cX = u32cX;
-        pItem->u32cY = u32cY;
-        pItem->i32DeltaZ = i32DeltaZ;
-        pItem->i32DeltaW = i32DeltaW;
+        pItem->iDeltaX = 0;
+        pItem->iDeltaY = 0;
+        pItem->iDeltaZ = iDeltaZ;
+        pItem->iDeltaW = iDeltaW;
         pItem->fButtonStates = fButtonStates;
+        pItem->uX = uX;
+        pItem->uY = uY;
         PDMQueueInsert(pDrv->pQueue, &pItem->Core);
         return VINF_SUCCESS;
@@ -208,7 +192,7 @@
     int rc;
     if (!pItem->fAbs)
-        rc = pThis->pUpPort->pfnPutEvent(pThis->pUpPort, pItem->i32DeltaX, pItem->i32DeltaY, pItem->i32DeltaZ, pItem->i32DeltaW, pItem->fButtonStates);
+        rc = pThis->pUpPort->pfnPutEvent(pThis->pUpPort, pItem->iDeltaX, pItem->iDeltaY, pItem->iDeltaZ, pItem->iDeltaW, pItem->fButtonStates);
     else
-        rc = pThis->pUpPort->pfnPutEventAbs(pThis->pUpPort, pItem->u32cX, pItem->u32cY, pItem->i32DeltaZ, pItem->i32DeltaW, pItem->fButtonStates);
+        rc = pThis->pUpPort->pfnPutEventAbs(pThis->pUpPort, pItem->uX,   pItem->uY,      pItem->iDeltaZ, pItem->iDeltaW, pItem->fButtonStates);
     return RT_SUCCESS(rc);
 }
Index: /trunk/src/VBox/Main/MouseImpl.cpp
===================================================================
--- /trunk/src/VBox/Main/MouseImpl.cpp	(revision 26649)
+++ /trunk/src/VBox/Main/MouseImpl.cpp	(revision 26650)
@@ -46,6 +46,4 @@
 } DRVMAINMOUSE, *PDRVMAINMOUSE;
 
-/** Converts a PDMIMOUSECONNECTOR pointer to a DRVMAINMOUSE pointer. */
-#define PPDMIMOUSECONNECTOR_2_MAINMOUSE(pInterface) ( (PDRVMAINMOUSE) ((uintptr_t)pInterface - RT_OFFSETOF(DRVMAINMOUSE, IConnector)) )
 
 // constructor / destructor
@@ -403,6 +401,4 @@
                                           LONG buttonState)
 {
-    HRESULT rc = S_OK;
-
     AutoCaller autoCaller(this);
     if (FAILED(autoCaller.rc())) return autoCaller.rc();
@@ -414,8 +410,9 @@
 
     uint32_t mouseXAbs;
-    rc = convertDisplayWidth(x, &mouseXAbs);
+    HRESULT rc = convertDisplayWidth(x, &mouseXAbs);
     ComAssertComRCRet(rc, rc);
     if (mouseXAbs > 0xffff)
         mouseXAbs = mLastAbsX;
+
     uint32_t mouseYAbs;
     rc = convertDisplayHeight(y, &mouseYAbs);
@@ -423,5 +420,7 @@
     if (mouseYAbs > 0xffff)
         mouseYAbs = mLastAbsY;
+
     uint32_t fButtons = mouseButtonsToPDM(buttonState);
+
     /* Older guest additions rely on a small phony movement event on the
      * PS/2 device to notice absolute events. */
@@ -435,4 +434,5 @@
         rc = getVMMDevMouseCaps(&mouseCaps);
         ComAssertComRCRet(rc, rc);
+
         /*
          * This method being called implies that the host wants
@@ -449,7 +449,9 @@
         fNeedsJiggle = !(mouseCaps & VMMDEV_MOUSE_GUEST_USES_VMMDEV);
     }
-    ComAssertComRCRet (rc, rc);
+    ComAssertComRCRet(rc, rc);
+
     mLastAbsX = mouseXAbs;
     mLastAbsY = mouseYAbs;
+
     if (!(uDevCaps & MOUSE_DEVCAP_ABSOLUTE))
     {
@@ -460,7 +462,9 @@
          * the way. */
         if (fNeedsJiggle || fButtons != mLastButtons || dz || dw)
+        {
             rc = reportRelEventToMouseDev(fNeedsJiggle ? 1 : 0, 0, dz, dw,
                                           fButtons);
-        ComAssertComRCRet (rc, rc);
+            ComAssertComRCRet(rc, rc);
+        }
     }
     mLastButtons = fButtons;
@@ -471,45 +475,16 @@
 /////////////////////////////////////////////////////////////////////////////
 
-/**
- * @interface_method_impl{PDMIBASE,pfnQueryInterface}
- */
-DECLCALLBACK(void *)  Mouse::drvQueryInterface(PPDMIBASE pInterface, const char *pszIID)
-{
-    PPDMDRVINS      pDrvIns = PDMIBASE_2_PDMDRV(pInterface);
-    PDRVMAINMOUSE   pDrv    = PDMINS_2_DATA(pDrvIns, PDRVMAINMOUSE);
-
-    PDMIBASE_RETURN_INTERFACE(pszIID, PDMIBASE, &pDrvIns->IBase);
-    PDMIBASE_RETURN_INTERFACE(pszIID, PDMIMOUSECONNECTOR, &pDrv->IConnector);
-    return NULL;
-}
-
-
-/**
- * Destruct a mouse driver instance.
- *
- * @returns VBox status.
- * @param   pDrvIns     The driver instance data.
- */
-DECLCALLBACK(void) Mouse::drvDestruct(PPDMDRVINS pDrvIns)
-{
-    PDRVMAINMOUSE pData = PDMINS_2_DATA(pDrvIns, PDRVMAINMOUSE);
-    LogFlow(("Mouse::drvDestruct: iInstance=%d\n", pDrvIns->iInstance));
-    PDMDRV_CHECK_VERSIONS_RETURN_VOID(pDrvIns);
-
-    if (pData->pMouse)
-    {
-        AutoWriteLock mouseLock(pData->pMouse COMMA_LOCKVAL_SRC_POS);
-        pData->pMouse->mpDrv = NULL;
-    }
-}
-
-
-DECLCALLBACK(void) Mouse::mouseAbsModeChange (PPDMIMOUSECONNECTOR pInterface, bool fAbs)
-{
-    PDRVMAINMOUSE pDrv = PPDMIMOUSECONNECTOR_2_MAINMOUSE (pInterface);
-    if (fAbs)
+
+/**
+ * @interface_method_impl{PDMIMOUSECONNECTOR,pfnAbsModeChange}
+ */
+DECLCALLBACK(void) Mouse::mouseAbsModeChange(PPDMIMOUSECONNECTOR pInterface, bool fEnabled)
+{
+    PDRVMAINMOUSE pDrv = RT_FROM_MEMBER(pInterface, DRVMAINMOUSE, IConnector);
+    if (fEnabled)
         pDrv->pMouse->uDevCaps |= MOUSE_DEVCAP_ABSOLUTE;
     else
         pDrv->pMouse->uDevCaps &= ~MOUSE_DEVCAP_ABSOLUTE;
+
     /** @todo we have to hack around the fact that VMMDev may not be
      * initialised too close to startup.  The real fix is to change the
@@ -523,5 +498,39 @@
         rc = pDrv->pMouse->getVMMDevMouseCaps(&fMouseCaps);
     AssertComRCReturnVoid(rc);
-    pDrv->pMouse->getParent()->onMouseCapabilityChange (fAbs, fMouseCaps & VMMDEV_MOUSE_GUEST_NEEDS_HOST_CURSOR);
+    pDrv->pMouse->getParent()->onMouseCapabilityChange(fEnabled, fMouseCaps & VMMDEV_MOUSE_GUEST_NEEDS_HOST_CURSOR);
+}
+
+
+/**
+ * @interface_method_impl{PDMIBASE,pfnQueryInterface}
+ */
+DECLCALLBACK(void *)  Mouse::drvQueryInterface(PPDMIBASE pInterface, const char *pszIID)
+{
+    PPDMDRVINS      pDrvIns = PDMIBASE_2_PDMDRV(pInterface);
+    PDRVMAINMOUSE   pDrv    = PDMINS_2_DATA(pDrvIns, PDRVMAINMOUSE);
+
+    PDMIBASE_RETURN_INTERFACE(pszIID, PDMIBASE, &pDrvIns->IBase);
+    PDMIBASE_RETURN_INTERFACE(pszIID, PDMIMOUSECONNECTOR, &pDrv->IConnector);
+    return NULL;
+}
+
+
+/**
+ * Destruct a mouse driver instance.
+ *
+ * @returns VBox status.
+ * @param   pDrvIns     The driver instance data.
+ */
+DECLCALLBACK(void) Mouse::drvDestruct(PPDMDRVINS pDrvIns)
+{
+    PDRVMAINMOUSE pData = PDMINS_2_DATA(pDrvIns, PDRVMAINMOUSE);
+    LogFlow(("Mouse::drvDestruct: iInstance=%d\n", pDrvIns->iInstance));
+    PDMDRV_CHECK_VERSIONS_RETURN_VOID(pDrvIns);
+
+    if (pData->pMouse)
+    {
+        AutoWriteLock mouseLock(pData->pMouse COMMA_LOCKVAL_SRC_POS);
+        pData->pMouse->mpDrv = NULL;
+    }
 }
 
