@@ -616,6 +616,71 @@ c = pickle.loads(b)
616616assert c[IP].dst == "192.168.0.1"
617617assert raw(c) == raw(a)
618618
619+ = Pickle preserves field values, payload and metadata
620+
621+ import pickle
622+
623+ p = IP(src='1.2.3.4', dst='5.6.7.8')/TCP(sport=1234, dport=80, flags='S')
624+ p.time = 12345.0
625+ p.sent_time = 12346.0
626+ p.direction = 1
627+ p.sniffed_on = 'eth0'
628+ p.wirelen = 100
629+ p.comment = b'test comment'
630+ p2 = pickle.loads(pickle.dumps(p))
631+ assert p2[IP].src == '1.2.3.4'
632+ assert p2[IP].dst == '5.6.7.8'
633+ assert p2[TCP].sport == 1234
634+ assert p2[TCP].dport == 80
635+ assert p2[TCP].flags == 'S'
636+ assert p2.time == 12345.0
637+ assert p2.sent_time == 12346.0
638+ assert p2.direction == 1
639+ assert p2.sniffed_on == 'eth0'
640+ assert p2.wirelen == 100
641+ assert p2.comment == b'test comment'
642+ assert raw(p2) == raw(p)
643+
644+ = Pickle a bare packet without payload
645+
646+ import pickle
647+
648+ p = IP(src='10.0.0.1')
649+ p2 = pickle.loads(pickle.dumps(p))
650+ assert p2.src == '10.0.0.1'
651+ assert raw(p2) == raw(p)
652+
653+ = Pickle preserves custom __slots__ from subclasses
654+
655+ import pickle
656+ import scapy.packet as _pkt_mod
657+
658+ class _PickleTestPacket(Packet):
659+ __slots__ = ["custom_id", "custom_tag"]
660+ name = "PickleTestPacket"
661+ fields_desc = [ByteField("val", 0)]
662+
663+ # Make the class discoverable by pickle
664+ _pkt_mod._PickleTestPacket = _PickleTestPacket
665+ _PickleTestPacket.__module__ = 'scapy.packet'
666+
667+ p = _PickleTestPacket(val=42)
668+ p.custom_id = 0x123
669+ p.custom_tag = "hello"
670+ p2 = pickle.loads(pickle.dumps(p))
671+ assert p2.val == 42
672+ assert p2.custom_id == 0x123
673+ assert p2.custom_tag == "hello"
674+
675+ # Slots not explicitly set are not serialized
676+ p3 = _PickleTestPacket(val=7)
677+ assert not hasattr(p3, 'custom_id')
678+ p4 = pickle.loads(pickle.dumps(p3))
679+ assert p4.val == 7
680+ assert not hasattr(p4, 'custom_id')
681+
682+ del _pkt_mod._PickleTestPacket
683+
619684= Usage test
620685
621686from scapy.main import _usage
@@ -948,7 +1013,7 @@ assert corrupt_bits("ABCDE") in [b"EBCDE", b"ABCDG"]
9481013assert sane(corrupt_bits("ABCDE", n=3)) in ["AF.EE", "QB.TE"]
9491014
9501015= Test whois function
951- ~ netaccess disabled
1016+ ~ netaccess
9521017
9531018if not WINDOWS:
9541019 result = whois("193.0.6.139")
@@ -1782,15 +1847,15 @@ def _test():
17821847retry_test(_test)
17831848
17841849= Whois request
1785- ~ netaccess IP as_resolvers disabled
1850+ ~ netaccess IP as_resolvers
17861851* This test retries on failure because it often fails
17871852def _test():
17881853 IP(src="8.8.8.8").whois()
17891854
17901855retry_test(_test)
17911856
17921857= AS resolvers
1793- ~ netaccess IP as_resolvers disabled
1858+ ~ netaccess IP as_resolvers
17941859* This test retries on failure because it often fails
17951860
17961861def _test():
@@ -1826,7 +1891,7 @@ assert len(tmp) == 3
18261891assert [l[1] for l in tmp] == ['AS24776', 'AS36459', 'AS26496']
18271892
18281893= AS resolver - IPv6
1829- ~ netaccess IP as_resolvers disabled
1894+ ~ netaccess IP as_resolvers
18301895* This test retries on failure because it often fails
18311896
18321897def _test():
0 commit comments