Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
model-checker : add stats in mmalloc
authorMarion Guthmuller <marion.guthmuller@loria.fr>
Tue, 19 Jun 2012 13:57:30 +0000 (15:57 +0200)
committerMarion Guthmuller <marion.guthmuller@loria.fr>
Tue, 19 Jun 2012 14:01:10 +0000 (16:01 +0200)
src/xbt/mmalloc/mfree.c
src/xbt/mmalloc/mmalloc.c
src/xbt/mmalloc/mmprivate.h

index 5d54412..c750d9a 100644 (file)
@@ -44,6 +44,13 @@ void mfree(struct mdesc *mdp, void *ptr)
     break;
 
   case 0:
+     /* Get as many statistics as early as we can.  */
+      mdp -> heapstats.chunks_used--;
+      mdp -> heapstats.bytes_used -=
+         mdp -> heapinfo[block].busy_block.size * BLOCKSIZE;
+      mdp -> heapstats.bytes_free +=
+         mdp -> heapinfo[block].busy_block.size * BLOCKSIZE;
+
     /* Find the free cluster previous to this one in the free list.
        Start searching at the last block referenced; this may benefit
        programs with locality of allocation.  */
@@ -84,6 +91,7 @@ void mfree(struct mdesc *mdp, void *ptr)
       mdp->heapinfo[block].free_block.prev = i;
       mdp->heapinfo[i].free_block.next = block;
       mdp->heapinfo[mdp->heapinfo[block].free_block.next].free_block.prev = block;
+      mdp -> heapstats.chunks_free++;
       /* Mark all my ex-blocks as free */
       for (it=0; it<mdp->heapinfo[block].free_block.size; it++) {
          if (mdp->heapinfo[block+it].type <0) {
@@ -105,6 +113,7 @@ void mfree(struct mdesc *mdp, void *ptr)
       mdp->heapinfo[block].free_block.next
           = mdp->heapinfo[mdp->heapinfo[block].free_block.next].free_block.next;
       mdp->heapinfo[mdp->heapinfo[block].free_block.next].free_block.prev = block;
+      mdp -> heapstats.chunks_free--;
     }
 
     /* Now see if we can return stuff to the system.  */
@@ -129,6 +138,13 @@ void mfree(struct mdesc *mdp, void *ptr)
     break;
 
   default:
+    /* Do some of the statistics.  */
+      mdp -> heapstats.chunks_used--;
+      mdp -> heapstats.bytes_used -= 1 << type;
+      mdp -> heapstats.chunks_free++;
+      mdp -> heapstats.bytes_free += 1 << type;
+
+    
     /* Get the address of the first free fragment in this block.  */
     prev = (struct list *)
         ((char *) ADDRESS(block) +
@@ -150,7 +166,13 @@ void mfree(struct mdesc *mdp, void *ptr)
       mdp->heapinfo[block].type = 0;
       mdp->heapinfo[block].busy_block.size = 1;
       mdp->heapinfo[block].busy_block.busy_size = 0;
-
+      
+      /* Keep the statistics accurate.  */
+      mdp -> heapstats.chunks_used++;
+      mdp -> heapstats.bytes_used += BLOCKSIZE;
+      mdp -> heapstats.chunks_free -= BLOCKSIZE >> type;
+      mdp -> heapstats.bytes_free -= BLOCKSIZE;
+      
       mfree((void *) mdp, (void *) ADDRESS(block));
     } else if (mdp->heapinfo[block].busy_frag.nfree != 0) {
       /* If some fragments of this block are free, link this
index bbdc937..37f8c6b 100644 (file)
@@ -164,6 +164,12 @@ void *mmalloc(xbt_mheap_t mdp, size_t size)
          RESIDUAL(next->next, BLOCKSIZE) >> log;
       }
 
+      /* Update the statistics.  */
+      mdp -> heapstats.chunks_used++;
+      mdp -> heapstats.bytes_used += 1 << log;
+      mdp -> heapstats.chunks_free--;
+      mdp -> heapstats.bytes_free -= 1 << log;
+      
     } else {
       /* No free fragments of the desired size, so get a new block
          and break it into fragments, returning the first.  */
@@ -190,6 +196,10 @@ void *mmalloc(xbt_mheap_t mdp, size_t size)
       mdp->heapinfo[block].type = log;
       mdp->heapinfo[block].busy_frag.nfree = i - 1;
       mdp->heapinfo[block].busy_frag.first = i - 1;
+
+      mdp -> heapstats.chunks_free += (BLOCKSIZE >> log) - 1;
+      mdp -> heapstats.bytes_free += BLOCKSIZE - (1 << log);
+      mdp -> heapstats.bytes_used -= BLOCKSIZE - (1 << log);
     }
   } else {
     /* Large allocation to receive one or more blocks.
@@ -231,7 +241,8 @@ void *mmalloc(xbt_mheap_t mdp, size_t size)
         mdp->heapinfo[block].busy_block.size = blocks;
         mdp->heapinfo[block].busy_block.busy_size = requested_size;
         mdp->heapinfo[block].busy_block.bt_size=xbt_backtrace_no_malloc(mdp->heapinfo[block].busy_block.bt,XBT_BACKTRACE_SIZE);
-
+       mdp -> heapstats.chunks_used++;
+       mdp -> heapstats.bytes_used += blocks * BLOCKSIZE;
         return result;
       }
       /* Need large block(s), but found some in the existing heap */
@@ -267,6 +278,10 @@ void *mmalloc(xbt_mheap_t mdp, size_t size)
     mdp->heapinfo[block].busy_block.busy_size = requested_size;
     //mdp->heapinfo[block].busy_block.bt_size = 0;
     mdp->heapinfo[block].busy_block.bt_size = xbt_backtrace_no_malloc(mdp->heapinfo[block].busy_block.bt,XBT_BACKTRACE_SIZE);
+
+    mdp -> heapstats.chunks_used++;
+    mdp -> heapstats.bytes_used += blocks * BLOCKSIZE;
+    mdp -> heapstats.bytes_free -= blocks * BLOCKSIZE;
   }
   //printf("(%s) Done mallocing. Result is %p\n",xbt_thread_self_name(),result);fflush(stdout);
   return (result);
index 4273e0d..d0eb81c 100644 (file)
@@ -96,6 +96,16 @@ struct list {
   struct list *prev;
 };
 
+/* Statistics available to the user. */
+struct mstats
+{
+  size_t bytes_total;          /* Total size of the heap. */
+  size_t chunks_used;          /* Chunks allocated by the user. */
+  size_t bytes_used;           /* Byte total of user-allocated chunks. */
+  size_t chunks_free;          /* Chunks in the free list. */
+  size_t bytes_free;           /* Byte total of chunks in the free list. */
+};
+
 /* Data structure giving per-block information.
  *
  * There is one such structure in the mdp->heapinfo array per block used in that heap,
@@ -222,6 +232,10 @@ struct mdesc {
 
   int fd;
 
+  /* Instrumentation.  */
+
+  struct mstats heapstats;
+
 };
 
 int mmalloc_compare_mdesc(struct mdesc *mdp1, struct mdesc *mdp2);