Этот вопрос относится к предыдущему вопросу, который я задал. А именно: this one, если кому-то интересно. В основном, я хочу показать массив C на Python, используя Py_buffer
, завернутый в объект memoryview
. Я получил его для работы с использованием PyBuffer_FillInfo
(work = я могу манипулировать данными в Python и записывать его в stdout в C), но если я попытаюсь свернуть собственный буфер, я получу segfault после функция C вернется.Использование Py_buffer и PyMemoryView_FromBuffer с различными товарами
Мне нужно, чтобы создать свой собственный буфер, поскольку PyBuffer_FillInfo предполагает, что формат голец, что делает itemsize поле 1. Мне нужно, чтобы быть в состоянии обеспечить детали размером 1, 2, 4 и 8.
Некоторые код , это рабочий пример:
Py_buffer *buf = (Py_buffer *) malloc(sizeof(*buf));
int r = PyBuffer_FillInfo(buf, NULL, malloc(sizeof(char) * 4), 4, 0, PyBUF_CONTIG);
PyObject *mv = PyMemoryView_FromBuffer(buf);
//Pack the memoryview object into an argument list and call the Python function
for (blah)
printf("%c\n", *buf->buf++); //this prints the values i set in the Python function
Глядя на реализацию PyBuffer_FillInfo
, которая на самом деле просто, я свернул свою собственную функцию, чтобы быть в состоянии предоставить пользовательские itemsizes:
//buffer creation function
Py_buffer *getReadWriteBuffer(int nitems, int itemsize, char *fmt) {
Py_buffer *buf = (Py_buffer *) malloc(sizeof(*buf));
buf->obj = NULL
buf->buf = malloc(nitems * itemsize);
buf->len = nitems * itemsize;
buf->readonly = 0;
buf->itemsize = itemsize;
buf->format = fmt;
buf->ndim = 1;
buf->shape = NULL;
buf->strides = NULL;
buf->suboffsets = NULL;
buf->internal = NULL;
return buf;
}
Как я использовать:
Py_buffer *buf = getReadWriteBuffer(32, 2, "h");
PyObject *mv = PyMemoryView_FromBuffer(buf);
// pack the memoryview into an argument list and call the Python function as before
for (blah)
printf("%d\n", *buf->buf); //this prints all zeroes even though i modify the array in Python
return 0;
//the segfault happens somewhere after here
В результате использования моего собственного объекта буфера является после выдаст ошибку сегментации функции C возвращается. Я действительно не понимаю, почему это происходит вообще. Любая помощь будет оценена по достоинству.
EDIT Согласно this question, который мне не удалось найти раньше, itemsize> 1 может даже не поддерживаться на всех. Это делает этот вопрос еще более интересным. Возможно, я мог бы использовать PyBuffer_FillInfo
с достаточно большим блоком памяти для хранения того, что я хочу (например, 32 C). В этом случае возникает вопрос о том, как назначать поплавки Python объекту memoryview
в функции Python. Вопросы вопросы.
Произошла утечка памяти, если 'Py_buffer' malloc'ed. Использовать стек, назначенный 'Py_buffer' – dyomas