Question

I have the following piece of code:

 int main(int argc, char *argv[])
    {
        int a = 2;
        int b = 5;
        int soma = a + b;
   //...}

The resulting llvm bitcode is:

       define i32 @main(i32 %argc, i8** %argv) #0 {
        entry:
          ...
          %a = alloca i32, align 4
          %b = alloca i32, align 4
          %soma = alloca i32, align 4
          ...
          call void @llvm.dbg.declare(metadata !{i32* %a}, metadata !15), !dbg !16
          store i32 2, i32* %a, align 4, !dbg !16
          call void @llvm.dbg.declare(metadata !{i32* %b}, metadata !17), !dbg !18
          store i32 5, i32* %b, align 4, !dbg !18
          call void @llvm.dbg.declare(metadata !{i32* %soma}, metadata !19), !dbg !20
          %0 = load i32* %a, align 4, !dbg !20
          %1 = load i32* %b, align 4, !dbg !20
          %add = add nsw i32 %0, %1, !dbg !20
          store i32 %add, i32* %soma, align 4, !dbg !20
          ...       
          !1 = metadata !{i32 0}
          !2 = metadata !{metadata !3}
          ...
          !15 = metadata !{i32 786688, metadata !3, metadata !"a", metadata !4, i32 6, metadata !7, i32 0, i32 0} ; [ DW_TAG_auto_variable ] [a] [line 6]
!16 = metadata !{i32 6, i32 0, metadata !3, null}
!17 = metadata !{i32 786688, metadata !3, metadata !"b", metadata !4, i32 7, metadata !7, i32 0, i32 0} ; [ DW_TAG_auto_variable ] [b] [line 7]
!18 = metadata !{i32 7, i32 0, metadata !3, null}
!19 = metadata !{i32 786688, metadata !3, metadata !"soma", metadata !4, i32 8, metadata !7, i32 0, i32 0} ; [ DW_TAG_auto_variable ] [soma] [line 8]
!20 = metadata !{i32 8, i32 0, metadata !3, null}

From the bitcode I need to get the following text:

a = 2
b = 5
soma = a + b

My doubt is how to extract the information I need from the metadata (dgb)?? Right now I only have the name of the instructions I-> getName () and the name of the operands with valueOp Value * = I-> getOperand (i); valueOp-> getName (). Str (); The metadata is very extensive. How do I get this information from the metadata?

Was it helpful?

Solution

Relying on I->getName() for finding the variable name is not a good idea - you have the debug info for that. The proper approach for finding out the names of all the C/C++ local variables is to traverse the IR and look for all calls to @llvm.dbg.declare, then go to their 2nd operand (the debug metadata), and retrieve the variable name from there.

Use the source-level debugging guide to find out how the debug metadata is laid out. In particular, for local variables, the 3rd argument will be a metadata string with the variable name in the C/C++ source.

So the remaining thing is to find out what the variables are initialized to. For that, follow the 1st argument to @llvm.dbg.declare for getting the actual LLVM value used, then locate the 1st store instruction into it, and check what data is used there.

If it's a constant, you now have everything you need to output a = 5-style information. If it's another instruction, you have to follow it yourself and "decode" it - e.g., if it's an "add", then you need to print its two operands with a "+" in-between, etc. And of course the prints have to be recursive... not simple. But it will provide you with the accurate initialization value.

If you're looking for something a lot more coarse and you have access to the original source, you can just get the line number in which the variable is declared (the 5th operand in the debug metadata, assuming the tag (1st operand) is indeed DW_TAG_auto_variable and not DW_TAG_arg_variable, which indicates a parameter). Then print out that line from the original source. But this will not print all the relevant information (if the initialization value is constructed from multiple lines) and can print irrelevant information (if there are multiple statements in that line, for example).

Finally, remember optimization can seriously screw with debug information. If getting those print-outs is important, be careful with your -O option, maybe stick to -O0.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top