fb9901d1776986c48fea90271b049294bfb6cee6
[libfirm] / ir / ir / ircons.c
1 /* Copyright (C) 1998 - 2000 by Universitaet Karlsruhe
2 ** All rights reserved.
3 **
4 ** Authors: Martin Trapp, Christian Schaefer
5 **
6 ** ircons.c: basic and more detailed irnode constructors
7 **           store, block and parameter administration.
8 ** Adapted to extended FIRM nodes (exceptions...) and commented
9 **   by Goetz Lindenmaier
10 */
11
12 #ifdef HAVE_CONFIG_H
13 # include <config.h>
14 #endif
15
16 # include "irgraph_t.h"
17 # include "irnode_t.h"
18 # include "irmode_t.h"
19 # include "ircons.h"
20 # include "common.h"
21 # include "irvrfy.h"
22 # include "irop.h"
23 # include "iropt.h"
24 # include "irgmod.h"
25 # include "array.h"
26 /* memset belongs to string.h */
27 # include "string.h"
28
29 #if USE_EXPICIT_PHI_IN_STACK
30 /* A stack needed for the automatic Phi node construction in constructor
31    Phi_in. Redefinition in irgraph.c!! */
32 struct Phi_in_stack {
33   ir_node **stack;
34   int       pos;
35 };
36 typedef struct Phi_in_stack Phi_in_stack;
37 #endif
38
39 /*** ******************************************** */
40 /** privat interfaces, for professional use only */
41
42 /* Constructs a Block with a fixed number of predecessors.
43    Does not set current_block.  Can not be used with automatic
44    Phi node construction. */
45 inline ir_node *
46 new_r_Block (ir_graph *irg,  int arity, ir_node **in)
47 {
48   ir_node *res;
49
50   res = new_ir_node (irg, NULL, op_Block, mode_R, arity, in);
51   set_Block_matured(res, 1);
52   set_Block_block_visited(res, 0);
53
54   irn_vrfy (res);
55   return res;
56 }
57
58 ir_node *
59 new_r_Start (ir_graph *irg, ir_node *block)
60 {
61   ir_node *res;
62
63   res = new_ir_node (irg, block, op_Start, mode_T, 0, NULL);
64
65   irn_vrfy (res);
66   return res;
67 }
68
69 ir_node *
70 new_r_End (ir_graph *irg, ir_node *block)
71 {
72   ir_node *res;
73
74   res = new_ir_node (irg, block, op_End, mode_X, -1, NULL);
75
76   irn_vrfy (res);
77   return res;
78 }
79
80 /* Creates a Phi node with all predecessors.  Calling this constructor
81    is only allowed if the corresponding block is mature.  */
82 ir_node *
83 new_r_Phi (ir_graph *irg, ir_node *block, int arity, ir_node **in, ir_mode *mode)
84 {
85   ir_node *res;
86
87   assert( get_Block_matured(block) );
88   assert( get_irn_arity(block) == arity );
89
90   res = new_ir_node (irg, block, op_Phi, mode, arity, in);
91
92   res = optimize (res);
93   irn_vrfy (res);
94   return res;
95 }
96
97 ir_node *
98 new_r_Const (ir_graph *irg, ir_node *block, ir_mode *mode, tarval *con)
99 {
100   ir_node *res;
101   res = new_ir_node (irg, block, op_Const, mode, 0, NULL);
102   res->attr.con = con;
103   res = optimize (res);
104   irn_vrfy (res);
105
106 #if 0
107   res = local_optimize_newby (res);
108 # endif
109
110   return res;
111 }
112
113 ir_node *
114 new_r_Id (ir_graph *irg, ir_node *block, ir_node *val, ir_mode *mode)
115 {
116   ir_node *in[1] = {val};
117   ir_node *res;
118   res = new_ir_node (irg, block, op_Id, mode, 1, in);
119   res = optimize (res);
120   irn_vrfy (res);
121   return res;
122 }
123
124 ir_node *
125 new_r_Proj (ir_graph *irg, ir_node *block, ir_node *arg, ir_mode *mode,
126             long proj)
127 {
128   ir_node *in[1] = {arg};
129   ir_node *res;
130   res = new_ir_node (irg, block, op_Proj, mode, 1, in);
131   res->attr.proj = proj;
132
133   assert(res);
134   assert(get_Proj_pred(res));
135   assert(get_nodes_Block(get_Proj_pred(res)));
136
137   res = optimize (res);
138
139   irn_vrfy (res);
140   return res;
141
142 }
143
144 ir_node *
145 new_r_Conv (ir_graph *irg, ir_node *block, ir_node *op, ir_mode *mode)
146 {
147   ir_node *in[1] = {op};
148   ir_node *res;
149   res = new_ir_node (irg, block, op_Conv, mode, 1, in);
150   res = optimize (res);
151   irn_vrfy (res);
152   return res;
153
154 }
155
156 ir_node *
157 new_r_Tuple (ir_graph *irg, ir_node *block, int arity, ir_node **in)
158 {
159   ir_node *res;
160
161   res = new_ir_node (irg, block, op_Tuple, mode_T, arity, in);
162   res = optimize (res);
163   irn_vrfy (res);
164   return res;
165 }
166
167 inline ir_node *
168 new_r_Add (ir_graph *irg, ir_node *block,
169            ir_node *op1, ir_node *op2, ir_mode *mode)
170 {
171   ir_node *in[2] = {op1, op2};
172   ir_node *res;
173   res = new_ir_node (irg, block, op_Add, mode, 2, in);
174   res = optimize (res);
175   irn_vrfy (res);
176   return res;
177 }
178
179 inline ir_node *
180 new_r_Sub (ir_graph *irg, ir_node *block,
181            ir_node *op1, ir_node *op2, ir_mode *mode)
182 {
183   ir_node *in[2] = {op1, op2};
184   ir_node *res;
185   res = new_ir_node (irg, block, op_Sub, mode, 2, in);
186   res = optimize (res);
187   irn_vrfy (res);
188   return res;
189 }
190
191 inline ir_node *
192 new_r_Minus (ir_graph *irg, ir_node *block,
193              ir_node *op,  ir_mode *mode)
194 {
195   ir_node *in[1] = {op};
196   ir_node *res;
197   res = new_ir_node (irg, block, op_Minus, mode, 1, in);
198   res = optimize (res);
199   irn_vrfy (res);
200   return res;
201 }
202
203 inline ir_node *
204 new_r_Mul (ir_graph *irg, ir_node *block,
205            ir_node *op1, ir_node *op2, ir_mode *mode)
206 {
207   ir_node *in[2] = {op1, op2};
208   ir_node *res;
209   res = new_ir_node (irg, block, op_Mul, mode, 2, in);
210   res = optimize (res);
211   irn_vrfy (res);
212   return res;
213 }
214
215 inline ir_node *
216 new_r_Quot (ir_graph *irg, ir_node *block,
217             ir_node *memop, ir_node *op1, ir_node *op2)
218 {
219   ir_node *in[3] = {memop, op1, op2};
220   ir_node *res;
221   res = new_ir_node (irg, block, op_Quot, mode_T, 3, in);
222   res = optimize (res);
223   irn_vrfy (res);
224   return res;
225 }
226
227 inline ir_node *
228 new_r_DivMod (ir_graph *irg, ir_node *block,
229               ir_node *memop, ir_node *op1, ir_node *op2)
230 {
231   ir_node *in[3] = {memop, op1, op2};
232   ir_node *res;
233   res = new_ir_node (irg, block, op_DivMod, mode_T, 3, in);
234   res = optimize (res);
235   irn_vrfy (res);
236   return res;
237 }
238
239 inline ir_node *
240 new_r_Div (ir_graph *irg, ir_node *block,
241            ir_node *memop, ir_node *op1, ir_node *op2)
242 {
243   ir_node *in[3] = {memop, op1, op2};
244   ir_node *res;
245   res = new_ir_node (irg, block, op_Div, mode_T, 3, in);
246   res = optimize (res);
247   irn_vrfy (res);
248   return res;
249 }
250
251 inline ir_node *
252 new_r_Mod (ir_graph *irg, ir_node *block,
253            ir_node *memop, ir_node *op1, ir_node *op2)
254 {
255   ir_node *in[3] = {memop, op1, op2};
256   ir_node *res;
257   res = new_ir_node (irg, block, op_Mod, mode_T, 3, in);
258   res = optimize (res);
259   irn_vrfy (res);
260   return res;
261 }
262
263 inline ir_node *
264 new_r_And (ir_graph *irg, ir_node *block,
265            ir_node *op1, ir_node *op2, ir_mode *mode)
266 {
267   ir_node *in[2] = {op1, op2};
268   ir_node *res;
269   res = new_ir_node (irg, block, op_And, mode, 2, in);
270   res = optimize (res);
271   irn_vrfy (res);
272   return res;
273 }
274
275 inline ir_node *
276 new_r_Or (ir_graph *irg, ir_node *block,
277           ir_node *op1, ir_node *op2, ir_mode *mode)
278 {
279   ir_node *in[2] = {op1, op2};
280   ir_node *res;
281   res = new_ir_node (irg, block, op_Or, mode, 2, in);
282   res = optimize (res);
283   irn_vrfy (res);
284   return res;
285 }
286
287 inline ir_node *
288 new_r_Eor (ir_graph *irg, ir_node *block,
289           ir_node *op1, ir_node *op2, ir_mode *mode)
290 {
291   ir_node *in[2] = {op1, op2};
292   ir_node *res;
293   res = new_ir_node (irg, block, op_Eor, mode, 2, in);
294   res = optimize (res);
295   irn_vrfy (res);
296   return res;
297 }
298
299 inline ir_node *
300 new_r_Not    (ir_graph *irg, ir_node *block,
301               ir_node *op, ir_mode *mode)
302 {
303   ir_node *in[1] = {op};
304   ir_node *res;
305   res = new_ir_node (irg, block, op_Not, mode, 1, in);
306   res = optimize (res);
307   irn_vrfy (res);
308   return res;
309 }
310
311 inline ir_node *
312 new_r_Shl (ir_graph *irg, ir_node *block,
313           ir_node *op, ir_node *k, ir_mode *mode)
314 {
315   ir_node *in[2] = {op, k};
316   ir_node *res;
317   res = new_ir_node (irg, block, op_Shl, mode, 2, in);
318   res = optimize (res);
319   irn_vrfy (res);
320   return res;
321 }
322
323 inline ir_node *
324 new_r_Shr (ir_graph *irg, ir_node *block,
325            ir_node *op, ir_node *k, ir_mode *mode)
326 {
327   ir_node *in[2] = {op, k};
328   ir_node *res;
329   res = new_ir_node (irg, block, op_Shr, mode, 2, in);
330   res = optimize (res);
331   irn_vrfy (res);
332   return res;
333 }
334
335 inline ir_node *
336 new_r_Shrs (ir_graph *irg, ir_node *block,
337            ir_node *op, ir_node *k, ir_mode *mode)
338 {
339   ir_node *in[2] = {op, k};
340   ir_node *res;
341   res = new_ir_node (irg, block, op_Shrs, mode, 2, in);
342   res = optimize (res);
343   irn_vrfy (res);
344   return res;
345 }
346
347 inline ir_node *
348 new_r_Rot (ir_graph *irg, ir_node *block,
349            ir_node *op, ir_node *k, ir_mode *mode)
350 {
351   ir_node *in[2] = {op, k};
352   ir_node *res;
353   res = new_ir_node (irg, block, op_Rot, mode, 2, in);
354   res = optimize (res);
355   irn_vrfy (res);
356   return res;
357 }
358
359 inline ir_node *
360 new_r_Abs (ir_graph *irg, ir_node *block,
361            ir_node *op, ir_mode *mode)
362 {
363   ir_node *in[1] = {op};
364   ir_node *res;
365   res = new_ir_node (irg, block, op_Abs, mode, 1, in);
366   res = optimize (res);
367   irn_vrfy (res);
368   return res;
369 }
370
371 inline ir_node *
372 new_r_Cmp (ir_graph *irg, ir_node *block,
373            ir_node *op1, ir_node *op2)
374 {
375   ir_node *in[2] = {op1, op2};
376   ir_node *res;
377   res = new_ir_node (irg, block, op_Cmp, mode_T, 2, in);
378   res = optimize (res);
379   irn_vrfy (res);
380   return res;
381 }
382
383 inline ir_node *
384 new_r_Jmp (ir_graph *irg, ir_node *block)
385 {
386   ir_node *in[0] = {};
387   ir_node *res;
388   res = new_ir_node (irg, block, op_Jmp, mode_X, 0, in);
389   res = optimize (res);
390   irn_vrfy (res);
391   return res;
392 }
393
394 inline ir_node *
395 new_r_Cond (ir_graph *irg, ir_node *block, ir_node *c)
396 {
397   ir_node *in[1] = {c};
398   ir_node *res;
399   res = new_ir_node (irg, block, op_Cond, mode_T, 1, in);
400   res = optimize (res);
401   irn_vrfy (res);
402   return res;
403 }
404
405 ir_node *
406 new_r_Call (ir_graph *irg, ir_node *block, ir_node *store,
407             ir_node *callee, int arity, ir_node **in, type *type)
408 {
409   ir_node **r_in;
410   ir_node *res;
411   int r_arity;
412
413   r_arity = arity+2;
414   NEW_ARR_A (ir_node *, r_in, r_arity);
415   r_in[0] = store;
416   r_in[1] = callee;
417   memcpy (&r_in[2], in, sizeof (ir_node *) * arity);
418
419   res = new_ir_node (irg, block, op_Call, mode_T, r_arity, r_in);
420
421   assert(is_method_type(type));
422   set_Call_type(res, type);
423   res = optimize (res);
424   irn_vrfy (res);
425   return res;
426 }
427
428 ir_node *
429 new_r_Return (ir_graph *irg, ir_node *block,
430               ir_node *store, int arity, ir_node **in)
431 {
432   ir_node **r_in;
433   ir_node *res;
434   int r_arity;
435
436   r_arity = arity+1;
437   NEW_ARR_A (ir_node *, r_in, r_arity);
438   r_in[0] = store;
439   memcpy (&r_in[1], in, sizeof (ir_node *) * arity);
440   res = new_ir_node (irg, block, op_Return, mode_X, r_arity, r_in);
441   res = optimize (res);
442   irn_vrfy (res);
443   return res;
444 }
445
446 inline ir_node *
447 new_r_Raise (ir_graph *irg, ir_node *block, ir_node *store, ir_node *obj)
448 {
449   ir_node *in[2] = {store, obj};
450   ir_node *res;
451   res = new_ir_node (irg, block, op_Raise, mode_X, 2, in);
452
453   res = optimize (res);
454   irn_vrfy (res);
455   return res;
456 }
457
458 inline ir_node *
459 new_r_Load (ir_graph *irg, ir_node *block,
460             ir_node *store, ir_node *adr)
461 {
462   ir_node *in[2] = {store, adr};
463   ir_node *res;
464   res = new_ir_node (irg, block, op_Load, mode_T, 2, in);
465
466   res = optimize (res);
467   irn_vrfy (res);
468   return res;
469 }
470
471 inline ir_node *
472 new_r_Store (ir_graph *irg, ir_node *block,
473              ir_node *store, ir_node *adr, ir_node *val)
474 {
475   ir_node *in[3] = {store, adr, val};
476   ir_node *res;
477   res = new_ir_node (irg, block, op_Store, mode_T, 3, in);
478
479   res = optimize (res);
480   irn_vrfy (res);
481   return res;
482 }
483
484 inline ir_node *
485 new_r_Alloc (ir_graph *irg, ir_node *block, ir_node *store,
486             ir_node *size, type *alloc_type, where_alloc where)
487 {
488   ir_node *in[2] = {store, size};
489   ir_node *res;
490   res = new_ir_node (irg, block, op_Alloc, mode_T, 2, in);
491
492   res->attr.a.where = where;
493   res->attr.a.type = alloc_type;
494
495   res = optimize (res);
496   irn_vrfy (res);
497   return res;
498 }
499
500 inline ir_node *
501 new_r_Free (ir_graph *irg, ir_node *block, ir_node *store,
502             ir_node *ptr, ir_node *size, type *free_type)
503 {
504   ir_node *in[3] = {store, ptr, size};
505   ir_node *res;
506   res = new_ir_node (irg, block, op_Free, mode_T, 3, in);
507
508   res->attr.f = free_type;
509
510   res = optimize (res);
511   irn_vrfy (res);
512   return res;
513 }
514
515 inline ir_node *
516 new_r_Sel (ir_graph *irg, ir_node *block, ir_node *store, ir_node *objptr,
517            int arity, ir_node **in, entity *ent)
518 {
519   ir_node **r_in;
520   ir_node *res;
521   int r_arity;
522
523   r_arity = arity + 2;
524   NEW_ARR_A (ir_node *, r_in, r_arity);
525   r_in[0] = store;
526   r_in[1] = objptr;
527   memcpy (&r_in[2], in, sizeof (ir_node *) * arity);
528   res = new_ir_node (irg, block, op_Sel, mode_p, r_arity, r_in);
529
530   res->attr.s.ltyp = static_linkage;
531   res->attr.s.ent = ent;
532
533   res = optimize (res);
534   irn_vrfy (res);
535   return res;
536 }
537
538 inline ir_node *
539 new_r_SymConst (ir_graph *irg, ir_node *block, type_or_id_p value,
540                 symconst_kind symkind)
541 {
542   ir_node *in[0] = {};
543   ir_node *res;
544   ir_mode *mode;
545   if (symkind == linkage_ptr_info)
546     mode = mode_p;
547   else
548     mode = mode_I;
549   res = new_ir_node (irg, block, op_SymConst, mode, 0, in);
550
551   res->attr.i.num = symkind;
552   if (symkind == linkage_ptr_info) {
553     res->attr.i.tori.ptrinfo = (ident *)value;
554   } else {
555     assert (   (   (symkind == type_tag)
556                 || (symkind == size))
557             && (is_type(value)));
558     res->attr.i.tori.typ = (type *)value;
559   }
560   res = optimize (res);
561   irn_vrfy (res);
562   return res;
563 }
564
565 ir_node *
566 new_r_Sync (ir_graph *irg, ir_node *block, int arity, ir_node **in)
567 {
568   ir_node *res;
569
570   res = new_ir_node (irg, block, op_Sync, mode_M, arity, in);
571
572   res = optimize (res);
573   irn_vrfy (res);
574   return res;
575 }
576
577 ir_node *
578 new_r_Bad ()
579 {
580   return current_ir_graph->bad;
581 }
582
583 /** ********************/
584 /** public interfaces  */
585 /** construction tools */
586
587 /****f* ircons/new_Start
588  *
589  * NAME
590  *   new_Start -- create a new Start node in the current block
591  *
592  * SYNOPSIS
593  *   s = new_Start(void);
594  *   ir_node* new_Start(void);
595  *
596  * RESULT
597  *   s - pointer to the created Start node
598  *
599  ****
600  */
601 ir_node *
602 new_Start (void)
603 {
604   ir_node *res;
605
606   res = new_ir_node (current_ir_graph, current_ir_graph->current_block,
607                      op_Start, mode_T, 0, NULL);
608
609   res = optimize (res);
610   irn_vrfy (res);
611   return res;
612 }
613
614 ir_node *
615 new_End (void)
616 {
617   ir_node *res;
618
619   res = new_ir_node (current_ir_graph,  current_ir_graph->current_block,
620                      op_End, mode_X, -1, NULL);
621
622   res = optimize (res);
623   irn_vrfy (res);
624
625   return res;
626 }
627
628 /* Constructs a Block with a fixed number of predecessors.
629    Does set current_block.  Can be used with automatic Phi
630    node construction. */
631 ir_node *
632 new_Block (int arity, ir_node **in)
633 {
634   ir_node *res;
635
636   res = new_r_Block (current_ir_graph, arity, in);
637   current_ir_graph->current_block = res;
638
639   /* Create and initialize array for Phi-node construction. */
640   res->attr.block.graph_arr = NEW_ARR_D (ir_node *, current_ir_graph->obst,
641                                          current_ir_graph->n_loc);
642   memset(res->attr.block.graph_arr, 0, sizeof(ir_node *)*current_ir_graph->n_loc);
643
644   res = optimize (res);
645   irn_vrfy (res);
646
647   return res;
648 }
649
650 /* ***********************************************************************/
651 /* Methods necessary for automatic Phi node creation                     */
652 /*
653   ir_node *phi_merge            (ir_node *block, int pos, ir_mode *mode, ir_node **nin, int ins)
654   ir_node *get_r_value_internal (ir_node *block, int pos, ir_mode *mode);
655   ir_node *new_r_Phi0           (ir_graph *irg, ir_node *block, ir_mode *mode)
656   ir_node *new_r_Phi_in         (ir_graph *irg, ir_node *block, ir_mode *mode,  ir_node **in, int ins)
657
658   Call Graph:   ( A ---> B == A "calls" B)
659
660        get_value         mature_block
661           |                   |
662           |                   |
663           |                   |
664           |          ---> phi_merge
665           |         /       /   \
666           |        /       /     \
667          \|/      /      |/_      \
668        get_r_value_internal        |
669                 |                  |
670                 |                  |
671                \|/                \|/
672             new_r_Phi0          new_r_Phi_in
673
674 * *************************************************************************** */
675
676 /* Creates a Phi node with 0 predecessors */
677 inline ir_node *
678 new_r_Phi0 (ir_graph *irg, ir_node *block, ir_mode *mode)
679 {
680   ir_node *res;
681   res = new_ir_node (irg, block, op_Phi, mode, 0, NULL);
682   irn_vrfy (res);
683   return res;
684 }
685
686 /* There are two implementations of the Phi node construction.  The first
687    is faster, but does not work for blocks with more than 2 predecessors.
688    The second works always but is slower and causes more unnecessary Phi
689    nodes.
690    Select the implementations by the following preprocessor flag set in
691    common/common.h: */
692 #if USE_FAST_PHI_CONSTRUCTION
693
694 /* This is a stack used for allocating and deallocating nodes in
695    new_r_Phi_in.  The original implementation used the obstack
696    to model this stack, now it is explicit.  This reduces side effects.
697 */
698 #if USE_EXPICIT_PHI_IN_STACK
699 Phi_in_stack *
700 new_Phi_in_stack() {
701   Phi_in_stack *res;
702
703   res = (Phi_in_stack *) malloc ( sizeof (Phi_in_stack));
704
705   res->stack = NEW_ARR_F (ir_node *, 1);
706   res->pos = 0;
707
708   return res;
709 }
710
711 void free_to_Phi_in_stack(ir_node *phi) {
712   assert(get_irn_opcode(phi) == iro_Phi);
713
714   if (ARR_LEN(current_ir_graph->Phi_in_stack->stack) ==
715       current_ir_graph->Phi_in_stack->pos)
716     ARR_APP1 (ir_node *, current_ir_graph->Phi_in_stack->stack, phi);
717   else
718     current_ir_graph->Phi_in_stack->stack[current_ir_graph->Phi_in_stack->pos] = phi;
719
720   (current_ir_graph->Phi_in_stack->pos)++;
721 }
722
723 ir_node *
724 alloc_or_pop_from_Phi_in_stack(ir_graph *irg, ir_node *block, ir_mode *mode,
725              int arity, ir_node **in) {
726   ir_node *res;
727   ir_node **stack = current_ir_graph->Phi_in_stack->stack;
728   int pos = current_ir_graph->Phi_in_stack->pos;
729
730
731   if (pos == 0) {
732     /* We need to allocate a new node */
733     res = new_ir_node (irg, block, op_Phi, mode, arity, in);
734   } else {
735     /* reuse the old node and initialize it again. */
736     res = stack[pos-1];
737
738     assert (res->kind == k_ir_node);
739     assert (res->op == op_Phi);
740     res->mode = mode;
741     res->visited = 0;
742     res->link = NULL;
743     assert (arity >= 0);
744     /* ???!!! How to free the old in array??  */
745     res->in = NEW_ARR_D (ir_node *, irg->obst, (arity+1));
746     res->in[0] = block;
747     memcpy (&res->in[1], in, sizeof (ir_node *) * arity);
748
749     (current_ir_graph->Phi_in_stack->pos)--;
750   }
751   return res;
752 }
753 #endif /* USE_EXPICIT_PHI_IN_STACK */
754
755 /* Creates a Phi node with a given, fixed array **in of predecessors.
756    If the Phi node is unnecessary, as the same value reaches the block
757    through all control flow paths, it is eliminated and the value
758    returned directly.  This constructor is only intended for use in
759    the automatic Phi node generation triggered by get_value or mature.
760    The implementation is quite tricky and depends on the fact, that
761    the nodes are allocated on a stack:
762    The in array contains predecessors and NULLs.  The NULLs appear,
763    if get_r_value_internal, that computed the predecessors, reached
764    the same block on two paths.  In this case the same value reaches
765    this block on both paths, there is no definition in between.  We need
766    not allocate a Phi where these path's merge, but we have to communicate
767    this fact to the caller.  This happens by returning a pointer to the
768    node the caller _will_ allocate.  (Yes, we predict the address. We can
769    do so because the nodes are allocated on the obstack.)  The caller then
770    finds a pointer to itself and, when this routine is called again,
771    eliminates itself.
772    */
773 inline ir_node *
774 new_r_Phi_in (ir_graph *irg, ir_node *block, ir_mode *mode,
775               ir_node **in, int ins)
776 {
777   int i;
778   ir_node *res, *known;
779
780   /* allocate a new node on the obstack.
781      This can return a node to which some of the pointers in the in-array
782      already point.
783      Attention: the constructor copies the in array, i.e., the later changes
784      to the array in this routine do not affect the constructed node!  If
785      the in array contains NULLs, there will be missing predecessors in the
786      returned node.
787      Is this a possible internal state of the Phi node generation? */
788 #if USE_EXPICIT_PHI_IN_STACK
789   res = known = alloc_or_pop_from_Phi_in_stack(irg, block, mode, ins, in);
790 #else
791   res = known = new_ir_node (irg, block, op_Phi, mode, ins, in);
792 #endif
793   /* The in-array can contain NULLs.  These were returned by
794      get_r_value_internal if it reached the same block/definition on a
795      second path.
796      The NULLs are replaced by the node itself to simplify the test in the
797      next loop. */
798   for (i=0;  i < ins;  ++i)
799     if (in[i] == NULL) in[i] = res;
800
801   /* This loop checks whether the Phi has more than one predecessor.
802      If so, it is a real Phi node and we break the loop.  Else the
803      Phi node merges the same definition on several paths and therefore
804      is not needed. */
805   for (i=0;  i < ins;  ++i)
806   {
807     if (in[i]==res || in[i]==known) continue;
808
809     if (known==res)
810       known = in[i];
811     else
812       break;
813   }
814
815   /* i==ins: there is at most one predecessor, we don't need a phi node. */
816   if (i==ins) {
817 #if USE_EXPICIT_PHI_IN_STACK
818     free_to_Phi_in_stack(res);
819 #else
820     obstack_free (current_ir_graph->obst, res);
821 #endif
822     res = known;
823   } else {
824     res = optimize (res);
825     irn_vrfy (res);
826   }
827
828   /* return the pointer to the Phi node.  This node might be deallocated! */
829   return res;
830 }
831
832 inline ir_node *
833 get_r_value_internal (ir_node *block, int pos, ir_mode *mode);
834
835 /** This function computes the predecessors for a real Phi node, and then
836     allocates and returns this node.  The routine called to allocate the
837     node might optimize it away and return a real value, or even a pointer
838     to a deallocated Phi node on top of the obstack!
839     This function is called with an in-array of proper size. **/
840 static inline ir_node *
841 phi_merge (ir_node *block, int pos, ir_mode *mode, ir_node **nin, int ins)
842 {
843   ir_node *prevBlock, *res;
844   int i;
845
846   /* This loop goes to all predecessor blocks of the block the Phi node is in
847      and there finds the operands of the Phi node by calling
848      get_r_value_internal. */
849   for (i = 1;  i <= ins;  ++i) {
850     assert (block->in[i]);
851     prevBlock = block->in[i]->in[0]; /* go past control flow op to prev block */
852     assert (prevBlock);
853     nin[i-1] = get_r_value_internal (prevBlock, pos, mode);
854   }
855
856   /* After collecting all predecessors into the array nin a new Phi node
857      with these predecessors is created.  This constructor contains an
858      optimization: If all predecessors of the Phi node are identical it
859      returns the only operand instead of a new Phi node.  If the value
860      passes two different control flow edges without being defined, and
861      this is the second path treated, a pointer to the node that will be
862      allocated for the first path (recursion) is returned.  We already
863      know the address of this node, as it is the next node to be allocated
864      and will be placed on top of the obstack. (The obstack is a _stack_!) */
865   res = new_r_Phi_in (current_ir_graph, block, mode, nin, ins);
866
867   /* Now we now the value for "pos" and can enter it in the array with
868      all known local variables.  Attention: this might be a pointer to
869      a node, that later will be allocated!!! See new_r_Phi_in.
870      If this is called in mature, after some set_value in the same block,
871      the proper value must not be overwritten:
872      The call order
873        get_value    (makes Phi0, put's it into graph_arr)
874        set_value    (overwrites Phi0 in graph_arr)
875        mature_block (upgrades Phi0, puts it again into graph_arr, overwriting
876                      the proper value.)
877      fails. */
878   if (!block->attr.block.graph_arr[pos]) {
879     block->attr.block.graph_arr[pos] = res;
880   } else {
881     /*  printf(" value already computed by %s\n",
882         id_to_str(block->attr.block.graph_arr[pos]->op->name));  */
883   }
884
885   return res;
886 }
887
888 /* This function returns the last definition of a variable.  In case
889    this variable was last defined in a previous block, Phi nodes are
890    inserted.  If the part of the firm graph containing the definition
891    is not yet constructed, a dummy Phi node is returned. */
892 inline ir_node *
893 get_r_value_internal (ir_node *block, int pos, ir_mode *mode)
894 {
895   ir_node *res;
896   /* There are 4 cases to treat.
897
898      1. The block is not mature and we visit it the first time.  We can not
899         create a proper Phi node, therefore a Phi0, i.e., a Phi without
900         predecessors is returned.  This node is added to the linked list (field
901         "link") of the containing block to be completed when this block is
902         matured. (Comlpletion will add a new Phi and turn the Phi0 into an Id
903         node.)
904
905      2. The value is already known in this block, graph_arr[pos] is set and we
906         visit the block the first time.  We can return the value without
907         creating any new nodes.
908
909      3. The block is mature and we visit it the first time.  A Phi node needs
910         to be created (phi_merge).  If the Phi is not needed, as all it's
911         operands are the same value reaching the block through different
912         paths, it's optimized away and the value itself is returned.
913
914      4. The block is mature, and we visit it the second time.  Now two
915         subcases are possible:
916         * The value was computed completely the last time we were here. This
917           is the case if there is no loop.  We can return the proper value.
918         * The recursion that visited this node and set the flag did not
919           return yet.  We are computing a value in a loop and need to
920           break the recursion without knowing the result yet.
921           @@@ strange case.  Straight forward we would create a Phi before
922           starting the computation of it's predecessors.  In this case we will
923           find a Phi here in any case.  The problem is that this implementation
924           only creates a Phi after computing the predecessors, so that it is
925           hard to compute self references of this Phi.  @@@
926         There is no simple check for the second subcase.  Therefore we check
927         for a second visit and treat all such cases as the second subcase.
928         Anyways, the basic situation is the same:  we reached a block
929         on two paths without finding a definition of the value:  No Phi
930         nodes are needed on both paths.
931         We return this information "Two paths, no Phi needed" by a very tricky
932         implementation that relies on the fact that an obstack is a stack and
933         will return a node with the same address on different allocations.
934         Look also at phi_merge and new_r_phi_in to understand this.
935         @@@ Unfortunately this does not work, see testprogram
936         three_cfpred_example.
937
938   */
939
940   /* case 4 -- already visited. */
941   if (get_irn_visited(block) == get_irg_visited(current_ir_graph)) return NULL;
942
943   /* visited the first time */
944   set_irn_visited(block, get_irg_visited(current_ir_graph));
945
946   /* Get the local valid value */
947   res = block->attr.block.graph_arr[pos];
948
949   /* case 2 -- If the value is actually computed, return it. */
950   if (res) { return res;};
951
952   if (block->attr.block.matured) { /* case 3 */
953
954     /* The Phi has the same amount of ins as the corresponding block. */
955     int ins = get_irn_arity(block);
956     ir_node **nin;
957     NEW_ARR_A (ir_node *, nin, ins);
958
959     /* Phi merge collects the predecessors and then creates a node. */
960     res = phi_merge (block, pos, mode, nin, ins);
961
962   } else {  /* case 1 */
963     /* The block is not mature, we don't know how many in's are needed.  A Phi
964        with zero predecessors is created.  Such a Phi node is called Phi0
965        node.  (There is also an obsolete Phi0 opcode.) The Phi0 is then added
966        to the list of Phi0 nodes in this block to be matured by mature_block
967        later.
968        The Phi0 has to remember the pos of it's internal value.  If the real
969        Phi is computed, pos is used to update the array with the local
970        values. */
971
972     res = new_r_Phi0 (current_ir_graph, block, mode);
973     res->attr.phi0_pos = pos;
974     res->link = block->link;
975     block->link = res;
976   }
977
978   /* If we get here, the frontend missed a use-before-definition error */
979   if (!res) {
980     /* Error Message */
981     printf("Error: no value set.  Use of undefined variable.  Initializing
982             to zero.\n");
983     assert (mode->code >= irm_f && mode->code <= irm_p);
984     res = new_r_Const (current_ir_graph, block, mode,
985                        tarval_mode_null[mode->code]);
986   }
987
988   /* The local valid value is available now. */
989   block->attr.block.graph_arr[pos] = res;
990
991   return res;
992 }
993
994 #else /* if 0 */
995
996 /** This is the simple algorithm.  If first generates a Phi0, then
997     it starts the recursion.  This causes an Id at the entry of
998     every block that has no definition of the value! **/
999
1000 #if USE_EXPICIT_PHI_IN_STACK
1001 /* Just a dummy */
1002 Phi_in_stack * new_Phi_in_stack() {  return NULL; }
1003 #endif
1004
1005 inline ir_node *
1006 new_r_Phi_in (ir_graph *irg, ir_node *block, ir_mode *mode,
1007               ir_node **in, int ins)
1008 {
1009   int i;
1010   ir_node *res, *known;
1011
1012   /* Allocate a new node on the obstack.  The allocation copies the in
1013      array. */
1014   res = new_ir_node (irg, block, op_Phi, mode, ins, in);
1015
1016   /* This loop checks whether the Phi has more than one predecessor.
1017      If so, it is a real Phi node and we break the loop.  Else the
1018      Phi node merges the same definition on several paths and therefore
1019      is not needed. Don't consider Bad nodes! */
1020   known = res;
1021   for (i=0;  i < ins;  ++i)
1022   {
1023     if (in[i]==res || in[i]==known || is_Bad(in[i])) continue;
1024
1025     if (known==res)
1026       known = in[i];
1027     else
1028       break;
1029   }
1030
1031   /* i==ins: there is at most one predecessor, we don't need a phi node. */
1032   if (i==ins) {
1033     if (res != known) {
1034       obstack_free (current_ir_graph->obst, res);
1035       res = known;
1036     } else {
1037       /* A undefined value, e.g., in unreachable code. */
1038       res = new_Bad();
1039     }
1040   } else {
1041     res = optimize (res);
1042     irn_vrfy (res);
1043   }
1044
1045   return res;
1046 }
1047
1048 inline ir_node *
1049 get_r_value_internal (ir_node *block, int pos, ir_mode *mode);
1050
1051 /** This function allocates a dummy Phi node to break recursions,
1052     computes the predecessors for the real phi node, and then
1053     allocates and returns this node.  The routine called to allocate the
1054     node might optimize it away and return a real value.
1055     This function is called with an in-array of proper size. **/
1056 static inline ir_node *
1057 phi_merge (ir_node *block, int pos, ir_mode *mode, ir_node **nin, int ins)
1058 {
1059   ir_node *prevBlock, *res, *phi0;
1060   int i;
1061
1062
1063   /* If this block has no value at pos create a Phi0 and remember it
1064      in graph_arr to break recursions. */
1065   phi0 = NULL;
1066   if (!block->attr.block.graph_arr[pos]) {
1067     /* This is commented out as collapsing to Bads is no good idea.
1068        Either we need an assert here, or we need to call a routine
1069        that deals with this case as appropriate for the given language.
1070        Right now a self referencing Id is created which will crash irg_vryfy().
1071
1072        Even if all variables are defined before use, it can happen that
1073        we get to the start block, if a cond has been replaced by a tuple
1074        (bad, jmp).  As the start has a self referencing control flow edge,
1075        we get a self referencing Id, which is hard to optimize away.  We avoid
1076        this by defining the value as a Bad node.
1077        Returning a const with tarval_bad is a preliminary solution.  In some
1078        situations we might want a Warning or an Error. */
1079
1080     if (block == get_irg_start_block(current_ir_graph)) {
1081       block->attr.block.graph_arr[pos] = new_Const(mode, tarval_bad);
1082       return block->attr.block.graph_arr[pos];
1083       } else  {
1084       phi0 = new_r_Phi0(current_ir_graph, block, mode);
1085       block->attr.block.graph_arr[pos] = phi0;
1086     }
1087   }
1088
1089   /* This loop goes to all predecessor blocks of the block the Phi node
1090      is in and there finds the operands of the Phi node by calling
1091      get_r_value_internal.  */
1092   for (i = 1;  i <= ins;  ++i) {
1093     assert (block->in[i]);
1094     if (is_Bad(block->in[i])) {
1095       /* In case a Cond has been optimized we would get right to the start block
1096          with an invalid definition. */
1097       nin[i-1] = new_Bad();
1098       continue;
1099     }
1100     prevBlock = block->in[i]->in[0]; /* go past control flow op to prev block */
1101     assert (prevBlock);
1102     if (!is_Bad(prevBlock)) {
1103       nin[i-1] = get_r_value_internal (prevBlock, pos, mode);
1104     } else {
1105       nin[i-1] = new_Bad();
1106     }
1107   }
1108
1109   /* After collecting all predecessors into the array nin a new Phi node
1110      with these predecessors is created.  This constructor contains an
1111      optimization: If all predecessors of the Phi node are identical it
1112      returns the only operand instead of a new Phi node.  */
1113   res = new_r_Phi_in (current_ir_graph, block, mode, nin, ins);
1114
1115   /* In case we allocated a Phi0 node at the beginning of this procedure,
1116      we need to exchange this Phi0 with the real Phi. */
1117   if (phi0) {
1118     exchange(phi0, res);
1119     block->attr.block.graph_arr[pos] = res;
1120   }
1121
1122   return res;
1123 }
1124
1125 /* This function returns the last definition of a variable.  In case
1126    this variable was last defined in a previous block, Phi nodes are
1127    inserted.  If the part of the firm graph containing the definition
1128    is not yet constructed, a dummy Phi node is returned. */
1129 inline ir_node *
1130 get_r_value_internal (ir_node *block, int pos, ir_mode *mode)
1131 {
1132   ir_node *res;
1133   /* There are 4 cases to treat.
1134
1135      1. The block is not mature and we visit it the first time.  We can not
1136         create a proper Phi node, therefore a Phi0, i.e., a Phi without
1137         predecessors is returned.  This node is added to the linked list (field
1138         "link") of the containing block to be completed when this block is
1139         matured. (Comlpletion will add a new Phi and turn the Phi0 into an Id
1140         node.)
1141
1142      2. The value is already known in this block, graph_arr[pos] is set and we
1143         visit the block the first time.  We can return the value without
1144         creating any new nodes.
1145
1146      3. The block is mature and we visit it the first time.  A Phi node needs
1147         to be created (phi_merge).  If the Phi is not needed, as all it's
1148         operands are the same value reaching the block through different
1149         paths, it's optimized away and the value itself is returned.
1150
1151      4. The block is mature, and we visit it the second time.  Now two
1152         subcases are possible:
1153         * The value was computed completely the last time we were here. This
1154           is the case if there is no loop.  We can return the proper value.
1155         * The recursion that visited this node and set the flag did not
1156           return yet.  We are computing a value in a loop and need to
1157           break the recursion.  This case only happens if we visited
1158           the same block with phi_merge before, which inserted a Phi0.
1159           So we return the Phi0.
1160   */
1161
1162   /* case 4 -- already visited. */
1163   if (get_irn_visited(block) == get_irg_visited(current_ir_graph)) {
1164     /* As phi_merge allocates a Phi0 this value is always defined. Here
1165      is the critical difference of the two algorithms. */
1166     assert(block->attr.block.graph_arr[pos]);
1167     return block->attr.block.graph_arr[pos];
1168   }
1169
1170   /* visited the first time */
1171   set_irn_visited(block, get_irg_visited(current_ir_graph));
1172
1173   /* Get the local valid value */
1174   res = block->attr.block.graph_arr[pos];
1175
1176   /* case 2 -- If the value is actually computed, return it. */
1177   if (res) { return res; };
1178
1179   if (block->attr.block.matured) { /* case 3 */
1180
1181     /* The Phi has the same amount of ins as the corresponding block. */
1182     int ins = get_irn_arity(block);
1183     ir_node **nin;
1184     NEW_ARR_A (ir_node *, nin, ins);
1185
1186     /* Phi merge collects the predecessors and then creates a node. */
1187     res = phi_merge (block, pos, mode, nin, ins);
1188
1189   } else {  /* case 1 */
1190     /* The block is not mature, we don't know how many in's are needed.  A Phi
1191        with zero predecessors is created.  Such a Phi node is called Phi0
1192        node.  The Phi0 is then added to the list of Phi0 nodes in this block
1193        to be matured by mature_block later.
1194        The Phi0 has to remember the pos of it's internal value.  If the real
1195        Phi is computed, pos is used to update the array with the local
1196        values. */
1197     res = new_r_Phi0 (current_ir_graph, block, mode);
1198     res->attr.phi0_pos = pos;
1199     res->link = block->link;
1200     block->link = res;
1201   }
1202
1203   /* If we get here, the frontend missed a use-before-definition error */
1204   if (!res) {
1205     /* Error Message */
1206     printf("Error: no value set.  Use of undefined variable.  Initializing
1207             to zero.\n");
1208     assert (mode->code >= irm_f && mode->code <= irm_p);
1209     res = new_r_Const (current_ir_graph, block, mode,
1210                        tarval_mode_null[mode->code]);
1211   }
1212
1213   /* The local valid value is available now. */
1214   block->attr.block.graph_arr[pos] = res;
1215
1216   return res;
1217 }
1218
1219 #endif /* USE_FAST_PHI_CONSTRUCTION */
1220
1221 /* ************************************************************************** */
1222
1223 /** Finalize a Block node, when all control flows are known.  */
1224 /** Acceptable parameters are only Block nodes.               */
1225 void
1226 mature_block (ir_node *block)
1227 {
1228
1229   int ins;
1230   ir_node *n, **nin;
1231   ir_node *next;
1232
1233   assert (get_irn_opcode(block) == iro_Block);
1234
1235   if (!get_Block_matured(block)) {
1236
1237     /* turn the dynamic in-array into a static one. */
1238     ins = ARR_LEN (block->in)-1;
1239     NEW_ARR_A (ir_node *, nin, ins);
1240     /*  @@@ something is strange here... why isn't the array copied? */
1241
1242     /* Traverse a chain of Phi nodes attached to this block and mature
1243        these, too. **/
1244     for (n = block->link;  n;  n=next) {
1245       inc_irg_visited(current_ir_graph);
1246       next = n->link;
1247       exchange (n, phi_merge (block, n->attr.phi0_pos, n->mode, nin, ins));
1248     }
1249
1250     block->attr.block.matured = 1;
1251
1252     /* Now, as the block is a finished firm node, we can optimize it.
1253        Since other nodes have been allocated since the block was created
1254        we can not free the node on the obstack.  Therefore we have to call
1255        optimize_in_place.
1256        Unfortunately the optimization does not change a lot, as all allocated
1257        nodes refer to the unoptimized node. */
1258     block = optimize_in_place(block);
1259     irn_vrfy(block);
1260   }
1261 }
1262
1263 ir_node *
1264 new_Phi (int arity, ir_node **in, ir_mode *mode)
1265 {
1266   return new_r_Phi (current_ir_graph, current_ir_graph->current_block,
1267                     arity, in, mode);
1268 }
1269
1270 ir_node *
1271 new_Const (ir_mode *mode, tarval *con)
1272 {
1273   return new_r_Const (current_ir_graph, current_ir_graph->start_block,
1274                       mode, con);
1275 }
1276
1277 ir_node *
1278 new_Id (ir_node *val, ir_mode *mode)
1279 {
1280   return new_r_Id (current_ir_graph, current_ir_graph->current_block,
1281                    val, mode);
1282 }
1283
1284 ir_node *
1285 new_Proj (ir_node *arg, ir_mode *mode, long proj)
1286 {
1287   return new_r_Proj (current_ir_graph, current_ir_graph->current_block,
1288                      arg, mode, proj);
1289 }
1290
1291 ir_node *
1292 new_Conv (ir_node *op, ir_mode *mode)
1293 {
1294   return new_r_Conv (current_ir_graph, current_ir_graph->current_block,
1295                      op, mode);
1296 }
1297
1298 ir_node *
1299 new_Tuple (int arity, ir_node **in)
1300 {
1301   return new_r_Tuple (current_ir_graph, current_ir_graph->current_block,
1302                       arity, in);
1303 }
1304
1305 ir_node *
1306 new_Add (ir_node *op1, ir_node *op2, ir_mode *mode)
1307 {
1308   return new_r_Add (current_ir_graph, current_ir_graph->current_block,
1309                     op1, op2, mode);
1310 }
1311
1312 ir_node *
1313 new_Sub (ir_node *op1, ir_node *op2, ir_mode *mode)
1314 {
1315   return new_r_Sub (current_ir_graph, current_ir_graph->current_block,
1316                     op1, op2, mode);
1317 }
1318
1319
1320 ir_node *
1321 new_Minus  (ir_node *op,  ir_mode *mode)
1322 {
1323   return new_r_Minus (current_ir_graph, current_ir_graph->current_block,
1324                       op, mode);
1325 }
1326
1327 ir_node *
1328 new_Mul (ir_node *op1, ir_node *op2, ir_mode *mode)
1329 {
1330   return new_r_Mul (current_ir_graph, current_ir_graph->current_block,
1331                     op1, op2, mode);
1332 }
1333
1334 ir_node *
1335 new_Quot (ir_node *memop, ir_node *op1, ir_node *op2)
1336 {
1337   return new_r_Quot (current_ir_graph, current_ir_graph->current_block,
1338                      memop, op1, op2);
1339 }
1340
1341 ir_node *
1342 new_DivMod (ir_node *memop, ir_node *op1, ir_node *op2)
1343 {
1344   return new_r_DivMod (current_ir_graph, current_ir_graph->current_block,
1345                        memop, op1, op2);
1346 }
1347
1348 ir_node *
1349 new_Div (ir_node *memop, ir_node *op1, ir_node *op2)
1350 {
1351   return new_r_Div (current_ir_graph, current_ir_graph->current_block,
1352                     memop, op1, op2);
1353 }
1354
1355 ir_node *
1356 new_Mod (ir_node *memop, ir_node *op1, ir_node *op2)
1357 {
1358   return new_r_Mod (current_ir_graph, current_ir_graph->current_block,
1359                     memop, op1, op2);
1360 }
1361
1362 ir_node *
1363 new_And (ir_node *op1, ir_node *op2, ir_mode *mode)
1364 {
1365   return new_r_And (current_ir_graph, current_ir_graph->current_block,
1366                     op1, op2, mode);
1367 }
1368
1369 ir_node *
1370 new_Or (ir_node *op1, ir_node *op2, ir_mode *mode)
1371 {
1372   return new_r_Or (current_ir_graph, current_ir_graph->current_block,
1373                    op1, op2, mode);
1374 }
1375
1376 ir_node *
1377 new_Eor (ir_node *op1, ir_node *op2, ir_mode *mode)
1378 {
1379   return new_r_Eor (current_ir_graph, current_ir_graph->current_block,
1380                     op1, op2, mode);
1381 }
1382
1383 ir_node *
1384 new_Not (ir_node *op, ir_mode *mode)
1385 {
1386   return new_r_Not (current_ir_graph, current_ir_graph->current_block,
1387                     op, mode);
1388 }
1389
1390 ir_node *
1391 new_Shl (ir_node *op, ir_node *k, ir_mode *mode)
1392 {
1393   return new_r_Shl (current_ir_graph, current_ir_graph->current_block,
1394                     op, k, mode);
1395 }
1396
1397 ir_node *
1398 new_Shr (ir_node *op, ir_node *k, ir_mode *mode)
1399 {
1400   return new_r_Shr (current_ir_graph, current_ir_graph->current_block,
1401                     op, k, mode);
1402 }
1403
1404 ir_node *
1405 new_Shrs (ir_node *op, ir_node *k, ir_mode *mode)
1406 {
1407   return new_r_Shrs (current_ir_graph, current_ir_graph->current_block,
1408                      op, k, mode);
1409 }
1410
1411 ir_node *
1412 new_Rotate (ir_node *op, ir_node *k, ir_mode *mode)
1413 {
1414   return new_r_Rot (current_ir_graph, current_ir_graph->current_block,
1415                      op, k, mode);
1416 }
1417
1418 ir_node *
1419 new_Abs (ir_node *op, ir_mode *mode)
1420 {
1421   return new_r_Abs (current_ir_graph, current_ir_graph->current_block,
1422                     op, mode);
1423 }
1424
1425 ir_node *
1426 new_Cmp (ir_node *op1, ir_node *op2)
1427 {
1428   return new_r_Cmp (current_ir_graph, current_ir_graph->current_block,
1429                     op1, op2);
1430 }
1431
1432 ir_node *
1433 new_Jmp (void)
1434 {
1435   return new_r_Jmp (current_ir_graph, current_ir_graph->current_block);
1436 }
1437
1438 ir_node *
1439 new_Cond (ir_node *c)
1440 {
1441   return new_r_Cond (current_ir_graph, current_ir_graph->current_block, c);
1442 }
1443
1444 ir_node *
1445 new_Call (ir_node *store, ir_node *callee, int arity, ir_node **in,
1446           type *type)
1447 {
1448   return new_r_Call (current_ir_graph, current_ir_graph->current_block,
1449                      store, callee, arity, in, type);
1450 }
1451
1452 ir_node *
1453 new_Return (ir_node* store, int arity, ir_node **in)
1454 {
1455   return new_r_Return (current_ir_graph, current_ir_graph->current_block,
1456                        store, arity, in);
1457 }
1458
1459 ir_node *
1460 new_Raise (ir_node *store, ir_node *obj)
1461 {
1462   return new_r_Raise (current_ir_graph, current_ir_graph->current_block,
1463                       store, obj);
1464 }
1465
1466 ir_node *
1467 new_Load (ir_node *store, ir_node *addr)
1468 {
1469   return new_r_Load (current_ir_graph, current_ir_graph->current_block,
1470                      store, addr);
1471 }
1472
1473 ir_node *
1474 new_Store (ir_node *store, ir_node *addr, ir_node *val)
1475 {
1476   return new_r_Store (current_ir_graph, current_ir_graph->current_block,
1477                       store, addr, val);
1478 }
1479
1480 ir_node *
1481 new_Alloc (ir_node *store, ir_node *size, type *alloc_type,
1482            where_alloc where)
1483 {
1484   return new_r_Alloc (current_ir_graph, current_ir_graph->current_block,
1485                       store, size, alloc_type, where);
1486 }
1487
1488 ir_node *
1489 new_Free (ir_node *store, ir_node *ptr, ir_node *size, type *free_type)
1490 {
1491   return new_r_Free (current_ir_graph, current_ir_graph->current_block,
1492                      store, ptr, size, free_type);
1493 }
1494
1495 ir_node *
1496 new_simpleSel (ir_node *store, ir_node *objptr, entity *ent)
1497 /* GL: objptr was called frame before.  Frame was a bad choice for the name
1498    as the operand could as well be a pointer to a dynamic object. */
1499 {
1500   return new_r_Sel (current_ir_graph, current_ir_graph->current_block,
1501                     store, objptr, 0, NULL, ent);
1502 }
1503
1504 ir_node *
1505 new_Sel (ir_node *store, ir_node *objptr, int n_index, ir_node **index, entity *sel)
1506 {
1507   return new_r_Sel (current_ir_graph, current_ir_graph->current_block,
1508                     store, objptr, n_index, index, sel);
1509 }
1510
1511 ir_node *
1512 new_SymConst (type_or_id_p value, symconst_kind kind)
1513 {
1514   return new_r_SymConst (current_ir_graph, current_ir_graph->current_block,
1515                          value, kind);
1516 }
1517
1518 ir_node *
1519 new_Sync (int arity, ir_node** in)
1520 {
1521   return new_r_Sync (current_ir_graph, current_ir_graph->current_block,
1522                      arity, in);
1523 }
1524
1525
1526 ir_node *
1527 new_Bad (void)
1528 {
1529   return current_ir_graph->bad;
1530 }
1531
1532 /* ********************************************************************* */
1533 /* Comfortable interface with automatic Phi node construction.           */
1534 /* (Uses also constructors of ?? interface, except new_Block.            */
1535 /* ********************************************************************* */
1536
1537 /** Block construction **/
1538 /* immature Block without predecessors */
1539 ir_node *new_immBlock (void) {
1540   ir_node *res;
1541
1542   /* creates a new dynamic in-array as length of in is -1 */
1543   res = new_ir_node (current_ir_graph, NULL, op_Block, mode_R, -1, NULL);
1544   current_ir_graph->current_block = res;
1545   res->attr.block.matured = 0;
1546   set_Block_block_visited(res, 0);
1547
1548   /* Create and initialize array for Phi-node construction. */
1549   res->attr.block.graph_arr = NEW_ARR_D (ir_node *, current_ir_graph->obst,
1550                                          current_ir_graph->n_loc);
1551   memset(res->attr.block.graph_arr, 0, sizeof(ir_node *)*current_ir_graph->n_loc);
1552
1553   /* Immature block may not be optimized! */
1554   irn_vrfy (res);
1555
1556   return res;
1557 }
1558
1559 /* add an adge to a jmp/control flow node */
1560 void
1561 add_in_edge (ir_node *block, ir_node *jmp)
1562 {
1563   if (block->attr.block.matured) {
1564     printf("Error: Block already matured!\n");
1565   }
1566   else {
1567     assert (jmp != NULL);
1568     ARR_APP1 (ir_node *, block->in, jmp);
1569   }
1570 }
1571
1572 /* changing the current block */
1573 void
1574 switch_block (ir_node *target)
1575 {
1576   current_ir_graph->current_block = target;
1577 }
1578
1579 /* ************************ */
1580 /* parameter administration */
1581
1582 /* get a value from the parameter array from the current block by its index */
1583 ir_node *
1584 get_value (int pos, ir_mode *mode)
1585 {
1586   inc_irg_visited(current_ir_graph);
1587   return get_r_value_internal (current_ir_graph->current_block, pos + 1, mode);
1588 }
1589
1590
1591 /* set a value at position pos in the parameter array from the current block */
1592 inline void
1593 set_value (int pos, ir_node *value)
1594 {
1595   current_ir_graph->current_block->attr.block.graph_arr[pos + 1] = value;
1596 }
1597
1598 /* get the current store */
1599 inline ir_node *
1600 get_store (void)
1601 {
1602   /* GL: one could call get_value instead */
1603   inc_irg_visited(current_ir_graph);
1604   return get_r_value_internal (current_ir_graph->current_block, 0, mode_M);
1605 }
1606
1607 /* set the current store */
1608 inline void
1609 set_store (ir_node *store)
1610 {
1611   /* GL: one could call set_value instead */
1612   current_ir_graph->current_block->attr.block.graph_arr[0] = store;
1613 }
1614
1615 /* ********************************************************************* */
1616 /* initialize */
1617
1618 /* call once for each run of the library */
1619 void
1620 init_cons (void)
1621 {
1622 }