Now other code accounts for reserved regions in the standard region_list as well.

Introduced RESERVED_REGION_ID definition.
Some minor cleanups.


git-svn-id: file:///srv/svn/repos/haiku/trunk/current@7886 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Axel Dörfler
2004-06-10 02:03:55 +00:00
parent c9df0d11c8
commit fab1cad1b8
2 changed files with 109 additions and 70 deletions
+50 -21
View File
@@ -82,14 +82,16 @@ static vm_region *vm_virtual_map_lookup(vm_virtual_map *map, addr_t address);
//static void vm_region_release_ref(vm_region *region);
//static void vm_region_release_ref2(vm_region *region);
static int region_compare(void *_r, const void *key)
static int
region_compare(void *_r, const void *key)
{
vm_region *r = _r;
const region_id *id = key;
if (r->id == *id)
return 0;
else
return -1;
}
@@ -101,9 +103,9 @@ region_hash(void *_r, const void *key, uint32 range)
const region_id *id = key;
if (r != NULL)
return (r->id % range);
else
return (*id % range);
return r->id % range;
return *id % range;
}
@@ -115,7 +117,7 @@ aspace_compare(void *_a, const void *key)
if (aspace->id == *id)
return 0;
else
return -1;
}
@@ -171,12 +173,15 @@ region_id vm_find_region_by_name(aspace_id aid, const char *name)
acquire_sem_etc(aspace->virtual_map.sem, READ_COUNT, 0, 0);
region = aspace->virtual_map.region_list;
while(region != NULL) {
for (; region != NULL; region = region->aspace_next) {
// ignore reserved space regions
if (region->id == RESERVED_REGION_ID)
continue;
if (strcmp(region->name, name) == 0) {
id = region->id;
break;
}
region = region->aspace_next;
}
release_sem_etc(aspace->virtual_map.sem, READ_COUNT, 0);
@@ -193,7 +198,7 @@ _vm_create_reserved_region_struct(vm_virtual_map *map)
return NULL;
memset(reserved, 0, sizeof(vm_region));
reserved->id = -1;
reserved->id = RESERVED_REGION_ID;
// this marks it as reserved space
reserved->map = map;
@@ -251,7 +256,7 @@ find_reserved_region(vm_virtual_map *map, addr_t start, addr_t size, vm_region *
while (next) {
if (next->base <= start && next->base + next->size >= start + size) {
// this region covers the requested range
if (next->id != -1) {
if (next->id != RESERVED_REGION_ID) {
// but it's not reserved space, it's a real region
return ERR_VM_NO_REGION_SLOT;
}
@@ -648,7 +653,7 @@ vm_unreserve_address_range(aspace_id aid, void *address, addr_t size)
area = addressSpace->virtual_map.region_list;
while (area) {
// the region must be completely part of the reserved range
if (area->id == -1 && area->base >= (addr_t)address
if (area->id == RESERVED_REGION_ID && area->base >= (addr_t)address
&& area->base + area->size <= (addr_t)address + size) {
// remove reserved range
vm_region *reserved = area;
@@ -1130,7 +1135,7 @@ vm_clone_region(aspace_id aid, char *name, void **address, int addr_type,
if (err < 0)
return err;
else
return new_region->id;
}
@@ -1191,6 +1196,10 @@ _vm_put_region(vm_region *region, bool aspace_locked)
vm_address_space *aspace;
bool removeit = false;
// we should never get here, but if we do, we can handle it
if (region->id == RESERVED_REGION_ID)
return;
acquire_sem_etc(region_hash_sem, WRITE_COUNT, 0, 0);
if (atomic_add(&region->ref_count, -1) == 1) {
hash_remove(region_table, region);
@@ -1239,7 +1248,6 @@ _vm_put_region(vm_region *region, bool aspace_locked)
// now we can give up the last ref to the aspace
vm_put_aspace(aspace);
if(region->name)
free(region->name);
free(region);
@@ -1512,17 +1520,21 @@ dump_region(int argc, char **argv)
region_id
find_region_by_address(addr_t vaddress)
find_region_by_address(addr_t address)
{
vm_address_space *aspace;
vm_region *region;
region_id result = B_ERROR;
aspace = vm_get_current_user_aspace();
for(region = aspace->virtual_map.region_list; region != NULL; region = region->aspace_next)
{
if ((vaddress>=region->base) && (vaddress<=(region->base+region->size)))
for (region = aspace->virtual_map.region_list; region != NULL; region = region->aspace_next) {
if (region->id == RESERVED_REGION_ID)
continue;
if (address >= region->base && address <= region->base + region->size) {
result = region->id;
break;
}
}
vm_put_aspace(aspace);
return result;
@@ -1802,6 +1814,13 @@ vm_delete_aspace(aspace_id aid)
region = aspace->virtual_map.region_list;
while (region) {
next = region->aspace_next;
if (region->id == RESERVED_REGION_ID) {
// just remove it
free(region);
region = next;
continue;
}
// decrement the ref on this region, may actually push the ref < 0, but that's okay
_vm_put_region(region, true);
region = next;
@@ -2103,7 +2122,8 @@ forbid_page_faults(void)
}
int vm_page_fault(addr_t address, addr_t fault_address, bool is_write, bool is_user, addr_t *newip)
int
vm_page_fault(addr_t address, addr_t fault_address, bool is_write, bool is_user, addr_t *newip)
{
int err;
@@ -2443,6 +2463,9 @@ vm_virtual_map_lookup(vm_virtual_map *map, addr_t address)
return region;
for (region = map->region_list; region != NULL; region = region->aspace_next) {
if (region->id == RESERVED_REGION_ID)
continue;
if (region->base <= address && (region->base + region->size) > address)
break;
}
@@ -2452,17 +2475,23 @@ vm_virtual_map_lookup(vm_virtual_map *map, addr_t address)
return region;
}
int vm_get_physical_page(addr_t paddr, addr_t *vaddr, int flags)
int
vm_get_physical_page(addr_t paddr, addr_t *vaddr, int flags)
{
return (*kernel_aspace->translation_map.ops->get_physical_page)(paddr, vaddr, flags);
}
int vm_put_physical_page(addr_t vaddr)
int
vm_put_physical_page(addr_t vaddr)
{
return (*kernel_aspace->translation_map.ops->put_physical_page)(vaddr);
}
void vm_increase_max_commit(addr_t delta)
void
vm_increase_max_commit(addr_t delta)
{
int state;
+11 -1
View File
@@ -2,6 +2,7 @@
** Copyright 2001, Travis Geiselbrecht. All rights reserved.
** Distributed under the terms of the NewOS License.
*/
#include <kernel.h>
#include <thread.h>
#include <debug.h>
@@ -17,7 +18,9 @@ bool trimming_cycle;
static addr free_memory_low_water;
static addr free_memory_high_water;
static void scan_pages(vm_address_space *aspace, addr free_target)
static void
scan_pages(vm_address_space *aspace, addr free_target)
{
vm_region *first_region;
vm_region *region;
@@ -46,6 +49,12 @@ static void scan_pages(vm_address_space *aspace, addr free_target)
region = first_region;
for (;;) {
// ignore reserved ranges
while (region != NULL && region->id == RESERVED_REGION_ID)
region = region->aspace_next;
if (region == NULL)
break;
// scan the pages in this region
mutex_lock(&region->cache_ref->lock);
if (!region->cache_ref->cache->scan_skip) {
@@ -121,6 +130,7 @@ static void scan_pages(vm_address_space *aspace, addr free_target)
// dprintf("exiting scan_pages\n");
}
static int32
page_daemon(void *unused)
{