2

Microsoft's Visual C++ fills memory with 'magic numbers' if it hasn't been initialized by the programmer itself. This helps with debugging of uninitialized memory. (In Visual Studio C++, what are the memory allocation representations?, 0xDEADBEEF vs. NULL)

Is there a similar function when using linux GNU tools (g++/gdb)?

Thanks!

Community
  • 1
  • 1
eagle123
  • 164
  • 9
  • https://github.com/google/sanitizers/wiki/AddressSanitizer – John Zwinck May 07 '16 at 15:17
  • None is a matter of the compiler, but the library and/or OS. gcc does not contain a library. And gdb is a debugger. – too honest for this site May 07 '16 at 15:37
  • 1
    Try with valgrind's [memcheck](http://valgrind.org/docs/manual/mc-manual.html) instead of gdb – xvan May 07 '16 at 17:32
  • @Olaf, if it's a matter of the OS: how do enable those "magic numbers" in GNU/Linux? – eagle123 May 07 '16 at 21:29
  • @xvan: thanks, I've used valgrind before. Does it fill uninitialized memory with magic numbers? (I think I could just try...) If so,is there some description what it uses? – eagle123 May 07 '16 at 21:31
  • @JohnZwinck: Thanks for the link. I have only GCC 4.4.7 available, which doesn't include AddressSanitizer. I am looking for a solution that works with the tools I have installed. – eagle123 May 07 '16 at 21:45
  • @eagle123 Valgrind memcheck can track all memory operations and report the code line and variable using the uninitialized variable. No magic numbers needed. – xvan May 07 '16 at 22:04
  • You need to use the option --track-origins=yes – xvan May 07 '16 at 22:06
  • @xvan : thanks, that's what I did and why I asked this question; it is not always crystal clear where the uninitialized value originated from that valgrind reports, e.g. if there are multiple variables, or if the currently used variable has been constructed from other uninitialized values. So it would be nice to run the program in the debugger up to the point where the value is used, and then look the memory for 'magic numbers' – eagle123 May 07 '16 at 22:20
  • @eagle123 : you can use valgrind and gdb together. See valgrind user manual http://www.valgrind.org/docs/manual/manual-core-adv.html#manual-core-adv.gdbserver for info. You can also combine valgrind+gdb+magic numbers, using --malloc-fill=xx and --free-fill=xx valgrind arguments. Note however that magic numbers are less precise than --track-origins=yes : they can only tell if the uninit is due to a malloc and/or free. Track origin is able to point at e.g. stack frame. – phd May 11 '16 at 18:57
  • @phd thanks for the tip with malloc-fill. I did not know that! – eagle123 May 14 '16 at 23:42
  • 3
    Possible duplicate of [Can g++ fill uninitialized POD variables with known values?](http://stackoverflow.com/questions/2653555/can-g-fill-uninitialized-pod-variables-with-known-values) – sashoalm Oct 09 '16 at 09:56

1 Answers1

2

You can override the C++ operator new to set allocations to your preferred byte pattern:

void* operator new(size_t size)
{
    void* mem = malloc(size);
    if (!mem) {
        throw std::bad_alloc();
    }
    memset(mem, 0xEE, size);
    return mem;
}

You can see the full GCC implementation here: https://github.com/gcc-mirror/gcc/blob/master/libstdc%2B%2B-v3/libsupc%2B%2B/new_op.cc in case you want to mirror it more closely.

That will work for anything using the default C++ allocators, but not for things using regular old malloc(). If you need to initialize memory from malloc() directly, you can override that too, but the mechanism to do it is different: you can use the linker's --wrap option to manipulate the symbol table and let you override malloc(). Then you don't need to overload operator new of course. The full approach is illustrated in an answer here: https://stackoverflow.com/a/3662951/4323

Community
  • 1
  • 1
John Zwinck
  • 239,568
  • 38
  • 324
  • 436