I have an old code with lots of subroutines, and they are all in Fortran 77, So now I want to update one subroutine which I need to update according to a Fortran 90/95 code, Is there any way to convert it to 77?
Some compilers have declarations that allow you to switch between fixed and free form Fortran-files.
As others have noted, use the newest compiler possible as they should be backwards compatible. Files are either in fixed form of free form and use the file endings .f or .f90 to separate them.
If you absolutely need to, in Intel the directives are !DIR$ FREEFORM and !DIR$ NOFREEFORM if you need to control the reading of the file per line or section. This can be useful if you "have to" use old include-files written in fixed form but you want to use free form Fortran in you code, then you can write:
module important_new_code
<lots of use-statements>
!DIR$ NOFREEFORM
include 'old_style_includes.incl'
!DIR$ FREEFORM
<rest of module in modern fortran>
end module
However, this makes your code compiler-specific and is generally not a good idea! The best is always to fix your problem properly.
I'm not entirely sure what you want to do. But as pointed out in the comments, you can mix Fortran 90/95 and Fortran 77 (but of course not in the same file). With ifort you could e.g. write an f90-file contaning you main program named file_1.f90 and another f77-file containing some subroutines called in in your main file which is named file_2.f77. To compile them together:
ifort -c file_1.f90
ifort -c file_2.f77
ifort file_1.o file_2.o -o file_1
In the first two lines you create object files (*.o) which you then link together creating a target file (here file_1). If you need further libraries you can link them in the usual way in the last line. Hope this helps you.
Related
I am trying to combine two Fortran projects using gFortran. But one project is written using f90 with free form and another one using .for with fixed 132 line length form. Can I set up the different line length according to Fortran file type in one project as below?
-ffixed-line-length-132 for .for
-ffree-line-length-none for .f90
Thank you
Yes, you can. I was not sure so I just went ahead and tried it.
gfortran -ffixed-line-length-1000 -ffree-line-length-1000 longline.for longline.f90
compiled two files with very long lines without any problem.
The same happened for 132 for the former and none for the latter, but it correctly complained when I exceeded 132 for the fixed form file.
Anyway, be aware that you can always compile your files in separate steps and use different flags in each of these steps:
gfortran -ffixed-line-length-132 longline.for -o longline-fixed.o
gfortran -ffree-line-length-1000 longline-fixed.o longline.f90
For large projects it is typical to use some build system that organizes the compilation into these steps automatically (make, CMake, SConstruct, FoBiS.py,...).
I have code that includes main program and many modules in separate files that I am linking. Currently I have a makefile that creates .o files for each module (one on separate line) and then I put them all together, such as here:
mpif90 - modutils
mpif90 -c modvarsym
mpif90 -c s1_Phi.f90
mpif90 -c s2_Lambda.f90
mpif90 maincode.f90 modutils.o modvarsym.o s1_Phi.o s2_Lambda.o -o maincode
The above compiles fine and runs OK - except tat I suspect that I suspect array bound problems in my variables. So I include -fbounds-check maincode statement such as here:
mpif90 maincode.f90 modutils.o modvarsym.o s1_Phi.o s2_Lambda.o -o -fbounds-check maincode
That's when numerous "multiple definition" errors appear, and the code will no longer compile. I imagine that is because of -fbounds-check: rather than just enabling checking for array bounds, it probably does some additional checks. I also suspect that the error is in the way that I enter files in the make file. However I could not find the way that would work. In these files, both modvarsym and modutils is used by the main code as well as by the other two modules. The main code uses all four modules.
There is no include statement in these files. Maincode is the only file with the program statement, the variables are declared only once in modvarsym. Overall, the code compiles and runs without -fbounds-check. However I really want to use -fbounds-check to make sure the arrays do not overrun. Would anybody be able to put me on the right track? Thank you.
This is the answer #dave_thompson_085 gave in his comments, it seems to solve the problem.
First, I assume your first command is meant to have -c, and your first two are meant to have .f90 (or .f95 or similar) suffix as otherwise the compiler shouldn't do anything for them. Second, -o -fbounds-check maincode (in the absence of -c) means to put the linked output in file -fbounds-check and include maincode (if it exists) among the files linked. Since you have already linked all your routines into maincode, linking those same routines again PLUS maincode produces duplicates.
Move -fbounds-check before the -o at least; even better, it is usual style (though not required) to put options that affect parsing and code generation before the source file(s) as well, and in your example that is maincode.f90. Also note that this generates bound checks only for the routines in maincode; if there are any subscripting errors in the other routines they won't be caught. When you have a bug in a compiled language the place where a problem is detected may not be the actual origin, and it usually best to apply debugging options to everything you can.
I was reading on Clang and Ch (c++ interpreters), but its not clear for me, is it possible to run a newly generated .cpp file without any installations? Because i need to run the final program on any pc...
ps. if yes, does anyone have a good example, where a .cpp file is being executed within c++ code?
This is probably impossible or at least very hard. You would have to include the whole compiler (including linker, assembler, optimizer, preprocessor, ...) inside your program and that would make it extremely big.
One way of doing this is with Clang (as you already noted), there is even a demo project called "Clang interpreter" in the source: http://llvm.org/viewvc/llvm-project/cfe/trunk/examples/clang-interpreter/
However I once tried to compile this "beast" into my program and gave up halfway, because the file size of the result binary (or binaries with external libraries) gets into tens of megabytes (maybe even a hundred).
My suggestion is to either produce a different script (e.g. bash/sh script, which you could execute on any unix machine) that can be interpreted easily.
As far as I know, it is impossible, because compilation process of a CPP file is like this-
Preprocessing: the preprocessor takes a C++ source code file and deals with the #includes, #defines and other preprocessor directives. The output of this step is a "pure" C++ file without pre-processor directives.
Compilation: the compiler takes the pre-processor's output and produces an object file from it.
Linking: the linker takes the object files produced by the compiler and produces either a library or an executable file.
So, there should be intermediate files and executable files.
More can be found here-
https://stackoverflow.com/a/6264256/7725220
Kind of depends on what you mean by "installations".
Yes you can distribute your program with a full compiler, compile the source code and then execute the final result (all from the original exe).
Question: what is the best way to convert a .c/.h based project (which is forcefully compiled as C++ via the makefiles) to a .cpp/.hpp based project?
Obviously, this is a triple-step process. The first would be to rename everything with *.c at the end to *.cpp; the second would be to rename everything with *.h at the end to *.hpp. What I'm getting caught up on is the third step- somehow building a list of what the files /were/ named (ie, myfile.c), then iterating through every single affected file and replacing every instance of the old filename with the new (myfile.c -> myfile.cpp). Obviously this would have to be done so the source files can still find everything that they need.
The source code in question consists of around 2700 individual source files.
The reason why I'm doing this is mostly because I'm porting said software package to Mac OS X, and that involves Xcode. Things are getting bloody messy trying to keep track of precisely what is C, C++, and the associated headers for either (then overriding the compiler for C++ compilation). It would be much simpler if everything C++ was *.cpp (with the associated headers being *.hpp), since then I can just leave Xcode at the default compiler setting as per the file extension and everything should work without any fancy intervention on my end.
I should probably also note that I know precisely what files need to be converted, because they already compile properly and in a sane fashion if I'm overriding Xcode to compile as C++. That's not a problem- my issue is trying to figure out how to batch rename everything then run through all the files and update the #includes.
Thank you in advance!
-Keven Tipping
You don't need to mess with the headers. filename.h is a perfectly good name for a C++ header.
If you're not using the old makefile, but creating a new XCode project, then you have only one step:
Rename *.c to *.cpp
If the makefile was written right (using rule patterns and not specific per-file rules), there shouldn't be any changes needed there either.
There's no reason to rename those C language header and source files to C++ and there are many reasons not to. Just three of the many:
Reason #1: C and C++ are diverging, different languages. Force-compiling a C file as if it were C++ risks introducing a bug.
Reason #2: Xcode can handle C, C++, and C and C++ mixed together.
Reason #3: C++ can easily call C routines. All you need to do is wrap the declarations of those C functions inside an extern "C" { /* C declarations here */ } construct.
Apologies if this is too naive or obvious but after a fair bit of searching around, I'm not 100% sure that I understand the fortran/unix interface. My uncertainty is regarding the nature of .src, .f, then .o, and .out files that you run into when compiling fortran programs into a unix executable. It's tough to google file extensions like this. But if you could tell me if I've got this straight, I'd really appreciate it!
.src is the source file which contains the meaty fortran code
.f is the 'host-language specific include file' that tells your fortran compiler a little bit about the source code. It's sometimes interactive.
--- After you've obtained .o or .out files, can throw away the .src and .f files, yeah?
.o is the binary object file that results from compiling but not linking the fortran .f and .src files. It contains the same meat but now converted into machine-specific instructions?
.out is the linked object file(s) which is executable and remains dependent on the .o file(s) and is machine-specific. The .out file extension is not really needed and is often omitted?
I think that covers it. Thanks for any corrects or further descriptions.
Kyle
Nothing about these file extensions is set in stone; as you said, they can even be omitted, or you can make up your own. However, it makes life far easier if you use the conventional ones.
I've never seen the .src extension. The directory where the source files are located is often referred to as ./src; maybe you've seen this.
Usually, the source code (plain text) is in a file with extension .f or .f90. The first one indicates fixed source form ("old style"), and the second one free source form ("modern"). Some compilers interpret uppercase file extensions (.F and .F90) as an indication that the source has to be run through the preprocessor first. Instead of letting the compiler use the extensions for these interpretations, all this can also be explicitly stated/overruled by passing flags to the compiler.
Compilation of the source code produces object code (the machine-specific instructions you mention), contained in an object file, usually with .o as extension (sometimes .obj, or other).
After creating the object files, you could indeed throw away your source code files, but you don't want to do that. You want to fix any bugs you most likely made, and also keep them for future alterations to your program.
The object code has to be linked to produce the final executable. If you have more than one object file, they are tied together, with inclusion of any system/external library code you referred to. On Unix, if you don't specify a name for the executable, the default name it gets is usually a.out. Again, you can overrule this by passing an argument to the compiler.
No, the Fortran code is usually in .f or .f90 files. In more detail, Fortran source code usually has the extension .f if it uses the fixed source form (the standard source form of Fortran 77 and earlier versions) or .f90 it uses free source form (present from Fortran 90 on).
After you've obtained .o or .out files, can throw away the .src and .f files, yeah?
No. As an addendum to the answers describing the various suffix conventions, I advise that you don't delete the Fortran source files (the .src or .f files in your description). You'll need these files if you ever want to modify the program, or if you need to investigate and fix errors you notice from running the executable file (a.out).