コード例 #1
0
ファイル: loader.py プロジェクト: Rinoahu/PeachPy
    def __init__(self, code_size, data_size=0):
        from peachpy.util import is_int
        if not is_int(code_size):
            raise TypeError("code size must be an integer")
        if not is_int(data_size):
            raise TypeError("data size must be an integer")
        if code_size <= 0:
            raise ValueError("code size must be positive")
        if data_size < 0:
            raise ValueError("data size must be non-negative")

        import mmap
        self.allocation_granularity = max(mmap.ALLOCATIONGRANULARITY, mmap.PAGESIZE)
        self.code_address = None
        self.code_size = self.allocation_size(code_size)
        self.data_address = None
        self.data_size = self.allocation_size(data_size)

        self._release_memory = None

        osname = sys.platform.lower()
        if osname == "darwin" or osname.startswith("linux"):
            import ctypes

            if osname == "darwin":
                libc = ctypes.cdll.LoadLibrary("libc.dylib")
            else:
                libc = ctypes.cdll.LoadLibrary("libc.so.6")

            # void* mmap(void* addr, size_t len, int prot, int flags, int fd, off_t offset)
            mmap_function = libc.mmap
            mmap_function.restype = ctypes.c_void_p
            mmap_function.argtype = [ctypes.c_void_p, ctypes.c_size_t,
                             ctypes.c_int, ctypes.c_int,
                             ctypes.c_int, ctypes.c_size_t]
            # int munmap(void* addr, size_t len)
            munmap_function = libc.munmap
            munmap_function.restype = ctypes.c_int
            munmap_function.argtype = [ctypes.c_void_p, ctypes.c_size_t]

            def munmap(address, size):
                munmap_result = munmap_function(ctypes.c_void_p(address), size)
                assert munmap_result == 0

            self._release_memory = lambda address_size: munmap(address_size[0], address_size[1])

            # Allocate code segment
            code_address = mmap_function(None, self.code_size,
                                         mmap.PROT_READ | mmap.PROT_WRITE | mmap.PROT_EXEC,
                                         mmap.MAP_ANON | mmap.MAP_PRIVATE,
                                         -1, 0)
            if code_address == -1:
                raise OSError("Failed to allocate memory for code segment")
            self.code_address = code_address

            if self.data_size > 0:
                # Allocate data segment
                data_address = mmap_function(None, self.data_size,
                                             mmap.PROT_READ | mmap.PROT_WRITE,
                                             mmap.MAP_ANON | mmap.MAP_PRIVATE,
                                             -1, 0)
                if data_address == -1:
                    raise OSError("Failed to allocate memory for data segment")
                self.data_address = data_address
        elif osname == "win32":
            import ctypes

            # From WinNT.h
            PAGE_READWRITE = 0x04
            PAGE_EXECUTE_READWRITE = 0x40
            MEM_COMMIT = 0x1000
            MEM_RESERVE = 0x2000
            MEM_RELEASE = 0x8000

            # LPVOID WINAPI VirtualAlloc(LPVOID address, SIZE_T size, DWORD allocationType, DWORD protect)
            VirtualAlloc_function = ctypes.windll.kernel32.VirtualAlloc
            VirtualAlloc_function.restype = ctypes.c_void_p
            VirtualAlloc_function.argtype = [ctypes.c_void_p, ctypes.c_size_t, ctypes.c_ulong, ctypes.c_ulong]
            # BOOL WINAPI VirtualFree(LPVOID lpAddress, SIZE_T dwSize, DWORD  dwFreeType)
            VirtualFree_function = ctypes.windll.kernel32.VirtualFree
            VirtualFree_function.restype = ctypes.c_int
            VirtualFree_function.argtype = [ctypes.c_void_p, ctypes.c_size_t, ctypes.c_ulong]

            def VirtualFree(address, size):
                VirtualFree_result = VirtualFree_function(address, size, MEM_RELEASE)
                assert VirtualFree_result != 0

            self._release_memory = lambda address_size: VirtualFree(address_size[0], address_size[1])

            # Allocate code segment
            code_address = VirtualAlloc_function(None, self.code_size,
                                                 MEM_RESERVE | MEM_COMMIT,
                                                 PAGE_EXECUTE_READWRITE)
            if not code_address:
                raise OSError("Failed to allocate memory for code segment")
            self.code_address = code_address

            if self.data_size > 0:
                # Allocate data segment
                data_address = VirtualAlloc_function(None, self.data_size,
                                                     MEM_RESERVE | MEM_COMMIT,
                                                     PAGE_READWRITE)
                if not data_address:
                    raise OSError("Failed to allocate memory for data segment")
                self.data_address = data_address
        elif osname == "nacl":
            import dynacl

            # Allocate code segment
            self.allocation = dynacl.allocate(self.code_size, self.data_size)
            self.code_address = self.allocation.code_address
            self.data_address = self.allocation.data_address
            self.copy_code = self._nacl_copy_code
        else:
            raise ValueError("Unknown host OS: " + osname)
コード例 #2
0
    def __init__(self, code_size, data_size=0):
        from peachpy.util import is_int
        if not is_int(code_size):
            raise TypeError("code size must be an integer")
        if not is_int(data_size):
            raise TypeError("data size must be an integer")
        if code_size <= 0:
            raise ValueError("code size must be positive")
        if data_size < 0:
            raise ValueError("data size must be non-negative")

        import mmap
        self.allocation_granularity = max(mmap.ALLOCATIONGRANULARITY, mmap.PAGESIZE)
        self.code_address = None
        self.code_size = self.allocation_size(code_size)
        self.data_address = None
        self.data_size = self.allocation_size(data_size)

        self._release_memory = None

        osname = sys.platform.lower()
        if osname == "darwin" or osname.startswith("linux"):
            import ctypes

            if osname == "darwin":
                libc = ctypes.cdll.LoadLibrary("libc.dylib")
            else:
                libc = ctypes.cdll.LoadLibrary("libc.so.6")

            # void* mmap(void* addr, size_t len, int prot, int flags, int fd, off_t offset)
            mmap_function = libc.mmap
            mmap_function.restype = ctypes.c_void_p
            mmap_function.argtype = [ctypes.c_void_p, ctypes.c_size_t,
                             ctypes.c_int, ctypes.c_int,
                             ctypes.c_int, ctypes.c_size_t]
            # int munmap(void* addr, size_t len)
            munmap_function = libc.munmap
            munmap_function.restype = ctypes.c_int
            munmap_function.argtype = [ctypes.c_void_p, ctypes.c_size_t]

            def munmap(address, size):
                munmap_result = munmap_function(address, size)
                assert munmap_result == 0

            self._release_memory = lambda address_size: munmap(address_size[0], address_size[1])

            # Allocate code segment
            code_address = mmap_function(None, self.code_size,
                                         mmap.PROT_READ | mmap.PROT_WRITE | mmap.PROT_EXEC,
                                         mmap.MAP_ANON | mmap.MAP_PRIVATE,
                                         -1, 0)
            if code_address == -1:
                raise OSError("Failed to allocate memory for code segment")
            self.code_address = code_address

            if self.data_size > 0:
                # Allocate data segment
                data_address = mmap_function(None, self.data_size,
                                             mmap.PROT_READ | mmap.PROT_WRITE,
                                             mmap.MAP_ANON | mmap.MAP_PRIVATE,
                                             -1, 0)
                if data_address == -1:
                    raise OSError("Failed to allocate memory for data segment")
                self.data_address = data_address
        elif osname == "win32":
            import ctypes

            # From WinNT.h
            PAGE_READWRITE = 0x04
            PAGE_EXECUTE_READWRITE = 0x40
            MEM_COMMIT = 0x1000
            MEM_RESERVE = 0x2000
            MEM_RELEASE = 0x8000

            # LPVOID WINAPI VirtualAlloc(LPVOID address, SIZE_T size, DWORD allocationType, DWORD protect)
            VirtualAlloc_function = ctypes.windll.kernel32.VirtualAlloc
            VirtualAlloc_function.restype = ctypes.c_void_p
            VirtualAlloc_function.argtype = [ctypes.c_void_p, ctypes.c_size_t, ctypes.c_ulong, ctypes.c_ulong]
            # BOOL WINAPI VirtualFree(LPVOID lpAddress, SIZE_T dwSize, DWORD  dwFreeType)
            VirtualFree_function = ctypes.windll.kernel32.VirtualFree
            VirtualFree_function.restype = ctypes.c_int
            VirtualFree_function.argtype = [ctypes.c_void_p, ctypes.c_size_t, ctypes.c_ulong]

            def VirtualFree(address, size):
                VirtualFree_result = VirtualFree_function(address, size, MEM_RELEASE)
                assert VirtualFree_result != 0

            self._release_memory = lambda address_size: VirtualFree(address_size[0], address_size[1])

            # Allocate code segment
            code_address = VirtualAlloc_function(None, self.code_size,
                                                 MEM_RESERVE | MEM_COMMIT,
                                                 PAGE_EXECUTE_READWRITE)
            if not code_address:
                raise OSError("Failed to allocate memory for code segment")
            self.code_address = code_address

            if self.data_size > 0:
                # Allocate data segment
                data_address = VirtualAlloc_function(None, self.data_size,
                                                     MEM_RESERVE | MEM_COMMIT,
                                                     PAGE_READWRITE)
                if not data_address:
                    raise OSError("Failed to allocate memory for data segment")
                self.data_address = data_address
        elif osname == "nacl":
            import dynacl

            # Allocate code segment
            self.allocation = dynacl.allocate(self.code_size, self.data_size)
            self.code_address = self.allocation.code_address
            self.data_address = self.allocation.data_address
            self.copy_code = self._nacl_copy_code
        else:
            raise ValueError("Unknown host OS: " + osname)