Changeset 1072

Show
Ignore:
Timestamp:
07/17/08 19:39:14 (6 weeks ago)
Author:
stevenhl
Message:

Add Fortify_SetOwner Fortify_ChangeOwner to support cross thread allocations

Location:
trunk/dll
Files:
2 modified

Legend:

Unmodified
Added
Removed
  • trunk/dll/fortify.c

    r1019 r1072  
    4343 /* 06 May 08 SHL Rework scope logic to be MT capable 
    4444    26 May 08 SHL Show TID for leaking scope 
     45    17 Jul 08 SHL Add Fortify_SetOwner Fortify_ChangeOwner 
    4546 */ 
    4647 
     
    6465 
    6566 
    66 #if defined(__WATCOMC__) && defined(_MT) 
    67 #define MT_SCOPES 1 
     67#ifdef MT_SCOPES 
    6868unsigned long Get_TID_Ordinal(void); 
    6969// Get tib_ptib2 from TIB 
     
    100100    struct Header *Next;        /* Next link                         */ 
    101101    char          *Label;       /* User's Label (may be null)        */ 
    102     unsigned char  Scope;       /* Scope level of the caller         */ 
     102    unsigned char  Scope;       /* Scope level of the owner          */ 
    103103    unsigned char  Allocator;   /* malloc/realloc/new/etc            */ 
    104104#   ifdef MT_SCOPES 
    105     unsigned short Ordinal;     /* TID ordinal of caller             */ 
     105    unsigned short Owner;       /* TID ordinal of block owner        */ 
    106106#   endif 
    107107}; 
    108108 
    109109#define FORTIFY_HEADER_SIZE ROUND_UP(sizeof(struct Header), sizeof(unsigned short)) 
    110  
    111110 
    112111 
     
    177176static unsigned long  st_LastVerifiedLine; 
    178177#ifdef MT_SCOPES 
    179 static unsigned volatile st_cScopes; 
    180 static unsigned volatile char*  st_pScopes; 
     178static unsigned volatile st_cOrdinals;          // Number of known threads 
     179static unsigned volatile char*  st_pScopes;     // Scope level of blocks allocated by thread 
     180static unsigned volatile long*  st_pOwners;     // Owner of blocks allocated by thread 
    181181#else 
    182182static unsigned char  st_Scope            = 0; 
     
    416416#   ifdef MT_SCOPES 
    417417    ordinal = Get_TID_Ordinal(); 
     418    // In case owner overridden by Fortify_SetOwner 
     419    if (ordinal < st_cOrdinals) 
     420        ordinal = st_pOwners[ordinal]; 
    418421#   endif 
    419422 
     
    428431    h->Prev      = 0; 
    429432#   ifdef MT_SCOPES 
    430     h->Scope     = ordinal < st_cScopes ? st_pScopes[ordinal] : 0; 
    431     h->Ordinal = ordinal; 
     433    h->Scope     = ordinal < st_cOrdinals ? st_pScopes[ordinal] : 0; 
     434    h->Owner = ordinal; 
    432435#   else 
    433436    h->Scope     = st_Scope; 
     
    690693#ifdef MT_SCOPES 
    691694    ordinal = Get_TID_Ordinal(); 
    692     if (ordinal < st_cScopes && st_pScopes[ordinal] > 0) 
     695    if (ordinal < st_cOrdinals && st_pScopes[ordinal] > 0) 
    693696#else 
    694697    if(st_Scope > 0) 
     
    977980#ifdef MT_SCOPES 
    978981    unsigned ordinal = Get_TID_Ordinal(); 
    979  
    980     if (ordinal >= st_cScopes) { 
    981         st_pScopes = realloc((void*)st_pScopes, sizeof(*st_pScopes) * (st_cScopes = (ordinal + 1))); 
    982         st_pScopes[ordinal] = 0; 
     982    unsigned i; 
     983    unsigned c; 
     984 
     985    if (ordinal >= st_cOrdinals) { 
     986        // Expand arrays 
     987        FORTIFY_LOCK(); 
     988        i = st_cOrdinals; 
     989        c = ordinal + 1; 
     990        st_pScopes = realloc((void*)st_pScopes, sizeof(*st_pScopes) * c); 
     991        st_pOwners = realloc((void*)st_pOwners, sizeof(*st_pOwners) * c); 
     992        for (; i <= ordinal; i++) { 
     993            st_pScopes[i] = 0;          // Default to scope level 0 
     994            st_pOwners[i] = i;          // Default block owner to self 
     995        } 
     996        st_cOrdinals = c; 
     997        FORTIFY_UNLOCK(); 
    983998    } 
    984999    return(++st_pScopes[ordinal]); 
     
    10101025    // Complain on leave without enter 06 May 08 SHL 
    10111026    ordinal = Get_TID_Ordinal(); 
    1012     if (ordinal < st_cScopes && st_pScopes[ordinal] > 0) 
     1027    if (ordinal < st_cOrdinals && st_pScopes[ordinal] > 0) 
    10131028        st_pScopes[ordinal]--; 
    10141029    else { 
     
    10291044    { 
    10301045#ifdef MT_SCOPES 
    1031         if(curr->Ordinal == ordinal && ordinal < st_cScopes && curr->Scope > st_pScopes[ordinal]) 
     1046        if(curr->Owner == ordinal && ordinal < st_cOrdinals && curr->Scope > st_pScopes[ordinal]) 
    10321047#else 
    10331048        if(curr->Scope > st_Scope) 
     
    10711086     */ 
    10721087#ifdef MT_SCOPES 
    1073     st_PurgeDeallocatedScope( ordinal < st_cScopes ? st_pScopes[ordinal] : 0, 
     1088    st_PurgeDeallocatedScope( ordinal < st_cOrdinals ? st_pScopes[ordinal] : 0, 
    10741089                              file, line ); 
    10751090#else 
     
    10801095    FORTIFY_UNLOCK(); 
    10811096#ifdef MT_SCOPES 
    1082     return(ordinal < st_cScopes ? st_pScopes[ordinal] : 0); 
     1097    return(ordinal < st_cOrdinals ? st_pScopes[ordinal] : 0); 
    10831098#else 
    10841099    return(st_Scope); 
     
    17001715        next = curr->Next; 
    17011716#ifdef MT_SCOPES 
    1702         if(curr->Ordinal == ordinal && curr->Scope >= Scope) 
     1717        if(curr->Owner == ordinal && curr->Scope >= Scope) 
    17031718#else 
    17041719        if(curr->Scope >= Scope) 
     
    23992414#endif /* __cplusplus */ 
    24002415 
     2416#ifdef MT_SCOPES 
     2417 
     2418/** 
     2419 * Set/reset owner of blocks allocated by this thread 
     2420 * Use when worker thread will allocate blocks for another thread 
     2421 * and other thread is known 
     2422 * More efficient than Fortify_ChangeOwner 
     2423 * @param lOwnerTID is new owner TID, -1 requests reset of self 
     2424 */ 
     2425 
     2426void Fortify_SetOwner(long lOwnerTID) 
     2427{ 
     2428    unsigned ordinal = Get_TID_Ordinal(); 
     2429 
     2430    if (ordinal >= st_cOrdinals) { 
     2431        // Expand arrays 
     2432        unsigned i; 
     2433        unsigned c; 
     2434        FORTIFY_LOCK(); 
     2435        i = st_cOrdinals; 
     2436        c = ordinal + 1; 
     2437        st_pScopes = realloc((void*)st_pScopes, sizeof(*st_pScopes) * c); 
     2438        st_pOwners = realloc((void*)st_pOwners, sizeof(*st_pOwners) * c); 
     2439        for (; i <= ordinal; i++) { 
     2440            st_pScopes[i] = 0; 
     2441            st_pOwners[i] = i;          // Block owner is self 
     2442        } 
     2443        st_cOrdinals = c; 
     2444        FORTIFY_UNLOCK(); 
     2445    } 
     2446    // Set owner for blocks allocated by this thread 
     2447    st_pOwners[ordinal] = lOwnerTID != -1 ? lOwnerTID : ordinal; 
     2448} 
     2449 
     2450/** 
     2451 * Take ownership of block allocated by some other thread 
     2452 * Allows scope enter/exit logic to correctly report leaks in  
     2453 * cross thread allocations 
     2454 * @param pVoid is point to block allocated by Fortify 
     2455 */ 
     2456 
     2457void Fortify_ChangeOwner(void *pBlock) 
     2458{ 
     2459    unsigned char *ptr = (unsigned char *)pBlock - 
     2460                             FORTIFY_HEADER_SIZE - 
     2461                             FORTIFY_ALIGNED_BEFORE_SIZE; 
     2462    struct Header *h = (struct Header *)ptr; 
     2463 
     2464    unsigned ordinal = Get_TID_Ordinal(); 
     2465 
     2466    h->Scope = ordinal < st_cOrdinals ? st_pScopes[ordinal] : 0; 
     2467    h->Owner = ordinal;         // Take ownership 
     2468} 
     2469 
     2470#endif // MT_SCOPES 
     2471 
    24012472#endif /* FORTIFY */ 
  • trunk/dll/fortify.h

    r1015 r1072  
    2727 */ 
    2828 
    29 /*   
     29/* 
    3030 *     If  you use this software at all, I'd love to hear from 
    3131 * you.   All  questions,  criticisms, suggestions, praise and 
    3232 * postcards are most welcome. 
    33  *  
     33 * 
    3434 *            email:    sbullen@cybergraphic.com.au 
    35  *  
     35 * 
    3636 *            snail:    Simon P. Bullen 
    3737 *                      PO BOX 12138 
     
    4141 */ 
    4242 
     43 /* 06 May 08 SHL Rework scope logic to be MT capable 
     44    17 Jul 08 SHL Add Fortify_SetOwner Fortify_ChangeOwner 
     45 */ 
     46 
    4347#ifndef __FORTIFY_H__ 
    4448#define __FORTIFY_H__ 
    4549 
    4650#include <stdlib.h>                     // Must include before fortify defintions 
    47 // 16 Jan 08 SHL Ensure  
     51// 16 Jan 08 SHL Ensure 
    4852#ifdef __BORLANDC__ 
    4953#ifdef __OS2__ 
     
    5660#include "ufortify.h" 
    5761 
     62#if defined(__WATCOMC__) && defined(_MT) 
     63#define MT_SCOPES 1 
     64#endif 
     65 
    5866/* Ensure the configuration parameters have sensible defaults */ 
    5967#ifndef FORTIFY_STORAGE 
     
    8088#endif 
    8189 
    82 #ifndef FORTIFY_FILL_ON_ALLOCATE_VALUE     
     90#ifndef FORTIFY_FILL_ON_ALLOCATE_VALUE 
    8391    #define FORTIFY_FILL_ON_ALLOCATE_VALUE       0xA7 
    8492#endif 
     
    8997 
    9098#ifndef FORTIFY_LOCK 
    91     #define FORTIFY_LOCK()    
     99    #define FORTIFY_LOCK() 
    92100#endif 
    93101 
    94102#ifndef FORTIFY_UNLOCK 
    95     #define FORTIFY_UNLOCK()   
     103    #define FORTIFY_UNLOCK() 
    96104#endif 
    97105 
     
    113121 */ 
    114122 
    115 #ifdef __GNUG__  
     123#ifdef __GNUG__ 
    116124    /* GCC configuration */ 
    117125    #define FORTIFY_PROVIDE_ARRAY_NEW 
     
    181189void  Fortify_Disable(const char *file, unsigned long line); 
    182190 
     191#ifdef MT_SCOPES 
     192void  Fortify_SetOwner(long lOwnerTID); 
     193void  Fortify_ChangeOwner(void *pBlock); 
     194#endif 
     195 
    183196/* Fortify versions of the ANSI C memory allocation functions */ 
    184197void *Fortify_malloc(size_t size, const char *file, unsigned long line); 
     
    242255    #define Fortify_OutputStatistics()     Fortify_OutputStatistics(__FILE__, __LINE__) 
    243256    #define Fortify_GetCurrentAllocation() Fortify_GetCurrentAllocation(__FILE__, __LINE__) 
    244     #define Fortify_SetAllocationLimit(x)  Fortify_SetAllocationLimit(x, __FILE__, __LINE__)     
     257    #define Fortify_SetAllocationLimit(x)  Fortify_SetAllocationLimit(x, __FILE__, __LINE__) 
    245258    #define Fortify_Disable()              Fortify_Disable(__FILE__, __LINE__) 
    246259 
     
    269282#else /* Define the special fortify functions away to nothing */ 
    270283 
     284    // 17 Jul 08 SHL fixme to avoid spurious OpenWatcom warnings 
    271285    #define Fortify_CheckAllMemory()       0 
    272286    #define Fortify_ListAllMemory()        0 
    273287    #define Fortify_DumpAllMemory()        0 
    274     #define Fortify_CheckPointer(ptr)      1  
    275     #define Fortify_LabelPointer(ptr,str)   
     288    #define Fortify_CheckPointer(ptr)      1 
     289    #define Fortify_LabelPointer(ptr,str) 
    276290    #define Fortify_SetOutputFunc()        0 
    277291    #define Fortify_SetMallocFailRate(p)   0 
     
    282296    #define Fortify_SetAllocationLimit(x)  0 
    283297    #define Fortify_Disable()              0 
    284  
    285     #ifdef __cplusplus     
    286         #define Fortify_New                    new 
    287         #define Fortify_Delete                 delete 
     298    #define Fortify_SetOwner()             0 
     299    #define Fortify_ChangeOwner            0 
     300 
     301    #ifdef __cplusplus 
     302        #define Fortify_New                    new 
     303        #define Fortify_Delete                 delete 
    288304    #endif /* __cplusplus */ 
    289305