Test phis in nested loops
[libfirm] / testprograms / three_cfpred_example.c
1 /*
2  * Project:     libFIRM
3  * File name:   testprograms/three_cfpred_example.c
4  * Purpose:     Construct a block with more than two predecessors.
5  * Author:      Christian Schaefer, Goetz Lindenmaier
6  * Modified by:
7  * Created:
8  * CVS-ID:      $Id$
9  * Copyright:   (c) 1999-2003 Universität Karlsruhe
10  * Licence:     This file protected by GPL -  GNU GENERAL PUBLIC LICENSE.
11  */
12
13
14 # include <stdio.h>
15 # include <string.h>
16
17 # include "irvrfy.h"
18 # include "irdump.h"
19 # include "firm.h"
20
21 /**
22  *  This file constructs a control flow of following shape:
23  *
24  *
25  *       firstCondBlock
26  *          /     \
27  *         /       \
28  *       |/_       _\|
29  *     Block1    scnCondBlock
30  *        |       |        |
31  *        |       |        |
32  *    |      \ /      \ /
33  *        |     Block2   Block3
34  *         \      |       /
35  *          \     |      /
36  *          _\|  \ /   |/_
37  *            nextBlock
38  *
39  *
40  *   This is a program as, e.g.,
41  *
42  *   if () then
43  *     { Jmp label1; } //  happens anyways
44  *   else
45  *     { Jmp label1; } //  happens anyways
46  * label1:
47  *   return();
48  *   Jmp label1;
49  *
50  **/
51
52 int main(int argc, char **argv)
53 {
54   type     *prim_t_int;
55   ir_graph *irg;          /* this variable contains the irgraph */
56   type *owner;      /* the class in which this method is defined */
57   type *proc_main; /* type information for the method main */
58   entity *ent;            /* represents this method as entity of owner */
59   ir_node *c1, *c2, *cond, *f, *t, *endBlock, *Block1, *jmp,
60           *scndCondBlock, *Block2, *Block3, *x;
61
62   /* init library */
63   init_firm (NULL);
64
65   set_optimize(1);
66
67   /*** Make basic type information for primitive type int. ***/
68   prim_t_int = new_type_primitive(id_from_str ("int", 3), mode_Is);
69
70   /* FIRM was designed for oo languages where all methods belong to a class.
71    * For imperative languages like C we view a file as a large class containing
72    * all functions as methods in this file.
73    * This class now is automatically generated.
74    */
75 #define METHODNAME "THREE_CFPRED_EXAMPLE_main"
76 #define NRARGS 1
77 #define NRES 1
78   printf("\nCreating an IR graph: THREE_CFPRED_EXAMPLE ...\n");
79
80   owner = get_glob_type();
81   proc_main = new_type_method(id_from_str(METHODNAME, strlen(METHODNAME)),
82                   NRARGS, NRES);
83   set_method_param_type(proc_main, 0, prim_t_int);
84   set_method_res_type(proc_main, 0, prim_t_int);
85
86   ent = new_entity (owner,
87                     id_from_str (METHODNAME, strlen(METHODNAME)),
88                     proc_main);
89
90 #define NUM_OF_LOCAL_VARS 2
91
92   irg = new_ir_graph (ent, NUM_OF_LOCAL_VARS);
93
94   /* to make a condition  */
95   c1 = new_Const (mode_Is, new_tarval_from_long (1, mode_Is));
96   c2 = new_Proj (get_irg_args(irg), mode_Is, 0);
97   set_value(1, c2);
98
99   cond = new_Cond(new_Proj(new_Cmp(c1, c2), mode_b, Eq));
100   set_value(0, new_Const (mode_Is, new_tarval_from_long (6, mode_Is)));
101   f = new_Proj(cond, mode_X, 0);
102   t = new_Proj(cond, mode_X, 1);
103   mature_block(get_irg_current_block(irg));
104
105   /* end block to add jmps */
106   endBlock = new_immBlock();
107
108   /* Block 1 */
109   Block1 = new_immBlock();
110   add_in_edge(Block1, t);
111   mature_block(Block1);
112   set_value(0, new_Const (mode_Is, new_tarval_from_long (5, mode_Is)));
113   jmp = new_Jmp();
114   add_in_edge(endBlock, jmp);
115
116   /* scndCondBlock */
117   scndCondBlock = new_immBlock();
118   add_in_edge(scndCondBlock, f);
119   mature_block(scndCondBlock);
120   c1 = new_Const (mode_Is, new_tarval_from_long (3, mode_Is));
121   cond = new_Cond(new_Proj(new_Cmp(c1, get_value(1, mode_Is)), mode_b, Eq));
122   f = new_Proj(cond, mode_X, 0);
123   t = new_Proj(cond, mode_X, 1);
124   mature_block(get_irg_current_block(irg));
125
126   /* Block 2 */
127   Block2 = new_immBlock();
128   add_in_edge(Block2, f);
129   mature_block(Block2);
130   jmp = new_Jmp();
131   add_in_edge(endBlock, jmp);
132
133   /* Block 3 */
134   Block3 = new_immBlock();
135   add_in_edge(Block3, t);
136   mature_block(Block3);
137   jmp = new_Jmp();
138   add_in_edge(endBlock, jmp);
139
140   /* finish the end Block */
141   switch_block(endBlock);
142   {
143     ir_node *in[1];
144     in[0] = get_value(0, mode_Is);
145     x = new_Return (get_store(), 1, in);
146   }
147   mature_block (get_irg_current_block(irg));
148
149   /* finish the Block with the end node */
150   add_in_edge (get_irg_end_block(irg), x);
151   mature_block (get_irg_end_block(irg));
152
153   /* verify the graph */
154   irg_vrfy(irg);
155   finalize_cons (irg);
156
157   printf("Optimizing ...\n");
158   dead_node_elimination(irg);
159
160   printf("Dumping the graph and a control flow graph.\n");
161   dump_ir_block_graph (irg);
162   dump_cfg (irg);
163   printf("Use xvcg to view these graphs:\n");
164   printf("/ben/goetz/bin/xvcg GRAPHNAME\n\n");
165
166   return (0);
167 }