Intel® Fortran Compiler
Build applications that can scale for the future with optimized code designed for Intel® Xeon® and compatible processors.
28343 Discussions

IMPLICIT statement does not take TYPE for intrinsic types

New Contributor II
! 8.7      IMPLICIT statement
! 1 In a scoping unit, an IMPLICIT statement specifies a type, and possibly
!   type parameters, for all implicitly typed data entities whose names
!   begin with one of the letters specified in the statement. An IMPLICIT
!   NONE statement can indicate that no implicit typing rules are to apply
!   in a particular scoping unit, or that external and dummy procedures
!   need to be explicitly given the EXTERNAL attribute.
program testit
use, intrinsic :: iso_fortran_env, only : real_kinds,sp=>real32,dp=>real64,qp=>real128
implicit type(null) (a)
implicit type(real) (b)          ! <== OK in a declaration, error in IMPLICIT
implicit type(real(kind=qp)) (c) ! <== OK in a declaration, error in IMPLICIT
type null
end type null
! the syntax works for a declaration
type(real)          :: float_default
type(real(kind=sp)) :: float
type(real(kind=dp)) :: long
type(real(kind=qp)) :: quad
end program testit
1 Solution

Thank you, @ur, for reporting this. And thank you, @FortranFan, for the tiny reproducer!

GOOD NEWS! I tested with versions of ifx and ifort that will be available in the next few weeks. NO ERROR MESSAGE!

View solution in original post

0 Kudos
10 Replies
New Contributor II

I can use a user-defined type in an IMPLICIT statement but when I use TYPE for specifying an intrinsic type so I can add a KIND, so I can make the default be REAL128  or an INTEGER type not the default kind it does not take the statement, even though the syntax works in a declaration of a variable. From the standard I take it I should be able to specify a type and optional arguments for the type.


I see no other way I could make the default be all quad-precision reals with IMPLICIT statements otherwise.

0 Kudos
Honored Contributor II


You are running into two issues:

1. syntax errors with missing parenthesis in the right places,

2. compiler shortcomings with an outdated feature that likely ain't worth much of compiler developers' time any longer.

Here's a short example you can consider that I will claim conforms to the standard:

   use, intrinsic :: iso_fortran_env, only : WP => real128
   implicit type(real(kind=WP))( m )
   type(real(kind=WP)) :: r
   print *, "kind(myreal) = ", kind(myreal), "; expected is ", kind(r)

You will notice Intel Fortran and gfortran fail to process line 2 but I am sure the standard supports it.  The expected output with Intel Fortran will be (not including the leading blanks in the WRITE)

 kind(myreal) = 16 ; expected is 16

Intel Team,

Will you be open to reviewing the short reproducer here and submitting a bug fix request?



Valued Contributor III

Screenshot 2023-03-20 085646.png

The specific errors for those interested.  

0 Kudos
Black Belt

I agree with @FortranFan that IMPLICIT TYPE(REAL) (letters) is valid F2018. The syntax for a declaration-type-spec was extended to allow TYPE(implicit-type). This was apparently overlooked in processing of the IMPLICIT statement.

In @ur 's example, IMPLICIT by itself is not allowed.

I'll comment that there's a proposal for a future revision of the standard to provide syntax that changes what "default kind" means, allowing you, for example, to make default real be double precision. This is analogous to popular compiler options such as -r8 or /real_size.

New Contributor II

I cleaned the example up; I was trying to retype a few lines from a working example where the syntax was correct as pasting and other features were not working reasonably and introduced the typos.  IMPLICIT typing is out of fashion and I rarely use it although I never had any trouble with the old default, but several people just recently were asking for a portable way to not depend on switches such as -r 8 but minimally change the code at this point, which is old code heavily using implicit typing.  IMPLICIT DOUBLEPRECISION(A-H,O-Z) seemed like a reasonable starting point but wanting an option for quad precision brought up this issue.  With LFortran emphasizing wanting to support interactive Fortran I suspect some opponents of anything but IMPLICIT NONE may rediscover implicit typing.


My personal interest in it was looking at some way to set the default for constants, including something equivalent to IMPLICIT NONE for constants so constants would all require a kind or have to be specified with named parameter constants, and toying with the IMPLICIT statement being extended to apply to constants as well as named variables.


In general I find it very useful for all Fortran compilers to support all of the standard so time working on portability issues is minimized so I would advocate for a fix even if I might not use it much myself in code, as if it works anywhere sooner or later I will probably have to kludge around it to compile the code with ifort/ifx so even dusty corners being made to support the standard has always been valuable to me.


Thanks for everyone's input; particularly in conforming it is standard-compliant.



0 Kudos
Honored Contributor II

@ur wrote:


Thanks for everyone's input; particularly in conforming it is standard-compliant.



Re: "particularly in conforming it is standard-compliant," not sure what you mean by this - the code in your original post does not conform in many ways.

Separately, note that trying to build on the existing semantics about IMPLICIT statement toward "looking at some way to set the default for constants" is a bad, bad, bad idea, you can be 100% sure it will do more harm than good.  If that's your intent, no one can stop you from proceeding along such lines of course, but one can only hope it does not get into the official standard some day.


0 Kudos
Black Belt

FWIW for default quad precision you can use the compiler option /real-size:128


However this will not be portable.

In the long term, it will be better to define your preferred kind, then explicitly use real(YourKind)

module mod_kinds
  integer, parameter :: sp = kind(1.0)
  integer, parameter :: dp = selected_real_kind(2*precision(1.0_sp))
  integer, parameter :: qp = selected_real_kind(2*precision(1.0_dp)) 
end module mod_kinds

You will (may) still have issues in the literal real numbers, without kind suffix, will be treated as single precision.

Do not assume the literal takes on the kind of where the result is placed.


Jim Dempsey



0 Kudos

Thank you, @ur, for reporting this. And thank you, @FortranFan, for the tiny reproducer!

GOOD NEWS! I tested with versions of ifx and ifort that will be available in the next few weeks. NO ERROR MESSAGE!

0 Kudos

I just confirmed that there is no error message using the Intel Fortran compilers that were released this week as part of oneAPI HPC Toolkit 2023.1.

Please try it!

New Contributor II

Worked with the new versions of ifort and ifx. Thanks for such a responsive resolution!




urbanjs@mercury:/tmp$ ifx --version
ifx (IFX) 2023.1.0 20230320
Copyright (C) 1985-2023 Intel Corporation. All rights reserved.

urbanjs@mercury:/tmp$ ifort --version
ifort (IFORT) 2021.9.0 20230302
Copyright (C) 1985-2023 Intel Corporation. All rights reserved.

0 Kudos