Fortran¶
This is the most vanilla example of all. We are simply
calling the Fortran example
module from a Fortran program.
The module is only “foreign” in the sense that we only interact
with the object file example.o
when creating the executable fortran_example
:
$ gfortran \
> -o fortran_example \
> fortran/main.f90 \
> fortran/example.o
However, this still requires the presence of a module file to build the executable
$ ls fortran/example.mod
fortran/example.mod
$ rm -f fortran/example.mod
$ gfortran \
> -o fortran_example \
> fortran/main.f90 \
> fortran/example.o
fortran/main.f90:4:6:
use example, only: &
1
Fatal Error: Can't open module file 'example.mod' for reading
at (1): No such file or directory
compilation terminated.
Finally, we run fortran_example
to verify the behavior of
several procedures in the public interface:
$ ./fortran_example
------------------------------------------------------------
quux = foo(1.000000, 16.000000) = 61.000000
------------------------------------------------------------
quuz = make_udf(1.250000, 5.000000, 1337)
= UserDefined(1.250000, 5.000000, 1337)
------------------------------------------------------------
foo_array(
4,
[[3.000000, 4.500000],
[1.000000, 1.250000],
[9.000000, 0.000000],
[-1.000000, 4.000000]],
) =
[[6.000000, 9.000000],
[2.000000, 2.500000],
[18.000000, 0.000000],
[-2.000000, 8.000000]]
------------------------------------------------------------
ptr_as_int = c_loc(made_it) ! type(c_ptr)
! integer(c_intptr_t)
! integer(kind=8)
ptr_as_int = 140733727194752 ! 0x7FFF1FD13E80
udf_ptr(ptr_as_int) ! Set memory in ``made_it``
made_it = UserDefined(3.125000, -10.500000, 101)
------------------------------------------------------------
just_print()
======== BEGIN FORTRAN ========
just_print() was called
======== END FORTRAN ========
------------------------------------------------------------
view_knob() = 1337
turn_knob(42)
view_knob() = 42
Using the shared library is as simple as declaring the public symbols used:
use example, only: &
dp, foo, foo_array, make_udf, udf_ptr, just_print, &
view_knob, turn_knob, UserDefined
Notice that the view_knob()
subroutine is in the public
Fortran interface even though it doesn’t have a bound
name in the ABI.