[Pyrex] Allocating an array.array of a specific length in pyrex
Chris Lambacher
lambacck at gmail.com
Wed Jun 8 20:56:29 CEST 2005
And we have a winner.
For reference the final code is below.
Thanks for your help,
-Chris
import array
cdef extern from "Python.h":
int PyObject_AsWriteBuffer(object obj, void **buffer, int *buffer_len)
int PyObject_AsReadBuffer(object obj, void **buffer, int *buffer_len)
object PyString_FromStringAndSize(char *, int)
char *PyString_AsString(object obj)
cdef int get_w_buffer(obj, unsigned char **data, int *length) except -1:
cdef int result
cdef void *vd
# use a void *
result = PyObject_AsWriteBuffer(obj, &vd, length)
data[0] = <unsigned char *>vd
return result
cdef int get_r_buffer(obj, unsigned char **data, int *length) except -1:
cdef int result
cdef void *vd
# use a void *
result = PyObject_AsReadBuffer(obj, &vd, length)
data[0] = <unsigned char *>vd
return result
def encode(int w, int h, in_a):
cdef unsigned int pixels, a_off, str_off#, buffer_len
cdef int res, inlen, buffer_len
cdef unsigned char *in_str, *out_str
res = get_r_buffer(in_a, &in_str, &inlen)
if res:
raise Exception, "Could not get a readable buffer from the input"
pixels = w * h
a = PyString_FromStringAndSize(NULL, pixels * 2)
out_str = <unsigned char *> PyString_AsString(a)
buffer_len = pixels * 2
str_off = 0
a_off = 0
while a_off < buffer_len and str_off < inlen:
out_str[a_off] = in_str[str_off]
out_str[a_off+1] = (in_str[str_off+1] + in_str[str_off+4])/2
out_str[a_off+2] = in_str[str_off+3]
out_str[a_off+3] = (in_str[str_off+2] + in_str[str_off+5])/2
str_off = str_off + 6
a_off = a_off + 4
return a
On 6/8/05, Chris Lambacher <lambacck at gmail.com> wrote:
> I replaced:
> a = array.array('B', , [0] * (pixels * 2))
> with:
> a = PyString_FromStringAndSize(NULL, pixels * 2)
>
> and got:
> C:\work\testing\plink_o_ip>python ycbycr.py
> Traceback (most recent call last):
> File "ycbycr.py", line 62, in ?
> ycbycr = image2ycbycr(im)
> File "ycbycr.py", line 38, in image2ycbycr
> return _ycbycr.ycbcr2ycbycr(w, h, ycbcrim.tostring())
> File "_ycbycr.pyx", line 42, in _ycbycr.ycbcr2ycbycr
> res = get_w_buffer(a, &out_str, &buffer_len)
> TypeError: Cannot use string as modifiable buffer
>
> Strings are not mutable so this is not going to work for me :(
>
> Is there a way to allocate a python buffer object and give that to
> array.array or a string object?
>
> -Chris
>
> On 6/8/05, Chris Lambacher <lambacck at gmail.com> wrote:
> > The memory is not temporary, I am passing it out as an array, thus the
> > malloc/free route will require double allocation(once for malloc/free,
> > once for array.array). I am not using string because when I tried to
> > pass the data in as string, pyrex complained about the conversion.
> > However, I could probably use the same PyObject_AsReadBuffer function
> > call to get at the data passed in to the function as a string and then
> > pass it out as a string as well using the interface suggested (
> > PyString_FromStringAndSize and PyString_AsString ). Perhapse I need
> > to substitute PyObject_AsWriteBuffer instead of PyString_AsString in
> > order for my changes to get propegated back to the string object?
> >
> > -Chris
> >
> >
> > On 6/8/05, Adam Langley <alangley at gmail.com> wrote:
> > > On 6/8/05, Chris Lambacher <lambacck at gmail.com> wrote:
> > > > My question is, is there a better way to
> > > > allocate the memory for the array.array object than:
> > > > a = array.array('B', [0] * (pixels * 2))
> > >
> > > cdef unsigned char *buffer
> > > temp_string = PyString_FromStringAndSize(NULL, length)
> > > buffer = <unsigned char *> PyString_AsString(temp_string)
> > >
> > > That's one way to do it. But it looks like you just want an area of
> > > memory so why not:
> > >
> > > cdef extern from "stdlib.h":
> > > ctypedef unsigned long size_t
> > > void *malloc(size_t size)
> > > void free(void *mem)
> > >
> > > ?
> > >
> > > AGL
> > >
> > > --
> > > Adam Langley agl at imperialviolet.org
> > > http://www.imperialviolet.org (+44) (0)7906 332512
> > > PGP: 9113 256A CC0F 71A6 4C84 5087 CDA5 52DF 2CB6 3D60
> > >
> >
> >
> > --
> > Christopher Lambacher
> > lambacck at computer.org
> >
>
>
> --
> Christopher Lambacher
> lambacck at computer.org
>
--
Christopher Lambacher
lambacck at computer.org
More information about the Pyrex
mailing list