I'm having problems with the mixed-language programming as mentioned in the title, more precisely getting arrays from Ada to the Fortran code. My Ada procedure declaration looks like:
procedure Get_Double_Array
(Double_Array : in System.Address;
Length_of_Array : in System.Address);
pragma Export(Fortran, Get_Double_Array, "Get_Double_Array_");
The corresponding body of my procedure is
procedure Get_Double_Array
(Double_Array : in System.Address;
Length_Of_Array : in System.Address)
is
use Interfaces.Fortran;
Array_Length : Fortran_Integer;
for Array_Length'Address use Length_Of_Array;
Result_Array : Double_Precision_Array(1..3);
for Result_Array'Address use Double_Array;
begin
Result_Array(1) := Double_Precision(1.0);
Result_Array(2) := Double_Precision(2.0);
Result_Array(3) := Double_Precision(3.0);
Array_Length := Fortran_Integer(Result_Array'Last);
end Get_Double_Array;
The declaration of the Double_Precision_Array looks like
type Double_Precision_Array is (Fortran_Integer range <>) of Double_Precision;
pragma Convention(Fortran, Double_Precision_Array);
Making this procedure available in the DLL is already working. dumpbin /exports on the created dll shows the Get_Double_Array_ as expected.
The Fortran program looks like
PROGRAM TPROG
IMPLICIT NONE
INTERFACE
SUBROUTINE GETARR(DPARR, LENGTH)
cDEC$ ATTRIBUTES DLLIMPORT, ALIAS : '_Get_Double_Array_' :: GETARR
DOUBLE PRECISION, DIMENSION (:) :: DPARR
INTEGER :: LENGTH
END SUBROUTINE
END INTERFACE
DOUBLE PRECISION, DIMENSION(3) :: XDOT
INTEGER :: LENGTH
CALL GETARR(XDOT, LENGTH)
END PROGRAM TPROG
The fortran code is compiled with gfortran and linked with the lib corresponding to the created dll. The command line is
gfortran -o test.exe test.f Ada_Lib.lib
When I inserted debugging output into the fortran code before the Call statement I can see that the Get_Double_Array procedure is called but I get the exception
raised PROGRAM_ERROR: Name_Of_The_Ada_Body.adb: misaligned address value
The line number in this message is the one where I declare the Array_Length variable. I know about the Ada Attribute 'Alignment, but I don't know how to use it in this situation, because I'm already using Fortran compatible data types (at least I think so).
When I export the C Convention on the Ada side and also use the C convention for the array declaration and adapt the cDEC$ line in Fortran with 'C, DLLIMPORT, ALIAs', the Length value is always correct but the contents of the array are completely useless.
The range of the Arrays is only fixed for debugging. Later the Array can be of any length, which is why I also need to return the length of the array.
Any useful tipps or explanations what I'm doing wrong and what I can try next?