diff options
author | Richard Henderson <rth@redhat.com> | 2002-05-28 18:37:22 -0700 |
---|---|---|
committer | Richard Henderson <rth@gcc.gnu.org> | 2002-05-28 18:37:22 -0700 |
commit | 66edd3b4ca7e6cc9a6d09fc4ba5d890f04c66ead (patch) | |
tree | 0ac9200a04b0ae4859b32189c21877c9a830da1a | |
parent | 52f4fff6829c14f4cdf754751566df0fb28f5ad5 (diff) | |
download | gcc-66edd3b4ca7e6cc9a6d09fc4ba5d890f04c66ead.zip gcc-66edd3b4ca7e6cc9a6d09fc4ba5d890f04c66ead.tar.gz gcc-66edd3b4ca7e6cc9a6d09fc4ba5d890f04c66ead.tar.bz2 |
i386.c (ix86_save_reg): Examine regs_ever_live...
* config/i386/i386.c (ix86_save_reg): Examine regs_ever_live,
not current_function_uses_pic_offset_table and
current_function_uses_const_pool; examine current_function_profile.
(ix86_expand_prologue): Likewise. Add pic_offset_table_rtx as
input to blockage if needed.
(ix86_expand_call): Do not set current_function_uses_pic_offset_table.
(legitimize_pic_address): Likewise. Set regs_ever_live for
pic_offset_table_rtx when invoked during reload.
* config/i386/i386.h (FINALIZE_PIC): Remove.
* config/i386/i386.md (tablejump): Reformat. Do not set
current_function_uses_pic_offset_table.
(tls_global_dynamic, tls_local_dynamic_base): Likewise.
(blockage): Accept anything as operand 0.
From-SVN: r53981
-rw-r--r-- | gcc/ChangeLog | 16 | ||||
-rw-r--r-- | gcc/config/i386/i386.c | 47 | ||||
-rw-r--r-- | gcc/config/i386/i386.h | 11 | ||||
-rw-r--r-- | gcc/config/i386/i386.md | 39 |
4 files changed, 61 insertions, 52 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index eb3f5f0..f391122 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,19 @@ +2002-05-28 Richard Henderson <rth@redhat.com> + + * config/i386/i386.c (ix86_save_reg): Examine regs_ever_live, + not current_function_uses_pic_offset_table and + current_function_uses_const_pool; examine current_function_profile. + (ix86_expand_prologue): Likewise. Add pic_offset_table_rtx as + input to blockage if needed. + (ix86_expand_call): Do not set current_function_uses_pic_offset_table. + (legitimize_pic_address): Likewise. Set regs_ever_live for + pic_offset_table_rtx when invoked during reload. + * config/i386/i386.h (FINALIZE_PIC): Remove. + * config/i386/i386.md (tablejump): Reformat. Do not set + current_function_uses_pic_offset_table. + (tls_global_dynamic, tls_local_dynamic_base): Likewise. + (blockage): Accept anything as operand 0. + 2002-05-28 Jason Thorpe <thorpej@wasabisystems.com> * config/netbsd-aout.h (NETBSD_OS_CPP_BUILTINS_AOUT): Define diff --git a/gcc/config/i386/i386.c b/gcc/config/i386/i386.c index 39831af..7e98741 100644 --- a/gcc/config/i386/i386.c +++ b/gcc/config/i386/i386.c @@ -4012,8 +4012,8 @@ ix86_save_reg (regno, maybe_eh_return) int maybe_eh_return; { if (regno == PIC_OFFSET_TABLE_REGNUM - && (current_function_uses_pic_offset_table - || current_function_uses_const_pool + && (regs_ever_live[regno] + || current_function_profile || current_function_calls_eh_return)) return 1; @@ -4235,9 +4235,9 @@ void ix86_expand_prologue () { rtx insn; - int pic_reg_used = (flag_pic && (current_function_uses_pic_offset_table - || current_function_uses_const_pool) - && !TARGET_64BIT); + int pic_reg_used = (PIC_OFFSET_TABLE_REGNUM != INVALID_REGNUM + && (regs_ever_live[PIC_OFFSET_TABLE_REGNUM] + || current_function_profile)); struct ix86_frame frame; int use_mov = 0; HOST_WIDE_INT allocate; @@ -4320,18 +4320,19 @@ ix86_expand_prologue () { insn = emit_insn (gen_set_got (pic_offset_table_rtx)); - /* ??? The current_function_uses_pic_offset_table flag is woefully - inaccurate, as it isn't updated as code gets deleted. Allow the - thing to be removed. A better solution would be to actually get - proper liveness for ebx, as then we won't save/restore it too. */ + /* Even with accurate pre-reload life analysis, we can wind up + deleting all references to the pic register after reload. + Consider if cross-jumping unifies two sides of a branch + controled by a comparison vs the only read from a global. + In which case, allow the set_got to be deleted, though we're + too late to do anything about the ebx save in the prologue. */ REG_NOTES (insn) = gen_rtx_EXPR_LIST (REG_MAYBE_DEAD, const0_rtx, NULL); } - /* If we are profiling, make sure no instructions are scheduled before - the call to mcount. However, if -fpic, the above call will have - done that. */ - if (current_function_profile && ! pic_reg_used) - emit_insn (gen_blockage ()); + /* Prevent function calls from be scheduled before the call to mcount. + In the pic_reg_used case, make sure that the got load isn't deleted. */ + if (current_function_profile) + emit_insn (gen_blockage (pic_reg_used ? pic_offset_table_rtx : const0_rtx)); } /* Emit code to restore saved registers using MOV insns. First register @@ -5245,7 +5246,8 @@ legitimize_pic_address (orig, reg) /* This symbol may be referenced via a displacement from the PIC base address (@GOTOFF). */ - current_function_uses_pic_offset_table = 1; + if (reload_in_progress) + regs_ever_live[PIC_OFFSET_TABLE_REGNUM] = 1; new = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_GOTOFF); new = gen_rtx_CONST (Pmode, new); new = gen_rtx_PLUS (Pmode, pic_offset_table_rtx, new); @@ -5261,7 +5263,6 @@ legitimize_pic_address (orig, reg) { if (TARGET_64BIT) { - current_function_uses_pic_offset_table = 1; new = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_GOTPCREL); new = gen_rtx_CONST (Pmode, new); new = gen_rtx_MEM (Pmode, new); @@ -5281,7 +5282,8 @@ legitimize_pic_address (orig, reg) /* This symbol must be referenced via a load from the Global Offset Table (@GOT). */ - current_function_uses_pic_offset_table = 1; + if (reload_in_progress) + regs_ever_live[PIC_OFFSET_TABLE_REGNUM] = 1; new = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_GOT); new = gen_rtx_CONST (Pmode, new); new = gen_rtx_PLUS (Pmode, pic_offset_table_rtx, new); @@ -5322,7 +5324,8 @@ legitimize_pic_address (orig, reg) { if (!TARGET_64BIT) { - current_function_uses_pic_offset_table = 1; + if (reload_in_progress) + regs_ever_live[PIC_OFFSET_TABLE_REGNUM] = 1; new = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, op0), UNSPEC_GOTOFF); new = gen_rtx_PLUS (Pmode, new, op1); @@ -5518,7 +5521,8 @@ legitimize_address (x, oldx, mode) case TLS_MODEL_INITIAL_EXEC: if (flag_pic) { - current_function_uses_pic_offset_table = 1; + if (reload_in_progress) + regs_ever_live[PIC_OFFSET_TABLE_REGNUM] = 1; pic = pic_offset_table_rtx; } else @@ -10464,10 +10468,7 @@ ix86_expand_call (retval, fnaddr, callarg1, callarg2, pop) if (! TARGET_64BIT && flag_pic && GET_CODE (XEXP (fnaddr, 0)) == SYMBOL_REF && ! SYMBOL_REF_FLAG (XEXP (fnaddr, 0))) - { - current_function_uses_pic_offset_table = 1; - use_reg (&use, pic_offset_table_rtx); - } + use_reg (&use, pic_offset_table_rtx); if (TARGET_64BIT && INTVAL (callarg2) >= 0) { diff --git a/gcc/config/i386/i386.h b/gcc/config/i386/i386.h index 5946370..970dfdf 100644 --- a/gcc/config/i386/i386.h +++ b/gcc/config/i386/i386.h @@ -2406,17 +2406,6 @@ enum ix86_builtins fputs (user_label_prefix, FILE); \ fputs (xname, FILE); \ } while (0) - -/* The `FINALIZE_PIC' macro serves as a hook to emit these special - codes once the function is being compiled into assembly code, but - not before. (It is not done before, because in the case of - compiling an inline function, it would lead to multiple PIC - prologues being included in functions which used inline functions - and were compiled to assembly language.) */ - -#define FINALIZE_PIC \ - (current_function_uses_pic_offset_table |= current_function_profile) - /* Max number of args passed in registers. If this is more than 3, we will have problems with ebx (register #4), since it is a caller save register and diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md index 2d19645..1c99f60 100644 --- a/gcc/config/i386/i386.md +++ b/gcc/config/i386/i386.md @@ -12699,29 +12699,34 @@ (use (label_ref (match_operand 1 "" "")))])] "" { - /* In PIC mode, the table entries are stored GOT-relative. Convert - the relative address to an absolute address. */ + /* In PIC mode, the table entries are stored GOT (32-bit) or PC (64-bit) + relative. Convert the relative address to an absolute address. */ if (flag_pic) { + rtx op0, op1; + enum rtx_code code; + if (TARGET_64BIT) - operands[0] = expand_simple_binop (Pmode, PLUS, operands[0], - gen_rtx_LABEL_REF (Pmode, operands[1]), - NULL_RTX, 0, - OPTAB_DIRECT); + { + code = PLUS; + op0 = operands[0]; + op1 = gen_rtx_LABEL_REF (Pmode, operands[1]); + } else if (HAVE_AS_GOTOFF_IN_DATA) { - operands[0] = expand_simple_binop (Pmode, PLUS, operands[0], - pic_offset_table_rtx, NULL_RTX, - 1, OPTAB_DIRECT); - current_function_uses_pic_offset_table = 1; + code = PLUS; + op0 = operands[0]; + op1 = pic_offset_table_rtx; } else { - operands[0] = expand_simple_binop (Pmode, MINUS, pic_offset_table_rtx, - operands[0], NULL_RTX, 1, - OPTAB_DIRECT); - current_function_uses_pic_offset_table = 1; + code = MINUS; + op0 = pic_offset_table_rtx; + op1 = operands[0]; } + + operands[0] = expand_simple_binop (Pmode, code, op0, op1, NULL_RTX, 1, + OPTAB_DIRECT); } }) @@ -13061,7 +13066,7 @@ registers we stored in the result block. We avoid problems by claiming that all hard registers are used and clobbered at this point. */ - emit_insn (gen_blockage ()); + emit_insn (gen_blockage (const0_rtx)); DONE; }) @@ -13072,7 +13077,7 @@ ;; all of memory. This blocks insns from being moved across this point. (define_insn "blockage" - [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)] + [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_BLOCKAGE)] "" "" [(set_attr "length" "0")]) @@ -13391,7 +13396,6 @@ { if (!flag_pic) abort (); - current_function_uses_pic_offset_table = 1; operands[2] = pic_offset_table_rtx; operands[3] = ix86_tls_get_addr (); }) @@ -13434,7 +13438,6 @@ { if (!flag_pic) abort (); - current_function_uses_pic_offset_table = 1; operands[1] = pic_offset_table_rtx; operands[2] = ix86_tls_get_addr (); }) |