Index: /trunk/include/VBox/vmm/pgm.h
===================================================================
--- /trunk/include/VBox/vmm/pgm.h	(revision 91242)
+++ /trunk/include/VBox/vmm/pgm.h	(revision 91243)
@@ -675,5 +675,5 @@
 VMMR0DECL(VBOXSTRICTRC) PGMR0Trap0eHandlerNPMisconfig(PGVM pGVM, PGVMCPU pGVCpu, PGMMODE enmShwPagingMode,
                                                       PCPUMCTXCORE pRegFrame, RTGCPHYS GCPhysFault, uint32_t uErr);
-VMMR0_INT_DECL(int)  PGMR0PoolGrow(PGVM pGVM);
+VMMR0_INT_DECL(int)  PGMR0PoolGrow(PGVM pGVM, VMCPUID idCpu);
 /** @} */
 #endif /* IN_RING0 */
Index: /trunk/include/VBox/vmm/vmm.h
===================================================================
--- /trunk/include/VBox/vmm/vmm.h	(revision 91242)
+++ /trunk/include/VBox/vmm/vmm.h	(revision 91243)
@@ -58,6 +58,4 @@
     VMMCALLRING3_VM_R0_ASSERTION,
 
-    /** Grow the PGM shadow page pool. */
-    VMMCALLRING3_PGM_POOL_GROW,
     /** Maps a chunk into ring-3. */
     VMMCALLRING3_PGM_MAP_CHUNK,
Index: /trunk/src/VBox/VMM/VMMAll/PGMAllPool.cpp
===================================================================
--- /trunk/src/VBox/VMM/VMMAll/PGMAllPool.cpp	(revision 91242)
+++ /trunk/src/VBox/VMM/VMMAll/PGMAllPool.cpp	(revision 91243)
@@ -4947,5 +4947,5 @@
         int rc = PGMR3PoolGrow(pVM, VMMGetCpu(pVM));
 #else
-        int rc = VMMRZCallRing3NoCpu(pVM, VMMCALLRING3_PGM_POOL_GROW, 0);
+        int rc = PGMR0PoolGrow(pVM, VMMGetCpuId(pVM));
 #endif
         if (RT_FAILURE(rc))
Index: /trunk/src/VBox/VMM/VMMR0/PGMR0Pool.cpp
===================================================================
--- /trunk/src/VBox/VMM/VMMR0/PGMR0Pool.cpp	(revision 91242)
+++ /trunk/src/VBox/VMM/VMMR0/PGMR0Pool.cpp	(revision 91243)
@@ -34,19 +34,10 @@
 
 
-
 /**
- * Grows the shadow page pool.
- *
- * I.e. adds more pages to it, assuming that hasn't reached cMaxPages yet.
- *
- * @returns VBox status code.
- * @param   pGVM    The ring-0 VM structure.
+ * Worker for PGMR0PoolGrow.
  */
-VMMR0_INT_DECL(int) PGMR0PoolGrow(PGVM pGVM)
+static int pgmR0PoolGrowInner(PGVM pGVM, PPGMPOOL pPool)
 {
-    PPGMPOOL pPool = pGVM->pgm.s.pPoolR0;
-    AssertReturn(pPool->cCurPages < pPool->cMaxPages, VERR_PGM_POOL_MAXED_OUT_ALREADY);
-    AssertReturn(pPool->pVMR3 == pGVM->pVMR3, VERR_PGM_POOL_IPE);
-    AssertReturn(pPool->pVMR0 == pGVM, VERR_PGM_POOL_IPE);
+    int rc;
 
     /* With 32-bit guests and no EPT, the CR3 limits the root pages to low
@@ -55,8 +46,4 @@
      *        required. */
     bool const fCanUseHighMemory = HMIsNestedPagingActive(pGVM);
-
-    STAM_REL_PROFILE_START(&pPool->StatGrow, a);
-    int rc = RTCritSectEnter(&pGVM->pgmr0.s.PoolGrowCritSect);
-    AssertRCReturn(rc, rc);
 
     /*
@@ -70,5 +57,5 @@
         if (cNewPages > PGMPOOL_CFG_MAX_GROW)
             cNewPages = PGMPOOL_CFG_MAX_GROW;
-        LogFlow(("PGMR3PoolGrow: Growing the pool by %u (%#x) pages to %u (%#x) pages. fCanUseHighMemory=%RTbool\n",
+        LogFlow(("PGMR0PoolGrow: Growing the pool by %u (%#x) pages to %u (%#x) pages. fCanUseHighMemory=%RTbool\n",
                  cNewPages, cNewPages, cCurPages + cNewPages, cCurPages + cNewPages, fCanUseHighMemory));
 
@@ -78,8 +65,7 @@
                       <= RT_ELEMENTS(pGVM->pgmr0.s.ahPoolMemObjs));
         AssertCompile(RT_ELEMENTS(pGVM->pgmr0.s.ahPoolMemObjs) == RT_ELEMENTS(pGVM->pgmr0.s.ahPoolMapObjs));
-        AssertLogRelMsgReturnStmt(   pGVM->pgmr0.s.ahPoolMemObjs[idxMemHandle] == NIL_RTR0MEMOBJ
-                                  && pGVM->pgmr0.s.ahPoolMapObjs[idxMemHandle] == NIL_RTR0MEMOBJ,
-                                  ("idxMemHandle=%#x\n", idxMemHandle), RTCritSectLeave(&pGVM->pgmr0.s.PoolGrowCritSect),
-                                  VERR_PGM_POOL_IPE);
+        AssertLogRelMsgReturn(   pGVM->pgmr0.s.ahPoolMemObjs[idxMemHandle] == NIL_RTR0MEMOBJ
+                              && pGVM->pgmr0.s.ahPoolMapObjs[idxMemHandle] == NIL_RTR0MEMOBJ, ("idxMemHandle=%#x\n", idxMemHandle),
+                              VERR_PGM_POOL_IPE);
 
         /*
@@ -120,5 +106,5 @@
                     pPage->enmKind          = PGMPOOLKIND_FREE;
                     pPage->idx              = pPage - &pPool->aPages[0];
-                    LogFlow(("PGMR3PoolGrow: insert page #%#x - %RHp\n", pPage->idx, pPage->Core.Key));
+                    LogFlow(("PGMR0PoolGrow: insert page #%#x - %RHp\n", pPage->idx, pPage->Core.Key));
                     pPage->iNext            = pPool->iFreeHead;
                     pPage->iUserHead        = NIL_PGMPOOL_USER_INDEX;
@@ -135,6 +121,4 @@
                 }
 
-                STAM_REL_PROFILE_STOP(&pPool->StatGrow, a);
-                RTCritSectLeave(&pGVM->pgmr0.s.PoolGrowCritSect);
                 return VINF_SUCCESS;
             }
@@ -149,6 +133,53 @@
                     rc, cNewPages, cCurPages, cMaxPages, fCanUseHighMemory));
     }
-    RTCritSectLeave(&pGVM->pgmr0.s.PoolGrowCritSect);
+    else
+        rc = VINF_SUCCESS;
     return rc;
 }
 
+
+/**
+ * Grows the shadow page pool.
+ *
+ * I.e. adds more pages to it, assuming that hasn't reached cMaxPages yet.
+ *
+ * @returns VBox status code.
+ * @param   pGVM    The ring-0 VM structure.
+ * @param   idCpu   The ID of the calling EMT.
+ * @thread  EMT(idCpu)
+ */
+VMMR0_INT_DECL(int) PGMR0PoolGrow(PGVM pGVM, VMCPUID idCpu)
+{
+    /*
+     * Validate input.
+     */
+    PPGMPOOL pPool = pGVM->pgm.s.pPoolR0;
+    AssertReturn(pPool->cCurPages < pPool->cMaxPages, VERR_PGM_POOL_MAXED_OUT_ALREADY);
+    AssertReturn(pPool->pVMR3 == pGVM->pVMR3, VERR_PGM_POOL_IPE);
+    AssertReturn(pPool->pVMR0 == pGVM, VERR_PGM_POOL_IPE);
+
+    AssertReturn(idCpu < pGVM->cCpus, VERR_VM_THREAD_NOT_EMT);
+    PGVMCPU const pGVCpu = &pGVM->aCpus[idCpu];
+
+    /*
+     * Enter the grow critical section and call worker.
+     */
+    STAM_REL_PROFILE_START(&pPool->StatGrow, a);
+
+    VMMR0EMTBLOCKCTX Ctx;
+    int rc = VMMR0EmtPrepareToBlock(pGVCpu, VINF_SUCCESS, __FUNCTION__, &pGVM->pgmr0.s.PoolGrowCritSect, &Ctx);
+    AssertRCReturn(rc, rc);
+
+    rc = RTCritSectEnter(&pGVM->pgmr0.s.PoolGrowCritSect);
+    AssertRCReturn(rc, rc);
+
+    rc = pgmR0PoolGrowInner(pGVM, pPool);
+
+    STAM_REL_PROFILE_STOP(&pPool->StatGrow, a);
+    RTCritSectLeave(&pGVM->pgmr0.s.PoolGrowCritSect);
+
+    VMMR0EmtResumeAfterBlocking(pGVCpu, &Ctx);
+
+    return rc;
+}
+
Index: /trunk/src/VBox/VMM/VMMR0/VMMR0.cpp
===================================================================
--- /trunk/src/VBox/VMM/VMMR0/VMMR0.cpp	(revision 91242)
+++ /trunk/src/VBox/VMM/VMMR0/VMMR0.cpp	(revision 91243)
@@ -1288,7 +1288,4 @@
             switch (pVCpu->vmm.s.enmCallRing3Operation)
             {
-                case VMMCALLRING3_PGM_POOL_GROW:
-                    STAM_COUNTER_INC(&pVM->vmm.s.StatRZCallPGMPoolGrow);
-                    break;
                 case VMMCALLRING3_PGM_MAP_CHUNK:
                     STAM_COUNTER_INC(&pVM->vmm.s.StatRZCallPGMMapChunk);
@@ -1883,5 +1880,5 @@
             if (idCpu == NIL_VMCPUID)
                 return VERR_INVALID_CPU_ID;
-            rc = PGMR0PoolGrow(pGVM);
+            rc = PGMR0PoolGrow(pGVM, idCpu);
             break;
 
Index: /trunk/src/VBox/VMM/VMMR3/VMM.cpp
===================================================================
--- /trunk/src/VBox/VMM/VMMR3/VMM.cpp	(revision 91242)
+++ /trunk/src/VBox/VMM/VMMR3/VMM.cpp	(revision 91243)
@@ -430,5 +430,4 @@
     STAM_REG(pVM, &pVM->vmm.s.StatRZRetPatchTPR,            STAMTYPE_COUNTER, "/VMM/RZRet/PatchTPR",            STAMUNIT_OCCURENCES, "Number of VINF_EM_HM_PATCH_TPR_INSTR returns.");
     STAM_REG(pVM, &pVM->vmm.s.StatRZRetCallRing3,           STAMTYPE_COUNTER, "/VMM/RZCallR3/Misc",             STAMUNIT_OCCURENCES, "Number of Other ring-3 calls.");
-    STAM_REG(pVM, &pVM->vmm.s.StatRZCallPGMPoolGrow,        STAMTYPE_COUNTER, "/VMM/RZCallR3/PGMPoolGrow",      STAMUNIT_OCCURENCES, "Number of VMMCALLRING3_PGM_POOL_GROW calls.");
     STAM_REG(pVM, &pVM->vmm.s.StatRZCallPGMMapChunk,        STAMTYPE_COUNTER, "/VMM/RZCallR3/PGMMapChunk",      STAMUNIT_OCCURENCES, "Number of VMMCALLRING3_PGM_MAP_CHUNK calls.");
     STAM_REG(pVM, &pVM->vmm.s.StatRZCallPGMAllocHandy,      STAMTYPE_COUNTER, "/VMM/RZCallR3/PGMAllocHandy",    STAMUNIT_OCCURENCES, "Number of VMMCALLRING3_PGM_ALLOCATE_HANDY_PAGES calls.");
@@ -2502,13 +2501,4 @@
     {
         /*
-         * Grow the PGM pool.
-         */
-        case VMMCALLRING3_PGM_POOL_GROW:
-        {
-            pVCpu->vmm.s.rcCallRing3 = PGMR3PoolGrow(pVM, pVCpu);
-            break;
-        }
-
-        /*
          * Maps an page allocation chunk into ring-3 so ring-0 can use it.
          */
