AQZZ's blog

By AQZZ, history, 4 years ago, In English

Currently I compile with these flags: alias bd='g++ -std=c++17 -Wshadow -Wall -Wextra -o "a" -g -fsanitize=address -fsanitize=undefined'

Most of the time when I access an out of bounds index I get an error from the sanitizer that tells me the line number, which is good. But sometimes I just get an error that memory is leaked but I get no line number. Are there any flags/compilers which can print the line number consistently when this error occurs, similar to Java's index out of bounds exception?

  • Vote: I like it
  • 0
  • Vote: I do not like it

»
4 years ago, # |
  Vote: I like it 0 Vote: I do not like it

Use std::vector::at() instead of std::vector::operator []() to get an exception on accessing elements out of range.

  • »
    »
    4 years ago, # ^ |
      Vote: I like it 0 Vote: I do not like it

    .at() dosen't tell me the line number so its worse than what I have now. The flags I have now tell me the line number most of the time (which is pretty good), but not all the time. I guess I just need to code better.

    • »
      »
      »
      4 years ago, # ^ |
        Vote: I like it 0 Vote: I do not like it

      Well, it does not tell you the line number but you can run gdb to find it out.

»
4 years ago, # |
  Vote: I like it 0 Vote: I do not like it

Add -D_GLIBCXX_DEBUG (slows your program, but does comprehensive checks) or -D_GLIBCXX_ASSERTIONS (faster, but less error checking) to your compiler flags. These flags check for out of bounds indexing. Then you can run your code in a debugger like gdb, and the debugger will stop the execution of the program when the program aborts on out of bounds indexing.

  • »
    »
    4 years ago, # ^ |
      Vote: I like it 0 Vote: I do not like it

    Is this similar to using -ftrapv flag while compiling?

    • »
      »
      »
      4 years ago, # ^ |
      Rev. 3   Vote: I like it 0 Vote: I do not like it

      -ftrapv enables checks for arithmetic overflow, while -D_GLIBCXX_DEBUG enables checks for out of bounds indexing, out of bound iterators, and other errors in STL containers. Note that this only works for STL containers, so you'll need to use std::array instead of a C array.`

»
4 years ago, # |
  Vote: I like it 0 Vote: I do not like it

You can use the __LINE__ C preprocessor macro to write your own bounds-checking function that prints the line number at which the out-of-range error takes place. The following is an example.

Example

»
4 years ago, # |
  Vote: I like it 0 Vote: I do not like it

If you look at https://github.com/google/sanitizers/wiki/AddressSanitizer, you would get:

To get nicer stack traces in error messages add -fno-omit-frame-pointer

»
4 years ago, # |
  Vote: I like it 0 Vote: I do not like it

Where can I find the line number?

  • »
    »
    4 years ago, # ^ |
      Vote: I like it 0 Vote: I do not like it

    If you use the D_GLIBCXX_DEBUG flag, then when you use gdb and type "run" and get to the error you can type "where" to see the line number. If you leave out the D_GLIBCXX_DEBUG flag, most of the time you get the line number at runtime from the sanitizers, and when you don't you will get a vague memory leak error, but using gdb you can find the line number just as before. Using the D_GLIBCXX_DEBUG flag, you don't get any line numbers at runtime, but the error description is more precise.