mirror of https://github.com/python/cpython
gh-105751: test_ctypes gets Windows attrs from ctypes (#105758)
test_ctypes now gets attributes specific to Windows from the ctypes module, rather than relying on "from ctypes import *". Attributes: * ctypes.FormatError * ctypes.WINFUNCTYPE * ctypes.WinError * ctypes.WinDLL * ctypes.windll * ctypes.oledll * ctypes.get_last_error() * ctypes.set_last_error()
This commit is contained in:
parent
b87d288275
commit
ac7b551bde
|
@ -1,4 +1,5 @@
|
|||
import unittest
|
||||
import ctypes
|
||||
from ctypes import *
|
||||
from test.test_ctypes import need_symbol
|
||||
import _ctypes_test
|
||||
|
@ -6,8 +7,8 @@ import _ctypes_test
|
|||
dll = CDLL(_ctypes_test.__file__)
|
||||
|
||||
try:
|
||||
CALLBACK_FUNCTYPE = WINFUNCTYPE
|
||||
except NameError:
|
||||
CALLBACK_FUNCTYPE = ctypes.WINFUNCTYPE
|
||||
except AttributeError:
|
||||
# fake to enable this test on Linux
|
||||
CALLBACK_FUNCTYPE = CFUNCTYPE
|
||||
|
||||
|
|
|
@ -2,6 +2,7 @@ import functools
|
|||
import unittest
|
||||
from test import support
|
||||
|
||||
import ctypes
|
||||
from ctypes import *
|
||||
from test.test_ctypes import need_symbol
|
||||
from _ctypes import CTYPES_MAX_ARGCOUNT
|
||||
|
@ -152,7 +153,7 @@ class Callbacks(unittest.TestCase):
|
|||
|
||||
@need_symbol('WINFUNCTYPE')
|
||||
def test_i38748_stackCorruption(self):
|
||||
callback_funcType = WINFUNCTYPE(c_long, c_long, c_longlong)
|
||||
callback_funcType = ctypes.WINFUNCTYPE(c_long, c_long, c_longlong)
|
||||
@callback_funcType
|
||||
def callback(a, b):
|
||||
c = a + b
|
||||
|
@ -163,12 +164,10 @@ class Callbacks(unittest.TestCase):
|
|||
self.assertEqual(dll._test_i38748_runCallback(callback, 5, 10), 15)
|
||||
|
||||
|
||||
@need_symbol('WINFUNCTYPE')
|
||||
if hasattr(ctypes, 'WINFUNCTYPE'):
|
||||
class StdcallCallbacks(Callbacks):
|
||||
try:
|
||||
functype = WINFUNCTYPE
|
||||
except NameError:
|
||||
pass
|
||||
functype = ctypes.WINFUNCTYPE
|
||||
|
||||
|
||||
################################################################
|
||||
|
||||
|
@ -216,13 +215,14 @@ class SampleCallbacksTestCase(unittest.TestCase):
|
|||
global windowCount
|
||||
windowCount = 0
|
||||
|
||||
@WINFUNCTYPE(BOOL, HWND, LPARAM)
|
||||
@ctypes.WINFUNCTYPE(BOOL, HWND, LPARAM)
|
||||
def EnumWindowsCallbackFunc(hwnd, lParam):
|
||||
global windowCount
|
||||
windowCount += 1
|
||||
return True #Allow windows to keep enumerating
|
||||
|
||||
windll.user32.EnumWindows(EnumWindowsCallbackFunc, 0)
|
||||
user32 = ctypes.windll.user32
|
||||
user32.EnumWindows(EnumWindowsCallbackFunc, 0)
|
||||
|
||||
def test_callback_register_int(self):
|
||||
# Issue #8275: buggy handling of callback args under Win64
|
||||
|
|
|
@ -2,6 +2,7 @@
|
|||
# Byte order related?
|
||||
|
||||
import unittest
|
||||
import ctypes
|
||||
from ctypes import *
|
||||
from test.test_ctypes import need_symbol
|
||||
|
||||
|
@ -197,12 +198,8 @@ class CFunctions(unittest.TestCase):
|
|||
|
||||
# The following repeats the above tests with stdcall functions (where
|
||||
# they are available)
|
||||
try:
|
||||
WinDLL
|
||||
except NameError:
|
||||
def stdcall_dll(*_): pass
|
||||
else:
|
||||
class stdcall_dll(WinDLL):
|
||||
if hasattr(ctypes, 'WinDLL'):
|
||||
class stdcall_dll(ctypes.WinDLL):
|
||||
def __getattr__(self, name):
|
||||
if name[:2] == '__' and name[-2:] == '__':
|
||||
raise AttributeError(name)
|
||||
|
@ -210,7 +207,6 @@ else:
|
|||
setattr(self, name, func)
|
||||
return func
|
||||
|
||||
@need_symbol('WinDLL')
|
||||
class stdcallCFunctions(CFunctions):
|
||||
_dll = stdcall_dll(_ctypes_test.__file__)
|
||||
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
import unittest
|
||||
|
||||
import ctypes
|
||||
from ctypes import *
|
||||
from test.test_ctypes import need_symbol
|
||||
|
||||
|
@ -28,9 +29,8 @@ class Test(unittest.TestCase):
|
|||
|
||||
@need_symbol('oledll')
|
||||
def test_oledll(self):
|
||||
self.assertRaises(OSError,
|
||||
oledll.oleaut32.CreateTypeLib2,
|
||||
0, None, None)
|
||||
oleaut32 = ctypes.oledll.oleaut32
|
||||
self.assertRaises(OSError, oleaut32.CreateTypeLib2, 0, None, None)
|
||||
|
||||
if __name__ == "__main__":
|
||||
unittest.main()
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
import unittest, os, errno
|
||||
import threading
|
||||
|
||||
import ctypes
|
||||
from ctypes import *
|
||||
from ctypes.util import find_library
|
||||
|
||||
|
@ -44,33 +45,33 @@ class Test(unittest.TestCase):
|
|||
|
||||
@unittest.skipUnless(os.name == "nt", 'Test specific to Windows')
|
||||
def test_GetLastError(self):
|
||||
dll = WinDLL("kernel32", use_last_error=True)
|
||||
dll = ctypes.WinDLL("kernel32", use_last_error=True)
|
||||
GetModuleHandle = dll.GetModuleHandleA
|
||||
GetModuleHandle.argtypes = [c_wchar_p]
|
||||
|
||||
self.assertEqual(0, GetModuleHandle("foo"))
|
||||
self.assertEqual(get_last_error(), 126)
|
||||
self.assertEqual(ctypes.get_last_error(), 126)
|
||||
|
||||
self.assertEqual(set_last_error(32), 126)
|
||||
self.assertEqual(get_last_error(), 32)
|
||||
self.assertEqual(ctypes.set_last_error(32), 126)
|
||||
self.assertEqual(ctypes.get_last_error(), 32)
|
||||
|
||||
def _worker():
|
||||
set_last_error(0)
|
||||
ctypes.set_last_error(0)
|
||||
|
||||
dll = WinDLL("kernel32", use_last_error=False)
|
||||
dll = ctypes.WinDLL("kernel32", use_last_error=False)
|
||||
GetModuleHandle = dll.GetModuleHandleW
|
||||
GetModuleHandle.argtypes = [c_wchar_p]
|
||||
GetModuleHandle("bar")
|
||||
|
||||
self.assertEqual(get_last_error(), 0)
|
||||
self.assertEqual(ctypes.get_last_error(), 0)
|
||||
|
||||
t = threading.Thread(target=_worker)
|
||||
t.start()
|
||||
t.join()
|
||||
|
||||
self.assertEqual(get_last_error(), 32)
|
||||
self.assertEqual(ctypes.get_last_error(), 32)
|
||||
|
||||
set_last_error(0)
|
||||
ctypes.set_last_error(0)
|
||||
|
||||
if __name__ == "__main__":
|
||||
unittest.main()
|
||||
|
|
|
@ -1,9 +1,10 @@
|
|||
import unittest
|
||||
import ctypes
|
||||
from ctypes import *
|
||||
|
||||
try:
|
||||
WINFUNCTYPE
|
||||
except NameError:
|
||||
WINFUNCTYPE = ctypes.WINFUNCTYPE
|
||||
except AttributeError:
|
||||
# fake to enable this test on Linux
|
||||
WINFUNCTYPE = CFUNCTYPE
|
||||
|
||||
|
@ -39,7 +40,7 @@ class CFuncPtrTestCase(unittest.TestCase):
|
|||
# possible, as in C, to call cdecl functions with more parameters.
|
||||
#self.assertRaises(TypeError, c, 1, 2, 3)
|
||||
self.assertEqual(c(1, 2, 3, 4, 5, 6), 3)
|
||||
if not WINFUNCTYPE is CFUNCTYPE:
|
||||
if WINFUNCTYPE is not CFUNCTYPE:
|
||||
self.assertRaises(TypeError, s, 1, 2, 3)
|
||||
|
||||
def test_structures(self):
|
||||
|
@ -91,7 +92,7 @@ class CFuncPtrTestCase(unittest.TestCase):
|
|||
|
||||
def NoNullHandle(value):
|
||||
if not value:
|
||||
raise WinError()
|
||||
raise ctypes.WinError()
|
||||
return value
|
||||
|
||||
strchr = lib.my_strchr
|
||||
|
|
|
@ -5,20 +5,21 @@ show how the type behave.
|
|||
Later...
|
||||
"""
|
||||
|
||||
import ctypes
|
||||
from ctypes import *
|
||||
from test.test_ctypes import need_symbol
|
||||
import sys, unittest
|
||||
|
||||
try:
|
||||
WINFUNCTYPE
|
||||
except NameError:
|
||||
WINFUNCTYPE = ctypes.WINFUNCTYPE
|
||||
except AttributeError:
|
||||
# fake to enable this test on Linux
|
||||
WINFUNCTYPE = CFUNCTYPE
|
||||
|
||||
import _ctypes_test
|
||||
dll = CDLL(_ctypes_test.__file__)
|
||||
if sys.platform == "win32":
|
||||
windll = WinDLL(_ctypes_test.__file__)
|
||||
windll = ctypes.WinDLL(_ctypes_test.__file__)
|
||||
|
||||
class POINT(Structure):
|
||||
_fields_ = [("x", c_int), ("y", c_int)]
|
||||
|
|
|
@ -1,4 +1,5 @@
|
|||
from ctypes import *
|
||||
import ctypes
|
||||
import os
|
||||
import shutil
|
||||
import subprocess
|
||||
|
@ -72,18 +73,18 @@ class LoaderTest(unittest.TestCase):
|
|||
print(find_library("user32"))
|
||||
|
||||
if os.name == "nt":
|
||||
windll.kernel32.GetModuleHandleW
|
||||
windll["kernel32"].GetModuleHandleW
|
||||
windll.LoadLibrary("kernel32").GetModuleHandleW
|
||||
WinDLL("kernel32").GetModuleHandleW
|
||||
ctypes.windll.kernel32.GetModuleHandleW
|
||||
ctypes.windll["kernel32"].GetModuleHandleW
|
||||
ctypes.windll.LoadLibrary("kernel32").GetModuleHandleW
|
||||
ctypes.WinDLL("kernel32").GetModuleHandleW
|
||||
# embedded null character
|
||||
self.assertRaises(ValueError, windll.LoadLibrary, "kernel32\0")
|
||||
self.assertRaises(ValueError, ctypes.windll.LoadLibrary, "kernel32\0")
|
||||
|
||||
@unittest.skipUnless(os.name == "nt",
|
||||
'test specific to Windows')
|
||||
def test_load_ordinal_functions(self):
|
||||
import _ctypes_test
|
||||
dll = WinDLL(_ctypes_test.__file__)
|
||||
dll = ctypes.WinDLL(_ctypes_test.__file__)
|
||||
# We load the same function both via ordinal and name
|
||||
func_ord = dll[2]
|
||||
func_name = dll.GetString
|
||||
|
@ -114,14 +115,16 @@ class LoaderTest(unittest.TestCase):
|
|||
# also has a high address. 'call_function' should accept
|
||||
# addresses so large.
|
||||
from _ctypes import call_function
|
||||
advapi32 = windll.advapi32
|
||||
|
||||
advapi32 = ctypes.windll.advapi32
|
||||
# Calling CloseEventLog with a NULL argument should fail,
|
||||
# but the call should not segfault or so.
|
||||
self.assertEqual(0, advapi32.CloseEventLog(None))
|
||||
windll.kernel32.GetProcAddress.argtypes = c_void_p, c_char_p
|
||||
windll.kernel32.GetProcAddress.restype = c_void_p
|
||||
proc = windll.kernel32.GetProcAddress(advapi32._handle,
|
||||
b"CloseEventLog")
|
||||
|
||||
kernel32 = ctypes.windll.kernel32
|
||||
kernel32.GetProcAddress.argtypes = c_void_p, c_char_p
|
||||
kernel32.GetProcAddress.restype = c_void_p
|
||||
proc = kernel32.GetProcAddress(advapi32._handle, b"CloseEventLog")
|
||||
self.assertTrue(proc)
|
||||
# This is the real test: call the function via 'call_function'
|
||||
self.assertEqual(0, call_function(proc, (None,)))
|
||||
|
@ -130,7 +133,7 @@ class LoaderTest(unittest.TestCase):
|
|||
'test specific to Windows')
|
||||
def test_load_hasattr(self):
|
||||
# bpo-34816: shouldn't raise OSError
|
||||
self.assertFalse(hasattr(windll, 'test'))
|
||||
self.assertFalse(hasattr(ctypes.windll, 'test'))
|
||||
|
||||
@unittest.skipUnless(os.name == "nt",
|
||||
'test specific to Windows')
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
import unittest, sys
|
||||
|
||||
import ctypes
|
||||
from ctypes import *
|
||||
import _ctypes_test
|
||||
|
||||
|
@ -193,7 +194,7 @@ class PointersTestCase(unittest.TestCase):
|
|||
|
||||
# COM methods are boolean True:
|
||||
if sys.platform == "win32":
|
||||
mth = WINFUNCTYPE(None)(42, "name", (), None)
|
||||
mth = ctypes.WINFUNCTYPE(None)(42, "name", (), None)
|
||||
self.assertEqual(bool(mth), True)
|
||||
|
||||
def test_pointer_type_name(self):
|
||||
|
|
|
@ -1,4 +1,5 @@
|
|||
from ctypes import *
|
||||
import ctypes
|
||||
import contextlib
|
||||
from test import support
|
||||
import unittest
|
||||
|
@ -16,15 +17,17 @@ class call_function_TestCase(unittest.TestCase):
|
|||
|
||||
def test(self):
|
||||
from _ctypes import call_function
|
||||
windll.kernel32.LoadLibraryA.restype = c_void_p
|
||||
windll.kernel32.GetProcAddress.argtypes = c_void_p, c_char_p
|
||||
windll.kernel32.GetProcAddress.restype = c_void_p
|
||||
|
||||
hdll = windll.kernel32.LoadLibraryA(b"kernel32")
|
||||
funcaddr = windll.kernel32.GetProcAddress(hdll, b"GetModuleHandleA")
|
||||
kernel32 = ctypes.windll.kernel32
|
||||
kernel32.LoadLibraryA.restype = c_void_p
|
||||
kernel32.GetProcAddress.argtypes = c_void_p, c_char_p
|
||||
kernel32.GetProcAddress.restype = c_void_p
|
||||
|
||||
hdll = kernel32.LoadLibraryA(b"kernel32")
|
||||
funcaddr = kernel32.GetProcAddress(hdll, b"GetModuleHandleA")
|
||||
|
||||
self.assertEqual(call_function(funcaddr, (None,)),
|
||||
windll.kernel32.GetModuleHandleA(None))
|
||||
kernel32.GetModuleHandleA(None))
|
||||
|
||||
class CallbackTracbackTestCase(unittest.TestCase):
|
||||
# When an exception is raised in a ctypes callback function, the C
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
# Windows specific tests
|
||||
|
||||
import ctypes
|
||||
from ctypes import *
|
||||
import unittest, sys
|
||||
from test import support
|
||||
|
@ -14,15 +15,17 @@ class FunctionCallTestCase(unittest.TestCase):
|
|||
def test_SEH(self):
|
||||
# Disable faulthandler to prevent logging the warning:
|
||||
# "Windows fatal exception: access violation"
|
||||
kernel32 = ctypes.windll.kernel32
|
||||
with support.disable_faulthandler():
|
||||
# Call functions with invalid arguments, and make sure
|
||||
# that access violations are trapped and raise an
|
||||
# exception.
|
||||
self.assertRaises(OSError, windll.kernel32.GetModuleHandleA, 32)
|
||||
self.assertRaises(OSError, kernel32.GetModuleHandleA, 32)
|
||||
|
||||
def test_noargs(self):
|
||||
# This is a special case on win32 x64
|
||||
windll.user32.GetDesktopWindow()
|
||||
user32 = ctypes.windll.user32
|
||||
user32.GetDesktopWindow()
|
||||
|
||||
|
||||
@unittest.skipUnless(sys.platform == "win32", 'Windows-specific test')
|
||||
|
@ -73,17 +76,18 @@ class TestWinError(unittest.TestCase):
|
|||
# see Issue 16169
|
||||
import errno
|
||||
ERROR_INVALID_PARAMETER = 87
|
||||
msg = FormatError(ERROR_INVALID_PARAMETER).strip()
|
||||
msg = ctypes.FormatError(ERROR_INVALID_PARAMETER).strip()
|
||||
args = (errno.EINVAL, msg, None, ERROR_INVALID_PARAMETER)
|
||||
|
||||
e = WinError(ERROR_INVALID_PARAMETER)
|
||||
e = ctypes.WinError(ERROR_INVALID_PARAMETER)
|
||||
self.assertEqual(e.args, args)
|
||||
self.assertEqual(e.errno, errno.EINVAL)
|
||||
self.assertEqual(e.winerror, ERROR_INVALID_PARAMETER)
|
||||
|
||||
windll.kernel32.SetLastError(ERROR_INVALID_PARAMETER)
|
||||
kernel32 = ctypes.windll.kernel32
|
||||
kernel32.SetLastError(ERROR_INVALID_PARAMETER)
|
||||
try:
|
||||
raise WinError()
|
||||
raise ctypes.WinError()
|
||||
except OSError as exc:
|
||||
e = exc
|
||||
self.assertEqual(e.args, args)
|
||||
|
|
Loading…
Reference in New Issue