Using ctypes with Python3 - arrays and structures

"Da Ronch," <[email protected]> Wed, 7 Dec 2011 11:01:42 +0000
Newsgroups gmane.comp.python.ctypes
Message-ID <[email protected]>

Hello Folks!

I try to call from Python several routines contained in a .so library generated from some Fortran 90 routines. All the objects in the library are resolved using the -fPIC flag when compiling the .so.

I have a sample code which looks like

[CODE]
#!/usr/bin/env python3
from numpy import *
from ctypes import *

lib_test = cdll.LoadLibrary("./lib_test.so")

method = lib_test.__test_MOD_wrap_xbelem
method.restype = None

MaxElNod = 3
NumElems = 2
NumNodes = (c_int *NumElems)()
Length   = zeros(NumElems, dtype=double, order="Fortran")
RBMass   = zeros((MaxElNod*NumElems,6,6), dtype=double, order="Fortran")

# Call the function in the .so
method(byref(c_int(NumElems)), byref(NumNodes), Length.ctypes.data_as(POINTER(c_double)), RBMass.ctypes.data_as(POINTER(c_double)) )
[/CODE]

I have few questions I hope you can help.

1) The code works fine as given above. However, I would like to pass the integer array as done with the array of type double. I would be keen to have a code which looks more like this

[CODE]
NumNodes = zeros(NumElems, dtype=int, order="Fortran")

method(byref(c_int(NumElems)), NumNodes.ctypes.data_as(POINTER(c_int)), Length.ctypes.data_as(POINTER(c_double)), RBMass.ctypes.data_as(POINTER(c_double)) )
[/CODE]

In this second case, the array NumNodes is equal to array([8589934594,          0]), whereas both elements of NumNodes should be equal to 2. I haven't said earlier, but NumNodes is only initialized in Python and it gets the values in the Fortran90 where they are computed in correct way. The correct results are produced with the first sample code. I am not able to figure out what I miss, as I presumed that the similar operations performed on the arrays of type double could be applied to arrays of type int.

2) The other question I have is about derived types. The Fortran 90 code makes use of derived types, and this is the reason that we have decided to create a .so library out of it to work with Python. At the moment, the Python script does not work with a corresponding structure and the fields of the derived types have been given each to a separate variable. This means that several input arguments are passed to a wrapper in the .so, and then appropriate fields are compacted to form a derived type in Fortran90. Arrays are also converted to multi-dimensional entities when it is the case.

I suppose I can ask for your expertice on how some tips. Imagine in Fortran90 there is a derived type of the form

[CODE]
 type xbelem
  integer:: NumNodes
  real(8):: Length
  real(8):: RBMass(MaxElNod,6,6)
 end type xbelem
[/CODE]

which is used in some routines, and it is initialized as

[CODE]
type(xbelem),intent(inout):: Elem(NumElems)
[/CODE]

What is the similar structure in Python? and how to pass it to the .so library?

I would like to thank you for any help.
Kind regards,

Andrea Da Ronch
Computational Fluid-Dynamics Laboratory,
Department of Engineering
Walker Building, The Quadrangle
University of Liverpool, Liverpool, L693GH

phone: +44-(0)151-7946843
cell: +44-(0)750-3346315
web: www.cfd4aircraft.com

------------------------------------------------------------------------------
Cloud Services Checklist: Pricing and Packaging Optimization
This white paper is intended to serve as a reference, checklist and point of 
discussion for anyone considering optimizing the pricing and packaging model 
of a cloud services business. Read Now!
http://www.accelacomm.com/jaw/sfnl/114/51491232/

_______________________________________________
ctypes-users mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/ctypes-users