Last active
August 24, 2016 12:23
-
-
Save ytti/29abab3d92a2c1da0b2c0486c7a6925b to your computer and use it in GitHub Desktop.
script to figure out what bits need to be flipped to get specific checksum on an IP header
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/env ruby | |
# your IP header | |
DATA = [0x4501, 0x0028, 0x87ea, 0x4000, 0x3006, 0x5bfd, 0xXXXX, 0xXXXX, 0xXXXX, 0xXXXX] | |
IS = DATA[5] # checksum on the packet | |
WANT = 0x5bfc # checksum you want | |
# output | |
# (here we can see that packet had ECN bit set, but had it not had, checksum would be correct) | |
## ------ element: 0 (version+ihl+tos) ------- | |
## we have 0100010100000001 (4501) | |
## we want 0100010100000000 (4500) | |
## ------ element: 1 (packet length) ------- | |
## we have 0000000000101000 (28) | |
## we want 0000000000100111 (27) | |
## ------ element: 2 (id) ------- | |
## we have 1000011111101010 (87ea) | |
## we want 1000011111101001 (87e9) | |
## ------ element: 3 (fragmentation info) ------- | |
## we have 0100000000000000 (4000) | |
## we want 0011111111111111 (3fff) | |
DATA[5] = 0x0 # it's not turtles all the way down | |
ELEMENT = [ | |
'version+ihl+tos', | |
'packet length', | |
'id', | |
'fragmentation info', | |
'ttl+protocol', | |
'checksum', | |
'saddr upper', | |
'saddr lower', | |
'daddr upper', | |
'daddr lower', | |
] | |
def csum data | |
sum = data.inject(0){|r,m|r+m} | |
sum1 = (sum & 0xffff0000) >> 16 | |
sum2 = (sum & 0xffff) | |
sum = (sum1+sum2)^0xffff | |
sum | |
end | |
my_data = DATA.dup | |
offset = nil | |
65535.times do |x| | |
my_data[0] = x | |
result = csum(my_data) | |
offset = WANT-result if result==IS | |
if result==WANT | |
unless my_data[0] == DATA[0] | |
warn 'packet incorrectly entered' | |
exit 42 | |
end | |
end | |
end | |
10.times do |element| | |
next if element == 5 # checksum is 0 | |
puts '------ element: %d (%s) -------' % [element, ELEMENT[element]] | |
x = DATA[element] | |
puts 'we have %016b (%x)' % [x, x] | |
puts 'we want %016b (%x)' % [x+offset, x+offset] | |
end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment