Skip to content Skip to sidebar Skip to footer

How Can A #defined C Value Be Exposed To Python In A Cython Module?

I'd like to make the integer constants (ACTIVE_TAG, etc) defined here: //island management, m_activationState1 #define ACTIVE_TAG 1 #define ISLAND_SLEEPING 2 #define WANTS_DEACTIVA

Solution 1:

Here's one way, which, while seemingly tedious, could feasibly be automated for any given .h file as input:

Step 1. Get all the constants you want into a file, say bulletdefs.h, which has the #defines but with leading underscores, e.g:

#define _ACTIVE_TAG 1
#define _ISLAND_SLEEPING 2
#define _WANTS_DEACTIVATION 3
#define _DISABLE_DEACTIVATION 4
#define _DISABLE_SIMULATION 5

Step 2. Insert a section into the pyx file for your module, say bullet.pyx:

cdef extern from "bulletdefs.h":
    cdef int _ACTIVE_TAG
    cdef int _ISLAND_SLEEPING
    cdef int _WANTS_DEACTIVATION
    cdef int _DISABLE_DEACTIVATION
    cdef int _DISABLE_SIMULATION

ACTIVE_TAG = _ACTIVE_TAG
ISLAND_SLEEPING = _ISLAND_SLEEPING
WANTS_DEACTIVATION = _WANTS_DEACTIVATION
DISABLE_DEACTIVATION = _DISABLE_DEACTIVATION
DISABLE_SIMULATION = _DISABLE_SIMULATION

Then, when you compile your module, you should get the intended effect:

Python 2.7.1+ (r271:86832, Apr 11 2011, 18:05:24) 
[GCC 4.5.2] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> import bullet
>>> bullet.ACTIVE_TAG
1
>>> bullet.DISABLE_SIMULATION
5
>>>

Solution 2:

It worked in my case. Maybe can be helpful for someone too:

In my case I needed to export a #define from a linux kernel library. And it worked for my:

# your_pxd_file.pxd
cdef extern from "sched.h": #here are lots of `#define`'s clauses. something like the link: https://github.com/spotify/linux/blob/master/include/linux/sched.h
    cdef enum:
        CLONE_NEWNS

In your .pyx file:

from your_compiled_cython_package cimport CLONE_NEWNS

print(CLONE_NEWNS)

I hope this can be helpful for someone as it was for me =)


Solution 3:

Example header:

// myheader.hh
#ifndef MYHEADER
#define MYHEADER

#define NONE 0

#endif

An answer from my experience for my similar case, without const keyword, a variable is created and it's not constant as of #define. I found some assignment to NONE at the end of the generated C++ file by Cython and it's not allowed to assign to macro.

cdef extern from "myheader.hh":
    int NONE

This is a real constant:

cdef extern from "myheader.hh":
    const int NONE

Bug in Cython without const keyword: https://github.com/cython/cython/issues/2621


Post a Comment for "How Can A #defined C Value Be Exposed To Python In A Cython Module?"