Changeset 18920 in vbox for trunk/src/VBox/Runtime/r0drv/freebsd
- Timestamp:
- Apr 15, 2009 8:59:03 PM (16 years ago)
- svn:sync-xref-src-repo-rev:
- 45983
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Runtime/r0drv/freebsd/memobj-r0drv-freebsd.c
r14824 r18920 44 44 #include "internal/memobj.h" 45 45 46 47 46 /******************************************************************************* 48 47 * Structures and Typedefs * … … 137 136 case RTR0MEMOBJTYPE_MAPPING: 138 137 { 139 /** @todo Figure out mapping... */ 138 vm_map_t pMap = kernel_map; 139 140 /* vm_map_remove will unmap the pages we inserted with pmap_enter */ 141 AssertMsg(pMemFreeBSD->pMappingObject != NULL, ("MappingObject is NULL\n")); 142 if (pMemFreeBSD->Core.u.Mapping.R0Process != NIL_RTR0PROCESS) 143 pMap = &((struct proc *)pMemFreeBSD->Core.u.Mapping.R0Process)->p_vmspace->vm_map; 144 145 rc = vm_map_remove(pMap, 146 (vm_offset_t)pMemFreeBSD->Core.pv, 147 (vm_offset_t)pMemFreeBSD->Core.pv + pMemFreeBSD->Core.cb); 148 AssertMsg(rc == KERN_SUCCESS, ("%#x", rc)); 149 break; 140 150 } 141 151 … … 148 158 return VERR_INTERNAL_ERROR; 149 159 } 150 151 Assert(!pMemFreeBSD->pMappingObject);152 160 153 161 return VINF_SUCCESS; … … 212 220 MapAddress + cb); 213 221 } 214 else215 vm_object_deallocate(pMemFreeBSD->pObject);216 222 rc = VERR_NO_MEMORY; /** @todo fix translation (borrow from darwin) */ 217 223 } … … 344 350 */ 345 351 rc = vm_map_wire(&((struct proc *)R0Process)->p_vmspace->vm_map, /* the map */ 346 (vm_offset_t)R3Ptr, /* start */347 (vm_offset_t)R3Ptr + cb, /* end */348 VM_MAP_WIRE_ SYSTEM | VM_MAP_WIRE_NOHOLES); /* flags - SYSTEM?*/352 (vm_offset_t)R3Ptr, /* start */ 353 (vm_offset_t)R3Ptr + cb, /* end */ 354 VM_MAP_WIRE_USER | VM_MAP_WIRE_NOHOLES); /* flags */ 349 355 if (rc == KERN_SUCCESS) 350 356 { … … 415 421 vm_offset_t MapAddress = pvFixed != (void *)-1 416 422 ? (vm_offset_t)pvFixed 417 : vm_map_min( kernel_map);423 : vm_map_min(pMap); 418 424 if (pvFixed) 419 425 vm_map_remove(pMap, … … 429 435 VM_PROT_NONE, /* protection */ 430 436 VM_PROT_ALL, /* max(_prot) ?? */ 431 FALSE);/* cow (copy-on-write) */437 0); /* cow (copy-on-write) */ 432 438 if (rc == KERN_SUCCESS) 433 439 { … … 543 549 } 544 550 545 551 /* see http://markmail.org/message/udhq33tefgtyfozs */ 546 552 int rtR0MemObjNativeMapUser(PPRTR0MEMOBJINTERNAL ppMem, RTR0MEMOBJ pMemToMap, RTR3PTR R3PtrFixed, size_t uAlignment, unsigned fProt, RTR0PROCESS R0Process) 547 553 { … … 549 555 AssertMsgReturn(R3PtrFixed == (RTR3PTR)-1, ("%p\n", R3PtrFixed), VERR_NOT_SUPPORTED); 550 556 551 #if 0552 557 int rc; 553 void *pvR0; 554 void *pvR3 = NULL; 555 PRTR0MEMOBJFREEBSD pMemToMapOs2 = (PRTR0MEMOBJFREEBSD)pMemToMap; 556 switch (pMemToMapOs2->Core.enmType) 558 vm_object_t pObjectToMap = ((PRTR0MEMOBJFREEBSD)pMemToMap)->pObject; 559 struct proc *pProc = (struct proc *)R0Process; 560 struct vm_map *pProcMap = &pProc->p_vmspace->vm_map; 561 vm_offset_t AddrR3 = 0; 562 vm_prot_t ProtectionFlags = 0; 563 564 if ((fProt & RTMEM_PROT_NONE) == RTMEM_PROT_NONE) 565 ProtectionFlags = VM_PROT_NONE; 566 if ((fProt & RTMEM_PROT_READ) == RTMEM_PROT_READ) 567 ProtectionFlags |= VM_PROT_READ; 568 if ((fProt & RTMEM_PROT_WRITE) == RTMEM_PROT_WRITE) 569 ProtectionFlags |= VM_PROT_WRITE; 570 if ((fProt & RTMEM_PROT_EXEC) == RTMEM_PROT_EXEC) 571 ProtectionFlags |= VM_PROT_EXECUTE; 572 573 PROC_LOCK(pProc); 574 AddrR3 = round_page((vm_offset_t)pProc->p_vmspace->vm_daddr + lim_max(pProc, RLIMIT_DATA)); 575 PROC_UNLOCK(pProc); 576 577 /* 578 * Mapping into R3 is easy if the mem object has a associated VM object. 579 * If there is not such an object we have to get it from the address. 580 */ 581 if (!pObjectToMap) 582 { 583 vm_object_t pObjectNew = vm_object_allocate(OBJT_PHYS, pMemToMap->cb >> PAGE_SHIFT); 584 if (pObjectNew) 585 { 586 /* Insert the object in the map. */ 587 rc = vm_map_find(pProcMap, /* Map to insert the object in */ 588 pObjectNew , /* Object to map */ 589 0, /* Start offset in the object */ 590 &AddrR3, /* Start address IN/OUT */ 591 pMemToMap->cb, /* Size of the mapping */ 592 TRUE, /* Whether a suitable address should be searched for first */ 593 ProtectionFlags, /* protection flags */ 594 VM_PROT_ALL, /* Maximum protection flags */ 595 0); /* Copy on write */ 596 if (rc == KERN_SUCCESS) 597 { 598 int cPages = pMemToMap->cb >> PAGE_SHIFT; 599 int iPage; 600 void *AddrToMap = pMemToMap->pv; 601 pmap_t pPhysicalMap = pProcMap->pmap; 602 vm_offset_t AddrR3Dest = AddrR3; 603 604 /* Insert the memory page by page into the mapping. */ 605 for (iPage = 0; iPage < cPages; iPage++) 606 { 607 vm_page_t Page = PHYS_TO_VM_PAGE(vtophys(AddrToMap)); 608 609 pmap_enter(pPhysicalMap, AddrR3Dest, Page, ProtectionFlags, TRUE); 610 AddrToMap = (uint8_t *)AddrToMap + PAGE_SIZE; 611 AddrR3Dest += PAGE_SIZE; 612 } 613 } 614 else 615 vm_object_deallocate(pObjectNew); 616 } 617 else 618 { 619 AssertMsgFailed(("Could not allocate VM object\n")); 620 rc = 1; /* @todo fix */ 621 } 622 } 623 else 624 { 625 /* 626 * Reference the object. If this isn't done the object will removed from kernel space 627 * if the mapping is destroyed. 628 */ 629 vm_object_reference(pObjectToMap); 630 631 rc = vm_map_find(pProcMap, /* Map to insert the object in */ 632 pObjectToMap, /* Object to map */ 633 0, /* Start offset in the object */ 634 &AddrR3, /* Start address IN/OUT */ 635 pMemToMap->cb, /* Size of the mapping */ 636 TRUE, /* Whether a suitable address should be searched for first */ 637 ProtectionFlags, /* protection flags */ 638 VM_PROT_ALL, /* Maximum protection flags */ 639 0); /* Copy on write */ 640 } 641 642 if (rc == KERN_SUCCESS) 557 643 { 558 644 /* 559 * These has kernel mappings.645 * Create a mapping object for it. 560 646 */ 647 PRTR0MEMOBJFREEBSD pMemFreeBSD = (PRTR0MEMOBJFREEBSD)rtR0MemObjNew(sizeof(RTR0MEMOBJFREEBSD), 648 RTR0MEMOBJTYPE_MAPPING, 649 (void *)AddrR3, 650 pMemToMap->cb); 651 if (pMemFreeBSD) 652 { 653 Assert(pMemFreeBSD->Core.pv == (void *)AddrR3); 654 pMemFreeBSD->Core.u.Mapping.R0Process = R0Process; 655 pMemFreeBSD->pMappingObject = pObjectToMap; 656 *ppMem = &pMemFreeBSD->Core; 657 return VINF_SUCCESS; 658 } 659 660 rc = vm_map_remove(pProcMap, ((vm_offset_t)AddrR3), ((vm_offset_t)AddrR3) + pMemToMap->cb); 661 AssertMsg(rc == KERN_SUCCESS, ("Deleting mapping failed\n")); 662 } 663 664 if (pObjectToMap) 665 vm_object_deallocate(pObjectToMap); 666 667 return VERR_NO_MEMORY; 668 } 669 670 671 RTHCPHYS rtR0MemObjNativeGetPagePhysAddr(PRTR0MEMOBJINTERNAL pMem, size_t iPage) 672 { 673 PRTR0MEMOBJFREEBSD pMemFreeBSD = (PRTR0MEMOBJFREEBSD)pMem; 674 675 switch (pMemFreeBSD->Core.enmType) 676 { 677 case RTR0MEMOBJTYPE_LOCK: 678 { 679 if ( pMemFreeBSD->Core.u.Lock.R0Process != NIL_RTR0PROCESS 680 && pMemFreeBSD->Core.u.Lock.R0Process != (RTR0PROCESS)curproc) 681 { 682 /* later */ 683 return NIL_RTHCPHYS; 684 } 685 } 561 686 case RTR0MEMOBJTYPE_PAGE: 562 case RTR0MEMOBJTYPE_LOW: 687 case RTR0MEMOBJTYPE_MAPPING: 688 { 689 uint8_t *pb = (uint8_t *)pMemFreeBSD->Core.pv + ((size_t)iPage << PAGE_SHIFT); 690 return vtophys(pb); 691 } 692 563 693 case RTR0MEMOBJTYPE_CONT: 564 pvR0 = pMemToMapOs2->Core.pv; 565 break; 694 return pMemFreeBSD->Core.u.Cont.Phys + (iPage << PAGE_SHIFT); 566 695 567 696 case RTR0MEMOBJTYPE_PHYS: 568 pvR0 = pMemToMapOs2->Core.pv; 569 #if 0/* this is wrong. */ 570 if (!pvR0) 571 { 572 /* no ring-0 mapping, so allocate a mapping in the process. */ 573 AssertMsgReturn(uAlignment == PAGE_SIZE, ("%#zx\n", uAlignment), VERR_NOT_SUPPORTED); 574 AssertMsgReturn(fProt & RTMEM_PROT_WRITE, ("%#x\n", fProt), VERR_NOT_SUPPORTED); 575 Assert(!pMemToMapOs2->Core.u.Phys.fAllocated); 576 ULONG ulPhys = pMemToMapOs2->Core.u.Phys.PhysBase; 577 rc = KernVMAlloc(pMemToMapOs2->Core.cb, VMDHA_PHYS | VMDHA_PROCESS, &pvR3, (PPVOID)&ulPhys, NULL); 578 if (rc) 579 return RTErrConvertFromOS2(rc); 580 } 581 break; 582 #endif 583 return VERR_NOT_SUPPORTED; 584 585 case RTR0MEMOBJTYPE_LOCK: 586 if (pMemToMapOs2->Core.u.Lock.R0Process != NIL_RTR0PROCESS) 587 return VERR_NOT_SUPPORTED; /** @todo implement this... */ 588 pvR0 = pMemToMapOs2->Core.pv; 589 break; 697 return pMemFreeBSD->Core.u.Phys.PhysBase + (iPage << PAGE_SHIFT); 590 698 591 699 case RTR0MEMOBJTYPE_PHYS_NC: 592 700 case RTR0MEMOBJTYPE_RES_VIRT: 593 case RTR0MEMOBJTYPE_MAPPING:594 default:595 AssertMsgFailed(("enmType=%d\n", pMemToMapOs2->Core.enmType));596 return VERR_INTERNAL_ERROR;597 }598 599 /*600 * Map the ring-0 memory into the current process.601 */602 if (!pvR3)603 {604 Assert(pvR0);605 ULONG flFlags = 0;606 if (uAlignment == PAGE_SIZE)607 flFlags |= VMDHGP_4MB;608 if (fProt & RTMEM_PROT_WRITE)609 flFlags |= VMDHGP_WRITE;610 rc = RTR0Os2DHVMGlobalToProcess(flFlags, pvR0, pMemToMapOs2->Core.cb, &pvR3);611 if (rc)612 return RTErrConvertFromOS2(rc);613 }614 Assert(pvR3);615 616 /*617 * Create a mapping object for it.618 */619 PRTR0MEMOBJFREEBSD pMemFreeBSD = (PRTR0MEMOBJFREEBSD)rtR0MemObjNew(RT_OFFSETOF(RTR0MEMOBJOS2, Lock), RTR0MEMOBJTYPE_MAPPING, pvR3, pMemToMapOs2->Core.cb);620 if (pMemFreeBSD)621 {622 Assert(pMemFreeBSD->Core.pv == pvR3);623 pMemFreeBSD->Core.u.Mapping.R0Process = R0Process;624 *ppMem = &pMemFreeBSD->Core;625 return VINF_SUCCESS;626 }627 KernVMFree(pvR3);628 return VERR_NO_MEMORY;629 #endif630 return VERR_NOT_IMPLEMENTED;631 }632 633 634 RTHCPHYS rtR0MemObjNativeGetPagePhysAddr(PRTR0MEMOBJINTERNAL pMem, size_t iPage)635 {636 PRTR0MEMOBJFREEBSD pMemFreeBSD = (PRTR0MEMOBJFREEBSD)pMem;637 638 switch (pMemFreeBSD->Core.enmType)639 {640 case RTR0MEMOBJTYPE_LOCK:641 {642 if ( pMemFreeBSD->Core.u.Lock.R0Process != NIL_RTR0PROCESS643 && pMemFreeBSD->Core.u.Lock.R0Process != (RTR0PROCESS)curproc)644 {645 /* later */646 return NIL_RTHCPHYS;647 }648 }649 case RTR0MEMOBJTYPE_PAGE:650 {651 uint8_t *pb = (uint8_t *)pMemFreeBSD->Core.pv + ((size_t)iPage << PAGE_SHIFT);652 return vtophys(pb);653 }654 655 case RTR0MEMOBJTYPE_CONT:656 return pMemFreeBSD->Core.u.Cont.Phys + (iPage << PAGE_SHIFT);657 658 case RTR0MEMOBJTYPE_PHYS:659 return pMemFreeBSD->Core.u.Phys.PhysBase + (iPage << PAGE_SHIFT);660 661 case RTR0MEMOBJTYPE_PHYS_NC:662 case RTR0MEMOBJTYPE_RES_VIRT:663 case RTR0MEMOBJTYPE_MAPPING:664 701 case RTR0MEMOBJTYPE_LOW: 665 702 default:
Note:
See TracChangeset
for help on using the changeset viewer.