From 7ec70495eaf949ca89abf196cc59a881e6f1b03a Mon Sep 17 00:00:00 2001 From: Jan Hubicka Date: Mon, 9 Sep 2002 13:00:55 +0200 Subject: [PATCH] i386.c (index_register_operand): New. 2002-09-09 Jan Hubicka * i386.c (index_register_operand): New. * i386.h (predicate_codes): Add new predicate. * i386.md (lea_general_*): Use index_regsiter_operand (ashift to lea splitter): Do not produce invalid leas (ashift to mov+ashift split): New. From-SVN: r56970 --- gcc/ChangeLog | 8 ++++++++ gcc/config/i386/i386.c | 24 ++++++++++++++++++++++++ gcc/config/i386/i386.h | 1 + gcc/config/i386/i386.md | 34 +++++++++++++++++++++++++++------- 4 files changed, 60 insertions(+), 7 deletions(-) diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 0503d56aecb..be663674b9b 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,11 @@ +2002-09-09 Jan Hubicka + + * i386.c (index_register_operand): New. + * i386.h (predicate_codes): Add new predicate. + * i386.md (lea_general_*): Use index_regsiter_operand + (ashift to lea splitter): Do not produce invalid leas + (ashift to mov+ashift split): New. + 2002-09-09 Nick Clifton * config/fr30/fr30.c (output.h): Move after inclusion of tree.h. diff --git a/gcc/config/i386/i386.c b/gcc/config/i386/i386.c index 1d0d1601820..81a9b97841d 100644 --- a/gcc/config/i386/i386.c +++ b/gcc/config/i386/i386.c @@ -3217,6 +3217,30 @@ nonmemory_no_elim_operand (op, mode) return GET_CODE (op) == CONST_INT || register_operand (op, mode); } +/* Return false if this is any eliminable register or stack register, + otherwise work like register_operand. */ + +int +index_register_operand (op, mode) + register rtx op; + enum machine_mode mode; +{ + rtx t = op; + if (GET_CODE (t) == SUBREG) + t = SUBREG_REG (t); + if (!REG_P (t)) + return 0; + if (t == arg_pointer_rtx + || t == frame_pointer_rtx + || t == virtual_incoming_args_rtx + || t == virtual_stack_vars_rtx + || t == virtual_stack_dynamic_rtx + || REGNO (t) == STACK_POINTER_REGNUM) + return 0; + + return general_operand (op, mode); +} + /* Return true if op is a Q_REGS class register. */ int diff --git a/gcc/config/i386/i386.h b/gcc/config/i386/i386.h index d04c60569a6..ddef1f9da39 100644 --- a/gcc/config/i386/i386.h +++ b/gcc/config/i386/i386.h @@ -3173,6 +3173,7 @@ do { \ {"general_no_elim_operand", {CONST_INT, CONST_DOUBLE, CONST, \ SYMBOL_REF, LABEL_REF, SUBREG, REG, MEM}}, \ {"nonmemory_no_elim_operand", {CONST_INT, REG, SUBREG}}, \ + {"index_register_operand", {SUBREG, REG}}, \ {"q_regs_operand", {SUBREG, REG}}, \ {"non_q_regs_operand", {SUBREG, REG}}, \ {"fcmov_comparison_operator", {EQ, NE, LTU, GTU, LEU, GEU, UNORDERED, \ diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md index 240880ddf9e..a306509c446 100644 --- a/gcc/config/i386/i386.md +++ b/gcc/config/i386/i386.md @@ -4845,7 +4845,7 @@ (define_insn_and_split "*lea_general_1" [(set (match_operand 0 "register_operand" "=r") - (plus (plus (match_operand 1 "register_operand" "r") + (plus (plus (match_operand 1 "index_register_operand" "r") (match_operand 2 "register_operand" "r")) (match_operand 3 "immediate_operand" "i")))] "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode @@ -4877,7 +4877,7 @@ (define_insn_and_split "*lea_general_1_zext" [(set (match_operand:DI 0 "register_operand" "=r") (zero_extend:DI - (plus:SI (plus:SI (match_operand:SI 1 "register_operand" "r") + (plus:SI (plus:SI (match_operand:SI 1 "index_register_operand" "r") (match_operand:SI 2 "register_operand" "r")) (match_operand:SI 3 "immediate_operand" "i"))))] "TARGET_64BIT" @@ -4897,7 +4897,7 @@ (define_insn_and_split "*lea_general_2" [(set (match_operand 0 "register_operand" "=r") - (plus (mult (match_operand 1 "register_operand" "r") + (plus (mult (match_operand 1 "index_register_operand" "r") (match_operand 2 "const248_operand" "i")) (match_operand 3 "nonmemory_operand" "ri")))] "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode @@ -4927,7 +4927,7 @@ (define_insn_and_split "*lea_general_2_zext" [(set (match_operand:DI 0 "register_operand" "=r") (zero_extend:DI - (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "r") + (plus:SI (mult:SI (match_operand:SI 1 "index_register_operand" "r") (match_operand:SI 2 "const248_operand" "n")) (match_operand:SI 3 "nonmemory_operand" "ri"))))] "TARGET_64BIT" @@ -4946,7 +4946,7 @@ (define_insn_and_split "*lea_general_3" [(set (match_operand 0 "register_operand" "=r") - (plus (plus (mult (match_operand 1 "register_operand" "r") + (plus (plus (mult (match_operand 1 "index_register_operand" "r") (match_operand 2 "const248_operand" "i")) (match_operand 3 "register_operand" "r")) (match_operand 4 "immediate_operand" "i")))] @@ -4980,7 +4980,7 @@ (define_insn_and_split "*lea_general_3_zext" [(set (match_operand:DI 0 "register_operand" "=r") (zero_extend:DI - (plus:SI (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "r") + (plus:SI (plus:SI (mult:SI (match_operand:SI 1 "index_register_operand" "r") (match_operand:SI 2 "const248_operand" "n")) (match_operand:SI 3 "register_operand" "r")) (match_operand:SI 4 "immediate_operand" "i"))))] @@ -10615,7 +10615,7 @@ ;; Convert lea to the lea pattern to avoid flags dependency. (define_split [(set (match_operand 0 "register_operand" "") - (ashift (match_operand 1 "register_operand" "") + (ashift (match_operand 1 "index_register_operand" "") (match_operand:QI 2 "const_int_operand" ""))) (clobber (reg:CC 17))] "reload_completed @@ -10633,6 +10633,26 @@ DONE; }) +;; Rare case of shifting RSP is handled by generating move and shift +(define_split + [(set (match_operand 0 "register_operand" "") + (ashift (match_operand 1 "register_operand" "") + (match_operand:QI 2 "const_int_operand" ""))) + (clobber (reg:CC 17))] + "reload_completed + && true_regnum (operands[0]) != true_regnum (operands[1])" + [(const_int 0)] +{ + rtx pat, clob; + emit_move_insn (operands[1], operands[0]); + pat = gen_rtx_SET (VOIDmode, operands[0], + gen_rtx_ASHIFT (GET_MODE (operands[0]), + operands[0], operands[2])); + clob = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, FLAGS_REG)); + emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, pat, clob))); + DONE; +}) + (define_insn "*ashlsi3_1_zext" [(set (match_operand:DI 0 "register_operand" "=r,r") (zero_extend:DI (ashift:SI (match_operand:SI 1 "register_operand" "0,r") -- 2.30.2