diff options
author | Nick Bofferding <bofferdn@us.ibm.com> | 2015-02-28 01:26:21 -0600 |
---|---|---|
committer | A. Patrick Williams III <iawillia@us.ibm.com> | 2015-03-01 16:55:08 -0600 |
commit | f2dd720826afaa6669feb9baed6196c960383899 (patch) | |
tree | 34d85a15a755ee7e685c911b2762f3c393e187d7 /src/kernel/pagemgr.C | |
parent | db9b6fed621390d10459834300924e0fafd6fa04 (diff) | |
download | talos-hostboot-f2dd720826afaa6669feb9baed6196c960383899.tar.gz talos-hostboot-f2dd720826afaa6669feb9baed6196c960383899.zip |
Reduce memory fragementation in large allocations
- Free excess allocation pages in reverse order
Change-Id: I4c5f2909275e2d3dc71b0806fbf177a101b47292
CQ: FW633822
Reviewed-on: http://gfw160.aus.stglabs.ibm.com:8080/gerrit/16066
Tested-by: Jenkins Server
Reviewed-by: Daniel M. Crowell <dcrowell@us.ibm.com>
Reviewed-by: A. Patrick Williams III <iawillia@us.ibm.com>
Diffstat (limited to 'src/kernel/pagemgr.C')
-rw-r--r-- | src/kernel/pagemgr.C | 21 |
1 files changed, 14 insertions, 7 deletions
diff --git a/src/kernel/pagemgr.C b/src/kernel/pagemgr.C index c6a65dd92..c5e7d6960 100644 --- a/src/kernel/pagemgr.C +++ b/src/kernel/pagemgr.C @@ -98,7 +98,7 @@ PageManagerCore::page_t * PageManagerCore::allocatePage( size_t i_pageCount ) freePage(reinterpret_cast<void*>( reinterpret_cast<uintptr_t>(page) + (i_pageCount*PAGESIZE)), - bucket_size - i_pageCount); + bucket_size - i_pageCount,true); } } @@ -107,7 +107,10 @@ PageManagerCore::page_t * PageManagerCore::allocatePage( size_t i_pageCount ) -void PageManagerCore::freePage( void * i_page, size_t i_pageCount ) +void PageManagerCore::freePage( + void* i_page, + size_t i_pageCount, + bool i_overAllocated) { if ((NULL == i_page) || (0 == i_pageCount)) return; @@ -115,7 +118,10 @@ void PageManagerCore::freePage( void * i_page, size_t i_pageCount ) __builtin_clzl(i_pageCount)); size_t bucket_size = ((size_t)1) << which_bucket; - push_bucket((page_t*)i_page, which_bucket); + push_bucket( + (page_t*)(reinterpret_cast<uintptr_t>(i_page) + + (i_overAllocated ? ((i_pageCount-bucket_size)*PAGESIZE) : 0)), + which_bucket); // Update statistics. __sync_add_and_fetch(&iv_available, bucket_size); @@ -124,10 +130,11 @@ void PageManagerCore::freePage( void * i_page, size_t i_pageCount ) // spare pages to free. ie. the non-2^k portion of i_pageCount. if (bucket_size != i_pageCount) { - freePage(reinterpret_cast<void*>( - reinterpret_cast<uintptr_t>(i_page) + - (bucket_size*PAGESIZE)), - i_pageCount - bucket_size); + freePage( + reinterpret_cast<void*>( + reinterpret_cast<uintptr_t>(i_page) + + (i_overAllocated ? 0 : (bucket_size*PAGESIZE))), + i_pageCount - bucket_size, i_overAllocated); } return; |