def test_repeated_alternating_put_get():
    jitter_buffer = JitterBuffer(buffer_length=0)

    for i in range(1000):
        jitter_buffer.put_packet(i, i)
        out = jitter_buffer.get_packet()
        assert out == i
        assert len(jitter_buffer) == 0
def test_overly_large_seq_no():
    jitter_buffer = JitterBuffer()

    # Set the roll-over value to a lower number to test the roll-over
    # code
    roll_over = 2
    jitter_buffer._seq_no_rollover = roll_over

    with pytest.raises(Exception):
        jitter_buffer.put_packet(roll_over, None)
Example #3
0
    def __init__(self, host, port):
        super().__init__()

        self._host = host
        self._port = port

        # Initialise the jitter buffer
        packets_to_buffer = 3
        self._jitter_buffer = JitterBuffer(packets_to_buffer)
        self._udp_packetizer = None
def test_get_out_of_order_packets():
    # Create jitter buffer
    buffer_length = 0
    jitter_buffer = JitterBuffer(buffer_length=buffer_length)

    # First valid put (sets expected value)
    value0 = 0
    jitter_buffer.put_packet(value0, value0)
    assert len(jitter_buffer) == buffer_length + 1

    # Out-of-order put
    value1 = 2
    jitter_buffer.put_packet(value1, value1)
    assert len(jitter_buffer) == buffer_length + 2

    # Get initial packet
    out = jitter_buffer.get_packet()
    assert out is value0
    assert len(jitter_buffer) == buffer_length + 1

    # Get missing packet
    out = jitter_buffer.get_packet()
    assert out is None
    assert len(jitter_buffer
               ) == buffer_length + 1  # because the None wasn't ever stored

    # Second get (from out-of-order packets)
    out = jitter_buffer.get_packet()
    assert out is value1
    assert len(jitter_buffer) == buffer_length
def test_repeated_alternating_put_get_with_buffer():
    buffer_length = 3
    jitter_buffer = JitterBuffer(buffer_length=buffer_length)

    for i in range(1000):
        jitter_buffer.put_packet(i, i)
        out = jitter_buffer.get_packet()
        if i < buffer_length:
            assert out is None
        else:
            assert out == i - buffer_length
        assert len(jitter_buffer) == buffer_length
def test_out_of_order_packet():
    jitter_buffer = JitterBuffer(buffer_length=0)

    jitter_buffer.put_packet(0, 0)
    assert len(jitter_buffer) == 1

    out = jitter_buffer.get_packet()
    assert out == 0
    assert len(jitter_buffer) == 0

    # Packet should be discarded
    jitter_buffer.put_packet(0, 0)
    assert len(jitter_buffer) == 0

    # Packet should be kept
    jitter_buffer.put_packet(2, 2)
    assert len(jitter_buffer) == 1
Example #7
0
class UDPClientBase(DatagramProtocol):
    def __init__(self, host, port):
        super().__init__()

        self._host = host
        self._port = port

        # Initialise the jitter buffer
        packets_to_buffer = 3
        self._jitter_buffer = JitterBuffer(packets_to_buffer)
        self._udp_packetizer = None

    def startProtocol(self):
        # "Connect" this to the server
        self.transport.connect(self._host, self._port)

        # Initialise UDP Packetizer
        self._udp_packetizer = UDPPacketizer(self.transport,
                                             (self._host, self._port))

    def announce(self, client_id):
        # Announce to UDP server
        self._udp_packetizer.write_with_seq_no(struct.pack(">Q", client_id),
                                               -1)

    def datagramReceived(self, data, addr):
        #print("Received UDP packet from", addr)

        # Extract the timestamp, sequence number, and encoded frame
        timestamp, seq_no, encoded_packet = self._udp_packetizer.decode(data)

        # Put the encoded packet in the jitter buffer
        self._jitter_buffer.put_packet(seq_no, encoded_packet)

    # Possibly invoked if there is no server listening on the
    # address to which we are sending.
    def connectionRefused(self):
        print("No one listening; stopping")
        if reactor.running:
            log.error("STOPPING CLIENT")
            reactor.stop()
def test_stress_test2():
    import random
    random.seed(1234)
    from collections import deque

    # Create jitter buffer
    jitter_buffer = JitterBuffer()

    # Set the roll-over value
    roll_over = 1000
    jitter_buffer._seq_no_rollover = roll_over

    # Number of packets to simulate
    number_of_packets = 200000

    # Duration per packet at source
    packet_duration = 20 / 1000  # seconds

    # Packet values
    packet_values = [i for i in range(number_of_packets)]

    # Generate missing packets
    prob_missing = 0.05
    keep = int(len(packet_values) * (1 - prob_missing))
    packet_values = random.sample(packet_values, keep)

    # Packet arrival times (no delay)
    packet_times = [i * packet_duration for i in packet_values]

    # Add noise in packet arrival time
    mu = 0
    sigma = packet_duration * 5
    packet_times = [t + random.gauss(mu, sigma) for t in packet_times]

    # Join the values and times
    packets = zip(packet_values, packet_times)

    # Sort the packets into the correct order
    sorted_packets = sorted(packets, key=lambda p: p[1])
    sorted_packets = deque(sorted_packets)

    t = 0 + packet_duration
    while True:
        # If the deque is empty, break
        if len(sorted_packets) == 0:
            break

        # Put first packet into the buffer if it appears before time t
        if sorted_packets[0][1] < t:
            value = sorted_packets[0][0]
            #print("putting", value)
            jitter_buffer.put_packet(value % roll_over, value)
            sorted_packets.popleft()
        else:
            # Get the next packet
            out = jitter_buffer.get_packet()
            #print("got", out)

            # Increment simulated time
            t += packet_duration
Example #9
0
    def _process_announcement(self, data, addr):
        print("In _process_announcement")
        # Extract components
        timestamp, seq_no, packet_data = UDPPacketizer.decode(data)
        
        # Check the sequence number is -1
        if seq_no != -1:
            log.warn(
                f"Expected announcement, but sequence number was "+
                f"{seq_no} and not -1"
            )
            return

        # Ensure packet data has exactly eight bytes
        if len(packet_data) != 8:
            log.warn(
                f"Expected announcement, but packet data had a "+
                f"length of {len(packet_data)} bytes and not 8."
            )
            return
        
        # Extract client_id from packet_data
        client_id = struct.unpack(">Q", packet_data)[0]
        print("after unpack")
        log.info(
            f"Creating UDP connection to client id {client_id} "+
            f"with address {addr}."
        )
        print("after log")
        
        # Create UDPPacketizer for this address
        udp_packetizer = UDPPacketizer(self.transport, addr)

        # Create a JitterBuffer for this address
        packets_to_buffer = 3
        jitter_buffer = JitterBuffer(packets_to_buffer)

        # Store connection details
        self._connections_by_address[addr] = {
            "udp_packetizer": udp_packetizer,
            "jitter_buffer": jitter_buffer
        }
        self._address_by_client_id[client_id] = addr
        
        # Announce to Participants
        self._participants.join_udp(client_id)
def test_get_from_empty():
    buffer_length = 0
    jitter_buffer = JitterBuffer(buffer_length=buffer_length)

    # First valid put
    value = 0
    jitter_buffer.put_packet(0, value)
    assert len(jitter_buffer) == buffer_length + 1

    # Get after put
    out = jitter_buffer.get_packet()
    assert out == value
    assert len(jitter_buffer) == buffer_length

    # Second get (from empty buffer)
    out = jitter_buffer.get_packet()
    assert out is None
    assert len(jitter_buffer) == 0
def test_ignores_before_first_put():
    buffer_length = 1
    jitter_buffer = JitterBuffer(buffer_length=buffer_length)

    # Get before put
    out = jitter_buffer.get_packet()
    assert out is None
    assert len(jitter_buffer) == buffer_length

    # First valid put
    value = 0
    jitter_buffer.put_packet(0, value)
    assert len(jitter_buffer) == buffer_length + 1

    # Get after put
    out = jitter_buffer.get_packet()
    assert out is None
    assert len(jitter_buffer) == buffer_length

    out = jitter_buffer.get_packet()
    assert out == value
    assert len(jitter_buffer) == buffer_length - 1
def test_len_zero_items_zero_buffer():
    jitter_buffer = JitterBuffer(buffer_length=0)
    assert len(jitter_buffer) == 0
def test_create_jitter_buffer():
    jitter_buffer = JitterBuffer()
def test_len_zero_items_non_zero_buffer():
    buffer_length = 2
    jitter_buffer = JitterBuffer(buffer_length=buffer_length)
    assert len(jitter_buffer) == buffer_length