def AlphaString(name): return StringAdapter( DoubleAdapter( Sequence( name, UBInt16("length"), MetaField("data", lambda ctx: ctx["length"] * 2), )), encoding="ucs2", )
class TestMetaField(unittest.TestCase): def setUp(self): self.mf = MetaField("metafield", lambda context: 3) def test_trivial(self): pass def test_parse(self): self.assertEqual(self.mf.parse(b"abc"), b"abc") def test_build(self): self.assertEqual(self.mf.build(b"abc"), b"abc") def test_parse_too_short(self): self.assertRaises(FieldError, self.mf.parse, b"ab") def test_build_too_short(self): self.assertRaises(FieldError, self.mf.build, b"ab") def test_sizeof(self): self.assertEqual(self.mf.sizeof(), 3)
class TestMetaField(unittest.TestCase): def setUp(self): self.mf = MetaField("metafield", lambda context: 3) def test_trivial(self): pass def test_parse(self): self.assertEqual(self.mf.parse("abc"), "abc") def test_build(self): self.assertEqual(self.mf.build("abc"), "abc") def test_parse_too_short(self): self.assertRaises(FieldError, self.mf.parse, "ab") def test_build_too_short(self): self.assertRaises(FieldError, self.mf.build, "ab") def test_sizeof(self): self.assertEqual(self.mf.sizeof(), 3)
def dispatch(stream, protodef): opcode = ULInt16("opcode").parse_stream(stream) if opcode in protodef: func, macro = protodef[opcode] data = macro.parse_stream(stream) func(data) else: data = '' pktlen = packet_lengths.get(opcode, -1) if pktlen > 0: data = stream.read(pktlen - 2) elif pktlen == -1: datadef = Struct( "data", ULInt16("length"), MetaField("ignore", lambda ctx: ctx["length"] - 4)) data = datadef.parse_stream(stream) netlog.warning('UNIMPLEMENTED opcode={:04x} data={}'.format( opcode, data))
class TestMetaFieldStruct(unittest.TestCase): def setUp(self): self.mf = MetaField("data", lambda context: context["length"]) self.s = Struct("foo", Byte("length"), self.mf) def test_trivial(self): pass def test_parse(self): c = self.s.parse(b"\x03ABC") self.assertEqual(c.length, 3) self.assertEqual(c.data, b"ABC") c = self.s.parse(b"\x04ABCD") self.assertEqual(c.length, 4) self.assertEqual(c.data, b"ABCD") def test_sizeof_default(self): self.assertRaises(SizeofError, self.mf.sizeof) def test_sizeof(self): context = Container(length=4) self.assertEqual(self.mf.sizeof(context), 4)
class TestMetaFieldStruct(unittest.TestCase): def setUp(self): self.mf = MetaField("data", lambda context: context["length"]) self.s = Struct("foo", Byte("length"), self.mf) def test_trivial(self): pass def test_parse(self): c = self.s.parse("\x03ABC") self.assertEqual(c.length, 3) self.assertEqual(c.data, "ABC") c = self.s.parse("\x04ABCD") self.assertEqual(c.length, 4) self.assertEqual(c.data, "ABCD") def test_sizeof_default(self): self.assertRaises(SizeofError, self.mf.sizeof) def test_sizeof(self): context = Container(length=4) self.assertEqual(self.mf.sizeof(context), 4)
bass=1, snare=2, click=3, bass_drum=4, ), UBInt8("pitch"), ), 60: Struct( "explosion", BFloat64("unknown1"), BFloat64("unknown2"), BFloat64("unknown3"), BFloat32("unknown4"), UBInt32("count"), MetaField("unknown5", lambda context: context["count"] * 3), ), 70: Struct( "unknown-0x46", UBInt8("unknown1"), ), 100: Struct( "window-open", UBInt8("wid"), Enum( UBInt8("type"), inventory=0, workbench=1, furnace=2,
def setUp(self): self.mf = MetaField("data", lambda context: context["length"]) self.s = Struct("foo", Byte("length"), self.mf)
def setUp(self): self.mf = MetaField("metafield", lambda context: 3)
255: InfiniPacket("disconnect", 0xff, Struct( "payload", AlphaString("explanation"), )), "__default__": Struct( "unknown", Struct( "header", UBInt8("identifier"), UBInt8("flags"), UBInt32("length"), ), MetaField("data", lambda context: context["length"]), ), } packets_by_name = { "ping": 0, "disconnect": 255, } infinipacket_parser = Struct( "parser", OptionalGreedyRange( Struct( "packets", Peek(UBInt8("header")), Embed(Switch("packet", lambda context: context["header"],
UBInt8("stage"), ), 56: Struct("bulk-chunk", UBInt16("count"), # Length # Data # metadata ), # TODO: Needs work? 60: Struct("explosion", BFloat64("x"), BFloat64("y"), BFloat64("z"), BFloat32("radius"), UBInt32("count"), MetaField("blocks", lambda context: context["count"] * 3), BFloat32("motionx"), BFloat32("motiony"), BFloat32("motionz"), ), 61: Struct("sound", Enum(UBInt32("sid"), click2=1000, click1=1001, bow_fire=1002, door_toggle=1003, extinguish=1004, record_play=1005, charge=1007, fireball=1008, zombie_wood=1010,
def ByteString(name, size_name, encoding=None): return StringAdapter(MetaField("data", lambda ctx: ctx[size_name]), encoding=encoding)
def NBTdata(name, size_name): return NBTAdapter(MetaField(name, lambda ctx: ctx[size_name]))
"set experience", BFloat32("current"), UBInt16("level"), UBInt16("total"), ), 51: Struct( "chunk data", SBInt32("x"), SBInt32("z"), Bool("continuous"), UBInt16("primary_bitmap"), UBInt16("add_bitmap"), SBInt32("size"), #ByteString("data", size_name="size", encoding="zlib"), MetaField("data", lambda ctx: ctx["size"]), ), 52: Struct( "multi block change", SBInt32("x"), SBInt32("z"), UBInt16("count"), SBInt32("datasize"), MetaArray( lambda ctx: ctx.count, BitStruct( "blocks", BitField("x", 4), BitField("z", 4), BitField("y", 8),
damage=obj.damage, nbt_len=len(obj) if len(obj) else -1, nbt=obj.nbt) slot = SlotAdapter( Struct( "slot", SBInt16("item_id"), If( lambda context: context["item_id"] >= 0, Embed( Struct( "item_information", UBInt8("count"), UBInt16("damage"), SBInt16("nbt_len"), If(lambda context: context["nbt_len"] >= 0, MetaField("nbt", lambda ctx: ctx["nbt_len"])))), ))) Metadata = namedtuple("Metadata", "type value") metadata_types = ["byte", "short", "int", "float", "string", "slot", "coords"] # Metadata adaptor. class MetadataAdapter(Adapter): def _decode(self, obj, context): d = {} for m in obj.data: d[m.id.key] = Metadata(metadata_types[m.id.type], m.value) return d def _encode(self, obj, context):