https://gcc.gnu.org/bugzilla/show_bug.cgi?id=93918

            Bug ID: 93918
           Summary: Segfault with -Ofast when calling a routine with an
                    array argument array(:)%component
           Product: gcc
           Version: 9.1.1
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: fortran
          Assignee: unassigned at gcc dot gnu.org
          Reporter: mscfd at gmx dot net
  Target Milestone: ---

The code below results in a SEGFAULT when compiled with -Ofast in gfortran
9.1.1 as well as some recent compiled gfortran-10 commit. With -O2 the program
finishes without errors (also no reports from valgrind).

The segfault only occurs, if the array size is sufficiently large (reducing n
by a factor of 10 avoids the problem). valgrind reports a stack problem:

==28808== Warning: client switching stacks?  SP change: 0x1ffeffea70 -->
0x1ffc9d9070
==28808==          to suppress, use: --max-stackframe=40000000 or greater
==28808== Invalid write of size 8
==28808==    at 0x400818: ppp (ppp.f90:31)
==28808==    by 0x400818: main (ppp.f90:19)
==28808==  Address 0x1ffc9d9068 is on thread 1's stack
==28808== 
==28808== Can't extend stack to 0x1ffc9d8118 during signal delivery for thread
1:
==28808==   no stack segment
==28808== 
==28808== Process terminating with default action of signal 11 (SIGSEGV):
dumping core
==28808==  Access not within mapped region at address 0x1FFC9D8118
==28808==    at 0x400818: ppp (ppp.f90:31)
==28808==    by 0x400818: main (ppp.f90:19)
==28808==  If you believe this happened as a result of a stack
==28808==  overflow in your program's main thread (unlikely but
==28808==  possible), you can try to increase the size of the
==28808==  main thread stack using the --main-stacksize= flag.
==28808==  The main thread stack size used in this run was 8388608.
==28808== Invalid write of size 8
==28808==    at 0x4A2861A: _vgnU_freeres (vg_preloaded.c:59)
==28808==  Address 0x1ffc9d8fe0 is on thread 1's stack

Also increasing stacksize as suggested by valgrind also avoids the invalid
write. Does gfortran generate a temporary array here (but only with -Ofast)?


module mod

implicit none
private
public foo

contains

subroutine foo(a, n)
   integer, dimension(:), intent(in) :: a
   integer, intent(in) :: n
   print *, sum(a(1:n)), n
end subroutine foo

end module mod


program ppp
use mod
implicit none

type :: tt
   integer :: u = 1
end type tt

type(tt), dimension(:), allocatable :: r
integer :: n

n = 10000000
allocate(r(1:n))
call foo(r(:)%u, n)
deallocate(r)

end program ppp

Reply via email to