]> git.ipfire.org Git - thirdparty/Python/cpython.git/commitdiff
gh-105751: test_ctypes gets Windows attrs from ctypes (#105758)
authorVictor Stinner <vstinner@python.org>
Wed, 14 Jun 2023 02:46:47 +0000 (04:46 +0200)
committerGitHub <noreply@github.com>
Wed, 14 Jun 2023 02:46:47 +0000 (04:46 +0200)
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()

Lib/test/test_ctypes/test_as_parameter.py
Lib/test/test_ctypes/test_callbacks.py
Lib/test/test_ctypes/test_cfuncs.py
Lib/test/test_ctypes/test_checkretval.py
Lib/test/test_ctypes/test_errno.py
Lib/test/test_ctypes/test_funcptr.py
Lib/test/test_ctypes/test_functions.py
Lib/test/test_ctypes/test_loading.py
Lib/test/test_ctypes/test_pointers.py
Lib/test/test_ctypes/test_random_things.py
Lib/test/test_ctypes/test_win32.py

index e9ec9ad847b487f440343e2f286fefb30f1ed17b..fcf99ff057920be55f77ca10c49ea53956011e74 100644 (file)
@@ -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
 
index b185e388ab1527d4f5ff095bd51273c5aab1383f..a5c2e430d85ad05c8dbdecb701fd8753687ee054 100644 (file)
@@ -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')
-class StdcallCallbacks(Callbacks):
-    try:
-        functype = WINFUNCTYPE
-    except NameError:
-        pass
+if hasattr(ctypes, 'WINFUNCTYPE'):
+    class StdcallCallbacks(Callbacks):
+        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
index 7cba4b0e527f4d9ad965f0b8540671f80d35f77a..d66e679799c54378973af3cf8a7bf0b10b54245e 100644 (file)
@@ -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,9 +207,8 @@ else:
             setattr(self, name, func)
             return func
 
-@need_symbol('WinDLL')
-class stdcallCFunctions(CFunctions):
-    _dll = stdcall_dll(_ctypes_test.__file__)
+    class stdcallCFunctions(CFunctions):
+        _dll = stdcall_dll(_ctypes_test.__file__)
 
 if __name__ == '__main__':
     unittest.main()
index 1492099f4b9e99c40d83b41975054b7147f2ed2c..b4834322ea7f8a57770dad468aa96824552ef8b8 100644 (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()
index 3685164dde62143a4dea31eef31aac88554c3e07..bfc20bd68fc7f0575f1a8ee19fd14847859e0fa5 100644 (file)
@@ -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()
index e0b9b54e97f67346f111dd32f48c8adc8aca290d..ef6772c6e88b654a350440b19fe2827c37c919c0 100644 (file)
@@ -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
index 703bd2c601ccf66173dc7ac7da0cce0ad390abdf..3f331703a0db220255e14dd2c063bf6e4bdd2f2d 100644 (file)
@@ -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)]
index f2434926a51714ba69307a0a04cb66f577c58790..fec26aab1d8031cbc023690e202163c4e3a6c3eb 100644 (file)
@@ -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')
index e97515879f1f0e09f529e84d91e6e9bfaeed7182..7b6c3f5babe481861b055b680ee81a6db1257186 100644 (file)
@@ -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):
index 2988e275cf4bbf273c55d17ba231cbb9aeb1c173..cfd355a7f0835f4389237454a186a768cf67318d 100644 (file)
@@ -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
index e51bdc8ad6b0719be53ff8dc4801e764fd4ea90b..43ed9dbe10c28e592fa02c2cc24c4a2f6970bc29 100644 (file)
@@ -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)