内存池主要分为三个部分:class buffer_t,class bufferpool_t,class mempool_t
1.class mempool_t:内存开辟与释放的接口,既可以通过内存池开辟释放或者在超过内存池最大内存分配大小时,通过系统进行开辟与释放。
2.class bufferpool_t:在mempool_t中申请的实际内存大小2^n(2^n<=最大内存分配大小)内存池)对应于一个bufferpool_t,一个bufferpool_t由list链表来管理多个2^n大小的内存块
3.class buffer_t:对实际内存块进行管理与存储。
话不多说,直接上源代码。
class mempool_t:
#include "bufferpool_t.h" class mempool_t { public: static mempool_t *get_instance(); /* 申请内存 @param uint32_t size_ 内存大小 如果size_ 大与max_alloc_size 将重系统请求内存 */ void *alloc(uint32_t size_); /* 释放内存 @param void* 内存句柄 */ bool free(void* ptr); /* 配置内存池最大内存分配大小 @param uint32_t max_alloc_size. 如果 mempool_t.alloc (size):其中 size > max_alloc_size 内存池将重系统分配内存,但是 释放的时候 也一定要调用 mempool_t.free 来释放,否则会内存错误 */ void config(const uint32_t &max_alloc_size = 1<<20); private: mempool_t(void); ~mempool_t(void); typedef std::map<uint32_t ,bufferpool_t *> bufferpool_set_t; bool get_bufferpool_size( uint32_t size_, uint32_t &buf_size_ ); /*向系统请求分配内存 @param uint32_t size_ 内存大小 @return void* 内存句柄 */ void * internal_malloc( const uint32_t &size_ ); /*直接释放内存 @param void *ptr_ 内存句柄 @return bool true成功, false失败,原因是内存不是internal_malloc返回的, 或是内存已经被破坏了*/ bool internal_free(void *ptr_); bufferpool_set_t bufferpool_set; uint32_t max_alloc_size; std::mutex bufferpool_set_mutex; };
#include "stdafx.h" #include "mempool_t.h" mempool_t::mempool_t(void) :max_alloc_size(1<<20)//1MB { } mempool_t::~mempool_t(void) { while (bufferpool_set.empty()==false) { bufferpool_t *bufferpool = bufferpool_set.begin()->second; bufferpool_set.erase(bufferpool_set.begin()); delete bufferpool; } } //设置内存分配对象的实例 mempool_t * mempool_t::get_instance() { static mempool_t *instance = new mempool_t; return instance; } void * mempool_t::alloc( uint32_t size_ ) { uint32_t buf_size; void *buf; bool rc = get_bufferpool_size(size_,buf_size); if (rc) { bufferpool_t *bufferpool; std::lock_guard<std::mutex> lock_guard(bufferpool_set_mutex); bufferpool_set_t::iterator it = bufferpool_set.find(buf_size); if (it == bufferpool_set.end ()) { bufferpool = new bufferpool_t(buf_size); bool rc = bufferpool_set.insert ( bufferpool_set_t::value_type(buf_size,bufferpool)).second; assert(rc); } else { bufferpool = it->second; } buf =(void*) bufferpool->alloc_buffer (); } else { buf = internal_malloc(size_); } return buf; } bool mempool_t::free( void* ptr ) { uint32_t data_size; bool rc = bufferpool_t::get_buffer_size ((char*)ptr,data_size); if (rc) { std::lock_guard<std::mutex> lock_guard(bufferpool_set_mutex); bufferpool_t *bufferpool; bufferpool_set_t::iterator it = bufferpool_set.find(data_size); if (it == bufferpool_set.end ()) { assert(false); } bufferpool = it->second; return bufferpool->free_buffer ((char*)ptr);; } else { return internal_free (ptr); } return false; } bool mempool_t::internal_free( void* ptr_) { char *buf = (char*)ptr_ - sizeof(uint32_t); uint32_t size = *(uint32_t*)buf; if (size > max_alloc_size) { uint32_t tail_size = *(uint32_t*)((char*)ptr_ + size); if (tail_size == size) { delete buf; return true; } } return false; } bool mempool_t::get_bufferpool_size( uint32_t size_, uint32_t &buf_size_ ) { if (size_ > max_alloc_size) { return false; } /* 求整数的最接近2的幂, 向上对齐 */ size_ = size_ - 1; size_ = size_ | (size_ >> 1); size_ = size_ | (size_ >> 2); size_ = size_ | (size_ >> 4); size_ = size_ | (size_ >> 8); size_ = size_ | (size_ >>16); size_ = size_ + 1; /*判断是否是2的幂*/ if(0 != (size_&(size_-1))) { assert(false); } buf_size_ = size_; return true; } void * mempool_t::internal_malloc( const uint32_t &size_ ) { uint32_t buf_size = size_ + sizeof(uint32_t)*2; void *buf = malloc (buf_size); *(uint32_t*)buf = size_; *(uint32_t*)((char*)buf + sizeof(uint32_t)+size_) = size_; return ((char*)buf+sizeof(uint32_t)); } void mempool_t::config( const uint32_t &max_buffer_size_ ) { max_alloc_size = max_buffer_size_; }
class
bufferpool_t:
#include "buffer_t.hpp" class bufferpool_t { public: bufferpool_t(const uint32_t &buffer_size_,const uint32_t &limit_size_ = 20); ~bufferpool_t(void); char *alloc_buffer(); bool free_buffer(char *buffer_); static bool get_buffer_size(char *buffer_, uint32_t &buffer_size_); private: typedef std::list<buffer_t*> buffer_list_t; buffer_list_t buffer_list; //buffer 类型大小,一个bufferpool_t只管理 //同样大小的内存 uint32_t buffer_type_size; //空闲内存最大数量 uint32_t limit_buffer_list_size; //获取内存次数 uint32_t alloc_times; //释放内存次数 uint32_t free_times; };
#include "stdafx.h" #include "bufferpool_t.h" bufferpool_t::bufferpool_t(const uint32_t &buffer_size_,const uint32_t &limit_size_) { buffer_type_size = buffer_size_; limit_buffer_list_size = limit_size_; free_times = 0; alloc_times = 0; } bufferpool_t::~bufferpool_t(void) { buffer_t *buffer; while (buffer_list.empty () == false) { buffer = buffer_list.front (); buffer_list.pop_back (); buffer->relase_buffer(); } } char * bufferpool_t::alloc_buffer() { buffer_t *buffer; char *buf; if (buffer_list.empty ()) { char *buf = new char[buffer_type_size+sizeof(buffer_t)]; buffer = new (buf)buffer_t(buffer_type_size,buf); //添加成员 } else { buffer = buffer_list.front (); buffer_list.pop_front (); } ++alloc_times ; buf = buffer->buf (); buffer->use (true); return buf; } bool bufferpool_t::free_buffer( char * buffer_) { buffer_t *buffer = (buffer_t*)(buffer_ - sizeof(buffer_t)); if (buffer->check_code () && buffer->length () == buffer_type_size) { if(buffer_list.size () < limit_buffer_list_size) { buffer->use (false); buffer_list.push_back (buffer); ++free_times; return true; } else { buffer->relase_buffer(); return true; } } return false; } bool bufferpool_t::get_buffer_size( char *buffer_ ,uint32_t &buffer_size_) { buffer_t *buffer = (buffer_t*)(buffer_ - sizeof(buffer_t)); if (buffer->check_code () && buffer->use()&& buffer->buf () == buffer_) { buffer_size_ = buffer->length (); return true; } else { return false; } }
class buffer_t:
#pragma once #include "stddef.hpp" class buffer_t { public: inline buffer_t(uint32_t length_, char *data_buf_) { buf_code = 0xbeaf; buf_length = length_; buf_data = data_buf_; } inline void relase_buffer(void) { delete []buf_data; } inline bool check_code() { return buf_code == 0xbeaf; } inline char *buf() { return buf_data+sizeof(*this); } inline uint32_t length() { return buf_length; } inline bool use() { return is_use; } inline void use(const bool &is_use_) { is_use = is_use_; } private: char *buf_data; bool is_use; uint32_t buf_code; uint32_t buf_length; };
写的不好的地方,请指出
时间: 2024-11-05 13:25:47