def test_constant(self): sym = Symbol(int_type('int', 4, True), value=1) self.assertEqual(sym.type, int_type('int', 4, True)) self.assertEqual(sym.value, 1) self.assertIsNone(sym.address) self.assertFalse(sym.is_enumerator) self.assertIsNone(sym.byteorder) self.assertRaises(TypeError, Symbol, int_type('int', 4, True), value='foo') self.assertEqual(sym, Symbol(int_type('int', 4, True), value=1)) self.assertNotEqual(sym, Symbol(int_type('int', 4, True), value=2)) self.assertNotEqual( sym, Symbol(int_type('unsigned int', 4, False), value=1)) sym = Symbol(float_type('double', 8), value=3.14) self.assertEqual(sym.type, float_type('double', 8)) self.assertEqual(sym.value, 3.14) self.assertIsNone(sym.address) self.assertFalse(sym.is_enumerator) self.assertIsNone(sym.byteorder) self.assertRaises(TypeError, Symbol, float_type('double', 8), value='foo') self.assertNotEqual( sym, Symbol(float_type('double', 8), address=0xffff0000, byteorder='little'))
def test_default_primitive_types(self): def spellings(tokens, num_optional=0): for i in range(len(tokens) - num_optional, len(tokens) + 1): for perm in itertools.permutations(tokens[:i]): yield " ".join(perm) for word_size in [8, 4]: prog = mock_program( MOCK_PLATFORM if word_size == 8 else MOCK_32BIT_PLATFORM ) self.assertEqual(prog.type("_Bool"), bool_type("_Bool", 1)) self.assertEqual(prog.type("char"), int_type("char", 1, True)) for spelling in spellings(["signed", "char"]): self.assertEqual(prog.type(spelling), int_type("signed char", 1, True)) for spelling in spellings(["unsigned", "char"]): self.assertEqual( prog.type(spelling), int_type("unsigned char", 1, False) ) for spelling in spellings(["short", "signed", "int"], 2): self.assertEqual(prog.type(spelling), int_type("short", 2, True)) for spelling in spellings(["short", "unsigned", "int"], 1): self.assertEqual( prog.type(spelling), int_type("unsigned short", 2, False) ) for spelling in spellings(["int", "signed"], 1): self.assertEqual(prog.type(spelling), int_type("int", 4, True)) for spelling in spellings(["unsigned", "int"]): self.assertEqual( prog.type(spelling), int_type("unsigned int", 4, False) ) for spelling in spellings(["long", "signed", "int"], 2): self.assertEqual(prog.type(spelling), int_type("long", word_size, True)) for spelling in spellings(["long", "unsigned", "int"], 1): self.assertEqual( prog.type(spelling), int_type("unsigned long", word_size, False) ) for spelling in spellings(["long", "long", "signed", "int"], 2): self.assertEqual(prog.type(spelling), int_type("long long", 8, True)) for spelling in spellings(["long", "long", "unsigned", "int"], 1): self.assertEqual( prog.type(spelling), int_type("unsigned long long", 8, False) ) self.assertEqual(prog.type("float"), float_type("float", 4)) self.assertEqual(prog.type("double"), float_type("double", 8)) for spelling in spellings(["long", "double"]): self.assertEqual(prog.type(spelling), float_type("long double", 16)) self.assertEqual( prog.type("size_t"), typedef_type("size_t", int_type("unsigned long", word_size, False)), ) self.assertEqual( prog.type("ptrdiff_t"), typedef_type("ptrdiff_t", int_type("long", word_size, True)), )
def test_default_primitive_types(self): def spellings(tokens, num_optional=0): for i in range(len(tokens) - num_optional, len(tokens) + 1): for perm in itertools.permutations(tokens[:i]): yield ' '.join(perm) for word_size in [8, 4]: prog = mock_program(MOCK_ARCH if word_size == 8 else MOCK_32BIT_ARCH) self.assertEqual(prog.type('_Bool'), bool_type('_Bool', 1)) self.assertEqual(prog.type('char'), int_type('char', 1, True)) for spelling in spellings(['signed', 'char']): self.assertEqual(prog.type(spelling), int_type('signed char', 1, True)) for spelling in spellings(['unsigned', 'char']): self.assertEqual(prog.type(spelling), int_type('unsigned char', 1, False)) for spelling in spellings(['short', 'signed', 'int'], 2): self.assertEqual(prog.type(spelling), int_type('short', 2, True)) for spelling in spellings(['short', 'unsigned', 'int'], 1): self.assertEqual(prog.type(spelling), int_type('unsigned short', 2, False)) for spelling in spellings(['int', 'signed'], 1): self.assertEqual(prog.type(spelling), int_type('int', 4, True)) for spelling in spellings(['unsigned', 'int']): self.assertEqual(prog.type(spelling), int_type('unsigned int', 4, False)) for spelling in spellings(['long', 'signed', 'int'], 2): self.assertEqual(prog.type(spelling), int_type('long', word_size, True)) for spelling in spellings(['long', 'unsigned', 'int'], 1): self.assertEqual(prog.type(spelling), int_type('unsigned long', word_size, False)) for spelling in spellings(['long', 'long', 'signed', 'int'], 2): self.assertEqual(prog.type(spelling), int_type('long long', 8, True)) for spelling in spellings(['long', 'long', 'unsigned', 'int'], 1): self.assertEqual(prog.type(spelling), int_type('unsigned long long', 8, False)) self.assertEqual(prog.type('float'), float_type('float', 4)) self.assertEqual(prog.type('double'), float_type('double', 8)) for spelling in spellings(['long', 'double']): self.assertEqual(prog.type(spelling), float_type('long double', 16)) self.assertEqual( prog.type('size_t'), typedef_type('size_t', int_type('unsigned long', word_size, False))) self.assertEqual( prog.type('ptrdiff_t'), typedef_type('ptrdiff_t', int_type('long', word_size, True)))
def test_complex(self): t = complex_type('double _Complex', 16, float_type('double', 8)) self.assertEqual(t.kind, TypeKind.COMPLEX) self.assertIsNone(t.primitive) self.assertEqual(t.name, 'double _Complex') self.assertEqual(t.size, 16) self.assertEqual(t.type, float_type('double', 8)) self.assertTrue(t.is_complete()) self.assertEqual( t, complex_type('double _Complex', 16, float_type('double', 8))) self.assertNotEqual( t, complex_type('float _Complex', 16, float_type('double', 8))) self.assertNotEqual( t, complex_type('double _Complex', 32, float_type('double', 8))) self.assertNotEqual( t, complex_type('double _Complex', 16, float_type('float', 4))) self.assertEqual( repr(t), "complex_type(name='double _Complex', size=16, type=float_type(name='double', size=8))" ) self.assertRaises(TypeError, complex_type, None, 16, float_type('double', 8)) self.assertRaises(TypeError, complex_type, 'double _Complex', 16, None) self.assertRaisesRegex(ValueError, 'must be floating-point or integer type', complex_type, 'double _Complex', 16, void_type()) self.assertRaisesRegex(ValueError, 'must be unqualified', complex_type, 'double _Complex', 16, float_type('double', 8, Qualifiers.CONST))
def test_float(self): t = float_type('float', 4) self.assertEqual(t.primitive, PrimitiveType.C_FLOAT) self.assertEqual(t.kind, TypeKind.FLOAT) self.assertEqual(t.name, 'float') self.assertEqual(t.size, 4) self.assertTrue(t.is_complete()) self.assertEqual(t, float_type('float', 4)) self.assertNotEqual(t, float_type('double', 4)) self.assertNotEqual(t, float_type('float', 8)) self.assertEqual(repr(t), "float_type(name='float', size=4)") self.assertRaises(TypeError, float_type, None, 4)
def test_complex(self): self.assertQualifiedTypeName( "double _Complex", True, complex_type, "double _Complex", 16, float_type("double", 8), )
def test_pointer_to_function(self): i = int_type('int', 4, True) self.assertTypeName( pointer_type(8, function_type(i, ((i, ), ), False)), 'int (*)(int)', True) self.assertTypeName( pointer_type(8, function_type(i, ((i, 'x'), ), False)), 'int (*)(int x)', True) self.assertTypeName( pointer_type( 8, function_type(i, ((i, ), (float_type('float', 4), )), False)), 'int (*)(int, float)', True)
def test_pointer_to_function(self): i = int_type("int", 4, True) self.assertTypeName( pointer_type(8, function_type(i, ((i,),), False)), "int (*)(int)", True ) self.assertTypeName( pointer_type(8, function_type(i, ((i, "x"),), False)), "int (*)(int x)", True, ) self.assertTypeName( pointer_type(8, function_type(i, ((i,), (float_type("float", 4),)), False)), "int (*)(int, float)", True, )
def test_complex(self): t = complex_type("double _Complex", 16, float_type("double", 8)) self.assertEqual(t.kind, TypeKind.COMPLEX) self.assertIsNone(t.primitive) self.assertEqual(t.language, DEFAULT_LANGUAGE) self.assertEqual(t.name, "double _Complex") self.assertEqual(t.size, 16) self.assertEqual(t.type, float_type("double", 8)) self.assertTrue(t.is_complete()) self.assertEqual( t, complex_type("double _Complex", 16, float_type("double", 8))) self.assertNotEqual( t, complex_type("float _Complex", 16, float_type("double", 8))) self.assertNotEqual( t, complex_type("double _Complex", 32, float_type("double", 8))) self.assertNotEqual( t, complex_type("double _Complex", 16, float_type("float", 4))) self.assertEqual( repr(t), "complex_type(name='double _Complex', size=16, type=float_type(name='double', size=8))", ) self.assertEqual(sizeof(t), 16) self.assertRaises(TypeError, complex_type, None, 16, float_type("double", 8)) self.assertRaises(TypeError, complex_type, "double _Complex", 16, None) self.assertRaisesRegex( ValueError, "must be floating-point or integer type", complex_type, "double _Complex", 16, void_type(), ) self.assertRaisesRegex( ValueError, "must be unqualified", complex_type, "double _Complex", 16, float_type("double", 8, Qualifiers.CONST), )
def test_union(self): t = union_type('option', 4, ( (int_type('int', 4, True), 'x'), (int_type('unsigned int', 4, False), 'y'), )) self.assertEqual(t.kind, TypeKind.UNION) self.assertIsNone(t.primitive) self.assertEqual(t.tag, 'option') self.assertEqual(t.size, 4) self.assertEqual(t.members, ( (int_type('int', 4, True), 'x', 0, 0), (int_type('unsigned int', 4, False), 'y', 0, 0), )) self.assertTrue(t.is_complete()) self.assertEqual( t, union_type('option', 4, ( (int_type('int', 4, True), 'x'), (int_type('unsigned int', 4, False), 'y'), ))) # Different tag. self.assertNotEqual( t, union_type('pt', 4, ( (int_type('int', 4, True), 'x'), (int_type('unsigned int', 4, False), 'y'), ))) # Different size. self.assertNotEqual( t, union_type('option', 8, ( (int_type('int', 4, True), 'x'), (int_type('unsigned int', 4, False), 'y'), ))) # One is anonymous. self.assertNotEqual( t, union_type(None, 4, ( (int_type('int', 4, True), 'x'), (int_type('unsigned int', 4, False), 'y'), ))) # Different members. self.assertNotEqual( t, union_type('option', 4, ( (int_type('long', 8, True), 'x'), (int_type('unsigned long', 8, False), 'y'), ))) # Different number of members. self.assertNotEqual( t, union_type('option', 4, ( (int_type('int', 4, True), 'x'), (int_type('unsigned int', 4, False), 'y'), (float_type('float', 4), 'z'), ))) # One member is anonymous. self.assertNotEqual( t, union_type('option', 4, ( (int_type('int', 4, True), 'x'), (int_type('unsigned int', 4, False), ), ))) # One is incomplete. self.assertNotEqual(t, union_type('option')) self.assertEqual( repr(t), "union_type(tag='option', size=4, members=((int_type(name='int', size=4, is_signed=True), 'x', 0, 0), (int_type(name='unsigned int', size=4, is_signed=False), 'y', 0, 0)))" ) t = union_type(None, 4, ( (int_type('int', 4, True), 'x'), (int_type('unsigned int', 4, False), 'y'), )) self.assertEqual(t.kind, TypeKind.UNION) self.assertIsNone(t.primitive) self.assertIsNone(t.tag) self.assertEqual(t.size, 4) self.assertEqual(t.members, ( (int_type('int', 4, True), 'x', 0, 0), (int_type('unsigned int', 4, False), 'y', 0, 0), )) self.assertTrue(t.is_complete()) t = union_type('color', 0, ()) self.assertEqual(t.kind, TypeKind.UNION) self.assertIsNone(t.primitive) self.assertEqual(t.tag, 'color') self.assertEqual(t.size, 0) self.assertEqual(t.members, ()) self.assertTrue(t.is_complete()) self.assertEqual(repr(t), "union_type(tag='color', size=0, members=())") t = union_type('color') self.assertEqual(t.kind, TypeKind.UNION) self.assertIsNone(t.primitive) self.assertEqual(t.tag, 'color') self.assertIsNone(t.size) self.assertIsNone(t.members) self.assertFalse(t.is_complete()) self.assertEqual(repr(t), "union_type(tag='color', size=None, members=None)") t = union_type(None, None, None) self.assertEqual(t.kind, TypeKind.UNION) self.assertIsNone(t.primitive) self.assertEqual(t.tag, None) self.assertIsNone(t.size) self.assertIsNone(t.members) self.assertFalse(t.is_complete()) self.assertEqual(repr(t), "union_type(tag=None, size=None, members=None)") self.assertRaises(TypeError, union_type, 4) self.assertRaisesRegex(ValueError, 'must not have size', union_type, 'option', 8, None) self.assertRaisesRegex(ValueError, 'must have size', union_type, 'option', None, ()) self.assertRaisesRegex(TypeError, 'must be sequence or None', union_type, 'option', 8, 4) self.assertRaisesRegex(TypeError, 'must be.*sequence', union_type, 'option', 8, (4, )) self.assertRaisesRegex(ValueError, 'must be.*sequence', union_type, 'option', 8, ((), )) self.assertRaisesRegex(TypeError, 'must be string or None', union_type, 'option', 8, ((int_type('int', 4, True), 4), )) self.assertRaisesRegex(TypeError, 'must be integer', union_type, 'option', 8, ((int_type('int', 4, True), 'x', None), )) self.assertRaisesRegex(TypeError, 'must be Type', union_type, 'option', 8, ((None, 'x'), )) # Bit size. t = union_type('option', 4, ( (int_type('int', 4, True), 'x', 0, 4), (int_type('unsigned int', 4, False), 'y', 0, 4), )) self.assertEqual(t.members, ( (int_type('int', 4, True), 'x', 0, 4), (int_type('unsigned int', 4, False), 'y', 0, 4), ))
"point", 8, ( TypeMember(int_type("int", 4, True), "x", 0), TypeMember(int_type("int", 4, True), "y", 32), ), ) line_segment_type = struct_type( "line_segment", 16, (TypeMember(point_type, "a"), TypeMember(point_type, "b", 64))) option_type = union_type( "option", 4, ( TypeMember(int_type("int", 4, True), "i"), TypeMember(float_type("float", 4), "f"), ), ) color_type = enum_type( "color", int_type("unsigned int", 4, False), (TypeEnumerator("RED", 0), TypeEnumerator("GREEN", 1), TypeEnumerator("BLUE", 2)), ) pid_type = typedef_type("pid_t", int_type("int", 4, True)) MOCK_32BIT_PLATFORM = Platform(Architecture.UNKNOWN, PlatformFlags.IS_LITTLE_ENDIAN) MOCK_PLATFORM = Platform( Architecture.UNKNOWN, PlatformFlags.IS_64_BIT | PlatformFlags.IS_LITTLE_ENDIAN)
struct_type, typedef_type, union_type, ) point_type = struct_type('point', 8, ( (int_type('int', 4, True), 'x', 0), (int_type('int', 4, True), 'y', 32), )) line_segment_type = struct_type('line_segment', 16, ( (point_type, 'a'), (point_type, 'b', 64), )) option_type = union_type('option', 4, ( (int_type('int', 4, True), 'i'), (float_type('float', 4), 'f'), )) color_type = enum_type('color', int_type('unsigned int', 4, False), (('RED', 0), ('GREEN', 1), ('BLUE', 2))) pid_type = typedef_type('pid_t', int_type('int', 4, True)) MOCK_32BIT_PLATFORM = Platform(Architecture.UNKNOWN, PlatformFlags.IS_LITTLE_ENDIAN) MOCK_PLATFORM = Platform( Architecture.UNKNOWN, PlatformFlags.IS_64_BIT | PlatformFlags.IS_LITTLE_ENDIAN) class MockMemorySegment(NamedTuple): buf: bytes virt_addr: Optional[int] = None
def test_complex(self): self.assertQualifiedTypeName('double _Complex', True, complex_type, 'double _Complex', 16, float_type('double', 8))
) point_type = struct_type( "point", 8, ( (int_type("int", 4, True), "x", 0), (int_type("int", 4, True), "y", 32), ), ) line_segment_type = struct_type("line_segment", 16, ( (point_type, "a"), (point_type, "b", 64), )) option_type = union_type("option", 4, ( (int_type("int", 4, True), "i"), (float_type("float", 4), "f"), )) color_type = enum_type("color", int_type("unsigned int", 4, False), (("RED", 0), ("GREEN", 1), ("BLUE", 2))) pid_type = typedef_type("pid_t", int_type("int", 4, True)) MOCK_32BIT_PLATFORM = Platform(Architecture.UNKNOWN, PlatformFlags.IS_LITTLE_ENDIAN) MOCK_PLATFORM = Platform( Architecture.UNKNOWN, PlatformFlags.IS_64_BIT | PlatformFlags.IS_LITTLE_ENDIAN) class MockMemorySegment(NamedTuple): buf: bytes virt_addr: Optional[int] = None
def test_union(self): t = union_type( "option", 4, ( TypeMember(int_type("int", 4, True), "x"), TypeMember(int_type("unsigned int", 4, False), "y"), ), ) self.assertEqual(t.kind, TypeKind.UNION) self.assertIsNone(t.primitive) self.assertEqual(t.language, DEFAULT_LANGUAGE) self.assertEqual(t.tag, "option") self.assertEqual(t.size, 4) self.assertEqual( t.members, ( TypeMember(int_type("int", 4, True), "x", 0, 0), TypeMember(int_type("unsigned int", 4, False), "y", 0, 0), ), ) self.assertTrue(t.is_complete()) self.assertEqual( t, union_type( "option", 4, ( TypeMember(int_type("int", 4, True), "x"), TypeMember(int_type("unsigned int", 4, False), "y"), ), ), ) # Different tag. self.assertNotEqual( t, union_type( "pt", 4, ( TypeMember(int_type("int", 4, True), "x"), TypeMember(int_type("unsigned int", 4, False), "y"), ), ), ) # Different size. self.assertNotEqual( t, union_type( "option", 8, ( TypeMember(int_type("int", 4, True), "x"), TypeMember(int_type("unsigned int", 4, False), "y"), ), ), ) # One is anonymous. self.assertNotEqual( t, union_type( None, 4, ( TypeMember(int_type("int", 4, True), "x"), TypeMember(int_type("unsigned int", 4, False), "y"), ), ), ) # Different members. self.assertNotEqual( t, union_type( "option", 4, ( TypeMember(int_type("long", 8, True), "x"), TypeMember(int_type("unsigned long", 8, False), "y"), ), ), ) # Different number of members. self.assertNotEqual( t, union_type( "option", 4, ( TypeMember(int_type("int", 4, True), "x"), TypeMember(int_type("unsigned int", 4, False), "y"), TypeMember(float_type("float", 4), "z"), ), ), ) # One member is anonymous. self.assertNotEqual( t, union_type( "option", 4, ( TypeMember(int_type("int", 4, True), "x"), TypeMember(int_type("unsigned int", 4, False), ), ), ), ) # One is incomplete. self.assertNotEqual(t, union_type("option")) self.assertEqual( repr(t), "union_type(tag='option', size=4, members=(TypeMember(type=int_type(name='int', size=4, is_signed=True), name='x', bit_offset=0), TypeMember(type=int_type(name='unsigned int', size=4, is_signed=False), name='y', bit_offset=0)))", ) self.assertEqual(sizeof(t), 4) t = union_type( None, 4, ( TypeMember(int_type("int", 4, True), "x"), TypeMember(int_type("unsigned int", 4, False), "y"), ), ) self.assertEqual(t.kind, TypeKind.UNION) self.assertIsNone(t.primitive) self.assertIsNone(t.tag) self.assertEqual(t.size, 4) self.assertEqual( t.members, ( TypeMember(int_type("int", 4, True), "x", 0, 0), TypeMember(int_type("unsigned int", 4, False), "y", 0, 0), ), ) self.assertTrue(t.is_complete()) t = union_type("color", 0, ()) self.assertEqual(t.kind, TypeKind.UNION) self.assertIsNone(t.primitive) self.assertEqual(t.tag, "color") self.assertEqual(t.size, 0) self.assertEqual(t.members, ()) self.assertTrue(t.is_complete()) self.assertEqual(repr(t), "union_type(tag='color', size=0, members=())") t = union_type("color") self.assertEqual(t.kind, TypeKind.UNION) self.assertIsNone(t.primitive) self.assertEqual(t.tag, "color") self.assertIsNone(t.size) self.assertIsNone(t.members) self.assertFalse(t.is_complete()) self.assertEqual(repr(t), "union_type(tag='color', size=None, members=None)") t = union_type(None, None, None) self.assertEqual(t.kind, TypeKind.UNION) self.assertIsNone(t.primitive) self.assertEqual(t.tag, None) self.assertIsNone(t.size) self.assertIsNone(t.members) self.assertFalse(t.is_complete()) self.assertEqual(repr(t), "union_type(tag=None, size=None, members=None)") self.assertRaises(TypeError, union_type, 4) self.assertRaisesRegex(ValueError, "must not have size", union_type, "option", 8, None) self.assertRaisesRegex(ValueError, "must have size", union_type, "option", None, ()) self.assertRaisesRegex(TypeError, "must be sequence or None", union_type, "option", 8, 4) self.assertRaisesRegex(TypeError, "must be TypeMember", union_type, "option", 8, (4, )) # Bit size. t = union_type( "option", 4, ( TypeMember(int_type("int", 4, True), "x", 0, 4), TypeMember(int_type("unsigned int", 4, False), "y", 0, 4), ), ) self.assertEqual( t.members, ( TypeMember(int_type("int", 4, True), "x", 0, 4), TypeMember(int_type("unsigned int", 4, False), "y", 0, 4), ), )