I'm writing a debug versions of global delete/new operator to detect memory leaks, double deletes and delete on unallocated memory.
As far as "new" operator is concerned, I overrode the global new operator and using macros I passed file name and line number information. The overridden "new" operator stores the memory address, file name, size and line number information in map keyed on address.
I overrode "delete" operator too, which removes the deleted address' entry from the map. Now i want to store the deleted memory information in another map which stores the file name and line number information from where the "delete" was called.
But the delete operator takes only argument (memory address of the object to be deleted). Can someone tell how to detect double deletes in the code?
You are already creating a map of allocated memory addresses(key) and filename, line number(value fields) inside your overloaded new
.
While in your overloaded delete just check if the address being passed exists in the map you created.
If Yes, You consider the call to delete
as valid and remove that address entry from your map.
If No, then consider the call to delete as faulty, delete called on a pointer not allocated through your new
or trying to call delete multiple times
.
If what you need is to differentiate a double delete from a delete from a never allocated memory, just map addresses to state of the allocated memory, instead of removing the element from the map, just update the state to mark it as already released. The test in each delete would verify if the address is present (if not the error is deleting a never allocated address), and if so, whether the memory has already been released (if it has, then the error is a double free).
There are two separate issues: detecting the double delete (as opposed
to a delete of memory that was never allocated, and determining where in
the program it occurred.
For the first, my debugging operator new
allocates guard zones before
and after the block it returns (also used for detecting writes past the
end on deallocation); I set them to a different pattern in operator
delete
, and check for this pattern. There's always the chance that
never allocated memory might contain this pattern, but the chance is
very, very small.
Determining where in the code the error occurred is more difficult.
I've written code which does a stack walkback, but it's very system
dependent. (I have versions for Solaris on Sparc, Linux on Intel, and
Windows.) And all it reports is the return addresses in hex; it's up to
the programmer to analyse those, using other tools. The GNU binutils
package has a program addr2line
, which works well under Linux, but
it's not that difficult to do manually, given a sorted map.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With