From f7ff9494d0f76325b53f09452c6491aaad4a6d06 Mon Sep 17 00:00:00 2001 From: Matthias Braun Date: Thu, 17 Nov 2011 00:08:12 +0100 Subject: [PATCH] differntiate entity kinds We already saved different entity attributes depending on the entity type and an is_parameter flag. This unifies handling of different entity types and introduces normal, method, parameter, label and compound_member entities. --- ir/ir/irnode.c | 9 ++----- ir/ir/irprog.c | 8 +++---- ir/tr/entity.c | 62 ++++++++++++++++++++++++++++++++++++++---------- ir/tr/entity_t.h | 31 ++++++++++++++++-------- ir/tr/type_t.h | 9 +++---- 5 files changed, 81 insertions(+), 38 deletions(-) diff --git a/ir/ir/irnode.c b/ir/ir/irnode.c index 63816e605..0f9e40437 100644 --- a/ir/ir/irnode.c +++ b/ir/ir/irnode.c @@ -627,15 +627,10 @@ ir_entity *create_Block_entity(ir_node *block) entity = block->attr.block.entity; if (entity == NULL) { - ir_label_t nr; - ir_type *glob; - - glob = get_glob_type(); - entity = new_entity(glob, id_unique("block_%u"), get_code_type()); + ir_label_t nr = get_irp_next_label_nr(); + entity = new_label_entity(nr); set_entity_visibility(entity, ir_visibility_local); set_entity_linkage(entity, IR_LINKAGE_CONSTANT); - nr = get_irp_next_label_nr(); - set_entity_label(entity, nr); set_entity_compiler_generated(entity, 1); block->attr.block.entity = entity; diff --git a/ir/ir/irprog.c b/ir/ir/irprog.c index e6abb6ed2..51e36377f 100644 --- a/ir/ir/irprog.c +++ b/ir/ir/irprog.c @@ -92,10 +92,10 @@ static ir_prog *complete_ir_prog(ir_prog *irp, const char *module_name) = new_type_class(IDENT("Destructors")); /* Set these flags for debugging. */ - irp->segment_types[IR_SEGMENT_GLOBAL]->flags |= tf_global_type; - irp->segment_types[IR_SEGMENT_THREAD_LOCAL]->flags |= tf_tls_type; - irp->segment_types[IR_SEGMENT_CONSTRUCTORS]->flags |= tf_constructors; - irp->segment_types[IR_SEGMENT_DESTRUCTORS]->flags |= tf_destructors; + irp->segment_types[IR_SEGMENT_GLOBAL]->flags |= tf_segment|tf_global_type; + irp->segment_types[IR_SEGMENT_THREAD_LOCAL]->flags |= tf_segment|tf_tls_type; + irp->segment_types[IR_SEGMENT_CONSTRUCTORS]->flags |= tf_segment|tf_constructors; + irp->segment_types[IR_SEGMENT_DESTRUCTORS]->flags |= tf_segment|tf_destructors; /* The global type is a class, but we cannot derive from it, so set the final property to assist optimizations that checks for it. */ diff --git a/ir/tr/entity.c b/ir/tr/entity.c index b70c0d74b..bd019b534 100644 --- a/ir/tr/entity.c +++ b/ir/tr/entity.c @@ -59,8 +59,8 @@ ir_entity *get_unknown_entity(void) { return unknown_entity; } /* ENTITY */ /*-----------------------------------------------------------------*/ -static ir_entity *intern_new_entity(ir_type *owner, ident *name, ir_type *type, - dbg_info *dbgi) +static ir_entity *intern_new_entity(ir_type *owner, ir_entity_kind kind, + ident *name, ir_type *type, dbg_info *dbgi) { ir_entity *res; @@ -72,6 +72,7 @@ static ir_entity *intern_new_entity(ir_type *owner, ident *name, ir_type *type, res->type = type; res->owner = owner; + res->entity_kind = kind; res->volatility = volatility_non_volatile; res->aligned = align_is_aligned; res->usage = ir_usage_unknown; @@ -99,12 +100,13 @@ static ir_entity *intern_new_entity(ir_type *owner, ident *name, ir_type *type, ir_entity *new_d_entity(ir_type *owner, ident *name, ir_type *type, dbg_info *db) { - ir_entity *res = intern_new_entity(owner, name, type, db); + ir_entity *res; if (is_Method_type(type)) { ir_graph *irg = get_const_code_irg(); symconst_symbol sym; ir_mode *mode = is_Method_type(type) ? mode_P_code : mode_P_data; + res = intern_new_entity(owner, IR_ENTITY_METHOD, name, type, db); sym.entity_p = res; set_atomic_ent_value(res, new_r_SymConst(irg, mode, sym, symconst_addr_ent)); res->linkage = IR_LINKAGE_CONSTANT; @@ -113,11 +115,13 @@ ir_entity *new_d_entity(ir_type *owner, ident *name, ir_type *type, res->attr.mtd_attr.param_access = NULL; res->attr.mtd_attr.param_weight = NULL; res->attr.mtd_attr.irg = NULL; - } else if (is_compound_type(type)) { + } else if (owner != NULL + && (is_compound_type(owner) && !(owner->flags & tf_segment))) { + res = intern_new_entity(owner, IR_ENTITY_COMPOUND_MEMBER, name, type, db); res->attr.cmpd_attr.values = NULL; res->attr.cmpd_attr.val_paths = NULL; - } else if (is_code_type(type)) { - res->attr.code_attr.label = (ir_label_t) -1; + } else { + res = intern_new_entity(owner, IR_ENTITY_NORMAL, name, type, db); } hook_new_entity(res); @@ -139,9 +143,9 @@ static ident *make_parameter_entity_name(size_t pos) ir_entity *new_d_parameter_entity(ir_type *owner, size_t pos, ir_type *type, dbg_info *dbgi) { - ident *name = make_parameter_entity_name(pos); - ir_entity *res = intern_new_entity(owner, name, type, dbgi); - res->is_parameter = true; + ident *name = make_parameter_entity_name(pos); + ir_entity *res + = intern_new_entity(owner, IR_ENTITY_PARAMETER, name, type, dbgi); res->attr.parameter.number = pos; hook_new_entity(res); return res; @@ -152,6 +156,23 @@ ir_entity *new_parameter_entity(ir_type *owner, size_t pos, ir_type *type) return new_d_parameter_entity(owner, pos, type, NULL); } +ir_entity *new_d_label_entity(ir_label_t label, dbg_info *dbgi) +{ + ident *name = id_unique("label_%u"); + ir_type *global_type = get_glob_type(); + ir_entity *res + = intern_new_entity(global_type, IR_ENTITY_LABEL, name, firm_code_type, + dbgi); + res->attr.code_attr.label = label; + hook_new_entity(res); + return res; +} + +ir_entity *new_label_entity(ir_label_t label) +{ + return new_d_label_entity(label, NULL); +} + /** * Free entity attributes. * @@ -175,9 +196,9 @@ static void free_entity_attrs(ir_entity *ent) * multiple times */ ent->attr.cmpd_attr.val_paths = NULL; } - if (is_compound_entity(ent)) { + if (ent->entity_kind == IR_ENTITY_COMPOUND_MEMBER) { ent->attr.cmpd_attr.values = NULL; - } else if (is_method_entity(ent)) { + } else if (ent->entity_kind == IR_ENTITY_METHOD) { if (ent->attr.mtd_attr.param_access) { DEL_ARR_F(ent->attr.mtd_attr.param_access); ent->attr.mtd_attr.param_access = NULL; @@ -338,9 +359,22 @@ ir_type *(get_entity_type)(const ir_entity *ent) return _get_entity_type(ent); } -void (set_entity_type)(ir_entity *ent, ir_type *type) +void set_entity_type(ir_entity *ent, ir_type *type) { - _set_entity_type(ent, type); + switch (ent->entity_kind) { + case IR_ENTITY_METHOD: + assert(is_Method_type(type)); + break; + case IR_ENTITY_NORMAL: + assert(!is_Method_type(type)); + break; + case IR_ENTITY_LABEL: + assert(type == firm_code_type); + break; + case IR_ENTITY_COMPOUND_MEMBER: + break; + } + ent->type = type; } ir_volatility (get_entity_volatility)(const ir_entity *ent) @@ -399,11 +433,13 @@ const char *get_align_name(ir_align a) void set_entity_label(ir_entity *ent, ir_label_t label) { + assert(ent->entity_kind == IR_ENTITY_LABEL); ent->attr.code_attr.label = label; } ir_label_t get_entity_label(const ir_entity *ent) { + assert(ent->entity_kind == IR_ENTITY_LABEL); return ent->attr.code_attr.label; } diff --git a/ir/tr/entity_t.h b/ir/tr/entity_t.h index 3e7c44f93..fe33ade65 100644 --- a/ir/tr/entity_t.h +++ b/ir/tr/entity_t.h @@ -111,6 +111,13 @@ typedef struct parameter_ent_attr { lowering...) */ } parameter_ent_attr; +typedef enum ir_entity_kind { + IR_ENTITY_NORMAL, + IR_ENTITY_METHOD, + IR_ENTITY_COMPOUND_MEMBER, + IR_ENTITY_PARAMETER, + IR_ENTITY_LABEL, +} ir_entity_kind; /** * An abstract data type to represent program entities. @@ -124,6 +131,7 @@ struct ir_entity { ir_type *type; /**< The type of this entity */ ir_type *owner; /**< The compound type (e.g. class type) this entity belongs to. */ + unsigned entity_kind:3; /**< entity kind */ unsigned linkage:10; /**< Specifies linkage type */ unsigned volatility:1; /**< Specifies volatility of entities content.*/ unsigned aligned:1; /**< Specifies alignment of entities content. */ @@ -139,7 +147,6 @@ struct ir_entity { /**< If the entity is a bit field, this is the offset of the start of the bit field within the byte specified by offset. */ - unsigned is_parameter:1; /**< 1 if this represents a function parameter */ int offset; /**< Offset in bytes for this entity. Fixed when layout of owner is determined. */ unsigned alignment; /**< entity alignment in bytes */ @@ -177,6 +184,17 @@ void ir_init_entity(void); /** Cleanup entity module */ void ir_finish_entity(void); +/** + * Creates an entity corresponding to the start address of a basic block + * (the basic block is marked with a label id). + */ +ir_entity *new_label_entity(ir_label_t label); + +/** + * Like new_label_entity() but with debug information. + */ +ir_entity *new_d_label_entity(ir_label_t label, dbg_info *dbgi); + /* ----------------------- inline functions ------------------------ */ static inline int _is_entity(const void *thing) { @@ -233,12 +251,6 @@ static inline ir_type *_get_entity_type(const ir_entity *ent) return ent->type; } -static inline void _set_entity_type(ir_entity *ent, ir_type *type) -{ - assert(ent && ent->kind == k_entity); - ent->type = type; -} - static inline ir_linkage _get_entity_linkage(const ir_entity *ent) { assert(ent && ent->kind == k_entity); @@ -381,12 +393,12 @@ static inline int _entity_not_visited(const ir_entity *ent) static inline int _is_parameter_entity(const ir_entity *entity) { - return entity->is_parameter; + return entity->entity_kind == IR_ENTITY_PARAMETER; } static inline size_t _get_entity_parameter_number(const ir_entity *entity) { - assert(entity->is_parameter); + assert(entity->entity_kind == IR_ENTITY_PARAMETER); return entity->attr.parameter.number; } @@ -415,7 +427,6 @@ static inline void _set_entity_dbg_info(ir_entity *ent, dbg_info *db) #define set_entity_ld_ident(ent, ld_ident) _set_entity_ld_ident(ent, ld_ident) #define get_entity_ld_name(ent) _get_entity_ld_name(ent) #define get_entity_type(ent) _get_entity_type(ent) -#define set_entity_type(ent, type) _set_entity_type(ent, type) #define get_entity_linkage(ent) _get_entity_linkage(ent) #define get_entity_volatility(ent) _get_entity_volatility(ent) #define set_entity_volatility(ent, vol) _set_entity_volatility(ent, vol) diff --git a/ir/tr/type_t.h b/ir/tr/type_t.h index 013e82ba5..ba5f2a251 100644 --- a/ir/tr/type_t.h +++ b/ir/tr/type_t.h @@ -134,10 +134,11 @@ enum type_flags { tf_layout_fixed = 1U << 1, /**< Set if the layout of a type is fixed */ tf_frame_type = 1U << 2, /**< Set if this is a frame type. */ - tf_global_type = 1U << 3, /**< Set only for the global type */ - tf_tls_type = 1U << 4, /**< Set only for the tls type */ - tf_constructors = 1U << 5, /**< Set only for the constructors segment type */ - tf_destructors = 1U << 6, /**< Set only for the destructors segment type */ + tf_segment = 1U << 3, /**< type represents a linker segment */ + tf_global_type = 1U << 4, /**< Set only for the global type */ + tf_tls_type = 1U << 5, /**< Set only for the tls type */ + tf_constructors = 1U << 6, /**< Set only for the constructors segment type */ + tf_destructors = 1U << 7, /**< Set only for the destructors segment type */ }; ENUM_BITSET(type_flags) -- 2.20.1