![]() |
Trying to debug segfault in ctypes binding to Fortran - Printable Version +- Python Forum (https://python-forum.io) +-- Forum: Python Coding (https://python-forum.io/forum-7.html) +--- Forum: General Coding Help (https://python-forum.io/forum-8.html) +--- Thread: Trying to debug segfault in ctypes binding to Fortran (/thread-40639.html) |
Trying to debug segfault in ctypes binding to Fortran - bthomas - Aug-30-2023 Hi, I am just trying to learn creating Python bindings to legacy Fortran using the ctypes module. My code is segfaulting in the Fortran function invocation. I was not able to decipher what gdb was telling me. I would be grateful to be pointed in the right direction here. A simple Fortran function I am trying to bind is given below. It was compiled using "gfortran -shared euler.f -o euler.so" subroutine euler(f, neq, y, t, tout, h) implicit none real y(neq), t, tout, h, dy(neq), ti integer neq, i, stepnum stepnum = 1 ti = t c Euler iteration 10 continue call f( neq, t, y, dy ) do 20 i = 1, neq y(i) = y(i) + h*dy(i) 20 continue t = ti + stepnum*h stepnum = stepnum + 1 if ( t < tout ) goto 10 return endThe Python code calling this Fortran subroutine is import ctypes as ct flib = ct.CDLL('euler.so') ode_spec = ct.CFUNCTYPE(None, ct.c_int, ct.c_float, ct.POINTER(ct.c_float), ct.POINTER(ct.c_float)) flib.euler_.restype = None flib.euler_.argtypes = [ ct.POINTER(ode_spec), ct.c_int, ct.POINTER(ct.c_float), ct.c_float, ct.c_float, ct.c_float ] @ode_spec def df(neq, t, y, dy): dy[0] = y[0] return t = 0.1 to = 0.2 neq = 1 realarr = ct.c_float * neq y = realarr(0.1) h = 0.001 flib.euler_(df, len(y), y, t, to, h) RE: Trying to debug segfault in ctypes binding to Fortran - bthomas - Sep-01-2023 Finally got it working. The code below worked. import ctypes as ct flib = ct.CDLL('euler.so') ode_spec = ct.CFUNCTYPE(None, ct.POINTER(ct.c_int), ct.POINTER(ct.c_float), ct.POINTER(ct.c_float * 1), ct.POINTER(ct.c_float * 1)) flib.euler_.restype = None flib.euler_.argtypes = [ ode_spec, ct.POINTER(ct.c_int), ct.POINTER(ct.c_float * 1), ct.POINTER(ct.c_float), ct.POINTER(ct.c_float), ct.POINTER(ct.c_float) ] @ode_spec def df(neq, t, y, dy): dy[0] = y[0] return t = ct.c_float(0.1) to = ct.c_float(0.2) neq = ct.c_int(1) relarr = ct.c_float * 1 y = relarr() y[0] = 0.1 h = ct.c_float(0.001) flib.euler_(df, ct.byref(neq) , ct.byref(y), ct.byref(t), ct.byref(to), ct.byref(h)) |