Changeset View
Changeset View
Standalone View
Standalone View
sys/vm/vm_phys.c
Show First 20 Lines • Show All 597 Lines • ▼ Show 20 Lines | |||||
* from the free lists. | * from the free lists. | ||||
* | * | ||||
* The free page queues must be locked. | * The free page queues must be locked. | ||||
*/ | */ | ||||
vm_page_t | vm_page_t | ||||
vm_phys_alloc_pages(int domain, int pool, int order) | vm_phys_alloc_pages(int domain, int pool, int order) | ||||
{ | { | ||||
vm_page_t m; | vm_page_t m; | ||||
int flind; | int freelist; | ||||
for (flind = 0; flind < vm_nfreelists; flind++) { | for (freelist = 0; freelist < VM_NFREELIST; freelist++) { | ||||
m = vm_phys_alloc_freelist_pages(domain, flind, pool, order); | /* Check if freelist is present */ | ||||
if (vm_freelist_to_flind[freelist] < 0) | |||||
continue; | |||||
jeff: Can we not do this check only once in vm_phys_alloc_freelist_pages? | |||||
m = vm_phys_alloc_freelist_pages(domain, freelist, pool, order); | |||||
if (m != NULL) | if (m != NULL) | ||||
return (m); | return (m); | ||||
} | } | ||||
return (NULL); | return (NULL); | ||||
} | } | ||||
/* | /* | ||||
* Allocate a contiguous, power of two-sized set of physical pages from the | * Allocate a contiguous, power of two-sized set of physical pages from the | ||||
* specified free list. The free list must be specified using one of the | * specified free list. The free list must be specified using one of the | ||||
* manifest constants VM_FREELIST_*. | * manifest constants VM_FREELIST_*. | ||||
* | * | ||||
* The free page queues must be locked. | * The free page queues must be locked. | ||||
*/ | */ | ||||
vm_page_t | vm_page_t | ||||
vm_phys_alloc_freelist_pages(int domain, int flind, int pool, int order) | vm_phys_alloc_freelist_pages(int domain, int freelist, int pool, int order) | ||||
{ | { | ||||
struct vm_freelist *alt, *fl; | struct vm_freelist *alt, *fl; | ||||
vm_page_t m; | vm_page_t m; | ||||
int oind, pind; | int oind, pind, flind; | ||||
KASSERT(domain >= 0 && domain < vm_ndomains, | KASSERT(domain >= 0 && domain < vm_ndomains, | ||||
("vm_phys_alloc_freelist_pages: domain %d is out of range", | ("vm_phys_alloc_freelist_pages: domain %d is out of range", | ||||
domain)); | domain)); | ||||
KASSERT(flind < VM_NFREELIST, | KASSERT(flind < VM_NFREELIST, | ||||
("vm_phys_alloc_freelist_pages: freelist %d is out of range", | ("vm_phys_alloc_freelist_pages: freelist %d is out of range", | ||||
flind)); | flind)); | ||||
KASSERT(pool < VM_NFREEPOOL, | KASSERT(pool < VM_NFREEPOOL, | ||||
("vm_phys_alloc_freelist_pages: pool %d is out of range", pool)); | ("vm_phys_alloc_freelist_pages: pool %d is out of range", pool)); | ||||
KASSERT(order < VM_NFREEORDER, | KASSERT(order < VM_NFREEORDER, | ||||
("vm_phys_alloc_freelist_pages: order %d is out of range", order)); | ("vm_phys_alloc_freelist_pages: order %d is out of range", order)); | ||||
flind = vm_freelist_to_flind[freelist]; | |||||
mtx_assert(&vm_page_queue_free_mtx, MA_OWNED); | mtx_assert(&vm_page_queue_free_mtx, MA_OWNED); | ||||
fl = &vm_phys_free_queues[domain][flind][pool][0]; | fl = &vm_phys_free_queues[domain][flind][pool][0]; | ||||
for (oind = order; oind < VM_NFREEORDER; oind++) { | for (oind = order; oind < VM_NFREEORDER; oind++) { | ||||
m = TAILQ_FIRST(&fl[oind].pl); | m = TAILQ_FIRST(&fl[oind].pl); | ||||
if (m != NULL) { | if (m != NULL) { | ||||
vm_freelist_rem(fl, m, oind); | vm_freelist_rem(fl, m, oind); | ||||
vm_phys_split_pages(m, oind, fl, order); | vm_phys_split_pages(m, oind, fl, order); | ||||
return (m); | return (m); | ||||
▲ Show 20 Lines • Show All 611 Lines • Show Last 20 Lines |
Can we not do this check only once in vm_phys_alloc_freelist_pages?