How To Add Debug Info To Autogenerated C Code
I just recently learned about the #line
directive in C/C++. This is not a very
well known feature (that is, I've never heard about it until now), but is very useful
for people writing compilers that export C code.
Why Would You Need This?
Suppose you have the following programming language:
print("Hello world!")
You might chose to use C as your compilation target, which means anyone with a C compiler can compile and run your programming language! Given the above example, your compiler might output the following C code:
#include <stdio.h>
int main(void) {
puts("Hello world!");
}
All you need to do compile and run it is:
$ cc file.c -g $ ./a.out Hello world!
The -g
flag is what adds the debug info
Great! But what happens when you try debugging this?
$ gdb a.out -q Reading symbols from a.out... (gdb) b main Breakpoint 1 at 0x113d: file file.c, line 4. (gdb) r Starting program: a.out [Thread debugging using libthread_db enabled] Using host libthread_db library "/usr/lib/libthread_db.so.1". Breakpoint 1, main () at file.c:4 4 puts("Hello world!"); (gdb)
The issue is that the debugger is using the line numbers of our C program, not our original program. This also means that the user will be debugging the generated C code, which probably isn't what we want.
The Solution
To fix this, include a #line
directive for every line that you want to have
different line numbers on:
#include <stdio.h>
#line 1 "file.dsl"
int main(void) {
#line 1 "file.dsl"
puts("Hello world!");
}
Here file.dsl
is the source file for our custom DSL (Domain Specific Language).
Now, when we recompile and debug we get the following:
$ gdb a.out -q Reading symbols from a.out... (gdb) b main Breakpoint 1 at 0x113d: file file.dsl, line 1. (gdb) r Starting program: a.out [Thread debugging using libthread_db enabled] Using host libthread_db library "/usr/lib/libthread_db.so.1". Breakpoint 1, main () at file.dsl:1 1 print("Hello world!") (gdb)
Ta da! Now the debugger shows the correct source line and line number for our code!