Updated header
[libfirm] / ir / ir / iropt.c
1 /*
2  * Copyright (C) 1995-2007 University of Karlsruhe.  All right reserved.
3  *
4  * This file is part of libFirm.
5  *
6  * This file may be distributed and/or modified under the terms of the
7  * GNU General Public License version 2 as published by the Free Software
8  * Foundation and appearing in the file LICENSE.GPL included in the
9  * packaging of this file.
10  *
11  * Licensees holding valid libFirm Professional Edition licenses may use
12  * this file in accordance with the libFirm Commercial License.
13  * Agreement provided with the Software.
14  *
15  * This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
16  * WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
17  * PURPOSE.
18  */
19
20 /*
21  * Project:     libFIRM
22  * File name:   ir/ir/iropt.c
23  * Purpose:     iropt --- optimizations intertwined with IR construction.
24  * Author:      Christian Schaefer
25  * Modified by: Goetz Lindenmaier, Michael Beck
26  * Created:
27  * CVS-ID:      $Id$
28  * Copyright:   (c) 1998-2006 Universität Karlsruhe
29  */
30
31 #ifdef HAVE_CONFIG_H
32 # include "config.h"
33 #endif
34
35 #ifdef HAVE_STRING_H
36 #include <string.h>
37 #endif
38
39 #include "irnode_t.h"
40 #include "irgraph_t.h"
41 #include "iredges_t.h"
42 #include "irmode_t.h"
43 #include "iropt_t.h"
44 #include "ircons_t.h"
45 #include "irgmod.h"
46 #include "irvrfy.h"
47 #include "tv_t.h"
48 #include "dbginfo_t.h"
49 #include "iropt_dbg.h"
50 #include "irflag_t.h"
51 #include "irhooks.h"
52 #include "irarch.h"
53 #include "hashptr.h"
54 #include "archop.h"
55 #include "opt_polymorphy.h"
56 #include "opt_confirms.h"
57 #include "irtools.h"
58 #include "xmalloc.h"
59
60 /* Make types visible to allow most efficient access */
61 #include "entity_t.h"
62
63 /**
64  * Return the value of a Constant.
65  */
66 static tarval *computed_value_Const(ir_node *n) {
67         return get_Const_tarval(n);
68 }  /* computed_value_Const */
69
70 /**
71  * Return the value of a 'sizeof', 'alignof' or 'offsetof' SymConst.
72  */
73 static tarval *computed_value_SymConst(ir_node *n) {
74         ir_type   *type;
75         ir_entity *ent;
76
77         switch (get_SymConst_kind(n)) {
78         case symconst_type_size:
79                 type = get_SymConst_type(n);
80                 if (get_type_state(type) == layout_fixed)
81                         return new_tarval_from_long(get_type_size_bytes(type), get_irn_mode(n));
82                 break;
83         case symconst_type_align:
84                 type = get_SymConst_type(n);
85                 if (get_type_state(type) == layout_fixed)
86                         return new_tarval_from_long(get_type_alignment_bytes(type), get_irn_mode(n));
87                 break;
88         case symconst_ofs_ent:
89                 ent  = get_SymConst_entity(n);
90                 type = get_entity_owner(ent);
91                 if (get_type_state(type) == layout_fixed)
92                         return new_tarval_from_long(get_entity_offset(ent), get_irn_mode(n));
93                 break;
94         default:
95                 break;
96         }
97         return tarval_bad;
98 }  /* computed_value_SymConst */
99
100 /**
101  * Return the value of an Add.
102  */
103 static tarval *computed_value_Add(ir_node *n) {
104         ir_node *a = get_Add_left(n);
105         ir_node *b = get_Add_right(n);
106
107         tarval *ta = value_of(a);
108         tarval *tb = value_of(b);
109
110         if ((ta != tarval_bad) && (tb != tarval_bad) && (get_irn_mode(a) == get_irn_mode(b)))
111                 return tarval_add(ta, tb);
112
113         return tarval_bad;
114 }  /* computed_value_Add */
115
116 /**
117  * Return the value of a Sub.
118  * Special case: a - a
119  */
120 static tarval *computed_value_Sub(ir_node *n) {
121         ir_node *a = get_Sub_left(n);
122         ir_node *b = get_Sub_right(n);
123         tarval *ta;
124         tarval *tb;
125
126         /* a - a */
127         if (a == b && !is_Bad(a))
128                 return get_mode_null(get_irn_mode(n));
129
130         ta = value_of(a);
131         tb = value_of(b);
132
133         if ((ta != tarval_bad) && (tb != tarval_bad) && (get_irn_mode(a) == get_irn_mode(b)))
134                 return tarval_sub(ta, tb);
135
136         return tarval_bad;
137 }  /* computed_value_Sub */
138
139 /**
140  * Return the value of a Carry.
141  * Special : a op 0, 0 op b
142  */
143 static tarval *computed_value_Carry(ir_node *n) {
144         ir_node *a = get_binop_left(n);
145         ir_node *b = get_binop_right(n);
146         ir_mode *m = get_irn_mode(n);
147
148         tarval *ta = value_of(a);
149         tarval *tb = value_of(b);
150
151         if ((ta != tarval_bad) && (tb != tarval_bad)) {
152                 tarval_add(ta, tb);
153                 return tarval_carry() ? get_mode_one(m) : get_mode_null(m);
154         } else {
155                 if (   (classify_tarval(ta) == TV_CLASSIFY_NULL)
156                         || (classify_tarval(tb) == TV_CLASSIFY_NULL))
157                         return get_mode_null(m);
158         }
159         return tarval_bad;
160 }  /* computed_value_Carry */
161
162 /**
163  * Return the value of a Borrow.
164  * Special : a op 0
165  */
166 static tarval *computed_value_Borrow(ir_node *n) {
167         ir_node *a = get_binop_left(n);
168         ir_node *b = get_binop_right(n);
169         ir_mode *m = get_irn_mode(n);
170
171         tarval *ta = value_of(a);
172         tarval *tb = value_of(b);
173
174         if ((ta != tarval_bad) && (tb != tarval_bad)) {
175                 return tarval_cmp(ta, tb) == pn_Cmp_Lt ? get_mode_one(m) : get_mode_null(m);
176         } else if (classify_tarval(ta) == TV_CLASSIFY_NULL) {
177                 return get_mode_null(m);
178         }
179         return tarval_bad;
180 }  /* computed_value_Borrow */
181
182 /**
183  * Return the value of an unary Minus.
184  */
185 static tarval *computed_value_Minus(ir_node *n) {
186         ir_node *a = get_Minus_op(n);
187         tarval *ta = value_of(a);
188
189         if ((ta != tarval_bad) && mode_is_signed(get_irn_mode(a)))
190                 return tarval_neg(ta);
191
192         return tarval_bad;
193 }  /* computed_value_Minus */
194
195 /**
196  * Return the value of a Mul.
197  */
198 static tarval *computed_value_Mul(ir_node *n) {
199         ir_node *a = get_Mul_left(n);
200         ir_node *b = get_Mul_right(n);
201
202         tarval *ta = value_of(a);
203         tarval *tb = value_of(b);
204
205         if ((ta != tarval_bad) && (tb != tarval_bad) && (get_irn_mode(a) == get_irn_mode(b))) {
206                 return tarval_mul(ta, tb);
207         } else {
208         /* a*0 = 0 or 0*b = 0:
209            calls computed_value recursive and returns the 0 with proper
210            mode. */
211                 if ((ta != tarval_bad) && (ta == get_mode_null(get_tarval_mode(ta))))
212                         return ta;
213                 if ((tb != tarval_bad) && (tb == get_mode_null(get_tarval_mode(tb))))
214                         return tb;
215         }
216         return tarval_bad;
217 }  /* computed_value_Mul */
218
219 /**
220  * Return the value of a floating point Quot.
221  */
222 static tarval *computed_value_Quot(ir_node *n) {
223         ir_node *a = get_Quot_left(n);
224         ir_node *b = get_Quot_right(n);
225
226         tarval *ta = value_of(a);
227         tarval *tb = value_of(b);
228
229         /* This was missing in original implementation. Why? */
230         if ((ta != tarval_bad) && (tb != tarval_bad) && (get_irn_mode(a) == get_irn_mode(b))) {
231                 if (tb != get_mode_null(get_tarval_mode(tb)))   /* div by zero: return tarval_bad */
232                         return tarval_quo(ta, tb);
233         }
234         return tarval_bad;
235 }  /* computed_value_Quot */
236
237 /**
238  * Calculate the value of an integer Div of two nodes.
239  * Special case: 0 / b
240  */
241 static tarval *do_computed_value_Div(ir_node *a, ir_node *b) {
242         tarval *ta = value_of(a);
243         tarval *tb = value_of(b);
244
245         /* Compute c1 / c2 or 0 / a, a != 0 */
246         if (ta != tarval_bad) {
247                 if ((tb != tarval_bad) && (tb != get_mode_null(get_irn_mode(b))))   /* div by zero: return tarval_bad */
248                         return tarval_div(ta, tb);
249                 else if (ta == get_mode_null(get_tarval_mode(ta)))  /* 0 / b == 0 */
250                         return ta;
251         }
252         return tarval_bad;
253 }  /* do_computed_value_Div */
254
255 /**
256  * Return the value of an integer Div.
257  */
258 static tarval *computed_value_Div(ir_node *n) {
259         return do_computed_value_Div(get_Div_left(n), get_Div_right(n));
260 }  /* computed_value_Div */
261
262 /**
263  * Calculate the value of an integer Mod of two nodes.
264  * Special case: a % 1
265  */
266 static tarval *do_computed_value_Mod(ir_node *a, ir_node *b) {
267         tarval *ta = value_of(a);
268         tarval *tb = value_of(b);
269
270         /* Compute c1 % c2 or a % 1 */
271         if (tb != tarval_bad) {
272                 if ((ta != tarval_bad) && (tb != get_mode_null(get_tarval_mode(tb))))   /* div by zero: return tarval_bad */
273                         return tarval_mod(ta, tb);
274                 else if (tb == get_mode_one(get_tarval_mode(tb)))    /* x mod 1 == 0 */
275                         return get_mode_null(get_irn_mode(a));
276         }
277         return tarval_bad;
278 }  /* do_computed_value_Mod */
279
280 /**
281  * Return the value of an integer Mod.
282  */
283 static tarval *computed_value_Mod(ir_node *n) {
284         return do_computed_value_Mod(get_Mod_left(n), get_Mod_right(n));
285 }  /* computed_value_Mod */
286
287 /**
288  * Return the value of an Abs.
289  */
290 static tarval *computed_value_Abs(ir_node *n) {
291         ir_node *a = get_Abs_op(n);
292         tarval *ta = value_of(a);
293
294         if (ta != tarval_bad)
295                 return tarval_abs(ta);
296
297         return tarval_bad;
298 }  /* computed_value_Abs */
299
300 /**
301  * Return the value of an And.
302  * Special case: a & 0, 0 & b
303  */
304 static tarval *computed_value_And(ir_node *n) {
305         ir_node *a = get_And_left(n);
306         ir_node *b = get_And_right(n);
307
308         tarval *ta = value_of(a);
309         tarval *tb = value_of(b);
310
311         if ((ta != tarval_bad) && (tb != tarval_bad)) {
312                 return tarval_and (ta, tb);
313         } else {
314                 tarval *v;
315
316                 if (   (classify_tarval ((v = ta)) == TV_CLASSIFY_NULL)
317                         || (classify_tarval ((v = tb)) == TV_CLASSIFY_NULL)) {
318                         return v;
319                 }
320         }
321         return tarval_bad;
322 }  /* computed_value_And */
323
324 /**
325  * Return the value of an Or.
326  * Special case: a | 1...1, 1...1 | b
327  */
328 static tarval *computed_value_Or(ir_node *n) {
329         ir_node *a = get_Or_left(n);
330         ir_node *b = get_Or_right(n);
331
332         tarval *ta = value_of(a);
333         tarval *tb = value_of(b);
334
335         if ((ta != tarval_bad) && (tb != tarval_bad)) {
336                 return tarval_or (ta, tb);
337         } else {
338                 tarval *v;
339                 if (   (classify_tarval ((v = ta)) == TV_CLASSIFY_ALL_ONE)
340                         || (classify_tarval ((v = tb)) == TV_CLASSIFY_ALL_ONE)) {
341                         return v;
342                 }
343         }
344         return tarval_bad;
345 }  /* computed_value_Or */
346
347 /**
348  * Return the value of an Eor.
349  */
350 static tarval *computed_value_Eor(ir_node *n) {
351         ir_node *a = get_Eor_left(n);
352         ir_node *b = get_Eor_right(n);
353
354         tarval *ta, *tb;
355
356         if (a == b)
357                 return get_mode_null(get_irn_mode(n));
358
359         ta = value_of(a);
360         tb = value_of(b);
361
362         if ((ta != tarval_bad) && (tb != tarval_bad)) {
363                 return tarval_eor (ta, tb);
364         }
365         return tarval_bad;
366 }  /* computed_value_Eor */
367
368 /**
369  * Return the value of a Not.
370  */
371 static tarval *computed_value_Not(ir_node *n) {
372         ir_node *a = get_Not_op(n);
373         tarval *ta = value_of(a);
374
375         if (ta != tarval_bad)
376                 return tarval_not(ta);
377
378         return tarval_bad;
379 }  /* computed_value_Not */
380
381 /**
382  * Return the value of a Shl.
383  */
384 static tarval *computed_value_Shl(ir_node *n) {
385         ir_node *a = get_Shl_left(n);
386         ir_node *b = get_Shl_right(n);
387
388         tarval *ta = value_of(a);
389         tarval *tb = value_of(b);
390
391         if ((ta != tarval_bad) && (tb != tarval_bad)) {
392                 return tarval_shl (ta, tb);
393         }
394         return tarval_bad;
395 }  /* computed_value_Shl */
396
397 /**
398  * Return the value of a Shr.
399  */
400 static tarval *computed_value_Shr(ir_node *n) {
401         ir_node *a = get_Shr_left(n);
402         ir_node *b = get_Shr_right(n);
403
404         tarval *ta = value_of(a);
405         tarval *tb = value_of(b);
406
407         if ((ta != tarval_bad) && (tb != tarval_bad)) {
408                 return tarval_shr (ta, tb);
409         }
410         return tarval_bad;
411 }  /* computed_value_Shr */
412
413 /**
414  * Return the value of a Shrs.
415  */
416 static tarval *computed_value_Shrs(ir_node *n) {
417         ir_node *a = get_Shrs_left(n);
418         ir_node *b = get_Shrs_right(n);
419
420         tarval *ta = value_of(a);
421         tarval *tb = value_of(b);
422
423         if ((ta != tarval_bad) && (tb != tarval_bad)) {
424                 return tarval_shrs (ta, tb);
425         }
426         return tarval_bad;
427 }  /* computed_value_Shrs */
428
429 /**
430  * Return the value of a Rot.
431  */
432 static tarval *computed_value_Rot(ir_node *n) {
433         ir_node *a = get_Rot_left(n);
434         ir_node *b = get_Rot_right(n);
435
436         tarval *ta = value_of(a);
437         tarval *tb = value_of(b);
438
439         if ((ta != tarval_bad) && (tb != tarval_bad)) {
440                 return tarval_rot (ta, tb);
441         }
442         return tarval_bad;
443 }  /* computed_value_Rot */
444
445 /**
446  * Return the value of a Conv.
447  */
448 static tarval *computed_value_Conv(ir_node *n) {
449         ir_node *a = get_Conv_op(n);
450         tarval *ta = value_of(a);
451
452         if (ta != tarval_bad)
453                 return tarval_convert_to(ta, get_irn_mode(n));
454
455         return tarval_bad;
456 }  /* computed_value_Conv */
457
458 /**
459  * Return the value of a Proj(Cmp).
460  *
461  * This performs a first step of unreachable code elimination.
462  * Proj can not be computed, but folding a Cmp above the Proj here is
463  * not as wasteful as folding a Cmp into a Tuple of 16 Consts of which
464  * only 1 is used.
465  * There are several case where we can evaluate a Cmp node, see later.
466  */
467 static tarval *computed_value_Proj_Cmp(ir_node *n) {
468         ir_node *a   = get_Proj_pred(n);
469         ir_node *aa  = get_Cmp_left(a);
470         ir_node *ab  = get_Cmp_right(a);
471         long proj_nr = get_Proj_proj(n);
472
473         /*
474          * BEWARE: a == a is NOT always True for floating Point values, as
475          * NaN != NaN is defined, so we must check this here.
476          */
477         if (aa == ab && (
478                 !mode_is_float(get_irn_mode(aa)) || proj_nr == pn_Cmp_Lt ||  proj_nr == pn_Cmp_Gt)
479                 ) { /* 1.: */
480
481                 /* This is a trick with the bits used for encoding the Cmp
482                    Proj numbers, the following statement is not the same:
483                 return new_tarval_from_long (proj_nr == pn_Cmp_Eq, mode_b) */
484                 return new_tarval_from_long (proj_nr & pn_Cmp_Eq, mode_b);
485         }
486         else {
487                 tarval *taa = value_of(aa);
488                 tarval *tab = value_of(ab);
489                 ir_mode *mode = get_irn_mode(aa);
490
491                 /*
492                  * The predecessors of Cmp are target values.  We can evaluate
493                  * the Cmp.
494                  */
495                 if ((taa != tarval_bad) && (tab != tarval_bad)) {
496                         /* strange checks... */
497                         pn_Cmp flags = tarval_cmp(taa, tab);
498                         if (flags != pn_Cmp_False) {
499                                 return new_tarval_from_long (proj_nr & flags, mode_b);
500                         }
501                 }
502                 /* for integer values, we can check against MIN/MAX */
503                 else if (mode_is_int(mode)) {
504                         /* MIN <=/> x.  This results in true/false. */
505                         if (taa == get_mode_min(mode)) {
506                                 /* a compare with the MIN value */
507                                 if (proj_nr == pn_Cmp_Le)
508                                         return get_tarval_b_true();
509                                 else if (proj_nr == pn_Cmp_Gt)
510                                         return get_tarval_b_false();
511                         }
512                         /* x >=/< MIN.  This results in true/false. */
513                         else
514                                 if (tab == get_mode_min(mode)) {
515                                         /* a compare with the MIN value */
516                                         if (proj_nr == pn_Cmp_Ge)
517                                                 return get_tarval_b_true();
518                                         else if (proj_nr == pn_Cmp_Lt)
519                                                 return get_tarval_b_false();
520                                 }
521                                 /* MAX >=/< x.  This results in true/false. */
522                                 else if (taa == get_mode_max(mode)) {
523                                         if (proj_nr == pn_Cmp_Ge)
524                                                 return get_tarval_b_true();
525                                         else if (proj_nr == pn_Cmp_Lt)
526                                                 return get_tarval_b_false();
527                                 }
528                                 /* x <=/> MAX.  This results in true/false. */
529                                 else if (tab == get_mode_max(mode)) {
530                                         if (proj_nr == pn_Cmp_Le)
531                                                 return get_tarval_b_true();
532                                         else if (proj_nr == pn_Cmp_Gt)
533                                                 return get_tarval_b_false();
534                                 }
535                 }
536                 /*
537                  * The predecessors are Allocs or (void*)(0) constants.  Allocs never
538                  * return NULL, they raise an exception.   Therefore we can predict
539                  * the Cmp result.
540                  */
541                 else {
542                         ir_node *aaa = skip_Id(skip_Proj(aa));
543                         ir_node *aba = skip_Id(skip_Proj(ab));
544
545                         if (   (   (/* aa is ProjP and aaa is Alloc */
546                                        (get_irn_op(aa) == op_Proj)
547                                     && (mode_is_reference(get_irn_mode(aa)))
548                                     && (get_irn_op(aaa) == op_Alloc))
549                                 && (   (/* ab is NULL */
550                                            (get_irn_op(ab) == op_Const)
551                                         && (mode_is_reference(get_irn_mode(ab)))
552                                         && (get_Const_tarval(ab) == get_mode_null(get_irn_mode(ab))))
553                                     || (/* ab is other Alloc */
554                                            (get_irn_op(ab) == op_Proj)
555                                         && (mode_is_reference(get_irn_mode(ab)))
556                                         && (get_irn_op(aba) == op_Alloc)
557                                         && (aaa != aba))))
558                             || (/* aa is NULL and aba is Alloc */
559                                    (get_irn_op(aa) == op_Const)
560                                 && (mode_is_reference(get_irn_mode(aa)))
561                                 && (get_Const_tarval(aa) == get_mode_null(get_irn_mode(aa)))
562                                 && (get_irn_op(ab) == op_Proj)
563                                 && (mode_is_reference(get_irn_mode(ab)))
564                                 && (get_irn_op(aba) == op_Alloc)))
565                                 /* 3.: */
566                         return new_tarval_from_long(proj_nr & pn_Cmp_Ne, mode_b);
567                 }
568         }
569         return computed_value_Cmp_Confirm(a, aa, ab, proj_nr);
570 }  /* computed_value_Proj_Cmp */
571
572 /**
573  * Return the value of a Proj, handle Proj(Cmp), Proj(Div), Proj(Mod),
574  * Proj(DivMod) and Proj(Quot).
575  */
576 static tarval *computed_value_Proj(ir_node *n) {
577         ir_node *a = get_Proj_pred(n);
578         long proj_nr;
579
580         switch (get_irn_opcode(a)) {
581         case iro_Cmp:
582                 return computed_value_Proj_Cmp(n);
583
584         case iro_DivMod:
585                 /* compute either the Div or the Mod part */
586                 proj_nr = get_Proj_proj(n);
587                 if (proj_nr == pn_DivMod_res_div)
588                         return do_computed_value_Div(get_DivMod_left(a), get_DivMod_right(a));
589                 else if (proj_nr == pn_DivMod_res_mod)
590                         return do_computed_value_Mod(get_DivMod_left(a), get_DivMod_right(a));
591                 break;
592
593         case iro_Div:
594                 if (get_Proj_proj(n) == pn_Div_res)
595                         return computed_value(a);
596                 break;
597
598         case iro_Mod:
599                 if (get_Proj_proj(n) == pn_Mod_res)
600                         return computed_value(a);
601                 break;
602
603         case iro_Quot:
604                 if (get_Proj_proj(n) == pn_Quot_res)
605                         return computed_value(a);
606                 break;
607
608         default:
609                 return tarval_bad;
610         }
611         return tarval_bad;
612 }  /* computed_value_Proj */
613
614 /**
615  * Calculate the value of a Mux: can be evaluated, if the
616  * sel and the right input are known.
617  */
618 static tarval *computed_value_Mux(ir_node *n) {
619         ir_node *sel = get_Mux_sel(n);
620         tarval *ts = value_of(sel);
621
622         if (ts == get_tarval_b_true()) {
623                 ir_node *v = get_Mux_true(n);
624                 return value_of(v);
625         }
626         else if (ts == get_tarval_b_false()) {
627                 ir_node *v = get_Mux_false(n);
628                 return value_of(v);
629         }
630         return tarval_bad;
631 }  /* computed_value_Mux */
632
633 /**
634  * Calculate the value of a Psi: can be evaluated, if a condition is true
635  * and all previous conditions are false. If all conditions are false
636  * we evaluate to the default one.
637  */
638 static tarval *computed_value_Psi(ir_node *n) {
639         if (is_Mux(n))
640                 return computed_value_Mux(n);
641         return tarval_bad;
642 }  /* computed_value_Psi */
643
644 /**
645  * Calculate the value of a Confirm: can be evaluated,
646  * if it has the form Confirm(x, '=', Const).
647  */
648 static tarval *computed_value_Confirm(ir_node *n) {
649         return get_Confirm_cmp(n) == pn_Cmp_Eq ?
650                 value_of(get_Confirm_bound(n)) : tarval_bad;
651 }  /* computed_value_Confirm */
652
653 /**
654  * If the parameter n can be computed, return its value, else tarval_bad.
655  * Performs constant folding.
656  *
657  * @param n  The node this should be evaluated
658  */
659 tarval *computed_value(ir_node *n) {
660         if (n->op->ops.computed_value)
661                 return n->op->ops.computed_value(n);
662         return tarval_bad;
663 }  /* computed_value */
664
665 /**
666  * Set the default computed_value evaluator in an ir_op_ops.
667  *
668  * @param code   the opcode for the default operation
669  * @param ops    the operations initialized
670  *
671  * @return
672  *    The operations.
673  */
674 static ir_op_ops *firm_set_default_computed_value(ir_opcode code, ir_op_ops *ops)
675 {
676 #define CASE(a)                                    \
677         case iro_##a:                                  \
678                 ops->computed_value  = computed_value_##a; \
679                 break
680
681         switch (code) {
682         CASE(Const);
683         CASE(SymConst);
684         CASE(Add);
685         CASE(Sub);
686         CASE(Minus);
687         CASE(Mul);
688         CASE(Quot);
689         CASE(Div);
690         CASE(Mod);
691         CASE(Abs);
692         CASE(And);
693         CASE(Or);
694         CASE(Eor);
695         CASE(Not);
696         CASE(Shl);
697         CASE(Shr);
698         CASE(Shrs);
699         CASE(Rot);
700         CASE(Carry);
701         CASE(Borrow);
702         CASE(Conv);
703         CASE(Proj);
704         CASE(Mux);
705         CASE(Psi);
706         CASE(Confirm);
707         default:
708                 /* leave NULL */;
709         }
710
711         return ops;
712 #undef CASE
713 }  /* firm_set_default_computed_value */
714
715 /**
716  * Returns a equivalent block for another block.
717  * If the block has only one predecessor, this is
718  * the equivalent one. If the only predecessor of a block is
719  * the block itself, this is a dead block.
720  *
721  * If both predecessors of a block are the branches of a binary
722  * Cond, the equivalent block is Cond's block.
723  *
724  * If all predecessors of a block are bad or lies in a dead
725  * block, the current block is dead as well.
726  *
727  * Note, that blocks are NEVER turned into Bad's, instead
728  * the dead_block flag is set. So, never test for is_Bad(block),
729  * always use is_dead_Block(block).
730  */
731 static ir_node *equivalent_node_Block(ir_node *n)
732 {
733         ir_node *oldn = n;
734         int n_preds   = get_Block_n_cfgpreds(n);
735
736         /* The Block constructor does not call optimize, but mature_immBlock
737         calls the optimization. */
738         assert(get_Block_matured(n));
739
740         /* Straightening: a single entry Block following a single exit Block
741            can be merged, if it is not the Start block. */
742         /* !!! Beware, all Phi-nodes of n must have been optimized away.
743            This should be true, as the block is matured before optimize is called.
744            But what about Phi-cycles with the Phi0/Id that could not be resolved?
745            Remaining Phi nodes are just Ids. */
746         if ((n_preds == 1) && (get_irn_op(get_Block_cfgpred(n, 0)) == op_Jmp)) {
747                 ir_node *predblock = get_nodes_block(get_Block_cfgpred(n, 0));
748                 if (predblock == oldn) {
749                         /* Jmp jumps into the block it is in -- deal self cycle. */
750                         n = set_Block_dead(n);
751                         DBG_OPT_DEAD_BLOCK(oldn, n);
752                 } else if (get_opt_control_flow_straightening()) {
753                         n = predblock;
754                         DBG_OPT_STG(oldn, n);
755                 }
756         } else if ((n_preds == 1) &&
757                    (get_irn_op(skip_Proj(get_Block_cfgpred(n, 0))) == op_Cond)) {
758                 ir_node *predblock = get_Block_cfgpred_block(n, 0);
759                 if (predblock == oldn) {
760                         /* Jmp jumps into the block it is in -- deal self cycle. */
761                         n = set_Block_dead(n);
762                         DBG_OPT_DEAD_BLOCK(oldn, n);
763                 }
764         } else if ((n_preds == 2) &&
765                    (get_opt_control_flow_weak_simplification())) {
766                 /* Test whether Cond jumps twice to this block
767                  * The more general case which more than 2 predecessors is handles
768                  * in optimize_cf(), we handle only this special case for speed here.
769                  */
770                 ir_node *a = get_Block_cfgpred(n, 0);
771                 ir_node *b = get_Block_cfgpred(n, 1);
772
773                 if ((get_irn_op(a) == op_Proj) &&
774                     (get_irn_op(b) == op_Proj) &&
775                     (get_Proj_pred(a) == get_Proj_pred(b)) &&
776                     (get_irn_op(get_Proj_pred(a)) == op_Cond) &&
777                     (get_irn_mode(get_Cond_selector(get_Proj_pred(a))) == mode_b)) {
778                         /* Also a single entry Block following a single exit Block.  Phis have
779                            twice the same operand and will be optimized away. */
780                         n = get_nodes_block(get_Proj_pred(a));
781                         DBG_OPT_IFSIM1(oldn, a, b, n);
782                 }
783         } else if (get_opt_unreachable_code() &&
784                    (n != get_irg_start_block(current_ir_graph)) &&
785                    (n != get_irg_end_block(current_ir_graph))    ) {
786                 int i;
787
788                 /* If all inputs are dead, this block is dead too, except if it is
789                    the start or end block.  This is one step of unreachable code
790                    elimination */
791                 for (i = get_Block_n_cfgpreds(n) - 1; i >= 0; --i) {
792                         ir_node *pred = get_Block_cfgpred(n, i);
793                         ir_node *pred_blk;
794
795                         if (is_Bad(pred)) continue;
796                         pred_blk = get_nodes_block(skip_Proj(pred));
797
798                         if (is_Block_dead(pred_blk)) continue;
799
800                         if (pred_blk != n) {
801                                 /* really found a living input */
802                                 break;
803                         }
804                 }
805                 if (i < 0) {
806                         n = set_Block_dead(n);
807                         DBG_OPT_DEAD_BLOCK(oldn, n);
808                 }
809         }
810
811         return n;
812 }  /* equivalent_node_Block */
813
814 /**
815  * Returns a equivalent node for a Jmp, a Bad :-)
816  * Of course this only happens if the Block of the Jmp is dead.
817  */
818 static ir_node *equivalent_node_Jmp(ir_node *n) {
819         /* unreachable code elimination */
820         if (is_Block_dead(get_nodes_block(n)))
821                 n = new_Bad();
822
823         return n;
824 }  /* equivalent_node_Jmp */
825
826 /** Raise is handled in the same way as Jmp. */
827 #define equivalent_node_Raise   equivalent_node_Jmp
828
829
830 /* We do not evaluate Cond here as we replace it by a new node, a Jmp.
831    See transform_node_Proj_Cond(). */
832
833 /**
834  * Optimize operations that are commutative and have neutral 0,
835  * so a op 0 = 0 op a = a.
836  */
837 static ir_node *equivalent_node_neutral_zero(ir_node *n)
838 {
839         ir_node *oldn = n;
840
841         ir_node *a = get_binop_left(n);
842         ir_node *b = get_binop_right(n);
843
844         tarval *tv;
845         ir_node *on;
846
847         /* After running compute_node there is only one constant predecessor.
848            Find this predecessors value and remember the other node: */
849         if ((tv = value_of(a)) != tarval_bad) {
850                 on = b;
851         } else if ((tv = value_of(b)) != tarval_bad) {
852                 on = a;
853         } else
854                 return n;
855
856         /* If this predecessors constant value is zero, the operation is
857          * unnecessary. Remove it.
858          *
859          * Beware: If n is a Add, the mode of on and n might be different
860          * which happens in this rare construction: NULL + 3.
861          * Then, a Conv would be needed which we cannot include here.
862          */
863         if (classify_tarval (tv) == TV_CLASSIFY_NULL) {
864                 if (get_irn_mode(on) == get_irn_mode(n)) {
865                         n = on;
866
867                         DBG_OPT_ALGSIM1(oldn, a, b, n, FS_OPT_NEUTRAL_0);
868                 }
869         }
870
871         return n;
872 }  /* equivalent_node_neutral_zero */
873
874 /**
875  * Eor is commutative and has neutral 0.
876  */
877 #define equivalent_node_Eor  equivalent_node_neutral_zero
878
879 /*
880  * Optimize a - 0 and (a - x) + x (for modes with wrap-around).
881  *
882  * The second one looks strange, but this construct
883  * is used heavily in the LCC sources :-).
884  *
885  * Beware: The Mode of an Add may be different than the mode of its
886  * predecessors, so we could not return a predecessors in all cases.
887  */
888 static ir_node *equivalent_node_Add(ir_node *n) {
889         ir_node *oldn = n;
890         ir_node *left, *right;
891         ir_mode *mode = get_irn_mode(n);
892
893         /* for FP these optimizations are only allowed if fp_strict_algebraic is disabled */
894         if (mode_is_float(mode) && (get_irg_fp_model(current_ir_graph) & fp_strict_algebraic))
895                 return n;
896
897         n = equivalent_node_neutral_zero(n);
898         if (n != oldn)
899                 return n;
900
901         left  = get_Add_left(n);
902         right = get_Add_right(n);
903
904         if (get_irn_op(left) == op_Sub) {
905                 if (get_Sub_right(left) == right) {
906                         /* (a - x) + x */
907
908                         n = get_Sub_left(left);
909                         if (mode == get_irn_mode(n)) {
910                                 DBG_OPT_ALGSIM1(oldn, left, right, n, FS_OPT_ADD_SUB);
911                                 return n;
912                         }
913                 }
914         }
915         if (get_irn_op(right) == op_Sub) {
916                 if (get_Sub_right(right) == left) {
917                         /* x + (a - x) */
918
919                         n = get_Sub_left(right);
920                         if (mode == get_irn_mode(n)) {
921                                 DBG_OPT_ALGSIM1(oldn, left, right, n, FS_OPT_ADD_SUB);
922                                 return n;
923                         }
924                 }
925         }
926         return n;
927 }  /* equivalent_node_Add */
928
929 /**
930  * optimize operations that are not commutative but have neutral 0 on left,
931  * so a op 0 = a.
932  */
933 static ir_node *equivalent_node_left_zero(ir_node *n) {
934         ir_node *oldn = n;
935
936         ir_node *a = get_binop_left(n);
937         ir_node *b = get_binop_right(n);
938
939         if (classify_tarval(value_of(b)) == TV_CLASSIFY_NULL) {
940                 n = a;
941
942                 DBG_OPT_ALGSIM1(oldn, a, b, n, FS_OPT_NEUTRAL_0);
943         }
944         return n;
945 }  /* equivalent_node_left_zero */
946
947 #define equivalent_node_Shl   equivalent_node_left_zero
948 #define equivalent_node_Shr   equivalent_node_left_zero
949 #define equivalent_node_Shrs  equivalent_node_left_zero
950 #define equivalent_node_Rot   equivalent_node_left_zero
951
952 /**
953  * Optimize a - 0 and (a + x) - x (for modes with wrap-around).
954  *
955  * The second one looks strange, but this construct
956  * is used heavily in the LCC sources :-).
957  *
958  * Beware: The Mode of a Sub may be different than the mode of its
959  * predecessors, so we could not return a predecessors in all cases.
960  */
961 static ir_node *equivalent_node_Sub(ir_node *n) {
962         ir_node *oldn = n;
963         ir_node *a, *b;
964         ir_mode *mode = get_irn_mode(n);
965
966         /* for FP these optimizations are only allowed if fp_strict_algebraic is disabled */
967         if (mode_is_float(mode) && (get_irg_fp_model(current_ir_graph) & fp_strict_algebraic))
968                 return n;
969
970         a = get_Sub_left(n);
971         b = get_Sub_right(n);
972
973         /* Beware: modes might be different */
974         if (classify_tarval(value_of(b)) == TV_CLASSIFY_NULL) {
975                 if (mode == get_irn_mode(a)) {
976                         n = a;
977
978                         DBG_OPT_ALGSIM1(oldn, a, b, n, FS_OPT_NEUTRAL_0);
979                 }
980         } else if (get_irn_op(a) == op_Add) {
981                 if (mode_wrap_around(mode)) {
982                         ir_node *left  = get_Add_left(a);
983                         ir_node *right = get_Add_right(a);
984
985                         if (left == b) {
986                                 if (mode == get_irn_mode(right)) {
987                                         n = right;
988                                         DBG_OPT_ALGSIM1(oldn, a, b, n, FS_OPT_ADD_SUB);
989                                 }
990                         } else if (right == b) {
991                                 if (mode == get_irn_mode(left)) {
992                                         n = left;
993                                         DBG_OPT_ALGSIM1(oldn, a, b, n, FS_OPT_ADD_SUB);
994                                 }
995                         }
996                 }
997         }
998         return n;
999 }  /* equivalent_node_Sub */
1000
1001
1002 /**
1003  * Optimize an "idempotent unary op", ie op(op(n)) = n.
1004  *
1005  * @todo
1006  *   -(-a) == a, but might overflow two times.
1007  *   We handle it anyway here but the better way would be a
1008  *   flag. This would be needed for Pascal for instance.
1009  */
1010 static ir_node *equivalent_node_idempotent_unop(ir_node *n) {
1011         ir_node *oldn = n;
1012         ir_node *pred = get_unop_op(n);
1013
1014         /* optimize symmetric unop */
1015         if (get_irn_op(pred) == get_irn_op(n)) {
1016                 n = get_unop_op(pred);
1017                 DBG_OPT_ALGSIM2(oldn, pred, n);
1018         }
1019         return n;
1020 }  /* equivalent_node_idempotent_unop */
1021
1022 /** Optimize Not(Not(x)) == x. */
1023 #define equivalent_node_Not    equivalent_node_idempotent_unop
1024
1025 /** --x == x       ??? Is this possible or can --x raise an
1026                        out of bounds exception if min =! max? */
1027 #define equivalent_node_Minus  equivalent_node_idempotent_unop
1028
1029 /**
1030  * Optimize a * 1 = 1 * a = a.
1031  */
1032 static ir_node *equivalent_node_Mul(ir_node *n) {
1033         ir_node *oldn = n;
1034         ir_node *a = get_Mul_left(n);
1035         ir_node *b = get_Mul_right(n);
1036
1037         /* Mul is commutative and has again an other neutral element. */
1038         if (classify_tarval(value_of(a)) == TV_CLASSIFY_ONE) {
1039                 n = b;
1040                 DBG_OPT_ALGSIM1(oldn, a, b, n, FS_OPT_NEUTRAL_1);
1041         } else if (classify_tarval(value_of(b)) == TV_CLASSIFY_ONE) {
1042                 n = a;
1043                 DBG_OPT_ALGSIM1(oldn, a, b, n, FS_OPT_NEUTRAL_1);
1044         }
1045         return n;
1046 }  /* equivalent_node_Mul */
1047
1048 /**
1049  * Optimize a / 1 = a.
1050  */
1051 static ir_node *equivalent_node_Div(ir_node *n) {
1052         ir_node *a = get_Div_left(n);
1053         ir_node *b = get_Div_right(n);
1054
1055         /* Div is not commutative. */
1056         if (classify_tarval(value_of(b)) == TV_CLASSIFY_ONE) { /* div(x, 1) == x */
1057                 /* Turn Div into a tuple (mem, bad, a) */
1058                 ir_node *mem = get_Div_mem(n);
1059                 turn_into_tuple(n, pn_Div_max);
1060                 set_Tuple_pred(n, pn_Div_M,        mem);
1061                 set_Tuple_pred(n, pn_Div_X_except, new_Bad());        /* no exception */
1062                 set_Tuple_pred(n, pn_Div_res,      a);
1063         }
1064         return n;
1065 }  /* equivalent_node_Div */
1066
1067 /**
1068  * Optimize a / 1.0 = a.
1069  */
1070 static ir_node *equivalent_node_Quot(ir_node *n) {
1071         ir_node *a = get_Quot_left(n);
1072         ir_node *b = get_Quot_right(n);
1073
1074         /* Div is not commutative. */
1075         if (classify_tarval(value_of(b)) == TV_CLASSIFY_ONE) { /* Quot(x, 1) == x */
1076                 /* Turn Quot into a tuple (mem, bad, a) */
1077                 ir_node *mem = get_Quot_mem(n);
1078                 turn_into_tuple(n, pn_Quot_max);
1079                 set_Tuple_pred(n, pn_Quot_M,        mem);
1080                 set_Tuple_pred(n, pn_Quot_X_except, new_Bad());        /* no exception */
1081                 set_Tuple_pred(n, pn_Quot_res,      a);
1082         }
1083         return n;
1084 }  /* equivalent_node_Quot */
1085
1086 /**
1087  * Optimize a / 1 = a.
1088  */
1089 static ir_node *equivalent_node_DivMod(ir_node *n) {
1090         ir_node *a = get_DivMod_left(n);
1091         ir_node *b = get_DivMod_right(n);
1092
1093         /* Div is not commutative. */
1094         if (classify_tarval(value_of(b)) == TV_CLASSIFY_ONE) { /* div(x, 1) == x */
1095                 /* Turn DivMod into a tuple (mem, bad, a, 0) */
1096                 ir_node *mem = get_Div_mem(n);
1097                 ir_mode *mode = get_irn_mode(b);
1098
1099                 turn_into_tuple(n, pn_DivMod_max);
1100                 set_Tuple_pred(n, pn_DivMod_M,        mem);
1101                 set_Tuple_pred(n, pn_DivMod_X_except, new_Bad());        /* no exception */
1102                 set_Tuple_pred(n, pn_DivMod_res_div,  a);
1103                 set_Tuple_pred(n, pn_DivMod_res_mod,  new_Const(mode, get_mode_null(mode)));
1104         }
1105         return n;
1106 }  /* equivalent_node_DivMod */
1107
1108 /**
1109  * Use algebraic simplification a | a = a | 0 = 0 | a = a.
1110  */
1111 static ir_node *equivalent_node_Or(ir_node *n) {
1112         ir_node *oldn = n;
1113
1114         ir_node *a = get_Or_left(n);
1115         ir_node *b = get_Or_right(n);
1116
1117         if (a == b) {
1118                 n = a;    /* Or has it's own neutral element */
1119                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_OR);
1120         } else if (classify_tarval(value_of(a)) == TV_CLASSIFY_NULL) {
1121                 n = b;
1122                 DBG_OPT_ALGSIM1(oldn, a, b, n, FS_OPT_OR);
1123         } else if (classify_tarval(value_of(b)) == TV_CLASSIFY_NULL) {
1124                 n = a;
1125                 DBG_OPT_ALGSIM1(oldn, a, b, n, FS_OPT_OR);
1126         }
1127
1128         return n;
1129 }  /* equivalent_node_Or */
1130
1131 /**
1132  * Optimize a & 0b1...1 = 0b1...1 & a =  a & a = a.
1133  */
1134 static ir_node *equivalent_node_And(ir_node *n) {
1135         ir_node *oldn = n;
1136
1137         ir_node *a = get_And_left(n);
1138         ir_node *b = get_And_right(n);
1139
1140         if (a == b) {
1141                 n = a;    /* And has it's own neutral element */
1142                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_AND);
1143         } else if (classify_tarval(value_of(a)) == TV_CLASSIFY_ALL_ONE) {
1144                 n = b;
1145                 DBG_OPT_ALGSIM1(oldn, a, b, n, FS_OPT_AND);
1146         } else if (classify_tarval(value_of(b)) == TV_CLASSIFY_ALL_ONE) {
1147                 n = a;
1148                 DBG_OPT_ALGSIM1(oldn, a, b, n, FS_OPT_AND);
1149         }
1150         return n;
1151 }  /* equivalent_node_And */
1152
1153 /**
1154  * Try to remove useless Conv's:
1155  */
1156 static ir_node *equivalent_node_Conv(ir_node *n) {
1157         ir_node *oldn = n;
1158         ir_node *a = get_Conv_op(n);
1159         ir_node *b;
1160
1161         ir_mode *n_mode = get_irn_mode(n);
1162         ir_mode *a_mode = get_irn_mode(a);
1163
1164         if (n_mode == a_mode) { /* No Conv necessary */
1165                 /* leave strict floating point Conv's */
1166                 if (get_Conv_strict(n))
1167                         return n;
1168                 n = a;
1169                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_CONV);
1170         } else if (get_irn_op(a) == op_Conv) { /* Conv(Conv(b)) */
1171                 ir_mode *b_mode;
1172
1173                 b = get_Conv_op(a);
1174                 n_mode = get_irn_mode(n);
1175                 b_mode = get_irn_mode(b);
1176
1177                 if (n_mode == b_mode) {
1178                         if (n_mode == mode_b) {
1179                                 n = b; /* Convb(Conv*(xxxb(...))) == xxxb(...) */
1180                                 DBG_OPT_ALGSIM1(oldn, a, b, n, FS_OPT_CONV);
1181                         } else if (mode_is_int(n_mode) || mode_is_character(n_mode)) {
1182                                 if (smaller_mode(b_mode, a_mode)){
1183                                         n = b;        /* ConvS(ConvL(xxxS(...))) == xxxS(...) */
1184                                         DBG_OPT_ALGSIM1(oldn, a, b, n, FS_OPT_CONV);
1185                                 }
1186                         }
1187                 }
1188         }
1189         return n;
1190 }  /* equivalent_node_Conv */
1191
1192 /**
1193  * A Cast may be removed if the type of the previous node
1194  * is already the type of the Cast.
1195  */
1196 static ir_node *equivalent_node_Cast(ir_node *n) {
1197         ir_node *oldn = n;
1198         ir_node *pred = get_Cast_op(n);
1199
1200         if (get_irn_type(pred) == get_Cast_type(n)) {
1201                 n = pred;
1202                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_CAST);
1203         }
1204         return n;
1205 }  /* equivalent_node_Cast */
1206
1207 /**
1208  * Several optimizations:
1209  * - no Phi in start block.
1210  * - remove Id operators that are inputs to Phi
1211  * - fold Phi-nodes, iff they have only one predecessor except
1212  *   themselves.
1213  */
1214 static ir_node *equivalent_node_Phi(ir_node *n) {
1215         int i, n_preds;
1216
1217         ir_node *oldn = n;
1218         ir_node *block = NULL;     /* to shutup gcc */
1219         ir_node *first_val = NULL; /* to shutup gcc */
1220
1221         if (!get_opt_normalize()) return n;
1222
1223         n_preds = get_Phi_n_preds(n);
1224
1225         block = get_nodes_block(n);
1226         /* @@@ fliegt 'raus, sollte aber doch immer wahr sein!!!
1227         assert(get_irn_arity(block) == n_preds && "phi in wrong block!"); */
1228         if ((is_Block_dead(block)) ||                  /* Control dead */
1229                 (block == get_irg_start_block(current_ir_graph)))  /* There should be no Phi nodes */
1230                 return new_Bad();                                    /* in the Start Block. */
1231
1232         if (n_preds == 0) return n;           /* Phi of dead Region without predecessors. */
1233
1234         /* If the Block has a Bad pred, we also have one. */
1235         for (i = 0;  i < n_preds;  ++i)
1236                 if (is_Bad(get_Block_cfgpred(block, i)))
1237                         set_Phi_pred(n, i, new_Bad());
1238
1239         /* Find first non-self-referencing input */
1240         for (i = 0; i < n_preds; ++i) {
1241                 first_val = get_Phi_pred(n, i);
1242                 if (   (first_val != n)                            /* not self pointer */
1243 #if 1
1244                     && (! is_Bad(first_val))
1245 #endif
1246                    ) {        /* value not dead */
1247                         break;          /* then found first value. */
1248                 }
1249         }
1250
1251         if (i >= n_preds) {
1252                 /* A totally Bad or self-referencing Phi (we didn't break the above loop) */
1253                 return new_Bad();
1254         }
1255
1256         /* search for rest of inputs, determine if any of these
1257         are non-self-referencing */
1258         while (++i < n_preds) {
1259                 ir_node *scnd_val = get_Phi_pred(n, i);
1260                 if (   (scnd_val != n)
1261                     && (scnd_val != first_val)
1262 #if 1
1263                     && (! is_Bad(scnd_val))
1264 #endif
1265                         ) {
1266                         break;
1267                 }
1268         }
1269
1270         if (i >= n_preds) {
1271                 /* Fold, if no multiple distinct non-self-referencing inputs */
1272                 n = first_val;
1273                 DBG_OPT_PHI(oldn, n);
1274         }
1275         return n;
1276 }  /* equivalent_node_Phi */
1277
1278 /**
1279  * Several optimizations:
1280  * - no Sync in start block.
1281  * - fold Sync-nodes, iff they have only one predecessor except
1282  *   themselves.
1283  */
1284 static ir_node *equivalent_node_Sync(ir_node *n) {
1285         int i, n_preds;
1286
1287         ir_node *oldn = n;
1288         ir_node *first_val = NULL; /* to shutup gcc */
1289
1290         if (!get_opt_normalize()) return n;
1291
1292         n_preds = get_Sync_n_preds(n);
1293
1294         /* Find first non-self-referencing input */
1295         for (i = 0; i < n_preds; ++i) {
1296                 first_val = get_Sync_pred(n, i);
1297                 if ((first_val != n)  /* not self pointer */ &&
1298                     (! is_Bad(first_val))
1299                    ) {                /* value not dead */
1300                         break;            /* then found first value. */
1301                 }
1302         }
1303
1304         if (i >= n_preds)
1305                 /* A totally Bad or self-referencing Sync (we didn't break the above loop) */
1306                 return new_Bad();
1307
1308         /* search the rest of inputs, determine if any of these
1309            are non-self-referencing */
1310         while (++i < n_preds) {
1311                 ir_node *scnd_val = get_Sync_pred(n, i);
1312                 if ((scnd_val != n) &&
1313                     (scnd_val != first_val) &&
1314                     (! is_Bad(scnd_val))
1315                    )
1316                         break;
1317         }
1318
1319         if (i >= n_preds) {
1320                 /* Fold, if no multiple distinct non-self-referencing inputs */
1321                 n = first_val;
1322                 DBG_OPT_SYNC(oldn, n);
1323         }
1324         return n;
1325 }  /* equivalent_node_Sync */
1326
1327 /**
1328  * Optimize Proj(Tuple) and gigo() for ProjX in Bad block,
1329  * ProjX(Load) and ProjX(Store).
1330  */
1331 static ir_node *equivalent_node_Proj(ir_node *n) {
1332         ir_node *oldn = n;
1333         ir_node *a = get_Proj_pred(n);
1334
1335         if ( get_irn_op(a) == op_Tuple) {
1336                 /* Remove the Tuple/Proj combination. */
1337                 if ( get_Proj_proj(n) <= get_Tuple_n_preds(a) ) {
1338                         n = get_Tuple_pred(a, get_Proj_proj(n));
1339                         DBG_OPT_TUPLE(oldn, a, n);
1340                 } else {
1341                         assert(0); /* This should not happen! */
1342                         n = new_Bad();
1343                 }
1344         } else if (get_irn_mode(n) == mode_X) {
1345                 if (is_Block_dead(get_nodes_block(skip_Proj(n)))) {
1346                         /* Remove dead control flow -- early gigo(). */
1347                         n = new_Bad();
1348                 } else if (get_opt_ldst_only_null_ptr_exceptions()) {
1349                         ir_op *op = get_irn_op(a);
1350
1351                         if (op == op_Load || op == op_Store) {
1352                                 /* get the load/store address */
1353                                 ir_node *addr = get_irn_n(a, 1);
1354                                 ir_node *confirm;
1355
1356                                 if (value_not_null(addr, &confirm)) {
1357                                         if (confirm == NULL) {
1358                                                 /* this node may float if it did not depend on a Confirm */
1359                                                 set_irn_pinned(a, op_pin_state_floats);
1360                                         }
1361                                         DBG_OPT_EXC_REM(n);
1362                                         return new_Bad();
1363                                 }
1364                         }
1365                 }
1366         }
1367
1368         return n;
1369 }  /* equivalent_node_Proj */
1370
1371 /**
1372  * Remove Id's.
1373  */
1374 static ir_node *equivalent_node_Id(ir_node *n) {
1375         ir_node *oldn = n;
1376
1377         do {
1378                 n = get_Id_pred(n);
1379         } while (get_irn_op(n) == op_Id);
1380
1381         DBG_OPT_ID(oldn, n);
1382         return n;
1383 }  /* equivalent_node_Id */
1384
1385 /**
1386  * Optimize a Mux.
1387  */
1388 static ir_node *equivalent_node_Mux(ir_node *n)
1389 {
1390         ir_node *oldn = n, *sel = get_Mux_sel(n);
1391         tarval *ts = value_of(sel);
1392
1393         /* Mux(true, f, t) == t */
1394         if (ts == tarval_b_true) {
1395                 n = get_Mux_true(n);
1396                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_MUX_C);
1397         }
1398         /* Mux(false, f, t) == f */
1399         else if (ts == tarval_b_false) {
1400                 n = get_Mux_false(n);
1401                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_MUX_C);
1402         }
1403         /* Mux(v, x, x) == x */
1404         else if (get_Mux_false(n) == get_Mux_true(n)) {
1405                 n = get_Mux_true(n);
1406                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_MUX_EQ);
1407         }
1408         else if (get_irn_op(sel) == op_Proj && !mode_honor_signed_zeros(get_irn_mode(n))) {
1409                 ir_node *cmp = get_Proj_pred(sel);
1410                 long proj_nr = get_Proj_proj(sel);
1411                 ir_node *b   = get_Mux_false(n);
1412                 ir_node *a   = get_Mux_true(n);
1413
1414                 /*
1415                  * Note: normalization puts the constant on the right site,
1416                  * so we check only one case.
1417                  *
1418                  * Note further that these optimization work even for floating point
1419                  * with NaN's because -NaN == NaN.
1420                  * However, if +0 and -0 is handled differently, we cannot use the first one.
1421                  */
1422                 if (get_irn_op(cmp) == op_Cmp && get_Cmp_left(cmp) == a) {
1423                         if (classify_Const(get_Cmp_right(cmp)) == CNST_NULL) {
1424                                 /* Mux(a CMP 0, X, a) */
1425                                 if (get_irn_op(b) == op_Minus && get_Minus_op(b) == a) {
1426                                         /* Mux(a CMP 0, -a, a) */
1427                                         if (proj_nr == pn_Cmp_Eq) {
1428                                                 /* Mux(a == 0, -a, a)  ==>  -a */
1429                                                 n = b;
1430                                                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_MUX_TRANSFORM);
1431                                         } else if (proj_nr == pn_Cmp_Lg || proj_nr == pn_Cmp_Ne) {
1432                                                 /* Mux(a != 0, -a, a)  ==> a */
1433                                                 n = a;
1434                                                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_MUX_TRANSFORM);
1435                                         }
1436                                 } else if (classify_Const(b) == CNST_NULL) {
1437                                         /* Mux(a CMP 0, 0, a) */
1438                                         if (proj_nr == pn_Cmp_Lg || proj_nr == pn_Cmp_Ne) {
1439                                                 /* Mux(a != 0, 0, a) ==> a */
1440                                                 n = a;
1441                                                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_MUX_TRANSFORM);
1442                                         } else if (proj_nr == pn_Cmp_Eq) {
1443                                                 /* Mux(a == 0, 0, a) ==> 0 */
1444                                                 n = b;
1445                                                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_MUX_TRANSFORM);
1446                                         }
1447                                 }
1448                         }
1449                 }
1450         }
1451         return n;
1452 }  /* equivalent_node_Mux */
1453
1454 /**
1455  * Returns a equivalent node of a Psi: if a condition is true
1456  * and all previous conditions are false we know its value.
1457  * If all conditions are false its value is the default one.
1458  */
1459 static ir_node *equivalent_node_Psi(ir_node *n) {
1460         if (is_Mux(n))
1461                 return equivalent_node_Mux(n);
1462         return n;
1463 }  /* equivalent_node_Psi */
1464
1465 /**
1466  * Optimize -a CMP -b into b CMP a.
1467  * This works only for for modes where unary Minus
1468  * cannot Overflow.
1469  * Note that two-complement integers can Overflow
1470  * so it will NOT work.
1471  *
1472  * For == and != can be handled in Proj(Cmp)
1473  */
1474 static ir_node *equivalent_node_Cmp(ir_node *n) {
1475         ir_node *left  = get_Cmp_left(n);
1476         ir_node *right = get_Cmp_right(n);
1477
1478         if (get_irn_op(left) == op_Minus && get_irn_op(right) == op_Minus &&
1479                 !mode_overflow_on_unary_Minus(get_irn_mode(left))) {
1480                 left  = get_Minus_op(left);
1481                 right = get_Minus_op(right);
1482                 set_Cmp_left(n, right);
1483                 set_Cmp_right(n, left);
1484         }
1485         return n;
1486 }  /* equivalent_node_Cmp */
1487
1488 /**
1489  * Remove Confirm nodes if setting is on.
1490  * Replace Confirms(x, '=', Constlike) by Constlike.
1491  */
1492 static ir_node *equivalent_node_Confirm(ir_node *n) {
1493         ir_node *pred = get_Confirm_value(n);
1494         pn_Cmp  pnc   = get_Confirm_cmp(n);
1495
1496         if (get_irn_op(pred) == op_Confirm && pnc == get_Confirm_cmp(pred)) {
1497                 /*
1498                  * rare case: two identical Confirms one after another,
1499                  * replace the second one with the first.
1500                  */
1501                 n = pred;
1502         }
1503         if (pnc == pn_Cmp_Eq) {
1504                 ir_node *bound = get_Confirm_bound(n);
1505
1506                 /*
1507                  * Optimize a rare case:
1508                  * Confirm(x, '=', Constlike) ==> Constlike
1509                  */
1510                 if (is_irn_constlike(bound)) {
1511                         DBG_OPT_CONFIRM(n, bound);
1512                         return bound;
1513                 }
1514         }
1515         return get_opt_remove_confirm() ? get_Confirm_value(n) : n;
1516 }
1517
1518 /**
1519  * Optimize CopyB(mem, x, x) into a Nop.
1520  */
1521 static ir_node *equivalent_node_CopyB(ir_node *n) {
1522         ir_node *a = get_CopyB_dst(n);
1523         ir_node *b = get_CopyB_src(n);
1524
1525         if (a == b) {
1526                 /* Turn CopyB into a tuple (mem, bad, bad) */
1527                 ir_node *mem = get_CopyB_mem(n);
1528                 turn_into_tuple(n, pn_CopyB_max);
1529                 set_Tuple_pred(n, pn_CopyB_M,        mem);
1530                 set_Tuple_pred(n, pn_CopyB_X_except, new_Bad());        /* no exception */
1531                 set_Tuple_pred(n, pn_CopyB_M_except, new_Bad());
1532         }
1533         return n;
1534 }  /* equivalent_node_CopyB */
1535
1536 /**
1537  * Optimize Bounds(idx, idx, upper) into idx.
1538  */
1539 static ir_node *equivalent_node_Bound(ir_node *n) {
1540         ir_node *idx   = get_Bound_index(n);
1541         ir_node *lower = get_Bound_lower(n);
1542         int ret_tuple = 0;
1543
1544         /* By definition lower < upper, so if idx == lower -->
1545         lower <= idx && idx < upper */
1546         if (idx == lower) {
1547                 /* Turn Bound into a tuple (mem, bad, idx) */
1548                 ret_tuple = 1;
1549         } else {
1550                 ir_node *pred = skip_Proj(idx);
1551
1552                 if (get_irn_op(pred) == op_Bound) {
1553                         /*
1554                          * idx was Bounds_check previously, it is still valid if
1555                          * lower <= pred_lower && pred_upper <= upper.
1556                          */
1557                         ir_node *upper = get_Bound_upper(n);
1558                         if (get_Bound_lower(pred) == lower &&
1559                                 get_Bound_upper(pred) == upper) {
1560                                 /*
1561                                  * One could expect that we simply return the previous
1562                                  * Bound here. However, this would be wrong, as we could
1563                                  * add an exception Proj to a new location than.
1564                                  * So, we must turn in into a tuple
1565                                  */
1566                                 ret_tuple = 1;
1567                         }
1568                 }
1569         }
1570         if (ret_tuple) {
1571                 /* Turn Bound into a tuple (mem, bad, idx) */
1572                 ir_node *mem = get_Bound_mem(n);
1573                 turn_into_tuple(n, pn_Bound_max);
1574                 set_Tuple_pred(n, pn_Bound_M,        mem);
1575                 set_Tuple_pred(n, pn_Bound_X_except, new_Bad());       /* no exception */
1576                 set_Tuple_pred(n, pn_Bound_res,      idx);
1577         }
1578         return n;
1579 }  /* equivalent_node_Bound */
1580
1581 /**
1582  * equivalent_node() returns a node equivalent to input n. It skips all nodes that
1583  * perform no actual computation, as, e.g., the Id nodes.  It does not create
1584  * new nodes.  It is therefore safe to free n if the node returned is not n.
1585  * If a node returns a Tuple we can not just skip it.  If the size of the
1586  * in array fits, we transform n into a tuple (e.g., Div).
1587  */
1588 ir_node *equivalent_node(ir_node *n) {
1589         if (n->op->ops.equivalent_node)
1590                 return n->op->ops.equivalent_node(n);
1591         return n;
1592 }  /* equivalent_node */
1593
1594 /**
1595  * Sets the default equivalent node operation for an ir_op_ops.
1596  *
1597  * @param code   the opcode for the default operation
1598  * @param ops    the operations initialized
1599  *
1600  * @return
1601  *    The operations.
1602  */
1603 static ir_op_ops *firm_set_default_equivalent_node(ir_opcode code, ir_op_ops *ops)
1604 {
1605 #define CASE(a)                                      \
1606         case iro_##a:                                    \
1607                 ops->equivalent_node  = equivalent_node_##a; \
1608                 break
1609
1610         switch (code) {
1611         CASE(Block);
1612         CASE(Jmp);
1613         CASE(Raise);
1614         CASE(Or);
1615         CASE(Add);
1616         CASE(Eor);
1617         CASE(Sub);
1618         CASE(Shl);
1619         CASE(Shr);
1620         CASE(Shrs);
1621         CASE(Rot);
1622         CASE(Not);
1623         CASE(Minus);
1624         CASE(Mul);
1625         CASE(Div);
1626         CASE(Quot);
1627         CASE(DivMod);
1628         CASE(And);
1629         CASE(Conv);
1630         CASE(Cast);
1631         CASE(Phi);
1632         CASE(Sync);
1633         CASE(Proj);
1634         CASE(Id);
1635         CASE(Mux);
1636         CASE(Psi);
1637         CASE(Cmp);
1638         CASE(Confirm);
1639         CASE(CopyB);
1640         CASE(Bound);
1641         default:
1642                 /* leave NULL */;
1643         }
1644
1645         return ops;
1646 #undef CASE
1647 }  /* firm_set_default_equivalent_node */
1648
1649 /**
1650  * Do node specific optimizations of nodes predecessors.
1651  */
1652 static void optimize_preds(ir_node *n) {
1653         switch (get_irn_opcode(n)) {
1654
1655         case iro_Cmp: { /* We don't want Cast as input to Cmp. */
1656                 ir_node *a = get_Cmp_left(n), *b = get_Cmp_right(n);
1657
1658                 if (get_irn_op(a) == op_Cast) {
1659                         a = get_Cast_op(a);
1660                         set_Cmp_left(n, a);
1661                 }
1662                 if (get_irn_op(b) == op_Cast) {
1663                         b = get_Cast_op(b);
1664                         set_Cmp_right(n, b);
1665                 }
1666                 break;
1667         }
1668
1669         default: break;
1670         } /* end switch */
1671 }  /* optimize_preds */
1672
1673 /**
1674  * Returns non-zero if a node is a Phi node
1675  * with all predecessors constant.
1676  */
1677 static int is_const_Phi(ir_node *n) {
1678         int i;
1679
1680         if (! is_Phi(n))
1681                 return 0;
1682         for (i = get_irn_arity(n) - 1; i >= 0; --i)
1683                 if (! is_Const(get_irn_n(n, i)))
1684                         return 0;
1685                 return 1;
1686 }  /* is_const_Phi */
1687
1688 /**
1689  * Apply an evaluator on a binop with a constant operators (and one Phi).
1690  *
1691  * @param phi    the Phi node
1692  * @param other  the other operand
1693  * @param eval   an evaluator function
1694  * @param left   if non-zero, other is the left operand, else the right
1695  *
1696  * @return a new Phi node if the conversion was successful, NULL else
1697  */
1698 static ir_node *apply_binop_on_phi(ir_node *phi, tarval *other, tarval *(*eval)(tarval *, tarval *), int left) {
1699         tarval   *tv;
1700         void     **res;
1701         ir_node  *pred;
1702         ir_mode  *mode;
1703         ir_graph *irg;
1704         int      i, n = get_irn_arity(phi);
1705
1706         NEW_ARR_A(void *, res, n);
1707         if (left) {
1708                 for (i = 0; i < n; ++i) {
1709                         pred = get_irn_n(phi, i);
1710                         tv   = get_Const_tarval(pred);
1711                         tv   = eval(other, tv);
1712
1713                         if (tv == tarval_bad) {
1714                                 /* folding failed, bad */
1715                                 return NULL;
1716                         }
1717                         res[i] = tv;
1718                 }
1719         } else {
1720                 for (i = 0; i < n; ++i) {
1721                         pred = get_irn_n(phi, i);
1722                         tv   = get_Const_tarval(pred);
1723                         tv   = eval(tv, other);
1724
1725                         if (tv == tarval_bad) {
1726                                 /* folding failed, bad */
1727                                 return 0;
1728                         }
1729                         res[i] = tv;
1730                 }
1731         }
1732         mode = get_irn_mode(phi);
1733         irg  = current_ir_graph;
1734         for (i = 0; i < n; ++i) {
1735                 pred = get_irn_n(phi, i);
1736                 res[i] = new_r_Const_type(irg, get_irg_start_block(irg),
1737                         mode, res[i], get_Const_type(pred));
1738         }
1739         return new_r_Phi(irg, get_nodes_block(phi), n, (ir_node **)res, mode);
1740 }  /* apply_binop_on_phi */
1741
1742 /**
1743  * Apply an evaluator on a unop with a constant operator (a Phi).
1744  *
1745  * @param phi    the Phi node
1746  * @param eval   an evaluator function
1747  *
1748  * @return a new Phi node if the conversion was successful, NULL else
1749  */
1750 static ir_node *apply_unop_on_phi(ir_node *phi, tarval *(*eval)(tarval *)) {
1751         tarval   *tv;
1752         void     **res;
1753         ir_node  *pred;
1754         ir_mode  *mode;
1755         ir_graph *irg;
1756         int      i, n = get_irn_arity(phi);
1757
1758         NEW_ARR_A(void *, res, n);
1759         for (i = 0; i < n; ++i) {
1760                 pred = get_irn_n(phi, i);
1761                 tv   = get_Const_tarval(pred);
1762                 tv   = eval(tv);
1763
1764                 if (tv == tarval_bad) {
1765                         /* folding failed, bad */
1766                         return 0;
1767                 }
1768                 res[i] = tv;
1769         }
1770         mode = get_irn_mode(phi);
1771         irg  = current_ir_graph;
1772         for (i = 0; i < n; ++i) {
1773                 pred = get_irn_n(phi, i);
1774                 res[i] = new_r_Const_type(irg, get_irg_start_block(irg),
1775                         mode, res[i], get_Const_type(pred));
1776         }
1777         return new_r_Phi(irg, get_nodes_block(phi), n, (ir_node **)res, mode);
1778 }  /* apply_unop_on_phi */
1779
1780 /**
1781  * Transform AddP(P, ConvIs(Iu)), AddP(P, ConvIu(Is)) and
1782  * SubP(P, ConvIs(Iu)), SubP(P, ConvIu(Is)).
1783  * If possible, remove the Conv's.
1784  */
1785 static ir_node *transform_node_AddSub(ir_node *n) {
1786         ir_mode *mode = get_irn_mode(n);
1787
1788         if (mode_is_reference(mode)) {
1789                 ir_node *left  = get_binop_left(n);
1790                 ir_node *right = get_binop_right(n);
1791                 int ref_bits   = get_mode_size_bits(mode);
1792
1793                 if (get_irn_op(left) == op_Conv) {
1794                         ir_mode *mode = get_irn_mode(left);
1795                         int bits      = get_mode_size_bits(mode);
1796
1797                         if (ref_bits == bits &&
1798                             mode_is_int(mode) &&
1799                             get_mode_arithmetic(mode) == irma_twos_complement) {
1800                                 ir_node *pre      = get_Conv_op(left);
1801                                 ir_mode *pre_mode = get_irn_mode(pre);
1802
1803                                 if (mode_is_int(pre_mode) &&
1804                                     get_mode_size_bits(pre_mode) == bits &&
1805                                     get_mode_arithmetic(pre_mode) == irma_twos_complement) {
1806                                         /* ok, this conv just changes to sign, moreover the calculation
1807                                          * is done with same number of bits as our address mode, so
1808                                          * we can ignore the conv as address calculation can be viewed
1809                                          * as either signed or unsigned
1810                                          */
1811                                         set_binop_left(n, pre);
1812                                 }
1813                         }
1814                 }
1815
1816                 if (get_irn_op(right) == op_Conv) {
1817                         ir_mode *mode = get_irn_mode(right);
1818                         int bits      = get_mode_size_bits(mode);
1819
1820                         if (ref_bits == bits &&
1821                                 mode_is_int(mode) &&
1822                                 get_mode_arithmetic(mode) == irma_twos_complement) {
1823                                 ir_node *pre      = get_Conv_op(right);
1824                                 ir_mode *pre_mode = get_irn_mode(pre);
1825
1826                                 if (mode_is_int(pre_mode) &&
1827                                     get_mode_size_bits(pre_mode) == bits &&
1828                                     get_mode_arithmetic(pre_mode) == irma_twos_complement) {
1829                                         /* ok, this conv just changes to sign, moreover the calculation
1830                                          * is done with same number of bits as our address mode, so
1831                                          * we can ignore the conv as address calculation can be viewed
1832                                          * as either signed or unsigned
1833                                          */
1834                                         set_binop_right(n, pre);
1835                                 }
1836                         }
1837                 }
1838         }
1839         return n;
1840 }  /* transform_node_AddSub */
1841
1842 #define HANDLE_BINOP_PHI(op,a,b,c)                          \
1843   c = NULL;                                                 \
1844   if (is_Const(b) && is_const_Phi(a)) {                     \
1845     /* check for Op(Phi, Const) */                          \
1846     c = apply_binop_on_phi(a, get_Const_tarval(b), op, 0);  \
1847   }                                                         \
1848   else if (is_Const(a) && is_const_Phi(b)) {                \
1849     /* check for Op(Const, Phi) */                          \
1850     c = apply_binop_on_phi(b, get_Const_tarval(a), op, 1);  \
1851   }                                                         \
1852   if (c) {                                                  \
1853     DBG_OPT_ALGSIM0(oldn, c, FS_OPT_CONST_PHI);             \
1854     return c;                                               \
1855   }
1856
1857 #define HANDLE_UNOP_PHI(op,a,c)                 \
1858   c = NULL;                                     \
1859   if (is_const_Phi(a)) {                        \
1860     /* check for Op(Phi) */                     \
1861     c = apply_unop_on_phi(a, op);               \
1862   }                                             \
1863   if (c) {                                      \
1864     DBG_OPT_ALGSIM0(oldn, c, FS_OPT_CONST_PHI); \
1865     return c;                                   \
1866   }
1867
1868
1869 /**
1870  * Do the AddSub optimization, then Transform
1871  *   Constant folding on Phi
1872  *   Add(a,a)          -> Mul(a, 2)
1873  *   Add(Mul(a, x), a) -> Mul(a, x+1)
1874  * if the mode is integer or float.
1875  * Transform Add(a,-b) into Sub(a,b).
1876  * Reassociation might fold this further.
1877  */
1878 static ir_node *transform_node_Add(ir_node *n) {
1879         ir_mode *mode;
1880         ir_node *a, *b, *c, *oldn = n;
1881
1882         n = transform_node_AddSub(n);
1883
1884         a = get_Add_left(n);
1885         b = get_Add_right(n);
1886
1887         HANDLE_BINOP_PHI(tarval_add, a,b,c);
1888
1889         mode = get_irn_mode(n);
1890
1891         /* for FP these optimizations are only allowed if fp_strict_algebraic is disabled */
1892         if (mode_is_float(mode) && (get_irg_fp_model(current_ir_graph) & fp_strict_algebraic))
1893                 return n;
1894
1895         if (mode_is_num(mode)) {
1896                 if (a == b) {
1897                         ir_node *block = get_irn_n(n, -1);
1898
1899                         n = new_rd_Mul(
1900                                 get_irn_dbg_info(n),
1901                                 current_ir_graph,
1902                                 block,
1903                                 a,
1904                                 new_r_Const_long(current_ir_graph, block, mode, 2),
1905                                 mode);
1906                         DBG_OPT_ALGSIM0(oldn, n, FS_OPT_ADD_A_A);
1907                 } else if (get_irn_op(a) == op_Minus) {
1908                         n = new_rd_Sub(
1909                                         get_irn_dbg_info(n),
1910                                         current_ir_graph,
1911                                         get_irn_n(n, -1),
1912                                         b,
1913                                         get_Minus_op(a),
1914                                         mode);
1915                         DBG_OPT_ALGSIM0(oldn, n, FS_OPT_ADD_A_MINUS_B);
1916                 } else if (get_irn_op(b) == op_Minus) {
1917                         n = new_rd_Sub(
1918                                         get_irn_dbg_info(n),
1919                                         current_ir_graph,
1920                                         get_irn_n(n, -1),
1921                                         a,
1922                                         get_Minus_op(b),
1923                                         mode);
1924                         DBG_OPT_ALGSIM0(oldn, n, FS_OPT_ADD_A_MINUS_B);
1925                 }
1926                 /* do NOT execute this code if reassociation is enabled, it does the inverse! */
1927                 else if (!get_opt_reassociation() && get_irn_op(a) == op_Mul) {
1928                         ir_node *ma = get_Mul_left(a);
1929                         ir_node *mb = get_Mul_right(a);
1930
1931                         if (b == ma) {
1932                                 ir_node *blk = get_irn_n(n, -1);
1933                                 n = new_rd_Mul(
1934                                                 get_irn_dbg_info(n), current_ir_graph, blk,
1935                                                 ma,
1936                                                 new_rd_Add(
1937                                                         get_irn_dbg_info(n), current_ir_graph, blk,
1938                                                         mb,
1939                                                         new_r_Const_long(current_ir_graph, blk, mode, 1),
1940                                                         mode),
1941                                                 mode);
1942                                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_ADD_MUL_A_X_A);
1943                         } else if (b == mb) {
1944                                 ir_node *blk = get_irn_n(n, -1);
1945                                 n = new_rd_Mul(
1946                                                 get_irn_dbg_info(n), current_ir_graph, blk,
1947                                                 mb,
1948                                                 new_rd_Add(
1949                                                         get_irn_dbg_info(n), current_ir_graph, blk,
1950                                                         ma,
1951                                                         new_r_Const_long(current_ir_graph, blk, mode, 1),
1952                                                         mode),
1953                                                 mode);
1954                                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_ADD_MUL_A_X_A);
1955                         }
1956                 }
1957                 /* do NOT execute this code if reassociation is enabled, it does the inverse! */
1958                 else if (!get_opt_reassociation() && get_irn_op(b) == op_Mul) {
1959                         ir_node *ma = get_Mul_left(b);
1960                         ir_node *mb = get_Mul_right(b);
1961
1962                         if (a == ma) {
1963                                 ir_node *blk = get_irn_n(n, -1);
1964                                 n = new_rd_Mul(
1965                                                 get_irn_dbg_info(n), current_ir_graph, blk,
1966                                                 ma,
1967                                                 new_rd_Add(
1968                                                         get_irn_dbg_info(n), current_ir_graph, blk,
1969                                                         mb,
1970                                                         new_r_Const_long(current_ir_graph, blk, mode, 1),
1971                                                         mode),
1972                                                 mode);
1973                                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_ADD_MUL_A_X_A);
1974                         } else if (a == mb) {
1975                                 ir_node *blk = get_irn_n(n, -1);
1976                                 n = new_rd_Mul(
1977                                                 get_irn_dbg_info(n), current_ir_graph, blk,
1978                                                 mb,
1979                                                 new_rd_Add(
1980                                                         get_irn_dbg_info(n), current_ir_graph, blk,
1981                                                         ma,
1982                                                         new_r_Const_long(current_ir_graph, blk, mode, 1),
1983                                                         mode),
1984                                                 mode);
1985                                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_ADD_MUL_A_X_A);
1986                         }
1987                 }
1988         }
1989         return n;
1990 }  /* transform_node_Add */
1991
1992 /**
1993  * Do the AddSub optimization, then Transform
1994  *   Constant folding on Phi
1995  *   Sub(0,a)          -> Minus(a)
1996  *   Sub(Mul(a, x), a) -> Mul(a, x-1)
1997  *   Sub(Sub(x, y), b) -> Sub(x, Add(y,b))
1998  */
1999 static ir_node *transform_node_Sub(ir_node *n) {
2000         ir_mode *mode;
2001         ir_node *oldn = n;
2002         ir_node *a, *b, *c;
2003
2004         n = transform_node_AddSub(n);
2005
2006         a = get_Sub_left(n);
2007         b = get_Sub_right(n);
2008
2009         HANDLE_BINOP_PHI(tarval_sub, a,b,c);
2010
2011         mode = get_irn_mode(n);
2012
2013         /* for FP these optimizations are only allowed if fp_strict_algebraic is disabled */
2014         if (mode_is_float(mode) && (get_irg_fp_model(current_ir_graph) & fp_strict_algebraic))
2015                 return n;
2016
2017         /* Beware of Sub(P, P) which cannot be optimized into a simple Minus ... */
2018         if (mode_is_num(mode) && mode == get_irn_mode(a) && (classify_Const(a) == CNST_NULL)) {
2019                 n = new_rd_Minus(
2020                                 get_irn_dbg_info(n),
2021                                 current_ir_graph,
2022                                 get_irn_n(n, -1),
2023                                 b,
2024                                 mode);
2025                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_SUB_0_A);
2026         }
2027         /* do NOT execute this code if reassociation is enabled, it does the inverse! */
2028         else if (get_opt_reassociation() && get_irn_op(a) == op_Mul) {
2029                 ir_node *ma = get_Mul_left(a);
2030                 ir_node *mb = get_Mul_right(a);
2031
2032                 if (ma == b) {
2033                         ir_node *blk = get_irn_n(n, -1);
2034                         n = new_rd_Mul(
2035                                         get_irn_dbg_info(n),
2036                                         current_ir_graph, blk,
2037                                         ma,
2038                                         new_rd_Sub(
2039                                                 get_irn_dbg_info(n),
2040                                                 current_ir_graph, blk,
2041                                                 mb,
2042                                                 new_r_Const_long(current_ir_graph, blk, mode, 1),
2043                                                 mode),
2044                                         mode);
2045                         DBG_OPT_ALGSIM0(oldn, n, FS_OPT_SUB_MUL_A_X_A);
2046                 } else if (mb == b) {
2047                         ir_node *blk = get_irn_n(n, -1);
2048                         n = new_rd_Mul(
2049                                         get_irn_dbg_info(n),
2050                                         current_ir_graph, blk,
2051                                         mb,
2052                                         new_rd_Sub(
2053                                                 get_irn_dbg_info(n),
2054                                                 current_ir_graph, blk,
2055                                                 ma,
2056                                                 new_r_Const_long(current_ir_graph, blk, mode, 1),
2057                                                 mode),
2058                                         mode);
2059                         DBG_OPT_ALGSIM0(oldn, n, FS_OPT_SUB_MUL_A_X_A);
2060                 }
2061         } else if (get_irn_op(a) == op_Sub) {
2062                 ir_node *x   = get_Sub_left(a);
2063                 ir_node *y   = get_Sub_right(a);
2064                 ir_node *blk = get_irn_n(n, -1);
2065                 ir_mode *m_b = get_irn_mode(b);
2066                 ir_mode *m_y = get_irn_mode(y);
2067                 ir_node *add;
2068
2069                 /* Determine the right mode for the Add. */
2070                 if (m_b == m_y)
2071                         mode = m_b;
2072                 else if (mode_is_reference(m_b))
2073                         mode = m_b;
2074                 else if (mode_is_reference(m_y))
2075                         mode = m_y;
2076                 else {
2077                         /*
2078                          * Both modes are different but none is reference,
2079                          * happens for instance in SubP(SubP(P, Iu), Is).
2080                          * We have two possibilities here: Cast or ignore.
2081                          * Currently we ignore this case.
2082                          */
2083                         return n;
2084                 }
2085
2086                 add = new_r_Add(current_ir_graph, blk, y, b, mode);
2087
2088                 set_Sub_left(n, x);
2089                 set_Sub_right(n, add);
2090                 DBG_OPT_ALGSIM0(n, n, FS_OPT_SUB_SUB_X_Y_Z);
2091         }
2092
2093         return n;
2094 }  /* transform_node_Sub */
2095
2096 /**
2097  * Transform Mul(a,-1) into -a.
2098  * Do constant evaluation of Phi nodes.
2099  * Do architecture dependent optimizations on Mul nodes
2100  */
2101 static ir_node *transform_node_Mul(ir_node *n) {
2102         ir_node *c, *oldn = n;
2103         ir_node *a = get_Mul_left(n);
2104         ir_node *b = get_Mul_right(n);
2105         ir_mode *mode;
2106
2107         HANDLE_BINOP_PHI(tarval_mul, a,b,c);
2108
2109         mode = get_irn_mode(n);
2110         if (mode_is_signed(mode)) {
2111                 ir_node *r = NULL;
2112
2113                 if (value_of(a) == get_mode_minus_one(mode))
2114                         r = b;
2115                 else if (value_of(b) == get_mode_minus_one(mode))
2116                         r = a;
2117                 if (r) {
2118                         n = new_rd_Minus(get_irn_dbg_info(n), current_ir_graph, get_irn_n(n, -1), r, mode);
2119                         DBG_OPT_ALGSIM1(oldn, a, b, n, FS_OPT_MUL_MINUS_1);
2120                         return n;
2121                 }
2122         }
2123         return arch_dep_replace_mul_with_shifts(n);
2124 }  /* transform_node_Mul */
2125
2126 /**
2127  * Transform a Div Node.
2128  */
2129 static ir_node *transform_node_Div(ir_node *n) {
2130         tarval *tv = value_of(n);
2131         ir_node *value = n;
2132
2133         /* BEWARE: it is NOT possible to optimize a/a to 1, as this may cause a exception */
2134
2135         if (tv != tarval_bad) {
2136                 value = new_Const(get_tarval_mode(tv), tv);
2137
2138                 DBG_OPT_CSTEVAL(n, value);
2139         } else /* Try architecture dependent optimization */
2140                 value = arch_dep_replace_div_by_const(n);
2141
2142         if (value != n) {
2143                 /* Turn Div into a tuple (mem, bad, value) */
2144                 ir_node *mem = get_Div_mem(n);
2145
2146                 turn_into_tuple(n, pn_Div_max);
2147                 set_Tuple_pred(n, pn_Div_M, mem);
2148                 set_Tuple_pred(n, pn_Div_X_except, new_Bad());
2149                 set_Tuple_pred(n, pn_Div_res, value);
2150         }
2151         return n;
2152 }  /* transform_node_Div */
2153
2154 /**
2155  * Transform a Mod node.
2156  */
2157 static ir_node *transform_node_Mod(ir_node *n) {
2158         tarval *tv = value_of(n);
2159         ir_node *value = n;
2160
2161         /* BEWARE: it is NOT possible to optimize a%a to 0, as this may cause a exception */
2162
2163         if (tv != tarval_bad) {
2164                 value = new_Const(get_tarval_mode(tv), tv);
2165
2166                 DBG_OPT_CSTEVAL(n, value);
2167         } else /* Try architecture dependent optimization */
2168                 value = arch_dep_replace_mod_by_const(n);
2169
2170         if (value != n) {
2171                 /* Turn Mod into a tuple (mem, bad, value) */
2172                 ir_node *mem = get_Mod_mem(n);
2173
2174                 turn_into_tuple(n, pn_Mod_max);
2175                 set_Tuple_pred(n, pn_Mod_M, mem);
2176                 set_Tuple_pred(n, pn_Mod_X_except, new_Bad());
2177                 set_Tuple_pred(n, pn_Mod_res, value);
2178         }
2179         return n;
2180 }  /* transform_node_Mod */
2181
2182 /**
2183  * Transform a DivMod node.
2184  */
2185 static ir_node *transform_node_DivMod(ir_node *n) {
2186         int evaluated = 0;
2187
2188         ir_node *a = get_DivMod_left(n);
2189         ir_node *b = get_DivMod_right(n);
2190         ir_mode *mode = get_irn_mode(a);
2191         tarval *ta = value_of(a);
2192         tarval *tb = value_of(b);
2193
2194         if (!(mode_is_int(mode) && mode_is_int(get_irn_mode(b))))
2195                 return n;
2196
2197         /* BEWARE: it is NOT possible to optimize a/a to 1, as this may cause a exception */
2198
2199         if (tb != tarval_bad) {
2200                 if (tb == get_mode_one(get_tarval_mode(tb))) {
2201                         b = new_Const (mode, get_mode_null(mode));
2202                         evaluated = 1;
2203
2204                         DBG_OPT_CSTEVAL(n, b);
2205                 } else if (ta != tarval_bad) {
2206                         tarval *resa, *resb;
2207                         resa = tarval_div (ta, tb);
2208                         if (resa == tarval_bad) return n; /* Causes exception!!! Model by replacing through
2209                                                              Jmp for X result!? */
2210                         resb = tarval_mod (ta, tb);
2211                         if (resb == tarval_bad) return n; /* Causes exception! */
2212                         a = new_Const (mode, resa);
2213                         b = new_Const (mode, resb);
2214                         evaluated = 1;
2215
2216                         DBG_OPT_CSTEVAL(n, a);
2217                         DBG_OPT_CSTEVAL(n, b);
2218                 } else { /* Try architecture dependent optimization */
2219                         arch_dep_replace_divmod_by_const(&a, &b, n);
2220                         evaluated = a != NULL;
2221                 }
2222         } else if (ta == get_mode_null(mode)) {
2223                 /* 0 / non-Const = 0 */
2224                 b = a;
2225                 evaluated = 1;
2226         }
2227
2228         if (evaluated) { /* replace by tuple */
2229                 ir_node *mem = get_DivMod_mem(n);
2230                 turn_into_tuple(n, pn_DivMod_max);
2231                 set_Tuple_pred(n, pn_DivMod_M,        mem);
2232                 set_Tuple_pred(n, pn_DivMod_X_except, new_Bad());  /* no exception */
2233                 set_Tuple_pred(n, pn_DivMod_res_div,  a);
2234                 set_Tuple_pred(n, pn_DivMod_res_mod,  b);
2235         }
2236
2237         return n;
2238 }  /* transform_node_DivMod */
2239
2240 /**
2241  * Optimize Abs(x) into  x if x is Confirmed >= 0
2242  * Optimize Abs(x) into -x if x is Confirmed <= 0
2243  */
2244 static ir_node *transform_node_Abs(ir_node *n) {
2245         ir_node        *oldn = n;
2246         ir_node        *a = get_Abs_op(n);
2247         value_classify_sign sign = classify_value_sign(a);
2248
2249         if (sign == value_classified_negative) {
2250                 ir_mode *mode = get_irn_mode(n);
2251
2252                 /*
2253                  * We can replace the Abs by -x here.
2254                  * We even could add a new Confirm here.
2255                  *
2256                  * Note that -x would create a new node, so we could
2257                  * not run it in the equivalent_node() context.
2258                  */
2259                 n = new_rd_Minus(get_irn_dbg_info(n), current_ir_graph,
2260                                 get_irn_n(n, -1), a, mode);
2261
2262                 DBG_OPT_CONFIRM(oldn, n);
2263         } else if (sign == value_classified_positive) {
2264                 /* n is positive, Abs is not needed */
2265                 n = a;
2266
2267                 DBG_OPT_CONFIRM(oldn, n);
2268         }
2269
2270         return n;
2271 }  /* transform_node_Abs */
2272
2273 /**
2274  * Transform a Cond node.
2275  *
2276  * Replace the Cond by a Jmp if it branches on a constant
2277  * condition.
2278  */
2279 static ir_node *transform_node_Cond(ir_node *n) {
2280
2281         ir_node *jmp;
2282         ir_node *a = get_Cond_selector(n);
2283         tarval *ta = value_of(a);
2284
2285         /* we need block info which is not available in floating irgs */
2286         if (get_irg_pinned(current_ir_graph) == op_pin_state_floats)
2287                 return n;
2288
2289         if ((ta != tarval_bad) &&
2290             (get_irn_mode(a) == mode_b) &&
2291             (get_opt_unreachable_code())) {
2292                 /* It's a boolean Cond, branching on a boolean constant.
2293                    Replace it by a tuple (Bad, Jmp) or (Jmp, Bad) */
2294                 jmp = new_r_Jmp(current_ir_graph, get_nodes_block(n));
2295                 turn_into_tuple(n, pn_Cond_max);
2296                 if (ta == tarval_b_true) {
2297                         set_Tuple_pred(n, pn_Cond_false, new_Bad());
2298                         set_Tuple_pred(n, pn_Cond_true, jmp);
2299                 } else {
2300                         set_Tuple_pred(n, pn_Cond_false, jmp);
2301                         set_Tuple_pred(n, pn_Cond_true, new_Bad());
2302                 }
2303                 /* We might generate an endless loop, so keep it alive. */
2304                 add_End_keepalive(get_irg_end(current_ir_graph), get_nodes_block(n));
2305         }
2306         return n;
2307 }  /* transform_node_Cond */
2308
2309 /**
2310  * Transform an And.
2311  */
2312 static ir_node *transform_node_And(ir_node *n) {
2313         ir_node *c, *oldn = n;
2314         ir_node *a = get_And_left(n);
2315         ir_node *b = get_And_right(n);
2316
2317         HANDLE_BINOP_PHI(tarval_and, a,b,c);
2318         return n;
2319 }  /* transform_node_And */
2320
2321 /**
2322  * Transform an Eor.
2323  */
2324 static ir_node *transform_node_Eor(ir_node *n) {
2325         ir_node *c, *oldn = n;
2326         ir_node *a = get_Eor_left(n);
2327         ir_node *b = get_Eor_right(n);
2328         ir_mode *mode = get_irn_mode(n);
2329
2330         HANDLE_BINOP_PHI(tarval_eor, a,b,c);
2331
2332         if (a == b) {
2333                 /* a ^ a = 0 */
2334                 n = new_rd_Const(get_irn_dbg_info(n), current_ir_graph, get_irn_n(n, -1),
2335                                  mode, get_mode_null(mode));
2336                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_EOR_A_A);
2337         } else if ((mode == mode_b)
2338                    && (get_irn_op(a) == op_Proj)
2339                    && (get_irn_mode(a) == mode_b)
2340                    && (classify_tarval (value_of(b)) == TV_CLASSIFY_ONE)
2341                    && (get_irn_op(get_Proj_pred(a)) == op_Cmp)) {
2342                 /* The Eor negates a Cmp. The Cmp has the negated result anyways! */
2343                 n = new_r_Proj(current_ir_graph, get_irn_n(n, -1), get_Proj_pred(a),
2344                                 mode_b, get_negated_pnc(get_Proj_proj(a), mode));
2345
2346                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_EOR_TO_NOT_BOOL);
2347         } else if ((mode == mode_b)
2348                && (classify_tarval (value_of(b)) == TV_CLASSIFY_ONE)) {
2349                 /* The Eor is a Not. Replace it by a Not. */
2350                 /*   ????!!!Extend to bitfield 1111111. */
2351                 n = new_r_Not(current_ir_graph, get_irn_n(n, -1), a, mode_b);
2352
2353                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_EOR_TO_NOT);
2354         }
2355
2356         return n;
2357 }  /* transform_node_Eor */
2358
2359 /**
2360  * Transform a Not.
2361  */
2362 static ir_node *transform_node_Not(ir_node *n) {
2363         ir_node *c, *oldn = n;
2364         ir_node *a = get_Not_op(n);
2365
2366         HANDLE_UNOP_PHI(tarval_not,a,c);
2367
2368         /* check for a boolean Not */
2369         if (   (get_irn_mode(n) == mode_b)
2370             && (get_irn_op(a) == op_Proj)
2371             && (get_irn_mode(a) == mode_b)
2372             && (get_irn_op(get_Proj_pred(a)) == op_Cmp)) {
2373                 /* We negate a Cmp. The Cmp has the negated result anyways! */
2374                 n = new_r_Proj(current_ir_graph, get_irn_n(n, -1), get_Proj_pred(a),
2375                                 mode_b, get_negated_pnc(get_Proj_proj(a), mode_b));
2376                 DBG_OPT_ALGSIM0(oldn, n, FS_OPT_NOT_CMP);
2377         }
2378         return n;
2379 }  /* transform_node_Not */
2380
2381 /**
2382  * Transform a Minus.
2383  */
2384 static ir_node *transform_node_Minus(ir_node *n) {
2385         ir_node *c, *oldn = n;
2386         ir_node *a = get_Minus_op(n);
2387
2388         HANDLE_UNOP_PHI(tarval_neg,a,c);
2389         return n;
2390 }  /* transform_node_Minus */
2391
2392 /**
2393  * Transform a Cast_type(Const) into a new Const_type
2394  */
2395 static ir_node *transform_node_Cast(ir_node *n) {
2396         ir_node *oldn = n;
2397         ir_node *pred = get_Cast_op(n);
2398         ir_type *tp = get_irn_type(n);
2399
2400         if (get_irn_op(pred) == op_Const && get_Const_type(pred) != tp) {
2401                 n = new_rd_Const_type(NULL, current_ir_graph, get_irn_n(pred, -1), get_irn_mode(pred),
2402                         get_Const_tarval(pred), tp);
2403                 DBG_OPT_CSTEVAL(oldn, n);
2404         } else if ((get_irn_op(pred) == op_SymConst) && (get_SymConst_value_type(pred) != tp)) {
2405                 n = new_rd_SymConst_type(NULL, current_ir_graph, get_irn_n(pred, -1), get_SymConst_symbol(pred),
2406                         get_SymConst_kind(pred), tp);
2407                 DBG_OPT_CSTEVAL(oldn, n);
2408         }
2409
2410         return n;
2411 }  /* transform_node_Cast */
2412
2413 /**
2414  * Transform a Proj(Div) with a non-zero value.
2415  * Removes the exceptions and routes the memory to the NoMem node.
2416  */
2417 static ir_node *transform_node_Proj_Div(ir_node *proj) {
2418         ir_node *n = get_Proj_pred(proj);
2419         ir_node *b = get_Div_right(n);
2420         ir_node *confirm;
2421         long proj_nr;
2422
2423         if (value_not_zero(b, &confirm)) {
2424                 /* div(x, y) && y != 0 */
2425                 proj_nr = get_Proj_proj(proj);
2426                 if (proj_nr == pn_Div_X_except) {
2427                         /* we found an exception handler, remove it */
2428                         DBG_OPT_EXC_REM(proj);
2429                         return new_Bad();
2430                 } else if (proj_nr == pn_Div_M) {
2431                         ir_node *res = get_Div_mem(n);
2432                         ir_node *new_mem = get_irg_no_mem(current_ir_graph);
2433
2434                         if (confirm) {
2435                                 /* This node can only float up to the Confirm block */
2436                                 new_mem = new_r_Pin(current_ir_graph, get_nodes_block(confirm), new_mem);
2437                         }
2438                         set_irn_pinned(n, op_pin_state_floats);
2439                         /* this is a Div without exception, we can remove the memory edge */
2440                         set_Div_mem(n, new_mem);
2441                         return res;
2442                 }
2443         }
2444         return proj;
2445 }  /* transform_node_Proj_Div */
2446
2447 /**
2448  * Transform a Proj(Mod) with a non-zero value.
2449  * Removes the exceptions and routes the memory to the NoMem node.
2450  */
2451 static ir_node *transform_node_Proj_Mod(ir_node *proj) {
2452         ir_node *n = get_Proj_pred(proj);
2453         ir_node *b = get_Mod_right(n);
2454         ir_node *confirm;
2455         long proj_nr;
2456
2457         if (value_not_zero(b, &confirm)) {
2458                 /* mod(x, y) && y != 0 */
2459                 proj_nr = get_Proj_proj(proj);
2460
2461                 if (proj_nr == pn_Mod_X_except) {
2462                         /* we found an exception handler, remove it */
2463                         DBG_OPT_EXC_REM(proj);
2464                         return new_Bad();
2465                 } else if (proj_nr == pn_Mod_M) {
2466                         ir_node *res = get_Mod_mem(n);
2467                         ir_node *new_mem = get_irg_no_mem(current_ir_graph);
2468
2469                         if (confirm) {
2470                                 /* This node can only float up to the Confirm block */
2471                                 new_mem = new_r_Pin(current_ir_graph, get_nodes_block(confirm), new_mem);
2472                         }
2473                         set_irn_pinned(n, op_pin_state_floats);
2474                         /* this is a Mod without exception, we can remove the memory edge */
2475                         set_Mod_mem(n, get_irg_no_mem(current_ir_graph));
2476                         return res;
2477                 } else if (proj_nr == pn_Mod_res && get_Mod_left(n) == b) {
2478                         /* a % a = 0 if a != 0 */
2479                         ir_mode *mode = get_irn_mode(proj);
2480                         ir_node *res  = new_Const(mode, get_mode_null(mode));
2481
2482                         DBG_OPT_CSTEVAL(n, res);
2483                         return res;
2484                 }
2485         }
2486         return proj;
2487 }  /* transform_node_Proj_Mod */
2488
2489 /**
2490  * Transform a Proj(DivMod) with a non-zero value.
2491  * Removes the exceptions and routes the memory to the NoMem node.
2492  */
2493 static ir_node *transform_node_Proj_DivMod(ir_node *proj) {
2494         ir_node *n = get_Proj_pred(proj);
2495         ir_node *b = get_DivMod_right(n);
2496         ir_node *confirm;
2497         long proj_nr;
2498
2499         if (value_not_zero(b, &confirm)) {
2500                 /* DivMod(x, y) && y != 0 */
2501                 proj_nr = get_Proj_proj(proj);
2502
2503                 if (proj_nr == pn_DivMod_X_except) {
2504                         /* we found an exception handler, remove it */
2505                         DBG_OPT_EXC_REM(proj);
2506                         return new_Bad();
2507                 } else if (proj_nr == pn_DivMod_M) {
2508                         ir_node *res = get_DivMod_mem(n);
2509                         ir_node *new_mem = get_irg_no_mem(current_ir_graph);
2510
2511                         if (confirm) {
2512                                 /* This node can only float up to the Confirm block */
2513                                 new_mem = new_r_Pin(current_ir_graph, get_nodes_block(confirm), new_mem);
2514                         }
2515                         set_irn_pinned(n, op_pin_state_floats);
2516                         /* this is a DivMod without exception, we can remove the memory edge */
2517                         set_DivMod_mem(n, get_irg_no_mem(current_ir_graph));
2518                         return res;
2519                 } else if (proj_nr == pn_DivMod_res_mod && get_DivMod_left(n) == b) {
2520                         /* a % a = 0 if a != 0 */
2521                         ir_mode *mode = get_irn_mode(proj);
2522                         ir_node *res  = new_Const(mode, get_mode_null(mode));
2523
2524                         DBG_OPT_CSTEVAL(n, res);
2525                         return res;
2526                 }
2527         }
2528         return proj;
2529 }  /* transform_node_Proj_DivMod */
2530
2531 /**
2532  * Optimizes jump tables (CondIs or CondIu) by removing all impossible cases.
2533  */
2534 static ir_node *transform_node_Proj_Cond(ir_node *proj) {
2535         if (get_opt_unreachable_code()) {
2536                 ir_node *n = get_Proj_pred(proj);
2537                 ir_node *b = get_Cond_selector(n);
2538
2539                 if (mode_is_int(get_irn_mode(b))) {
2540                         tarval *tb = value_of(b);
2541
2542                         if (tb != tarval_bad) {
2543                                 /* we have a constant switch */
2544                                 long num = get_Proj_proj(proj);
2545
2546                                 if (num != get_Cond_defaultProj(n)) { /* we cannot optimize default Proj's yet */
2547                                         if (get_tarval_long(tb) == num) {
2548                                                 /* Do NOT create a jump here, or we will have 2 control flow ops
2549                                                  * in a block. This case is optimized away in optimize_cf(). */
2550                                                 return proj;
2551                                         } else {
2552                                                 /* this case will NEVER be taken, kill it */
2553                                                 return new_Bad();
2554                                         }
2555                                 }
2556                         }
2557                 }
2558         }
2559         return proj;
2560 }  /* transform_node_Proj_Cond */
2561
2562 /**
2563  * Normalizes and optimizes Cmp nodes.
2564  */
2565 static ir_node *transform_node_Proj_Cmp(ir_node *proj) {
2566         if (get_opt_reassociation()) {
2567                 ir_node *n     = get_Proj_pred(proj);
2568                 ir_node *left  = get_Cmp_left(n);
2569                 ir_node *right = get_Cmp_right(n);
2570                 ir_node *c     = NULL;
2571                 tarval *tv     = NULL;
2572                 int changed    = 0;
2573                 ir_mode *mode  = NULL;
2574                 long proj_nr   = get_Proj_proj(proj);
2575
2576                 /*
2577                  * First step: normalize the compare op
2578                  * by placing the constant on the right site
2579                  * or moving the lower address node to the left.
2580                  * We ignore the case that both are constants
2581                  * this case should be optimized away.
2582                  */
2583                 if (get_irn_op(right) == op_Const) {
2584                         c = right;
2585                 } else if (get_irn_op(left) == op_Const) {
2586                         c     = left;
2587                         left  = right;
2588                         right = c;
2589
2590                         proj_nr = get_inversed_pnc(proj_nr);
2591                         changed |= 1;
2592                 } else if (get_irn_idx(left) > get_irn_idx(right)) {
2593                         ir_node *t = left;
2594
2595                         left  = right;
2596                         right = t;
2597
2598                         proj_nr = get_inversed_pnc(proj_nr);
2599                         changed |= 1;
2600                 }
2601
2602                 /*
2603                  * Second step: Try to reduce the magnitude
2604                  * of a constant. This may help to generate better code
2605                  * later and may help to normalize more compares.
2606                  * Of course this is only possible for integer values.
2607                  */
2608                 if (c) {
2609                         mode = get_irn_mode(c);
2610                         tv = get_Const_tarval(c);
2611
2612                         if (tv != tarval_bad) {
2613                                 /* the following optimization is possible on modes without Overflow
2614                                  * on Unary Minus or on == and !=:
2615                                  * -a CMP c  ==>  a swap(CMP) -c
2616                                  *
2617                                  * Beware: for two-complement Overflow may occur, so only == and != can
2618                                  * be optimized, see this:
2619                                  * -MININT < 0 =/=> MININT > 0 !!!
2620                                  */
2621                                 if (get_opt_constant_folding() && get_irn_op(left) == op_Minus &&
2622                                     (!mode_overflow_on_unary_Minus(mode) ||
2623                                     (mode_is_int(mode) && (proj_nr == pn_Cmp_Eq || proj_nr == pn_Cmp_Lg)))) {
2624                                         left = get_Minus_op(left);
2625                                         tv = tarval_sub(get_mode_null(mode), tv);
2626
2627                                         proj_nr = get_inversed_pnc(proj_nr);
2628                                         changed |= 2;
2629                                 }
2630
2631                                 /* for integer modes, we have more */
2632                                 if (mode_is_int(mode)) {
2633                                         /* Ne includes Unordered which is not possible on integers.
2634                                          * However, frontends often use this wrong, so fix it here */
2635                                         if (proj_nr & pn_Cmp_Uo) {
2636                                                 proj_nr &= ~pn_Cmp_Uo;
2637                                                 set_Proj_proj(proj, proj_nr);
2638                                         }
2639
2640                                         /* c > 0 : a < c  ==>  a <= (c-1)    a >= c  ==>  a > (c-1) */
2641                                         if ((proj_nr == pn_Cmp_Lt || proj_nr == pn_Cmp_Ge) &&
2642                                                 tarval_cmp(tv, get_mode_null(mode)) == pn_Cmp_Gt) {
2643                                                 tv = tarval_sub(tv, get_mode_one(mode));
2644
2645                                                 proj_nr ^= pn_Cmp_Eq;
2646                                                 changed |= 2;
2647                                         }
2648                                         /* c < 0 : a > c  ==>  a >= (c+1)    a <= c  ==>  a < (c+1) */
2649                                         else if ((proj_nr == pn_Cmp_Gt || proj_nr == pn_Cmp_Le) &&
2650                                                 tarval_cmp(tv, get_mode_null(mode)) == pn_Cmp_Lt) {
2651                                                 tv = tarval_add(tv, get_mode_one(mode));
2652
2653                                                 proj_nr ^= pn_Cmp_Eq;
2654                                                 changed |= 2;
2655                                         }
2656
2657                                         /* the following reassociations work only for == and != */
2658                                         if (proj_nr == pn_Cmp_Eq || proj_nr == pn_Cmp_Lg) {
2659
2660                                                 /* a-b == 0  ==>  a == b,  a-b != 0  ==>  a != b */
2661                                                 if (classify_tarval(tv) == TV_CLASSIFY_NULL && get_irn_op(left) == op_Sub) {
2662                                                         right = get_Sub_right(left);
2663                                                         left  = get_Sub_left(left);
2664
2665                                                         tv = value_of(right);
2666                                                         changed = 1;
2667                                                 }
2668
2669                                                 if (tv != tarval_bad) {
2670                                                         ir_op *op = get_irn_op(left);
2671
2672                                                         /* a-c1 == c2  ==>  a == c2+c1,  a-c1 != c2  ==>  a != c2+c1 */
2673                                                         if (op == op_Sub) {
2674                                                                 ir_node *c1 = get_Sub_right(left);
2675                                                                 tarval *tv2 = value_of(c1);
2676
2677                                                                 if (tv2 != tarval_bad) {
2678                                                                         tv2 = tarval_add(tv, value_of(c1));
2679
2680                                                                         if (tv2 != tarval_bad) {
2681                                                                                 left    = get_Sub_left(left);
2682                                                                                 tv      = tv2;
2683                                                                                 changed |= 2;
2684                                                                         }
2685                                                                 }
2686                                                         }
2687                                                         /* a+c1 == c2  ==>  a == c2-c1,  a+c1 != c2  ==>  a != c2-c1 */
2688                                                         else if (op == op_Add) {
2689                                                                 ir_node *a_l = get_Add_left(left);
2690                                                                 ir_node *a_r = get_Add_right(left);
2691                                                                 ir_node *a;
2692                                                                 tarval *tv2;
2693
2694                                                                 if (get_irn_op(a_l) == op_Const) {
2695                                                                         a = a_r;
2696                                                                         tv2 = value_of(a_l);
2697                                                                 } else {
2698                                                                         a = a_l;
2699                                                                         tv2 = value_of(a_r);
2700                                                                 }
2701
2702                                                                 if (tv2 != tarval_bad) {
2703                                                                         tv2 = tarval_sub(tv, tv2);
2704
2705                                                                         if (tv2 != tarval_bad) {
2706                                                                                 left    = a;
2707                                                                                 tv      = tv2;
2708                                                                                 changed |= 2;
2709                                                                         }
2710                                                                 }
2711                                                         }
2712                                                         /* -a == c ==> a == -c, -a != c ==> a != -c */
2713                                                         else if (op == op_Minus) {
2714                                                                 tarval *tv2 = tarval_sub(get_mode_null(mode), tv);
2715
2716                                                                 if (tv2 != tarval_bad) {
2717                                                                         left    = get_Minus_op(left);
2718                                                                         tv      = tv2;
2719                                                                         changed |= 2;
2720                                                                 }
2721                                                         }
2722                                                 }
2723                                         } /* == or != */
2724                                         /* the following reassociations work only for <= */
2725                                         else if (proj_nr == pn_Cmp_Le || proj_nr == pn_Cmp_Lt) {
2726                                                 if (tv != tarval_bad) {
2727                                                         ir_op *op = get_irn_op(left);
2728
2729                                                         /* c >= 0 : Abs(a) <= c  ==>  (unsigned)(a + c) <= 2*c */
2730                                                         if (op == op_Abs) {
2731                                                         }
2732                                                 }
2733                                         }
2734                                 } /* mode_is_int */
2735
2736                                 /*
2737                                  * optimization for AND:
2738                                  * Optimize:
2739                                  *   And(x, C) == C  ==>  And(x, C) != 0
2740                                  *   And(x, C) != C  ==>  And(X, C) == 0
2741                                  *
2742                                  * if C is a single Bit constant.
2743                                  */
2744                                 if ((proj_nr == pn_Cmp_Eq || proj_nr == pn_Cmp_Lg) &&
2745                                     (get_irn_op(left) == op_And)) {
2746                                         if (is_single_bit_tarval(tv)) {
2747                                                 /* check for Constant's match. We have check hare the tarvals,
2748                                                    because our const might be changed */
2749                                                 ir_node *la = get_And_left(left);
2750                                                 ir_node *ra = get_And_right(left);
2751                                                 if ((is_Const(la) && get_Const_tarval(la) == tv) ||
2752                                                     (is_Const(ra) && get_Const_tarval(ra) == tv)) {
2753                                                                 /* fine: do the transformation */
2754                                                                 tv = get_mode_null(get_tarval_mode(tv));
2755                                                                 proj_nr ^= pn_Cmp_Leg;
2756                                                                 changed |= 2;
2757                                                 }
2758                                         }
2759                                 }
2760                         } /* tarval != bad */
2761                 }
2762
2763                 if (changed) {
2764                         ir_node *block = get_irn_n(n, -1); /* Beware of get_nodes_Block() */
2765
2766                         if (changed & 2)      /* need a new Const */
2767                                 right = new_Const(mode, tv);
2768
2769                         /* create a new compare */
2770                         n = new_rd_Cmp(get_irn_dbg_info(n), current_ir_graph, block,
2771                                 left, right);
2772
2773                         set_Proj_pred(proj, n);
2774                         set_Proj_proj(proj, proj_nr);
2775                 }
2776         }
2777         return proj;
2778 }  /* transform_node_Proj_Cmp */
2779
2780 /**
2781  * Does all optimizations on nodes that must be done on it's Proj's
2782  * because of creating new nodes.
2783  */
2784 static ir_node *transform_node_Proj(ir_node *proj) {
2785         ir_node *n = get_Proj_pred(proj);
2786
2787         switch (get_irn_opcode(n)) {
2788         case iro_Div:
2789                 return transform_node_Proj_Div(proj);
2790
2791         case iro_Mod:
2792                 return transform_node_Proj_Mod(proj);
2793
2794         case iro_DivMod:
2795                 return transform_node_Proj_DivMod(proj);
2796
2797         case iro_Cond:
2798                 return transform_node_Proj_Cond(proj);
2799
2800         case iro_Cmp:
2801                 return transform_node_Proj_Cmp(proj);
2802
2803         case iro_Tuple:
2804                 /* should not happen, but if it does will be optimized away */
2805                 return equivalent_node_Proj(proj);
2806
2807         default:
2808                 /* do nothing */
2809                 return proj;
2810         }
2811 }  /* transform_node_Proj */
2812
2813 /**
2814  * Move Confirms down through Phi nodes.
2815  */
2816 static ir_node *transform_node_Phi(ir_node *phi) {
2817         int i, n;
2818         ir_mode *mode = get_irn_mode(phi);
2819
2820         if (mode_is_reference(mode)) {
2821                 n = get_irn_arity(phi);
2822
2823                 /* Beware of Phi0 */
2824                 if (n > 0) {
2825                         ir_node *pred = get_irn_n(phi, 0);
2826                         ir_node *bound, *new_Phi, *block, **in;
2827                         pn_Cmp  pnc;
2828
2829                         if (! is_Confirm(pred))
2830                                 return phi;
2831
2832                         bound = get_Confirm_bound(pred);
2833                         pnc   = get_Confirm_cmp(pred);
2834
2835                         NEW_ARR_A(ir_node *, in, n);
2836                         in[0] = get_Confirm_value(pred);
2837
2838                         for (i = 1; i < n; ++i) {
2839                                 pred = get_irn_n(phi, i);
2840
2841                                 if (! is_Confirm(pred) ||
2842                                         get_Confirm_bound(pred) != bound ||
2843                                         get_Confirm_cmp(pred) != pnc)
2844                                         return phi;
2845                                 in[i] = get_Confirm_value(pred);
2846                         }
2847                         /* move the Confirm nodes "behind" the Phi */
2848                         block = get_irn_n(phi, -1);
2849                         new_Phi = new_r_Phi(current_ir_graph, block, n, in, get_irn_mode(phi));
2850                         return new_r_Confirm(current_ir_graph, block, new_Phi, bound, pnc);
2851                 }
2852         }
2853         return phi;
2854 }  /* transform_node_Phi */
2855
2856 /**
2857  * Returns the operands of a commutative bin-op, if one operand is
2858  * a const, it is returned as the second one.
2859  */
2860 static void get_comm_Binop_Ops(ir_node *binop, ir_node **a, ir_node **c) {
2861         ir_node *op_a = get_binop_left(binop);
2862         ir_node *op_b = get_binop_right(binop);
2863
2864         assert(is_op_commutative(get_irn_op(binop)));
2865
2866         if (get_irn_op(op_a) == op_Const) {
2867                 *a = op_b;
2868                 *c = op_a;
2869         } else {
2870                 *a = op_a;
2871                 *c = op_b;
2872         }
2873 }  /* get_comm_Binop_Ops */
2874
2875 /**
2876  * Optimize a Or(And(Or(And(v,c4),c3),c2),c1) pattern if possible.
2877  * Such pattern may arise in bitfield stores.
2878  *
2879  * value  c4                  value      c4 & c2
2880  *    AND     c3                    AND           c1 | c3
2881  *        OR     c2      ===>               OR
2882  *           AND    c1
2883  *               OR
2884  */
2885 static ir_node *transform_node_Or_bf_store(ir_node *or) {
2886         ir_node *and, *c1;
2887         ir_node *or_l, *c2;
2888         ir_node *and_l, *c3;
2889         ir_node *value, *c4;
2890         ir_node *new_and, *new_const, *block;
2891         ir_mode *mode = get_irn_mode(or);
2892
2893         tarval *tv1, *tv2, *tv3, *tv4, *tv, *n_tv4, *n_tv2;
2894
2895         get_comm_Binop_Ops(or, &and, &c1);
2896         if ((get_irn_op(c1) != op_Const) || (get_irn_op(and) != op_And))
2897                 return or;
2898
2899         get_comm_Binop_Ops(and, &or_l, &c2);
2900         if ((get_irn_op(c2) != op_Const) || (get_irn_op(or_l) != op_Or))
2901                 return or;
2902
2903         get_comm_Binop_Ops(or_l, &and_l, &c3);
2904         if ((get_irn_op(c3) != op_Const) || (get_irn_op(and_l) != op_And))
2905                 return or;
2906
2907         get_comm_Binop_Ops(and_l, &value, &c4);
2908         if (get_irn_op(c4) != op_Const)
2909                 return or;
2910
2911         /* ok, found the pattern, check for conditions */
2912         assert(mode == get_irn_mode(and));
2913         assert(mode == get_irn_mode(or_l));
2914         assert(mode == get_irn_mode(and_l));
2915
2916         tv1 = get_Const_tarval(c1);
2917         tv2 = get_Const_tarval(c2);
2918         tv3 = get_Const_tarval(c3);
2919         tv4 = get_Const_tarval(c4);
2920
2921         tv = tarval_or(tv4, tv2);
2922         if (classify_tarval(tv) != TV_CLASSIFY_ALL_ONE) {
2923                 /* have at least one 0 at the same bit position */
2924                 return or;
2925         }
2926
2927         n_tv4 = tarval_not(tv4);
2928         if (tv3 != tarval_and(tv3, n_tv4)) {
2929                 /* bit in the or_mask is outside the and_mask */
2930                 return or;
2931         }
2932
2933         n_tv2 = tarval_not(tv2);
2934         if (tv1 != tarval_and(tv1, n_tv2)) {
2935                 /* bit in the or_mask is outside the and_mask */
2936                 return or;
2937         }
2938
2939         /* ok, all conditions met */
2940         block = get_irn_n(or, -1);
2941
2942         new_and = new_r_And(current_ir_graph, block,
2943                 value, new_r_Const(current_ir_graph, block, mode, tarval_and(tv4, tv2)), mode);
2944
2945         new_const = new_r_Const(current_ir_graph, block, mode, tarval_or(tv3, tv1));
2946
2947         set_Or_left(or, new_and);
2948         set_Or_right(or, new_const);
2949
2950         /* check for more */
2951         return transform_node_Or_bf_store(or);
2952 }  /* transform_node_Or_bf_store */
2953
2954 /**
2955  * Optimize an Or(shl(x, c), shr(x, bits - c)) into a Rot
2956  */
2957 static ir_node *transform_node_Or_Rot(ir_node *or) {
2958         ir_mode *mode = get_irn_mode(or);
2959         ir_node *shl, *shr, *block;
2960         ir_node *irn, *x, *c1, *c2, *v, *sub, *n;
2961         tarval *tv1, *tv2;
2962
2963         if (! mode_is_int(mode))
2964                 return or;
2965
2966         shl = get_binop_left(or);
2967         shr = get_binop_right(or);
2968
2969         if (get_irn_op(shl) == op_Shr) {
2970                 if (get_irn_op(shr) != op_Shl)
2971                         return or;
2972
2973                 irn = shl;
2974                 shl = shr;
2975                 shr = irn;
2976         } else if (get_irn_op(shl) != op_Shl) {
2977                 return or;
2978         } else if (get_irn_op(shr) != op_Shr) {
2979                 return or;
2980         }
2981         x = get_Shl_left(shl);
2982         if (x != get_Shr_left(shr))
2983                 return or;
2984
2985         c1 = get_Shl_right(shl);
2986         c2 = get_Shr_right(shr);
2987         if (get_irn_op(c1) == op_Const && get_irn_op(c2) == op_Const) {
2988                 tv1 = get_Const_tarval(c1);
2989                 if (! tarval_is_long(tv1))
2990                         return or;
2991
2992                 tv2 = get_Const_tarval(c2);
2993                 if (! tarval_is_long(tv2))
2994                         return or;
2995
2996                 if (get_tarval_long(tv1) + get_tarval_long(tv2)
2997                         != get_mode_size_bits(mode))
2998                         return or;
2999
3000                 /* yet, condition met */
3001                 block = get_irn_n(or, -1);
3002
3003                 n = new_r_Rot(current_ir_graph, block, x, c1, mode);
3004
3005                 DBG_OPT_ALGSIM1(or, shl, shr, n, FS_OPT_OR_SHFT_TO_ROT);
3006                 return n;
3007         } else if (get_irn_op(c1) == op_Sub) {
3008                 v   = c2;
3009                 sub = c1;
3010
3011                 if (get_Sub_right(sub) != v)
3012                         return or;
3013
3014                 c1 = get_Sub_left(sub);
3015                 if (get_irn_op(c1) != op_Const)
3016                         return or;
3017
3018                 tv1 = get_Const_tarval(c1);
3019                 if (! tarval_is_long(tv1))
3020                         return or;
3021
3022                 if (get_tarval_long(tv1) != get_mode_size_bits(mode))
3023                         return or;
3024
3025                 /* yet, condition met */
3026                 block = get_nodes_block(or);
3027
3028                 /* a Rot right is not supported, so use a rot left */
3029                 n =  new_r_Rot(current_ir_graph, block, x, sub, mode);
3030
3031                 DBG_OPT_ALGSIM0(or, n, FS_OPT_OR_SHFT_TO_ROT);
3032                 return n;
3033         } else if (get_irn_op(c2) == op_Sub) {
3034                 v   = c1;
3035                 sub = c2;
3036
3037                 c1 = get_Sub_left(sub);
3038                 if (get_irn_op(c1) != op_Const)
3039                         return or;
3040
3041                 tv1 = get_Const_tarval(c1);
3042                 if (! tarval_is_long(tv1))
3043                         return or;
3044
3045                 if (get_tarval_long(tv1) != get_mode_size_bits(mode))
3046                         return or;
3047
3048                 /* yet, condition met */
3049                 block = get_irn_n(or, -1);
3050
3051                 /* a Rot Left */
3052                 n = new_r_Rot(current_ir_graph, block, x, v, mode);
3053
3054                 DBG_OPT_ALGSIM0(or, n, FS_OPT_OR_SHFT_TO_ROT);
3055                 return n;
3056         }
3057
3058         return or;
3059 }  /* transform_node_Or_Rot */
3060
3061 /**
3062  * Transform an Or.
3063  */
3064 static ir_node *transform_node_Or(ir_node *n) {
3065         ir_node *c, *oldn = n;
3066         ir_node *a = get_Or_left(n);
3067         ir_node *b = get_Or_right(n);
3068
3069         HANDLE_BINOP_PHI(tarval_or, a,b,c);
3070
3071         n = transform_node_Or_bf_store(n);
3072         n = transform_node_Or_Rot(n);
3073
3074         return n;
3075 }  /* transform_node_Or */
3076
3077
3078 /* forward */
3079 static ir_node *transform_node(ir_node *n);
3080
3081 /**
3082  * Optimize (a >> c1) >> c2), works for Shr, Shrs, Shl.
3083  *
3084  * Should be moved to reassociation?
3085  */
3086 static ir_node *transform_node_shift(ir_node *n) {
3087         ir_node *left, *right;
3088         tarval *tv1, *tv2, *res;
3089         ir_mode *mode;
3090         int modulo_shf, flag;
3091
3092         left = get_binop_left(n);
3093
3094         /* different operations */
3095         if (get_irn_op(left) != get_irn_op(n))
3096                 return n;
3097
3098         right = get_binop_right(n);
3099         tv1 = value_of(right);
3100         if (tv1 == tarval_bad)
3101                 return n;
3102
3103         tv2 = value_of(get_binop_right(left));
3104         if (tv2 == tarval_bad)
3105                 return n;
3106
3107         res = tarval_add(tv1, tv2);
3108
3109         /* beware: a simple replacement works only, if res < modulo shift */
3110         mode = get_irn_mode(n);
3111
3112         flag = 0;
3113
3114         modulo_shf = get_mode_modulo_shift(mode);
3115         if (modulo_shf > 0) {
3116                 tarval *modulo = new_tarval_from_long(modulo_shf, get_tarval_mode(res));
3117
3118                 if (tarval_cmp(res, modulo) & pn_Cmp_Lt)
3119                         flag = 1;
3120         } else
3121                 flag = 1;
3122
3123         if (flag) {
3124                 /* ok, we can replace it */
3125                 ir_node *in[2], *irn, *block = get_irn_n(n, -1);
3126
3127                 in[0] = get_binop_left(left);
3128                 in[1] = new_r_Const(current_ir_graph, block, get_tarval_mode(res), res);
3129
3130                 irn = new_ir_node(NULL, current_ir_graph, block, get_irn_op(n), mode, 2, in);
3131
3132                 DBG_OPT_ALGSIM0(n, irn, FS_OPT_REASSOC_SHIFT);
3133
3134                 return transform_node(irn);
3135         }
3136         return n;
3137 }  /* transform_node_shift */
3138
3139 /**
3140  * Transform a Shr.
3141  */
3142 static ir_node *transform_node_Shr(ir_node *n) {
3143         ir_node *c, *oldn = n;
3144         ir_node *a = get_Shr_left(n);
3145         ir_node *b = get_Shr_right(n);
3146
3147         HANDLE_BINOP_PHI(tarval_shr, a, b, c);
3148         return transform_node_shift(n);
3149 }  /* transform_node_Shr */
3150
3151 /**
3152  * Transform a Shrs.
3153  */
3154 static ir_node *transform_node_Shrs(ir_node *n) {
3155         ir_node *c, *oldn = n;
3156         ir_node *a = get_Shrs_left(n);
3157         ir_node *b = get_Shrs_right(n);
3158
3159         HANDLE_BINOP_PHI(tarval_shrs, a, b, c);
3160         return transform_node_shift(n);
3161 }  /* transform_node_Shrs */
3162
3163 /**
3164  * Transform a Shl.
3165  */
3166 static ir_node *transform_node_Shl(ir_node *n) {
3167         ir_node *c, *oldn = n;
3168         ir_node *a = get_Shl_left(n);
3169         ir_node *b = get_Shl_right(n);
3170
3171         HANDLE_BINOP_PHI(tarval_shl, a, b, c);
3172         return transform_node_shift(n);
3173 }  /* transform_node_Shl */
3174
3175 /**
3176  * Remove dead blocks and nodes in dead blocks
3177  * in keep alive list.  We do not generate a new End node.
3178  */
3179 static ir_node *transform_node_End(ir_node *n) {
3180         int i, n_keepalives = get_End_n_keepalives(n);
3181
3182         for (i = 0; i < n_keepalives; ++i) {
3183                 ir_node *ka = get_End_keepalive(n, i);
3184                 if (is_Block(ka)) {
3185                         if (is_Block_dead(ka)) {
3186                                 set_End_keepalive(n, i, new_Bad());
3187                         }
3188                 } else if (is_irn_pinned_in_irg(ka) && is_Block_dead(get_nodes_block(ka)))
3189                         set_End_keepalive(n, i, new_Bad());
3190         }
3191         return n;
3192 }  /* transform_node_End */
3193
3194 /**
3195  * Optimize a Mux into some simpler cases.
3196  */
3197 static ir_node *transform_node_Mux(ir_node *n) {
3198         ir_node *oldn = n, *sel = get_Mux_sel(n);
3199         ir_mode *mode = get_irn_mode(n);
3200
3201         if (get_irn_op(sel) == op_Proj && !mode_honor_signed_zeros(mode)) {
3202                 ir_node *cmp = get_Proj_pred(sel);
3203                 long proj_nr = get_Proj_proj(sel);
3204                 ir_node *f   =  get_Mux_false(n);
3205                 ir_node *t   = get_Mux_true(n);
3206
3207                 if (get_irn_op(cmp) == op_Cmp && classify_Const(get_Cmp_right(cmp)) == CNST_NULL) {
3208                         ir_node *block = get_irn_n(n, -1);
3209
3210                         /*
3211                          * Note: normalization puts the constant on the right site,
3212                          * so we check only one case.
3213                          *
3214                          * Note further that these optimization work even for floating point
3215                          * with NaN's because -NaN == NaN.
3216                          * However, if +0 and -0 is handled differently, we cannot use the first one.
3217                          */
3218                         if (get_irn_op(f) == op_Minus &&
3219                                 get_Minus_op(f)   == t &&
3220                                 get_Cmp_left(cmp) == t) {
3221
3222                                 if (proj_nr == pn_Cmp_Ge || proj_nr == pn_Cmp_Gt) {
3223                                         /* Mux(a >=/> 0, -a, a)  ==>  Abs(a) */
3224                                         n = new_rd_Abs(get_irn_dbg_info(n),
3225                                                 current_ir_graph,
3226                                                 block,
3227                                                 t, mode);
3228                                         DBG_OPT_ALGSIM1(oldn, cmp, sel, n, FS_OPT_MUX_TO_ABS);
3229                                         return n;
3230                                 } else if (proj_nr == pn_Cmp_Le || proj_nr == pn_Cmp_Lt) {
3231                                         /* Mux(a <=/< 0, -a, a)  ==>  Minus(Abs(a)) */
3232                                         n = new_rd_Abs(get_irn_dbg_info(n),
3233                                                         current_ir_graph,
3234                                                         block,
3235                                                         t, mode);
3236                                         n = new_rd_Minus(get_irn_dbg_info(n),
3237                                                         current_ir_graph,
3238                                                         block,
3239                                                         n, mode);
3240
3241                                         DBG_OPT_ALGSIM1(oldn, cmp, sel, n, FS_OPT_MUX_TO_ABS);
3242                                         return n;
3243                                 }
3244                         } else if (get_irn_op(t) == op_Minus &&
3245                                    get_Minus_op(t)   == f &&
3246                                    get_Cmp_left(cmp) == f) {
3247
3248                                 if (proj_nr == pn_Cmp_Le || proj_nr == pn_Cmp_Lt) {
3249                                         /* Mux(a <=/< 0, a, -a)  ==>  Abs(a) */
3250                                         n = new_rd_Abs(get_irn_dbg_info(n),
3251                                                         current_ir_graph,
3252                                                         block,
3253                                                         f, mode);
3254                                         DBG_OPT_ALGSIM1(oldn, cmp, sel, n, FS_OPT_MUX_TO_ABS);
3255                                         return n;
3256                                 } else if (proj_nr == pn_Cmp_Ge || proj_nr == pn_Cmp_Gt) {
3257                                         /* Mux(a >=/> 0, a, -a)  ==>  Minus(Abs(a)) */
3258                                         n = new_rd_Abs(get_irn_dbg_info(n),
3259                                                         current_ir_graph,
3260                                                         block,
3261                                                         f, mode);
3262                                         n = new_rd_Minus(get_irn_dbg_info(n),
3263                                                         current_ir_graph,
3264                                                         block,
3265                                                         n, mode);
3266
3267                                         DBG_OPT_ALGSIM1(oldn, cmp, sel, n, FS_OPT_MUX_TO_ABS);
3268                                         return n;
3269                                 }
3270                         }
3271
3272                         if (mode_is_int(mode) && mode_is_signed(mode) &&
3273                                 get_mode_arithmetic(mode) == irma_twos_complement) {
3274                                 ir_node *x = get_Cmp_left(cmp);
3275
3276                                 /* the following optimization works only with signed integer two-complement mode */
3277
3278                                 if (mode == get_irn_mode(x)) {
3279                                         /*
3280                                          * FIXME: this restriction is two rigid, as it would still
3281                                          * work if mode(x) = Hs and mode == Is, but at least it removes
3282                                          * all wrong cases.
3283                                          */
3284                                         if ((proj_nr == pn_Cmp_Lt || proj_nr == pn_Cmp_Le) &&
3285                                             classify_Const(t) == CNST_ALL_ONE &&
3286                                             classify_Const(f) == CNST_NULL) {
3287                                                 /*
3288                                                  * Mux(x:T </<= 0, 0, -1) -> Shrs(x, sizeof_bits(T) - 1)
3289                                                  * Conditions:
3290                                                  * T must be signed.
3291                                                  */
3292                                                 n = new_rd_Shrs(get_irn_dbg_info(n),
3293                                                                 current_ir_graph, block, x,
3294                                                                 new_r_Const_long(current_ir_graph, block, mode_Iu,
3295                                                                 get_mode_size_bits(mode) - 1),
3296                                                                 mode);
3297                                                 DBG_OPT_ALGSIM1(oldn, cmp, sel, n, FS_OPT_MUX_TO_SHR);
3298                                                 return n;
3299                                         } else if ((proj_nr == pn_Cmp_Gt || proj_nr == pn_Cmp_Ge) &&
3300                                                    classify_Const(t) == CNST_ONE &&
3301                                                    classify_Const(f) == CNST_NULL) {
3302                                                 /*
3303                                                  * Mux(x:T >/>= 0, 0, 1) -> Shr(-x, sizeof_bits(T) - 1)
3304                                                  * Conditions:
3305                                                  * T must be signed.
3306                                                  */
3307                                                 n = new_rd_Shr(get_irn_dbg_info(n),
3308                                                         current_ir_graph, block,
3309                                                         new_r_Minus(current_ir_graph, block, x, mode),
3310                                                         new_r_Const_long(current_ir_graph, block, mode_Iu,
3311                                                         get_mode_size_bits(mode) - 1),
3312                                                         mode);
3313                                                 DBG_OPT_ALGSIM1(oldn, cmp, sel, n, FS_OPT_MUX_TO_SHR);
3314                                                 return n;
3315                                         }
3316                                 }
3317                         }
3318                 }
3319         }
3320         return arch_transform_node_Mux(n);
3321 }  /* transform_node_Mux */
3322
3323 /**
3324  * Optimize a Psi into some simpler cases.
3325  */
3326 static ir_node *transform_node_Psi(ir_node *n) {
3327         if (is_Mux(n))
3328                 return transform_node_Mux(n);
3329
3330         return n;
3331 }  /* transform_node_Psi */
3332
3333 /**
3334  * Tries several [inplace] [optimizing] transformations and returns an
3335  * equivalent node.  The difference to equivalent_node() is that these
3336  * transformations _do_ generate new nodes, and thus the old node must
3337  * not be freed even if the equivalent node isn't the old one.
3338  */
3339 static ir_node *transform_node(ir_node *n) {
3340         if (n->op->ops.transform_node)
3341                 n = n->op->ops.transform_node(n);
3342         return n;
3343 }  /* transform_node */
3344
3345 /**
3346  * Sets the default transform node operation for an ir_op_ops.
3347  *
3348  * @param code   the opcode for the default operation
3349  * @param ops    the operations initialized
3350  *
3351  * @return
3352  *    The operations.
3353  */
3354 static ir_op_ops *firm_set_default_transform_node(ir_opcode code, ir_op_ops *ops)
3355 {
3356 #define CASE(a)                                 \
3357         case iro_##a:                                 \
3358                 ops->transform_node  = transform_node_##a;  \
3359                 break
3360
3361         switch (code) {
3362         CASE(Add);
3363         CASE(Sub);
3364         CASE(Mul);
3365         CASE(Div);
3366         CASE(Mod);
3367         CASE(DivMod);
3368         CASE(Abs);
3369         CASE(Cond);
3370         CASE(And);
3371         CASE(Or);
3372         CASE(Eor);
3373         CASE(Minus);
3374         CASE(Not);
3375         CASE(Cast);
3376         CASE(Proj);
3377         CASE(Phi);
3378         CASE(Sel);
3379         CASE(Shr);
3380         CASE(Shrs);
3381         CASE(Shl);
3382         CASE(End);
3383         CASE(Mux);
3384         CASE(Psi);
3385         default:
3386           /* leave NULL */;
3387         }
3388
3389         return ops;
3390 #undef CASE
3391 }  /* firm_set_default_transform_node */
3392
3393
3394 /* **************** Common Subexpression Elimination **************** */
3395
3396 /** The size of the hash table used, should estimate the number of nodes
3397     in a graph. */
3398 #define N_IR_NODES 512
3399
3400 /** Compares the attributes of two Const nodes. */
3401 static int node_cmp_attr_Const(ir_node *a, ir_node *b) {
3402         return (get_Const_tarval(a) != get_Const_tarval(b))
3403             || (get_Const_type(a) != get_Const_type(b));
3404 }  /* node_cmp_attr_Const */
3405
3406 /** Compares the attributes of two Proj nodes. */
3407 static int node_cmp_attr_Proj(ir_node *a, ir_node *b) {
3408         return get_irn_proj_attr (a) != get_irn_proj_attr (b);
3409 }  /* node_cmp_attr_Proj */
3410
3411 /** Compares the attributes of two Filter nodes. */
3412 static int node_cmp_attr_Filter(ir_node *a, ir_node *b) {
3413         return get_Filter_proj(a) != get_Filter_proj(b);
3414 }  /* node_cmp_attr_Filter */
3415
3416 /** Compares the attributes of two Alloc nodes. */
3417 static int node_cmp_attr_Alloc(ir_node *a, ir_node *b) {
3418         return (get_irn_alloc_attr(a).where != get_irn_alloc_attr(b).where)
3419             || (get_irn_alloc_attr(a).type != get_irn_alloc_attr(b).type);
3420 }  /* node_cmp_attr_Alloc */
3421
3422 /** Compares the attributes of two Free nodes. */
3423 static int node_cmp_attr_Free(ir_node *a, ir_node *b) {
3424         return (get_irn_free_attr(a).where != get_irn_free_attr(b).where)
3425             || (get_irn_free_attr(a).type != get_irn_free_attr(b).type);
3426 }  /* node_cmp_attr_Free */
3427
3428 /** Compares the attributes of two SymConst nodes. */
3429 static int node_cmp_attr_SymConst(ir_node *a, ir_node *b) {
3430         return (get_irn_symconst_attr(a).num != get_irn_symconst_attr(b).num)
3431             || (get_irn_symconst_attr(a).sym.type_p != get_irn_symconst_attr(b).sym.type_p)
3432             || (get_irn_symconst_attr(a).tp != get_irn_symconst_attr(b).tp);
3433 }  /* node_cmp_attr_SymConst */
3434
3435 /** Compares the attributes of two Call nodes. */
3436 static int node_cmp_attr_Call(ir_node *a, ir_node *b) {
3437         return (get_irn_call_attr(a) != get_irn_call_attr(b));
3438 }  /* node_cmp_attr_Call */
3439
3440 /** Compares the attributes of two Sel nodes. */
3441 static int node_cmp_attr_Sel(ir_node *a, ir_node *b) {
3442         return (get_irn_sel_attr(a).ent->kind  != get_irn_sel_attr(b).ent->kind)
3443             || (get_irn_sel_attr(a).ent->name    != get_irn_sel_attr(b).ent->name)
3444             || (get_irn_sel_attr(a).ent->owner   != get_irn_sel_attr(b).ent->owner)
3445             || (get_irn_sel_attr(a).ent->ld_name != get_irn_sel_attr(b).ent->ld_name)
3446             || (get_irn_sel_attr(a).ent->type    != get_irn_sel_attr(b).ent->type);
3447 }  /* node_cmp_attr_Sel */
3448
3449 /** Compares the attributes of two Phi nodes. */
3450 static int node_cmp_attr_Phi(ir_node *a, ir_node *b) {
3451         return get_irn_phi_attr (a) != get_irn_phi_attr (b);
3452 }  /* node_cmp_attr_Phi */
3453
3454 /** Compares the attributes of two Conv nodes. */
3455 static int node_cmp_attr_Conv(ir_node *a, ir_node *b) {
3456         return get_Conv_strict(a) != get_Conv_strict(b);
3457 }  /* node_cmp_attr_Conv */
3458
3459 /** Compares the attributes of two Cast nodes. */
3460 static int node_cmp_attr_Cast(ir_node *a, ir_node *b) {
3461         return get_Cast_type(a) != get_Cast_type(b);
3462 }  /* node_cmp_attr_Cast */
3463
3464 /** Compares the attributes of two Load nodes. */
3465 static int node_cmp_attr_Load(ir_node *a, ir_node *b) {
3466         if (get_Load_volatility(a) == volatility_is_volatile ||
3467             get_Load_volatility(b) == volatility_is_volatile)
3468                 /* NEVER do CSE on volatile Loads */
3469                 return 1;
3470
3471         return get_Load_mode(a) != get_Load_mode(b);
3472 }  /* node_cmp_attr_Load */
3473
3474 /** Compares the attributes of two Store nodes. */
3475 static int node_cmp_attr_Store(ir_node *a, ir_node *b) {
3476         /* NEVER do CSE on volatile Stores */
3477         return (get_Store_volatility(a) == volatility_is_volatile ||
3478                 get_Store_volatility(b) == volatility_is_volatile);
3479 }  /* node_cmp_attr_Store */
3480
3481 /** Compares the attributes of two Confirm nodes. */
3482 static int node_cmp_attr_Confirm(ir_node *a, ir_node *b) {
3483         return (get_Confirm_cmp(a) != get_Confirm_cmp(b));
3484 }  /* node_cmp_attr_Confirm */
3485
3486 /**
3487  * Set the default node attribute compare operation for an ir_op_ops.
3488  *
3489  * @param code   the opcode for the default operation
3490  * @param ops    the operations initialized
3491  *
3492  * @return
3493  *    The operations.
3494  */
3495 static ir_op_ops *firm_set_default_node_cmp_attr(ir_opcode code, ir_op_ops *ops)
3496 {
3497 #define CASE(a)                              \
3498         case iro_##a:                              \
3499                 ops->node_cmp_attr  = node_cmp_attr_##a; \
3500                 break
3501
3502         switch (code) {
3503         CASE(Const);
3504         CASE(Proj);
3505         CASE(Filter);
3506         CASE(Alloc);
3507         CASE(Free);
3508         CASE(SymConst);
3509         CASE(Call);
3510         CASE(Sel);
3511         CASE(Phi);
3512         CASE(Conv);
3513         CASE(Cast);
3514         CASE(Load);
3515         CASE(Store);
3516         CASE(Confirm);
3517         default:
3518           /* leave NULL */;
3519         }
3520
3521         return ops;
3522 #undef CASE
3523 }  /* firm_set_default_node_cmp_attr */
3524
3525 /*
3526  * Compare function for two nodes in the hash table. Gets two
3527  * nodes as parameters.  Returns 0 if the nodes are a cse.
3528  */
3529 int identities_cmp(const void *elt, const void *key) {
3530         ir_node *a, *b;
3531         int i, irn_arity_a;
3532
3533         a = (void *)elt;
3534         b = (void *)key;
3535
3536         if (a == b) return 0;
3537
3538         if ((get_irn_op(a) != get_irn_op(b)) ||
3539             (get_irn_mode(a) != get_irn_mode(b))) return 1;
3540
3541         /* compare if a's in and b's in are of equal length */
3542         irn_arity_a = get_irn_intra_arity (a);
3543         if (irn_arity_a != get_irn_intra_arity(b))
3544                 return 1;
3545
3546         /* for block-local cse and op_pin_state_pinned nodes: */
3547         if (!get_opt_global_cse() || (get_irn_pinned(a) == op_pin_state_pinned)) {
3548                 if (get_irn_intra_n(a, -1) != get_irn_intra_n(b, -1))
3549                         return 1;
3550         }
3551
3552         /* compare a->in[0..ins] with b->in[0..ins] */
3553         for (i = 0; i < irn_arity_a; i++)
3554                 if (get_irn_intra_n(a, i) != get_irn_intra_n(b, i))
3555                         return 1;
3556
3557         /*
3558          * here, we already now that the nodes are identical except their
3559          * attributes
3560          */
3561         if (a->op->ops.node_cmp_attr)
3562                 return a->op->ops.node_cmp_attr(a, b);
3563
3564         return 0;
3565 }  /* identities_cmp */
3566
3567 /*
3568  * Calculate a hash value of a node.
3569  */
3570 unsigned ir_node_hash(ir_node *node) {
3571         unsigned h;
3572         int i, irn_arity;
3573
3574         if (node->op == op_Const) {
3575                 /* special value for const, as they only differ in their tarval. */
3576                 h = HASH_PTR(node->attr.con.tv);
3577                 h = 9*h + HASH_PTR(get_irn_mode(node));
3578         } else if (node->op == op_SymConst) {
3579                 /* special value for const, as they only differ in their symbol. */
3580                 h = HASH_PTR(node->attr.symc.sym.type_p);
3581                 h = 9*h + HASH_PTR(get_irn_mode(node));
3582         } else {
3583
3584                 /* hash table value = 9*(9*(9*(9*(9*arity+in[0])+in[1])+ ...)+mode)+code */
3585                 h = irn_arity = get_irn_intra_arity(node);
3586
3587                 /* consider all in nodes... except the block if not a control flow. */
3588                 for (i = is_cfop(node) ? -1 : 0;  i < irn_arity;  i++) {
3589                         h = 9*h + HASH_PTR(get_irn_intra_n(node, i));
3590                 }
3591
3592                 /* ...mode,... */
3593                 h = 9*h + HASH_PTR(get_irn_mode(node));
3594                 /* ...and code */
3595                 h = 9*h + HASH_PTR(get_irn_op(node));
3596         }
3597
3598         return h;
3599 }  /* ir_node_hash */
3600
3601 pset *new_identities(void) {
3602         return new_pset(identities_cmp, N_IR_NODES);
3603 }  /* new_identities */
3604
3605 void del_identities(pset *value_table) {
3606         del_pset(value_table);
3607 }  /* del_identities */
3608
3609 /**
3610  * Return the canonical node computing the same value as n.
3611  *
3612  * @param value_table  The value table
3613  * @param n            The node to lookup
3614  *
3615  * Looks up the node in a hash table.
3616  *
3617  * For Const nodes this is performed in the constructor, too.  Const
3618  * nodes are extremely time critical because of their frequent use in
3619  * constant string arrays.
3620  */
3621 static INLINE ir_node *identify(pset *value_table, ir_node *n) {
3622         ir_node *o = NULL;
3623
3624         if (!value_table) return n;
3625
3626         if (get_opt_reassociation()) {
3627                 if (is_op_commutative(get_irn_op(n))) {
3628                         ir_node *l = get_binop_left(n);
3629                         ir_node *r = get_binop_right(n);
3630
3631                         /* for commutative operators perform  a OP b == b OP a */
3632                         if (get_irn_idx(l) > get_irn_idx(r)) {
3633                                 set_binop_left(n, r);
3634                                 set_binop_right(n, l);
3635                         }
3636                 }
3637         }
3638
3639         o = pset_find(value_table, n, ir_node_hash(n));
3640         if (!o) return n;
3641
3642         DBG_OPT_CSE(n, o);
3643
3644         return o;
3645 }  /* identify */
3646
3647 /**
3648  * During construction we set the op_pin_state_pinned flag in the graph right when the
3649  * optimization is performed.  The flag turning on procedure global cse could
3650  * be changed between two allocations.  This way we are safe.
3651  */
3652 static INLINE ir_node *identify_cons(pset *value_table, ir_node *n) {
3653         ir_node *old = n;
3654
3655         n = identify(value_table, n);
3656         if (get_irn_n(old, -1) != get_irn_n(n, -1))
3657                 set_irg_pinned(current_ir_graph, op_pin_state_floats);
3658         return n;
3659 }  /* identify_cons */
3660
3661 /*
3662  * Return the canonical node computing the same value as n.
3663  * Looks up the node in a hash table, enters it in the table
3664  * if it isn't there yet.
3665  */
3666 ir_node *identify_remember(pset *value_table, ir_node *n) {
3667         ir_node *o = NULL;
3668
3669         if (!value_table) return n;
3670
3671         if (get_opt_reassociation()) {
3672                 if (is_op_commutative(get_irn_op(n))) {
3673                         ir_node *l = get_binop_left(n);
3674                         ir_node *r = get_binop_right(n);
3675
3676                         /* for commutative operators perform  a OP b == b OP a */
3677                         if (l > r) {
3678                                 set_binop_left(n, r);
3679                                 set_binop_right(n, l);
3680                         }
3681                 }
3682         }
3683
3684         /* lookup or insert in hash table with given hash key. */
3685         o = pset_insert (value_table, n, ir_node_hash (n));
3686
3687         if (o != n) {
3688                 DBG_OPT_CSE(n, o);
3689         }
3690
3691         return o;
3692 }  /* identify_remember */
3693
3694 /* Add a node to the identities value table. */
3695 void add_identities(pset *value_table, ir_node *node) {
3696         if (get_opt_cse() && is_no_Block(node))
3697                 identify_remember(value_table, node);
3698 }  /* add_identities */
3699
3700 /* Visit each node in the value table of a graph. */
3701 void visit_all_identities(ir_graph *irg, irg_walk_func visit, void *env) {
3702         ir_node *node;
3703         ir_graph *rem = current_ir_graph;
3704
3705         current_ir_graph = irg;
3706         foreach_pset(irg->value_table, node)
3707                 visit(node, env);
3708         current_ir_graph = rem;
3709 }  /* visit_all_identities */
3710
3711 /**
3712  * Garbage in, garbage out. If a node has a dead input, i.e., the
3713  * Bad node is input to the node, return the Bad node.
3714  */
3715 static INLINE ir_node *gigo(ir_node *node) {
3716         int i, irn_arity;
3717         ir_op *op = get_irn_op(node);
3718
3719         /* remove garbage blocks by looking at control flow that leaves the block
3720            and replacing the control flow by Bad. */
3721         if (get_irn_mode(node) == mode_X) {
3722                 ir_node *block = get_nodes_block(skip_Proj(node));
3723
3724                 /* Don't optimize nodes in immature blocks. */
3725                 if (!get_Block_matured(block)) return node;
3726                 /* Don't optimize End, may have Bads. */
3727                 if (op == op_End) return node;
3728
3729                 if (is_Block(block)) {
3730                         irn_arity = get_irn_arity(block);
3731                         for (i = 0; i < irn_arity; i++) {
3732                                 if (!is_Bad(get_irn_n(block, i)))
3733                                         break;
3734                         }
3735                         if (i == irn_arity) {
3736                                 ir_graph *irg = get_irn_irg(block);
3737                                 /* the start block is never dead */
3738                                 if (block != get_irg_start_block(irg)
3739                                         && block != get_irg_end_block(irg))
3740                                         return new_Bad();
3741                         }
3742                 }
3743         }
3744
3745         /* Blocks, Phis and Tuples may have dead inputs, e.g., if one of the
3746            blocks predecessors is dead. */
3747         if (op != op_Block && op != op_Phi && op != op_Tuple) {
3748                 irn_arity = get_irn_arity(node);
3749
3750                 /*
3751                  * Beware: we can only read the block of a non-floating node.
3752                  */
3753                 if (is_irn_pinned_in_irg(node) &&
3754                         is_Block_dead(get_nodes_block(node)))
3755                         return new_Bad();
3756
3757                 for (i = 0; i < irn_arity; i++) {
3758                         ir_node *pred = get_irn_n(node, i);
3759
3760                         if (is_Bad(pred))
3761                                 return new_Bad();
3762 #if 0
3763                         /* Propagating Unknowns here seems to be a bad idea, because
3764                            sometimes we need a node as a input and did not want that
3765                            it kills it's user.
3766                            However, it might be useful to move this into a later phase
3767                            (if you think that optimizing such code is useful). */
3768                         if (is_Unknown(pred) && mode_is_data(get_irn_mode(node)))
3769                                 return new_Unknown(get_irn_mode(node));
3770 #endif
3771                 }
3772         }
3773 #if 0
3774         /* With this code we violate the agreement that local_optimize
3775            only leaves Bads in Block, Phi and Tuple nodes. */
3776         /* If Block has only Bads as predecessors it's garbage. */
3777         /* If Phi has only Bads as predecessors it's garbage. */
3778         if ((op == op_Block && get_Block_matured(node)) || op == op_Phi)  {
3779                 irn_arity = get_irn_arity(node);
3780                 for (i = 0; i < irn_arity; i++) {
3781                         if (!is_Bad(get_irn_n(node, i))) break;
3782                 }
3783                 if (i == irn_arity) node = new_Bad();
3784         }
3785 #endif
3786         return node;
3787 }  /* gigo */
3788
3789 /**
3790  * These optimizations deallocate nodes from the obstack.
3791  * It can only be called if it is guaranteed that no other nodes
3792  * reference this one, i.e., right after construction of a node.
3793  *
3794  * @param n   The node to optimize
3795  *
3796  * current_ir_graph must be set to the graph of the node!
3797  */
3798 ir_node *optimize_node(ir_node *n) {
3799         tarval *tv;
3800         ir_node *oldn = n;
3801         ir_opcode iro = get_irn_opcode(n);
3802
3803         /* Always optimize Phi nodes: part of the construction. */
3804         if ((!get_opt_optimize()) && (iro != iro_Phi)) return n;
3805
3806         /* constant expression evaluation / constant folding */
3807         if (get_opt_constant_folding()) {
3808                 /* neither constants nor Tuple values can be evaluated */
3809                 if (iro != iro_Const && (get_irn_mode(n) != mode_T)) {
3810                         /* try to evaluate */
3811                         tv = computed_value(n);
3812                         if (tv != tarval_bad) {
3813                                 ir_node *nw;
3814                                 ir_type *old_tp = get_irn_type(n);
3815                                 int i, arity = get_irn_arity(n);
3816                                 int node_size;
3817
3818                                 /*
3819                                  * Try to recover the type of the new expression.
3820                                  */
3821                                 for (i = 0; i < arity && !old_tp; ++i)
3822                                         old_tp = get_irn_type(get_irn_n(n, i));
3823
3824                                 /*
3825                                  * we MUST copy the node here temporary, because it's still needed
3826                                  * for DBG_OPT_CSTEVAL
3827                                  */
3828                                 node_size = offsetof(ir_node, attr) +  n->op->attr_size;
3829                                 oldn = alloca(node_size);
3830
3831                                 memcpy(oldn, n, node_size);
3832                                 CLONE_ARR_A(ir_node *, oldn->in, n->in);
3833
3834                                 /* ARG, copy the in array, we need it for statistics */
3835                                 memcpy(oldn->in, n->in, ARR_LEN(n->in) * sizeof(n->in[0]));
3836
3837                                 /* note the inplace edges module */
3838                                 edges_node_deleted(n, current_ir_graph);
3839
3840                                 /* evaluation was successful -- replace the node. */
3841                                 irg_kill_node(current_ir_graph, n);
3842                                 nw = new_Const(get_tarval_mode (tv), tv);
3843
3844                                 if (old_tp && get_type_mode(old_tp) == get_tarval_mode (tv))
3845                                         set_Const_type(nw, old_tp);
3846                                 DBG_OPT_CSTEVAL(oldn, nw);
3847                                 return nw;
3848                         }
3849                 }
3850         }
3851
3852         /* remove unnecessary nodes */
3853         if (get_opt_constant_folding() ||
3854             (iro == iro_Phi)  ||   /* always optimize these nodes. */
3855             (iro == iro_Id)   ||
3856             (iro == iro_Proj) ||
3857             (iro == iro_Block)  )  /* Flags tested local. */
3858                 n = equivalent_node(n);
3859
3860         optimize_preds(n);                  /* do node specific optimizations of nodes predecessors. */
3861
3862         /* Common Subexpression Elimination.
3863          *
3864          * Checks whether n is already available.
3865          * The block input is used to distinguish different subexpressions. Right
3866          * now all nodes are op_pin_state_pinned to blocks, i.e., the CSE only finds common
3867          * subexpressions within a block.
3868          */
3869         if (get_opt_cse())
3870                 n = identify_cons(current_ir_graph->value_table, n);
3871
3872         if (n != oldn) {
3873                 edges_node_deleted(oldn, current_ir_graph);
3874
3875                 /* We found an existing, better node, so we can deallocate the old node. */
3876                 irg_kill_node(current_ir_graph, oldn);
3877                 return n;
3878         }
3879
3880         /* Some more constant expression evaluation that does not allow to
3881            free the node. */
3882         iro = get_irn_opcode(n);
3883         if (get_opt_constant_folding() ||
3884             (iro == iro_Cond) ||
3885             (iro == iro_Proj))     /* Flags tested local. */
3886                 n = transform_node(n);
3887
3888         /* Remove nodes with dead (Bad) input.
3889            Run always for transformation induced Bads. */
3890         n = gigo (n);
3891
3892         /* Now we have a legal, useful node. Enter it in hash table for CSE */
3893         if (get_opt_cse() && (get_irn_opcode(n) != iro_Block)) {
3894                 n = identify_remember(current_ir_graph->value_table, n);
3895         }
3896
3897         return n;
3898 }  /* optimize_node */
3899
3900
3901 /**
3902  * These optimizations never deallocate nodes (in place).  This can cause dead
3903  * nodes lying on the obstack.  Remove these by a dead node elimination,
3904  * i.e., a copying garbage collection.
3905  */
3906 ir_node *optimize_in_place_2(ir_node *n) {
3907         tarval *tv;
3908         ir_node *oldn = n;
3909         ir_opcode iro = get_irn_opcode(n);
3910
3911         if (!get_opt_optimize() && (get_irn_op(n) != op_Phi)) return n;
3912
3913         /* constant expression evaluation / constant folding */
3914         if (get_opt_constant_folding()) {
3915                 /* neither constants nor Tuple values can be evaluated */
3916                 if (iro != iro_Const && get_irn_mode(n) != mode_T) {
3917                         /* try to evaluate */
3918                         tv = computed_value(n);
3919                         if (tv != tarval_bad) {
3920                                 /* evaluation was successful -- replace the node. */
3921                                 ir_type *old_tp = get_irn_type(n);
3922                                 int i, arity = get_irn_arity(n);
3923
3924                                 /*
3925                                  * Try to recover the type of the new expression.
3926                                  */
3927                                 for (i = 0; i < arity && !old_tp; ++i)
3928                                         old_tp = get_irn_type(get_irn_n(n, i));
3929
3930                                 n = new_Const(get_tarval_mode(tv), tv);
3931
3932                                 if (old_tp && get_type_mode(old_tp) == get_tarval_mode(tv))
3933                                         set_Const_type(n, old_tp);
3934
3935                                 DBG_OPT_CSTEVAL(oldn, n);
3936                                 return n;
3937                         }
3938                 }
3939         }
3940
3941         /* remove unnecessary nodes */
3942         if (get_opt_constant_folding() ||
3943             (iro == iro_Phi)  ||   /* always optimize these nodes. */
3944             (iro == iro_Id)   ||   /* ... */
3945             (iro == iro_Proj) ||   /* ... */
3946             (iro == iro_Block)  )  /* Flags tested local. */
3947                 n = equivalent_node(n);
3948
3949         optimize_preds(n);                  /* do node specific optimizations of nodes predecessors. */
3950
3951         /** common subexpression elimination **/
3952         /* Checks whether n is already available. */
3953         /* The block input is used to distinguish different subexpressions.  Right
3954            now all nodes are op_pin_state_pinned to blocks, i.e., the cse only finds common
3955            subexpressions within a block. */
3956         if (get_opt_cse()) {
3957                 n = identify(current_ir_graph->value_table, n);
3958         }
3959
3960         /* Some more constant expression evaluation. */
3961         iro = get_irn_opcode(n);
3962         if (get_opt_constant_folding() ||
3963                 (iro == iro_Cond) ||
3964                 (iro == iro_Proj))     /* Flags tested local. */
3965                 n = transform_node(n);
3966
3967         /* Remove nodes with dead (Bad) input.
3968            Run always for transformation induced Bads.  */
3969         n = gigo(n);
3970
3971         /* Now we can verify the node, as it has no dead inputs any more. */
3972         irn_vrfy(n);
3973
3974         /* Now we have a legal, useful node. Enter it in hash table for cse.
3975            Blocks should be unique anyways.  (Except the successor of start:
3976            is cse with the start block!) */
3977         if (get_opt_cse() && (get_irn_opcode(n) != iro_Block))
3978                 n = identify_remember(current_ir_graph->value_table, n);
3979
3980         return n;
3981 }  /* optimize_in_place_2 */
3982
3983 /**
3984  * Wrapper for external use, set proper status bits after optimization.
3985  */
3986 ir_node *optimize_in_place(ir_node *n) {
3987         /* Handle graph state */
3988         assert(get_irg_phase_state(current_ir_graph) != phase_building);
3989
3990         if (get_opt_global_cse())
3991                 set_irg_pinned(current_ir_graph, op_pin_state_floats);
3992         if (get_irg_outs_state(current_ir_graph) == outs_consistent)
3993                 set_irg_outs_inconsistent(current_ir_graph);
3994
3995         /* FIXME: Maybe we could also test whether optimizing the node can
3996            change the control graph. */
3997         set_irg_doms_inconsistent(current_ir_graph);
3998         return optimize_in_place_2(n);
3999 }  /* optimize_in_place */
4000
4001 /*
4002  * Sets the default operation for an ir_ops.
4003  */
4004 ir_op_ops *firm_set_default_operations(ir_opcode code, ir_op_ops *ops) {
4005         ops = firm_set_default_computed_value(code, ops);
4006         ops = firm_set_default_equivalent_node(code, ops);
4007         ops = firm_set_default_transform_node(code, ops);
4008         ops = firm_set_default_node_cmp_attr(code, ops);
4009         ops = firm_set_default_get_type(code, ops);
4010         ops = firm_set_default_get_type_attr(code, ops);
4011         ops = firm_set_default_get_entity_attr(code, ops);
4012
4013         return ops;
4014 }  /* firm_set_default_operations */