Add the GOT base for GOT32 relocs against IFUNC

Add the GOT base for R_386_GOT32/R_386_GOT32X relocations against IFUNC
symbols if there is no base register and disallow them for PIC.

bfd/

	PR ld/20244
	* elf32-i386.c (elf_i386_relocate_section): Add the .got.plt
	section address for R_386_GOT32/R_386_GOT32X relocations against
	IFUNC symbols if there is no base register and return error for
	PIC.

ld/

	PR ld/20244
	* testsuite/ld-i386/i386.exp: Run pr20244-2a, pr20244-2b,
	pr20244-2c and pr20244-2d.
	* testsuite/ld-i386/no-plt.exp: Run pr20244-3a and pr20244-3b.
	* testsuite/ld-i386/pr20244-2.s: New file.
	* testsuite/ld-i386/pr20244-2a.d: Likewise.
	* testsuite/ld-i386/pr20244-2b.d: Likewise.
	* testsuite/ld-i386/pr20244-2c.d: Likewise.
	* testsuite/ld-i386/pr20244-2d.d: Likewise.
	* testsuite/ld-i386/pr20244-3a.c: Likewise.
	* testsuite/ld-i386/pr20244-3b.S: Likewise.
	* testsuite/ld-i386/pr20244-3c.S: Likewise.
	* testsuite/ld-i386/pr20244-3d.S: Likewise.
This commit is contained in:
H.J. Lu 2016-06-13 11:06:10 -07:00
parent ca8c86efe7
commit 712ec27916
14 changed files with 260 additions and 5 deletions

View File

@ -1,3 +1,11 @@
2016-06-13 H.J. Lu <hongjiu.lu@intel.com>
PR ld/20244
* elf32-i386.c (elf_i386_relocate_section): Add the .got.plt
section address for R_386_GOT32/R_386_GOT32X relocations against
IFUNC symbols if there is no base register and return error for
PIC.
2016-06-13 H.J. Lu <hongjiu.lu@intel.com>
* elf32-i386.c (elf_i386_relocate_section): Simplify IFUNC

View File

@ -4039,9 +4039,20 @@ elf_i386_relocate_section (bfd *output_bfd,
- gotplt->output_section->vma
- gotplt->output_offset);
/* Adjust for static executables. */
if (htab->elf.splt == NULL)
relocation += gotplt->output_offset;
if ((*(contents + rel->r_offset - 1) & 0xc7) == 0x5)
{
if (bfd_link_pic (info))
goto disallow_got32;
/* Add the GOT base if there is no base register. */
relocation += (gotplt->output_section->vma
+ gotplt->output_offset);
}
else if (htab->elf.splt == NULL)
{
/* Adjust for static executables. */
relocation += gotplt->output_offset;
}
goto do_relocation;
@ -4214,6 +4225,7 @@ r_386_got32:
is. */
const char *name;
disallow_got32:
if (h == NULL)
name = bfd_elf_sym_name (input_bfd, symtab_hdr, sym,
NULL);
@ -4221,8 +4233,8 @@ r_386_got32:
name = h->root.root.string;
(*_bfd_error_handler)
(_("%B: direct GOT relocation R_386_GOT32 against `%s' without base register can not be used when making a shared object"),
input_bfd, name);
(_("%B: direct GOT relocation %s against `%s' without base register can not be used when making a shared object"),
input_bfd, howto->name, name);
bfd_set_error (bfd_error_bad_value);
return FALSE;
}

View File

@ -1,3 +1,19 @@
2016-06-13 H.J. Lu <hongjiu.lu@intel.com>
PR ld/20244
* testsuite/ld-i386/i386.exp: Run pr20244-2a, pr20244-2b,
pr20244-2c and pr20244-2d.
* testsuite/ld-i386/no-plt.exp: Run pr20244-3a and pr20244-3b.
* testsuite/ld-i386/pr20244-2.s: New file.
* testsuite/ld-i386/pr20244-2a.d: Likewise.
* testsuite/ld-i386/pr20244-2b.d: Likewise.
* testsuite/ld-i386/pr20244-2c.d: Likewise.
* testsuite/ld-i386/pr20244-2d.d: Likewise.
* testsuite/ld-i386/pr20244-3a.c: Likewise.
* testsuite/ld-i386/pr20244-3b.S: Likewise.
* testsuite/ld-i386/pr20244-3c.S: Likewise.
* testsuite/ld-i386/pr20244-3d.S: Likewise.
2016-06-13 H.J. Lu <hongjiu.lu@intel.com>
* testsuite/ld-i386/i386.exp: Run ifunc-1a and ifunc-1b.

View File

@ -403,6 +403,10 @@ run_dump_test "pr20117"
run_dump_test "pr20244-1a"
run_dump_test "pr20244-1b"
run_dump_test "pr20244-1c"
run_dump_test "pr20244-2a"
run_dump_test "pr20244-2b"
run_dump_test "pr20244-2c"
run_dump_test "pr20244-2d"
if { !([istarget "i?86-*-linux*"]
|| [istarget "i?86-*-gnu*"]

View File

@ -255,3 +255,36 @@ run_ld_link_exec_tests [] [list \
"pass.out" \
] \
]
# Run-time tests which require working IFUNC support.
if { [check_ifunc_available] } {
run_cc_link_tests [list \
[list \
"Build pr20244-3a.o pr20244-3b.o pr20244-3c.o pr20244-3d.o" \
"" \
"-fPIC -O2 -g" \
{ pr20244-3a.c pr20244-3b.S pr20244-3c.S pr20244-3d.S } \
] \
]
run_ld_link_exec_tests [] [list \
[list \
"Run pr20244-3a" \
"tmpdir/pr20244-3a.o tmpdir/pr20244-3b.o \
tmpdir/pr20244-3c.o tmpdir/pr20244-3d.o" \
"" \
{ dummy.c } \
"pr20244-3a" \
"pass.out" \
] \
[list \
"Run pr20244-3b" \
"--static tmpdir/pr20244-3a.o tmpdir/pr20244-3b.o \
tmpdir/pr20244-3c.o tmpdir/pr20244-3d.o" \
"" \
{ dummy.c } \
"pr20244-3b" \
"pass.out" \
] \
]
}

View File

@ -0,0 +1,17 @@
.text
.globl foo
.type foo, @gnu_indirect_function
foo:
ret
.text
.type bar, @gnu_indirect_function
bar:
ret
.globl _start
.type _start, @function
_start:
call *foo@GOT
jmp *bar@GOT
movl $0, bar@GOT
cmpl $0, foo@GOT
movl $bar@GOT, %ecx

View File

@ -0,0 +1,43 @@
#source: pr20244-2.s
#as: --32
#ld: -m elf_i386
#objdump: --sym -dw
#notarget: i?86-*-nacl* x86_64-*-nacl*
.*: +file format .*
SYMBOL TABLE:
#...
0+80480b1 l i .text 00000000 bar
#...
0+80480b2 g F .text 00000000 _start
#...
0+80480b0 g i .text 00000000 foo
#...
Disassembly of section .plt:
0+8048090 <.plt>:
+[a-f0-9]+: ff 25 e0 90 04 08 jmp \*0x80490e0
+[a-f0-9]+: 68 00 00 00 00 push \$0x0
+[a-f0-9]+: e9 00 00 00 00 jmp 80480a0 <foo-0x10>
+[a-f0-9]+: ff 25 e4 90 04 08 jmp \*0x80490e4
+[a-f0-9]+: 68 00 00 00 00 push \$0x0
+[a-f0-9]+: e9 00 00 00 00 jmp 80480b0 <foo>
Disassembly of section .text:
0+80480b0 <foo>:
+[a-f0-9]+: c3 ret
0+80480b1 <bar>:
+[a-f0-9]+: c3 ret
0+80480b2 <_start>:
+[a-f0-9]+: ff 15 e0 90 04 08 call \*0x80490e0
+[a-f0-9]+: ff 25 e4 90 04 08 jmp \*0x80490e4
+[a-f0-9]+: c7 05 e4 90 04 08 00 00 00 00 movl \$0x0,0x80490e4
+[a-f0-9]+: 83 3d e0 90 04 08 00 cmpl \$0x0,0x80490e0
+[a-f0-9]+: b9 10 00 00 00 mov \$0x10,%ecx
#pass

View File

@ -0,0 +1,11 @@
#source: pr20244-2.s
#as: --32
#ld: -m elf_i386
#objdump: -s -j .got.plt
#notarget: i?86-*-nacl* x86_64-*-nacl*
.*: +file format .*
Contents of section .got.plt:
80490d4 00000000 00000000 00000000 b0800408 ................
80490e4 b1800408 ....

View File

@ -0,0 +1,10 @@
#source: pr20244-2.s
#as: --32
#ld: -m elf_i386
#readelf: -rW
#notarget: i?86-*-nacl* x86_64-*-nacl*
Relocation section '.rel.plt' at offset 0x74 contains 2 entries:
Offset Info Type Sym. Value Symbol's Name
0+80490e4 0000002a R_386_IRELATIVE
0+80490e0 0000002a R_386_IRELATIVE

View File

@ -0,0 +1,4 @@
#source: pr20244-2.s
#as: --32
#ld: -pie -m elf_i386
#error: direct GOT relocation R_386_GOT32X against `foo' without base register can not be used when making a shared object

View File

@ -0,0 +1,8 @@
extern void check (void);
int
main ()
{
check ();
return 0;
}

View File

@ -0,0 +1,30 @@
.section .rodata.str1.1,"aMS",@progbits,1
.LC0:
.string "PASS"
.text
.p2align 4,,15
.globl check
.type check, @function
check:
subl $12, %esp
call *get_func1@GOT
cmpl $func1, %eax
jne .L3
call *func1@GOT
cmpl $1, %eax
jne .L3
call *call_func1@GOT
cmpl $1, %eax
jne .L3
call *call_func2@GOT
cmpl $2, %eax
jne .L3
subl $12, %esp
pushl $.LC0
call *puts@GOT
addl $28, %esp
ret
.L3:
call *abort@GOT
.size check, .-check
.section .note.GNU-stack,"",@progbits

View File

@ -0,0 +1,15 @@
.text
.p2align 4,,15
.globl get_func1
.type get_func1, @function
get_func1:
movl func1@GOT, %eax
ret
.size get_func1, .-get_func1
.p2align 4,,15
.globl call_func1
.type call_func1, @function
call_func1:
jmp *func1@GOT
.size call_func1, .-call_func1
.section .note.GNU-stack,"",@progbits

View File

@ -0,0 +1,44 @@
.text
.p2align 4,,15
.type implementation1, @function
implementation1:
movl $1, %eax
ret
.size implementation1, .-implementation1
.p2align 4,,15
.type implementation2, @function
implementation2:
movl $2, %eax
ret
.size implementation2, .-implementation2
.p2align 4,,15
.type resolver2, @function
resolver2:
movl implementation2@GOT, %eax
ret
.size resolver2, .-resolver2
.type func2, @gnu_indirect_function
.set func2,resolver2
.p2align 4,,15
.type resolver1, @function
resolver1:
movl implementation1@GOT, %eax
ret
.size resolver1, .-resolver1
.globl func1
.type func1, @gnu_indirect_function
.set func1,resolver1
.p2align 4,,15
.globl get_func2
.type get_func2, @function
get_func2:
movl func2@GOT, %eax
ret
.size get_func2, .-get_func2
.p2align 4,,15
.globl call_func2
.type call_func2, @function
call_func2:
jmp *func2@GOT
.size call_func2, .-call_func2
.section .note.GNU-stack,"",@progbits