现在的位置: 首页 > 综合 > 正文

嵌入式(标准C环境下)下通用的内存池的实现—C文件

2014年10月16日 ⁄ 综合 ⁄ 共 7509字 ⁄ 字号 评论关闭
  1. #include "avit_memory_pool.h"
  2. #include "avit_oc_print.h"
  3. static UINT32 peak_memory_use = 0;
  4. static UINT32 now_memory_use = 0;
  5. static BYTE* pool_adr = NULL;
  6. static MemNode* pool_link = NULL;
  7. static MemNode* memory_pool_first_fitting(UINT32 size);
  8. void memory_pool_dump()
  9. {
  10.     MemNode* temp_node = pool_link;
  11.     temp_node = pool_link;
  12.     while(TRUE)
  13.     {
  14.         if( temp_node == NULL ) break;
  15.         oc_println("[0x%08X][0x%08X][0x%08X][0x%08X][%d][%d]",
  16.             temp_node->last,
  17.             temp_node,
  18.             temp_node->next,
  19.             temp_node->addr,
  20.             temp_node->size,
  21.             temp_node->used
  22.             );
  23.         temp_node = temp_node->next ;       
  24.     }
  25. }
  26. UINT32 memory_pool_get_available_size()
  27. {
  28.     return (MEMORY_POOL_SIZE-now_memory_use);
  29. }
  30. UINT32 memory_pool_get_peak_use()
  31. {
  32.     return peak_memory_use;
  33. }
  34. UINT32 memory_pool_get_now_use()
  35. {
  36.     return now_memory_use;
  37. }
  38. INT32 memory_pool_init()
  39. {
  40.     if(!MEMORY_POOL_ENABLE) return J_SUCCESS;
  41.     memory_pool_release();
  42.     oc_println("memory pool initialized");
  43.     oc_println("memory pool size is %d",MEMORY_POOL_SIZE);
  44.     if(J_OSP_GetAvailableMemorySize() < MEMORY_POOL_SIZE )
  45.     {
  46.         oc_println("There is no enough memor for oc");
  47.         return J_FAILURE;
  48.     }
  49.     
  50.     // 分配池所要用到的内存
  51.     pool_adr = J_OSP_AllocateMemory(MEMORY_POOL_SIZE);
  52.     if(pool_adr == NULL) return J_FAILURE;
  53.     // 建立池的第一个结点
  54.     pool_link = (MemNode*)J_OSP_AllocateMemory(sizeof(MemNode));
  55.     pool_link->addr = pool_adr;
  56.     pool_link->used = FALSE;
  57.     pool_link->last = NULL;
  58.     pool_link->next = NULL;
  59.     pool_link->size = MEMORY_POOL_SIZE;
  60.     if(MEMORY_POOL_COUNTER_ENABLE)
  61.     {
  62.         peak_memory_use = 0;    
  63.         now_memory_use = 0;
  64.     }
  65.     return J_SUCCESS;
  66. }
  67. static MemNode* memory_pool_first_fitting(UINT32 size)
  68. {
  69.     MemNode* this_node = NULL;
  70.     MemNode* temp_node = pool_link; 
  71.     while(TRUE)
  72.     {
  73.         if(temp_node == NULL) break;
  74.         if( (temp_node->size >= size) && (temp_node->used == FALSE) )
  75.         {
  76.             this_node = temp_node;
  77.             break;
  78.         }
  79.         temp_node = temp_node->next;
  80.     }   
  81.     return this_node;
  82. }
  83. void* memory_pool_malloc(UINT32 size)
  84. {
  85.     // 目前采用首次拟合
  86.     MemNode* this_node = NULL;
  87.     UINT32 nee_size = size;
  88.     if(!MEMORY_POOL_ENABLE) return J_OSP_AllocateMemory(size);
  89.     if(size == 0)
  90.     {
  91.         oc_println("abnormal memeory malloc size is 0");
  92.         return NULL;
  93.     }
  94.     if( (nee_size % 4) != 0 )
  95.         nee_size += (4-(nee_size%4));
  96.     
  97.     this_node = memory_pool_first_fitting(nee_size);
  98.     if(this_node == NULL)
  99.     {
  100.         oc_println("malloc memeory faild,size is %d",size);
  101.         return NULL;
  102.     }
  103.     size = nee_size;
  104.     if(this_node->size == size)
  105.     {
  106.         this_node->used = TRUE;
  107.         if(MEMORY_POOL_COUNTER_ENABLE)
  108.         {
  109.             now_memory_use += size;
  110.             if(now_memory_use >= peak_memory_use) peak_memory_use = now_memory_use;
  111.         }
  112.         return (void*)this_node->addr;
  113.     }
  114.     // 操作链表关系
  115.     {       
  116.         MemNode* last_node = this_node->last;
  117.         MemNode* new_node = (MemNode *)J_OSP_AllocateMemory(sizeof(MemNode));
  118.         if( this_node == pool_link ) 
  119.             pool_link = new_node;
  120.         else
  121.             last_node->next = new_node;
  122.         // 处理 new node
  123.         new_node->addr = this_node->addr;
  124.         new_node->used = TRUE;
  125.         new_node->last = last_node;
  126.         new_node->next = this_node;
  127.         new_node->size = size;
  128.         // 处理 this node
  129.         this_node->addr += size;
  130.         this_node->last = new_node; 
  131.         this_node->size -= size;
  132.         if(MEMORY_POOL_COUNTER_ENABLE)
  133.         {
  134.             now_memory_use += size;
  135.             if(now_memory_use >= peak_memory_use) peak_memory_use = now_memory_use;
  136.         }
  137.         return (void*)new_node->addr;
  138.     }
  139. }
  140. void memory_pool_free(void* pAddr)
  141. {
  142.     // 找到 pAddr 所在的 memnode
  143.     MemNode* this_node = NULL;
  144.     MemNode* temp_node = pool_link;
  145.     if(!MEMORY_POOL_ENABLE)
  146.     {
  147.         J_OSP_FreeMemory(pAddr);
  148.         return;
  149.     }
  150.     while(TRUE)
  151.     {
  152.         if( temp_node == NULL ) break;
  153.         if( temp_node->addr == pAddr)
  154.         {
  155.             this_node = temp_node;
  156.             break;
  157.         }
  158.         temp_node = temp_node->next ;
  159.     }
  160.     if(this_node == NULL)
  161.     {
  162.         oc_println("abnormal memory free!!");
  163.         return;
  164.     }
  165.     this_node->used = FALSE;
  166.     if(MEMORY_POOL_COUNTER_ENABLE) now_memory_use -= this_node->size;                                   
  167.     // 处理链表关系
  168.     {
  169.         MemNode* last_node = this_node->last;       
  170.         MemNode* next_node = this_node->next;
  171.         
  172.         // 第一次合并,和前一个块(last_node)进行合并
  173.         if(last_node != NULL)
  174.         {
  175.             // 与 last_node 合并
  176.             if( last_node->used == FALSE)
  177.             {               
  178.                 last_node->size += this_node->size;
  179.                 last_node->next = next_node;
  180.                 if(next_node != NULL)
  181.                     next_node->last = last_node;
  182.                 // 释放 this_node
  183.                 J_OSP_FreeMemory(this_node);
  184.                 this_node = NULL;
  185.             }           
  186.         }       
  187.         // 第二次合并,需要判断前面合并过没
  188.         if(this_node == NULL)// 已经和前面合并过了
  189.         {
  190.             // 判断是否需要和下一个块合并
  191.             if(next_node != NULL)
  192.             {
  193.                 if(next_node->used == FALSE) // next node 是空闲的
  194.                 {
  195.                     // 处理 last node                 
  196.                     last_node->next = next_node->next;
  197.                     last_node->size += next_node->size;
  198.                     // 处理 next_node;
  199.                     if(next_node->next != NULL)                 
  200.                         next_node->next->last = last_node;                  
  201.                     // 清除next_node
  202.                     J_OSP_FreeMemory(next_node);
  203.                     next_node = NULL;
  204.                 }
  205.             }
  206.         }
  207.         else // 没合并过
  208.         {
  209.             // 判断是否需要和下一个块合并
  210.             if(next_node != NULL)
  211.             {
  212.                 if(next_node->used == FALSE) // next node 是空闲的
  213.                 {                   
  214.                     this_node->next = next_node->next;
  215.                     this_node->size += next_node->size;
  216.                     if(next_node->next != NULL)                 
  217.                         next_node->next->last = this_node;                  
  218.                     J_OSP_FreeMemory(next_node);
  219.                     next_node = NULL;                   
  220.                 }
  221.             }
  222.         }           
  223.     }
  224. }
  225. void memory_pool_release()
  226. {
  227.     if(!MEMORY_POOL_ENABLE) return;
  228.     memory_pool_clear();
  229.     // 清除第一个结点
  230.     if(pool_link != NULL)
  231.     {   
  232.         J_OSP_FreeMemory(pool_link);
  233.         pool_link = NULL;
  234.     }
  235.     if( pool_adr != NULL)
  236.     {
  237.         J_OSP_FreeMemory(pool_adr);
  238.         pool_adr = NULL;
  239.     }       
  240.     if(MEMORY_POOL_COUNTER_ENABLE)
  241.         oc_println("peak memory use %d",peak_memory_use);   
  242.     peak_memory_use = 0;    
  243.     now_memory_use = 0;
  244.     oc_println("memory pool released.");
  245. }
  246. void memory_pool_clear()
  247. {
  248.     // 释放池的管理内存,删到只剩下一个结点
  249.     UINT32 garbage_count = 0;
  250.     MemNode* temp = NULL;
  251.     if(pool_link == NULL) return;
  252.     if(pool_link->next == NULL) return;
  253.     while(TRUE)
  254.     {       
  255.         temp = pool_link;
  256.         pool_link = pool_link->next;        
  257.         J_OSP_FreeMemory(temp);
  258.         temp = NULL;
  259.         if(MEMORY_POOL_COUNTER_ENABLE) garbage_count++;                                 
  260.         if(pool_link->next == NULL) break;
  261.     }
  262.     pool_link->addr = pool_adr;
  263.     pool_link->used = FALSE;
  264.     pool_link->last = NULL;
  265.     pool_link->next = NULL;
  266.     pool_link->size = MEMORY_POOL_SIZE;
  267.     now_memory_use = 0;
  268.     if(MEMORY_POOL_COUNTER_ENABLE) oc_println("memory garbage count is %d",garbage_count);  
  269. }

 

抱歉!评论已关闭.