Merge branch 'vendor/GCC50' - gcc 5.0 snapshot 1 FEB 2015
[dragonfly.git] / contrib / gcc-5.0 / gcc / simplify-rtx.c
1 /* RTL simplification functions for GNU compiler.
2    Copyright (C) 1987-2015 Free Software Foundation, Inc.
3
4 This file is part of GCC.
5
6 GCC is free software; you can redistribute it and/or modify it under
7 the terms of the GNU General Public License as published by the Free
8 Software Foundation; either version 3, or (at your option) any later
9 version.
10
11 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
12 WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
14 for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with GCC; see the file COPYING3.  If not see
18 <http://www.gnu.org/licenses/>.  */
19
20
21 #include "config.h"
22 #include "system.h"
23 #include "coretypes.h"
24 #include "tm.h"
25 #include "rtl.h"
26 #include "hash-set.h"
27 #include "machmode.h"
28 #include "vec.h"
29 #include "double-int.h"
30 #include "input.h"
31 #include "alias.h"
32 #include "symtab.h"
33 #include "wide-int.h"
34 #include "inchash.h"
35 #include "tree.h"
36 #include "fold-const.h"
37 #include "varasm.h"
38 #include "tm_p.h"
39 #include "regs.h"
40 #include "hard-reg-set.h"
41 #include "flags.h"
42 #include "insn-config.h"
43 #include "recog.h"
44 #include "function.h"
45 #include "insn-codes.h"
46 #include "optabs.h"
47 #include "hashtab.h"
48 #include "statistics.h"
49 #include "real.h"
50 #include "fixed-value.h"
51 #include "expmed.h"
52 #include "dojump.h"
53 #include "explow.h"
54 #include "calls.h"
55 #include "emit-rtl.h"
56 #include "stmt.h"
57 #include "expr.h"
58 #include "diagnostic-core.h"
59 #include "ggc.h"
60 #include "target.h"
61 #include "predict.h"
62
63 /* Simplification and canonicalization of RTL.  */
64
65 /* Much code operates on (low, high) pairs; the low value is an
66    unsigned wide int, the high value a signed wide int.  We
67    occasionally need to sign extend from low to high as if low were a
68    signed wide int.  */
69 #define HWI_SIGN_EXTEND(low) \
70  ((((HOST_WIDE_INT) low) < 0) ? ((HOST_WIDE_INT) -1) : ((HOST_WIDE_INT) 0))
71
72 static rtx neg_const_int (machine_mode, const_rtx);
73 static bool plus_minus_operand_p (const_rtx);
74 static bool simplify_plus_minus_op_data_cmp (rtx, rtx);
75 static rtx simplify_plus_minus (enum rtx_code, machine_mode, rtx, rtx);
76 static rtx simplify_immed_subreg (machine_mode, rtx, machine_mode,
77                                   unsigned int);
78 static rtx simplify_associative_operation (enum rtx_code, machine_mode,
79                                            rtx, rtx);
80 static rtx simplify_relational_operation_1 (enum rtx_code, machine_mode,
81                                             machine_mode, rtx, rtx);
82 static rtx simplify_unary_operation_1 (enum rtx_code, machine_mode, rtx);
83 static rtx simplify_binary_operation_1 (enum rtx_code, machine_mode,
84                                         rtx, rtx, rtx, rtx);
85 \f
86 /* Negate a CONST_INT rtx, truncating (because a conversion from a
87    maximally negative number can overflow).  */
88 static rtx
89 neg_const_int (machine_mode mode, const_rtx i)
90 {
91   return gen_int_mode (-(unsigned HOST_WIDE_INT) INTVAL (i), mode);
92 }
93
94 /* Test whether expression, X, is an immediate constant that represents
95    the most significant bit of machine mode MODE.  */
96
97 bool
98 mode_signbit_p (machine_mode mode, const_rtx x)
99 {
100   unsigned HOST_WIDE_INT val;
101   unsigned int width;
102
103   if (GET_MODE_CLASS (mode) != MODE_INT)
104     return false;
105
106   width = GET_MODE_PRECISION (mode);
107   if (width == 0)
108     return false;
109
110   if (width <= HOST_BITS_PER_WIDE_INT
111       && CONST_INT_P (x))
112     val = INTVAL (x);
113 #if TARGET_SUPPORTS_WIDE_INT
114   else if (CONST_WIDE_INT_P (x))
115     {
116       unsigned int i;
117       unsigned int elts = CONST_WIDE_INT_NUNITS (x);
118       if (elts != (width + HOST_BITS_PER_WIDE_INT - 1) / HOST_BITS_PER_WIDE_INT)
119         return false;
120       for (i = 0; i < elts - 1; i++)
121         if (CONST_WIDE_INT_ELT (x, i) != 0)
122           return false;
123       val = CONST_WIDE_INT_ELT (x, elts - 1);
124       width %= HOST_BITS_PER_WIDE_INT;
125       if (width == 0)
126         width = HOST_BITS_PER_WIDE_INT;
127     }
128 #else
129   else if (width <= HOST_BITS_PER_DOUBLE_INT
130            && CONST_DOUBLE_AS_INT_P (x)
131            && CONST_DOUBLE_LOW (x) == 0)
132     {
133       val = CONST_DOUBLE_HIGH (x);
134       width -= HOST_BITS_PER_WIDE_INT;
135     }
136 #endif
137   else
138     /* X is not an integer constant.  */
139     return false;
140
141   if (width < HOST_BITS_PER_WIDE_INT)
142     val &= ((unsigned HOST_WIDE_INT) 1 << width) - 1;
143   return val == ((unsigned HOST_WIDE_INT) 1 << (width - 1));
144 }
145
146 /* Test whether VAL is equal to the most significant bit of mode MODE
147    (after masking with the mode mask of MODE).  Returns false if the
148    precision of MODE is too large to handle.  */
149
150 bool
151 val_signbit_p (machine_mode mode, unsigned HOST_WIDE_INT val)
152 {
153   unsigned int width;
154
155   if (GET_MODE_CLASS (mode) != MODE_INT)
156     return false;
157
158   width = GET_MODE_PRECISION (mode);
159   if (width == 0 || width > HOST_BITS_PER_WIDE_INT)
160     return false;
161
162   val &= GET_MODE_MASK (mode);
163   return val == ((unsigned HOST_WIDE_INT) 1 << (width - 1));
164 }
165
166 /* Test whether the most significant bit of mode MODE is set in VAL.
167    Returns false if the precision of MODE is too large to handle.  */
168 bool
169 val_signbit_known_set_p (machine_mode mode, unsigned HOST_WIDE_INT val)
170 {
171   unsigned int width;
172
173   if (GET_MODE_CLASS (mode) != MODE_INT)
174     return false;
175
176   width = GET_MODE_PRECISION (mode);
177   if (width == 0 || width > HOST_BITS_PER_WIDE_INT)
178     return false;
179
180   val &= (unsigned HOST_WIDE_INT) 1 << (width - 1);
181   return val != 0;
182 }
183
184 /* Test whether the most significant bit of mode MODE is clear in VAL.
185    Returns false if the precision of MODE is too large to handle.  */
186 bool
187 val_signbit_known_clear_p (machine_mode mode, unsigned HOST_WIDE_INT val)
188 {
189   unsigned int width;
190
191   if (GET_MODE_CLASS (mode) != MODE_INT)
192     return false;
193
194   width = GET_MODE_PRECISION (mode);
195   if (width == 0 || width > HOST_BITS_PER_WIDE_INT)
196     return false;
197
198   val &= (unsigned HOST_WIDE_INT) 1 << (width - 1);
199   return val == 0;
200 }
201 \f
202 /* Make a binary operation by properly ordering the operands and
203    seeing if the expression folds.  */
204
205 rtx
206 simplify_gen_binary (enum rtx_code code, machine_mode mode, rtx op0,
207                      rtx op1)
208 {
209   rtx tem;
210
211   /* If this simplifies, do it.  */
212   tem = simplify_binary_operation (code, mode, op0, op1);
213   if (tem)
214     return tem;
215
216   /* Put complex operands first and constants second if commutative.  */
217   if (GET_RTX_CLASS (code) == RTX_COMM_ARITH
218       && swap_commutative_operands_p (op0, op1))
219     tem = op0, op0 = op1, op1 = tem;
220
221   return gen_rtx_fmt_ee (code, mode, op0, op1);
222 }
223 \f
224 /* If X is a MEM referencing the constant pool, return the real value.
225    Otherwise return X.  */
226 rtx
227 avoid_constant_pool_reference (rtx x)
228 {
229   rtx c, tmp, addr;
230   machine_mode cmode;
231   HOST_WIDE_INT offset = 0;
232
233   switch (GET_CODE (x))
234     {
235     case MEM:
236       break;
237
238     case FLOAT_EXTEND:
239       /* Handle float extensions of constant pool references.  */
240       tmp = XEXP (x, 0);
241       c = avoid_constant_pool_reference (tmp);
242       if (c != tmp && CONST_DOUBLE_AS_FLOAT_P (c))
243         {
244           REAL_VALUE_TYPE d;
245
246           REAL_VALUE_FROM_CONST_DOUBLE (d, c);
247           return CONST_DOUBLE_FROM_REAL_VALUE (d, GET_MODE (x));
248         }
249       return x;
250
251     default:
252       return x;
253     }
254
255   if (GET_MODE (x) == BLKmode)
256     return x;
257
258   addr = XEXP (x, 0);
259
260   /* Call target hook to avoid the effects of -fpic etc....  */
261   addr = targetm.delegitimize_address (addr);
262
263   /* Split the address into a base and integer offset.  */
264   if (GET_CODE (addr) == CONST
265       && GET_CODE (XEXP (addr, 0)) == PLUS
266       && CONST_INT_P (XEXP (XEXP (addr, 0), 1)))
267     {
268       offset = INTVAL (XEXP (XEXP (addr, 0), 1));
269       addr = XEXP (XEXP (addr, 0), 0);
270     }
271
272   if (GET_CODE (addr) == LO_SUM)
273     addr = XEXP (addr, 1);
274
275   /* If this is a constant pool reference, we can turn it into its
276      constant and hope that simplifications happen.  */
277   if (GET_CODE (addr) == SYMBOL_REF
278       && CONSTANT_POOL_ADDRESS_P (addr))
279     {
280       c = get_pool_constant (addr);
281       cmode = get_pool_mode (addr);
282
283       /* If we're accessing the constant in a different mode than it was
284          originally stored, attempt to fix that up via subreg simplifications.
285          If that fails we have no choice but to return the original memory.  */
286       if ((offset != 0 || cmode != GET_MODE (x))
287           && offset >= 0 && offset < GET_MODE_SIZE (cmode))
288         {
289           rtx tem = simplify_subreg (GET_MODE (x), c, cmode, offset);
290           if (tem && CONSTANT_P (tem))
291             return tem;
292         }
293       else
294         return c;
295     }
296
297   return x;
298 }
299 \f
300 /* Simplify a MEM based on its attributes.  This is the default
301    delegitimize_address target hook, and it's recommended that every
302    overrider call it.  */
303
304 rtx
305 delegitimize_mem_from_attrs (rtx x)
306 {
307   /* MEMs without MEM_OFFSETs may have been offset, so we can't just
308      use their base addresses as equivalent.  */
309   if (MEM_P (x)
310       && MEM_EXPR (x)
311       && MEM_OFFSET_KNOWN_P (x))
312     {
313       tree decl = MEM_EXPR (x);
314       machine_mode mode = GET_MODE (x);
315       HOST_WIDE_INT offset = 0;
316
317       switch (TREE_CODE (decl))
318         {
319         default:
320           decl = NULL;
321           break;
322
323         case VAR_DECL:
324           break;
325
326         case ARRAY_REF:
327         case ARRAY_RANGE_REF:
328         case COMPONENT_REF:
329         case BIT_FIELD_REF:
330         case REALPART_EXPR:
331         case IMAGPART_EXPR:
332         case VIEW_CONVERT_EXPR:
333           {
334             HOST_WIDE_INT bitsize, bitpos;
335             tree toffset;
336             int unsignedp, volatilep = 0;
337
338             decl = get_inner_reference (decl, &bitsize, &bitpos, &toffset,
339                                         &mode, &unsignedp, &volatilep, false);
340             if (bitsize != GET_MODE_BITSIZE (mode)
341                 || (bitpos % BITS_PER_UNIT)
342                 || (toffset && !tree_fits_shwi_p (toffset)))
343               decl = NULL;
344             else
345               {
346                 offset += bitpos / BITS_PER_UNIT;
347                 if (toffset)
348                   offset += tree_to_shwi (toffset);
349               }
350             break;
351           }
352         }
353
354       if (decl
355           && mode == GET_MODE (x)
356           && TREE_CODE (decl) == VAR_DECL
357           && (TREE_STATIC (decl)
358               || DECL_THREAD_LOCAL_P (decl))
359           && DECL_RTL_SET_P (decl)
360           && MEM_P (DECL_RTL (decl)))
361         {
362           rtx newx;
363
364           offset += MEM_OFFSET (x);
365
366           newx = DECL_RTL (decl);
367
368           if (MEM_P (newx))
369             {
370               rtx n = XEXP (newx, 0), o = XEXP (x, 0);
371
372               /* Avoid creating a new MEM needlessly if we already had
373                  the same address.  We do if there's no OFFSET and the
374                  old address X is identical to NEWX, or if X is of the
375                  form (plus NEWX OFFSET), or the NEWX is of the form
376                  (plus Y (const_int Z)) and X is that with the offset
377                  added: (plus Y (const_int Z+OFFSET)).  */
378               if (!((offset == 0
379                      || (GET_CODE (o) == PLUS
380                          && GET_CODE (XEXP (o, 1)) == CONST_INT
381                          && (offset == INTVAL (XEXP (o, 1))
382                              || (GET_CODE (n) == PLUS
383                                  && GET_CODE (XEXP (n, 1)) == CONST_INT
384                                  && (INTVAL (XEXP (n, 1)) + offset
385                                      == INTVAL (XEXP (o, 1)))
386                                  && (n = XEXP (n, 0))))
387                          && (o = XEXP (o, 0))))
388                     && rtx_equal_p (o, n)))
389                 x = adjust_address_nv (newx, mode, offset);
390             }
391           else if (GET_MODE (x) == GET_MODE (newx)
392                    && offset == 0)
393             x = newx;
394         }
395     }
396
397   return x;
398 }
399 \f
400 /* Make a unary operation by first seeing if it folds and otherwise making
401    the specified operation.  */
402
403 rtx
404 simplify_gen_unary (enum rtx_code code, machine_mode mode, rtx op,
405                     machine_mode op_mode)
406 {
407   rtx tem;
408
409   /* If this simplifies, use it.  */
410   if ((tem = simplify_unary_operation (code, mode, op, op_mode)) != 0)
411     return tem;
412
413   return gen_rtx_fmt_e (code, mode, op);
414 }
415
416 /* Likewise for ternary operations.  */
417
418 rtx
419 simplify_gen_ternary (enum rtx_code code, machine_mode mode,
420                       machine_mode op0_mode, rtx op0, rtx op1, rtx op2)
421 {
422   rtx tem;
423
424   /* If this simplifies, use it.  */
425   if (0 != (tem = simplify_ternary_operation (code, mode, op0_mode,
426                                               op0, op1, op2)))
427     return tem;
428
429   return gen_rtx_fmt_eee (code, mode, op0, op1, op2);
430 }
431
432 /* Likewise, for relational operations.
433    CMP_MODE specifies mode comparison is done in.  */
434
435 rtx
436 simplify_gen_relational (enum rtx_code code, machine_mode mode,
437                          machine_mode cmp_mode, rtx op0, rtx op1)
438 {
439   rtx tem;
440
441   if (0 != (tem = simplify_relational_operation (code, mode, cmp_mode,
442                                                  op0, op1)))
443     return tem;
444
445   return gen_rtx_fmt_ee (code, mode, op0, op1);
446 }
447 \f
448 /* If FN is NULL, replace all occurrences of OLD_RTX in X with copy_rtx (DATA)
449    and simplify the result.  If FN is non-NULL, call this callback on each
450    X, if it returns non-NULL, replace X with its return value and simplify the
451    result.  */
452
453 rtx
454 simplify_replace_fn_rtx (rtx x, const_rtx old_rtx,
455                          rtx (*fn) (rtx, const_rtx, void *), void *data)
456 {
457   enum rtx_code code = GET_CODE (x);
458   machine_mode mode = GET_MODE (x);
459   machine_mode op_mode;
460   const char *fmt;
461   rtx op0, op1, op2, newx, op;
462   rtvec vec, newvec;
463   int i, j;
464
465   if (__builtin_expect (fn != NULL, 0))
466     {
467       newx = fn (x, old_rtx, data);
468       if (newx)
469         return newx;
470     }
471   else if (rtx_equal_p (x, old_rtx))
472     return copy_rtx ((rtx) data);
473
474   switch (GET_RTX_CLASS (code))
475     {
476     case RTX_UNARY:
477       op0 = XEXP (x, 0);
478       op_mode = GET_MODE (op0);
479       op0 = simplify_replace_fn_rtx (op0, old_rtx, fn, data);
480       if (op0 == XEXP (x, 0))
481         return x;
482       return simplify_gen_unary (code, mode, op0, op_mode);
483
484     case RTX_BIN_ARITH:
485     case RTX_COMM_ARITH:
486       op0 = simplify_replace_fn_rtx (XEXP (x, 0), old_rtx, fn, data);
487       op1 = simplify_replace_fn_rtx (XEXP (x, 1), old_rtx, fn, data);
488       if (op0 == XEXP (x, 0) && op1 == XEXP (x, 1))
489         return x;
490       return simplify_gen_binary (code, mode, op0, op1);
491
492     case RTX_COMPARE:
493     case RTX_COMM_COMPARE:
494       op0 = XEXP (x, 0);
495       op1 = XEXP (x, 1);
496       op_mode = GET_MODE (op0) != VOIDmode ? GET_MODE (op0) : GET_MODE (op1);
497       op0 = simplify_replace_fn_rtx (op0, old_rtx, fn, data);
498       op1 = simplify_replace_fn_rtx (op1, old_rtx, fn, data);
499       if (op0 == XEXP (x, 0) && op1 == XEXP (x, 1))
500         return x;
501       return simplify_gen_relational (code, mode, op_mode, op0, op1);
502
503     case RTX_TERNARY:
504     case RTX_BITFIELD_OPS:
505       op0 = XEXP (x, 0);
506       op_mode = GET_MODE (op0);
507       op0 = simplify_replace_fn_rtx (op0, old_rtx, fn, data);
508       op1 = simplify_replace_fn_rtx (XEXP (x, 1), old_rtx, fn, data);
509       op2 = simplify_replace_fn_rtx (XEXP (x, 2), old_rtx, fn, data);
510       if (op0 == XEXP (x, 0) && op1 == XEXP (x, 1) && op2 == XEXP (x, 2))
511         return x;
512       if (op_mode == VOIDmode)
513         op_mode = GET_MODE (op0);
514       return simplify_gen_ternary (code, mode, op_mode, op0, op1, op2);
515
516     case RTX_EXTRA:
517       if (code == SUBREG)
518         {
519           op0 = simplify_replace_fn_rtx (SUBREG_REG (x), old_rtx, fn, data);
520           if (op0 == SUBREG_REG (x))
521             return x;
522           op0 = simplify_gen_subreg (GET_MODE (x), op0,
523                                      GET_MODE (SUBREG_REG (x)),
524                                      SUBREG_BYTE (x));
525           return op0 ? op0 : x;
526         }
527       break;
528
529     case RTX_OBJ:
530       if (code == MEM)
531         {
532           op0 = simplify_replace_fn_rtx (XEXP (x, 0), old_rtx, fn, data);
533           if (op0 == XEXP (x, 0))
534             return x;
535           return replace_equiv_address_nv (x, op0);
536         }
537       else if (code == LO_SUM)
538         {
539           op0 = simplify_replace_fn_rtx (XEXP (x, 0), old_rtx, fn, data);
540           op1 = simplify_replace_fn_rtx (XEXP (x, 1), old_rtx, fn, data);
541
542           /* (lo_sum (high x) y) -> y where x and y have the same base.  */
543           if (GET_CODE (op0) == HIGH)
544             {
545               rtx base0, base1, offset0, offset1;
546               split_const (XEXP (op0, 0), &base0, &offset0);
547               split_const (op1, &base1, &offset1);
548               if (rtx_equal_p (base0, base1))
549                 return op1;
550             }
551
552           if (op0 == XEXP (x, 0) && op1 == XEXP (x, 1))
553             return x;
554           return gen_rtx_LO_SUM (mode, op0, op1);
555         }
556       break;
557
558     default:
559       break;
560     }
561
562   newx = x;
563   fmt = GET_RTX_FORMAT (code);
564   for (i = 0; fmt[i]; i++)
565     switch (fmt[i])
566       {
567       case 'E':
568         vec = XVEC (x, i);
569         newvec = XVEC (newx, i);
570         for (j = 0; j < GET_NUM_ELEM (vec); j++)
571           {
572             op = simplify_replace_fn_rtx (RTVEC_ELT (vec, j),
573                                           old_rtx, fn, data);
574             if (op != RTVEC_ELT (vec, j))
575               {
576                 if (newvec == vec)
577                   {
578                     newvec = shallow_copy_rtvec (vec);
579                     if (x == newx)
580                       newx = shallow_copy_rtx (x);
581                     XVEC (newx, i) = newvec;
582                   }
583                 RTVEC_ELT (newvec, j) = op;
584               }
585           }
586         break;
587
588       case 'e':
589         if (XEXP (x, i))
590           {
591             op = simplify_replace_fn_rtx (XEXP (x, i), old_rtx, fn, data);
592             if (op != XEXP (x, i))
593               {
594                 if (x == newx)
595                   newx = shallow_copy_rtx (x);
596                 XEXP (newx, i) = op;
597               }
598           }
599         break;
600       }
601   return newx;
602 }
603
604 /* Replace all occurrences of OLD_RTX in X with NEW_RTX and try to simplify the
605    resulting RTX.  Return a new RTX which is as simplified as possible.  */
606
607 rtx
608 simplify_replace_rtx (rtx x, const_rtx old_rtx, rtx new_rtx)
609 {
610   return simplify_replace_fn_rtx (x, old_rtx, 0, new_rtx);
611 }
612 \f
613 /* Try to simplify a MODE truncation of OP, which has OP_MODE.
614    Only handle cases where the truncated value is inherently an rvalue.
615
616    RTL provides two ways of truncating a value:
617
618    1. a lowpart subreg.  This form is only a truncation when both
619       the outer and inner modes (here MODE and OP_MODE respectively)
620       are scalar integers, and only then when the subreg is used as
621       an rvalue.
622
623       It is only valid to form such truncating subregs if the
624       truncation requires no action by the target.  The onus for
625       proving this is on the creator of the subreg -- e.g. the
626       caller to simplify_subreg or simplify_gen_subreg -- and typically
627       involves either TRULY_NOOP_TRUNCATION_MODES_P or truncated_to_mode.
628
629    2. a TRUNCATE.  This form handles both scalar and compound integers.
630
631    The first form is preferred where valid.  However, the TRUNCATE
632    handling in simplify_unary_operation turns the second form into the
633    first form when TRULY_NOOP_TRUNCATION_MODES_P or truncated_to_mode allow,
634    so it is generally safe to form rvalue truncations using:
635
636       simplify_gen_unary (TRUNCATE, ...)
637
638    and leave simplify_unary_operation to work out which representation
639    should be used.
640
641    Because of the proof requirements on (1), simplify_truncation must
642    also use simplify_gen_unary (TRUNCATE, ...) to truncate parts of OP,
643    regardless of whether the outer truncation came from a SUBREG or a
644    TRUNCATE.  For example, if the caller has proven that an SImode
645    truncation of:
646
647       (and:DI X Y)
648
649    is a no-op and can be represented as a subreg, it does not follow
650    that SImode truncations of X and Y are also no-ops.  On a target
651    like 64-bit MIPS that requires SImode values to be stored in
652    sign-extended form, an SImode truncation of:
653
654       (and:DI (reg:DI X) (const_int 63))
655
656    is trivially a no-op because only the lower 6 bits can be set.
657    However, X is still an arbitrary 64-bit number and so we cannot
658    assume that truncating it too is a no-op.  */
659
660 static rtx
661 simplify_truncation (machine_mode mode, rtx op,
662                      machine_mode op_mode)
663 {
664   unsigned int precision = GET_MODE_UNIT_PRECISION (mode);
665   unsigned int op_precision = GET_MODE_UNIT_PRECISION (op_mode);
666   gcc_assert (precision <= op_precision);
667
668   /* Optimize truncations of zero and sign extended values.  */
669   if (GET_CODE (op) == ZERO_EXTEND
670       || GET_CODE (op) == SIGN_EXTEND)
671     {
672       /* There are three possibilities.  If MODE is the same as the
673          origmode, we can omit both the extension and the subreg.
674          If MODE is not larger than the origmode, we can apply the
675          truncation without the extension.  Finally, if the outermode
676          is larger than the origmode, we can just extend to the appropriate
677          mode.  */
678       machine_mode origmode = GET_MODE (XEXP (op, 0));
679       if (mode == origmode)
680         return XEXP (op, 0);
681       else if (precision <= GET_MODE_UNIT_PRECISION (origmode))
682         return simplify_gen_unary (TRUNCATE, mode,
683                                    XEXP (op, 0), origmode);
684       else
685         return simplify_gen_unary (GET_CODE (op), mode,
686                                    XEXP (op, 0), origmode);
687     }
688
689   /* If the machine can perform operations in the truncated mode, distribute
690      the truncation, i.e. simplify (truncate:QI (op:SI (x:SI) (y:SI))) into
691      (op:QI (truncate:QI (x:SI)) (truncate:QI (y:SI))).  */
692   if (1
693 #ifdef WORD_REGISTER_OPERATIONS
694       && precision >= BITS_PER_WORD
695 #endif
696       && (GET_CODE (op) == PLUS
697           || GET_CODE (op) == MINUS
698           || GET_CODE (op) == MULT))
699     {
700       rtx op0 = simplify_gen_unary (TRUNCATE, mode, XEXP (op, 0), op_mode);
701       if (op0)
702         {
703           rtx op1 = simplify_gen_unary (TRUNCATE, mode, XEXP (op, 1), op_mode);
704           if (op1)
705             return simplify_gen_binary (GET_CODE (op), mode, op0, op1);
706         }
707     }
708
709   /* Simplify (truncate:QI (lshiftrt:SI (sign_extend:SI (x:QI)) C)) into
710      to (ashiftrt:QI (x:QI) C), where C is a suitable small constant and
711      the outer subreg is effectively a truncation to the original mode.  */
712   if ((GET_CODE (op) == LSHIFTRT
713        || GET_CODE (op) == ASHIFTRT)
714       /* Ensure that OP_MODE is at least twice as wide as MODE
715          to avoid the possibility that an outer LSHIFTRT shifts by more
716          than the sign extension's sign_bit_copies and introduces zeros
717          into the high bits of the result.  */
718       && 2 * precision <= op_precision
719       && CONST_INT_P (XEXP (op, 1))
720       && GET_CODE (XEXP (op, 0)) == SIGN_EXTEND
721       && GET_MODE (XEXP (XEXP (op, 0), 0)) == mode
722       && UINTVAL (XEXP (op, 1)) < precision)
723     return simplify_gen_binary (ASHIFTRT, mode,
724                                 XEXP (XEXP (op, 0), 0), XEXP (op, 1));
725
726   /* Likewise (truncate:QI (lshiftrt:SI (zero_extend:SI (x:QI)) C)) into
727      to (lshiftrt:QI (x:QI) C), where C is a suitable small constant and
728      the outer subreg is effectively a truncation to the original mode.  */
729   if ((GET_CODE (op) == LSHIFTRT
730        || GET_CODE (op) == ASHIFTRT)
731       && CONST_INT_P (XEXP (op, 1))
732       && GET_CODE (XEXP (op, 0)) == ZERO_EXTEND
733       && GET_MODE (XEXP (XEXP (op, 0), 0)) == mode
734       && UINTVAL (XEXP (op, 1)) < precision)
735     return simplify_gen_binary (LSHIFTRT, mode,
736                                 XEXP (XEXP (op, 0), 0), XEXP (op, 1));
737
738   /* Likewise (truncate:QI (ashift:SI (zero_extend:SI (x:QI)) C)) into
739      to (ashift:QI (x:QI) C), where C is a suitable small constant and
740      the outer subreg is effectively a truncation to the original mode.  */
741   if (GET_CODE (op) == ASHIFT
742       && CONST_INT_P (XEXP (op, 1))
743       && (GET_CODE (XEXP (op, 0)) == ZERO_EXTEND
744           || GET_CODE (XEXP (op, 0)) == SIGN_EXTEND)
745       && GET_MODE (XEXP (XEXP (op, 0), 0)) == mode
746       && UINTVAL (XEXP (op, 1)) < precision)
747     return simplify_gen_binary (ASHIFT, mode,
748                                 XEXP (XEXP (op, 0), 0), XEXP (op, 1));
749
750   /* Recognize a word extraction from a multi-word subreg.  */
751   if ((GET_CODE (op) == LSHIFTRT
752        || GET_CODE (op) == ASHIFTRT)
753       && SCALAR_INT_MODE_P (mode)
754       && SCALAR_INT_MODE_P (op_mode)
755       && precision >= BITS_PER_WORD
756       && 2 * precision <= op_precision
757       && CONST_INT_P (XEXP (op, 1))
758       && (INTVAL (XEXP (op, 1)) & (precision - 1)) == 0
759       && UINTVAL (XEXP (op, 1)) < op_precision)
760     {
761       int byte = subreg_lowpart_offset (mode, op_mode);
762       int shifted_bytes = INTVAL (XEXP (op, 1)) / BITS_PER_UNIT;
763       return simplify_gen_subreg (mode, XEXP (op, 0), op_mode,
764                                   (WORDS_BIG_ENDIAN
765                                    ? byte - shifted_bytes
766                                    : byte + shifted_bytes));
767     }
768
769   /* If we have a TRUNCATE of a right shift of MEM, make a new MEM
770      and try replacing the TRUNCATE and shift with it.  Don't do this
771      if the MEM has a mode-dependent address.  */
772   if ((GET_CODE (op) == LSHIFTRT
773        || GET_CODE (op) == ASHIFTRT)
774       && SCALAR_INT_MODE_P (op_mode)
775       && MEM_P (XEXP (op, 0))
776       && CONST_INT_P (XEXP (op, 1))
777       && (INTVAL (XEXP (op, 1)) % GET_MODE_BITSIZE (mode)) == 0
778       && INTVAL (XEXP (op, 1)) > 0
779       && INTVAL (XEXP (op, 1)) < GET_MODE_BITSIZE (op_mode)
780       && ! mode_dependent_address_p (XEXP (XEXP (op, 0), 0),
781                                      MEM_ADDR_SPACE (XEXP (op, 0)))
782       && ! MEM_VOLATILE_P (XEXP (op, 0))
783       && (GET_MODE_SIZE (mode) >= UNITS_PER_WORD
784           || WORDS_BIG_ENDIAN == BYTES_BIG_ENDIAN))
785     {
786       int byte = subreg_lowpart_offset (mode, op_mode);
787       int shifted_bytes = INTVAL (XEXP (op, 1)) / BITS_PER_UNIT;
788       return adjust_address_nv (XEXP (op, 0), mode,
789                                 (WORDS_BIG_ENDIAN
790                                  ? byte - shifted_bytes
791                                  : byte + shifted_bytes));
792     }
793
794   /* (truncate:SI (OP:DI ({sign,zero}_extend:DI foo:SI))) is
795      (OP:SI foo:SI) if OP is NEG or ABS.  */
796   if ((GET_CODE (op) == ABS
797        || GET_CODE (op) == NEG)
798       && (GET_CODE (XEXP (op, 0)) == SIGN_EXTEND
799           || GET_CODE (XEXP (op, 0)) == ZERO_EXTEND)
800       && GET_MODE (XEXP (XEXP (op, 0), 0)) == mode)
801     return simplify_gen_unary (GET_CODE (op), mode,
802                                XEXP (XEXP (op, 0), 0), mode);
803
804   /* (truncate:A (subreg:B (truncate:C X) 0)) is
805      (truncate:A X).  */
806   if (GET_CODE (op) == SUBREG
807       && SCALAR_INT_MODE_P (mode)
808       && SCALAR_INT_MODE_P (op_mode)
809       && SCALAR_INT_MODE_P (GET_MODE (SUBREG_REG (op)))
810       && GET_CODE (SUBREG_REG (op)) == TRUNCATE
811       && subreg_lowpart_p (op))
812     {
813       rtx inner = XEXP (SUBREG_REG (op), 0);
814       if (GET_MODE_PRECISION (mode)
815           <= GET_MODE_PRECISION (GET_MODE (SUBREG_REG (op))))
816         return simplify_gen_unary (TRUNCATE, mode, inner, GET_MODE (inner));
817       else
818         /* If subreg above is paradoxical and C is narrower
819            than A, return (subreg:A (truncate:C X) 0).  */
820         return simplify_gen_subreg (mode, SUBREG_REG (op),
821                                     GET_MODE (SUBREG_REG (op)), 0);
822     }
823
824   /* (truncate:A (truncate:B X)) is (truncate:A X).  */
825   if (GET_CODE (op) == TRUNCATE)
826     return simplify_gen_unary (TRUNCATE, mode, XEXP (op, 0),
827                                GET_MODE (XEXP (op, 0)));
828
829   return NULL_RTX;
830 }
831 \f
832 /* Try to simplify a unary operation CODE whose output mode is to be
833    MODE with input operand OP whose mode was originally OP_MODE.
834    Return zero if no simplification can be made.  */
835 rtx
836 simplify_unary_operation (enum rtx_code code, machine_mode mode,
837                           rtx op, machine_mode op_mode)
838 {
839   rtx trueop, tem;
840
841   trueop = avoid_constant_pool_reference (op);
842
843   tem = simplify_const_unary_operation (code, mode, trueop, op_mode);
844   if (tem)
845     return tem;
846
847   return simplify_unary_operation_1 (code, mode, op);
848 }
849
850 /* Perform some simplifications we can do even if the operands
851    aren't constant.  */
852 static rtx
853 simplify_unary_operation_1 (enum rtx_code code, machine_mode mode, rtx op)
854 {
855   enum rtx_code reversed;
856   rtx temp;
857
858   switch (code)
859     {
860     case NOT:
861       /* (not (not X)) == X.  */
862       if (GET_CODE (op) == NOT)
863         return XEXP (op, 0);
864
865       /* (not (eq X Y)) == (ne X Y), etc. if BImode or the result of the
866          comparison is all ones.   */
867       if (COMPARISON_P (op)
868           && (mode == BImode || STORE_FLAG_VALUE == -1)
869           && ((reversed = reversed_comparison_code (op, NULL_RTX)) != UNKNOWN))
870         return simplify_gen_relational (reversed, mode, VOIDmode,
871                                         XEXP (op, 0), XEXP (op, 1));
872
873       /* (not (plus X -1)) can become (neg X).  */
874       if (GET_CODE (op) == PLUS
875           && XEXP (op, 1) == constm1_rtx)
876         return simplify_gen_unary (NEG, mode, XEXP (op, 0), mode);
877
878       /* Similarly, (not (neg X)) is (plus X -1).  */
879       if (GET_CODE (op) == NEG)
880         return simplify_gen_binary (PLUS, mode, XEXP (op, 0),
881                                     CONSTM1_RTX (mode));
882
883       /* (not (xor X C)) for C constant is (xor X D) with D = ~C.  */
884       if (GET_CODE (op) == XOR
885           && CONST_INT_P (XEXP (op, 1))
886           && (temp = simplify_unary_operation (NOT, mode,
887                                                XEXP (op, 1), mode)) != 0)
888         return simplify_gen_binary (XOR, mode, XEXP (op, 0), temp);
889
890       /* (not (plus X C)) for signbit C is (xor X D) with D = ~C.  */
891       if (GET_CODE (op) == PLUS
892           && CONST_INT_P (XEXP (op, 1))
893           && mode_signbit_p (mode, XEXP (op, 1))
894           && (temp = simplify_unary_operation (NOT, mode,
895                                                XEXP (op, 1), mode)) != 0)
896         return simplify_gen_binary (XOR, mode, XEXP (op, 0), temp);
897
898
899       /* (not (ashift 1 X)) is (rotate ~1 X).  We used to do this for
900          operands other than 1, but that is not valid.  We could do a
901          similar simplification for (not (lshiftrt C X)) where C is
902          just the sign bit, but this doesn't seem common enough to
903          bother with.  */
904       if (GET_CODE (op) == ASHIFT
905           && XEXP (op, 0) == const1_rtx)
906         {
907           temp = simplify_gen_unary (NOT, mode, const1_rtx, mode);
908           return simplify_gen_binary (ROTATE, mode, temp, XEXP (op, 1));
909         }
910
911       /* (not (ashiftrt foo C)) where C is the number of bits in FOO
912          minus 1 is (ge foo (const_int 0)) if STORE_FLAG_VALUE is -1,
913          so we can perform the above simplification.  */
914       if (STORE_FLAG_VALUE == -1
915           && GET_CODE (op) == ASHIFTRT
916           && CONST_INT_P (XEXP (op, 1))
917           && INTVAL (XEXP (op, 1)) == GET_MODE_PRECISION (mode) - 1)
918         return simplify_gen_relational (GE, mode, VOIDmode,
919                                         XEXP (op, 0), const0_rtx);
920
921
922       if (GET_CODE (op) == SUBREG
923           && subreg_lowpart_p (op)
924           && (GET_MODE_SIZE (GET_MODE (op))
925               < GET_MODE_SIZE (GET_MODE (SUBREG_REG (op))))
926           && GET_CODE (SUBREG_REG (op)) == ASHIFT
927           && XEXP (SUBREG_REG (op), 0) == const1_rtx)
928         {
929           machine_mode inner_mode = GET_MODE (SUBREG_REG (op));
930           rtx x;
931
932           x = gen_rtx_ROTATE (inner_mode,
933                               simplify_gen_unary (NOT, inner_mode, const1_rtx,
934                                                   inner_mode),
935                               XEXP (SUBREG_REG (op), 1));
936           temp = rtl_hooks.gen_lowpart_no_emit (mode, x);
937           if (temp)
938             return temp;
939         }
940
941       /* Apply De Morgan's laws to reduce number of patterns for machines
942          with negating logical insns (and-not, nand, etc.).  If result has
943          only one NOT, put it first, since that is how the patterns are
944          coded.  */
945       if (GET_CODE (op) == IOR || GET_CODE (op) == AND)
946         {
947           rtx in1 = XEXP (op, 0), in2 = XEXP (op, 1);
948           machine_mode op_mode;
949
950           op_mode = GET_MODE (in1);
951           in1 = simplify_gen_unary (NOT, op_mode, in1, op_mode);
952
953           op_mode = GET_MODE (in2);
954           if (op_mode == VOIDmode)
955             op_mode = mode;
956           in2 = simplify_gen_unary (NOT, op_mode, in2, op_mode);
957
958           if (GET_CODE (in2) == NOT && GET_CODE (in1) != NOT)
959             {
960               rtx tem = in2;
961               in2 = in1; in1 = tem;
962             }
963
964           return gen_rtx_fmt_ee (GET_CODE (op) == IOR ? AND : IOR,
965                                  mode, in1, in2);
966         }
967
968       /* (not (bswap x)) -> (bswap (not x)).  */
969       if (GET_CODE (op) == BSWAP)
970         {
971           rtx x = simplify_gen_unary (NOT, mode, XEXP (op, 0), mode);
972           return simplify_gen_unary (BSWAP, mode, x, mode);
973         }
974       break;
975
976     case NEG:
977       /* (neg (neg X)) == X.  */
978       if (GET_CODE (op) == NEG)
979         return XEXP (op, 0);
980
981       /* (neg (plus X 1)) can become (not X).  */
982       if (GET_CODE (op) == PLUS
983           && XEXP (op, 1) == const1_rtx)
984         return simplify_gen_unary (NOT, mode, XEXP (op, 0), mode);
985
986       /* Similarly, (neg (not X)) is (plus X 1).  */
987       if (GET_CODE (op) == NOT)
988         return simplify_gen_binary (PLUS, mode, XEXP (op, 0),
989                                     CONST1_RTX (mode));
990
991       /* (neg (minus X Y)) can become (minus Y X).  This transformation
992          isn't safe for modes with signed zeros, since if X and Y are
993          both +0, (minus Y X) is the same as (minus X Y).  If the
994          rounding mode is towards +infinity (or -infinity) then the two
995          expressions will be rounded differently.  */
996       if (GET_CODE (op) == MINUS
997           && !HONOR_SIGNED_ZEROS (mode)
998           && !HONOR_SIGN_DEPENDENT_ROUNDING (mode))
999         return simplify_gen_binary (MINUS, mode, XEXP (op, 1), XEXP (op, 0));
1000
1001       if (GET_CODE (op) == PLUS
1002           && !HONOR_SIGNED_ZEROS (mode)
1003           && !HONOR_SIGN_DEPENDENT_ROUNDING (mode))
1004         {
1005           /* (neg (plus A C)) is simplified to (minus -C A).  */
1006           if (CONST_SCALAR_INT_P (XEXP (op, 1))
1007               || CONST_DOUBLE_AS_FLOAT_P (XEXP (op, 1)))
1008             {
1009               temp = simplify_unary_operation (NEG, mode, XEXP (op, 1), mode);
1010               if (temp)
1011                 return simplify_gen_binary (MINUS, mode, temp, XEXP (op, 0));
1012             }
1013
1014           /* (neg (plus A B)) is canonicalized to (minus (neg A) B).  */
1015           temp = simplify_gen_unary (NEG, mode, XEXP (op, 0), mode);
1016           return simplify_gen_binary (MINUS, mode, temp, XEXP (op, 1));
1017         }
1018
1019       /* (neg (mult A B)) becomes (mult A (neg B)).
1020          This works even for floating-point values.  */
1021       if (GET_CODE (op) == MULT
1022           && !HONOR_SIGN_DEPENDENT_ROUNDING (mode))
1023         {
1024           temp = simplify_gen_unary (NEG, mode, XEXP (op, 1), mode);
1025           return simplify_gen_binary (MULT, mode, XEXP (op, 0), temp);
1026         }
1027
1028       /* NEG commutes with ASHIFT since it is multiplication.  Only do
1029          this if we can then eliminate the NEG (e.g., if the operand
1030          is a constant).  */
1031       if (GET_CODE (op) == ASHIFT)
1032         {
1033           temp = simplify_unary_operation (NEG, mode, XEXP (op, 0), mode);
1034           if (temp)
1035             return simplify_gen_binary (ASHIFT, mode, temp, XEXP (op, 1));
1036         }
1037
1038       /* (neg (ashiftrt X C)) can be replaced by (lshiftrt X C) when
1039          C is equal to the width of MODE minus 1.  */
1040       if (GET_CODE (op) == ASHIFTRT
1041           && CONST_INT_P (XEXP (op, 1))
1042           && INTVAL (XEXP (op, 1)) == GET_MODE_PRECISION (mode) - 1)
1043         return simplify_gen_binary (LSHIFTRT, mode,
1044                                     XEXP (op, 0), XEXP (op, 1));
1045
1046       /* (neg (lshiftrt X C)) can be replaced by (ashiftrt X C) when
1047          C is equal to the width of MODE minus 1.  */
1048       if (GET_CODE (op) == LSHIFTRT
1049           && CONST_INT_P (XEXP (op, 1))
1050           && INTVAL (XEXP (op, 1)) == GET_MODE_PRECISION (mode) - 1)
1051         return simplify_gen_binary (ASHIFTRT, mode,
1052                                     XEXP (op, 0), XEXP (op, 1));
1053
1054       /* (neg (xor A 1)) is (plus A -1) if A is known to be either 0 or 1.  */
1055       if (GET_CODE (op) == XOR
1056           && XEXP (op, 1) == const1_rtx
1057           && nonzero_bits (XEXP (op, 0), mode) == 1)
1058         return plus_constant (mode, XEXP (op, 0), -1);
1059
1060       /* (neg (lt x 0)) is (ashiftrt X C) if STORE_FLAG_VALUE is 1.  */
1061       /* (neg (lt x 0)) is (lshiftrt X C) if STORE_FLAG_VALUE is -1.  */
1062       if (GET_CODE (op) == LT
1063           && XEXP (op, 1) == const0_rtx
1064           && SCALAR_INT_MODE_P (GET_MODE (XEXP (op, 0))))
1065         {
1066           machine_mode inner = GET_MODE (XEXP (op, 0));
1067           int isize = GET_MODE_PRECISION (inner);
1068           if (STORE_FLAG_VALUE == 1)
1069             {
1070               temp = simplify_gen_binary (ASHIFTRT, inner, XEXP (op, 0),
1071                                           GEN_INT (isize - 1));
1072               if (mode == inner)
1073                 return temp;
1074               if (GET_MODE_PRECISION (mode) > isize)
1075                 return simplify_gen_unary (SIGN_EXTEND, mode, temp, inner);
1076               return simplify_gen_unary (TRUNCATE, mode, temp, inner);
1077             }
1078           else if (STORE_FLAG_VALUE == -1)
1079             {
1080               temp = simplify_gen_binary (LSHIFTRT, inner, XEXP (op, 0),
1081                                           GEN_INT (isize - 1));
1082               if (mode == inner)
1083                 return temp;
1084               if (GET_MODE_PRECISION (mode) > isize)
1085                 return simplify_gen_unary (ZERO_EXTEND, mode, temp, inner);
1086               return simplify_gen_unary (TRUNCATE, mode, temp, inner);
1087             }
1088         }
1089       break;
1090
1091     case TRUNCATE:
1092       /* Don't optimize (lshiftrt (mult ...)) as it would interfere
1093          with the umulXi3_highpart patterns.  */
1094       if (GET_CODE (op) == LSHIFTRT
1095           && GET_CODE (XEXP (op, 0)) == MULT)
1096         break;
1097
1098       if (GET_MODE_CLASS (mode) == MODE_PARTIAL_INT)
1099         {
1100           if (TRULY_NOOP_TRUNCATION_MODES_P (mode, GET_MODE (op)))
1101             {
1102               temp = rtl_hooks.gen_lowpart_no_emit (mode, op);
1103               if (temp)
1104                 return temp;
1105             }
1106           /* We can't handle truncation to a partial integer mode here
1107              because we don't know the real bitsize of the partial
1108              integer mode.  */
1109           break;
1110         }
1111
1112       if (GET_MODE (op) != VOIDmode)
1113         {
1114           temp = simplify_truncation (mode, op, GET_MODE (op));
1115           if (temp)
1116             return temp;
1117         }
1118
1119       /* If we know that the value is already truncated, we can
1120          replace the TRUNCATE with a SUBREG.  */
1121       if (GET_MODE_NUNITS (mode) == 1
1122           && (TRULY_NOOP_TRUNCATION_MODES_P (mode, GET_MODE (op))
1123               || truncated_to_mode (mode, op)))
1124         {
1125           temp = rtl_hooks.gen_lowpart_no_emit (mode, op);
1126           if (temp)
1127             return temp;
1128         }
1129
1130       /* A truncate of a comparison can be replaced with a subreg if
1131          STORE_FLAG_VALUE permits.  This is like the previous test,
1132          but it works even if the comparison is done in a mode larger
1133          than HOST_BITS_PER_WIDE_INT.  */
1134       if (HWI_COMPUTABLE_MODE_P (mode)
1135           && COMPARISON_P (op)
1136           && (STORE_FLAG_VALUE & ~GET_MODE_MASK (mode)) == 0)
1137         {
1138           temp = rtl_hooks.gen_lowpart_no_emit (mode, op);
1139           if (temp)
1140             return temp;
1141         }
1142
1143       /* A truncate of a memory is just loading the low part of the memory
1144          if we are not changing the meaning of the address. */
1145       if (GET_CODE (op) == MEM
1146           && !VECTOR_MODE_P (mode)
1147           && !MEM_VOLATILE_P (op)
1148           && !mode_dependent_address_p (XEXP (op, 0), MEM_ADDR_SPACE (op)))
1149         {
1150           temp = rtl_hooks.gen_lowpart_no_emit (mode, op);
1151           if (temp)
1152             return temp;
1153         }
1154
1155       break;
1156
1157     case FLOAT_TRUNCATE:
1158       if (DECIMAL_FLOAT_MODE_P (mode))
1159         break;
1160
1161       /* (float_truncate:SF (float_extend:DF foo:SF)) = foo:SF.  */
1162       if (GET_CODE (op) == FLOAT_EXTEND
1163           && GET_MODE (XEXP (op, 0)) == mode)
1164         return XEXP (op, 0);
1165
1166       /* (float_truncate:SF (float_truncate:DF foo:XF))
1167          = (float_truncate:SF foo:XF).
1168          This may eliminate double rounding, so it is unsafe.
1169
1170          (float_truncate:SF (float_extend:XF foo:DF))
1171          = (float_truncate:SF foo:DF).
1172
1173          (float_truncate:DF (float_extend:XF foo:SF))
1174          = (float_extend:SF foo:DF).  */
1175       if ((GET_CODE (op) == FLOAT_TRUNCATE
1176            && flag_unsafe_math_optimizations)
1177           || GET_CODE (op) == FLOAT_EXTEND)
1178         return simplify_gen_unary (GET_MODE_SIZE (GET_MODE (XEXP (op,
1179                                                             0)))
1180                                    > GET_MODE_SIZE (mode)
1181                                    ? FLOAT_TRUNCATE : FLOAT_EXTEND,
1182                                    mode,
1183                                    XEXP (op, 0), mode);
1184
1185       /*  (float_truncate (float x)) is (float x)  */
1186       if (GET_CODE (op) == FLOAT
1187           && (flag_unsafe_math_optimizations
1188               || (SCALAR_FLOAT_MODE_P (GET_MODE (op))
1189                   && ((unsigned)significand_size (GET_MODE (op))
1190                       >= (GET_MODE_PRECISION (GET_MODE (XEXP (op, 0)))
1191                           - num_sign_bit_copies (XEXP (op, 0),
1192                                                  GET_MODE (XEXP (op, 0))))))))
1193         return simplify_gen_unary (FLOAT, mode,
1194                                    XEXP (op, 0),
1195                                    GET_MODE (XEXP (op, 0)));
1196
1197       /* (float_truncate:SF (OP:DF (float_extend:DF foo:sf))) is
1198          (OP:SF foo:SF) if OP is NEG or ABS.  */
1199       if ((GET_CODE (op) == ABS
1200            || GET_CODE (op) == NEG)
1201           && GET_CODE (XEXP (op, 0)) == FLOAT_EXTEND
1202           && GET_MODE (XEXP (XEXP (op, 0), 0)) == mode)
1203         return simplify_gen_unary (GET_CODE (op), mode,
1204                                    XEXP (XEXP (op, 0), 0), mode);
1205
1206       /* (float_truncate:SF (subreg:DF (float_truncate:SF X) 0))
1207          is (float_truncate:SF x).  */
1208       if (GET_CODE (op) == SUBREG
1209           && subreg_lowpart_p (op)
1210           && GET_CODE (SUBREG_REG (op)) == FLOAT_TRUNCATE)
1211         return SUBREG_REG (op);
1212       break;
1213
1214     case FLOAT_EXTEND:
1215       if (DECIMAL_FLOAT_MODE_P (mode))
1216         break;
1217
1218       /*  (float_extend (float_extend x)) is (float_extend x)
1219
1220           (float_extend (float x)) is (float x) assuming that double
1221           rounding can't happen.
1222           */
1223       if (GET_CODE (op) == FLOAT_EXTEND
1224           || (GET_CODE (op) == FLOAT
1225               && SCALAR_FLOAT_MODE_P (GET_MODE (op))
1226               && ((unsigned)significand_size (GET_MODE (op))
1227                   >= (GET_MODE_PRECISION (GET_MODE (XEXP (op, 0)))
1228                       - num_sign_bit_copies (XEXP (op, 0),
1229                                              GET_MODE (XEXP (op, 0)))))))
1230         return simplify_gen_unary (GET_CODE (op), mode,
1231                                    XEXP (op, 0),
1232                                    GET_MODE (XEXP (op, 0)));
1233
1234       break;
1235
1236     case ABS:
1237       /* (abs (neg <foo>)) -> (abs <foo>) */
1238       if (GET_CODE (op) == NEG)
1239         return simplify_gen_unary (ABS, mode, XEXP (op, 0),
1240                                    GET_MODE (XEXP (op, 0)));
1241
1242       /* If the mode of the operand is VOIDmode (i.e. if it is ASM_OPERANDS),
1243          do nothing.  */
1244       if (GET_MODE (op) == VOIDmode)
1245         break;
1246
1247       /* If operand is something known to be positive, ignore the ABS.  */
1248       if (GET_CODE (op) == FFS || GET_CODE (op) == ABS
1249           || val_signbit_known_clear_p (GET_MODE (op),
1250                                         nonzero_bits (op, GET_MODE (op))))
1251         return op;
1252
1253       /* If operand is known to be only -1 or 0, convert ABS to NEG.  */
1254       if (num_sign_bit_copies (op, mode) == GET_MODE_PRECISION (mode))
1255         return gen_rtx_NEG (mode, op);
1256
1257       break;
1258
1259     case FFS:
1260       /* (ffs (*_extend <X>)) = (ffs <X>) */
1261       if (GET_CODE (op) == SIGN_EXTEND
1262           || GET_CODE (op) == ZERO_EXTEND)
1263         return simplify_gen_unary (FFS, mode, XEXP (op, 0),
1264                                    GET_MODE (XEXP (op, 0)));
1265       break;
1266
1267     case POPCOUNT:
1268       switch (GET_CODE (op))
1269         {
1270         case BSWAP:
1271         case ZERO_EXTEND:
1272           /* (popcount (zero_extend <X>)) = (popcount <X>) */
1273           return simplify_gen_unary (POPCOUNT, mode, XEXP (op, 0),
1274                                      GET_MODE (XEXP (op, 0)));
1275
1276         case ROTATE:
1277         case ROTATERT:
1278           /* Rotations don't affect popcount.  */
1279           if (!side_effects_p (XEXP (op, 1)))
1280             return simplify_gen_unary (POPCOUNT, mode, XEXP (op, 0),
1281                                        GET_MODE (XEXP (op, 0)));
1282           break;
1283
1284         default:
1285           break;
1286         }
1287       break;
1288
1289     case PARITY:
1290       switch (GET_CODE (op))
1291         {
1292         case NOT:
1293         case BSWAP:
1294         case ZERO_EXTEND:
1295         case SIGN_EXTEND:
1296           return simplify_gen_unary (PARITY, mode, XEXP (op, 0),
1297                                      GET_MODE (XEXP (op, 0)));
1298
1299         case ROTATE:
1300         case ROTATERT:
1301           /* Rotations don't affect parity.  */
1302           if (!side_effects_p (XEXP (op, 1)))
1303             return simplify_gen_unary (PARITY, mode, XEXP (op, 0),
1304                                        GET_MODE (XEXP (op, 0)));
1305           break;
1306
1307         default:
1308           break;
1309         }
1310       break;
1311
1312     case BSWAP:
1313       /* (bswap (bswap x)) -> x.  */
1314       if (GET_CODE (op) == BSWAP)
1315         return XEXP (op, 0);
1316       break;
1317
1318     case FLOAT:
1319       /* (float (sign_extend <X>)) = (float <X>).  */
1320       if (GET_CODE (op) == SIGN_EXTEND)
1321         return simplify_gen_unary (FLOAT, mode, XEXP (op, 0),
1322                                    GET_MODE (XEXP (op, 0)));
1323       break;
1324
1325     case SIGN_EXTEND:
1326       /* (sign_extend (truncate (minus (label_ref L1) (label_ref L2))))
1327          becomes just the MINUS if its mode is MODE.  This allows
1328          folding switch statements on machines using casesi (such as
1329          the VAX).  */
1330       if (GET_CODE (op) == TRUNCATE
1331           && GET_MODE (XEXP (op, 0)) == mode
1332           && GET_CODE (XEXP (op, 0)) == MINUS
1333           && GET_CODE (XEXP (XEXP (op, 0), 0)) == LABEL_REF
1334           && GET_CODE (XEXP (XEXP (op, 0), 1)) == LABEL_REF)
1335         return XEXP (op, 0);
1336
1337       /* Extending a widening multiplication should be canonicalized to
1338          a wider widening multiplication.  */
1339       if (GET_CODE (op) == MULT)
1340         {
1341           rtx lhs = XEXP (op, 0);
1342           rtx rhs = XEXP (op, 1);
1343           enum rtx_code lcode = GET_CODE (lhs);
1344           enum rtx_code rcode = GET_CODE (rhs);
1345
1346           /* Widening multiplies usually extend both operands, but sometimes
1347              they use a shift to extract a portion of a register.  */
1348           if ((lcode == SIGN_EXTEND
1349                || (lcode == ASHIFTRT && CONST_INT_P (XEXP (lhs, 1))))
1350               && (rcode == SIGN_EXTEND
1351                   || (rcode == ASHIFTRT && CONST_INT_P (XEXP (rhs, 1)))))
1352             {
1353               machine_mode lmode = GET_MODE (lhs);
1354               machine_mode rmode = GET_MODE (rhs);
1355               int bits;
1356
1357               if (lcode == ASHIFTRT)
1358                 /* Number of bits not shifted off the end.  */
1359                 bits = GET_MODE_PRECISION (lmode) - INTVAL (XEXP (lhs, 1));
1360               else /* lcode == SIGN_EXTEND */
1361                 /* Size of inner mode.  */
1362                 bits = GET_MODE_PRECISION (GET_MODE (XEXP (lhs, 0)));
1363
1364               if (rcode == ASHIFTRT)
1365                 bits += GET_MODE_PRECISION (rmode) - INTVAL (XEXP (rhs, 1));
1366               else /* rcode == SIGN_EXTEND */
1367                 bits += GET_MODE_PRECISION (GET_MODE (XEXP (rhs, 0)));
1368
1369               /* We can only widen multiplies if the result is mathematiclly
1370                  equivalent.  I.e. if overflow was impossible.  */
1371               if (bits <= GET_MODE_PRECISION (GET_MODE (op)))
1372                 return simplify_gen_binary
1373                          (MULT, mode,
1374                           simplify_gen_unary (SIGN_EXTEND, mode, lhs, lmode),
1375                           simplify_gen_unary (SIGN_EXTEND, mode, rhs, rmode));
1376             }
1377         }
1378
1379       /* Check for a sign extension of a subreg of a promoted
1380          variable, where the promotion is sign-extended, and the
1381          target mode is the same as the variable's promotion.  */
1382       if (GET_CODE (op) == SUBREG
1383           && SUBREG_PROMOTED_VAR_P (op)
1384           && SUBREG_PROMOTED_SIGNED_P (op)
1385           && GET_MODE_SIZE (mode) <= GET_MODE_SIZE (GET_MODE (XEXP (op, 0))))
1386         {
1387           temp = rtl_hooks.gen_lowpart_no_emit (mode, op);
1388           if (temp)
1389             return temp;
1390         }
1391
1392       /* (sign_extend:M (sign_extend:N <X>)) is (sign_extend:M <X>).
1393          (sign_extend:M (zero_extend:N <X>)) is (zero_extend:M <X>).  */
1394       if (GET_CODE (op) == SIGN_EXTEND || GET_CODE (op) == ZERO_EXTEND)
1395         {
1396           gcc_assert (GET_MODE_PRECISION (mode)
1397                       > GET_MODE_PRECISION (GET_MODE (op)));
1398           return simplify_gen_unary (GET_CODE (op), mode, XEXP (op, 0),
1399                                      GET_MODE (XEXP (op, 0)));
1400         }
1401
1402       /* (sign_extend:M (ashiftrt:N (ashift <X> (const_int I)) (const_int I)))
1403          is (sign_extend:M (subreg:O <X>)) if there is mode with
1404          GET_MODE_BITSIZE (N) - I bits.
1405          (sign_extend:M (lshiftrt:N (ashift <X> (const_int I)) (const_int I)))
1406          is similarly (zero_extend:M (subreg:O <X>)).  */
1407       if ((GET_CODE (op) == ASHIFTRT || GET_CODE (op) == LSHIFTRT)
1408           && GET_CODE (XEXP (op, 0)) == ASHIFT
1409           && CONST_INT_P (XEXP (op, 1))
1410           && XEXP (XEXP (op, 0), 1) == XEXP (op, 1)
1411           && GET_MODE_BITSIZE (GET_MODE (op)) > INTVAL (XEXP (op, 1)))
1412         {
1413           machine_mode tmode
1414             = mode_for_size (GET_MODE_BITSIZE (GET_MODE (op))
1415                              - INTVAL (XEXP (op, 1)), MODE_INT, 1);
1416           gcc_assert (GET_MODE_BITSIZE (mode)
1417                       > GET_MODE_BITSIZE (GET_MODE (op)));
1418           if (tmode != BLKmode)
1419             {
1420               rtx inner =
1421                 rtl_hooks.gen_lowpart_no_emit (tmode, XEXP (XEXP (op, 0), 0));
1422               if (inner)
1423                 return simplify_gen_unary (GET_CODE (op) == ASHIFTRT
1424                                            ? SIGN_EXTEND : ZERO_EXTEND,
1425                                            mode, inner, tmode);
1426             }
1427         }
1428
1429 #if defined(POINTERS_EXTEND_UNSIGNED) && !defined(HAVE_ptr_extend)
1430       /* As we do not know which address space the pointer is referring to,
1431          we can do this only if the target does not support different pointer
1432          or address modes depending on the address space.  */
1433       if (target_default_pointer_address_modes_p ()
1434           && ! POINTERS_EXTEND_UNSIGNED
1435           && mode == Pmode && GET_MODE (op) == ptr_mode
1436           && (CONSTANT_P (op)
1437               || (GET_CODE (op) == SUBREG
1438                   && REG_P (SUBREG_REG (op))
1439                   && REG_POINTER (SUBREG_REG (op))
1440                   && GET_MODE (SUBREG_REG (op)) == Pmode)))
1441         return convert_memory_address (Pmode, op);
1442 #endif
1443       break;
1444
1445     case ZERO_EXTEND:
1446       /* Check for a zero extension of a subreg of a promoted
1447          variable, where the promotion is zero-extended, and the
1448          target mode is the same as the variable's promotion.  */
1449       if (GET_CODE (op) == SUBREG
1450           && SUBREG_PROMOTED_VAR_P (op)
1451           && SUBREG_PROMOTED_UNSIGNED_P (op)
1452           && GET_MODE_SIZE (mode) <= GET_MODE_SIZE (GET_MODE (XEXP (op, 0))))
1453         {
1454           temp = rtl_hooks.gen_lowpart_no_emit (mode, op);
1455           if (temp)
1456             return temp;
1457         }
1458
1459       /* Extending a widening multiplication should be canonicalized to
1460          a wider widening multiplication.  */
1461       if (GET_CODE (op) == MULT)
1462         {
1463           rtx lhs = XEXP (op, 0);
1464           rtx rhs = XEXP (op, 1);
1465           enum rtx_code lcode = GET_CODE (lhs);
1466           enum rtx_code rcode = GET_CODE (rhs);
1467
1468           /* Widening multiplies usually extend both operands, but sometimes
1469              they use a shift to extract a portion of a register.  */
1470           if ((lcode == ZERO_EXTEND
1471                || (lcode == LSHIFTRT && CONST_INT_P (XEXP (lhs, 1))))
1472               && (rcode == ZERO_EXTEND
1473                   || (rcode == LSHIFTRT && CONST_INT_P (XEXP (rhs, 1)))))
1474             {
1475               machine_mode lmode = GET_MODE (lhs);
1476               machine_mode rmode = GET_MODE (rhs);
1477               int bits;
1478
1479               if (lcode == LSHIFTRT)
1480                 /* Number of bits not shifted off the end.  */
1481                 bits = GET_MODE_PRECISION (lmode) - INTVAL (XEXP (lhs, 1));
1482               else /* lcode == ZERO_EXTEND */
1483                 /* Size of inner mode.  */
1484                 bits = GET_MODE_PRECISION (GET_MODE (XEXP (lhs, 0)));
1485
1486               if (rcode == LSHIFTRT)
1487                 bits += GET_MODE_PRECISION (rmode) - INTVAL (XEXP (rhs, 1));
1488               else /* rcode == ZERO_EXTEND */
1489                 bits += GET_MODE_PRECISION (GET_MODE (XEXP (rhs, 0)));
1490
1491               /* We can only widen multiplies if the result is mathematiclly
1492                  equivalent.  I.e. if overflow was impossible.  */
1493               if (bits <= GET_MODE_PRECISION (GET_MODE (op)))
1494                 return simplify_gen_binary
1495                          (MULT, mode,
1496                           simplify_gen_unary (ZERO_EXTEND, mode, lhs, lmode),
1497                           simplify_gen_unary (ZERO_EXTEND, mode, rhs, rmode));
1498             }
1499         }
1500
1501       /* (zero_extend:M (zero_extend:N <X>)) is (zero_extend:M <X>).  */
1502       if (GET_CODE (op) == ZERO_EXTEND)
1503         return simplify_gen_unary (ZERO_EXTEND, mode, XEXP (op, 0),
1504                                    GET_MODE (XEXP (op, 0)));
1505
1506       /* (zero_extend:M (lshiftrt:N (ashift <X> (const_int I)) (const_int I)))
1507          is (zero_extend:M (subreg:O <X>)) if there is mode with
1508          GET_MODE_PRECISION (N) - I bits.  */
1509       if (GET_CODE (op) == LSHIFTRT
1510           && GET_CODE (XEXP (op, 0)) == ASHIFT
1511           && CONST_INT_P (XEXP (op, 1))
1512           && XEXP (XEXP (op, 0), 1) == XEXP (op, 1)
1513           && GET_MODE_PRECISION (GET_MODE (op)) > INTVAL (XEXP (op, 1)))
1514         {
1515           machine_mode tmode
1516             = mode_for_size (GET_MODE_PRECISION (GET_MODE (op))
1517                              - INTVAL (XEXP (op, 1)), MODE_INT, 1);
1518           if (tmode != BLKmode)
1519             {
1520               rtx inner =
1521                 rtl_hooks.gen_lowpart_no_emit (tmode, XEXP (XEXP (op, 0), 0));
1522               if (inner)
1523                 return simplify_gen_unary (ZERO_EXTEND, mode, inner, tmode);
1524             }
1525         }
1526
1527       /* (zero_extend:M (subreg:N <X:O>)) is <X:O> (for M == O) or
1528          (zero_extend:M <X:O>), if X doesn't have any non-zero bits outside
1529          of mode N.  E.g.
1530          (zero_extend:SI (subreg:QI (and:SI (reg:SI) (const_int 63)) 0)) is
1531          (and:SI (reg:SI) (const_int 63)).  */
1532       if (GET_CODE (op) == SUBREG
1533           && GET_MODE_PRECISION (GET_MODE (op))
1534              < GET_MODE_PRECISION (GET_MODE (SUBREG_REG (op)))
1535           && GET_MODE_PRECISION (GET_MODE (SUBREG_REG (op)))
1536              <= HOST_BITS_PER_WIDE_INT
1537           && GET_MODE_PRECISION (mode)
1538              >= GET_MODE_PRECISION (GET_MODE (SUBREG_REG (op)))
1539           && subreg_lowpart_p (op)
1540           && (nonzero_bits (SUBREG_REG (op), GET_MODE (SUBREG_REG (op)))
1541               & ~GET_MODE_MASK (GET_MODE (op))) == 0)
1542         {
1543           if (GET_MODE_PRECISION (mode)
1544               == GET_MODE_PRECISION (GET_MODE (SUBREG_REG (op))))
1545             return SUBREG_REG (op);
1546           return simplify_gen_unary (ZERO_EXTEND, mode, SUBREG_REG (op),
1547                                      GET_MODE (SUBREG_REG (op)));
1548         }
1549
1550 #if defined(POINTERS_EXTEND_UNSIGNED) && !defined(HAVE_ptr_extend)
1551       /* As we do not know which address space the pointer is referring to,
1552          we can do this only if the target does not support different pointer
1553          or address modes depending on the address space.  */
1554       if (target_default_pointer_address_modes_p ()
1555           && POINTERS_EXTEND_UNSIGNED > 0
1556           && mode == Pmode && GET_MODE (op) == ptr_mode
1557           && (CONSTANT_P (op)
1558               || (GET_CODE (op) == SUBREG
1559                   && REG_P (SUBREG_REG (op))
1560                   && REG_POINTER (SUBREG_REG (op))
1561                   && GET_MODE (SUBREG_REG (op)) == Pmode)))
1562         return convert_memory_address (Pmode, op);
1563 #endif
1564       break;
1565
1566     default:
1567       break;
1568     }
1569
1570   return 0;
1571 }
1572
1573 /* Try to compute the value of a unary operation CODE whose output mode is to
1574    be MODE with input operand OP whose mode was originally OP_MODE.
1575    Return zero if the value cannot be computed.  */
1576 rtx
1577 simplify_const_unary_operation (enum rtx_code code, machine_mode mode,
1578                                 rtx op, machine_mode op_mode)
1579 {
1580   unsigned int width = GET_MODE_PRECISION (mode);
1581
1582   if (code == VEC_DUPLICATE)
1583     {
1584       gcc_assert (VECTOR_MODE_P (mode));
1585       if (GET_MODE (op) != VOIDmode)
1586       {
1587         if (!VECTOR_MODE_P (GET_MODE (op)))
1588           gcc_assert (GET_MODE_INNER (mode) == GET_MODE (op));
1589         else
1590           gcc_assert (GET_MODE_INNER (mode) == GET_MODE_INNER
1591                                                 (GET_MODE (op)));
1592       }
1593       if (CONST_SCALAR_INT_P (op) || CONST_DOUBLE_AS_FLOAT_P (op)
1594           || GET_CODE (op) == CONST_VECTOR)
1595         {
1596           int elt_size = GET_MODE_SIZE (GET_MODE_INNER (mode));
1597           unsigned n_elts = (GET_MODE_SIZE (mode) / elt_size);
1598           rtvec v = rtvec_alloc (n_elts);
1599           unsigned int i;
1600
1601           if (GET_CODE (op) != CONST_VECTOR)
1602             for (i = 0; i < n_elts; i++)
1603               RTVEC_ELT (v, i) = op;
1604           else
1605             {
1606               machine_mode inmode = GET_MODE (op);
1607               int in_elt_size = GET_MODE_SIZE (GET_MODE_INNER (inmode));
1608               unsigned in_n_elts = (GET_MODE_SIZE (inmode) / in_elt_size);
1609
1610               gcc_assert (in_n_elts < n_elts);
1611               gcc_assert ((n_elts % in_n_elts) == 0);
1612               for (i = 0; i < n_elts; i++)
1613                 RTVEC_ELT (v, i) = CONST_VECTOR_ELT (op, i % in_n_elts);
1614             }
1615           return gen_rtx_CONST_VECTOR (mode, v);
1616         }
1617     }
1618
1619   if (VECTOR_MODE_P (mode) && GET_CODE (op) == CONST_VECTOR)
1620     {
1621       int elt_size = GET_MODE_SIZE (GET_MODE_INNER (mode));
1622       unsigned n_elts = (GET_MODE_SIZE (mode) / elt_size);
1623       machine_mode opmode = GET_MODE (op);
1624       int op_elt_size = GET_MODE_SIZE (GET_MODE_INNER (opmode));
1625       unsigned op_n_elts = (GET_MODE_SIZE (opmode) / op_elt_size);
1626       rtvec v = rtvec_alloc (n_elts);
1627       unsigned int i;
1628
1629       gcc_assert (op_n_elts == n_elts);
1630       for (i = 0; i < n_elts; i++)
1631         {
1632           rtx x = simplify_unary_operation (code, GET_MODE_INNER (mode),
1633                                             CONST_VECTOR_ELT (op, i),
1634                                             GET_MODE_INNER (opmode));
1635           if (!x)
1636             return 0;
1637           RTVEC_ELT (v, i) = x;
1638         }
1639       return gen_rtx_CONST_VECTOR (mode, v);
1640     }
1641
1642   /* The order of these tests is critical so that, for example, we don't
1643      check the wrong mode (input vs. output) for a conversion operation,
1644      such as FIX.  At some point, this should be simplified.  */
1645
1646   if (code == FLOAT && CONST_SCALAR_INT_P (op))
1647     {
1648       REAL_VALUE_TYPE d;
1649
1650       if (op_mode == VOIDmode)
1651         {
1652           /* CONST_INT have VOIDmode as the mode.  We assume that all
1653              the bits of the constant are significant, though, this is
1654              a dangerous assumption as many times CONST_INTs are
1655              created and used with garbage in the bits outside of the
1656              precision of the implied mode of the const_int.  */
1657           op_mode = MAX_MODE_INT;
1658         }
1659
1660       real_from_integer (&d, mode, std::make_pair (op, op_mode), SIGNED);
1661       d = real_value_truncate (mode, d);
1662       return CONST_DOUBLE_FROM_REAL_VALUE (d, mode);
1663     }
1664   else if (code == UNSIGNED_FLOAT && CONST_SCALAR_INT_P (op))
1665     {
1666       REAL_VALUE_TYPE d;
1667
1668       if (op_mode == VOIDmode)
1669         {
1670           /* CONST_INT have VOIDmode as the mode.  We assume that all
1671              the bits of the constant are significant, though, this is
1672              a dangerous assumption as many times CONST_INTs are
1673              created and used with garbage in the bits outside of the
1674              precision of the implied mode of the const_int.  */
1675           op_mode = MAX_MODE_INT;
1676         }
1677
1678       real_from_integer (&d, mode, std::make_pair (op, op_mode), UNSIGNED);
1679       d = real_value_truncate (mode, d);
1680       return CONST_DOUBLE_FROM_REAL_VALUE (d, mode);
1681     }
1682
1683   if (CONST_SCALAR_INT_P (op) && width > 0)
1684     {
1685       wide_int result;
1686       machine_mode imode = op_mode == VOIDmode ? mode : op_mode;
1687       rtx_mode_t op0 = std::make_pair (op, imode);
1688       int int_value;
1689
1690 #if TARGET_SUPPORTS_WIDE_INT == 0
1691       /* This assert keeps the simplification from producing a result
1692          that cannot be represented in a CONST_DOUBLE but a lot of
1693          upstream callers expect that this function never fails to
1694          simplify something and so you if you added this to the test
1695          above the code would die later anyway.  If this assert
1696          happens, you just need to make the port support wide int.  */
1697       gcc_assert (width <= HOST_BITS_PER_DOUBLE_INT);
1698 #endif
1699
1700       switch (code)
1701         {
1702         case NOT:
1703           result = wi::bit_not (op0);
1704           break;
1705
1706         case NEG:
1707           result = wi::neg (op0);
1708           break;
1709
1710         case ABS:
1711           result = wi::abs (op0);
1712           break;
1713
1714         case FFS:
1715           result = wi::shwi (wi::ffs (op0), mode);
1716           break;
1717
1718         case CLZ:
1719           if (wi::ne_p (op0, 0))
1720             int_value = wi::clz (op0);
1721           else if (! CLZ_DEFINED_VALUE_AT_ZERO (mode, int_value))
1722             int_value = GET_MODE_PRECISION (mode);
1723           result = wi::shwi (int_value, mode);
1724           break;
1725
1726         case CLRSB:
1727           result = wi::shwi (wi::clrsb (op0), mode);
1728           break;
1729
1730         case CTZ:
1731           if (wi::ne_p (op0, 0))
1732             int_value = wi::ctz (op0);
1733           else if (! CTZ_DEFINED_VALUE_AT_ZERO (mode, int_value))
1734             int_value = GET_MODE_PRECISION (mode);
1735           result = wi::shwi (int_value, mode);
1736           break;
1737
1738         case POPCOUNT:
1739           result = wi::shwi (wi::popcount (op0), mode);
1740           break;
1741
1742         case PARITY:
1743           result = wi::shwi (wi::parity (op0), mode);
1744           break;
1745
1746         case BSWAP:
1747           result = wide_int (op0).bswap ();
1748           break;
1749
1750         case TRUNCATE:
1751         case ZERO_EXTEND:
1752           result = wide_int::from (op0, width, UNSIGNED);
1753           break;
1754
1755         case SIGN_EXTEND:
1756           result = wide_int::from (op0, width, SIGNED);
1757           break;
1758
1759         case SQRT:
1760         default:
1761           return 0;
1762         }
1763
1764       return immed_wide_int_const (result, mode);
1765     }
1766
1767   else if (CONST_DOUBLE_AS_FLOAT_P (op) 
1768            && SCALAR_FLOAT_MODE_P (mode)
1769            && SCALAR_FLOAT_MODE_P (GET_MODE (op)))
1770     {
1771       REAL_VALUE_TYPE d;
1772       REAL_VALUE_FROM_CONST_DOUBLE (d, op);
1773
1774       switch (code)
1775         {
1776         case SQRT:
1777           return 0;
1778         case ABS:
1779           d = real_value_abs (&d);
1780           break;
1781         case NEG:
1782           d = real_value_negate (&d);
1783           break;
1784         case FLOAT_TRUNCATE:
1785           d = real_value_truncate (mode, d);
1786           break;
1787         case FLOAT_EXTEND:
1788           /* All this does is change the mode, unless changing
1789              mode class.  */
1790           if (GET_MODE_CLASS (mode) != GET_MODE_CLASS (GET_MODE (op)))
1791             real_convert (&d, mode, &d);
1792           break;
1793         case FIX:
1794           real_arithmetic (&d, FIX_TRUNC_EXPR, &d, NULL);
1795           break;
1796         case NOT:
1797           {
1798             long tmp[4];
1799             int i;
1800
1801             real_to_target (tmp, &d, GET_MODE (op));
1802             for (i = 0; i < 4; i++)
1803               tmp[i] = ~tmp[i];
1804             real_from_target (&d, tmp, mode);
1805             break;
1806           }
1807         default:
1808           gcc_unreachable ();
1809         }
1810       return CONST_DOUBLE_FROM_REAL_VALUE (d, mode);
1811     }
1812   else if (CONST_DOUBLE_AS_FLOAT_P (op)
1813            && SCALAR_FLOAT_MODE_P (GET_MODE (op))
1814            && GET_MODE_CLASS (mode) == MODE_INT
1815            && width > 0)
1816     {
1817       /* Although the overflow semantics of RTL's FIX and UNSIGNED_FIX
1818          operators are intentionally left unspecified (to ease implementation
1819          by target backends), for consistency, this routine implements the
1820          same semantics for constant folding as used by the middle-end.  */
1821
1822       /* This was formerly used only for non-IEEE float.
1823          eggert@twinsun.com says it is safe for IEEE also.  */
1824       REAL_VALUE_TYPE x, t;
1825       REAL_VALUE_FROM_CONST_DOUBLE (x, op);
1826       wide_int wmax, wmin;
1827       /* This is part of the abi to real_to_integer, but we check
1828          things before making this call.  */
1829       bool fail;
1830
1831       switch (code)
1832         {
1833         case FIX:
1834           if (REAL_VALUE_ISNAN (x))
1835             return const0_rtx;
1836
1837           /* Test against the signed upper bound.  */
1838           wmax = wi::max_value (width, SIGNED);
1839           real_from_integer (&t, VOIDmode, wmax, SIGNED);
1840           if (REAL_VALUES_LESS (t, x))
1841             return immed_wide_int_const (wmax, mode);
1842
1843           /* Test against the signed lower bound.  */
1844           wmin = wi::min_value (width, SIGNED);
1845           real_from_integer (&t, VOIDmode, wmin, SIGNED);
1846           if (REAL_VALUES_LESS (x, t))
1847             return immed_wide_int_const (wmin, mode);
1848
1849           return immed_wide_int_const (real_to_integer (&x, &fail, width), mode);
1850           break;
1851
1852         case UNSIGNED_FIX:
1853           if (REAL_VALUE_ISNAN (x) || REAL_VALUE_NEGATIVE (x))
1854             return const0_rtx;
1855
1856           /* Test against the unsigned upper bound.  */
1857           wmax = wi::max_value (width, UNSIGNED);
1858           real_from_integer (&t, VOIDmode, wmax, UNSIGNED);
1859           if (REAL_VALUES_LESS (t, x))
1860             return immed_wide_int_const (wmax, mode);
1861
1862           return immed_wide_int_const (real_to_integer (&x, &fail, width),
1863                                        mode);
1864           break;
1865
1866         default:
1867           gcc_unreachable ();
1868         }
1869     }
1870
1871   return NULL_RTX;
1872 }
1873 \f
1874 /* Subroutine of simplify_binary_operation to simplify a binary operation
1875    CODE that can commute with byte swapping, with result mode MODE and
1876    operating on OP0 and OP1.  CODE is currently one of AND, IOR or XOR.
1877    Return zero if no simplification or canonicalization is possible.  */
1878
1879 static rtx
1880 simplify_byte_swapping_operation (enum rtx_code code, machine_mode mode,
1881                                   rtx op0, rtx op1)
1882 {
1883   rtx tem;
1884
1885   /* (op (bswap x) C1)) -> (bswap (op x C2)) with C2 swapped.  */
1886   if (GET_CODE (op0) == BSWAP && CONST_SCALAR_INT_P (op1))
1887     {
1888       tem = simplify_gen_binary (code, mode, XEXP (op0, 0),
1889                                  simplify_gen_unary (BSWAP, mode, op1, mode));
1890       return simplify_gen_unary (BSWAP, mode, tem, mode);
1891     }
1892
1893   /* (op (bswap x) (bswap y)) -> (bswap (op x y)).  */
1894   if (GET_CODE (op0) == BSWAP && GET_CODE (op1) == BSWAP)
1895     {
1896       tem = simplify_gen_binary (code, mode, XEXP (op0, 0), XEXP (op1, 0));
1897       return simplify_gen_unary (BSWAP, mode, tem, mode);
1898     }
1899
1900   return NULL_RTX;
1901 }
1902
1903 /* Subroutine of simplify_binary_operation to simplify a commutative,
1904    associative binary operation CODE with result mode MODE, operating
1905    on OP0 and OP1.  CODE is currently one of PLUS, MULT, AND, IOR, XOR,
1906    SMIN, SMAX, UMIN or UMAX.  Return zero if no simplification or
1907    canonicalization is possible.  */
1908
1909 static rtx
1910 simplify_associative_operation (enum rtx_code code, machine_mode mode,
1911                                 rtx op0, rtx op1)
1912 {
1913   rtx tem;
1914
1915   /* Linearize the operator to the left.  */
1916   if (GET_CODE (op1) == code)
1917     {
1918       /* "(a op b) op (c op d)" becomes "((a op b) op c) op d)".  */
1919       if (GET_CODE (op0) == code)
1920         {
1921           tem = simplify_gen_binary (code, mode, op0, XEXP (op1, 0));
1922           return simplify_gen_binary (code, mode, tem, XEXP (op1, 1));
1923         }
1924
1925       /* "a op (b op c)" becomes "(b op c) op a".  */
1926       if (! swap_commutative_operands_p (op1, op0))
1927         return simplify_gen_binary (code, mode, op1, op0);
1928
1929       tem = op0;
1930       op0 = op1;
1931       op1 = tem;
1932     }
1933
1934   if (GET_CODE (op0) == code)
1935     {
1936       /* Canonicalize "(x op c) op y" as "(x op y) op c".  */
1937       if (swap_commutative_operands_p (XEXP (op0, 1), op1))
1938         {
1939           tem = simplify_gen_binary (code, mode, XEXP (op0, 0), op1);
1940           return simplify_gen_binary (code, mode, tem, XEXP (op0, 1));
1941         }
1942
1943       /* Attempt to simplify "(a op b) op c" as "a op (b op c)".  */
1944       tem = simplify_binary_operation (code, mode, XEXP (op0, 1), op1);
1945       if (tem != 0)
1946         return simplify_gen_binary (code, mode, XEXP (op0, 0), tem);
1947
1948       /* Attempt to simplify "(a op b) op c" as "(a op c) op b".  */
1949       tem = simplify_binary_operation (code, mode, XEXP (op0, 0), op1);
1950       if (tem != 0)
1951         return simplify_gen_binary (code, mode, tem, XEXP (op0, 1));
1952     }
1953
1954   return 0;
1955 }
1956
1957
1958 /* Simplify a binary operation CODE with result mode MODE, operating on OP0
1959    and OP1.  Return 0 if no simplification is possible.
1960
1961    Don't use this for relational operations such as EQ or LT.
1962    Use simplify_relational_operation instead.  */
1963 rtx
1964 simplify_binary_operation (enum rtx_code code, machine_mode mode,
1965                            rtx op0, rtx op1)
1966 {
1967   rtx trueop0, trueop1;
1968   rtx tem;
1969
1970   /* Relational operations don't work here.  We must know the mode
1971      of the operands in order to do the comparison correctly.
1972      Assuming a full word can give incorrect results.
1973      Consider comparing 128 with -128 in QImode.  */
1974   gcc_assert (GET_RTX_CLASS (code) != RTX_COMPARE);
1975   gcc_assert (GET_RTX_CLASS (code) != RTX_COMM_COMPARE);
1976
1977   /* Make sure the constant is second.  */
1978   if (GET_RTX_CLASS (code) == RTX_COMM_ARITH
1979       && swap_commutative_operands_p (op0, op1))
1980     {
1981       tem = op0, op0 = op1, op1 = tem;
1982     }
1983
1984   trueop0 = avoid_constant_pool_reference (op0);
1985   trueop1 = avoid_constant_pool_reference (op1);
1986
1987   tem = simplify_const_binary_operation (code, mode, trueop0, trueop1);
1988   if (tem)
1989     return tem;
1990   return simplify_binary_operation_1 (code, mode, op0, op1, trueop0, trueop1);
1991 }
1992
1993 /* Subroutine of simplify_binary_operation.  Simplify a binary operation
1994    CODE with result mode MODE, operating on OP0 and OP1.  If OP0 and/or
1995    OP1 are constant pool references, TRUEOP0 and TRUEOP1 represent the
1996    actual constants.  */
1997
1998 static rtx
1999 simplify_binary_operation_1 (enum rtx_code code, machine_mode mode,
2000                              rtx op0, rtx op1, rtx trueop0, rtx trueop1)
2001 {
2002   rtx tem, reversed, opleft, opright;
2003   HOST_WIDE_INT val;
2004   unsigned int width = GET_MODE_PRECISION (mode);
2005
2006   /* Even if we can't compute a constant result,
2007      there are some cases worth simplifying.  */
2008
2009   switch (code)
2010     {
2011     case PLUS:
2012       /* Maybe simplify x + 0 to x.  The two expressions are equivalent
2013          when x is NaN, infinite, or finite and nonzero.  They aren't
2014          when x is -0 and the rounding mode is not towards -infinity,
2015          since (-0) + 0 is then 0.  */
2016       if (!HONOR_SIGNED_ZEROS (mode) && trueop1 == CONST0_RTX (mode))
2017         return op0;
2018
2019       /* ((-a) + b) -> (b - a) and similarly for (a + (-b)).  These
2020          transformations are safe even for IEEE.  */
2021       if (GET_CODE (op0) == NEG)
2022         return simplify_gen_binary (MINUS, mode, op1, XEXP (op0, 0));
2023       else if (GET_CODE (op1) == NEG)
2024         return simplify_gen_binary (MINUS, mode, op0, XEXP (op1, 0));
2025
2026       /* (~a) + 1 -> -a */
2027       if (INTEGRAL_MODE_P (mode)
2028           && GET_CODE (op0) == NOT
2029           && trueop1 == const1_rtx)
2030         return simplify_gen_unary (NEG, mode, XEXP (op0, 0), mode);
2031
2032       /* Handle both-operands-constant cases.  We can only add
2033          CONST_INTs to constants since the sum of relocatable symbols
2034          can't be handled by most assemblers.  Don't add CONST_INT
2035          to CONST_INT since overflow won't be computed properly if wider
2036          than HOST_BITS_PER_WIDE_INT.  */
2037
2038       if ((GET_CODE (op0) == CONST
2039            || GET_CODE (op0) == SYMBOL_REF
2040            || GET_CODE (op0) == LABEL_REF)
2041           && CONST_INT_P (op1))
2042         return plus_constant (mode, op0, INTVAL (op1));
2043       else if ((GET_CODE (op1) == CONST
2044                 || GET_CODE (op1) == SYMBOL_REF
2045                 || GET_CODE (op1) == LABEL_REF)
2046                && CONST_INT_P (op0))
2047         return plus_constant (mode, op1, INTVAL (op0));
2048
2049       /* See if this is something like X * C - X or vice versa or
2050          if the multiplication is written as a shift.  If so, we can
2051          distribute and make a new multiply, shift, or maybe just
2052          have X (if C is 2 in the example above).  But don't make
2053          something more expensive than we had before.  */
2054
2055       if (SCALAR_INT_MODE_P (mode))
2056         {
2057           rtx lhs = op0, rhs = op1;
2058
2059           wide_int coeff0 = wi::one (GET_MODE_PRECISION (mode));
2060           wide_int coeff1 = wi::one (GET_MODE_PRECISION (mode));
2061
2062           if (GET_CODE (lhs) == NEG)
2063             {
2064               coeff0 = wi::minus_one (GET_MODE_PRECISION (mode));
2065               lhs = XEXP (lhs, 0);
2066             }
2067           else if (GET_CODE (lhs) == MULT
2068                    && CONST_SCALAR_INT_P (XEXP (lhs, 1)))
2069             {
2070               coeff0 = std::make_pair (XEXP (lhs, 1), mode);
2071               lhs = XEXP (lhs, 0);
2072             }
2073           else if (GET_CODE (lhs) == ASHIFT
2074                    && CONST_INT_P (XEXP (lhs, 1))
2075                    && INTVAL (XEXP (lhs, 1)) >= 0
2076                    && INTVAL (XEXP (lhs, 1)) < GET_MODE_PRECISION (mode))
2077             {
2078               coeff0 = wi::set_bit_in_zero (INTVAL (XEXP (lhs, 1)),
2079                                             GET_MODE_PRECISION (mode));
2080               lhs = XEXP (lhs, 0);
2081             }
2082
2083           if (GET_CODE (rhs) == NEG)
2084             {
2085               coeff1 = wi::minus_one (GET_MODE_PRECISION (mode));
2086               rhs = XEXP (rhs, 0);
2087             }
2088           else if (GET_CODE (rhs) == MULT
2089                    && CONST_INT_P (XEXP (rhs, 1)))
2090             {
2091               coeff1 = std::make_pair (XEXP (rhs, 1), mode);
2092               rhs = XEXP (rhs, 0);
2093             }
2094           else if (GET_CODE (rhs) == ASHIFT
2095                    && CONST_INT_P (XEXP (rhs, 1))
2096                    && INTVAL (XEXP (rhs, 1)) >= 0
2097                    && INTVAL (XEXP (rhs, 1)) < GET_MODE_PRECISION (mode))
2098             {
2099               coeff1 = wi::set_bit_in_zero (INTVAL (XEXP (rhs, 1)),
2100                                             GET_MODE_PRECISION (mode));
2101               rhs = XEXP (rhs, 0);
2102             }
2103
2104           if (rtx_equal_p (lhs, rhs))
2105             {
2106               rtx orig = gen_rtx_PLUS (mode, op0, op1);
2107               rtx coeff;
2108               bool speed = optimize_function_for_speed_p (cfun);
2109
2110               coeff = immed_wide_int_const (coeff0 + coeff1, mode);
2111
2112               tem = simplify_gen_binary (MULT, mode, lhs, coeff);
2113               return set_src_cost (tem, speed) <= set_src_cost (orig, speed)
2114                 ? tem : 0;
2115             }
2116         }
2117
2118       /* (plus (xor X C1) C2) is (xor X (C1^C2)) if C2 is signbit.  */
2119       if (CONST_SCALAR_INT_P (op1)
2120           && GET_CODE (op0) == XOR
2121           && CONST_SCALAR_INT_P (XEXP (op0, 1))
2122           && mode_signbit_p (mode, op1))
2123         return simplify_gen_binary (XOR, mode, XEXP (op0, 0),
2124                                     simplify_gen_binary (XOR, mode, op1,
2125                                                          XEXP (op0, 1)));
2126
2127       /* Canonicalize (plus (mult (neg B) C) A) to (minus A (mult B C)).  */
2128       if (!HONOR_SIGN_DEPENDENT_ROUNDING (mode)
2129           && GET_CODE (op0) == MULT
2130           && GET_CODE (XEXP (op0, 0)) == NEG)
2131         {
2132           rtx in1, in2;
2133
2134           in1 = XEXP (XEXP (op0, 0), 0);
2135           in2 = XEXP (op0, 1);
2136           return simplify_gen_binary (MINUS, mode, op1,
2137                                       simplify_gen_binary (MULT, mode,
2138                                                            in1, in2));
2139         }
2140
2141       /* (plus (comparison A B) C) can become (neg (rev-comp A B)) if
2142          C is 1 and STORE_FLAG_VALUE is -1 or if C is -1 and STORE_FLAG_VALUE
2143          is 1.  */
2144       if (COMPARISON_P (op0)
2145           && ((STORE_FLAG_VALUE == -1 && trueop1 == const1_rtx)
2146               || (STORE_FLAG_VALUE == 1 && trueop1 == constm1_rtx))
2147           && (reversed = reversed_comparison (op0, mode)))
2148         return
2149           simplify_gen_unary (NEG, mode, reversed, mode);
2150
2151       /* If one of the operands is a PLUS or a MINUS, see if we can
2152          simplify this by the associative law.
2153          Don't use the associative law for floating point.
2154          The inaccuracy makes it nonassociative,
2155          and subtle programs can break if operations are associated.  */
2156
2157       if (INTEGRAL_MODE_P (mode)
2158           && (plus_minus_operand_p (op0)
2159               || plus_minus_operand_p (op1))
2160           && (tem = simplify_plus_minus (code, mode, op0, op1)) != 0)
2161         return tem;
2162
2163       /* Reassociate floating point addition only when the user
2164          specifies associative math operations.  */
2165       if (FLOAT_MODE_P (mode)
2166           && flag_associative_math)
2167         {
2168           tem = simplify_associative_operation (code, mode, op0, op1);
2169           if (tem)
2170             return tem;
2171         }
2172       break;
2173
2174     case COMPARE:
2175       /* Convert (compare (gt (flags) 0) (lt (flags) 0)) to (flags).  */
2176       if (((GET_CODE (op0) == GT && GET_CODE (op1) == LT)
2177            || (GET_CODE (op0) == GTU && GET_CODE (op1) == LTU))
2178           && XEXP (op0, 1) == const0_rtx && XEXP (op1, 1) == const0_rtx)
2179         {
2180           rtx xop00 = XEXP (op0, 0);
2181           rtx xop10 = XEXP (op1, 0);
2182
2183 #ifdef HAVE_cc0
2184           if (GET_CODE (xop00) == CC0 && GET_CODE (xop10) == CC0)
2185 #else
2186             if (REG_P (xop00) && REG_P (xop10)
2187                 && GET_MODE (xop00) == GET_MODE (xop10)
2188                 && REGNO (xop00) == REGNO (xop10)
2189                 && GET_MODE_CLASS (GET_MODE (xop00)) == MODE_CC
2190                 && GET_MODE_CLASS (GET_MODE (xop10)) == MODE_CC)
2191 #endif
2192               return xop00;
2193         }
2194       break;
2195
2196     case MINUS:
2197       /* We can't assume x-x is 0 even with non-IEEE floating point,
2198          but since it is zero except in very strange circumstances, we
2199          will treat it as zero with -ffinite-math-only.  */
2200       if (rtx_equal_p (trueop0, trueop1)
2201           && ! side_effects_p (op0)
2202           && (!FLOAT_MODE_P (mode) || !HONOR_NANS (mode)))
2203         return CONST0_RTX (mode);
2204
2205       /* Change subtraction from zero into negation.  (0 - x) is the
2206          same as -x when x is NaN, infinite, or finite and nonzero.
2207          But if the mode has signed zeros, and does not round towards
2208          -infinity, then 0 - 0 is 0, not -0.  */
2209       if (!HONOR_SIGNED_ZEROS (mode) && trueop0 == CONST0_RTX (mode))
2210         return simplify_gen_unary (NEG, mode, op1, mode);
2211
2212       /* (-1 - a) is ~a.  */
2213       if (trueop0 == constm1_rtx)
2214         return simplify_gen_unary (NOT, mode, op1, mode);
2215
2216       /* Subtracting 0 has no effect unless the mode has signed zeros
2217          and supports rounding towards -infinity.  In such a case,
2218          0 - 0 is -0.  */
2219       if (!(HONOR_SIGNED_ZEROS (mode)
2220             && HONOR_SIGN_DEPENDENT_ROUNDING (mode))
2221           && trueop1 == CONST0_RTX (mode))
2222         return op0;
2223
2224       /* See if this is something like X * C - X or vice versa or
2225          if the multiplication is written as a shift.  If so, we can
2226          distribute and make a new multiply, shift, or maybe just
2227          have X (if C is 2 in the example above).  But don't make
2228          something more expensive than we had before.  */
2229
2230       if (SCALAR_INT_MODE_P (mode))
2231         {
2232           rtx lhs = op0, rhs = op1;
2233
2234           wide_int coeff0 = wi::one (GET_MODE_PRECISION (mode));
2235           wide_int negcoeff1 = wi::minus_one (GET_MODE_PRECISION (mode));
2236
2237           if (GET_CODE (lhs) == NEG)
2238             {
2239               coeff0 = wi::minus_one (GET_MODE_PRECISION (mode));
2240               lhs = XEXP (lhs, 0);
2241             }
2242           else if (GET_CODE (lhs) == MULT
2243                    && CONST_SCALAR_INT_P (XEXP (lhs, 1)))
2244             {
2245               coeff0 = std::make_pair (XEXP (lhs, 1), mode);
2246               lhs = XEXP (lhs, 0);
2247             }
2248           else if (GET_CODE (lhs) == ASHIFT
2249                    && CONST_INT_P (XEXP (lhs, 1))
2250                    && INTVAL (XEXP (lhs, 1)) >= 0
2251                    && INTVAL (XEXP (lhs, 1)) < GET_MODE_PRECISION (mode))
2252             {
2253               coeff0 = wi::set_bit_in_zero (INTVAL (XEXP (lhs, 1)),
2254                                             GET_MODE_PRECISION (mode));
2255               lhs = XEXP (lhs, 0);
2256             }
2257
2258           if (GET_CODE (rhs) == NEG)
2259             {
2260               negcoeff1 = wi::one (GET_MODE_PRECISION (mode));
2261               rhs = XEXP (rhs, 0);
2262             }
2263           else if (GET_CODE (rhs) == MULT
2264                    && CONST_INT_P (XEXP (rhs, 1)))
2265             {
2266               negcoeff1 = wi::neg (std::make_pair (XEXP (rhs, 1), mode));
2267               rhs = XEXP (rhs, 0);
2268             }
2269           else if (GET_CODE (rhs) == ASHIFT
2270                    && CONST_INT_P (XEXP (rhs, 1))
2271                    && INTVAL (XEXP (rhs, 1)) >= 0
2272                    && INTVAL (XEXP (rhs, 1)) < GET_MODE_PRECISION (mode))
2273             {
2274               negcoeff1 = wi::set_bit_in_zero (INTVAL (XEXP (rhs, 1)),
2275                                                GET_MODE_PRECISION (mode));
2276               negcoeff1 = -negcoeff1;
2277               rhs = XEXP (rhs, 0);
2278             }
2279
2280           if (rtx_equal_p (lhs, rhs))
2281             {
2282               rtx orig = gen_rtx_MINUS (mode, op0, op1);
2283               rtx coeff;
2284               bool speed = optimize_function_for_speed_p (cfun);
2285
2286               coeff = immed_wide_int_const (coeff0 + negcoeff1, mode);
2287
2288               tem = simplify_gen_binary (MULT, mode, lhs, coeff);
2289               return set_src_cost (tem, speed) <= set_src_cost (orig, speed)
2290                 ? tem : 0;
2291             }
2292         }
2293
2294       /* (a - (-b)) -> (a + b).  True even for IEEE.  */
2295       if (GET_CODE (op1) == NEG)
2296         return simplify_gen_binary (PLUS, mode, op0, XEXP (op1, 0));
2297
2298       /* (-x - c) may be simplified as (-c - x).  */
2299       if (GET_CODE (op0) == NEG
2300           && (CONST_SCALAR_INT_P (op1) || CONST_DOUBLE_AS_FLOAT_P (op1)))
2301         {
2302           tem = simplify_unary_operation (NEG, mode, op1, mode);
2303           if (tem)
2304             return simplify_gen_binary (MINUS, mode, tem, XEXP (op0, 0));
2305         }
2306
2307       /* Don't let a relocatable value get a negative coeff.  */
2308       if (CONST_INT_P (op1) && GET_MODE (op0) != VOIDmode)
2309         return simplify_gen_binary (PLUS, mode,
2310                                     op0,
2311                                     neg_const_int (mode, op1));
2312
2313       /* (x - (x & y)) -> (x & ~y) */
2314       if (INTEGRAL_MODE_P (mode) && GET_CODE (op1) == AND)
2315         {
2316           if (rtx_equal_p (op0, XEXP (op1, 0)))
2317             {
2318               tem = simplify_gen_unary (NOT, mode, XEXP (op1, 1),
2319                                         GET_MODE (XEXP (op1, 1)));
2320               return simplify_gen_binary (AND, mode, op0, tem);
2321             }
2322           if (rtx_equal_p (op0, XEXP (op1, 1)))
2323             {
2324               tem = simplify_gen_unary (NOT, mode, XEXP (op1, 0),
2325                                         GET_MODE (XEXP (op1, 0)));
2326               return simplify_gen_binary (AND, mode, op0, tem);
2327             }
2328         }
2329
2330       /* If STORE_FLAG_VALUE is 1, (minus 1 (comparison foo bar)) can be done
2331          by reversing the comparison code if valid.  */
2332       if (STORE_FLAG_VALUE == 1
2333           && trueop0 == const1_rtx
2334           && COMPARISON_P (op1)
2335           && (reversed = reversed_comparison (op1, mode)))
2336         return reversed;
2337
2338       /* Canonicalize (minus A (mult (neg B) C)) to (plus (mult B C) A).  */
2339       if (!HONOR_SIGN_DEPENDENT_ROUNDING (mode)
2340           && GET_CODE (op1) == MULT
2341           && GET_CODE (XEXP (op1, 0)) == NEG)
2342         {
2343           rtx in1, in2;
2344
2345           in1 = XEXP (XEXP (op1, 0), 0);
2346           in2 = XEXP (op1, 1);
2347           return simplify_gen_binary (PLUS, mode,
2348                                       simplify_gen_binary (MULT, mode,
2349                                                            in1, in2),
2350                                       op0);
2351         }
2352
2353       /* Canonicalize (minus (neg A) (mult B C)) to
2354          (minus (mult (neg B) C) A).  */
2355       if (!HONOR_SIGN_DEPENDENT_ROUNDING (mode)
2356           && GET_CODE (op1) == MULT
2357           && GET_CODE (op0) == NEG)
2358         {
2359           rtx in1, in2;
2360
2361           in1 = simplify_gen_unary (NEG, mode, XEXP (op1, 0), mode);
2362           in2 = XEXP (op1, 1);
2363           return simplify_gen_binary (MINUS, mode,
2364                                       simplify_gen_binary (MULT, mode,
2365                                                            in1, in2),
2366                                       XEXP (op0, 0));
2367         }
2368
2369       /* If one of the operands is a PLUS or a MINUS, see if we can
2370          simplify this by the associative law.  This will, for example,
2371          canonicalize (minus A (plus B C)) to (minus (minus A B) C).
2372          Don't use the associative law for floating point.
2373          The inaccuracy makes it nonassociative,
2374          and subtle programs can break if operations are associated.  */
2375
2376       if (INTEGRAL_MODE_P (mode)
2377           && (plus_minus_operand_p (op0)
2378               || plus_minus_operand_p (op1))
2379           && (tem = simplify_plus_minus (code, mode, op0, op1)) != 0)
2380         return tem;
2381       break;
2382
2383     case MULT:
2384       if (trueop1 == constm1_rtx)
2385         return simplify_gen_unary (NEG, mode, op0, mode);
2386
2387       if (GET_CODE (op0) == NEG)
2388         {
2389           rtx temp = simplify_unary_operation (NEG, mode, op1, mode);
2390           /* If op1 is a MULT as well and simplify_unary_operation
2391              just moved the NEG to the second operand, simplify_gen_binary
2392              below could through simplify_associative_operation move
2393              the NEG around again and recurse endlessly.  */
2394           if (temp
2395               && GET_CODE (op1) == MULT
2396               && GET_CODE (temp) == MULT
2397               && XEXP (op1, 0) == XEXP (temp, 0)
2398               && GET_CODE (XEXP (temp, 1)) == NEG
2399               && XEXP (op1, 1) == XEXP (XEXP (temp, 1), 0))
2400             temp = NULL_RTX;
2401           if (temp)
2402             return simplify_gen_binary (MULT, mode, XEXP (op0, 0), temp);
2403         }
2404       if (GET_CODE (op1) == NEG)
2405         {
2406           rtx temp = simplify_unary_operation (NEG, mode, op0, mode);
2407           /* If op0 is a MULT as well and simplify_unary_operation
2408              just moved the NEG to the second operand, simplify_gen_binary
2409              below could through simplify_associative_operation move
2410              the NEG around again and recurse endlessly.  */
2411           if (temp
2412               && GET_CODE (op0) == MULT
2413               && GET_CODE (temp) == MULT
2414               && XEXP (op0, 0) == XEXP (temp, 0)
2415               && GET_CODE (XEXP (temp, 1)) == NEG
2416               && XEXP (op0, 1) == XEXP (XEXP (temp, 1), 0))
2417             temp = NULL_RTX;
2418           if (temp)
2419             return simplify_gen_binary (MULT, mode, temp, XEXP (op1, 0));
2420         }
2421
2422       /* Maybe simplify x * 0 to 0.  The reduction is not valid if
2423          x is NaN, since x * 0 is then also NaN.  Nor is it valid
2424          when the mode has signed zeros, since multiplying a negative
2425          number by 0 will give -0, not 0.  */
2426       if (!HONOR_NANS (mode)
2427           && !HONOR_SIGNED_ZEROS (mode)
2428           && trueop1 == CONST0_RTX (mode)
2429           && ! side_effects_p (op0))
2430         return op1;
2431
2432       /* In IEEE floating point, x*1 is not equivalent to x for
2433          signalling NaNs.  */
2434       if (!HONOR_SNANS (mode)
2435           && trueop1 == CONST1_RTX (mode))
2436         return op0;
2437
2438       /* Convert multiply by constant power of two into shift.  */
2439       if (CONST_SCALAR_INT_P (trueop1))
2440         {
2441           val = wi::exact_log2 (std::make_pair (trueop1, mode));
2442           if (val >= 0)
2443             return simplify_gen_binary (ASHIFT, mode, op0, GEN_INT (val));
2444         }
2445
2446       /* x*2 is x+x and x*(-1) is -x */
2447       if (CONST_DOUBLE_AS_FLOAT_P (trueop1)
2448           && SCALAR_FLOAT_MODE_P (GET_MODE (trueop1))
2449           && !DECIMAL_FLOAT_MODE_P (GET_MODE (trueop1))
2450           && GET_MODE (op0) == mode)
2451         {
2452           REAL_VALUE_TYPE d;
2453           REAL_VALUE_FROM_CONST_DOUBLE (d, trueop1);
2454
2455           if (REAL_VALUES_EQUAL (d, dconst2))
2456             return simplify_gen_binary (PLUS, mode, op0, copy_rtx (op0));
2457
2458           if (!HONOR_SNANS (mode)
2459               && REAL_VALUES_EQUAL (d, dconstm1))
2460             return simplify_gen_unary (NEG, mode, op0, mode);
2461         }
2462
2463       /* Optimize -x * -x as x * x.  */
2464       if (FLOAT_MODE_P (mode)
2465           && GET_CODE (op0) == NEG
2466           && GET_CODE (op1) == NEG
2467           && rtx_equal_p (XEXP (op0, 0), XEXP (op1, 0))
2468           && !side_effects_p (XEXP (op0, 0)))
2469         return simplify_gen_binary (MULT, mode, XEXP (op0, 0), XEXP (op1, 0));
2470
2471       /* Likewise, optimize abs(x) * abs(x) as x * x.  */
2472       if (SCALAR_FLOAT_MODE_P (mode)
2473           && GET_CODE (op0) == ABS
2474           && GET_CODE (op1) == ABS
2475           && rtx_equal_p (XEXP (op0, 0), XEXP (op1, 0))
2476           && !side_effects_p (XEXP (op0, 0)))
2477         return simplify_gen_binary (MULT, mode, XEXP (op0, 0), XEXP (op1, 0));
2478
2479       /* Reassociate multiplication, but for floating point MULTs
2480          only when the user specifies unsafe math optimizations.  */
2481       if (! FLOAT_MODE_P (mode)
2482           || flag_unsafe_math_optimizations)
2483         {
2484           tem = simplify_associative_operation (code, mode, op0, op1);
2485           if (tem)
2486             return tem;
2487         }
2488       break;
2489
2490     case IOR:
2491       if (trueop1 == CONST0_RTX (mode))
2492         return op0;
2493       if (INTEGRAL_MODE_P (mode)
2494           && trueop1 == CONSTM1_RTX (mode)
2495           && !side_effects_p (op0))
2496         return op1;
2497       if (rtx_equal_p (trueop0, trueop1) && ! side_effects_p (op0))
2498         return op0;
2499       /* A | (~A) -> -1 */
2500       if (((GET_CODE (op0) == NOT && rtx_equal_p (XEXP (op0, 0), op1))
2501            || (GET_CODE (op1) == NOT && rtx_equal_p (XEXP (op1, 0), op0)))
2502           && ! side_effects_p (op0)
2503           && SCALAR_INT_MODE_P (mode))
2504         return constm1_rtx;
2505
2506       /* (ior A C) is C if all bits of A that might be nonzero are on in C.  */
2507       if (CONST_INT_P (op1)
2508           && HWI_COMPUTABLE_MODE_P (mode)
2509           && (nonzero_bits (op0, mode) & ~UINTVAL (op1)) == 0
2510           && !side_effects_p (op0))
2511         return op1;
2512
2513       /* Canonicalize (X & C1) | C2.  */
2514       if (GET_CODE (op0) == AND
2515           && CONST_INT_P (trueop1)
2516           && CONST_INT_P (XEXP (op0, 1)))
2517         {
2518           HOST_WIDE_INT mask = GET_MODE_MASK (mode);
2519           HOST_WIDE_INT c1 = INTVAL (XEXP (op0, 1));
2520           HOST_WIDE_INT c2 = INTVAL (trueop1);
2521
2522           /* If (C1&C2) == C1, then (X&C1)|C2 becomes X.  */
2523           if ((c1 & c2) == c1
2524               && !side_effects_p (XEXP (op0, 0)))
2525             return trueop1;
2526
2527           /* If (C1|C2) == ~0 then (X&C1)|C2 becomes X|C2.  */
2528           if (((c1|c2) & mask) == mask)
2529             return simplify_gen_binary (IOR, mode, XEXP (op0, 0), op1);
2530
2531           /* Minimize the number of bits set in C1, i.e. C1 := C1 & ~C2.  */
2532           if (((c1 & ~c2) & mask) != (c1 & mask))
2533             {
2534               tem = simplify_gen_binary (AND, mode, XEXP (op0, 0),
2535                                          gen_int_mode (c1 & ~c2, mode));
2536               return simplify_gen_binary (IOR, mode, tem, op1);
2537             }
2538         }
2539
2540       /* Convert (A & B) | A to A.  */
2541       if (GET_CODE (op0) == AND
2542           && (rtx_equal_p (XEXP (op0, 0), op1)
2543               || rtx_equal_p (XEXP (op0, 1), op1))
2544           && ! side_effects_p (XEXP (op0, 0))
2545           && ! side_effects_p (XEXP (op0, 1)))
2546         return op1;
2547
2548       /* Convert (ior (ashift A CX) (lshiftrt A CY)) where CX+CY equals the
2549          mode size to (rotate A CX).  */
2550
2551       if (GET_CODE (op1) == ASHIFT
2552           || GET_CODE (op1) == SUBREG)
2553         {
2554           opleft = op1;
2555           opright = op0;
2556         }
2557       else
2558         {
2559           opright = op1;
2560           opleft = op0;
2561         }
2562
2563       if (GET_CODE (opleft) == ASHIFT && GET_CODE (opright) == LSHIFTRT
2564           && rtx_equal_p (XEXP (opleft, 0), XEXP (opright, 0))
2565           && CONST_INT_P (XEXP (opleft, 1))
2566           && CONST_INT_P (XEXP (opright, 1))
2567           && (INTVAL (XEXP (opleft, 1)) + INTVAL (XEXP (opright, 1))
2568               == GET_MODE_PRECISION (mode)))
2569         return gen_rtx_ROTATE (mode, XEXP (opright, 0), XEXP (opleft, 1));
2570
2571       /* Same, but for ashift that has been "simplified" to a wider mode
2572         by simplify_shift_const.  */
2573
2574       if (GET_CODE (opleft) == SUBREG
2575           && GET_CODE (SUBREG_REG (opleft)) == ASHIFT
2576           && GET_CODE (opright) == LSHIFTRT
2577           && GET_CODE (XEXP (opright, 0)) == SUBREG
2578           && GET_MODE (opleft) == GET_MODE (XEXP (opright, 0))
2579           && SUBREG_BYTE (opleft) == SUBREG_BYTE (XEXP (opright, 0))
2580           && (GET_MODE_SIZE (GET_MODE (opleft))
2581               < GET_MODE_SIZE (GET_MODE (SUBREG_REG (opleft))))
2582           && rtx_equal_p (XEXP (SUBREG_REG (opleft), 0),
2583                           SUBREG_REG (XEXP (opright, 0)))
2584           && CONST_INT_P (XEXP (SUBREG_REG (opleft), 1))
2585           && CONST_INT_P (XEXP (opright, 1))
2586           && (INTVAL (XEXP (SUBREG_REG (opleft), 1)) + INTVAL (XEXP (opright, 1))
2587               == GET_MODE_PRECISION (mode)))
2588         return gen_rtx_ROTATE (mode, XEXP (opright, 0),
2589                                XEXP (SUBREG_REG (opleft), 1));
2590
2591       /* If we have (ior (and (X C1) C2)), simplify this by making
2592          C1 as small as possible if C1 actually changes.  */
2593       if (CONST_INT_P (op1)
2594           && (HWI_COMPUTABLE_MODE_P (mode)
2595               || INTVAL (op1) > 0)
2596           && GET_CODE (op0) == AND
2597           && CONST_INT_P (XEXP (op0, 1))
2598           && CONST_INT_P (op1)
2599           && (UINTVAL (XEXP (op0, 1)) & UINTVAL (op1)) != 0)
2600         {
2601           rtx tmp = simplify_gen_binary (AND, mode, XEXP (op0, 0),
2602                                          gen_int_mode (UINTVAL (XEXP (op0, 1))
2603                                                        & ~UINTVAL (op1),
2604                                                        mode));
2605           return simplify_gen_binary (IOR, mode, tmp, op1);
2606         }
2607
2608       /* If OP0 is (ashiftrt (plus ...) C), it might actually be
2609          a (sign_extend (plus ...)).  Then check if OP1 is a CONST_INT and
2610          the PLUS does not affect any of the bits in OP1: then we can do
2611          the IOR as a PLUS and we can associate.  This is valid if OP1
2612          can be safely shifted left C bits.  */
2613       if (CONST_INT_P (trueop1) && GET_CODE (op0) == ASHIFTRT
2614           && GET_CODE (XEXP (op0, 0)) == PLUS
2615           && CONST_INT_P (XEXP (XEXP (op0, 0), 1))
2616           && CONST_INT_P (XEXP (op0, 1))
2617           && INTVAL (XEXP (op0, 1)) < HOST_BITS_PER_WIDE_INT)
2618         {
2619           int count = INTVAL (XEXP (op0, 1));
2620           HOST_WIDE_INT mask = INTVAL (trueop1) << count;
2621
2622           if (mask >> count == INTVAL (trueop1)
2623               && trunc_int_for_mode (mask, mode) == mask
2624               && (mask & nonzero_bits (XEXP (op0, 0), mode)) == 0)
2625             return simplify_gen_binary (ASHIFTRT, mode,
2626                                         plus_constant (mode, XEXP (op0, 0),
2627                                                        mask),
2628                                         XEXP (op0, 1));
2629         }
2630
2631       tem = simplify_byte_swapping_operation (code, mode, op0, op1);
2632       if (tem)
2633         return tem;
2634
2635       tem = simplify_associative_operation (code, mode, op0, op1);
2636       if (tem)
2637         return tem;
2638       break;
2639
2640     case XOR:
2641       if (trueop1 == CONST0_RTX (mode))
2642         return op0;
2643       if (INTEGRAL_MODE_P (mode) && trueop1 == CONSTM1_RTX (mode))
2644         return simplify_gen_unary (NOT, mode, op0, mode);
2645       if (rtx_equal_p (trueop0, trueop1)
2646           && ! side_effects_p (op0)
2647           && GET_MODE_CLASS (mode) != MODE_CC)
2648          return CONST0_RTX (mode);
2649
2650       /* Canonicalize XOR of the most significant bit to PLUS.  */
2651       if (CONST_SCALAR_INT_P (op1)
2652           && mode_signbit_p (mode, op1))
2653         return simplify_gen_binary (PLUS, mode, op0, op1);
2654       /* (xor (plus X C1) C2) is (xor X (C1^C2)) if C1 is signbit.  */
2655       if (CONST_SCALAR_INT_P (op1)
2656           && GET_CODE (op0) == PLUS
2657           && CONST_SCALAR_INT_P (XEXP (op0, 1))
2658           && mode_signbit_p (mode, XEXP (op0, 1)))
2659         return simplify_gen_binary (XOR, mode, XEXP (op0, 0),
2660                                     simplify_gen_binary (XOR, mode, op1,
2661                                                          XEXP (op0, 1)));
2662
2663       /* If we are XORing two things that have no bits in common,
2664          convert them into an IOR.  This helps to detect rotation encoded
2665          using those methods and possibly other simplifications.  */
2666
2667       if (HWI_COMPUTABLE_MODE_P (mode)
2668           && (nonzero_bits (op0, mode)
2669               & nonzero_bits (op1, mode)) == 0)
2670         return (simplify_gen_binary (IOR, mode, op0, op1));
2671
2672       /* Convert (XOR (NOT x) (NOT y)) to (XOR x y).
2673          Also convert (XOR (NOT x) y) to (NOT (XOR x y)), similarly for
2674          (NOT y).  */
2675       {
2676         int num_negated = 0;
2677
2678         if (GET_CODE (op0) == NOT)
2679           num_negated++, op0 = XEXP (op0, 0);
2680         if (GET_CODE (op1) == NOT)
2681           num_negated++, op1 = XEXP (op1, 0);
2682
2683         if (num_negated == 2)
2684           return simplify_gen_binary (XOR, mode, op0, op1);
2685         else if (num_negated == 1)
2686           return simplify_gen_unary (NOT, mode,
2687                                      simplify_gen_binary (XOR, mode, op0, op1),
2688                                      mode);
2689       }
2690
2691       /* Convert (xor (and A B) B) to (and (not A) B).  The latter may
2692          correspond to a machine insn or result in further simplifications
2693          if B is a constant.  */
2694
2695       if (GET_CODE (op0) == AND
2696           && rtx_equal_p (XEXP (op0, 1), op1)
2697           && ! side_effects_p (op1))
2698         return simplify_gen_binary (AND, mode,
2699                                     simplify_gen_unary (NOT, mode,
2700                                                         XEXP (op0, 0), mode),
2701                                     op1);
2702
2703       else if (GET_CODE (op0) == AND
2704                && rtx_equal_p (XEXP (op0, 0), op1)
2705                && ! side_effects_p (op1))
2706         return simplify_gen_binary (AND, mode,
2707                                     simplify_gen_unary (NOT, mode,
2708                                                         XEXP (op0, 1), mode),
2709                                     op1);
2710
2711       /* Given (xor (and A B) C), using P^Q == (~P&Q) | (~Q&P),
2712          we can transform like this:
2713             (A&B)^C == ~(A&B)&C | ~C&(A&B)
2714                     == (~A|~B)&C | ~C&(A&B)    * DeMorgan's Law
2715                     == ~A&C | ~B&C | A&(~C&B)  * Distribute and re-order
2716          Attempt a few simplifications when B and C are both constants.  */
2717       if (GET_CODE (op0) == AND
2718           && CONST_INT_P (op1)
2719           && CONST_INT_P (XEXP (op0, 1)))
2720         {
2721           rtx a = XEXP (op0, 0);
2722           rtx b = XEXP (op0, 1);
2723           rtx c = op1;
2724           HOST_WIDE_INT bval = INTVAL (b);
2725           HOST_WIDE_INT cval = INTVAL (c);
2726
2727           rtx na_c
2728             = simplify_binary_operation (AND, mode,
2729                                          simplify_gen_unary (NOT, mode, a, mode),
2730                                          c);
2731           if ((~cval & bval) == 0)
2732             {
2733               /* Try to simplify ~A&C | ~B&C.  */
2734               if (na_c != NULL_RTX)
2735                 return simplify_gen_binary (IOR, mode, na_c,
2736                                             gen_int_mode (~bval & cval, mode));
2737             }
2738           else
2739             {
2740               /* If ~A&C is zero, simplify A&(~C&B) | ~B&C.  */
2741               if (na_c == const0_rtx)
2742                 {
2743                   rtx a_nc_b = simplify_gen_binary (AND, mode, a,
2744                                                     gen_int_mode (~cval & bval,
2745                                                                   mode));
2746                   return simplify_gen_binary (IOR, mode, a_nc_b,
2747                                               gen_int_mode (~bval & cval,
2748                                                             mode));
2749                 }
2750             }
2751         }
2752
2753       /* (xor (comparison foo bar) (const_int 1)) can become the reversed
2754          comparison if STORE_FLAG_VALUE is 1.  */
2755       if (STORE_FLAG_VALUE == 1
2756           && trueop1 == const1_rtx
2757           && COMPARISON_P (op0)
2758           && (reversed = reversed_comparison (op0, mode)))
2759         return reversed;
2760
2761       /* (lshiftrt foo C) where C is the number of bits in FOO minus 1
2762          is (lt foo (const_int 0)), so we can perform the above
2763          simplification if STORE_FLAG_VALUE is 1.  */
2764
2765       if (STORE_FLAG_VALUE == 1
2766           && trueop1 == const1_rtx
2767           && GET_CODE (op0) == LSHIFTRT
2768           && CONST_INT_P (XEXP (op0, 1))
2769           && INTVAL (XEXP (op0, 1)) == GET_MODE_PRECISION (mode) - 1)
2770         return gen_rtx_GE (mode, XEXP (op0, 0), const0_rtx);
2771
2772       /* (xor (comparison foo bar) (const_int sign-bit))
2773          when STORE_FLAG_VALUE is the sign bit.  */
2774       if (val_signbit_p (mode, STORE_FLAG_VALUE)
2775           && trueop1 == const_true_rtx
2776           && COMPARISON_P (op0)
2777           && (reversed = reversed_comparison (op0, mode)))
2778         return reversed;
2779
2780       tem = simplify_byte_swapping_operation (code, mode, op0, op1);
2781       if (tem)
2782         return tem;
2783
2784       tem = simplify_associative_operation (code, mode, op0, op1);
2785       if (tem)
2786         return tem;
2787       break;
2788
2789     case AND:
2790       if (trueop1 == CONST0_RTX (mode) && ! side_effects_p (op0))
2791         return trueop1;
2792       if (INTEGRAL_MODE_P (mode) && trueop1 == CONSTM1_RTX (mode))
2793         return op0;
2794       if (HWI_COMPUTABLE_MODE_P (mode))
2795         {
2796           HOST_WIDE_INT nzop0 = nonzero_bits (trueop0, mode);
2797           HOST_WIDE_INT nzop1;
2798           if (CONST_INT_P (trueop1))
2799             {
2800               HOST_WIDE_INT val1 = INTVAL (trueop1);
2801               /* If we are turning off bits already known off in OP0, we need
2802                  not do an AND.  */
2803               if ((nzop0 & ~val1) == 0)
2804                 return op0;
2805             }
2806           nzop1 = nonzero_bits (trueop1, mode);
2807           /* If we are clearing all the nonzero bits, the result is zero.  */
2808           if ((nzop1 & nzop0) == 0
2809               && !side_effects_p (op0) && !side_effects_p (op1))
2810             return CONST0_RTX (mode);
2811         }
2812       if (rtx_equal_p (trueop0, trueop1) && ! side_effects_p (op0)
2813           && GET_MODE_CLASS (mode) != MODE_CC)
2814         return op0;
2815       /* A & (~A) -> 0 */
2816       if (((GET_CODE (op0) == NOT && rtx_equal_p (XEXP (op0, 0), op1))
2817            || (GET_CODE (op1) == NOT && rtx_equal_p (XEXP (op1, 0), op0)))
2818           && ! side_effects_p (op0)
2819           && GET_MODE_CLASS (mode) != MODE_CC)
2820         return CONST0_RTX (mode);
2821
2822       /* Transform (and (extend X) C) into (zero_extend (and X C)) if
2823          there are no nonzero bits of C outside of X's mode.  */
2824       if ((GET_CODE (op0) == SIGN_EXTEND
2825            || GET_CODE (op0) == ZERO_EXTEND)
2826           && CONST_INT_P (trueop1)
2827           && HWI_COMPUTABLE_MODE_P (mode)
2828           && (~GET_MODE_MASK (GET_MODE (XEXP (op0, 0)))
2829               & UINTVAL (trueop1)) == 0)
2830         {
2831           machine_mode imode = GET_MODE (XEXP (op0, 0));
2832           tem = simplify_gen_binary (AND, imode, XEXP (op0, 0),
2833                                      gen_int_mode (INTVAL (trueop1),
2834                                                    imode));
2835           return simplify_gen_unary (ZERO_EXTEND, mode, tem, imode);
2836         }
2837
2838       /* Transform (and (truncate X) C) into (truncate (and X C)).  This way
2839          we might be able to further simplify the AND with X and potentially
2840          remove the truncation altogether.  */
2841       if (GET_CODE (op0) == TRUNCATE && CONST_INT_P (trueop1))
2842         {
2843           rtx x = XEXP (op0, 0);
2844           machine_mode xmode = GET_MODE (x);
2845           tem = simplify_gen_binary (AND, xmode, x,
2846                                      gen_int_mode (INTVAL (trueop1), xmode));
2847           return simplify_gen_unary (TRUNCATE, mode, tem, xmode);
2848         }
2849
2850       /* Canonicalize (A | C1) & C2 as (A & C2) | (C1 & C2).  */
2851       if (GET_CODE (op0) == IOR
2852           && CONST_INT_P (trueop1)
2853           && CONST_INT_P (XEXP (op0, 1)))
2854         {
2855           HOST_WIDE_INT tmp = INTVAL (trueop1) & INTVAL (XEXP (op0, 1));
2856           return simplify_gen_binary (IOR, mode,
2857                                       simplify_gen_binary (AND, mode,
2858                                                            XEXP (op0, 0), op1),
2859                                       gen_int_mode (tmp, mode));
2860         }
2861
2862       /* Convert (A ^ B) & A to A & (~B) since the latter is often a single
2863          insn (and may simplify more).  */
2864       if (GET_CODE (op0) == XOR
2865           && rtx_equal_p (XEXP (op0, 0), op1)
2866           && ! side_effects_p (op1))
2867         return simplify_gen_binary (AND, mode,
2868                                     simplify_gen_unary (NOT, mode,
2869                                                         XEXP (op0, 1), mode),
2870                                     op1);
2871
2872       if (GET_CODE (op0) == XOR
2873           && rtx_equal_p (XEXP (op0, 1), op1)
2874           && ! side_effects_p (op1))
2875         return simplify_gen_binary (AND, mode,
2876                                     simplify_gen_unary (NOT, mode,
2877                                                         XEXP (op0, 0), mode),
2878                                     op1);
2879
2880       /* Similarly for (~(A ^ B)) & A.  */
2881       if (GET_CODE (op0) == NOT
2882           && GET_CODE (XEXP (op0, 0)) == XOR
2883           && rtx_equal_p (XEXP (XEXP (op0, 0), 0), op1)
2884           && ! side_effects_p (op1))
2885         return simplify_gen_binary (AND, mode, XEXP (XEXP (op0, 0), 1), op1);
2886
2887       if (GET_CODE (op0) == NOT
2888           && GET_CODE (XEXP (op0, 0)) == XOR
2889           && rtx_equal_p (XEXP (XEXP (op0, 0), 1), op1)
2890           && ! side_effects_p (op1))
2891         return simplify_gen_binary (AND, mode, XEXP (XEXP (op0, 0), 0), op1);
2892
2893       /* Convert (A | B) & A to A.  */
2894       if (GET_CODE (op0) == IOR
2895           && (rtx_equal_p (XEXP (op0, 0), op1)
2896               || rtx_equal_p (XEXP (op0, 1), op1))
2897           && ! side_effects_p (XEXP (op0, 0))
2898           && ! side_effects_p (XEXP (op0, 1)))
2899         return op1;
2900
2901       /* For constants M and N, if M == (1LL << cst) - 1 && (N & M) == M,
2902          ((A & N) + B) & M -> (A + B) & M
2903          Similarly if (N & M) == 0,
2904          ((A | N) + B) & M -> (A + B) & M
2905          and for - instead of + and/or ^ instead of |.
2906          Also, if (N & M) == 0, then
2907          (A +- N) & M -> A & M.  */
2908       if (CONST_INT_P (trueop1)
2909           && HWI_COMPUTABLE_MODE_P (mode)
2910           && ~UINTVAL (trueop1)
2911           && (UINTVAL (trueop1) & (UINTVAL (trueop1) + 1)) == 0
2912           && (GET_CODE (op0) == PLUS || GET_CODE (op0) == MINUS))
2913         {
2914           rtx pmop[2];
2915           int which;
2916
2917           pmop[0] = XEXP (op0, 0);
2918           pmop[1] = XEXP (op0, 1);
2919
2920           if (CONST_INT_P (pmop[1])
2921               && (UINTVAL (pmop[1]) & UINTVAL (trueop1)) == 0)
2922             return simplify_gen_binary (AND, mode, pmop[0], op1);
2923
2924           for (which = 0; which < 2; which++)
2925             {
2926               tem = pmop[which];
2927               switch (GET_CODE (tem))
2928                 {
2929                 case AND:
2930                   if (CONST_INT_P (XEXP (tem, 1))
2931                       && (UINTVAL (XEXP (tem, 1)) & UINTVAL (trueop1))
2932                       == UINTVAL (trueop1))
2933                     pmop[which] = XEXP (tem, 0);
2934                   break;
2935                 case IOR:
2936                 case XOR:
2937                   if (CONST_INT_P (XEXP (tem, 1))
2938                       && (UINTVAL (XEXP (tem, 1)) & UINTVAL (trueop1)) == 0)
2939                     pmop[which] = XEXP (tem, 0);
2940                   break;
2941                 default:
2942                   break;
2943                 }
2944             }
2945
2946           if (pmop[0] != XEXP (op0, 0) || pmop[1] != XEXP (op0, 1))
2947             {
2948               tem = simplify_gen_binary (GET_CODE (op0), mode,
2949                                          pmop[0], pmop[1]);
2950               return simplify_gen_binary (code, mode, tem, op1);
2951             }
2952         }
2953
2954       /* (and X (ior (not X) Y) -> (and X Y) */
2955       if (GET_CODE (op1) == IOR
2956           && GET_CODE (XEXP (op1, 0)) == NOT
2957           && rtx_equal_p (op0, XEXP (XEXP (op1, 0), 0)))
2958        return simplify_gen_binary (AND, mode, op0, XEXP (op1, 1));
2959
2960       /* (and (ior (not X) Y) X) -> (and X Y) */
2961       if (GET_CODE (op0) == IOR
2962           && GET_CODE (XEXP (op0, 0)) == NOT
2963           && rtx_equal_p (op1, XEXP (XEXP (op0, 0), 0)))
2964         return simplify_gen_binary (AND, mode, op1, XEXP (op0, 1));
2965
2966       /* (and X (ior Y (not X)) -> (and X Y) */
2967       if (GET_CODE (op1) == IOR
2968           && GET_CODE (XEXP (op1, 1)) == NOT
2969           && rtx_equal_p (op0, XEXP (XEXP (op1, 1), 0)))
2970        return simplify_gen_binary (AND, mode, op0, XEXP (op1, 0));
2971
2972       /* (and (ior Y (not X)) X) -> (and X Y) */
2973       if (GET_CODE (op0) == IOR
2974           && GET_CODE (XEXP (op0, 1)) == NOT
2975           && rtx_equal_p (op1, XEXP (XEXP (op0, 1), 0)))
2976         return simplify_gen_binary (AND, mode, op1, XEXP (op0, 0));
2977
2978       tem = simplify_byte_swapping_operation (code, mode, op0, op1);
2979       if (tem)
2980         return tem;
2981
2982       tem = simplify_associative_operation (code, mode, op0, op1);
2983       if (tem)
2984         return tem;
2985       break;
2986
2987     case UDIV:
2988       /* 0/x is 0 (or x&0 if x has side-effects).  */
2989       if (trueop0 == CONST0_RTX (mode))
2990         {
2991           if (side_effects_p (op1))
2992             return simplify_gen_binary (AND, mode, op1, trueop0);
2993           return trueop0;
2994         }
2995       /* x/1 is x.  */
2996       if (trueop1 == CONST1_RTX (mode))
2997         {
2998           tem = rtl_hooks.gen_lowpart_no_emit (mode, op0);
2999           if (tem)
3000             return tem;
3001         }
3002       /* Convert divide by power of two into shift.  */
3003       if (CONST_INT_P (trueop1)
3004           && (val = exact_log2 (UINTVAL (trueop1))) > 0)
3005         return simplify_gen_binary (LSHIFTRT, mode, op0, GEN_INT (val));
3006       break;
3007
3008     case DIV:
3009       /* Handle floating point and integers separately.  */
3010       if (SCALAR_FLOAT_MODE_P (mode))
3011         {
3012           /* Maybe change 0.0 / x to 0.0.  This transformation isn't
3013              safe for modes with NaNs, since 0.0 / 0.0 will then be
3014              NaN rather than 0.0.  Nor is it safe for modes with signed
3015              zeros, since dividing 0 by a negative number gives -0.0  */
3016           if (trueop0 == CONST0_RTX (mode)
3017               && !HONOR_NANS (mode)
3018               && !HONOR_SIGNED_ZEROS (mode)
3019               && ! side_effects_p (op1))
3020             return op0;
3021           /* x/1.0 is x.  */
3022           if (trueop1 == CONST1_RTX (mode)
3023               && !HONOR_SNANS (mode))
3024             return op0;
3025
3026           if (CONST_DOUBLE_AS_FLOAT_P (trueop1)
3027               && trueop1 != CONST0_RTX (mode))
3028             {
3029               REAL_VALUE_TYPE d;
3030               REAL_VALUE_FROM_CONST_DOUBLE (d, trueop1);
3031
3032               /* x/-1.0 is -x.  */
3033               if (REAL_VALUES_EQUAL (d, dconstm1)
3034                   && !HONOR_SNANS (mode))
3035                 return simplify_gen_unary (NEG, mode, op0, mode);
3036
3037               /* Change FP division by a constant into multiplication.
3038                  Only do this with -freciprocal-math.  */
3039               if (flag_reciprocal_math
3040                   && !REAL_VALUES_EQUAL (d, dconst0))
3041                 {
3042                   REAL_ARITHMETIC (d, RDIV_EXPR, dconst1, d);
3043                   tem = CONST_DOUBLE_FROM_REAL_VALUE (d, mode);
3044                   return simplify_gen_binary (MULT, mode, op0, tem);
3045                 }
3046             }
3047         }
3048       else if (SCALAR_INT_MODE_P (mode))
3049         {
3050           /* 0/x is 0 (or x&0 if x has side-effects).  */
3051           if (trueop0 == CONST0_RTX (mode)
3052               && !cfun->can_throw_non_call_exceptions)
3053             {
3054               if (side_effects_p (op1))
3055                 return simplify_gen_binary (AND, mode, op1, trueop0);
3056               return trueop0;
3057             }
3058           /* x/1 is x.  */
3059           if (trueop1 == CONST1_RTX (mode))
3060             {
3061               tem = rtl_hooks.gen_lowpart_no_emit (mode, op0);
3062               if (tem)
3063                 return tem;
3064             }
3065           /* x/-1 is -x.  */
3066           if (trueop1 == constm1_rtx)
3067             {
3068               rtx x = rtl_hooks.gen_lowpart_no_emit (mode, op0);
3069               if (x)
3070                 return simplify_gen_unary (NEG, mode, x, mode);
3071             }
3072         }
3073       break;
3074
3075     case UMOD:
3076       /* 0%x is 0 (or x&0 if x has side-effects).  */
3077       if (trueop0 == CONST0_RTX (mode))
3078         {
3079           if (side_effects_p (op1))
3080             return simplify_gen_binary (AND, mode, op1, trueop0);
3081           return trueop0;
3082         }
3083       /* x%1 is 0 (of x&0 if x has side-effects).  */
3084       if (trueop1 == CONST1_RTX (mode))
3085         {
3086           if (side_effects_p (op0))
3087             return simplify_gen_binary (AND, mode, op0, CONST0_RTX (mode));
3088           return CONST0_RTX (mode);
3089         }
3090       /* Implement modulus by power of two as AND.  */
3091       if (CONST_INT_P (trueop1)
3092           && exact_log2 (UINTVAL (trueop1)) > 0)
3093         return simplify_gen_binary (AND, mode, op0,
3094                                     gen_int_mode (INTVAL (op1) - 1, mode));
3095       break;
3096
3097     case MOD:
3098       /* 0%x is 0 (or x&0 if x has side-effects).  */
3099       if (trueop0 == CONST0_RTX (mode))
3100         {
3101           if (side_effects_p (op1))
3102             return simplify_gen_binary (AND, mode, op1, trueop0);
3103           return trueop0;
3104         }
3105       /* x%1 and x%-1 is 0 (or x&0 if x has side-effects).  */
3106       if (trueop1 == CONST1_RTX (mode) || trueop1 == constm1_rtx)
3107         {
3108           if (side_effects_p (op0))
3109             return simplify_gen_binary (AND, mode, op0, CONST0_RTX (mode));
3110           return CONST0_RTX (mode);
3111         }
3112       break;
3113
3114     case ROTATERT:
3115     case ROTATE:
3116       /* Canonicalize rotates by constant amount.  If op1 is bitsize / 2,
3117          prefer left rotation, if op1 is from bitsize / 2 + 1 to
3118          bitsize - 1, use other direction of rotate with 1 .. bitsize / 2 - 1
3119          amount instead.  */
3120 #if defined(HAVE_rotate) && defined(HAVE_rotatert)
3121       if (CONST_INT_P (trueop1)
3122           && IN_RANGE (INTVAL (trueop1),
3123                        GET_MODE_PRECISION (mode) / 2 + (code == ROTATE),
3124                        GET_MODE_PRECISION (mode) - 1))
3125         return simplify_gen_binary (code == ROTATE ? ROTATERT : ROTATE,
3126                                     mode, op0, GEN_INT (GET_MODE_PRECISION (mode)
3127                                                         - INTVAL (trueop1)));
3128 #endif
3129       /* FALLTHRU */
3130     case ASHIFTRT:
3131       if (trueop1 == CONST0_RTX (mode))
3132         return op0;
3133       if (trueop0 == CONST0_RTX (mode) && ! side_effects_p (op1))
3134         return op0;
3135       /* Rotating ~0 always results in ~0.  */
3136       if (CONST_INT_P (trueop0) && width <= HOST_BITS_PER_WIDE_INT
3137           && UINTVAL (trueop0) == GET_MODE_MASK (mode)
3138           && ! side_effects_p (op1))
3139         return op0;
3140       /* Given:
3141          scalar modes M1, M2
3142          scalar constants c1, c2
3143          size (M2) > size (M1)
3144          c1 == size (M2) - size (M1)
3145          optimize:
3146          (ashiftrt:M1 (subreg:M1 (lshiftrt:M2 (reg:M2) (const_int <c1>))
3147                                  <low_part>)
3148                       (const_int <c2>))
3149          to:
3150          (subreg:M1 (ashiftrt:M2 (reg:M2) (const_int <c1 + c2>))
3151                     <low_part>).  */
3152       if (code == ASHIFTRT
3153           && !VECTOR_MODE_P (mode)
3154           && SUBREG_P (op0)
3155           && CONST_INT_P (op1)
3156           && GET_CODE (SUBREG_REG (op0)) == LSHIFTRT
3157           && !VECTOR_MODE_P (GET_MODE (SUBREG_REG (op0)))
3158           && CONST_INT_P (XEXP (SUBREG_REG (op0), 1))
3159           && (GET_MODE_BITSIZE (GET_MODE (SUBREG_REG (op0)))
3160               > GET_MODE_BITSIZE (mode))
3161           && (INTVAL (XEXP (SUBREG_REG (op0), 1))
3162               == (GET_MODE_BITSIZE (GET_MODE (SUBREG_REG (op0)))
3163                   - GET_MODE_BITSIZE (mode)))
3164           && subreg_lowpart_p (op0))
3165         {
3166           rtx tmp = GEN_INT (INTVAL (XEXP (SUBREG_REG (op0), 1))
3167                              + INTVAL (op1));
3168           machine_mode inner_mode = GET_MODE (SUBREG_REG (op0));
3169           tmp = simplify_gen_binary (ASHIFTRT,
3170                                      GET_MODE (SUBREG_REG (op0)),
3171                                      XEXP (SUBREG_REG (op0), 0),
3172                                      tmp);
3173           return simplify_gen_subreg (mode, tmp, inner_mode,
3174                                       subreg_lowpart_offset (mode,
3175                                                              inner_mode));
3176         }
3177     canonicalize_shift:
3178       if (SHIFT_COUNT_TRUNCATED && CONST_INT_P (op1))
3179         {
3180           val = INTVAL (op1) & (GET_MODE_PRECISION (mode) - 1);
3181           if (val != INTVAL (op1))
3182             return simplify_gen_binary (code, mode, op0, GEN_INT (val));
3183         }
3184       break;
3185
3186     case ASHIFT:
3187     case SS_ASHIFT:
3188     case US_ASHIFT:
3189       if (trueop1 == CONST0_RTX (mode))
3190         return op0;
3191       if (trueop0 == CONST0_RTX (mode) && ! side_effects_p (op1))
3192         return op0;
3193       goto canonicalize_shift;
3194
3195     case LSHIFTRT:
3196       if (trueop1 == CONST0_RTX (mode))
3197         return op0;
3198       if (trueop0 == CONST0_RTX (mode) && ! side_effects_p (op1))
3199         return op0;
3200       /* Optimize (lshiftrt (clz X) C) as (eq X 0).  */
3201       if (GET_CODE (op0) == CLZ
3202           && CONST_INT_P (trueop1)
3203           && STORE_FLAG_VALUE == 1
3204           && INTVAL (trueop1) < (HOST_WIDE_INT)width)
3205         {
3206           machine_mode imode = GET_MODE (XEXP (op0, 0));
3207           unsigned HOST_WIDE_INT zero_val = 0;
3208
3209           if (CLZ_DEFINED_VALUE_AT_ZERO (imode, zero_val)
3210               && zero_val == GET_MODE_PRECISION (imode)
3211               && INTVAL (trueop1) == exact_log2 (zero_val))
3212             return simplify_gen_relational (EQ, mode, imode,
3213                                             XEXP (op0, 0), const0_rtx);
3214         }
3215       goto canonicalize_shift;
3216
3217     case SMIN:
3218       if (width <= HOST_BITS_PER_WIDE_INT
3219           && mode_signbit_p (mode, trueop1)
3220           && ! side_effects_p (op0))
3221         return op1;
3222       if (rtx_equal_p (trueop0, trueop1) && ! side_effects_p (op0))
3223         return op0;
3224       tem = simplify_associative_operation (code, mode, op0, op1);
3225       if (tem)
3226         return tem;
3227       break;
3228
3229     case SMAX:
3230       if (width <= HOST_BITS_PER_WIDE_INT
3231           && CONST_INT_P (trueop1)
3232           && (UINTVAL (trueop1) == GET_MODE_MASK (mode) >> 1)
3233           && ! side_effects_p (op0))
3234         return op1;
3235       if (rtx_equal_p (trueop0, trueop1) && ! side_effects_p (op0))
3236         return op0;
3237       tem = simplify_associative_operation (code, mode, op0, op1);
3238       if (tem)
3239         return tem;
3240       break;
3241
3242     case UMIN:
3243       if (trueop1 == CONST0_RTX (mode) && ! side_effects_p (op0))
3244         return op1;
3245       if (rtx_equal_p (trueop0, trueop1) && ! side_effects_p (op0))
3246         return op0;
3247       tem = simplify_associative_operation (code, mode, op0, op1);
3248       if (tem)
3249         return tem;
3250       break;
3251
3252     case UMAX:
3253       if (trueop1 == constm1_rtx && ! side_effects_p (op0))
3254         return op1;
3255       if (rtx_equal_p (trueop0, trueop1) && ! side_effects_p (op0))
3256         return op0;
3257       tem = simplify_associative_operation (code, mode, op0, op1);
3258       if (tem)
3259         return tem;
3260       break;
3261
3262     case SS_PLUS:
3263     case US_PLUS:
3264     case SS_MINUS:
3265     case US_MINUS:
3266     case SS_MULT:
3267     case US_MULT:
3268     case SS_DIV:
3269     case US_DIV:
3270       /* ??? There are simplifications that can be done.  */
3271       return 0;
3272
3273     case VEC_SELECT:
3274       if (!VECTOR_MODE_P (mode))
3275         {
3276           gcc_assert (VECTOR_MODE_P (GET_MODE (trueop0)));
3277           gcc_assert (mode == GET_MODE_INNER (GET_MODE (trueop0)));
3278           gcc_assert (GET_CODE (trueop1) == PARALLEL);
3279           gcc_assert (XVECLEN (trueop1, 0) == 1);
3280           gcc_assert (CONST_INT_P (XVECEXP (trueop1, 0, 0)));
3281
3282           if (GET_CODE (trueop0) == CONST_VECTOR)
3283             return CONST_VECTOR_ELT (trueop0, INTVAL (XVECEXP
3284                                                       (trueop1, 0, 0)));
3285
3286           /* Extract a scalar element from a nested VEC_SELECT expression
3287              (with optional nested VEC_CONCAT expression).  Some targets
3288              (i386) extract scalar element from a vector using chain of
3289              nested VEC_SELECT expressions.  When input operand is a memory
3290              operand, this operation can be simplified to a simple scalar
3291              load from an offseted memory address.  */
3292           if (GET_CODE (trueop0) == VEC_SELECT)
3293             {
3294               rtx op0 = XEXP (trueop0, 0);
3295               rtx op1 = XEXP (trueop0, 1);
3296
3297               machine_mode opmode = GET_MODE (op0);
3298               int elt_size = GET_MODE_SIZE (GET_MODE_INNER (opmode));
3299               int n_elts = GET_MODE_SIZE (opmode) / elt_size;
3300
3301               int i = INTVAL (XVECEXP (trueop1, 0, 0));
3302               int elem;
3303
3304               rtvec vec;
3305               rtx tmp_op, tmp;
3306
3307               gcc_assert (GET_CODE (op1) == PARALLEL);
3308               gcc_assert (i < n_elts);
3309
3310               /* Select element, pointed by nested selector.  */
3311               elem = INTVAL (XVECEXP (op1, 0, i));
3312
3313               /* Handle the case when nested VEC_SELECT wraps VEC_CONCAT.  */
3314               if (GET_CODE (op0) == VEC_CONCAT)
3315                 {
3316                   rtx op00 = XEXP (op0, 0);
3317                   rtx op01 = XEXP (op0, 1);
3318
3319                   machine_mode mode00, mode01;
3320                   int n_elts00, n_elts01;
3321
3322                   mode00 = GET_MODE (op00);
3323                   mode01 = GET_MODE (op01);
3324
3325                   /* Find out number of elements of each operand.  */
3326                   if (VECTOR_MODE_P (mode00))
3327                     {
3328                       elt_size = GET_MODE_SIZE (GET_MODE_INNER (mode00));
3329                       n_elts00 = GET_MODE_SIZE (mode00) / elt_size;
3330                     }
3331                   else
3332                     n_elts00 = 1;
3333
3334                   if (VECTOR_MODE_P (mode01))
3335                     {
3336                       elt_size = GET_MODE_SIZE (GET_MODE_INNER (mode01));
3337                       n_elts01 = GET_MODE_SIZE (mode01) / elt_size;
3338                     }
3339                   else
3340                     n_elts01 = 1;
3341
3342                   gcc_assert (n_elts == n_elts00 + n_elts01);
3343
3344                   /* Select correct operand of VEC_CONCAT
3345                      and adjust selector. */
3346                   if (elem < n_elts01)
3347                     tmp_op = op00;
3348                   else
3349                     {
3350                       tmp_op = op01;
3351                       elem -= n_elts00;
3352                     }
3353                 }
3354               else
3355                 tmp_op = op0;
3356
3357               vec = rtvec_alloc (1);
3358               RTVEC_ELT (vec, 0) = GEN_INT (elem);
3359
3360               tmp = gen_rtx_fmt_ee (code, mode,
3361                                     tmp_op, gen_rtx_PARALLEL (VOIDmode, vec));
3362               return tmp;
3363             }
3364           if (GET_CODE (trueop0) == VEC_DUPLICATE
3365               && GET_MODE (XEXP (trueop0, 0)) == mode)
3366             return XEXP (trueop0, 0);
3367         }
3368       else
3369         {
3370           gcc_assert (VECTOR_MODE_P (GET_MODE (trueop0)));
3371           gcc_assert (GET_MODE_INNER (mode)
3372                       == GET_MODE_INNER (GET_MODE (trueop0)));
3373           gcc_assert (GET_CODE (trueop1) == PARALLEL);
3374
3375           if (GET_CODE (trueop0) == CONST_VECTOR)
3376             {
3377               int elt_size = GET_MODE_SIZE (GET_MODE_INNER (mode));
3378               unsigned n_elts = (GET_MODE_SIZE (mode) / elt_size);
3379               rtvec v = rtvec_alloc (n_elts);
3380               unsigned int i;
3381
3382               gcc_assert (XVECLEN (trueop1, 0) == (int) n_elts);
3383               for (i = 0; i < n_elts; i++)
3384                 {
3385                   rtx x = XVECEXP (trueop1, 0, i);
3386
3387                   gcc_assert (CONST_INT_P (x));
3388                   RTVEC_ELT (v, i) = CONST_VECTOR_ELT (trueop0,
3389                                                        INTVAL (x));
3390                 }
3391
3392               return gen_rtx_CONST_VECTOR (mode, v);
3393             }
3394
3395           /* Recognize the identity.  */
3396           if (GET_MODE (trueop0) == mode)
3397             {
3398               bool maybe_ident = true;
3399               for (int i = 0; i < XVECLEN (trueop1, 0); i++)
3400                 {
3401                   rtx j = XVECEXP (trueop1, 0, i);
3402                   if (!CONST_INT_P (j) || INTVAL (j) != i)
3403                     {
3404                       maybe_ident = false;
3405                       break;
3406                     }
3407                 }
3408               if (maybe_ident)
3409                 return trueop0;
3410             }
3411
3412           /* If we build {a,b} then permute it, build the result directly.  */
3413           if (XVECLEN (trueop1, 0) == 2
3414               && CONST_INT_P (XVECEXP (trueop1, 0, 0))
3415               && CONST_INT_P (XVECEXP (trueop1, 0, 1))
3416               && GET_CODE (trueop0) == VEC_CONCAT
3417               && GET_CODE (XEXP (trueop0, 0)) == VEC_CONCAT
3418               && GET_MODE (XEXP (trueop0, 0)) == mode
3419               && GET_CODE (XEXP (trueop0, 1)) == VEC_CONCAT
3420               && GET_MODE (XEXP (trueop0, 1)) == mode)
3421             {
3422               unsigned int i0 = INTVAL (XVECEXP (trueop1, 0, 0));
3423               unsigned int i1 = INTVAL (XVECEXP (trueop1, 0, 1));
3424               rtx subop0, subop1;
3425
3426               gcc_assert (i0 < 4 && i1 < 4);
3427               subop0 = XEXP (XEXP (trueop0, i0 / 2), i0 % 2);
3428               subop1 = XEXP (XEXP (trueop0, i1 / 2), i1 % 2);
3429
3430               return simplify_gen_binary (VEC_CONCAT, mode, subop0, subop1);
3431             }
3432
3433           if (XVECLEN (trueop1, 0) == 2
3434               && CONST_INT_P (XVECEXP (trueop1, 0, 0))
3435               && CONST_INT_P (XVECEXP (trueop1, 0, 1))
3436               && GET_CODE (trueop0) == VEC_CONCAT
3437               && GET_MODE (trueop0) == mode)
3438             {
3439               unsigned int i0 = INTVAL (XVECEXP (trueop1, 0, 0));
3440               unsigned int i1 = INTVAL (XVECEXP (trueop1, 0, 1));
3441               rtx subop0, subop1;
3442
3443               gcc_assert (i0 < 2 && i1 < 2);
3444               subop0 = XEXP (trueop0, i0);
3445               subop1 = XEXP (trueop0, i1);
3446
3447               return simplify_gen_binary (VEC_CONCAT, mode, subop0, subop1);
3448             }
3449
3450           /* If we select one half of a vec_concat, return that.  */
3451           if (GET_CODE (trueop0) == VEC_CONCAT
3452               && CONST_INT_P (XVECEXP (trueop1, 0, 0)))
3453             {
3454               rtx subop0 = XEXP (trueop0, 0);
3455               rtx subop1 = XEXP (trueop0, 1);
3456               machine_mode mode0 = GET_MODE (subop0);
3457               machine_mode mode1 = GET_MODE (subop1);
3458               int li = GET_MODE_SIZE (GET_MODE_INNER (mode0));
3459               int l0 = GET_MODE_SIZE (mode0) / li;
3460               int l1 = GET_MODE_SIZE (mode1) / li;
3461               int i0 = INTVAL (XVECEXP (trueop1, 0, 0));
3462               if (i0 == 0 && !side_effects_p (op1) && mode == mode0)
3463                 {
3464                   bool success = true;
3465                   for (int i = 1; i < l0; ++i)
3466                     {
3467                       rtx j = XVECEXP (trueop1, 0, i);
3468                       if (!CONST_INT_P (j) || INTVAL (j) != i)
3469                         {
3470                           success = false;
3471                           break;
3472                         }
3473                     }
3474                   if (success)
3475                     return subop0;
3476                 }
3477               if (i0 == l0 && !side_effects_p (op0) && mode == mode1)
3478                 {
3479                   bool success = true;
3480                   for (int i = 1; i < l1; ++i)
3481                     {
3482                       rtx j = XVECEXP (trueop1, 0, i);
3483                       if (!CONST_INT_P (j) || INTVAL (j) != i0 + i)
3484                         {
3485                           success = false;
3486                           break;
3487                         }
3488                     }
3489                   if (success)
3490                     return subop1;
3491                 }
3492             }
3493         }
3494
3495       if (XVECLEN (trueop1, 0) == 1
3496           && CONST_INT_P (XVECEXP (trueop1, 0, 0))
3497           && GET_CODE (trueop0) == VEC_CONCAT)
3498         {
3499           rtx vec = trueop0;
3500           int offset = INTVAL (XVECEXP (trueop1, 0, 0)) * GET_MODE_SIZE (mode);
3501
3502           /* Try to find the element in the VEC_CONCAT.  */
3503           while (GET_MODE (vec) != mode
3504                  && GET_CODE (vec) == VEC_CONCAT)
3505             {
3506               HOST_WIDE_INT vec_size = GET_MODE_SIZE (GET_MODE (XEXP (vec, 0)));
3507               if (offset < vec_size)
3508                 vec = XEXP (vec, 0);
3509               else
3510                 {
3511                   offset -= vec_size;
3512                   vec = XEXP (vec, 1);
3513                 }
3514               vec = avoid_constant_pool_reference (vec);
3515             }
3516
3517           if (GET_MODE (vec) == mode)
3518             return vec;
3519         }
3520
3521       /* If we select elements in a vec_merge that all come from the same
3522          operand, select from that operand directly.  */
3523       if (GET_CODE (op0) == VEC_MERGE)
3524         {
3525           rtx trueop02 = avoid_constant_pool_reference (XEXP (op0, 2));
3526           if (CONST_INT_P (trueop02))
3527             {
3528               unsigned HOST_WIDE_INT sel = UINTVAL (trueop02);
3529               bool all_operand0 = true;
3530               bool all_operand1 = true;
3531               for (int i = 0; i < XVECLEN (trueop1, 0); i++)
3532                 {
3533                   rtx j = XVECEXP (trueop1, 0, i);
3534                   if (sel & (1 << UINTVAL (j)))
3535                     all_operand1 = false;
3536                   else
3537                     all_operand0 = false;
3538                 }
3539               if (all_operand0 && !side_effects_p (XEXP (op0, 1)))
3540                 return simplify_gen_binary (VEC_SELECT, mode, XEXP (op0, 0), op1);
3541               if (all_operand1 && !side_effects_p (XEXP (op0, 0)))
3542                 return simplify_gen_binary (VEC_SELECT, mode, XEXP (op0, 1), op1);
3543             }
3544         }
3545
3546       /* If we have two nested selects that are inverses of each
3547          other, replace them with the source operand.  */
3548       if (GET_CODE (trueop0) == VEC_SELECT
3549           && GET_MODE (XEXP (trueop0, 0)) == mode)
3550         {
3551           rtx op0_subop1 = XEXP (trueop0, 1);
3552           gcc_assert (GET_CODE (op0_subop1) == PARALLEL);
3553           gcc_assert (XVECLEN (trueop1, 0) == GET_MODE_NUNITS (mode));
3554
3555           /* Apply the outer ordering vector to the inner one.  (The inner
3556              ordering vector is expressly permitted to be of a different
3557              length than the outer one.)  If the result is { 0, 1, ..., n-1 }
3558              then the two VEC_SELECTs cancel.  */
3559           for (int i = 0; i < XVECLEN (trueop1, 0); ++i)
3560             {
3561               rtx x = XVECEXP (trueop1, 0, i);
3562               if (!CONST_INT_P (x))
3563                 return 0;
3564               rtx y = XVECEXP (op0_subop1, 0, INTVAL (x));
3565               if (!CONST_INT_P (y) || i != INTVAL (y))
3566                 return 0;
3567             }
3568           return XEXP (trueop0, 0);
3569         }
3570
3571       return 0;
3572     case VEC_CONCAT:
3573       {
3574         machine_mode op0_mode = (GET_MODE (trueop0) != VOIDmode
3575                                       ? GET_MODE (trueop0)
3576                                       : GET_MODE_INNER (mode));
3577         machine_mode op1_mode = (GET_MODE (trueop1) != VOIDmode
3578                                       ? GET_MODE (trueop1)
3579                                       : GET_MODE_INNER (mode));
3580
3581         gcc_assert (VECTOR_MODE_P (mode));
3582         gcc_assert (GET_MODE_SIZE (op0_mode) + GET_MODE_SIZE (op1_mode)
3583                     == GET_MODE_SIZE (mode));
3584
3585         if (VECTOR_MODE_P (op0_mode))
3586           gcc_assert (GET_MODE_INNER (mode)
3587                       == GET_MODE_INNER (op0_mode));
3588         else
3589           gcc_assert (GET_MODE_INNER (mode) == op0_mode);
3590
3591         if (VECTOR_MODE_P (op1_mode))
3592           gcc_assert (GET_MODE_INNER (mode)
3593                       == GET_MODE_INNER (op1_mode));
3594         else
3595           gcc_assert (GET_MODE_INNER (mode) == op1_mode);
3596
3597         if ((GET_CODE (trueop0) == CONST_VECTOR
3598              || CONST_SCALAR_INT_P (trueop0) 
3599              || CONST_DOUBLE_AS_FLOAT_P (trueop0))
3600             && (GET_CODE (trueop1) == CONST_VECTOR
3601                 || CONST_SCALAR_INT_P (trueop1) 
3602                 || CONST_DOUBLE_AS_FLOAT_P (trueop1)))
3603           {
3604             int elt_size = GET_MODE_SIZE (GET_MODE_INNER (mode));
3605             unsigned n_elts = (GET_MODE_SIZE (mode) / elt_size);
3606             rtvec v = rtvec_alloc (n_elts);
3607             unsigned int i;
3608             unsigned in_n_elts = 1;
3609
3610             if (VECTOR_MODE_P (op0_mode))
3611               in_n_elts = (GET_MODE_SIZE (op0_mode) / elt_size);
3612             for (i = 0; i < n_elts; i++)
3613               {
3614                 if (i < in_n_elts)
3615                   {
3616                     if (!VECTOR_MODE_P (op0_mode))
3617                       RTVEC_ELT (v, i) = trueop0;
3618                     else
3619                       RTVEC_ELT (v, i) = CONST_VECTOR_ELT (trueop0, i);
3620                   }
3621                 else
3622                   {
3623                     if (!VECTOR_MODE_P (op1_mode))
3624                       RTVEC_ELT (v, i) = trueop1;
3625                     else
3626                       RTVEC_ELT (v, i) = CONST_VECTOR_ELT (trueop1,
3627                                                            i - in_n_elts);
3628                   }
3629               }
3630
3631             return gen_rtx_CONST_VECTOR (mode, v);
3632           }
3633
3634         /* Try to merge two VEC_SELECTs from the same vector into a single one.
3635            Restrict the transformation to avoid generating a VEC_SELECT with a
3636            mode unrelated to its operand.  */
3637         if (GET_CODE (trueop0) == VEC_SELECT
3638             && GET_CODE (trueop1) == VEC_SELECT
3639             && rtx_equal_p (XEXP (trueop0, 0), XEXP (trueop1, 0))
3640             && GET_MODE (XEXP (trueop0, 0)) == mode)
3641           {
3642             rtx par0 = XEXP (trueop0, 1);
3643             rtx par1 = XEXP (trueop1, 1);
3644             int len0 = XVECLEN (par0, 0);
3645             int len1 = XVECLEN (par1, 0);
3646             rtvec vec = rtvec_alloc (len0 + len1);
3647             for (int i = 0; i < len0; i++)
3648               RTVEC_ELT (vec, i) = XVECEXP (par0, 0, i);
3649             for (int i = 0; i < len1; i++)
3650               RTVEC_ELT (vec, len0 + i) = XVECEXP (par1, 0, i);
3651             return simplify_gen_binary (VEC_SELECT, mode, XEXP (trueop0, 0),
3652                                         gen_rtx_PARALLEL (VOIDmode, vec));
3653           }
3654       }
3655       return 0;
3656
3657     default:
3658       gcc_unreachable ();
3659     }
3660
3661   return 0;
3662 }
3663
3664 rtx
3665 simplify_const_binary_operation (enum rtx_code code, machine_mode mode,
3666                                  rtx op0, rtx op1)
3667 {
3668   unsigned int width = GET_MODE_PRECISION (mode);
3669
3670   if (VECTOR_MODE_P (mode)
3671       && code != VEC_CONCAT
3672       && GET_CODE (op0) == CONST_VECTOR
3673       && GET_CODE (op1) == CONST_VECTOR)
3674     {
3675       unsigned n_elts = GET_MODE_NUNITS (mode);
3676       machine_mode op0mode = GET_MODE (op0);
3677       unsigned op0_n_elts = GET_MODE_NUNITS (op0mode);
3678       machine_mode op1mode = GET_MODE (op1);
3679       unsigned op1_n_elts = GET_MODE_NUNITS (op1mode);
3680       rtvec v = rtvec_alloc (n_elts);
3681       unsigned int i;
3682
3683       gcc_assert (op0_n_elts == n_elts);
3684       gcc_assert (op1_n_elts == n_elts);
3685       for (i = 0; i < n_elts; i++)
3686         {
3687           rtx x = simplify_binary_operation (code, GET_MODE_INNER (mode),
3688                                              CONST_VECTOR_ELT (op0, i),
3689                                              CONST_VECTOR_ELT (op1, i));
3690           if (!x)
3691             return 0;
3692           RTVEC_ELT (v, i) = x;
3693         }
3694
3695       return gen_rtx_CONST_VECTOR (mode, v);
3696     }
3697
3698   if (VECTOR_MODE_P (mode)
3699       && code == VEC_CONCAT
3700       && (CONST_SCALAR_INT_P (op0)
3701           || GET_CODE (op0) == CONST_FIXED
3702           || CONST_DOUBLE_AS_FLOAT_P (op0))
3703       && (CONST_SCALAR_INT_P (op1)
3704           || CONST_DOUBLE_AS_FLOAT_P (op1)
3705           || GET_CODE (op1) == CONST_FIXED))
3706     {
3707       unsigned n_elts = GET_MODE_NUNITS (mode);
3708       rtvec v = rtvec_alloc (n_elts);
3709
3710       gcc_assert (n_elts >= 2);
3711       if (n_elts == 2)
3712         {
3713           gcc_assert (GET_CODE (op0) != CONST_VECTOR);
3714           gcc_assert (GET_CODE (op1) != CONST_VECTOR);
3715
3716           RTVEC_ELT (v, 0) = op0;