mmap内存使用浅析
mmap内存使用浅析
mmap的两个flag
MAP_ANONYMOUS
生成无backend的内存mapping.
MAP_POPULATE
populate page table,减少后面的page fault导致的延迟。Side effect是会将申请的所有内存映射到物理内存中,优点是后面从此内存池中申请内存不会发生page fault,速度应该更快。
auto mapped = mmap(nullptr, TOT_SIZE, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS | MAP_POPULATE , -1, 0);
citrix环境中测试
测试无MAP_POPULATE标志
auto mapped = mmap(nullptr, TOT_SIZE, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS , -1, 0);
在测试a.out的时候用top发现,当内存泄漏发生的时候,RES的大小不会随着测试程序中的泄漏增加(因为测试程序只是分配了内存,并没有读写这块内存,没有发生page fault;而当读写发生后触发PAGE FAULT,RES的大小会相应增加)。
真实的linux机(enable 了swap)应该也是这种情况。
clouding环境中测试
测试无MAP_POPULATE标志
auto mapped = mmap(nullptr, TOT_SIZE, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS , -1, 0);
在测试a.out的时候用top发现,当内存泄漏发生的时候,RES的大小会随着测试程序中的泄漏增加(因为在clouding主机中, 没有内存swap)。
##测试代码
#include <memory>
#include <thread>
#include <chrono>
#include <iostream>
#define PMALLOC_TOT_SIZE 30 * 1000 * 1000
#include "pmalloc_impl.h"
class BaseClass{
public:
BaseClass() = default;
private:
BaseClass(const BaseClass&) = delete;
BaseClass& operator = (const BaseClass&) = delete;
constexpr static unsigned int SIZE = 1*1024*1024;
//constexpr static unsigned int SIZE = 1*1024;
char _mem[SIZE];
};
class DerivedClass:public BaseClass{
public:
DerivedClass() = default;
};
int main(int argc, char* argv[]){
pmalloc_enable();
using namespace std::literals::chrono_literals;
while(true){
//std::unique_ptr<DerivedClass> p(new DerivedClass);
BaseClass* p = new BaseClass(); //leak
std::this_thread::sleep_for(1s);
std::cout<<".";
std::cout.flush();
}
pmalloc_disable();
return 0;
}