Reputation: 1503
I'm writing a Python (2.6) extension, and I have a situation where I need to pass an opaque binary blob (with embedded null bytes) to my extension.
Here is a snippet of my code:
from authbind import authenticate
creds = 'foo\x00bar\x00'
authenticate(creds)
which throws the following:
TypeError: argument 1 must be string without null bytes, not str
Here is some of authbind.cc:
static PyObject* authenticate(PyObject *self, PyObject *args) {
const char* creds;
if (!PyArg_ParseTuple(args, "s", &creds))
return NULL;
}
So far, I have tried passing the blob as a raw string, like creds = '%r' % creds
, but that not only gives me embedded quotes around the string but also turns the \x00
bytes into their literal string representations, which I do not want to mess around with in C.
How can I accomplish what I need? I know about the y
, y#
and y*
PyArg_ParseTuple() format characters in 3.2, but I am limited to 2.6.
Upvotes: 4
Views: 3404
Reputation: 1503
Ok, I figured out a with the help of this link.
I used a PyByteArrayObject
(docs here) like this:
from authbind import authenticate
creds = 'foo\x00bar\x00'
authenticate(bytearray(creds))
And then in the extension code:
static PyObject* authenticate(PyObject *self, PyObject *args) {
PyByteArrayObject *creds;
if (!PyArg_ParseTuple(args, "O", &creds))
return NULL;
char* credsCopy;
credsCopy = PyByteArray_AsString((PyObject*) creds);
}
credsCopy
now holds the string of bytes, exactly as they are needed.
Upvotes: 4