Version 1 (modified by trac, 15 years ago) |
---|
Fortran Support in ZOO Kernel
This page will contain full information about the Fortran support in the ZOO Kernel.
Fortran code snipest
Let us create a small example of a Fortran function which simply multiply by two the value passed as argument.
C ex4.for C ARRAYS X, Y and Z are respectively : C main_conf, inputs and outputs FUNCTION HELLOWORLD(X, Y, Z, X0) RESULT (R) INTEGER(4) :: R CHARACTER*1024 X(10,10) CHARACTER*1024 Y(10,10) CHARACTER*1024 Z(10,10) CHARACTER*100 X0 C CHARACTER*(*) X(10,10), Y(10,10), Z(10,10) C The following will display the right string PRINT *,'FROM FORTRAN : '//X0 C The following won't display the right string C PRINT *,Y(1,4) Z(1,1) = 'name' Z(1,2) = 'result' Z(1,3) = 'value' Z(1,4) = 'Hello from the Fortran world !' Z(1,5) = 'dataType' Z(1,6) = 'string' PRINT *,Z(1,4) R = 3 END
To create a shared library of this code snipest, use the following command :
gfortran -fno-f2c -shared -s -o ex4.so ex4.for
Then the loading process isthe same as before, using the dlload, dlsym then use the funcion.
The snipest C++ code bellow will load, extract the function from the fortran shared library then run the function and finally close the shared library.
// ex4fortranloader.c #include <iostream> #include <dlfcn.h> int main() { void *hDll = dlopen("./ex3.so", RTLD_NOW); typedef int (* LPFNDLLFUNC) (char***,char***,char***,char*); LPFNDLLFUNC lpFunc = NULL; lpFunc = (LPFNDLLFUNC)dlsym(hDll, "helloworld_"); int i, numPts = 10; char*** main_conf=(char***)malloc(10*sizeof(char**)); char*** inputs=(char***)malloc(10*sizeof(char**)); char*** outputs=(char***)malloc(10*sizeof(char**)); printf("first allocation has been made\n"); for(int i=0;i<10;i++){ main_conf[i]=(char**)malloc(10*sizeof(char*)); inputs[i]=(char**)malloc(10*sizeof(char*)); outputs[i]=(char**)malloc(10*sizeof(char*)); printf("allocation for level %d\n",i+1); for(int j=0;j<10;j++){ main_conf[i][j]=(char*)malloc(1024*sizeof(char)); memset(main_conf[i][j],0,1024); main_conf[i][j][0]=0; inputs[i][j]=(char*)malloc(1024*sizeof(char)); memset(inputs[i][j],0,1024); inputs[i][j][0]=0; outputs[i][j]=(char*)malloc(1024*sizeof(char)); memset(outputs[i][j],0,1024); outputs[i][j][0]=0; printf("allocation for elements (%d,%d)\n",i+1,j+1); } } sprintf(inputs[0][0],"name"); inputs[0][0][4]=0; printf("inputs[0][0] = %s\n",inputs[0][0]); sprintf(inputs[0][1],"S"); inputs[0][1][1]=0; printf("inputs[0][1] = %s\n",inputs[0][1]); sprintf(inputs[0][2],"value"); inputs[0][2][5]=0; printf("inputs[0][2] = %s\n",inputs[0][2]); sprintf(inputs[0][3]," Your Name Here "); inputs[0][3][16]=0; printf("inputs[0][3] = %s\n",inputs[0][3]); printf("Allocation made of inputs values\n"); char *tmp=(char*)malloc(100*sizeof(char)); sprintf(tmp,"My Test String"); int res=lpFunc(main_conf,inputs,outputs,tmp); printf("function ran successfully and retruned : %d\n",res); // Unable to get back the outputs array //printf("z[1][4] = %s\n",outputs[0][0]); dlclose(hDll); return 0; }
Compile this code using the following command :
g++ -o ex1fortranloader ex1fortranloader.cpp -ldl
Now, to process the function you'll only have to run the following command :
./ex1fortranloader
Which should output :
first allocation has been made inputs[0][0] = name inputs[0][1] = S inputs[0][2] = value inputs[0][3] = Your Name Here Allocation made of inputs values FROM FORTRAN : My Test String Hello from the Fortran world ! function ran successfully
Conclusion
So we can say that loading a C SSO (Service Shared Object) or a Fortran one work in the same way.
The goal is now to be able to pass maps* datastructure to the fortran function then let user easily get/set its data using this datastructure. Maybe a simple multidimentional array of CHARACTER* can be used. This way maps will be translated into CHARACTERS[][][] before being passed to the Fortran function.