mirror of
https://github.com/llvm/llvm-project.git
synced 2025-04-17 15:16:36 +00:00

This was a subtle problem. When the shape of a function result is explicit but not constant, it is characterized with bounds expressions that use Extremum<SubscriptInteger> operations to force extents to 0 rather than be negative. These Extremum operations are formatted as "max()" intrinsic functions in the module file. Upon being read from the module file, they are not folded back into Extremum operations, but remain as function references; and this then leads to expressions not comparing equal when the procedure characteristics are compared to those of a local procedure declared identically. The real fix here would be for folding to just always change max and min function references into Extremum<> operations, constant operands or not, and I tried that, but it lead to test failures and crashes in lowering that I couldn't resolve. So, until those can be fixed, here's a change that will read max/min operations in module file declarations back into Extremum operations to solve the compatibility checking problem, but leave other non-constant max/min operations as function calls.
36 lines
822 B
Fortran
36 lines
822 B
Fortran
!RUN: %flang_fc1 -fsyntax-only -J%S/Inputs %s
|
|
|
|
#if 0
|
|
!modfile67.mod was produced from this source, and must be read into this
|
|
!compilation from its module file in order to truly test this fix.
|
|
module modfile67
|
|
type t
|
|
procedure(foo), nopass, pointer :: p
|
|
end type
|
|
contains
|
|
pure function foo(n,a) result(r)
|
|
integer, intent(in) :: n
|
|
real, intent(in), dimension(n) :: a
|
|
logical, dimension(size(a)) :: r
|
|
r = .false.
|
|
end
|
|
type(t) function fooptr(f)
|
|
procedure(foo) f
|
|
fooptr%p => f
|
|
end
|
|
end
|
|
#endif
|
|
|
|
program test
|
|
use modfile67
|
|
type(t) x
|
|
x = fooptr(bar) ! ensure no bogus error about procedure incompatibility
|
|
contains
|
|
pure function bar(n,a) result(r)
|
|
integer, intent(in) :: n
|
|
real, intent(in), dimension(n) :: a
|
|
logical, dimension(size(a)) :: r
|
|
r = .false.
|
|
end
|
|
end
|