diff --git a/scapy/packet.py b/scapy/packet.py index 2a1c949a9f4..6b813986f3d 100644 --- a/scapy/packet.py +++ b/scapy/packet.py @@ -664,10 +664,10 @@ def _raw_packet_cache_field_value(self, fld, val, copy=False): # avoid copying whole packets (perf: #GH3894) if fld.islist: return [ - _cpy(x.fields) for x in val + (_cpy(x.fields), x.payload.raw_packet_cache) for x in val ] else: - return _cpy(val.fields) + return (_cpy(val.fields), val.payload.raw_packet_cache) elif fld.islist or fld.ismutable: return _cpy(val) return None diff --git a/test/fields.uts b/test/fields.uts index 2262ec32d6f..81b2566683c 100644 --- a/test/fields.uts +++ b/test/fields.uts @@ -863,6 +863,53 @@ while p.pl: assert i == 100 += Test cache handling of payload modification in a PacketListField +~ field + +# GH4414 +class SubPacket(Packet): + fields_desc = [ + ByteField("b", 0), + ] + +class MyPacket(Packet): + fields_desc = [ + PacketListField("a", [], SubPacket), + ] + + +p = MyPacket(b"\x00extrapayload") +p.a[0] = SubPacket(b=0) / b"test" + +assert bytes(p) == b"\x00test" + += Test cache handling of payload modification in a PacketField +~ field + +# also GH4414 +class PayloadPacket(Packet): + fields_desc = [ + StrField("b", ""), + ] + +class SubPacket(Packet): + fields_desc = [] + +bind_layers(SubPacket, PayloadPacket) + +class MyPacket(Packet): + fields_desc = [ + PacketField("a", None, SubPacket), + ] + + +s = b'test' +p = MyPacket(s) + +p[PayloadPacket].b = b'new' +assert p.build() != s + + ############ ############ + Tests on MultiFlagsField