implemented get_Proj_type(), moved get_irn_type() here,
[libfirm] / ir / ir / irnode.c
1 /*
2  * Project:     libFIRM
3  * File name:   ir/ir/irnode.c
4  * Purpose:     Representation of an intermediate operation.
5  * Author:      Martin Trapp, Christian Schaefer
6  * Modified by: Goetz Lindenmaier
7  * Created:
8  * CVS-ID:      $Id$
9  * Copyright:   (c) 1998-2003 Universität Karlsruhe
10  * Licence:     This file protected by GPL -  GNU GENERAL PUBLIC LICENSE.
11  */
12
13 #ifdef HAVE_CONFIG_H
14 # include "config.h"
15 #endif
16
17 #ifdef HAVE_STRING_H
18 # include <string.h>
19 #endif
20
21 #include "ident.h"
22 #include "irnode_t.h"
23 #include "irgraph_t.h"
24 #include "irmode_t.h"
25 #include "typegmod.h"
26 #include "irbackedge_t.h"
27 #include "irdump.h"
28 #include "irop_t.h"
29 #include "irprog_t.h"
30 #include "iredges_t.h"
31
32 #include "irhooks.h"
33
34 /* some constants fixing the positions of nodes predecessors
35    in the in array */
36 #define CALL_PARAM_OFFSET     2
37 #define FUNCCALL_PARAM_OFFSET 1
38 #define SEL_INDEX_OFFSET      2
39 #define RETURN_RESULT_OFFSET  1  /* mem is not a result */
40 #define END_KEEPALIVE_OFFSET  0
41
42 static const char *pnc_name_arr [] = {
43   "False", "Eq", "Lt", "Le",
44   "Gt", "Ge", "Lg", "Leg", "Uo",
45   "Ue", "Ul", "Ule", "Ug", "Uge",
46   "Ne", "True"
47 };
48
49 /**
50  * returns the pnc name from an pnc constant
51  */
52 const char *get_pnc_string(int pnc) {
53   return pnc_name_arr[pnc];
54 }
55
56 /**
57  * Calculates the negated pnc condition.
58  */
59 int
60 get_negated_pnc(int pnc) {
61   switch (pnc) {
62   case pn_Cmp_False: return pn_Cmp_True;  break;
63   case pn_Cmp_Eq:    return pn_Cmp_Ne;    break;
64   case pn_Cmp_Lt:    return pn_Cmp_Uge;   break;
65   case pn_Cmp_Le:    return pn_Cmp_Ug;    break;
66   case pn_Cmp_Gt:    return pn_Cmp_Ule;   break;
67   case pn_Cmp_Ge:    return pn_Cmp_Ul;    break;
68   case pn_Cmp_Lg:    return pn_Cmp_Ue;    break;
69   case pn_Cmp_Leg:   return pn_Cmp_Uo;    break;
70   case pn_Cmp_Uo:    return pn_Cmp_Leg;   break;
71   case pn_Cmp_Ue:    return pn_Cmp_Lg;    break;
72   case pn_Cmp_Ul:    return pn_Cmp_Ge;    break;
73   case pn_Cmp_Ule:   return pn_Cmp_Gt;    break;
74   case pn_Cmp_Ug:    return pn_Cmp_Le;    break;
75   case pn_Cmp_Uge:   return pn_Cmp_Lt;    break;
76   case pn_Cmp_Ne:    return pn_Cmp_Eq;    break;
77   case pn_Cmp_True:  return pn_Cmp_False; break;
78   }
79   return 99; /* to shut up gcc */
80 }
81
82 const char *pns_name_arr [] = {
83   "initial_exec", "global_store",
84   "frame_base", "globals", "args"
85 };
86
87 const char *symconst_name_arr [] = {
88   "type_tag", "size", "addr_name", "addr_ent"
89 };
90
91 /**
92  * Indicates, whether additional data can be registered to ir nodes.
93  * If set to 1, this is not possible anymore.
94  */
95 static int forbid_new_data = 0;
96
97 /**
98  * The amount of additional space for custom data to be allocated upon
99  * creating a new node.
100  */
101 unsigned firm_add_node_size = 0;
102
103
104 /* register new space for every node */
105 unsigned register_additional_node_data(unsigned size) {
106   assert(!forbid_new_data && "Too late to register additional node data");
107
108   if (forbid_new_data)
109     return 0;
110
111   return firm_add_node_size += size;
112 }
113
114
115 void
116 init_irnode(void) {
117         /* Forbid the addition of new data to an ir node. */
118         forbid_new_data = 1;
119 }
120
121 /*
122  * irnode constructor.
123  * Create a new irnode in irg, with an op, mode, arity and
124  * some incoming irnodes.
125  * If arity is negative, a node with a dynamic array is created.
126  */
127 ir_node *
128 new_ir_node (dbg_info *db, ir_graph *irg, ir_node *block, ir_op *op, ir_mode *mode,
129          int arity, ir_node **in)
130 {
131   ir_node *res;
132   size_t node_size = offsetof(ir_node, attr) + op->attr_size + firm_add_node_size;
133         char *p;
134
135   assert(irg && op && mode);
136   p = obstack_alloc (irg->obst, node_size);
137   memset(p, 0, node_size);
138         res = (ir_node *) (p + firm_add_node_size);
139
140   res->kind    = k_ir_node;
141   res->op      = op;
142   res->mode    = mode;
143   res->visited = 0;
144   res->link    = NULL;
145   if (arity < 0) {
146     res->in = NEW_ARR_F (ir_node *, 1);  /* 1: space for block */
147   } else {
148     res->in = NEW_ARR_D (ir_node *, irg->obst, (arity+1));
149     memcpy (&res->in[1], in, sizeof (ir_node *) * arity);
150   }
151
152   res->in[0] = block;
153   set_irn_dbg_info(res, db);
154   res->out = NULL;
155
156 #ifdef DEBUG_libfirm
157   res->node_nr = get_irp_new_node_nr();
158 #endif
159
160 #if FIRM_EDGES_INPLACE
161   {
162     int i, n;
163     int not_a_block = is_no_Block(res);
164
165     INIT_LIST_HEAD(&res->edge_info.outs_head);
166
167     for (i = 0, n = arity + not_a_block; i < n; ++i)
168       edges_notify_edge(res, i - not_a_block, res->in[i], NULL, irg);
169   }
170 #endif
171
172   hook_new_node(irg, res);
173
174   return res;
175 }
176
177 /*-- getting some parameters from ir_nodes --*/
178
179 int
180 (is_ir_node)(const void *thing) {
181   return _is_ir_node(thing);
182 }
183
184 int
185 (get_irn_intra_arity)(const ir_node *node) {
186   return _get_irn_intra_arity(node);
187 }
188
189 int
190 (get_irn_inter_arity)(const ir_node *node) {
191   return _get_irn_inter_arity(node);
192 }
193
194 int (*_get_irn_arity)(const ir_node *node) = _get_irn_intra_arity;
195
196 int
197 (get_irn_arity)(const ir_node *node) {
198   return _get_irn_arity(node);
199 }
200
201 /* Returns the array with ins. This array is shifted with respect to the
202    array accessed by get_irn_n: The block operand is at position 0 not -1.
203    (@@@ This should be changed.)
204    The order of the predecessors in this array is not guaranteed, except that
205    lists of operands as predecessors of Block or arguments of a Call are
206    consecutive. */
207 ir_node **
208 get_irn_in (const ir_node *node) {
209   assert(node);
210   if (get_interprocedural_view()) { /* handle Filter and Block specially */
211     if (get_irn_opcode(node) == iro_Filter) {
212       assert(node->attr.filter.in_cg);
213       return node->attr.filter.in_cg;
214     } else if (get_irn_opcode(node) == iro_Block && node->attr.block.in_cg) {
215       return node->attr.block.in_cg;
216     }
217     /* else fall through */
218   }
219   return node->in;
220 }
221
222 void
223 set_irn_in (ir_node *node, int arity, ir_node **in) {
224   ir_node *** arr;
225   assert(node);
226   if (get_interprocedural_view()) { /* handle Filter and Block specially */
227     if (get_irn_opcode(node) == iro_Filter) {
228       assert(node->attr.filter.in_cg);
229       arr = &node->attr.filter.in_cg;
230     } else if (get_irn_opcode(node) == iro_Block && node->attr.block.in_cg) {
231       arr = &node->attr.block.in_cg;
232     } else {
233       arr = &node->in;
234     }
235   } else {
236     arr = &node->in;
237   }
238   if (arity != ARR_LEN(*arr) - 1) {
239     ir_node * block = (*arr)[0];
240     *arr = NEW_ARR_D(ir_node *, current_ir_graph->obst, arity + 1);
241     (*arr)[0] = block;
242   }
243   fix_backedges(current_ir_graph->obst, node);
244   memcpy((*arr) + 1, in, sizeof(ir_node *) * arity);
245 }
246
247 ir_node *
248 (get_irn_intra_n)(const ir_node *node, int n) {
249   return _get_irn_intra_n (node, n);
250 }
251
252 ir_node *
253 (get_irn_inter_n)(const ir_node *node, int n) {
254   return _get_irn_inter_n (node, n);
255 }
256
257 ir_node *(*_get_irn_n)(const ir_node *node, int n) = _get_irn_intra_n;
258
259 ir_node *
260 (get_irn_n)(const ir_node *node, int n) {
261   return _get_irn_n(node, n);
262 }
263
264 void
265 set_irn_n (ir_node *node, int n, ir_node *in) {
266   assert(node && node->kind == k_ir_node);
267   assert(-1 <= n);
268   assert(n < get_irn_arity(node));
269   assert(in && in->kind == k_ir_node);
270
271   if ((n == -1) && (get_irn_opcode(node) == iro_Filter)) {
272     /* Change block pred in both views! */
273     node->in[n + 1] = in;
274     assert(node->attr.filter.in_cg);
275     node->attr.filter.in_cg[n + 1] = in;
276     return;
277   }
278   if (get_interprocedural_view()) { /* handle Filter and Block specially */
279     if (get_irn_opcode(node) == iro_Filter) {
280       assert(node->attr.filter.in_cg);
281       node->attr.filter.in_cg[n + 1] = in;
282       return;
283     } else if (get_irn_opcode(node) == iro_Block && node->attr.block.in_cg) {
284       node->attr.block.in_cg[n + 1] = in;
285       return;
286     }
287     /* else fall through */
288   }
289
290   /* Call the hook */
291   hook_set_irn_n(node, n, in, node->in[n + 1]);
292
293   /* Here, we rely on src and tgt being in the current ir graph */
294   edges_notify_edge(node, n, in, node->in[n + 1], current_ir_graph);
295
296   node->in[n + 1] = in;
297 }
298
299 ir_mode *
300 (get_irn_mode)(const ir_node *node) {
301   return _get_irn_mode(node);
302 }
303
304 void
305 (set_irn_mode)(ir_node *node, ir_mode *mode)
306 {
307   _set_irn_mode(node, mode);
308 }
309
310 modecode
311 get_irn_modecode (const ir_node *node)
312 {
313   assert (node);
314   return node->mode->code;
315 }
316
317 /** Gets the string representation of the mode .*/
318 const char *
319 get_irn_modename (const ir_node *node)
320 {
321   assert(node);
322   return get_mode_name(node->mode);
323 }
324
325 ident *
326 get_irn_modeident (const ir_node *node)
327 {
328   assert(node);
329   return get_mode_ident(node->mode);
330 }
331
332 ir_op *
333 (get_irn_op)(const ir_node *node)
334 {
335   return _get_irn_op(node);
336 }
337
338 /* should be private to the library: */
339 void
340 set_irn_op (ir_node *node, ir_op *op)
341 {
342   assert (node);
343   node->op = op;
344 }
345
346 opcode
347 (get_irn_opcode)(const ir_node *node)
348 {
349   return _get_irn_opcode(node);
350 }
351
352 const char *
353 get_irn_opname (const ir_node *node)
354 {
355   assert(node);
356   if ((get_irn_op((ir_node *)node) == op_Phi) &&
357       (get_irg_phase_state(get_irn_irg((ir_node *)node)) == phase_building) &&
358       (get_irn_arity((ir_node *)node) == 0)) return "Phi0";
359   return get_id_str(node->op->name);
360 }
361
362 ident *
363 get_irn_opident (const ir_node *node)
364 {
365   assert(node);
366   return node->op->name;
367 }
368
369 unsigned long
370 (get_irn_visited)(const ir_node *node)
371 {
372   return _get_irn_visited(node);
373 }
374
375 void
376 (set_irn_visited)(ir_node *node, unsigned long visited)
377 {
378   _set_irn_visited(node, visited);
379 }
380
381 void
382 (mark_irn_visited)(ir_node *node) {
383   _mark_irn_visited(node);
384 }
385
386 int
387 (irn_not_visited)(const ir_node *node) {
388   return _irn_not_visited(node);
389 }
390
391 int
392 (irn_visited)(const ir_node *node) {
393   return _irn_visited(node);
394 }
395
396 void
397 (set_irn_link)(ir_node *node, void *link) {
398   _set_irn_link(node, link);
399 }
400
401 void *
402 (get_irn_link)(const ir_node *node) {
403   return _get_irn_link(node);
404 }
405
406 op_pin_state
407 (get_irn_pinned)(const ir_node *node) {
408   return _get_irn_pinned(node);
409 }
410
411 void set_irn_pinned(ir_node *node, op_pin_state state) {
412   /* due to optimization an opt may be turned into a Tuple */
413   if (get_irn_op(node) == op_Tuple)
414     return;
415
416   assert(node && get_op_pinned(get_irn_op(node)) >= op_pin_state_exc_pinned);
417   assert(state == op_pin_state_pinned || state == op_pin_state_floats);
418
419   node->attr.except.pin_state = state;
420 }
421
422 #ifdef DO_HEAPANALYSIS
423 /* Access the abstract interpretation information of a node.
424    Returns NULL if no such information is available. */
425 struct abstval *get_irn_abst_value(ir_node *n) {
426   return n->av;
427 }
428 /* Set the abstract interpretation information of a node. */
429 void set_irn_abst_value(ir_node *n, struct abstval *os) {
430   n->av = os;
431 }
432 struct section *firm_get_irn_section(ir_node *n) {
433   return n->sec;
434 }
435 void firm_set_irn_section(ir_node *n, struct section *s) {
436   n->sec = s;
437 }
438 #else
439 /* Dummies needed for firmjni. */
440 struct abstval *get_irn_abst_value(ir_node *n) { return NULL; }
441 void set_irn_abst_value(ir_node *n, struct abstval *os) {}
442 struct section *firm_get_irn_section(ir_node *n) { return NULL; }
443 void firm_set_irn_section(ir_node *n, struct section *s) {}
444 #endif /* DO_HEAPANALYSIS */
445
446
447 /* Outputs a unique number for this node */
448 long
449 get_irn_node_nr(const ir_node *node) {
450   assert(node);
451 #ifdef DEBUG_libfirm
452   return node->node_nr;
453 #else
454   return (long)node;
455 #endif
456 }
457
458 const_attr
459 get_irn_const_attr (ir_node *node)
460 {
461   assert (node->op == op_Const);
462   return node->attr.con;
463 }
464
465 long
466 get_irn_proj_attr (ir_node *node)
467 {
468   assert (node->op == op_Proj);
469   return node->attr.proj;
470 }
471
472 alloc_attr
473 get_irn_alloc_attr (ir_node *node)
474 {
475   assert (node->op == op_Alloc);
476   return node->attr.a;
477 }
478
479 free_attr
480 get_irn_free_attr     (ir_node *node)
481 {
482   assert (node->op == op_Free);
483   return node->attr.f;
484 }
485
486 symconst_attr
487 get_irn_symconst_attr (ir_node *node)
488 {
489   assert (node->op == op_SymConst);
490   return node->attr.i;
491 }
492
493 type *
494 get_irn_call_attr (ir_node *node)
495 {
496   assert (node->op == op_Call);
497   return node->attr.call.cld_tp = skip_tid(node->attr.call.cld_tp);
498 }
499
500 sel_attr
501 get_irn_sel_attr (ir_node *node)
502 {
503   assert (node->op == op_Sel);
504   return node->attr.s;
505 }
506
507 int
508 get_irn_phi_attr (ir_node *node)
509 {
510   assert (node->op == op_Phi);
511   return node->attr.phi0_pos;
512 }
513
514 block_attr
515 get_irn_block_attr (ir_node *node)
516 {
517   assert (node->op == op_Block);
518   return node->attr.block;
519 }
520
521 load_attr
522 get_irn_load_attr (ir_node *node)
523 {
524   assert (node->op == op_Load);
525   return node->attr.load;
526 }
527
528 store_attr
529 get_irn_store_attr (ir_node *node)
530 {
531   assert (node->op == op_Store);
532   return node->attr.store;
533 }
534
535 except_attr
536 get_irn_except_attr (ir_node *node)
537 {
538   assert (node->op == op_Div || node->op == op_Quot ||
539           node->op == op_DivMod || node->op == op_Mod || node->op == op_Call || node->op == op_Alloc);
540   return node->attr.except;
541 }
542
543 /** manipulate fields of individual nodes **/
544
545 /* this works for all except Block */
546 ir_node *
547 get_nodes_block (const ir_node *node) {
548   assert (!(node->op == op_Block));
549   return get_irn_n(node, -1);
550 }
551
552 void
553 set_nodes_block (ir_node *node, ir_node *block) {
554   assert (!(node->op == op_Block));
555   set_irn_n(node, -1, block);
556 }
557
558 /* Test whether arbitrary node is frame pointer, i.e. Proj(pn_Start_P_frame_base)
559  * from Start.  If so returns frame type, else Null. */
560 type *is_frame_pointer(ir_node *n) {
561   if ((get_irn_op(n) == op_Proj) &&
562       (get_Proj_proj(n) == pn_Start_P_frame_base)) {
563     ir_node *start = get_Proj_pred(n);
564     if (get_irn_op(start) == op_Start) {
565       return get_irg_frame_type(get_irn_irg(start));
566     }
567   }
568   return NULL;
569 }
570
571 /* Test whether arbitrary node is globals pointer, i.e. Proj(pn_Start_P_globals)
572  * from Start.  If so returns global type, else Null. */
573 type *is_globals_pointer(ir_node *n) {
574   if ((get_irn_op(n) == op_Proj) &&
575       (get_Proj_proj(n) == pn_Start_P_globals)) {
576     ir_node *start = get_Proj_pred(n);
577     if (get_irn_op(start) == op_Start) {
578       return get_glob_type();
579     }
580   }
581   return NULL;
582 }
583
584 /* Test whether arbitrary node is value arg base, i.e. Proj(pn_Start_P_value_arg_base)
585  * from Start.  If so returns 1, else 0. */
586 int is_value_arg_pointer(ir_node *n) {
587   if ((get_irn_op(n) == op_Proj) &&
588       (get_Proj_proj(n) == pn_Start_P_value_arg_base) &&
589       (get_irn_op(get_Proj_pred(n)) == op_Start))
590     return 1;
591   return 0;
592 }
593
594 /* Returns an array with the predecessors of the Block. Depending on
595    the implementation of the graph data structure this can be a copy of
596    the internal representation of predecessors as well as the internal
597    array itself. Therefore writing to this array might obstruct the ir. */
598 ir_node **
599 get_Block_cfgpred_arr (ir_node *node)
600 {
601   assert ((node->op == op_Block));
602   return (ir_node **)&(get_irn_in(node)[1]);
603 }
604
605
606 int
607 get_Block_n_cfgpreds (ir_node *node) {
608   assert ((node->op == op_Block));
609   return get_irn_arity(node);
610 }
611
612 ir_node *
613 get_Block_cfgpred (ir_node *node, int pos) {
614   assert(-1 <= pos && pos < get_irn_arity(node));
615   assert(node->op == op_Block);
616   return get_irn_n(node, pos);
617 }
618
619 void
620 set_Block_cfgpred (ir_node *node, int pos, ir_node *pred) {
621   assert (node->op == op_Block);
622   set_irn_n(node, pos, pred);
623 }
624
625 bool
626 get_Block_matured (ir_node *node) {
627   assert (node->op == op_Block);
628   return node->attr.block.matured;
629 }
630
631 void
632 set_Block_matured (ir_node *node, bool matured) {
633   assert (node->op == op_Block);
634   node->attr.block.matured = matured;
635 }
636 unsigned long
637 get_Block_block_visited (ir_node *node) {
638   assert (node->op == op_Block);
639   return node->attr.block.block_visited;
640 }
641
642 void
643 set_Block_block_visited (ir_node *node, unsigned long visit) {
644   assert (node->op == op_Block);
645   node->attr.block.block_visited = visit;
646 }
647
648 /* For this current_ir_graph must be set. */
649 void
650 mark_Block_block_visited (ir_node *node) {
651   assert (node->op == op_Block);
652   node->attr.block.block_visited = get_irg_block_visited(current_ir_graph);
653 }
654
655 int
656 Block_not_block_visited(ir_node *node) {
657   assert (node->op == op_Block);
658   return (node->attr.block.block_visited < get_irg_block_visited(current_ir_graph));
659 }
660
661 ir_node *
662 get_Block_graph_arr (ir_node *node, int pos) {
663   assert (node->op == op_Block);
664   return node->attr.block.graph_arr[pos+1];
665 }
666
667 void
668 set_Block_graph_arr (ir_node *node, int pos, ir_node *value) {
669   assert (node->op == op_Block);
670   node->attr.block.graph_arr[pos+1] = value;
671 }
672
673 void set_Block_cg_cfgpred_arr(ir_node * node, int arity, ir_node ** in) {
674   assert(node->op == op_Block);
675   if (node->attr.block.in_cg == NULL || arity != ARR_LEN(node->attr.block.in_cg) - 1) {
676     node->attr.block.in_cg = NEW_ARR_D(ir_node *, current_ir_graph->obst, arity + 1);
677     node->attr.block.in_cg[0] = NULL;
678     node->attr.block.cg_backedge = new_backedge_arr(current_ir_graph->obst, arity);
679     {
680       /* Fix backedge array.  fix_backedges operates depending on
681      interprocedural_view. */
682       int ipv = get_interprocedural_view();
683       set_interprocedural_view(true);
684       fix_backedges(current_ir_graph->obst, node);
685       set_interprocedural_view(ipv);
686     }
687   }
688   memcpy(node->attr.block.in_cg + 1, in, sizeof(ir_node *) * arity);
689 }
690
691 void set_Block_cg_cfgpred(ir_node * node, int pos, ir_node * pred) {
692   assert(node->op == op_Block &&
693      node->attr.block.in_cg &&
694      0 <= pos && pos < ARR_LEN(node->attr.block.in_cg) - 1);
695   node->attr.block.in_cg[pos + 1] = pred;
696 }
697
698 ir_node ** get_Block_cg_cfgpred_arr(ir_node * node) {
699   assert(node->op == op_Block);
700   return node->attr.block.in_cg == NULL ? NULL : node->attr.block.in_cg  + 1;
701 }
702
703 int get_Block_cg_n_cfgpreds(ir_node * node) {
704   assert(node->op == op_Block);
705   return node->attr.block.in_cg == NULL ? 0 : ARR_LEN(node->attr.block.in_cg) - 1;
706 }
707
708 ir_node * get_Block_cg_cfgpred(ir_node * node, int pos) {
709   assert(node->op == op_Block && node->attr.block.in_cg);
710   return node->attr.block.in_cg[pos + 1];
711 }
712
713 void remove_Block_cg_cfgpred_arr(ir_node * node) {
714   assert(node->op == op_Block);
715   node->attr.block.in_cg = NULL;
716 }
717
718 ir_node *(set_Block_dead)(ir_node *block) {
719   return _set_Block_dead(block);
720 }
721
722 int (is_Block_dead)(const ir_node *block) {
723   return _is_Block_dead(block);
724 }
725
726 void
727 set_Start_irg(ir_node *node, ir_graph *irg) {
728   assert(node->op == op_Start);
729   assert(is_ir_graph(irg));
730   assert(0 && " Why set irg? -- use set_irn_irg");
731 }
732
733 int
734 get_End_n_keepalives(ir_node *end) {
735   assert (end->op == op_End);
736   return (get_irn_arity(end) - END_KEEPALIVE_OFFSET);
737 }
738
739 ir_node *
740 get_End_keepalive(ir_node *end, int pos) {
741   assert (end->op == op_End);
742   return get_irn_n(end, pos + END_KEEPALIVE_OFFSET);
743 }
744
745 void
746 add_End_keepalive (ir_node *end, ir_node *ka) {
747   assert (end->op == op_End);
748   ARR_APP1 (ir_node *, end->in, ka);
749 }
750
751 void
752 set_End_keepalive(ir_node *end, int pos, ir_node *ka) {
753   assert (end->op == op_End);
754   set_irn_n(end, pos + END_KEEPALIVE_OFFSET, ka);
755 }
756
757 void
758 free_End (ir_node *end) {
759   assert (end->op == op_End);
760   end->kind = k_BAD;
761   DEL_ARR_F(end->in);  /* GL @@@ tut nicht ! */
762   end->in = NULL;   /* @@@ make sure we get an error if we use the
763                in array afterwards ... */
764 }
765
766
767 /*
768 > Implementing the case construct (which is where the constant Proj node is
769 > important) involves far more than simply determining the constant values.
770 > We could argue that this is more properly a function of the translator from
771 > Firm to the target machine.  That could be done if there was some way of
772 > projecting "default" out of the Cond node.
773 I know it's complicated.
774 Basically there are two proglems:
775  - determining the gaps between the projs
776  - determining the biggest case constant to know the proj number for
777    the default node.
778 I see several solutions:
779 1. Introduce a ProjDefault node.  Solves both problems.
780    This means to extend all optimizations executed during construction.
781 2. Give the Cond node for switch two flavors:
782    a) there are no gaps in the projs  (existing flavor)
783    b) gaps may exist, default proj is still the Proj with the largest
784       projection number.  This covers also the gaps.
785 3. Fix the semantic of the Cond to that of 2b)
786
787 Solution 2 seems to be the best:
788 Computing the gaps in the Firm representation is not too hard, i.e.,
789 libFIRM can implement a routine that transforms between the two
790 flavours.  This is also possible for 1) but 2) does not require to
791 change any existing optimization.
792 Further it should be far simpler to determine the biggest constant than
793 to compute all gaps.
794 I don't want to choose 3) as 2a) seems to have advantages for
795 dataflow analysis and 3) does not allow to convert the representation to
796 2a).
797 */
798 ir_node *
799 get_Cond_selector (ir_node *node) {
800   assert (node->op == op_Cond);
801   return get_irn_n(node, 0);
802 }
803
804 void
805 set_Cond_selector (ir_node *node, ir_node *selector) {
806   assert (node->op == op_Cond);
807   set_irn_n(node, 0, selector);
808 }
809
810 cond_kind
811 get_Cond_kind (ir_node *node) {
812   assert (node->op == op_Cond);
813   return node->attr.c.kind;
814 }
815
816 void
817 set_Cond_kind (ir_node *node, cond_kind kind) {
818   assert (node->op == op_Cond);
819   node->attr.c.kind = kind;
820 }
821
822 long
823 get_Cond_defaultProj (ir_node *node) {
824   assert (node->op == op_Cond);
825   return node->attr.c.default_proj;
826 }
827
828 ir_node *
829 get_Return_mem (ir_node *node) {
830   assert (node->op == op_Return);
831   return get_irn_n(node, 0);
832 }
833
834 void
835 set_Return_mem (ir_node *node, ir_node *mem) {
836   assert (node->op == op_Return);
837   set_irn_n(node, 0, mem);
838 }
839
840 int
841 get_Return_n_ress (ir_node *node) {
842   assert (node->op == op_Return);
843   return (get_irn_arity(node) - RETURN_RESULT_OFFSET);
844 }
845
846 ir_node **
847 get_Return_res_arr (ir_node *node)
848 {
849   assert ((node->op == op_Return));
850   if (get_Return_n_ress(node) > 0)
851     return (ir_node **)&(get_irn_in(node)[1 + RETURN_RESULT_OFFSET]);
852   else
853     return NULL;
854 }
855
856 /*
857 void
858 set_Return_n_res (ir_node *node, int results) {
859   assert (node->op == op_Return);
860 }
861 */
862
863 ir_node *
864 get_Return_res (ir_node *node, int pos) {
865   assert (node->op == op_Return);
866   assert (get_Return_n_ress(node) > pos);
867   return get_irn_n(node, pos + RETURN_RESULT_OFFSET);
868 }
869
870 void
871 set_Return_res (ir_node *node, int pos, ir_node *res){
872   assert (node->op == op_Return);
873   set_irn_n(node, pos + RETURN_RESULT_OFFSET, res);
874 }
875
876 ir_node *
877 get_Raise_mem (ir_node *node) {
878   assert (node->op == op_Raise);
879   return get_irn_n(node, 0);
880 }
881
882 void
883 set_Raise_mem (ir_node *node, ir_node *mem) {
884   assert (node->op == op_Raise);
885   set_irn_n(node, 0, mem);
886 }
887
888 ir_node *
889 get_Raise_exo_ptr (ir_node *node) {
890   assert (node->op == op_Raise);
891   return get_irn_n(node, 1);
892 }
893
894 void
895 set_Raise_exo_ptr (ir_node *node, ir_node *exo_ptr) {
896   assert (node->op == op_Raise);
897   set_irn_n(node, 1, exo_ptr);
898 }
899
900 tarval *(get_Const_tarval)(ir_node *node) {
901         return _get_Const_tarval(node);
902 }
903
904 void
905 set_Const_tarval (ir_node *node, tarval *con) {
906   assert (node->op == op_Const);
907   node->attr.con.tv = con;
908 }
909
910 cnst_classify_t (classify_Const)(ir_node *node)
911 {
912         return _classify_Const(node);
913 }
914
915
916 /* The source language type.  Must be an atomic type.  Mode of type must
917    be mode of node. For tarvals from entities type must be pointer to
918    entity type. */
919 type *
920 get_Const_type (ir_node *node) {
921   assert (node->op == op_Const);
922   return node->attr.con.tp;
923 }
924
925 void
926 set_Const_type (ir_node *node, type *tp) {
927   assert (node->op == op_Const);
928   if (tp != firm_unknown_type) {
929     assert (is_atomic_type(tp));
930     assert (get_type_mode(tp) == get_irn_mode(node));
931   }
932   node->attr.con.tp = tp;
933 }
934
935
936 symconst_kind
937 get_SymConst_kind (const ir_node *node) {
938   assert (node->op == op_SymConst);
939   return node->attr.i.num;
940 }
941
942 void
943 set_SymConst_kind (ir_node *node, symconst_kind num) {
944   assert (node->op == op_SymConst);
945   node->attr.i.num = num;
946 }
947
948 type *
949 get_SymConst_type (ir_node *node) {
950   assert (   (node->op == op_SymConst)
951           && (   get_SymConst_kind(node) == symconst_type_tag
952               || get_SymConst_kind(node) == symconst_size));
953   return node->attr.i.sym.type_p = skip_tid(node->attr.i.sym.type_p);
954 }
955
956 void
957 set_SymConst_type (ir_node *node, type *tp) {
958   assert (   (node->op == op_SymConst)
959           && (   get_SymConst_kind(node) == symconst_type_tag
960               || get_SymConst_kind(node) == symconst_size));
961   node->attr.i.sym.type_p = tp;
962 }
963
964 ident *
965 get_SymConst_name (ir_node *node) {
966   assert (   (node->op == op_SymConst)
967           && (get_SymConst_kind(node) == symconst_addr_name));
968   return node->attr.i.sym.ident_p;
969 }
970
971 void
972 set_SymConst_name (ir_node *node, ident *name) {
973   assert (   (node->op == op_SymConst)
974           && (get_SymConst_kind(node) == symconst_addr_name));
975   node->attr.i.sym.ident_p = name;
976 }
977
978
979 /* Only to access SymConst of kind symconst_addr_ent.  Else assertion: */
980 entity   *get_SymConst_entity (ir_node *node) {
981   assert (   (node->op == op_SymConst)
982           && (get_SymConst_kind (node) == symconst_addr_ent));
983   return node->attr.i.sym.entity_p;
984 }
985
986 void     set_SymConst_entity (ir_node *node, entity *ent) {
987   assert (   (node->op == op_SymConst)
988           && (get_SymConst_kind(node) == symconst_addr_ent));
989   node->attr.i.sym.entity_p  = ent;
990 }
991
992 union symconst_symbol
993 get_SymConst_symbol (ir_node *node) {
994   assert (node->op == op_SymConst);
995   return node->attr.i.sym;
996 }
997
998 void
999 set_SymConst_symbol (ir_node *node, union symconst_symbol sym) {
1000   assert (node->op == op_SymConst);
1001   //memcpy (&(node->attr.i.sym), sym, sizeof(type_or_id));
1002   node->attr.i.sym = sym;
1003 }
1004
1005 type *
1006 get_SymConst_value_type (ir_node *node) {
1007   assert (node->op == op_SymConst);
1008   if (node->attr.i.tp) node->attr.i.tp = skip_tid(node->attr.i.tp);
1009   return node->attr.i.tp;
1010 }
1011
1012 void
1013 set_SymConst_value_type (ir_node *node, type *tp) {
1014   assert (node->op == op_SymConst);
1015   node->attr.i.tp = tp;
1016 }
1017
1018 ir_node *
1019 get_Sel_mem (ir_node *node) {
1020   assert (node->op == op_Sel);
1021   return get_irn_n(node, 0);
1022 }
1023
1024 void
1025 set_Sel_mem (ir_node *node, ir_node *mem) {
1026   assert (node->op == op_Sel);
1027   set_irn_n(node, 0, mem);
1028 }
1029
1030 ir_node *
1031 get_Sel_ptr (ir_node *node) {
1032   assert (node->op == op_Sel);
1033   return get_irn_n(node, 1);
1034 }
1035
1036 void
1037 set_Sel_ptr (ir_node *node, ir_node *ptr) {
1038   assert (node->op == op_Sel);
1039   set_irn_n(node, 1, ptr);
1040 }
1041
1042 int
1043 get_Sel_n_indexs (ir_node *node) {
1044   assert (node->op == op_Sel);
1045   return (get_irn_arity(node) - SEL_INDEX_OFFSET);
1046 }
1047
1048 ir_node **
1049 get_Sel_index_arr (ir_node *node)
1050 {
1051   assert ((node->op == op_Sel));
1052   if (get_Sel_n_indexs(node) > 0)
1053     return (ir_node **)& get_irn_in(node)[SEL_INDEX_OFFSET + 1];
1054   else
1055     return NULL;
1056 }
1057
1058 ir_node *
1059 get_Sel_index (ir_node *node, int pos) {
1060   assert (node->op == op_Sel);
1061   return get_irn_n(node, pos + SEL_INDEX_OFFSET);
1062 }
1063
1064 void
1065 set_Sel_index (ir_node *node, int pos, ir_node *index) {
1066   assert (node->op == op_Sel);
1067   set_irn_n(node, pos + SEL_INDEX_OFFSET, index);
1068 }
1069
1070 entity *
1071 get_Sel_entity (ir_node *node) {
1072   assert (node->op == op_Sel);
1073   return node->attr.s.ent;
1074 }
1075
1076 void
1077 set_Sel_entity (ir_node *node, entity *ent) {
1078   assert (node->op == op_Sel);
1079   node->attr.s.ent = ent;
1080 }
1081
1082 type *
1083 get_InstOf_ent (ir_node *node) {
1084   assert (node->op = op_InstOf);
1085   return (node->attr.io.ent);
1086 }
1087
1088 void
1089 set_InstOf_ent (ir_node *node, type *ent) {
1090   assert (node->op = op_InstOf);
1091   node->attr.io.ent = ent;
1092 }
1093
1094 ir_node *
1095 get_InstOf_store (ir_node *node) {
1096   assert (node->op = op_InstOf);
1097   return (get_irn_n (node, 0));
1098 }
1099
1100 void
1101 set_InstOf_store (ir_node *node, ir_node *obj) {
1102   assert (node->op = op_InstOf);
1103   set_irn_n (node, 0, obj);
1104 }
1105
1106 ir_node *
1107 get_InstOf_obj (ir_node *node) {
1108   assert (node->op = op_InstOf);
1109   return (get_irn_n (node, 1));
1110 }
1111
1112 void
1113 set_InstOf_obj (ir_node *node, ir_node *obj) {
1114   assert (node->op = op_InstOf);
1115   set_irn_n (node, 1, obj);
1116 }
1117
1118
1119 /* For unary and binary arithmetic operations the access to the
1120    operands can be factored out.  Left is the first, right the
1121    second arithmetic value  as listed in tech report 0999-33.
1122    unops are: Minus, Abs, Not, Conv, Cast
1123    binops are: Add, Sub, Mul, Quot, DivMod, Div, Mod, And, Or, Eor, Shl,
1124    Shr, Shrs, Rotate, Cmp */
1125
1126
1127 ir_node *
1128 get_Call_mem (ir_node *node) {
1129   assert (node->op == op_Call);
1130   return get_irn_n(node, 0);
1131 }
1132
1133 void
1134 set_Call_mem (ir_node *node, ir_node *mem) {
1135   assert (node->op == op_Call);
1136   set_irn_n(node, 0, mem);
1137 }
1138
1139 ir_node *
1140 get_Call_ptr (ir_node *node) {
1141   assert (node->op == op_Call);
1142   return get_irn_n(node, 1);
1143 }
1144
1145 void
1146 set_Call_ptr (ir_node *node, ir_node *ptr) {
1147   assert (node->op == op_Call);
1148   set_irn_n(node, 1, ptr);
1149 }
1150
1151 ir_node **
1152 get_Call_param_arr (ir_node *node) {
1153   assert (node->op == op_Call);
1154   return (ir_node **)&get_irn_in(node)[CALL_PARAM_OFFSET + 1];
1155 }
1156
1157 int
1158 get_Call_n_params (ir_node *node)  {
1159   assert (node->op == op_Call);
1160   return (get_irn_arity(node) - CALL_PARAM_OFFSET);
1161 }
1162
1163 int
1164 get_Call_arity (ir_node *node) {
1165   assert (node->op == op_Call);
1166   return get_Call_n_params(node);
1167 }
1168
1169 /* void
1170 set_Call_arity (ir_node *node, ir_node *arity) {
1171   assert (node->op == op_Call);
1172 }
1173 */
1174
1175 ir_node *
1176 get_Call_param (ir_node *node, int pos) {
1177   assert (node->op == op_Call);
1178   return get_irn_n(node, pos + CALL_PARAM_OFFSET);
1179 }
1180
1181 void
1182 set_Call_param (ir_node *node, int pos, ir_node *param) {
1183   assert (node->op == op_Call);
1184   set_irn_n(node, pos + CALL_PARAM_OFFSET, param);
1185 }
1186
1187 type *
1188 get_Call_type (ir_node *node) {
1189   assert (node->op == op_Call);
1190   return node->attr.call.cld_tp = skip_tid(node->attr.call.cld_tp);
1191 }
1192
1193 void
1194 set_Call_type (ir_node *node, type *tp) {
1195   assert (node->op == op_Call);
1196   assert ((get_unknown_type() == tp) || is_Method_type(tp));
1197   node->attr.call.cld_tp = tp;
1198 }
1199
1200 int Call_has_callees(ir_node *node) {
1201   assert(node && node->op == op_Call);
1202   return ((get_irg_callee_info_state(get_irn_irg(node)) != irg_callee_info_none) &&
1203       (node->attr.call.callee_arr != NULL));
1204 }
1205
1206 int get_Call_n_callees(ir_node * node) {
1207   assert(node && node->op == op_Call && node->attr.call.callee_arr);
1208   return ARR_LEN(node->attr.call.callee_arr);
1209 }
1210
1211 entity * get_Call_callee(ir_node * node, int pos) {
1212   assert(pos >= 0 && pos < get_Call_n_callees(node));
1213   return node->attr.call.callee_arr[pos];
1214 }
1215
1216 void set_Call_callee_arr(ir_node * node, const int n, entity ** arr) {
1217   assert(node->op == op_Call);
1218   if (node->attr.call.callee_arr == NULL || get_Call_n_callees(node) != n) {
1219     node->attr.call.callee_arr = NEW_ARR_D(entity *, current_ir_graph->obst, n);
1220   }
1221   memcpy(node->attr.call.callee_arr, arr, n * sizeof(entity *));
1222 }
1223
1224 void remove_Call_callee_arr(ir_node * node) {
1225   assert(node->op == op_Call);
1226   node->attr.call.callee_arr = NULL;
1227 }
1228
1229 ir_node * get_CallBegin_ptr (ir_node *node) {
1230   assert(node->op == op_CallBegin);
1231   return get_irn_n(node, 0);
1232 }
1233 void set_CallBegin_ptr (ir_node *node, ir_node *ptr) {
1234   assert(node->op == op_CallBegin);
1235   set_irn_n(node, 0, ptr);
1236 }
1237 ir_node * get_CallBegin_call (ir_node *node) {
1238   assert(node->op == op_CallBegin);
1239   return node->attr.callbegin.call;
1240 }
1241 void  set_CallBegin_call (ir_node *node, ir_node *call) {
1242   assert(node->op == op_CallBegin);
1243   node->attr.callbegin.call = call;
1244 }
1245
1246
1247 #define BINOP(OP)                   \
1248 ir_node * get_##OP##_left(ir_node *node) {      \
1249   assert(node->op == op_##OP);              \
1250   return get_irn_n(node, node->op->op_index);       \
1251 }                           \
1252 void set_##OP##_left(ir_node *node, ir_node *left) {    \
1253   assert(node->op == op_##OP);              \
1254   set_irn_n(node, node->op->op_index, left);        \
1255 }                           \
1256 ir_node *get_##OP##_right(ir_node *node) {      \
1257   assert(node->op == op_##OP);              \
1258   return get_irn_n(node, node->op->op_index + 1);   \
1259 }                           \
1260 void set_##OP##_right(ir_node *node, ir_node *right) {  \
1261   assert(node->op == op_##OP);              \
1262   set_irn_n(node, node->op->op_index + 1, right);   \
1263 }
1264
1265 #define UNOP(OP)                    \
1266 ir_node *get_##OP##_op(ir_node *node) {         \
1267   assert(node->op == op_##OP);              \
1268   return get_irn_n(node, node->op->op_index);       \
1269 }                           \
1270 void set_##OP##_op (ir_node *node, ir_node *op) {   \
1271   assert(node->op == op_##OP);              \
1272   set_irn_n(node, node->op->op_index, op);      \
1273 }
1274
1275 BINOP(Add)
1276 BINOP(Sub)
1277 UNOP(Minus)
1278 BINOP(Mul)
1279 BINOP(Quot)
1280
1281 ir_node *
1282 get_Quot_mem (ir_node *node) {
1283   assert (node->op == op_Quot);
1284   return get_irn_n(node, 0);
1285 }
1286
1287 void
1288 set_Quot_mem (ir_node *node, ir_node *mem) {
1289   assert (node->op == op_Quot);
1290   set_irn_n(node, 0, mem);
1291 }
1292
1293 BINOP(DivMod)
1294
1295 ir_node *
1296 get_DivMod_mem (ir_node *node) {
1297   assert (node->op == op_DivMod);
1298   return get_irn_n(node, 0);
1299 }
1300
1301 void
1302 set_DivMod_mem (ir_node *node, ir_node *mem) {
1303   assert (node->op == op_DivMod);
1304   set_irn_n(node, 0, mem);
1305 }
1306
1307 BINOP(Div)
1308
1309 ir_node *
1310 get_Div_mem (ir_node *node) {
1311   assert (node->op == op_Div);
1312   return get_irn_n(node, 0);
1313 }
1314
1315 void
1316 set_Div_mem (ir_node *node, ir_node *mem) {
1317   assert (node->op == op_Div);
1318   set_irn_n(node, 0, mem);
1319 }
1320
1321 BINOP(Mod)
1322
1323 ir_node *
1324 get_Mod_mem (ir_node *node) {
1325   assert (node->op == op_Mod);
1326   return get_irn_n(node, 0);
1327 }
1328
1329 void
1330 set_Mod_mem (ir_node *node, ir_node *mem) {
1331   assert (node->op == op_Mod);
1332   set_irn_n(node, 0, mem);
1333 }
1334
1335 UNOP(Abs)
1336 BINOP(And)
1337 BINOP(Or)
1338 BINOP(Eor)
1339 UNOP(Not)
1340 BINOP(Shl)
1341 BINOP(Shr)
1342 BINOP(Shrs)
1343 BINOP(Rot)
1344 BINOP(Cmp)
1345 UNOP(Conv)
1346 UNOP(Cast)
1347
1348 type *
1349 get_Cast_type (ir_node *node) {
1350   assert (node->op == op_Cast);
1351   return node->attr.cast.totype;
1352 }
1353
1354 void
1355 set_Cast_type (ir_node *node, type *to_tp) {
1356   assert (node->op == op_Cast);
1357   node->attr.cast.totype = to_tp;
1358 }
1359
1360 int
1361 (is_unop)(const ir_node *node) {
1362   return _is_unop(node);
1363 }
1364
1365 ir_node *
1366 get_unop_op (ir_node *node) {
1367   if (node->op->opar == oparity_unary)
1368     return get_irn_n(node, node->op->op_index);
1369
1370   assert(node->op->opar == oparity_unary);
1371   return NULL;
1372 }
1373
1374 void
1375 set_unop_op (ir_node *node, ir_node *op) {
1376   if (node->op->opar == oparity_unary)
1377     set_irn_n(node, node->op->op_index, op);
1378
1379   assert(node->op->opar == oparity_unary);
1380 }
1381
1382 int
1383 (is_binop)(const ir_node *node) {
1384   return _is_binop(node);
1385 }
1386
1387 ir_node *
1388 get_binop_left (ir_node *node) {
1389   if (node->op->opar == oparity_binary)
1390     return get_irn_n(node, node->op->op_index);
1391
1392   assert(node->op->opar == oparity_binary);
1393   return NULL;
1394 }
1395
1396 void
1397 set_binop_left (ir_node *node, ir_node *left) {
1398   if (node->op->opar == oparity_binary)
1399     set_irn_n(node, node->op->op_index, left);
1400
1401   assert (node->op->opar == oparity_binary);
1402 }
1403
1404 ir_node *
1405 get_binop_right (ir_node *node) {
1406   if (node->op->opar == oparity_binary)
1407     return get_irn_n(node, node->op->op_index + 1);
1408
1409   assert(node->op->opar == oparity_binary);
1410   return NULL;
1411 }
1412
1413 void
1414 set_binop_right (ir_node *node, ir_node *right) {
1415   if (node->op->opar == oparity_binary)
1416     set_irn_n(node, node->op->op_index + 1, right);
1417
1418   assert (node->op->opar == oparity_binary);
1419 }
1420
1421 int is_Phi (const ir_node *n) {
1422   ir_op *op;
1423
1424   assert(n);
1425   op = get_irn_op(n);
1426
1427   if (op == op_Filter) return get_interprocedural_view();
1428
1429   if (op == op_Phi)
1430     return  ((get_irg_phase_state(get_irn_irg(n)) !=  phase_building) ||
1431          (get_irn_arity(n) > 0));
1432
1433   return 0;
1434 }
1435
1436 int is_Phi0 (const ir_node *n) {
1437   assert(n);
1438
1439   return ((get_irn_op(n) == op_Phi) &&
1440       (get_irn_arity(n) == 0) &&
1441       (get_irg_phase_state(get_irn_irg(n)) ==  phase_building));
1442 }
1443
1444 ir_node **
1445 get_Phi_preds_arr (ir_node *node) {
1446   assert (node->op == op_Phi);
1447   return (ir_node **)&(get_irn_in(node)[1]);
1448 }
1449
1450 int
1451 get_Phi_n_preds (ir_node *node) {
1452   assert (is_Phi(node) || is_Phi0(node));
1453   return (get_irn_arity(node));
1454 }
1455
1456 /*
1457 void set_Phi_n_preds (ir_node *node, int n_preds) {
1458   assert (node->op == op_Phi);
1459 }
1460 */
1461
1462 ir_node *
1463 get_Phi_pred (ir_node *node, int pos) {
1464   assert (is_Phi(node) || is_Phi0(node));
1465   return get_irn_n(node, pos);
1466 }
1467
1468 void
1469 set_Phi_pred (ir_node *node, int pos, ir_node *pred) {
1470   assert (is_Phi(node) || is_Phi0(node));
1471   set_irn_n(node, pos, pred);
1472 }
1473
1474
1475 int is_memop(ir_node *node) {
1476   return ((get_irn_op(node) == op_Load) || (get_irn_op(node) == op_Store));
1477 }
1478
1479 ir_node *get_memop_mem (ir_node *node) {
1480   assert(is_memop(node));
1481   return get_irn_n(node, 0);
1482 }
1483
1484 void     set_memop_mem (ir_node *node, ir_node *mem) {
1485   assert(is_memop(node));
1486   set_irn_n(node, 0, mem);
1487 }
1488
1489 ir_node *get_memop_ptr (ir_node *node) {
1490   assert(is_memop(node));
1491   return get_irn_n(node, 1);
1492 }
1493
1494 void     set_memop_ptr (ir_node *node, ir_node *ptr) {
1495   assert(is_memop(node));
1496   set_irn_n(node, 1, ptr);
1497 }
1498
1499 ir_node *
1500 get_Load_mem (ir_node *node) {
1501   assert (node->op == op_Load);
1502   return get_irn_n(node, 0);
1503 }
1504
1505 void
1506 set_Load_mem (ir_node *node, ir_node *mem) {
1507   assert (node->op == op_Load);
1508   set_irn_n(node, 0, mem);
1509 }
1510
1511 ir_node *
1512 get_Load_ptr (ir_node *node) {
1513   assert (node->op == op_Load);
1514   return get_irn_n(node, 1);
1515 }
1516
1517 void
1518 set_Load_ptr (ir_node *node, ir_node *ptr) {
1519   assert (node->op == op_Load);
1520   set_irn_n(node, 1, ptr);
1521 }
1522
1523 ir_mode *
1524 get_Load_mode (ir_node *node) {
1525   assert (node->op == op_Load);
1526   return node->attr.load.load_mode;
1527 }
1528
1529 void
1530 set_Load_mode (ir_node *node, ir_mode *mode) {
1531   assert (node->op == op_Load);
1532   node->attr.load.load_mode = mode;
1533 }
1534
1535 ent_volatility
1536 get_Load_volatility (ir_node *node) {
1537   assert (node->op == op_Load);
1538   return node->attr.load.volatility;
1539 }
1540
1541 void
1542 set_Load_volatility (ir_node *node, ent_volatility volatility) {
1543   assert (node->op == op_Load);
1544   node->attr.load.volatility = volatility;
1545 }
1546
1547
1548 ir_node *
1549 get_Store_mem (ir_node *node) {
1550   assert (node->op == op_Store);
1551   return get_irn_n(node, 0);
1552 }
1553
1554 void
1555 set_Store_mem (ir_node *node, ir_node *mem) {
1556   assert (node->op == op_Store);
1557   set_irn_n(node, 0, mem);
1558 }
1559
1560 ir_node *
1561 get_Store_ptr (ir_node *node) {
1562   assert (node->op == op_Store);
1563   return get_irn_n(node, 1);
1564 }
1565
1566 void
1567 set_Store_ptr (ir_node *node, ir_node *ptr) {
1568   assert (node->op == op_Store);
1569   set_irn_n(node, 1, ptr);
1570 }
1571
1572 ir_node *
1573 get_Store_value (ir_node *node) {
1574   assert (node->op == op_Store);
1575   return get_irn_n(node, 2);
1576 }
1577
1578 void
1579 set_Store_value (ir_node *node, ir_node *value) {
1580   assert (node->op == op_Store);
1581   set_irn_n(node, 2, value);
1582 }
1583
1584 ent_volatility
1585 get_Store_volatility (ir_node *node) {
1586   assert (node->op == op_Store);
1587   return node->attr.store.volatility;
1588 }
1589
1590 void
1591 set_Store_volatility (ir_node *node, ent_volatility volatility) {
1592   assert (node->op == op_Store);
1593   node->attr.store.volatility = volatility;
1594 }
1595
1596
1597 ir_node *
1598 get_Alloc_mem (ir_node *node) {
1599   assert (node->op == op_Alloc);
1600   return get_irn_n(node, 0);
1601 }
1602
1603 void
1604 set_Alloc_mem (ir_node *node, ir_node *mem) {
1605   assert (node->op == op_Alloc);
1606   set_irn_n(node, 0, mem);
1607 }
1608
1609 ir_node *
1610 get_Alloc_size (ir_node *node) {
1611   assert (node->op == op_Alloc);
1612   return get_irn_n(node, 1);
1613 }
1614
1615 void
1616 set_Alloc_size (ir_node *node, ir_node *size) {
1617   assert (node->op == op_Alloc);
1618   set_irn_n(node, 1, size);
1619 }
1620
1621 type  *
1622 get_Alloc_type (ir_node *node) {
1623   assert (node->op == op_Alloc);
1624   return node->attr.a.type = skip_tid(node->attr.a.type);
1625 }
1626
1627 void
1628 set_Alloc_type (ir_node *node, type *tp) {
1629   assert (node->op == op_Alloc);
1630   node->attr.a.type = tp;
1631 }
1632
1633 where_alloc
1634 get_Alloc_where (ir_node *node) {
1635   assert (node->op == op_Alloc);
1636   return node->attr.a.where;
1637 }
1638
1639 void
1640 set_Alloc_where (ir_node *node, where_alloc where) {
1641   assert (node->op == op_Alloc);
1642   node->attr.a.where = where;
1643 }
1644
1645
1646 ir_node *
1647 get_Free_mem (ir_node *node) {
1648   assert (node->op == op_Free);
1649   return get_irn_n(node, 0);
1650 }
1651
1652 void
1653 set_Free_mem (ir_node *node, ir_node *mem) {
1654   assert (node->op == op_Free);
1655   set_irn_n(node, 0, mem);
1656 }
1657
1658 ir_node *
1659 get_Free_ptr (ir_node *node) {
1660   assert (node->op == op_Free);
1661   return get_irn_n(node, 1);
1662 }
1663
1664 void
1665 set_Free_ptr (ir_node *node, ir_node *ptr) {
1666   assert (node->op == op_Free);
1667   set_irn_n(node, 1, ptr);
1668 }
1669
1670 ir_node *
1671 get_Free_size (ir_node *node) {
1672   assert (node->op == op_Free);
1673   return get_irn_n(node, 2);
1674 }
1675
1676 void
1677 set_Free_size (ir_node *node, ir_node *size) {
1678   assert (node->op == op_Free);
1679   set_irn_n(node, 2, size);
1680 }
1681
1682 type  *
1683 get_Free_type (ir_node *node) {
1684   assert (node->op == op_Free);
1685   return node->attr.f.type = skip_tid(node->attr.f.type);
1686 }
1687
1688 void
1689 set_Free_type (ir_node *node, type *tp) {
1690   assert (node->op == op_Free);
1691   node->attr.f.type = tp;
1692 }
1693
1694 where_alloc
1695 get_Free_where (ir_node *node) {
1696   assert (node->op == op_Free);
1697   return node->attr.f.where;
1698 }
1699
1700 void
1701 set_Free_where (ir_node *node, where_alloc where) {
1702   assert (node->op == op_Free);
1703   node->attr.f.where = where;
1704 }
1705
1706 ir_node **
1707 get_Sync_preds_arr (ir_node *node) {
1708   assert (node->op == op_Sync);
1709   return (ir_node **)&(get_irn_in(node)[1]);
1710 }
1711
1712 int
1713 get_Sync_n_preds (ir_node *node) {
1714   assert (node->op == op_Sync);
1715   return (get_irn_arity(node));
1716 }
1717
1718 /*
1719 void
1720 set_Sync_n_preds (ir_node *node, int n_preds) {
1721   assert (node->op == op_Sync);
1722 }
1723 */
1724
1725 ir_node *
1726 get_Sync_pred (ir_node *node, int pos) {
1727   assert (node->op == op_Sync);
1728   return get_irn_n(node, pos);
1729 }
1730
1731 void
1732 set_Sync_pred (ir_node *node, int pos, ir_node *pred) {
1733   assert (node->op == op_Sync);
1734   set_irn_n(node, pos, pred);
1735 }
1736
1737 type *get_Proj_type(ir_node *n)
1738 {
1739   type *tp      = NULL;
1740   ir_node *pred = get_Proj_pred(n);
1741
1742   switch (get_irn_opcode(pred)) {
1743   case iro_Proj: {
1744     ir_node *pred_pred;
1745     /* Deal with Start / Call here: we need to know the Proj Nr. */
1746     assert(get_irn_mode(pred) == mode_T);
1747     pred_pred = get_Proj_pred(pred);
1748     if (get_irn_op(pred_pred) == op_Start)  {
1749       type *mtp = get_entity_type(get_irg_entity(get_irn_irg(pred_pred)));
1750       tp = get_method_param_type(mtp, get_Proj_proj(n));
1751     } else if (get_irn_op(pred_pred) == op_Call) {
1752       type *mtp = get_Call_type(pred_pred);
1753       tp = get_method_res_type(mtp, get_Proj_proj(n));
1754     }
1755   } break;
1756   case iro_Start: break;
1757   case iro_Call: break;
1758   case iro_Load: {
1759     ir_node *a = get_Load_ptr(pred);
1760     if (get_irn_op(a) == op_Sel)
1761       tp = get_entity_type(get_Sel_entity(a));
1762   } break;
1763   default:
1764     break;
1765   }
1766   return tp;
1767 }
1768
1769 ir_node *
1770 get_Proj_pred (ir_node *node) {
1771   assert (is_Proj(node));
1772   return get_irn_n(node, 0);
1773 }
1774
1775 void
1776 set_Proj_pred (ir_node *node, ir_node *pred) {
1777   assert (is_Proj(node));
1778   set_irn_n(node, 0, pred);
1779 }
1780
1781 long
1782 get_Proj_proj (ir_node *node) {
1783   assert (is_Proj(node));
1784   if (get_irn_opcode(node) == iro_Proj) {
1785     return node->attr.proj;
1786   } else {
1787     assert(get_irn_opcode(node) == iro_Filter);
1788     return node->attr.filter.proj;
1789   }
1790 }
1791
1792 void
1793 set_Proj_proj (ir_node *node, long proj) {
1794   assert (node->op == op_Proj);
1795   node->attr.proj = proj;
1796 }
1797
1798 ir_node **
1799 get_Tuple_preds_arr (ir_node *node) {
1800   assert (node->op == op_Tuple);
1801   return (ir_node **)&(get_irn_in(node)[1]);
1802 }
1803
1804 int
1805 get_Tuple_n_preds (ir_node *node) {
1806   assert (node->op == op_Tuple);
1807   return (get_irn_arity(node));
1808 }
1809
1810 /*
1811 void
1812 set_Tuple_n_preds (ir_node *node, int n_preds) {
1813   assert (node->op == op_Tuple);
1814 }
1815 */
1816
1817 ir_node *
1818 get_Tuple_pred (ir_node *node, int pos) {
1819   assert (node->op == op_Tuple);
1820   return get_irn_n(node, pos);
1821 }
1822
1823 void
1824 set_Tuple_pred (ir_node *node, int pos, ir_node *pred) {
1825   assert (node->op == op_Tuple);
1826   set_irn_n(node, pos, pred);
1827 }
1828
1829 ir_node *
1830 get_Id_pred (ir_node *node) {
1831   assert (node->op == op_Id);
1832   return get_irn_n(node, 0);
1833 }
1834
1835 void
1836 set_Id_pred (ir_node *node, ir_node *pred) {
1837   assert (node->op == op_Id);
1838   set_irn_n(node, 0, pred);
1839 }
1840
1841 ir_node *get_Confirm_value (ir_node *node) {
1842   assert (node->op == op_Confirm);
1843   return get_irn_n(node, 0);
1844 }
1845 void     set_Confirm_value (ir_node *node, ir_node *value) {
1846   assert (node->op == op_Confirm);
1847   set_irn_n(node, 0, value);
1848 }
1849 ir_node *get_Confirm_bound (ir_node *node) {
1850   assert (node->op == op_Confirm);
1851   return get_irn_n(node, 1);
1852 }
1853 void     set_Confirm_bound (ir_node *node, ir_node *bound) {
1854   assert (node->op == op_Confirm);
1855   set_irn_n(node, 0, bound);
1856 }
1857 pn_Cmp   get_Confirm_cmp   (ir_node *node) {
1858   assert (node->op == op_Confirm);
1859   return node->attr.confirm_cmp;
1860 }
1861 void     set_Confirm_cmp   (ir_node *node, pn_Cmp cmp) {
1862   assert (node->op == op_Confirm);
1863   node->attr.confirm_cmp = cmp;
1864 }
1865
1866
1867 ir_node *
1868 get_Filter_pred (ir_node *node) {
1869   assert(node->op == op_Filter);
1870   return node->in[1];
1871 }
1872 void
1873 set_Filter_pred (ir_node *node, ir_node *pred) {
1874   assert(node->op == op_Filter);
1875   node->in[1] = pred;
1876 }
1877 long
1878 get_Filter_proj(ir_node *node) {
1879   assert(node->op == op_Filter);
1880   return node->attr.filter.proj;
1881 }
1882 void
1883 set_Filter_proj (ir_node *node, long proj) {
1884   assert(node->op == op_Filter);
1885   node->attr.filter.proj = proj;
1886 }
1887
1888 /* Don't use get_irn_arity, get_irn_n in implementation as access
1889    shall work independent of view!!! */
1890 void set_Filter_cg_pred_arr(ir_node * node, int arity, ir_node ** in) {
1891   assert(node->op == op_Filter);
1892   if (node->attr.filter.in_cg == NULL || arity != ARR_LEN(node->attr.filter.in_cg) - 1) {
1893     node->attr.filter.in_cg = NEW_ARR_D(ir_node *, current_ir_graph->obst, arity + 1);
1894     node->attr.filter.backedge = NEW_ARR_D (int, current_ir_graph->obst, arity);
1895     memset(node->attr.filter.backedge, 0, sizeof(int) * arity);
1896     node->attr.filter.in_cg[0] = node->in[0];
1897   }
1898   memcpy(node->attr.filter.in_cg + 1, in, sizeof(ir_node *) * arity);
1899 }
1900
1901 void set_Filter_cg_pred(ir_node * node, int pos, ir_node * pred) {
1902   assert(node->op == op_Filter && node->attr.filter.in_cg &&
1903      0 <= pos && pos < ARR_LEN(node->attr.filter.in_cg) - 1);
1904   node->attr.filter.in_cg[pos + 1] = pred;
1905 }
1906 int get_Filter_n_cg_preds(ir_node *node) {
1907   assert(node->op == op_Filter && node->attr.filter.in_cg);
1908   return (ARR_LEN(node->attr.filter.in_cg) - 1);
1909 }
1910 ir_node *get_Filter_cg_pred(ir_node *node, int pos) {
1911   int arity;
1912   assert(node->op == op_Filter && node->attr.filter.in_cg &&
1913      0 <= pos);
1914   arity = ARR_LEN(node->attr.filter.in_cg);
1915   assert(pos <  arity - 1);
1916   return node->attr.filter.in_cg[pos + 1];
1917 }
1918
1919 /* Mux support */
1920 ir_node *get_Mux_sel   (ir_node *node) {
1921   assert(node->op == op_Mux);
1922   return node->in[1];
1923 }
1924 void     set_Mux_sel   (ir_node *node, ir_node *sel) {
1925   assert(node->op == op_Mux);
1926   node->in[1] = sel;
1927 }
1928
1929 ir_node *get_Mux_false (ir_node *node) {
1930   assert(node->op == op_Mux);
1931   return node->in[2];
1932 }
1933 void     set_Mux_false (ir_node *node, ir_node *ir_false) {
1934   assert(node->op == op_Mux);
1935   node->in[2] = ir_false;
1936 }
1937
1938 ir_node *get_Mux_true  (ir_node *node) {
1939   assert(node->op == op_Mux);
1940   return node->in[3];
1941 }
1942 void     set_Mux_true  (ir_node *node, ir_node *ir_true) {
1943   assert(node->op == op_Mux);
1944   node->in[3] = ir_true;
1945 }
1946
1947
1948 ir_graph *
1949 get_irn_irg(const ir_node *node) {
1950   if (! is_Block(node))
1951     node = get_nodes_block(node);
1952   if (is_Bad(node))  /* sometimes bad is predecessor of nodes instead of block: in case of optimization */
1953     node = get_nodes_block(node);
1954   assert(get_irn_op(node) == op_Block);
1955   return node->attr.block.irg;
1956 }
1957
1958
1959 /*----------------------------------------------------------------*/
1960 /*  Auxiliary routines                                            */
1961 /*----------------------------------------------------------------*/
1962
1963 ir_node *
1964 skip_Proj (ir_node *node) {
1965   /* don't assert node !!! */
1966   if (node && is_Proj(node)) {
1967     return get_Proj_pred(node);
1968   } else {
1969     return node;
1970   }
1971 }
1972
1973 ir_node *
1974 skip_Tuple (ir_node *node) {
1975   ir_node *pred;
1976
1977   if (!get_opt_normalize()) return node;
1978
1979   node = skip_Id(node);
1980   if (get_irn_op(node) == op_Proj) {
1981     pred = skip_Id(get_Proj_pred(node));
1982     if (get_irn_op(pred) == op_Proj) /* nested Tuple ? */
1983       pred = skip_Id(skip_Tuple(pred));
1984     if (get_irn_op(pred) == op_Tuple)
1985       return get_Tuple_pred(pred, get_Proj_proj(node));
1986   }
1987   return node;
1988 }
1989
1990 /** returns operand of node if node is a Cast */
1991 ir_node *skip_Cast  (ir_node *node) {
1992   if (node && get_irn_op(node) == op_Cast) {
1993     return skip_Id(get_irn_n(node, 0));
1994   } else {
1995     return node;
1996   }
1997 }
1998
1999 #if 0
2000 /* This should compact Id-cycles to self-cycles. It has the same (or less?) complexity
2001    than any other approach, as Id chains are resolved and all point to the real node, or
2002    all id's are self loops. */
2003 ir_node *
2004 skip_Id (ir_node *node) {
2005   /* don't assert node !!! */
2006
2007   if (!get_opt_normalize()) return node;
2008
2009   /* Don't use get_Id_pred:  We get into an endless loop for
2010      self-referencing Ids. */
2011   if (node && (node->op == op_Id) && (node != node->in[0+1])) {
2012     ir_node *rem_pred = node->in[0+1];
2013     ir_node *res;
2014
2015     assert (get_irn_arity (node) > 0);
2016
2017     node->in[0+1] = node;
2018     res = skip_Id(rem_pred);
2019     if (res->op == op_Id) /* self-loop */ return node;
2020
2021     node->in[0+1] = res;
2022     return res;
2023   } else {
2024     return node;
2025   }
2026 }
2027 #else
2028 /* This should compact Id-cycles to self-cycles. It has the same (or less?) complexity
2029    than any other approach, as Id chains are resolved and all point to the real node, or
2030    all id's are self loops. */
2031 ir_node *
2032 skip_Id (ir_node *node) {
2033   ir_node *pred;
2034   /* don't assert node !!! */
2035
2036   if (!node || (node->op != op_Id)) return node;
2037
2038   if (!get_opt_normalize()) return node;
2039
2040   /* Don't use get_Id_pred:  We get into an endless loop for
2041      self-referencing Ids. */
2042   pred = node->in[0+1];
2043
2044   if (pred->op != op_Id) return pred;
2045
2046   if (node != pred) {  /* not a self referencing Id. Resolve Id chain. */
2047     ir_node *rem_pred, *res;
2048
2049     if (pred->op != op_Id) return pred; /* shortcut */
2050     rem_pred = pred;
2051
2052     assert (get_irn_arity (node) > 0);
2053
2054     node->in[0+1] = node;   /* turn us into a self referencing Id:  shorten Id cycles. */
2055     res = skip_Id(rem_pred);
2056     if (res->op == op_Id) /* self-loop */ return node;
2057
2058     node->in[0+1] = res;    /* Turn Id chain into Ids all referencing the chain end. */
2059     return res;
2060   } else {
2061     return node;
2062   }
2063 }
2064 #endif
2065
2066 int
2067 (is_Bad)(const ir_node *node) {
2068   return _is_Bad(node);
2069 }
2070
2071 int
2072 (is_no_Block)(const ir_node *node) {
2073   return _is_no_Block(node);
2074 }
2075
2076 int
2077 (is_Block)(const ir_node *node) {
2078   return _is_Block(node);
2079 }
2080
2081 /* returns true if node is a Unknown node. */
2082 int
2083 is_Unknown (const ir_node *node) {
2084   assert(node);
2085   return (get_irn_op(node) == op_Unknown);
2086 }
2087
2088 int
2089 is_Proj (const ir_node *node) {
2090   assert(node);
2091   return node->op == op_Proj
2092     || (!get_interprocedural_view() && node->op == op_Filter);
2093 }
2094
2095 /* Returns true if the operation manipulates control flow. */
2096 int
2097 is_cfop(const ir_node *node) {
2098   return is_cfopcode(get_irn_op(node));
2099 }
2100
2101 /* Returns true if the operation manipulates interprocedural control flow:
2102    CallBegin, EndReg, EndExcept */
2103 int is_ip_cfop(const ir_node *node) {
2104   return is_ip_cfopcode(get_irn_op(node));
2105 }
2106
2107 /* Returns true if the operation can change the control flow because
2108    of an exception. */
2109 int
2110 is_fragile_op(const ir_node *node) {
2111   return is_op_fragile(get_irn_op(node));
2112 }
2113
2114 /* Returns the memory operand of fragile operations. */
2115 ir_node *get_fragile_op_mem(ir_node *node) {
2116   assert(node && is_fragile_op(node));
2117
2118   switch (get_irn_opcode (node)) {
2119   case iro_Call  :
2120   case iro_Quot  :
2121   case iro_DivMod:
2122   case iro_Div   :
2123   case iro_Mod   :
2124   case iro_Load  :
2125   case iro_Store :
2126   case iro_Alloc :
2127     return get_irn_n(node, 0);
2128   case iro_Bad   :
2129   case iro_Unknown:
2130     return node;
2131   default: ;
2132     assert(0 && "should not be reached");
2133     return NULL;
2134   }
2135 }
2136
2137 /* Returns true if the operation is a forking control flow operation. */
2138 int
2139 is_forking_op(const ir_node *node) {
2140   return is_op_forking(get_irn_op(node));
2141 }
2142
2143 type *(get_irn_type)(ir_node *node) {
2144   return _get_irn_type(node);
2145 }
2146
2147 /** the get_type operation must be always implemented */
2148 static type *get_Null_type(ir_node *n) {
2149   return NULL;
2150 }
2151
2152 /* set the get_type operation */
2153 ir_op *firm_set_default_get_type(ir_op *op)
2154 {
2155   switch (op->code) {
2156   case iro_Const:    op->get_type = get_Const_type; break;
2157   case iro_SymConst: op->get_type = get_SymConst_value_type; break;
2158   case iro_Cast:     op->get_type = get_Cast_type; break;
2159   case iro_Proj:     op->get_type = get_Proj_type; break;
2160   default:           op->get_type = get_Null_type; break;
2161   }
2162   return op;
2163 }
2164
2165 #ifdef DEBUG_libfirm
2166 void dump_irn (ir_node *n) {
2167   int i, arity = get_irn_arity(n);
2168   printf("%s%s: %ld (%p)\n", get_irn_opname(n), get_mode_name(get_irn_mode(n)), get_irn_node_nr(n), (void *)n);
2169   if (!is_Block(n)) {
2170     ir_node *pred = get_irn_n(n, -1);
2171     printf("  block: %s%s: %ld (%p)\n", get_irn_opname(pred), get_mode_name(get_irn_mode(pred)),
2172        get_irn_node_nr(pred), (void *)pred);
2173   }
2174   printf("  preds: \n");
2175   for (i = 0; i < arity; ++i) {
2176     ir_node *pred = get_irn_n(n, i);
2177     printf("    %d: %s%s: %ld (%p)\n", i, get_irn_opname(pred), get_mode_name(get_irn_mode(pred)),
2178        get_irn_node_nr(pred), (void *)pred);
2179   }
2180 }
2181
2182 #else  /* DEBUG_libfirm */
2183 void dump_irn (ir_node *n) {}
2184 #endif /* DEBUG_libfirm */