- Timestamp:
- Oct 7, 2010 10:08:00 AM (14 years ago)
- svn:sync-xref-src-repo-rev:
- 66475
- Location:
- trunk/src/VBox/Runtime
- Files:
-
- 3 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Runtime/Makefile.kmk
r32966 r32970 453 453 generic/RTRandAdvCreateSystemTruer-generic.cpp \ 454 454 generic/RTSemEventWait-generic.cpp \ 455 generic/RTSemEventMultiWait-generic.cpp \ 455 generic/RTSemEventMultiWait-2-ex-generic.cpp \ 456 generic/RTSemEventMultiWaitNoResume-2-ex-generic.cpp \ 456 457 generic/RTSemMutexRequest-generic.cpp \ 457 458 generic/RTSemMutexRequestDebug-generic.cpp \ -
trunk/src/VBox/Runtime/r3/win/semeventmulti-win.cpp
r28800 r32970 44 44 #include <iprt/mem.h> 45 45 #include <iprt/thread.h> 46 #include <iprt/time.h> 46 47 #include "internal/magics.h" 47 48 #include "internal/strict.h" … … 202 203 203 204 /** Goto avoidance. */ 204 DECL_FORCE_INLINE(int) rtSemEventWaitHandleStatus(struct RTSEMEVENTMULTIINTERNAL *pThis, DWORD rc) 205 DECL_FORCE_INLINE(int) 206 rtSemEventWaitHandleStatus(struct RTSEMEVENTMULTIINTERNAL *pThis, uint32_t fFlags, DWORD rc) 205 207 { 206 208 switch (rc) … … 208 210 case WAIT_OBJECT_0: return VINF_SUCCESS; 209 211 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; 211 213 case WAIT_ABANDONED: return VERR_SEM_OWNER_DIED; 212 214 default: … … 226 228 227 229 228 #undef RTSemEventMultiWaitNoResume 229 RTDECL(int) RTSemEventMultiWaitNoResume(RTSEMEVENTMULTI hEventMultiSem, RTMSINTERVAL cMillies) 230 { 231 PCRTLOCKVALSRCPOS pSrcPos = NULL; 232 230 DECLINLINE(int) rtSemEventMultiWinWait(RTSEMEVENTMULTI hEventMultiSem, uint32_t fFlags, uint64_t uTimeout, 231 PCRTLOCKVALSRCPOS pSrcPos) 232 { 233 233 /* 234 234 * Validate input. … … 237 237 AssertPtrReturn(pThis, VERR_INVALID_HANDLE); 238 238 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; 243 280 #ifdef RTSEMEVENT_STRICT 244 281 RTTHREAD hThreadSelf = RTThreadSelfAutoAdopt(); 245 282 if (pThis->fEverHadSignallers) 246 283 { 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); 252 289 int rc9 = RTLockValidatorRecSharedCheckBlocking(&pThis->Signallers, hThreadSelf, pSrcPos, false, 253 cMillies, RTTHREADSTATE_EVENT_MULTI, true);290 dwMsTimeout, RTTHREADSTATE_EVENT_MULTI, true); 254 291 if (RT_FAILURE(rc9)) 255 292 return rc9; … … 259 296 #endif 260 297 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 } 264 306 RTThreadUnblocked(hThreadSelf, RTTHREADSTATE_EVENT_MULTI); 265 return rtSemEventWaitHandleStatus(pThis, rc); 266 } 307 return rtSemEventWaitHandleStatus(pThis, fFlags, rc); 308 } 309 310 311 312 #undef RTSemEventMultiWaitEx 313 RTDECL(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 324 RTDECL(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 267 331 268 332 -
trunk/src/VBox/Runtime/testcase/tstRTSemEventMulti.cpp
r32966 r32970 100 100 { 101 101 RTTESTI_CHECK_RC_RETV(RTSemEventMultiWait(hSem, 0), VERR_TIMEOUT); 102 #if 1102 #if 0 103 103 RTTESTI_CHECK_RC_RETV(RTSemEventMultiWaitNoResume(hSem, 0), VERR_TIMEOUT); 104 104 #else … … 128 128 RTTESTI_CHECK_RC_RETV(RTSemEventMultiWait(hSem, 0), VINF_SUCCESS); 129 129 RTTESTI_CHECK_RC_RETV(RTSemEventMultiWait(hSem, RT_INDEFINITE_WAIT), VINF_SUCCESS); 130 #if 1130 #if 0 131 131 RTTESTI_CHECK_RC_RETV(RTSemEventMultiWaitNoResume(hSem, 0), VINF_SUCCESS); 132 132 RTTESTI_CHECK_RC_RETV(RTSemEventMultiWaitNoResume(hSem, RT_INDEFINITE_WAIT), VINF_SUCCESS);
Note:
See TracChangeset
for help on using the changeset viewer.