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

            Bug ID: 89219
           Summary: [gfortran 7.3] compiler throws internal compiler
                    error: segmentation fault
           Product: gcc
           Version: 7.3.0
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: fortran
          Assignee: unassigned at gcc dot gnu.org
          Reporter: cih_dmc at yahoo dot com.mx
  Target Milestone: ---

Created attachment 45615
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=45615&action=edit
simplied version

This internal compiler error seems to occur when a fuction returns a class
pointer of a derived type directly in a user defined i/o procedure

$gfortran main.f90

compiler output:

main.f90:88:0:

     print*, l%get()

internal compiler error: Segmentation fault
Please submit a full bug report,
with preprocessed source if appropriate.
See <file:///usr/share/doc/gcc-7/README.Bugs> for instructions.

here a simplified version of the code

module Test
  implicit none

    type :: Parent
      contains
        procedure :: toString
        procedure :: wio
        generic :: write(formatted) => wio
    end type

    type, extends(Parent) :: Child1
        real :: x = 0
      contains
        procedure :: toString => toString1
    end type

    type, extends(Parent) :: Child2
        class(Parent), pointer :: p => null()
      contains
        procedure :: set
        procedure :: get
        procedure :: toString => toString2
    end type

  contains
    subroutine set(this, o)
        class(Child2), intent(inout) :: this
        class(*), intent(in), target :: o

        select type(o)
            type is (real)
                allocate(this%p, source=Child1(o))
            class is (Parent)
                this%p => o
            class default
                stop "unknown type"
        end select
    end subroutine

    function get(this) result(p)
        class(Child2), intent(in) :: this
        class(Parent), pointer :: p

        p => this%p
    end function

    function toString1(this) result(str)
        class(Child1), intent(in) :: this
        character(50) :: str
        write(str, *) this%x
    end function

    function toString2(this) result(str)
        class(Child2), intent(in) :: this
        character(50) :: str
        str = "child2"
    end function

    function toString(this) result(str)
        class(Parent), intent(in) :: this
        character(50) :: str
        write(str, *) loc(this)
    end function

    subroutine wio(this, unit, iotype, v_list, iostat, iomsg)
        class(Parent), intent(in) :: this
        integer, intent(in) :: unit
        character(*), intent(in) :: iotype
        integer, intent(in) :: v_list(:)
        integer, intent(out) :: iostat
        character(*), intent(inout) :: iomsg

        write(unit, fmt=*, iostat=iostat, iomsg=iomsg) this%toString()
    end subroutine
end module

program main
use Test
  implicit none

    type(Child2) :: l
    class(Parent), pointer :: pch1 => null()

    call l%set(234434.)

    !print*, l%get() ! in this way doesn't work, throws internal compile error

    pch1 => l%get() !!!!!!!!!!!!!!!!!!!!!!!!
    print*, pch1    ! in this way compiles !

end program

Reply via email to