This is the mail archive of the
binutils@sources.redhat.com
mailing list for the binutils project.
MIPS patch to avoid lazy binding in la macros
- From: Richard Sandiford <rsandifo at redhat dot com>
- To: binutils at sources dot redhat dot com
- Cc: echristo at redhat dot com
- Date: 21 Feb 2003 00:23:45 +0000
- Subject: MIPS patch to avoid lazy binding in la macros
Suppose foo is a weak function. For -KPIC, one implementation of:
if (foo)
foo ()
might be:
la $25,foo
beqz $25,1f
jal $25
1:
But due to a suspect feature, gas treats
la $25,foo
as a special case and allows foo to be lazily bound. Not the
desired effect. ;)
I hit this on mips-rewrite branch while trying to improve the call
patterns. Indirect calls have traditionally had an 'r' constraint,
even for TARGET_ABICALLS. So although gcc can sometimes use $25
as the call destination, it often uses some other register instead.
The assembler then has to copy that register into $25.
The mips-rewrite patterns know about $25, giving the code above.
I guess it's just luck that we haven't been bitten by this before...
Patch tested in the same way as the last one. OK to install?
Richard
PS. I checked that the new behaviour is consistent with SGI's assembler.
gas/
* config/tc-mips.c (macro): Don't use BFD_RELOC_MIPS_CALL16
in LA macros.
gas/testsuite
* gas/mips/elf-rel15.[sd]: New test.
* gas/mips/mips.exp: Run it.
diff -cpdrN gas.bak/config/tc-mips.c gas/config/tc-mips.c
*** gas.bak/config/tc-mips.c Thu Feb 20 21:59:00 2003
--- gas/config/tc-mips.c Thu Feb 20 22:00:08 2003
*************** macro (ip)
*** 5000,5008 ****
expr1.X_add_number = offset_expr.X_add_number;
offset_expr.X_add_number = 0;
frag_grow (32);
! if (expr1.X_add_number == 0 && tempreg == PIC_CALL_REG)
! lw_reloc_type = (int) BFD_RELOC_MIPS_CALL16;
! else if (HAVE_NEWABI)
lw_reloc_type = (int) BFD_RELOC_MIPS_GOT_DISP;
macro_build ((char *) NULL, &icnt, &offset_expr,
HAVE_32BIT_ADDRESSES ? "lw" : "ld",
--- 5000,5006 ----
expr1.X_add_number = offset_expr.X_add_number;
offset_expr.X_add_number = 0;
frag_grow (32);
! if (HAVE_NEWABI)
lw_reloc_type = (int) BFD_RELOC_MIPS_GOT_DISP;
macro_build ((char *) NULL, &icnt, &offset_expr,
HAVE_32BIT_ADDRESSES ? "lw" : "ld",
diff -cpdrN gas.bak/testsuite/gas/mips/elf-rel15.d gas/testsuite/gas/mips/elf-rel15.d
*** gas.bak/testsuite/gas/mips/elf-rel15.d Thu Jan 1 01:00:00 1970
--- gas/testsuite/gas/mips/elf-rel15.d Thu Feb 20 21:08:03 2003
***************
*** 0 ****
--- 1,12 ----
+ #as: -march=mips2 -mabi=32 -KPIC
+ #objdump: -M gpr-names=numeric -dr
+ #name: MIPS ELF reloc 15
+
+ .*: file format .*
+
+ Disassembly of section \.text:
+
+ 0+00 <foo>:
+ 0: 8f990000 lw \$25,0\(\$28\)
+ 0: R_MIPS_GOT16 bar
+ \.\.\.
diff -cpdrN gas.bak/testsuite/gas/mips/elf-rel15.s gas/testsuite/gas/mips/elf-rel15.s
*** gas.bak/testsuite/gas/mips/elf-rel15.s Thu Jan 1 01:00:00 1970
--- gas/testsuite/gas/mips/elf-rel15.s Thu Feb 20 21:09:09 2003
***************
*** 0 ****
--- 1,5 ----
+ .ent foo
+ foo:
+ la $25,bar
+ .space 32
+ .end foo
diff -cpdrN gas.bak/testsuite/gas/mips/mips.exp gas/testsuite/gas/mips/mips.exp
*** gas.bak/testsuite/gas/mips/mips.exp Thu Feb 20 22:01:04 2003
--- gas/testsuite/gas/mips/mips.exp Thu Feb 20 21:57:59 2003
*************** if { [istarget mips*-*-*] } then {
*** 611,616 ****
--- 611,617 ----
run_dump_test "elf-rel12"
run_dump_test "elf-rel13"
run_dump_test "elf-rel14"
+ run_dump_test "elf-rel15"
run_dump_test "${tmips}${el}empic"
run_dump_test "empic2"
run_dump_test "empic3_e"