Changeset 1078 for trunk/dll/fortify.c


Ignore:
Timestamp:
Jul 19, 2008, 6:08:02 AM (17 years ago)
Author:
Steven Levine
Message:

More Fortify infrastructure enhancements
Rework Fortify_SetOwner
Add Fortify_BecomeOwner
Avoid more spurious leak reports

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/dll/fortify.c

    r1077 r1078  
    22/* $Id$ */
    33/* fortify.cxx - A fortified memory allocation shell - V2.2 */
     4 /* vim: tabs 4 */
    45
    56/*
     
    4243
    4344 /* 06 May 08 SHL Rework scope logic to be MT capable
    44     26 May 08 SHL Show TID for leaking scope
    45     17 Jul 08 SHL Add Fortify_SetOwner Fortify_ChangeOwner Fortify_ChangeScope
    46     18 Jul 08 SHL Add FORTIFY_VERBOSE_SCOPE_ENTER_EXIT
     45        26 May 08 SHL Show TID for leaking scope
     46        17 Jul 08 SHL Add Fortify_PresetOwner Fortify_BecomeOwner Fortify_ChangeScope
     47        18 Jul 08 SHL Add FORTIFY_VERBOSE_SCOPE_ENTER_EXIT
     48        18 Jul 08 SHL Add Fortify_SetScope
     49        18 Jul 08 SHL Rename Fortify_ChangeOwner to Fortify_BecomeOwner
     50        18 Jul 08 SHL Add reworked Fortify_SetOwner
    4751 */
    4852
     
    8993struct Header
    9094{
    91     unsigned short Checksum;    /* For the integrity of our goodies  */
    92     const char    *File;        /* The sourcefile of the allocator   */
    93     unsigned long  Line;        /* The sourceline of the allocator   */
    94 #ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
    95     const char    *FreedFile;   /* The sourcefile of the deallocator */
    96     unsigned long  FreedLine;   /* The sourceline of the deallocator */
    97     unsigned char  Deallocator; /* The deallocator used              */
    98 #endif
    99     size_t         Size;        /* The size of the malloc'd block    */
    100     struct Header *Prev;        /* Previous link                     */
    101     struct Header *Next;        /* Next link                         */
    102     char          *Label;       /* User's Label (may be null)        */
    103     unsigned char  Scope;       /* Scope level of the owner          */
    104     unsigned char  Allocator;   /* malloc/realloc/new/etc            */
    105 #   ifdef MT_SCOPES
    106     unsigned short Owner;       /* TID ordinal of block owner        */
    107 #   endif
     95        unsigned short Checksum;    /* For the integrity of our goodies  */
     96        const char    *File;        /* The sourcefile of the allocator   */
     97        unsigned long  Line;        /* The sourceline of the allocator   */
     98#       ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
     99        const char    *FreedFile;   /* The sourcefile of the deallocator */
     100        unsigned long  FreedLine;   /* The sourceline of the deallocator */
     101        unsigned char  Deallocator; /* The deallocator used              */
     102#       endif
     103        size_t         Size;        /* The size of the malloc'd block    */
     104        struct Header *Prev;        /* Previous link                     */
     105        struct Header *Next;        /* Next link                         */
     106        char          *Label;   /* User's Label (may be null)        */
     107        unsigned char  Scope;       /* Scope level of the owner          */
     108        unsigned char  Allocator;   /* malloc/realloc/new/etc            */
     109#       ifdef MT_SCOPES
     110        unsigned short Owner;       /* TID ordinal of block owner        */
     111#       endif
    108112};
    109113
     
    153157#ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
    154158#ifdef FORTIFY_WARN_WHEN_DISCARDING_DEALLOCATED_MEMORY
     159
    155160#ifdef FORTIFY_VERBOSE_WARN_WHEN_DISCARDING_DEALLOCATED_MEMORY
    156     static const char *st_DeallocatedMemoryBlockString(struct Header *h);
     161static const char *st_DeallocatedMemoryBlockString(struct Header *h);
    157162#endif /* FORTIFY_WARN_WHEN_DISCARDING_DEALLOCATED_MEMORY */
     163
    158164#endif /* FORTIFY_VERBOSE_WARN_WHEN_DISCARDING_DEALLOCATED_MEMORY */
    159     static int  st_IsOnDeallocatedList(struct Header *h);
    160     static int st_PurgeDeallocatedBlocks(unsigned long Bytes, const char *file, unsigned long line);
    161     static int st_PurgeDeallocatedScope(unsigned char Scope, const char *file, unsigned long line);
    162     static int st_CheckDeallocatedBlock(struct Header *h, const char *file, unsigned long line);
    163     static void st_FreeDeallocatedBlock(struct Header *h, const char *file, unsigned long line);
     165static int  st_IsOnDeallocatedList(struct Header *h);
     166static int st_PurgeDeallocatedBlocks(unsigned long Bytes, const char *file, unsigned long line);
     167static int st_PurgeDeallocatedScope(unsigned char Scope, const char *file, unsigned long line);
     168static int st_CheckDeallocatedBlock(struct Header *h, const char *file, unsigned long line);
     169static void st_FreeDeallocatedBlock(struct Header *h, const char *file, unsigned long line);
    164170#endif /* FORTIFY_TRACK_DEALLOCATED_MEMORY */
    165171
     
    176182static const char    *st_LastVerifiedFile = "unknown";
    177183static unsigned long  st_LastVerifiedLine;
     184
    178185#ifdef MT_SCOPES
    179186static unsigned volatile st_cOrdinals;          // Number of known threads
     
    183190static unsigned char  st_Scope            = 0;
    184191#endif
     192
    185193static unsigned char  st_Disabled = 0;
    186194
    187195#ifdef __cplusplus
    188     int FORTIFY_STORAGE                 gbl_FortifyMagic = 0;   // 28 Jan 08 SHL
    189     static const    char *st_DeleteFile[FORTIFY_DELETE_STACK_SIZE];
    190     static unsigned long  st_DeleteLine[FORTIFY_DELETE_STACK_SIZE];
    191     static unsigned long  st_DeleteStackTop;
     196int FORTIFY_STORAGE                 gbl_FortifyMagic = 0;       // 28 Jan 08 SHL
     197static const    char *st_DeleteFile[FORTIFY_DELETE_STACK_SIZE];
     198static unsigned long  st_DeleteLine[FORTIFY_DELETE_STACK_SIZE];
     199static unsigned long  st_DeleteStackTop;
    192200#endif /* __cplusplus */
    193201
     
    203211
    204212#ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
    205     static struct Header *st_DeallocatedHead = 0;
    206     static struct Header *st_DeallocatedTail = 0;
    207     static unsigned long  st_TotalDeallocated = 0;
     213static struct Header *st_DeallocatedHead = 0;
     214static struct Header *st_DeallocatedTail = 0;
     215static unsigned long  st_TotalDeallocated = 0;
    208216#endif
    209217
     
    212220static const char *st_AllocatorName[] =
    213221{
    214     "malloc()",
    215     "calloc()",
    216     "realloc()",
    217     "strdup()",
    218     "new",
    219     "new[]"
     222        "malloc()",
     223        "calloc()",
     224        "realloc()",
     225        "strdup()",
     226        "new",
     227        "new[]"
    220228};
    221229
     
    223231static const char *st_DeallocatorName[] =
    224232{
    225     "nobody",
    226     "free()",
    227     "realloc()",
    228     "delete",
    229     "delete[]"
     233        "nobody",
     234        "free()",
     235        "realloc()",
     236        "delete",
     237        "delete[]"
    230238};
    231239
    232240static const unsigned char st_ValidDeallocator[] =
    233241{
    234     (1<<Fortify_Deallocator_free) | (1<<Fortify_Deallocator_realloc),
    235     (1<<Fortify_Deallocator_free) | (1<<Fortify_Deallocator_realloc),
    236     (1<<Fortify_Deallocator_free) | (1<<Fortify_Deallocator_realloc),
    237     (1<<Fortify_Deallocator_free) | (1<<Fortify_Deallocator_realloc),
     242        (1<<Fortify_Deallocator_free) | (1<<Fortify_Deallocator_realloc),
     243        (1<<Fortify_Deallocator_free) | (1<<Fortify_Deallocator_realloc),
     244        (1<<Fortify_Deallocator_free) | (1<<Fortify_Deallocator_realloc),
     245        (1<<Fortify_Deallocator_free) | (1<<Fortify_Deallocator_realloc),
    238246#if defined(FORTIFY_PROVIDE_ARRAY_NEW) && defined(FORTIFY_PROVIDE_ARRAY_DELETE)
    239     (1<<Fortify_Deallocator_delete),
    240     (1<<Fortify_Deallocator_array_delete)
     247        (1<<Fortify_Deallocator_delete),
     248        (1<<Fortify_Deallocator_array_delete)
    241249#else
    242     (1<<Fortify_Deallocator_delete) | (1<<Fortify_Deallocator_array_delete),
    243     (1<<Fortify_Deallocator_delete) | (1<<Fortify_Deallocator_array_delete)
     250        (1<<Fortify_Deallocator_delete) | (1<<Fortify_Deallocator_array_delete),
     251        (1<<Fortify_Deallocator_delete) | (1<<Fortify_Deallocator_array_delete)
    244252#endif
    245253};
     
    252260Fortify_Allocate(size_t size, unsigned char allocator, const char *file, unsigned long line)
    253261{
    254     unsigned char *ptr;
    255     struct Header *h;
    256     int another_try;
     262        unsigned char *ptr;
     263        struct Header *h;
     264        int another_try;
    257265
    258266#ifdef MT_SCOPES
    259     unsigned ordinal;
     267        unsigned ordinal;
    260268#endif
    261269
    262     /*
    263     * If Fortify has been disabled, then it's easy
    264     */
    265     if(st_Disabled)
    266     {
    267 #ifdef FORTIFY_FAIL_ON_ZERO_MALLOC
    268         if(size == 0 && (allocator == Fortify_Allocator_new
    269                       || allocator == Fortify_Allocator_array_new))
     270        /*
     271        * If Fortify has been disabled, then it's easy
     272        */
     273        if(st_Disabled)
     274        {
     275#               ifdef FORTIFY_FAIL_ON_ZERO_MALLOC
     276                if(size == 0 && (allocator == Fortify_Allocator_new
     277                                  || allocator == Fortify_Allocator_array_new))
    270278                {
    271279                        /*
    272280                         * A new of zero bytes must succeed, but a malloc of
    273             * zero bytes probably won't
    274             */
     281                        * zero bytes probably won't
     282                        */
    275283                        return malloc(1);
    276284                }
     285#               endif
     286
     287                return malloc(size);
     288        }
     289
     290#ifdef FORTIFY_CHECK_ALL_MEMORY_ON_ALLOCATE
     291        Fortify_CheckAllMemory(file, line);
    277292#endif
    278293
    279         return malloc(size);
    280     }
    281 
    282 #ifdef FORTIFY_CHECK_ALL_MEMORY_ON_ALLOCATE
    283     Fortify_CheckAllMemory(file, line);
    284 #endif
    285 
    286     if(st_AllocateFailRate > 0)
    287     {
    288         if(rand() % 100 < st_AllocateFailRate)
    289         {
    290 #ifdef FORTIFY_WARN_ON_FALSE_FAIL
    291             sprintf(st_Buffer,
    292                     "\nFortify: A \"%s\" of %lu bytes \"false failed\" at %s.%lu\n",
    293                     st_AllocatorName[allocator], (unsigned long)size, file, line);
    294             st_Output(st_Buffer);
    295 #endif
    296             return(0);
    297         }
    298     }
    299 
    300     /* Check to see if this allocation will
    301      * push us over the artificial limit
    302      */
    303     if(st_CurAllocation + size > st_AllocationLimit)
    304     {
    305 #ifdef FORTIFY_WARN_ON_FALSE_FAIL
    306         sprintf(st_Buffer,
    307                 "\nFortify: A \"%s\" of %lu bytes \"false failed\" at %s.%lu\n",
    308                 st_AllocatorName[allocator], (unsigned long)size, file, line);
    309         st_Output(st_Buffer);
    310 #endif
    311         return(0);
    312     }
     294        if(st_AllocateFailRate > 0)
     295        {
     296                if(rand() % 100 < st_AllocateFailRate)
     297                {
     298#                       ifdef FORTIFY_WARN_ON_FALSE_FAIL
     299                        sprintf(st_Buffer,
     300                                "\nFortify: A \"%s\" of %lu bytes \"false failed\" at %s.%lu\n",
     301                                st_AllocatorName[allocator], (unsigned long)size, file, line);
     302                        st_Output(st_Buffer);
     303#                       endif
     304                        return(0);
     305                }
     306        }
     307
     308        /* Check to see if this allocation will
     309         * push us over the artificial limit
     310         */
     311        if(st_CurAllocation + size > st_AllocationLimit)
     312        {
     313#               ifdef FORTIFY_WARN_ON_FALSE_FAIL
     314                sprintf(st_Buffer,
     315                        "\nFortify: A \"%s\" of %lu bytes \"false failed\" at %s.%lu\n",
     316                        st_AllocatorName[allocator], (unsigned long)size, file, line);
     317                st_Output(st_Buffer);
     318#               endif
     319                return(0);
     320        }
    313321
    314322#ifdef FORTIFY_WARN_ON_ZERO_MALLOC
    315323        if(size == 0 && (allocator == Fortify_Allocator_malloc ||
    316                     allocator == Fortify_Allocator_calloc ||
    317                     allocator == Fortify_Allocator_realloc ))
     324                        allocator == Fortify_Allocator_calloc ||
     325                        allocator == Fortify_Allocator_realloc ))
    318326        {
    319327                sprintf(st_Buffer,
    320                 "\nFortify: A \"%s\" of 0 bytes attempted at %s.%lu\n",
    321                 st_AllocatorName[allocator], file, line);
    322         st_Output(st_Buffer);
     328                                "\nFortify: A \"%s\" of 0 bytes attempted at %s.%lu\n",
     329                                st_AllocatorName[allocator], file, line);
     330                st_Output(st_Buffer);
    323331        }
    324332#endif /* FORTIFY_WARN_ON_ZERO_MALLOC */
     
    326334#ifdef FORTIFY_FAIL_ON_ZERO_MALLOC
    327335        if(size == 0 && (allocator == Fortify_Allocator_malloc ||
    328                     allocator == Fortify_Allocator_calloc ||
    329                     allocator == Fortify_Allocator_realloc ))
     336                        allocator == Fortify_Allocator_calloc ||
     337                        allocator == Fortify_Allocator_realloc ))
    330338        {
    331339#ifdef FORTIFY_WARN_ON_ALLOCATE_FAIL
    332         sprintf(st_Buffer, "\nFortify: A \"%s\" of %lu bytes failed at %s.%lu\n",
    333                 st_AllocatorName[allocator], (unsigned long)size, file, line);
    334         st_Output(st_Buffer);
     340                sprintf(st_Buffer, "\nFortify: A \"%s\" of %lu bytes failed at %s.%lu\n",
     341                                st_AllocatorName[allocator], (unsigned long)size, file, line);
     342                st_Output(st_Buffer);
    335343#endif /* FORTIFY_WARN_ON_ALLOCATE_FAIL */
    336344                return 0;
     
    339347
    340348#ifdef FORTIFY_WARN_ON_SIZE_T_OVERFLOW
    341     /*
    342     * Ensure the size of the memory block
    343     * plus the overhead isn't bigger than
    344     * size_t (that'd be a drag)
    345     */
    346     {
     349        /*
     350        * Ensure the size of the memory block
     351        * plus the overhead isn't bigger than
     352        * size_t (that'd be a drag)
     353        */
     354        {
    347355        size_t private_size = FORTIFY_HEADER_SIZE
    348                             + FORTIFY_ALIGNED_BEFORE_SIZE + size + FORTIFY_AFTER_SIZE;
     356                                + FORTIFY_ALIGNED_BEFORE_SIZE + size + FORTIFY_AFTER_SIZE;
    349357
    350358        if(private_size < size)
    351359        {
    352             sprintf(st_Buffer,
    353                     "\nFortify: A \"%s\" of %lu bytes has overflowed size_t at %s.%lu\n",
    354                     st_AllocatorName[allocator], (unsigned long)size, file, line);
    355             st_Output(st_Buffer);
    356             return(0);
    357         }
    358     }
     360                sprintf(st_Buffer,
     361                        "\nFortify: A \"%s\" of %lu bytes has overflowed size_t at %s.%lu\n",
     362                        st_AllocatorName[allocator], (unsigned long)size, file, line);
     363                st_Output(st_Buffer);
     364                return(0);
     365        }
     366        }
    359367#endif
    360368
    361     another_try = 1;
    362     do
    363     {
    364         /*
    365          * malloc the memory, including the space
    366          * for the header and fortification buffers
    367          */
    368         ptr = (unsigned char *)malloc(  FORTIFY_HEADER_SIZE
    369                                       + FORTIFY_ALIGNED_BEFORE_SIZE
    370                                       + size
    371                                       + FORTIFY_AFTER_SIZE );
    372 
     369        another_try = 1;
     370        do
     371        {
     372                /*
     373                 * malloc the memory, including the space
     374                 * for the header and fortification buffers
     375                 */
     376                ptr = (unsigned char *)malloc(  FORTIFY_HEADER_SIZE
     377                                                  + FORTIFY_ALIGNED_BEFORE_SIZE
     378                                                  + size
     379                                                  + FORTIFY_AFTER_SIZE );
     380
     381#               ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
     382                /*
     383                 * If we're tracking deallocated memory, then
     384                 * we can free some of it, rather than let
     385                 * this malloc fail
     386                 */
     387                if(!ptr)
     388                {
     389                        another_try = st_PurgeDeallocatedBlocks(size, file, line);
     390                }
     391#               endif /* FORTIFY_TRACK_DEALLOCATED_MEMORY */
     392
     393        }
     394        while(!ptr && another_try);
     395
     396        if(!ptr)
     397        {
     398#               ifdef FORTIFY_WARN_ON_ALLOCATE_FAIL
     399                sprintf(st_Buffer, "\nFortify: A \"%s\" of %lu bytes failed at %s.%lu\n",
     400                        st_AllocatorName[allocator], (unsigned long)size, file, line);
     401                st_Output(st_Buffer);
     402#               endif
     403                return(0);
     404        }
     405
     406        /*
     407         * Begin Critical Region
     408         */
     409        FORTIFY_LOCK();
     410
     411
     412        /*
     413         * Make the head's prev pointer point to us
     414         * ('cos we're about to become the head)
     415         */
     416        if(st_AllocatedHead)
     417        {
     418                st_CheckBlock(st_AllocatedHead, file, line);
     419                /* what should we do if this fails? (apart from panic) */
     420
     421                st_AllocatedHead->Prev = (struct Header *)ptr;
     422                st_MakeHeaderValid(st_AllocatedHead);
     423        }
     424
     425#   ifdef MT_SCOPES
     426        ordinal = Get_TID_Ordinal();
     427#   endif
     428
     429        /*
     430         * Initialize and validate the header
     431         */
     432        h = (struct Header *)ptr;
     433        h->Size      = size;
     434        h->File      = file;
     435        h->Line      = line;
     436        h->Next      = st_AllocatedHead;
     437        h->Prev      = 0;
     438#   ifdef MT_SCOPES
     439        h->Owner     = ordinal < st_cOrdinals ? st_pOwners[ordinal] : ordinal;
     440        h->Scope     = h->Owner < st_cOrdinals ? st_pScopes[h->Owner] : 0;
     441#   else
     442        h->Scope     = st_Scope;
     443#   endif
     444        h->Allocator = allocator;
     445        h->Label     = 0;
    373446#ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
    374         /*
    375          * If we're tracking deallocated memory, then
    376          * we can free some of it, rather than let
    377          * this malloc fail
    378          */
    379         if(!ptr)
    380         {
    381             another_try = st_PurgeDeallocatedBlocks(size, file, line);
    382         }
     447        h->FreedFile = 0;
     448        h->FreedLine = 0;
     449        h->Deallocator = Fortify_Deallocator_nobody;
    383450#endif /* FORTIFY_TRACK_DEALLOCATED_MEMORY */
    384 
    385     }
    386     while(!ptr && another_try);
    387 
    388     if(!ptr)
    389     {
    390 #ifdef FORTIFY_WARN_ON_ALLOCATE_FAIL
    391         sprintf(st_Buffer, "\nFortify: A \"%s\" of %lu bytes failed at %s.%lu\n",
    392                 st_AllocatorName[allocator], (unsigned long)size, file, line);
    393         st_Output(st_Buffer);
    394 #endif
    395         return(0);
    396     }
    397 
    398     /*
    399      * Begin Critical Region
    400      */
    401     FORTIFY_LOCK();
    402 
    403 
    404     /*
    405      * Make the head's prev pointer point to us
    406      * ('cos we're about to become the head)
    407      */
    408     if(st_AllocatedHead)
    409     {
    410         st_CheckBlock(st_AllocatedHead, file, line);
    411         /* what should we do if this fails? (apart from panic) */
    412 
    413         st_AllocatedHead->Prev = (struct Header *)ptr;
    414         st_MakeHeaderValid(st_AllocatedHead);
    415     }
    416 
    417 #   ifdef MT_SCOPES
    418     ordinal = Get_TID_Ordinal();
    419     // In case owner overridden by Fortify_SetOwner
    420     if (ordinal < st_cOrdinals)
    421         ordinal = st_pOwners[ordinal];
    422 #   endif
    423 
    424     /*
    425      * Initialize and validate the header
    426      */
    427     h = (struct Header *)ptr;
    428     h->Size      = size;
    429     h->File      = file;
    430     h->Line      = line;
    431     h->Next      = st_AllocatedHead;
    432     h->Prev      = 0;
    433 #   ifdef MT_SCOPES
    434     h->Scope     = ordinal < st_cOrdinals ? st_pScopes[ordinal] : 0;
    435     h->Owner = ordinal;
    436 #   else
    437     h->Scope     = st_Scope;
    438 #   endif
    439     h->Allocator = allocator;
    440     h->Label     = 0;
    441 #ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
    442     h->FreedFile = 0;
    443     h->FreedLine = 0;
    444     h->Deallocator = Fortify_Deallocator_nobody;
    445 #endif /* FORTIFY_TRACK_DEALLOCATED_MEMORY */
    446     st_MakeHeaderValid(h);
    447     st_AllocatedHead = h;
    448 
    449     /*
    450      * Initialize the fortifications
    451      */
    452     st_SetFortification(ptr + FORTIFY_HEADER_SIZE,
    453                      FORTIFY_BEFORE_VALUE, FORTIFY_ALIGNED_BEFORE_SIZE);
    454     st_SetFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE + size,
    455                      FORTIFY_AFTER_VALUE, FORTIFY_AFTER_SIZE);
    456 
    457 #ifdef FORTIFY_FILL_ON_ALLOCATE
    458     /*
    459      * Fill the actual user memory
    460      */
    461     st_SetFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
    462                         FORTIFY_FILL_ON_ALLOCATE_VALUE, size);
    463 #endif
    464 
    465     /*
    466      * End Critical Region
    467      */
    468     FORTIFY_UNLOCK();
    469 
    470 
    471     /*
    472      * update the statistics
    473      */
    474     st_TotalAllocation += size;
    475     st_Allocations++;
    476     st_CurBlocks++;
    477     st_CurAllocation += size;
    478     if(st_CurBlocks > st_MaxBlocks)
    479         st_MaxBlocks = st_CurBlocks;
    480     if(st_CurAllocation > st_MaxAllocation)
    481         st_MaxAllocation = st_CurAllocation;
    482 
    483     /*
    484      * We return the address of the user's memory, not the start of the block,
    485      * which points to our magic cookies
    486      */
    487     return(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE);
     451        st_MakeHeaderValid(h);
     452        st_AllocatedHead = h;
     453
     454        /*
     455         * Initialize the fortifications
     456         */
     457        st_SetFortification(ptr + FORTIFY_HEADER_SIZE,
     458                         FORTIFY_BEFORE_VALUE, FORTIFY_ALIGNED_BEFORE_SIZE);
     459        st_SetFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE + size,
     460                         FORTIFY_AFTER_VALUE, FORTIFY_AFTER_SIZE);
     461
     462#       ifdef FORTIFY_FILL_ON_ALLOCATE
     463        /*
     464         * Fill the actual user memory
     465         */
     466        st_SetFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     467                                                FORTIFY_FILL_ON_ALLOCATE_VALUE, size);
     468#       endif
     469
     470        /*
     471         * End Critical Region
     472         */
     473        FORTIFY_UNLOCK();
     474
     475
     476        /*
     477         * update the statistics
     478         */
     479        st_TotalAllocation += size;
     480        st_Allocations++;
     481        st_CurBlocks++;
     482        st_CurAllocation += size;
     483        if(st_CurBlocks > st_MaxBlocks)
     484                st_MaxBlocks = st_CurBlocks;
     485        if(st_CurAllocation > st_MaxAllocation)
     486                st_MaxAllocation = st_CurAllocation;
     487
     488        /*
     489         * We return the address of the user's memory, not the start of the block,
     490         * which points to our magic cookies
     491         */
     492        return(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE);
    488493}
    489494
     
    496501Fortify_Deallocate(void *uptr, unsigned char deallocator, const char *file, unsigned long line)
    497502{
    498     unsigned char *ptr = (unsigned char *)uptr
     503        unsigned char *ptr = (unsigned char *)uptr
    499504                        - FORTIFY_HEADER_SIZE
    500505                        - FORTIFY_ALIGNED_BEFORE_SIZE;
    501     struct Header *h   = (struct Header *)ptr;
     506        struct Header *h   = (struct Header *)ptr;
     507
     508#       ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
     509#       ifdef MT_SCOPES
     510        unsigned ordinal = Get_TID_Ordinal();
     511#       endif
     512#       endif
     513
     514#       ifdef FORTIFY_CHECK_ALL_MEMORY_ON_DEALLOCATE
     515        Fortify_CheckAllMemory(file, line);
     516#       endif
     517
     518        /*
     519         * If Fortify has been disabled, then it's easy
     520         * (well, almost)
     521         */
     522        if(st_Disabled)
     523        {
     524                /* there is a possibility that this memory
     525                 * block was allocated when Fortify was
     526                 * enabled, so we must check the Allocated
     527                 * list before we free it.
     528                 */
     529                if(!st_IsOnAllocatedList(h))
     530                {
     531                        free(uptr);
     532                        return;
     533                }
     534                else
     535                {
     536                        /* the block was allocated by Fortify, so we
     537                         * gotta free it differently.
     538                         */
     539                        /*
     540                         * Begin critical region
     541                         */
     542                        FORTIFY_LOCK();
     543
     544                        /*
     545                         * Remove the block from the list
     546                         */
     547                        if(h->Prev)
     548                                h->Prev->Next = h->Next;
     549                        else
     550                                st_AllocatedHead = h->Next;
     551
     552                        if(h->Next)
     553                                h->Next->Prev = h->Prev;
     554
     555                        /*
     556                         * End Critical Region
     557                         */
     558                        FORTIFY_UNLOCK();
     559
     560                        /*
     561                         * actually free the memory
     562                         */
     563                        free(ptr);
     564                        return;
     565                }
     566        }
     567
     568
     569#       ifdef FORTIFY_PARANOID_DEALLOCATE
     570        if(!st_IsOnAllocatedList(h))
     571        {
     572#               ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
     573                if(st_IsOnDeallocatedList(h))
     574                {
     575                        sprintf(st_Buffer, "\nFortify: \"%s\" twice of %s detected at %s.%lu\n",
     576                                        st_DeallocatorName[deallocator],
     577                                        st_MemoryBlockString(h), file, line);
     578                        st_Output(st_Buffer);
     579
     580                        sprintf(st_Buffer, "         Memory block was deallocated by \"%s\" at %s.%lu\n",
     581                                        st_DeallocatorName[h->Deallocator], h->FreedFile, h->FreedLine);
     582                        st_Output(st_Buffer);
     583                        st_OutputDeleteTrace();
     584                        return;
     585                }
     586#               endif /* FORTIFY_TRACK_DEALLOCATED_MEMORY */
     587
     588#               ifdef FORTIFY_NO_PERCENT_P
     589                sprintf(st_Buffer, "\nFortify: Possible \"%s\" twice of (0x%08lx) was detected at %s.%lu\n",
     590#               else
     591                sprintf(st_Buffer, "\nFortify: Possible \"%s\" twice of (%p) was detected at %s.%lu\n",
     592#               endif
     593                                st_DeallocatorName[deallocator],
     594                                uptr, file, line);
     595                st_Output(st_Buffer);
     596                st_OutputDeleteTrace();
     597                return;
     598        }
     599#       endif /* FORTIFY_PARANOID_DEALLOCATE */
     600
     601        /*
     602         * Make sure the block is okay before we free it.
     603         * If it's not okay, don't free it - it might not
     604         * be a real memory block. Or worse still, someone
     605         * might still be writing to it
     606         */
     607        if(!st_CheckBlock(h, file, line))
     608        {
     609                st_OutputDeleteTrace();
     610                return;
     611        }
     612
     613#       ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
     614        /*
     615         * Make sure the block hasn't been freed already
     616         * (we can get to here if FORTIFY_PARANOID_DEALLOCATE
     617         * is off, but FORTIFY_TRACK_DEALLOCATED_MEMORY
     618         * is on).
     619         */
     620        if(h->Deallocator != Fortify_Deallocator_nobody)
     621        {
     622                sprintf(st_Buffer, "\nFortify: \"%s\" twice of %s detected at %s.%lu\n",
     623                                st_DeallocatorName[deallocator],
     624                                st_MemoryBlockString(h), file, line);
     625                st_Output(st_Buffer);
     626
     627                sprintf(st_Buffer, "         Memory block was deallocated by \"%s\" at %s.%lu\n",
     628                                st_DeallocatorName[h->Deallocator], h->FreedFile, h->FreedLine);
     629                st_Output(st_Buffer);
     630                st_OutputDeleteTrace();
     631                return;
     632        }
     633#       endif /* FORTIFY_TRACK_DEALLOCATED_MEMORY */
     634
     635        /*
     636         * Make sure the block is being freed with a valid
     637         * deallocator. If not, complain. (but free it anyway)
     638         */
     639        if((st_ValidDeallocator[h->Allocator] & (1<<deallocator)) == 0)
     640        {
     641                sprintf(st_Buffer, "\nFortify: Incorrect deallocator \"%s\" detected at %s.%lu\n",
     642                                st_DeallocatorName[deallocator], file, line);
     643                st_Output(st_Buffer);
     644                sprintf(st_Buffer,   "         %s was allocated with \"%s\"\n",
     645                                st_MemoryBlockString(h), st_AllocatorName[h->Allocator]);
     646                st_Output(st_Buffer);
     647                st_OutputDeleteTrace();
     648        }
     649
     650        /*
     651         * Begin critical region
     652         */
     653        FORTIFY_LOCK();
     654
     655        /*
     656         * Remove the block from the list
     657         */
     658        if(h->Prev)
     659        {
     660                if(!st_CheckBlock(h->Prev, file, line))
     661                {
     662                        FORTIFY_UNLOCK();
     663                        st_OutputDeleteTrace();
     664                        return;
     665                }
     666
     667                h->Prev->Next = h->Next;
     668                st_MakeHeaderValid(h->Prev);
     669        }
     670        else
     671                st_AllocatedHead = h->Next;
     672
     673        if(h->Next)
     674        {
     675                if(!st_CheckBlock(h->Next, file, line))
     676                {
     677                        FORTIFY_UNLOCK();
     678                        st_OutputDeleteTrace();
     679                        return;
     680                }
     681
     682                h->Next->Prev = h->Prev;
     683                st_MakeHeaderValid(h->Next);
     684        }
     685
     686        /*
     687         * End Critical Region
     688         */
     689        FORTIFY_UNLOCK();
     690
     691        /*
     692         * update the statistics
     693         */
     694        st_Frees++;
     695        st_CurBlocks--;
     696        st_CurAllocation -= h->Size;
    502697
    503698#ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
    504699#ifdef MT_SCOPES
    505     unsigned ordinal = Get_TID_Ordinal();
     700        ordinal = Get_TID_Ordinal();
     701        if (ordinal < st_cOrdinals && st_pScopes[ordinal] > 0)
     702#else
     703        if(st_Scope > 0)
    506704#endif
    507 #endif
    508 
    509 #ifdef FORTIFY_CHECK_ALL_MEMORY_ON_DEALLOCATE
    510     Fortify_CheckAllMemory(file, line);
    511 #endif
    512 
    513     /*
    514      * If Fortify has been disabled, then it's easy
    515      * (well, almost)
    516      */
    517     if(st_Disabled)
    518     {
    519         /* there is a possibility that this memory
    520          * block was allocated when Fortify was
    521          * enabled, so we must check the Allocated
    522          * list before we free it.
    523          */
    524         if(!st_IsOnAllocatedList(h))
    525         {
    526             free(uptr);
    527             return;
     705        {
     706                /*
     707                 * Don't _actually_ free the memory block, just yet.
     708                 * Place it onto the deallocated list, instead, so
     709                 * we can check later to see if it's been written to.
     710                 */
     711#               ifdef FORTIFY_FILL_ON_DEALLOCATE
     712                /*
     713                 * Nuke out all user memory that is about to be freed
     714                 */
     715                st_SetFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     716                                                FORTIFY_FILL_ON_DEALLOCATE_VALUE,
     717                                          h->Size);
     718#               endif /* FORTIFY_FILL_ON_DEALLOCATE */
     719
     720                /*
     721                 * Begin critical region
     722                 */
     723                FORTIFY_LOCK();
     724
     725                /*
     726                 * Place the block on the deallocated list
     727                 */
     728                if(st_DeallocatedHead)
     729                {
     730                        st_DeallocatedHead->Prev = (struct Header *)ptr;
     731                        st_MakeHeaderValid(st_DeallocatedHead);
     732                }
     733
     734                h = (struct Header *)ptr;
     735                h->FreedFile   = file;
     736                h->FreedLine   = line;
     737                h->Deallocator = deallocator;
     738                h->Next        = st_DeallocatedHead;
     739                h->Prev        = 0;
     740                st_MakeHeaderValid(h);
     741                st_DeallocatedHead = h;
     742
     743                if(!st_DeallocatedTail)
     744                        st_DeallocatedTail = h;
     745
     746                st_TotalDeallocated += h->Size;
     747
     748#               ifdef FORTIFY_DEALLOCATED_MEMORY_LIMIT
     749                /*
     750                 * If we've got too much on the deallocated list; free some
     751                 */
     752                if(st_TotalDeallocated > FORTIFY_DEALLOCATED_MEMORY_LIMIT)
     753                {
     754                         st_PurgeDeallocatedBlocks(st_TotalDeallocated - FORTIFY_DEALLOCATED_MEMORY_LIMIT, file, line);
     755                }
     756#               endif
     757
     758                /*
     759                 * End critical region
     760                 */
     761                FORTIFY_UNLOCK();
    528762        }
    529763        else
    530         {
    531             /* the block was allocated by Fortify, so we
    532              * gotta free it differently.
    533              */
    534             /*
    535              * Begin critical region
    536              */
    537             FORTIFY_LOCK();
    538 
    539             /*
    540              * Remove the block from the list
    541              */
    542             if(h->Prev)
    543                 h->Prev->Next = h->Next;
    544             else
    545                 st_AllocatedHead = h->Next;
    546 
    547             if(h->Next)
    548                 h->Next->Prev = h->Prev;
    549 
    550             /*
    551              * End Critical Region
    552              */
    553             FORTIFY_UNLOCK();
    554 
    555             /*
    556              * actually free the memory
    557              */
    558             free(ptr);
    559             return;
    560         }
    561     }
    562 
    563 
    564 #ifdef FORTIFY_PARANOID_DEALLOCATE
    565     if(!st_IsOnAllocatedList(h))
    566     {
    567 #ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
    568         if(st_IsOnDeallocatedList(h))
    569         {
    570             sprintf(st_Buffer, "\nFortify: \"%s\" twice of %s detected at %s.%lu\n",
    571                                 st_DeallocatorName[deallocator],
    572                                 st_MemoryBlockString(h), file, line);
    573             st_Output(st_Buffer);
    574 
    575             sprintf(st_Buffer, "         Memory block was deallocated by \"%s\" at %s.%lu\n",
    576                                 st_DeallocatorName[h->Deallocator], h->FreedFile, h->FreedLine);
    577             st_Output(st_Buffer);
    578             st_OutputDeleteTrace();
    579             return;
    580         }
    581 #endif /* FORTIFY_TRACK_DEALLOCATED_MEMORY */
    582 
    583 #ifdef FORTIFY_NO_PERCENT_P
    584         sprintf(st_Buffer, "\nFortify: Possible \"%s\" twice of (0x%08lx) was detected at %s.%lu\n",
    585 #else
    586         sprintf(st_Buffer, "\nFortify: Possible \"%s\" twice of (%p) was detected at %s.%lu\n",
    587 #endif
    588                             st_DeallocatorName[deallocator],
    589                             uptr, file, line);
    590         st_Output(st_Buffer);
    591         st_OutputDeleteTrace();
    592         return;
    593     }
    594 #endif /* FORTIFY_PARANOID_DEALLOCATE */
    595 
    596     /*
    597      * Make sure the block is okay before we free it.
    598      * If it's not okay, don't free it - it might not
    599      * be a real memory block. Or worse still, someone
    600      * might still be writing to it
    601      */
    602     if(!st_CheckBlock(h, file, line))
    603     {
    604         st_OutputDeleteTrace();
    605         return;
    606     }
    607 
    608 #ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
    609     /*
    610      * Make sure the block hasn't been freed already
    611      * (we can get to here if FORTIFY_PARANOID_DEALLOCATE
    612      * is off, but FORTIFY_TRACK_DEALLOCATED_MEMORY
    613      * is on).
    614      */
    615     if(h->Deallocator != Fortify_Deallocator_nobody)
    616     {
    617         sprintf(st_Buffer, "\nFortify: \"%s\" twice of %s detected at %s.%lu\n",
    618                               st_DeallocatorName[deallocator],
    619                             st_MemoryBlockString(h), file, line);
    620         st_Output(st_Buffer);
    621 
    622         sprintf(st_Buffer, "         Memory block was deallocated by \"%s\" at %s.%lu\n",
    623                             st_DeallocatorName[h->Deallocator], h->FreedFile, h->FreedLine);
    624         st_Output(st_Buffer);
    625         st_OutputDeleteTrace();
    626         return;
    627     }
    628 #endif /* FORTIFY_TRACK_DEALLOCATED_MEMORY */
    629 
    630     /*
    631      * Make sure the block is being freed with a valid
    632      * deallocator. If not, complain. (but free it anyway)
    633      */
    634     if((st_ValidDeallocator[h->Allocator] & (1<<deallocator)) == 0)
    635     {
    636         sprintf(st_Buffer, "\nFortify: Incorrect deallocator \"%s\" detected at %s.%lu\n",
    637                               st_DeallocatorName[deallocator], file, line);
    638         st_Output(st_Buffer);
    639         sprintf(st_Buffer,   "         %s was allocated with \"%s\"\n",
    640                               st_MemoryBlockString(h), st_AllocatorName[h->Allocator]);
    641         st_Output(st_Buffer);
    642         st_OutputDeleteTrace();
    643     }
    644 
    645     /*
    646      * Begin critical region
    647      */
    648     FORTIFY_LOCK();
    649 
    650     /*
    651      * Remove the block from the list
    652      */
    653     if(h->Prev)
    654     {
    655         if(!st_CheckBlock(h->Prev, file, line))
    656         {
    657             FORTIFY_UNLOCK();
    658             st_OutputDeleteTrace();
    659             return;
    660         }
    661 
    662         h->Prev->Next = h->Next;
    663         st_MakeHeaderValid(h->Prev);
    664     }
    665     else
    666         st_AllocatedHead = h->Next;
    667 
    668     if(h->Next)
    669     {
    670         if(!st_CheckBlock(h->Next, file, line))
    671         {
    672             FORTIFY_UNLOCK();
    673             st_OutputDeleteTrace();
    674             return;
    675         }
    676 
    677         h->Next->Prev = h->Prev;
    678         st_MakeHeaderValid(h->Next);
    679     }
    680 
    681     /*
    682      * End Critical Region
    683      */
    684     FORTIFY_UNLOCK();
    685 
    686     /*
    687      * update the statistics
    688      */
    689     st_Frees++;
    690     st_CurBlocks--;
    691     st_CurAllocation -= h->Size;
    692 
    693 #ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
    694 #ifdef MT_SCOPES
    695     ordinal = Get_TID_Ordinal();
    696     if (ordinal < st_cOrdinals && st_pScopes[ordinal] > 0)
    697 #else
    698     if(st_Scope > 0)
    699 #endif
    700     {
    701         /*
    702          * Don't _actually_ free the memory block, just yet.
    703          * Place it onto the deallocated list, instead, so
    704          * we can check later to see if it's been written to.
    705          */
    706     #ifdef FORTIFY_FILL_ON_DEALLOCATE
    707         /*
    708          * Nuke out all user memory that is about to be freed
    709          */
    710         st_SetFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
    711                                     FORTIFY_FILL_ON_DEALLOCATE_VALUE,
    712                                   h->Size);
    713     #endif /* FORTIFY_FILL_ON_DEALLOCATE */
    714 
    715         /*
    716          * Begin critical region
    717          */
    718         FORTIFY_LOCK();
    719 
    720         /*
    721          * Place the block on the deallocated list
    722          */
    723         if(st_DeallocatedHead)
    724         {
    725             st_DeallocatedHead->Prev = (struct Header *)ptr;
    726             st_MakeHeaderValid(st_DeallocatedHead);
    727         }
    728 
    729         h = (struct Header *)ptr;
    730         h->FreedFile   = file;
    731         h->FreedLine   = line;
    732         h->Deallocator = deallocator;
    733         h->Next        = st_DeallocatedHead;
    734         h->Prev        = 0;
    735         st_MakeHeaderValid(h);
    736         st_DeallocatedHead = h;
    737 
    738         if(!st_DeallocatedTail)
    739             st_DeallocatedTail = h;
    740 
    741         st_TotalDeallocated += h->Size;
    742 
    743     #ifdef FORTIFY_DEALLOCATED_MEMORY_LIMIT
    744         /*
    745          * If we've got too much on the deallocated list; free some
    746          */
    747         if(st_TotalDeallocated > FORTIFY_DEALLOCATED_MEMORY_LIMIT)
    748         {
    749              st_PurgeDeallocatedBlocks(st_TotalDeallocated - FORTIFY_DEALLOCATED_MEMORY_LIMIT, file, line);
    750         }
    751     #endif
    752 
    753         /*
    754          * End critical region
    755          */
    756         FORTIFY_UNLOCK();
    757     }
    758     else
    759 #endif /* FORTIFY_TRACK_DEALLOCATED_MEMORY */
    760     {
     764#       endif /* FORTIFY_TRACK_DEALLOCATED_MEMORY */
     765        {
    761766                /*
    762767                 * Free the User Label
     
    767772                }
    768773
    769 #ifdef FORTIFY_FILL_ON_DEALLOCATE
    770         /*
    771         * Nuke out all memory that is about to be freed, including the header
    772         */
    773         st_SetFortification(ptr, FORTIFY_FILL_ON_DEALLOCATE_VALUE,
    774                               FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE + h->Size + FORTIFY_AFTER_SIZE);
    775 #endif /* FORTIFY_FILL_ON_DEALLOCATE */
    776 
    777         /*
    778         * And do the actual free
    779         */
    780         free(ptr);
    781     }
     774#               ifdef FORTIFY_FILL_ON_DEALLOCATE
     775                /*
     776                * Nuke out all memory that is about to be freed, including the header
     777                */
     778                st_SetFortification(ptr, FORTIFY_FILL_ON_DEALLOCATE_VALUE,
     779                                          FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE + h->Size + FORTIFY_AFTER_SIZE);
     780#               endif /* FORTIFY_FILL_ON_DEALLOCATE */
     781
     782                /*
     783                * And do the actual free
     784                */
     785                free(ptr);
     786        }
    782787}
    783788
     
    787792 * with a string provided by the user. This function
    788793 * takes a copy of the passed in string.
    789  * The pointer MUST be one returned by a Fortify
     794 * The block MUST be one returned by a Fortify
    790795 * allocation function.
    791796 */
     
    796801        {
    797802                unsigned char *ptr = (unsigned char *)uptr
    798                               - FORTIFY_HEADER_SIZE - FORTIFY_ALIGNED_BEFORE_SIZE;
     803                                  - FORTIFY_HEADER_SIZE - FORTIFY_ALIGNED_BEFORE_SIZE;
    799804                struct Header *h = (struct Header *)ptr;
    800805
     
    830835Fortify_CheckPointer(void *uptr, const char *file, unsigned long line)
    831836{
    832     unsigned char *ptr = (unsigned char *)uptr
    833                               - FORTIFY_HEADER_SIZE - FORTIFY_ALIGNED_BEFORE_SIZE;
    834     struct Header *h = (struct Header *)ptr;
    835     int r;
    836 
    837     if(st_Disabled)
     837        unsigned char *ptr = (unsigned char *)uptr
     838                                  - FORTIFY_HEADER_SIZE - FORTIFY_ALIGNED_BEFORE_SIZE;
     839        struct Header *h = (struct Header *)ptr;
     840        int r;
     841
     842        if(st_Disabled)
    838843        return 1;
    839844
    840     FORTIFY_LOCK();
    841 
    842     if(!st_IsOnAllocatedList(h))
    843     {
    844 #ifdef FORTIFY_NO_PERCENT_P
    845         sprintf(st_Buffer, "\nFortify: Invalid pointer (0x%08lx) detected at %s.%lu\n",
    846 #else
    847         sprintf(st_Buffer, "\nFortify: Invalid pointer (%p) detected at %s.%lu\n",
     845        FORTIFY_LOCK();
     846
     847        if(!st_IsOnAllocatedList(h))
     848        {
     849#               ifdef FORTIFY_NO_PERCENT_P
     850                sprintf(st_Buffer, "\nFortify: Invalid pointer (0x%08lx) detected at %s.%lu\n",
     851                                uptr, file, line);
     852#               else
     853                sprintf(st_Buffer, "\nFortify: Invalid pointer (%p) detected at %s.%lu\n",
     854                                uptr, file, line);
     855#               endif
     856                st_Output(st_Buffer);
     857                FORTIFY_UNLOCK();
     858                return(0);
     859        }
     860
     861#ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
     862        if(st_IsOnDeallocatedList(h))
     863        {
     864#               ifdef FORTIFY_NO_PERCENT_P
     865                sprintf(st_Buffer, "\nFortify: Deallocated pointer (0x%08lx) detected at %s.%lu\n",
     866                                uptr, file, line);
     867#               else
     868                sprintf(st_Buffer, "\nFortify: Deallocated pointer (%p) detected at %s.%lu\n",
     869                                uptr, file, line);
     870#               endif
     871                st_Output(st_Buffer);
     872                sprintf(st_Buffer, "         Memory block was deallocated by \"%s\" at %s.%lu\n",
     873                                st_DeallocatorName[h->Deallocator], h->FreedFile, h->FreedLine);
     874                st_Output(st_Buffer);
     875                FORTIFY_UNLOCK();
     876                return(0);
     877        }
    848878#endif
    849                                  uptr, file, line);
    850         st_Output(st_Buffer);
     879
     880        r = st_CheckBlock(h, file, line);
    851881        FORTIFY_UNLOCK();
    852         return(0);
    853     }
    854 
    855 #ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
    856     if(st_IsOnDeallocatedList(h))
    857     {
    858 #ifdef FORTIFY_NO_PERCENT_P
    859         sprintf(st_Buffer, "\nFortify: Deallocated pointer (0x%08lx) detected at %s.%lu\n",
    860 #else
    861         sprintf(st_Buffer, "\nFortify: Deallocated pointer (%p) detected at %s.%lu\n",
    862 #endif
    863                            uptr, file, line);
    864         st_Output(st_Buffer);
    865         sprintf(st_Buffer, "         Memory block was deallocated by \"%s\" at %s.%lu\n",
    866                            st_DeallocatorName[h->Deallocator], h->FreedFile, h->FreedLine);
    867         st_Output(st_Buffer);
    868         FORTIFY_UNLOCK();
    869         return(0);
    870     }
    871 #endif
    872 
    873     r = st_CheckBlock(h, file, line);
    874     FORTIFY_UNLOCK();
    875     return r;
     882        return r;
    876883}
    877884
     
    887894Fortify_SetOutputFunc(Fortify_OutputFuncPtr Output)
    888895{
    889     Fortify_OutputFuncPtr Old = st_Output;
    890 
    891     st_Output = Output;
    892 
    893     return(Old);
     896        Fortify_OutputFuncPtr Old = st_Output;
     897
     898        st_Output = Output;
     899
     900        return(Old);
    894901}
    895902
     
    905912Fortify_SetAllocateFailRate(int Percent)
    906913{
    907     int Old = st_AllocateFailRate;
    908 
    909     st_AllocateFailRate = Percent;
    910 
    911     return(Old);
     914        int Old = st_AllocateFailRate;
     915
     916        st_AllocateFailRate = Percent;
     917
     918        return(Old);
    912919}
    913920
     
    924931Fortify_CheckAllMemory(const char *file, unsigned long line)
    925932{
    926     struct Header *curr = st_AllocatedHead;
    927     unsigned long count = 0;
    928 
    929     if(st_Disabled)
    930         return 0;
    931 
    932     FORTIFY_LOCK();
    933 
    934     /*
    935     * Check the allocated memory
    936     */
    937     while(curr)
    938     {
    939         if(!st_CheckBlock(curr, file, line))
    940             count++;
    941 
    942         curr = curr->Next;
    943     }
    944 
    945     /*
    946     * Check the deallocated memory while you're at it
    947     */
    948 #ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
    949     curr = st_DeallocatedHead;
    950     while(curr)
    951     {
    952         if(!st_CheckDeallocatedBlock(curr, file, line))
    953             count++;
    954 
    955         curr = curr->Next;
    956     }
    957 #endif
    958 
    959     /*
    960     * If we know where we are, and everything is cool,
    961     * remember that. It might be important.
    962     */
    963     if(file && count == 0)
    964     {
    965         st_LastVerifiedFile = file;
    966         st_LastVerifiedLine = line;
    967     }
    968 
    969     FORTIFY_UNLOCK();
    970     return(count);
     933        struct Header *curr = st_AllocatedHead;
     934        unsigned long count = 0;
     935
     936        if(st_Disabled)
     937                return 0;
     938
     939        FORTIFY_LOCK();
     940
     941        /*
     942        * Check the allocated memory
     943        */
     944        while(curr)
     945        {
     946                if(!st_CheckBlock(curr, file, line))
     947                        count++;
     948
     949                curr = curr->Next;
     950        }
     951
     952        /*
     953        * Check the deallocated memory while you're at it
     954        */
     955#       ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
     956        curr = st_DeallocatedHead;
     957        while(curr)
     958        {
     959                if(!st_CheckDeallocatedBlock(curr, file, line))
     960                        count++;
     961
     962                curr = curr->Next;
     963        }
     964#       endif
     965
     966        /*
     967        * If we know where we are, and everything is cool,
     968        * remember that. It might be important.
     969        */
     970        if(file && count == 0)
     971        {
     972                st_LastVerifiedFile = file;
     973                st_LastVerifiedLine = line;
     974        }
     975
     976        FORTIFY_UNLOCK();
     977        return(count);
    971978}
    972979
     
    980987{
    981988#ifdef MT_SCOPES
    982     unsigned ordinal = Get_TID_Ordinal();
    983     unsigned i;
    984     unsigned c;
    985 
    986     if (ordinal >= st_cOrdinals) {
    987         // Expand arrays
    988         FORTIFY_LOCK();
    989         i = st_cOrdinals;
    990         c = ordinal + 1;
    991         st_pScopes = realloc((void*)st_pScopes, sizeof(*st_pScopes) * c);
    992         st_pOwners = realloc((void*)st_pOwners, sizeof(*st_pOwners) * c);
    993         for (; i <= ordinal; i++) {
    994             st_pScopes[i] = 0;          // Default to scope level 0
    995             st_pOwners[i] = i;          // Default block owner to self
    996         }
    997         st_cOrdinals = c;
    998         FORTIFY_UNLOCK();
    999     }
    1000     i = ++st_pScopes[ordinal];
     989        unsigned ordinal = Get_TID_Ordinal();
     990        unsigned i;
     991        unsigned c;
     992
     993        if (ordinal >= st_cOrdinals) {
     994                // Expand arrays
     995                FORTIFY_LOCK();
     996                i = st_cOrdinals;
     997                c = ordinal + 1;
     998                st_pScopes = realloc((void*)st_pScopes, sizeof(*st_pScopes) * c);
     999                st_pOwners = realloc((void*)st_pOwners, sizeof(*st_pOwners) * c);
     1000                for (; i <= ordinal; i++) {
     1001                        st_pScopes[i] = 0;              // Default to scope level 0
     1002                        st_pOwners[i] = i;              // Default block owner to self
     1003                }
     1004                st_cOrdinals = c;
     1005                FORTIFY_UNLOCK();
     1006        }
     1007        i = ++st_pScopes[ordinal];
    10011008#   ifdef FORTIFY_VERBOSE_SCOPE_ENTER_EXIT
    1002     sprintf(st_Buffer,
    1003             "Fortify: Entering scope %u in TID %u at %s.%lu\n",
    1004             i, ordinal,
    1005             file, line);        // 26 May 08 SHL
    1006     st_Output(st_Buffer);
     1009        sprintf(st_Buffer,
     1010                        "Fortify: Entering scope %u in TID %u at %s.%lu\n",
     1011                        i, ordinal,
     1012                        file, line);    // 26 May 08 SHL
     1013        st_Output(st_Buffer);
    10071014#   endif
    1008     return(i);
     1015        return(i);
    10091016#else
    1010     return(++st_Scope);
     1017        return(++st_Scope);
    10111018#endif
    10121019}
     
    10201027Fortify_LeaveScope(const char *file, unsigned long line)
    10211028{
    1022     struct Header *curr = st_AllocatedHead;
    1023     unsigned long size = 0, count = 0;
    1024 #ifdef MT_SCOPES
    1025     unsigned ordinal;
     1029        struct Header *curr = st_AllocatedHead;
     1030        unsigned long size = 0, count = 0;
     1031#       ifdef MT_SCOPES
     1032        unsigned ordinal;
     1033#       endif
     1034
     1035        if(st_Disabled)
     1036                return 0;
     1037
     1038        FORTIFY_LOCK();
     1039
     1040#       ifdef MT_SCOPES
     1041        // Complain on leave without enter 06 May 08 SHL
     1042        ordinal = Get_TID_Ordinal();
     1043        if (ordinal < st_cOrdinals && st_pScopes[ordinal] > 0) {
     1044                st_pScopes[ordinal]--;
     1045        }
     1046        else {
     1047                sprintf(st_Buffer,
     1048                                "\nFortify: Attempting to leave scope before enter in TID %u at %s.%lu\n",
     1049                                ordinal, file, line);   // 26 May 08 SHL
     1050                st_Output(st_Buffer);
     1051        }
     1052#       else
     1053        if (st_Scope > 0)
     1054                st_Scope--;
     1055        else {
     1056                sprintf(st_Buffer, "\nFortify: Attempting to leave scope before enter at %s.%lu\n", file, line);
     1057                st_Output(st_Buffer);
     1058        }
    10261059#endif
    1027 
    1028     if(st_Disabled)
    1029         return 0;
    1030 
    1031     FORTIFY_LOCK();
    1032 
    1033 #ifdef MT_SCOPES
    1034     // Complain on leave without enter 06 May 08 SHL
    1035     ordinal = Get_TID_Ordinal();
    1036     if (ordinal < st_cOrdinals && st_pScopes[ordinal] > 0) {
    1037         st_pScopes[ordinal]--;
    1038     }
    1039     else {
    1040         sprintf(st_Buffer,
    1041                 "\nFortify: Attempting to leave scope before enter in TID %u at %s.%lu\n",
    1042                 ordinal, file, line);   // 26 May 08 SHL
    1043         st_Output(st_Buffer);
    1044     }
    1045 #else
    1046     if (st_Scope > 0)
    1047         st_Scope--;
    1048     else {
    1049         sprintf(st_Buffer, "\nFortify: Attempting to leave scope before enter at %s.%lu\n", file, line);
    1050         st_Output(st_Buffer);
    1051     }
    1052 #endif
    1053     while(curr)
    1054     {
    1055 #ifdef MT_SCOPES
    1056         if(curr->Owner == ordinal && ordinal < st_cOrdinals && curr->Scope > st_pScopes[ordinal])
    1057 #else
    1058         if(curr->Scope > st_Scope)
    1059 #endif
    1060         {
    1061             if(count == 0)
    1062             {
    1063                 // Report just first occurrance
    1064 #ifdef MT_SCOPES
     1060        while(curr)
     1061        {
     1062#               ifdef MT_SCOPES
     1063                if(curr->Owner == ordinal && ordinal < st_cOrdinals && curr->Scope > st_pScopes[ordinal])
     1064#               else
     1065                if(curr->Scope > st_Scope)
     1066#               endif
     1067                {
     1068                        if(count == 0)
     1069                        {
     1070                                // Output leak report and header just once
     1071#                               ifdef MT_SCOPES
     1072                                sprintf(st_Buffer,
     1073                                        "\nFortify: Memory leak detected leaving scope %d in TID %u at %s.%lu\n",
     1074                                        ordinal < st_cOrdinals ? st_pScopes[ordinal] + 1 : 0,
     1075                                        ordinal,
     1076                                        file, line);
     1077#                               else // not MT_SCOPES
     1078                                sprintf(st_Buffer, "\nFortify: Memory leak detected leaving scope at %s.%lu\n", file, line);
     1079#                               endif
     1080                                st_Output(st_Buffer);
     1081                                sprintf(st_Buffer, "%10s %8s %s\n", "Address", "Size", "Allocator");
     1082                                st_Output(st_Buffer);
     1083                        }
     1084
     1085                        st_OutputHeader(curr);
     1086                        count++;
     1087                        size += curr->Size;
     1088                }
     1089
     1090                curr = curr->Next;
     1091        } // while
     1092
     1093        if(count)
     1094        {
     1095                sprintf(st_Buffer,"%10s %8lu bytes in %lu blocks with %lu bytes overhead\n",
     1096                                "total", size, count, count * FORTIFY_OVERHEAD);
     1097                st_Output(st_Buffer);
     1098        }
     1099#   ifdef FORTIFY_VERBOSE_SCOPE_ENTER_EXIT
     1100        else {
    10651101                sprintf(st_Buffer,
    1066                         "\nFortify: Memory leak detected leaving scope %d in TID %u at %s.%lu\n",
    1067                         ordinal < st_cOrdinals ? st_pScopes[ordinal] + 1 : 0,
    1068                         ordinal,
    1069                         file, line);
    1070 #else
    1071                 sprintf(st_Buffer, "\nFortify: Memory leak detected leaving scope at %s.%lu\n", file, line);
    1072 #endif
    1073                 st_Output(st_Buffer);
    1074                 sprintf(st_Buffer, "%10s %8s %s\n", "Address", "Size", "Allocator");
    1075                 st_Output(st_Buffer);
    1076             }
    1077 
    1078             st_OutputHeader(curr);
    1079             count++;
    1080             size += curr->Size;
    1081         }
    1082 
    1083         curr = curr->Next;
    1084     }
    1085 
    1086     if(count)
    1087     {
    1088         sprintf(st_Buffer,"%10s %8lu bytes in %lu blocks with %lu bytes overhead\n",
    1089                 "total", size, count, count * FORTIFY_OVERHEAD);
    1090         st_Output(st_Buffer);
    1091     }
    1092 #   ifdef FORTIFY_VERBOSE_SCOPE_ENTER_EXIT
    1093     else {
    1094         sprintf(st_Buffer,
    1095                 "Fortify: Leaving scope %u in TID %u at %s.%lu\n",
    1096                 ordinal < st_cOrdinals ? st_pScopes[ordinal] + 1 : 0,
    1097                 ordinal,
    1098                 file, line);    // 26 May 08 SHL
    1099         st_Output(st_Buffer);
    1100     }
     1102                                "Fortify: Leaving scope %u in TID %u at %s.%lu\n",
     1103                                ordinal < st_cOrdinals ? st_pScopes[ordinal] + 1 : 0,
     1104                                ordinal,
     1105                                file, line);    // 26 May 08 SHL
     1106                st_Output(st_Buffer);
     1107        }
    11011108#   endif
    11021109
    1103 #ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
    1104     /*
    1105     * Quietly free all the deallocated memory
    1106     * that was allocated in this scope that
    1107     * we are still tracking
    1108     */
    1109 #ifdef MT_SCOPES
    1110     st_PurgeDeallocatedScope( ordinal < st_cOrdinals ? st_pScopes[ordinal] : 0,
    1111                               file, line );
    1112 #else
    1113     st_PurgeDeallocatedScope( st_Scope, file, line );
    1114 #endif
    1115 #endif /* FORTIFY_TRACK_DEALLOCATED_MEMORY */
    1116 
    1117     FORTIFY_UNLOCK();
    1118 #ifdef MT_SCOPES
    1119     return(ordinal < st_cOrdinals ? st_pScopes[ordinal] : 0);
    1120 #else
    1121     return(st_Scope);
    1122 #endif
     1110#       ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
     1111        /*
     1112        * Quietly free all the deallocated memory
     1113        * that was allocated in this scope that
     1114        * we are still tracking
     1115        */
     1116#       ifdef MT_SCOPES
     1117        st_PurgeDeallocatedScope( ordinal < st_cOrdinals ? st_pScopes[ordinal] : 0,
     1118                                  file, line );
     1119#       else
     1120        st_PurgeDeallocatedScope( st_Scope, file, line );
     1121#       endif
     1122#       endif /* FORTIFY_TRACK_DEALLOCATED_MEMORY */
     1123
     1124        FORTIFY_UNLOCK();
     1125#       ifdef MT_SCOPES
     1126        return(ordinal < st_cOrdinals ? st_pScopes[ordinal] : 0);
     1127#       else
     1128        return(st_Scope);
     1129#       endif
    11231130}
    11241131
     
    11391146Fortify_ListAllMemory(const char *file, unsigned long line)
    11401147{
    1141     struct Header *curr = st_AllocatedHead;
    1142     unsigned long size = 0, count = 0;
    1143 
    1144     if(st_Disabled)
    1145         return 0;
    1146 
    1147     Fortify_CheckAllMemory(file, line);
    1148 
    1149     FORTIFY_LOCK();
    1150 
    1151     if(curr)
    1152     {
    1153         sprintf(st_Buffer, "\nFortify: Memory List at %s.%lu\n", file, line);
    1154         st_Output(st_Buffer);
    1155         sprintf(st_Buffer, "%10s %8s %s\n", "Address", "Size", "Allocator");
    1156         st_Output(st_Buffer);
    1157 
    1158         while(curr)
    1159         {
    1160             st_OutputHeader(curr);
    1161             count++;
    1162             size += curr->Size;
    1163             curr = curr->Next;
    1164         }
    1165 
    1166         sprintf(st_Buffer, "%10s %8lu bytes in %lu blocks and %lu bytes overhead\n",
    1167                            "total", size, count, count * FORTIFY_OVERHEAD);
    1168         st_Output(st_Buffer);
    1169     }
    1170 
    1171     FORTIFY_UNLOCK();
    1172     return(count);
     1148        struct Header *curr = st_AllocatedHead;
     1149        unsigned long size = 0, count = 0;
     1150
     1151        if(st_Disabled)
     1152                return 0;
     1153
     1154        Fortify_CheckAllMemory(file, line);
     1155
     1156        FORTIFY_LOCK();
     1157
     1158        if(curr)
     1159        {
     1160                sprintf(st_Buffer, "\nFortify: Memory List at %s.%lu\n", file, line);
     1161                st_Output(st_Buffer);
     1162                sprintf(st_Buffer, "%10s %8s %s\n", "Address", "Size", "Allocator");
     1163                st_Output(st_Buffer);
     1164
     1165                while(curr)
     1166                {
     1167                        st_OutputHeader(curr);
     1168                        count++;
     1169                        size += curr->Size;
     1170                        curr = curr->Next;
     1171                }
     1172
     1173                sprintf(st_Buffer, "%10s %8lu bytes in %lu blocks and %lu bytes overhead\n",
     1174                                "total", size, count, count * FORTIFY_OVERHEAD);
     1175                st_Output(st_Buffer);
     1176        }
     1177
     1178        FORTIFY_UNLOCK();
     1179        return(count);
    11731180}
    11741181
     
    11851192Fortify_DumpAllMemory(const char *file, unsigned long line)
    11861193{
    1187     struct Header *curr = st_AllocatedHead;
    1188     unsigned long count = 0;
    1189 
    1190     if(st_Disabled)
    1191         return 0;
    1192 
    1193     Fortify_CheckAllMemory(file, line);
    1194 
    1195     FORTIFY_LOCK();
    1196 
    1197     while(curr)
    1198     {
    1199         sprintf(st_Buffer, "\nFortify: Hex Dump of %s at %s.%lu\n",
    1200                 st_MemoryBlockString(curr), file, line);
    1201         st_Output(st_Buffer);
    1202         st_OutputMemory(curr);
    1203         st_Output("\n");
    1204         count++;
    1205 
    1206         curr = curr->Next;
    1207     }
    1208 
    1209     FORTIFY_UNLOCK();
    1210     return(count);
     1194        struct Header *curr = st_AllocatedHead;
     1195        unsigned long count = 0;
     1196
     1197        if(st_Disabled)
     1198                return 0;
     1199
     1200        Fortify_CheckAllMemory(file, line);
     1201
     1202        FORTIFY_LOCK();
     1203
     1204        while(curr)
     1205        {
     1206                sprintf(st_Buffer, "\nFortify: Hex Dump of %s at %s.%lu\n",
     1207                                st_MemoryBlockString(curr), file, line);
     1208                st_Output(st_Buffer);
     1209                st_OutputMemory(curr);
     1210                st_Output("\n");
     1211                count++;
     1212
     1213                curr = curr->Next;
     1214        }
     1215
     1216        FORTIFY_UNLOCK();
     1217        return(count);
    12111218}
    12121219
     
    12181225Fortify_OutputStatistics(const char *file, unsigned long line)
    12191226{
    1220     if(st_Disabled)
    1221         return;
    1222 
    1223     sprintf(st_Buffer, "\nFortify: Statistics at %s.%lu\n", file, line);
    1224     st_Output(st_Buffer);
    1225 
    1226     sprintf(st_Buffer, "         Memory currently allocated: %lu bytes in %lu blocks\n",
     1227        if(st_Disabled)
     1228                return;
     1229
     1230        sprintf(st_Buffer, "\nFortify: Statistics at %s.%lu\n", file, line);
     1231        st_Output(st_Buffer);
     1232
     1233        sprintf(st_Buffer, "         Memory currently allocated: %lu bytes in %lu blocks\n",
    12271234                                 st_CurAllocation, st_CurBlocks);
    1228     st_Output(st_Buffer);
    1229     sprintf(st_Buffer, "         Maximum memory allocated at one time: %lu bytes in %lu blocks\n",
     1235        st_Output(st_Buffer);
     1236        sprintf(st_Buffer, "         Maximum memory allocated at one time: %lu bytes in %lu blocks\n",
    12301237                                 st_MaxAllocation, st_MaxBlocks);
    1231     st_Output(st_Buffer);
    1232     sprintf(st_Buffer, "         There have been %lu allocations and %lu deallocations\n",
     1238        st_Output(st_Buffer);
     1239        sprintf(st_Buffer, "         There have been %lu allocations and %lu deallocations\n",
    12331240                                 st_Allocations, st_Frees);
    1234     st_Output(st_Buffer);
    1235     sprintf(st_Buffer, "         There was a total of %lu bytes allocated\n",
     1241        st_Output(st_Buffer);
     1242        sprintf(st_Buffer, "         There was a total of %lu bytes allocated\n",
    12361243                                 st_TotalAllocation);
    1237     st_Output(st_Buffer);
    1238 
    1239     if(st_Allocations > 0)
    1240     {
    1241         sprintf(st_Buffer, "         The average allocation was %lu bytes\n",
    1242                                      st_TotalAllocation / st_Allocations);
    12431244        st_Output(st_Buffer);
    1244     }
     1245
     1246        if(st_Allocations > 0)
     1247        {
     1248                sprintf(st_Buffer, "         The average allocation was %lu bytes\n",
     1249                                st_TotalAllocation / st_Allocations);
     1250                st_Output(st_Buffer);
     1251        }
    12451252}
    12461253
     
    12511258Fortify_GetCurrentAllocation(const char *file, unsigned long line)
    12521259{
    1253     if(st_Disabled)
    1254         return 0;
    1255 
    1256     return st_CurAllocation;
     1260        if(st_Disabled)
     1261                return 0;
     1262
     1263        return st_CurAllocation;
    12571264}
    12581265
     
    12631270Fortify_SetAllocationLimit(unsigned long NewLimit, const char *file, unsigned long line)
    12641271{
    1265     st_AllocationLimit = NewLimit;
     1272        st_AllocationLimit = NewLimit;
    12661273}
    12671274
     
    12811288Fortify_Disable(const char *file, unsigned long line)
    12821289{
    1283 #ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
    1284     /* free all deallocated memory we might be tracking */
    1285     st_PurgeDeallocatedScope( 0, file, line );
    1286 #endif /* FORTIFY_TRACK_DEALLOCATED_MEMORY */
    1287 
    1288     st_Disabled = 1;
     1290#       ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
     1291        /* free all deallocated memory we might be tracking */
     1292        st_PurgeDeallocatedScope( 0, file, line );
     1293#       endif /* FORTIFY_TRACK_DEALLOCATED_MEMORY */
     1294
     1295        st_Disabled = 1;
    12891296}
    12901297
     
    12981305st_CheckBlock(struct Header *h, const char *file, unsigned long line)
    12991306{
    1300     unsigned char *ptr = (unsigned char *)h;
    1301     int result = 1;
    1302 
    1303     if(!st_IsHeaderValid(h))
    1304     {
    1305         sprintf(st_Buffer,
    1306 #ifdef FORTIFY_NO_PERCENT_P
    1307                 "\nFortify: Invalid pointer (0x%08lx) or corrupted header detected at %s.%lu\n",
    1308 #else
    1309                 "\nFortify: Invalid pointer (%p) or corrupted header detected at %s.%lu\n",
    1310 #endif
    1311                 ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE, file, line);
    1312         st_Output(st_Buffer);
    1313         st_OutputLastVerifiedPoint();
    1314         return(0);
    1315     }
    1316 
    1317     if(!st_CheckFortification(ptr + FORTIFY_HEADER_SIZE,
     1307        unsigned char *ptr = (unsigned char *)h;
     1308        int result = 1;
     1309
     1310        if(!st_IsHeaderValid(h))
     1311        {
     1312#               ifdef FORTIFY_NO_PERCENT_P
     1313                sprintf(st_Buffer,
     1314                                "\nFortify: Invalid pointer (0x%08lx) or corrupted header detected at %s.%lu\n",
     1315                                ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE, file, line);
     1316#               else
     1317                sprintf(st_Buffer,
     1318                                "\nFortify: Invalid pointer (%p) or corrupted header detected at %s.%lu\n",
     1319                                ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE, file, line);
     1320#               endif
     1321                st_Output(st_Buffer);
     1322                st_OutputLastVerifiedPoint();
     1323                return(0);
     1324        }
     1325
     1326        if(!st_CheckFortification(ptr + FORTIFY_HEADER_SIZE,
    13181327                           FORTIFY_BEFORE_VALUE, FORTIFY_ALIGNED_BEFORE_SIZE))
    1319     {
    1320         sprintf(st_Buffer, "\nFortify: Underwrite detected before block %s at %s.%lu\n",
    1321                            st_MemoryBlockString(h), file, line);
    1322         st_Output(st_Buffer);
    1323 
    1324         st_OutputLastVerifiedPoint();
    1325         st_OutputFortification(ptr + FORTIFY_HEADER_SIZE,
    1326                             FORTIFY_BEFORE_VALUE, FORTIFY_ALIGNED_BEFORE_SIZE);
    1327         result = 0;
    1328 
    1329 #ifdef FORTIFY_FILL_ON_CORRUPTION
    1330         st_SetFortification(ptr + FORTIFY_HEADER_SIZE, FORTIFY_BEFORE_VALUE, FORTIFY_ALIGNED_BEFORE_SIZE);
    1331 #endif
    1332     }
    1333 
    1334     if(!st_CheckFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE + h->Size,
     1328        {
     1329                sprintf(st_Buffer, "\nFortify: Underwrite detected before block %s at %s.%lu\n",
     1330                                st_MemoryBlockString(h), file, line);
     1331                st_Output(st_Buffer);
     1332
     1333                st_OutputLastVerifiedPoint();
     1334                st_OutputFortification(ptr + FORTIFY_HEADER_SIZE,
     1335                                                           FORTIFY_BEFORE_VALUE, FORTIFY_ALIGNED_BEFORE_SIZE);
     1336                result = 0;
     1337
     1338#               ifdef FORTIFY_FILL_ON_CORRUPTION
     1339                st_SetFortification(ptr + FORTIFY_HEADER_SIZE, FORTIFY_BEFORE_VALUE, FORTIFY_ALIGNED_BEFORE_SIZE);
     1340#               endif
     1341        }
     1342
     1343        if(!st_CheckFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE + h->Size,
    13351344                           FORTIFY_AFTER_VALUE, FORTIFY_AFTER_SIZE))
    1336     {
    1337         sprintf(st_Buffer, "\nFortify: Overwrite detected after block %s at %s.%lu\n",
    1338                            st_MemoryBlockString(h), file, line);
    1339         st_Output(st_Buffer);
    1340 
    1341         st_OutputLastVerifiedPoint();
    1342         st_OutputFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE + h->Size,
    1343                             FORTIFY_AFTER_VALUE, FORTIFY_AFTER_SIZE);
    1344         result = 0;
    1345 
    1346 #ifdef FORTIFY_FILL_ON_CORRUPTION
    1347         st_SetFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE + h->Size,
    1348                          FORTIFY_AFTER_VALUE, FORTIFY_AFTER_SIZE);
    1349 #endif
    1350     }
    1351 
    1352     return(result);
     1345        {
     1346                sprintf(st_Buffer, "\nFortify: Overwrite detected after block %s at %s.%lu\n",
     1347                                st_MemoryBlockString(h), file, line);
     1348                st_Output(st_Buffer);
     1349
     1350                st_OutputLastVerifiedPoint();
     1351                st_OutputFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE + h->Size,
     1352                                                           FORTIFY_AFTER_VALUE, FORTIFY_AFTER_SIZE);
     1353                result = 0;
     1354
     1355#               ifdef FORTIFY_FILL_ON_CORRUPTION
     1356                st_SetFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE + h->Size,
     1357                                                        FORTIFY_AFTER_VALUE, FORTIFY_AFTER_SIZE);
     1358#               endif
     1359        }
     1360
     1361        return(result);
    13531362}
    13541363
     
    13621371st_CheckDeallocatedBlock(struct Header *h, const char *file, unsigned long line)
    13631372{
    1364     unsigned char *ptr = (unsigned char *)h;
    1365     int result = 1;
    1366 
    1367     if(!st_IsHeaderValid(h))
    1368     {
    1369         sprintf(st_Buffer,
     1373        unsigned char *ptr = (unsigned char *)h;
     1374        int result = 1;
     1375
     1376        if(!st_IsHeaderValid(h))
     1377        {
    13701378#ifdef FORTIFY_NO_PERCENT_P
    1371                 "\nFortify: Invalid deallocated pointer (0x%08lx) or corrupted header detected at %s.%lu\n",
     1379                sprintf(st_Buffer,
     1380                                "\nFortify: Invalid deallocated pointer (0x%08lx) or corrupted header detected at %s.%lu\n",
     1381                                ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE, file, line);
    13721382#else
    1373                 "\nFortify: Invalid deallocated pointer (%p) or corrupted header detected at %s.%lu\n",
     1383                sprintf(st_Buffer,
     1384                                "\nFortify: Invalid deallocated pointer (%p) or corrupted header detected at %s.%lu\n",
     1385                                ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE, file, line);
    13741386#endif
    1375                 ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE, file, line);
    1376         st_Output(st_Buffer);
    1377         st_OutputLastVerifiedPoint();
    1378         return(0);
    1379     }
    1380 
    1381     if(!st_CheckFortification(ptr + FORTIFY_HEADER_SIZE,
    1382                            FORTIFY_BEFORE_VALUE, FORTIFY_ALIGNED_BEFORE_SIZE))
    1383     {
    1384         sprintf(st_Buffer, "\nFortify: Underwrite detected before deallocated block %s at %s.%lu\n",
    1385                            st_MemoryBlockString(h), file, line);
    1386         st_Output(st_Buffer);
    1387         sprintf(st_Buffer, "         Memory block was deallocated by \"%s\" at %s.%lu\n",
    1388                            st_DeallocatorName[h->Deallocator], h->FreedFile, h->FreedLine);
    1389         st_Output(st_Buffer);
    1390 
    1391         st_OutputLastVerifiedPoint();
    1392         st_OutputFortification(ptr + FORTIFY_HEADER_SIZE,
    1393                             FORTIFY_BEFORE_VALUE, FORTIFY_ALIGNED_BEFORE_SIZE);
    1394 
    1395 #ifdef FORTIFY_FILL_ON_CORRUPTION
    1396         st_SetFortification(ptr + FORTIFY_HEADER_SIZE, FORTIFY_BEFORE_VALUE, FORTIFY_ALIGNED_BEFORE_SIZE);
    1397 #endif
    1398         result = 0;
    1399     }
    1400 
    1401     if(!st_CheckFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE + h->Size,
     1387                st_Output(st_Buffer);
     1388                st_OutputLastVerifiedPoint();
     1389                return(0);
     1390        }
     1391
     1392        if(!st_CheckFortification(ptr + FORTIFY_HEADER_SIZE,
     1393                                                          FORTIFY_BEFORE_VALUE, FORTIFY_ALIGNED_BEFORE_SIZE))
     1394        {
     1395                sprintf(st_Buffer, "\nFortify: Underwrite detected before deallocated block %s at %s.%lu\n",
     1396                                st_MemoryBlockString(h), file, line);
     1397                st_Output(st_Buffer);
     1398                sprintf(st_Buffer, "         Memory block was deallocated by \"%s\" at %s.%lu\n",
     1399                                st_DeallocatorName[h->Deallocator], h->FreedFile, h->FreedLine);
     1400                st_Output(st_Buffer);
     1401
     1402                st_OutputLastVerifiedPoint();
     1403                st_OutputFortification(ptr + FORTIFY_HEADER_SIZE,
     1404                                                           FORTIFY_BEFORE_VALUE, FORTIFY_ALIGNED_BEFORE_SIZE);
     1405
     1406#               ifdef FORTIFY_FILL_ON_CORRUPTION
     1407                st_SetFortification(ptr + FORTIFY_HEADER_SIZE, FORTIFY_BEFORE_VALUE, FORTIFY_ALIGNED_BEFORE_SIZE);
     1408#               endif
     1409                result = 0;
     1410        }
     1411
     1412        if(!st_CheckFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE + h->Size,
    14021413                           FORTIFY_AFTER_VALUE, FORTIFY_AFTER_SIZE))
    1403     {
    1404         sprintf(st_Buffer, "\nFortify: Overwrite detected after deallocated block %s at %s.%lu\n",
    1405                            st_MemoryBlockString(h), file, line);
    1406         st_Output(st_Buffer);
    1407         sprintf(st_Buffer, "         Memory block was deallocated by \"%s\" at %s.%lu\n",
    1408                            st_DeallocatorName[h->Deallocator], h->FreedFile, h->FreedLine);
    1409         st_Output(st_Buffer);
    1410 
    1411         st_OutputLastVerifiedPoint();
    1412         st_OutputFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE + h->Size,
    1413                             FORTIFY_AFTER_VALUE, FORTIFY_AFTER_SIZE);
    1414 
    1415 #ifdef FORTIFY_FILL_ON_CORRUPTION
    1416         st_SetFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE + h->Size,
    1417                          FORTIFY_AFTER_VALUE, FORTIFY_AFTER_SIZE);
    1418 #endif
    1419         result = 0;
    1420     }
     1414        {
     1415                sprintf(st_Buffer, "\nFortify: Overwrite detected after deallocated block %s at %s.%lu\n",
     1416                                st_MemoryBlockString(h), file, line);
     1417                st_Output(st_Buffer);
     1418                sprintf(st_Buffer, "         Memory block was deallocated by \"%s\" at %s.%lu\n",
     1419                                st_DeallocatorName[h->Deallocator], h->FreedFile, h->FreedLine);
     1420                st_Output(st_Buffer);
     1421
     1422                st_OutputLastVerifiedPoint();
     1423                st_OutputFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE + h->Size,
     1424                                                           FORTIFY_AFTER_VALUE, FORTIFY_AFTER_SIZE);
     1425
     1426#               ifdef FORTIFY_FILL_ON_CORRUPTION
     1427                st_SetFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE + h->Size,
     1428                                                        FORTIFY_AFTER_VALUE, FORTIFY_AFTER_SIZE);
     1429#               endif
     1430                result = 0;
     1431        }
    14211432
    14221433#ifdef FORTIFY_FILL_ON_DEALLOCATE
    1423     if(!st_CheckFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1434        if(!st_CheckFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
    14241435                           FORTIFY_FILL_ON_DEALLOCATE_VALUE, h->Size))
    1425     {
    1426         sprintf(st_Buffer, "\nFortify: Write to deallocated block %s detected at %s.%lu\n",
    1427                            st_MemoryBlockString(h), file, line);
    1428         st_Output(st_Buffer);
    1429 
    1430         sprintf(st_Buffer, "         Memory block was deallocated by \"%s\" at %s.%lu\n",
    1431                            st_DeallocatorName[h->Deallocator], h->FreedFile, h->FreedLine);
    1432         st_Output(st_Buffer);
    1433         st_OutputLastVerifiedPoint();
    1434 
    1435         st_OutputFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
    1436                             FORTIFY_FILL_ON_DEALLOCATE_VALUE, h->Size);
    1437 
    1438 #ifdef FORTIFY_FILL_ON_CORRUPTION
    1439         st_SetFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
    1440                             FORTIFY_FILL_ON_DEALLOCATE_VALUE, h->Size);
    1441 #endif /* FORTIFY_FILL_ON_CORRUPTION */
    1442         result = 0;
    1443     }
     1436        {
     1437                sprintf(st_Buffer, "\nFortify: Write to deallocated block %s detected at %s.%lu\n",
     1438                                st_MemoryBlockString(h), file, line);
     1439                st_Output(st_Buffer);
     1440
     1441                sprintf(st_Buffer, "         Memory block was deallocated by \"%s\" at %s.%lu\n",
     1442                                st_DeallocatorName[h->Deallocator], h->FreedFile, h->FreedLine);
     1443                st_Output(st_Buffer);
     1444                st_OutputLastVerifiedPoint();
     1445
     1446                st_OutputFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1447                                                           FORTIFY_FILL_ON_DEALLOCATE_VALUE, h->Size);
     1448
     1449#               ifdef FORTIFY_FILL_ON_CORRUPTION
     1450                st_SetFortification(ptr + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1451                                                        FORTIFY_FILL_ON_DEALLOCATE_VALUE, h->Size);
     1452#               endif /* FORTIFY_FILL_ON_CORRUPTION */
     1453                result = 0;
     1454        }
    14441455#endif /* FORTIFY_FILL_ON_DEALLOCATE */
    1445     return result;
     1456        return result;
    14461457 }
    14471458
     
    14571468st_CheckFortification(unsigned char *ptr, unsigned char value, size_t size)
    14581469{
    1459     while(size--)
     1470        while(size--)
    14601471        if(*ptr++ != value)
    1461             return(0);
    1462 
    1463     return(1);
     1472                return(0);
     1473
     1474        return(1);
    14641475}
    14651476
     
    14701481st_SetFortification(unsigned char *ptr, unsigned char value, size_t size)
    14711482{
    1472     memset(ptr, value, size);
     1483        memset(ptr, value, size);
    14731484}
    14741485
     
    14791490st_OutputFortification(unsigned char *ptr, unsigned char value, size_t size)
    14801491{
    1481     size_t offset, skipped, advance;
    1482     offset = 0;
    1483 
    1484     sprintf(st_Buffer, "   Address   Offset Data (%02x)", value);
    1485     st_Output(st_Buffer);
    1486 
    1487     while(offset < size)
    1488     {
    1489         /*
    1490          * Skip 3 or more 'correct' lines
    1491          */
    1492         if((size - offset) < 3 * 16)
    1493             advance = size - offset;
    1494         else
    1495             advance = 3 * 16;
    1496         if(advance > 0 && st_CheckFortification(ptr+offset, value, advance))
    1497         {
    1498             offset += advance;
    1499             skipped = advance;
    1500 
    1501             if(size - offset < 16)
    1502                 advance = size - offset;
    1503             else
    1504                 advance = 16;
    1505 
    1506             while(advance > 0 && st_CheckFortification(ptr+offset, value, advance))
    1507             {
    1508                 offset  += advance;
    1509                 skipped += advance;
    1510                 if(size - offset < 16)
    1511                     advance = size - offset;
     1492        size_t offset, skipped, advance;
     1493        offset = 0;
     1494
     1495        sprintf(st_Buffer, "   Address   Offset Data (%02x)", value);
     1496        st_Output(st_Buffer);
     1497
     1498        while(offset < size)
     1499        {
     1500                /*
     1501                 * Skip 3 or more 'correct' lines
     1502                 */
     1503                if((size - offset) < 3 * 16)
     1504                        advance = size - offset;
    15121505                else
    1513                     advance = 16;
    1514             }
    1515             sprintf(st_Buffer, "\n                        ...%lu bytes skipped...", (unsigned long)skipped);
    1516             st_Output(st_Buffer);
    1517             continue;
    1518         }
    1519         else
    1520         {
    1521             if(size - offset < 16)
    1522                 st_HexDump(ptr, offset, size-offset, 0);
    1523             else
    1524                 st_HexDump(ptr, offset, 16, 0);
    1525 
    1526             offset += 16;
    1527         }
    1528     }
    1529 
    1530     st_Output("\n");
     1506                        advance = 3 * 16;
     1507                if(advance > 0 && st_CheckFortification(ptr+offset, value, advance))
     1508                {
     1509                        offset += advance;
     1510                        skipped = advance;
     1511
     1512                        if(size - offset < 16)
     1513                                advance = size - offset;
     1514                        else
     1515                                advance = 16;
     1516
     1517                        while(advance > 0 && st_CheckFortification(ptr+offset, value, advance))
     1518                        {
     1519                                offset  += advance;
     1520                                skipped += advance;
     1521                                if(size - offset < 16)
     1522                                        advance = size - offset;
     1523                                else
     1524                                        advance = 16;
     1525                        }
     1526                        sprintf(st_Buffer, "\n                        ...%lu bytes skipped...", (unsigned long)skipped);
     1527                        st_Output(st_Buffer);
     1528                        continue;
     1529                }
     1530                else
     1531                {
     1532                        if(size - offset < 16)
     1533                                st_HexDump(ptr, offset, size-offset, 0);
     1534                        else
     1535                                st_HexDump(ptr, offset, 16, 0);
     1536
     1537                        offset += 16;
     1538                }
     1539        }
     1540
     1541        st_Output("\n");
    15311542}
    15321543
     
    15371548st_HexDump(unsigned char *ptr, size_t offset, size_t size, int title)
    15381549{
    1539     char ascii[17];
    1540     int  column;
    1541     int  output;
    1542 
    1543     if(title)
     1550        char ascii[17];
     1551        int  column;
     1552        int  output;
     1553
     1554        if(title)
    15441555        st_Output("   Address   Offset Data");
    15451556
    1546     column = 0;
    1547     ptr += offset;
    1548     output = 0;
    1549 
    1550     while(output < size)
    1551     {
    1552         if(column == 0)
    1553         {
    1554 #ifdef FORTIFY_NO_PERCENT_P
    1555             sprintf(st_Buffer, "\n0x%08lx %8lu ", ptr, (unsigned long)offset);
    1556 #else
    1557             sprintf(st_Buffer, "\n%10p %8lu ", ptr, (unsigned long)offset);
    1558 #endif
    1559             st_Output(st_Buffer);
    1560         }
    1561 
    1562         sprintf(st_Buffer, "%02x%s", *ptr, ((column % 4) == 3) ? " " : "");
    1563         st_Output(st_Buffer);
    1564 
    1565         ascii[ column ] = isprint( *ptr ) ? (char)(*ptr) : (char)('.');
    1566         ascii[ column + 1 ] = '\0';
    1567 
    1568         ptr++;
    1569         offset++;
    1570         output++;
    1571         column++;
    1572 
    1573         if(column == 16)
    1574         {
    1575             st_Output( "   \"" );
    1576             st_Output( ascii );
    1577             st_Output( "\"" );
    1578             column = 0;
    1579         }
    1580     }
    1581 
    1582     if ( column != 0 )
    1583     {
    1584         while ( column < 16 )
    1585         {
    1586             if( column % 4 == 3 )
    1587                 st_Output( "   " );
    1588             else
    1589                 st_Output( "  " );
    1590 
    1591             column++;
    1592         }
    1593         st_Output( "   \"" );
    1594         st_Output( ascii );
    1595         st_Output( "\"" );
    1596     }
     1557        column = 0;
     1558        ptr += offset;
     1559        output = 0;
     1560
     1561        while(output < size)
     1562        {
     1563                if(column == 0)
     1564                {
     1565#                       ifdef FORTIFY_NO_PERCENT_P
     1566                        sprintf(st_Buffer, "\n0x%08lx %8lu ", ptr, (unsigned long)offset);
     1567#                       else
     1568                        sprintf(st_Buffer, "\n%10p %8lu ", ptr, (unsigned long)offset);
     1569#                       endif
     1570                        st_Output(st_Buffer);
     1571                }
     1572
     1573                sprintf(st_Buffer, "%02x%s", *ptr, ((column % 4) == 3) ? " " : "");
     1574                st_Output(st_Buffer);
     1575
     1576                ascii[ column ] = isprint( *ptr ) ? (char)(*ptr) : (char)('.');
     1577                ascii[ column + 1 ] = '\0';
     1578
     1579                ptr++;
     1580                offset++;
     1581                output++;
     1582                column++;
     1583
     1584                if(column == 16)
     1585                {
     1586                        st_Output( "   \"" );
     1587                        st_Output( ascii );
     1588                        st_Output( "\"" );
     1589                        column = 0;
     1590                }
     1591        }
     1592
     1593        if ( column != 0 )
     1594        {
     1595                while ( column < 16 )
     1596                {
     1597                        if( column % 4 == 3 )
     1598                        st_Output( "   " );
     1599                        else
     1600                        st_Output( "  " );
     1601
     1602                        column++;
     1603                }
     1604                st_Output( "   \"" );
     1605                st_Output( ascii );
     1606                st_Output( "\"" );
     1607        }
    15971608}
    15981609
     
    16051616st_IsHeaderValid(struct Header *h)
    16061617{
    1607     return(st_ChecksumHeader(h) == FORTIFY_CHECKSUM_VALUE);
     1618        return(st_ChecksumHeader(h) == FORTIFY_CHECKSUM_VALUE);
    16081619}
    16091620
     
    16151626st_MakeHeaderValid(struct Header *h)
    16161627{
    1617     h->Checksum = 0;
    1618     h->Checksum = (unsigned short)(FORTIFY_CHECKSUM_VALUE - st_ChecksumHeader(h));
     1628        h->Checksum = 0;
     1629        h->Checksum = (unsigned short)(FORTIFY_CHECKSUM_VALUE - st_ChecksumHeader(h));
    16191630}
    16201631
     
    16291640st_ChecksumHeader(struct Header *h)
    16301641{
    1631     unsigned short c, checksum, *p;
    1632 
    1633     for(c = 0, checksum = 0, p = (unsigned short *)h;
    1634         c < FORTIFY_HEADER_SIZE/sizeof(unsigned short); c++)
    1635     {
    1636         checksum += *p++;
    1637     }
    1638 
    1639     return(checksum);
     1642        unsigned short c, checksum, *p;
     1643
     1644        for(c = 0, checksum = 0, p = (unsigned short *)h;
     1645                c < FORTIFY_HEADER_SIZE/sizeof(unsigned short); c++)
     1646        {
     1647                checksum += *p++;
     1648        }
     1649
     1650        return(checksum);
    16401651}
    16411652
     
    16471658st_IsOnAllocatedList(struct Header *h)
    16481659{
    1649     struct Header *curr;
    1650 
    1651     curr = st_AllocatedHead;
    1652     while(curr)
    1653     {
    1654         if(curr == h)
    1655             return(1);
    1656 
    1657         curr = curr->Next;
    1658     }
    1659 
    1660     return(0);
     1660        struct Header *curr;
     1661
     1662        curr = st_AllocatedHead;
     1663        while(curr)
     1664        {
     1665                if(curr == h)
     1666                        return(1);
     1667
     1668                curr = curr->Next;
     1669        }
     1670
     1671        return(0);
    16611672}
    16621673
     
    16691680st_IsOnDeallocatedList(struct Header *h)
    16701681{
    1671     struct Header *curr;
    1672 
    1673     curr = st_DeallocatedHead;
    1674     while(curr)
    1675     {
    1676         if(curr == h)
    1677             return(1);
    1678 
    1679         curr = curr->Next;
    1680     }
    1681 
    1682     return(0);
     1682        struct Header *curr;
     1683
     1684        curr = st_DeallocatedHead;
     1685        while(curr)
     1686        {
     1687                if(curr == h)
     1688                        return(1);
     1689
     1690                curr = curr->Next;
     1691        }
     1692
     1693        return(0);
    16831694}
    16841695
     
    16921703st_PurgeDeallocatedBlocks(unsigned long Bytes, const char *file, unsigned long line)
    16931704{
    1694     unsigned long FreedBytes = 0;
    1695     unsigned long FreedBlocks = 0;
    1696 
    1697 #ifdef FORTIFY_WARN_WHEN_DISCARDING_DEALLOCATED_MEMORY
    1698     sprintf(st_Buffer, "\nFortify: Warning - Discarding deallocated memory at %s.%lu\n",
    1699                        file, line);
    1700     st_Output(st_Buffer);
    1701 #endif /* FORTIFY_WARN_WHEN_DISCARDING_DEALLOCATED_MEMORY */
    1702 
    1703     while(st_DeallocatedTail && FreedBytes < Bytes)
    1704     {
    1705         st_CheckDeallocatedBlock(st_DeallocatedTail, file, line);
    1706         FreedBytes += st_DeallocatedTail->Size;
    1707         FreedBlocks++;
    1708 #ifdef FORTIFY_WARN_WHEN_DISCARDING_DEALLOCATED_MEMORY
    1709 #ifdef FORTIFY_VERBOSE_WARN_WHEN_DISCARDING_DEALLOCATED_MEMORY
    1710         sprintf(st_Buffer, "                %s\n",
    1711                            st_DeallocatedMemoryBlockString(st_DeallocatedTail));
     1705        unsigned long FreedBytes = 0;
     1706        unsigned long FreedBlocks = 0;
     1707
     1708#       ifdef FORTIFY_WARN_WHEN_DISCARDING_DEALLOCATED_MEMORY
     1709        sprintf(st_Buffer, "\nFortify: Warning - Discarding deallocated memory at %s.%lu\n",
     1710                        file, line);
    17121711        st_Output(st_Buffer);
    1713 #endif /* FORTIFY_VERBOSE_WARN_WHEN_DISCARDING_DEALLOCATED_MEMORY */
    1714 #endif /* FORTIFY_WARN_WHEN_DISCARDING_DEALLOCATED_MEMORY */
    1715         st_FreeDeallocatedBlock(st_DeallocatedTail, file, line);
    1716     }
    1717 
    1718     return FreedBlocks != 0;
     1712#       endif /* FORTIFY_WARN_WHEN_DISCARDING_DEALLOCATED_MEMORY */
     1713
     1714        while(st_DeallocatedTail && FreedBytes < Bytes)
     1715        {
     1716                st_CheckDeallocatedBlock(st_DeallocatedTail, file, line);
     1717                FreedBytes += st_DeallocatedTail->Size;
     1718                FreedBlocks++;
     1719#               ifdef FORTIFY_WARN_WHEN_DISCARDING_DEALLOCATED_MEMORY
     1720#               ifdef FORTIFY_VERBOSE_WARN_WHEN_DISCARDING_DEALLOCATED_MEMORY
     1721                sprintf(st_Buffer, "                %s\n",
     1722                                st_DeallocatedMemoryBlockString(st_DeallocatedTail));
     1723                st_Output(st_Buffer);
     1724#               endif /* FORTIFY_VERBOSE_WARN_WHEN_DISCARDING_DEALLOCATED_MEMORY */
     1725#               endif /* FORTIFY_WARN_WHEN_DISCARDING_DEALLOCATED_MEMORY */
     1726                st_FreeDeallocatedBlock(st_DeallocatedTail, file, line);
     1727        }
     1728
     1729        return FreedBlocks != 0;
    17191730}
    17201731
     
    17261737st_PurgeDeallocatedScope(unsigned char Scope, const char *file, unsigned long line)
    17271738{
    1728     struct Header *curr, *next;
    1729     unsigned long FreedBlocks = 0;
    1730 #ifdef MT_SCOPES
    1731     unsigned ordinal = Get_TID_Ordinal();
    1732 #endif
    1733 
    1734     curr = st_DeallocatedHead;
    1735     while(curr)
    1736     {
    1737         next = curr->Next;
    1738 #ifdef MT_SCOPES
    1739         if(curr->Owner == ordinal && curr->Scope >= Scope)
    1740 #else
    1741         if(curr->Scope >= Scope)
    1742 #endif
    1743         {
    1744             st_FreeDeallocatedBlock(curr, file, line);
    1745             FreedBlocks++;
    1746         }
    1747 
    1748         curr = next;
    1749     }
    1750 
    1751     return FreedBlocks != 0;
     1739        struct Header *curr, *next;
     1740        unsigned long FreedBlocks = 0;
     1741#       ifdef MT_SCOPES
     1742        unsigned ordinal = Get_TID_Ordinal();
     1743#       endif
     1744
     1745        curr = st_DeallocatedHead;
     1746        while(curr)
     1747        {
     1748                next = curr->Next;
     1749#               ifdef MT_SCOPES
     1750                if(curr->Owner == ordinal && curr->Scope >= Scope)
     1751#               else
     1752                if(curr->Scope >= Scope)
     1753#               endif
     1754                {
     1755                        st_FreeDeallocatedBlock(curr, file, line);
     1756                        FreedBlocks++;
     1757                }
     1758
     1759                curr = next;
     1760        }
     1761
     1762        return FreedBlocks != 0;
    17521763}
    17531764
     
    17601771st_FreeDeallocatedBlock(struct Header *h, const char *file, unsigned long line)
    17611772{
    1762     st_CheckDeallocatedBlock( h, file, line );
     1773        st_CheckDeallocatedBlock( h, file, line );
    17631774
    17641775   /*
    1765     * Begin Critical region
    1766     */
    1767     FORTIFY_LOCK();
    1768 
    1769     st_TotalDeallocated -= h->Size;
    1770 
    1771     if(st_DeallocatedHead == h)
    1772     {
    1773         st_DeallocatedHead = h->Next;
    1774     }
    1775 
    1776     if(st_DeallocatedTail == h)
    1777     {
    1778         st_DeallocatedTail = h->Prev;
    1779     }
    1780 
    1781     if(h->Prev)
    1782     {
    1783         st_CheckDeallocatedBlock(h->Prev, file, line);
    1784         h->Prev->Next = h->Next;
    1785         st_MakeHeaderValid(h->Prev);
    1786     }
    1787 
    1788     if(h->Next)
    1789     {
    1790         st_CheckDeallocatedBlock(h->Next, file, line);
    1791         h->Next->Prev = h->Prev;
    1792         st_MakeHeaderValid(h->Next);
    1793     }
     1776        * Begin Critical region
     1777        */
     1778        FORTIFY_LOCK();
     1779
     1780        st_TotalDeallocated -= h->Size;
     1781
     1782        if(st_DeallocatedHead == h)
     1783        {
     1784                st_DeallocatedHead = h->Next;
     1785        }
     1786
     1787        if(st_DeallocatedTail == h)
     1788        {
     1789                st_DeallocatedTail = h->Prev;
     1790        }
     1791
     1792        if(h->Prev)
     1793        {
     1794                st_CheckDeallocatedBlock(h->Prev, file, line);
     1795                h->Prev->Next = h->Next;
     1796                st_MakeHeaderValid(h->Prev);
     1797        }
     1798
     1799        if(h->Next)
     1800        {
     1801                st_CheckDeallocatedBlock(h->Next, file, line);
     1802                h->Next->Prev = h->Prev;
     1803                st_MakeHeaderValid(h->Next);
     1804        }
    17941805
    17951806        /*
     
    18011812        }
    18021813
    1803     /*
    1804     * Nuke out all memory that is about to be freed, including the header
    1805     */
    1806     st_SetFortification((unsigned char*)h, FORTIFY_FILL_ON_DEALLOCATE_VALUE,
     1814        /*
     1815        * Nuke out all memory that is about to be freed, including the header
     1816        */
     1817        st_SetFortification((unsigned char*)h, FORTIFY_FILL_ON_DEALLOCATE_VALUE,
    18071818                        FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE + h->Size + FORTIFY_AFTER_SIZE);
    18081819
    1809     /*
    1810     * And do the actual free
    1811     */
    1812     free(h);
    1813 
    1814     /*
    1815     * End critical region
    1816     */
    1817     FORTIFY_UNLOCK();
     1820        /*
     1821        * And do the actual free
     1822        */
     1823        free(h);
     1824
     1825        /*
     1826        * End critical region
     1827        */
     1828        FORTIFY_UNLOCK();
    18181829}
    18191830
     
    18271838st_OutputMemory(struct Header *h)
    18281839{
    1829     st_HexDump((unsigned char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
    1830                0, h->Size, 1);
     1840        st_HexDump((unsigned char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1841                           0, h->Size, 1);
    18311842}
    18321843
     
    18401851        if(h->Label == NULL)
    18411852        {
    1842 #ifdef FORTIFY_NO_PERCENT_P
    1843             sprintf(st_Buffer, "0x%08lx %8lu %s.%lu\n",
     1853#               ifdef  MT_SCOPES
     1854#               ifdef FORTIFY_NO_PERCENT_P
     1855                sprintf(st_Buffer, "0x%08lx %8lu %s.%lu TID %u\n",
     1856                                (unsigned char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1857                                (unsigned long)h->Size,
     1858                                h->File, h->Line, h->Owner);
     1859#               else
     1860                sprintf(st_Buffer, "%10p %8lu %s.%lu TID %u\n",
     1861                                (unsigned char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1862                                (unsigned long)h->Size,
     1863                                h->File, h->Line, h->Owner);
     1864#               endif
     1865#               else
     1866#               ifdef FORTIFY_NO_PERCENT_P
     1867                sprintf(st_Buffer, "0x%08lx %8lu %s.%lu\n",
     1868                                (unsigned char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1869                                (unsigned long)h->Size,
     1870                                h->File, h->Line);
     1871#               else
     1872                sprintf(st_Buffer, "%10p %8lu %s.%lu\n",
     1873                                (unsigned char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1874                                (unsigned long)h->Size,
     1875                                h->File, h->Line);
     1876#               endif
     1877#               endif // MT_SCOPES
     1878        }
     1879        else
     1880        {
     1881#               ifdef  MT_SCOPES
     1882#               ifdef FORTIFY_NO_PERCENT_P
     1883                sprintf(st_Buffer, "%10p %8lu %s.%lu TID %u %s\n",
     1884                                (unsigned char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1885                                (unsigned long)h->Size,
     1886                                h->File, h->Line, h->Owner, h->Label);
    18441887#else
    1845             sprintf(st_Buffer, "%10p %8lu %s.%lu\n",
    1846 #endif
    1847                                (unsigned char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
    1848                            (unsigned long)h->Size,
    1849                        h->File, h->Line);
    1850     }
    1851     else
    1852     {
    1853 #ifdef FORTIFY_NO_PERCENT_P
    1854             sprintf(st_Buffer, "0x%08lx %8lu %s.%lu %s\n",
    1855 #else
    1856             sprintf(st_Buffer, "%10p %8lu %s.%lu %s\n",
    1857 #endif
    1858                            (unsigned char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
    1859                        (unsigned long)h->Size,
    1860                    h->File, h->Line, h->Label);
    1861     }
    1862     st_Output(st_Buffer);
     1888                sprintf(st_Buffer, "0x%08lx %8lu %s.%lu TID %u %s\n",
     1889                                (unsigned char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1890                                (unsigned long)h->Size,
     1891                                h->File, h->Line, h->Owner, h->Label);
     1892#               endif
     1893#               else // not MT_SCOPES
     1894#               ifdef FORTIFY_NO_PERCENT_P
     1895                sprintf(st_Buffer, "0x%08lx %8lu %s.%lu %s\n",
     1896                                (unsigned char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1897                                (unsigned long)h->Size,
     1898                                h->File, h->Line, h->Label);
     1899#               else
     1900                sprintf(st_Buffer, "%10p %8lu %s.%lu %s\n",
     1901                                (unsigned char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1902                                (unsigned long)h->Size,
     1903                                h->File, h->Line, h->Label);
     1904#               endif
     1905#               endif // MT_SCOPES
     1906        }
     1907        st_Output(st_Buffer);
    18631908}
    18641909
     
    18701915st_OutputLastVerifiedPoint()
    18711916{
    1872     sprintf(st_Buffer, "         Memory integrity was last verified at %s.%lu\n",
    1873                        st_LastVerifiedFile,
    1874                        st_LastVerifiedLine);
    1875     st_Output(st_Buffer);
     1917        sprintf(st_Buffer, "         Memory integrity was last verified at %s.%lu\n",
     1918                        st_LastVerifiedFile,
     1919                        st_LastVerifiedLine);
     1920        st_Output(st_Buffer);
    18761921}
    18771922
     
    18831928st_MemoryBlockString(struct Header *h)
    18841929{
    1885     static char st_BlockString[512];
    1886 
    1887     if(h->Label == 0)
    1888     {
    1889 #ifdef FORTIFY_NO_PERCENT_P
    1890             sprintf(st_BlockString,"(0x%08lx,%lu,%s.%lu)",
    1891 #else
    1892             sprintf(st_BlockString,"(%p,%lu,%s.%lu)",
    1893 #endif
    1894                 (char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
    1895                     (unsigned long)h->Size, h->File, h->Line);
     1930        static char st_BlockString[512];
     1931
     1932        if(h->Label == 0)
     1933        {
     1934#               ifdef FORTIFY_NO_PERCENT_P
     1935                sprintf(st_BlockString,"(0x%08lx,%lu,%s.%lu)",
     1936                                (char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1937                                (unsigned long)h->Size, h->File, h->Line);
     1938#               else
     1939                sprintf(st_BlockString,"(%p,%lu,%s.%lu)",
     1940                           (char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1941                           (unsigned long)h->Size, h->File, h->Line);
     1942#               endif
    18961943        }
    18971944        else
    18981945        {
    1899 #ifdef FORTIFY_NO_PERCENT_P
    1900             sprintf(st_BlockString,"(0x%08lx,%lu,%s.%lu,%s)",
    1901 #else
    1902             sprintf(st_BlockString,"(%p,%lu,%s.%lu,%s)",
    1903 #endif
    1904                 (char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
    1905                     (unsigned long)h->Size, h->File, h->Line, h->Label);
    1906         }
    1907 
    1908     return st_BlockString;
     1946#               ifdef FORTIFY_NO_PERCENT_P
     1947                sprintf(st_BlockString,"(0x%08lx,%lu,%s.%lu,%s)",
     1948                                (char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1949                                (unsigned long)h->Size, h->File, h->Line, h->Label);
     1950#               else
     1951                sprintf(st_BlockString,"(%p,%lu,%s.%lu,%s)",
     1952                                (char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1953                                (unsigned long)h->Size, h->File, h->Line, h->Label);
     1954#               endif
     1955        }
     1956
     1957        return st_BlockString;
    19091958}
    19101959
     
    19211970st_DeallocatedMemoryBlockString(struct Header *h)
    19221971{
    1923     static char st_BlockString[256];
     1972        static char st_BlockString[256];
    19241973
    19251974        if(h->Label == 0)
    19261975        {
    1927 #ifdef FORTIFY_NO_PERCENT_P
    1928             sprintf(st_BlockString,"(0x%08lx,%lu,%s.%lu,%s.%lu)",
    1929 #else
    1930             sprintf(st_BlockString,"(%p,%lu,%s.%lu,%s.%lu)",
    1931 #endif
    1932                 (char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
    1933                     (unsigned long)h->Size, h->File, h->Line, h->FreedFile, h->FreedLine);
     1976                #ifdef FORTIFY_NO_PERCENT_P
     1977                sprintf(st_BlockString,"(0x%08lx,%lu,%s.%lu,%s.%lu)",
     1978#               else
     1979                sprintf(st_BlockString,"(%p,%lu,%s.%lu,%s.%lu)",
     1980#               endif
     1981                                (char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1982                                (unsigned long)h->Size, h->File, h->Line, h->FreedFile, h->FreedLine);
    19341983        }
    19351984        else
    19361985        {
    1937 #ifdef FORTIFY_NO_PERCENT_P
    1938             sprintf(st_BlockString,"(0x%08lx,%lu,%s.%lu,%s.%lu,%s)",
    1939 #else
    1940             sprintf(st_BlockString,"(%p,%lu,%s.%lu,%s.%lu,%s)",
    1941 #endif
    1942                 (char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
    1943                     (unsigned long)h->Size, h->File, h->Line, h->FreedFile, h->FreedLine, h->Label);
    1944         }
    1945 
    1946     return st_BlockString;
     1986#               ifdef FORTIFY_NO_PERCENT_P
     1987                sprintf(st_BlockString,"(0x%08lx,%lu,%s.%lu,%s.%lu,%s)",
     1988#               else
     1989                sprintf(st_BlockString,"(%p,%lu,%s.%lu,%s.%lu,%s)",
     1990#               endif
     1991                                (char*)h + FORTIFY_HEADER_SIZE + FORTIFY_ALIGNED_BEFORE_SIZE,
     1992                                (unsigned long)h->Size, h->File, h->Line, h->FreedFile, h->FreedLine, h->Label);
     1993        }
     1994
     1995        return st_BlockString;
    19471996}
    19481997#endif /* FORTIFY_VERBOSE_WARN_WHEN_DISCARDING_DEALLOCATED_MEMORY */
     
    19572006st_DefaultOutput(const char *String)
    19582007{
    1959     fprintf(stdout, String);
    1960     fflush(stdout);
     2008        fprintf(stdout, String);
     2009        fflush(stdout);
    19612010}
    19622011
     
    19672016Fortify_malloc(size_t size, const char *file, unsigned long line)
    19682017{
    1969     return Fortify_Allocate(size, Fortify_Allocator_malloc, file, line);
     2018        return Fortify_Allocate(size, Fortify_Allocator_malloc, file, line);
    19702019}
    19712020
     
    19762025Fortify_realloc(void *uptr, size_t new_size, const char *file, unsigned long line)
    19772026{
    1978     unsigned char *ptr = (unsigned char *)uptr - FORTIFY_HEADER_SIZE - FORTIFY_ALIGNED_BEFORE_SIZE;
    1979     struct Header *h = (struct Header *)ptr;
    1980     void *new_ptr;
    1981 
    1982     /*
    1983      * If Fortify is disabled, we gotta do this a little
    1984      * differently.
    1985      */
    1986     if(!st_Disabled)
    1987     {
    1988         if(!uptr)
    1989             return(Fortify_Allocate(new_size, Fortify_Allocator_realloc, file, line));
    1990 
    1991         if(!st_IsOnAllocatedList(h))
    1992         {
    1993 #ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
    1994             if(st_IsOnDeallocatedList(h))
    1995             {
    1996                 sprintf(st_Buffer, "\nFortify: Deallocated memory block passed to \"%s\" at %s.%lu\n",
    1997                                     st_AllocatorName[Fortify_Allocator_realloc], file, line);
    1998                 st_Output(st_Buffer);
    1999                 sprintf(st_Buffer,   "         Memory block %s was deallocated by \"%s\" at %s.%lu\n",
    2000                                    st_MemoryBlockString(h),
    2001                                    st_DeallocatorName[h->Deallocator], h->FreedFile, h->FreedLine);
    2002                 st_Output(st_Buffer);
    2003                 return 0;
    2004             }
    2005 #endif
    2006 
    2007             sprintf(st_Buffer,
    2008 #ifdef FORTIFY_NO_PERCENT_P
    2009                     "\nFortify: Invalid pointer (0x%08lx) passed to realloc at %s.%lu\n",
    2010 #else
    2011                     "\nFortify: Invalid pointer (%p) passed to realloc at %s.%lu\n",
    2012 #endif
    2013                     ptr, file, line);
    2014             st_Output(st_Buffer);
    2015             return 0;
    2016         }
    2017 
    2018         if(!st_CheckBlock(h, file, line))
    2019             return 0;
    2020 
    2021         new_ptr = Fortify_Allocate(new_size, Fortify_Allocator_realloc, file, line);
    2022         if(!new_ptr)
    2023         {
    2024             return(0);
    2025         }
    2026 
    2027         if(h->Size < new_size)
    2028             memcpy(new_ptr, uptr, h->Size);
     2027        unsigned char *ptr = (unsigned char *)uptr - FORTIFY_HEADER_SIZE - FORTIFY_ALIGNED_BEFORE_SIZE;
     2028        struct Header *h = (struct Header *)ptr;
     2029        void *new_ptr;
     2030
     2031        /*
     2032         * If Fortify is disabled, we gotta do this a little
     2033         * differently.
     2034         */
     2035        if(!st_Disabled)
     2036        {
     2037                if(!uptr)
     2038                        return(Fortify_Allocate(new_size, Fortify_Allocator_realloc, file, line));
     2039
     2040                if(!st_IsOnAllocatedList(h))
     2041                {
     2042#                       ifdef FORTIFY_TRACK_DEALLOCATED_MEMORY
     2043                        if(st_IsOnDeallocatedList(h))
     2044                        {
     2045                                sprintf(st_Buffer, "\nFortify: Deallocated memory block passed to \"%s\" at %s.%lu\n",
     2046                                                st_AllocatorName[Fortify_Allocator_realloc], file, line);
     2047                                st_Output(st_Buffer);
     2048                                sprintf(st_Buffer,   "         Memory block %s was deallocated by \"%s\" at %s.%lu\n",
     2049                                                st_MemoryBlockString(h),
     2050                                                st_DeallocatorName[h->Deallocator], h->FreedFile, h->FreedLine);
     2051                                st_Output(st_Buffer);
     2052                                return 0;
     2053                        }
     2054#                       endif
     2055
     2056                        sprintf(st_Buffer,
     2057#                       ifdef FORTIFY_NO_PERCENT_P
     2058                                        "\nFortify: Invalid pointer (0x%08lx) passed to realloc at %s.%lu\n",
     2059#                       else
     2060                                        "\nFortify: Invalid pointer (%p) passed to realloc at %s.%lu\n",
     2061#                       endif
     2062                                        ptr, file, line);
     2063                        st_Output(st_Buffer);
     2064                        return 0;
     2065                }
     2066
     2067                if(!st_CheckBlock(h, file, line))
     2068                        return 0;
     2069
     2070                new_ptr = Fortify_Allocate(new_size, Fortify_Allocator_realloc, file, line);
     2071                if(!new_ptr)
     2072                {
     2073                        return(0);
     2074                }
     2075
     2076                if(h->Size < new_size)
     2077                        memcpy(new_ptr, uptr, h->Size);
     2078                else
     2079                        memcpy(new_ptr, uptr, new_size);
     2080
     2081                Fortify_Deallocate(uptr, Fortify_Deallocator_realloc, file, line);
     2082                return(new_ptr);
     2083        }
    20292084        else
    2030             memcpy(new_ptr, uptr, new_size);
    2031 
    2032         Fortify_Deallocate(uptr, Fortify_Deallocator_realloc, file, line);
    2033         return(new_ptr);
    2034     }
    2035     else
    2036     {
    2037         /*
    2038          * If the old block was fortified, we can't use normal realloc.
    2039          */
    2040         if(st_IsOnAllocatedList(h))
    2041         {
    2042             new_ptr = Fortify_Allocate(new_size, Fortify_Allocator_realloc, file, line);
    2043             if(!new_ptr)
    2044                 return(0);
    2045 
    2046             if(h->Size < new_size)
    2047                 memcpy(new_ptr, uptr, h->Size);
    2048             else
    2049                 memcpy(new_ptr, uptr, new_size);
    2050 
    2051             Fortify_Deallocate(uptr, Fortify_Deallocator_realloc, file, line);
    2052             return(new_ptr);
    2053         }
    2054         else /* easy */
    2055         {
    2056             return realloc(uptr, new_size);
    2057         }
    2058     }
     2085        {
     2086                /*
     2087                 * If the old block was fortified, we can't use normal realloc.
     2088                 */
     2089                if(st_IsOnAllocatedList(h))
     2090                {
     2091                        new_ptr = Fortify_Allocate(new_size, Fortify_Allocator_realloc, file, line);
     2092                        if(!new_ptr)
     2093                                return(0);
     2094
     2095                        if(h->Size < new_size)
     2096                                memcpy(new_ptr, uptr, h->Size);
     2097                        else
     2098                                memcpy(new_ptr, uptr, new_size);
     2099
     2100                        Fortify_Deallocate(uptr, Fortify_Deallocator_realloc, file, line);
     2101                        return(new_ptr);
     2102                }
     2103                else /* easy */
     2104                {
     2105                        return realloc(uptr, new_size);
     2106                }
     2107        }
    20592108}
    20602109
     
    20652114Fortify_calloc(size_t num, size_t size, const char *file, unsigned long line)
    20662115{
    2067     if(!st_Disabled)
    2068     {
    2069         void *ptr = Fortify_Allocate(size * num, Fortify_Allocator_calloc, file, line);
    2070         if(ptr)
    2071         {
    2072             memset(ptr, 0, size*num);
    2073         }
    2074         return ptr;
    2075     }
    2076     else
    2077     {
    2078         return calloc(num, size);
    2079     }
     2116        if(!st_Disabled)
     2117        {
     2118                void *ptr = Fortify_Allocate(size * num, Fortify_Allocator_calloc, file, line);
     2119                if(ptr)
     2120                {
     2121                        memset(ptr, 0, size*num);
     2122                }
     2123                return ptr;
     2124        }
     2125        else
     2126        {
     2127                return calloc(num, size);
     2128        }
    20802129}
    20812130
     
    20882137        /* it is defined to be safe to free(0) */
    20892138        if(uptr == 0)
    2090         return;
    2091 
    2092     Fortify_Deallocate(uptr, Fortify_Deallocator_free, file, line);
     2139                return;
     2140
     2141        Fortify_Deallocate(uptr, Fortify_Deallocator_free, file, line);
    20932142}
    20942143
     
    21012150Fortify_strdup(const char *oldStr, const char *file, unsigned long line)
    21022151{
    2103     if(!st_Disabled)
    2104     {
    2105         char *newStr = (char *)Fortify_Allocate(strlen(oldStr)+1, Fortify_Allocator_strdup, file, line);
    2106         if(newStr)
    2107         {
    2108             strcpy(newStr, oldStr);
    2109         }
    2110 
    2111         return newStr;
    2112     }
    2113     else
    2114     {
    2115         return strdup(oldStr);
    2116     }
     2152        if(!st_Disabled)
     2153        {
     2154                char *newStr = (char *)Fortify_Allocate(strlen(oldStr)+1, Fortify_Allocator_strdup, file, line);
     2155                if(newStr)
     2156                {
     2157                        strcpy(newStr, oldStr);
     2158                }
     2159
     2160                return newStr;
     2161        }
     2162        else
     2163        {
     2164                return strdup(oldStr);
     2165        }
    21172166}
    21182167#endif /* FORTIFY_STRDUP */
     
    21212170st_OutputDeleteTrace()
    21222171{
    2123 #ifdef __cplusplus
    2124     if(st_DeleteStackTop > 1)
    2125     {
    2126         sprintf(st_Buffer, "Delete Trace: %s.%lu\n", st_DeleteFile[st_DeleteStackTop-1],
    2127                                                     st_DeleteLine[st_DeleteStackTop-1]);
    2128         st_Output(st_Buffer);
    2129         for(int c = st_DeleteStackTop-2; c >= 0; c--)
    2130         {
    2131             sprintf(st_Buffer, "              %s.%lu\n", st_DeleteFile[c],
    2132                                                          st_DeleteLine[c]);
    2133             st_Output(st_Buffer);
    2134         }
    2135     }
    2136 #endif
     2172#       ifdef __cplusplus
     2173        if(st_DeleteStackTop > 1)
     2174        {
     2175                sprintf(st_Buffer, "Delete Trace: %s.%lu\n", st_DeleteFile[st_DeleteStackTop-1],
     2176                                                                st_DeleteLine[st_DeleteStackTop-1]);
     2177                st_Output(st_Buffer);
     2178                for(int c = st_DeleteStackTop-2; c >= 0; c--)
     2179                {
     2180                        sprintf(st_Buffer, "              %s.%lu\n", st_DeleteFile[c],
     2181                                        st_DeleteLine[c]);
     2182                        st_Output(st_Buffer);
     2183                }
     2184        }
     2185#       endif
    21372186}
    21382187
     
    21492198st_NewHandler()
    21502199{
    2151     /* get the current handler */
    2152     Fortify_NewHandlerFunc handler = set_new_handler(0);
    2153 
    2154     /* and set it back (since we cant
    2155     * get it without changing it)
    2156     */
    2157     set_new_handler(handler);
    2158 
    2159     return handler;
     2200        /* get the current handler */
     2201        Fortify_NewHandlerFunc handler = set_new_handler(0);
     2202
     2203        /* and set it back (since we cant
     2204        * get it without changing it)
     2205        */
     2206        set_new_handler(handler);
     2207
     2208        return handler;
    21602209}
    21612210
     
    21672216operator new(size_t size)
    21682217{
    2169     void *p;
    2170 
    2171     while((p = Fortify_Allocate(size, Fortify_Allocator_new,
     2218        void *p;
     2219
     2220        while((p = Fortify_Allocate(size, Fortify_Allocator_new,
    21722221                                st_AllocatorName[Fortify_Allocator_new], 0)) == 0)
    2173     {
    2174         if(st_NewHandler())
    2175             (*st_NewHandler())();
    2176         else
    2177             return 0;
    2178     }
    2179 
    2180     return p;
     2222        {
     2223                if(st_NewHandler())
     2224                        (*st_NewHandler())();
     2225                else
     2226                        return 0;
     2227        }
     2228
     2229        return p;
    21812230}
    21822231
     
    21882237operator new(size_t size, const char *file, int line)
    21892238{
    2190     void *p;
    2191 
    2192     while((p = Fortify_Allocate(size, Fortify_Allocator_new, file, line)) == 0)
    2193     {
    2194         if(st_NewHandler())
    2195             (*st_NewHandler())();
     2239        void *p;
     2240
     2241        while((p = Fortify_Allocate(size, Fortify_Allocator_new, file, line)) == 0)
     2242        {
     2243                if(st_NewHandler())
     2244                        (*st_NewHandler())();
    21962245        else
    2197             return 0;
    2198     }
    2199 
    2200     return p;
     2246                return 0;
     2247        }
     2248
     2249        return p;
    22012250}
    22022251
     
    22092258operator new[](size_t size)
    22102259{
    2211     void *p;
    2212 
    2213     while((p = Fortify_Allocate(size, Fortify_Allocator_array_new,
     2260        void *p;
     2261
     2262        while((p = Fortify_Allocate(size, Fortify_Allocator_array_new,
    22142263                                st_AllocatorName[Fortify_Allocator_array_new], 0)) == 0)
    2215     {
    2216         if(st_NewHandler())
    2217             (*st_NewHandler())();
    2218         else
    2219             return 0;
    2220     }
    2221 
    2222     return p;
     2264        {
     2265                if(st_NewHandler())
     2266                        (*st_NewHandler())();
     2267                else
     2268                        return 0;
     2269        }
     2270
     2271        return p;
    22232272}
    22242273
     
    22292278operator new[](size_t size, const char *file, unsigned long line)
    22302279{
    2231     void *p;
    2232 
    2233     while((p = Fortify_Allocate(size, Fortify_Allocator_array_new, file, line)) == 0)
    2234     {
    2235         if(st_NewHandler())
    2236             (*st_NewHandler())();
    2237         else
    2238             return 0;
    2239     }
    2240 
    2241     return p;
     2280        void *p;
     2281
     2282        while((p = Fortify_Allocate(size, Fortify_Allocator_array_new, file, line)) == 0)
     2283        {
     2284                if(st_NewHandler())
     2285                        (*st_NewHandler())();
     2286                else
     2287                        return 0;
     2288        }
     2289
     2290        return p;
    22422291}
    22432292
     
    22522301Fortify_PreDelete(const char *file, int line)
    22532302{
    2254     FORTIFY_LOCK();
    2255 
    2256     /*
    2257     * Push the source code info for the delete onto the delete stack
    2258     * (if we have enough room, of course)
    2259     */
    2260     if(st_DeleteStackTop < FORTIFY_DELETE_STACK_SIZE)
    2261     {
    2262         st_DeleteFile[st_DeleteStackTop] = file;
    2263         st_DeleteLine[st_DeleteStackTop] = line;
    2264     }
    2265 
    2266     st_DeleteStackTop++;
     2303        FORTIFY_LOCK();
     2304
     2305        /*
     2306        * Push the source code info for the delete onto the delete stack
     2307        * (if we have enough room, of course)
     2308        */
     2309        if(st_DeleteStackTop < FORTIFY_DELETE_STACK_SIZE)
     2310        {
     2311                st_DeleteFile[st_DeleteStackTop] = file;
     2312                st_DeleteLine[st_DeleteStackTop] = line;
     2313        }
     2314
     2315        st_DeleteStackTop++;
    22672316}
    22682317
     
    22742323Fortify_PostDelete()
    22752324{
    2276     st_DeleteStackTop--;
    2277 
    2278     FORTIFY_UNLOCK();
     2325        st_DeleteStackTop--;
     2326
     2327        FORTIFY_UNLOCK();
    22792328}
    22802329
     
    22852334operator delete(void *uptr)
    22862335{
    2287     const char *file;
    2288     unsigned long line;
    2289 
    2290      /*
    2291       * It is defined to be harmless to delete 0
    2292       */
    2293     if(uptr == 0)
    2294         return;
    2295 
    2296     /*
    2297      * find the source-code info
    2298      */
    2299     if(st_DeleteStackTop)
    2300     {
    2301         if(st_DeleteStackTop < FORTIFY_DELETE_STACK_SIZE)
    2302         {
    2303             file = st_DeleteFile[st_DeleteStackTop-1];
    2304             line = st_DeleteLine[st_DeleteStackTop-1];
     2336        const char *file;
     2337        unsigned long line;
     2338
     2339         /*
     2340          * It is defined to be harmless to delete 0
     2341          */
     2342        if(uptr == 0)
     2343                return;
     2344
     2345        /*
     2346         * find the source-code info
     2347         */
     2348        if(st_DeleteStackTop)
     2349        {
     2350                if(st_DeleteStackTop < FORTIFY_DELETE_STACK_SIZE)
     2351                {
     2352                        file = st_DeleteFile[st_DeleteStackTop-1];
     2353                        line = st_DeleteLine[st_DeleteStackTop-1];
     2354                }
     2355                else
     2356                {
     2357                        file = st_DeleteFile[FORTIFY_DELETE_STACK_SIZE-1];
     2358                        line = st_DeleteLine[FORTIFY_DELETE_STACK_SIZE-1];
     2359                }
    23052360        }
    23062361        else
    23072362        {
    2308             file = st_DeleteFile[FORTIFY_DELETE_STACK_SIZE-1];
    2309             line = st_DeleteLine[FORTIFY_DELETE_STACK_SIZE-1];
    2310         }
    2311     }
    2312     else
    2313     {
    2314         file = st_DeallocatorName[Fortify_Deallocator_delete];
    2315         line = 0;
    2316     }
    2317 
    2318     Fortify_Deallocate(uptr, Fortify_Deallocator_delete, file, line);
     2363                file = st_DeallocatorName[Fortify_Deallocator_delete];
     2364                line = 0;
     2365        }
     2366
     2367        Fortify_Deallocate(uptr, Fortify_Deallocator_delete, file, line);
    23192368}
    23202369
     
    23272376operator delete[](void *uptr)
    23282377{
    2329     const char *file;
    2330     unsigned long line;
    2331 
    2332      /*
    2333       * It is defined to be harmless to delete 0
    2334       */
    2335     if(uptr == 0)
    2336         return;
    2337 
    2338     /*
    2339      * find the source-code info
    2340      */
    2341     if(st_DeleteStackTop)
    2342     {
    2343         if(st_DeleteStackTop < FORTIFY_DELETE_STACK_SIZE)
    2344         {
    2345             file = st_DeleteFile[st_DeleteStackTop-1];
    2346             line = st_DeleteLine[st_DeleteStackTop-1];
     2378        const char *file;
     2379        unsigned long line;
     2380
     2381         /*
     2382          * It is defined to be harmless to delete 0
     2383          */
     2384        if(uptr == 0)
     2385                return;
     2386
     2387        /*
     2388         * find the source-code info
     2389         */
     2390        if(st_DeleteStackTop)
     2391        {
     2392                if(st_DeleteStackTop < FORTIFY_DELETE_STACK_SIZE)
     2393                {
     2394                        file = st_DeleteFile[st_DeleteStackTop-1];
     2395                        line = st_DeleteLine[st_DeleteStackTop-1];
     2396                }
     2397                else
     2398                {
     2399                        file = st_DeleteFile[FORTIFY_DELETE_STACK_SIZE-1];
     2400                        line = st_DeleteLine[FORTIFY_DELETE_STACK_SIZE-1];
     2401                }
    23472402        }
    23482403        else
    23492404        {
    2350             file = st_DeleteFile[FORTIFY_DELETE_STACK_SIZE-1];
    2351             line = st_DeleteLine[FORTIFY_DELETE_STACK_SIZE-1];
    2352         }
    2353     }
    2354     else
    2355     {
    2356         file = st_DeallocatorName[Fortify_Deallocator_array_delete];
    2357         line = 0;
    2358     }
    2359 
    2360     Fortify_Deallocate(uptr, Fortify_Deallocator_array_delete, file, line);
     2405                file = st_DeallocatorName[Fortify_Deallocator_array_delete];
     2406                line = 0;
     2407        }
     2408
     2409        Fortify_Deallocate(uptr, Fortify_Deallocator_array_delete, file, line);
    23612410}
    23622411
     
    23762425class Fortify_AutoLogFile
    23772426{
    2378     static FILE *fp;
    2379     static int   written_something;
    2380     static char *init_string, *term_string;
     2427        static FILE *fp;
     2428        static int   written_something;
     2429        static char *init_string, *term_string;
    23812430
    23822431public:
    2383     Fortify_AutoLogFile()
    2384     {
    2385         written_something = 0;
    2386         Fortify_SetOutputFunc(Fortify_AutoLogFile::Output);
    2387         Fortify_EnterScope(init_string, 0);
    2388     }
    2389 
    2390     static void Output(const char *s)
    2391     {
     2432        Fortify_AutoLogFile()
     2433        {
     2434                written_something = 0;
     2435                Fortify_SetOutputFunc(Fortify_AutoLogFile::Output);
     2436                Fortify_EnterScope(init_string, 0);
     2437        }
     2438
     2439        static void Output(const char *s)
     2440        {
    23922441        if(written_something == 0)
    23932442        {
    2394             FORTIFY_FIRST_ERROR_FUNCTION;
    2395             fp = fopen(FORTIFY_LOG_FILENAME, "w");
    2396             if(fp)
    2397             {
    2398                 time_t t;
    2399                 time(&t);
    2400                 fprintf(fp, "Fortify log started at %s\n", ctime(&t));
    2401                 written_something = 1;
    2402             }
     2443                FORTIFY_FIRST_ERROR_FUNCTION;
     2444                fp = fopen(FORTIFY_LOG_FILENAME, "w");
     2445                if(fp)
     2446                {
     2447                        time_t t;
     2448                        time(&t);
     2449                        fprintf(fp, "Fortify log started at %s\n", ctime(&t));
     2450                        written_something = 1;
     2451                }
    24032452        }
    24042453
    24052454        if(fp)
    24062455        {
    2407             fputs(s, fp);
    2408             fflush(fp);
    2409         }
    2410     }
    2411 
    2412     ~Fortify_AutoLogFile()
    2413     {
     2456                fputs(s, fp);
     2457                fflush(fp);
     2458        }
     2459        }
     2460
     2461        ~Fortify_AutoLogFile()
     2462        {
    24142463        Fortify_LeaveScope(term_string, 0);
    24152464        Fortify_CheckAllMemory(term_string, 0);
    24162465        if(fp)
    24172466        {
    2418             time_t t;
    2419             time(&t);
    2420             fprintf(fp, "\nFortify log closed at %s\n", ctime(&t));
    2421             fclose(fp);
    2422             fp = 0;
    2423         }
    2424     }
     2467                time_t t;
     2468                time(&t);
     2469                fprintf(fp, "\nFortify log closed at %s\n", ctime(&t));
     2470                fclose(fp);
     2471                fp = 0;
     2472        }
     2473        }
    24252474};
    24262475
     
    24382487#ifdef MT_SCOPES
    24392488
     2489#if 0 // 18 Jul 08 SHL fixme to be gone
     2490
    24402491/**
    24412492 * Set/reset owner of blocks allocated by this thread
    24422493 * Use when worker thread will allocate blocks for another thread
    24432494 * and other thread is known
    2444  * More efficient than Fortify_ChangeOwner
     2495 * Slightly more efficient than Fortify_BecomeOwner
    24452496 * @param lOwnerTID is new owner TID, -1 requests reset of self
    24462497 */
    24472498
    2448 void Fortify_SetOwner(long lOwnerTID)
    2449 {
    2450     unsigned ordinal = Get_TID_Ordinal();
    2451 
    2452     if (ordinal >= st_cOrdinals) {
    2453         // Expand arrays
    2454         unsigned i;
    2455         unsigned c;
    2456         FORTIFY_LOCK();
    2457         i = st_cOrdinals;
    2458         c = ordinal + 1;
    2459         st_pScopes = realloc((void*)st_pScopes, sizeof(*st_pScopes) * c);
    2460         st_pOwners = realloc((void*)st_pOwners, sizeof(*st_pOwners) * c);
    2461         for (; i <= ordinal; i++) {
    2462             st_pScopes[i] = 0;
    2463             st_pOwners[i] = i;          // Block owner is self
    2464         }
    2465         st_cOrdinals = c;
    2466         FORTIFY_UNLOCK();
    2467     }
    2468     // Set owner for blocks allocated by this thread
    2469     st_pOwners[ordinal] = lOwnerTID != -1 ? lOwnerTID : ordinal;
    2470 }
     2499void Fortify_PresetOwner(long lOwnerTID)
     2500{
     2501        unsigned ordinal = Get_TID_Ordinal();
     2502
     2503        if (ordinal >= st_cOrdinals) {
     2504                // Expand arrays
     2505                unsigned i;
     2506                unsigned c;
     2507                FORTIFY_LOCK();
     2508                i = st_cOrdinals;
     2509                c = ordinal + 1;
     2510                st_pScopes = realloc((void*)st_pScopes, sizeof(*st_pScopes) * c);
     2511                st_pOwners = realloc((void*)st_pOwners, sizeof(*st_pOwners) * c);
     2512                for (; i <= ordinal; i++) {
     2513                        st_pScopes[i] = 0;
     2514                        st_pOwners[i] = i;              // Block owner is self
     2515                }
     2516                st_cOrdinals = c;
     2517                FORTIFY_UNLOCK();
     2518        }
     2519        // Set owner for blocks allocated by this thread
     2520        st_pOwners[ordinal] = lOwnerTID != -1 ? lOwnerTID : ordinal;
     2521}
     2522#endif // 18 Jul 08 SHL fixme to be gone
    24712523
    24722524/**
     
    24772529 */
    24782530
    2479 void Fortify_ChangeOwner(void *pBlock)
    2480 {
    2481     unsigned char *ptr = (unsigned char *)pBlock -
    2482                              FORTIFY_HEADER_SIZE -
    2483                              FORTIFY_ALIGNED_BEFORE_SIZE;
    2484     struct Header *h = (struct Header *)ptr;
    2485 
    2486     unsigned ordinal = Get_TID_Ordinal();
    2487 
    2488     h->Scope = ordinal < st_cOrdinals ? st_pScopes[ordinal] : 0;
    2489     h->Owner = ordinal;         // Take ownership
    2490     st_MakeHeaderValid(h);
     2531void Fortify_BecomeOwner(void *pBlock)
     2532{
     2533        unsigned char *ptr = (unsigned char *)pBlock -
     2534                                                 FORTIFY_HEADER_SIZE -
     2535                                                 FORTIFY_ALIGNED_BEFORE_SIZE;
     2536        struct Header *h = (struct Header *)ptr;
     2537
     2538        unsigned ordinal = Get_TID_Ordinal();
     2539
     2540        h->Owner = ordinal;             // Take ownership
     2541        h->Scope = ordinal < st_cOrdinals ? st_pScopes[ordinal] : 0;
     2542        st_MakeHeaderValid(h);
     2543}
     2544
     2545/**
     2546 * Take ownership of block allocated by some other thread
     2547 * Allows scope enter/exit logic to correctly report leaks in
     2548 * cross thread allocations
     2549 * @param pBlock points to block allocated by Fortify
     2550 */
     2551
     2552void Fortify_SetOwner(void *pBlock, unsigned ordinal)
     2553{
     2554        unsigned char *ptr = (unsigned char *)pBlock -
     2555                                                 FORTIFY_HEADER_SIZE -
     2556                                                 FORTIFY_ALIGNED_BEFORE_SIZE;
     2557        struct Header *h = (struct Header *)ptr;
     2558
     2559        h->Owner = (unsigned short)ordinal;             // Take ownership
     2560        h->Scope = ordinal < st_cOrdinals ? st_pScopes[ordinal] : 0;
     2561        st_MakeHeaderValid(h);
    24912562}
    24922563
     
    25002571void Fortify_ChangeScope(void *pBlock, int delta)
    25012572{
    2502     unsigned char *ptr = (unsigned char *)pBlock -
    2503                              FORTIFY_HEADER_SIZE -
    2504                              FORTIFY_ALIGNED_BEFORE_SIZE;
    2505     struct Header *h = (struct Header *)ptr;
    2506     h->Scope += delta;
    2507     st_MakeHeaderValid(h);
     2573        unsigned char *ptr = (unsigned char *)pBlock -
     2574                                 FORTIFY_HEADER_SIZE -
     2575                                 FORTIFY_ALIGNED_BEFORE_SIZE;
     2576        struct Header *h = (struct Header *)ptr;
     2577        h->Scope += delta;
     2578        st_MakeHeaderValid(h);
     2579}
     2580
     2581/**
     2582 * Force scope level of allocated block
     2583 * Allows scope enter/exit logic to correctly report leaks in
     2584 * window procedure related allocations
     2585 * @param pBlock points to block allocated by Fortify
     2586 */
     2587
     2588void Fortify_SetScope(void *pBlock, unsigned char scope)
     2589{
     2590        unsigned char *ptr = (unsigned char *)pBlock -
     2591                                 FORTIFY_HEADER_SIZE -
     2592                                 FORTIFY_ALIGNED_BEFORE_SIZE;
     2593        struct Header *h = (struct Header *)ptr;
     2594        h->Scope = scope;
     2595        st_MakeHeaderValid(h);
    25082596}
    25092597
Note: See TracChangeset for help on using the changeset viewer.