scapy icon indicating copy to clipboard operation
scapy copied to clipboard

Wrong checksum calculation for Icmp Extension Header

Open malayaz opened this issue 7 years ago • 4 comments

Brief description

CheckSum for Icmp Extension Header does not involve payload in calculation.

Environment

  • Scapy version: scapy 2.4.0

RFC 4884 defines the checksum for Icmp Extension Header " The one's complement of the one's complement sum of the data structure, with the checksum field replaced by zero for the purpose of computing the checksum."

Below attached Wireshark logs also shows the case in which packet's checksum only includes icmp extension header and not the payload ( icmp object header and mpls object in the example case ). Wireshark correctly displays it as wrong checksum in this case. When calculation of checksum involved the payload, wireshark correctly interpreted the checksum.

file : scapy/contrib/icmp_extensions.py

Current Implementation

class ICMPExtensionHeader(Packet):
    name = 'ICMP Extension Header (RFC4884)'
    fields_desc = [ BitField('version', 2, 4),
                    BitField('reserved', 0, 12),
                    BitField('chksum', None, 16) ]

    _min_ieo_len = len(ICMPExtensionObject())

    def post_build(self, p, pay):
        if self.chksum is None:
            ck = checksum(p)
            p = p[:2]+chr(ck>>8)+chr(ck&0xff)+p[4:]
        return p+pay

After Fixing Checksum Calculation

class ICMPExtensionHeader(Packet):
    name = 'ICMP Extension Header (RFC4884)'
    fields_desc = [ BitField('version', 2, 4),
                    BitField('reserved', 0, 12),
                    BitField('chksum', None, 16) ]

    _min_ieo_len = len(ICMPExtensionObject())

    def post_build(self, p, pay):
        p += pay
        if self.chksum is None:
            ck = checksum(p)
            p = p[:2]+chr(ck>>8)+chr(ck&0xff)+p[4:]
        return p

Expected result

current_impl.pcap Icmp TTL exceeded packet matches with icmp extension header checksum calculation of scapy but fails with wireshark saying incorrect checksum.

expected_impl.pcap Icmp TTL exceeded packet does not match with icmp extension header checksum calculation of scapy and includes the payload in checksum calculation and passes with wireshark.

Current_and_expected.zip

malayaz avatar Jan 07 '19 20:01 malayaz

Could you provide a Scapy example that successfully build a packet with a valid checksum? I having spent a lot of time trying to come up with an unit test but did not manage to do it =/

guedou avatar Jun 24 '19 14:06 guedou

@malayaz Any word on the crc32 thoughts or?

stryngs avatar Dec 03 '22 07:12 stryngs

Could you provide a Scapy example that successfully build a packet with a valid checksum?

@guedou is this what you mean? pkt = ICMPExtensionHeader() / ICMPExtensionMPLS(stack=MPLS(label=0x2714, ttl=1))

A possible unit test of the above implementation (with chb() instead of chr()) could be: assert checksum(raw(ICMPExtensionHeader() / ICMPExtensionMPLS(stack=MPLS(label=0x2714, ttl=1)))) == 0

Or I misunderstood your request.

micpez avatar Jan 21 '24 00:01 micpez

@mcpat do you know how to build a full valid packet starting with Ether?

guedou avatar Jan 29 '24 15:01 guedou

This should be fixed in https://github.com/secdev/scapy/pull/4332

gpotter2 avatar Mar 23 '24 19:03 gpotter2