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

Automatic code generation for only covered code?

awa5114
Beginner
662 Views

Does ifort support automatic code generation for only covered code for a particular run? I would like to hack a project down into smaller pieces that I most frequently used. For my current needs I only use maybe 10% percent of a particular code. It would be good to automate the generation of a reduced version that wouldn't include the remaining 90%....

0 Kudos
7 Replies
Steve_Lionel
Honored Contributor III
662 Views
No, there's not such an option. But I don't quite understand what you're trying to accomplish. Can you explain in more detail?
0 Kudos
awa5114
Beginner
662 Views

Lets say I have a program that uses 4 modules but only covers code from 2 of them for a particular run:

file: test.f90
program test 
use module1
use module2
use module3
use module4
call prinstuff1()
call prinstuff2()
end program test
file: module1.f90
module module1
contains
subroutine prinstuff1
print *, 'I am module 1'
end subroutine
end module
file: module2.f90
module module2
contains
subroutine prinstuff2
print *, 'I am module 2'
end subroutine
end module
file: module3.f90
module module3
contains
subroutine prinstuff3
print *, 'I am module 3'
end subroutine
end module
file: module4.f90
module module4
contains
subroutine prinstuff4
print *, 'I am module 4'
end subroutine
end module

The main program only calls routines from modules 1 and 2. After this kind of functionality I am seeking it would result in the following:

file:test_1.f90
program test 
use module1
use module2

call prinstuff1()
call prinstuff2()

end program test
file:module1_1.f90
module module1
contains
subroutine prinstuff1
print *, 'I am module 1'
end subroutine
end module
file:module2_1.f90
module module2
contains
subroutine prinstuff2
print *, 'I am module 2'
end subroutine
end module

Which is what I mean when I say "hack it down" into a smaller version of the same program. Anything remotely close to this in ifort? Short of copying and pasting covered code from a coverage run manually (which could take days)....

0 Kudos
gib
New Contributor II
662 Views

Why do you want to do this?

0 Kudos
FortranFan
Honored Contributor II
662 Views

What you might be interested in is automatic code refactoring: if so, you can look elsewhere for help, say starting here - https://en.wikipedia.org/wiki/Code_refactoring#Automated_code_refactoring

For the kind of code you show in Quote #3, I would strongly suggest TWO basic coding aspects as a starting point toward code refactorng:

  1. IMPLICIT NONE (TYPE, EXTERNAL) in all the applicable program scopes; this is a Fortran 201X (2015?) standard feature not yet supported by Intel Fortran but I hope it's high priority on their list.
  2. , ONLY : attribute on all USE statements

So the code will then appear:

module module1
   implicit none (type, external)
contains
   subroutine prinstuff1
      print *, 'I am module 1'
   end subroutine
end module

module module2
   implicit none (type, external)
contains
   subroutine prinstuff2
      print *, 'I am module 2'
   end subroutine
end module

And initially the test.f90 can be refactored to include IMPLICIT NONE (TYPE, EXTERNAL) as well as 'empty' USE <xx>, ONLY : statements:

program test
! Iteration 1 
   use module1, only :
   use module2, only :
   use module3, only :
   use module4, only :

   implicit none (type, external)

   call prinstuff1()
   call prinstuff2()

end program test

which will then lead to compilation errors along the lines of 

test.f90:31:17:
 call prinstuff1()
                 1
Error: Procedure 'prinstuff1' called at (1) is not explicitly declared
test.f90:32:17:
 call prinstuff2()
                 1
Error: Procedure 'prinstuff2' called at (1) is not explicitly declared

Coder can then easily fix the above with

program test

   use module1, only : prinstuff1
   use module2, only : prinstuff2
   use module3, only :
   use module4, only :

   implicit none (type, external)

   call prinstuff1()
   call prinstuff2()

end program test

leading to successful compilation.  Then the programmer can strip all the 'empty' USE statements to yield:

program test

   use module1, only : prinstuff1
   use module2, only : prinstuff2

   implicit none (type, external)

   call prinstuff1()
   call prinstuff2()

end program test

Clearly it can be painstaking to do such refactoring for large codes but it is feasible nonetheless.  But I personally doubt there are any tools that can automatically and reliably refactor the Fortran code like so, but readers can investigate and report here if they locate any.  Also, some bravhearts might be motivated to automate the above steps, good luck to them!

0 Kudos
jimdempseyatthecove
Honored Contributor III
662 Views

awa5114,

I agree with FortranFan that you should manually refactor the code (barring you locating a tool elsewhere).

Coding with a list of USE statements that encompass all available modules is bad practice and can get you into trouble in the event that your modules may come from different vendors and which may have the same entry point names and/or variable names.

I haven't used the empty ONLY clause. I prefer to simply comment out the USE statement(s) until all errors resolved. Then I remove the unnecessary ones.

Note, it may be confusing for the next code maintainer to have a USE statement referencing a missing module file.

Jim Dempsey

0 Kudos
awa5114
Beginner
662 Views

Thanks for your responses. It sounds like this is not such an easy task and might need additional investigation. @gib, I would like to do this because I have inherited a large, badly documented program that I need to work on. It uses a number of finite element routines to simulate solid and fluid mechanics problems. I only use the dynamic solid mechanics portion of the code to do dynamic simulation of buildings under hurricane loads, for example. I also use a couple of add-ons but this only amounts to about 10% of the code as I mentioned.

Also the code is so interrelated and the modules are quite dis-organized since the developers who created this code are not necessarily software engineers who know what they're doing. Mostly Fortran enthusiasts and amateurs. I need to basically dumb the code down to something restricted and manageable, suited to my own purposes. I would eventually like to simplify that dumbed down version and then apply the same to other parts of the code as needed.

 

 

0 Kudos
gib
New Contributor II
662 Views

OK, I understand.  It sounds to me like a lot a manual work.  Presumably you can identify modules that are obviously part of the fluid mechanics functionality, and remove them.  The complication would arise when these modules contain procedures that are used for the solid mechanics as well.  Compilation would reveal those missing procedures, which you'd then have to move to another module.  I can see that it could get complicated.

0 Kudos
Reply