Location of global variables with DWARF (and movement)

When linking a binary file to libraries dynamically, relocation information is used to link the variables / functions of various ELF objects. However, DWARF is motion independent: how should the debugger resolve global variables?

Say I have liba.so (ac) defining a global variable (using GNU / Linux with GCC or Clang):

#include <stdio.h>

int foo = 10;

int test(void) {
  printf("&foo=%p\n", &foo);
}

and program b related to liba.so (bc):

#include <stdio.h>

extern int foo;

int main(int argc, char** argv) {
  test();
  printf("&foo=%p\n", &foo);  
  return 0;
}

I expect that "foo" will instantiate in liba.so but in fact it will instantiate in both liba.so and b:

$ ./b 
&foo=0x600c68 # <- b .bss
&foo=0x600c68 # <- b .bss

The variable foo used (in both b and lib.so) is located in .bss of b and not in liba.so:

[...]
0x0000000000600c68 - 0x0000000000600c70 is .bss
[...]
0x00007ffff7dda9c8 - 0x00007ffff7dda9d4 is .data in /home/foo/bar/liba.so
0x00007ffff7dda9d4 - 0x00007ffff7dda9d8 is .bss in  /home/foo/bar/liba.so

The variable foo is initialized twice:

  • once in liba.so (this instance is not used when connecting to program b)

  • b ( b).

( , .)

DWARF b ( ):

$ readelf -wi b
[...]
<1><ca>: Abbrev Number: 9 (DW_TAG_variable)
  <cb>   DW_AT_name        : foo      
  <cf>   DW_AT_decl_file   : 1        
  <d0>   DW_AT_decl_line   : 3        
  <d1>   DW_AT_type        : <0x57>   
  <d5>   DW_AT_external    : 1        
  <d5>   DW_AT_declaration : 1
[...]

liba.so:

$ readelf -wi liba.so
[...]
<1><90>: Abbrev Number: 5 (DW_TAG_variable)
  <91>   DW_AT_name        : foo      
  <95>   DW_AT_decl_file   : 1        
  <96>   DW_AT_decl_line   : 3        
  <97>   DW_AT_type        : <0x57>   
  <9b>   DW_AT_external    : 1        
  <9b>   DW_AT_location    : 9 bloc d'octets: 3 d0 9 20 0 0 0 0 0     (DW_OP_addr: 2009d0)
[...]

(unsued) foo liba.so(.data).

  • 2 foo ( liba.so b);
  • DWARF ;
  • secone.

foo?

+3
2

, .

.

foo

( ), foo b, liba.so:

nm b | grep foo
0000000000600c68 B foo
+1

( Oracle, @Employed Russian.)

, PIC, , PIC- , PIC:

  • -PIC-;
  • ;
  • ;
  • ( ).

:

$readelf -r b

Relocation section '.rela.dyn' at offset 0x638 contains 2 entries:
  Offset          Info           Type           Sym. Value    Sym. Name + Addend
000000600c58  000300000006 R_X86_64_GLOB_DAT 0000000000000000 __gmon_start__ + 0
000000600ca8  001200000005 R_X86_64_COPY     0000000000600ca8 foo + 0

GOT + PLT , PIC.

0

All Articles