Advertisement
Guest User

Untitled

a guest
Nov 23rd, 2019
532
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 3.66 KB | None | 0 0
  1. from socket import *
  2. import os
  3. import sys
  4. import struct
  5. import time
  6. import select
  7. import binascii
  8. ICMP_ECHO_REQUEST = 8
  9. MAX_HOPS = 30
  10. TIMEOUT = 2.0
  11. TRIES = 2
  12. # The packet that we shall send to each router along the path is the ICMP echo
  13. # request packet, which is exactly what we had used in the ICMP ping exercise.
  14. # We shall use the same packet that we built in the Ping exercise
  15. def checksum(string):
  16. # In this function we make the checksum of our packet
  17.     csum = 0
  18.     countTo = (len(string) // 2) * 2
  19.     count = 0
  20.    
  21.     while count < countTo:
  22.         thisVal = ord(string[count+1]) * 256 + ord(string[count])
  23.         csum = csum + thisVal
  24.         csum = csum & 0xffffffff
  25.         count = count + 2
  26.     if countTo < len(string):
  27.         csum = csum + ord(string[len(string) - 1])
  28.         csum = csum & 0xffffffff
  29.    
  30.     csum = (csum >> 16) + (csum & 0xffff)
  31.     csum = csum + (csum >> 16)
  32.     answer = ~csum
  33.     answer = answer & 0xffff
  34.     answer = answer >> 8 | (answer << 8 & 0xff00)
  35.     return answer
  36. # hint: see icmpPing lab
  37. def build_packet():
  38. # In the sendOnePing() method of the ICMP Ping exercise ,firstly the header of our
  39. # packet to be sent was made, secondly the checksum was appended to the header and
  40. # then finally the complete packet was sent to the destination.
  41. # Make the header in a similar way to the ping exercise.
  42.     myChecksum = 0
  43.     myID = os.getpid() & 0xFFFF
  44.     header = struct.pack("bbHHh", ICMP_ECHO_REQUEST, 0, myChecksum, myID, 1)
  45.     data = struct.pack("d", time.time())
  46.     # Append checksum to the header.
  47.     myChecksum = checksum(header + data)
  48.     if sys.platform == 'darwin':
  49.         myChecksum = htons(myChecksum) & 0xffff
  50.     else:
  51.         myChecksum = htons(myChecksum)
  52. # So the function ending should look like this
  53.     header = struct.pack("bbHHh", ICMP_ECHO_REQUEST, 0, myChecksum, myID, 1)
  54.     packet = header + data
  55.     return packet
  56.  
  57. def get_route(hostname):
  58.     timeLeft = TIMEOUT
  59.     for ttl in range(1,MAX_HOPS):
  60.         for tries in range(TRIES):
  61.             destAddr = gethostbyname(hostname)
  62.             #Fill in start
  63.             # Make a raw socket named mySocket
  64.             icmp = getprotobyname("icmp")
  65.             mySocket = socket(AF_INET, SOCK_RAW, icmp)
  66.             #Fill in end
  67.             mySocket.setsockopt(IPPROTO_IP, IP_TTL, struct.pack('I', ttl))
  68.             mySocket.settimeout(TIMEOUT)
  69.             try:
  70.                 d = build_packet()
  71.                 mySocket.sendto(d, (hostname, 0))
  72.                 t= time.time()
  73.                 startedSelect = time.time()
  74.                 whatReady = select.select([mySocket], [], [], timeLeft)
  75.                 howLongInSelect = (time.time() - startedSelect)
  76.                 if whatReady[0] == []: # Timeout
  77.                     print(" * * * Request timed out.")
  78.                 recvPacket, addr = mySocket.recvfrom(1024)
  79.                 timeReceived = time.time()
  80.                 timeLeft = timeLeft - howLongInSelect
  81.                 if timeLeft <= 0:
  82.                     print(" * * * Request timed out.")
  83.             except timeout:
  84.                 continue
  85.             else:
  86.             #Fill in start
  87.              #Fetch the icmp type from the IP packet
  88.                 icmpHeader = recvPacket[20:28]
  89.                 types, code, checksum, packetID, sequence = struct.unpack("bbHHh", icmpHeader)
  90.              #Fill in end
  91.                 if types == 11:
  92.                     bytes = struct.calcsize("d")
  93.                     timeSent = struct.unpack("d", recvPacket[28:28 +
  94.                     bytes])[0]
  95.                     print(" %d rtt=%.0f ms %s" %(ttl,
  96.                     (timeReceived -t)*1000, addr[0]))
  97.                 elif types == 3:
  98.                     bytes = struct.calcsize("d")
  99.                     timeSent = struct.unpack("d", recvPacket[28:28 +
  100.                     bytes])[0]
  101.                     print(" %d rtt=%.0f ms %s" %(ttl,
  102.                     (timeReceived-t)*1000, addr[0]))
  103.                 elif types == 0:
  104.                     bytes = struct.calcsize("d")
  105.                     timeSent = struct.unpack("d", recvPacket[28:28 +
  106.                     bytes])[0]
  107.                     print(" %d rtt=%.0f ms %s" %(ttl,
  108.                     (timeReceived - timeSent)*1000, addr[0]))
  109.                     return
  110.                 else:
  111.                     print("error")
  112.                     break
  113.  
  114.             finally:
  115.                 mySocket.close()
  116.                
  117. get_route("google.com")
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement