ctypes для отображения и копирования данных - PullRequest
1 голос
/ 07 февраля 2020

Моя цель очень проста. Я хочу использовать mmap для выделения страницы памяти, а затем скопировать строку приветствия в эту страницу памяти.

Однако я получаю ошибку сегментации в строке libc.memcpy(pageLoc, temp, ctypes.c_int(len(temp.value)))

Как я Я все еще новичок в ctypes, я подозреваю, что это как-то связано с неправильным использованием указателя. Может кто-нибудь сказать мне, почему это происходит, и что я делаю не так?

import ctypes

# initialize the ctype library
libc = ctypes.CDLL("libc.so.6")
pthread = ctypes.CDLL("libpthread.so.0")

# size of pages on system
PAGESIZE = ctypes.c_int(libc.getpagesize())

# allocate the page
pageLoc = ctypes.c_void_p(libc.mmap(0, PAGESIZE, 0x7, 0x22, 0, 0)) # defined in https://sites.uclouvain.be/SystInfo/usr/include/bits/mman.h.html
print "[*] Created a page in memory at address %s" % hex(pageLoc.value)

# copy hello world into the memory space
temp = ctypes.c_char_p("Hello world!\n\x00")
print hex(ctypes.c_void_p(
    libc.memcpy(pageLoc, temp, ctypes.c_int(len(temp.value)))
))

# free the page
libc.munmap(pageLoc, PAGESIZE)

1 Ответ

1 голос
/ 07 февраля 2020

ctypes по умолчанию предполагает, что все функции возвращают int, что означает, что на 64-битной машине возвращенный указатель будет усечен до 32 бит, что приведет к его повреждению.

На всякий случай следует указать аргументы и типы результатов для каждой lib c вызываемой функции следующим образом:

from ctypes import *
libc.getpagesize.argtypes = []
libc.getpagesize.restype = c_int
libc.mmap.argtypes = [c_void_p, c_size_t, c_int, c_int, c_int, c_long]
libc.mmap.restype = c_void_p
libc.memcpy.argtypes = [c_void_p, c_void_p, c_size_t]
libc.memcpy.restype = c_void_p
libc.munmap.argtypes = [c_void_p, c_size_t]
libc.munmap.restype = c_int

С этими определениями типов ваш код работает правильно. Кроме того, он правильно проверяет все параметры и приводит к ним типы возвращаемых значений, поэтому вы можете удалить приведения к вызовам libc.

...