DECLHIDDEN(int) rtR0MemObjNativeFree(RTR0MEMOBJ pMem) { PRTR0MEMOBJOS2 pMemOs2 = (PRTR0MEMOBJOS2)pMem; int rc; switch (pMemOs2->Core.enmType) { case RTR0MEMOBJTYPE_PHYS_NC: AssertMsgFailed(("RTR0MEMOBJTYPE_PHYS_NC\n")); return VERR_INTERNAL_ERROR; break; case RTR0MEMOBJTYPE_PHYS: if (!pMemOs2->Core.pv) break; case RTR0MEMOBJTYPE_MAPPING: if (pMemOs2->Core.u.Mapping.R0Process == NIL_RTR0PROCESS) break; /* fall thru */ case RTR0MEMOBJTYPE_PAGE: case RTR0MEMOBJTYPE_LOW: case RTR0MEMOBJTYPE_CONT: rc = KernVMFree(pMemOs2->Core.pv); AssertMsg(!rc, ("rc=%d type=%d pv=%p cb=%#zx\n", rc, pMemOs2->Core.enmType, pMemOs2->Core.pv, pMemOs2->Core.cb)); break; case RTR0MEMOBJTYPE_LOCK: rc = KernVMUnlock(&pMemOs2->Lock); AssertMsg(!rc, ("rc=%d\n", rc)); break; case RTR0MEMOBJTYPE_RES_VIRT: default: AssertMsgFailed(("enmType=%d\n", pMemOs2->Core.enmType)); return VERR_INTERNAL_ERROR; } return VINF_SUCCESS; }
DECLASM(int) VBoxDrvIOCtl(uint16_t sfn, uint8_t iCat, uint8_t iFunction, void *pvParm, void *pvData, uint16_t *pcbParm, uint16_t *pcbData) { /* * Find the session. */ const RTPROCESS Process = RTProcSelf(); const unsigned iHash = SESSION_HASH(sfn); PSUPDRVSESSION pSession; RTSpinlockAcquire(g_Spinlock); pSession = g_apSessionHashTab[iHash]; if (pSession && pSession->Process != Process) { do pSession = pSession->pNextHash; while ( pSession && ( pSession->sfn != sfn || pSession->Process != Process)); if (RT_LIKELY(pSession)) supdrvSessionRetain(pSession); } RTSpinlockReleaseNoInts(g_Spinlock); if (!pSession) { OSDBGPRINT(("VBoxDrvIoctl: WHUT?!? pSession == NULL! This must be a mistake... pid=%d\n", (int)Process)); return VERR_INVALID_PARAMETER; } /* * Verify the category and dispatch the IOCtl. */ if (RT_LIKELY(iCat == SUP_CTL_CATEGORY)) { Log(("VBoxDrvIOCtl: pSession=%p iFunction=%#x pvParm=%p pvData=%p *pcbParm=%d *pcbData=%d\n", pSession, iFunction, pvParm, pvData, *pcbParm, *pcbData)); Assert(pvParm); Assert(!pvData); /* * Lock the header. */ PSUPREQHDR pHdr = (PSUPREQHDR)pvParm; AssertReturn(*pcbParm == sizeof(*pHdr), VERR_INVALID_PARAMETER); KernVMLock_t Lock; int rc = KernVMLock(VMDHL_WRITE, pHdr, *pcbParm, &Lock, (KernPageList_t *)-1, NULL); AssertMsgReturn(!rc, ("KernVMLock(VMDHL_WRITE, %p, %#x, &p, NULL, NULL) -> %d\n", pHdr, *pcbParm, &Lock, rc), VERR_LOCK_FAILED); /* * Validate the header. */ if (RT_LIKELY((pHdr->fFlags & SUPREQHDR_FLAGS_MAGIC_MASK) == SUPREQHDR_FLAGS_MAGIC)) { uint32_t cbReq = RT_MAX(pHdr->cbIn, pHdr->cbOut); if (RT_LIKELY( pHdr->cbIn >= sizeof(*pHdr) && pHdr->cbOut >= sizeof(*pHdr) && cbReq <= _1M*16)) { /* * Lock the rest of the buffer if necessary. */ if (((uintptr_t)pHdr & PAGE_OFFSET_MASK) + cbReq > PAGE_SIZE) { rc = KernVMUnlock(&Lock); AssertMsgReturn(!rc, ("KernVMUnlock(Lock) -> %#x\n", rc), VERR_LOCK_FAILED); rc = KernVMLock(VMDHL_WRITE, pHdr, cbReq, &Lock, (KernPageList_t *)-1, NULL); AssertMsgReturn(!rc, ("KernVMLock(VMDHL_WRITE, %p, %#x, &p, NULL, NULL) -> %d\n", pHdr, cbReq, &Lock, rc), VERR_LOCK_FAILED); } /* * Process the IOCtl. */ rc = supdrvIOCtl(iFunction, &g_DevExt, pSession, pHdr); } else { OSDBGPRINT(("VBoxDrvIOCtl: max(%#x,%#x); iCmd=%#x\n", pHdr->cbIn, pHdr->cbOut, iFunction)); rc = VERR_INVALID_PARAMETER; } } else { OSDBGPRINT(("VBoxDrvIOCtl: bad magic fFlags=%#x; iCmd=%#x\n", pHdr->fFlags, iFunction)); rc = VERR_INVALID_PARAMETER; } /* * Unlock and return. */ int rc2 = KernVMUnlock(&Lock); AssertMsg(!rc2, ("rc2=%d\n", rc2)); NOREF(rc2);s }