0

I am trying to calculate the checksum of an IS-IS LSP (Link State PDU) by using Python but the end result is not matching the expected checksum. With regards to the checksum I am referring to the ISO

ISO 8473 checksum algorithm

Here below is the Python code:

LSP PDU in binary format , the checksum is 0xc7be

LSP = b'\x01_\x04\xa0\x00\x00\x00\x00\x00\x03\x00\x00\x00\x00\x00*\xc7\xbe\x03\x07\x04\x00d\x00\x00\x01\x04\x03I\x00\x01\x81\x01\xcc\x84\x04\x02\x02\x02\x03\x86\x04\x02\x02\x02\x03\x87v\x00\x00\x00\x00`\x02\x02\x02\x03\x11\x03\x06p\x00\x00\x00\x00\x03\x04\x01 \x0b\x04\x02\x02\x02\x03\x00\x00\x00\x00`\x04\x04\x04\x02\x03\x04\x01\x80\x00\x00\x00\x00`\x17\x17\x17\x01\x11\x03\x06p\x00\x00\x00\x00r\x04\x01 \x0b\x04\x02\x02\x02\x03\x00\x00\x00\n^\xc0\xa8!\x04\x03\x04\x01\x00\x00\x00\x00\n^\xc0\xa8!\x0c\x03\x04\x01\x00\x00\x00\x00\n^\xc0\xa8!\x10\x03\x04\x01\x00\x00\x00\x00\nX\xc0\xa8M\x03\x04\x01\x00\x89\x05vsim3\xf2#\x02\x02\x02\x03\x00\x02\t\x80\x00\x07\xd1\x01\x03\x00>\x80\x16\t\x00\x00\x03\xe8\x01\x03\x00:\x98\x17\x02\x01\n\x13\x02\x00\x01\x16\x833333""\x00\x00\x00\nx\x04\x08\x00\x00\x00\x0e\x00\x00\x024\x06\x04\xc0\xa8M\x12\x08\x04\xc0\xa8M\x11\x03\x04\x00\x00\x00\x00\t\x04L\xeek(\n\x04\x00\x00\x00\x00\x0b \x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x12\x03\x00\x00\n\xfc \x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x1f\x050\x00\x00]\xc3'

#initialising counters for the string slicing, as per the ISO10589 the checksum calculation start from  the LSDP-ID field
leftcounter = 4
rightcounter = 5


global C0
#initialise C0 and C1
C0=0
C1=0
L=len(LSP)
global Octet
Octet = None
while (rightcounter <= L):

    #print (Octet)
    # if the Octets are referring to the checksum set Octet variable to 0
    if (leftcounter >=16 and  leftcounter <=17 ):
        print (LSP[leftcounter:rightcounter])
        Octet = 0
    else:
        Octet = struct.unpack("B", LSP[leftcounter:rightcounter])[0]
    C0=(C0 + Octet) % 255
    C1 =(C1 + C0) % 255
    #print(LSP[leftcounter:rightcounter])
    leftcounter+=1
    rightcounter+=1
print(L)
#L = L - 1
X=((L-8)*C0 -C1) % 255
Y=((L-7)*(-1)*(C0) + C1) % 255
#X = (255-((C0+C1)%255))
#Y = (C1%255)
if (X == 0):
    X=255
if (Y == 0):
    Y=255
print (hex(X))
print (hex(Y))
joanis
  • 10,635
  • 14
  • 30
  • 40
Paolo
  • 11
  • 2
  • I don't understand where your left and right counters come from, given the algorithm you shared. Your code seems to implement a related but different algorithm... I would have expected a simple loop over the bytes in LSP, but I don't see that in your code. – joanis Aug 17 '22 at 14:31
  • Joanis , thanks for your feedback , I have managed to find the issue , I have to add 12 Bytes to the L variable which represent the length of the IS-IS common header . So in a nutshell the to below operation is modified from L=len(LSP) to L=len(LSP) + 12 – Paolo Aug 18 '22 at 12:40

1 Answers1

1

Joanis , thanks for your feedback , I have managed to find the issue , I have to add 12 Bytes to the L variable which represent the length of the IS-IS common header . So in a nutshell the to below operation is modified from L=len(LSP) to L=len(LSP) + 12

Final code :

def calculate (LSP):
    leftcounter = 4
    rightcounter = 5

    global C0

    C0 = 0
    C1 = 0
    L = len(LSP) +12
    global Octet
    Octet = None
    while (rightcounter <= L):

        # print (Octet)
        # if the Octets are referring to the checksum set Octet variable to 0
        if (leftcounter >= 16 and leftcounter <= 17):

            Octet = 0

        else:
            Octet = struct.unpack("B", LSP[leftcounter:rightcounter])[0]

        C0 = C0 + Octet
        C1 = C1 + C0

        leftcounter += 1
        rightcounter += 1


    X = ((L - 8) * C0 - C1) % 255
    Y = ((L - 7) * (-C0) + C1) % 255

    if (X == 0):
        X = 255
    if (Y == 0):
        Y = 255



    return (X & 65535) | (Y & 65535) << 8
Paolo
  • 11
  • 2
  • I'm glad you could figure it out. One recommendation: this isn't a standard chat board, we don't normally use multiple answer posts for what is effectively one answer. It would be best if you edit one answer to contain the text and code from both of your answers here, and delete the other. – joanis Aug 18 '22 at 13:57