Commit 3c0b6c43 by Daniel Berlin Committed by Daniel Berlin

tree.c (init_ttree): Add STRUCT_FIELD_TAG handling.

2006-02-15 Daniel Berlin  <dberlin@dberlin.org>

	* tree.c (init_ttree): Add STRUCT_FIELD_TAG handling.
	(tree_code_size): Ditto.
	* tree.h (struct tree_memory_tag): Remove parent_var.
	(struct tree_struct_field_tag): New.
	(SFT_OFFSET): New.
	(SFT_SIZE): New.
	(union tree_node): Add sft member.
	* tree-ssa-alias.c (get_tmt_for): Don't handle TYPE_READONLY
	specially here.
	(create_sft): Add size and offset argument, set SFT_OFFSET and
	SFT_SIZE.
	(create_overlap_variables_for): Update for SFT_OFFSET/SFT_SIZE.
	* treestruct.def: Add TS_STRUCT_FIELD_TAG.
	* tree-flow-inline.h (get_subvar_at): Update for
	SFT_OFFSET/SFT_SIZE.
	(var_can_have_subvars): Ditto.
	(overlap_subvar): Ditto.
	* print-tree.c (print_node): Print out interesting things for
	SFT's.
	* tree-flow.h (struct subvar): Remove offset and size members.
	* tree-ssa-operands.c (get_expr_operands): Update for
	get_indirect_ref_operands changes.
	(get_indirect_ref_operands): Call add_virtual_operand instead of
	add_stmt_operand.  Only recurse on base var if requested.
	(access_can_touch_variable): New function.
	(add_stmt_operand): Split virtual operand handling into ...
	(add_virtual_operand): Here.  Add offset, size, and for_clobber
	arguments.  Prune alias sets.
	(add_call_clobber_ops): Call add_virtual_operand.

From-SVN: r111120
parent cce283c7
2006-02-15 Daniel Berlin <dberlin@dberlin.org>
* tree.c (init_ttree): Add STRUCT_FIELD_TAG handling.
(tree_code_size): Ditto.
* tree.h (struct tree_memory_tag): Remove parent_var.
(struct tree_struct_field_tag): New.
(SFT_OFFSET): New.
(SFT_SIZE): New.
(union tree_node): Add sft member.
* tree-ssa-alias.c (get_tmt_for): Don't handle TYPE_READONLY
specially here.
(create_sft): Add size and offset argument, set SFT_OFFSET and
SFT_SIZE.
(create_overlap_variables_for): Update for SFT_OFFSET/SFT_SIZE.
* treestruct.def: Add TS_STRUCT_FIELD_TAG.
* tree-flow-inline.h (get_subvar_at): Update for
SFT_OFFSET/SFT_SIZE.
(var_can_have_subvars): Ditto.
(overlap_subvar): Ditto.
* print-tree.c (print_node): Print out interesting things for
SFT's.
* tree-flow.h (struct subvar): Remove offset and size members.
* tree-ssa-operands.c (get_expr_operands): Update for
get_indirect_ref_operands changes.
(get_indirect_ref_operands): Call add_virtual_operand instead of
add_stmt_operand. Only recurse on base var if requested.
(access_can_touch_variable): New function.
(add_stmt_operand): Split virtual operand handling into ...
(add_virtual_operand): Here. Add offset, size, and for_clobber
arguments. Prune alias sets.
(add_call_clobber_ops): Call add_virtual_operand.
2006-02-15 Jakub Jelinek <jakub@redhat.com> 2006-02-15 Jakub Jelinek <jakub@redhat.com>
PR middle-end/26300 PR middle-end/26300
......
...@@ -510,6 +510,15 @@ print_node (FILE *file, const char *prefix, tree node, int indent) ...@@ -510,6 +510,15 @@ print_node (FILE *file, const char *prefix, tree node, int indent)
&& DECL_HAS_VALUE_EXPR_P (node)) && DECL_HAS_VALUE_EXPR_P (node))
print_node (file, "value-expr", DECL_VALUE_EXPR (node), indent + 4); print_node (file, "value-expr", DECL_VALUE_EXPR (node), indent + 4);
if (TREE_CODE (node) == STRUCT_FIELD_TAG)
{
fprintf (file, " sft size " HOST_WIDE_INT_PRINT_DEC,
SFT_SIZE (node));
fprintf (file, " sft offset " HOST_WIDE_INT_PRINT_DEC,
SFT_OFFSET (node));
print_node_brief (file, "parent var", SFT_PARENT_VAR (node),
indent + 4);
}
/* Print the decl chain only if decl is at second level. */ /* Print the decl chain only if decl is at second level. */
if (indent == 4) if (indent == 4)
print_node (file, "chain", TREE_CHAIN (node), indent + 4); print_node (file, "chain", TREE_CHAIN (node), indent + 4);
......
...@@ -1450,7 +1450,7 @@ get_subvar_at (tree var, unsigned HOST_WIDE_INT offset) ...@@ -1450,7 +1450,7 @@ get_subvar_at (tree var, unsigned HOST_WIDE_INT offset)
subvar_t sv; subvar_t sv;
for (sv = get_subvars_for_var (var); sv; sv = sv->next) for (sv = get_subvars_for_var (var); sv; sv = sv->next)
if (sv->offset == offset) if (SFT_OFFSET (sv->var) == offset)
return sv->var; return sv->var;
return NULL_TREE; return NULL_TREE;
...@@ -1491,7 +1491,7 @@ var_can_have_subvars (tree v) ...@@ -1491,7 +1491,7 @@ var_can_have_subvars (tree v)
static inline bool static inline bool
overlap_subvar (unsigned HOST_WIDE_INT offset, unsigned HOST_WIDE_INT size, overlap_subvar (unsigned HOST_WIDE_INT offset, unsigned HOST_WIDE_INT size,
subvar_t sv, bool *exact) tree sv, bool *exact)
{ {
/* There are three possible cases of overlap. /* There are three possible cases of overlap.
1. We can have an exact overlap, like so: 1. We can have an exact overlap, like so:
...@@ -1511,17 +1511,19 @@ overlap_subvar (unsigned HOST_WIDE_INT offset, unsigned HOST_WIDE_INT size, ...@@ -1511,17 +1511,19 @@ overlap_subvar (unsigned HOST_WIDE_INT offset, unsigned HOST_WIDE_INT size,
if (exact) if (exact)
*exact = false; *exact = false;
if (offset == sv->offset && size == sv->size) if (offset == SFT_OFFSET (sv) && size == SFT_SIZE (sv))
{ {
if (exact) if (exact)
*exact = true; *exact = true;
return true; return true;
} }
else if (offset >= sv->offset && offset < (sv->offset + sv->size)) else if (offset >= SFT_OFFSET (sv)
&& offset < (SFT_OFFSET (sv) + SFT_SIZE (sv)))
{ {
return true; return true;
} }
else if (offset < sv->offset && (size > sv->offset - offset)) else if (offset < SFT_OFFSET (sv)
&& (size > SFT_OFFSET (sv) - offset))
{ {
return true; return true;
} }
......
...@@ -149,12 +149,6 @@ struct subvar GTY(()) ...@@ -149,12 +149,6 @@ struct subvar GTY(())
/* Fake variable. */ /* Fake variable. */
tree var; tree var;
/* Offset inside structure. */
unsigned HOST_WIDE_INT offset;
/* Size of the field. */
unsigned HOST_WIDE_INT size;
/* Next subvar for this structure. */ /* Next subvar for this structure. */
subvar_t next; subvar_t next;
}; };
...@@ -610,7 +604,7 @@ extern tree get_ref_base_and_extent (tree, HOST_WIDE_INT *, ...@@ -610,7 +604,7 @@ extern tree get_ref_base_and_extent (tree, HOST_WIDE_INT *,
static inline bool var_can_have_subvars (tree); static inline bool var_can_have_subvars (tree);
static inline bool overlap_subvar (unsigned HOST_WIDE_INT, static inline bool overlap_subvar (unsigned HOST_WIDE_INT,
unsigned HOST_WIDE_INT, unsigned HOST_WIDE_INT,
subvar_t, bool *); tree, bool *);
/* Call-back function for walk_use_def_chains(). At each reaching /* Call-back function for walk_use_def_chains(). At each reaching
definition, a function with this prototype is called. */ definition, a function with this prototype is called. */
......
...@@ -2061,8 +2061,7 @@ get_tmt_for (tree ptr, struct alias_info *ai) ...@@ -2061,8 +2061,7 @@ get_tmt_for (tree ptr, struct alias_info *ai)
{ {
struct alias_map_d *curr = ai->pointers[i]; struct alias_map_d *curr = ai->pointers[i];
tree curr_tag = var_ann (curr->var)->type_mem_tag; tree curr_tag = var_ann (curr->var)->type_mem_tag;
if (tag_set == curr->set if (tag_set == curr->set)
&& TYPE_READONLY (tag_type) == TYPE_READONLY (TREE_TYPE (curr_tag)))
{ {
tag = curr_tag; tag = curr_tag;
break; break;
...@@ -2099,10 +2098,6 @@ get_tmt_for (tree ptr, struct alias_info *ai) ...@@ -2099,10 +2098,6 @@ get_tmt_for (tree ptr, struct alias_info *ai)
pointed-to type. */ pointed-to type. */
gcc_assert (tag_set == get_alias_set (tag)); gcc_assert (tag_set == get_alias_set (tag));
/* If PTR's pointed-to type is read-only, then TAG's type must also
be read-only. */
gcc_assert (TYPE_READONLY (tag_type) == TYPE_READONLY (TREE_TYPE (tag)));
return tag; return tag;
} }
...@@ -2749,11 +2744,12 @@ get_or_create_used_part_for (size_t uid) ...@@ -2749,11 +2744,12 @@ get_or_create_used_part_for (size_t uid)
} }
/* Create and return a structure sub-variable for field type FIELD of /* Create and return a structure sub-variable for field type FIELD at
variable VAR. */ offset OFFSET, with size SIZE, of variable VAR. */
static tree static tree
create_sft (tree var, tree field) create_sft (tree var, tree field, unsigned HOST_WIDE_INT offset,
unsigned HOST_WIDE_INT size)
{ {
var_ann_t ann; var_ann_t ann;
tree subvar = create_tag_raw (STRUCT_FIELD_TAG, field, "SFT"); tree subvar = create_tag_raw (STRUCT_FIELD_TAG, field, "SFT");
...@@ -2771,7 +2767,8 @@ create_sft (tree var, tree field) ...@@ -2771,7 +2767,8 @@ create_sft (tree var, tree field)
ann->type_mem_tag = NULL; ann->type_mem_tag = NULL;
add_referenced_tmp_var (subvar); add_referenced_tmp_var (subvar);
SFT_PARENT_VAR (subvar) = var; SFT_PARENT_VAR (subvar) = var;
SFT_OFFSET (subvar) = offset;
SFT_SIZE (subvar) = size;
return subvar; return subvar;
} }
...@@ -2882,19 +2879,17 @@ create_overlap_variables_for (tree var) ...@@ -2882,19 +2879,17 @@ create_overlap_variables_for (tree var)
&& currfotype == lastfotype)) && currfotype == lastfotype))
continue; continue;
sv = GGC_NEW (struct subvar); sv = GGC_NEW (struct subvar);
sv->offset = fo->offset;
sv->size = fosize;
sv->next = *subvars; sv->next = *subvars;
sv->var = create_sft (var, fo->type); sv->var = create_sft (var, fo->type, fo->offset, fosize);
if (dump_file) if (dump_file)
{ {
fprintf (dump_file, "structure field tag %s created for var %s", fprintf (dump_file, "structure field tag %s created for var %s",
get_name (sv->var), get_name (var)); get_name (sv->var), get_name (var));
fprintf (dump_file, " offset " HOST_WIDE_INT_PRINT_DEC, fprintf (dump_file, " offset " HOST_WIDE_INT_PRINT_DEC,
sv->offset); SFT_OFFSET (sv->var));
fprintf (dump_file, " size " HOST_WIDE_INT_PRINT_DEC, fprintf (dump_file, " size " HOST_WIDE_INT_PRINT_DEC,
sv->size); SFT_SIZE (sv->var));
fprintf (dump_file, "\n"); fprintf (dump_file, "\n");
} }
......
...@@ -276,6 +276,8 @@ init_ttree (void) ...@@ -276,6 +276,8 @@ init_ttree (void)
tree_contains_struct[NAME_MEMORY_TAG][TS_MEMORY_TAG] = 1; tree_contains_struct[NAME_MEMORY_TAG][TS_MEMORY_TAG] = 1;
tree_contains_struct[TYPE_MEMORY_TAG][TS_MEMORY_TAG] = 1; tree_contains_struct[TYPE_MEMORY_TAG][TS_MEMORY_TAG] = 1;
tree_contains_struct[STRUCT_FIELD_TAG][TS_STRUCT_FIELD_TAG] = 1;
tree_contains_struct[VAR_DECL][TS_DECL_WITH_VIS] = 1; tree_contains_struct[VAR_DECL][TS_DECL_WITH_VIS] = 1;
tree_contains_struct[FUNCTION_DECL][TS_DECL_WITH_VIS] = 1; tree_contains_struct[FUNCTION_DECL][TS_DECL_WITH_VIS] = 1;
tree_contains_struct[TYPE_DECL][TS_DECL_WITH_VIS] = 1; tree_contains_struct[TYPE_DECL][TS_DECL_WITH_VIS] = 1;
...@@ -335,8 +337,9 @@ tree_code_size (enum tree_code code) ...@@ -335,8 +337,9 @@ tree_code_size (enum tree_code code)
return sizeof (struct tree_function_decl); return sizeof (struct tree_function_decl);
case NAME_MEMORY_TAG: case NAME_MEMORY_TAG:
case TYPE_MEMORY_TAG: case TYPE_MEMORY_TAG:
case STRUCT_FIELD_TAG:
return sizeof (struct tree_memory_tag); return sizeof (struct tree_memory_tag);
case STRUCT_FIELD_TAG:
return sizeof (struct tree_struct_field_tag);
default: default:
return sizeof (struct tree_decl_non_common); return sizeof (struct tree_decl_non_common);
} }
......
...@@ -2309,12 +2309,28 @@ struct tree_decl_minimal GTY(()) ...@@ -2309,12 +2309,28 @@ struct tree_decl_minimal GTY(())
struct tree_memory_tag GTY(()) struct tree_memory_tag GTY(())
{ {
struct tree_decl_minimal common; struct tree_decl_minimal common;
tree parent_var;
unsigned int is_global:1; unsigned int is_global:1;
}; };
#define MTAG_GLOBAL(NODE) (TREE_MEMORY_TAG_CHECK (NODE)->mtag.is_global) #define MTAG_GLOBAL(NODE) (TREE_MEMORY_TAG_CHECK (NODE)->mtag.is_global)
#define SFT_PARENT_VAR(NODE) (STRUCT_FIELD_TAG_CHECK (NODE)->mtag.parent_var)
struct tree_struct_field_tag GTY(())
{
struct tree_memory_tag common;
/* Parent variable. */
tree parent_var;
/* Offset inside structure. */
unsigned HOST_WIDE_INT offset;
/* Size of the field. */
unsigned HOST_WIDE_INT size;
};
#define SFT_PARENT_VAR(NODE) (STRUCT_FIELD_TAG_CHECK (NODE)->sft.parent_var)
#define SFT_OFFSET(NODE) (STRUCT_FIELD_TAG_CHECK (NODE)->sft.offset)
#define SFT_SIZE(NODE) (STRUCT_FIELD_TAG_CHECK (NODE)->sft.size)
/* For any sort of a ..._DECL node, this points to the original (abstract) /* For any sort of a ..._DECL node, this points to the original (abstract)
decl node which this decl is an instance of, or else it is NULL indicating decl node which this decl is an instance of, or else it is NULL indicating
...@@ -3124,6 +3140,7 @@ union tree_node GTY ((ptr_alias (union lang_tree_node), ...@@ -3124,6 +3140,7 @@ union tree_node GTY ((ptr_alias (union lang_tree_node),
struct tree_value_handle GTY ((tag ("TS_VALUE_HANDLE"))) value_handle; struct tree_value_handle GTY ((tag ("TS_VALUE_HANDLE"))) value_handle;
struct tree_constructor GTY ((tag ("TS_CONSTRUCTOR"))) constructor; struct tree_constructor GTY ((tag ("TS_CONSTRUCTOR"))) constructor;
struct tree_memory_tag GTY ((tag ("TS_MEMORY_TAG"))) mtag; struct tree_memory_tag GTY ((tag ("TS_MEMORY_TAG"))) mtag;
struct tree_struct_field_tag GTY ((tag ("TS_STRUCT_FIELD_TAG"))) sft;
struct tree_omp_clause GTY ((tag ("TS_OMP_CLAUSE"))) omp_clause; struct tree_omp_clause GTY ((tag ("TS_OMP_CLAUSE"))) omp_clause;
}; };
......
...@@ -60,4 +60,5 @@ DEFTREESTRUCT(TS_STATEMENT_LIST, "statement list") ...@@ -60,4 +60,5 @@ DEFTREESTRUCT(TS_STATEMENT_LIST, "statement list")
DEFTREESTRUCT(TS_VALUE_HANDLE, "value handle") DEFTREESTRUCT(TS_VALUE_HANDLE, "value handle")
DEFTREESTRUCT(TS_CONSTRUCTOR, "constructor") DEFTREESTRUCT(TS_CONSTRUCTOR, "constructor")
DEFTREESTRUCT(TS_MEMORY_TAG, "memory tag") DEFTREESTRUCT(TS_MEMORY_TAG, "memory tag")
DEFTREESTRUCT(TS_STRUCT_FIELD_TAG, "struct field tag")
DEFTREESTRUCT(TS_OMP_CLAUSE, "omp clause") DEFTREESTRUCT(TS_OMP_CLAUSE, "omp clause")
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment