1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-05-31 13:38:11 +00:00

Kernel: Refactor MemoryManager to use a Bitmap rather than a Vector

This significantly reduces the pressure on the kernel heap when
allocating a lot of pages.

Previously at about 250MB allocated, the free page list would outgrow
the kernel's heap. Given that there is no longer a page list, this does
not happen.

The next barrier will be the kernel memory used by the page records for
in-use memory. This kicks in at about 1GB.
This commit is contained in:
Conrad Pankoff 2019-06-11 21:13:02 +10:00 committed by Andreas Kling
parent 1a77dfed23
commit aee9317d86
8 changed files with 278 additions and 51 deletions

View file

@ -13,6 +13,7 @@
#include <Kernel/Arch/i386/CPU.h>
#include <Kernel/FileSystem/InodeIdentifier.h>
#include <Kernel/VM/PhysicalPage.h>
#include <Kernel/VM/PhysicalRegion.h>
#include <Kernel/VM/Region.h>
#include <Kernel/VM/VMObject.h>
#include <Kernel/VirtualAddress.h>
@ -32,6 +33,7 @@ class MemoryManager {
AK_MAKE_ETERNAL
friend class PageDirectory;
friend class PhysicalPage;
friend class PhysicalRegion;
friend class Region;
friend class VMObject;
friend ByteBuffer procfs$mm(InodeIdentifier);
@ -59,19 +61,23 @@ public:
Yes
};
RetainPtr<PhysicalPage> allocate_physical_page(ShouldZeroFill);
RetainPtr<PhysicalPage> allocate_user_physical_page(ShouldZeroFill);
RetainPtr<PhysicalPage> allocate_supervisor_physical_page();
void deallocate_user_physical_page(PhysicalPage&);
void deallocate_supervisor_physical_page(PhysicalPage&);
void remap_region(PageDirectory&, Region&);
int user_physical_pages_in_existence() const { return s_user_physical_pages_in_existence; }
int super_physical_pages_in_existence() const { return s_super_physical_pages_in_existence; }
void map_for_kernel(VirtualAddress, PhysicalAddress);
RetainPtr<Region> allocate_kernel_region(size_t, String&& name);
void map_region_at_address(PageDirectory&, Region&, VirtualAddress, bool user_accessible);
unsigned user_physical_pages() const { return m_user_physical_pages; }
unsigned user_physical_pages_used() const { return m_user_physical_pages_used; }
unsigned super_physical_pages() const { return m_super_physical_pages; }
unsigned super_physical_pages_used() const { return m_super_physical_pages_used; }
private:
MemoryManager();
~MemoryManager();
@ -206,9 +212,6 @@ private:
dword* m_pte;
};
static unsigned s_user_physical_pages_in_existence;
static unsigned s_super_physical_pages_in_existence;
PageTableEntry ensure_pte(PageDirectory&, VirtualAddress);
RetainPtr<PageDirectory> m_kernel_page_directory;
@ -217,8 +220,13 @@ private:
VirtualAddress m_quickmap_addr;
Vector<Retained<PhysicalPage>> m_free_physical_pages;
Vector<Retained<PhysicalPage>> m_free_supervisor_physical_pages;
unsigned m_user_physical_pages { 0 };
unsigned m_user_physical_pages_used { 0 };
unsigned m_super_physical_pages { 0 };
unsigned m_super_physical_pages_used { 0 };
Vector<Retained<PhysicalRegion>> m_user_physical_regions {};
Vector<Retained<PhysicalRegion>> m_super_physical_regions {};
HashTable<VMObject*> m_vmos;
HashTable<Region*> m_user_regions;