4

I need to learn how to handle the char** in the C++ method below through Python ctypes. I was doing fine calling other methods that only need single pointers by using create_string_buffer(), but this method requires a pointer to an array of pointers.

ladybugConvertToMultipleBGRU32(
         LadybugContext          context,
        const  LadybugImage * pImage,
        unsigned char**        arpDestBuffers,
         LadybugImageInfo *   pImageInfo  )

How do I create a pointer to an array of six create_string_buffer(7963648) buffers in ctypes to pass to this C++ method for writing?

arpDestBuffers = pointer to [create_string_buffer(7963648) for i in xrange(6)]

Thank you for any help.


Both the answers given below work. I just didn't realize I had another problem in my code which prevented me from seeing the results right away. The first example is just as Luc wrote:

SixBuffers = c_char_p * 6
arpDestBuffers = SixBuffers(
            *[c_char_p(create_string_buffer(7963648).raw) for i in xrange(6)] )

The second example coming from omu_negru's answer is:

arpDestBuffers = (POINTER(c_char) * 6)()
arpDestBuffers[:] = [create_string_buffer(7963648) for i in xrange(6)]

Both are accepted by the function and overwritten. Typing print repr(arpDestBuffers[4][:10]) before and after calling the function gives:

'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00'
'\x15\x10\x0e\xff\x15\x10\x0e\xff\x14\x0f'

which shows that the function successfully overwrote the buffer with data.

2 Answers 2

1

Maybe Something like

SixBuffers = c_char_p * 6
arpDestBuffers = SixBuffers(*[c_char_p(create_string_buffer(7963648).raw) for i in xrange(6)])

Didin't try myself, so not sure that it works. Inspired by http://python.net/crew/theller/ctypes/tutorial.html#arrays

Sign up to request clarification or add additional context in comments.

3 Comments

Thanks. I tried it but it's not working for me. SixBuffers = c_char_p * 6 arpDestBuffers = SixBuffers(*[c_char_p(create_string_buffer('\x00'*10).raw) for i in xrange(6)]) print type(arpDestBuffers), repr(arpDestBuffers) print type(arpDestBuffers[0]), repr(arpDestBuffers[0]) This has the following output: <class '__main__.c_char_p_Array_6'> <__main__.c_char_p_Array_6 object at 0x01CB9F80> <type 'str'> ''
What happens when your call your C API? The buffers is empty? Is it the problem?
When passing the arpDestBuffers to the method, I get this error:ctypes.ArgumentError: argument 2: <type 'exceptions.TypeError'>: Don't know how to convert parameter 2 It's the same for most of the things I've tried.
0

after you create all the string_buffers you need by calling create_string_buffer you can create an array for them with :

var=(POINTER(c_char)*size)()  /* pointer_to_pointer */

Then you can fill it up by indexing it with var[index] and finally just call your function using it as an argument.... Works fine for me and i just tested it on a function with the signature void test_fn(char*,char**,unsigned char); written in C

4 Comments

I guess I don't know enough about Python to implement what you suggested. Where does 'your_pointer_to_pointer' come from? Thanks
sorry about that...was supposed to be a comment but i guess it just slipped....now it should be ok :) you make a new type (pointer array of size "size") and call the constructor and bind it to var.
To fill the var I have:var[:] = [create_string_buffer(7963648) for i in xrange(6)]. It seems that this var is what I want but I'm still getting a ctypes.ArgumentError when I try to pass it to the method. ctypes.ArgumentError: argument 2: <type 'exceptions.TypeError'>: Don't know how to convert parameter 2
The var did work! Thanks. I just found that parameter 2 actually means the 2nd parameter. I assumed it meant the 3rd. So now both parameters are good now.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.