BOSS 6.6.4.p01
BESIII Offline Software System
Loading...
Searching...
No Matches
KalFitMemLeak.h File Reference
#include <stdlib.h>

Go to the source code of this file.

Macros

#define MW_ARI_NULLREAD   0x10 /* Null read (to start debugger) */
 
#define MW_ARI_ABORT   0x04 /* ARI handler says: abort program! */
 
#define MW_ARI_RETRY   0x02 /* ARI handler says: retry action! */
 
#define MW_ARI_IGNORE   0x01 /* ARI handler says: ignore error! */
 
#define MW_VAL_NEW   0xFE /* value in newly allocated memory */
 
#define MW_VAL_DEL   0xFD /* value in newly deleted memory */
 
#define MW_VAL_NML   0xFC /* value in no-mans-land */
 
#define MW_VAL_GRB   0xFB /* value in grabbed memory */
 
#define MW_TEST_ALL   0xFFFF /* perform all tests */
 
#define MW_TEST_CHAIN   0x0001 /* walk the heap chain */
 
#define MW_TEST_ALLOC   0x0002 /* test allocations & NML guards */
 
#define MW_TEST_NML   0x0004 /* test all-NML areas for modifications */
 
#define MW_NML_NONE   0 /* no NML */
 
#define MW_NML_FREE   1 /* turn FREE'd memory into NML */
 
#define MW_NML_ALL   2 /* all unused memory is NML */
 
#define MW_NML_DEFAULT   0 /* the default NML setting */
 
#define MW_STAT_GLOBAL   0 /* only global statistics collected */
 
#define MW_STAT_MODULE   1 /* collect statistics on a module basis */
 
#define MW_STAT_LINE   2 /* collect statistics on a line basis */
 
#define MW_STAT_DEFAULT   0 /* the default statistics setting */
 
#define MW_TRACE_BUFFER   2048 /* (min 160) size of TRACE()'s output buffer */
 
#define MW_FREE_LIST   64 /* (min 4) number of free()'s to track */
 
#define mwASSERT(exp)
 
#define ASSERT   mwASSERT
 
#define mwVERIFY(exp)   exp
 
#define VERIFY   mwVERIFY
 
#define mwTRACE   /*lint -save -e506 */ 1?(void)0:mwDummyTraceFunction /*lint -restore */
 
#define TRACE   mwTRACE
 
#define mwDoFlush(n)
 
#define mwPuts(s)
 
#define mwInit()
 
#define mwGrab(n)
 
#define mwDrop(n)
 
#define mwLimit(n)
 
#define mwTest(f, l)
 
#define mwSetOutFunc(f)
 
#define mwSetAriFunc(f)
 
#define mwDefaultAri()
 
#define mwNomansland()
 
#define mwStatistics(f)
 
#define mwMark(p, t, f, n)   (p)
 
#define mwUnmark(p, f, n)   (p)
 
#define mwMalloc(n, f, l)   malloc(n)
 
#define mwStrdup(p, f, l)   strdup(p)
 
#define mwRealloc(p, n, f, l)   realloc(p,n)
 
#define mwCalloc(n, m, f, l)   calloc(n,m)
 
#define mwFree(p)   free(p)
 
#define mwMalloc_(n)   malloc(n)
 
#define mwRealloc_(p, n)   realloc(p,n)
 
#define mwCalloc_(n, m)   calloc(n,m)
 
#define mwFree_(p)   free(p)
 
#define mwAssert(e, es, f, l)
 
#define mwVerify(e, es, f, l)   (e)
 
#define mwTrace   mwDummyTrace
 
#define mwTestBuffer(f, l, b)   (0)
 
#define CHECK()
 
#define CHECK_THIS(n)
 
#define CHECK_BUFFER(b)
 
#define MARK(p)   (p)
 
#define UNMARK(p)   (p)
 

Functions

void mwTerm (void)
 
void mwAbort (void)
 
void mwFlushNow (void)
 
void mwDoFlush (int onoff)
 
void mwLimit (long bytes)
 
unsigned mwGrab (unsigned kilobytes)
 
unsigned mwDrop (unsigned kilobytes)
 
void mwNoMansLand (int mw_nml_level)
 
void mwStatistics (int level)
 
void mwFreeBufferInfo (int onoff)
 
void mwAutoCheck (int onoff)
 
void mwCalcCheck (void)
 
void mwDumpCheck (void)
 
void * mwMark (void *p, const char *description, const char *file, unsigned line)
 
void * mwUnmark (void *p, const char *file, unsigned line)
 
int mwIsReadAddr (const void *p, unsigned len)
 
int mwIsSafeAddr (void *p, unsigned len)
 
int mwTest (const char *file, int line, int mw_test_flags)
 
int mwTestBuffer (const char *file, int line, void *p)
 
int mwAssert (int, const char *, const char *, int)
 
int mwVerify (int, const char *, const char *, int)
 
void mwTrace (const char *format_string,...)
 
void mwPuts (const char *text)
 
void mwSetOutFunc (void(*func)(int))
 
void mwSetAriFunc (int(*func)(const char *))
 
void mwSetAriAction (int mw_ari_value)
 
int mwAriHandler (const char *cause)
 
void mwBreakOut (const char *cause)
 
void * mwMalloc (size_t, const char *, int)
 
void * mwMalloc_ (size_t)
 
void * mwRealloc (void *, size_t, const char *, int)
 
void * mwRealloc_ (void *, size_t)
 
void * mwCalloc (size_t, size_t, const char *, int)
 
void * mwCalloc_ (size_t, size_t)
 
void mwFree (void *, const char *, int)
 
void mwFree_ (void *)
 
char * mwStrdup (const char *, const char *, int)
 
void mwDummyTraceFunction (const char *,...)
 

Variables

const unsigned long mwCounter
 

Macro Definition Documentation

◆ ASSERT

#define ASSERT   mwASSERT

Definition at line 594 of file KalFitMemLeak.h.

◆ CHECK

#define CHECK ( )

Definition at line 643 of file KalFitMemLeak.h.

◆ CHECK_BUFFER

#define CHECK_BUFFER (   b)

Definition at line 645 of file KalFitMemLeak.h.

◆ CHECK_THIS

#define CHECK_THIS (   n)

Definition at line 644 of file KalFitMemLeak.h.

◆ MARK

#define MARK (   p)    (p)

Definition at line 646 of file KalFitMemLeak.h.

◆ MW_ARI_ABORT

#define MW_ARI_ABORT   0x04 /* ARI handler says: abort program! */

Definition at line 349 of file KalFitMemLeak.h.

◆ MW_ARI_IGNORE

#define MW_ARI_IGNORE   0x01 /* ARI handler says: ignore error! */

Definition at line 351 of file KalFitMemLeak.h.

◆ MW_ARI_NULLREAD

#define MW_ARI_NULLREAD   0x10 /* Null read (to start debugger) */

Definition at line 348 of file KalFitMemLeak.h.

◆ MW_ARI_RETRY

#define MW_ARI_RETRY   0x02 /* ARI handler says: retry action! */

Definition at line 350 of file KalFitMemLeak.h.

◆ MW_FREE_LIST

#define MW_FREE_LIST   64 /* (min 4) number of free()'s to track */

Definition at line 379 of file KalFitMemLeak.h.

◆ MW_NML_ALL

#define MW_NML_ALL   2 /* all unused memory is NML */

Definition at line 365 of file KalFitMemLeak.h.

◆ MW_NML_DEFAULT

#define MW_NML_DEFAULT   0 /* the default NML setting */

Definition at line 366 of file KalFitMemLeak.h.

◆ MW_NML_FREE

#define MW_NML_FREE   1 /* turn FREE'd memory into NML */

Definition at line 364 of file KalFitMemLeak.h.

◆ MW_NML_NONE

#define MW_NML_NONE   0 /* no NML */

Definition at line 363 of file KalFitMemLeak.h.

◆ MW_STAT_DEFAULT

#define MW_STAT_DEFAULT   0 /* the default statistics setting */

Definition at line 371 of file KalFitMemLeak.h.

◆ MW_STAT_GLOBAL

#define MW_STAT_GLOBAL   0 /* only global statistics collected */

Definition at line 368 of file KalFitMemLeak.h.

◆ MW_STAT_LINE

#define MW_STAT_LINE   2 /* collect statistics on a line basis */

Definition at line 370 of file KalFitMemLeak.h.

◆ MW_STAT_MODULE

#define MW_STAT_MODULE   1 /* collect statistics on a module basis */

Definition at line 369 of file KalFitMemLeak.h.

◆ MW_TEST_ALL

#define MW_TEST_ALL   0xFFFF /* perform all tests */

Definition at line 358 of file KalFitMemLeak.h.

◆ MW_TEST_ALLOC

#define MW_TEST_ALLOC   0x0002 /* test allocations & NML guards */

Definition at line 360 of file KalFitMemLeak.h.

◆ MW_TEST_CHAIN

#define MW_TEST_CHAIN   0x0001 /* walk the heap chain */

Definition at line 359 of file KalFitMemLeak.h.

◆ MW_TEST_NML

#define MW_TEST_NML   0x0004 /* test all-NML areas for modifications */

Definition at line 361 of file KalFitMemLeak.h.

◆ MW_TRACE_BUFFER

#define MW_TRACE_BUFFER   2048 /* (min 160) size of TRACE()'s output buffer */

Definition at line 378 of file KalFitMemLeak.h.

◆ MW_VAL_DEL

#define MW_VAL_DEL   0xFD /* value in newly deleted memory */

Definition at line 354 of file KalFitMemLeak.h.

◆ MW_VAL_GRB

#define MW_VAL_GRB   0xFB /* value in grabbed memory */

Definition at line 356 of file KalFitMemLeak.h.

◆ MW_VAL_NEW

#define MW_VAL_NEW   0xFE /* value in newly allocated memory */

Definition at line 353 of file KalFitMemLeak.h.

◆ MW_VAL_NML

#define MW_VAL_NML   0xFC /* value in no-mans-land */

Definition at line 355 of file KalFitMemLeak.h.

◆ mwAssert

#define mwAssert (   e,
  es,
  f,
 
)

Definition at line 639 of file KalFitMemLeak.h.

◆ mwASSERT

#define mwASSERT (   exp)

Definition at line 591 of file KalFitMemLeak.h.

◆ mwCalloc

#define mwCalloc (   n,
  m,
  f,
 
)    calloc(n,m)

Definition at line 633 of file KalFitMemLeak.h.

◆ mwCalloc_

#define mwCalloc_ (   n,
 
)    calloc(n,m)

Definition at line 637 of file KalFitMemLeak.h.

◆ mwDefaultAri

#define mwDefaultAri ( )

Definition at line 625 of file KalFitMemLeak.h.

◆ mwDoFlush

#define mwDoFlush (   n)

Definition at line 616 of file KalFitMemLeak.h.

◆ mwDrop

#define mwDrop (   n)

Definition at line 620 of file KalFitMemLeak.h.

◆ mwFree

#define mwFree (   p)    free(p)

Definition at line 634 of file KalFitMemLeak.h.

◆ mwFree_

#define mwFree_ (   p)    free(p)

Definition at line 638 of file KalFitMemLeak.h.

◆ mwGrab

#define mwGrab (   n)

Definition at line 619 of file KalFitMemLeak.h.

◆ mwInit

void mwInit ( )

Definition at line 618 of file KalFitMemLeak.h.

◆ mwLimit

#define mwLimit (   n)

Definition at line 621 of file KalFitMemLeak.h.

◆ mwMalloc

#define mwMalloc (   n,
  f,
 
)    malloc(n)

Definition at line 630 of file KalFitMemLeak.h.

◆ mwMalloc_

#define mwMalloc_ (   n)    malloc(n)

Definition at line 635 of file KalFitMemLeak.h.

◆ mwMark

#define mwMark (   p,
  t,
  f,
  n 
)    (p)

Definition at line 628 of file KalFitMemLeak.h.

◆ mwNomansland

#define mwNomansland ( )

Definition at line 626 of file KalFitMemLeak.h.

◆ mwPuts

#define mwPuts (   s)

Definition at line 617 of file KalFitMemLeak.h.

◆ mwRealloc

#define mwRealloc (   p,
  n,
  f,
 
)    realloc(p,n)

Definition at line 632 of file KalFitMemLeak.h.

◆ mwRealloc_

#define mwRealloc_ (   p,
  n 
)    realloc(p,n)

Definition at line 636 of file KalFitMemLeak.h.

◆ mwSetAriFunc

#define mwSetAriFunc (   f)

Definition at line 624 of file KalFitMemLeak.h.

◆ mwSetOutFunc

#define mwSetOutFunc (   f)

Definition at line 623 of file KalFitMemLeak.h.

◆ mwStatistics

#define mwStatistics (   f)

Definition at line 627 of file KalFitMemLeak.h.

◆ mwStrdup

#define mwStrdup (   p,
  f,
 
)    strdup(p)

Definition at line 631 of file KalFitMemLeak.h.

◆ mwTest

#define mwTest (   f,
 
)

Definition at line 622 of file KalFitMemLeak.h.

◆ mwTestBuffer

#define mwTestBuffer (   f,
  l,
 
)    (0)

Definition at line 642 of file KalFitMemLeak.h.

◆ mwTRACE

#define mwTRACE   /*lint -save -e506 */ 1?(void)0:mwDummyTraceFunction /*lint -restore */

Definition at line 606 of file KalFitMemLeak.h.

◆ mwTrace

#define mwTrace   mwDummyTrace

Definition at line 641 of file KalFitMemLeak.h.

◆ mwUnmark

#define mwUnmark (   p,
  f,
  n 
)    (p)

Definition at line 629 of file KalFitMemLeak.h.

◆ mwVerify

#define mwVerify (   e,
  es,
  f,
 
)    (e)

Definition at line 640 of file KalFitMemLeak.h.

◆ mwVERIFY

#define mwVERIFY (   exp)    exp

Definition at line 598 of file KalFitMemLeak.h.

◆ TRACE

#define TRACE   mwTRACE

Definition at line 610 of file KalFitMemLeak.h.

◆ UNMARK

#define UNMARK (   p)    (p)

Definition at line 647 of file KalFitMemLeak.h.

◆ VERIFY

#define VERIFY   mwVERIFY

Definition at line 601 of file KalFitMemLeak.h.

Function Documentation

◆ mwAbort()

void mwAbort ( void  )

Definition at line 517 of file KalFitMemLeak.c.

517 {
518 mwData *mw;
519 mwMarker *mrk;
520 char *data;
521 time_t tid;
522 int c, i, j;
523 int errors;
524
525 tid = time( NULL );
526 mwWrite( "\nStopped at %s\n", ctime( &tid) );
527
528 if( !mwInited )
529 mwWrite( "internal: mwAbort(): MEMWATCH not initialized!\n" );
530
531 /* release the grab list */
532 mwDropAll();
533
534 /* report mwMarked items */
535 while( mwFirstMark ) {
536 mrk = mwFirstMark->next;
537 mwWrite( "mark: %p: %s\n", mwFirstMark->host, mwFirstMark->text );
538 free( mwFirstMark->text );
539 free( mwFirstMark );
540 mwFirstMark = mrk;
541 mwErrors ++;
542 }
543
544 /* release all still allocated memory */
545 errors = 0;
546 while( mwHead != NULL && errors < 3 ) {
547 if( !mwIsOwned(mwHead, __FILE__, __LINE__ ) ) {
548 if( errors < 3 )
549 {
550 errors ++;
551 mwWrite( "internal: NML/unfreed scan restarting\n" );
552 FLUSH();
553 mwHead = mwHead;
554 continue;
555 }
556 mwWrite( "internal: NML/unfreed scan aborted, heap too damaged\n" );
557 FLUSH();
558 break;
559 }
560 mwFlushW(0);
561 if( !(mwHead->flag & MW_NML) ) {
562 mwErrors++;
563 data = ((char*)mwHead)+mwDataSize;
564 mwWrite( "unfreed: <%ld> %s(%d), %ld bytes at %p ",
565 mwHead->count, mwHead->file, mwHead->line, (long)mwHead->size, data+mwOverflowZoneSize );
566 if( mwCheckOF( data ) ) {
567 mwWrite( "[underflowed] ");
568 FLUSH();
569 }
570 if( mwCheckOF( (data+mwOverflowZoneSize+mwHead->size) ) ) {
571 mwWrite( "[overflowed] ");
572 FLUSH();
573 }
574 mwWrite( " \t{" );
575 j = 16; if( mwHead->size < 16 ) j = (int) mwHead->size;
576 for( i=0;i<16;i++ ) {
577 if( i<j ) mwWrite( "%02X ",
578 (unsigned char) *(data+mwOverflowZoneSize+i) );
579 else mwWrite( ".. " );
580 }
581 for( i=0;i<j;i++ ) {
582 c = *(data+mwOverflowZoneSize+i);
583 if( c < 32 || c > 126 ) c = '.';
584 mwWrite( "%c", c );
585 }
586 mwWrite( "}\n" );
587 mw = mwHead;
588 mwUnlink( mw, __FILE__, __LINE__ );
589 free( mw );
590 }
591 else {
592 data = ((char*)mwHead) + mwDataSize + mwOverflowZoneSize;
593 if( mwTestMem( data, mwHead->size, MW_VAL_NML ) ) {
594 mwErrors++;
595 mwWrite( "wild pointer: <%ld> NoMansLand %p alloc'd at %s(%d)\n",
596 mwHead->count, data + mwOverflowZoneSize, mwHead->file, mwHead->line );
597 FLUSH();
598 }
599 mwNmlNumAlloc --;
600 mwNmlCurAlloc -= mwHead->size;
601 mw = mwHead;
602 mwUnlink( mw, __FILE__, __LINE__ );
603 free( mw );
604 }
605 }
606
607 if( mwNmlNumAlloc ) mwWrite("internal: NoMansLand block counter %ld, not zero\n", mwNmlNumAlloc );
608 if( mwNmlCurAlloc ) mwWrite("internal: NoMansLand byte counter %ld, not zero\n", mwNmlCurAlloc );
609
610 /* report statistics */
611 mwStatReport();
612 FLUSH();
613
614 mwInited = 0;
615 mwHead = mwTail = NULL;
616 if( mwErrors )
617 fprintf(mwSTDERR,"MEMWATCH detected %ld anomalies\n",mwErrors);
618 mwLogFile( NULL );
619 mwErrors = 0;
620
622
623 }
TTree * data
Double_t time
#define MW_NML
#define MW_MUTEX_TERM()
#define mwSTDERR
#define FLUSH()
#define MW_VAL_NML
size_t size
const char * file
unsigned flag
long count
mwMarker * next
void * host
char * text

Referenced by mwInit(), and mwTerm().

◆ mwAriHandler()

int mwAriHandler ( const char *  cause)

Definition at line 848 of file KalFitMemLeak.c.

848 {
849 mwAutoInit();
850 return mwARI( estr );
851 }

◆ mwAssert()

int mwAssert ( int  exp,
const char *  exps,
const char *  fn,
int  ln 
)

Definition at line 1228 of file KalFitMemLeak.c.

1228 {
1229 int i;
1230 char buffer[MW_TRACE_BUFFER+8];
1231 if( exp ) {
1232 return 0;
1233 }
1234 mwAutoInit();
1235 MW_MUTEX_LOCK();
1236 TESTS(fn,ln);
1237 mwIncErr();
1238 mwCounter++;
1239 mwWrite( "assert trap: <%ld> %s(%d), %s\n", mwCounter, fn, ln, exps );
1240 if( mwAriFunction != NULL ) {
1241 sprintf( buffer, "MEMWATCH: assert trap: %s(%d), %s", fn, ln, exps );
1242 i = (*mwAriFunction)(buffer);
1243 switch( i ) {
1244 case MW_ARI_IGNORE:
1245 mwWrite( "assert trap: <%ld> IGNORED - execution continues\n", mwCounter );
1247 return 0;
1248 case MW_ARI_RETRY:
1249 mwWrite( "assert trap: <%ld> RETRY - executing again\n", mwCounter );
1251 return 1;
1252 }
1253 }
1254 else {
1255 if( mwAriAction & MW_ARI_IGNORE ) {
1256 mwWrite( "assert trap: <%ld> AUTO IGNORED - execution continues\n", mwCounter );
1258 return 0;
1259 }
1260 fprintf(mwSTDERR,"\nMEMWATCH: assert trap: %s(%d), %s\n", fn, ln, exps );
1261 }
1262
1263 FLUSH();
1264 (void) mwTestNow( fn, ln, 1 );
1265 FLUSH();
1266
1267 if( mwAriAction & MW_ARI_NULLREAD ) {
1268 /* This is made in an attempt to kick in */
1269 /* any debuggers or OS stack traces */
1270 FLUSH();
1271 /*lint -save -e413 */
1272 i = *((int*)NULL);
1273 mwDummy( (char)i );
1274 /*lint -restore */
1275 }
1276
1278 exit(255);
1279 /* NOT REACHED - the return statement is in to keep */
1280 /* stupid compilers from squeaking about differing return modes. */
1281 /* Smart compilers instead say 'code unreachable...' */
1282 /*lint -save -e527 */
1283 return 0;
1284 /*lint -restore */
1285 }
EvtComplex exp(const EvtComplex &c)
Definition: EvtComplex.hh:252
#define MW_MUTEX_UNLOCK()
#define TESTS(f, l)
#define MW_MUTEX_LOCK()
#define MW_ARI_RETRY
#define MW_ARI_IGNORE
#define MW_TRACE_BUFFER
#define MW_ARI_NULLREAD
const unsigned long mwCounter

◆ mwAutoCheck()

void mwAutoCheck ( int  onoff)

Definition at line 649 of file KalFitMemLeak.c.

649 {
650 mwAutoInit();
651 mwTestAlways = onoff;
652 if( onoff ) mwTestFlags = MW_TEST_ALL;
653 }
#define MW_TEST_ALL

◆ mwBreakOut()

void mwBreakOut ( const char *  cause)

Definition at line 709 of file KalFitMemLeak.c.

709 {
710 fprintf(mwSTDERR, "breakout: %s\n", cause);
711 mwWrite("breakout: %s\n", cause );
712 return;
713 }

◆ mwCalcCheck()

void mwCalcCheck ( void  )

◆ mwCalloc()

void * mwCalloc ( size_t  a,
size_t  b,
const char *  file,
int  line 
)

Definition at line 1154 of file KalFitMemLeak.c.

1154 {
1155 void *p;
1156 size_t size = a * b;
1157 p = mwMalloc( size, file, line );
1158 if( p == NULL ) return NULL;
1159 memset( p, 0, size );
1160 return p;
1161 }
#define mwMalloc(n, f, l)

◆ mwCalloc_()

void * mwCalloc_ ( size_t  a,
size_t  b 
)

Definition at line 1184 of file KalFitMemLeak.c.

1184 {
1185 MW_MUTEX_LOCK();
1186 TESTS(NULL,0);
1188 return calloc( a, b );
1189 }

◆ mwDoFlush()

void mwDoFlush ( int  onoff)

Definition at line 1196 of file KalFitMemLeak.c.

1196 {
1197 mwFlushW( onoff<1?0:onoff );
1198 if( onoff ) if( mwLogR() ) fflush( mwLogR() );
1199 return;
1200 }

◆ mwDrop()

unsigned mwDrop ( unsigned  kilobytes)

Definition at line 1377 of file KalFitMemLeak.c.

1377 {
1378 TESTS(NULL,0);
1379 return mwDrop_( kb, MW_VAL_GRB, 0 );
1380 }
#define MW_VAL_GRB

◆ mwDummyTraceFunction()

void mwDummyTraceFunction ( const char *  ,
  ... 
)

◆ mwDumpCheck()

void mwDumpCheck ( void  )

◆ mwFlushNow()

void mwFlushNow ( void  )

Definition at line 1191 of file KalFitMemLeak.c.

1191 {
1192 if( mwLogR() ) fflush( mwLogR() );
1193 return;
1194 }

◆ mwFree()

void mwFree ( void *  p,
const char *  file,
int  line 
)

Definition at line 1051 of file KalFitMemLeak.c.

1051 {
1052 int i;
1053 mwData* mw;
1054 char buffer[ sizeof(mwData) + (mwROUNDALLOC*3) + 64 ];
1055
1056 /* this code is in support of C++ delete */
1057 if( file == NULL ) {
1058 mwFree_( p );
1060 return;
1061 }
1062
1063 mwAutoInit();
1064
1065 MW_MUTEX_LOCK();
1066 TESTS(file,line);
1067 mwCounter ++;
1068
1069 /* on NULL free, write a warning and return */
1070 if( p == NULL ) {
1071 mwWrite( "NULL free: <%ld> %s(%d), NULL pointer free'd\n",
1072 mwCounter, file, line );
1073 FLUSH();
1075 return;
1076 }
1077
1078 /* do the quick ownership test */
1079 mw = (mwData*) mwBUFFER_TO_MW( p );
1080
1081 if( mwIsOwned( mw, file, line ) ) {
1082 (void) mwTestBuf( mw, file, line );
1083
1084 /* if the buffer is an NML, treat this as a double-free */
1085 if( mw->flag & MW_NML )
1086 {
1087 if( *(((unsigned char*)mw)+mwDataSize+mwOverflowZoneSize) != MW_VAL_NML )
1088 {
1089 mwWrite( "internal: <%ld> %s(%d), no-mans-land MW-%p is corrupted\n",
1090 mwCounter, file, line, mw );
1091 }
1092 goto check_dbl_free;
1093 }
1094
1095 /* update the statistics */
1096 mwNumCurAlloc --;
1097 mwStatCurAlloc -= (long) mw->size;
1098 if( mwStatLevel ) mwStatFree( mw->size, mw->file, mw->line );
1099
1100 /* we should either free the allocation or keep it as NML */
1101 if( mwNML ) {
1102 mw->flag |= MW_NML;
1103 mwNmlNumAlloc ++;
1104 mwNmlCurAlloc += (long) mw->size;
1105 memset( ((char*)mw)+mwDataSize+mwOverflowZoneSize, MW_VAL_NML, mw->size );
1106 }
1107 else {
1108 /* unlink the allocation, and enter the post-free data */
1109 mwUnlink( mw, file, line );
1110 memset( mw, MW_VAL_DEL,
1111 mw->size + mwDataSize+mwOverflowZoneSize+mwOverflowZoneSize );
1112 if( mwFBI ) {
1113 memset( mw, '.', mwDataSize + mwOverflowZoneSize );
1114 sprintf( buffer, "FBI<%ld>%s(%d)", mwCounter, file, line );
1115 strncpy( (char*)(void*)mw, buffer, mwDataSize + mwOverflowZoneSize );
1116 }
1117 free( mw );
1118 }
1119
1120 /* add the pointer to the last-free track */
1121 mwLFfile[ mwLFcur ] = file;
1122 mwLFline[ mwLFcur ] = line;
1123 mwLastFree[ mwLFcur++ ] = p;
1124 if( mwLFcur == MW_FREE_LIST ) mwLFcur = 0;
1125
1127 return;
1128 }
1129
1130 /* check for double-freeing */
1131check_dbl_free:
1132 for(i=0;i<MW_FREE_LIST;i++) {
1133 if( mwLastFree[i] == p ) {
1134 mwIncErr();
1135 mwWrite( "double-free: <%ld> %s(%d), %p was"
1136 " freed from %s(%d)\n",
1137 mwCounter, file, line, p,
1138 mwLFfile[i], mwLFline[i] );
1139 FLUSH();
1141 return;
1142 }
1143 }
1144
1145 /* some weird pointer... block the free */
1146 mwIncErr();
1147 mwWrite( "WILD free: <%ld> %s(%d), unknown pointer %p\n",
1148 mwCounter, file, line, p );
1149 FLUSH();
1151 return;
1152 }
#define mwBUFFER_TO_MW(p)
#define mwROUNDALLOC
struct mwData_ mwData
#define mwFree_(p)
#define MW_FREE_LIST
#define MW_VAL_DEL

◆ mwFree_()

void mwFree_ ( void *  p)

Definition at line 1163 of file KalFitMemLeak.c.

1163 {
1164 MW_MUTEX_LOCK();
1165 TESTS(NULL,0);
1167 free(p);
1168 }

◆ mwFreeBufferInfo()

void mwFreeBufferInfo ( int  onoff)

◆ mwGrab()

unsigned mwGrab ( unsigned  kilobytes)

Definition at line 1372 of file KalFitMemLeak.c.

1372 {
1373 TESTS(NULL,0);
1374 return mwGrab_( kb, MW_VAL_GRB, 0 );
1375 }

◆ mwIsReadAddr()

int mwIsReadAddr ( const void *  p,
unsigned  len 
)

Definition at line 2491 of file KalFitMemLeak.c.

2492{
2493 if( p == NULL ) return 0;
2494 if( len == 0 ) return 1;
2495 return 1;
2496}

Referenced by mwMark().

◆ mwIsSafeAddr()

int mwIsSafeAddr ( void *  p,
unsigned  len 
)

Definition at line 2497 of file KalFitMemLeak.c.

2498{
2499 if( p == NULL ) return 0;
2500 if( len == 0 ) return 1;
2501 return 1;
2502}

◆ mwLimit()

void mwLimit ( long  bytes)

Definition at line 1202 of file KalFitMemLeak.c.

1202 {
1203 TESTS(NULL,0);
1204 mwWrite("limit: old limit = ");
1205 if( !mwAllocLimit ) mwWrite( "none" );
1206 else mwWrite( "%ld bytes", mwAllocLimit );
1207 mwWrite( ", new limit = ");
1208 if( !lim ) {
1209 mwWrite( "none\n" );
1210 mwUseLimit = 0;
1211 }
1212 else {
1213 mwWrite( "%ld bytes\n", lim );
1214 mwUseLimit = 1;
1215 }
1216 mwAllocLimit = lim;
1217 FLUSH();
1218 }

◆ mwMalloc()

void * mwMalloc ( size_t  size,
const char *  file,
int  line 
)

Definition at line 863 of file KalFitMemLeak.c.

863 {
864 size_t needed;
865 mwData *mw;
866 char *ptr;
867 void *p;
868
869 mwAutoInit();
870
872
873 TESTS(file,line);
874
875 mwCounter ++;
876 needed = mwDataSize + mwOverflowZoneSize*2 + size;
877 if( needed < size )
878 {
879 /* theoretical case: req size + mw overhead exceeded size_t limits */
880 return NULL;
881 }
882
883 /* if this allocation would violate the limit, fail it */
884 if( mwUseLimit && ((long)size + mwStatCurAlloc > mwAllocLimit) ) {
885 mwWrite( "limit fail: <%ld> %s(%d), %ld wanted %ld available\n",
886 mwCounter, file, line, (long)size, mwAllocLimit - mwStatCurAlloc );
887 mwIncErr();
888 FLUSH();
890 return NULL;
891 }
892
893 mw = (mwData*) malloc( needed );
894 if( mw == NULL ) {
895 if( mwFreeUp(needed,0) >= needed ) {
896 mw = (mwData*) malloc(needed);
897 if( mw == NULL ) {
898 mwWrite( "internal: mwFreeUp(%u) reported success, but malloc() fails\n", needed );
899 mwIncErr();
900 FLUSH();
901 }
902 }
903 if( mw == NULL ) {
904 mwWrite( "fail: <%ld> %s(%d), %ld wanted %ld allocated\n",
905 mwCounter, file, line, (long)size, mwStatCurAlloc );
906 mwIncErr();
907 FLUSH();
909 return NULL;
910 }
911 }
912
913 mw->count = mwCounter;
914 mw->prev = NULL;
915 mw->next = mwHead;
916 mw->file = file;
917 mw->size = size;
918 mw->line = line;
919 mw->flag = 0;
920 mw->check = CHKVAL(mw);
921
922 if( mwHead ) mwHead->prev = mw;
923 mwHead = mw;
924 if( mwTail == NULL ) mwTail = mw;
925
926 ptr = ((char*)mw) + mwDataSize;
927 mwWriteOF( ptr ); /* '*(long*)ptr = PRECHK;' */
928 ptr += mwOverflowZoneSize;
929 p = ptr;
930 memset( ptr, MW_VAL_NEW, size );
931 ptr += size;
932 mwWriteOF( ptr ); /* '*(long*)ptr = POSTCHK;' */
933
934 mwNumCurAlloc ++;
935 mwStatCurAlloc += (long) size;
936 mwStatTotAlloc += (long) size;
937 if( mwStatCurAlloc > mwStatMaxAlloc )
938 mwStatMaxAlloc = mwStatCurAlloc;
939 mwStatNumAlloc ++;
940
941 if( mwStatLevel ) mwStatAlloc( size, file, line );
942
944 return p;
945 }
#define CHKVAL(mw)
#define MW_VAL_NEW
long check
mwData * prev
mwData * next

◆ mwMalloc_()

void * mwMalloc_ ( size_t  size)

Definition at line 1170 of file KalFitMemLeak.c.

1170 {
1171 MW_MUTEX_LOCK();
1172 TESTS(NULL,0);
1174 return malloc( size );
1175 }

◆ mwMark()

void * mwMark ( void *  p,
const char *  description,
const char *  file,
unsigned  line 
)

Definition at line 718 of file KalFitMemLeak.c.

718 {
719 mwMarker *mrk;
720 unsigned n, isnew;
721 char *buf;
722 int tot, oflow = 0;
723 char wherebuf[128];
724
725 mwAutoInit();
726 TESTS(NULL,0);
727
728 if( desc == NULL ) desc = "unknown";
729 if( file == NULL ) file = "unknown";
730
731 tot = sprintf( wherebuf, "%.48s called from %s(%d)", desc, file, line );
732 if( tot >= (int)sizeof(wherebuf) ) { wherebuf[sizeof(wherebuf)-1] = 0; oflow = 1; }
733
734 if( p == NULL ) {
735 mwWrite("mark: %s(%d), no mark for NULL:'%s' may be set\n", file, line, desc );
736 return p;
737 }
738
739 if( mwFirstMark != NULL && !mwIsReadAddr( mwFirstMark, sizeof( mwMarker ) ) )
740 {
741 mwWrite("mark: %s(%d), mwFirstMark (%p) is trashed, can't mark for %s\n",
742 file, line, mwFirstMark, desc );
743 return p;
744 }
745
746 for( mrk=mwFirstMark; mrk; mrk=mrk->next )
747 {
748 if( mrk->next != NULL && !mwIsReadAddr( mrk->next, sizeof( mwMarker ) ) )
749 {
750 mwWrite("mark: %s(%d), mark(%p)->next(%p) is trashed, can't mark for %s\n",
751 file, line, mrk, mrk->next, desc );
752 return p;
753 }
754 if( mrk->host == p ) break;
755 }
756
757 if( mrk == NULL ) {
758 isnew = 1;
759 mrk = (mwMarker*) malloc( sizeof( mwMarker ) );
760 if( mrk == NULL ) {
761 mwWrite("mark: %s(%d), no mark for %p:'%s', out of memory\n", file, line, p, desc );
762 return p;
763 }
764 mrk->next = NULL;
765 n = 0;
766 }
767 else {
768 isnew = 0;
769 n = strlen( mrk->text );
770 }
771
772 n += strlen( wherebuf );
773 buf = (char*) malloc( n+3 );
774 if( buf == NULL ) {
775 if( isnew ) free( mrk );
776 mwWrite("mark: %s(%d), no mark for %p:'%s', out of memory\n", file, line, p, desc );
777 return p;
778 }
779
780 if( isnew ) {
781 memcpy( buf, wherebuf, n+1 );
782 mrk->next = mwFirstMark;
783 mrk->host = p;
784 mrk->text = buf;
785 mrk->level = 1;
786 mwFirstMark = mrk;
787 }
788 else {
789 strcpy( buf, mrk->text );
790 strcat( buf, ", " );
791 strcat( buf, wherebuf );
792 free( mrk->text );
793 mrk->text = buf;
794 mrk->level ++;
795 }
796
797 if( oflow ) {
798 mwIncErr();
799 mwTrace( " [WARNING: OUTPUT BUFFER OVERFLOW - SYSTEM UNSTABLE]\n" );
800 }
801 return p;
802 }
const Int_t n
int mwIsReadAddr(const void *p, unsigned len)
#define mwTrace

◆ mwNoMansLand()

void mwNoMansLand ( int  mw_nml_level)

Definition at line 1489 of file KalFitMemLeak.c.

1489 {
1490 mwAutoInit();
1491 TESTS(NULL,0);
1492 switch( level ) {
1493 case MW_NML_NONE:
1494 (void) mwDrop_( 0, MW_VAL_NML, 0 );
1495 break;
1496 case MW_NML_FREE:
1497 break;
1498 case MW_NML_ALL:
1499 (void) mwGrab_( 0, MW_VAL_NML, 0 );
1500 break;
1501 default:
1502 return;
1503 }
1504 mwNML = level;
1505 }
#define MW_NML_NONE
#define MW_NML_ALL
#define MW_NML_FREE

◆ mwPuts()

void mwPuts ( const char *  text)

◆ mwRealloc()

void * mwRealloc ( void *  p,
size_t  size,
const char *  file,
int  line 
)

Definition at line 947 of file KalFitMemLeak.c.

947 {
948 int oldUseLimit, i;
949 mwData *mw;
950 char *ptr;
951
952 mwAutoInit();
953
954 if( p == NULL ) return mwMalloc( size, file, line );
955 if( size == 0 ) { mwFree( p, file, line ); return NULL; }
956
958
959 /* do the quick ownership test */
960 mw = (mwData*) mwBUFFER_TO_MW( p );
961 if( mwIsOwned( mw, file, line ) ) {
962
963 /* if the buffer is an NML, treat this as a double-free */
964 if( mw->flag & MW_NML )
965 {
966 mwIncErr();
967 if( *((unsigned char*)(mw)+mwDataSize+mwOverflowZoneSize) != MW_VAL_NML )
968 {
969 mwWrite( "internal: <%ld> %s(%d), no-mans-land MW-%p is corrupted\n",
970 mwCounter, file, line, mw );
971 }
972 goto check_dbl_free;
973 }
974
975 /* if this allocation would violate the limit, fail it */
976 if( mwUseLimit && ((long)size + mwStatCurAlloc - (long)mw->size > mwAllocLimit) ) {
977 TESTS(file,line);
978 mwCounter ++;
979 mwWrite( "limit fail: <%ld> %s(%d), %ld wanted %ld available\n",
980 mwCounter, file, line, (unsigned long)size - mw->size, mwAllocLimit - mwStatCurAlloc );
981 mwIncErr();
982 FLUSH();
984 return NULL;
985 }
986
987 /* fake realloc operation */
988 oldUseLimit = mwUseLimit;
989 mwUseLimit = 0;
990 ptr = (char*) mwMalloc( size, file, line );
991 if( ptr != NULL ) {
992 if( size < mw->size )
993 memcpy( ptr, p, size );
994 else
995 memcpy( ptr, p, mw->size );
996 mwFree( p, file, line );
997 }
998 mwUseLimit = oldUseLimit;
1000 return (void*) ptr;
1001 }
1002
1003 /* Unknown pointer! */
1004
1005 /* using free'd pointer? */
1006check_dbl_free:
1007 for(i=0;i<MW_FREE_LIST;i++) {
1008 if( mwLastFree[i] == p ) {
1009 mwIncErr();
1010 mwWrite( "realloc: <%ld> %s(%d), %p was"
1011 " freed from %s(%d)\n",
1012 mwCounter, file, line, p,
1013 mwLFfile[i], mwLFline[i] );
1014 FLUSH();
1016 return NULL;
1017 }
1018 }
1019
1020 /* some weird pointer */
1021 mwIncErr();
1022 mwWrite( "realloc: <%ld> %s(%d), unknown pointer %p\n",
1023 mwCounter, file, line, p );
1024 FLUSH();
1026 return NULL;
1027 }
#define mwFree(p)

◆ mwRealloc_()

void * mwRealloc_ ( void *  p,
size_t  size 
)

Definition at line 1177 of file KalFitMemLeak.c.

1177 {
1178 MW_MUTEX_LOCK();
1179 TESTS(NULL,0);
1181 return realloc( p, size );
1182 }

◆ mwSetAriAction()

void mwSetAriAction ( int  mw_ari_value)

Definition at line 1220 of file KalFitMemLeak.c.

1220 {
1221 MW_MUTEX_LOCK();
1222 TESTS(NULL,0);
1223 mwAriAction = action;
1225 return;
1226 }

◆ mwSetAriFunc()

void mwSetAriFunc ( int(*)(const char *)  func)

Definition at line 854 of file KalFitMemLeak.c.

854 {
855 mwAutoInit();
856 mwAriFunction = func;
857 }

◆ mwSetOutFunc()

void mwSetOutFunc ( void(*)(int)  func)

Definition at line 655 of file KalFitMemLeak.c.

655 {
656 mwAutoInit();
657 mwOutFunction = func;
658 }

◆ mwStatistics()

void mwStatistics ( int  level)

Definition at line 637 of file KalFitMemLeak.c.

638{
639 mwAutoInit();
640 if( level<0 ) level=0;
641 if( mwStatLevel != level )
642 {
643 mwWrite( "statistics: now collecting on a %s basis\n",
644 level<1?"global":(level<2?"module":"line") );
645 mwStatLevel = level;
646 }
647}

◆ mwStrdup()

char * mwStrdup ( const char *  str,
const char *  file,
int  line 
)

Definition at line 1029 of file KalFitMemLeak.c.

1029 {
1030 size_t len;
1031 char *newstring;
1032
1033 MW_MUTEX_LOCK();
1034
1035 if( str == NULL ) {
1036 mwIncErr();
1037 mwWrite( "strdup: <%ld> %s(%d), strdup(NULL) called\n",
1038 mwCounter, file, line );
1039 FLUSH();
1041 return NULL;
1042 }
1043
1044 len = strlen( str ) + 1;
1045 newstring = (char*) mwMalloc( len, file, line );
1046 if( newstring != NULL ) memcpy( newstring, str, len );
1048 return newstring;
1049 }

◆ mwTerm()

void mwTerm ( void  )

Definition at line 625 of file KalFitMemLeak.c.

625 {
626 if( mwInited == 1 )
627 {
628 mwAbort();
629 return;
630 }
631 if( !mwInited )
632 mwWrite("internal: mwTerm(): MEMWATCH has not been started!\n");
633 else
634 mwInited --;
635 }
void mwAbort(void)

◆ mwTest()

int mwTest ( const char *  file,
int  line,
int  mw_test_flags 
)

Definition at line 685 of file KalFitMemLeak.c.

685 {
686 mwAutoInit();
687 mwTestFlags = items;
688 return mwTestNow( file, line, 0 );
689 }

◆ mwTestBuffer()

int mwTestBuffer ( const char *  file,
int  line,
void *  p 
)

Definition at line 695 of file KalFitMemLeak.c.

695 {
696 mwData* mw;
697
698 mwAutoInit();
699
700 /* do the quick ownership test */
701 mw = (mwData*) mwBUFFER_TO_MW( p );
702
703 if( mwIsOwned( mw, file, line ) ) {
704 return mwTestBuf( mw, file, line );
705 }
706 return 1;
707 }

◆ mwTrace()

void mwTrace ( const char *  format_string,
  ... 
)

Definition at line 1343 of file KalFitMemLeak.c.

1343 {
1344 int tot, oflow = 0;
1345 va_list mark;
1346
1347 mwAutoInit();
1348 MW_MUTEX_LOCK();
1349 TESTS(NULL,0);
1350 if( mwOutFunction == NULL ) mwOutFunction = mwDefaultOutFunc;
1351
1352 va_start( mark, format );
1353 tot = vsprintf( mwPrintBuf, format, mark );
1354 va_end( mark );
1355 if( tot >= MW_TRACE_BUFFER ) { mwPrintBuf[MW_TRACE_BUFFER] = 0; oflow = 1; }
1356 for(tot=0;mwPrintBuf[tot];tot++)
1357 (*mwOutFunction)( mwPrintBuf[tot] );
1358 if( oflow ) {
1359 mwIncErr();
1360 mwTrace( " [WARNING: OUTPUT BUFFER OVERFLOW - SYSTEM UNSTABLE]\n" );
1361 }
1362
1363 FLUSH();
1365 }

◆ mwUnmark()

void * mwUnmark ( void *  p,
const char *  file,
unsigned  line 
)

Definition at line 804 of file KalFitMemLeak.c.

804 {
805 mwMarker *mrk, *prv;
806 mrk = mwFirstMark;
807 prv = NULL;
808 while( mrk ) {
809 if( mrk->host == p ) {
810 if( mrk->level < 2 ) {
811 if( prv ) prv->next = mrk->next;
812 else mwFirstMark = mrk->next;
813 free( mrk->text );
814 free( mrk );
815 return p;
816 }
817 mrk->level --;
818 return p;
819 }
820 prv = mrk;
821 mrk = mrk->next;
822 }
823 mwWrite("mark: %s(%d), no mark found for %p\n", file, line, p );
824 return p;
825 }

◆ mwVerify()

int mwVerify ( int  exp,
const char *  exps,
const char *  fn,
int  ln 
)

Definition at line 1287 of file KalFitMemLeak.c.

1287 {
1288 int i;
1289 char buffer[MW_TRACE_BUFFER+8];
1290 if( exp ) {
1291 return 0;
1292 }
1293 mwAutoInit();
1294 MW_MUTEX_LOCK();
1295 TESTS(fn,ln);
1296 mwIncErr();
1297 mwCounter++;
1298 mwWrite( "verify trap: <%ld> %s(%d), %s\n", mwCounter, fn, ln, exps );
1299 if( mwAriFunction != NULL ) {
1300 sprintf( buffer, "MEMWATCH: verify trap: %s(%d), %s", fn, ln, exps );
1301 i = (*mwAriFunction)(buffer);
1302 if( i == 0 ) {
1303 mwWrite( "verify trap: <%ld> IGNORED - execution continues\n", mwCounter );
1305 return 0;
1306 }
1307 if( i == 1 ) {
1308 mwWrite( "verify trap: <%ld> RETRY - executing again\n", mwCounter );
1310 return 1;
1311 }
1312 }
1313 else {
1314 if( mwAriAction & MW_ARI_NULLREAD ) {
1315 /* This is made in an attempt to kick in */
1316 /* any debuggers or OS stack traces */
1317 FLUSH();
1318 /*lint -save -e413 */
1319 i = *((int*)NULL);
1320 mwDummy( (char)i );
1321 /*lint -restore */
1322 }
1323 if( mwAriAction & MW_ARI_IGNORE ) {
1324 mwWrite( "verify trap: <%ld> AUTO IGNORED - execution continues\n", mwCounter );
1326 return 0;
1327 }
1328 fprintf(mwSTDERR,"\nMEMWATCH: verify trap: %s(%d), %s\n", fn, ln, exps );
1329 }
1330 FLUSH();
1331 (void) mwTestNow( fn, ln, 1 );
1332 FLUSH();
1334 exit(255);
1335 /* NOT REACHED - the return statement is in to keep */
1336 /* stupid compilers from squeaking about differing return modes. */
1337 /* Smart compilers instead say 'code unreachable...' */
1338 /*lint -save -e527 */
1339 return 0;
1340 /*lint -restore */
1341 }

Variable Documentation

◆ mwCounter

const unsigned long mwCounter
extern