X-Git-Url: http://git.pk910.de/?p=ircu2.10.12-pk.git;a=blobdiff_plain;f=doc%2Ffda.txt;fp=doc%2Ffda.txt;h=d993ae52eda3b4ffc940c6c51b58be22e7383a45;hp=0000000000000000000000000000000000000000;hb=0400a5a6479398d82526785c18c0df8bc8b92dce;hpb=d17e10da972ce5776c60b4c317267c6abe0e1ead diff --git a/doc/fda.txt b/doc/fda.txt new file mode 100644 index 0000000..d993ae5 --- /dev/null +++ b/doc/fda.txt @@ -0,0 +1,151 @@ +fdaman.txt - brief usage information for FDA (Free Debug Allocator) + +Copyright (C) 1998 Thomas Helvey + +1. Base Functionality +Basic use of the fda tools is as simple as including the header +and source file with your source defining DEBUG and using capitalized +versions of malloc(), calloc(), realloc(), and free(). +The fda allocation functions verify all your arguments and will call +assert() if something is wrong. FDA trashes all allocated memory +in a predictable manner and applies prefix and postfix bounds checking +signatures to every allocation. When a pointer is freed it's validated, +and checked for overflows and underflows. The fda Realloc function +does not allow malloc or free through realloc and forces reallocation +if the required memory is larger than the current allocation. + +In both the DEBUG and non-debug versions of fda, if a memory allocation +fails once, a low memory callback function is called to allow you to +release some memory and allow malloc to succeed, the default version +prints a warning message to stderr. If the low memory callback returns +the allocation is attempted again, if the second allocation fails a +no memory callback function is called to allow you to clean up before +terminating the application, if you allow the no memory callback to +return the results are undefined. (a NULL ptr will be returned from the +allocation call) The default no memory handler prints an error message +to stderr and calls abort(). The DEBUG version will assert if you allow +the no memory function to return. +Both the low memory and no memory callbacks have the signature of: +void handler(void) + +The debug version of fda will not allow you to do the following: +Allocate a zero length chunk of memory. +Free a non-allocated pointer. +Free a pointer twice. +Free a pointer at the wrong offset. +Use realloc to free memory. (realloc(p, 0)) +Use realloc to malloc memory. (realloc(0, s)) +Overwrite the bounds of the memory you allocated. (checked on free) + +The base functions for fda are: +void* malloc(size_t) +void* realloc(void*, size_t) +void* calloc(size_t, size_t) +void free(void*) +char* strdup(const char*) +void set_lowmem_handler(void (*fn)(void)) +void set_nomem_handler(void (*fn)(void)) + +FDA uses a hash table to lookup pointers. The size of the hash table can +be changed at compile time by using -DFDA_HASH_TABLE_SIZE +where prime is a prime number somewhere around the number of allocations +expected. The default hash table size is 16339 which should be large enough +to hold most medium sized applications. FDA allocates memory for it's +debugging records so if your application uses a lot of memory you +may want to make sure you have enough memory available to use the debug +version. FDA allocates 20 bytes to store each allocation and 20 bytes +to store location information (file and line info). This overhead only +applies if you have DEBUG or _DEBUG defined. + +2. Extended functionality +FDA provides a few handy functions for validating pointers and +checking for overruns before they occur when debugging. +The first function fda_sizeof(ptr) returns the size of the buffer +pointed to by ptr, this allows you to verify that your pointer +is what it says it is. fda_sizeof() will call assert() if the +pointer you pass it is not at the start of an allocation. + +The second function valid_ptr(ptr, size) verifies that ptr lies within +allocated memory and there are at least size bytes available in the buffer. +You can pass valid_ptr() a pointer to any location in allocated memory. +valid_ptr() calls assert if the pointer points outside of allocated memory +or the remaining size is less than the size specified. +valid_ptr() is more efficient if the pointer argument is the value +returned from malloc because it's a simple hash table lookup, a more +exhaustive algorithm is used if it's not found in the hash table. + +FDA extended functions: +size_t fda_sizeof(const void*) +int valid_ptr(const void*, size_t) + +Typical usage for the fda extended functions: +Note: the assert macro compiles to nothing if NDEBUG is defined. +Verify a foo_ptr: +assert(sizeof(struct foo) == fda_sizeof(foo_ptr)); +assert(valid_ptr(foo_ptr, sizeof(struct foo))); +Check for room to write: +assert(valid_ptr(buf, len)); + +3. Leak checking and block validation +FDA has several functions for leak checking, and reference marking. +fda_clear_refs() iterates through all of the allocated blocks of +memory and clears the referenced flag. +fda_set_ref() marks a single allocation(block) as being referenced or +in use by somebody. +fda_assert_refs() iterates through all the allocated blocks of +memory and calls assert() if it finds one that's not referenced. + +Typical usage of the block validation functions: +fda_clear_refs(); /* clear all block references */ + +for each allocation do +fda_set_ref(allocation); /* mark allocation in use */ +done + +fda_assert_refs(); /* this will assert if a leak is found */ + +4. Reporting functions: +FDA has 4 functions for reporting various aspects of allocation +status. +fda_get_byte_count() tells you the current total number of bytes +your application has allocated. (this does not include debugging records) +This will give you an idea of how much memory your application is +using at any given time. + +fda_get_block_count() returns the total count of current allocations. + +fda_enum_locations() calls a user supplied enumeration function with +file, line, count information, this allows you to see your file by +file allocation density. ;) fda_enum_locations() returns the total +number of locations that have memory allocated. + +fda_enum_leaks() calls a user supplied enumeration function with +file, line, size, and ptr for every block not marked as referenced. +One use for fda_enum_leaks() is checking for leaks when your program +exits: +void enum_fn(const char* file, int line, size_t size, void* ptr) +{ + printf("Memory leak: %s: %d - %d bytes at (%p)\n", file, line, size, ptr); +} + +int main(void) +{ + ... +#if defined(DEBUG) + /* check for memory leaks before exiting */ + fda_clear_refs(); + fda_enum_leaks(enum_fn); +#endif + return 0; /* return from main */ +} + +The test file fdatest.c gives examples of usage for most of the functions +available with FDA. + +Please let me know if you encounter any problems with FDA. +So far FDA has been built and tested on linux and Windows NT. +If you find that it works with or without change on other platforms +please let me know so I can make the appropriate changes to the +code and add it to the list of tested platforms. + +