我想创建一个可变大小的数组传递给Fortran DLL并获得结果(通过引用),这样我就可以直接获得值。在
在Fortran代码中,我使用可分配变量,我认为它就像指向分配地址的指针。在
我可以做到以下几点,但我不知道如何在结构上做到:
test = POINTER(c_double)()
sim.structtest(input, byref(test))
Fortran中test
的定义是
原代码:
Python代码(结构测试.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代码(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)
我将Fortran编译为DLL,如下所示:
ifort -shared -fPIC -static-intel -o struct.so struct.f90
我将Python执行为:
python structtest.py
我得到的结果是:
*** 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)
谢谢大家
下面是Python向Fortran传递多维数组的工作示例
python代码:
fortran代码:
^{pr2}$输出:
内存中所谓的可分配组件描述符的布局是Fortran处理器特有的。对于一个可分配的数组组件,它永远不仅仅是一个内存地址。有关描述符的详细信息,您需要查阅Fortran处理器的文档。依赖于描述符布局的代码本质上是特定于处理器的。在
“英特尔编译器”当前版本的相关文档可在Handling Fortran Array Descriptors部分找到。在
Fortran 2018的当前草案提供了与可分配伪参数进行互操作的附加功能,但仍存在特定于平台的特性。在
(在所示的代码中,您使用了内部模块ISO\u绑定,但代码似乎没有引用其中的任何内容……)
相关问题 更多 >
编程相关推荐