From: Richard Henderson Date: Thu, 23 May 2002 05:20:25 +0000 (-0700) Subject: i386.c (ix86_expand_call): New function, extracted from md call patterns. X-Git-Tag: releases/gcc-3.3.0~4871 X-Git-Url: https://gcc.gnu.org/git/?a=commitdiff_plain;h=0e07aff3464497cde5a8f24fe1f4571e8499750a;p=gcc.git i386.c (ix86_expand_call): New function, extracted from md call patterns. * config/i386/i386.c (ix86_expand_call): New function, extracted from md call patterns. Add pic_offset_table_rtx to CALL_INSN_FUNCTION_USAGE when needed. * config/i386/i386.md (call_pop, call): Use ix86_expand_call. (call_value_pop, call_value, untyped_call): Likewise. (call_exp, call_value_exp): Remove. * config/i386/i386-protos.h: Update. From-SVN: r53763 --- diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 7225f3915d0d..42368e2ab3b0 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,13 @@ +2002-05-22 Richard Henderson + + * config/i386/i386.c (ix86_expand_call): New function, extracted + from md call patterns. Add pic_offset_table_rtx to + CALL_INSN_FUNCTION_USAGE when needed. + * config/i386/i386.md (call_pop, call): Use ix86_expand_call. + (call_value_pop, call_value, untyped_call): Likewise. + (call_exp, call_value_exp): Remove. + * config/i386/i386-protos.h: Update. + 2002-05-22 Richard Henderson * varasm.c (default_section_type_flags): Check for VAR_DECL diff --git a/gcc/config/i386/i386-protos.h b/gcc/config/i386/i386-protos.h index a33a81502227..c02e2e3ffc76 100644 --- a/gcc/config/i386/i386-protos.h +++ b/gcc/config/i386/i386-protos.h @@ -121,6 +121,7 @@ extern void ix86_expand_branch PARAMS ((enum rtx_code, rtx)); extern int ix86_expand_setcc PARAMS ((enum rtx_code, rtx)); extern int ix86_expand_int_movcc PARAMS ((rtx[])); extern int ix86_expand_fp_movcc PARAMS ((rtx[])); +extern void ix86_expand_call PARAMS ((rtx, rtx, rtx, rtx, rtx)); extern void x86_initialize_trampoline PARAMS ((rtx, rtx, rtx)); extern rtx ix86_zero_extend_to_Pmode PARAMS ((rtx)); extern void ix86_split_long_move PARAMS ((rtx[])); diff --git a/gcc/config/i386/i386.c b/gcc/config/i386/i386.c index 1b8c9b8e1242..650513191697 100644 --- a/gcc/config/i386/i386.c +++ b/gcc/config/i386/i386.c @@ -9850,6 +9850,55 @@ ix86_expand_strlensi_unroll_1 (out, align_rtx) emit_label (end_0_label); } + +void +ix86_expand_call (retval, fnaddr, callarg1, callarg2, pop) + rtx retval, fnaddr, callarg1, callarg2, pop; +{ + rtx use = NULL, call; + + if (pop == const0_rtx) + pop = NULL; + if (TARGET_64BIT && pop) + abort (); + + /* Static functions and indirect calls don't need the pic register. */ + 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); + } + + if (TARGET_64BIT && INTVAL (callarg2) >= 0) + { + rtx al = gen_rtx_REG (QImode, 0); + emit_move_insn (al, callarg2); + use_reg (&use, al); + } + + if (! call_insn_operand (XEXP (fnaddr, 0), Pmode)) + { + fnaddr = copy_to_mode_reg (Pmode, XEXP (fnaddr, 0)); + fnaddr = gen_rtx_MEM (QImode, fnaddr); + } + + call = gen_rtx_CALL (VOIDmode, fnaddr, callarg1); + if (retval) + call = gen_rtx_SET (VOIDmode, retval, call); + if (pop) + { + pop = gen_rtx_PLUS (Pmode, stack_pointer_rtx, pop); + pop = gen_rtx_SET (VOIDmode, stack_pointer_rtx, pop); + call = gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, call, pop)); + } + + call = emit_call_insn (call); + if (use) + CALL_INSN_FUNCTION_USAGE (call) = use; +} + /* Clear stack slot assignments remembered from previous functions. This is called from INIT_EXPANDERS once before RTL is emitted for each diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md index 9fdff5ccc32e..cdd99fc22d50 100644 --- a/gcc/config/i386/i386.md +++ b/gcc/config/i386/i386.md @@ -12891,21 +12891,8 @@ (match_operand:SI 3 "" "")))])] "!TARGET_64BIT" { - if (operands[3] == const0_rtx) - { - emit_insn (gen_call (operands[0], operands[1], constm1_rtx)); - DONE; - } - /* Static functions and indirect calls don't need - current_function_uses_pic_offset_table. */ - if (flag_pic - && GET_CODE (XEXP (operands[0], 0)) == SYMBOL_REF - && ! SYMBOL_REF_FLAG (XEXP (operands[0], 0))) - current_function_uses_pic_offset_table = 1; - if (! call_insn_operand (XEXP (operands[0], 0), Pmode)) - XEXP (operands[0], 0) = copy_to_mode_reg (Pmode, XEXP (operands[0], 0)); - if (TARGET_64BIT) - abort(); + ix86_expand_call (NULL, operands[0], operands[1], operands[2], operands[3]); + DONE; }) (define_insn "*call_pop_0" @@ -12947,37 +12934,12 @@ [(call (match_operand:QI 0 "" "") (match_operand 1 "" "")) (use (match_operand 2 "" ""))] - ;; Operand 1 not used on the i386. "" { - rtx insn; - /* Static functions and indirect calls don't need - current_function_uses_pic_offset_table. */ - if (flag_pic - && GET_CODE (XEXP (operands[0], 0)) == SYMBOL_REF - && ! SYMBOL_REF_FLAG (XEXP (operands[0], 0))) - current_function_uses_pic_offset_table = 1; - - if (! call_insn_operand (XEXP (operands[0], 0), Pmode)) - XEXP (operands[0], 0) = copy_to_mode_reg (Pmode, XEXP (operands[0], 0)); - if (TARGET_64BIT && INTVAL (operands[2]) >= 0) - { - rtx reg = gen_rtx_REG (QImode, 0); - emit_move_insn (reg, operands[2]); - insn = emit_call_insn (gen_call_exp (operands[0], operands[1])); - use_reg (&CALL_INSN_FUNCTION_USAGE (insn), reg); - DONE; - } - insn = emit_call_insn (gen_call_exp (operands[0], operands[1])); - DONE; + ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL); + DONE; }) -(define_expand "call_exp" - [(call (match_operand:QI 0 "" "") - (match_operand 1 "" ""))] - "" - "") - (define_insn "*call_0" [(call (mem:QI (match_operand 0 "constant_call_address_operand" "")) (match_operand 1 "" ""))] @@ -13029,7 +12991,6 @@ [(set_attr "type" "call")]) ;; Call subroutine, returning value in operand 0 -;; (which must be a hard register). (define_expand "call_value_pop" [(parallel [(set (match_operand 0 "" "") @@ -13040,20 +13001,9 @@ (match_operand:SI 4 "" "")))])] "!TARGET_64BIT" { - if (operands[4] == const0_rtx) - { - emit_insn (gen_call_value (operands[0], operands[1], operands[2], - constm1_rtx)); - DONE; - } - /* Static functions and indirect calls don't need - current_function_uses_pic_offset_table. */ - if (flag_pic - && GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF - && ! SYMBOL_REF_FLAG (XEXP (operands[1], 0))) - current_function_uses_pic_offset_table = 1; - if (! call_insn_operand (XEXP (operands[1], 0), Pmode)) - XEXP (operands[1], 0) = copy_to_mode_reg (Pmode, XEXP (operands[1], 0)); + ix86_expand_call (operands[0], operands[1], operands[2], + operands[3], operands[4]); + DONE; }) (define_expand "call_value" @@ -13064,36 +13014,10 @@ ;; Operand 2 not used on the i386. "" { - rtx insn; - /* Static functions and indirect calls don't need - current_function_uses_pic_offset_table. */ - if (flag_pic - && GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF - && ! SYMBOL_REF_FLAG (XEXP (operands[1], 0))) - current_function_uses_pic_offset_table = 1; - if (! call_insn_operand (XEXP (operands[1], 0), Pmode)) - XEXP (operands[1], 0) = copy_to_mode_reg (Pmode, XEXP (operands[1], 0)); - if (TARGET_64BIT && INTVAL (operands[3]) >= 0) - { - rtx reg = gen_rtx_REG (QImode, 0); - emit_move_insn (reg, operands[3]); - insn = emit_call_insn (gen_call_value_exp (operands[0], operands[1], - operands[2])); - use_reg (&CALL_INSN_FUNCTION_USAGE (insn), reg); - DONE; - } - insn = emit_call_insn (gen_call_value_exp (operands[0], operands[1], - operands[2])); + ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL); DONE; }) -(define_expand "call_value_exp" - [(set (match_operand 0 "" "") - (call (match_operand:QI 1 "" "") - (match_operand:SI 2 "" "")))] - "" - "") - ;; Call subroutine returning any type. (define_expand "untyped_call" @@ -13110,12 +13034,10 @@ simply pretend the untyped call returns a complex long double value. */ - emit_call_insn (TARGET_FLOAT_RETURNS_IN_80387 - ? gen_call_value (gen_rtx_REG (XCmode, FIRST_FLOAT_REG), - operands[0], const0_rtx, - GEN_INT (SSE_REGPARM_MAX - 1)) - : gen_call (operands[0], const0_rtx, - GEN_INT (SSE_REGPARM_MAX - 1))); + ix86_expand_call ((TARGET_FLOAT_RETURNS_IN_80387 + ? gen_rtx_REG (XCmode, FIRST_FLOAT_REG) : NULL), + operands[0], const0_rtx, GEN_INT (SSE_REGPARM_MAX - 1), + NULL); for (i = 0; i < XVECLEN (operands[2], 0); i++) {