From 581e427c3c5e96ab52bf4470cdeeba9c7ef8f339 Mon Sep 17 00:00:00 2001 From: CPython Developers <> Date: Wed, 21 Jan 2026 02:07:28 +0900 Subject: [PATCH] Update struct from v3.14.2 --- Lib/struct.py | 4 +-- Lib/test/test_struct.py | 63 ++++++++++++++++++++++++++++++++--------- 2 files changed, 52 insertions(+), 15 deletions(-) diff --git a/Lib/struct.py b/Lib/struct.py index d6bba588636..ff98e8c4cb3 100644 --- a/Lib/struct.py +++ b/Lib/struct.py @@ -11,5 +11,5 @@ ] from _struct import * -from _struct import _clearcache -from _struct import __doc__ +from _struct import _clearcache # noqa: F401 +from _struct import __doc__ # noqa: F401 diff --git a/Lib/test/test_struct.py b/Lib/test/test_struct.py index ef5602d083b..a03438f1604 100644 --- a/Lib/test/test_struct.py +++ b/Lib/test/test_struct.py @@ -1,22 +1,28 @@ from collections import abc +from itertools import combinations import array import gc import math import operator import unittest +import platform import struct import sys import weakref from test import support -from test.support import import_helper, suppress_immortalization +from test.support import import_helper from test.support.script_helper import assert_python_ok +from test.support.testcase import ComplexesAreIdenticalMixin ISBIGENDIAN = sys.byteorder == "big" integer_codes = 'b', 'B', 'h', 'H', 'i', 'I', 'l', 'L', 'q', 'Q', 'n', 'N' byteorders = '', '@', '=', '<', '>', '!' +INF = float('inf') +NAN = float('nan') + def iter_integer_formats(byteorders=byteorders): for code in integer_codes: for byteorder in byteorders: @@ -33,7 +39,7 @@ def bigendian_to_native(value): else: return string_reverse(value) -class StructTest(unittest.TestCase): +class StructTest(ComplexesAreIdenticalMixin, unittest.TestCase): def test_isbigendian(self): self.assertEqual((struct.pack('=i', 1)[0] == 0), ISBIGENDIAN) @@ -360,8 +366,7 @@ def test_p_code(self): (got,) = struct.unpack(code, got) self.assertEqual(got, expectedback) - # TODO: RUSTPYTHON - @unittest.expectedFailure + @unittest.expectedFailure # TODO: RUSTPYTHON def test_705836(self): # SF bug 705836. "f" had a severe rounding bug, where a carry # from the low-order discarded bits could propagate into the exponent @@ -670,8 +675,7 @@ def test_format_attr(self): s2 = struct.Struct(s.format.encode()) self.assertEqual(s2.format, s.format) - # TODO: RUSTPYTHON - @unittest.expectedFailure + @unittest.expectedFailure # TODO: RUSTPYTHON def test_struct_cleans_up_at_runtime_shutdown(self): code = """if 1: import struct @@ -687,10 +691,9 @@ def __del__(self): rc, stdout, stderr = assert_python_ok("-c", code) self.assertEqual(rc, 0) self.assertEqual(stdout.rstrip(), b"") - self.assertIn(b"Exception ignored in:", stderr) + self.assertIn(b"Exception ignored while calling deallocator", stderr) self.assertIn(b"C.__del__", stderr) - @suppress_immortalization() def test__struct_reference_cycle_cleaned_up(self): # Regression test for python/cpython#94207. @@ -777,8 +780,7 @@ def test_error_propagation(fmt_str): test_error_propagation('N') test_error_propagation('n') - # TODO: RUSTPYTHON - @unittest.expectedFailure + @unittest.expectedFailure # TODO: RUSTPYTHON def test_struct_subclass_instantiation(self): # Regression test for https://github.com/python/cpython/issues/112358 class MyStruct(struct.Struct): @@ -792,6 +794,34 @@ def test_repr(self): s = struct.Struct('=i2H') self.assertEqual(repr(s), f'Struct({s.format!r})') + @unittest.expectedFailure # TODO: RUSTPYTHON + def test_c_complex_round_trip(self): + values = [complex(*_) for _ in combinations([1, -1, 0.0, -0.0, 2, + -3, INF, -INF, NAN], 2)] + for z in values: + for f in ['F', 'D', '>F', '>D', '