- add sources.
[platform/framework/web/crosswalk.git] / src / content / browser / renderer_host / p2p / socket_host_test_utils.h
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #ifndef CONTENT_BROWSER_RENDERER_HOST_P2P_SOCKET_HOST_TEST_UTILS_H_
6 #define CONTENT_BROWSER_RENDERER_HOST_P2P_SOCKET_HOST_TEST_UTILS_H_
7
8 #include <vector>
9
10 #include "base/location.h"
11 #include "base/single_thread_task_runner.h"
12 #include "base/sys_byteorder.h"
13 #include "base/thread_task_runner_handle.h"
14 #include "content/common/p2p_messages.h"
15 #include "ipc/ipc_message_utils.h"
16 #include "ipc/ipc_sender.h"
17 #include "net/base/address_list.h"
18 #include "net/base/completion_callback.h"
19 #include "net/base/io_buffer.h"
20 #include "net/base/net_errors.h"
21 #include "net/socket/stream_socket.h"
22 #include "testing/gmock/include/gmock/gmock.h"
23 #include "testing/gtest/include/gtest/gtest.h"
24
25 namespace {
26
27 const char kTestLocalIpAddress[] = "123.44.22.4";
28 const char kTestIpAddress1[] = "123.44.22.31";
29 const int kTestPort1 = 234;
30 const char kTestIpAddress2[] = "133.11.22.33";
31 const int kTestPort2 = 543;
32
33 const int kStunHeaderSize = 20;
34 const uint16 kStunBindingRequest = 0x0001;
35 const uint16 kStunBindingResponse = 0x0102;
36 const uint16 kStunBindingError = 0x0111;
37 const uint32 kStunMagicCookie = 0x2112A442;
38
39 class MockIPCSender : public IPC::Sender {
40  public:
41   MockIPCSender();
42   virtual ~MockIPCSender();
43
44   MOCK_METHOD1(Send, bool(IPC::Message* msg));
45 };
46
47 MockIPCSender::MockIPCSender() { }
48 MockIPCSender::~MockIPCSender() { }
49
50 class FakeSocket : public net::StreamSocket {
51  public:
52   FakeSocket(std::string* written_data);
53   virtual ~FakeSocket();
54
55   void set_async_write(bool async_write) { async_write_ = async_write; }
56   void AppendInputData(const char* data, int data_size);
57   int input_pos() const { return input_pos_; }
58   bool read_pending() const { return read_pending_; }
59   void SetPeerAddress(const net::IPEndPoint& peer_address);
60   void SetLocalAddress(const net::IPEndPoint& local_address);
61
62   // net::Socket implementation.
63   virtual int Read(net::IOBuffer* buf, int buf_len,
64                    const net::CompletionCallback& callback) OVERRIDE;
65   virtual int Write(net::IOBuffer* buf, int buf_len,
66                     const net::CompletionCallback& callback) OVERRIDE;
67   virtual bool SetReceiveBufferSize(int32 size) OVERRIDE;
68   virtual bool SetSendBufferSize(int32 size) OVERRIDE;
69   virtual int Connect(const net::CompletionCallback& callback) OVERRIDE;
70   virtual void Disconnect() OVERRIDE;
71   virtual bool IsConnected() const OVERRIDE;
72   virtual bool IsConnectedAndIdle() const OVERRIDE;
73   virtual int GetPeerAddress(net::IPEndPoint* address) const OVERRIDE;
74   virtual int GetLocalAddress(net::IPEndPoint* address) const OVERRIDE;
75   virtual const net::BoundNetLog& NetLog() const OVERRIDE;
76   virtual void SetSubresourceSpeculation() OVERRIDE;
77   virtual void SetOmniboxSpeculation() OVERRIDE;
78   virtual bool WasEverUsed() const OVERRIDE;
79   virtual bool UsingTCPFastOpen() const OVERRIDE;
80   virtual bool WasNpnNegotiated() const OVERRIDE;
81   virtual net::NextProto GetNegotiatedProtocol() const OVERRIDE;
82   virtual bool GetSSLInfo(net::SSLInfo* ssl_info) OVERRIDE;
83
84  private:
85   void DoAsyncWrite(scoped_refptr<net::IOBuffer> buf, int buf_len,
86                     const net::CompletionCallback& callback);
87
88   bool read_pending_;
89   scoped_refptr<net::IOBuffer> read_buffer_;
90   int read_buffer_size_;
91   net::CompletionCallback read_callback_;
92
93   std::string input_data_;
94   int input_pos_;
95
96   std::string* written_data_;
97   bool async_write_;
98   bool write_pending_;
99
100   net::IPEndPoint peer_address_;
101   net::IPEndPoint local_address_;
102
103   net::BoundNetLog net_log_;
104 };
105
106 FakeSocket::FakeSocket(std::string* written_data)
107     : read_pending_(false),
108       input_pos_(0),
109       written_data_(written_data),
110       async_write_(false),
111       write_pending_(false) {
112 }
113
114 FakeSocket::~FakeSocket() { }
115
116 void FakeSocket::AppendInputData(const char* data, int data_size) {
117   input_data_.insert(input_data_.end(), data, data + data_size);
118   // Complete pending read if any.
119   if (read_pending_) {
120     read_pending_ = false;
121     int result = std::min(read_buffer_size_,
122                           static_cast<int>(input_data_.size() - input_pos_));
123     CHECK(result > 0);
124     memcpy(read_buffer_->data(), &input_data_[0] + input_pos_, result);
125     input_pos_ += result;
126     read_buffer_ = NULL;
127     net::CompletionCallback cb = read_callback_;
128     read_callback_.Reset();
129     cb.Run(result);
130   }
131 }
132
133 void FakeSocket::SetPeerAddress(const net::IPEndPoint& peer_address) {
134   peer_address_ = peer_address;
135 }
136
137 void FakeSocket::SetLocalAddress(const net::IPEndPoint& local_address) {
138   local_address_ = local_address;
139 }
140
141 int FakeSocket::Read(net::IOBuffer* buf, int buf_len,
142                      const net::CompletionCallback& callback) {
143   DCHECK(buf);
144   if (input_pos_ < static_cast<int>(input_data_.size())){
145     int result = std::min(buf_len,
146                           static_cast<int>(input_data_.size()) - input_pos_);
147     memcpy(buf->data(), &(*input_data_.begin()) + input_pos_, result);
148     input_pos_ += result;
149     return result;
150   } else {
151     read_pending_ = true;
152     read_buffer_ = buf;
153     read_buffer_size_ = buf_len;
154     read_callback_ = callback;
155     return net::ERR_IO_PENDING;
156   }
157 }
158
159 int FakeSocket::Write(net::IOBuffer* buf, int buf_len,
160                       const net::CompletionCallback& callback) {
161   DCHECK(buf);
162   DCHECK(!write_pending_);
163
164   if (async_write_) {
165
166     base::ThreadTaskRunnerHandle::Get()->PostTask(FROM_HERE, base::Bind(
167         &FakeSocket::DoAsyncWrite, base::Unretained(this),
168         scoped_refptr<net::IOBuffer>(buf), buf_len, callback));
169     write_pending_ = true;
170     return net::ERR_IO_PENDING;
171   }
172
173   if (written_data_) {
174     written_data_->insert(written_data_->end(),
175                           buf->data(), buf->data() + buf_len);
176   }
177   return buf_len;
178 }
179
180 void FakeSocket::DoAsyncWrite(scoped_refptr<net::IOBuffer> buf, int buf_len,
181                               const net::CompletionCallback& callback) {
182   write_pending_ = false;
183
184   if (written_data_) {
185     written_data_->insert(written_data_->end(),
186                           buf->data(), buf->data() + buf_len);
187   }
188   callback.Run(buf_len);
189 }
190
191 bool FakeSocket::SetReceiveBufferSize(int32 size) {
192   NOTIMPLEMENTED();
193   return false;
194 }
195 bool FakeSocket::SetSendBufferSize(int32 size) {
196   NOTIMPLEMENTED();
197   return false;
198 }
199
200 int FakeSocket::Connect(const net::CompletionCallback& callback) {
201   return 0;
202 }
203
204 void FakeSocket::Disconnect() {
205   NOTREACHED();
206 }
207
208 bool FakeSocket::IsConnected() const {
209   return true;
210 }
211
212 bool FakeSocket::IsConnectedAndIdle() const {
213   return false;
214 }
215
216 int FakeSocket::GetPeerAddress(net::IPEndPoint* address) const {
217   *address = peer_address_;
218   return net::OK;
219 }
220
221 int FakeSocket::GetLocalAddress(net::IPEndPoint* address) const {
222   *address = local_address_;
223   return net::OK;
224 }
225
226 const net::BoundNetLog& FakeSocket::NetLog() const {
227   NOTREACHED();
228   return net_log_;
229 }
230
231 void FakeSocket::SetSubresourceSpeculation() {
232   NOTREACHED();
233 }
234
235 void FakeSocket::SetOmniboxSpeculation() {
236   NOTREACHED();
237 }
238
239 bool FakeSocket::WasEverUsed() const {
240   return true;
241 }
242
243 bool FakeSocket::UsingTCPFastOpen() const {
244   return false;
245 }
246
247 bool FakeSocket::WasNpnNegotiated() const {
248   return false;
249 }
250
251 net::NextProto FakeSocket::GetNegotiatedProtocol() const {
252   return net::kProtoUnknown;
253 }
254
255 bool FakeSocket::GetSSLInfo(net::SSLInfo* ssl_info) {
256   return false;
257 }
258
259 void CreateRandomPacket(std::vector<char>* packet) {
260   size_t size = kStunHeaderSize + rand() % 1000;
261   packet->resize(size);
262   for (size_t i = 0; i < size; i++) {
263     (*packet)[i] = rand() % 256;
264   }
265   // Always set the first bit to ensure that generated packet is not
266   // valid STUN packet.
267   (*packet)[0] = (*packet)[0] | 0x80;
268 }
269
270 void CreateStunPacket(std::vector<char>* packet, uint16 type) {
271   CreateRandomPacket(packet);
272   *reinterpret_cast<uint16*>(&*packet->begin()) = base::HostToNet16(type);
273   *reinterpret_cast<uint16*>(&*packet->begin() + 2) =
274       base::HostToNet16(packet->size() - kStunHeaderSize);
275   *reinterpret_cast<uint32*>(&*packet->begin() + 4) =
276       base::HostToNet32(kStunMagicCookie);
277 }
278
279 void CreateStunRequest(std::vector<char>* packet) {
280   CreateStunPacket(packet, kStunBindingRequest);
281 }
282
283 void CreateStunResponse(std::vector<char>* packet) {
284   CreateStunPacket(packet, kStunBindingResponse);
285 }
286
287 void CreateStunError(std::vector<char>* packet) {
288   CreateStunPacket(packet, kStunBindingError);
289 }
290
291 net::IPEndPoint ParseAddress(const std::string ip_str, int port) {
292   net::IPAddressNumber ip;
293   EXPECT_TRUE(net::ParseIPLiteralToNumber(ip_str, &ip));
294   return net::IPEndPoint(ip, port);
295 }
296
297 MATCHER_P(MatchMessage, type, "") {
298   return arg->type() == type;
299 }
300
301 MATCHER_P(MatchPacketMessage, packet_content, "") {
302   if (arg->type() != P2PMsg_OnDataReceived::ID)
303     return false;
304   P2PMsg_OnDataReceived::Param params;
305   P2PMsg_OnDataReceived::Read(arg, &params);
306   return params.c == packet_content;
307 }
308
309 MATCHER_P(MatchIncomingSocketMessage, address, "") {
310   if (arg->type() != P2PMsg_OnIncomingTcpConnection::ID)
311     return false;
312   P2PMsg_OnIncomingTcpConnection::Param params;
313   P2PMsg_OnIncomingTcpConnection::Read(
314       arg, &params);
315   return params.b == address;
316 }
317
318 }  // namespace
319
320 #endif  // CONTENT_BROWSER_RENDERER_HOST_P2P_SOCKET_HOST_TEST_UTILS_H_