Fortran generic warnings containing procedures whose dummy argument is an unbounded polymorphic pointer
I wrote a generic interface that contains three module procedures
module MTest
implicit none
interface Mesh
module procedure :: MeshG,MeshR,Meshc
end interface Mesh
contains
logical function MeshR(IVal)
real(4),intent(in) :: IVal
MeshR=.true.
end function MeshR
logical function MeshC(IVal)
complex(4),intent(in) :: IVal
MeshC=.true.
end function MeshC
logical function MeshG(IVal)
class(*),pointer,intent(in) :: IVal
MeshG=.false.
end function MeshG
end module MTest
program main
use MTest
implicit none
real(4) :: a
write(*,*) Mesh(a)
end program main
when i compile it with ifort the compiler gives me two warings:
Test.f90 (8): Warning # 6738: The type / rank / keyword signature for this particular procedure matches another specific procedure that uses the same common name. [MESHR]
logical function MeshR(IVal)
--------------------- ^
Test.f90 (13): Warning # 6738: The type / rank / keyword signature for this particular procedure matches another specific procedure that uses the same common name. [MESHC]
logical function MeshC(IVal)
--------------------- ^
Since we cannot pass specific data, such as real or complex, to an unbounded polymorphological pointer in a function or procedure call, I don't quite understand why the compiler is giving me such warings. However, it looks like these warnings will not cause any problems in my simple test program. So can someone please explain to me what is happening with these wars and can they cause serious problems in some specific cases? Many thanks.
source to share
(Editing the material did the following because I forgot about the limitation in F2008 12.5.2.5p2.)
The rules for choosing the appropriate particular procedure for a generic reference do not take into account the current pointer constraints and assigned dummy arguments that require matching in the declared type.
In Fortran 2003, the rules do not even consider the attributed or pointed attribute of a dummy argument. The choice of a particular procedure in F2003 is based on the number, name and type + kind + rank of the actual arguments.
Hence, in terms of choosing a particular procedure - since an unbounded polymorphic object is compatible with anything with anything, there is ambiguity in determining which particular procedure should be chosen to reference, where the actual argument is real (4) or complex (4) ...
Compilers should diagnose this ambiguity when ever extending the interface (i.e., how the interface is declared), even if yours, even if your actual use of the interface is not ambiguous.
(The rules requiring an intent pointer (in) or an allocatable argument to match the declared type for polymorphic arguments are also more restrictive than they should be. If they were relaxed in future versions, then an ambiguous call would certainly be possible. an argument more restrictive than usual leaves the possibility of backward compatible language changes in the future.)
source to share
According to the f2003 standard:
A non-polymorphic object is only compatible with objects of the same declared type. A polymorphic object that is not an unrestricted polymorphic object is a type that is compatible with objects of the same declared type, or any extension thereof. Although an unconstrained polymorphic object is not considered a declared type, it is compatible with all objects . An entity is said to be type-compatible if it is compatible with objects of that type
so the interface cannot be resolved (gfortran returns an error at this point). And therefore, an unlimited polymorphic can be of any type, including real.
In the following code, you can see an example where the variable CLASS(*), pointer
is of real type
module mod1
implicit none
contains
function fun1(x)
real,target :: x
class(*), pointer ::fun1
fun1 => x
end function
function fun2(IVal)
class(*),pointer,intent(in) :: IVal
logical fun2
fun2=.false.
select type(IVal)
type is (real)
print*, 'type is real'
fun2 = .true.
end select
end function fun2
end module mod1
program main
use mod1
implicit none
real :: a
write(*,*) fun2(fun1(a))
end program main
returns:
type is real
T
source to share