diff options
author | Miss Islington (bot) <31488909+miss-islington@users.noreply.github.com> | 2019-11-18 14:29:15 (GMT) |
---|---|---|
committer | Vinay Sajip <vinay_sajip@yahoo.co.uk> | 2019-11-18 14:29:15 (GMT) |
commit | bef2815533011be9f0ce5fa2965bcada76b509b8 (patch) | |
tree | 662015be47ab7ac9d760fcc4e6de7bdf344d321c /Lib | |
parent | 21eb731057d614fb642c609ae89f66d75fa0ac3a (diff) | |
download | cpython-bef2815533011be9f0ce5fa2965bcada76b509b8.zip cpython-bef2815533011be9f0ce5fa2965bcada76b509b8.tar.gz cpython-bef2815533011be9f0ce5fa2965bcada76b509b8.tar.bz2 |
bpo-16576: Add checks for bitfields passed by value to functions. (GH-17097) (GH-17223)
(cherry picked from commit 106271568c58cfebae58f0c52b640dbe716ba2ce)
Diffstat (limited to 'Lib')
-rw-r--r-- | Lib/ctypes/test/test_structures.py | 81 |
1 files changed, 81 insertions, 0 deletions
diff --git a/Lib/ctypes/test/test_structures.py b/Lib/ctypes/test/test_structures.py index 8541674..19c4430 100644 --- a/Lib/ctypes/test/test_structures.py +++ b/Lib/ctypes/test/test_structures.py @@ -651,6 +651,87 @@ class StructureTestCase(unittest.TestCase): self.assertEqual(test5.nested.an_int, 0) self.assertEqual(test5.another_int, 0) + #@unittest.skipIf('s390' in MACHINE, 'Test causes segfault on S390') + def test_bitfield_by_value(self): + # See bpo-16576 + + # These should mirror the structures in Modules/_ctypes/_ctypes_test.c + + class Test6(Structure): + _fields_ = [ + ('A', c_int, 1), + ('B', c_int, 2), + ('C', c_int, 3), + ('D', c_int, 2), + ] + + test6 = Test6() + # As these are signed int fields, all are logically -1 due to sign + # extension. + test6.A = 1 + test6.B = 3 + test6.C = 7 + test6.D = 3 + dll = CDLL(_ctypes_test.__file__) + with self.assertRaises(TypeError) as ctx: + func = dll._testfunc_bitfield_by_value1 + func.restype = c_long + func.argtypes = (Test6,) + result = func(test6) + self.assertEqual(ctx.exception.args[0], 'item 1 in _argtypes_ passes ' + 'a struct/union with a bitfield by value, which is ' + 'unsupported.') + # passing by reference should be OK + func = dll._testfunc_bitfield_by_reference1 + func.restype = c_long + func.argtypes = (POINTER(Test6),) + result = func(byref(test6)) + self.assertEqual(result, -4) + self.assertEqual(test6.A, 0) + self.assertEqual(test6.B, 0) + self.assertEqual(test6.C, 0) + self.assertEqual(test6.D, 0) + + class Test7(Structure): + _fields_ = [ + ('A', c_uint, 1), + ('B', c_uint, 2), + ('C', c_uint, 3), + ('D', c_uint, 2), + ] + test7 = Test7() + test7.A = 1 + test7.B = 3 + test7.C = 7 + test7.D = 3 + func = dll._testfunc_bitfield_by_reference2 + func.restype = c_long + func.argtypes = (POINTER(Test7),) + result = func(byref(test7)) + self.assertEqual(result, 14) + self.assertEqual(test7.A, 0) + self.assertEqual(test7.B, 0) + self.assertEqual(test7.C, 0) + self.assertEqual(test7.D, 0) + + # for a union with bitfields, the union check happens first + class Test8(Union): + _fields_ = [ + ('A', c_int, 1), + ('B', c_int, 2), + ('C', c_int, 3), + ('D', c_int, 2), + ] + + test8 = Test8() + with self.assertRaises(TypeError) as ctx: + func = dll._testfunc_bitfield_by_value2 + func.restype = c_long + func.argtypes = (Test8,) + result = func(test8) + self.assertEqual(ctx.exception.args[0], 'item 1 in _argtypes_ passes ' + 'a union by value, which is unsupported.') + class PointerMemberTestCase(unittest.TestCase): def test(self): |