2015-11-19 63 views
0

在C或C++程序內部分配內存時,有一種方法(即使是外來的)來設置swappiness,或者向操作系統提供關於它的提示?爲分配的內存設置swappiness

請注意,我不想爲整個過程設置swappiness,而是設置對象/變量級別。

+1

* swappiness *是什麼意思? – NathanOliver

+1

Swappiness是一個Linux內核參數,用於控制交換運行時內存的相對權重,而不是從系統頁面緩存中刪除頁面。 https://en.wikipedia.org/wiki/Swappiness – Nicola

+0

這是一個錘子,並沒有提供任何調整,但POSIX提供'mlock()'和'mlockall()'。這不是一個真正的答案,但從這裏開始:http://pubs.opengroup.org/onlinepubs/7908799/xsh/mlock.html –

回答

3

一般來說,如果沒有自定義分配器,就無法做到這一點。像mlockposix_madvise這樣的東西在頁面級別上工作,並且它們基本上是開/關開關。所以對於普通的堆,你會調整你分配的對象的「swappiness」(但是你定義了它)和其他發生共享相同頁面的東西,如果你隨後分配了一個不同的新對象「swappiness」,它結束了在同一頁面,你會覆蓋舊的設置。

要完成這項工作,基本上需要爲「swappiness」維護一堆具有不同堆全局設置的獨立堆,並根據需要爲每個堆分配對象。並且因爲超載operator new是基於每種類型的,所以如果您想要更改同一類型的不同對象的行爲,則會卡住手動執行每個堆的原始分配並執行放置new/delete以動態更改所需的「 swappiness」。

無論你做什麼,分配的任何堆棧都不能使用這種方法,因爲堆棧不能像這樣拆分,所以爲一個堆棧對象調整「swappiness」也會調整它的大量內容(變量以及返回地址存儲和註冊泄漏等)。

注意:如果你正在談論Linux內核swappiness作爲@nicolacdnil suggests in the comments,那是不可能的。這是適用於整個系統的內核級別設置,甚至在每個進程級別都不可調,更不用說每個對象級別。

+0

「這是一個適用於整個系統的內核級設置,甚至在每個進程級別都不可調,更不用說每個對象級別了。」這是我所期待的。謝謝。 – Nicola

0

您可以使用mlock

struct MyStruct { // ... }; 

void * memory_pool = malloc(sizeof(MyStruct)); 
mlock(memory_pool, sizeof(MyStruct)); 

MyStruct * my_struct = new(memory_pool) MyStruct(); 

// (You must check all values returned by `malloc`, `mlock` and `new`!) 

my_struct會在物理內存中並不會被交換到磁盤,直到調用munlock()或進程退出。

+0

當然,如果你再'malloc'第二個'MyStruct'和'mlock',它們就會出現在同一個頁面中。如果你在「釋放」它們之前先「解鎖」其中的任何一個,你就會「解鎖」它們兩個。 'mlock'是頁面粒度和布爾標誌;任何數量的鎖都由一個「munlock」撤消。 – ShadowRanger

+0

@ShadowRanger你可能會得到足夠大的memory_pool對象,然後使用一個'mlock'。 – vladon

+2

另外,'mlock' /'munlock'的POSIX標準允許一個實現要求爲鎖定傳遞的地址是頁面對齊的,所以你的例子不保證是可移植的。你需要明確地強制頁面對齊,如'void * pool_base_addr =(void *)((intptr_t)memory_pool&〜(sysconf(_SC_PAGESIZE) - 1)); mlock(pool_base_addr,memory_pool + sizeof(MyStruct) - pool_base_addr);',醜陋,但可移植(可能需要一個或兩個沉默簽名警告)。 – ShadowRanger