diff options
author | sasha@mysql.sashanet.com <> | 2002-03-26 22:19:23 -0700 |
---|---|---|
committer | sasha@mysql.sashanet.com <> | 2002-03-26 22:19:23 -0700 |
commit | f28f8d086d3f5e1ede685b86ce64da5641437bcf (patch) | |
tree | ab4d73690dcb8e3ef54e70015f1838cf17a2577a /mysys/safemalloc.c | |
parent | 2e6b48afd31008809439900db2d577ea0ff9d90f (diff) | |
download | mariadb-git-f28f8d086d3f5e1ede685b86ce64da5641437bcf.tar.gz |
coverted my_thread_init() /end to use my_malloc()/my_free() to help track
down replication corruption
Diffstat (limited to 'mysys/safemalloc.c')
-rw-r--r-- | mysys/safemalloc.c | 70 |
1 files changed, 69 insertions, 1 deletions
diff --git a/mysys/safemalloc.c b/mysys/safemalloc.c index d8c089c2ff0..062f9b9db02 100644 --- a/mysys/safemalloc.c +++ b/mysys/safemalloc.c @@ -73,14 +73,25 @@ #include "mysys_err.h" ulonglong safemalloc_mem_limit = ~(ulonglong)0; +pthread_t shutdown_th=0,main_th=0,signal_th=0; #define pNext tInt._pNext #define pPrev tInt._pPrev #define sFileName tInt._sFileName #define uLineNum tInt._uLineNum #define uDataSize tInt._uDataSize +#define thread_id tInt.thread_id #define lSpecialValue tInt._lSpecialValue +#ifndef PEDANTIC_SAFEMALLOC +static int sf_malloc_tampered = 0; /* set to 1 after TERMINATE() if we had + to fiddle with cNewCount and the linked + list of blocks so that _sanity() will + not fuss when it is not supposed to + */ +#endif + + /* Static functions prototypes */ static int check_ptr(const char *where, byte *ptr, const char *sFile, @@ -174,6 +185,7 @@ gptr _mymalloc (uint uSize, const char *sFile, uint uLine, myf MyFlags) pTmp -> sFileName = (my_string) sFile; pTmp -> uLineNum = uLine; pTmp -> uDataSize = uSize; + pTmp->thread_id = pthread_self(); pTmp -> pPrev = NULL; /* Add this remember structure to the linked list */ @@ -359,6 +371,12 @@ static int check_ptr(const char *where, byte *ptr, const char *sFile, return 0; } +static int legal_leak(struct remember* pPtr) +{ + return pthread_self() == pPtr->thread_id || main_th == pPtr->thread_id + || shutdown_th == pPtr->thread_id + || signal_th == pPtr->thread_id; +} /* * TERMINATE(FILE *file) @@ -376,6 +394,47 @@ void TERMINATE (FILE *file) /* NEW and the number of calls to FREE. >0 means more */ /* NEWs than FREEs. <0, etc. */ +#ifndef PEDANTIC_SAFEMALLOC + /* Avoid false alarms for blocks that we cannot free before my_end() + This does miss some positives, but that is ok. This will only miss + failures to free things allocated in the main thread which + performs only one-time allocations. If you really need to + debug memory allocations in the main thread, + #define PEDANTIC_SAFEMALLOC + */ + if ((pPtr=pRememberRoot)) + { + while (pPtr) + { + if (legal_leak(pPtr)) + { + sf_malloc_tampered=1; + cNewCount--; + lCurMemory -= pPtr->uDataSize; + if (pPtr->pPrev) + { + struct remember* tmp; + tmp = pPtr->pPrev->pNext = pPtr->pNext; + if (tmp) + tmp->pPrev = pPtr->pPrev; + pPtr->pNext = pPtr->pPrev = 0; + pPtr = tmp; + } + else + { + pRememberRoot = pPtr->pNext; + pPtr->pNext = pPtr->pPrev = 0; + pPtr = pRememberRoot; + if (pPtr) + pPtr->pPrev=0; + } + } + else + pPtr = pPtr->pNext; + } + } +#endif + if (cNewCount) { if (file) @@ -402,10 +461,14 @@ void TERMINATE (FILE *file) if (file) { fprintf (file, - "\t%6u bytes at 0x%09lx, allocated at line %4u in '%s'\n", + "\t%6u bytes at 0x%09lx, allocated at line %4u in '%s'", pPtr -> uDataSize, (ulong) &(pPtr -> aData[sf_malloc_prehunc]), pPtr -> uLineNum, pPtr -> sFileName); +#ifdef THREAD + fprintf(file, " in thread %ld", pPtr->thread_id); +#endif + fprintf(file, "\n"); (void) fflush(file); } DBUG_PRINT("safe", @@ -484,6 +547,10 @@ int _sanity (const char *sFile, uint uLine) uint count=0; pthread_mutex_lock(&THR_LOCK_malloc); +#ifndef PEDANTIC_SAFEMALLOC + if (sf_malloc_tampered && cNewCount < 0) + cNewCount=0; +#endif count=cNewCount; for (pTmp = pRememberRoot; pTmp != NULL && count-- ; pTmp = pTmp -> pNext) flag+=_checkchunk (pTmp, sFile, uLine); @@ -492,6 +559,7 @@ int _sanity (const char *sFile, uint uLine) { const char *format="Safemalloc link list destroyed, discovered at '%s:%d'"; fprintf (stderr, format, sFile, uLine); fputc('\n',stderr); + fprintf (stderr, "root=%p,count=%d,pTmp=%p\n", pRememberRoot,count,pTmp); (void) fflush(stderr); DBUG_PRINT("safe",(format, sFile, uLine)); flag=1; |