blob: fdcd2f2cd1106c1463467a07efc0c0d18164a42d [file] [log] [blame]
wu@webrtc.orgd64719d2013-08-01 00:00:07 +00001/*
2 * libjingle
3 * Copyright 2013, Google Inc.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 *
8 * 1. Redistributions of source code must retain the above copyright notice,
9 * this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright notice,
11 * this list of conditions and the following disclaimer in the documentation
12 * and/or other materials provided with the distribution.
13 * 3. The name of the author may not be used to endorse or promote products
14 * derived from this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
17 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
18 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
19 * EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
20 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
21 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
22 * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
23 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
24 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
25 * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 */
27
28#include "talk/app/webrtc/datachannel.h"
wu@webrtc.orgcecfd182013-10-30 05:18:12 +000029#include "talk/app/webrtc/test/fakedatachannelprovider.h"
wu@webrtc.orgd64719d2013-08-01 00:00:07 +000030#include "talk/base/gunit.h"
sergeyu@chromium.orga23f0ca2013-11-13 22:48:52 +000031#include "testing/base/public/gmock.h"
wu@webrtc.orgd64719d2013-08-01 00:00:07 +000032
wu@webrtc.org78187522013-10-07 23:32:02 +000033using webrtc::DataChannel;
wu@webrtc.orgd64719d2013-08-01 00:00:07 +000034
sergeyu@chromium.orga23f0ca2013-11-13 22:48:52 +000035class FakeDataChannelObserver : public webrtc::DataChannelObserver {
36 public:
37 MOCK_METHOD0(OnStateChange, void());
38 MOCK_METHOD1(OnMessage, void(const webrtc::DataBuffer& buffer));
39};
40
wu@webrtc.orgd64719d2013-08-01 00:00:07 +000041class SctpDataChannelTest : public testing::Test {
42 protected:
43 SctpDataChannelTest()
wu@webrtc.org78187522013-10-07 23:32:02 +000044 : webrtc_data_channel_(
wu@webrtc.orgcecfd182013-10-30 05:18:12 +000045 DataChannel::Create(&provider_, cricket::DCT_SCTP, "test", &init_)) {
wu@webrtc.orgd64719d2013-08-01 00:00:07 +000046 }
47
wu@webrtc.org78187522013-10-07 23:32:02 +000048 void SetChannelReady() {
wu@webrtc.org07a6fbe2013-11-04 18:41:34 +000049 provider_.set_transport_available(true);
wu@webrtc.orgcecfd182013-10-30 05:18:12 +000050 webrtc_data_channel_->OnTransportChannelCreated();
51 if (webrtc_data_channel_->id() < 0) {
52 webrtc_data_channel_->SetSctpSid(0);
53 }
wu@webrtc.org07a6fbe2013-11-04 18:41:34 +000054 provider_.set_ready_to_send(true);
wu@webrtc.orgd64719d2013-08-01 00:00:07 +000055 }
wu@webrtc.org78187522013-10-07 23:32:02 +000056
sergeyu@chromium.orga23f0ca2013-11-13 22:48:52 +000057 void AddObserver() {
58 observer_.reset(new FakeDataChannelObserver());
59 webrtc_data_channel_->RegisterObserver(observer_.get());
60 }
61
wu@webrtc.org78187522013-10-07 23:32:02 +000062 webrtc::DataChannelInit init_;
wu@webrtc.orgcecfd182013-10-30 05:18:12 +000063 FakeDataChannelProvider provider_;
sergeyu@chromium.orga23f0ca2013-11-13 22:48:52 +000064 talk_base::scoped_ptr<FakeDataChannelObserver> observer_;
wu@webrtc.org78187522013-10-07 23:32:02 +000065 talk_base::scoped_refptr<DataChannel> webrtc_data_channel_;
wu@webrtc.orgd64719d2013-08-01 00:00:07 +000066};
67
wu@webrtc.orgcecfd182013-10-30 05:18:12 +000068// Verifies that the data channel is connected to the transport after creation.
69TEST_F(SctpDataChannelTest, ConnectedToTransportOnCreated) {
wu@webrtc.org07a6fbe2013-11-04 18:41:34 +000070 provider_.set_transport_available(true);
71 talk_base::scoped_refptr<DataChannel> dc = DataChannel::Create(
72 &provider_, cricket::DCT_SCTP, "test1", &init_);
wu@webrtc.orgcecfd182013-10-30 05:18:12 +000073
wu@webrtc.org07a6fbe2013-11-04 18:41:34 +000074 EXPECT_TRUE(provider_.IsConnected(dc.get()));
75 // The sid is not set yet, so it should not have added the streams.
76 EXPECT_FALSE(provider_.IsSendStreamAdded(dc->id()));
77 EXPECT_FALSE(provider_.IsRecvStreamAdded(dc->id()));
78
79 dc->SetSctpSid(0);
80 EXPECT_TRUE(provider_.IsSendStreamAdded(dc->id()));
81 EXPECT_TRUE(provider_.IsRecvStreamAdded(dc->id()));
wu@webrtc.orgcecfd182013-10-30 05:18:12 +000082}
83
84// Verifies that the data channel is connected to the transport if the transport
85// is not available initially and becomes available later.
86TEST_F(SctpDataChannelTest, ConnectedAfterTransportBecomesAvailable) {
wu@webrtc.org07a6fbe2013-11-04 18:41:34 +000087 EXPECT_FALSE(provider_.IsConnected(webrtc_data_channel_.get()));
wu@webrtc.orgcecfd182013-10-30 05:18:12 +000088
89 provider_.set_transport_available(true);
wu@webrtc.org07a6fbe2013-11-04 18:41:34 +000090 webrtc_data_channel_->OnTransportChannelCreated();
91 EXPECT_TRUE(provider_.IsConnected(webrtc_data_channel_.get()));
wu@webrtc.orgcecfd182013-10-30 05:18:12 +000092}
93
wu@webrtc.org78187522013-10-07 23:32:02 +000094// Tests the state of the data channel.
95TEST_F(SctpDataChannelTest, StateTransition) {
96 EXPECT_EQ(webrtc::DataChannelInterface::kConnecting,
97 webrtc_data_channel_->state());
98 SetChannelReady();
wu@webrtc.org07a6fbe2013-11-04 18:41:34 +000099
wu@webrtc.org78187522013-10-07 23:32:02 +0000100 EXPECT_EQ(webrtc::DataChannelInterface::kOpen, webrtc_data_channel_->state());
101 webrtc_data_channel_->Close();
102 EXPECT_EQ(webrtc::DataChannelInterface::kClosed,
103 webrtc_data_channel_->state());
wu@webrtc.orgcecfd182013-10-30 05:18:12 +0000104 // Verifies that it's disconnected from the transport.
105 EXPECT_FALSE(provider_.IsConnected(webrtc_data_channel_.get()));
wu@webrtc.org78187522013-10-07 23:32:02 +0000106}
107
wu@webrtc.orgd64719d2013-08-01 00:00:07 +0000108// Tests that DataChannel::buffered_amount() is correct after the channel is
109// blocked.
110TEST_F(SctpDataChannelTest, BufferedAmountWhenBlocked) {
wu@webrtc.org78187522013-10-07 23:32:02 +0000111 SetChannelReady();
wu@webrtc.orgd64719d2013-08-01 00:00:07 +0000112 webrtc::DataBuffer buffer("abcd");
113 EXPECT_TRUE(webrtc_data_channel_->Send(buffer));
114
115 EXPECT_EQ(0U, webrtc_data_channel_->buffered_amount());
116
wu@webrtc.orgcecfd182013-10-30 05:18:12 +0000117 provider_.set_send_blocked(true);
wu@webrtc.org78187522013-10-07 23:32:02 +0000118
wu@webrtc.orgd64719d2013-08-01 00:00:07 +0000119 const int number_of_packets = 3;
120 for (int i = 0; i < number_of_packets; ++i) {
121 EXPECT_TRUE(webrtc_data_channel_->Send(buffer));
122 }
123 EXPECT_EQ(buffer.data.length() * number_of_packets,
124 webrtc_data_channel_->buffered_amount());
125}
126
127// Tests that the queued data are sent when the channel transitions from blocked
128// to unblocked.
129TEST_F(SctpDataChannelTest, QueuedDataSentWhenUnblocked) {
wu@webrtc.org78187522013-10-07 23:32:02 +0000130 SetChannelReady();
wu@webrtc.orgd64719d2013-08-01 00:00:07 +0000131 webrtc::DataBuffer buffer("abcd");
wu@webrtc.orgcecfd182013-10-30 05:18:12 +0000132 provider_.set_send_blocked(true);
wu@webrtc.orgd64719d2013-08-01 00:00:07 +0000133 EXPECT_TRUE(webrtc_data_channel_->Send(buffer));
134
wu@webrtc.orgcecfd182013-10-30 05:18:12 +0000135 provider_.set_send_blocked(false);
wu@webrtc.org78187522013-10-07 23:32:02 +0000136 SetChannelReady();
wu@webrtc.orgd64719d2013-08-01 00:00:07 +0000137 EXPECT_EQ(0U, webrtc_data_channel_->buffered_amount());
138}
wu@webrtc.org78187522013-10-07 23:32:02 +0000139
140// Tests that the queued control message is sent when channel is ready.
wu@webrtc.orgcecfd182013-10-30 05:18:12 +0000141TEST_F(SctpDataChannelTest, OpenMessageSent) {
142 // Initially the id is unassigned.
143 EXPECT_EQ(-1, webrtc_data_channel_->id());
144
wu@webrtc.org78187522013-10-07 23:32:02 +0000145 SetChannelReady();
wu@webrtc.orgcecfd182013-10-30 05:18:12 +0000146 EXPECT_GE(webrtc_data_channel_->id(), 0);
147 EXPECT_EQ(cricket::DMT_CONTROL, provider_.last_send_data_params().type);
148 EXPECT_EQ(provider_.last_send_data_params().ssrc,
149 static_cast<uint32>(webrtc_data_channel_->id()));
wu@webrtc.org78187522013-10-07 23:32:02 +0000150}
wu@webrtc.org07a6fbe2013-11-04 18:41:34 +0000151
152// Tests that the DataChannel created after transport gets ready can enter OPEN
153// state.
154TEST_F(SctpDataChannelTest, LateCreatedChannelTransitionToOpen) {
155 SetChannelReady();
156 webrtc::DataChannelInit init;
157 init.id = 1;
158 talk_base::scoped_refptr<DataChannel> dc =
159 DataChannel::Create(&provider_, cricket::DCT_SCTP, "test1", &init);
160 EXPECT_EQ(webrtc::DataChannelInterface::kConnecting, dc->state());
161 EXPECT_TRUE_WAIT(webrtc::DataChannelInterface::kOpen == dc->state(),
162 1000);
163}
sergeyu@chromium.orga23f0ca2013-11-13 22:48:52 +0000164
165// Tests that messages are sent with the right ssrc.
166TEST_F(SctpDataChannelTest, SendDataSsrc) {
167 webrtc_data_channel_->SetSctpSid(1);
168 SetChannelReady();
169 webrtc::DataBuffer buffer("data");
170 EXPECT_TRUE(webrtc_data_channel_->Send(buffer));
171 EXPECT_EQ(1U, provider_.last_send_data_params().ssrc);
172}
173
174// Tests that the incoming messages with wrong ssrcs are rejected.
175TEST_F(SctpDataChannelTest, ReceiveDataWithInvalidSsrc) {
176 webrtc_data_channel_->SetSctpSid(1);
177 SetChannelReady();
178
179 AddObserver();
180 EXPECT_CALL(*(observer_.get()), OnMessage(testing::_)).Times(0);
181
182 cricket::ReceiveDataParams params;
183 params.ssrc = 0;
184 webrtc::DataBuffer buffer("abcd");
185 webrtc_data_channel_->OnDataReceived(NULL, params, buffer.data);
186}
187
188// Tests that the incoming messages with right ssrcs are acceted.
189TEST_F(SctpDataChannelTest, ReceiveDataWithValidSsrc) {
190 webrtc_data_channel_->SetSctpSid(1);
191 SetChannelReady();
192
193 AddObserver();
194 EXPECT_CALL(*(observer_.get()), OnMessage(testing::_)).Times(1);
195
196 cricket::ReceiveDataParams params;
197 params.ssrc = 1;
198 webrtc::DataBuffer buffer("abcd");
199
200 webrtc_data_channel_->OnDataReceived(NULL, params, buffer.data);
201}