Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Cython - converting list of strings to char **

How can I convert a python list of python strings to a null-terminated char** so I can pass it to external C function?

I have:

struct saferun_task:
    saferun_jail   *jail
    saferun_limits *limits

    char **argv
    int stdin_fd  
    int stdout_fd
    int stderr_fd

int saferun_run(saferun_inst *inst, saferun_task *task, saferun_stat *stat)

in cdef extern block

I want to convert something like ('./a.out', 'param1', 'param2') to something that I can assign to saferun_task.argv

How?

like image 520
xelez Avatar asked Mar 12 '12 10:03

xelez


Video Answer


1 Answers

From the Cython docs:

char* PyString_AsString (PyObject *string)

Returns a null-terminated representation of the contents of string. The pointer refers to the internal buffer of string, not a copy. The data must not be modified in any way. It must not be de-allocated.

I don't have a Cython compiler setup and handy atm (I can run this later and check) but, this should results in code that looks something like:

from libc.stdlib cimport malloc, free

cdef char **string_buf = malloc(len(pystr_list) * sizeof(char*))

for i in range(len(pystr_list)):
    string_buf[i] = PyString_AsString(pystr_list[i])

# Do stuff with string_buf as a char**
# ...

free(string_buf)

The pointer stringBuf is now a char ** to your original data without copying any strings -- though you shouldn't edit the data in each string as the strings should be treated as const char* (from docs). If you need to manipulate the strings you will have to memcpy the data or make new objects which you don't care about trashing in Python -- though since you have a tuple of strings I doubt you are editing them.

like image 170
Pyrce Avatar answered Sep 20 '22 02:09

Pyrce