def test_dirent(): dirent = rffi_platform.getstruct("struct dirent", """ struct dirent /* for this example only, not the exact dirent */ { long d_ino; int d_off; unsigned short d_reclen; char d_name[32]; }; """, [("d_reclen", rffi.USHORT)]) assert isinstance(dirent, lltype.Struct) # check that we have the desired field assert dirent.c_d_reclen is rffi.USHORT ctypes = import_ctypes() class CTypesDirent(ctypes.Structure): _fields_ = [('d_ino', ctypes.c_long), ('d_off', ctypes.c_int), ('d_reclen', ctypes.c_ushort), ('d_name', ctypes.c_char * 32)] assert dirent._hints['size'] == ctypes.sizeof(CTypesDirent)
def test_array_varsized_struct(): dirent = rffi_platform.getstruct( "struct dirent", """ struct dirent /* for this example only, not the exact dirent */ { int d_off; char d_name[1]; }; """, [("d_name", rffi.CArray(rffi.CHAR))]) assert rffi.offsetof(dirent, 'c_d_name') == 4 assert dirent.c_d_name == rffi.CArray(rffi.CHAR)
def test_array_varsized_struct(): dirent = rffi_platform.getstruct("struct dirent", """ struct dirent /* for this example only, not the exact dirent */ { int d_off; char d_name[1]; }; """, [("d_name", rffi.CArray(rffi.CHAR))]) assert rffi.offsetof(dirent, 'c_d_name') == 4 assert dirent.c_d_name == rffi.CArray(rffi.CHAR)
def test_array(): dirent = rffi_platform.getstruct("struct dirent", """ struct dirent /* for this example only, not the exact dirent */ { long d_ino; int d_off; unsigned short d_reclen; char d_name[32]; }; """, [("d_name", lltype.FixedSizeArray(rffi.CHAR, 1))]) assert dirent.c_d_name.length == 32
def test_array(): dirent = rffi_platform.getstruct( "struct dirent", """ struct dirent /* for this example only, not the exact dirent */ { long d_ino; int d_off; unsigned short d_reclen; char d_name[32]; }; """, [("d_name", lltype.FixedSizeArray(rffi.CHAR, 1))]) assert dirent.c_d_name.length == 32
def test_rffi_offsetof(self): import struct from rpython.rtyper.tool import rffi_platform S = rffi_platform.getstruct("struct S", """ struct S { short a; int b, c; }; """, [("a", INT), ("b", INT), ("c", INT)]) assert sizeof(S) == struct.calcsize("hii") assert offsetof(S, "c_a") == 0 assert offsetof(S, "c_b") == struct.calcsize("hi") - struct.calcsize("i") assert offsetof(S, "c_c") == struct.calcsize("hii") - struct.calcsize("i")
def test_rffi_offsetof(self): import struct from rpython.rtyper.tool import rffi_platform S = rffi_platform.getstruct( "struct S", """ struct S { short a; int b, c; }; """, [("a", INT), ("b", INT), ("c", INT)]) assert sizeof(S) == struct.calcsize("hii") assert offsetof(S, "c_a") == 0 assert offsetof(S, "c_b") == struct.calcsize("hi") - struct.calcsize("i") assert offsetof(S, "c_c") == struct.calcsize("hii") - struct.calcsize("i")
def test_fit_type(): S = rffi_platform.getstruct("struct S", """ struct S { signed char c; unsigned char uc; short s; unsigned short us; int i; unsigned int ui; long l; unsigned long ul; long long ll; unsigned long long ull; double d; }; """, [("c", rffi.INT), ("uc", rffi.INT), ("s", rffi.UINT), ("us", rffi.INT), ("i", rffi.INT), ("ui", rffi.INT), ("l", rffi.INT), ("ul", rffi.INT), ("ll", rffi.INT), ("ull", rffi.INT), ("d", rffi.DOUBLE)]) # XXX we need to have a float here as well as soon as we'll # have support assert isinstance(S, lltype.Struct) assert S.c_c == rffi.SIGNEDCHAR assert S.c_uc == rffi.UCHAR assert S.c_s == rffi.SHORT assert S.c_us == rffi.USHORT assert S.c_i == rffi.INT assert S.c_ui == rffi.UINT assert S.c_l == rffi.LONG assert S.c_ul == rffi.ULONG assert S.c_ll == rffi.LONGLONG assert S.c_ull == rffi.ULONGLONG assert S.c_d == rffi.DOUBLE
def test_fit_type(): S = rffi_platform.getstruct( "struct S", """ struct S { signed char c; unsigned char uc; short s; unsigned short us; int i; unsigned int ui; long l; unsigned long ul; long long ll; unsigned long long ull; double d; }; """, [("c", rffi.INT), ("uc", rffi.INT), ("s", rffi.UINT), ("us", rffi.INT), ("i", rffi.INT), ("ui", rffi.INT), ("l", rffi.INT), ("ul", rffi.INT), ("ll", rffi.INT), ("ull", rffi.INT), ("d", rffi.DOUBLE)]) # XXX we need to have a float here as well as soon as we'll # have support assert isinstance(S, lltype.Struct) assert S.c_c == rffi.SIGNEDCHAR assert S.c_uc == rffi.UCHAR assert S.c_s == rffi.SHORT assert S.c_us == rffi.USHORT assert S.c_i == rffi.INT assert S.c_ui == rffi.UINT assert S.c_l == rffi.LONG assert S.c_ul == rffi.ULONG assert S.c_ll == rffi.LONGLONG assert S.c_ull == rffi.ULONGLONG assert S.c_d == rffi.DOUBLE
def test_dirent(): dirent = rffi_platform.getstruct( "struct dirent", """ struct dirent /* for this example only, not the exact dirent */ { long d_ino; int d_off; unsigned short d_reclen; char d_name[32]; }; """, [("d_reclen", rffi.USHORT)]) assert isinstance(dirent, lltype.Struct) # check that we have the desired field assert dirent.c_d_reclen is rffi.USHORT ctypes = import_ctypes() class CTypesDirent(ctypes.Structure): _fields_ = [('d_ino', ctypes.c_long), ('d_off', ctypes.c_int), ('d_reclen', ctypes.c_ushort), ('d_name', ctypes.c_char * 32)] assert dirent._hints['size'] == ctypes.sizeof(CTypesDirent)
def test_generate_padding(): # 'padding_drop' is a bit strange, but is what we need to write C code # that defines prebuilt structures of that type. Normally, the C # backend would generate '0' entries for every field c__pad#. That's # usually much more than the number of real fields in the real structure # definition. So 'padding_drop' allows a quick fix: it lists fields # that should be ignored by the C backend. It should only be used in # that situation because it lists some of the c__pad# fields a bit # randomly -- to the effect that writing '0' for the other fields gives # the right amount of '0's. S = rffi_platform.getstruct("foobar_t", """ typedef struct { char c1; /* followed by one byte of padding */ short s1; } foobar_t; """, [("c1", lltype.Signed), ("s1", lltype.Signed)]) assert S._hints['padding'] == ('c__pad0',) d = {'c_c1': 'char', 'c_s1': 'short'} assert S._hints['get_padding_drop'](d) == ['c__pad0'] # S = rffi_platform.getstruct("foobar_t", """ typedef struct { char c1; char c2; /* _pad0 */ short s1; } foobar_t; """, [("c1", lltype.Signed), ("s1", lltype.Signed)]) assert S._hints['padding'] == ('c__pad0',) d = {'c_c1': 'char', 'c_s1': 'short'} assert S._hints['get_padding_drop'](d) == [] # S = rffi_platform.getstruct("foobar_t", """ typedef struct { char c1; char c2; /* _pad0 */ /* _pad1, _pad2 */ int i1; } foobar_t; """, [("c1", lltype.Signed), ("i1", lltype.Signed)]) assert S._hints['padding'] == ('c__pad0', 'c__pad1', 'c__pad2') d = {'c_c1': 'char', 'c_i1': 'int'} assert S._hints['get_padding_drop'](d) == ['c__pad1', 'c__pad2'] # S = rffi_platform.getstruct("foobar_t", """ typedef struct { char c1; char c2; /* _pad0 */ char c3; /* _pad1 */ /* _pad2 */ int i1; } foobar_t; """, [("c1", lltype.Signed), ("i1", lltype.Signed)]) assert S._hints['padding'] == ('c__pad0', 'c__pad1', 'c__pad2') d = {'c_c1': 'char', 'c_i1': 'int'} assert S._hints['get_padding_drop'](d) == ['c__pad2'] # S = rffi_platform.getstruct("foobar_t", """ typedef struct { char c1; /* _pad0 */ short s1; /* _pad1, _pad2 */ int i1; } foobar_t; """, [("c1", lltype.Signed), ("i1", lltype.Signed)]) assert S._hints['padding'] == ('c__pad0', 'c__pad1', 'c__pad2') d = {'c_c1': 'char', 'c_i1': 'int'} assert S._hints['get_padding_drop'](d) == ['c__pad1', 'c__pad2'] # S = rffi_platform.getstruct("foobar_t", """ typedef struct { char c1; char c2; /* _pad0 */ /* _pad1, _pad2 */ int i1; char c3; /* _pad3 */ /* _pad4 */ short s1; } foobar_t; """, [("c1", lltype.Signed), ("i1", lltype.Signed), ("s1", lltype.Signed)]) assert S._hints['padding'] == ('c__pad0', 'c__pad1', 'c__pad2', 'c__pad3', 'c__pad4') d = {'c_c1': 'char', 'c_i1': 'int', 'c_s1': 'short'} assert S._hints['get_padding_drop'](d) == ['c__pad1', 'c__pad2', 'c__pad4'] # S = rffi_platform.getstruct("foobar_t", """ typedef struct { char c1; long l2; /* some number of _pads */ } foobar_t; """, [("c1", lltype.Signed)]) padding = list(S._hints['padding']) d = {'c_c1': 'char'} assert S._hints['get_padding_drop'](d) == padding
def test_generate_padding(): # 'padding_drop' is a bit strange, but is what we need to write C code # that defines prebuilt structures of that type. Normally, the C # backend would generate '0' entries for every field c__pad#. That's # usually much more than the number of real fields in the real structure # definition. So 'padding_drop' allows a quick fix: it lists fields # that should be ignored by the C backend. It should only be used in # that situation because it lists some of the c__pad# fields a bit # randomly -- to the effect that writing '0' for the other fields gives # the right amount of '0's. S = rffi_platform.getstruct( "foobar_t", """ typedef struct { char c1; /* followed by one byte of padding */ short s1; } foobar_t; """, [("c1", lltype.Signed), ("s1", lltype.Signed)]) assert S._hints['padding'] == ('c__pad0', ) d = {'c_c1': 'char', 'c_s1': 'short'} assert S._hints['get_padding_drop'](d) == ['c__pad0'] # S = rffi_platform.getstruct( "foobar_t", """ typedef struct { char c1; char c2; /* _pad0 */ short s1; } foobar_t; """, [("c1", lltype.Signed), ("s1", lltype.Signed)]) assert S._hints['padding'] == ('c__pad0', ) d = {'c_c1': 'char', 'c_s1': 'short'} assert S._hints['get_padding_drop'](d) == [] # S = rffi_platform.getstruct( "foobar_t", """ typedef struct { char c1; char c2; /* _pad0 */ /* _pad1, _pad2 */ int i1; } foobar_t; """, [("c1", lltype.Signed), ("i1", lltype.Signed)]) assert S._hints['padding'] == ('c__pad0', 'c__pad1', 'c__pad2') d = {'c_c1': 'char', 'c_i1': 'int'} assert S._hints['get_padding_drop'](d) == ['c__pad1', 'c__pad2'] # S = rffi_platform.getstruct( "foobar_t", """ typedef struct { char c1; char c2; /* _pad0 */ char c3; /* _pad1 */ /* _pad2 */ int i1; } foobar_t; """, [("c1", lltype.Signed), ("i1", lltype.Signed)]) assert S._hints['padding'] == ('c__pad0', 'c__pad1', 'c__pad2') d = {'c_c1': 'char', 'c_i1': 'int'} assert S._hints['get_padding_drop'](d) == ['c__pad2'] # S = rffi_platform.getstruct( "foobar_t", """ typedef struct { char c1; /* _pad0 */ short s1; /* _pad1, _pad2 */ int i1; } foobar_t; """, [("c1", lltype.Signed), ("i1", lltype.Signed)]) assert S._hints['padding'] == ('c__pad0', 'c__pad1', 'c__pad2') d = {'c_c1': 'char', 'c_i1': 'int'} assert S._hints['get_padding_drop'](d) == ['c__pad1', 'c__pad2'] # S = rffi_platform.getstruct( "foobar_t", """ typedef struct { char c1; char c2; /* _pad0 */ /* _pad1, _pad2 */ int i1; char c3; /* _pad3 */ /* _pad4 */ short s1; } foobar_t; """, [("c1", lltype.Signed), ("i1", lltype.Signed), ("s1", lltype.Signed)]) assert S._hints['padding'] == ('c__pad0', 'c__pad1', 'c__pad2', 'c__pad3', 'c__pad4') d = {'c_c1': 'char', 'c_i1': 'int', 'c_s1': 'short'} assert S._hints['get_padding_drop'](d) == ['c__pad1', 'c__pad2', 'c__pad4'] # S = rffi_platform.getstruct( "foobar_t", """ typedef struct { char c1; long l2; /* some number of _pads */ } foobar_t; """, [("c1", lltype.Signed)]) padding = list(S._hints['padding']) d = {'c_c1': 'char'} assert S._hints['get_padding_drop'](d) == padding