VirtualBox

Ignore:
Timestamp:
Jul 10, 2009 5:29:54 PM (16 years ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
49935
Message:

VBoxGuest: Implemented missing VBOXGUEST_IOCTL_CANCEL_ALL_WAITEVENTS. VBoxClient should exit cleanly now.

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

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Additions/common/VBoxGuest/VBoxGuest.cpp

    r21456 r21491  
    277277        rc2 = RTSemEventMultiDestroy(pWait->Event); AssertRC(rc2);
    278278        pWait->Event = NIL_RTSEMEVENTMULTI;
     279        pWait->pSession = NULL;
    279280        RTMemFree(pWait);
    280281    }
     
    458459 * @returns The wait-for-event entry.
    459460 * @param   pDevExt         The device extension.
    460  */
    461 static PVBOXGUESTWAIT VBoxGuestWaitAlloc(PVBOXGUESTDEVEXT pDevExt)
     461 * @param   pSession        The session that's allocating this. Can be NULL.
     462 */
     463static PVBOXGUESTWAIT VBoxGuestWaitAlloc(PVBOXGUESTDEVEXT pDevExt, PVBOXGUESTSESSION pSession)
    462464{
    463465    /*
     
    506508    pWait->fReqEvents = 0;
    507509    pWait->fResEvents = 0;
     510    pWait->pSession = pSession;
    508511#ifdef VBOX_WITH_HGCM
    509512    pWait->pHGCMReq = NULL;
     
    641644
    642645
    643 static int VBoxGuestCommonIOCtl_WaitEvent(PVBOXGUESTDEVEXT pDevExt, VBoxGuestWaitEventInfo *pInfo, size_t *pcbDataReturned,
    644                                           bool fInterruptible)
     646static int VBoxGuestCommonIOCtl_WaitEvent(PVBOXGUESTDEVEXT pDevExt, PVBOXGUESTSESSION pSession,
     647                                          VBoxGuestWaitEventInfo *pInfo,  size_t *pcbDataReturned, bool fInterruptible)
    645648{
    646649    pInfo->u32EventFlagsOut = 0;
     
    677680    }
    678681
    679     PVBOXGUESTWAIT pWait = VBoxGuestWaitAlloc(pDevExt);
     682    PVBOXGUESTWAIT pWait = VBoxGuestWaitAlloc(pDevExt, pSession);
    680683    if (!pWait)
    681684        return VERR_NO_MEMORY;
     
    724727     * Now deal with the return code.
    725728     */
    726     if (fResEvents)
     729    if (    fResEvents
     730        &&  fResEvents != UINT32_MAX)
    727731    {
    728732        pInfo->u32EventFlagsOut = fResEvents;
     
    734738        rc = VINF_SUCCESS;
    735739    }
     740    else if (   fResEvents == UINT32_MAX
     741             || rc == VERR_INTERRUPTED)
     742    {
     743        pInfo->u32Result = VBOXGUEST_WAITEVENT_INTERRUPTED;
     744        rc == VERR_INTERRUPTED;
     745        Log(("VBoxGuestCommonIOCtl: WAITEVENT: returns VERR_INTERRUPTED\n"));
     746    }
    736747    else if (rc == VERR_TIMEOUT)
    737748    {
    738749        pInfo->u32Result = VBOXGUEST_WAITEVENT_TIMEOUT;
    739750        Log(("VBoxGuestCommonIOCtl: WAITEVENT: returns VERR_TIMEOUT\n"));
    740     }
    741     else if (rc == VERR_INTERRUPTED)
    742     {
    743         pInfo->u32Result = VBOXGUEST_WAITEVENT_INTERRUPTED;
    744         Log(("VBoxGuestCommonIOCtl: WAITEVENT: returns VERR_INTERRUPTED\n"));
    745751    }
    746752    else
     
    761767
    762768
     769static int VBoxGuestCommonIOCtl_CancelAllWaitEvents(PVBOXGUESTDEVEXT pDevExt, PVBOXGUESTSESSION pSession)
     770{
     771    RTSPINLOCKTMP   Tmp = RTSPINLOCKTMP_INITIALIZER;
     772    PVBOXGUESTWAIT  pWait;
     773    int             rc = 0;
     774
     775    Log(("VBoxGuestCommonIOCtl: CANCEL_ALL_WAITEVENTS\n"));
     776
     777    /*
     778     * Walk the event list and wake up anyone with a matching session.
     779     */
     780    RTSpinlockAcquireNoInts(pDevExt->EventSpinlock, &Tmp);
     781    for (pWait = pDevExt->WaitList.pHead; pWait; pWait = pWait->pNext)
     782        if (pWait->pSession == pSession)
     783        {
     784            pWait->fResEvents = UINT32_MAX;
     785            rc |= RTSemEventMultiSignal(pWait->Event);
     786        }
     787    RTSpinlockReleaseNoInts(pDevExt->EventSpinlock, &Tmp);
     788    Assert(rc == 0);
     789
     790    return VINF_SUCCESS;
     791}
     792
     793
    763794static int VBoxGuestCommonIOCtl_VMMRequest(PVBOXGUESTDEVEXT pDevExt, PVBOXGUESTSESSION pSession,
    764795                                           VMMDevRequestHeader *pReqHdr, size_t cbData, size_t *pcbDataReturned)
     
    884915        RTSpinlockReleaseNoInts(pDevExt->EventSpinlock, &Tmp);
    885916
    886         pWait = VBoxGuestWaitAlloc(pDevExt);
     917        pWait = VBoxGuestWaitAlloc(pDevExt, NULL);
    887918        if (pWait)
    888919            break;
     
    13541385            case VBOXGUEST_IOCTL_WAITEVENT:
    13551386                CHECKRET_MIN_SIZE("WAITEVENT", sizeof(VBoxGuestWaitEventInfo));
    1356                 rc = VBoxGuestCommonIOCtl_WaitEvent(pDevExt, (VBoxGuestWaitEventInfo *)pvData, pcbDataReturned,
    1357                                                     pSession->R0Process != NIL_RTR0PROCESS);
     1387                rc = VBoxGuestCommonIOCtl_WaitEvent(pDevExt, pSession, (VBoxGuestWaitEventInfo *)pvData,
     1388                                                    pcbDataReturned, pSession->R0Process != NIL_RTR0PROCESS);
     1389                break;
     1390
     1391            case VBOXGUEST_IOCTL_CANCEL_ALL_WAITEVENTS:
     1392                if (cbData != 0)
     1393                    rc = VERR_INVALID_PARAMETER;
     1394                rc = VBoxGuestCommonIOCtl_CancelAllWaitEvents(pDevExt, pSession);
    13581395                break;
    13591396
  • trunk/src/VBox/Additions/common/VBoxGuest/VBoxGuestInternal.h

    r21376 r21491  
    3131
    3232
     33/** Pointer to the VBoxGuest per session data. */
     34typedef struct VBOXGUESTSESSION *PVBOXGUESTSESSION;
     35
    3336/** Pointer to a wait-for-event entry. */
    3437typedef struct VBOXGUESTWAIT *PVBOXGUESTWAIT;
     
    5255    /** The events we received. */
    5356    uint32_t volatile           fResEvents;
     57    /** The session that's waiting. */
     58    PVBOXGUESTSESSION           pSession;
    5459#ifdef VBOX_WITH_HGCM
    5560    /** The HGCM request we're waiting for to complete. */
     
    117122typedef VBOXGUESTDEVEXT *PVBOXGUESTDEVEXT;
    118123
    119 
    120 /** Pointer to the VBoxGuest per session data. */
    121 typedef struct VBOXGUESTSESSION *PVBOXGUESTSESSION;
    122124
    123125/**
Note: See TracChangeset for help on using the changeset viewer.

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