re PR ipa/65334 (r221099 caused: FAIL: gfortran.fortran-torture/execute/in-pack.f90 execution, -O2 -ftree-vectorize -msse2)
PR ipa/65334 * cgraph.h (symtab_node): Add definition_alignment, can_increase_alignment_p and increase_alignment. * symtab.c (symtab_node::can_increase_alignment_p, increase_alignment_1, symtab_node::increase_alignment, symtab_node::definition_alignment): New. * tree-vect-data-refs.c (vect_can_force_dr_alignment_p): Use can_increase_alignment_p. * tree-vectorizer.c (increase_alignment): Use increase_alignment. * tree-vect-stmts.c (ensure_base_align): Likewise. From-SVN: r221268
This commit is contained in:
parent
fb460c3da0
commit
428f0c67ee
@ -1,3 +1,16 @@
|
||||
2015-03-05 Jan Hubicka <hubicka@ucw.cz>
|
||||
|
||||
PR ipa/65334
|
||||
* cgraph.h (symtab_node): Add definition_alignment,
|
||||
can_increase_alignment_p and increase_alignment.
|
||||
* symtab.c (symtab_node::can_increase_alignment_p,
|
||||
increase_alignment_1, symtab_node::increase_alignment,
|
||||
symtab_node::definition_alignment): New.
|
||||
* tree-vect-data-refs.c (vect_can_force_dr_alignment_p): Use
|
||||
can_increase_alignment_p.
|
||||
* tree-vectorizer.c (increase_alignment): Use increase_alignment.
|
||||
* tree-vect-stmts.c (ensure_base_align): Likewise.
|
||||
|
||||
2015-03-05 Jan Hubicka <hubicka@ucw.cz>
|
||||
|
||||
PR ipa/65316
|
||||
|
12
gcc/cgraph.h
12
gcc/cgraph.h
@ -289,6 +289,18 @@ public:
|
||||
/* Make DECL local. */
|
||||
void make_decl_local (void);
|
||||
|
||||
/* Return desired alignment of the definition. This is NOT alignment useful
|
||||
to access THIS, because THIS may be interposable and DECL_ALIGN should
|
||||
be used instead. It however must be guaranteed when output definition
|
||||
of THIS. */
|
||||
unsigned int definition_alignment ();
|
||||
|
||||
/* Return true if alignment can be increased. */
|
||||
bool can_increase_alignment_p ();
|
||||
|
||||
/* Increase alignment of symbol to ALIGN. */
|
||||
void increase_alignment (unsigned int align);
|
||||
|
||||
/* Return true if list contains an alias. */
|
||||
bool has_aliases_p (void);
|
||||
|
||||
|
96
gcc/symtab.c
96
gcc/symtab.c
@ -1908,3 +1908,99 @@ symtab_node::address_matters_p ()
|
||||
gcc_assert (!alias);
|
||||
return call_for_symbol_and_aliases (address_matters_1, NULL, true);
|
||||
}
|
||||
|
||||
/* Return ture if symbol's alignment may be increased. */
|
||||
|
||||
bool
|
||||
symtab_node::can_increase_alignment_p (void)
|
||||
{
|
||||
symtab_node *target = ultimate_alias_target ();
|
||||
|
||||
/* For now support only variables. */
|
||||
if (TREE_CODE (decl) != VAR_DECL)
|
||||
return false;
|
||||
|
||||
/* With -fno-toplevel-reorder we may have already output the constant. */
|
||||
if (TREE_ASM_WRITTEN (target->decl))
|
||||
return false;
|
||||
|
||||
/* Constant pool entries may be shared. */
|
||||
if (DECL_IN_CONSTANT_POOL (target->decl))
|
||||
return false;
|
||||
|
||||
/* We cannot change alignment of symbols that may bind to symbols
|
||||
in other translation unit that may contain a definition with lower
|
||||
alignment. */
|
||||
if (!decl_binds_to_current_def_p (decl))
|
||||
return false;
|
||||
|
||||
/* When compiling partition, be sure the symbol is not output by other
|
||||
partition. */
|
||||
if (flag_ltrans
|
||||
&& (target->in_other_partition
|
||||
|| target->get_partitioning_class () == SYMBOL_DUPLICATE))
|
||||
return false;
|
||||
|
||||
/* Do not override the alignment as specified by the ABI when the used
|
||||
attribute is set. */
|
||||
if (DECL_PRESERVE_P (decl) || DECL_PRESERVE_P (target->decl))
|
||||
return false;
|
||||
|
||||
/* Do not override explicit alignment set by the user when an explicit
|
||||
section name is also used. This is a common idiom used by many
|
||||
software projects. */
|
||||
if (DECL_SECTION_NAME (target->decl) != NULL && !target->implicit_section)
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/* Worker for symtab_node::increase_alignment. */
|
||||
|
||||
static bool
|
||||
increase_alignment_1 (symtab_node *n, void *v)
|
||||
{
|
||||
unsigned int align = (size_t)v;
|
||||
if (DECL_ALIGN (n->decl) < align
|
||||
&& n->can_increase_alignment_p ())
|
||||
{
|
||||
DECL_ALIGN (n->decl) = align;
|
||||
DECL_USER_ALIGN (n->decl) = 1;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/* Increase alignment of THIS to ALIGN. */
|
||||
|
||||
void
|
||||
symtab_node::increase_alignment (unsigned int align)
|
||||
{
|
||||
gcc_assert (can_increase_alignment_p () && align < MAX_OFILE_ALIGNMENT);
|
||||
ultimate_alias_target()->call_for_symbol_and_aliases (increase_alignment_1,
|
||||
(void *)(size_t) align,
|
||||
true);
|
||||
gcc_assert (DECL_ALIGN (decl) >= align);
|
||||
}
|
||||
|
||||
/* Helper for symtab_node::definition_alignment. */
|
||||
|
||||
static bool
|
||||
get_alignment_1 (symtab_node *n, void *v)
|
||||
{
|
||||
*((unsigned int *)v) = MAX (*((unsigned int *)v), DECL_ALIGN (n->decl));
|
||||
return false;
|
||||
}
|
||||
|
||||
/* Return desired alignment of the definition. This is NOT alignment useful
|
||||
to access THIS, because THIS may be interposable and DECL_ALIGN should
|
||||
be used instead. It however must be guaranteed when output definition
|
||||
of THIS. */
|
||||
|
||||
unsigned int
|
||||
symtab_node::definition_alignment ()
|
||||
{
|
||||
unsigned int align = 0;
|
||||
gcc_assert (!alias);
|
||||
call_for_symbol_and_aliases (get_alignment_1, &align, true);
|
||||
return align;
|
||||
}
|
||||
|
@ -5703,58 +5703,10 @@ vect_can_force_dr_alignment_p (const_tree decl, unsigned int alignment)
|
||||
if (TREE_CODE (decl) != VAR_DECL)
|
||||
return false;
|
||||
|
||||
/* With -fno-toplevel-reorder we may have already output the constant. */
|
||||
if (TREE_ASM_WRITTEN (decl))
|
||||
if (decl_in_symtab_p (decl)
|
||||
&& !symtab_node::get (decl)->can_increase_alignment_p ())
|
||||
return false;
|
||||
|
||||
/* Constant pool entries may be shared and not properly merged by LTO. */
|
||||
if (DECL_IN_CONSTANT_POOL (decl))
|
||||
return false;
|
||||
|
||||
if (TREE_PUBLIC (decl) || DECL_EXTERNAL (decl))
|
||||
{
|
||||
symtab_node *snode;
|
||||
|
||||
/* We cannot change alignment of symbols that may bind to symbols
|
||||
in other translation unit that may contain a definition with lower
|
||||
alignment. */
|
||||
if (!decl_binds_to_current_def_p (decl))
|
||||
return false;
|
||||
|
||||
/* When compiling partition, be sure the symbol is not output by other
|
||||
partition. */
|
||||
snode = symtab_node::get (decl);
|
||||
if (flag_ltrans
|
||||
&& (snode->in_other_partition
|
||||
|| snode->get_partitioning_class () == SYMBOL_DUPLICATE))
|
||||
return false;
|
||||
}
|
||||
|
||||
/* Do not override the alignment as specified by the ABI when the used
|
||||
attribute is set. */
|
||||
if (DECL_PRESERVE_P (decl))
|
||||
return false;
|
||||
|
||||
/* Do not override explicit alignment set by the user when an explicit
|
||||
section name is also used. This is a common idiom used by many
|
||||
software projects. */
|
||||
if (TREE_STATIC (decl)
|
||||
&& DECL_SECTION_NAME (decl) != NULL
|
||||
&& !symtab_node::get (decl)->implicit_section)
|
||||
return false;
|
||||
|
||||
/* If symbol is an alias, we need to check that target is OK. */
|
||||
if (TREE_STATIC (decl))
|
||||
{
|
||||
tree target = symtab_node::get (decl)->ultimate_alias_target ()->decl;
|
||||
if (target != decl)
|
||||
{
|
||||
if (DECL_PRESERVE_P (target))
|
||||
return false;
|
||||
decl = target;
|
||||
}
|
||||
}
|
||||
|
||||
if (TREE_STATIC (decl))
|
||||
return (alignment <= MAX_OFILE_ALIGNMENT);
|
||||
else
|
||||
|
@ -4956,8 +4956,13 @@ ensure_base_align (stmt_vec_info stmt_info, struct data_reference *dr)
|
||||
tree vectype = STMT_VINFO_VECTYPE (stmt_info);
|
||||
tree base_decl = ((dataref_aux *)dr->aux)->base_decl;
|
||||
|
||||
DECL_ALIGN (base_decl) = TYPE_ALIGN (vectype);
|
||||
DECL_USER_ALIGN (base_decl) = 1;
|
||||
if (decl_in_symtab_p (base_decl))
|
||||
symtab_node::get (base_decl)->increase_alignment (TYPE_ALIGN (vectype));
|
||||
else
|
||||
{
|
||||
DECL_ALIGN (base_decl) = TYPE_ALIGN (vectype);
|
||||
DECL_USER_ALIGN (base_decl) = 1;
|
||||
}
|
||||
((dataref_aux *)dr->aux)->base_misaligned = false;
|
||||
}
|
||||
}
|
||||
|
@ -719,14 +719,7 @@ increase_alignment (void)
|
||||
|
||||
if (vect_can_force_dr_alignment_p (decl, alignment))
|
||||
{
|
||||
DECL_ALIGN (decl) = TYPE_ALIGN (vectype);
|
||||
DECL_USER_ALIGN (decl) = 1;
|
||||
if (TREE_STATIC (decl))
|
||||
{
|
||||
tree target = symtab_node::get (decl)->ultimate_alias_target ()->decl;
|
||||
DECL_ALIGN (target) = TYPE_ALIGN (vectype);
|
||||
DECL_USER_ALIGN (target) = 1;
|
||||
}
|
||||
vnode->increase_alignment (TYPE_ALIGN (vectype));
|
||||
dump_printf (MSG_NOTE, "Increasing alignment of decl: ");
|
||||
dump_generic_expr (MSG_NOTE, TDF_SLIM, decl);
|
||||
dump_printf (MSG_NOTE, "\n");
|
||||
|
Loading…
Reference in New Issue
Block a user