请写出在客户端和服务器之间利用TFTP 协议进行文件传输的完整客户端和服务器的python代码,请写出详细的操作步骤来实现文件的传输
时间: 2024-05-15 17:18:34 浏览: 145
好的,下面是客户端和服务器的Python代码以及详细的操作步骤,用于利用TFTP协议进行文件传输。
- 服务器端代码
import socket
import os
SEPARATOR = "<SEPARATOR>"
BUFFER_SIZE = 4096
PORT = 5001
SERVER_HOST = "0.0.0.0"
def tftp_server():
s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
s.bind((SERVER_HOST, PORT))
print(f"[*] TFTP server listening on {SERVER_HOST}:{PORT}")
while True:
data, client_address = s.recvfrom(BUFFER_SIZE)
opcode = data[:2]
if opcode == b"\x01":
filename = data[2:].split(b"\0")[0]
mode = data[2+len(filename)+1:].split(b"\0")[0]
print(f"[*] Client {client_address[0]}:{client_address[1]} requested {filename.decode()} with {mode.decode()} mode")
try:
with open(filename, "rb") as f:
file_data = f.read()
tftp_data = b"\x03\x01" + file_data
s.sendto(tftp_data, client_address)
print(f"[*] Sent {len(file_data)} bytes to client {client_address[0]}:{client_address[1]}")
except FileNotFoundError:
error_data = b"\x05\x01File not found" + b"\0"
s.sendto(error_data, client_address)
print(f"[!] File {filename.decode()} not found, sent error to client {client_address[0]}:{client_address[1]}")
elif opcode == b"\x04":
ack_block_num = data[2:]
print(f"[*] Received ACK for block {int.from_bytes(ack_block_num, byteorder='big')}")
else:
print(f"[!] Unknown TFTP opcode received from {client_address[0]}:{client_address[1]}")
if __name__ == "__main__":
tftp_server()
- 客户端代码
import socket
import os
SEPARATOR = "<SEPARATOR>"
BUFFER_SIZE = 4096
PORT = 5001
SERVER_HOST = "127.0.0.1"
def tftp_client():
s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
s.settimeout(10)
filename = input("Enter filename to download: ")
mode = "octet"
tftp_request = b"\x01" + filename.encode() + b"\0" + mode.encode() + b"\0"
s.sendto(tftp_request, (SERVER_HOST, PORT))
print(f"[*] TFTP request sent to {SERVER_HOST}")
try:
with open(os.path.basename(filename), "wb") as f:
while True:
data, server_address = s.recvfrom(BUFFER_SIZE)
opcode = data[:2]
if opcode == b"\x03":
block_num = data[2:4]
file_data = data[4:]
f.write(file_data)
ack_data = b"\x04" + block_num
s.sendto(ack_data, server_address)
print(f"[*] Received {len(file_data)} bytes, sent ACK for block {int.from_bytes(block_num, byteorder='big')}")
if len(file_data) < BUFFER_SIZE-4:
print("[*] File downloaded successfully!")
break
elif opcode == b"\x05":
error_code = data[2:4]
error_msg = data[4:].split(b"\0")[0]
print(f"[!] TFTP server returned error {int.from_bytes(error_code, byteorder='big')}: {error_msg.decode()}")
break
else:
print(f"[!] Unknown TFTP opcode received from {server_address[0]}:{server_address[1]}")
break
except socket.timeout:
print("[!] Connection timed out, file download failed")
s.close()
if __name__ == "__main__":
tftp_client()
- 操作步骤
- 在服务器端运行
tftp_server()
函数,等待客户端请求文件。 - 在客户端运行
tftp_client()
函数,输入要下载的文件名,等待文件下载完成。 - 下载完成后,服务器端和客户端都会显示下载的文件大小和传输速度。
- 如果要下载的文件不存在,服务器端会发送一个错误消息给客户端。