1 import sys
2 from ctypes import *
3
4 _array_type = type(Array)
5
6 def _other_endian(typ):
7 """Return the type with the 'other' byte order. Simple types like
8 c_int and so on already have __ctype_be__ and __ctype_le__
9 attributes which contain the types, for more complicated types
10 arrays and structures are supported.
11 """
12 # check _OTHER_ENDIAN attribute (present if typ is primitive type)
13 if hasattr(typ, _OTHER_ENDIAN):
14 return getattr(typ, _OTHER_ENDIAN)
15 # if typ is array
16 if isinstance(typ, _array_type):
17 return _other_endian(typ._type_) * typ._length_
18 # if typ is structure
19 if issubclass(typ, Structure):
20 return typ
21 raise TypeError("This type does not support other endian: %s" % typ)
22
23 class ESC[4;38;5;81m_swapped_meta:
24 def __setattr__(self, attrname, value):
25 if attrname == "_fields_":
26 fields = []
27 for desc in value:
28 name = desc[0]
29 typ = desc[1]
30 rest = desc[2:]
31 fields.append((name, _other_endian(typ)) + rest)
32 value = fields
33 super().__setattr__(attrname, value)
34 class ESC[4;38;5;81m_swapped_struct_meta(ESC[4;38;5;149m_swapped_meta, ESC[4;38;5;149mtype(Structure)): pass
35 class ESC[4;38;5;81m_swapped_union_meta(ESC[4;38;5;149m_swapped_meta, ESC[4;38;5;149mtype(Union)): pass
36
37 ################################################################
38
39 # Note: The Structure metaclass checks for the *presence* (not the
40 # value!) of a _swapped_bytes_ attribute to determine the bit order in
41 # structures containing bit fields.
42
43 if sys.byteorder == "little":
44 _OTHER_ENDIAN = "__ctype_be__"
45
46 LittleEndianStructure = Structure
47
48 class ESC[4;38;5;81mBigEndianStructure(ESC[4;38;5;149mStructure, metaclass=ESC[4;38;5;149m_swapped_struct_meta):
49 """Structure with big endian byte order"""
50 __slots__ = ()
51 _swappedbytes_ = None
52
53 LittleEndianUnion = Union
54
55 class ESC[4;38;5;81mBigEndianUnion(ESC[4;38;5;149mUnion, metaclass=ESC[4;38;5;149m_swapped_union_meta):
56 """Union with big endian byte order"""
57 __slots__ = ()
58 _swappedbytes_ = None
59
60 elif sys.byteorder == "big":
61 _OTHER_ENDIAN = "__ctype_le__"
62
63 BigEndianStructure = Structure
64
65 class ESC[4;38;5;81mLittleEndianStructure(ESC[4;38;5;149mStructure, metaclass=ESC[4;38;5;149m_swapped_struct_meta):
66 """Structure with little endian byte order"""
67 __slots__ = ()
68 _swappedbytes_ = None
69
70 BigEndianUnion = Union
71
72 class ESC[4;38;5;81mLittleEndianUnion(ESC[4;38;5;149mUnion, metaclass=ESC[4;38;5;149m_swapped_union_meta):
73 """Union with little endian byte order"""
74 __slots__ = ()
75 _swappedbytes_ = None
76
77 else:
78 raise RuntimeError("Invalid byteorder")