[haiku-commits] r34309 - in haiku/trunk: headers/private/kernel src/system/kernel src/system/kernel/vm

  • From: axeld@xxxxxxxxxxxxxxxx
  • To: haiku-commits@xxxxxxxxxxxxx
  • Date: Fri, 27 Nov 2009 14:03:28 +0100 (CET)

Author: axeld
Date: 2009-11-27 14:03:28 +0100 (Fri, 27 Nov 2009)
New Revision: 34309
Changeset: http://dev.haiku-os.org/changeset/34309/haiku

Modified:
   haiku/trunk/headers/private/kernel/low_resource_manager.h
   haiku/trunk/headers/private/kernel/vm.h
   haiku/trunk/src/system/kernel/low_resource_manager.cpp
   haiku/trunk/src/system/kernel/vm/vm.cpp
Log:
* The kernel's address space is now also a resource that is known to the low
  resource manager.
* Could be drastically improved, though, by taking the fragmentation into
  account.


Modified: haiku/trunk/headers/private/kernel/low_resource_manager.h
===================================================================
--- haiku/trunk/headers/private/kernel/low_resource_manager.h   2009-11-27 
12:34:15 UTC (rev 34308)
+++ haiku/trunk/headers/private/kernel/low_resource_manager.h   2009-11-27 
13:03:28 UTC (rev 34309)
@@ -1,6 +1,6 @@
 /*
  * Copyright 2008, Ingo Weinhold, ingo_weinhold@xxxxxxx
- * Copyright 2005-2007, Axel Dörfler, axeld@xxxxxxxxxxxxxxxxx All rights 
reserved.
+ * Copyright 2005-2009, Axel Dörfler, axeld@xxxxxxxxxxxxxxxxx
  * Distributed under the terms of the MIT License.
  */
 #ifndef _KERNEL_LOW_RESOURCE_MANAGER_H
@@ -22,10 +22,12 @@
        B_KERNEL_RESOURCE_PAGES                 = 0x01, /* physical pages */
        B_KERNEL_RESOURCE_MEMORY                = 0x02, /* reservable memory */
        B_KERNEL_RESOURCE_SEMAPHORES    = 0x04, /* semaphores */
+       B_KERNEL_RESOURCE_ADDRESS_SPACE = 0x08, /* address space */
 
        B_ALL_KERNEL_RESOURCES                  = B_KERNEL_RESOURCE_PAGES
                                                                                
| B_KERNEL_RESOURCE_MEMORY
                                                                                
| B_KERNEL_RESOURCE_SEMAPHORES
+                                                                               
| B_KERNEL_RESOURCE_ADDRESS_SPACE
 };
 
 typedef void (*low_resource_func)(void *data, uint32 resources, int32 level);

Modified: haiku/trunk/headers/private/kernel/vm.h
===================================================================
--- haiku/trunk/headers/private/kernel/vm.h     2009-11-27 12:34:15 UTC (rev 
34308)
+++ haiku/trunk/headers/private/kernel/vm.h     2009-11-27 13:03:28 UTC (rev 
34309)
@@ -115,6 +115,7 @@
 uint32 vm_num_page_faults(void);
 off_t vm_available_memory(void);
 off_t vm_available_not_needed_memory(void);
+size_t vm_kernel_address_space_left(void);
 
 status_t vm_memset_physical(addr_t address, int value, size_t length);
 status_t vm_memcpy_from_physical(void* to, addr_t from, size_t length,

Modified: haiku/trunk/src/system/kernel/low_resource_manager.cpp
===================================================================
--- haiku/trunk/src/system/kernel/low_resource_manager.cpp      2009-11-27 
12:34:15 UTC (rev 34308)
+++ haiku/trunk/src/system/kernel/low_resource_manager.cpp      2009-11-27 
13:03:28 UTC (rev 34309)
@@ -1,6 +1,6 @@
 /*
  * Copyright 2008, Ingo Weinhold, ingo_weinhold@xxxxxxx
- * Copyright 2005-2008, Axel Dörfler, axeld@xxxxxxxxxxxxxxxxx
+ * Copyright 2005-2009, Axel Dörfler, axeld@xxxxxxxxxxxxxxxxx
  * Distributed under the terms of the MIT License.
  */
 
@@ -35,7 +35,7 @@
 struct low_resource_handler
                : public DoublyLinkedListLinkImpl<low_resource_handler> {
        low_resource_func       function;
-       void                            *data;
+       void*                           data;
        uint32                          resources;
        int32                           priority;
 };
@@ -63,6 +63,7 @@
 static int32 sLowPagesState = B_NO_LOW_RESOURCE;
 static int32 sLowMemoryState = B_NO_LOW_RESOURCE;
 static int32 sLowSemaphoresState = B_NO_LOW_RESOURCE;
+static int32 sLowSpaceState = B_NO_LOW_RESOURCE;
 static uint32 sLowResources = 0;       // resources that are not 
B_NO_LOW_RESOURCE
 static bigtime_t sLastMeasurement;
 
@@ -85,6 +86,8 @@
                state = max_c(state, sLowMemoryState);
        if ((resources & B_KERNEL_RESOURCE_SEMAPHORES) != 0)
                state = max_c(state, sLowSemaphoresState);
+       if ((resources & B_KERNEL_RESOURCE_ADDRESS_SPACE) != 0)
+               state = max_c(state, sLowSpaceState);
 
        return state;
 }
@@ -104,7 +107,7 @@
        low_resource_handler marker;
        sLowResourceHandlers.Insert(&marker, false);
 
-       while (low_resource_handler *handler
+       while (low_resource_handler* handler
                        = sLowResourceHandlers.GetNext(&marker)) {
                // swap with handler
                sLowResourceHandlers.Swap(&marker, handler);
@@ -173,11 +176,27 @@
                sLowSemaphoresState = B_NO_LOW_RESOURCE;
                sLowResources &= ~B_KERNEL_RESOURCE_SEMAPHORES;
        }
+       
+       // free kernel address space state
+       // TODO: this should take fragmentation into account
+       size_t maxSpace = KERNEL_SIZE;
+       size_t freeSpace = vm_kernel_address_space_left();
+
+       if (freeSpace < maxSpace >> 16)
+               sLowSpaceState = B_LOW_RESOURCE_CRITICAL;
+       if (freeSpace < maxSpace >> 8)
+               sLowSpaceState = B_LOW_RESOURCE_WARNING;
+       if (freeSpace < maxSpace >> 4)
+               sLowSpaceState = B_LOW_RESOURCE_NOTE;
+       else {
+               sLowSpaceState = B_NO_LOW_RESOURCE;
+               sLowResources &= ~B_KERNEL_RESOURCE_ADDRESS_SPACE;
+       }
 }
 
 
-static int32
-low_resource_manager(void *)
+static status_t
+low_resource_manager(void*)
 {
        bigtime_t timeout = kLowResourceInterval;
        while (true) {
@@ -231,15 +250,17 @@
 
 
 static int
-dump_handlers(int argc, char **argv)
+dump_handlers(int argc, char** argv)
 {
-       kprintf("current state: %c%c%c\n",
+       kprintf("current state: %c%c%c%c\n",
                (sLowResources & B_KERNEL_RESOURCE_PAGES) != 0 ? 'p' : '-',
                (sLowResources & B_KERNEL_RESOURCE_MEMORY) != 0 ? 'm' : '-',
-               (sLowResources & B_KERNEL_RESOURCE_SEMAPHORES) != 0 ? 's' : 
'-');
+               (sLowResources & B_KERNEL_RESOURCE_SEMAPHORES) != 0 ? 's' : '-',
+               (sLowResources & B_KERNEL_RESOURCE_ADDRESS_SPACE) != 0 ? 'a' : 
'-');
        kprintf("  pages:  %s\n", state_to_string(sLowPagesState));
        kprintf("  memory: %s\n", state_to_string(sLowMemoryState));
-       kprintf("  sems:   %s\n\n", state_to_string(sLowSemaphoresState));
+       kprintf("  sems:   %s\n", state_to_string(sLowSemaphoresState));
+       kprintf("  aspace: %s\n\n", state_to_string(sLowSpaceState));
 
        HandlerList::Iterator iterator = sLowResourceHandlers.GetIterator();
        kprintf("function    data         resources  prio  function-name\n");
@@ -282,9 +303,10 @@
                case B_KERNEL_RESOURCE_PAGES:
                        vm_schedule_page_scanner(requirements);
                        break;
+
                case B_KERNEL_RESOURCE_MEMORY:
-                       break;
                case B_KERNEL_RESOURCE_SEMAPHORES:
+               case B_KERNEL_RESOURCE_ADDRESS_SPACE:
                        break;
        }
 
@@ -354,7 +376,7 @@
 
 
 status_t
-unregister_low_resource_handler(low_resource_func function, void *data)
+unregister_low_resource_handler(low_resource_func function, void* data)
 {
        TRACE(("unregister_low_resource_handler(function = %p, data = %p)\n",
                function, data));
@@ -363,7 +385,7 @@
        HandlerList::Iterator iterator = sLowResourceHandlers.GetIterator();
 
        while (iterator.HasNext()) {
-               low_resource_handler *handler = iterator.Next();
+               low_resource_handler* handler = iterator.Next();
 
                if (handler->function == function && handler->data == data) {
                        sLowResourceHandlers.Remove(handler);
@@ -380,13 +402,13 @@
        the handler will be called in low resource situations.
 */
 status_t
-register_low_resource_handler(low_resource_func function, void *data,
+register_low_resource_handler(low_resource_func function, void* data,
        uint32 resources, int32 priority)
 {
        TRACE(("register_low_resource_handler(function = %p, data = %p)\n",
                function, data));
 
-       low_resource_handler *newHandler = (low_resource_handler *)malloc(
+       low_resource_handler *newHandler = (low_resource_handler*)malloc(
                sizeof(low_resource_handler));
        if (newHandler == NULL)
                return B_NO_MEMORY;
@@ -402,7 +424,7 @@
 
        HandlerList::ReverseIterator iterator
                = sLowResourceHandlers.GetReverseIterator();
-       low_resource_handler *last = NULL;
+       low_resource_handler* last = NULL;
        while (iterator.HasNext()) {
                low_resource_handler *handler = iterator.Next();
 

Modified: haiku/trunk/src/system/kernel/vm/vm.cpp
===================================================================
--- haiku/trunk/src/system/kernel/vm/vm.cpp     2009-11-27 12:34:15 UTC (rev 
34308)
+++ haiku/trunk/src/system/kernel/vm/vm.cpp     2009-11-27 13:03:28 UTC (rev 
34309)
@@ -227,6 +227,9 @@
        vm_area** _area, const char* areaName, bool unmapAddressRange, bool 
kernel);
 
 
+static size_t sKernelAddressSpaceLeft = KERNEL_SIZE;
+
+
 //     #pragma mark -
 
 
@@ -1383,8 +1386,12 @@
 
        status = find_and_insert_area_slot(addressSpace, searchBase, size,
                searchEnd, addressSpec, area);
-       if (status == B_OK)
+       if (status == B_OK) {
                *_address = (void*)area->base;
+               
+               if (addressSpace == vm_kernel_address_space())
+                       sKernelAddressSpaceLeft -= area->size;
+       }
 
        return status;
 }
@@ -1668,8 +1675,16 @@
        }
 
        status = insert_area(addressSpace, _virtualAddress, addressSpec, size, 
area);
-       if (status != B_OK)
+       if (status != B_OK) {
+               // TODO: wait and try again once this is working in the backend
+#if 0
+               if (status == B_NO_MEMORY && addressSpec == 
B_ANY_KERNEL_ADDRESS) {
+                       low_resource(B_KERNEL_RESOURCE_ADDRESS_SPACE, size,
+                               0, 0);
+               }
+#endif
                goto err2;
+       }
 
        // attach the cache to the area
        area->cache = cache;
@@ -2006,7 +2021,7 @@
                addressSpec, wiring, protection, REGION_NO_PRIVATE_MAP, &area, 
name,
                (flags & CREATE_AREA_UNMAP_ADDRESS_RANGE) != 0, kernel);
 
-       if (status < B_OK) {
+       if (status != B_OK) {
                cache->ReleaseRefAndUnlock();
                goto err1;
        }
@@ -2751,6 +2766,9 @@
        if (area == addressSpace->area_hint)
                addressSpace->area_hint = NULL;
 
+       if (addressSpace == vm_kernel_address_space())
+               sKernelAddressSpaceLeft -= area->size;
+
        if (temp == NULL)
                panic("vm_area_release_ref: area not found in aspace's area 
list\n");
 }
@@ -5264,6 +5282,13 @@
 }
 
 
+size_t
+vm_kernel_address_space_left(void)
+{
+       return sKernelAddressSpaceLeft;
+}
+
+
 void
 vm_unreserve_memory(size_t amount)
 {


Other related posts:

  • » [haiku-commits] r34309 - in haiku/trunk: headers/private/kernel src/system/kernel src/system/kernel/vm - axeld