re PR target/53961 (internal compiler error: in memory_address_length, at config...
authorUros Bizjak <uros@gcc.gnu.org>
Sun, 22 Jul 2012 15:44:51 +0000 (17:44 +0200)
committerUros Bizjak <uros@gcc.gnu.org>
Sun, 22 Jul 2012 15:44:51 +0000 (17:44 +0200)
PR target/53961
* config/i386/i386.md (*lea): New insn pattern.
(*lea_1): Remove.
(*lea<mode>_2): Ditto.
(*lea_{3,4,5,6}_zext): Ditto.
* config/i386/constraints.md (j): Remove address constraint.
* config/i386/i386.c (ix86_decompose_address): Allow SImode subreg
of an address.
(ix86_print_operand_address): Handle SImode subreg of an address.
(ix86_avoid_lea_for_add): Reject zero-extended addresses for now.

From-SVN: r189756

gcc/ChangeLog
gcc/config/i386/constraints.md
gcc/config/i386/i386.c
gcc/config/i386/i386.md
gcc/config/i386/predicates.md

index 321d96de6ec1b1acb0089940089c4a9986ce34f5..df66271ef566a7d141540c601c202cf822983b63 100644 (file)
@@ -1,3 +1,16 @@
+2012-07-22  Uros Bizjak  <ubizjak@gmail.com>
+
+       PR target/53961
+       * config/i386/i386.md (*lea): New insn pattern.
+       (*lea_1): Remove.
+       (*lea<mode>_2): Ditto.
+       (*lea_{3,4,5,6}_zext): Ditto.
+       * config/i386/constraints.md (j): Remove address constraint.
+       * config/i386/i386.c (ix86_decompose_address): Allow SImode subreg
+       of an address.
+       (ix86_print_operand_address): Handle SImode subreg of an address.
+       (ix86_avoid_lea_for_add): Reject zero-extended addresses for now.
+
 2012-07-22  Hans-Peter Nilsson  <hp@axis.com>
 
        Emit executable-stack note correctly for CRIS targets.
@@ -35,7 +48,7 @@
        mips_expand_ext_as_unaligned_load.
        (mips_expand_ext_as_unaligned_load): Add unsigned_p argument.
        Accept DImode dest when the width is that of SImode.
-        * config/mips/mips.md (extv): Update call to
+       * config/mips/mips.md (extv): Update call to
        mips_expand_ext_as_unaligned_load.
        (extzv): Likewise.
 
@@ -54,9 +67,9 @@
        New reservations.
        * gcc/config/mips/10000.md, gcc/config/mips/20kc.md,
        * gcc/config/mips/24k.md, gcc/config/mips/4130.md,
-        * gcc/config/mips/4k.md, gcc/config/mips/5400.md,
+       * gcc/config/mips/4k.md, gcc/config/mips/5400.md,
        * gcc/config/mips/5500.md, gcc/config/mips/5k.md,
-        * gcc/config/mips/7000.md, gcc/config/mips/74k.md,
+       * gcc/config/mips/7000.md, gcc/config/mips/74k.md,
        * gcc/config/mips/9000.md, gcc/config/mips/loongson2ef.md,
        * gcc/config/mips/loongson3a.md, gcc/config/mips/octeon.md,
        * gcc/config/mips/sb1.md, gcc/config/mips/sr71k.md,
        (brief_dump_cfg): Take a flags argument, and filter out
        TDF_COMMENT and TDF_DETAILS.
        * pretty-print.c (pp_base_newline): Set pp_needs_newline to false.
-       * gimple-pretty-print.c (dump_gimple_bb_header): Do not use dump_bb_info
-       here, it is already called from dump_bb.  Idem for check_bb_profile.
+       * gimple-pretty-print.c (dump_gimple_bb_header): Do not use
+       dump_bb_info here, it is already called from dump_bb.  Idem for
+       check_bb_profile.
        (dump_gimple_bb_footer): Likewise.
        (gimple_dump_bb_buff): Call pp_flush after dump_gimple_stmt to
        avoid broken dumps for statement histograms.
        * passes.c (execute_function_dump): Always call print_rtl_with_bb
        for RTL dumps.
        * cfgrtl.c (print_rtl_with_bb): Handle printing without an up-to-date
-       CFG.  With TDF_BLOCKS and TDF_DETAILS, do DF dumps at the top and bottom
-       of each basic block.
+       CFG.  With TDF_BLOCKS and TDF_DETAILS, do DF dumps at the top and
+       bottom of each basic block.
 
 2012-07-20  Richard Guenther  <rguenther@suse.de>
 
index fda1a0488e83744c14ed5e31d3156d0bd8e7404f..b73cf5c32dbf18efabd44371be92ce56976416b4 100644 (file)
@@ -19,7 +19,7 @@
 
 ;;; Unused letters:
 ;;;     B     H           T
-;;;           h  k          v
+;;;           h jk          v
 
 ;; Integer register constraints.
 ;; It is not necessary to define 'r' here.
   (and (not (match_test "TARGET_X32"))
        (match_operand 0 "memory_operand")))
 
-(define_address_constraint "j"
-  "@internal Address operand that can be zero extended in LEA instruction."
-  (and (not (match_code "const_int"))
-       (match_operand 0 "address_operand")))
-
 ;; Integer constant constraints.
 (define_constraint "I"
   "Integer constant in the range 0 @dots{} 31, for 32-bit shifts."
index 8bdbc05a7462522eb9b6221b3a6a16ffed3016c7..5770ed26aa2bb33059410ed71b065ef03016690e 100644 (file)
@@ -11576,9 +11576,18 @@ ix86_decompose_address (rtx addr, struct ix86_address *out)
   int retval = 1;
   enum ix86_address_seg seg = SEG_DEFAULT;
 
+  /* Allow SImode subregs of DImode addresses,
+     they will be emitted with addr32 prefix.  */
+  if (TARGET_64BIT && GET_MODE (addr) == SImode)
+    {
+      if (GET_CODE (addr) == SUBREG
+         && GET_MODE (XEXP (addr, 0)) == DImode)
+       addr = SUBREG_REG (addr);
+    }
+
   /* Allow zero-extended SImode addresses,
      they will be emitted with addr32 prefix.  */
-  if (TARGET_64BIT && GET_MODE (addr) == DImode)
+  else if (TARGET_64BIT && GET_MODE (addr) == DImode)
     {
       if (GET_CODE (addr) == ZERO_EXTEND
          && GET_MODE (XEXP (addr, 0)) == SImode)
@@ -14755,10 +14764,10 @@ ix86_print_operand_address (FILE *file, rtx addr)
     }
   else
     {
-      /* Print SImode register names for zero-extended
-        addresses to force addr32 prefix.  */
+      /* Print SImode register names to force addr32 prefix.  */
       if (TARGET_64BIT
-         && (GET_CODE (addr) == ZERO_EXTEND
+         && (GET_CODE (addr) == SUBREG
+             || GET_CODE (addr) == ZERO_EXTEND
              || GET_CODE (addr) == AND))
        {
          gcc_assert (!code);
@@ -16855,6 +16864,11 @@ ix86_avoid_lea_for_add (rtx insn, rtx operands[])
   unsigned int regno1 = true_regnum (operands[1]);
   unsigned int regno2 = true_regnum (operands[2]);
 
+  /* FIXME: Handle zero-extended addresses.  */
+  if (GET_CODE (operands[1]) == ZERO_EXTEND
+      || GET_CODE (operands[1]) == AND)
+    return false;
+
   /* Check if we need to optimize.  */
   if (!TARGET_OPT_AGU || optimize_function_for_size_p (cfun))
     return false;
index 49a56863617a6bfe6c5a9096d5140a4feb37bf8e..7f5814dfeec76b8b7d6f42016fd8859b236433bb 100644 (file)
   [(set_attr "type" "alu")
    (set_attr "mode" "QI")])
 
-(define_insn_and_split "*lea_1"
-  [(set (match_operand:SI 0 "register_operand" "=r")
-       (subreg:SI (match_operand:DI 1 "lea_address_operand" "p") 0))]
-  "TARGET_64BIT"
-  "lea{l}\t{%E1, %0|%0, %E1}"
-  "&& reload_completed && ix86_avoid_lea_for_addr (insn, operands)"
-  [(const_int 0)]
-{
-  ix86_split_lea_for_addr (operands, SImode);
-  DONE;
-}
-  [(set_attr "type" "lea")
-   (set_attr "mode" "SI")])
-
-(define_insn_and_split "*lea<mode>_2"
+(define_insn_and_split "*lea<mode>"
   [(set (match_operand:SWI48 0 "register_operand" "=r")
        (match_operand:SWI48 1 "lea_address_operand" "p"))]
   ""
-  "lea{<imodesuffix>}\t{%E1, %0|%0, %E1}"
+{
+  rtx addr = operands[1];
+
+  if (GET_CODE (addr) == SUBREG)
+    return "lea{l}\t{%E1, %0|%0, %E1}";
+  else if (GET_CODE (addr) == ZERO_EXTEND
+          || GET_CODE (addr) == AND)
+    return "lea{l}\t{%E1, %k0|%k0, %E1}";
+  else 
+    return "lea{<imodesuffix>}\t{%E1, %0|%0, %E1}";
+}
   "reload_completed && ix86_avoid_lea_for_addr (insn, operands)"
   [(const_int 0)]
 {
   [(set_attr "type" "lea")
    (set_attr "mode" "<MODE>")])
 
-(define_insn "*lea_3_zext"
-  [(set (match_operand:DI 0 "register_operand" "=r")
-       (zero_extend:DI
-         (subreg:SI (match_operand:DI 1 "lea_address_operand" "j") 0)))]
-  "TARGET_64BIT"
-  "lea{l}\t{%E1, %k0|%k0, %E1}"
-  [(set_attr "type" "lea")
-   (set_attr "mode" "SI")])
-
-(define_insn "*lea_4_zext"
-  [(set (match_operand:DI 0 "register_operand" "=r")
-       (zero_extend:DI
-         (match_operand:SI 1 "lea_address_operand" "j")))]
-  "TARGET_64BIT"
-  "lea{l}\t{%E1, %k0|%k0, %E1}"
-  [(set_attr "type" "lea")
-   (set_attr "mode" "SI")])
-
-(define_insn "*lea_5_zext"
-  [(set (match_operand:DI 0 "register_operand" "=r")
-       (and:DI
-         (subreg:DI (match_operand:SI 1 "lea_address_operand" "p") 0)
-         (match_operand:DI 2 "const_32bit_mask" "n")))]
-  "TARGET_64BIT"
-  "lea{l}\t{%E1, %k0|%k0, %E1}"
-  [(set_attr "type" "lea")
-   (set_attr "mode" "SI")])
-
-(define_insn "*lea_6_zext"
-  [(set (match_operand:DI 0 "register_operand" "=r")
-       (and:DI
-         (match_operand:DI 1 "lea_address_operand" "p")
-         (match_operand:DI 2 "const_32bit_mask" "n")))]
-  "TARGET_64BIT"
-  "lea{l}\t{%E1, %k0|%k0, %E1}"
-  [(set_attr "type" "lea")
-   (set_attr "mode" "SI")])
-
 (define_insn "*add<mode>_1"
   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=r,rm,r,r")
        (plus:SWI48
index 92db80912befaec5c3ef2909ab7185ca4a00d6f5..3dbc6c0ccea69a38467e8e1ad3d1c8d71d90dc23 100644 (file)
   struct ix86_address parts;
   int ok;
 
-  /*  LEA handles zero-extend by itself.  */
-  if (GET_CODE (op) == ZERO_EXTEND
-      || GET_CODE (op) == AND)
-    return false;
-
   ok = ix86_decompose_address (op, &parts);
   gcc_assert (ok);
   return parts.seg == SEG_DEFAULT;