VirtualBox

Ignore:
Timestamp:
Jul 7, 2009 10:51:24 PM (16 years ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
49732
Message:

VBoxGuest: Fixed VBoxGuestCommonIOCtl bug where pcbDataReturned wasn't set in several cases. Fixed bug where any clients could mask the HGCM and mouse position events if they liked. Rearranged the ISR to execute the right bits with interrupts off.

Location:
trunk/src/VBox/Additions/common/VBoxGuest
Files:
4 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Additions/common/VBoxGuest/VBoxGuest-linux.c

    r21267 r21376  
    118118/** Asynchronous notification stuff.  */
    119119static struct fasync_struct    *g_pFAsyncQueue;
     120#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 0)
     121/** Whether we've create the logger or not. */
     122static volatile bool            g_fLoggerCreated;
     123/** Release logger group settings. */
     124static char                     g_szLogGrp[128];
     125/** Release logger flags settings. */
     126static char                     g_szLogFlags[128];
     127# if 0
     128/** Release logger destination settings. */
     129static char                     g_szLogDst[128];
     130/** Debug logger group settings. */
     131static char                     g_szDbgLogGrp[128];
     132/** Debug logger flags settings. */
     133static char                     g_szDbgLogFlags[128];
     134/** Debug logger destination settings. */
     135static char                     g_szDbgLogDst[128];
     136# endif
     137#endif
    120138
    121139/** Our file node major id.
     
    335353
    336354/**
    337  * Registers the ISR.
     355 * Registers the ISR and initializes the poll wait queue.
    338356 */
    339357static int __init vboxguestLinuxInitISR(void)
     
    341359    int rc;
    342360
     361    init_waitqueue_head(&g_PollEventQueue);
    343362    rc = request_irq(g_pPciDev->irq,
    344363                     vboxguestLinuxISR,
     
    461480                     RTLOGDEST_STDOUT | RTLOGDEST_DEBUGGER | RTLOGDEST_USER, NULL);
    462481    if (RT_SUCCESS(rc))
     482    {
     483#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 0)
     484        RTLogGroupSettings(pRelLogger, g_szLogGrp);
     485        RTLogFlags(pRelLogger, g_szLogFlags);
     486        //RTLogDestination(pRelLogger, g_szLogDst);
     487#endif
    463488        RTLogRelSetDefaultInstance(pRelLogger);
    464 /** @todo Add module parameters with flags, groups and destination
    465  *        specifiers. Apply them here. */
     489    }
     490#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 0)
     491    g_fLoggerCreated = true;
     492#endif
    466493
    467494    /*
     
    767794     * subscribed to async notifications.
    768795     */
     796    Log(("VBoxGuestNativeISRMousePollEvent: wake_up_all\n"));
    769797    wake_up_all(&g_PollEventQueue);
     798    Log(("VBoxGuestNativeISRMousePollEvent: kill_fasync\n"));
    770799    kill_fasync(&g_pFAsyncQueue, SIGIO, POLL_IN);
     800    Log(("VBoxGuestNativeISRMousePollEvent: done\n"));
    771801}
    772802
     
    778808EXPORT_SYMBOL(VBoxGuestIDCClose);
    779809EXPORT_SYMBOL(VBoxGuestIDCCall);
     810
     811
     812#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 0)
     813
     814/** log and dbg_log parameter setter. */
     815static int vboxguestLinuxParamLogGrpSet(const char *pszValue, struct kernel_param *pParam)
     816{
     817    if (g_fLoggerCreated)
     818    {
     819        PRTLOGGER pLogger = pParam->name[0] == 'd' ? RTLogDefaultInstance() : RTLogRelDefaultInstance();
     820        if (pLogger)
     821            RTLogGroupSettings(pLogger, pszValue);
     822    }
     823    else if (pParam->name[0] != 'd')
     824        strlcpy(&g_szLogGrp[0], pszValue, sizeof(g_szLogGrp));
     825
     826    return 0;
     827}
     828
     829
     830/** log and dbg_log parameter getter. */
     831static int vboxguestLinuxParamLogGrpGet(char *pszBuf, struct kernel_param *pParam)
     832{
     833    /** @todo add a serializer */
     834    *pszBuf = '\0';
     835    return 0;
     836}
     837
     838
     839/** log and dbg_log_flags parameter setter. */
     840static int vboxguestLinuxParamLogFlagsSet(const char *pszValue, struct kernel_param *pParam)
     841{
     842    if (g_fLoggerCreated)
     843    {
     844        PRTLOGGER pLogger = pParam->name[0] == 'd' ? RTLogDefaultInstance() : RTLogRelDefaultInstance();
     845        if (pLogger)
     846            RTLogFlags(pLogger, pszValue);
     847    }
     848    else if (pParam->name[0] != 'd')
     849        strlcpy(&g_szLogFlags[0], pszValue, sizeof(g_szLogFlags));
     850    return 0;
     851}
     852
     853
     854/** log and dbg_log_flags parameter getter. */
     855static int vboxguestLinuxParamLogFlagsGet(char *pszBuf, struct kernel_param *pParam)
     856{
     857    /** @todo add a flags serializer */
     858    *pszBuf = '\0';
     859    return 0;
     860}
     861
     862
     863/** log and dbg_log_dest parameter setter. */
     864static int vboxguestLinuxParamLogDstSet(const char *pszValue, struct kernel_param *pParam)
     865{
     866    /** @todo  */
     867    return 0;
     868}
     869
     870
     871/** log and dbg_log_dest parameter getter. */
     872static int vboxguestLinuxParamLogDstGet(char *pszBuf, struct kernel_param *pParam)
     873{
     874    /** @todo add a destination serializer */
     875    *pszBuf = '\0';
     876    return 0;
     877}
     878
     879/*
     880 * Define module parameters.
     881 */
     882module_param_call(log,            vboxguestLinuxParamLogGrpSet,   vboxguestLinuxParamLogGrpGet,   NULL, 0664);
     883module_param_call(log_flags,      vboxguestLinuxParamLogFlagsSet, vboxguestLinuxParamLogFlagsGet, NULL, 0664);
     884module_param_call(log_dest,       vboxguestLinuxParamLogDstSet,   vboxguestLinuxParamLogDstGet,   NULL, 0664);
     885# ifdef LOG_ENABLED
     886module_param_call(dbg_log,        vboxguestLinuxParamLogGrpSet,   vboxguestLinuxParamLogGrpGet,   NULL, 0664);
     887module_param_call(dbg_log_flags,  vboxguestLinuxParamLogFlagsSet, vboxguestLinuxParamLogFlagsGet, NULL, 0664);
     888module_param_call(dbg_log_dest,   vboxguestLinuxParamLogDstSet,   vboxguestLinuxParamLogDstGet,   NULL, 0664);
     889# endif
     890
     891#endif /* 2.6.0 and later */
     892
    780893
    781894module_init(vboxguestLinuxModInit);
  • trunk/src/VBox/Additions/common/VBoxGuest/VBoxGuest-os2.cpp

    r21227 r21376  
    607607         * Process the IOCtl.
    608608         */
    609         size_t cbDataReturned = 0;
    610         rc = VBoxGuestCommonIOCtl(iFunction, &g_DevExt, pSession,
    611                                   pvParm, *pcbParm, &cbDataReturned);
     609        size_t cbDataReturned;
     610        rc = VBoxGuestCommonIOCtl(iFunction, &g_DevExt, pSession, pvParm, *pcbParm, &cbDataReturned);
    612611
    613612        /*
  • trunk/src/VBox/Additions/common/VBoxGuest/VBoxGuest.cpp

    r21337 r21376  
    142142 *                          This is optional, pass 0 if not present.
    143143 * @param   enmOSType       The guest OS type to report to the VMMDev.
    144  * @param   fEvents         Additional requested events (like Mouse events).
     144 * @param   fFixedEvents    Events that will be enabled upon init and no client
     145 *                          will ever be allowed to mask.
    145146 */
    146147int VBoxGuestInitDevExt(PVBOXGUESTDEVEXT pDevExt, uint16_t IOPortBase,
    147                         void *pvMMIOBase, uint32_t cbMMIO, VBOXOSTYPE enmOSType, uint32_t fEvents)
     148                        void *pvMMIOBase, uint32_t cbMMIO, VBOXOSTYPE enmOSType, uint32_t fFixedEvents)
    148149{
    149150    int rc, rc2;
     151
     152    /*
     153     * Adjust fFixedEvents.
     154     */
     155#ifdef VBOX_WITH_HGCM
     156    fFixedEvents |= VMMDEV_EVENT_HGCM;
     157#endif
    150158
    151159    /*
     
    154162    pDevExt->IOPortBase = IOPortBase;
    155163    pDevExt->pVMMDevMemory = NULL;
     164    pDevExt->fFixedEvents = fFixedEvents;
    156165    pDevExt->pIrqAckEvents = NULL;
     166    pDevExt->PhysIrqAckEvents = NIL_RTCCPHYS;
    157167    pDevExt->WaitList.pHead = NULL;
    158168    pDevExt->WaitList.pTail = NULL;
     
    190200     * Create the wait and seesion spinlocks.
    191201     */
    192     rc = RTSpinlockCreate(&pDevExt->WaitSpinlock);
     202    rc = RTSpinlockCreate(&pDevExt->EventSpinlock);
    193203    if (RT_SUCCESS(rc))
    194204        rc = RTSpinlockCreate(&pDevExt->SessionSpinlock);
     
    196206    {
    197207        Log(("VBoxGuestInitDevExt: failed to spinlock, rc=%d!\n", rc));
    198         if (pDevExt->WaitSpinlock != NIL_RTSPINLOCK)
    199             RTSpinlockDestroy(pDevExt->WaitSpinlock);
     208        if (pDevExt->EventSpinlock != NIL_RTSPINLOCK)
     209            RTSpinlockDestroy(pDevExt->EventSpinlock);
    200210        return rc;
    201211    }
     
    212222        if (RT_SUCCESS(rc))
    213223        {
     224            pDevExt->PhysIrqAckEvents = VbglPhysHeapGetPhysAddr(pDevExt->pIrqAckEvents);
     225            Assert(pDevExt->PhysIrqAckEvents != 0);
     226
    214227            rc = vboxGuestInitReportGuestInfo(pDevExt, enmOSType);
    215228            if (RT_SUCCESS(rc))
    216229            {
    217 #ifdef VBOX_WITH_HGCM
    218                 fEvents |= VMMDEV_EVENT_HGCM;
    219 #endif
    220                 rc = vboxGuestInitFilterMask(pDevExt, fEvents);
     230                rc = vboxGuestInitFilterMask(pDevExt, fFixedEvents);
    221231                if (RT_SUCCESS(rc))
    222232                {
     
    245255        Log(("VBoxGuestInitDevExt: VbglInit failed, rc=%Rrc\n", rc));
    246256
    247     rc2 = RTSpinlockDestroy(pDevExt->WaitSpinlock); AssertRC(rc2);
     257    rc2 = RTSpinlockDestroy(pDevExt->EventSpinlock); AssertRC(rc2);
    248258    rc2 = RTSpinlockDestroy(pDevExt->SessionSpinlock); AssertRC(rc2);
    249259    return rc; /* (failed) */
     
    292302 */
    293303
    294     rc2 = RTSpinlockDestroy(pDevExt->WaitSpinlock); AssertRC(rc2);
     304    rc2 = RTSpinlockDestroy(pDevExt->EventSpinlock); AssertRC(rc2);
    295305    rc2 = RTSpinlockDestroy(pDevExt->SessionSpinlock); AssertRC(rc2);
    296306
     
    458468    {
    459469        RTSPINLOCKTMP Tmp = RTSPINLOCKTMP_INITIALIZER;
    460         RTSpinlockAcquireNoInts(pDevExt->WaitSpinlock, &Tmp);
     470        RTSpinlockAcquireNoInts(pDevExt->EventSpinlock, &Tmp);
    461471
    462472        pWait = pDevExt->FreeList.pTail;
     
    464474            VBoxGuestWaitUnlink(&pDevExt->FreeList, pWait);
    465475
    466         RTSpinlockReleaseNoInts(pDevExt->WaitSpinlock, &Tmp);
     476        RTSpinlockReleaseNoInts(pDevExt->EventSpinlock, &Tmp);
    467477    }
    468478    if (!pWait)
     
    531541{
    532542    RTSPINLOCKTMP Tmp = RTSPINLOCKTMP_INITIALIZER;
    533     RTSpinlockAcquireNoInts(pDevExt->WaitSpinlock, &Tmp);
     543    RTSpinlockAcquireNoInts(pDevExt->EventSpinlock, &Tmp);
    534544    VBoxGuestWaitFreeLocked(pDevExt, pWait);
    535     RTSpinlockReleaseNoInts(pDevExt->WaitSpinlock, &Tmp);
     545    RTSpinlockReleaseNoInts(pDevExt->EventSpinlock, &Tmp);
    536546}
    537547
     
    617627    {
    618628        ASMAtomicAndU32(&pDevExt->f32PendingEvents, ~fMatches);
    619         RTSpinlockReleaseNoInts(pDevExt->WaitSpinlock, pTmp);
     629        RTSpinlockReleaseNoInts(pDevExt->EventSpinlock, pTmp);
    620630
    621631        pInfo->u32EventFlagsOut = fMatches;
     
    654664     */
    655665    RTSPINLOCKTMP Tmp = RTSPINLOCKTMP_INITIALIZER;
    656     RTSpinlockAcquireNoInts(pDevExt->WaitSpinlock, &Tmp);
     666    RTSpinlockAcquireNoInts(pDevExt->EventSpinlock, &Tmp);
    657667    int rc = WaitEventCheckCondition(pDevExt, pInfo, iEvent, fReqEvents, &Tmp);
    658668    if (rc == VINF_SUCCESS)
    659669        return rc;
    660     RTSpinlockReleaseNoInts(pDevExt->WaitSpinlock, &Tmp);
     670    RTSpinlockReleaseNoInts(pDevExt->EventSpinlock, &Tmp);
    661671
    662672    if (!pInfo->u32TimeoutIn)
     
    677687     * Otherwise enter into the list and go to sleep waiting for the ISR to signal us.
    678688     */
    679     RTSpinlockAcquireNoInts(pDevExt->WaitSpinlock, &Tmp);
     689    RTSpinlockAcquireNoInts(pDevExt->EventSpinlock, &Tmp);
    680690    rc = WaitEventCheckCondition(pDevExt, pInfo, iEvent, fReqEvents, &Tmp);
    681691    if (rc == VINF_SUCCESS)
     
    685695    }
    686696    VBoxGuestWaitAppend(&pDevExt->WaitList, pWait);
    687     RTSpinlockReleaseNoInts(pDevExt->WaitSpinlock, &Tmp);
     697    RTSpinlockReleaseNoInts(pDevExt->EventSpinlock, &Tmp);
    688698
    689699    if (fInterruptible)
     
    705715     * Unlink the wait item and dispose of it.
    706716     */
    707     RTSpinlockAcquireNoInts(pDevExt->WaitSpinlock, &Tmp);
     717    RTSpinlockAcquireNoInts(pDevExt->EventSpinlock, &Tmp);
    708718    VBoxGuestWaitUnlink(&pDevExt->WaitList, pWait);
    709719    const uint32_t fResEvents = pWait->fResEvents;
    710720    VBoxGuestWaitFreeLocked(pDevExt, pWait);
    711     RTSpinlockReleaseNoInts(pDevExt->WaitSpinlock, &Tmp);
     721    RTSpinlockReleaseNoInts(pDevExt->EventSpinlock, &Tmp);
    712722
    713723    /*
     
    832842    pReq->u32OrMask = pInfo->u32OrMask;
    833843    pReq->u32NotMask = pInfo->u32NotMask;
    834 
     844    pReq->u32NotMask &= ~pDevExt->fFixedEvents; /* don't permit these to be cleared! */
    835845    rc = VbglGRPerform(&pReq->header);
    836846    if (RT_FAILURE(rc))
     
    866876    for (;;)
    867877    {
    868         RTSpinlockAcquireNoInts(pDevExt->WaitSpinlock, &Tmp);
     878        RTSpinlockAcquireNoInts(pDevExt->EventSpinlock, &Tmp);
    869879        if ((pHdr->fu32Flags & VBOX_HGCM_REQ_DONE) != 0)
    870880        {
    871             RTSpinlockReleaseNoInts(pDevExt->WaitSpinlock, &Tmp);
     881            RTSpinlockReleaseNoInts(pDevExt->EventSpinlock, &Tmp);
    872882            return;
    873883        }
    874         RTSpinlockReleaseNoInts(pDevExt->WaitSpinlock, &Tmp);
     884        RTSpinlockReleaseNoInts(pDevExt->EventSpinlock, &Tmp);
    875885
    876886        pWait = VBoxGuestWaitAlloc(pDevExt);
     
    889899     * Otherwise link us into the HGCM wait list and go to sleep.
    890900     */
    891     RTSpinlockAcquireNoInts(pDevExt->WaitSpinlock, &Tmp);
     901    RTSpinlockAcquireNoInts(pDevExt->EventSpinlock, &Tmp);
    892902    if ((pHdr->fu32Flags & VBOX_HGCM_REQ_DONE) != 0)
    893903    {
    894904        VBoxGuestWaitFreeLocked(pDevExt, pWait);
    895         RTSpinlockReleaseNoInts(pDevExt->WaitSpinlock, &Tmp);
     905        RTSpinlockReleaseNoInts(pDevExt->EventSpinlock, &Tmp);
    896906        return;
    897907    }
    898908    VBoxGuestWaitAppend(&pDevExt->HGCMWaitList, pWait);
    899     RTSpinlockReleaseNoInts(pDevExt->WaitSpinlock, &Tmp);
     909    RTSpinlockReleaseNoInts(pDevExt->EventSpinlock, &Tmp);
    900910
    901911    int rc;
     
    914924        LogRel(("VBoxGuestHGCMAsyncWaitCallback: wait failed! %Rrc\n", rc));
    915925
    916     RTSpinlockAcquireNoInts(pDevExt->WaitSpinlock, &Tmp);
     926    RTSpinlockAcquireNoInts(pDevExt->EventSpinlock, &Tmp);
    917927    VBoxGuestWaitUnlink(&pDevExt->HGCMWaitList, pWait);
    918928    VBoxGuestWaitFreeLocked(pDevExt, pWait);
    919     RTSpinlockReleaseNoInts(pDevExt->WaitSpinlock, &Tmp);
     929    RTSpinlockReleaseNoInts(pDevExt->EventSpinlock, &Tmp);
    920930}
    921931
     
    929939{
    930940    PVBOXGUESTDEVEXT pDevExt = (PVBOXGUESTDEVEXT)pvUser;
    931     LogFunc(("requestType=%d\n", pHdr->header.requestType));
     941    Log(("VBoxGuestHGCMAsyncWaitCallback: requestType=%d\n", pHdr->header.requestType));
    932942    VBoxGuestHGCMAsyncWaitCallbackWorker((VMMDevHGCMRequestHeader volatile *)pHdr,
    933943                                         pDevExt,
     
    946956{
    947957    PVBOXGUESTDEVEXT pDevExt = (PVBOXGUESTDEVEXT)pvUser;
    948     LogFunc(("requestType=%d\n", pHdr->header.requestType));
     958    Log(("VBoxGuestHGCMAsyncWaitCallbackInterruptible: requestType=%d\n", pHdr->header.requestType));
    949959    VBoxGuestHGCMAsyncWaitCallbackWorker((VMMDevHGCMRequestHeader volatile *)pHdr,
    950960                                         pDevExt,
     
    12371247 * @param   pcbDataReturned     Where to store the amount of returned data. Can be NULL.
    12381248 */
    1239 int  VBoxGuestCommonIOCtl(unsigned iFunction, PVBOXGUESTDEVEXT pDevExt, PVBOXGUESTSESSION pSession,
    1240                           void *pvData, size_t cbData, size_t *pcbDataReturned)
     1249int VBoxGuestCommonIOCtl(unsigned iFunction, PVBOXGUESTDEVEXT pDevExt, PVBOXGUESTSESSION pSession,
     1250                         void *pvData, size_t cbData, size_t *pcbDataReturned)
    12411251{
    12421252    Log(("VBoxGuestCommonIOCtl: iFunction=%#x pDevExt=%p pSession=%p pvData=%p cbData=%zu\n",
    12431253         iFunction, pDevExt, pSession, pvData, cbData));
     1254
     1255    /*
     1256     * Make sure the returned data size is set to zero.
     1257     */
     1258    if (pcbDataReturned)
     1259        *pcbDataReturned = 0;
    12441260
    12451261    /*
     
    13961412bool VBoxGuestCommonISR(PVBOXGUESTDEVEXT pDevExt)
    13971413{
    1398     /*
    1399      * Now we have to find out whether it was our IRQ. Read the event mask
    1400      * from our device to see if there are any pending events.
    1401      */
    1402     bool fOurIrq = pDevExt->pVMMDevMemory->V.V1_04.fHaveEvents;
     1414    bool                    fMousePositionChanged = false;
     1415    RTSPINLOCKTMP           Tmp                   = RTSPINLOCKTMP_INITIALIZER;
     1416    VMMDevEvents volatile  *pReq                  = pDevExt->pIrqAckEvents;
     1417    int                     rc                    = 0;
     1418    bool                    fOurIrq;
     1419
     1420    /*
     1421     * Make sure we've initalized the device extension.
     1422     */
     1423    if (RT_UNLIKELY(!pReq))
     1424        return false;
     1425
     1426    /*
     1427     * Enter the spinlock and check if it's our IRQ or not.
     1428     */
     1429    RTSpinlockAcquireNoInts(pDevExt->EventSpinlock, &Tmp);
     1430    fOurIrq = pDevExt->pVMMDevMemory->V.V1_04.fHaveEvents;
    14031431    if (fOurIrq)
    14041432    {
    1405         /* Acknowlegde events. */
    1406         VMMDevEvents *pReq = pDevExt->pIrqAckEvents;
    1407         int rc = VbglGRPerform(&pReq->header);
    1408         if (    RT_SUCCESS(rc)
    1409             &&  RT_SUCCESS(pReq->header.rc))
     1433        /*
     1434         * Acknowlegde events.
     1435         * We don't use VbglGRPerform here as it may take another spinlocks.
     1436         */
     1437        pReq->header.rc = VERR_INTERNAL_ERROR;
     1438        pReq->events    = 0;
     1439        ASMCompilerBarrier();
     1440        ASMOutU32(pDevExt->IOPortBase + VMMDEV_PORT_OFF_REQUEST, (uint32_t)pDevExt->PhysIrqAckEvents);
     1441        ASMCompilerBarrier();   /* paranoia */
     1442        if (RT_SUCCESS(pReq->header.rc))
    14101443        {
    1411             uint32_t fEvents = pReq->events;
     1444            uint32_t        fEvents = pReq->events;
     1445            PVBOXGUESTWAIT  pWait;
     1446
    14121447            Log(("VBoxGuestCommonISR: acknowledge events succeeded %#RX32\n", fEvents));
    14131448
    14141449            /*
    1415              * Enter the spinlock and examin the waiting threads.
     1450             * VMMDEV_EVENT_MOUSE_POSITION_CHANGED can only be polled for.
    14161451             */
    1417             int rc2 = 0;
    1418             PVBOXGUESTWAIT pWait;
    1419             RTSPINLOCKTMP Tmp = RTSPINLOCKTMP_INITIALIZER;
    1420             RTSpinlockAcquireNoInts(pDevExt->WaitSpinlock, &Tmp);
    1421 
    1422             /** @todo This looks wrong: Seems like VMMDEV_EVENT_HGCM will always be set in
    1423              *        f32PendingEvents... */
     1452            if (fEvents & VMMDEV_EVENT_MOUSE_POSITION_CHANGED)
     1453            {
     1454                fMousePositionChanged = true;
     1455                fEvents &= ~VMMDEV_EVENT_MOUSE_POSITION_CHANGED;
     1456            }
     1457
    14241458#ifdef VBOX_WITH_HGCM
    1425             /* The HGCM event/list is kind of different in that we evaluate all entries. */
     1459            /*
     1460             * The HGCM event/list is kind of different in that we evaluate all entries.
     1461             */
    14261462            if (fEvents & VMMDEV_EVENT_HGCM)
     1463            {
    14271464                for (pWait = pDevExt->HGCMWaitList.pHead; pWait; pWait = pWait->pNext)
    14281465                    if (    !pWait->fResEvents
     
    14301467                    {
    14311468                        pWait->fResEvents = VMMDEV_EVENT_HGCM;
    1432                         rc2 |= RTSemEventMultiSignal(pWait->Event);
     1469                        rc |= RTSemEventMultiSignal(pWait->Event);
    14331470                    }
    1434 #endif
    1435 
    1436             /* VMMDEV_EVENT_MOUSE_POSITION_CHANGED can only be polled for. */
    1437 #if defined(RT_OS_LINUX) || defined(RT_OS_SOLARIS)
    1438             if (fEvents & VMMDEV_EVENT_MOUSE_POSITION_CHANGED)
    1439             {
    1440                 pDevExt->u32MousePosChangedSeq++;
    1441                 VBoxGuestNativeISRMousePollEvent(pDevExt);
     1471                fEvents &= ~VMMDEV_EVENT_HGCM;
    14421472            }
    14431473#endif
    1444             fEvents &= ~VMMDEV_EVENT_MOUSE_POSITION_CHANGED;
    1445 
    1446             /* Normal FIFO evaluation. */
     1474
     1475            /*
     1476             * Normal FIFO waiter evaluation.
     1477             */
    14471478            fEvents |= pDevExt->f32PendingEvents;
    14481479            for (pWait = pDevExt->WaitList.pHead; pWait; pWait = pWait->pNext)
     
    14511482                    pWait->fResEvents = pWait->fReqEvents & fEvents;
    14521483                    fEvents &= ~pWait->fResEvents;
    1453                     rc2 |= RTSemEventMultiSignal(pWait->Event);
     1484                    rc |= RTSemEventMultiSignal(pWait->Event);
    14541485                    if (!fEvents)
    14551486                        break;
    14561487                }
    1457 
    1458             ASMAtomicXchgU32(&pDevExt->f32PendingEvents, fEvents);
    1459             RTSpinlockReleaseNoInts(pDevExt->WaitSpinlock, &Tmp);
    1460             Assert(rc2 == 0);
     1488            ASMAtomicWriteU32(&pDevExt->f32PendingEvents, fEvents);
    14611489        }
    14621490        else /* something is serious wrong... */
    1463             Log(("VBoxGuestCommonISR: acknowledge events failed rc=%d, header rc=%d (events=%#x)!!\n",
    1464                  rc, pReq->header.rc, pReq->events));
     1491            Log(("VBoxGuestCommonISR: acknowledge events failed rc=%d (events=%#x)!!\n",
     1492                 pReq->header.rc, pReq->events));
    14651493    }
    14661494    else
    14671495        LogFlow(("VBoxGuestCommonISR: not ours\n"));
    14681496
     1497    /*
     1498     * Work the poll and async notification queues on OSes that implements that.
     1499     * Do this outside the spinlock to prevent some recursive spinlocking.
     1500     */
     1501    RTSpinlockReleaseNoInts(pDevExt->EventSpinlock, &Tmp);
     1502
     1503    if (fMousePositionChanged)
     1504    {
     1505        ASMAtomicIncU32(&pDevExt->u32MousePosChangedSeq);
     1506        VBoxGuestNativeISRMousePollEvent(pDevExt);
     1507    }
     1508
     1509    Assert(rc == 0);
    14691510    return fOurIrq;
    14701511}
  • trunk/src/VBox/Additions/common/VBoxGuest/VBoxGuestInternal.h

    r21227 r21376  
    8181    /** Pointer to the mapping of the VMMDev adapter memory. */
    8282    VMMDevMemory volatile      *pVMMDevMemory;
     83    /** Events we won't permit anyone to filter out. */
     84    uint32_t                    fFixedEvents;
    8385
     86    /** Spinlock protecting the signaling and resetting of the wait-for-event
     87     * semaphores as well as the event acking in the ISR. */
     88    RTSPINLOCK                  EventSpinlock;
    8489    /** Preallocated VMMDevEvents for the IRQ handler. */
    8590    VMMDevEvents               *pIrqAckEvents;
    86     /** Spinlock protecting the signaling and resetting of the wait-for-event semaphores. */
    87     RTSPINLOCK                  WaitSpinlock;
     91    /** The physical address of pIrqAckEvents. */
     92    RTCCPHYS                    PhysIrqAckEvents;
    8893    /** Wait-for-event list for threads waiting for multiple events. */
    8994    VBOXGUESTWAITLIST           WaitList;
     
    179184 * ISR callback for notifying threads polling for mouse events.
    180185 *
     186 * This is called at the end of the ISR, after leaving the event spinlock, if
     187 * VMMDEV_EVENT_MOUSE_POSITION_CHANGED was raised by the host.
     188 *
    181189 * @param   pDevExt     The device extension.
    182190 */
Note: See TracChangeset for help on using the changeset viewer.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette