from struct import pack, unpack _UINT_16_SIZE = 2 _UINT_32_SIZE = 4 class Decoder: _position: int _data: bytes def __init__(self, data: bytes): self._position = 0 self._data = data def read_uint16(self): value = int.from_bytes(self._data[self._position:self._position + _UINT_16_SIZE], "big") self._position += _UINT_16_SIZE return value def read_uint32(self): value = int.from_bytes(self._data[self._position:self._position + _UINT_32_SIZE], "big") self._position += _UINT_32_SIZE return value def read_float(self) -> float: return unpack(">f", pack(">L", self.read_uint32()))[0] def read_str(self): length = self._data[self._position] self._position += 1 value = self._data[self._position:self._position + length] self._position += length return value.decode() def read_sized_str(self, length: int): value = self._data[self._position:self._position + length] self._position += length return value.decode() @property def eof(self): return self._position >= len(self._data)