*** empty log message ***
[libfirm] / ir / tr / entity.c
1 /* Copyright (C) 1998 - 2000 by Universitaet Karlsruhe
2 ** All rights reserved.
3 **
4 ** Authors: Martin Trapp, Christian Schaefer
5 **
6 */
7
8 /* $Id$ */
9
10 #ifdef HAVE_CONFIG_H
11 # include <config.h>
12 #endif
13
14 # include <stdlib.h>
15 # include <stddef.h>
16 # include "entity_t.h"
17 # include "mangle.h"
18 # include "typegmod_t.h"
19 # include "array.h"
20 /* All this is needed to build the constant node for methods: */
21 # include "irprog.h"
22 # include "ircons.h"
23
24 /*******************************************************************/
25 /** general                                                       **/
26 /*******************************************************************/
27
28 void
29 init_entity (void)
30 {
31 }
32
33 /*******************************************************************/
34 /** ENTITY                                                        **/
35 /*******************************************************************/
36
37 inline void insert_entity_in_owner (entity *ent) {
38   type *owner = ent->owner;
39   switch (get_type_tpop_code(owner)) {
40   case tpo_class: {
41     add_class_member (owner, ent);
42   } break;
43   case tpo_struct: {
44     add_struct_member (owner, ent);
45   } break;
46   case tpo_union: {
47     add_union_member (owner, ent);
48   } break;
49   case tpo_array: {
50     set_array_element_entity(owner, ent);
51   } break;
52   default: assert(0);
53   }
54 }
55
56 entity *
57 new_entity (type *owner, ident *name, type *type)
58 {
59   entity *res;
60   ir_graph *rem;
61
62   res = (entity *) malloc (sizeof (entity));
63   res->kind = k_entity;
64   assert_legal_owner_of_ent(owner);
65   res->owner = owner;
66   res->name = name;
67   res->type = type;
68   if (get_type_tpop(type) == type_method)
69     res->allocation = static_allocated;
70   else
71     res->allocation = automatic_allocated;
72   res->visibility = local;
73   res->offset = -1;
74   if (is_method_type(type)) {
75     res->variability = constant;
76     rem = current_ir_graph;
77     current_ir_graph = get_const_code_irg();
78     res->value = new_Const(mode_p, tarval_p_from_entity(res));
79     current_ir_graph = rem;
80   } else {
81     res->variability = uninitialized;
82   }
83   res->peculiarity = existent;
84   res->volatility = non_volatile;
85   res->ld_name = NULL;
86   res->overwrites = NEW_ARR_F(entity *, 1);
87
88   res->irg = NULL;
89
90   res->visit = 0;
91
92   /* Remember entity in it's owner. */
93   insert_entity_in_owner (res);
94   return res;
95 }
96 inline void free_entity_attrs(entity *ent) {
97   assert(ent);
98   DEL_ARR_F(ent->overwrites);
99 }
100
101 entity *
102 copy_entity_own (entity *old, type *new_owner) {
103   entity *new;
104
105   assert_legal_owner_of_ent(new_owner);
106   if (old->owner == new_owner) return old;
107   new = (entity *) malloc (sizeof (entity));
108   memcpy (new, old, sizeof (entity));
109   new->owner = new_owner;
110   new->overwrites = DUP_ARR_F(entity *, old->overwrites);
111
112   insert_entity_in_owner (new);
113
114   return new;
115 }
116
117 entity *
118 copy_entity_name (entity *old, ident *new_name) {
119   entity *new;
120
121   if (old->name == new_name) return old;
122   new = (entity *) malloc (sizeof (entity));
123   memcpy (new, old, sizeof (entity));
124   new->name = new_name;
125   new->ld_name = NULL;
126   new->overwrites = DUP_ARR_F(entity *, old->overwrites);
127
128   insert_entity_in_owner (new);
129
130   return new;
131 }
132
133 inline const char *
134 get_entity_name (entity *ent) {
135   assert (ent);
136   return id_to_str(get_entity_ident(ent));
137 }
138
139 ident *
140 get_entity_ident    (entity *ent) {
141   assert(ent);
142   return ent->name;
143 }
144
145 /*
146 void   set_entity_ld_name  (entity *, char *ld_name);
147 void   set_entity_ld_ident (entity *, ident *ld_ident);
148 */
149
150 inline type *
151 get_entity_owner (entity *ent) {
152   return ent->owner = skip_tid(ent->owner);
153 }
154
155 inline void
156 set_entity_owner (entity *ent, type *owner) {
157   assert_legal_owner_of_ent(owner);
158   ent->owner = owner;
159 }
160
161 inline void   /* should this go into type.c? */
162 assert_legal_owner_of_ent(type *owner) {
163   assert (get_type_tpop_code(owner) == tpo_class ||
164           get_type_tpop_code(owner) == tpo_union ||
165           get_type_tpop_code(owner) == tpo_struct ||
166           get_type_tpop_code(owner) == tpo_array);   /* Yes, array has an entity
167                                                         -- to select fields! */
168 }
169
170 inline ident *
171 get_entity_ld_ident (entity *ent)
172 {
173   if (ent->ld_name == NULL)
174     ent->ld_name = mangle_entity (ent);
175   return ent->ld_name;
176 }
177
178 inline void
179 set_entity_ld_ident (entity *ent, ident *ld_ident) {
180   ent->ld_name = ld_ident;
181 }
182
183 inline const char *
184 get_entity_ld_name (entity *ent) {
185   return id_to_str(get_entity_ld_ident(ent));
186 }
187
188 /*
189 char  *get_entity_ld_name  (entity *);
190 void   set_entity_ld_name  (entity *, char *ld_name);
191 */
192
193 inline type *
194 get_entity_type (entity *ent) {
195   return ent->type = skip_tid(ent->type);
196 }
197
198 inline void
199 set_entity_type (entity *ent, type *type) {
200   ent->type = type;
201 }
202
203
204 inline ent_allocation
205 get_entity_allocation (entity *ent) {
206   return ent->allocation;
207 }
208
209 inline void
210 set_entity_allocation (entity *ent, ent_allocation al) {
211   ent->allocation = al;
212 }
213
214
215 inline ent_visibility
216 get_entity_visibility (entity *ent) {
217   return ent->visibility;
218 }
219
220 inline void
221 set_entity_visibility (entity *ent, ent_visibility vis) {
222   if (vis != local) assert(ent->allocation == static_allocated);
223   ent->visibility = vis;
224 }
225
226 inline ent_variability
227 get_entity_variability (entity *ent) {
228   return ent->variability;
229 }
230
231 inline void
232 set_entity_variability (entity *ent, ent_variability var){
233   if (var == part_constant)
234     assert(is_class_type(ent->type) || is_struct_type(ent->type));
235   if ((is_compound_type(ent->type)) &&
236       (ent->variability == uninitialized) && (var != uninitialized)) {
237     /* Allocate datastructures for constant values */
238     ent->values = NEW_ARR_F(ir_node *, 1);
239     ent->val_ents = NEW_ARR_F(entity *, 1);
240   }
241   if ((is_compound_type(ent->type)) &&
242       (var == uninitialized) && (ent->variability != uninitialized)) {
243     /* Free datastructures for constant values */
244     DEL_ARR_F(ent->values);
245     DEL_ARR_F(ent->val_ents);
246   }
247   ent->variability = var;
248 }
249
250
251 inline ent_volatility
252 get_entity_volatility (entity *ent) {
253   return ent->volatility;
254 }
255
256 inline void
257 set_entity_volatility (entity *ent, ent_volatility vol) {
258   ent->volatility = vol;
259 }
260
261 inline peculiarity
262 get_entity_peculiarity (entity *ent) {
263   assert (ent);
264   assert (is_method_type(ent->type));
265   return ent->peculiarity;
266 }
267
268 inline void
269 set_entity_peculiarity (entity *ent, peculiarity pec) {
270   assert (ent);
271   assert (is_method_type(ent->type));
272   ent->peculiarity = pec;
273 }
274
275 /* Set has no effect for entities of type method. */
276 inline ir_node *
277 get_atomic_ent_value(entity *ent) {
278   assert(ent); assert(is_atomic_entity(ent)); assert((ent->variability != uninitialized));
279   return ent->value;
280 }
281
282 inline void
283 set_atomic_ent_value(entity *ent, ir_node *val) {
284   assert(ent && is_atomic_entity(ent) && (ent->variability != uninitialized));
285   if (is_method_type(ent->type)) return;
286   ent->value = val;
287 }
288
289 ir_node *copy_value(ir_node *n) {
290   ir_node *nn;
291   ir_mode *m;
292
293   m = get_irn_mode(n);
294   switch(get_irn_opcode(n)) {
295   case iro_Const:
296     nn = new_Const(m, get_Const_tarval(n)); break;
297   case iro_SymConst:
298     nn = new_SymConst(get_SymConst_type_or_id(n), get_SymConst_kind(n)); break;
299   case iro_Add:
300     nn = new_Add(copy_value(get_Add_left(n)), copy_value(get_Add_right(n)), m); break;
301   default:
302     assert(0 && "opdope invalid or not implemented"); break;
303   }
304   return nn;
305 }
306
307 /* Copies the value represented by the entity to current_block
308    in current_ir_graph. */
309 ir_node *copy_atomic_ent_value(entity *ent) {
310   assert(ent && is_atomic_entity(ent) && (ent->variability != uninitialized));
311   return copy_value(ent->value);
312 }
313
314 /* A value of a compound entity is a pair of value and the corresponding member of
315    the compound. */
316 inline void
317 add_compound_ent_value(entity *ent, ir_node *val, entity *member) {
318   assert(ent && is_compound_entity(ent) && (ent->variability != uninitialized));
319   ARR_APP1 (ir_node *, ent->values, val);
320   ARR_APP1 (entity *, ent->val_ents, member);
321 }
322
323 inline int
324 get_compound_ent_n_values(entity *ent) {
325   assert(ent && is_compound_entity(ent) && (ent->variability != uninitialized));
326   return (ARR_LEN (ent->values))-1;
327 }
328
329 inline ir_node  *
330 get_compound_ent_value(entity *ent, int pos) {
331   assert(ent && is_compound_entity(ent) && (ent->variability != uninitialized));
332   return ent->values[pos+1];
333 }
334
335 /* Copies the value i of the entity to current_block in current_ir_graph. */
336 ir_node *copy_compound_ent_value(entity *ent, int pos) {
337   assert(ent && is_compound_entity(ent) && (ent->variability != uninitialized));
338   return copy_value(ent->values[pos+1]);
339 }
340
341 inline entity   *
342 get_compound_ent_value_member(entity *ent, int pos) {
343   assert(ent && is_compound_entity(ent) && (ent->variability != uninitialized));
344   return ent->val_ents[pos+1];
345 }
346
347 inline void
348 set_compound_ent_value(entity *ent, ir_node *val, entity *member, int pos) {
349   assert(ent && is_compound_entity(ent) && (ent->variability != uninitialized));
350   ent->values[pos+1] = val;
351   ent->val_ents[pos+1] = member;
352 }
353
354 inline int
355 get_entity_offset (entity *ent) {
356   return ent->offset;
357 }
358
359 inline void
360 set_entity_offset (entity *ent, int offset) {
361   ent->offset = offset;
362 }
363
364 inline void
365 add_entity_overwrites   (entity *ent, entity *overwritten) {
366   assert(ent);
367   ARR_APP1 (entity *, ent->overwrites, overwritten);
368 }
369
370 inline int
371 get_entity_n_overwrites (entity *ent){
372   assert(ent);
373   return (ARR_LEN (ent->overwrites))-1;
374 }
375
376 inline entity *
377 get_entity_overwrites   (entity *ent, int pos){
378   assert(ent);
379   return ent->overwrites[pos+1];
380 }
381
382 inline void
383 set_entity_overwrites   (entity *ent, int pos, entity *overwritten) {
384   assert(ent);
385   ent->overwrites[pos+1] = overwritten;
386 }
387
388 /* A link to store intermediate information */
389 void *
390 get_entity_link(entity *ent) {
391   assert(ent);
392   return ent->link;
393 }
394
395 void
396 set_entity_link(entity *ent, void *l) {
397   assert(ent);
398   ent->link = l;
399 }
400
401 inline ir_graph *
402 get_entity_irg(entity *ent) {
403   assert (ent);
404   assert (is_method_type(ent->type));
405   return ent->irg;
406 }
407
408 inline void
409 set_entity_irg(entity *ent, ir_graph *irg) {
410   assert (ent && ent->type);
411   assert (irg);
412   assert (is_method_type(ent->type));
413   ent->irg = irg;
414 }
415
416 int is_atomic_entity(entity *ent) {
417   type* t = get_entity_type(ent);
418   return (is_primitive_type(t) || is_pointer_type(t) ||
419           is_enumeration_type(t) || is_method_type(t));
420 }
421
422 int is_compound_entity(entity *ent) {
423   type* t = get_entity_type(ent);
424   return (is_class_type(t) || is_struct_type(t) ||
425           is_array_type(t) || is_union_type(t));
426 }