diff options
author | alc <alc@FreeBSD.org> | 2003-10-03 22:46:53 +0000 |
---|---|---|
committer | alc <alc@FreeBSD.org> | 2003-10-03 22:46:53 +0000 |
commit | b1691aebe4218b5dedfc2dac5620bc1e02226f72 (patch) | |
tree | 10ac1c9d9b930d5a0606d41e87f29b5d53946de0 /sys/ia64 | |
parent | 678d7d93783f9161ce47727c8e23987c819d7ab6 (diff) | |
download | FreeBSD-src-b1691aebe4218b5dedfc2dac5620bc1e02226f72.zip FreeBSD-src-b1691aebe4218b5dedfc2dac5620bc1e02226f72.tar.gz |
Migrate pmap_prefault() into the machine-independent virtual memory layer.
A small helper function pmap_is_prefaultable() is added. This function
encapsulate the few lines of pmap_prefault() that actually vary from
machine to machine. Note: pmap_is_prefaultable() and pmap_mincore() have
much in common. Going forward, it's worth considering their merger.
Diffstat (limited to 'sys/ia64')
-rw-r--r-- | sys/ia64/ia64/pmap.c | 112 |
1 files changed, 17 insertions, 95 deletions
diff --git a/sys/ia64/ia64/pmap.c b/sys/ia64/ia64/pmap.c index a404707..40400cf 100644 --- a/sys/ia64/ia64/pmap.c +++ b/sys/ia64/ia64/pmap.c @@ -1736,101 +1736,6 @@ pmap_object_init_pt(pmap_t pmap, vm_offset_t addr, } /* - * pmap_prefault provides a quick way of clustering - * pagefaults into a processes address space. It is a "cousin" - * of pmap_object_init_pt, except it runs at page fault time instead - * of mmap time. - */ -#define PFBAK 4 -#define PFFOR 4 -#define PAGEORDER_SIZE (PFBAK+PFFOR) - -static int pmap_prefault_pageorder[] = { - -1 * PAGE_SIZE, 1 * PAGE_SIZE, - -2 * PAGE_SIZE, 2 * PAGE_SIZE, - -3 * PAGE_SIZE, 3 * PAGE_SIZE, - -4 * PAGE_SIZE, 4 * PAGE_SIZE -}; - -void -pmap_prefault(pmap, addra, entry) - pmap_t pmap; - vm_offset_t addra; - vm_map_entry_t entry; -{ - int i; - vm_offset_t starta; - vm_offset_t addr; - vm_pindex_t pindex; - vm_page_t m, mpte; - vm_object_t object; - - if (!curthread || (pmap != vmspace_pmap(curthread->td_proc->p_vmspace))) - return; - - object = entry->object.vm_object; - - starta = addra - PFBAK * PAGE_SIZE; - if (starta < entry->start) { - starta = entry->start; - } else if (starta > addra) { - starta = 0; - } - - mpte = NULL; - for (i = 0; i < PAGEORDER_SIZE; i++) { - vm_object_t backing_object, lobject; - struct ia64_lpte *pte; - - addr = addra + pmap_prefault_pageorder[i]; - if (addr > addra + (PFFOR * PAGE_SIZE)) - addr = 0; - - if (addr < starta || addr >= entry->end) - continue; - - pte = pmap_find_vhpt(addr); - if (pte && pte->pte_p) - continue; - - pindex = ((addr - entry->start) + entry->offset) >> PAGE_SHIFT; - lobject = object; - VM_OBJECT_LOCK(lobject); - while ((m = vm_page_lookup(lobject, pindex)) == NULL && - lobject->type == OBJT_DEFAULT && - (backing_object = lobject->backing_object) != NULL) { - if (lobject->backing_object_offset & PAGE_MASK) - break; - pindex += lobject->backing_object_offset >> PAGE_SHIFT; - VM_OBJECT_LOCK(backing_object); - VM_OBJECT_UNLOCK(lobject); - lobject = backing_object; - } - VM_OBJECT_UNLOCK(lobject); - /* - * give-up when a page is not in memory - */ - if (m == NULL) - break; - vm_page_lock_queues(); - if (((m->valid & VM_PAGE_BITS_ALL) == VM_PAGE_BITS_ALL) && - (m->busy == 0) && - (m->flags & (PG_BUSY | PG_FICTITIOUS)) == 0) { - - if ((m->queue - m->pc) == PQ_CACHE) { - vm_page_deactivate(m); - } - vm_page_busy(m); - vm_page_unlock_queues(); - pmap_enter_quick(pmap, addr, m, NULL); - vm_page_lock_queues(); - vm_page_wakeup(m); - } - vm_page_unlock_queues(); - } -} - -/* * Routine: pmap_change_wiring * Function: Change the wiring attribute for a map/virtual-address * pair. @@ -2148,6 +2053,23 @@ pmap_is_modified(vm_page_t m) } /* + * pmap_is_prefaultable: + * + * Return whether or not the specified virtual address is elgible + * for prefault. + */ +boolean_t +pmap_is_prefaultable(pmap_t pmap, vm_offset_t addr) +{ + struct ia64_lpte *pte; + + pte = pmap_find_vhpt(addr); + if (pte && pte->pte_p) + return (FALSE); + return (TRUE); +} + +/* * Clear the modify bits on the specified physical page. */ void |