Changeset 90608 in vbox
- Timestamp:
- Aug 10, 2021 9:33:32 PM (3 years ago)
- Location:
- trunk/src/VBox/VMM/VMMAll
- Files:
-
- 2 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/VMM/VMMAll/PDMAllCritSect.cpp
r90572 r90608 508 508 * account when waiting on contended locks. 509 509 * 510 * While we usually (it can be VINF_SUCCESS) have to option via the rcBusy 511 * parameter of going to back to ring-3 and to re-start the work there, it's 512 * almost always more efficient to try wait for the lock here. The rcBusy 513 * will be used if we encounter an VERR_INTERRUPTED situation though. 514 * 515 * We must never block if VMMRZCallRing3Disable is active. 510 * While we usually (it can be VINF_SUCCESS) have the option of returning 511 * rcBusy and force the caller to go back to ring-3 and to re-start the work 512 * there, it's almost always more efficient to try wait for the lock here. 513 * The rcBusy will be used if we encounter an VERR_INTERRUPTED situation 514 * though. 516 515 */ 517 516 PVMCPUCC pVCpu = VMMGetCpu(pVM); -
trunk/src/VBox/VMM/VMMAll/PDMAllCritSectRw.cpp
r90573 r90608 734 734 735 735 /** 736 * Worker for pdmCritSectRwEnterExcl that bails out on wait failure. 737 * 738 * @returns @a rc unless corrupted. 739 * @param pVM The cross context VM structure. 740 * @param rc The status to return. 741 */ 742 DECL_NO_INLINE(static, int) pdmCritSectRwEnterExclBailOut(PPDMCRITSECTRW pThis, int rc) 743 { 744 /* 745 * Decrement the counts and return the error. 746 */ 747 for (;;) 748 { 749 uint64_t u64State = ASMAtomicReadU64(&pThis->s.Core.u64State); 750 uint64_t const u64OldState = u64State; 751 uint64_t c = (u64State & RTCSRW_CNT_WR_MASK) >> RTCSRW_CNT_WR_SHIFT; 752 AssertReturn(c > 0, pdmCritSectRwCorrupted(pThis, "Invalid write count on bailout")); 753 c--; 754 u64State &= ~RTCSRW_CNT_WR_MASK; 755 u64State |= c << RTCSRW_CNT_WR_SHIFT; 756 if (ASMAtomicCmpXchgU64(&pThis->s.Core.u64State, u64State, u64OldState)) 757 return rc; 758 759 ASMNopPause(); 760 AssertReturn(pThis->s.Core.u32Magic == RTCRITSECTRW_MAGIC, VERR_SEM_DESTROYED); 761 ASMNopPause(); 762 } 763 } 764 765 766 /** 736 767 * Worker that enters a read/write critical section with exclusive access. 737 768 * … … 879 910 ) 880 911 { 881 882 912 /* 883 913 * Wait for our turn. … … 918 948 } 919 949 if (RT_FAILURE(rc)) 920 { 921 /* Decrement the counts and return the error. */ 922 for (;;) 923 { 924 u64OldState = u64State = ASMAtomicReadU64(&pThis->s.Core.u64State); 925 uint64_t c = (u64State & RTCSRW_CNT_WR_MASK) >> RTCSRW_CNT_WR_SHIFT; 926 AssertReturn(c > 0, pdmCritSectRwCorrupted(pThis, "Invalid write count on bailout")); 927 c--; 928 u64State &= ~RTCSRW_CNT_WR_MASK; 929 u64State |= c << RTCSRW_CNT_WR_SHIFT; 930 if (ASMAtomicCmpXchgU64(&pThis->s.Core.u64State, u64State, u64OldState)) 931 break; 932 } 933 return rc; 934 } 935 950 return pdmCritSectRwEnterExclBailOut(pThis, rc); 951 952 /* Try take exclusive write ownership. */ 936 953 u64State = ASMAtomicReadU64(&pThis->s.Core.u64State); 937 954 if ((u64State & RTCSRW_DIR_MASK) == (RTCSRW_DIR_WRITE << RTCSRW_DIR_SHIFT)) … … 950 967 #ifdef IN_RING3 951 968 /* TryEnter call - decrement the number of (waiting) writers. */ 969 return pdmCritSectRwEnterExclBailOut(pThis, VERR_SEM_BUSY); 952 970 #else 953 971 /* We cannot call SUPSemEventWaitNoResume in this context. Go back to 954 972 ring-3 and do it there or return rcBusy. */ 955 #endif 956 957 for (;;) 958 { 959 u64OldState = u64State = ASMAtomicReadU64(&pThis->s.Core.u64State); 960 uint64_t c = (u64State & RTCSRW_CNT_WR_MASK) >> RTCSRW_CNT_WR_SHIFT; 961 AssertReturn(c > 0, pdmCritSectRwCorrupted(pThis, "Invalid write count on bailout")); 962 c--; 963 u64State &= ~RTCSRW_CNT_WR_MASK; 964 u64State |= c << RTCSRW_CNT_WR_SHIFT; 965 if (ASMAtomicCmpXchgU64(&pThis->s.Core.u64State, u64State, u64OldState)) 966 break; 967 } 968 969 #ifdef IN_RING3 970 return VERR_SEM_BUSY; 971 #else 973 rcBusy = pdmCritSectRwEnterExclBailOut(pThis, rcBusy); 972 974 if (rcBusy == VINF_SUCCESS) 973 975 { … … 987 989 */ 988 990 Assert((ASMAtomicReadU64(&pThis->s.Core.u64State) & RTCSRW_DIR_MASK) == (RTCSRW_DIR_WRITE << RTCSRW_DIR_SHIFT)); 991 #if 1 /** @todo consider generating less noise... */ 989 992 ASMAtomicWriteU32(&pThis->s.Core.cWriteRecursions, 1); 993 #else 994 pThis->s.Core.cWriteRecursions = 1; 995 #endif 990 996 Assert(pThis->s.Core.cWriterReads == 0); 991 997 #if defined(PDMCRITSECTRW_STRICT) && defined(IN_RING3)
Note:
See TracChangeset
for help on using the changeset viewer.