blob: 7ec70f40d1f5bf563594bcf29798f685fb2d8824 [file] [log] [blame]
henrike@webrtc.orgf0488722014-05-13 18:00:26 +00001/*
2 * Copyright 2004 The WebRTC Project Authors. All rights reserved.
3 *
4 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree.
9 */
10
11#include "webrtc/base/testclient.h"
nisse32f25052017-05-08 01:57:18 -070012#include "webrtc/base/ptr_util.h"
henrike@webrtc.orgf0488722014-05-13 18:00:26 +000013#include "webrtc/base/thread.h"
14#include "webrtc/base/timeutils.h"
15
16namespace rtc {
17
18// DESIGN: Each packet received is put it into a list of packets.
19// Callers can retrieve received packets from any thread by calling
20// NextPacket.
21
nisse32f25052017-05-08 01:57:18 -070022TestClient::TestClient(std::unique_ptr<AsyncPacketSocket> socket)
23 : socket_(std::move(socket)), prev_packet_timestamp_(-1) {
henrike@webrtc.orgf0488722014-05-13 18:00:26 +000024 socket_->SignalReadPacket.connect(this, &TestClient::OnPacket);
25 socket_->SignalReadyToSend.connect(this, &TestClient::OnReadyToSend);
26}
27
nisse32f25052017-05-08 01:57:18 -070028TestClient::~TestClient() {}
henrike@webrtc.orgf0488722014-05-13 18:00:26 +000029
30bool TestClient::CheckConnState(AsyncPacketSocket::State state) {
31 // Wait for our timeout value until the socket reaches the desired state.
Taylor Brandstetter2b3bf6b2016-05-19 14:57:31 -070032 int64_t end = TimeAfter(kTimeoutMs);
33 while (socket_->GetState() != state && TimeUntil(end) > 0) {
henrike@webrtc.orgf0488722014-05-13 18:00:26 +000034 Thread::Current()->ProcessMessages(1);
Taylor Brandstetter2b3bf6b2016-05-19 14:57:31 -070035 }
henrike@webrtc.orgf0488722014-05-13 18:00:26 +000036 return (socket_->GetState() == state);
37}
38
39int TestClient::Send(const char* buf, size_t size) {
40 rtc::PacketOptions options;
41 return socket_->Send(buf, size, options);
42}
43
44int TestClient::SendTo(const char* buf, size_t size,
45 const SocketAddress& dest) {
46 rtc::PacketOptions options;
47 return socket_->SendTo(buf, size, dest, options);
48}
49
nisse32f25052017-05-08 01:57:18 -070050std::unique_ptr<TestClient::Packet> TestClient::NextPacket(int timeout_ms) {
henrike@webrtc.orgf0488722014-05-13 18:00:26 +000051 // If no packets are currently available, we go into a get/dispatch loop for
jlmiller@webrtc.orgec499be2015-02-07 22:37:59 +000052 // at most timeout_ms. If, during the loop, a packet arrives, then we can
53 // stop early and return it.
henrike@webrtc.orgf0488722014-05-13 18:00:26 +000054
55 // Note that the case where no packet arrives is important. We often want to
56 // test that a packet does not arrive.
57
58 // Note also that we only try to pump our current thread's message queue.
59 // Pumping another thread's queue could lead to messages being dispatched from
60 // the wrong thread to non-thread-safe objects.
61
Taylor Brandstetter2b3bf6b2016-05-19 14:57:31 -070062 int64_t end = TimeAfter(timeout_ms);
henrike@webrtc.orgf0488722014-05-13 18:00:26 +000063 while (TimeUntil(end) > 0) {
64 {
65 CritScope cs(&crit_);
nisse32f25052017-05-08 01:57:18 -070066 if (packets_.size() != 0) {
henrike@webrtc.orgf0488722014-05-13 18:00:26 +000067 break;
68 }
69 }
70 Thread::Current()->ProcessMessages(1);
71 }
72
73 // Return the first packet placed in the queue.
nisse32f25052017-05-08 01:57:18 -070074 std::unique_ptr<Packet> packet;
henrike@webrtc.orgf0488722014-05-13 18:00:26 +000075 CritScope cs(&crit_);
nisse32f25052017-05-08 01:57:18 -070076 if (packets_.size() > 0) {
77 packet = std::move(packets_.front());
78 packets_.erase(packets_.begin());
henrike@webrtc.orgf0488722014-05-13 18:00:26 +000079 }
80
81 return packet;
82}
83
84bool TestClient::CheckNextPacket(const char* buf, size_t size,
85 SocketAddress* addr) {
86 bool res = false;
nisse32f25052017-05-08 01:57:18 -070087 std::unique_ptr<Packet> packet = NextPacket(kTimeoutMs);
henrike@webrtc.orgf0488722014-05-13 18:00:26 +000088 if (packet) {
Stefan Holmer9131efd2016-05-23 18:19:26 +020089 res = (packet->size == size && memcmp(packet->buf, buf, size) == 0 &&
90 CheckTimestamp(packet->packet_time.timestamp));
henrike@webrtc.orgf0488722014-05-13 18:00:26 +000091 if (addr)
92 *addr = packet->addr;
henrike@webrtc.orgf0488722014-05-13 18:00:26 +000093 }
94 return res;
95}
96
Stefan Holmer9131efd2016-05-23 18:19:26 +020097bool TestClient::CheckTimestamp(int64_t packet_timestamp) {
98 bool res = true;
99 if (packet_timestamp == -1) {
100 res = false;
101 }
Stefan Holmer9131efd2016-05-23 18:19:26 +0200102 if (prev_packet_timestamp_ != -1) {
103 if (packet_timestamp < prev_packet_timestamp_) {
104 res = false;
105 }
Stefan Holmer9131efd2016-05-23 18:19:26 +0200106 }
107 prev_packet_timestamp_ = packet_timestamp;
Stefan Holmer9131efd2016-05-23 18:19:26 +0200108 return res;
109}
110
henrike@webrtc.orgf0488722014-05-13 18:00:26 +0000111bool TestClient::CheckNoPacket() {
nisse32f25052017-05-08 01:57:18 -0700112 return NextPacket(kNoPacketTimeoutMs) == nullptr;
henrike@webrtc.orgf0488722014-05-13 18:00:26 +0000113}
114
115int TestClient::GetError() {
116 return socket_->GetError();
117}
118
119int TestClient::SetOption(Socket::Option opt, int value) {
120 return socket_->SetOption(opt, value);
121}
122
henrike@webrtc.orgf0488722014-05-13 18:00:26 +0000123void TestClient::OnPacket(AsyncPacketSocket* socket, const char* buf,
124 size_t size, const SocketAddress& remote_addr,
125 const PacketTime& packet_time) {
126 CritScope cs(&crit_);
nisse32f25052017-05-08 01:57:18 -0700127 packets_.push_back(MakeUnique<Packet>(remote_addr, buf, size, packet_time));
henrike@webrtc.orgf0488722014-05-13 18:00:26 +0000128}
129
130void TestClient::OnReadyToSend(AsyncPacketSocket* socket) {
Taylor Brandstettere7536412016-09-09 13:16:15 -0700131 ++ready_to_send_count_;
henrike@webrtc.orgf0488722014-05-13 18:00:26 +0000132}
133
Stefan Holmer9131efd2016-05-23 18:19:26 +0200134TestClient::Packet::Packet(const SocketAddress& a,
135 const char* b,
136 size_t s,
137 const PacketTime& packet_time)
138 : addr(a), buf(0), size(s), packet_time(packet_time) {
henrike@webrtc.orgf0488722014-05-13 18:00:26 +0000139 buf = new char[size];
140 memcpy(buf, b, size);
141}
142
143TestClient::Packet::Packet(const Packet& p)
Stefan Holmer9131efd2016-05-23 18:19:26 +0200144 : addr(p.addr), buf(0), size(p.size), packet_time(p.packet_time) {
henrike@webrtc.orgf0488722014-05-13 18:00:26 +0000145 buf = new char[size];
146 memcpy(buf, p.buf, size);
147}
148
149TestClient::Packet::~Packet() {
150 delete[] buf;
151}
152
153} // namespace rtc