I have used swig to generate a wrapper of a library in C.
I need to replicate a code in C in python, but I don't know how to go from mmap to void **
in C:
char *image_buf;
...
axidma_fd = open("/dev/axidma", O_RDWR|O_EXCL);
...
image_buf = mmap(NULL, image_byte_size, PROT_READ|PROT_WRITE,
MAP_SHARED, axidma_fd, 0);
...
trans.num_frame_buffers = 1;
trans.frame_buffers = (void **)&image_buf;
in python
axidma_fd = os.open("/dev/axidma", os.O_RDWR|os.O_EXCL)
...
image_buf_1 = mmap.mmap(vdma_fd,188, mmap.MAP_SHARED,mmap.ACCESS_WRITE| mmap.ACCESS_READ);
...
# Convert mmap to c_char
char_pointer = c_char.from_buffer(image_buf_1) ???? (but type is c_char not pointer)
# Double void
trans.frame_buffers = ??
How do I convert an mmap to a pointer?
How do I get the double pointer?
Would it be more efficient to do it in python directly or by instantiating the libc library? for example like this
libc = ctypes.CDLL("libc.so.6")
image_mmap = ctypes.c_void_p(libc.mmap(0,188,mmap.ACCESS_WRITE| mmap.ACCESS_READ,mmap.MAP_SHARED,vdma_fd)
Thank you so much
EDITED 1 It explains me a little badly
if I do:
image_buf_1 = mmap.mmap(vdma_fd,188, mmap.MAP_SHARED,mmap.ACCESS_WRITE| mmap.ACCESS_READ)
image_map = c_void_p.from_buffer(image_buf_1)
image_map is None
>>> image_map
c_void_p(None)
On the other hand if I do
libc = ctypes.CDLL("libc.so.6")
image_mmap = ctypes.c_void_p(libc.mmap(0,188,mmap.ACCESS_WRITE| mmap.ACCESS_READ,mmap.MAP_SHARED,vdma_fd))
image_mmap is a valid pointer.
>>> image_mmap
c_void_p(18446744073709551615)
But when trying to assign it to
trans.frame_buffers = image_mmap
report:
trans.frame_buffers=image_mmap
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: in method 'axidma_video_transaction_frame_buffers_set', argument 2 of type 'void **'
I need convert mmap to void **
EDITED 2
Not working :(
I have defined:
class struct_axidma_video_transaction(Structure):
pass
struct_axidma_video_transaction.__slots__ = [
'channel_id',
'num_frame_buffers',
'frame_buffers',
'frame',
]
struct_axidma_video_transaction._fields_ = [
('channel_id', c_int),
('num_frame_buffers', c_int),
('frame_buffers', POINTER(POINTER(None))),
('frame', struct_axidma_video_frame),
]
I need to convert a mmap to a POINTER(POINTER to pass it to the frame_buffers parameter:
>>> from ctypes import c_int, c_void_p, byref, CDLL, POINTER,c_int64
>>> import mmap
>>> vdma_fd = os.open("/dev/axidma",os.O_RDWR|os.O_EXCL)
>>> type(vdma_fd)
<class 'int'>
>>> vdma_buf = mmap.mmap (vdma_fd,188,mmap.MAP_SHARED, mmap.ACCESS_READ | mmap.ACCESS_WRITE)
>>> type(vdma_buf)
<class 'mmap.mmap'>
>>> image_buf_p = c_void_p.from_buffer(vdma_buf)
>>> type(image_buf_p)
<class 'ctypes.c_void_p'>
>>> image_buf_pp = byref(image_buf_p)
>>> type(image_buf_pp)
<class 'CArgObject'>
>>> trans.frame_buffers = image_buf_pp
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: expected LP_c_void_p instance, got CArgObject
If I define:
>>> image_buf_pp = c_void_p.from_buffer(image_buf_p)
>>> type(image_buf_pp)
<class 'ctypes.c_void_p'>
>>> trans.frame_buffers = image_buf_pp
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: incompatible types, c_void_p instance instead of LP_c_void_p instance
>>>