Changeset View
Changeset View
Standalone View
Standalone View
sys/vm/vm_swapout.c
| Show First 20 Lines • Show All 216 Lines • ▼ Show 20 Lines | |||||
| * deactivate some number of pages in a map, try to do it fairly, but | * deactivate some number of pages in a map, try to do it fairly, but | ||||
| * that is really hard to do. | * that is really hard to do. | ||||
| */ | */ | ||||
| static void | static void | ||||
| vm_swapout_map_deactivate_pages(vm_map_t map, long desired) | vm_swapout_map_deactivate_pages(vm_map_t map, long desired) | ||||
| { | { | ||||
| vm_map_entry_t tmpe; | vm_map_entry_t tmpe; | ||||
| vm_object_t obj, bigobj; | vm_object_t obj, bigobj; | ||||
| int nothingwired; | |||||
| if (!vm_map_trylock_read(map)) | if (!vm_map_trylock_read(map)) | ||||
| return; | return; | ||||
| bigobj = NULL; | bigobj = NULL; | ||||
| nothingwired = TRUE; | |||||
| /* | /* | ||||
| * first, search out the biggest object, and try to free pages from | * first, search out the biggest object, and try to free pages from | ||||
| * that. | * that. | ||||
| */ | */ | ||||
| VM_MAP_ENTRY_FOREACH(tmpe, map) { | VM_MAP_ENTRY_FOREACH(tmpe, map) { | ||||
| if ((tmpe->eflags & MAP_ENTRY_IS_SUB_MAP) == 0) { | if ((tmpe->eflags & MAP_ENTRY_IS_SUB_MAP) == 0) { | ||||
| obj = tmpe->object.vm_object; | obj = tmpe->object.vm_object; | ||||
| if (obj != NULL && VM_OBJECT_TRYRLOCK(obj)) { | if (obj != NULL && VM_OBJECT_TRYRLOCK(obj)) { | ||||
| if (obj->shadow_count <= 1 && | if (obj->shadow_count <= 1 && | ||||
| (bigobj == NULL || | (bigobj == NULL || | ||||
| bigobj->resident_page_count < | bigobj->resident_page_count < | ||||
| obj->resident_page_count)) { | obj->resident_page_count)) { | ||||
| if (bigobj != NULL) | if (bigobj != NULL) | ||||
| VM_OBJECT_RUNLOCK(bigobj); | VM_OBJECT_RUNLOCK(bigobj); | ||||
| bigobj = obj; | bigobj = obj; | ||||
| } else | } else | ||||
| VM_OBJECT_RUNLOCK(obj); | VM_OBJECT_RUNLOCK(obj); | ||||
| } | } | ||||
| } | } | ||||
| if (tmpe->wired_count > 0) | |||||
| nothingwired = FALSE; | |||||
| } | } | ||||
| if (bigobj != NULL) { | if (bigobj != NULL) { | ||||
| vm_swapout_object_deactivate(map->pmap, bigobj, desired); | vm_swapout_object_deactivate(map->pmap, bigobj, desired); | ||||
| VM_OBJECT_RUNLOCK(bigobj); | VM_OBJECT_RUNLOCK(bigobj); | ||||
| } | } | ||||
| /* | /* | ||||
| * Next, hunt around for other pages to deactivate. We actually | * Next, hunt around for other pages to deactivate. We actually | ||||
| * do this search sort of wrong -- .text first is not the best idea. | * do this search sort of wrong -- .text first is not the best idea. | ||||
| */ | */ | ||||
| VM_MAP_ENTRY_FOREACH(tmpe, map) { | VM_MAP_ENTRY_FOREACH(tmpe, map) { | ||||
| if (pmap_resident_count(vm_map_pmap(map)) <= desired) | if (pmap_resident_count(vm_map_pmap(map)) <= desired) | ||||
| break; | break; | ||||
| if ((tmpe->eflags & MAP_ENTRY_IS_SUB_MAP) == 0) { | if ((tmpe->eflags & MAP_ENTRY_IS_SUB_MAP) == 0) { | ||||
| obj = tmpe->object.vm_object; | obj = tmpe->object.vm_object; | ||||
| if (obj != NULL) { | if (obj != NULL) { | ||||
| VM_OBJECT_RLOCK(obj); | VM_OBJECT_RLOCK(obj); | ||||
| vm_swapout_object_deactivate(map->pmap, obj, | vm_swapout_object_deactivate(map->pmap, obj, | ||||
| desired); | desired); | ||||
| VM_OBJECT_RUNLOCK(obj); | VM_OBJECT_RUNLOCK(obj); | ||||
| } | } | ||||
| } | } | ||||
| } | |||||
| /* | |||||
| * Remove all mappings if a process is swapped out, this will free page | |||||
| * table pages. | |||||
| */ | |||||
| if (desired == 0 && nothingwired) { | |||||
| pmap_remove(vm_map_pmap(map), vm_map_min(map), | |||||
| vm_map_max(map)); | |||||
| } | } | ||||
| vm_map_unlock_read(map); | vm_map_unlock_read(map); | ||||
| } | } | ||||
| static void | static void | ||||
| vm_daemon(void) | vm_daemon(void) | ||||
| { | { | ||||
| ▲ Show 20 Lines • Show All 129 Lines • Show Last 20 Lines | |||||