8 #include "firm_types.h"
10 #include "ia32_new_nodes.h"
11 #include "bearch_ia32_t.h"
14 * creates a unique ident by adding a number to a tag
16 * @param tag the tag string, must contain a %d if a number
19 static ident *unique_id(const char *tag)
21 static unsigned id = 0;
24 snprintf(str, sizeof(str), tag, ++id);
25 return new_id_from_str(str);
31 * Transforms a SymConst.
33 * @param mod the debug module
34 * @param block the block the new node should belong to
35 * @param node the ir SymConst node
36 * @param mode mode of the SymConst
37 * @return the created ia32 Const node
39 static ir_node *gen_SymConst(ia32_transform_env_t *env) {
41 dbg_info *dbg = env->dbg;
42 ir_mode *mode = env->mode;
43 ir_graph *irg = env->irg;
44 ir_node *block = env->block;
46 cnst = new_rd_ia32_Const(dbg, irg, block, mode);
47 set_ia32_Const_attr(cnst, env->irn);
52 * Get a primitive type for a mode.
54 static ir_type *get_prim_type(pmap *types, ir_mode *mode)
56 pmap_entry *e = pmap_find(types, mode);
61 snprintf(buf, sizeof(buf), "prim_type_%s", get_mode_name(mode));
62 res = new_type_primitive(new_id_from_str(buf), mode);
63 pmap_insert(types, mode, res);
71 * Get an entity that is initialized with a tarval
73 static entity *get_entity_for_tv(ia32_code_gen_t *cg, ir_node *cnst)
75 tarval *tv = get_Const_tarval(cnst);
76 pmap_entry *e = pmap_find(cg->tv_ent, tv);
81 ir_mode *mode = get_irn_mode(cnst);
82 ir_type *tp = get_Const_type(cnst);
83 if (tp == firm_unknown_type)
84 tp = get_prim_type(cg->types, mode);
86 res = new_entity(get_glob_type(), unique_id("ia32FloatCnst_%u"), tp);
88 set_entity_ld_ident(res, get_entity_ident(res));
89 set_entity_visibility(res, visibility_local);
90 set_entity_variability(res, variability_constant);
91 set_entity_allocation(res, allocation_static);
93 /* we create a new entity here: It's initialization must resist on the
95 rem = current_ir_graph;
96 current_ir_graph = get_const_code_irg();
97 set_atomic_ent_value(res, new_Const_type(tv, tp));
98 current_ir_graph = rem;
106 * Transforms a Const.
108 * @param mod the debug module
109 * @param block the block the new node should belong to
110 * @param node the ir Const node
111 * @param mode mode of the Const
112 * @return the created ia32 Const node
114 static ir_node *gen_Const(ia32_transform_env_t *env) {
117 ir_graph *irg = env->irg;
118 ir_node *block = env->block;
119 ir_node *node = env->irn;
120 dbg_info *dbg = env->dbg;
121 ir_mode *mode = env->mode;
123 if (mode_is_float(mode)) {
124 sym.entity_p = get_entity_for_tv(env->cg, node);
126 cnst = new_rd_SymConst(dbg, irg, block, sym, symconst_addr_ent);
128 cnst = gen_SymConst(env);
131 cnst = new_rd_ia32_Const(dbg, irg, block, get_irn_mode(node));
132 set_ia32_Const_attr(cnst, node);
140 * Transforms (all) Const's into ia32_Const and places them in the
141 * block where they are used (or in the cfg-pred Block in case of Phi's)
143 void ia32_place_consts(ir_node *irn, void *env) {
144 ia32_code_gen_t *cg = env;
145 ia32_transform_env_t tenv;
147 ir_node *pred, *cnst;
154 mode = get_irn_mode(irn);
156 tenv.arch_env = cg->arch_env;
157 tenv.block = get_nodes_block(irn);
160 tenv.mod = firm_dbg_register("ir.be.ia32.optimize");
162 /* Loop over all predecessors and check for Sym/Const nodes */
163 for (i = get_irn_arity(irn) - 1; i >= 0; --i) {
164 pred = get_irn_n(irn, i);
166 opc = get_irn_opcode(pred);
168 tenv.mode = get_irn_mode(pred);
169 tenv.dbg = get_irn_dbg_info(pred);
171 /* If it's a Phi, then we need to create the */
172 /* new Const in it's predecessor block */
174 tenv.block = get_Block_cfgpred_block(get_nodes_block(irn), i);
179 cnst = gen_Const(&tenv);
182 cnst = gen_SymConst(&tenv);
188 /* if we found a const, then set it */
190 set_irn_n(irn, i, cnst);