Fixed indentation.
[libfirm] / ir / ir / irverify.c
1 /*
2  * This file is part of libFirm.
3  * Copyright (C) 2012 University of Karlsruhe.
4  */
5
6 /**
7  * @file
8  * @brief    Check irnodes for correctness.
9  * @author   Christian Schaefer, Goetz Lindenmaier, Till Riedel, Michael Beck
10  */
11 #include "config.h"
12
13 #include "irnode_t.h"
14 #include "irprog.h"
15 #include "irop_t.h"
16 #include "irgraph_t.h"
17 #include "irverify_t.h"
18 #include "irgwalk.h"
19 #include "irdump.h"
20 #include "irdom_t.h"
21 #include "irprintf.h"
22 #include "irouts.h"
23 #include "irflag_t.h"
24 #include "irpass_t.h"
25 #include "irnodeset.h"
26 #include "ircons.h"
27
28 const char *firm_verify_failure_msg;
29
30 #ifndef NDEBUG
31
32 /**
33  * little helper for NULL modes
34  */
35 static const char *get_mode_name_ex(ir_mode *mode)
36 {
37         if (! mode)
38                 return "<no mode>";
39         return get_mode_name(mode);
40 }
41
42 /** the last IRG, on which a verification error was found */
43 static ir_graph *last_irg_error = NULL;
44
45 /**
46  * print the name of the entity of an verification failure
47  *
48  * @param node  the node caused the failure
49  */
50 static void show_entity_failure(const ir_node *node)
51 {
52         ir_graph *irg = get_irn_irg(node);
53
54         if (last_irg_error == irg)
55                 return;
56
57         last_irg_error = irg;
58
59         if (irg == get_const_code_irg()) {
60                 fprintf(stderr, "\nFIRM: irn_verify_irg() <of CONST_CODE_IRG> failed\n");
61         } else {
62                 ir_entity *ent = get_irg_entity(irg);
63
64                 if (ent) {
65                         ir_type *ent_type = get_entity_owner(ent);
66                         ir_fprintf(stderr, "\nFIRM: irn_verify_irg() %+F::%s failed\n", ent_type, get_entity_name(ent));
67                 } else {
68                         fprintf(stderr, "\nFIRM: irn_verify_irg() <IRG %p> failed\n", (void *)irg);
69                 }
70         }
71 }
72
73 static const char *get_irn_modename(const ir_node *node)
74 {
75         ir_mode *mode = get_irn_mode(node);
76         return get_mode_name(mode);
77 }
78
79 /**
80  * Prints a failure for a Node
81  */
82 static void show_node_failure(const ir_node *n)
83 {
84         show_entity_failure(n);
85         fprintf(stderr, "  node %ld %s%s\n" ,
86                 get_irn_node_nr(n),
87                 get_irn_opname(n), get_irn_modename(n)
88         );
89 }
90
91 /**
92  * Prints a failure message for a binop
93  */
94 static void show_binop_failure(const ir_node *n, const char *text)
95 {
96         ir_node *left  = get_binop_left(n);
97         ir_node *right = get_binop_right(n);
98
99         show_entity_failure(n);
100         fprintf(stderr, "  node %ld %s%s(%s%s, %s%s) did not match (%s)\n",
101                 get_irn_node_nr(n),
102                 get_irn_opname(n), get_irn_modename(n),
103                 get_irn_opname(left), get_irn_modename(left),
104                 get_irn_opname(right), get_irn_modename(right),
105                 text);
106 }
107
108 /**
109  * Prints a failure message for an unop
110  */
111 static void show_unop_failure(const ir_node *n, const char *text)
112 {
113         ir_node *op  = get_unop_op(n);
114
115         show_entity_failure(n);
116         fprintf(stderr, "  node %ld %s%s(%s%s) did not match (%s)\n",
117                 get_irn_node_nr(n),
118                 get_irn_opname(n), get_irn_modename(n),
119                 get_irn_opname(op), get_irn_modename(op),
120                 text);
121 }
122
123 /**
124  * Prints a failure message for an op with 3 operands
125  */
126 static void show_triop_failure(const ir_node *n, const char *text)
127 {
128         ir_node *op0  = get_irn_n(n, 0);
129         ir_node *op1  = get_irn_n(n, 1);
130         ir_node *op2  = get_irn_n(n, 2);
131
132         show_entity_failure(n);
133         fprintf(stderr, "  of node %ld %s%s(%s%s, %s%s, %s%s) did not match (%s)\n",
134                 get_irn_node_nr(n),
135                 get_irn_opname(n), get_irn_modename(n),
136                 get_irn_opname(op0), get_irn_modename(op0),
137                 get_irn_opname(op1), get_irn_modename(op1),
138                 get_irn_opname(op2), get_irn_modename(op2),
139                 text);
140 }
141
142 /**
143  * Prints a failure message for a proj
144  */
145 static void show_proj_failure(const ir_node *n)
146 {
147         ir_node *op  = get_Proj_pred(n);
148         int proj     = get_Proj_proj(n);
149
150         show_entity_failure(n);
151         fprintf(stderr, "  node %ld %s%s %d(%s%s) failed\n" ,
152                 get_irn_node_nr(n),
153                 get_irn_opname(n), get_irn_modename(n), proj,
154                 get_irn_opname(op), get_irn_modename(op));
155 }
156
157 /**
158  * Prints a failure message for a proj from Start
159  */
160 static void show_proj_mode_failure(const ir_node *n, ir_type *ty)
161 {
162         long proj  = get_Proj_proj(n);
163         ir_mode *m = get_type_mode(ty);
164         char type_name[256];
165         ir_print_type(type_name, sizeof(type_name), ty);
166
167         show_entity_failure(n);
168         fprintf(stderr, "  Proj %ld mode %s proj %ld (type %s mode %s) failed\n" ,
169                 get_irn_node_nr(n),
170                 get_irn_modename(n),
171                 proj,
172                 type_name,
173                 get_mode_name_ex(m));
174 }
175
176 /**
177  * Show a node and a graph
178  */
179 static void show_node_on_graph(const ir_graph *irg, const ir_node *n)
180 {
181         ir_fprintf(stderr, "\nFIRM: irn_verify_irg() of %+F, node %+F\n", irg, n);
182 }
183
184 /**
185  * Show call parameters
186  */
187 static void show_call_param(const ir_node *n, ir_type *mt)
188 {
189         char type_name[256];
190         ir_print_type(type_name, sizeof(type_name), mt);
191
192         show_entity_failure(n);
193         fprintf(stderr, "  Call type-check failed: %s(", type_name);
194         size_t n_method_params = get_method_n_params(mt);
195         for (size_t i = 0; i < n_method_params; ++i) {
196                 fprintf(stderr, "%s ", get_mode_name_ex(get_type_mode(get_method_param_type(mt, i))));
197         }
198         fprintf(stderr, ") != CALL(");
199
200         int n_params = get_Call_n_params(n);
201         for (int i = 0; i < n_params; ++i) {
202                 fprintf(stderr, "%s ", get_mode_name_ex(get_irn_mode(get_Call_param(n, i))));
203         }
204         fprintf(stderr, ")\n");
205 }
206
207 /**
208  * Show return modes
209  */
210 static void show_return_modes(const ir_graph *irg, const ir_node *n,
211                               ir_type *mt, int i)
212 {
213         ir_entity *ent = get_irg_entity(irg);
214
215         show_entity_failure(n);
216         fprintf(stderr, "  Return node %ld in entity \"%s\" mode %s different from type mode %s\n",
217                 get_irn_node_nr(n), get_entity_name(ent),
218                 get_mode_name_ex(get_irn_mode(get_Return_res(n, i))),
219                 get_mode_name_ex(get_type_mode(get_method_res_type(mt, i)))
220         );
221 }
222
223 /**
224  * Show return number of results
225  */
226 static void show_return_nres(const ir_graph *irg, const ir_node *n, ir_type *mt)
227 {
228         ir_entity *ent = get_irg_entity(irg);
229
230         show_entity_failure(n);
231         fprintf(stderr, "  Return node %ld in entity \"%s\" has %lu results different from type %lu\n",
232                 get_irn_node_nr(n), get_entity_name(ent),
233                 (unsigned long) get_Return_n_ress(n),
234                 (unsigned long) get_method_n_ress(mt));
235 }
236
237 /**
238  * Show Phi input
239  */
240 static void show_phi_failure(const ir_node *phi, const ir_node *pred, int pos)
241 {
242         (void) pos;
243         show_entity_failure(phi);
244         fprintf(stderr, "  Phi node %ld has mode %s different from predeccessor node %ld mode %s\n",
245                 get_irn_node_nr(phi), get_mode_name_ex(get_irn_mode(phi)),
246                 get_irn_node_nr(pred), get_mode_name_ex(get_irn_mode(pred)));
247 }
248
249 /**
250  * Show Phi inputs
251  */
252 static void show_phi_inputs(const ir_node *phi, const ir_node *block)
253 {
254         show_entity_failure(phi);
255         fprintf(stderr, "  Phi node %ld has %d inputs, its Block %ld has %d\n",
256                 get_irn_node_nr(phi),   get_irn_arity(phi),
257                 get_irn_node_nr(block), get_irn_arity(block));
258 }
259
260 #endif /* #ifndef NDEBUG */
261
262 /**
263  * verify a Proj(Start) node
264  */
265 static int verify_node_Proj_Start(const ir_node *p)
266 {
267         ir_mode *mode = get_irn_mode(p);
268         long proj     = get_Proj_proj(p);
269
270         ASSERT_AND_RET_DBG(
271                 (
272                         (proj == pn_Start_X_initial_exec && mode == mode_X) ||
273                         (proj == pn_Start_M              && mode == mode_M) ||
274                         (proj == pn_Start_P_frame_base   && mode_is_reference(mode)) ||
275                         (proj == pn_Start_T_args         && mode == mode_T)
276                 ),
277                 "wrong Proj from Start", 0,
278                 show_proj_failure(p);
279         );
280         return 1;
281 }
282
283 /**
284  * verify a Proj(Cond) node
285  */
286 static int verify_node_Proj_Cond(const ir_node *p)
287 {
288         ir_mode *mode = get_irn_mode(p);
289         long     proj = get_Proj_proj(p);
290
291         ASSERT_AND_RET_DBG(
292                 mode == mode_X && (proj == pn_Cond_false || proj == pn_Cond_true),
293                 "wrong Proj from Cond", 0,
294                 show_proj_failure(p);
295         );
296         return 1;
297 }
298
299 static int verify_node_Proj_Switch(const ir_node *p)
300 {
301         ir_mode *mode = get_irn_mode(p);
302         long     pn   = get_Proj_proj(p);
303         ir_node *pred = get_Proj_pred(p);
304         ASSERT_AND_RET_DBG(
305                 mode == mode_X && (pn >= 0 && pn < (long)get_Switch_n_outs(pred)),
306                 "wrong Proj from Switch", 0,
307                 show_proj_failure(p);
308         );
309         return 1;
310 }
311
312 /**
313  * verify a Proj(Raise) node
314  */
315 static int verify_node_Proj_Raise(const ir_node *p)
316 {
317         ir_mode *mode = get_irn_mode(p);
318         long proj     = get_Proj_proj(p);
319
320         ASSERT_AND_RET_DBG(
321                 ((proj == pn_Raise_X && mode == mode_X) || (proj == pn_Raise_M && mode == mode_M)),
322                 "wrong Proj from Raise", 0,
323                 show_proj_failure(p);
324         );
325         return 1;
326 }
327
328 /**
329  * verify a Proj(InstOf) node
330  */
331 static int verify_node_Proj_InstOf(const ir_node *p)
332 {
333         ir_mode *mode = get_irn_mode(p);
334         long proj     = get_Proj_proj(p);
335
336         ASSERT_AND_RET_DBG(
337                 (
338                         (proj == pn_InstOf_M         && mode == mode_M) ||
339                         (proj == pn_InstOf_X_regular && mode == mode_X) ||
340                         (proj == pn_InstOf_X_except  && mode == mode_X) ||
341                         (proj == pn_InstOf_res       && mode_is_reference(mode))
342                 ),
343                 "wrong Proj from InstOf", 0,
344                 show_proj_failure(p);
345         );
346         return 1;
347 }
348
349 /**
350  * verify a Proj(Call) node
351  */
352 static int verify_node_Proj_Call(const ir_node *p)
353 {
354         ir_mode *mode = get_irn_mode(p);
355         ir_node *n    = get_Proj_pred(p);
356         long proj     = get_Proj_proj(p);
357
358         ASSERT_AND_RET_DBG(
359                 (
360                         (proj == pn_Call_M                && mode == mode_M) ||
361                         (proj == pn_Call_X_regular        && mode == mode_X) ||
362                         (proj == pn_Call_X_except         && mode == mode_X) ||
363                         (proj == pn_Call_T_result         && mode == mode_T)
364                 ),
365                 "wrong Proj from Call", 0,
366                 show_proj_failure(p);
367         );
368         /* if we have exception flow, we must have a real Memory input */
369         if (proj == pn_Call_X_regular)
370                 ASSERT_AND_RET(
371                         !is_NoMem(get_Call_mem(n)),
372                         "Regular Proj from FunctionCall", 0);
373         else if (proj == pn_Call_X_except)
374                 ASSERT_AND_RET(
375                         !is_NoMem(get_Call_mem(n)),
376                         "Exception Proj from FunctionCall", 0);
377         return 1;
378 }
379
380 /**
381  * verify a Proj(Div) node
382  */
383 static int verify_node_Proj_Div(const ir_node *p)
384 {
385         ir_mode *mode = get_irn_mode(p);
386         ir_node *n    = get_Proj_pred(p);
387         long proj     = get_Proj_proj(p);
388
389         ASSERT_AND_RET_DBG(
390                 (
391                         (proj == pn_Div_M         && mode == mode_M) ||
392                         (proj == pn_Div_X_regular && mode == mode_X) ||
393                         (proj == pn_Div_X_except  && mode == mode_X) ||
394                         (proj == pn_Div_res       && mode == get_Div_resmode(n))
395                 ),
396                 "wrong Proj from Div", 0,
397                 show_proj_failure(p);
398         );
399         if (proj == pn_Div_X_regular)
400                 ASSERT_AND_RET(
401                         get_irn_pinned(n) == op_pin_state_pinned,
402                         "Regular Proj from unpinned Div", 0);
403         else if (proj == pn_Div_X_except)
404                 ASSERT_AND_RET(
405                         get_irn_pinned(n) == op_pin_state_pinned,
406                         "Exception Proj from unpinned Div", 0);
407         else if (proj == pn_Div_M)
408                 ASSERT_AND_RET(
409                         get_irn_pinned(n) == op_pin_state_pinned,
410                         "Memory Proj from unpinned Div", 0);
411         return 1;
412 }
413
414 /**
415  * verify a Proj(Mod) node
416  */
417 static int verify_node_Proj_Mod(const ir_node *p)
418 {
419         ir_mode *mode = get_irn_mode(p);
420         ir_node *n    = get_Proj_pred(p);
421         long proj     = get_Proj_proj(p);
422
423         ASSERT_AND_RET_DBG(
424                 (
425                         (proj == pn_Mod_M         && mode == mode_M) ||
426                         (proj == pn_Mod_X_regular && mode == mode_X) ||
427                         (proj == pn_Mod_X_except  && mode == mode_X) ||
428                         (proj == pn_Mod_res       && mode == get_Mod_resmode(n))
429                 ),
430                 "wrong Proj from Mod", 0,
431                 show_proj_failure(p);
432         );
433         if (proj == pn_Mod_X_regular)
434                 ASSERT_AND_RET(
435                         get_irn_pinned(n) == op_pin_state_pinned,
436                         "Regular Proj from unpinned Mod", 0);
437         else if (proj == pn_Mod_X_except)
438                 ASSERT_AND_RET(
439                         get_irn_pinned(n) == op_pin_state_pinned,
440                         "Exception Proj from unpinned Mod", 0);
441         else if (proj == pn_Mod_M)
442                 ASSERT_AND_RET(
443                         get_irn_pinned(n) == op_pin_state_pinned,
444                         "Memory Proj from unpinned Div", 0);
445         return 1;
446 }
447
448 /**
449  * verify a Proj(Load) node
450  */
451 static int verify_node_Proj_Load(const ir_node *p)
452 {
453         ir_mode *mode = get_irn_mode(p);
454         ir_node *n    = get_Proj_pred(p);
455         long proj     = get_Proj_proj(p);
456
457         if (proj == pn_Load_res) {
458                 ASSERT_AND_RET_DBG(
459                         mode_is_data(mode) && mode == get_Load_mode(n),
460                         "wrong data Proj from Load", 0,
461                         show_proj_failure(p);
462                 );
463         } else {
464                 ASSERT_AND_RET_DBG(
465                         (
466                                 (proj == pn_Load_M         && mode == mode_M) ||
467                                 (proj == pn_Load_X_regular && mode == mode_X) ||
468                                 (proj == pn_Load_X_except  && mode == mode_X)
469                         ),
470                         "wrong Proj from Load", 0,
471                         show_proj_failure(p);
472                 );
473         }
474         if (proj == pn_Load_X_regular) {
475                 ASSERT_AND_RET(
476                         get_irn_pinned(n) == op_pin_state_pinned,
477                         "Regular Proj from unpinned Load", 0);
478         } else if (proj == pn_Load_X_except) {
479                 ASSERT_AND_RET(
480                         get_irn_pinned(n) == op_pin_state_pinned,
481                         "Exception Proj from unpinned Load", 0);
482         }
483         return 1;
484 }
485
486 /**
487  * verify a Proj(Store) node
488  */
489 static int verify_node_Proj_Store(const ir_node *p)
490 {
491         ir_mode *mode = get_irn_mode(p);
492         ir_node *n    = get_Proj_pred(p);
493         long proj     = get_Proj_proj(p);
494
495         ASSERT_AND_RET_DBG(
496                 (
497                         (proj == pn_Store_M         && mode == mode_M) ||
498                         (proj == pn_Store_X_regular && mode == mode_X) ||
499                         (proj == pn_Store_X_except  && mode == mode_X)
500                 ),
501                 "wrong Proj from Store", 0,
502                 show_proj_failure(p);
503         );
504         if (proj == pn_Store_X_regular) {
505                 ASSERT_AND_RET(
506                         get_irn_pinned(n) == op_pin_state_pinned,
507                         "Regular Proj from unpinned Store", 0);
508         } else if (proj == pn_Store_X_except) {
509                 ASSERT_AND_RET(
510                         get_irn_pinned(n) == op_pin_state_pinned,
511                         "Exception Proj from unpinned Store", 0);
512         }
513         return 1;
514 }
515
516 /**
517  * verify a Proj(Alloc) node
518  */
519 static int verify_node_Proj_Alloc(const ir_node *p)
520 {
521         ir_mode *mode = get_irn_mode(p);
522         long proj     = get_Proj_proj(p);
523
524         ASSERT_AND_RET_DBG(
525                 (
526                         (proj == pn_Alloc_M         && mode == mode_M) ||
527                         (proj == pn_Alloc_X_regular && mode == mode_X) ||
528                         (proj == pn_Alloc_X_except  && mode == mode_X) ||
529                         (proj == pn_Alloc_res       && mode_is_reference(mode))
530                 ),
531                 "wrong Proj from Alloc", 0,
532                 show_proj_failure(p);
533         );
534         return 1;
535 }
536
537 /**
538  * verify a Proj(Proj) node
539  */
540 static int verify_node_Proj_Proj(const ir_node *p)
541 {
542         ir_mode *mode     = get_irn_mode(p);
543         ir_node *pred     = get_Proj_pred(p);
544         ir_node *predpred = get_Proj_pred(pred);
545         long     proj     = get_Proj_proj(p);
546         long     nr       = get_Proj_proj(pred);
547
548         switch (get_irn_opcode(predpred)) {
549         case iro_Start: {
550                 ir_graph *irg = get_irn_irg(p);
551                 ir_type  *mt  = get_entity_type(get_irg_entity(irg));
552
553                 if (nr == pn_Start_T_args) {
554                         ASSERT_AND_RET(
555                                 (proj >= 0 && mode_is_datab(mode)),
556                                 "wrong Proj from Proj from Start", 0);
557                         ASSERT_AND_RET(
558                                 (proj < (int)get_method_n_params(mt)),
559                                 "More Projs for args than args in type", 0
560                                 );
561                         ir_type *param_type = get_method_param_type(mt, proj);
562                         if (!irg_is_constrained(irg, IR_GRAPH_CONSTRAINT_BACKEND)) {
563                                 ASSERT_AND_RET_DBG(
564                                                 (mode == get_type_mode(param_type)),
565                                                 "Mode of Proj from Start doesn't match mode of param type.", 0,
566                                                 show_proj_mode_failure(p, get_method_param_type(mt, proj));
567                                                 );
568                         }
569                 }
570                 break;
571         }
572
573         case iro_Call: {
574                 ASSERT_AND_RET(
575                         (proj >= 0 && mode_is_datab(mode)),
576                         "wrong Proj from Proj from Call", 0);
577                 ir_type *mt = get_Call_type(predpred);
578                 ASSERT_AND_RET(is_unknown_type(mt) || is_Method_type(mt),
579                                 "wrong call type on call", 0);
580                 ASSERT_AND_RET(
581                         (proj < (int)get_method_n_ress(mt)),
582                         "More Projs for results than results in type.", 0);
583                 ir_type *res_type = get_method_res_type(mt, proj);
584                 /* value result */
585                 if ((mode_is_reference(mode)) &&
586                         (is_compound_type(res_type) || is_Array_type(res_type)))
587                         break;
588
589                 ASSERT_AND_RET(
590                         (mode == get_type_mode(get_method_res_type(mt, proj))),
591                         "Mode of Proj from Call doesn't match mode of result type.", 0);
592                 break;
593         }
594
595         case iro_Tuple:
596                 /* We don't test */
597                 break;
598
599         default:
600                 /* ASSERT_AND_RET(0, "Unknown opcode", 0); */
601                 break;
602         }
603         return 1;
604 }
605
606 /**
607  * verify a Proj(Tuple) node
608  */
609 static int verify_node_Proj_Tuple(const ir_node *p)
610 {
611         (void) p;
612         /* We don't test */
613         return 1;
614 }
615
616 /**
617  * verify a Proj(CopyB) node
618  */
619 static int verify_node_Proj_CopyB(const ir_node *p)
620 {
621         ir_mode *mode = get_irn_mode(p);
622         ir_node *n    = get_Proj_pred(p);
623         long proj     = get_Proj_proj(p);
624
625         ASSERT_AND_RET_DBG(
626                 (
627                         (proj == pn_CopyB_M         && mode == mode_M) ||
628                         (proj == pn_CopyB_X_regular && mode == mode_X) ||
629                         (proj == pn_CopyB_X_except  && mode == mode_X)
630                 ),
631                 "wrong Proj from CopyB", 0,
632                 show_proj_failure(p);
633         );
634         if (proj == pn_CopyB_X_regular)
635                 ASSERT_AND_RET(
636                         get_irn_pinned(n) == op_pin_state_pinned,
637                         "Regular Proj from unpinned CopyB", 0);
638         else if (proj == pn_CopyB_X_except)
639                 ASSERT_AND_RET(
640                         get_irn_pinned(n) == op_pin_state_pinned,
641                         "Exception Proj from unpinned CopyB", 0);
642         return 1;
643 }
644
645 static int verify_node_Proj_fragile(const ir_node *node)
646 {
647         ir_node *pred             = get_Proj_pred(node);
648         int      throws_exception = ir_throws_exception(pred);
649         ASSERT_AND_RET((!is_x_except_Proj(node) || throws_exception)
650             && (!is_x_regular_Proj(node) || throws_exception),
651             "X_except und X_regular Proj only allowed when throws_exception is set",
652             0);
653         return 1;
654 }
655
656 /**
657  * verify a Proj node
658  */
659 static int verify_node_Proj(const ir_node *p)
660 {
661         ir_graph *irg = get_irn_irg(p);
662         ir_node *pred;
663         ir_op *op;
664
665         pred = skip_Id(get_Proj_pred(p));
666         ASSERT_AND_RET(get_irn_mode(pred) == mode_T, "mode of a 'projed' node is not Tuple", 0);
667         ASSERT_AND_RET(get_irg_pinned(irg) == op_pin_state_floats || get_nodes_block(pred) == get_nodes_block(p), "Proj must be in same block as its predecessor", 0);
668
669         if (is_fragile_op(pred)) {
670                 int res = verify_node_Proj_fragile(p);
671                 if (res != 1)
672                         return res;
673         }
674
675         op = get_irn_op(pred);
676         if (op->ops.verify_proj_node)
677                 return op->ops.verify_proj_node(p);
678
679         /* all went ok */
680         return 1;
681 }
682
683 /**
684  * verify a Block node
685  */
686 static int verify_node_Block(const ir_node *n)
687 {
688         ir_graph *irg = get_irn_irg(n);
689         int i;
690
691         for (i = get_Block_n_cfgpreds(n) - 1; i >= 0; --i) {
692                 ir_node *pred         = get_Block_cfgpred(n, i);
693                 ir_node *skipped_pred = skip_Proj(skip_Tuple(pred));
694                 ASSERT_AND_RET(get_irn_mode(pred) == mode_X,
695                         "Block node must have a mode_X predecessor", 0);
696                 ASSERT_AND_RET(is_cfop(skipped_pred) || is_Bad(skipped_pred), "Block predecessor must be a cfop (or Bad)", 0);
697         }
698
699         if (n == get_irg_start_block(irg)) {
700                 ASSERT_AND_RET(get_Block_n_cfgpreds(n) == 0, "Start Block node", 0);
701         }
702
703         if (n == get_irg_end_block(irg) && !irg_is_constrained(irg, IR_GRAPH_CONSTRAINT_BACKEND)) {
704                 /* End block may only have Return, Raise or fragile ops as preds. */
705                 for (i = get_Block_n_cfgpreds(n) - 1; i >= 0; --i) {
706                         ir_node *pred =  skip_Proj(get_Block_cfgpred(n, i));
707                         if (is_Proj(pred) || is_Tuple(pred))
708                                 break;   /*  We can not test properly.  How many tuples are there? */
709                         ASSERT_AND_RET(
710                                 (
711                                         is_Return(pred) ||
712                                         is_Bad(pred)    ||
713                                         is_Raise(pred)  ||
714                                         is_fragile_op(pred)
715                                 ),
716                                 "End Block node", 0);
717                 }
718         }
719         /*  irg attr must == graph we are in. */
720         ASSERT_AND_RET(((get_irn_irg(n) && get_irn_irg(n) == irg)), "Block node has wrong irg attribute", 0);
721         return 1;
722 }
723
724 /**
725  * verify a Start node
726  */
727 static int verify_node_Start(const ir_node *n)
728 {
729         ir_mode *mymode = get_irn_mode(n);
730
731         ASSERT_AND_RET(
732                 /* Start: BB --> X x M x ref x data1 x ... x datan x ref */
733                 mymode == mode_T, "Start node", 0
734                 );
735         return 1;
736 }
737
738 /**
739  * verify a Jmp node
740  */
741 static int verify_node_Jmp(const ir_node *n)
742 {
743         ir_mode *mymode = get_irn_mode(n);
744
745         ASSERT_AND_RET(
746                 /* Jmp: BB --> X */
747                 mymode == mode_X, "Jmp node", 0
748         );
749         return 1;
750 }
751
752 /**
753  * verify an IJmp node
754  */
755 static int verify_node_IJmp(const ir_node *n)
756 {
757         ir_mode *mymode  = get_irn_mode(n);
758         ir_mode *op1mode = get_irn_mode(get_IJmp_target(n));
759
760         ASSERT_AND_RET(
761                 /* IJmp: BB x ref --> X */
762                 mymode == mode_X && mode_is_reference(op1mode), "IJmp node", 0
763         );
764         return 1;
765 }
766
767 /**
768  * verify a Cond node
769  */
770 static int verify_node_Cond(const ir_node *n)
771 {
772         ir_mode *mymode  = get_irn_mode(n);
773         ir_mode *op1mode = get_irn_mode(get_Cond_selector(n));
774
775         ASSERT_AND_RET(op1mode == mode_b, "Cond operand not mode_b", 0);
776         ASSERT_AND_RET(mymode == mode_T, "Cond mode is not a tuple", 0);
777         return 1;
778 }
779
780 static int verify_switch_table(const ir_node *n)
781 {
782         const ir_switch_table *table     = get_Switch_table(n);
783         unsigned               n_outs    = get_Switch_n_outs(n);
784         ir_node               *selector  = get_Switch_selector(n);
785         ir_mode               *mode      = get_irn_mode(selector);
786         size_t                 n_entries;
787         size_t                 e;
788
789         ASSERT_AND_RET(table != NULL, "switch table is NULL", 0);
790
791         n_entries = ir_switch_table_get_n_entries(table);
792         for (e = 0; e < n_entries; ++e) {
793                 const ir_switch_table_entry *entry
794                         = ir_switch_table_get_entry_const(table, e);
795                 if (entry->pn == 0)
796                         continue;
797                 ASSERT_AND_RET(entry->min != NULL && entry->max != NULL,
798                                "switch table entry without min+max value", 0);
799                 ASSERT_AND_RET(get_tarval_mode(entry->min) == mode &&
800                                get_tarval_mode(entry->max) == mode,
801                                "switch table entry with wrong modes", 0);
802                 ASSERT_AND_RET(tarval_cmp(entry->min, entry->max) != ir_relation_greater,
803                                "switch table entry without min+max value", 0);
804                 ASSERT_AND_RET(entry->pn >= 0 && entry->pn < (long)n_outs,
805                                            "switch table entry with invalid proj number", 0);
806         }
807         return 1;
808 }
809
810 static int verify_node_Switch(const ir_node *n)
811 {
812         ir_mode *mymode  = get_irn_mode(n);
813         ir_mode *op1mode = get_irn_mode(get_Switch_selector(n));
814         if (!verify_switch_table(n))
815                 return 0;
816
817         ASSERT_AND_RET(mode_is_int(op1mode), "Switch operand not integer", 0);
818         ASSERT_AND_RET(mymode == mode_T, "Switch mode is not a tuple", 0);
819         return 1;
820 }
821
822 /**
823  * verify a Return node
824  */
825 static int verify_node_Return(const ir_node *n)
826 {
827         ir_graph *irg      = get_irn_irg(n);
828         ir_mode  *mymode   = get_irn_mode(n);
829         ir_mode  *mem_mode = get_irn_mode(get_Return_mem(n));
830         ir_type  *mt;
831         int       i;
832
833         /* Return: BB x M x data1 x ... x datan --> X */
834
835         ASSERT_AND_RET( mem_mode == mode_M, "Return node", 0 );  /* operand M */
836
837         for (i = get_Return_n_ress(n) - 1; i >= 0; --i) {
838                 ASSERT_AND_RET( mode_is_datab(get_irn_mode(get_Return_res(n, i))), "Return node", 0 );  /* operand datai */
839         }
840         ASSERT_AND_RET( mymode == mode_X, "Result X", 0 );   /* result X */
841         /* Compare returned results with result types of method type */
842         mt = get_entity_type(get_irg_entity(irg));
843         ASSERT_AND_RET_DBG((size_t)get_Return_n_ress(n) == get_method_n_ress(mt),
844                 "Number of results for Return doesn't match number of results in type.", 0,
845                 show_return_nres(irg, n, mt););
846         for (i = get_Return_n_ress(n) - 1; i >= 0; --i) {
847                 ir_type *res_type = get_method_res_type(mt, i);
848
849                 if (irg_is_constrained(irg, IR_GRAPH_CONSTRAINT_BACKEND)) {
850                         if (is_atomic_type(res_type)) {
851                                 ASSERT_AND_RET_DBG(
852                                         get_irn_mode(get_Return_res(n, i)) == get_type_mode(res_type),
853                                         "Mode of result for Return doesn't match mode of result type.", 0,
854                                         show_return_modes(irg, n, mt, i);
855                                 );
856                         } else {
857                                 ASSERT_AND_RET_DBG(
858                                         mode_is_reference(get_irn_mode(get_Return_res(n, i))),
859                                         "Mode of result for Return doesn't match mode of result type.", 0,
860                                         show_return_modes(irg, n, mt, i);
861                                 );
862                         }
863                 }
864         }
865         return 1;
866 }
867
868 /**
869  * verify a Raise node
870  */
871 static int verify_node_Raise(const ir_node *n)
872 {
873         ir_mode *mymode  = get_irn_mode(n);
874         ir_mode *op1mode = get_irn_mode(get_Raise_mem(n));
875         ir_mode *op2mode = get_irn_mode(get_Raise_exo_ptr(n));
876
877         ASSERT_AND_RET(
878                 /* Sel: BB x M x ref --> X x M */
879                 op1mode == mode_M && mode_is_reference(op2mode) &&
880                 mymode == mode_T, "Raise node", 0
881         );
882         return 1;
883 }
884
885 /**
886  * verify a Const node
887  */
888 static int verify_node_Const(const ir_node *n)
889 {
890         ir_mode *mymode = get_irn_mode(n);
891
892         ASSERT_AND_RET(
893                 /* Const: BB --> data */
894                 (mode_is_data(mymode) ||
895                 mymode == mode_b)      /* we want boolean constants for static evaluation */
896                 ,"Const node", 0       /* of Cmp. */
897         );
898         ASSERT_AND_RET(
899                 /* the modes of the constant and teh tarval must match */
900                 mymode == get_tarval_mode(get_Const_tarval(n)),
901                 "Const node, tarval and node mode mismatch", 0
902         );
903         return 1;
904 }
905
906 /**
907  * verify a SymConst node
908  */
909 static int verify_node_SymConst(const ir_node *n)
910 {
911         ir_mode *mymode = get_irn_mode(n);
912
913         ASSERT_AND_RET(
914                 /* SymConst: BB --> int*/
915                 (mode_is_int(mymode) ||
916                 /* SymConst: BB --> ref */
917                 mode_is_reference(mymode))
918                 ,"SymConst node", 0);
919         if (SYMCONST_HAS_ENT(get_SymConst_kind(n))) {
920                 ir_entity *ent = get_SymConst_entity(n);
921                 /* the is_method_entity(ent) exception is for nested functions... */
922                 ASSERT_AND_RET_DBG((get_entity_owner(ent)->flags & tf_segment)
923                                    || is_method_entity(ent),
924                                    "SymConst node with non-segment entity", 0,
925                                    show_node_failure(n););
926         }
927         return 1;
928 }
929
930 /**
931  * verify a Sel node
932  */
933 static int verify_node_Sel(const ir_node *n)
934 {
935         int i;
936         ir_mode *mymode  = get_irn_mode(n);
937         ir_mode *op1mode = get_irn_mode(get_Sel_mem(n));
938         ir_mode *op2mode = get_irn_mode(get_Sel_ptr(n));
939         ir_entity *ent;
940
941         ASSERT_AND_RET_DBG(
942                 /* Sel: BB x M x ref x int^n --> ref */
943                 (op1mode == mode_M && op2mode == mymode && mode_is_reference(mymode)),
944                 "Sel node", 0, show_node_failure(n);
945         );
946
947         for (i = get_Sel_n_indexs(n) - 1; i >= 0; --i) {
948                 ASSERT_AND_RET_DBG(mode_is_int(get_irn_mode(get_Sel_index(n, i))), "Sel node", 0, show_node_failure(n););
949         }
950         ent = get_Sel_entity(n);
951         ASSERT_AND_RET_DBG(ent, "Sel node with empty entity", 0, show_node_failure(n););
952         ASSERT_AND_RET_DBG(!(get_entity_owner(ent)->flags & tf_segment),
953                            "Sel node with global entity", 0, show_node_failure(n););
954         return 1;
955 }
956
957 /**
958  * verify an InstOf node
959  */
960 static int verify_node_InstOf(const ir_node *n)
961 {
962         ir_mode *mymode  = get_irn_mode(n);
963         ir_mode *op1mode = get_irn_mode(get_InstOf_obj(n));
964
965         ASSERT_AND_RET(mode_T == mymode, "mode of Instof is not a tuple", 0);
966         ASSERT_AND_RET(mode_is_data(op1mode), "Instof not on data", 0);
967         return 1;
968 }
969
970 /**
971  * Check if the pinned state is right.
972  */
973 static int verify_right_pinned(const ir_node *n)
974 {
975         ir_node *mem;
976
977         if (get_irn_pinned(n) == op_pin_state_pinned)
978                 return 1;
979         mem = get_Call_mem(n);
980
981         /* if it's not pinned, its memory predecessor must be NoMem or Pin */
982         if (is_NoMem(mem) || is_Pin(mem))
983                 return 1;
984         return 0;
985 }
986
987 /**
988  * verify a Call node
989  */
990 static int verify_node_Call(const ir_node *n)
991 {
992         ir_graph *irg     = get_irn_irg(n);
993         ir_mode  *mymode  = get_irn_mode(n);
994         ir_mode  *op1mode = get_irn_mode(get_Call_mem(n));
995         ir_mode  *op2mode = get_irn_mode(get_Call_ptr(n));
996         ir_type  *mt;
997         size_t    i;
998         size_t    n_params;
999
1000         /* Call: BB x M x ref x data1 x ... x datan
1001         --> M x datan+1 x ... x data n+m */
1002         ASSERT_AND_RET( op1mode == mode_M && mode_is_reference(op2mode), "Call node", 0 );  /* operand M x ref */
1003
1004         /* NoMem nodes are only allowed as memory input if the Call is NOT pinned */
1005         ASSERT_AND_RET(verify_right_pinned(n),"Call node with wrong memory input", 0 );
1006
1007         mt = get_Call_type(n);
1008         if (get_unknown_type() == mt) {
1009                 return 1;
1010         }
1011
1012         n_params = get_Call_n_params(n);
1013         for (i = 0; i < n_params; ++i) {
1014                 ASSERT_AND_RET( mode_is_datab(get_irn_mode(get_Call_param(n, i))), "Call node", 0 );  /* operand datai */
1015         }
1016
1017         ASSERT_AND_RET( mymode == mode_T, "Call result not a tuple", 0 );   /* result T */
1018         /* Compare arguments of node with those of type */
1019
1020         if (get_method_variadicity(mt) == variadicity_variadic) {
1021                 ASSERT_AND_RET_DBG(
1022                         (size_t)get_Call_n_params(n) >= get_method_n_params(mt),
1023                         "Number of args for Call doesn't match number of args in variadic type.",
1024                         0,
1025                         ir_fprintf(stderr, "Call %+F has %d params, type %d\n",
1026                         n, get_Call_n_params(n), get_method_n_params(mt));
1027                 );
1028         } else {
1029                 ASSERT_AND_RET_DBG(
1030                         (size_t)get_Call_n_params(n) == get_method_n_params(mt),
1031                         "Number of args for Call doesn't match number of args in non variadic type.",
1032                         0,
1033                         ir_fprintf(stderr, "Call %+F has %d params, type %d\n",
1034                         n, get_Call_n_params(n), get_method_n_params(mt));
1035                 );
1036         }
1037
1038         for (i = 0; i < get_method_n_params(mt); i++) {
1039                 ir_type *t = get_method_param_type(mt, i);
1040
1041                 if (irg_is_constrained(irg, IR_GRAPH_CONSTRAINT_BACKEND)) {
1042                         if (is_atomic_type(t)) {
1043                                 ASSERT_AND_RET_DBG(
1044                                         get_irn_mode(get_Call_param(n, i)) == get_type_mode(t),
1045                                         "Mode of arg for Call doesn't match mode of arg type.", 0,
1046                                         show_call_param(n, mt);
1047                                 );
1048                         } else {
1049                                 /* call with a compound type, mode must be reference */
1050                                 ASSERT_AND_RET_DBG(
1051                                         mode_is_reference(get_irn_mode(get_Call_param(n, i))),
1052                                         "Mode of arg for Call doesn't match mode of arg type.", 0,
1053                                         show_call_param(n, mt);
1054                                 );
1055                         }
1056                 }
1057         }
1058
1059         return 1;
1060 }
1061
1062 /**
1063  * verify an Add node
1064  */
1065 static int verify_node_Add(const ir_node *n)
1066 {
1067         ir_mode *mymode  = get_irn_mode(n);
1068         ir_mode *op1mode = get_irn_mode(get_Add_left(n));
1069         ir_mode *op2mode = get_irn_mode(get_Add_right(n));
1070
1071         ASSERT_AND_RET_DBG(
1072                 (
1073                         /* common Add: BB x numP x numP --> numP */
1074                         (op1mode == mymode && op2mode == op1mode && mode_is_data(mymode)) ||
1075                         /* Pointer Add: BB x ref x int --> ref */
1076                         (mode_is_reference(op1mode) && mode_is_int(op2mode) && op1mode == mymode) ||
1077                         /* Pointer Add: BB x int x ref --> ref */
1078                         (mode_is_int(op1mode) && op2mode == mymode && mode_is_reference(mymode))
1079                 ),
1080                 "Add node", 0,
1081                 show_binop_failure(n, "/* common Add: BB x numP x numP --> numP */ |\n"
1082                         "/* Pointer Add: BB x ref x int --> ref */   |\n"
1083                         "/* Pointer Add: BB x int x ref --> ref */");
1084         );
1085         return 1;
1086 }
1087
1088 /**
1089  * verify a Sub node
1090  */
1091 static int verify_node_Sub(const ir_node *n)
1092 {
1093         ir_mode *mymode  = get_irn_mode(n);
1094         ir_mode *op1mode = get_irn_mode(get_Sub_left(n));
1095         ir_mode *op2mode = get_irn_mode(get_Sub_right(n));
1096
1097         ASSERT_AND_RET_DBG(
1098                 (
1099                         /* common Sub: BB x numP x numP --> numP */
1100                         (mymode ==op1mode && mymode == op2mode && mode_is_data(op1mode)) ||
1101                         /* Pointer Sub: BB x ref x int --> ref */
1102                         (op1mode == mymode && mode_is_int(op2mode) && mode_is_reference(mymode)) ||
1103                         /* Pointer Sub: BB x ref x ref --> int */
1104                         (op1mode == op2mode && mode_is_reference(op2mode) && mode_is_int(mymode))
1105                 ),
1106                 "Sub node", 0,
1107                 show_binop_failure(n, "/* common Sub: BB x numP x numP --> numP */ |\n"
1108                         "/* Pointer Sub: BB x ref x int --> ref */   |\n"
1109                         "/* Pointer Sub: BB x ref x ref --> int */" );
1110                 );
1111         return 1;
1112 }
1113
1114 /**
1115  * verify a Minus node
1116  */
1117 static int verify_node_Minus(const ir_node *n)
1118 {
1119         ir_mode *mymode  = get_irn_mode(n);
1120         ir_mode *op1mode = get_irn_mode(get_Minus_op(n));
1121
1122         ASSERT_AND_RET_DBG(
1123                 /* Minus: BB x num --> num */
1124                 op1mode == mymode && mode_is_num(op1mode), "Minus node", 0,
1125                 show_unop_failure(n , "/* Minus: BB x num --> num */");
1126         );
1127         return 1;
1128 }
1129
1130 /**
1131  * verify a Mul node
1132  */
1133 static int verify_node_Mul(const ir_node *n)
1134 {
1135         ir_mode *mymode  = get_irn_mode(n);
1136         ir_mode *op1mode = get_irn_mode(get_Mul_left(n));
1137         ir_mode *op2mode = get_irn_mode(get_Mul_right(n));
1138
1139         ASSERT_AND_RET_DBG(
1140                 (
1141                         /* Mul: BB x int_n x int_n --> int_n|int_2n */
1142                         (mode_is_int(op1mode)   && op2mode == op1mode && mode_is_int(mymode) &&
1143                          (op1mode == mymode || get_mode_size_bits(op1mode) * 2 == get_mode_size_bits(mymode))) ||
1144                         /* Mul: BB x float x float --> float */
1145                         (mode_is_float(op1mode) && op2mode == op1mode && mymode == op1mode)
1146                 ),
1147                 "Mul node",0,
1148                 show_binop_failure(n, "/* Mul: BB x int_n x int_n --> int_n|int_2n */ |\n"
1149                 "/* Mul: BB x float x float --> float */");
1150         );
1151         return 1;
1152 }
1153
1154 /**
1155  * verify a Mulh node
1156  */
1157 static int verify_node_Mulh(const ir_node *n)
1158 {
1159         ir_mode *mymode  = get_irn_mode(n);
1160         ir_mode *op1mode = get_irn_mode(get_Mulh_left(n));
1161         ir_mode *op2mode = get_irn_mode(get_Mulh_right(n));
1162
1163         ASSERT_AND_RET_DBG(
1164                 (
1165                         /* Mulh: BB x int x int --> int */
1166                         (mode_is_int(op1mode) && op2mode == op1mode && op1mode == mymode)
1167                 ),
1168                 "Mulh node",0,
1169                 show_binop_failure(n, "/* Mulh: BB x int x int --> int */");
1170         );
1171         return 1;
1172 }
1173
1174 /**
1175  * verify a Div node
1176  */
1177 static int verify_node_Div(const ir_node *n)
1178 {
1179         ir_mode *mymode  = get_irn_mode(n);
1180         ir_mode *op1mode = get_irn_mode(get_Div_mem(n));
1181         ir_mode *op2mode = get_irn_mode(get_Div_left(n));
1182         ir_mode *op3mode = get_irn_mode(get_Div_right(n));
1183         ir_mode *resmode = get_Div_resmode(n);
1184
1185         ASSERT_AND_RET(
1186                 /* Div: BB x M x num x num --> M x X x num */
1187                 op1mode == mode_M    &&
1188                 op2mode == resmode   &&
1189                 op3mode == resmode   &&
1190                 mode_is_num(resmode) &&
1191                 mymode == mode_T,
1192                 "Div node", 0
1193                 );
1194         return 1;
1195 }
1196
1197 /**
1198  * verify a Mod node
1199  */
1200 static int verify_node_Mod(const ir_node *n)
1201 {
1202         ir_mode *mymode  = get_irn_mode(n);
1203         ir_mode *op1mode = get_irn_mode(get_Mod_mem(n));
1204         ir_mode *op2mode = get_irn_mode(get_Mod_left(n));
1205         ir_mode *op3mode = get_irn_mode(get_Mod_right(n));
1206         ir_mode *resmode = get_Mod_resmode(n);
1207
1208         ASSERT_AND_RET(
1209                 /* Mod: BB x M x int x int --> M x X x int */
1210                 op1mode == mode_M    &&
1211                 op2mode == resmode   &&
1212                 op3mode == resmode   &&
1213                 mode_is_int(resmode) &&
1214                 mymode == mode_T,
1215                 "Mod node", 0
1216                 );
1217         return 1;
1218 }
1219
1220 /**
1221  * verify a logical And, Or, Eor node
1222  */
1223 static int verify_node_Logic(const ir_node *n)
1224 {
1225         ir_mode *mymode  = get_irn_mode(n);
1226         ir_mode *op1mode = get_irn_mode(get_binop_left(n));
1227         ir_mode *op2mode = get_irn_mode(get_binop_right(n));
1228
1229         ASSERT_AND_RET_DBG(
1230                 /* And or Or or Eor: BB x int x int --> int */
1231                 (mode_is_int(mymode) || mode_is_reference(mymode) || mymode == mode_b) &&
1232                 op2mode == op1mode &&
1233                 mymode == op2mode,
1234                 "And, Or or Eor node", 0,
1235                 show_binop_failure(n, "/* And or Or or Eor: BB x int x int --> int */");
1236         );
1237         return 1;
1238 }
1239
1240 static int verify_node_And(const ir_node *n)
1241 {
1242         return verify_node_Logic(n);
1243 }
1244
1245 static int verify_node_Or(const ir_node *n)
1246 {
1247         return verify_node_Logic(n);
1248 }
1249
1250 static int verify_node_Eor(const ir_node *n)
1251 {
1252         return verify_node_Logic(n);
1253 }
1254
1255 /**
1256  * verify a Not node
1257  */
1258 static int verify_node_Not(const ir_node *n)
1259 {
1260         ir_mode *mymode  = get_irn_mode(n);
1261         ir_mode *op1mode = get_irn_mode(get_Not_op(n));
1262
1263         ASSERT_AND_RET_DBG(
1264                 /* Not: BB x int --> int */
1265                 (mode_is_int(mymode) || mymode == mode_b) &&
1266                 mymode == op1mode,
1267                 "Not node", 0,
1268                 show_unop_failure(n, "/* Not: BB x int --> int */");
1269         );
1270         return 1;
1271 }
1272
1273 /**
1274  * verify a Cmp node
1275  */
1276 static int verify_node_Cmp(const ir_node *n)
1277 {
1278         ir_mode *mymode  = get_irn_mode(n);
1279         ir_mode *op1mode = get_irn_mode(get_Cmp_left(n));
1280         ir_mode *op2mode = get_irn_mode(get_Cmp_right(n));
1281
1282         ASSERT_AND_RET_DBG(
1283                 /* Cmp: BB x datab x datab --> b16 */
1284                 mode_is_datab(op1mode) &&
1285                 op2mode == op1mode &&
1286                 mymode == mode_b,
1287                 "Cmp node", 0,
1288                 show_binop_failure(n, "/* Cmp: BB x datab x datab --> b16 */");
1289         );
1290         return 1;
1291 }
1292
1293 /**
1294  * verify a Shift node
1295  */
1296 static int verify_node_Shift(const ir_node *n)
1297 {
1298         ir_mode *mymode  = get_irn_mode(n);
1299         ir_mode *op1mode = get_irn_mode(get_binop_left(n));
1300         ir_mode *op2mode = get_irn_mode(get_binop_right(n));
1301
1302         ASSERT_AND_RET_DBG(
1303                 /* Shl, Shr or Shrs: BB x int x int_u --> int */
1304                 mode_is_int(op1mode) &&
1305                 mode_is_int(op2mode) &&
1306                 !mode_is_signed(op2mode) &&
1307                 mymode == op1mode,
1308                 "Shl, Shr or Shrs node", 0,
1309                 show_binop_failure(n, "/* Shl, Shr or Shrs: BB x int x int_u --> int */");
1310         );
1311         return 1;
1312 }
1313
1314 static int verify_node_Shl(const ir_node *n)
1315 {
1316         return verify_node_Shift(n);
1317 }
1318
1319 static int verify_node_Shr(const ir_node *n)
1320 {
1321         return verify_node_Shift(n);
1322 }
1323
1324 static int verify_node_Shrs(const ir_node *n)
1325 {
1326         return verify_node_Shift(n);
1327 }
1328
1329 /**
1330  * verify a Rotl node
1331  */
1332 static int verify_node_Rotl(const ir_node *n)
1333 {
1334         ir_mode *mymode  = get_irn_mode(n);
1335         ir_mode *op1mode = get_irn_mode(get_Rotl_left(n));
1336         ir_mode *op2mode = get_irn_mode(get_Rotl_right(n));
1337
1338         ASSERT_AND_RET_DBG(
1339                 /* Rotl: BB x int x int --> int */
1340                 mode_is_int(op1mode) &&
1341                 mode_is_int(op2mode) &&
1342                 mymode == op1mode,
1343                 "Rotl node", 0,
1344                 show_binop_failure(n, "/* Rotl: BB x int x int --> int */");
1345         );
1346         return 1;
1347 }
1348
1349 /**
1350  * verify a Conv node
1351  */
1352 static int verify_node_Conv(const ir_node *n)
1353 {
1354         ir_mode *mymode  = get_irn_mode(n);
1355         ir_mode *op1mode = get_irn_mode(get_Conv_op(n));
1356
1357         ASSERT_AND_RET_DBG(mode_is_data(op1mode) && mode_is_data(mymode),
1358                 "Conv node", 0,
1359                 show_unop_failure(n, "/* Conv: BB x data --> data */");
1360         );
1361         return 1;
1362 }
1363
1364 /**
1365  * verify a Phi node
1366  */
1367 static int verify_node_Phi(const ir_node *n)
1368 {
1369         ir_mode *mymode = get_irn_mode(n);
1370         ir_node *block  = get_nodes_block(n);
1371         int i;
1372
1373         /* a Phi node MUST have the same number of inputs as its block
1374          * Exception is a phi with 0 inputs which is used when (re)constructing the
1375          * SSA form */
1376         if (! is_Bad(block)
1377             && !irg_is_constrained(get_irn_irg(n), IR_GRAPH_CONSTRAINT_CONSTRUCTION)
1378             && get_irn_arity(n) > 0) {
1379                 ASSERT_AND_RET_DBG(
1380                         get_irn_arity(n) == get_irn_arity(block),
1381                         "wrong number of inputs in Phi node", 0,
1382                         show_phi_inputs(n, block);
1383                 );
1384         }
1385
1386         /* Phi: BB x dataM^n --> dataM */
1387         for (i = get_Phi_n_preds(n) - 1; i >= 0; --i) {
1388                 ir_node *pred = get_Phi_pred(n, i);
1389                 ASSERT_AND_RET_DBG(get_irn_mode(pred) == mymode,
1390                                    "Phi node", 0, show_phi_failure(n, pred, i);
1391                 );
1392         }
1393         ASSERT_AND_RET(mode_is_dataM(mymode) || mymode == mode_b, "Phi node", 0 );
1394
1395         return 1;
1396 }
1397
1398 /**
1399  * verify a Load node
1400  */
1401 static int verify_node_Load(const ir_node *n)
1402 {
1403         ir_graph *irg     = get_irn_irg(n);
1404         ir_mode  *mymode  = get_irn_mode(n);
1405         ir_mode  *op1mode = get_irn_mode(get_Load_mem(n));
1406         ir_mode  *op2mode = get_irn_mode(get_Load_ptr(n));
1407
1408         ASSERT_AND_RET(op1mode == mode_M, "Load node", 0);
1409         if (!irg_is_constrained(irg, IR_GRAPH_CONSTRAINT_BACKEND)) {
1410                 ASSERT_AND_RET(mode_is_reference(op2mode), "Load node", 0 );
1411         }
1412         ASSERT_AND_RET( mymode == mode_T, "Load node", 0 );
1413
1414         return 1;
1415 }
1416
1417 /**
1418  * verify a Store node
1419  */
1420 static int verify_node_Store(const ir_node *n)
1421 {
1422         ir_graph  *irg = get_irn_irg(n);
1423
1424         ir_mode *mymode  = get_irn_mode(n);
1425         ir_mode *op1mode = get_irn_mode(get_Store_mem(n));
1426         ir_mode *op2mode = get_irn_mode(get_Store_ptr(n));
1427         ir_mode *op3mode = get_irn_mode(get_Store_value(n));
1428
1429         ASSERT_AND_RET(op1mode == mode_M && mode_is_datab(op3mode), "Store node", 0 );
1430         if (!irg_is_constrained(irg, IR_GRAPH_CONSTRAINT_BACKEND)) {
1431                 ASSERT_AND_RET(mode_is_reference(op2mode), "Store node", 0 );
1432         }
1433         ASSERT_AND_RET(mymode == mode_T, "Store node", 0);
1434
1435         return 1;
1436 }
1437
1438 /**
1439  * verify an Alloc node
1440  */
1441 static int verify_node_Alloc(const ir_node *n)
1442 {
1443         ir_mode *mymode  = get_irn_mode(n);
1444         ir_mode *op1mode = get_irn_mode(get_Alloc_mem(n));
1445         ir_mode *op2mode = get_irn_mode(get_Alloc_count(n));
1446
1447         ASSERT_AND_RET_DBG(
1448                 /* Alloc: BB x M x int_u --> M x X x ref */
1449                 op1mode == mode_M &&
1450                 mode_is_int(op2mode) &&
1451                 !mode_is_signed(op2mode) &&
1452                 mymode == mode_T,
1453                 "Alloc node", 0,
1454                 show_node_failure(n);
1455         );
1456         return 1;
1457 }
1458
1459 /**
1460  * verify a Free node
1461  */
1462 static int verify_node_Free(const ir_node *n)
1463 {
1464         ir_mode *mymode  = get_irn_mode(n);
1465         ir_mode *op1mode = get_irn_mode(get_Free_mem(n));
1466         ir_mode *op2mode = get_irn_mode(get_Free_ptr(n));
1467         ir_mode *op3mode = get_irn_mode(get_Free_count(n));
1468
1469         ASSERT_AND_RET_DBG(
1470                 /* Free: BB x M x ref x int_u --> M */
1471                 op1mode == mode_M && mode_is_reference(op2mode) &&
1472                 mode_is_int(op3mode) &&
1473                 !mode_is_signed(op3mode) &&
1474                 mymode == mode_M,
1475                 "Free node", 0,
1476                 show_triop_failure(n, "/* Free: BB x M x ref x int_u --> M */");
1477         );
1478         return 1;
1479 }
1480
1481 /**
1482  * verify a Sync node
1483  */
1484 static int verify_node_Sync(const ir_node *n)
1485 {
1486         int i;
1487         ir_mode *mymode  = get_irn_mode(n);
1488
1489         /* Sync: BB x M^n --> M */
1490         for (i = get_Sync_n_preds(n) - 1; i >= 0; --i) {
1491                 ASSERT_AND_RET( get_irn_mode(get_Sync_pred(n, i)) == mode_M, "Sync node", 0 );
1492         }
1493         ASSERT_AND_RET( mymode == mode_M, "Sync node", 0 );
1494         return 1;
1495 }
1496
1497 /**
1498  * verify a Confirm node
1499  */
1500 static int verify_node_Confirm(const ir_node *n)
1501 {
1502         ir_mode *mymode  = get_irn_mode(n);
1503         ir_mode *op1mode = get_irn_mode(get_Confirm_value(n));
1504         ir_mode *op2mode = get_irn_mode(get_Confirm_bound(n));
1505
1506         ASSERT_AND_RET_DBG(
1507                 /* Confirm: BB x T x T --> T */
1508                 op1mode == mymode &&
1509                 op2mode == mymode,
1510                 "Confirm node", 0,
1511                 show_binop_failure(n, "/* Confirm: BB x T x T --> T */");
1512         );
1513         return 1;
1514 }
1515
1516 /**
1517  * verify a Mux node
1518  */
1519 static int verify_node_Mux(const ir_node *n)
1520 {
1521         ir_mode *mymode  = get_irn_mode(n);
1522         ir_mode *op1mode = get_irn_mode(get_Mux_sel(n));
1523         ir_mode *op2mode = get_irn_mode(get_Mux_true(n));
1524         ir_mode *op3mode = get_irn_mode(get_Mux_false(n));
1525
1526         ASSERT_AND_RET(
1527                 /* Mux: BB x b x datab x datab --> datab */
1528                 op1mode == mode_b &&
1529                 op2mode == mymode &&
1530                 op3mode == mymode &&
1531                 mode_is_datab(mymode),
1532                 "Mux node", 0
1533                 );
1534         return 1;
1535 }
1536
1537 /**
1538  * verify a CopyB node
1539  */
1540 static int verify_node_CopyB(const ir_node *n)
1541 {
1542         ir_graph *irg     = get_irn_irg(n);
1543         ir_mode  *mymode  = get_irn_mode(n);
1544         ir_mode  *op1mode = get_irn_mode(get_CopyB_mem(n));
1545         ir_mode  *op2mode = get_irn_mode(get_CopyB_dst(n));
1546         ir_mode  *op3mode = get_irn_mode(get_CopyB_src(n));
1547         ir_type  *t = get_CopyB_type(n);
1548
1549         /* CopyB: BB x M x ref x ref --> M x X */
1550         ASSERT_AND_RET(mymode == mode_T && op1mode == mode_M, "CopyB node", 0);
1551         if (!irg_is_constrained(irg, IR_GRAPH_CONSTRAINT_BACKEND)) {
1552                 ASSERT_AND_RET(mode_is_reference(op2mode) && mode_is_reference(op3mode),
1553                         "CopyB node", 0 );
1554         }
1555
1556         ASSERT_AND_RET(
1557                 is_compound_type(t) || is_Array_type(t),
1558                 "CopyB node should copy compound types only", 0 );
1559
1560         /* NoMem nodes are only allowed as memory input if the CopyB is NOT pinned.
1561            This should happen RARELY, as CopyB COPIES MEMORY */
1562         ASSERT_AND_RET(verify_right_pinned(n), "CopyB node with wrong memory input", 0 );
1563         return 1;
1564 }
1565
1566 /**
1567  * Check dominance.
1568  * For each usage of a node, it is checked, if the block of the
1569  * node dominates the block of the usage (for phis: the predecessor
1570  * block of the phi for the corresponding edge).
1571  *
1572  * @return non-zero on success, 0 on dominance error
1573  */
1574 static int check_dominance_for_node(const ir_node *use)
1575 {
1576         /* This won't work for blocks and the end node */
1577         if (!is_Block(use) && !is_End(use) && !is_Anchor(use)) {
1578                 int i;
1579                 ir_node *bl = get_nodes_block(use);
1580
1581                 for (i = get_irn_arity(use) - 1; i >= 0; --i) {
1582                         ir_node  *def    = get_irn_n(use, i);
1583                         ir_node  *def_bl = get_nodes_block(def);
1584                         ir_node  *use_bl = bl;
1585                         ir_graph *irg;
1586
1587                         /* we have no dominance relation for unreachable blocks, so we can't
1588                          * check the dominance property there */
1589                         if (!is_Block(def_bl) || get_Block_dom_depth(def_bl) == -1)
1590                                 continue;
1591
1592                         if (is_Phi(use)) {
1593                                 if (is_Bad(def))
1594                                         continue;
1595                                 use_bl = get_Block_cfgpred_block(bl, i);
1596                         }
1597
1598                         if (!is_Block(use_bl) || get_Block_dom_depth(use_bl) == -1)
1599                                 continue;
1600
1601                         irg = get_irn_irg(use);
1602                         ASSERT_AND_RET_DBG(
1603                                 block_dominates(def_bl, use_bl),
1604                                 "the definition of a value used violates the dominance property", 0,
1605                                 ir_fprintf(stderr,
1606                                 "graph %+F: %+F of %+F must dominate %+F of user %+F input %d\n",
1607                                 irg, def_bl, def, use_bl, use, i
1608                                 );
1609                         );
1610                 }
1611         }
1612         return 1;
1613 }
1614
1615 int irn_verify_irg(const ir_node *n, ir_graph *irg)
1616 {
1617         ir_op *op;
1618
1619         if (!get_node_verification_mode())
1620                 return 1;
1621
1622         /*
1623          * do NOT check placement in interprocedural view, as we don't always
1624          * know the "right" graph ...
1625          */
1626
1627 #ifndef NDEBUG
1628         /* this is an expensive check for large graphs (it has a quadratic
1629          * runtime but with a small constant); so do NOT run it in release mode
1630          */
1631         ASSERT_AND_RET_DBG(
1632                 node_is_in_irgs_storage(irg, n),
1633                 "Node is not stored on proper IR graph!", 0,
1634                 show_node_on_graph(irg, n);
1635         );
1636 #endif
1637         assert(get_irn_irg(n) == irg);
1638         {
1639                 unsigned idx           = get_irn_idx(n);
1640                 ir_node *node_from_map = get_idx_irn(irg, idx);
1641                 ASSERT_AND_RET_DBG(node_from_map == n, "Node index and index map entry differ", 0,
1642                         ir_printf("node %+F node in map %+F(%p)\n", n, node_from_map, node_from_map);
1643                 );
1644         }
1645
1646         op = get_irn_op(n);
1647
1648         if (get_op_pinned(op) >= op_pin_state_exc_pinned) {
1649                 op_pin_state state = get_irn_pinned(n);
1650                 ASSERT_AND_RET_DBG(
1651                         state == op_pin_state_floats ||
1652                         state == op_pin_state_pinned,
1653                         "invalid pin state", 0,
1654                         ir_printf("node %+F", n);
1655                 );
1656         } else if (!is_Block(n) && is_irn_pinned_in_irg(n)
1657                    && irg_has_properties(irg, IR_GRAPH_PROPERTY_NO_BADS)) {
1658                 ASSERT_AND_RET_DBG(is_Block(get_nodes_block(n)) || is_Anchor(n),
1659                                 "block input is not a block", 0,
1660                                 ir_printf("node %+F", n);
1661                 );
1662         }
1663
1664         ASSERT_AND_RET_DBG(
1665                 !is_irn_start_block_placed(n) || get_nodes_block(n) == get_irg_start_block(irg),
1666                 "node should be in start block", 0,
1667                 ir_printf("node %+F", n);
1668         );
1669
1670         if (op->ops.verify_node)
1671                 return op->ops.verify_node(n);
1672
1673         /* All went ok */
1674         return 1;
1675 }
1676
1677 int irn_verify(const ir_node *n)
1678 {
1679 #ifdef DEBUG_libfirm
1680         return irn_verify_irg(n, get_irn_irg(n));
1681 #else
1682         (void)n;
1683         return 1;
1684 #endif
1685 }
1686
1687 /*-----------------------------------------------------------------*/
1688 /* Verify the whole graph.                                         */
1689 /*-----------------------------------------------------------------*/
1690
1691 #ifdef DEBUG_libfirm
1692 /**
1693  * Walker to check every node
1694  */
1695 static void verify_wrap(ir_node *node, void *env)
1696 {
1697         int *res = (int*)env;
1698         *res = irn_verify_irg(node, get_irn_irg(node));
1699 }
1700
1701 /**
1702  * Walker to check every node including SSA property.
1703  * Only called if dominance info is available.
1704  */
1705 static void verify_wrap_ssa(ir_node *node, void *env)
1706 {
1707         int *res = (int*)env;
1708
1709         *res = irn_verify_irg(node, get_irn_irg(node));
1710         if (*res) {
1711                 *res = check_dominance_for_node(node);
1712         }
1713 }
1714
1715 #endif /* DEBUG_libfirm */
1716
1717 typedef struct check_cfg_env_t {
1718         pmap *branch_nodes; /**< map blocks to their branching nodes,
1719                                  map mode_X nodes to the blocks they branch to */
1720         int   res;
1721         ir_nodeset_t reachable_blocks;
1722         ir_nodeset_t kept_nodes;
1723         ir_nodeset_t true_projs;
1724         ir_nodeset_t false_projs;
1725 } check_cfg_env_t;
1726
1727 static int check_block_cfg(const ir_node *block, check_cfg_env_t *env)
1728 {
1729         pmap *branch_nodes;
1730         int   n_cfgpreds;
1731         int   i;
1732
1733         ASSERT_AND_RET_DBG(ir_nodeset_contains(&env->reachable_blocks, block),
1734                            "Block is not reachable by blockwalker (endless loop with no kept block?)", 0,
1735                            ir_printf("block %+F\n", block);
1736         );
1737
1738         n_cfgpreds   = get_Block_n_cfgpreds(block);
1739         branch_nodes = env->branch_nodes;
1740         for (i = 0; i < n_cfgpreds; ++i) {
1741                 /* check that each mode_X node is only connected
1742                  * to 1 user */
1743                 ir_node *branch = get_Block_cfgpred(block, i);
1744                 ir_node *former_dest;
1745                 ir_node *former_branch;
1746                 ir_node *branch_proj;
1747                 ir_node *branch_block;
1748                 branch = skip_Tuple(branch);
1749                 if (is_Bad(branch))
1750                         continue;
1751                 former_dest = pmap_get(ir_node, branch_nodes, branch);
1752                 ASSERT_AND_RET_DBG(former_dest==NULL || is_unknown_jump(skip_Proj(branch)),
1753                                                    "Multiple users on mode_X node", 0,
1754                                                    ir_printf("node %+F\n", branch);
1755                 );
1756                 pmap_insert(branch_nodes, branch, (void*)block);
1757
1758                 /* check that there's only 1 branching instruction in each block */
1759                 branch_block = get_nodes_block(branch);
1760                 branch_proj  = branch;
1761                 if (is_Proj(branch)) {
1762                         branch = skip_Proj(branch);
1763                 }
1764                 former_branch = pmap_get(ir_node, branch_nodes, branch_block);
1765
1766                 ASSERT_AND_RET_DBG(former_branch == NULL || former_branch == branch,
1767                                                    "Multiple branching nodes in a block", 0,
1768                                                    ir_printf("nodes %+F,%+F in block %+F\n",
1769                                                                          branch, former_branch, branch_block);
1770                 );
1771                 pmap_insert(branch_nodes, branch_block, branch);
1772
1773                 if (is_Cond(branch)) {
1774                         long pn = get_Proj_proj(branch_proj);
1775                         if (pn == pn_Cond_true)
1776                                 ir_nodeset_insert(&env->true_projs, branch);
1777                         if (pn == pn_Cond_false)
1778                                 ir_nodeset_insert(&env->false_projs, branch);
1779                 } else if (is_Switch(branch)) {
1780                         long pn = get_Proj_proj(branch_proj);
1781                         if (pn == pn_Switch_default)
1782                                 ir_nodeset_insert(&env->true_projs, branch);
1783                 }
1784         }
1785
1786         return 1;
1787 }
1788
1789 static void check_cfg_walk_func(ir_node *node, void *data)
1790 {
1791         check_cfg_env_t *env = (check_cfg_env_t*)data;
1792         if (!is_Block(node))
1793                 return;
1794         env->res &= check_block_cfg(node, env);
1795 }
1796
1797 static int verify_block_branch(const ir_node *block, check_cfg_env_t *env)
1798 {
1799         ir_node *branch = pmap_get(ir_node, env->branch_nodes, block);
1800         ASSERT_AND_RET_DBG(branch != NULL
1801                            || ir_nodeset_contains(&env->kept_nodes, block)
1802                            || block == get_irg_end_block(get_irn_irg(block)),
1803                            "block contains no cfop", 0,
1804                            ir_printf("block %+F\n", block);
1805         );
1806         return 1;
1807 }
1808
1809 static int verify_cond_projs(const ir_node *cond, check_cfg_env_t *env)
1810 {
1811         ASSERT_AND_RET_DBG(ir_nodeset_contains(&env->true_projs, cond),
1812                                            "Cond node lacks true proj", 0,
1813                                            ir_printf("Cond %+F\n", cond);
1814         );
1815         ASSERT_AND_RET_DBG(ir_nodeset_contains(&env->false_projs, cond),
1816                                            "Cond node lacks false proj", 0,
1817                                            ir_printf("Cond %+F\n", cond);
1818         );
1819         return 1;
1820 }
1821
1822 static int verify_switch_projs(const ir_node *sw, check_cfg_env_t *env)
1823 {
1824         ASSERT_AND_RET_DBG(ir_nodeset_contains(&env->true_projs, sw),
1825                                            "Switch node lacks default Proj", 0,
1826                                            ir_printf("Switch %+F\n", sw);
1827         );
1828         return 1;
1829 }
1830
1831 static void assert_branch(ir_node *node, void *data)
1832 {
1833         check_cfg_env_t *env = (check_cfg_env_t*)data;
1834         if (is_Block(node)) {
1835                 env->res &= verify_block_branch(node, env);
1836         } else if (is_Cond(node)) {
1837                 env->res &= verify_cond_projs(node, env);
1838         } else if (is_Switch(node)) {
1839                 env->res &= verify_switch_projs(node, env);
1840         }
1841 }
1842
1843 static void collect_reachable_blocks(ir_node *block, void *data)
1844 {
1845         ir_nodeset_t *reachable_blocks = (ir_nodeset_t*) data;
1846         ir_nodeset_insert(reachable_blocks, block);
1847 }
1848
1849 /**
1850  * Checks CFG well-formedness
1851  */
1852 static int check_cfg(ir_graph *irg)
1853 {
1854         check_cfg_env_t env;
1855         env.branch_nodes = pmap_create(); /**< map blocks to branch nodes */
1856         env.res          = 1;
1857         ir_nodeset_init(&env.reachable_blocks);
1858         ir_nodeset_init(&env.true_projs);
1859         ir_nodeset_init(&env.false_projs);
1860
1861         irg_block_walk_graph(irg, collect_reachable_blocks, NULL,
1862                              &env.reachable_blocks);
1863
1864         /* note that we do not use irg_walk_block because it will miss these
1865          * invalid blocks without a jump instruction which we want to detect
1866          * here */
1867         irg_walk_graph(irg, check_cfg_walk_func, NULL, &env);
1868
1869         ir_nodeset_init(&env.kept_nodes);
1870         {
1871                 ir_node *end   = get_irg_end(irg);
1872                 int      arity = get_irn_arity(end);
1873                 int      i;
1874                 for (i = 0; i < arity; ++i) {
1875                         ir_node *n = get_irn_n(end, i);
1876                         ir_nodeset_insert(&env.kept_nodes, n);
1877                 }
1878         }
1879         irg_walk_graph(irg, assert_branch, NULL, &env);
1880
1881         ir_nodeset_destroy(&env.false_projs);
1882         ir_nodeset_destroy(&env.true_projs);
1883         ir_nodeset_destroy(&env.kept_nodes);
1884         ir_nodeset_destroy(&env.reachable_blocks);
1885         pmap_destroy(env.branch_nodes);
1886         return env.res;
1887 }
1888
1889 int irg_verify(ir_graph *irg, unsigned flags)
1890 {
1891         int res = 1;
1892 #ifdef DEBUG_libfirm
1893         int pinned = get_irg_pinned(irg) == op_pin_state_pinned;
1894
1895 #ifndef NDEBUG
1896         last_irg_error = NULL;
1897 #endif /* NDEBUG */
1898
1899         if (pinned && !check_cfg(irg))
1900                 res = 0;
1901
1902         if (res == 1 && (flags & VERIFY_ENFORCE_SSA) && pinned)
1903                 compute_doms(irg);
1904
1905         irg_walk_anchors(
1906                 irg,
1907                 pinned && irg_has_properties(irg, IR_GRAPH_PROPERTY_CONSISTENT_DOMINANCE)
1908                         ? verify_wrap_ssa : verify_wrap,
1909                 NULL,
1910                 &res
1911         );
1912
1913         if (get_node_verification_mode() == FIRM_VERIFICATION_REPORT && ! res) {
1914                 ir_entity *ent = get_irg_entity(irg);
1915
1916                 if (ent)
1917                         fprintf(stderr, "irg_verify: Verifying graph %s failed\n", get_entity_name(ent));
1918                 else
1919                         fprintf(stderr, "irg_verify: Verifying graph %p failed\n", (void *)irg);
1920         }
1921
1922 #else
1923         (void)irg;
1924         (void)flags;
1925 #endif /* DEBUG_libfirm */
1926
1927         return res;
1928 }
1929
1930 typedef struct pass_t {
1931         ir_graph_pass_t pass;
1932         unsigned        flags;
1933 } pass_t;
1934
1935 /**
1936  * Wrapper to irg_verify to be run as an ir_graph pass.
1937  */
1938 static int irg_verify_wrapper(ir_graph *irg, void *context)
1939 {
1940         pass_t *pass = (pass_t*)context;
1941         irg_verify(irg, pass->flags);
1942         /* do NOT rerun the pass if verify is ok :-) */
1943         return 0;
1944 }
1945
1946 ir_graph_pass_t *irg_verify_pass(const char *name, unsigned flags)
1947 {
1948         pass_t *pass = XMALLOCZ(pass_t);
1949
1950         def_graph_pass_constructor(
1951                 &pass->pass, name ? name : "irg_verify", irg_verify_wrapper);
1952
1953         /* neither dump for verify */
1954         pass->pass.dump_irg   = (DUMP_ON_IRG_FUNC)ir_prog_no_dump;
1955         pass->pass.verify_irg = (RUN_ON_IRG_FUNC)ir_prog_no_verify;
1956
1957         pass->flags = flags;
1958         return &pass->pass;
1959 }
1960
1961 int irn_verify_irg_dump(const ir_node *n, ir_graph *irg,
1962                         const char **bad_string)
1963 {
1964         int res;
1965         firm_verification_t old = get_node_verification_mode();
1966
1967         firm_verify_failure_msg = NULL;
1968         do_node_verification(FIRM_VERIFICATION_ERROR_ONLY);
1969         res = irn_verify_irg(n, irg);
1970         if (res && irg_has_properties(irg, IR_GRAPH_PROPERTY_CONSISTENT_DOMINANCE) &&
1971             get_irg_pinned(irg) == op_pin_state_pinned)
1972                 res = check_dominance_for_node(n);
1973         do_node_verification(old);
1974         *bad_string = firm_verify_failure_msg;
1975
1976         return res;
1977 }
1978
1979 typedef struct verify_bad_env_t {
1980         int flags;
1981         int res;
1982 } verify_bad_env_t;
1983
1984 /**
1985  * Pre-Walker: check Bad predecessors of node.
1986  */
1987 static void check_bads(ir_node *node, void *env)
1988 {
1989         verify_bad_env_t *venv = (verify_bad_env_t*)env;
1990         int i, arity = get_irn_arity(node);
1991         ir_graph *irg = get_irn_irg(node);
1992
1993         if (is_Block(node)) {
1994                 if ((venv->flags & BAD_CF) == 0) {
1995
1996                         /* check for Bad Block predecessor */
1997                         for (i = 0; i < arity; ++i) {
1998                                 ir_node *pred = get_irn_n(node, i);
1999
2000                                 if (is_Bad(pred)) {
2001                                         venv->res |= BAD_CF;
2002
2003                                         if (get_node_verification_mode() == FIRM_VERIFICATION_REPORT) {
2004                                                 fprintf(stderr, "irg_verify_bads: Block %ld has Bad predecessor\n", get_irn_node_nr(node));
2005                                         }
2006                                         if (get_node_verification_mode() == FIRM_VERIFICATION_ON) {
2007                                                 dump_ir_graph(irg, "assert");
2008                                                 assert(0 && "Bad CF detected");
2009                                         }
2010                                 }
2011                         }
2012                 }
2013         } else {
2014                 if ((venv->flags & BAD_BLOCK) == 0) {
2015
2016                         /* check for Bad Block */
2017                         if (is_Bad(get_nodes_block(node))) {
2018                                 venv->res |= BAD_BLOCK;
2019
2020                                 if (get_node_verification_mode() == FIRM_VERIFICATION_REPORT) {
2021                                         fprintf(stderr, "irg_verify_bads: node %ld has Bad Block\n", get_irn_node_nr(node));
2022                                 }
2023                                 if (get_node_verification_mode() == FIRM_VERIFICATION_ON) {
2024                                         dump_ir_graph(irg, "assert");
2025                                         assert(0 && "Bad CF detected");
2026                                 }
2027                         }
2028                 }
2029
2030                 if ((venv->flags & TUPLE) == 0) {
2031                         if (is_Tuple(node)) {
2032                                 venv->res |= TUPLE;
2033
2034                                 if (get_node_verification_mode() == FIRM_VERIFICATION_REPORT) {
2035                                         fprintf(stderr, "irg_verify_bads: node %ld is a Tuple\n", get_irn_node_nr(node));
2036                                 }
2037                                 if (get_node_verification_mode() == FIRM_VERIFICATION_ON) {
2038                                         dump_ir_graph(irg, "assert");
2039                                         assert(0 && "Tuple detected");
2040                                 }
2041                         }
2042                 }
2043
2044                 for (i = 0; i < arity; ++i) {
2045                         ir_node *pred = get_irn_n(node, i);
2046
2047                         if (is_Bad(pred)) {
2048                                 /* check for Phi with Bad inputs */
2049                                 if (is_Phi(node) && !is_Bad(get_nodes_block(node)) && is_Bad(get_irn_n(get_nodes_block(node), i))) {
2050                                         if (venv->flags & BAD_CF)
2051                                                 continue;
2052                                         else {
2053                                                 venv->res |= BAD_CF;
2054
2055                                                 if (get_node_verification_mode() == FIRM_VERIFICATION_REPORT) {
2056                                                         fprintf(stderr, "irg_verify_bads: Phi %ld has Bad Input\n", get_irn_node_nr(node));
2057                                                 }
2058                                                 if (get_node_verification_mode() == FIRM_VERIFICATION_ON) {
2059                                                         dump_ir_graph(irg, "assert");
2060                                                         assert(0 && "Bad CF detected");
2061                                                 }
2062                                         }
2063                                 }
2064
2065                                 /* Bad node input */
2066                                 if ((venv->flags & BAD_DF) == 0) {
2067                                         venv->res |= BAD_DF;
2068
2069                                         if (get_node_verification_mode() == FIRM_VERIFICATION_REPORT) {
2070                                                 fprintf(stderr, "irg_verify_bads: node %ld has Bad Input\n", get_irn_node_nr(node));
2071                                         }
2072                                         if (get_node_verification_mode() == FIRM_VERIFICATION_ON) {
2073                                                 dump_ir_graph(irg, "assert");
2074                                                 assert(0 && "Bad NON-CF detected");
2075                                         }
2076                                 }
2077                         }
2078                 }
2079         }
2080 }
2081
2082 int irg_verify_bads(ir_graph *irg, int flags)
2083 {
2084         verify_bad_env_t env;
2085
2086         env.flags = flags;
2087         env.res   = 0;
2088
2089         irg_walk_graph(irg, check_bads, NULL, &env);
2090
2091         return env.res;
2092 }
2093
2094 static void register_verify_node_func(ir_op *op, verify_node_func func)
2095 {
2096         op->ops.verify_node = func;
2097 }
2098
2099 static void register_verify_node_func_proj(ir_op *op, verify_node_func func)
2100 {
2101         op->ops.verify_proj_node = func;
2102 }
2103
2104 void ir_register_verify_node_ops(void)
2105 {
2106         register_verify_node_func(op_Add,      verify_node_Add);
2107         register_verify_node_func(op_Alloc,    verify_node_Alloc);
2108         register_verify_node_func(op_And,      verify_node_And);
2109         register_verify_node_func(op_Block,    verify_node_Block);
2110         register_verify_node_func(op_Call,     verify_node_Call);
2111         register_verify_node_func(op_Cmp,      verify_node_Cmp);
2112         register_verify_node_func(op_Cond,     verify_node_Cond);
2113         register_verify_node_func(op_Confirm,  verify_node_Confirm);
2114         register_verify_node_func(op_Const,    verify_node_Const);
2115         register_verify_node_func(op_Conv,     verify_node_Conv);
2116         register_verify_node_func(op_CopyB,    verify_node_CopyB);
2117         register_verify_node_func(op_Div,      verify_node_Div);
2118         register_verify_node_func(op_Eor,      verify_node_Eor);
2119         register_verify_node_func(op_Free,     verify_node_Free);
2120         register_verify_node_func(op_IJmp,     verify_node_IJmp);
2121         register_verify_node_func(op_InstOf,   verify_node_InstOf);
2122         register_verify_node_func(op_Jmp,      verify_node_Jmp);
2123         register_verify_node_func(op_Load,     verify_node_Load);
2124         register_verify_node_func(op_Minus,    verify_node_Minus);
2125         register_verify_node_func(op_Mod,      verify_node_Mod);
2126         register_verify_node_func(op_Mul,      verify_node_Mul);
2127         register_verify_node_func(op_Mulh,     verify_node_Mulh);
2128         register_verify_node_func(op_Mux,      verify_node_Mux);
2129         register_verify_node_func(op_Not,      verify_node_Not);
2130         register_verify_node_func(op_Or,       verify_node_Or);
2131         register_verify_node_func(op_Phi,      verify_node_Phi);
2132         register_verify_node_func(op_Proj,     verify_node_Proj);
2133         register_verify_node_func(op_Raise,    verify_node_Raise);
2134         register_verify_node_func(op_Return,   verify_node_Return);
2135         register_verify_node_func(op_Rotl,     verify_node_Rotl);
2136         register_verify_node_func(op_Sel,      verify_node_Sel);
2137         register_verify_node_func(op_Shl,      verify_node_Shl);
2138         register_verify_node_func(op_Shr,      verify_node_Shr);
2139         register_verify_node_func(op_Shrs,     verify_node_Shrs);
2140         register_verify_node_func(op_Start,    verify_node_Start);
2141         register_verify_node_func(op_Store,    verify_node_Store);
2142         register_verify_node_func(op_Sub,      verify_node_Sub);
2143         register_verify_node_func(op_Switch,   verify_node_Switch);
2144         register_verify_node_func(op_SymConst, verify_node_SymConst);
2145         register_verify_node_func(op_Sync,     verify_node_Sync);
2146
2147         register_verify_node_func_proj(op_Alloc,  verify_node_Proj_Alloc);
2148         register_verify_node_func_proj(op_Call,   verify_node_Proj_Call);
2149         register_verify_node_func_proj(op_Cond,   verify_node_Proj_Cond);
2150         register_verify_node_func_proj(op_CopyB,  verify_node_Proj_CopyB);
2151         register_verify_node_func_proj(op_Div,    verify_node_Proj_Div);
2152         register_verify_node_func_proj(op_InstOf, verify_node_Proj_InstOf);
2153         register_verify_node_func_proj(op_Load,   verify_node_Proj_Load);
2154         register_verify_node_func_proj(op_Mod,    verify_node_Proj_Mod);
2155         register_verify_node_func_proj(op_Proj,   verify_node_Proj_Proj);
2156         register_verify_node_func_proj(op_Raise,  verify_node_Proj_Raise);
2157         register_verify_node_func_proj(op_Start,  verify_node_Proj_Start);
2158         register_verify_node_func_proj(op_Store,  verify_node_Proj_Store);
2159         register_verify_node_func_proj(op_Switch, verify_node_Proj_Switch);
2160         register_verify_node_func_proj(op_Tuple,  verify_node_Proj_Tuple);
2161 }