儲存庫 vbox 的更動 37203
- 時間撮記:
- 2011-5-24 下午04:12:43 (14 年 以前)
- 檔案:
-
- 修改 1 筆資料
圖例:
- 未更動
- 新增
- 刪除
-
trunk/src/VBox/VMM/VMMR0/GMMR0.cpp
r37195 r37203 400 400 /** The mapping lock this chunk is using using. UINT16_MAX if nobody is 401 401 * mapping or freeing anything. (Giant mtx.) */ 402 uint8_t volatile i MemLock;402 uint8_t volatile iChunkMtx; 403 403 /** Flags field reserved for future use (like eliminating enmType). 404 404 * (Giant mtx.) */ … … 571 571 /** Chunk locks for reducing lock contention without having to allocate 572 572 * one lock per chunk. */ 573 RTSEMFASTMUTEX ahChunkMtx[64]; 573 struct 574 { 575 /** The mutex */ 576 RTSEMFASTMUTEX hMtx; 577 /** The number of threads currently using this mutex. */ 578 uint32_t volatile cUsers; 579 } aChunkMtx[64]; 574 580 } GMM; 575 581 /** Pointer to the GMM instance. */ … … 730 736 { 731 737 unsigned iMtx; 732 for (iMtx = 0; iMtx < RT_ELEMENTS(pGMM->a hChunkMtx); iMtx++)738 for (iMtx = 0; iMtx < RT_ELEMENTS(pGMM->aChunkMtx); iMtx++) 733 739 { 734 rc = RTSemFastMutexCreate(&pGMM->a hChunkMtx[iMtx]);740 rc = RTSemFastMutexCreate(&pGMM->aChunkMtx[iMtx].hMtx); 735 741 if (RT_FAILURE(rc)) 736 742 break; … … 783 789 */ 784 790 while (iMtx-- > 0) 785 RTSemFastMutexDestroy(pGMM->a hChunkMtx[iMtx]);791 RTSemFastMutexDestroy(pGMM->aChunkMtx[iMtx].hMtx); 786 792 } 787 793 RTSemFastMutexDestroy(pGMM->hMtx); … … 829 835 830 836 /* Destroy the chunk locks. */ 831 for (unsigned iMtx = 0; iMtx++ < RT_ELEMENTS(pGMM->ahChunkMtx); iMtx++) 832 { 833 RTSemFastMutexDestroy(pGMM->ahChunkMtx[iMtx]); 834 pGMM->ahChunkMtx[iMtx] = NIL_RTSEMFASTMUTEX; 837 for (unsigned iMtx = 0; iMtx++ < RT_ELEMENTS(pGMM->aChunkMtx); iMtx++) 838 { 839 Assert(pGMM->aChunkMtx[iMtx].cUsers == 0); 840 RTSemFastMutexDestroy(pGMM->aChunkMtx[iMtx].hMtx); 841 pGMM->aChunkMtx[iMtx].hMtx = NIL_RTSEMFASTMUTEX; 835 842 } 836 843 … … 993 1000 { 994 1001 Assert(fFlags > GMMR0CHUNK_MTX_INVALID && fFlags < GMMR0CHUNK_MTX_END); 1002 Assert(pGMM->hMtxOwner == RTThreadNativeSelf()); 1003 995 1004 pMtxState->pGMM = pGMM; 996 1005 pMtxState->fFlags = (uint8_t)fFlags; 997 1006 998 1007 /* 999 * Get the lock index .1008 * Get the lock index and reference the lock. 1000 1009 */ 1001 1010 Assert(pGMM->hMtxOwner == RTThreadNativeSelf()); 1002 uint32_t iChunkMtx = pChunk->i MemLock;1011 uint32_t iChunkMtx = pChunk->iChunkMtx; 1003 1012 if (iChunkMtx == UINT8_MAX) 1004 1013 { 1005 /** @todo skip mutexes that are currently owned. */1006 1014 iChunkMtx = pGMM->iNextChunkMtx++; 1007 iChunkMtx %= RT_ELEMENTS(pGMM->ahChunkMtx); 1008 pChunk->iMemLock = iChunkMtx; 1009 } 1010 AssertCompile(RT_ELEMENTS(pGMM->ahChunkMtx) < UINT8_MAX); 1015 iChunkMtx %= RT_ELEMENTS(pGMM->aChunkMtx); 1016 1017 /* Try get an unused one... */ 1018 if (pGMM->aChunkMtx[iChunkMtx].cUsers) 1019 { 1020 iChunkMtx = pGMM->iNextChunkMtx++; 1021 iChunkMtx %= RT_ELEMENTS(pGMM->aChunkMtx); 1022 if (pGMM->aChunkMtx[iChunkMtx].cUsers) 1023 { 1024 iChunkMtx = pGMM->iNextChunkMtx++; 1025 iChunkMtx %= RT_ELEMENTS(pGMM->aChunkMtx); 1026 if (pGMM->aChunkMtx[iChunkMtx].cUsers) 1027 { 1028 iChunkMtx = pGMM->iNextChunkMtx++; 1029 iChunkMtx %= RT_ELEMENTS(pGMM->aChunkMtx); 1030 } 1031 } 1032 } 1033 1034 pChunk->iChunkMtx = iChunkMtx; 1035 } 1036 AssertCompile(RT_ELEMENTS(pGMM->aChunkMtx) < UINT8_MAX); 1011 1037 pMtxState->iChunkMtx = (uint8_t)iChunkMtx; 1038 ASMAtomicIncU32(&pGMM->aChunkMtx[iChunkMtx].cUsers); 1012 1039 1013 1040 /* … … 1024 1051 * Take the chunk mutex. 1025 1052 */ 1026 int rc = RTSemFastMutexRequest(pGMM->a hChunkMtx[iChunkMtx]);1053 int rc = RTSemFastMutexRequest(pGMM->aChunkMtx[iChunkMtx].hMtx); 1027 1054 AssertRC(rc); 1028 1055 return rc; … … 1036 1063 * @param pGMM Pointer to the GMM instance. 1037 1064 * @param pChunk Pointer to the chunk if it's still 1038 * alive, NULL if it isn't. This is 1039 * inteded for later optimizations where we1040 * will deassociate the chunk mutex if1041 * considered safe.1065 * alive, NULL if it isn't. This is used to deassociate 1066 * the chunk from the mutex on the way out so a new one 1067 * can be selected next time, thus avoiding contented 1068 * mutexes. 1042 1069 */ 1043 1070 static int gmmR0ChunkMutexRelease(PGMMR0CHUNKMTXSTATE pMtxState, PGMMCHUNK pChunk) 1044 1071 { 1045 int rc = RTSemFastMutexRelease(pMtxState->pGMM->ahChunkMtx[pMtxState->iChunkMtx]); 1072 PGMM pGMM = pMtxState->pGMM; 1073 1074 /* 1075 * Release the chunk mutex and reacquire the giant if requested. 1076 */ 1077 int rc = RTSemFastMutexRelease(pGMM->aChunkMtx[pMtxState->iChunkMtx].hMtx); 1046 1078 AssertRC(rc); 1047 1079 if (pMtxState->fFlags == GMMR0CHUNK_MTX_RETAKE_GIANT) 1048 rc = gmmR0MutexAcquire(pMtxState->pGMM); 1080 rc = gmmR0MutexAcquire(pGMM); 1081 else 1082 Assert((pMtxState->fFlags != GMMR0CHUNK_MTX_DROP_GIANT) == (pGMM->hMtxOwner == RTThreadNativeSelf())); 1083 1084 /* 1085 * Drop the chunk mutex user reference and deassociate it from the chunk 1086 * when possible. 1087 */ 1088 if ( ASMAtomicDecU32(&pGMM->aChunkMtx[pMtxState->iChunkMtx].cUsers) == 0 1089 && pChunk 1090 && RT_SUCCESS(rc) ) 1091 { 1092 if (pMtxState->fFlags != GMMR0CHUNK_MTX_DROP_GIANT) 1093 pChunk->iChunkMtx = UINT8_MAX; 1094 else 1095 { 1096 rc = gmmR0MutexAcquire(pGMM); 1097 if (RT_SUCCESS(rc)) 1098 { 1099 if (pGMM->aChunkMtx[pMtxState->iChunkMtx].cUsers == 0) 1100 pChunk->iChunkMtx = UINT8_MAX; 1101 rc = gmmR0MutexRelease(pGMM); 1102 } 1103 } 1104 } 1105 1049 1106 pMtxState->pGMM = NULL; 1050 1107 return rc; … … 1878 1935 /*pChunk->iFreeHead = 0;*/ 1879 1936 pChunk->idNumaNode = GMM_CHUNK_NUMA_ID_UNKNOWN; 1937 pChunk->iChunkMtx = UINT8_MAX; 1880 1938 pChunk->fFlags = fChunkFlags; 1881 1939 for (unsigned iPage = 0; iPage < RT_ELEMENTS(pChunk->aPages) - 1; iPage++)
注意:
瀏覽 TracChangeset
來幫助您使用更動檢視器