[pypy-svn] r54796 - pypy/dist/pypy/rlib
afa at codespeak.net
afa at codespeak.net
Fri May 16 19:34:07 CEST 2008
Author: afa
Date: Fri May 16 19:34:06 2008
New Revision: 54796
Added:
pypy/dist/pypy/rlib/rwin32.py
Modified:
pypy/dist/pypy/rlib/libffi.py
Log:
Start a new rlib\rwin32 module, to hold common types and functions from the win32 API,
and use it in libffi.
The module should be importable from all platforms, the WIN32 symbol
will always be available:
from pypy.rlib import rwin32
if rwin32.WIN32:
...
Tests will follow.
Modified: pypy/dist/pypy/rlib/libffi.py
==============================================================================
--- pypy/dist/pypy/rlib/libffi.py (original)
+++ pypy/dist/pypy/rlib/libffi.py Fri May 16 19:34:06 2008
@@ -14,6 +14,9 @@
_MS_WINDOWS = os.name == "nt"
+if _MS_WINDOWS:
+ from pypy.rlib import rwin32
+
if not _MS_WINDOWS:
includes = ['dlfcn.h', 'ffi.h']
include_dirs = []
@@ -75,10 +78,6 @@
ffi_closure = rffi_platform.Struct('ffi_closure', [])
- if _MS_WINDOWS:
- DWORD = rffi_platform.SimpleType("DWORD", rffi.UINT)
- BOOL = rffi_platform.SimpleType("BOOL", rffi.LONG)
-
def add_simple_type(type_name):
for name in ['size', 'alignment', 'type']:
setattr(CConfig, type_name + '_' + name,
@@ -198,32 +197,30 @@
return res
if _MS_WINDOWS:
- LoadLibrary = winexternal('LoadLibraryA', [rffi.CCHARP], rffi.VOIDP)
- GetProcAddress = winexternal('GetProcAddress', [rffi.VOIDP, rffi.CCHARP], rffi.VOIDP)
- FreeLibrary = winexternal('FreeLibrary', [rffi.VOIDP], cConfig.BOOL)
- GetLastError = winexternal('GetLastError', [], cConfig.DWORD)
-
def dlopen(name):
- res = LoadLibrary(name)
+ res = rwin32.LoadLibrary(name)
if not res:
# XXX format error message
- raise WindowsError(2, GetLastError())
+ raise WindowsError(2, rwin32.GetLastError())
return res
def dlclose(handle):
- res = FreeLibrary(handle)
+ res = rwin32.FreeLibrary(handle)
if res:
return -1
else:
return 0
def dlsym(handle, name):
- res = GetProcAddress(handle, name)
+ res = rwin32.GetProcAddress(handle, name)
if not res:
raise KeyError(name)
# XXX rffi.cast here...
return res
+ FormatError = rwin32.FormatError
+ LoadLibrary = rwin32.LoadLibrary
+
FFI_OK = cConfig.FFI_OK
FFI_BAD_TYPEDEF = cConfig.FFI_BAD_TYPEDEF
FFI_DEFAULT_ABI = rffi.cast(rffi.USHORT, cConfig.FFI_DEFAULT_ABI)
@@ -323,8 +320,9 @@
closureHeap = ClosureHeap()
-FUNCFLAG_STDCALL = 0
-FUNCFLAG_CDECL = 1 # for WINAPI calls
+FUNCFLAG_STDCALL = 0
+FUNCFLAG_CDECL = 1 # for WINAPI calls
+FUNCFLAG_PYTHONAPI = 4
class AbstractFuncPtr(object):
ll_cif = lltype.nullptr(FFI_CIFP.TO)
Added: pypy/dist/pypy/rlib/rwin32.py
==============================================================================
--- (empty file)
+++ pypy/dist/pypy/rlib/rwin32.py Fri May 16 19:34:06 2008
@@ -0,0 +1,81 @@
+""" External functions accessing the win32 api.
+Common types, functions from core win32 libraries, such as kernel32
+"""
+
+from pypy.rpython.tool import rffi_platform
+from pypy.translator.tool.cbuild import ExternalCompilationInfo
+from pypy.rpython.lltypesystem import lltype, rffi
+import os
+
+# This module can be imported on any platform,
+# but most symbols are not usable...
+WIN32 = os.name == "nt"
+
+if WIN32:
+ eci = ExternalCompilationInfo(
+ includes = ['windows.h'],
+ libraries = ['kernel32'],
+ )
+else:
+ eci = ExternalCompilationInfo()
+
+class CConfig:
+ _compilation_info_ = eci
+
+ if WIN32:
+ DWORD = rffi_platform.SimpleType("DWORD", rffi.UINT)
+ BOOL = rffi_platform.SimpleType("BOOL", rffi.LONG)
+
+ HANDLE = rffi_platform.SimpleType("HANDLE", rffi.VOIDP)
+ HLOCAL = rffi_platform.SimpleType("HLOCAL", rffi.VOIDP)
+
+ DEFAULT_LANGUAGE = rffi_platform.ConstantInteger(
+ "MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT)")
+
+ for name in """FORMAT_MESSAGE_ALLOCATE_BUFFER FORMAT_MESSAGE_FROM_SYSTEM
+ """.split():
+ locals()[name] = rffi_platform.ConstantInteger(name)
+
+
+for k, v in rffi_platform.configure(CConfig).items():
+ globals()[k] = v
+
+def winexternal(name, args, result):
+ return rffi.llexternal(name, args, result, compilation_info=eci, calling_conv='win')
+
+if WIN32:
+ GetLastError = winexternal('GetLastError', [], DWORD)
+
+ LoadLibrary = winexternal('LoadLibraryA', [rffi.CCHARP], rffi.VOIDP)
+ GetProcAddress = winexternal('GetProcAddress',
+ [rffi.VOIDP, rffi.CCHARP],
+ rffi.VOIDP)
+ FreeLibrary = winexternal('FreeLibrary', [rffi.VOIDP], BOOL)
+
+ LocalFree = winexternal('LocalFree', [HLOCAL], DWORD)
+
+ FormatMessage = winexternal(
+ 'FormatMessageA',
+ [DWORD, rffi.VOIDP, DWORD, DWORD, rffi.CCHARP, DWORD, rffi.VOIDP],
+ DWORD)
+
+
+ # A bit like strerror...
+ def FormatError(code):
+ "Return a message corresponding to the given Windows error code."
+ buf = lltype.malloc(rffi.VOIDPP.TO, 1, flavor='raw')
+
+ msglen = FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER |
+ FORMAT_MESSAGE_FROM_SYSTEM,
+ None,
+ code,
+ DEFAULT_LANGUAGE,
+ rffi.cast(rffi.VOIDP, buf),
+ 0, None)
+
+ # FormatMessage always appends a \n.
+ msglen -= 1
+
+ result = ''.join([buf[0][i] for i in range(msglen)])
+ LocalFree(buf[0])
+ return result
More information about the Pypy-commit
mailing list