This is the mail archive of the glibc-bugs@sourceware.org mailing list for the glibc project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[Bug dynamic-link/19818] Absolute (SHN_ABS) symbols incorrectly relocated by the base address


https://sourceware.org/bugzilla/show_bug.cgi?id=19818

Maciej W. Rozycki <macro@linux-mips.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |macro@linux-mips.org
          Component|ld                          |dynamic-link
            Version|2.27                        |2.26
             Blocks|                            |21375
            Product|binutils                    |glibc
            Summary|Absolute symbol is handled  |Absolute (SHN_ABS) symbols
                   |incorrectly in PIE          |incorrectly relocated by
                   |                            |the base address

--- Comment #3 from Maciej W. Rozycki <macro@linux-mips.org> ---
This is a bug in the dynamic loader, not the static linker, and has been
also observed in the course of PR ld/21375 investigation, which it is a
blocker for (due to the peculiarities of the MIPS psABI, and its implicit
GOT handling in particular).

We have a bug in the run-time loader in the handling of absolute symbols
(symbols relative to the special SHN_ABS section).  Such symbols are
supposed to retain their numeric value across the static link and then
dynamic loading.  However our run-time loader does not pay attention to
the special section index and treats absolute symbols like regular
symbols; in fact there is no mention of the SHN_ABS macro anywhere except
from its definition in the elf/elf.h header.

To reproduce with the `x86_64-linux-gnu' target use the following program
and recipe:

$ cat test.c
#include <stdio.h>

char *x (void);

int
main (void)
{
  printf ("a: %p\n", x ());

  return 0;
}
$ cat libtest.c
extern char a __attribute__ ((weak));

char *
x (void)
{
  return &a;
}
$ gcc -fPIC -shared -Wl,--defsym=a=3 -o libtest.so libtest.c
$ gcc -o test test.c -Wl,-rpath,$(pwd) libtest.so

Here's the result obtained -- as you can see the GOT relocation and the
symbol table have both been set up correctly for `a':

$ readelf --relocs libtest.so

Relocation section '.rela.dyn' at offset 0x468 contains 9 entries:
  Offset          Info           Type           Sym. Value    Sym. Name +
Addend
000000200e28  000000000008 R_X86_64_RELATIVE                    650
000000200e30  000000000008 R_X86_64_RELATIVE                    610
000000201018  000000000008 R_X86_64_RELATIVE                    201018
000000200fd0  000200000006 R_X86_64_GLOB_DAT 0000000000000000
_ITM_deregisterTMClone + 0
000000200fd8  000300000006 R_X86_64_GLOB_DAT 0000000000000000 __gmon_start__ +
0
000000200fe0  000a00000006 R_X86_64_GLOB_DAT 0000000000000003 a + 0
000000200fe8  000400000006 R_X86_64_GLOB_DAT 0000000000000000
_Jv_RegisterClasses + 0
000000200ff0  000500000006 R_X86_64_GLOB_DAT 0000000000000000
_ITM_registerTMCloneTa + 0
000000200ff8  000600000006 R_X86_64_GLOB_DAT 0000000000000000
__cxa_finalize@GLIBC_2.2.5 + 0
$ readelf --dyn-syms libtest.so

Symbol table '.dynsym' contains 14 entries:
   Num:    Value          Size Type    Bind   Vis      Ndx Name
     0: 0000000000000000     0 NOTYPE  LOCAL  DEFAULT  UND
     1: 0000000000000540     0 SECTION LOCAL  DEFAULT    8
     2: 0000000000000000     0 NOTYPE  WEAK   DEFAULT  UND
_ITM_deregisterTMCloneTab
     3: 0000000000000000     0 NOTYPE  WEAK   DEFAULT  UND __gmon_start__
     4: 0000000000000000     0 NOTYPE  WEAK   DEFAULT  UND _Jv_RegisterClasses
     5: 0000000000000000     0 NOTYPE  WEAK   DEFAULT  UND
_ITM_registerTMCloneTable
     6: 0000000000000000     0 FUNC    WEAK   DEFAULT  UND
__cxa_finalize@GLIBC_2.2.5 (2)
     7: 0000000000201020     0 NOTYPE  GLOBAL DEFAULT   21 _edata
     8: 0000000000000680    13 FUNC    GLOBAL DEFAULT   11 x
     9: 0000000000201028     0 NOTYPE  GLOBAL DEFAULT   22 _end
    10: 0000000000000003     0 NOTYPE  GLOBAL DEFAULT  ABS a
    11: 0000000000201020     0 NOTYPE  GLOBAL DEFAULT   22 __bss_start
    12: 0000000000000540     0 FUNC    GLOBAL DEFAULT    8 _init
    13: 0000000000000690     0 FUNC    GLOBAL DEFAULT   12 _fini
$ ./test
a: 0x7ff43a511003
$ 

-- and yet the value of `a' printed is not 3.  Similarly with the
`mips-linux-gnu' target (o32 ABI):

$ readelf -A libtest.so
Attribute Section: gnu
File Attributes
  Tag_GNU_MIPS_ABI_FP: Hard float (32-bit CPU, Any FPU)

MIPS ABI Flags Version: 0

ISA: MIPS32r2
GPR size: 32
CPR1 size: 32
CPR2 size: 0
FP ABI: Hard float (32-bit CPU, Any FPU)
ISA Extension: None
ASEs:
        None
FLAGS 1: 00000000
FLAGS 2: 00000000

Primary GOT:
 Canonical gp value: 00018810

 Reserved entries:
   Address     Access  Initial Purpose
  00010820 -32752(gp) 00000000 Lazy resolver
  00010824 -32748(gp) 80000000 Module pointer (GNU extension)

 Local entries:
   Address     Access  Initial
  00010828 -32744(gp) 00010820
  0001082c -32740(gp) 00010000
  00010830 -32736(gp) 0001085c
  00010834 -32732(gp) 00010818
  00010838 -32728(gp) 00000000
  0001083c -32724(gp) 00000000
  00010840 -32720(gp) 00000000
  00010844 -32716(gp) 00000000

 Global entries:
   Address     Access  Initial Sym.Val. Type    Ndx Name
  00010848 -32712(gp) 00000000 00000000 NOTYPE  UND _ITM_registerTMCloneTable
  0001084c -32708(gp) 00000003 00000003 NOTYPE  ABS a
  00010850 -32704(gp) 00000000 00000000 FUNC    UND __gmon_start__
  00010854 -32700(gp) 00000000 00000000 NOTYPE  UND _ITM_deregisterTMCloneTable
  00010858 -32696(gp) 00000000 00000000 FUNC    UND __cxa_finalize

$ readelf --dyn-syms libtest.so

Symbol table '.dynsym' contains 17 entries:
   Num:    Value  Size Type    Bind   Vis      Ndx Name
     0: 00000000     0 NOTYPE  LOCAL  DEFAULT  UND
     1: 00000510     0 SECTION LOCAL  DEFAULT   10
     2: 00010860     0 NOTYPE  GLOBAL DEFAULT   17 _edata
     3: 00000730    48 FUNC    GLOBAL DEFAULT   11 x
     4: 000007c0     0 FUNC    GLOBAL DEFAULT   12 _fini
     5: 00010820     0 NOTYPE  GLOBAL DEFAULT   16 _fdata
     6: 00010870     0 NOTYPE  GLOBAL DEFAULT   18 _end
     7: 00010860     0 NOTYPE  GLOBAL DEFAULT   18 __bss_start
     8: 00018810     0 SECTION GLOBAL DEFAULT  ABS _gp_disp
     9: 000005a0     0 NOTYPE  GLOBAL DEFAULT   11 _ftext
    10: 00010860     0 NOTYPE  GLOBAL DEFAULT   18 _fbss
    11: 00000510     0 FUNC    GLOBAL DEFAULT   10 _init
    12: 00000000     0 NOTYPE  WEAK   DEFAULT  UND _ITM_registerTMCloneTable
    13: 00000003     0 NOTYPE  GLOBAL DEFAULT  ABS a
    14: 00000000     0 FUNC    WEAK   DEFAULT  UND __gmon_start__
    15: 00000000     0 NOTYPE  WEAK   DEFAULT  UND _ITM_deregisterTMCloneTab
    16: 00000000     0 FUNC    WEAK   DEFAULT  UND __cxa_finalize@GLIBC_2.2 (2)
$ ./test
a: 0x77a14003
$ 

-- again, the value of `a' printed is not 3.

This is contrary to the ELF gABI that mandates [1]:

"SHN_ABS
    The symbol has an absolute value that will not change because of
    relocation."

Further observations have been made in the course of discussion regarding
PR ld/20402, which is a corresponding static linker issue affecting some
targets.

References:

[1] "System V Application Binary Interface - DRAFT - 19 October 2010",
    The SCO Group, Section "Symbol Table",
    <http://www.sco.com/developers/gabi/2012-12-31/ch4.symtab.html>


Referenced Bugs:

https://sourceware.org/bugzilla/show_bug.cgi?id=21375
[Bug 21375] MIPS: Non-zero run-time value produced for PIC references to
undefined hidden or internal weak symbols
-- 
You are receiving this mail because:
You are on the CC list for the bug.

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]