home *** CD-ROM | disk | FTP | other *** search
- Newsgroups: comp.unix.aix
- Path: sparky!uunet!zaphod.mps.ohio-state.edu!cs.utexas.edu!sun-barr!ames!agate!dog.ee.lbl.gov!hellgate.utah.edu!asylum.cs.utah.edu!bytheway
- From: bytheway%asylum.cs.utah.edu@cs.utah.edu (Sidney Bytheway)
- Subject: Re: memory leak detection
- Date: 29 Dec 92 11:27:53 MST
- Message-ID: <1992Dec29.112753.3407@hellgate.utah.edu>
- Organization: University of Utah CS Dept
- References: <2423@sdrc.COM>
- Lines: 320
-
- In article <2423@sdrc.COM> crgreg@rios1.sdrc.com (Greg Marion) writes:
- >I would like to know if anyone has heard of any software that would assist
- >developers in detecting when an application allocates memory and does
- >not free it. We would have to know which routine/function and maybe
- >a range of line numbers that are suspect.
- >
- >Thanks
-
-
- I wrote a malloc wrapper that increased the size of the malloc so I could
- 1) chain all of my malloced memory together, 2) tack on an informative string
- 3) attach a structure printing function, 4) check for storage violations.
- The malloc wrapper returns a pointer to the "data" portion of the malloced
- storage to the caller just like malloc.
-
- At certain places I call a checking routing that will run through all of the
- malloced memory and check for storage violations and, if requested, print the
- invormative string and the memory using the printing function.
-
- It has proved very useful. I have included it below.
-
- Sid Bytheway
-
- ---------------------------------------------------------------------------
- Sid Bytheway, (801) 581-3989 ! Internet: udpsid@snow.usi.utah.edu
- Senior Systems Programmer ! Bitnet: UDPSID at UTAHUSI
- Utah Supercomputing Institute ! US Mail: 150 Park Bldg, SLC, UT 84112
- ---------------------------------------------------------------------------
-
-
- /***********************************************************************
- *
- * File: sid_mem.h
- * Desc: Include file for the memory allocation and debugging
- * routines. Part of the Support for Improved Development
- * (SID) library included in the TrISH Migration System.
- *
- * Copyright: Sid Bytheway
- * University of Utah
- * March 1992
- *
- * This code is supplied "AS IS" with no warranty expressed or implied.
- * Permission to copy, modify, distribute, fold, spindle and mutilate
- * this source code in any way shape or form is hereby granted to everyone.
- * Please include the proper credit.
- *
- ***********************************************************************/
-
- #ifndef SID_MEM_H
- #define SID_MEM_H
-
-
- /*
- * Function Prototypes
- * -------------------
- */
- char *sid_malloc(long size, char *desc, int (*prtfunc)() );
- int sid_free(char *ptr);
- int sid_memscan(int print_flag);
-
-
- /*
- * If we are not in DEBUG mode, over-ride all my memory allocation stuff
- * ---------------------------------------------------------------------
- */
- #ifndef _DEBUG_
-
- #define sid_malloc(size, desc, prtfunc) malloc(size)
- #define sid_free(ptr) free(ptr)
- #define sid_memscan(print_flag) FALSE
-
- #endif /* _DEBUG_ */
-
-
- /*
- * Macro Definitions
- * -----------------
- *
- * Allocates memory for a new object of type objtype.
- *
- * Usage: ptr = newobj( structure_name );
- * delobj( ptr );
- */
-
- #define newobj(objtype) \
- (objtype *) sid_malloc( sizeof(objtype), "objtype Object", NULL )
-
- #define delobj( obj ) \
- sid_free( (char *) obj )
-
-
-
- #endif /* SID_MEM_H */
-
-
- /***********************************************************************
- *
- * File: sid_mem.c
- * Desc: Contains memory allocation and debugging routines.
- * Part of the Support for Improved Development (SID)
- * library included in the TrISH Migration System.
- *
- * Copyright: Sid Bytheway
- * University of Utah
- * March 1992
- *
- * This code is supplied "AS IS" with no warranty expressed or implied.
- * Permission to copy, modify, distribute, fold, spindle and mutilate
- * this source code in any way shape or form is hereby granted to everyone.
- * Please include the proper credit.
- *
- * ----------------------------------------------------------------------
- *
- * Memory allocation debugging consists of allocating a little extra memory
- * for pattern checking fields, description string, pointers for printing
- * allocated memory, and the size of the user portion of the memory.
- *
- ***********************************************************************/
-
- #ifndef _DEBUG_
- # define _DEBUG_ /* required for this file */
- #endif /* _DEBUG_ */
-
- #include <stdio.h>
- #include <signal.h>
- #include <sys/types.h>
-
- #include "sid.h"
- #include "sid_mem.h"
-
-
- /*
- * The memory check pattern - Define to anything you like.
- * -------------------------------------------------------
- */
- #define SID_CHECK_PATTERN 0xffabacab /* storage violation pattern */
-
-
- /*
- * This is the structure that glues all memory allocations together.
- * -----------------------------------------------------------------
- */
- typedef struct _sid_memstruct {
- struct _sid_memstruct *next; /* ptr to next memory allocation */
- struct _sid_memstruct *prev; /* ptr to previous allocation */
- char *desc; /* char string description */
- long usr_size; /* size of user data */
- int (* prt_callback)(); /* callback func to print memory */
- long check1; /* first check field */
- /* user data is here */
- long check2; /* second check field */
- } sid_memstruct;
-
-
- /*
- * Global variables used by this file and these routines.
- * ------------------------------------------------------
- */
- sid_memstruct *sid_mem_first; /* first memory allocation */
- sid_memstruct *sid_mem_last; /* last memory allocation */
-
-
-
- /*************************************************************
- *
- * sid_malloc()
- *
- * My memory allocation routine that allocates memory and links
- * it together with a description, printing function and fields
- * to check for storage violations.
- *
- *************************************************************/
- char *sid_malloc(
- long size, /* size of user data */
- char *desc, /* char string description */
- int (* prtfunc)() /* callback func to print memory */
- )
- {
-
- char *newch;
- sid_memstruct *new;
- long *check2;
-
- /* first scan memory to see if anything is hosed */
- sid_memscan( FALSE );
-
- /* allocate requested memory plus enough for tracing structure */
- if( (newch = (char *) malloc( size + sizeof(sid_memstruct))) == NULL ){
- fprintf(stderr, "sid_malloc(): Memory allocation error - %s\n", desc);
- exit( 1 );
- }
- new = (sid_memstruct *) newch;
-
- /* put data into my malloc structure */
- new->usr_size = size;
- new->desc = desc;
- new->prt_callback = prtfunc;
- new->check1 = SID_CHECK_PATTERN;
- check2 = (long *) (newch + size + sizeof(sid_memstruct) - sizeof(long));
- *check2 = SID_CHECK_PATTERN;
-
- /* link this dude in with everyone else */
- new->next = NULL;
- if( sid_mem_last != NULL )
- sid_mem_last->next = new;
- new->prev = sid_mem_last;
- sid_mem_last = new;
- if( sid_mem_first == NULL )
- sid_mem_first = new;
-
- /* return to the user a pointer to his data area */
- return( newch + sizeof(sid_memstruct) - sizeof(long) );
-
- }
-
-
- /*************************************************************
- *
- * sid_free()
- *
- * My memory de-allocation routine. Looks at storage violation
- * fields for violations, prints a message if it finds one.
- * Frees user and structure memory.
- *
- *************************************************************/
- int sid_free(
- char *usr_data /* ptr to user data*/
- )
- {
- sid_memstruct *ptr;
- long *check2;
-
- /* Point to real head of allocated memory */
- ptr = (sid_memstruct *) (usr_data - sizeof(sid_memstruct) + sizeof(long));
- check2 = (long *) (usr_data + ptr->usr_size);
-
- /* unlink this dude from everyone else */
- if( ptr->prev == NULL )
- sid_mem_first = ptr->next;
- else
- ptr->prev->next = ptr->next;
-
- if( ptr->next == NULL )
- sid_mem_last = ptr->prev;
- else
- ptr->next->prev = ptr->prev;
-
-
- /* Check storage violation fields */
- if(ptr->check1 != SID_CHECK_PATTERN || *check2 != SID_CHECK_PATTERN) {
- fprintf(stderr, "sid_free: A storage violation has occured!!!\n" );
- fprintf(stderr, "desc = \"%s\"\n", ptr->desc );
- fprintf(stderr, "size = %d, check1 = %8.8x, check2 = %8.8x\n",
- ptr->usr_size, ptr->check1, *check2 );
- if( ptr->prt_callback != NULL ) {
- fprintf( stderr, "sid_free: User Data Follows...\n\n" );
- (* ptr->prt_callback)( usr_data );
- }
- fputc( '\n', stderr );
- fprintf( stderr, "Forcing core dump and exit\n" );
- kill( 0, SIGTRAP );
- exit( 1 );
- }
-
- return( free( (char *) ptr) );
- }
-
-
- /*************************************************************
- *
- * sid_memscan()
- *
- * Scans all linked together storage looking for storage
- * violations. If print_flag is set then runs the callback
- * routine to print the memory. Returns 0 if no storage
- * violations, 1 if any storage violations.
- *
- *************************************************************/
- int sid_memscan(
- int print_flag
- )
- {
- sid_memstruct *walker;
- char *usr_data;
- long *check2;
- int violation, any_violation=FALSE;
-
-
- for(walker = sid_mem_first; walker != NULL; walker = walker->next) {
-
- violation = FALSE;
- usr_data = ((char *) walker) + sizeof(sid_memstruct) - sizeof(long);
- check2 = (long *) (usr_data + walker->usr_size);
-
- /* Test for storage violation - print messages if so */
- if( walker->check1 != SID_CHECK_PATTERN
- || *check2 != SID_CHECK_PATTERN ) {
- fprintf(stderr, "sid_memscan: A storage violation has occured!!!\n" );
- fprintf(stderr, "desc = \"%s\"\n", walker->desc);
- fprintf(stderr, "size = %d check1 = %8.8x check2 = %8.8x\n",
- walker->usr_size, walker->check1, *check2 );
- fprintf(stderr, "next = %8.8x, prev = %8.8x\n",
- walker->next, walker->prev);
- violation = TRUE;
- any_violation = TRUE;
- }
-
- /* print the structure if violation or if print flag is set */
- if((violation || print_flag) && walker->prt_callback != NULL) {
- fprintf( stderr, "sid_memscan: User Data Follows...\n\n" );
- (* walker->prt_callback)( usr_data );
- }
- if( violation || (print_flag && walker->prt_callback != NULL))
- fputc( '\n', stderr );
- }
-
- return( any_violation );
-
- }
-
-