Lines 410-416
kmem_malloc_domain(int domain, vm_size_t size, int flags)
Link Here
|
410 |
if (vmem_alloc(arena, size, flags | M_BESTFIT, &addr)) |
410 |
if (vmem_alloc(arena, size, flags | M_BESTFIT, &addr)) |
411 |
return (0); |
411 |
return (0); |
412 |
|
412 |
|
413 |
rv = kmem_back_domain(domain, kernel_object, addr, size, flags); |
413 |
rv = kmem_back_domain(domain, kernel_object, addr, size, flags, false); |
414 |
if (rv != KERN_SUCCESS) { |
414 |
if (rv != KERN_SUCCESS) { |
415 |
vmem_free(arena, addr, size); |
415 |
vmem_free(arena, addr, size); |
416 |
return (0); |
416 |
return (0); |
Lines 450-456
kmem_malloc_domainset(struct domainset *ds, vm_size_t size, int flags)
Link Here
|
450 |
*/ |
450 |
*/ |
451 |
int |
451 |
int |
452 |
kmem_back_domain(int domain, vm_object_t object, vm_offset_t addr, |
452 |
kmem_back_domain(int domain, vm_object_t object, vm_offset_t addr, |
453 |
vm_size_t size, int flags) |
453 |
vm_size_t size, int flags, bool locked) |
454 |
{ |
454 |
{ |
455 |
vm_offset_t offset, i; |
455 |
vm_offset_t offset, i; |
456 |
vm_page_t m, mpred; |
456 |
vm_page_t m, mpred; |
Lines 468-474
kmem_back_domain(int domain, vm_object_t object, vm_offset_t addr,
Link Here
|
468 |
prot = (flags & M_EXEC) != 0 ? VM_PROT_ALL : VM_PROT_RW; |
468 |
prot = (flags & M_EXEC) != 0 ? VM_PROT_ALL : VM_PROT_RW; |
469 |
|
469 |
|
470 |
i = 0; |
470 |
i = 0; |
471 |
VM_OBJECT_WLOCK(object); |
471 |
if (!locked) |
|
|
472 |
VM_OBJECT_WLOCK(object); |
472 |
retry: |
473 |
retry: |
473 |
mpred = vm_radix_lookup_le(&object->rtree, atop(offset + i)); |
474 |
mpred = vm_radix_lookup_le(&object->rtree, atop(offset + i)); |
474 |
for (; i < size; i += PAGE_SIZE, mpred = m) { |
475 |
for (; i < size; i += PAGE_SIZE, mpred = m) { |
Lines 483-490
kmem_back_domain(int domain, vm_object_t object, vm_offset_t addr,
Link Here
|
483 |
if (m == NULL) { |
484 |
if (m == NULL) { |
484 |
if ((flags & M_NOWAIT) == 0) |
485 |
if ((flags & M_NOWAIT) == 0) |
485 |
goto retry; |
486 |
goto retry; |
486 |
VM_OBJECT_WUNLOCK(object); |
487 |
if (locked) |
487 |
kmem_unback(object, addr, i); |
488 |
kmem_unback_locked(object, addr, i); |
|
|
489 |
else { |
490 |
VM_OBJECT_WUNLOCK(object); |
491 |
kmem_unback(object, addr, i); |
492 |
} |
488 |
return (KERN_NO_SPACE); |
493 |
return (KERN_NO_SPACE); |
489 |
} |
494 |
} |
490 |
KASSERT(vm_phys_domain(m) == domain, |
495 |
KASSERT(vm_phys_domain(m) == domain, |
Lines 502-508
kmem_back_domain(int domain, vm_object_t object, vm_offset_t addr,
Link Here
|
502 |
m->oflags |= VPO_KMEM_EXEC; |
507 |
m->oflags |= VPO_KMEM_EXEC; |
503 |
#endif |
508 |
#endif |
504 |
} |
509 |
} |
505 |
VM_OBJECT_WUNLOCK(object); |
510 |
if (!locked) |
|
|
511 |
VM_OBJECT_WUNLOCK(object); |
506 |
|
512 |
|
507 |
return (KERN_SUCCESS); |
513 |
return (KERN_SUCCESS); |
508 |
} |
514 |
} |
Lines 512-519
kmem_back_domain(int domain, vm_object_t object, vm_offset_t addr,
Link Here
|
512 |
* |
518 |
* |
513 |
* Allocate physical pages for the specified virtual address range. |
519 |
* Allocate physical pages for the specified virtual address range. |
514 |
*/ |
520 |
*/ |
515 |
int |
521 |
static int |
516 |
kmem_back(vm_object_t object, vm_offset_t addr, vm_size_t size, int flags) |
522 |
_kmem_back(vm_object_t object, vm_offset_t addr, vm_size_t size, int flags, |
|
|
523 |
bool locked) |
517 |
{ |
524 |
{ |
518 |
vm_offset_t end, next, start; |
525 |
vm_offset_t end, next, start; |
519 |
int domain, rv; |
526 |
int domain, rv; |
Lines 537-551
kmem_back(vm_object_t object, vm_offset_t addr, vm_size_t size, int flags)
Link Here
|
537 |
domain = 0; |
544 |
domain = 0; |
538 |
next = end; |
545 |
next = end; |
539 |
} |
546 |
} |
540 |
rv = kmem_back_domain(domain, object, addr, next - addr, flags); |
547 |
rv = kmem_back_domain(domain, object, addr, next - addr, flags, |
|
|
548 |
locked); |
541 |
if (rv != KERN_SUCCESS) { |
549 |
if (rv != KERN_SUCCESS) { |
542 |
kmem_unback(object, start, addr - start); |
550 |
if (locked) |
|
|
551 |
kmem_unback_locked(object, start, addr - start); |
552 |
else |
553 |
kmem_unback(object, start, addr - start); |
543 |
break; |
554 |
break; |
544 |
} |
555 |
} |
545 |
} |
556 |
} |
546 |
return (rv); |
557 |
return (rv); |
547 |
} |
558 |
} |
548 |
|
559 |
|
|
|
560 |
int |
561 |
kmem_back(vm_object_t object, vm_offset_t addr, vm_size_t size, int flags) |
562 |
{ |
563 |
|
564 |
return _kmem_back(object, addr, size, flags, false); |
565 |
} |
566 |
|
567 |
int |
568 |
kmem_back_locked(vm_object_t object, vm_offset_t addr, vm_size_t size, int flags) |
569 |
{ |
570 |
|
571 |
return _kmem_back(object, addr, size, flags, true); |
572 |
} |
573 |
|
549 |
/* |
574 |
/* |
550 |
* kmem_unback: |
575 |
* kmem_unback: |
551 |
* |
576 |
* |
Lines 556-562
kmem_back(vm_object_t object, vm_offset_t addr, vm_size_t size, int flags)
Link Here
|
556 |
* that is being unmapped. |
581 |
* that is being unmapped. |
557 |
*/ |
582 |
*/ |
558 |
static struct vmem * |
583 |
static struct vmem * |
559 |
_kmem_unback(vm_object_t object, vm_offset_t addr, vm_size_t size) |
584 |
_kmem_unback(vm_object_t object, vm_offset_t addr, vm_size_t size, bool locked) |
560 |
{ |
585 |
{ |
561 |
struct vmem *arena; |
586 |
struct vmem *arena; |
562 |
vm_page_t m, next; |
587 |
vm_page_t m, next; |
Lines 568-577
_kmem_unback(vm_object_t object, vm_offset_t addr, vm_size_t size)
Link Here
|
568 |
|
593 |
|
569 |
if (size == 0) |
594 |
if (size == 0) |
570 |
return (NULL); |
595 |
return (NULL); |
|
|
596 |
if (!locked) |
597 |
VM_OBJECT_WLOCK(object); |
571 |
pmap_remove(kernel_pmap, addr, addr + size); |
598 |
pmap_remove(kernel_pmap, addr, addr + size); |
572 |
offset = addr - VM_MIN_KERNEL_ADDRESS; |
599 |
offset = addr - VM_MIN_KERNEL_ADDRESS; |
573 |
end = offset + size; |
600 |
end = offset + size; |
574 |
VM_OBJECT_WLOCK(object); |
|
|
575 |
m = vm_page_lookup(object, atop(offset)); |
601 |
m = vm_page_lookup(object, atop(offset)); |
576 |
domain = vm_phys_domain(m); |
602 |
domain = vm_phys_domain(m); |
577 |
#if VM_NRESERVLEVEL > 0 |
603 |
#if VM_NRESERVLEVEL > 0 |
Lines 587-593
_kmem_unback(vm_object_t object, vm_offset_t addr, vm_size_t size)
Link Here
|
587 |
vm_page_unwire(m, PQ_NONE); |
613 |
vm_page_unwire(m, PQ_NONE); |
588 |
vm_page_free(m); |
614 |
vm_page_free(m); |
589 |
} |
615 |
} |
590 |
VM_OBJECT_WUNLOCK(object); |
616 |
if (!locked) |
|
|
617 |
VM_OBJECT_WUNLOCK(object); |
591 |
|
618 |
|
592 |
return (arena); |
619 |
return (arena); |
593 |
} |
620 |
} |
Lines 596-604
void
Link Here
|
596 |
kmem_unback(vm_object_t object, vm_offset_t addr, vm_size_t size) |
623 |
kmem_unback(vm_object_t object, vm_offset_t addr, vm_size_t size) |
597 |
{ |
624 |
{ |
598 |
|
625 |
|
599 |
(void)_kmem_unback(object, addr, size); |
626 |
(void)_kmem_unback(object, addr, size, false); |
600 |
} |
627 |
} |
601 |
|
628 |
|
|
|
629 |
void |
630 |
kmem_unback_locked(vm_object_t object, vm_offset_t addr, vm_size_t size) |
631 |
{ |
632 |
|
633 |
(void)_kmem_unback(object, addr, size, true); |
634 |
} |
635 |
|
636 |
|
602 |
/* |
637 |
/* |
603 |
* kmem_free: |
638 |
* kmem_free: |
604 |
* |
639 |
* |
Lines 611-617
kmem_free(vm_offset_t addr, vm_size_t size)
Link Here
|
611 |
struct vmem *arena; |
646 |
struct vmem *arena; |
612 |
|
647 |
|
613 |
size = round_page(size); |
648 |
size = round_page(size); |
614 |
arena = _kmem_unback(kernel_object, addr, size); |
649 |
arena = _kmem_unback(kernel_object, addr, size, false); |
615 |
if (arena != NULL) |
650 |
if (arena != NULL) |
616 |
vmem_free(arena, addr, size); |
651 |
vmem_free(arena, addr, size); |
617 |
} |
652 |
} |