I have the following test function:
#include <stdlib.h>
#include <stdio.h>
void print_string(char *text);
void print_string(char *text) {
printf("---\n%s\n---\n", text);
}
And the following module which encapsulates the call with a Fortran subroutine using iso c bindings:
module test_c_lib
use iso_c_binding
implicit none
contains
subroutine test(text)
use iso_c_binding
character,intent(in) :: text(:)
! Interface to C function
interface
subroutine c_print_string(t) bind(C, name="print_string")
import
character(kind=c_char) :: t(:)
end subroutine
end interface
! Call C function
print *,"AAAAA"
print *,text
print *,"AAAAA"
call c_print_string(text // C_NULL_CHAR)
end subroutine
end module
The way to define the subroutine in Fortran using ISO C BINDINGS is extracted from this documentation link. I further encapsulate it a bit as f2py
does not support iso c bindings.
I compile everything via makefile
:
$ cat makefile
f_mod.so: f_mod.f90 c_lib.o
f2py -c f_mod.f90 c_lib.o -m f_mod
c_lib.o: c_lib.c
gcc -c -fpic c_lib.c -o c_lib.o
It compiles but:
- I get the following warning:
150 | call c_print_string(text // C_NULL_CHAR)
| 1
Warning: Character length mismatch (2/1) between actual argument and assumed-shape dummy argument 't' at (1) [-Wargument-mismatch]
- I get the following output when invoking via
import fmod; f_mod.test_c_lib.test("Foo")
:
AAAAA
Foo
AAAAA
---
8v$
---
So f2py
is working but when passing text // C_NULL_CHAR
as parameter it does not seem to work as I get garbage from the C function output.