Monday 13 May 2013

Simple Memory pool Implementation for Real Time Applications

Dear readers,

   In this post, I would like to introduce about the Simple Memory Pool Implementation which can be used for real time applications.

Before looking in to actual Implementation, first know about what is memory pool and why is required in real time applications.

In real time applications, performance plays a very important role. That means any real time system should have high performance to get desirable results else it is considered as useless system.

Hence, when ever a developer writing any code, he/she should keep in mind that how much code optimization and performance that is going to achieve with the implementation.

In the code often developers allocate the memory using dynamic allocation macros such as MALLOC in 
case of C and NEW in case of C++. 

Suppose, you have packet receptor system which receives the packets from other device. And this receptor system responsibility to add a extra header to the received packet and sends the modified packet out to the end device. 

What happens when code allocates/dellocates memory using malloc/free for every packet. 

Do you think there is a performance degradation? Yes, obviously there is performance degradation. 

Then what is the solution? Solution is Memory pools.
   A more efficient solution is preallocating a number of memory blocks with the same size called the memory pool. The application can allocate, access, and free blocks represented by handles at run time.

What is Memory Pool?
   Memory pool is pre-allocation of fixed size of memory or it also defined as fixed size of memory allocated using MALLOC or New during initialization of the system.

Why it is required?
   To avoid the performance degradation in real time systems.

How it is implemented?

Step 1 :  Create a memory Pool. 
Application needs to initialize a pool. Application allocates the memory required during initialization time using MALLOC/NEW.
Step 2:    Get memory from Pool
Whenever a memory is required and the same memory would be fetched from the Pool.              
Step3:   Add memory to Pool
Once the Memory is no more used then add the same memory to Pool.
Step4:  Destroy/Deallocate memory Pool
And finally, before application quits, it should de-allocate the pool, to make sure that all memory blocks allocated by the factory are released back to the operating system. After this, of course no more memory pool allocation can be requested.

Simple Program for Memory Pool:



#include<stdio.h>
#include<stdlib.h>
#include<string.h>

#define MAX_MEMORY_POOL_NODES 10

/* Node */
typedef struct node
{
    int    data;
    int    nodeAllocated;
}NODE;

typedef struct Memorypool
{
    NODE       *array[MAX_MEMORY_POOL_NODES];
    int        nodeCounter;
}MEMORYPOOL;

MEMORYPOOL allocNode;

/*
 * initialiseMemoryPool()
 */
void initialiseMemoryPool()
{
   unsigned char uIndx;
   
   /* Initialise the Memory for the Nodes */      
   for(uIndx = 0; uIndx<MAX_MEMORY_POOL_NODES; uIndx++)
   {
      allocNode.array[uIndx]= (NODE *)malloc(sizeof(NODE));
      allocNode.array[uIndx]->nodeAllocated = 0;

      allocNode.nodeCounter++;
   }
}

NODE *getTheFreeNodeFromPool()
{
  int uIndx;
  
   /* Get the Memory from the Pool of Nodes */
   for(uIndx = 0; uIndx<MAX_MEMORY_POOL_NODES; uIndx++)
   {
      if(allocNode.array[uIndx]->nodeAllocated == 0) 
      {
          allocNode.array[uIndx]->nodeAllocated = 1;
          allocNode.nodeCounter--; 
          break;
      }
   }  

  if(uIndx == MAX_MEMORY_POOL_NODES) 
  {
     printf(" No Free Nodes are available \n");
     return NULL;
  }
  return allocNode.array[uIndx];
}

/* 
 *  Add the Node to Memory pool
 */
void addTheNodeToMemoryPool(unsigned char uIndx)
{
   /* Add the Node to Pool */
   if(allocNode.array[uIndx]->nodeAllocated == 1 )
   {
         allocNode.array[uIndx]->data = 0;
         allocNode.array[uIndx]->nodeAllocated = 0; 
         allocNode.nodeCounter++;
    }
   else
   {
      printf("No Nodes are there Add \n");
      return;
   }
}

/*
 * deallocateTheMemoryPool-  Deallocate the Memory Pool
 */
void deallocateTheMemoryPool(void)
{
  unsigned char uIndx;

  /* De-allocate the Memory Pool */
  for(uIndx = 0; uIndx<MAX_MEMORY_POOL_NODES; uIndx++)
    {
        free(allocNode.array[uIndx]);
    }
}
              
/* Main */
int main()
{
    unsigned char uIndx, index;
   
   // Step 1:
   /* Initialise the Memory Pool */
   initialiseMemoryPool();

   // Step 2:
   /* Get the Node from the Memory Pool */
   for(uIndx=0 ; uIndx< MAX_MEMORY_POOL_NODES; uIndx++)
   { 
      NODE *node= NULL; 
      int data;
      
      node = getTheFreeNodeFromPool();

      if(node)
      {
          printf("Enter the Data to be added in the Linklist \n");
          scanf("%d", &data);
    
          node->data = data;
      }
   }
  
   /* Display the Data */
   printf(" Display Data \n");
   for (uIndx=0 ; uIndx<MAX_MEMORY_POOL_NODES; uIndx++)
    {
      printf("%d\n", allocNode.array[uIndx]->data);
    }

   
   //Step 3:
   /* Add the Node to Memory Pool */   
   printf(" Enter the Node to be added to memory pool \n");
   scanf("%d", &index);
   
   addTheNodeToMemoryPool(index);

   /* Display the Data */
   printf(" Display Data after adding Node to Free Pool \n");
   for (uIndx=0 ; uIndx<MAX_MEMORY_POOL_NODES; uIndx++)
    {
      printf("%d\n", allocNode.array[uIndx]->data);
    }

   //Step 4:
   /* De Allocate the Memory Pool */
   deallocateTheMemoryPool();
   return 0;
}








6 comments:

  1. thank u very much. after long search i found this good article about memory pool :). also expecting more articles from you

    ReplyDelete
  2. Thanks for your feedback. Pls keep visit this blog for more interesting updates.

    ReplyDelete
  3. I think if addTheNodeToMemoryPool takes NODE* as the input parameter than it makes more sense and more generic.
    But otherwise good article simple and clear!!!.

    ReplyDelete