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

PRIVATE and cascading USE

Hervé_Martin
Beginner
456 Views

Hello,

I have stumbled about a non intuitive (at least for me) feature fo the Intel Compiler (2016 and 2017) which I am not sure is standard compliant or not.

If I have a type TT defined (as public) in a module M1, and that I do a USE M1 in a module M2, the type is then visible and useable in the module M2. This is clear to me. But if the module M2 does not use the PRIVATE keyword, using of M2 seems also to imply USE M1. Is it a behavior documented in the standard?

Here some simple code showing what I mean:

program Console
  use m2
  implicit none
  type(TT) :: var ! Why can I use TT without a USE m1 ???
  print *, 'Hello World'
end program

module m2
  use m1
  implicit none
  ! module is public
end module
  
module m1
  implicit none
  private
  type, public :: tt
  end type
end module
  

 

0 Kudos
1 Solution
Steven_L_Intel1
Employee
456 Views

When one module USEs another, all public entities of the USEd module become entities of the USEing module. If the default accessibility of that is PUBLIC, then all those use-inherited entities will also be PUBLIC. This is a fundamental aspect of Fortran and one that many applications depend on.

View solution in original post

0 Kudos
7 Replies
Arjen_Markus
Honored Contributor I
456 Views

Yes, PUBLIC is the default. If you do not want that, you should use either the PRIVATE statement or PRIVATE attributes.

0 Kudos
Hervé_Martin
Beginner
456 Views

Thanks for your answer, I know that PUBLIC is the default. My question was specific to the recursion of USE statements: is it standard compliant that PUBLIC means also that USE is propagated? I thought that in order to use a public type in a subprogram, I had to make explicitely a USE of the module in which it is defined. Apparently you can also implicity use a type by using another module which is public.

0 Kudos
Arjen_Markus
Honored Contributor I
456 Views

As far as I know it is standard-compliant. I have never seen it handled differently. It means that you use modules to bundle certain facilities and exclude unwanted ones without having to specify the exact list that you want in each and every program unit that uses them. (I have seen program code where there was a long list of all the modules that were used - just creating an overall module would have reduced such lists enormously)

0 Kudos
Steven_L_Intel1
Employee
457 Views

When one module USEs another, all public entities of the USEd module become entities of the USEing module. If the default accessibility of that is PUBLIC, then all those use-inherited entities will also be PUBLIC. This is a fundamental aspect of Fortran and one that many applications depend on.

0 Kudos
Hervé_Martin
Beginner
456 Views

Ok, that settles it then. I did not think it was the case, but it means than Fortran USEs behave a lot like an INCLUDE. What would be really nice would be the ability to specify that entities imported from a certain module should stay private to the USEing module...

0 Kudos
Arjen_Markus
Honored Contributor I
456 Views

There is: just use the PRIVATE statement and make only those entities PUBLIC that you want to be public. There is no difference in that respect for entities defined in the module itself or entities that were imported into that module via USE statements.

0 Kudos
andrew_4619
Honored Contributor II
456 Views

If you want more namespace clarity the USE xxxx, ONLY: A,B,C syntax is helpful....

0 Kudos
Reply