Ich möchte ein Array variabler Größe zu einer Fortran-DLL übergeben und das Ergebnis (per Referenz) erhalten, so dass ich direkt Wert erhalten kann.Python Ctypes übergeben Zeiger im Strukturfeld zu Fortran-abgeleiteten Typen
Im Fortran-Code verwende ich zuweisbare Variablen, die ich denke, ist wie ein Zeiger, um zugeordnete Adresse zu zeigen.
Ich kann wie folgt tun, aber ich weiß nicht, wie es in der Struktur zu tun:
test = POINTER(c_double)()
sim.structtest(input, byref(test))
die Definition von test
in Fortran ist
real(kind=8), allocatable, dimension (:) :: test
allocate(test(1))
Der ursprüngliche Code:
Python-Code (structtest.py):
from ctypes import *
import sys
import os
sim = cdll.LoadLibrary("struct.so")
class Input(Structure):
_fields_ = [("a", c_double * 1),
("b", c_double)]
class Output(Structure):
_fields_ = [("a", c_double),
("b", POINTER(c_double))] #-> don't know how to do
def main():
input = Input()
output = Output()
input.a[0] = 1
input.b = 2
sim.structtest(input, byref(output))
Fortran-Code (struct.f90):
subroutine structtest(input, output) bind(c, name='structtest')
USE ISO_C_BINDING
IMPLICIT NONE
!define input structure
TYPE T_INPUT
!real*8, allocatable :: a(:)
real(kind=8) :: a(1)
real(kind=8) :: b
END TYPE T_INPUT
!define output structure
TYPE T_OUTPUT
real(kind=8) :: a
real(kind=8), allocatable, dimension (:) :: b
END TYPE T_OUTPUT
!define a variable "input" with structure "INPUT"
TYPE (T_INPUT), value :: input
TYPE (T_OUTPUT) :: output
allocate(output%d(1))
output%b(1) = 5
PRINT *, output%d(1)
kompilieren ich die Fortran DLL wie:
python structtest.py
ich das Ergebnis:
ifort -shared -fPIC -static-intel -o struct.so struct.f90
ich die Python als ausführen :
*** Error in `python': free(): corrupted unsorted chunks: 0x0000000001f7af00 ***
======= Backtrace: =========
/lib/x86_64-linux-gnu/libc.so.6(+0x777e5)[0x7fc9027f57e5]
/lib/x86_64-linux-gnu/libc.so.6(+0x8037a)[0x7fc9027fe37a]
/lib/x86_64-linux-gnu/libc.so.6(cfree+0x4c)[0x7fc90280253c]
/lib/x86_64-linux-gnu/libc.so.6(__open_catalog+0xe8)[0x7fc9027b2008]
/lib/x86_64-linux-gnu/libc.so.6(catopen+0x4c)[0x7fc9027b1c2c]
/home/mingster/simGeo.docker/simgeo/lib/struct.so(for__issue_diagnostic+0x11e)[0x7fc90147a77e]
/home/mingster/simGeo.docker/simgeo/lib/struct.so(for_allocate+0x303)[0x7fc90146b9a3]
/home/mingster/simGeo.docker/simgeo/lib/struct.so(structtest+0xae)[0x7fc90146b16e]
/usr/lib/x86_64-linux-gnu/libffi.so.6(ffi_call_unix64+0x4c)[0x7fc901757e40]
/usr/lib/x86_64-linux-gnu/libffi.so.6(ffi_call+0x2eb)[0x7fc9017578ab]
/usr/lib/python2.7/lib-dynload/_ctypes.x86_64-linux-gnu.so(_ctypes_callproc+0x48f)[0x7fc9019673df]
/usr/lib/python2.7/lib-dynload/_ctypes.x86_64-linux-gnu.so(+0x11d82)[0x7fc90196bd82]
python(PyObject_Call+0x43)[0x4b0c93]
python(PyEval_EvalFrameEx+0x602f)[0x4c9f9f]
python(PyEval_EvalFrameEx+0x5e0f)[0x4c9d7f]
python(PyEval_EvalCodeEx+0x255)[0x4c2705]
python(PyEval_EvalCode+0x19)[0x4c24a9]
python[0x4f19ef]
python(PyRun_FileExFlags+0x82)[0x4ec372]
python(PyRun_SimpleFileExFlags+0x191)[0x4eaaf1]
python(Py_Main+0x6c8)[0x49e208]
/lib/x86_64-linux-gnu/libc.so.6(__libc_start_main+0xf0)[0x7fc90279e830]
python(_start+0x29)[0x49da59]
======= Memory map: ========
00400000-006e9000 r-xp 00000000 08:01 525090 /usr/bin/python2.7
008e8000-008ea000 r--p 002e8000 08:01 525090 /usr/bin/python2.7
008ea000-00961000 rw-p 002ea000 08:01 525090 /usr/bin/python2.7
00961000-00984000 rw-p 00000000 00:00 0
01f10000-01ff6000 rw-p 00000000 00:00 0 [heap]
7fc8fc000000-7fc8fc021000 rw-p 00000000 00:00 0
7fc8fc021000-7fc900000000 ---p 00000000 00:00 0
7fc901246000-7fc90125c000 r-xp 00000000 08:01 38797837 /lib/x86_64-linux-gnu/libgcc_s.so.1
7fc90125c000-7fc90145b000 ---p 00016000 08:01 38797837 /lib/x86_64-linux-gnu/libgcc_s.so.1
7fc90145b000-7fc90145c000 rw-p 00015000 08:01 38797837 /lib/x86_64-linux-gnu/libgcc_s.so.1
7fc90145c000-7fc901504000 r-xp 00000000 08:01 51643749 /home/mingster/simGeo.docker/simgeo/lib/struct.so
7fc901504000-7fc901704000 ---p 000a8000 08:01 51643749 /home/mingster/simGeo.docker/simgeo/lib/struct.so
7fc901704000-7fc90170a000 rw-p 000a8000 08:01 51643749 /home/mingster/simGeo.docker/simgeo/lib/struct.so
7fc90170a000-7fc901752000 rw-p 00000000 00:00 0
7fc901752000-7fc901759000 r-xp 00000000 08:01 526635 /usr/lib/x86_64-linux-gnu/libffi.so.6.0.4
7fc901759000-7fc901958000 ---p 00007000 08:01 526635 /usr/lib/x86_64-linux-gnu/libffi.so.6.0.4
7fc901958000-7fc901959000 r--p 00006000 08:01 526635 /usr/lib/x86_64-linux-gnu/libffi.so.6.0.4
7fc901959000-7fc90195a000 rw-p 00007000 08:01 526635 /usr/lib/x86_64-linux-gnu/libffi.so.6.0.4
7fc90195a000-7fc901978000 r-xp 00000000 08:01 30543353 /usr/lib/python2.7/lib-dynload/_ctypes.x86_64-linux-gnu.so
7fc901978000-7fc901b77000 ---p 0001e000 08:01 30543353 /usr/lib/python2.7/lib-dynload/_ctypes.x86_64-linux-gnu.so
7fc901b77000-7fc901b78000 r--p 0001d000 08:01 30543353 /usr/lib/python2.7/lib-dynload/_ctypes.x86_64-linux-gnu.so
7fc901b78000-7fc901b7c000 rw-p 0001e000 08:01 30543353 /usr/lib/python2.7/lib-dynload/_ctypes.x86_64-linux-gnu.so
7fc901b7c000-7fc901e54000 r--p 00000000 08:01 529135 /usr/lib/locale/locale-archive
7fc901e54000-7fc901f5c000 r-xp 00000000 08:01 38797852 /lib/x86_64-linux-gnu/libm-2.23.so
7fc901f5c000-7fc90215b000 ---p 00108000 08:01 38797852 /lib/x86_64-linux-gnu/libm-2.23.so
7fc90215b000-7fc90215c000 r--p 00107000 08:01 38797852 /lib/x86_64-linux-gnu/libm-2.23.so
7fc90215c000-7fc90215d000 rw-p 00108000 08:01 38797852 /lib/x86_64-linux-gnu/libm-2.23.so
7fc90215d000-7fc902176000 r-xp 00000000 08:01 38797934 /lib/x86_64-linux-gnu/libz.so.1.2.8
7fc902176000-7fc902375000 ---p 00019000 08:01 38797934 /lib/x86_64-linux-gnu/libz.so.1.2.8
7fc902375000-7fc902376000 r--p 00018000 08:01 38797934 /lib/x86_64-linux-gnu/libz.so.1.2.8
7fc902376000-7fc902377000 rw-p 00019000 08:01 38797934 /lib/x86_64-linux-gnu/libz.so.1.2.8
7fc902377000-7fc902379000 r-xp 00000000 08:01 38797927 /lib/x86_64-linux-gnu/libutil-2.23.so
7fc902379000-7fc902578000 ---p 00002000 08:01 38797927 /lib/x86_64-linux-gnu/libutil-2.23.so
7fc902578000-7fc902579000 r--p 00001000 08:01 38797927 /lib/x86_64-linux-gnu/libutil-2.23.so
7fc902579000-7fc90257a000 rw-p 00002000 08:01 38797927 /lib/x86_64-linux-gnu/libutil-2.23.so
7fc90257a000-7fc90257d000 r-xp 00000000 08:01 38797825 /lib/x86_64-linux-gnu/libdl-2.23.so
7fc90257d000-7fc90277c000 ---p 00003000 08:01 38797825 /lib/x86_64-linux-gnu/libdl-2.23.so
7fc90277c000-7fc90277d000 r--p 00002000 08:01 38797825 /lib/x86_64-linux-gnu/libdl-2.23.so
7fc90277d000-7fc90277e000 rw-p 00003000 08:01 38797825 /lib/x86_64-linux-gnu/libdl-2.23.so
7fc90277e000-7fc90293e000 r-xp 00000000 08:01 38797811 /lib/x86_64-linux-gnu/libc-2.23.so
7fc90293e000-7fc902b3e000 ---p 001c0000 08:01 38797811 /lib/x86_64-linux-gnu/libc-2.23.so
7fc902b3e000-7fc902b42000 r--p 001c0000 08:01 38797811 /lib/x86_64-linux-gnu/libc-2.23.so
7fc902b42000-7fc902b44000 rw-p 001c4000 08:01 38797811 /lib/x86_64-linux-gnu/libc-2.23.so
7fc902b44000-7fc902b48000 rw-p 00000000 00:00 0
7fc902b48000-7fc902b60000 r-xp 00000000 08:01 38797898 /lib/x86_64-linux-gnu/libpthread-2.23.so
7fc902b60000-7fc902d5f000 ---p 00018000 08:01 38797898 /lib/x86_64-linux-gnu/libpthread-2.23.so
7fc902d5f000-7fc902d60000 r--p 00017000 08:01 38797898 /lib/x86_64-linux-gnu/libpthread-2.23.so
7fc902d60000-7fc902d61000 rw-p 00018000 08:01 38797898 /lib/x86_64-linux-gnu/libpthread-2.23.so
7fc902d61000-7fc902d65000 rw-p 00000000 00:00 0
7fc902d65000-7fc902d8b000 r-xp 00000000 08:01 38797787 /lib/x86_64-linux-gnu/ld-2.23.so
7fc902dc5000-7fc902f7b000 rw-p 00000000 00:00 0
7fc902f86000-7fc902f87000 rw-p 00000000 00:00 0
7fc902f87000-7fc902f88000 rwxp 00000000 00:00 0
7fc902f88000-7fc902f8a000 rw-p 00000000 00:00 0
7fc902f8a000-7fc902f8b000 r--p 00025000 08:01 38797787 /lib/x86_64-linux-gnu/ld-2.23.so
7fc902f8b000-7fc902f8c000 rw-p 00026000 08:01 38797787 /lib/x86_64-linux-gnu/ld-2.23.so
7fc902f8c000-7fc902f8d000 rw-p 00000000 00:00 0
7ffc38bde000-7ffc38bff000 rw-p 00000000 00:00 0 [stack]
7ffc38cd8000-7ffc38cda000 r--p 00000000 00:00 0 [vvar]
7ffc38cda000-7ffc38cdc000 r-xp 00000000 00:00 0 [vdso]
ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0 [vsyscall]
Aborted (core dumped)
Obwohl Sie der Fortran-Subroutine das 'bind'-Attribut geben, ist es bemerkenswert, dass die Dummy-Argumente nicht C-interoperabel sind (und sie haben nicht das Attribut' bind'). – francescalus
Sehr eng verwandt https://stackoverflow.com/questions/28543180/fortran-derived-types-containing-pinters-to-be-accessible-from-c –
@VladimirF Vielen Dank, das hilft sehr. Über C-Interoperabilität von Intel Fortran's mit C: [Fortran2003_InterOpC.ppt] (https://modelingguru.nasa.gov/servlet/JiveServlet/previewBody/1376-102-5-1827/Fortran2003_InterOpC.ppt) –