using external modules in Fortran - module

I try to use two external Fortran module which are in same name (in this case mod_param). So, when i try to compile my code, the compiler gives the following error,
mod_param.o: In function mod_param._':
mod_param.f90:(.text+0x0): multiple definition ofmod_param._'
mod_param.o:mod_param.F90:(.text+0x0): first defined here
is there any way to solve it without renaming the one of the module file and its name? I don't prefer the renaming because the external modules are maintained by someone else and i don't want to play with them. Is there any special use statement to do that?

No. It is necessary to change the function name in the source code in at least one of the modules.
Since the code is being maintained by someone else, consider automating the renaming: perhaps the project Makefile can run a sed script which changes the function names. So that the dependencies are clear, be sure to make the output of the sed script a new file name which is used to be compiled—the virgin module would have a filename which is not compiled or linked into the project.
Even if it were somehow possible to link them both in with the same name, how would you control which was called with the name?

According to F2003 standard module names are global entities and must be unique in a program, with some exteptions for intrinsic modules.
So, that would be a no (Besides, how would you tell them apart were they of the same name?)

Related

How to prevent the perl compiler from changing the name of dynamic link library

I'm making a perl6 package which contains some c source files that will be compiled into a dynamic link library. I found that the name of the library, such as libperl.so, will be changed into something like "A858A3D6EC5363B3D3F59B1.so" after "zef install". However, the name is used in python code as a module name(libperl). After the change, it is no longer a valid identifier. So, is it possible to prevent the change? If it is, what should I do?
I am not sure if it's possible to do that. Maybe it is.
Inspired by #raiph's link, however, I decided to create a soft link. Now the package works well.

Personal modules in OCaml

I'm working on a school project that consists of handling a list of contact in OCaml. The thing is that we have to make modules but I'm not really sure to have understand how that works. I have an agenda.ml, agenda.mli, contact.ml and contact.mli but when I wanna use agenda.ml it says that Contact is an unbound value when I call a Contact.function even if I already did #use "contact.ml".
Could someone explain me that whole thingy of module please?
If you are using the toplevel, you need to use #mod_use <filename> rather than #use <filename>: #use <filename> simply reads the contents of the filename inside the current scope, whereas #mod_use <filename> use the file to define a new module <Filename> in the current scope.
However, both #mod_use and #use are simple textual directive that cannot work with pair of ml and mli files. You will need at some point to read on OCaml build system. For simple school project, ocamlbuild might be a good idea: compiling a whole project might be as simple as ocamlbuild <main>.native.

Using different variants of module in routines shared between two programs

in two directories I have two different, independent Fortran 90 programs, and I want them to share certain routines that use some variables defined in modules. In other words, I have a directory dirA with program prgA.f90 and a couple of routines in an extra file sub.f90, and these routines use some stuff from a module in the file modA; all of them reside in dirA. In another directory, dirB, I have the independent code prgB.f90 that is supposed to use routines from sub.f90 and hence needs modules that define the stuff needed by it. For technical reasons, I cannot use the modules from modA in dirA directly, but write a variant of it, modB, with the same module name and containing the variables of interest with the same names as in modA as well as other variables only used by prgB. Will the routines from sub.f90 work with modA in the executable of prgA and with modB in the executable of prgB?
I have partly tried to adapt my codes to this, and the compiler seems to accept it somehow, but I'm not sure if it will really work and not produce garbage results in spite of compiling seemingly ok.
Basically the question is this: Can I share functions USEing certain modules between different programs if I ensure that the modules have the same name and have a subset of variables in common, or do the modules USEd by the functions have to be exactly the same for both programs?
Thomas
If I understand correctly then what you are doing is just fine.
When you build progA the compiler encounters, on tackling sub.f90, a statement such as use globals. At that point the compiler will look for a file called globals.mod which it should, by that point, have created by compiling the module source. Of course, that module source need not be in a file called globals.f90 but that's neither here nor there. The module source might, for example, be in a file called globals_for_a.f90.
When you build progB the compiler encounters, on tackling sub.f90, a statement such as use globals. At that point the compiler will look for a file called globals.mod which it should, by that point, have created by compiling the module source. Of course, that module source need not be in a file called globals.f90 but that's neither here nor there. The module source might, for example, be in a file called globals_for_b.f90.
So long as the compilation for each program finds the right source for globals.mod everything should compile as you wish. You've chosen to divide your source files across a number of directories but that's not strictly necessary; a make file with suitably defined targets could build either program or both however you organise the source files and directories.
Note that almost all of this is outside the concern of the Fortran standards, it's more a question of how compilers and compilation work.

FORTRAN 95: is it possible to share a module without sharing the source code?

I would like to be able to share a FORTRAN 95 module without sharing its source code. Is it possible to do so (maybe by sharing the .MOD file)? In case this is relevant, I use Silverfrost FTN95 compiler on Plato. So far, I only manage to make this work by using the source code of the external module. Here is an example:
file: module_test.f95
module TEST
contains
subroutine 1
code...
end module TEST
file: main_program.f95
include "module_test.f95"
program MAIN_PROGRAM
use TEST
implicit none
code...
end program MAIN_PROGRAM
So, would it be possible for someone to use my module TEST without having my file module_test.f95 nor the line include "module_test.f95" on the main code?
Thanks a lot!
You could provide two things. 1) Compiled object code, possibly in library form. The disadvantage is that this would depend on compiler, OS, perhaps compiler version, and so could be large burden to support. 2) Instead of providing the source code so that others could use the module, you could write equivalent interface descriptions of your routines. This, at least, is at the source code level and would not be compiler dependent. It would some work to write and would have to be maintained if you changed the arguments of any of your procedures.
The solution I am using is, as M. S. B. recommended, to compile the module in library form. I am explicitly showing how I am doing this in case this might be helpful to someone, as this is what I did not know in those days.
First, one needs to compile the module module_test.f95. Using the gfortran compiler, this can be accomplished by the command gfortran -c module_test.f95. This will create two files, module_test.o and module_test.mod. These are the compiled module files that can be shared without sharing the source code.
Now to the main program. For it to make use of the module, one still needs to add the line use TEST but no include <source code>:
program MAIN_PROGRAM
use TEST
implicit none
<...code...>
end program MAIN_PROGRAM
Now when compiling the main program, one must include the location of the .o module file in the command. In the case above, it would be gfortran main_program.f95 module_test.o (supposing that module_test.o is on the same folder as the project). This will compile the main program using the module without the need for its source code.

YGuard obfuscate single class, package and exclude libraries

I'm trying to use YGuard to obfuscate some parts of my program which contain encryption methods and other sensitive information (which I'll further protect in other ways once I figure this out).
Because the program is quite complex and contains quite many libraries it obviously gives a series of warning and finally fails with:
WARNING: Method initialize_ffi_type is native but com/sun/jna/Native is not kept/exposed.
WARNING: Method getAPIChecksum is native but com/sun/jna/Native is not kept/exposed.
[...]
yGuard was unable to resolve a class (java.lang.ClassNotFoundException: com.sun.tools.javac.parser.Parser$Factory)
Now whatever that means I'd like to
exclude libraries which being all open source have nothing to hide so far
obfuscate just the methods and variables of some Class or some package and leave the rest untouched.
So far in YGuard it seems I have to specify what I don't want to be obfuscated, however I have far too many classes, I'd like instead to do the opposite: Specify what I'd like to obfuscate and proceed increasing the number of Classes and packages I want obfuscated.
Thanks
It is the normal practice for obfuscators to specify what should be kept and not the other way around.
However, you can define library classpaths with the externalclasses rule (link). Classes that are defined in this path are neither obfuscated nor shrinked. The second error you are getting (ClassNotFoundException) indicates that you have not specified all libraries that your project depends on.
In order to obfuscate your code now, what you could do is:
Pack the code that you want to be obfuscated in one jar and define everything else as a library
use a patternset in your keep rule (link) to define everything to be kept except the classes that you want to have obfuscated.