VirtualBox

Changeset 32970 in vbox for trunk/src


Ignore:
Timestamp:
Oct 7, 2010 10:08:00 AM (14 years ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
66475
Message:

RTSemEventMultiWaitEx and RTSemEventMultiWaitExDebug for windows.

Location:
trunk/src/VBox/Runtime
Files:
3 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Runtime/Makefile.kmk

    r32966 r32970  
    453453        generic/RTRandAdvCreateSystemTruer-generic.cpp \
    454454        generic/RTSemEventWait-generic.cpp \
    455         generic/RTSemEventMultiWait-generic.cpp \
     455        generic/RTSemEventMultiWait-2-ex-generic.cpp \
     456        generic/RTSemEventMultiWaitNoResume-2-ex-generic.cpp \
    456457        generic/RTSemMutexRequest-generic.cpp \
    457458        generic/RTSemMutexRequestDebug-generic.cpp \
  • trunk/src/VBox/Runtime/r3/win/semeventmulti-win.cpp

    r28800 r32970  
    4444#include <iprt/mem.h>
    4545#include <iprt/thread.h>
     46#include <iprt/time.h>
    4647#include "internal/magics.h"
    4748#include "internal/strict.h"
     
    202203
    203204/** Goto avoidance. */
    204 DECL_FORCE_INLINE(int) rtSemEventWaitHandleStatus(struct RTSEMEVENTMULTIINTERNAL *pThis, DWORD rc)
     205DECL_FORCE_INLINE(int)
     206rtSemEventWaitHandleStatus(struct RTSEMEVENTMULTIINTERNAL *pThis, uint32_t fFlags, DWORD rc)
    205207{
    206208    switch (rc)
     
    208210        case WAIT_OBJECT_0:         return VINF_SUCCESS;
    209211        case WAIT_TIMEOUT:          return VERR_TIMEOUT;
    210         case WAIT_IO_COMPLETION:    return VERR_INTERRUPTED;
     212        case WAIT_IO_COMPLETION:    return fFlags & RTSEMWAIT_FLAGS_RESUME ? VERR_TIMEOUT : VERR_INTERRUPTED;
    211213        case WAIT_ABANDONED:        return VERR_SEM_OWNER_DIED;
    212214        default:
     
    226228
    227229
    228 #undef RTSemEventMultiWaitNoResume
    229 RTDECL(int)  RTSemEventMultiWaitNoResume(RTSEMEVENTMULTI hEventMultiSem, RTMSINTERVAL cMillies)
    230 {
    231     PCRTLOCKVALSRCPOS pSrcPos = NULL;
    232 
     230DECLINLINE(int) rtSemEventMultiWinWait(RTSEMEVENTMULTI hEventMultiSem, uint32_t fFlags, uint64_t uTimeout,
     231                                       PCRTLOCKVALSRCPOS pSrcPos)
     232{
    233233    /*
    234234     * Validate input.
     
    237237    AssertPtrReturn(pThis, VERR_INVALID_HANDLE);
    238238    AssertReturn(pThis->u32Magic == RTSEMEVENTMULTI_MAGIC, VERR_INVALID_HANDLE);
    239 
    240     /*
    241      * Wait for condition.
    242      */
     239    AssertReturn(RTSEMWAIT_FLAGS_ARE_VALID(fFlags), VERR_INVALID_PARAMETER);
     240
     241    /*
     242     * Convert the timeout to a millisecond count.
     243     */
     244    uint64_t uAbsDeadline;
     245    DWORD    dwMsTimeout;
     246    if (fFlags & RTSEMWAIT_FLAGS_INDEFINITE)
     247    {
     248        dwMsTimeout  = INFINITE;
     249        uAbsDeadline = UINT64_MAX;
     250    }
     251    else
     252    {
     253        if (fFlags & RTSEMWAIT_FLAGS_NANOSECS)
     254            uTimeout = uTimeout < UINT64_MAX - UINT32_C(1000000) / 2
     255                     ? (uTimeout + UINT32_C(1000000) / 2) / UINT32_C(1000000)
     256                     : UINT64_MAX / UINT32_C(1000000);
     257        if (fFlags & RTSEMWAIT_FLAGS_ABSOLUTE)
     258        {
     259            uAbsDeadline = uTimeout;
     260            uint64_t u64Now = RTTimeSystemMilliTS();
     261            if (u64Now < uTimeout)
     262                uTimeout -= u64Now;
     263            else
     264                uTimeout = 0;
     265        }
     266        else if (fFlags & RTSEMWAIT_FLAGS_RESUME)
     267            uAbsDeadline = RTTimeSystemMilliTS() + uTimeout;
     268        else
     269            uAbsDeadline = UINT64_MAX;
     270
     271        dwMsTimeout = uTimeout < UINT32_MAX
     272                    ? (DWORD)uTimeout
     273                    : INFINITE;
     274    }
     275
     276    /*
     277     * Do the wait.
     278     */
     279    DWORD rc;
    243280#ifdef RTSEMEVENT_STRICT
    244281    RTTHREAD hThreadSelf = RTThreadSelfAutoAdopt();
    245282    if (pThis->fEverHadSignallers)
    246283    {
    247         DWORD rc = WaitForSingleObjectEx(pThis->hev,
    248                                          0 /*Timeout*/,
    249                                          TRUE /*fAlertable*/);
    250         if (rc != WAIT_TIMEOUT || cMillies == 0)
    251             return rtSemEventWaitHandleStatus(pThis, rc);
     284        do
     285            rc = WaitForSingleObjectEx(pThis->hev, 0 /*Timeout*/, TRUE /*fAlertable*/);
     286        while (rc == WAIT_IO_COMPLETION && (fFlags & RTSEMWAIT_FLAGS_RESUME));
     287        if (rc != WAIT_TIMEOUT || dwMsTimeout == 0)
     288            return rtSemEventWaitHandleStatus(pThis, fFlags, rc);
    252289        int rc9 = RTLockValidatorRecSharedCheckBlocking(&pThis->Signallers, hThreadSelf, pSrcPos, false,
    253                                                         cMillies, RTTHREADSTATE_EVENT_MULTI, true);
     290                                                        dwMsTimeout, RTTHREADSTATE_EVENT_MULTI, true);
    254291        if (RT_FAILURE(rc9))
    255292            return rc9;
     
    259296#endif
    260297    RTThreadBlocking(hThreadSelf, RTTHREADSTATE_EVENT_MULTI, true);
    261     DWORD rc = WaitForSingleObjectEx(pThis->hev,
    262                                      cMillies == RT_INDEFINITE_WAIT ? INFINITE : cMillies,
    263                                      TRUE /*fAlertable*/);
     298    rc = WaitForSingleObjectEx(pThis->hev, dwMsTimeout, TRUE /*fAlertable*/);
     299    if (rc == WAIT_IO_COMPLETION && (fFlags & RTSEMWAIT_FLAGS_RESUME))
     300    {
     301        while (   rc == WAIT_IO_COMPLETION
     302               && RTTimeSystemMilliTS() < uAbsDeadline)
     303            rc = WaitForSingleObjectEx(pThis->hev, dwMsTimeout, TRUE /*fAlertable*/);
     304
     305    }
    264306    RTThreadUnblocked(hThreadSelf, RTTHREADSTATE_EVENT_MULTI);
    265     return rtSemEventWaitHandleStatus(pThis, rc);
    266 }
     307    return rtSemEventWaitHandleStatus(pThis, fFlags, rc);
     308}
     309
     310
     311
     312#undef RTSemEventMultiWaitEx
     313RTDECL(int)  RTSemEventMultiWaitEx(RTSEMEVENTMULTI hEventMultiSem, uint32_t fFlags, uint64_t uTimeout)
     314{
     315#ifndef RTSEMEVENT_STRICT
     316    return rtSemEventMultiWinWait(hEventMultiSem, fFlags, uTimeout, NULL);
     317#else
     318    RTLOCKVALSRCPOS SrcPos = RTLOCKVALSRCPOS_INIT_NORMAL_API();
     319    return rtSemEventMultiWinWait(hEventMultiSem, fFlags, uTimeout, &SrcPos);
     320#endif
     321}
     322
     323
     324RTDECL(int)  RTSemEventMultiWaitExDebug(RTSEMEVENTMULTI hEventMultiSem, uint32_t fFlags, uint64_t uTimeout,
     325                                        RTHCUINTPTR uId, RT_SRC_POS_DECL)
     326{
     327    RTLOCKVALSRCPOS SrcPos = RTLOCKVALSRCPOS_INIT_DEBUG_API();
     328    return rtSemEventMultiWinWait(hEventMultiSem, fFlags, uTimeout, &SrcPos);
     329}
     330
    267331
    268332
  • trunk/src/VBox/Runtime/testcase/tstRTSemEventMulti.cpp

    r32966 r32970  
    100100{
    101101    RTTESTI_CHECK_RC_RETV(RTSemEventMultiWait(hSem, 0), VERR_TIMEOUT);
    102 #if 1
     102#if 0
    103103    RTTESTI_CHECK_RC_RETV(RTSemEventMultiWaitNoResume(hSem, 0), VERR_TIMEOUT);
    104104#else
     
    128128    RTTESTI_CHECK_RC_RETV(RTSemEventMultiWait(hSem, 0), VINF_SUCCESS);
    129129    RTTESTI_CHECK_RC_RETV(RTSemEventMultiWait(hSem, RT_INDEFINITE_WAIT), VINF_SUCCESS);
    130 #if 1
     130#if 0
    131131    RTTESTI_CHECK_RC_RETV(RTSemEventMultiWaitNoResume(hSem, 0), VINF_SUCCESS);
    132132    RTTESTI_CHECK_RC_RETV(RTSemEventMultiWaitNoResume(hSem, RT_INDEFINITE_WAIT), VINF_SUCCESS);
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