This is the mail archive of the
gcc-bugs@gcc.gnu.org
mailing list for the GCC project.
[Bug fortran/34686] New: Aliasing bug when returning character pointers
- From: "rsandifo at gcc dot gnu dot org" <gcc-bugzilla at gcc dot gnu dot org>
- To: gcc-bugs at gcc dot gnu dot org
- Date: 6 Jan 2008 12:23:26 -0000
- Subject: [Bug fortran/34686] New: Aliasing bug when returning character pointers
- Reply-to: gcc-bugzilla at gcc dot gnu dot org
char_pointer_func.f90 is failing at -O3 on mips-linux-gnu because
of an aliasing bug. We have a function sfoo() that returns a pointer
to a string of length 4:
function sfoo () result (sc1)
character*4, pointer :: sc1
allocate (sc1)
sc1 = "abcd"
end function sfoo
It gets the C prototype:
static void sfoo (character(kind=1)[1:4] * &, integer(kind=4));
However, the first caller is:
c1 = sfoo ()
and it passes a 0-based array, pstr.3:
{
character(kind=1)[4] * pstr.3;
sfoo (&pstr.3, 4);
__builtin_memmove ((void *) c1, (void *) pstr.3, 4);
}
So after inlining sfoo(), we get the following code at final_cleanup:
D.617 = (character(kind=1)[1:4] *) D.616;
*(character(kind=1)[1:4] * &) &pstr.3 = D.617;
__builtin_memcpy (D.617, &"abcd"[1]{lb: 1 sz: 1}, 4);
__builtin_memmove (c1, pstr.3, 4);
where __builtin_memcpy is small enough to open-code; we do not use a call.
The two pointer types ([4]-based and [1:4]-based) have different alias sets,
so in the failing case, we then schedule the read of pstr.3 before the
store to *(character(kind=1)[1:4] * &) &pstr.3.
The problem appears to be in this part of gfc_conv_function_call.
which deliberately ignores the bounds on the return value:
/* Pass the string length. */
type = gfc_get_character_type (ts.kind, ts.cl);
type = build_pointer_type (type);
/* Return an address to a char[0:len-1]* temporary for
character pointers. */
if (sym->attr.pointer || sym->attr.allocatable)
{
/* Build char[0:len-1] * pstr. */
tmp = fold_build2 (MINUS_EXPR, gfc_charlen_type_node, len,
build_int_cst (gfc_charlen_type_node, 1));
tmp = build_range_type (gfc_array_index_type,
gfc_index_zero_node, tmp);
tmp = build_array_type (gfc_character1_type_node, tmp);
var = gfc_create_var (build_pointer_type (tmp), "pstr");
/* Provide an address expression for the function arguments. */
var = build_fold_addr_expr (var);
}
else
var = gfc_conv_string_tmp (se, type, len);
(I believe TYPE is unused in the sym->attr.pointer || sym->attr.allocatable
case).
--
Summary: Aliasing bug when returning character pointers
Product: gcc
Version: 4.3.0
Status: UNCONFIRMED
Keywords: wrong-code
Severity: normal
Priority: P3
Component: fortran
AssignedTo: unassigned at gcc dot gnu dot org
ReportedBy: rsandifo at gcc dot gnu dot org
GCC target triplet: mips-linux-gnu
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=34686