[英]UDP socket with sequence check
我需要构建一个特定的解决方案,其中客户端将 UDP 流量发送到另一个 IP 并选择检查数据包序列(乱序检测)。
数据传输很清晰,我可以正常工作,但是我不清楚检测乱序帧的序列号。
我是否必须向接收者发送 litteraly 数字,保存到文件中,然后 litteraly 检查序列? 那会是什么样子?
客户:
import socket
import time
import sys
if len(sys.argv) > 1:
maxSendRateBytesPerSecond = (int(sys.argv[1])*1024)
else:
maxSendRateBytesPerSecond = (100*1024)
run_time = 60
total_packets = (maxSendRateBytesPerSecond/1024) * run_time
def ConvertSecondsToBytes(numSeconds):
return numSeconds*maxSendRateBytesPerSecond
def ConvertBytesToSeconds(numBytes):
return float(numBytes)/maxSendRateBytesPerSecond
sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
sock.connect(('10.20.30.1', 6789))
# We'll add to this tally as we send() bytes, and subtract from
# at the schedule specified by (maxSendRateBytesPerSecond)
bytesAheadOfSchedule = 0
# Dummy data buffer, just for testing
dataBuf = bytearray(1024)
prevTime = None
t_end = time.time() + run_time
print("Sending %s Kbps for %s seconds (%s packets in total)" % (maxSendRateBytesPerSecond * 8, run_time, int(total_packets)))
while time.time() < t_end:
now = time.time()
if (prevTime != None):
bytesAheadOfSchedule -= ConvertSecondsToBytes(now-prevTime)
prevTime = now
numBytesSent = sock.send(dataBuf)
if (numBytesSent > 0):
bytesAheadOfSchedule += numBytesSent
if (bytesAheadOfSchedule > 0):
time.sleep(ConvertBytesToSeconds(bytesAheadOfSchedule))
else:
print ("Error sending data, exiting!")
break
end_string = b'END!'
sock.send(end_string)
服务器:
#!/usr/bin/python3
import socket
from datetime import datetime
UDP_IP_ADDRESS = "10.20.30.1"
UDP_PORT_NO = 6789
serverSock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
serverSock.bind((UDP_IP_ADDRESS, UDP_PORT_NO))
PACKET_COUNT = 0
while True:
dt = datetime.now()
data, addr = serverSock.recvfrom(1024)
PACKET_COUNT = PACKET_COUNT + 1
if data == b'END!':
print ("Received " + str(PACKET_COUNT - 1))
break
通过对每个数据包的有效载荷(1、2、3...)进行编号来实现序列检查,在收到数字时保存它们,然后检查序列,计算存在多少唯一序列
客户:
import socket
import time
import sys
if len(sys.argv) > 1:
maxSendRateBytesPerSecond = int(sys.argv[1])*128
if len(sys.argv) > 2:
maxSendRateBytesPerSecond = int(sys.argv[1])*128
run_time = int(sys.argv[2])
else:
maxSendRateBytesPerSecond = (100*1472)
run_time = 5
#Hard stop the app if it attempts to send traffic above 100mbit/s
if maxSendRateBytesPerSecond > 99000000:
sys.exit("Bandwidth above 99Mbps is not allowed")
#Hard limit maximum running time to 5 minutes.
if run_time > 300:
run_time = 300
#Total packets to be sent which is used for detecting packet loss.
total_packets = (maxSendRateBytesPerSecond/1472) * run_time
def ConvertSecondsToBytes(numSeconds):
return numSeconds*maxSendRateBytesPerSecond
def ConvertBytesToSeconds(numBytes):
return float(numBytes)/maxSendRateBytesPerSecond
sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
sock.connect(('10.20.30.1', 6789))
# We'll add to this tally as we send() bytes, and subtract from
# at the schedule specified by (maxSendRateBytesPerSecond)
bytesAheadOfSchedule = 0
#Counter for packet sequencing.
counter = 0
prevTime = None
#Timer to break the loop.
t_end = time.time() + run_time
print("Sending %s Kbps for %s seconds (%s packets in total)" % (maxSendRateBytesPerSecond * 8, run_time, int(total_packets)))
while time.time() < t_end:
now = time.time()
#Create a DataBuf with the counter for integrity in bytes. Frame size is always 1472 bytes.
dataBuf = counter.to_bytes(1472, 'big')
#We calculate amount of time the script needed to send the data to the socket.
if (prevTime != None):
bytesAheadOfSchedule -= ConvertSecondsToBytes(now-prevTime)
prevTime = now
numBytesSent = sock.send(dataBuf)
if (numBytesSent > 0):
bytesAheadOfSchedule += numBytesSent
if (bytesAheadOfSchedule > 0):
time.sleep(ConvertBytesToSeconds(bytesAheadOfSchedule))
else:
print( "Error sending data, exiting!")
break
counter += 1
print(int.from_bytes(dataBuf, byteorder='big'))
end_string = b'END!'
sock.send(end_string)
服务器:
import socket
from datetime import datetime
UDP_IP_ADDRESS = "10.20.30.1"
UDP_PORT_NO = 6789
serverSock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
serverSock.bind((UDP_IP_ADDRESS, UDP_PORT_NO))
PACKET_COUNT = 0
sequence_list = []
while True:
dt = datetime.now()
data, addr = serverSock.recvfrom(1472)
if data == b'END!':
print ("Received " + str(PACKET_COUNT - 1))
break
else:
sequence_list.append(int.from_bytes(data, byteorder='big'))
PACKET_COUNT = PACKET_COUNT + 1
unique_sequences = []
count = 0
for i in range(len(sequence_list)-1):
if sequence_list[i] + 1 == sequence_list[i+1]:
if unique_sequences == []:
unique_sequences.append([sequence_list[i]])
count = count + 1
elif sequence_list[i] != unique_sequences[-1][-1]:
unique_sequences.append([sequence_list[i]])
count = count + 1
if sequence_list[i+1] != unique_sequences[-1]:
unique_sequences[-1].extend([sequence_list[i+1]])
print("Out of order packets:", (len(unique_sequences)-1))
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.