[Pyrex] opaque types and pyrex

Lenard Lindstrom len-l at telus.net
Thu Aug 14 07:59:42 CEST 2008


Mattias Holm wrote:
> I am trying to wrap a couple of functions returning pointers to  
> opaque / extern types:
>
> cdef extern from "physics/orbit.h":
>      ctypedef struct orb_sys_t
>      ctypedef struct orb_obj_t
>      orb_sys_t* orbit_add_sys(orb_sys_t *parent,  char *name, float  
> radius, float w0)
>      orb_obj_t* orbit_add_obj(orb_sys_t *sys,  char *name, float  
> radius, float w0, float m)
>
>
> def addOrbitalSys(name, radius, w0):
>      return orbit_add_sys(NULL, name, radius, w0)
>
> def addOrbitalSysWithParent(parent, name, radius, w0):
>      return orbit_add_sys(parent, name, radius, w0)
>
>
> Then I get the error message: Cannot convert 'orb_sys_t *' to Python  
> object
>
> Is there a good way to get around it?
>
>
>
>   
The preferred way is to wrap the C pointers in extension types. The 
factory functions would be called in the constructor method __cinit__. 
Other C functions that use the structures would then be called from methods.

cdef class OrbitObj:
    cdef orb_sys_t *orb_sys

    def __cinit__(self, parent, char *name, float radius, float w0):
        if parent is None:
            self.orb_sys = orb_add_sys(NULL, name, radius, w0)
        elif isinstance(parent, OrbitObj):
            self.orb_sys = orb_add_sys(parent.orb_sys, name, radius, w0)
        else:
            raise TypeError("Parent not an OrbitObj object or None")

    def __dealloc__(self):
        # C function call to delete obj_sys object.


Alternatively you can a CObject, described in section 7.5.10 or the 
"Python/C API Reference Manual", to pass C pointers between functions. 
But it is intended more for passing C function pointers between 
extension modules.

-- 
Lenard Lindstrom
<len-l at telus.net>




More information about the Pyrex mailing list