Я работаю над большим кодом на Фортране, состоящим из нескольких модулей и использующим функции ООП. Я сталкиваюсь с ошибкой при компиляции этого кода с версиями gfortran с 7 по 9.
- Ниже приведен минимальный рабочий пример для воспроизведения ошибки. Его можно сохранить как
test.f95
и скомпилировать с помощью gfortran -fcheck=all -c test.f95
. - Ошибка запускается, когда
-fcheck=all
передается компилятору. - Ошибка появляется с gfortran 7, 8 и9, но не с предыдущими версиями (протестировано с gfortran 5 и 6). См. Выходные данные компилятора.
- Я использую Ubuntu 18.04.3 LTS, 4.15.0-65-generic x86_64
Может кто-нибудь попытаться воспроизвести и подтвердить эту ошибку? Я посмотрел на различные системы отслеживания ошибок, но не смог найти ничего похожего. Я еще не сообщал об этом и хотел бы убедиться, что о нем стоит сообщить, прежде чем сделать это.
Кроме того, есть ли способ обойти эту ошибку компилятора?
Минимальный рабочий пример:
module buggy
implicit none
type :: par
contains
procedure, public :: fun => fun_par
end type par
type comp
class(par), allocatable :: p
end type comp
type foo
type(comp), allocatable :: m(:)
contains
procedure, public :: init => init_foo
procedure, public :: update => update_foo
end type foo
contains
function fun_par(this, x) result(y)
implicit none
class(par) :: this
integer, intent(in) :: x(:)
integer :: y(size(x))
end function fun_par
subroutine init_foo(this, n)
implicit none
class(foo) :: this
integer, intent(in) :: n
integer :: k
allocate(this%m(n))
do k = 1, n
allocate(par :: this%m(k)%p)
end do
end subroutine init_foo
subroutine update_foo(this, x)
implicit none
class(foo) :: this
integer, intent(in) :: x(:)
integer :: k
do k = 1, size(this%m)
write(*,*) this%m(k)%p%fun(x)
end do
end subroutine update_foo
end module buggy
Несколько замечаний из проб и ошибок:
- В определении
foo
та же ошибка возникает, если m
задается как вектор фиксированной длины (например, type(comp) :: m(10)
). allocatable
здесь не является виновником. - Определение
p
в comp
с использованием type(par)
вместо class(par)
не вызывает ошибку. Но мне нужно, чтобы p
был полиморфным в моем коде. - Та же ошибка, когда
p
указан как указатель вместо выделяемого вектора. - Размерность результата
y
в fun_par()
кажется проблематичным: например, когда речь идет о скаляре (y
вместо y(size(x))
), ошибка не срабатывает.
Компиляторсообщения об ошибках
с gfortran 9.2.1:
$ /usr/bin/gfortran-9 -fcheck=all -c test.f95
test.f95:50:0:
50 | write(*,*) this%m(k)%p%fun(x)
|
internal compiler error: in gfc_conv_procedure_call, at fortran/trans-expr.c:6785
Please submit a full bug report,
with preprocessed source if appropriate.
See <file:///usr/share/doc/gcc-9/README.Bugs> for instructions.
с gfortran 8.3.0:
$ /usr/bin/gfortran-8 -fcheck=all -c test.f95
test.f95:50:0:
write(*,*) this%m(k)%p%fun(x)
internal compiler error: in gfc_conv_procedure_call, at fortran/trans-expr.c:6410
Please submit a full bug report,
with preprocessed source if appropriate.
See <file:///usr/share/doc/gcc-8/README.Bugs> for instructions.
с gfortran 7.4.0:
$ /usr/bin/gfortran-7 -fcheck=all -c test.f95
test.f95:50:0:
write(*,*) this%m(k)%p%fun(x)
internal compiler error: in gfc_conv_procedure_call, at fortran/trans-expr.c:6290
Please submit a full bug report,
with preprocessed source if appropriate.
See <file:///usr/share/doc/gcc-7/README.Bugs> for instructions.
с gfortran 6.5.0 и gfortran 5.5.0: без ошибок.