re PR fortran/41212 (miscompilation at -O2)

PR fortran/41212
	* tree.h (struct tree_decl_common): Add decl_restricted_flag,
	shorten decl_common_unused.
	(DECL_RESTRICTED_P): New accessor.
	* tree-ssa-alias.c (ptr_deref_may_alias_decl_p): Use it
	to disambiguate marked decls and restrict pointers.

fortran/
	* trans.h (struct lang_type): Remove nontarget_type member.
	* trans.c (gfc_add_modify): Don't access it.
	* trans-decl.c (gfc_finish_var_decl): Don't allocate and set it,
	instead set DECL_RESTRICTED_P on affected decls.

testsuite/
	* gfortran.dg/pr41212.f90: New test.

From-SVN: r151761
This commit is contained in:
Michael Matz 2009-09-16 16:12:18 +00:00 committed by Michael Matz
parent 798763075f
commit 9b87db3c0f
9 changed files with 78 additions and 29 deletions

View File

@ -1,3 +1,12 @@
2009-09-16 Michael Matz <matz@suse.de>
PR fortran/41212
* tree.h (struct tree_decl_common): Add decl_restricted_flag,
shorten decl_common_unused.
(DECL_RESTRICTED_P): New accessor.
* tree-ssa-alias.c (ptr_deref_may_alias_decl_p): Use it
to disambiguate marked decls and restrict pointers.
2009-09-16 Richard Henderson <rth@redhat.com>
PR middle-end/41360

View File

@ -1,3 +1,11 @@
2009-09-16 Michael Matz <matz@suse.de>
PR fortran/41212
* trans.h (struct lang_type): Remove nontarget_type member.
* trans.c (gfc_add_modify): Don't access it.
* trans-decl.c (gfc_finish_var_decl): Don't allocate and set it,
instead set DECL_RESTRICTED_P on affected decls.
2009-09-14 Richard Henderson <rth@redhat.com>
* f95-lang.c (gfc_init_builtin_functions): Update call to

View File

@ -581,26 +581,8 @@ gfc_finish_var_decl (tree decl, gfc_symbol * sym)
if (!sym->attr.target
&& !sym->attr.pointer
&& !sym->attr.proc_pointer
/* For now, don't bother with aggregate types. We would need
to adjust DECL_CONTEXT of all field decls. */
&& !AGGREGATE_TYPE_P (TREE_TYPE (decl)))
{
tree type = TREE_TYPE (decl);
if (!TYPE_LANG_SPECIFIC (type))
TYPE_LANG_SPECIFIC (type) = (struct lang_type *)
ggc_alloc_cleared (sizeof (struct lang_type));
if (!TYPE_LANG_SPECIFIC (type)->nontarget_type)
{
alias_set_type set = new_alias_set ();
type = build_distinct_type_copy (type);
TYPE_ALIAS_SET (type) = set;
TYPE_LANG_SPECIFIC (type)->nontarget_type = type;
}
else
type = TYPE_LANG_SPECIFIC (type)->nontarget_type;
TREE_TYPE (decl) = type;
}
&& !sym->attr.proc_pointer)
DECL_RESTRICTED_P (decl) = 1;
}

View File

@ -162,13 +162,6 @@ gfc_add_modify (stmtblock_t * pblock, tree lhs, tree rhs)
tree t1, t2;
t1 = TREE_TYPE (rhs);
t2 = TREE_TYPE (lhs);
/* ??? This is actually backwards, we should test the "base" type
from which the nontarget_type was copied, but we don't have this
backlink. This will do for now, it's for checking anyway. */
if (TYPE_LANG_SPECIFIC (t1))
t1 = TYPE_LANG_SPECIFIC (t1)->nontarget_type;
if (TYPE_LANG_SPECIFIC (t2))
t2 = TYPE_LANG_SPECIFIC (t2)->nontarget_type;
/* Make sure that the types of the rhs and the lhs are the same
for scalar assignments. We should probably have something
similar for aggregates, but right now removing that check just

View File

@ -629,7 +629,6 @@ struct GTY(()) lang_type {
tree dataptr_type;
tree span;
tree base_decl[2];
tree nontarget_type;
};
struct GTY(()) lang_decl {

View File

@ -1,3 +1,8 @@
2009-09-16 Michael Matz <matz@suse.de>
PR fortran/41212
* gfortran.dg/pr41212.f90: New test.
2009-09-16 Eric Botcazou <ebotcazou@adacore.com>
* gnat.dg/alignment9.adb: New test.

View File

@ -0,0 +1,34 @@
! { dg-do run }
! { dg-options "-O2" }
program m
double precision :: y,z
call b(1.0d0,y,z)
if (ABS (z - 1.213) > 0.1) call abort
contains
subroutine b( x, y, z)
implicit none
double precision :: x,y,z
integer :: i, k
double precision :: h, r
y = 1.0d0
z = 0.0d0
h = 0
DO k = 1,10
h = h + 1.0d0/k
r = 1
DO i = 1,k
r = (x/(2*i) ) * r
END DO
y = y + (-1)**k * r
z = z + (-1)**(k+1) * h * r
IF ( ABS(2*k/x*r) < 1d-6 ) EXIT
END DO
z = 2*y
end subroutine b
end program m

View File

@ -208,6 +208,14 @@ ptr_deref_may_alias_decl_p (tree ptr, tree decl)
if (!pi)
return true;
/* If the decl can be used as a restrict tag and we have a restrict
pointer and that pointers points-to set doesn't contain this decl
then they can't alias. */
if (DECL_RESTRICTED_P (decl)
&& TYPE_RESTRICT (TREE_TYPE (ptr))
&& pi->pt.vars_contains_restrict)
return bitmap_bit_p (pi->pt.vars, DECL_UID (decl));
return pt_solution_includes (&pi->pt, decl);
}

View File

@ -1306,6 +1306,15 @@ extern void omp_clause_range_check_failed (const_tree, const char *, int,
(TREE_CHECK3 (NODE, VAR_DECL, PARM_DECL, \
RESULT_DECL)->decl_common.decl_by_reference_flag)
/* In a RESULT_DECL, PARM_DECL and VAR_DECL, means that this decl
can be used as restricted tag to disambiguate against other restrict
pointers. Used by fortran to capture something like non-addressability
(which it isn't really because the middle-end does take addresses of
such variables). */
#define DECL_RESTRICTED_P(NODE) \
(TREE_CHECK3 (NODE, VAR_DECL, PARM_DECL, \
RESULT_DECL)->decl_common.decl_restricted_flag)
/* In a CALL_EXPR, means that the call is the jump from a thunk to the
thunked-to function. */
#define CALL_FROM_THUNK_P(NODE) (CALL_EXPR_CHECK (NODE)->base.protected_flag)
@ -2646,8 +2655,10 @@ struct GTY(()) tree_decl_common {
unsigned gimple_reg_flag : 1;
/* In VAR_DECL, PARM_DECL and RESULT_DECL, this is DECL_BY_REFERENCE. */
unsigned decl_by_reference_flag : 1;
/* In VAR_DECL, PARM_DECL and RESULT_DECL, this is DECL_RESTRICTED_P. */
unsigned decl_restricted_flag : 1;
/* Padding so that 'off_align' can be on a 32-bit boundary. */
unsigned decl_common_unused : 4;
unsigned decl_common_unused : 3;
/* DECL_OFFSET_ALIGN, used only for FIELD_DECLs. */
unsigned int off_align : 8;