CFD Online Logo CFD Online URL
www.cfd-online.com
[Sponsors]
Home > Forums > OpenFOAM Programming & Development

How to interface a Fortran thermodynamic tool with OpenFOAM?

Register Blogs Members List Search Today's Posts Mark Forums Read

Like Tree4Likes

Reply
 
LinkBack Thread Tools Display Modes
Old   March 9, 2011, 14:45
Default mixing Fortran with OpenFOAM, Towards to a unified solution
  #21
New Member
 
Evren
Join Date: Mar 2010
Posts: 20
Rep Power: 7
pbe_cfd is on a distinguished road


So, I came up with a solution to my prototype problem. Calling an external Fortran90 subroutine from an OpenFoam application.

STEPS
1) Declare an interface C function in the main file or in .H file and include it

extern "C"
{
void fortfunc_(int *ii, double *ff); // underscore is important (gfortran linux)!
}

When mixing Fortran with C++, name mangling must be prevented. You may use "objdump -t <file>" file: object or library files. In this example the subroutine named as fortfunc in the Fortran 90 code. But it's referred as fortfunc_

2) Compile your Fortran code and obtain object files "*.o". You may link the object files or you may create a static library form object files as follows,

ar rc myPbeLib.a fortfunc.o other.o object.o files.o // specific to Linux system

3) In your solver folder Make/options append -lgfortran (runtime fortran libraries) and your object or library files. If your fortran subroutine call some other routines from other libraries, add them as well. (Last case is not tested. )

EXE_LIBS = -lfiniteVolume\
-lgfortran\
$(FOAM_USER_LIBBIN)/fortfunc.o

4) Build your executable with wmake in solver folder.

This approach worked for my prototype problem. However I don't know if this is the best way, most probably NOT. Cyp's suggestion sounds really cool. But, I had a problem with obtaining the shared object files (*.so). I had done it before for a C++ code for boundary conditions. There it had worked very nicely. But with Fortran code I had problems. It doesn't compile the fortran code. If someone can describe how to obtain shared object files for Fortran codes, it will be really cool. Then, we can close this thread with a happy end ;-)

All the best;
Evren
mm.abdollahzadeh and hz283 like this.
pbe_cfd is offline   Reply With Quote

Old   May 6, 2011, 13:46
Arrow
  #22
New Member
 
Nicolas
Join Date: May 2011
Posts: 4
Rep Power: 6
Nicolas Périnet is on a distinguished road
Dear all,

I have posted in this thread because it is the closest to the topic of my problem.

I want to code a Hookstep-Newton-Krylov algorithm to find peculiar solutions of the flow with some symmetry properties in a rotating annulus. This algorithm involves OpenFOAM for solving Navier-Stokes equations and additional routines in FORTRAN 90, especially from linear algebra libraries.

I have created a main program in C++ which calls the fortran fsubroutines (here a test case nothing.h. Some of these fortran subroutines call OpenFOAM. I am trying to make interact the main program with the fortran subroutines and OpenFOAM.

I have made a test case where:
-the main program is "icoDHRAFoamEssai.C"
-it calls the fortran function "nothing in "nothing.f90"
-which calls at its turn "integration" in "integration.C" that gathers all the OpenFOAM functions that are dedicated to solve Navier-Stokes equations in my case.

Here you can find some parts of my code.
First the main function in "icoDHRAFoamEssai.C"

Code:
#include "fvCFD.H"
#include <iostream>
#include <fstream>
#include <string>
using namespace std;

// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //

extern "C" { void nothing_(double* AA, int &lengthAA,int* argvLength, int &argc,char* argvChar, int& argv1StrLength); } 
void integration_(double* AA, int* lengthAA, int& argc);

int main(int argc, char* argv[])
{
      //commands that I didn't attach here

      nothing_(AA, lengthAA, argvLength, argc, argvChar, argv1StrLength); 

      //some other commands
}
the subroutine "nothing" is as follows:

Code:
subroutine nothing(AA, lengthAA, argvLength, argc, argvChar, argv1StrLength)
	  
integer lengthAA
real*8  AA(lengthAA)
integer argc
integer argvLength(argc)
integer argv1StrLength
character argvChar(argv1StrLength+1)

!some fortran instructions
      
call integration(AA, lengthAA, argc)

return
end
And then "integration" in "integration.C"

Code:
void Integration_(double* AA, int* lengthAA,int& argc)
{
      #   include "setRootCase.H"
      #   include "createTime.H"
      #   include "createMesh.H"
      #   include "readEnvironmentalProperties.H"
      #   include "createFields.H"
      #   include "initContinuityErrs.H"

      Info<< "\nStarting time loop\n" << endl;
	
      #   include "readPISOControls.H"
      #   include "CourantNo.H"

      //some instructions that I added
      
      for (runTime++; !runTime.end(); runTime++)
      {
             //OpenFOAM instructions
      }

      Info<< "End\n" << endl;

      //other instructions

}
I have first compiled it using the commands:

Code:
gfortran -c nothing.f90 -o nothing.o
To link "nothing" with the main code I changed the "Make/options" file in the directory of my project to:

Code:
EXE_INC = \
    -I$(LIB_SRC)/finiteVolume/lnInclude

EXE_LIBS = \
    -lfiniteVolume\
	/usr/lib64/libgfortran.so.1\	
	$(HOME)/OpenFOAM/nperinet-1.4.1/applications/solvers/icoDHRAFoamEssai/nothing.o
As stated in this thread, I just added the two last lines.
I compile with "wmake"; if I don't call the function "integration" in "nothing.f90", everything goes well. When I call it, I get the error message:

Code:
In function `nothing_':
:undefined reference to `integration_'
Then it is most likely because I don't link "integration" to "nothing" and the main program, but I can mistake (I am beginner in OpenFOAM and C++ as well). The problem is that I absolutely don't know how to do this (which commands I have to add to which file to make this work, etc...).

I would be very grateful to anyone who may supply any suggestion.

Nicolas Périnet
Nicolas Périnet is offline   Reply With Quote

Old   May 30, 2011, 13:14
Default Differences in Library Linking
  #23
Member
 
Join Date: Sep 2010
Posts: 31
Rep Power: 6
anfho is on a distinguished road
Dear All,

I am also going to call a whole list of FORTRAN 90 subroutines from OF (in my case 1.7.1 though). I do this by adding the *.o files to the "objectFiles".

Apparently, as I am reading through this really helpful thread, it seems like there are different methods to do this: static library, dynamic library, static objects, dynamic objects, shared objects, objects, ...

I would appreciate, if someone could comment on the differences of these strategies (efficiency, ease of use, ...). This question came up earlier in the thread but has not been answered.

Thanks guys. Best regards,
Andreas
anfho is offline   Reply With Quote

Old   June 29, 2011, 14:51
Default link OF to fortran reading an input file
  #24
Member
 
Join Date: Sep 2010
Posts: 31
Rep Power: 6
anfho is on a distinguished road
Hi All,
did anyone try to link OF with fortran to read from an input file, something like:

integer temp
open(unit=10,file='input.dat')
read(10,*,end=100)temp
100 continue
close(10)

where the input file simply contains an integer, e.g.: "1",
and calling this from an OF application?

If I do this, I am getting a random output for "temp". It does work however, if I link a separate c++ main program and a fortran subroutine... so not sure why OF is causing trouble there...

Any help is appreciated.
Thanks, Andreas
anfho is offline   Reply With Quote

Old   July 30, 2012, 01:45
Default please tell me ???
  #25
Member
 
vahid
Join Date: Feb 2012
Location: Mashhad-Iran
Posts: 80
Rep Power: 4
vahid.najafi is an unknown quantity at this point
Hi Dear Nima again:
I want to add surface tension(sigma) in one solver,for this reason I added :
#include ''fvCFD.H''
fvc::interpolate(interface.sigma())

in this code:
Foam::tmp<Foam::volScalarField>
Foam:haseChangeTwoPhaseMixtures::SchnerrSauer: Coeff
(
const volScalarField& p
) const
{
volScalarField limitedAlpha1(min(max(alpha1_, scalar(0)), scalar(1)));
volScalarField rho
(
limitedAlpha1*rho1() + (scalar(1) - limitedAlpha1)*rho2()
);
return

//......I want to change it( <<sigma>> surface tension multiple in it):
(3*rho1()*rho2())*sqrt(2/(3*rho1()))* (fvc::interpolate(interface.sigma()))
*rRb(limitedAlpha1)/(rho*sqrt(mag(p - pSat()) + 0.01*pSat()));
//.................................................. ......
}
dont successful wmake, and seen(was not declared ):
phaseChangeTwoPhaseMixtures/SchnerrSauer/SchnerrSauer.C:113: error: 'interface' was not declared in this scope
make: *** [Make/linux64GccDPOpt/SchnerrSauer.o] Error 1
please help me,and tell me ,How to correct this problem???
vahid.najafi is offline   Reply With Quote

Old   July 30, 2012, 03:46
Default
  #26
Senior Member
 
Nima Sam
Join Date: Sep 2009
Location: Tehran, Iran
Posts: 1,123
Blog Entries: 1
Rep Power: 14
nimasam is on a distinguished road
Send a message via Yahoo to nimasam
dear vahid, instead of multiple posts of the same question, in different place, open new thread! with appropriate title,ask your question there!

it is an inappropriate to ask non-related issue under a post!
and about your problem, i told you here (Adding a new term in momentum equation of Interfoam).
you need a background of C++, look at here:
"http://cplus.about.com/od/learning1/ss/cppobjects.htm"
jameswilson620 likes this.
nimasam is online now   Reply With Quote

Old   July 30, 2012, 03:53
Default Thanks
  #27
Member
 
vahid
Join Date: Feb 2012
Location: Mashhad-Iran
Posts: 80
Rep Power: 4
vahid.najafi is an unknown quantity at this point
ok.mr nima.
Thanks
vahid.najafi is offline   Reply With Quote

Old   May 7, 2013, 11:56
Default
  #28
Senior Member
 
Join Date: Nov 2012
Posts: 168
Rep Power: 4
hz283 is on a distinguished road
Hi pge_cfd,

I am reading your thread and but this solution work well for my testing. But I did not run the following command as you mentioned:

ar rc myPbeLib.a fortfunc.o other.o object.o files.o // specific to Linux system

The coupled code can run well (but this is my simple test and so there is no complex in the fortran code). Could you please tell me what is the role for the
creation of the library?

Thanks.

Quote:
Originally Posted by pbe_cfd View Post


So, I came up with a solution to my prototype problem. Calling an external Fortran90 subroutine from an OpenFoam application.

STEPS
1) Declare an interface C function in the main file or in .H file and include it

extern "C"
{
void fortfunc_(int *ii, double *ff); // underscore is important (gfortran linux)!
}

When mixing Fortran with C++, name mangling must be prevented. You may use "objdump -t <file>" file: object or library files. In this example the subroutine named as fortfunc in the Fortran 90 code. But it's referred as fortfunc_

2) Compile your Fortran code and obtain object files "*.o". You may link the object files or you may create a static library form object files as follows,

ar rc myPbeLib.a fortfunc.o other.o object.o files.o // specific to Linux system

3) In your solver folder Make/options append -lgfortran (runtime fortran libraries) and your object or library files. If your fortran subroutine call some other routines from other libraries, add them as well. (Last case is not tested. )

EXE_LIBS = -lfiniteVolume\
-lgfortran\
$(FOAM_USER_LIBBIN)/fortfunc.o

4) Build your executable with wmake in solver folder.

This approach worked for my prototype problem. However I don't know if this is the best way, most probably NOT. Cyp's suggestion sounds really cool. But, I had a problem with obtaining the shared object files (*.so). I had done it before for a C++ code for boundary conditions. There it had worked very nicely. But with Fortran code I had problems. It doesn't compile the fortran code. If someone can describe how to obtain shared object files for Fortran codes, it will be really cool. Then, we can close this thread with a happy end ;-)

All the best;
Evren
hz283 is offline   Reply With Quote

Old   May 17, 2013, 07:53
Default
  #29
New Member
 
Evren
Join Date: Mar 2010
Posts: 20
Rep Power: 7
pbe_cfd is on a distinguished road
Hi

The role of creating the library is: you can call the functions/subroutines in the created library once you include the library in your make file before compiling your code. When one needs to use the functions/subroutines of the created library in other applications, she/he includes the library and compile it, and there you are.

Beside this, it was convenient for my purposes. I hope that I could explain it.

All the best,
Evren
pbe_cfd is offline   Reply With Quote

Old   July 11, 2013, 14:56
Question
  #30
Senior Member
 
Join Date: Jan 2013
Posts: 197
Rep Power: 4
openfoammaofnepo is on a distinguished road
Hello everybody,

When you use your own thermodynamic library, instead of OF's, do you provide the density from your own thermodynamic library? Or still use the openfoam's default method to update the density ---thermo.rho(). Because I also developed my own fortran thermodyanmic library to provide the density for the OF solver, however, I also have the numerical instabilisty problem. Does anybody have the same problem when you implement your thermodyanmic models?

Thank you very much.

OFer

Quote:
Originally Posted by Cyp View Post
Hi everybody!

I am looking to interface a specific thermodynamic tool with OpenFOAM. This program is written in Fortran. From a Pressure, a temperature and a composition it can provide a density : rho=f(P,T,x)

I wonder how to bound these different programs. I would like to keep the OpenFOAM structure and evaluate the density at each time step with a command as : thermo.rho();

Is anybody already performed such an interfacing ? Can you give some hints to start ? from which thermophysicalModels can I be inspired?

Regards,
Cyp
openfoammaofnepo is offline   Reply With Quote

Old   July 12, 2013, 04:17
Default
  #31
Senior Member
 
Christian Lucas
Join Date: Aug 2009
Location: Braunschweig, Germany
Posts: 198
Rep Power: 7
Chris Lucas is on a distinguished road
HI,

to get an idea how I use the external library, have a look at my water properties library in OpenFOAM ext. (which uses an external library to calculate the fluid propertiess)

IAPWSIF97 water properties

Kind Regards,
Christian
Chris Lucas is offline   Reply With Quote

Old   June 9, 2014, 14:30
Default Coupling interFoam/interDyMFoam with FORTRAN 90 code
  #32
Member
 
Gautami Erukulla
Join Date: Mar 2009
Posts: 30
Rep Power: 8
gautami is on a distinguished road
Dear All,

I would like to couple mooring cable dynamic code written in FORTRAN 90 to interFoam & interDyMFoam.

For every time step

1.InterFoam/InterDyMFoam solves for numerical wave tank.Based on the current wave field,the solver should provide velocities and accelerations at particular grid points (at mooring cable positions)as an input to the mooring cable code.
2.Based on these velocities and accelerations, the mooring cable fortran code solves for the tensions in the mooring cable and provides the tension at the fairlead point(particular grid point) as an input to the solver.

Kindly can somebody please explain how I could perform this dynamic coupling between OpenFOAM and FORTRAN 90.

Thank you.

Regards,
Gautami.
gautami is offline   Reply With Quote

Reply

Thread Tools
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are On


Similar Threads
Thread Thread Starter Forum Replies Last Post
Call Fortran program from OpenFoam tsjb00 OpenFOAM Running, Solving & CFD 6 April 22, 2013 15:26
2D Mesh Generation Tutorial for GMSH aeroslacker Open Source Meshers: Gmsh, Netgen, CGNS, ... 12 January 19, 2012 04:52
Native OpenFOAM interface in Pointwise Chris Sideroff Main CFD Forum 0 January 16, 2009 13:37
Convective Heat Transfer - Heat Exchanger Mark CFX 6 November 15, 2004 16:55
Replace periodic by inlet-outlet pair lego CFX 3 November 5, 2002 21:09


All times are GMT -4. The time now is 03:25.