99 c_short , c_ushort , c_int , c_uint ,
1010 c_long , c_ulong , c_longlong , c_ulonglong , c_float , c_double )
1111from struct import calcsize
12+ from collections import namedtuple
1213from test import support
1314
1415
@@ -474,36 +475,53 @@ class X(Structure):
474475 def test_array_in_struct (self ):
475476 # See bpo-22273
476477
478+ # Load the shared library
479+ dll = CDLL (_ctypes_test .__file__ )
480+
477481 # These should mirror the structures in Modules/_ctypes/_ctypes_test.c
478482 class Test2 (Structure ):
479483 _fields_ = [
480484 ('data' , c_ubyte * 16 ),
481485 ]
482486
483- class Test3 (Structure ):
487+ class Test3AParent (Structure ):
488+ _fields_ = [
489+ ('data' , c_float * 2 ),
490+ ]
491+
492+ class Test3A (Test3AParent ):
493+ _fields_ = [
494+ ('more_data' , c_float * 2 ),
495+ ]
496+
497+ class Test3B (Structure ):
484498 _fields_ = [
485499 ('data' , c_double * 2 ),
486500 ]
487501
488- class Test3A (Structure ):
502+ class Test3C (Structure ):
489503 _fields_ = [
490- (' data' , c_float * 2 ),
504+ (" data" , c_double * 4 )
491505 ]
492506
493- class Test3B ( Test3A ):
507+ class Test3D ( Structure ):
494508 _fields_ = [
495- ('more_data' , c_float * 2 ),
509+ ("data" , c_double * 8 )
510+ ]
511+
512+ class Test3E (Structure ):
513+ _fields_ = [
514+ ("data" , c_double * 9 )
496515 ]
497516
498- # Load the shared library
499- dll = CDLL (_ctypes_test .__file__ )
500517
518+ # Tests for struct Test2
501519 s = Test2 ()
502520 expected = 0
503521 for i in range (16 ):
504522 s .data [i ] = i
505523 expected += i
506- func = dll ._testfunc_array_in_struct1
524+ func = dll ._testfunc_array_in_struct2
507525 func .restype = c_int
508526 func .argtypes = (Test2 ,)
509527 result = func (s )
@@ -512,29 +530,16 @@ class Test3B(Test3A):
512530 for i in range (16 ):
513531 self .assertEqual (s .data [i ], i )
514532
515- s = Test3 ()
516- s .data [0 ] = 3.14159
517- s .data [1 ] = 2.71828
518- expected = 3.14159 + 2.71828
519- func = dll ._testfunc_array_in_struct2
520- func .restype = c_double
521- func .argtypes = (Test3 ,)
522- result = func (s )
523- self .assertEqual (result , expected )
524- # check the passed-in struct hasn't changed
525- self .assertEqual (s .data [0 ], 3.14159 )
526- self .assertEqual (s .data [1 ], 2.71828 )
527-
528- s = Test3B ()
533+ # Tests for struct Test3A
534+ s = Test3A ()
529535 s .data [0 ] = 3.14159
530536 s .data [1 ] = 2.71828
531537 s .more_data [0 ] = - 3.0
532538 s .more_data [1 ] = - 2.0
533-
534- expected = 3.14159 + 2.71828 - 5.0
535- func = dll ._testfunc_array_in_struct2a
539+ expected = 3.14159 + 2.71828 - 3.0 - 2.0
540+ func = dll ._testfunc_array_in_struct3A
536541 func .restype = c_double
537- func .argtypes = (Test3B ,)
542+ func .argtypes = (Test3A ,)
538543 result = func (s )
539544 self .assertAlmostEqual (result , expected , places = 6 )
540545 # check the passed-in struct hasn't changed
@@ -543,129 +548,60 @@ class Test3B(Test3A):
543548 self .assertAlmostEqual (s .more_data [0 ], - 3.0 , places = 6 )
544549 self .assertAlmostEqual (s .more_data [1 ], - 2.0 , places = 6 )
545550
546- @unittest .skipIf (
547- 'ppc64le' in platform .uname ().machine ,
548- "gh-110190: currently fails on ppc64le" ,
549- )
550- def test_array_in_struct_registers (self ):
551- dll = CDLL (_ctypes_test .__file__ )
552-
553- class Test3C1 (Structure ):
554- _fields_ = [
555- ("data" , c_double * 4 )
556- ]
557-
558- class DataType4 (Array ):
559- _type_ = c_double
560- _length_ = 4
561-
562- class Test3C2 (Structure ):
563- _fields_ = [
564- ("data" , DataType4 )
565- ]
566-
567- class Test3C3 (Structure ):
568- _fields_ = [
569- ("x" , c_double ),
570- ("y" , c_double ),
571- ("z" , c_double ),
572- ("t" , c_double )
573- ]
574-
575- class Test3D1 (Structure ):
576- _fields_ = [
577- ("data" , c_double * 5 )
578- ]
579-
580- class DataType5 (Array ):
581- _type_ = c_double
582- _length_ = 5
583-
584- class Test3D2 (Structure ):
585- _fields_ = [
586- ("data" , DataType5 )
587- ]
588-
589- class Test3D3 (Structure ):
590- _fields_ = [
591- ("x" , c_double ),
592- ("y" , c_double ),
593- ("z" , c_double ),
594- ("t" , c_double ),
595- ("u" , c_double )
596- ]
597-
598- # Tests for struct Test3C
599- expected = (1.0 , 2.0 , 3.0 , 4.0 )
600- func = dll ._testfunc_array_in_struct_set_defaults_3C
601- func .restype = Test3C1
602- result = func ()
603- # check the default values have been set properly
604- self .assertEqual (
605- (result .data [0 ],
606- result .data [1 ],
607- result .data [2 ],
608- result .data [3 ]),
609- expected
551+ # Test3B, Test3C, Test3D, Test3E have the same logic with different
552+ # sizes hence putting them in a loop.
553+ StructCtype = namedtuple (
554+ "StructCtype" ,
555+ ["cls" , "cfunc1" , "cfunc2" , "items" ]
610556 )
611-
612- func = dll ._testfunc_array_in_struct_set_defaults_3C
613- func .restype = Test3C2
614- result = func ()
615- # check the default values have been set properly
616- self .assertEqual (
617- (result .data [0 ],
618- result .data [1 ],
619- result .data [2 ],
620- result .data [3 ]),
621- expected
622- )
623-
624- func = dll ._testfunc_array_in_struct_set_defaults_3C
625- func .restype = Test3C3
626- result = func ()
627- # check the default values have been set properly
628- self .assertEqual ((result .x , result .y , result .z , result .t ), expected )
629-
630- # Tests for struct Test3D
631- expected = (1.0 , 2.0 , 3.0 , 4.0 , 5.0 )
632- func = dll ._testfunc_array_in_struct_set_defaults_3D
633- func .restype = Test3D1
634- result = func ()
635- # check the default values have been set properly
636- self .assertEqual (
637- (result .data [0 ],
638- result .data [1 ],
639- result .data [2 ],
640- result .data [3 ],
641- result .data [4 ]),
642- expected
643- )
644-
645- func = dll ._testfunc_array_in_struct_set_defaults_3D
646- func .restype = Test3D2
647- result = func ()
648- # check the default values have been set properly
649- self .assertEqual (
650- (result .data [0 ],
651- result .data [1 ],
652- result .data [2 ],
653- result .data [3 ],
654- result .data [4 ]),
655- expected
656- )
657-
658- func = dll ._testfunc_array_in_struct_set_defaults_3D
659- func .restype = Test3D3
660- result = func ()
661- # check the default values have been set properly
662- self .assertEqual (
663- (result .x ,
664- result .y ,
665- result .z ,
666- result .t ,
667- result .u ),
668- expected )
557+ structs_to_test = [
558+ StructCtype (
559+ Test3B ,
560+ dll ._testfunc_array_in_struct3B ,
561+ dll ._testfunc_array_in_struct3B_set_defaults ,
562+ 2 ),
563+ StructCtype (
564+ Test3C ,
565+ dll ._testfunc_array_in_struct3C ,
566+ dll ._testfunc_array_in_struct3C_set_defaults ,
567+ 4 ),
568+ StructCtype (
569+ Test3D ,
570+ dll ._testfunc_array_in_struct3D ,
571+ dll ._testfunc_array_in_struct3D_set_defaults ,
572+ 8 ),
573+ StructCtype (
574+ Test3E ,
575+ dll ._testfunc_array_in_struct3E ,
576+ dll ._testfunc_array_in_struct3E_set_defaults ,
577+ 9 ),
578+ ]
579+
580+ for sut in structs_to_test :
581+ s = sut .cls ()
582+
583+ # Test for cfunc1
584+ expected = 0
585+ for i in range (sut .items ):
586+ float_i = float (i )
587+ s .data [i ] = float_i
588+ expected += float_i
589+ func = sut .cfunc1
590+ func .restype = c_double
591+ func .argtypes = (sut .cls ,)
592+ result = func (s )
593+ self .assertEqual (result , expected )
594+ # check the passed-in struct hasn't changed
595+ for i in range (sut .items ):
596+ self .assertEqual (s .data [i ], float (i ))
597+
598+ # Test for cfunc2
599+ func = sut .cfunc2
600+ func .restype = sut .cls
601+ result = func ()
602+ # check if the default values have been set correctly
603+ for i in range (sut .items ):
604+ self .assertEqual (result .data [i ], float (i + 1 ))
669605
670606 def test_38368 (self ):
671607 class U (Union ):
0 commit comments