《自頂向下方法》筆記 · 編程作業2 · UDPping程序
作業描述
《計算機網路:自頂向下方法》中第二章末尾給出了此編程作業的簡單描述:
在這個編程作業中,你將用Python編寫一個客戶ping程序。該客戶將發送一個簡單的ping報文,接受一個從伺服器返回的pong報文,並確定從該客戶發送ping報文到接收到pong報文為止的時延。該時延稱為往返時延(RTT)。由該客戶和伺服器提供的功能類似於在現代操作系統中可用的標準ping程序,然而,標準的ping使用互聯網控制報文協議(ICMP)(我們將在第4章中學習ICMP)。此時我們將創建一個非標準(但簡單)的基於UDP的ping程序。
你的ping程序經UDP向目標伺服器發送10個ping報文,對於每個報文,當對應的pong報文返回時,你的客戶要確定和列印RTT。因為UDP是一個不可靠協議,由客戶發送的分組可能會丟失。為此,客戶不能無限期地等待對ping報文的回答。客戶等待伺服器回答的時間至多為1秒;如果沒有收到回答,客戶假定該分組丟失並相應地列印一條報文。
在此作業中,我們給出伺服器的完整代碼(在配套網站中可以找到。你的任務是編寫客戶代碼,該代碼與伺服器代碼非常類似。建議你先仔細學習伺服器的代碼,然後編寫你的客戶代碼,可以不受限制地從伺服器代碼中剪貼代碼行。
詳細描述
見官方文檔:Socket2_UDPpinger.pdf
以及筆者翻譯:編程作業2-UDPping程序-中文文檔.md
實現
讀懂文檔給出的Ping程序伺服器端代碼後,可已很容易的寫出Ping程序。首先建立一個UDP套接字,並指定目的IP地址和埠。隨之使用一個循環來發送數據包,共循環10次。其中每次在發送前從系統提取一次時間,接收到伺服器返回的消息後 ,再提取一次時間,兩次相減,即可得到每個消息的往返時延(RTT)。
代碼
UDPPinger.py
from socket import *nimport timennserverName = 191.101.232.165 # 伺服器地址,本例中使用一台遠程主機nserverPort = 12000 # 伺服器指定的埠nclientSocket = socket(AF_INET, SOCK_DGRAM) # 創建UDP套接字,使用IPv4協議nclientSocket.settimeout(1) # 設置套接字超時值1秒nnfor i in range(0, 10):ntsendTime = time.time()ntmessage = (Ping %d %s % (i+1, sendTime)).encode() # 生成數據報,編碼為bytes以便發送nttry:nttclientSocket.sendto(message, (serverName, serverPort)) # 將信息發送到伺服器nttmodifiedMessage, serverAddress = clientSocket.recvfrom(1024) # 從伺服器接收信息,同時也能得到伺服器地址nttrtt = time.time() - sendTime # 計算往返時間nttprint(Sequence %d: Reply from %s RTT = %.3fs % (i+1, serverName, rtt)) # 顯示信息ntexcept Exception as e:nttprint(Sequence %d: Request timed out % (i+1))nttnclientSocket.close() # 關閉套接字n
UDPPingerServer.py
# UDPPingerServer.pyn# We will need the following module to generate randomized lost packets import randomnfrom socket import *nimport randomnn# Create a UDP socketn# Notice the use of SOCK_DGRAM for UDP packetsnserverSocket = socket(AF_INET, SOCK_DGRAM)n# Assign IP address and port number to socketnserverSocket.bind((, 12000))nnwhile True:nt# Generate random number in the range of 0 to 10ntrand = random.randint(0, 10)nt# Receive the client packet along with the address it is coming fromntmessage, address = serverSocket.recvfrom(1024)nt# Capitalize the message from the clientntmessage = message.upper()nt# If rand is less is than 4, we consider the packet lost and do not respondntif rand < 4:nttcontinuent# Otherwise, the server respondsntserverSocket.sendto(message, address)n
代碼文件
UDPPinger.pyhttps://github.com/moranzcw/Computer-Networking-A-Top-Down-Approach-NOTES/blob/master/ProgrammingAssignment/%E7%BC%96%E7%A8%8B%E4%BD%9C%E4%B8%9A2-UDPping%E7%A8%8B%E5%BA%8F/source/UDPPinger.pyUDPPingerServer.py運行
伺服器端:
在一台主機上運行UDPPingerServer.py,作為接收ping程序數據的伺服器。
效果如下:
客戶端:
在另一台主機上運行UDPPinger.py,效果如下:
——————更多《計算機網路:自頂向下方法》筆記請訪問:
moranzcw/Computer-Networking-A-Top-Down-Approach-NOTES推薦閱讀:
※Spotify 如何對歌曲隨機播放?
※帶你入門Spark(資源整理)
※自己寫的編譯器一般幾個符號表比較合適?
※句柄是什麼?
※XAML與XML的關係與語法的區別,學習wpf應該怎麼學?學XML用什麼教材比較好?