This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

fix target/11327


The problem shown in this test case is that we hamstrung CSE by
not bringing operands into registers where it could work on them.

I now get 

.L4:
        movq    -8(%eax,%esi), %mm2
        movq    -8(%eax,%edi), %mm1
        movq    %mm1, %mm0
        psubusb %mm2, %mm0
        psubusb %mm1, %mm2
        por     %mm2, %mm0
        cmpl    %edx, %ecx
        pminub  %mm3, %mm0
        pcmpeqb %mm3, %mm0
        movq    %mm0, -8(%eax,%ebx)
        jne     .L8

as the main loop, which is as nice as you could ask for.

Of course, we've still got the weird loop latch placement
problem in mainline, so things aren't *quite* as good as
they ought to be.


r~


        * config/i386/i386.c (BUILTIN_DESC_SWAP_OPERANDS): New.
        (bdesc_2arg): Use it.
        (ix86_expand_binop_builtin): Force operands into registers
        when optimizing.
        (ix86_expand_unop_builtin, ix86_expand_unop1_builtin,
        ix86_expand_sse_compare, ix86_expand_sse_comi,
        ix86_expand_builtin): Likewise.

Index: config/i386/i386.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/i386/i386.c,v
retrieving revision 1.769
diff -c -p -d -r1.769 i386.c
*** config/i386/i386.c	5 Jan 2005 20:29:05 -0000	1.769
--- config/i386/i386.c	6 Jan 2005 06:18:50 -0000
*************** do {									\
*** 12077,12082 ****
--- 12077,12088 ----
  				 NULL, NULL_TREE);			\
  } while (0)
  
+ /* Bits for builtin_description.flag.  */
+ 
+ /* Set when we don't support the comparison natively, and should
+    swap_comparison in order to support it.  */
+ #define BUILTIN_DESC_SWAP_OPERANDS	1
+ 
  struct builtin_description
  {
    const unsigned int mask;
*************** static const struct builtin_description 
*** 12130,12143 ****
    { MASK_SSE, CODE_FOR_maskcmpv4sf3, "__builtin_ia32_cmpeqps", IX86_BUILTIN_CMPEQPS, EQ, 0 },
    { MASK_SSE, CODE_FOR_maskcmpv4sf3, "__builtin_ia32_cmpltps", IX86_BUILTIN_CMPLTPS, LT, 0 },
    { MASK_SSE, CODE_FOR_maskcmpv4sf3, "__builtin_ia32_cmpleps", IX86_BUILTIN_CMPLEPS, LE, 0 },
!   { MASK_SSE, CODE_FOR_maskcmpv4sf3, "__builtin_ia32_cmpgtps", IX86_BUILTIN_CMPGTPS, LT, 1 },
!   { MASK_SSE, CODE_FOR_maskcmpv4sf3, "__builtin_ia32_cmpgeps", IX86_BUILTIN_CMPGEPS, LE, 1 },
    { MASK_SSE, CODE_FOR_maskcmpv4sf3, "__builtin_ia32_cmpunordps", IX86_BUILTIN_CMPUNORDPS, UNORDERED, 0 },
    { MASK_SSE, CODE_FOR_maskncmpv4sf3, "__builtin_ia32_cmpneqps", IX86_BUILTIN_CMPNEQPS, EQ, 0 },
    { MASK_SSE, CODE_FOR_maskncmpv4sf3, "__builtin_ia32_cmpnltps", IX86_BUILTIN_CMPNLTPS, LT, 0 },
    { MASK_SSE, CODE_FOR_maskncmpv4sf3, "__builtin_ia32_cmpnleps", IX86_BUILTIN_CMPNLEPS, LE, 0 },
!   { MASK_SSE, CODE_FOR_maskncmpv4sf3, "__builtin_ia32_cmpngtps", IX86_BUILTIN_CMPNGTPS, LT, 1 },
!   { MASK_SSE, CODE_FOR_maskncmpv4sf3, "__builtin_ia32_cmpngeps", IX86_BUILTIN_CMPNGEPS, LE, 1 },
    { MASK_SSE, CODE_FOR_maskncmpv4sf3, "__builtin_ia32_cmpordps", IX86_BUILTIN_CMPORDPS, UNORDERED, 0 },
    { MASK_SSE, CODE_FOR_vmmaskcmpv4sf3, "__builtin_ia32_cmpeqss", IX86_BUILTIN_CMPEQSS, EQ, 0 },
    { MASK_SSE, CODE_FOR_vmmaskcmpv4sf3, "__builtin_ia32_cmpltss", IX86_BUILTIN_CMPLTSS, LT, 0 },
--- 12136,12153 ----
    { MASK_SSE, CODE_FOR_maskcmpv4sf3, "__builtin_ia32_cmpeqps", IX86_BUILTIN_CMPEQPS, EQ, 0 },
    { MASK_SSE, CODE_FOR_maskcmpv4sf3, "__builtin_ia32_cmpltps", IX86_BUILTIN_CMPLTPS, LT, 0 },
    { MASK_SSE, CODE_FOR_maskcmpv4sf3, "__builtin_ia32_cmpleps", IX86_BUILTIN_CMPLEPS, LE, 0 },
!   { MASK_SSE, CODE_FOR_maskcmpv4sf3, "__builtin_ia32_cmpgtps", IX86_BUILTIN_CMPGTPS, LT,
!     BUILTIN_DESC_SWAP_OPERANDS },
!   { MASK_SSE, CODE_FOR_maskcmpv4sf3, "__builtin_ia32_cmpgeps", IX86_BUILTIN_CMPGEPS, LE,
!     BUILTIN_DESC_SWAP_OPERANDS },
    { MASK_SSE, CODE_FOR_maskcmpv4sf3, "__builtin_ia32_cmpunordps", IX86_BUILTIN_CMPUNORDPS, UNORDERED, 0 },
    { MASK_SSE, CODE_FOR_maskncmpv4sf3, "__builtin_ia32_cmpneqps", IX86_BUILTIN_CMPNEQPS, EQ, 0 },
    { MASK_SSE, CODE_FOR_maskncmpv4sf3, "__builtin_ia32_cmpnltps", IX86_BUILTIN_CMPNLTPS, LT, 0 },
    { MASK_SSE, CODE_FOR_maskncmpv4sf3, "__builtin_ia32_cmpnleps", IX86_BUILTIN_CMPNLEPS, LE, 0 },
!   { MASK_SSE, CODE_FOR_maskncmpv4sf3, "__builtin_ia32_cmpngtps", IX86_BUILTIN_CMPNGTPS, LT,
!     BUILTIN_DESC_SWAP_OPERANDS },
!   { MASK_SSE, CODE_FOR_maskncmpv4sf3, "__builtin_ia32_cmpngeps", IX86_BUILTIN_CMPNGEPS, LE,
!     BUILTIN_DESC_SWAP_OPERANDS },
    { MASK_SSE, CODE_FOR_maskncmpv4sf3, "__builtin_ia32_cmpordps", IX86_BUILTIN_CMPORDPS, UNORDERED, 0 },
    { MASK_SSE, CODE_FOR_vmmaskcmpv4sf3, "__builtin_ia32_cmpeqss", IX86_BUILTIN_CMPEQSS, EQ, 0 },
    { MASK_SSE, CODE_FOR_vmmaskcmpv4sf3, "__builtin_ia32_cmpltss", IX86_BUILTIN_CMPLTSS, LT, 0 },
*************** static const struct builtin_description 
*** 12258,12271 ****
    { MASK_SSE2, CODE_FOR_maskcmpv2df3, "__builtin_ia32_cmpeqpd", IX86_BUILTIN_CMPEQPD, EQ, 0 },
    { MASK_SSE2, CODE_FOR_maskcmpv2df3, "__builtin_ia32_cmpltpd", IX86_BUILTIN_CMPLTPD, LT, 0 },
    { MASK_SSE2, CODE_FOR_maskcmpv2df3, "__builtin_ia32_cmplepd", IX86_BUILTIN_CMPLEPD, LE, 0 },
!   { MASK_SSE2, CODE_FOR_maskcmpv2df3, "__builtin_ia32_cmpgtpd", IX86_BUILTIN_CMPGTPD, LT, 1 },
!   { MASK_SSE2, CODE_FOR_maskcmpv2df3, "__builtin_ia32_cmpgepd", IX86_BUILTIN_CMPGEPD, LE, 1 },
    { MASK_SSE2, CODE_FOR_maskcmpv2df3, "__builtin_ia32_cmpunordpd", IX86_BUILTIN_CMPUNORDPD, UNORDERED, 0 },
    { MASK_SSE2, CODE_FOR_maskncmpv2df3, "__builtin_ia32_cmpneqpd", IX86_BUILTIN_CMPNEQPD, EQ, 0 },
    { MASK_SSE2, CODE_FOR_maskncmpv2df3, "__builtin_ia32_cmpnltpd", IX86_BUILTIN_CMPNLTPD, LT, 0 },
    { MASK_SSE2, CODE_FOR_maskncmpv2df3, "__builtin_ia32_cmpnlepd", IX86_BUILTIN_CMPNLEPD, LE, 0 },
!   { MASK_SSE2, CODE_FOR_maskncmpv2df3, "__builtin_ia32_cmpngtpd", IX86_BUILTIN_CMPNGTPD, LT, 1 },
!   { MASK_SSE2, CODE_FOR_maskncmpv2df3, "__builtin_ia32_cmpngepd", IX86_BUILTIN_CMPNGEPD, LE, 1 },
    { MASK_SSE2, CODE_FOR_maskncmpv2df3, "__builtin_ia32_cmpordpd", IX86_BUILTIN_CMPORDPD, UNORDERED, 0 },
    { MASK_SSE2, CODE_FOR_vmmaskcmpv2df3, "__builtin_ia32_cmpeqsd", IX86_BUILTIN_CMPEQSD, EQ, 0 },
    { MASK_SSE2, CODE_FOR_vmmaskcmpv2df3, "__builtin_ia32_cmpltsd", IX86_BUILTIN_CMPLTSD, LT, 0 },
--- 12268,12285 ----
    { MASK_SSE2, CODE_FOR_maskcmpv2df3, "__builtin_ia32_cmpeqpd", IX86_BUILTIN_CMPEQPD, EQ, 0 },
    { MASK_SSE2, CODE_FOR_maskcmpv2df3, "__builtin_ia32_cmpltpd", IX86_BUILTIN_CMPLTPD, LT, 0 },
    { MASK_SSE2, CODE_FOR_maskcmpv2df3, "__builtin_ia32_cmplepd", IX86_BUILTIN_CMPLEPD, LE, 0 },
!   { MASK_SSE2, CODE_FOR_maskcmpv2df3, "__builtin_ia32_cmpgtpd", IX86_BUILTIN_CMPGTPD, LT,
!     BUILTIN_DESC_SWAP_OPERANDS },
!   { MASK_SSE2, CODE_FOR_maskcmpv2df3, "__builtin_ia32_cmpgepd", IX86_BUILTIN_CMPGEPD, LE,
!     BUILTIN_DESC_SWAP_OPERANDS },
    { MASK_SSE2, CODE_FOR_maskcmpv2df3, "__builtin_ia32_cmpunordpd", IX86_BUILTIN_CMPUNORDPD, UNORDERED, 0 },
    { MASK_SSE2, CODE_FOR_maskncmpv2df3, "__builtin_ia32_cmpneqpd", IX86_BUILTIN_CMPNEQPD, EQ, 0 },
    { MASK_SSE2, CODE_FOR_maskncmpv2df3, "__builtin_ia32_cmpnltpd", IX86_BUILTIN_CMPNLTPD, LT, 0 },
    { MASK_SSE2, CODE_FOR_maskncmpv2df3, "__builtin_ia32_cmpnlepd", IX86_BUILTIN_CMPNLEPD, LE, 0 },
!   { MASK_SSE2, CODE_FOR_maskncmpv2df3, "__builtin_ia32_cmpngtpd", IX86_BUILTIN_CMPNGTPD, LT,
!     BUILTIN_DESC_SWAP_OPERANDS },
!   { MASK_SSE2, CODE_FOR_maskncmpv2df3, "__builtin_ia32_cmpngepd", IX86_BUILTIN_CMPNGEPD, LE,
!     BUILTIN_DESC_SWAP_OPERANDS },
    { MASK_SSE2, CODE_FOR_maskncmpv2df3, "__builtin_ia32_cmpordpd", IX86_BUILTIN_CMPORDPD, UNORDERED, 0 },
    { MASK_SSE2, CODE_FOR_vmmaskcmpv2df3, "__builtin_ia32_cmpeqsd", IX86_BUILTIN_CMPEQSD, EQ, 0 },
    { MASK_SSE2, CODE_FOR_vmmaskcmpv2df3, "__builtin_ia32_cmpltsd", IX86_BUILTIN_CMPLTSD, LT, 0 },
*************** ix86_expand_binop_builtin (enum insn_cod
*** 13137,13143 ****
    if (VECTOR_MODE_P (mode1))
      op1 = safe_vector_operand (op1, mode1);
  
!   if (! target
        || GET_MODE (target) != tmode
        || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
      target = gen_reg_rtx (tmode);
--- 13151,13157 ----
    if (VECTOR_MODE_P (mode1))
      op1 = safe_vector_operand (op1, mode1);
  
!   if (optimize || !target
        || GET_MODE (target) != tmode
        || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
      target = gen_reg_rtx (tmode);
*************** ix86_expand_binop_builtin (enum insn_cod
*** 13155,13163 ****
        || (GET_MODE (op1) != mode1 && GET_MODE (op1) != VOIDmode))
      abort ();
  
!   if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
      op0 = copy_to_mode_reg (mode0, op0);
!   if (! (*insn_data[icode].operand[2].predicate) (op1, mode1))
      op1 = copy_to_mode_reg (mode1, op1);
  
    /* In the commutative cases, both op0 and op1 are nonimmediate_operand,
--- 13169,13179 ----
        || (GET_MODE (op1) != mode1 && GET_MODE (op1) != VOIDmode))
      abort ();
  
!   if ((optimize && !register_operand (op0, mode0))
!       || !(*insn_data[icode].operand[1].predicate) (op0, mode0))
      op0 = copy_to_mode_reg (mode0, op0);
!   if ((optimize && !register_operand (op1, mode1))
!       || !(*insn_data[icode].operand[2].predicate) (op1, mode1))
      op1 = copy_to_mode_reg (mode1, op1);
  
    /* In the commutative cases, both op0 and op1 are nonimmediate_operand,
*************** ix86_expand_unop_builtin (enum insn_code
*** 13210,13216 ****
    enum machine_mode tmode = insn_data[icode].operand[0].mode;
    enum machine_mode mode0 = insn_data[icode].operand[1].mode;
  
!   if (! target
        || GET_MODE (target) != tmode
        || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
      target = gen_reg_rtx (tmode);
--- 13226,13232 ----
    enum machine_mode tmode = insn_data[icode].operand[0].mode;
    enum machine_mode mode0 = insn_data[icode].operand[1].mode;
  
!   if (optimize || !target
        || GET_MODE (target) != tmode
        || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
      target = gen_reg_rtx (tmode);
*************** ix86_expand_unop_builtin (enum insn_code
*** 13221,13227 ****
        if (VECTOR_MODE_P (mode0))
  	op0 = safe_vector_operand (op0, mode0);
  
!       if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
  	op0 = copy_to_mode_reg (mode0, op0);
      }
  
--- 13237,13244 ----
        if (VECTOR_MODE_P (mode0))
  	op0 = safe_vector_operand (op0, mode0);
  
!       if ((optimize && !register_operand (op0, mode0))
! 	  || ! (*insn_data[icode].operand[1].predicate) (op0, mode0))
  	op0 = copy_to_mode_reg (mode0, op0);
      }
  
*************** ix86_expand_unop1_builtin (enum insn_cod
*** 13244,13250 ****
    enum machine_mode tmode = insn_data[icode].operand[0].mode;
    enum machine_mode mode0 = insn_data[icode].operand[1].mode;
  
!   if (! target
        || GET_MODE (target) != tmode
        || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
      target = gen_reg_rtx (tmode);
--- 13261,13267 ----
    enum machine_mode tmode = insn_data[icode].operand[0].mode;
    enum machine_mode mode0 = insn_data[icode].operand[1].mode;
  
!   if (optimize || !target
        || GET_MODE (target) != tmode
        || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
      target = gen_reg_rtx (tmode);
*************** ix86_expand_unop1_builtin (enum insn_cod
*** 13252,13258 ****
    if (VECTOR_MODE_P (mode0))
      op0 = safe_vector_operand (op0, mode0);
  
!   if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
      op0 = copy_to_mode_reg (mode0, op0);
  
    op1 = op0;
--- 13269,13276 ----
    if (VECTOR_MODE_P (mode0))
      op0 = safe_vector_operand (op0, mode0);
  
!   if ((optimize && !register_operand (op0, mode0))
!       || ! (*insn_data[icode].operand[1].predicate) (op0, mode0))
      op0 = copy_to_mode_reg (mode0, op0);
  
    op1 = op0;
*************** ix86_expand_sse_compare (const struct bu
*** 13290,13296 ****
  
    /* Swap operands if we have a comparison that isn't available in
       hardware.  */
!   if (d->flag)
      {
        rtx tmp = gen_reg_rtx (mode1);
        emit_move_insn (tmp, op1);
--- 13308,13314 ----
  
    /* Swap operands if we have a comparison that isn't available in
       hardware.  */
!   if (d->flag & BUILTIN_DESC_SWAP_OPERANDS)
      {
        rtx tmp = gen_reg_rtx (mode1);
        emit_move_insn (tmp, op1);
*************** ix86_expand_sse_compare (const struct bu
*** 13298,13311 ****
        op0 = tmp;
      }
  
!   if (! target
        || GET_MODE (target) != tmode
        || ! (*insn_data[d->icode].operand[0].predicate) (target, tmode))
      target = gen_reg_rtx (tmode);
  
!   if (! (*insn_data[d->icode].operand[1].predicate) (op0, mode0))
      op0 = copy_to_mode_reg (mode0, op0);
!   if (! (*insn_data[d->icode].operand[2].predicate) (op1, mode1))
      op1 = copy_to_mode_reg (mode1, op1);
  
    op2 = gen_rtx_fmt_ee (comparison, mode0, op0, op1);
--- 13316,13331 ----
        op0 = tmp;
      }
  
!   if (optimize || !target
        || GET_MODE (target) != tmode
        || ! (*insn_data[d->icode].operand[0].predicate) (target, tmode))
      target = gen_reg_rtx (tmode);
  
!   if ((optimize && !register_operand (op0, mode0))
!       || ! (*insn_data[d->icode].operand[1].predicate) (op0, mode0))
      op0 = copy_to_mode_reg (mode0, op0);
!   if ((optimize && !register_operand (op1, mode1))
!       || ! (*insn_data[d->icode].operand[2].predicate) (op1, mode1))
      op1 = copy_to_mode_reg (mode1, op1);
  
    op2 = gen_rtx_fmt_ee (comparison, mode0, op0, op1);
*************** ix86_expand_sse_comi (const struct built
*** 13339,13345 ****
  
    /* Swap operands if we have a comparison that isn't available in
       hardware.  */
!   if (d->flag)
      {
        rtx tmp = op1;
        op1 = op0;
--- 13359,13365 ----
  
    /* Swap operands if we have a comparison that isn't available in
       hardware.  */
!   if (d->flag & BUILTIN_DESC_SWAP_OPERANDS)
      {
        rtx tmp = op1;
        op1 = op0;
*************** ix86_expand_sse_comi (const struct built
*** 13350,13358 ****
    emit_move_insn (target, const0_rtx);
    target = gen_rtx_SUBREG (QImode, target, 0);
  
!   if (! (*insn_data[d->icode].operand[0].predicate) (op0, mode0))
      op0 = copy_to_mode_reg (mode0, op0);
!   if (! (*insn_data[d->icode].operand[1].predicate) (op1, mode1))
      op1 = copy_to_mode_reg (mode1, op1);
  
    op2 = gen_rtx_fmt_ee (comparison, mode0, op0, op1);
--- 13370,13380 ----
    emit_move_insn (target, const0_rtx);
    target = gen_rtx_SUBREG (QImode, target, 0);
  
!   if ((optimize && !register_operand (op0, mode0))
!       || !(*insn_data[d->icode].operand[0].predicate) (op0, mode0))
      op0 = copy_to_mode_reg (mode0, op0);
!   if ((optimize && !register_operand (op1, mode1))
!       || !(*insn_data[d->icode].operand[1].predicate) (op1, mode1))
      op1 = copy_to_mode_reg (mode1, op1);
  
    op2 = gen_rtx_fmt_ee (comparison, mode0, op0, op1);
*************** ix86_expand_builtin (tree exp, rtx targe
*** 13449,13455 ****
  
        if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
  	op0 = copy_to_mode_reg (mode0, op0);
!       if (! (*insn_data[icode].operand[2].predicate) (op1, mode1))
  	op1 = copy_to_mode_reg (mode1, op1);
        if (! (*insn_data[icode].operand[3].predicate) (op2, mode2))
  	{
--- 13471,13478 ----
  
        if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
  	op0 = copy_to_mode_reg (mode0, op0);
!       if ((optimize && !register_operand (op1, mode1))
! 	  || ! (*insn_data[icode].operand[2].predicate) (op1, mode1))
  	op1 = copy_to_mode_reg (mode1, op1);
        if (! (*insn_data[icode].operand[3].predicate) (op2, mode2))
  	{
*************** ix86_expand_builtin (tree exp, rtx targe
*** 13470,13476 ****
      case IX86_BUILTIN_MASKMOVQ:
      case IX86_BUILTIN_MASKMOVDQU:
        icode = (fcode == IX86_BUILTIN_MASKMOVQ
! 	       ? (TARGET_64BIT ? CODE_FOR_mmx_maskmovq_rex : CODE_FOR_mmx_maskmovq)
  	       : (TARGET_64BIT ? CODE_FOR_sse2_maskmovdqu_rex64
  		  : CODE_FOR_sse2_maskmovdqu));
        /* Note the arg order is different from the operand order.  */
--- 13493,13500 ----
      case IX86_BUILTIN_MASKMOVQ:
      case IX86_BUILTIN_MASKMOVDQU:
        icode = (fcode == IX86_BUILTIN_MASKMOVQ
! 	       ? (TARGET_64BIT ? CODE_FOR_mmx_maskmovq_rex
! 		  : CODE_FOR_mmx_maskmovq)
  	       : (TARGET_64BIT ? CODE_FOR_sse2_maskmovdqu_rex64
  		  : CODE_FOR_sse2_maskmovdqu));
        /* Note the arg order is different from the operand order.  */
*************** ix86_expand_builtin (tree exp, rtx targe
*** 13537,13548 ****
        mode0 = insn_data[icode].operand[1].mode;
        mode1 = insn_data[icode].operand[2].mode;
  
!       if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
! 	op0 = copy_to_mode_reg (mode0, op0);
        op1 = gen_rtx_MEM (mode1, copy_to_mode_reg (Pmode, op1));
!       if (target == 0
  	  || GET_MODE (target) != tmode
! 	  || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
  	target = gen_reg_rtx (tmode);
        pat = GEN_FCN (icode) (target, op0, op1);
        if (! pat)
--- 13561,13571 ----
        mode0 = insn_data[icode].operand[1].mode;
        mode1 = insn_data[icode].operand[2].mode;
  
!       op0 = force_reg (mode0, op0);
        op1 = gen_rtx_MEM (mode1, copy_to_mode_reg (Pmode, op1));
!       if (optimize || target == 0
  	  || GET_MODE (target) != tmode
! 	  || !register_operand (target, tmode))
  	target = gen_reg_rtx (tmode);
        pat = GEN_FCN (icode) (target, op0, op1);
        if (! pat)
*************** ix86_expand_builtin (tree exp, rtx targe
*** 13566,13573 ****
        mode1 = insn_data[icode].operand[1].mode;
  
        op0 = gen_rtx_MEM (mode0, copy_to_mode_reg (Pmode, op0));
!       if (! (*insn_data[icode].operand[1].predicate) (op1, mode1))
! 	op1 = copy_to_mode_reg (mode1, op1);
  
        pat = GEN_FCN (icode) (op0, op1);
        if (! pat)
--- 13589,13595 ----
        mode1 = insn_data[icode].operand[1].mode;
  
        op0 = gen_rtx_MEM (mode0, copy_to_mode_reg (Pmode, op0));
!       op1 = force_reg (mode1, op1);
  
        pat = GEN_FCN (icode) (op0, op1);
        if (! pat)
*************** ix86_expand_builtin (tree exp, rtx targe
*** 13610,13616 ****
  
        if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
  	op0 = copy_to_mode_reg (mode0, op0);
!       if (! (*insn_data[icode].operand[2].predicate) (op1, mode1))
  	op1 = copy_to_mode_reg (mode1, op1);
        if (! (*insn_data[icode].operand[3].predicate) (op2, mode2))
  	{
--- 13632,13639 ----
  
        if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
  	op0 = copy_to_mode_reg (mode0, op0);
!       if ((optimize && !register_operand (op1, mode1))
! 	  || !(*insn_data[icode].operand[2].predicate) (op1, mode1))
  	op1 = copy_to_mode_reg (mode1, op1);
        if (! (*insn_data[icode].operand[3].predicate) (op2, mode2))
  	{
*************** ix86_expand_builtin (tree exp, rtx targe
*** 13618,13624 ****
  	  error ("mask must be an immediate");
  	  return gen_reg_rtx (tmode);
  	}
!       if (target == 0
  	  || GET_MODE (target) != tmode
  	  || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
  	target = gen_reg_rtx (tmode);
--- 13641,13647 ----
  	  error ("mask must be an immediate");
  	  return gen_reg_rtx (tmode);
  	}
!       if (optimize || target == 0
  	  || GET_MODE (target) != tmode
  	  || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
  	target = gen_reg_rtx (tmode);


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]