• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 #include "net/udp/udp_socket.h"
6 
7 #include "net/udp/udp_client_socket.h"
8 #include "net/udp/udp_server_socket.h"
9 
10 #include "base/basictypes.h"
11 #include "base/bind.h"
12 #include "base/metrics/histogram.h"
13 #include "base/stl_util.h"
14 #include "net/base/io_buffer.h"
15 #include "net/base/ip_endpoint.h"
16 #include "net/base/net_errors.h"
17 #include "net/base/net_log_unittest.h"
18 #include "net/base/net_util.h"
19 #include "net/base/test_completion_callback.h"
20 #include "net/test/net_test_suite.h"
21 #include "testing/gtest/include/gtest/gtest.h"
22 #include "testing/platform_test.h"
23 
24 namespace net {
25 
26 namespace {
27 
28 class UDPSocketTest : public PlatformTest {
29  public:
UDPSocketTest()30   UDPSocketTest()
31       : buffer_(new IOBufferWithSize(kMaxRead)) {
32   }
33 
34   // Blocks until data is read from the socket.
RecvFromSocket(UDPServerSocket * socket)35   std::string RecvFromSocket(UDPServerSocket* socket) {
36     TestCompletionCallback callback;
37 
38     int rv = socket->RecvFrom(
39         buffer_.get(), kMaxRead, &recv_from_address_, callback.callback());
40     if (rv == ERR_IO_PENDING)
41       rv = callback.WaitForResult();
42     if (rv < 0)
43       return std::string();  // error!
44     return std::string(buffer_->data(), rv);
45   }
46 
47   // Loop until |msg| has been written to the socket or until an
48   // error occurs.
49   // If |address| is specified, then it is used for the destination
50   // to send to. Otherwise, will send to the last socket this server
51   // received from.
SendToSocket(UDPServerSocket * socket,std::string msg)52   int SendToSocket(UDPServerSocket* socket, std::string msg) {
53     return SendToSocket(socket, msg, recv_from_address_);
54   }
55 
SendToSocket(UDPServerSocket * socket,std::string msg,const IPEndPoint & address)56   int SendToSocket(UDPServerSocket* socket,
57                    std::string msg,
58                    const IPEndPoint& address) {
59     TestCompletionCallback callback;
60 
61     int length = msg.length();
62     scoped_refptr<StringIOBuffer> io_buffer(new StringIOBuffer(msg));
63     scoped_refptr<DrainableIOBuffer> buffer(
64         new DrainableIOBuffer(io_buffer.get(), length));
65 
66     int bytes_sent = 0;
67     while (buffer->BytesRemaining()) {
68       int rv = socket->SendTo(
69           buffer.get(), buffer->BytesRemaining(), address, callback.callback());
70       if (rv == ERR_IO_PENDING)
71         rv = callback.WaitForResult();
72       if (rv <= 0)
73         return bytes_sent > 0 ? bytes_sent : rv;
74       bytes_sent += rv;
75       buffer->DidConsume(rv);
76     }
77     return bytes_sent;
78   }
79 
ReadSocket(UDPClientSocket * socket)80   std::string ReadSocket(UDPClientSocket* socket) {
81     TestCompletionCallback callback;
82 
83     int rv = socket->Read(buffer_.get(), kMaxRead, callback.callback());
84     if (rv == ERR_IO_PENDING)
85       rv = callback.WaitForResult();
86     if (rv < 0)
87       return std::string();  // error!
88     return std::string(buffer_->data(), rv);
89   }
90 
91   // Loop until |msg| has been written to the socket or until an
92   // error occurs.
WriteSocket(UDPClientSocket * socket,std::string msg)93   int WriteSocket(UDPClientSocket* socket, std::string msg) {
94     TestCompletionCallback callback;
95 
96     int length = msg.length();
97     scoped_refptr<StringIOBuffer> io_buffer(new StringIOBuffer(msg));
98     scoped_refptr<DrainableIOBuffer> buffer(
99         new DrainableIOBuffer(io_buffer.get(), length));
100 
101     int bytes_sent = 0;
102     while (buffer->BytesRemaining()) {
103       int rv = socket->Write(
104           buffer.get(), buffer->BytesRemaining(), callback.callback());
105       if (rv == ERR_IO_PENDING)
106         rv = callback.WaitForResult();
107       if (rv <= 0)
108         return bytes_sent > 0 ? bytes_sent : rv;
109       bytes_sent += rv;
110       buffer->DidConsume(rv);
111     }
112     return bytes_sent;
113   }
114 
115  protected:
116   static const int kMaxRead = 1024;
117   scoped_refptr<IOBufferWithSize> buffer_;
118   IPEndPoint recv_from_address_;
119 };
120 
121 // Creates and address from an ip/port and returns it in |address|.
CreateUDPAddress(std::string ip_str,int port,IPEndPoint * address)122 void CreateUDPAddress(std::string ip_str, int port, IPEndPoint* address) {
123   IPAddressNumber ip_number;
124   bool rv = ParseIPLiteralToNumber(ip_str, &ip_number);
125   if (!rv)
126     return;
127   *address = IPEndPoint(ip_number, port);
128 }
129 
TEST_F(UDPSocketTest,Connect)130 TEST_F(UDPSocketTest, Connect) {
131   const int kPort = 9999;
132   std::string simple_message("hello world!");
133 
134   // Setup the server to listen.
135   IPEndPoint bind_address;
136   CreateUDPAddress("127.0.0.1", kPort, &bind_address);
137   CapturingNetLog server_log;
138   scoped_ptr<UDPServerSocket> server(
139       new UDPServerSocket(&server_log, NetLog::Source()));
140   server->AllowAddressReuse();
141   int rv = server->Listen(bind_address);
142   ASSERT_EQ(OK, rv);
143 
144   // Setup the client.
145   IPEndPoint server_address;
146   CreateUDPAddress("127.0.0.1", kPort, &server_address);
147   CapturingNetLog client_log;
148   scoped_ptr<UDPClientSocket> client(
149       new UDPClientSocket(DatagramSocket::DEFAULT_BIND,
150                           RandIntCallback(),
151                           &client_log,
152                           NetLog::Source()));
153   rv = client->Connect(server_address);
154   EXPECT_EQ(OK, rv);
155 
156   // Client sends to the server.
157   rv = WriteSocket(client.get(), simple_message);
158   EXPECT_EQ(simple_message.length(), static_cast<size_t>(rv));
159 
160   // Server waits for message.
161   std::string str = RecvFromSocket(server.get());
162   DCHECK(simple_message == str);
163 
164   // Server echoes reply.
165   rv = SendToSocket(server.get(), simple_message);
166   EXPECT_EQ(simple_message.length(), static_cast<size_t>(rv));
167 
168   // Client waits for response.
169   str = ReadSocket(client.get());
170   DCHECK(simple_message == str);
171 
172   // Delete sockets so they log their final events.
173   server.reset();
174   client.reset();
175 
176   // Check the server's log.
177   CapturingNetLog::CapturedEntryList server_entries;
178   server_log.GetEntries(&server_entries);
179   EXPECT_EQ(4u, server_entries.size());
180   EXPECT_TRUE(LogContainsBeginEvent(
181       server_entries, 0, NetLog::TYPE_SOCKET_ALIVE));
182   EXPECT_TRUE(LogContainsEvent(
183       server_entries, 1, NetLog::TYPE_UDP_BYTES_RECEIVED, NetLog::PHASE_NONE));
184   EXPECT_TRUE(LogContainsEvent(
185       server_entries, 2, NetLog::TYPE_UDP_BYTES_SENT, NetLog::PHASE_NONE));
186   EXPECT_TRUE(LogContainsEndEvent(
187       server_entries, 3, NetLog::TYPE_SOCKET_ALIVE));
188 
189   // Check the client's log.
190   CapturingNetLog::CapturedEntryList client_entries;
191   client_log.GetEntries(&client_entries);
192   EXPECT_EQ(6u, client_entries.size());
193   EXPECT_TRUE(LogContainsBeginEvent(
194       client_entries, 0, NetLog::TYPE_SOCKET_ALIVE));
195   EXPECT_TRUE(LogContainsBeginEvent(
196       client_entries, 1, NetLog::TYPE_UDP_CONNECT));
197   EXPECT_TRUE(LogContainsEndEvent(
198       client_entries, 2, NetLog::TYPE_UDP_CONNECT));
199   EXPECT_TRUE(LogContainsEvent(
200       client_entries, 3, NetLog::TYPE_UDP_BYTES_SENT, NetLog::PHASE_NONE));
201   EXPECT_TRUE(LogContainsEvent(
202       client_entries, 4, NetLog::TYPE_UDP_BYTES_RECEIVED, NetLog::PHASE_NONE));
203   EXPECT_TRUE(LogContainsEndEvent(
204       client_entries, 5, NetLog::TYPE_SOCKET_ALIVE));
205 }
206 
207 #if defined(OS_MACOSX)
208 // UDPSocketPrivate_Broadcast is disabled for OSX because it requires
209 // root permissions on OSX 10.7+.
TEST_F(UDPSocketTest,DISABLED_Broadcast)210 TEST_F(UDPSocketTest, DISABLED_Broadcast) {
211 #elif defined(OS_ANDROID)
212 // It is also disabled for Android because it is extremely flaky.
213 // The first call to SendToSocket returns -109 (Address not reachable)
214 // in some unpredictable cases. crbug.com/139144.
215 TEST_F(UDPSocketTest, DISABLED_Broadcast) {
216 #else
217 TEST_F(UDPSocketTest, Broadcast) {
218 #endif
219   const int kPort = 9999;
220   std::string first_message("first message"), second_message("second message");
221 
222   IPEndPoint broadcast_address;
223   CreateUDPAddress("255.255.255.255", kPort, &broadcast_address);
224   IPEndPoint listen_address;
225   CreateUDPAddress("0.0.0.0", kPort, &listen_address);
226 
227   CapturingNetLog server1_log, server2_log;
228   scoped_ptr<UDPServerSocket> server1(
229       new UDPServerSocket(&server1_log, NetLog::Source()));
230   scoped_ptr<UDPServerSocket> server2(
231       new UDPServerSocket(&server2_log, NetLog::Source()));
232   server1->AllowAddressReuse();
233   server1->AllowBroadcast();
234   server2->AllowAddressReuse();
235   server2->AllowBroadcast();
236 
237   int rv = server1->Listen(listen_address);
238   EXPECT_EQ(OK, rv);
239   rv = server2->Listen(listen_address);
240   EXPECT_EQ(OK, rv);
241 
242   rv = SendToSocket(server1.get(), first_message, broadcast_address);
243   ASSERT_EQ(static_cast<int>(first_message.size()), rv);
244   std::string str = RecvFromSocket(server1.get());
245   ASSERT_EQ(first_message, str);
246   str = RecvFromSocket(server2.get());
247   ASSERT_EQ(first_message, str);
248 
249   rv = SendToSocket(server2.get(), second_message, broadcast_address);
250   ASSERT_EQ(static_cast<int>(second_message.size()), rv);
251   str = RecvFromSocket(server1.get());
252   ASSERT_EQ(second_message, str);
253   str = RecvFromSocket(server2.get());
254   ASSERT_EQ(second_message, str);
255 }
256 
257 // In this test, we verify that random binding logic works, which attempts
258 // to bind to a random port and returns if succeeds, otherwise retries for
259 // |kBindRetries| number of times.
260 
261 // To generate the scenario, we first create |kBindRetries| number of
262 // UDPClientSockets with default binding policy and connect to the same
263 // peer and save the used port numbers.  Then we get rid of the last
264 // socket, making sure that the local port it was bound to is available.
265 // Finally, we create a socket with random binding policy, passing it a
266 // test PRNG that would serve used port numbers in the array, one after
267 // another.  At the end, we make sure that the test socket was bound to the
268 // port that became available after deleting the last socket with default
269 // binding policy.
270 
271 // We do not test the randomness of bound ports, but that we are using
272 // passed in PRNG correctly, thus, it's the duty of PRNG to produce strong
273 // random numbers.
274 static const int kBindRetries = 10;
275 
276 class TestPrng {
277  public:
278   explicit TestPrng(const std::deque<int>& numbers) : numbers_(numbers) {}
279   int GetNext(int /* min */, int /* max */) {
280     DCHECK(!numbers_.empty());
281     int rv = numbers_.front();
282     numbers_.pop_front();
283     return rv;
284   }
285  private:
286   std::deque<int> numbers_;
287 
288   DISALLOW_COPY_AND_ASSIGN(TestPrng);
289 };
290 
291 #if defined(OS_ANDROID)
292 // Disabled on Android for lack of 192.168.1.13. crbug.com/161245
293 TEST_F(UDPSocketTest, DISABLED_ConnectRandomBind) {
294 #else
295 TEST_F(UDPSocketTest, ConnectRandomBind) {
296 #endif
297   std::vector<UDPClientSocket*> sockets;
298   IPEndPoint peer_address;
299   CreateUDPAddress("192.168.1.13", 53, &peer_address);
300 
301   // Create and connect sockets and save port numbers.
302   std::deque<int> used_ports;
303   for (int i = 0; i < kBindRetries; ++i) {
304     UDPClientSocket* socket =
305         new UDPClientSocket(DatagramSocket::DEFAULT_BIND,
306                             RandIntCallback(),
307                             NULL,
308                             NetLog::Source());
309     sockets.push_back(socket);
310     EXPECT_EQ(OK, socket->Connect(peer_address));
311 
312     IPEndPoint client_address;
313     EXPECT_EQ(OK, socket->GetLocalAddress(&client_address));
314     used_ports.push_back(client_address.port());
315   }
316 
317   // Free the last socket, its local port is still in |used_ports|.
318   delete sockets.back();
319   sockets.pop_back();
320 
321   TestPrng test_prng(used_ports);
322   RandIntCallback rand_int_cb =
323       base::Bind(&TestPrng::GetNext, base::Unretained(&test_prng));
324 
325   // Create a socket with random binding policy and connect.
326   scoped_ptr<UDPClientSocket> test_socket(
327       new UDPClientSocket(DatagramSocket::RANDOM_BIND,
328                           rand_int_cb,
329                           NULL,
330                           NetLog::Source()));
331   EXPECT_EQ(OK, test_socket->Connect(peer_address));
332 
333   // Make sure that the last port number in the |used_ports| was used.
334   IPEndPoint client_address;
335   EXPECT_EQ(OK, test_socket->GetLocalAddress(&client_address));
336   EXPECT_EQ(used_ports.back(), client_address.port());
337 
338   STLDeleteElements(&sockets);
339 }
340 
341 // Return a privileged port (under 1024) so binding will fail.
342 int PrivilegedRand(int min, int max) {
343   // Chosen by fair dice roll.  Guaranteed to be random.
344   return 4;
345 }
346 
347 TEST_F(UDPSocketTest, ConnectFail) {
348   IPEndPoint peer_address;
349   CreateUDPAddress("0.0.0.0", 53, &peer_address);
350 
351   scoped_ptr<UDPSocket> socket(
352       new UDPSocket(DatagramSocket::RANDOM_BIND,
353                     base::Bind(&PrivilegedRand),
354                     NULL,
355                     NetLog::Source()));
356   int rv = socket->Connect(peer_address);
357   // Connect should have failed since we couldn't bind to that port,
358   EXPECT_NE(OK, rv);
359   // Make sure that UDPSocket actually closed the socket.
360   EXPECT_FALSE(socket->is_connected());
361 }
362 
363 // In this test, we verify that connect() on a socket will have the effect
364 // of filtering reads on this socket only to data read from the destination
365 // we connected to.
366 //
367 // The purpose of this test is that some documentation indicates that connect
368 // binds the client's sends to send to a particular server endpoint, but does
369 // not bind the client's reads to only be from that endpoint, and that we need
370 // to always use recvfrom() to disambiguate.
371 TEST_F(UDPSocketTest, VerifyConnectBindsAddr) {
372   const int kPort1 = 9999;
373   const int kPort2 = 10000;
374   std::string simple_message("hello world!");
375   std::string foreign_message("BAD MESSAGE TO GET!!");
376 
377   // Setup the first server to listen.
378   IPEndPoint bind_address;
379   CreateUDPAddress("127.0.0.1", kPort1, &bind_address);
380   UDPServerSocket server1(NULL, NetLog::Source());
381   server1.AllowAddressReuse();
382   int rv = server1.Listen(bind_address);
383   ASSERT_EQ(OK, rv);
384 
385   // Setup the second server to listen.
386   CreateUDPAddress("127.0.0.1", kPort2, &bind_address);
387   UDPServerSocket server2(NULL, NetLog::Source());
388   server2.AllowAddressReuse();
389   rv = server2.Listen(bind_address);
390   ASSERT_EQ(OK, rv);
391 
392   // Setup the client, connected to server 1.
393   IPEndPoint server_address;
394   CreateUDPAddress("127.0.0.1", kPort1, &server_address);
395   UDPClientSocket client(DatagramSocket::DEFAULT_BIND,
396                          RandIntCallback(),
397                          NULL,
398                          NetLog::Source());
399   rv = client.Connect(server_address);
400   EXPECT_EQ(OK, rv);
401 
402   // Client sends to server1.
403   rv = WriteSocket(&client, simple_message);
404   EXPECT_EQ(simple_message.length(), static_cast<size_t>(rv));
405 
406   // Server1 waits for message.
407   std::string str = RecvFromSocket(&server1);
408   DCHECK(simple_message == str);
409 
410   // Get the client's address.
411   IPEndPoint client_address;
412   rv = client.GetLocalAddress(&client_address);
413   EXPECT_EQ(OK, rv);
414 
415   // Server2 sends reply.
416   rv = SendToSocket(&server2, foreign_message,
417                     client_address);
418   EXPECT_EQ(foreign_message.length(), static_cast<size_t>(rv));
419 
420   // Server1 sends reply.
421   rv = SendToSocket(&server1, simple_message,
422                     client_address);
423   EXPECT_EQ(simple_message.length(), static_cast<size_t>(rv));
424 
425   // Client waits for response.
426   str = ReadSocket(&client);
427   DCHECK(simple_message == str);
428 }
429 
430 TEST_F(UDPSocketTest, ClientGetLocalPeerAddresses) {
431   struct TestData {
432     std::string remote_address;
433     std::string local_address;
434     bool may_fail;
435   } tests[] = {
436     { "127.0.00.1", "127.0.0.1", false },
437     { "::1", "::1", true },
438 #if !defined(OS_ANDROID)
439     // Addresses below are disabled on Android. See crbug.com/161248
440     { "192.168.1.1", "127.0.0.1", false },
441     { "2001:db8:0::42", "::1", true },
442 #endif
443   };
444   for (size_t i = 0; i < ARRAYSIZE_UNSAFE(tests); i++) {
445     SCOPED_TRACE(std::string("Connecting from ") +  tests[i].local_address +
446                  std::string(" to ") + tests[i].remote_address);
447 
448     IPAddressNumber ip_number;
449     ParseIPLiteralToNumber(tests[i].remote_address, &ip_number);
450     IPEndPoint remote_address(ip_number, 80);
451     ParseIPLiteralToNumber(tests[i].local_address, &ip_number);
452     IPEndPoint local_address(ip_number, 80);
453 
454     UDPClientSocket client(DatagramSocket::DEFAULT_BIND,
455                            RandIntCallback(),
456                            NULL,
457                            NetLog::Source());
458     int rv = client.Connect(remote_address);
459     if (tests[i].may_fail && rv == ERR_ADDRESS_UNREACHABLE) {
460       // Connect() may return ERR_ADDRESS_UNREACHABLE for IPv6
461       // addresses if IPv6 is not configured.
462       continue;
463     }
464 
465     EXPECT_LE(ERR_IO_PENDING, rv);
466 
467     IPEndPoint fetched_local_address;
468     rv = client.GetLocalAddress(&fetched_local_address);
469     EXPECT_EQ(OK, rv);
470 
471     // TODO(mbelshe): figure out how to verify the IP and port.
472     //                The port is dynamically generated by the udp stack.
473     //                The IP is the real IP of the client, not necessarily
474     //                loopback.
475     //EXPECT_EQ(local_address.address(), fetched_local_address.address());
476 
477     IPEndPoint fetched_remote_address;
478     rv = client.GetPeerAddress(&fetched_remote_address);
479     EXPECT_EQ(OK, rv);
480 
481     EXPECT_EQ(remote_address, fetched_remote_address);
482   }
483 }
484 
485 TEST_F(UDPSocketTest, ServerGetLocalAddress) {
486   IPEndPoint bind_address;
487   CreateUDPAddress("127.0.0.1", 0, &bind_address);
488   UDPServerSocket server(NULL, NetLog::Source());
489   int rv = server.Listen(bind_address);
490   EXPECT_EQ(OK, rv);
491 
492   IPEndPoint local_address;
493   rv = server.GetLocalAddress(&local_address);
494   EXPECT_EQ(rv, 0);
495 
496   // Verify that port was allocated.
497   EXPECT_GT(local_address.port(), 0);
498   EXPECT_EQ(local_address.address(), bind_address.address());
499 }
500 
501 TEST_F(UDPSocketTest, ServerGetPeerAddress) {
502   IPEndPoint bind_address;
503   CreateUDPAddress("127.0.0.1", 0, &bind_address);
504   UDPServerSocket server(NULL, NetLog::Source());
505   int rv = server.Listen(bind_address);
506   EXPECT_EQ(OK, rv);
507 
508   IPEndPoint peer_address;
509   rv = server.GetPeerAddress(&peer_address);
510   EXPECT_EQ(rv, ERR_SOCKET_NOT_CONNECTED);
511 }
512 
513 // Close the socket while read is pending.
514 TEST_F(UDPSocketTest, CloseWithPendingRead) {
515   IPEndPoint bind_address;
516   CreateUDPAddress("127.0.0.1", 0, &bind_address);
517   UDPServerSocket server(NULL, NetLog::Source());
518   int rv = server.Listen(bind_address);
519   EXPECT_EQ(OK, rv);
520 
521   TestCompletionCallback callback;
522   IPEndPoint from;
523   rv = server.RecvFrom(buffer_.get(), kMaxRead, &from, callback.callback());
524   EXPECT_EQ(rv, ERR_IO_PENDING);
525 
526   server.Close();
527 
528   EXPECT_FALSE(callback.have_result());
529 }
530 
531 #if defined(OS_ANDROID)
532 // Some Android devices do not support multicast socket.
533 // The ones supporting multicast need WifiManager.MulitcastLock to enable it.
534 // http://goo.gl/jjAk9
535 #define MAYBE_JoinMulticastGroup DISABLED_JoinMulticastGroup
536 #else
537 #define MAYBE_JoinMulticastGroup JoinMulticastGroup
538 #endif  // defined(OS_ANDROID)
539 
540 TEST_F(UDPSocketTest, MAYBE_JoinMulticastGroup) {
541   const int kPort = 9999;
542   const char* const kGroup = "237.132.100.17";
543 
544   IPEndPoint bind_address;
545   CreateUDPAddress("0.0.0.0", kPort, &bind_address);
546   IPAddressNumber group_ip;
547   EXPECT_TRUE(ParseIPLiteralToNumber(kGroup, &group_ip));
548 
549   UDPSocket socket(DatagramSocket::DEFAULT_BIND,
550                    RandIntCallback(),
551                    NULL,
552                    NetLog::Source());
553   EXPECT_EQ(OK, socket.Bind(bind_address));
554   EXPECT_EQ(OK, socket.JoinGroup(group_ip));
555   // Joining group multiple times.
556   EXPECT_NE(OK, socket.JoinGroup(group_ip));
557   EXPECT_EQ(OK, socket.LeaveGroup(group_ip));
558   // Leaving group multiple times.
559   EXPECT_NE(OK, socket.LeaveGroup(group_ip));
560 
561   socket.Close();
562 }
563 
564 TEST_F(UDPSocketTest, MulticastOptions) {
565   const int kPort = 9999;
566   IPEndPoint bind_address;
567   CreateUDPAddress("0.0.0.0", kPort, &bind_address);
568 
569   UDPSocket socket(DatagramSocket::DEFAULT_BIND,
570                    RandIntCallback(),
571                    NULL,
572                    NetLog::Source());
573   // Before binding.
574   EXPECT_EQ(OK, socket.SetMulticastLoopbackMode(false));
575   EXPECT_EQ(OK, socket.SetMulticastLoopbackMode(true));
576   EXPECT_EQ(OK, socket.SetMulticastTimeToLive(0));
577   EXPECT_EQ(OK, socket.SetMulticastTimeToLive(3));
578   EXPECT_NE(OK, socket.SetMulticastTimeToLive(-1));
579   EXPECT_EQ(OK, socket.SetMulticastInterface(0));
580 
581   EXPECT_EQ(OK, socket.Bind(bind_address));
582 
583   EXPECT_NE(OK, socket.SetMulticastLoopbackMode(false));
584   EXPECT_NE(OK, socket.SetMulticastTimeToLive(0));
585   EXPECT_NE(OK, socket.SetMulticastInterface(0));
586 
587   socket.Close();
588 }
589 
590 // Checking that DSCP bits are set correctly is difficult,
591 // but let's check that the code doesn't crash at least.
592 TEST_F(UDPSocketTest, SetDSCP) {
593   // Setup the server to listen.
594   IPEndPoint bind_address;
595   UDPSocket client(DatagramSocket::DEFAULT_BIND,
596                    RandIntCallback(),
597                    NULL,
598                    NetLog::Source());
599   // We need a real IP, but we won't actually send anything to it.
600   CreateUDPAddress("8.8.8.8", 9999, &bind_address);
601   int rv = client.Connect(bind_address);
602   if (rv != OK) {
603     // Let's try localhost then..
604     CreateUDPAddress("127.0.0.1", 9999, &bind_address);
605     rv = client.Connect(bind_address);
606   }
607   EXPECT_EQ(OK, rv);
608 
609   client.SetDiffServCodePoint(DSCP_NO_CHANGE);
610   client.SetDiffServCodePoint(DSCP_AF41);
611   client.SetDiffServCodePoint(DSCP_DEFAULT);
612   client.SetDiffServCodePoint(DSCP_CS2);
613   client.SetDiffServCodePoint(DSCP_NO_CHANGE);
614   client.SetDiffServCodePoint(DSCP_DEFAULT);
615   client.Close();
616 }
617 
618 }  // namespace
619 
620 #if defined(OS_WIN)
621 
622 namespace {
623 
624 const HANDLE kFakeHandle = (HANDLE)19;
625 const QOS_FLOWID kFakeFlowId = (QOS_FLOWID)27;
626 
627 BOOL WINAPI FakeQOSCreateHandleFAIL(PQOS_VERSION version, PHANDLE handle) {
628   EXPECT_EQ(0, version->MinorVersion);
629   EXPECT_EQ(1, version->MajorVersion);
630   SetLastError(ERROR_OPEN_FAILED);
631   return false;
632 }
633 
634 BOOL WINAPI FakeQOSCreateHandle(PQOS_VERSION version, PHANDLE handle) {
635   EXPECT_EQ(0, version->MinorVersion);
636   EXPECT_EQ(1, version->MajorVersion);
637   *handle = kFakeHandle;
638   return true;
639 }
640 
641 BOOL WINAPI FakeQOSCloseHandle(HANDLE handle) {
642   EXPECT_EQ(kFakeHandle, handle);
643   return true;
644 }
645 
646 QOS_TRAFFIC_TYPE g_expected_traffic_type;
647 
648 BOOL WINAPI FakeQOSAddSocketToFlow(HANDLE handle,
649                                    SOCKET socket,
650                                    PSOCKADDR addr,
651                                    QOS_TRAFFIC_TYPE traffic_type,
652                                    DWORD flags,
653                                    PQOS_FLOWID flow_id) {
654   EXPECT_EQ(kFakeHandle, handle);
655   EXPECT_EQ(NULL, addr);
656   EXPECT_EQ(QOS_NON_ADAPTIVE_FLOW, flags);
657   EXPECT_EQ(0, *flow_id);
658   *flow_id = kFakeFlowId;
659   return true;
660 }
661 
662 BOOL WINAPI FakeQOSRemoveSocketFromFlow(HANDLE handle,
663                                         SOCKET socket,
664                                         QOS_FLOWID flowid,
665                                         DWORD reserved) {
666   EXPECT_EQ(kFakeHandle, handle);
667   EXPECT_EQ(NULL, socket);
668   EXPECT_EQ(kFakeFlowId, flowid);
669   EXPECT_EQ(0, reserved);
670   return true;
671 }
672 
673 DWORD g_expected_dscp;
674 
675 BOOL WINAPI FakeQOSSetFlow(HANDLE handle,
676                            QOS_FLOWID flow_id,
677                            QOS_SET_FLOW op,
678                            ULONG size,
679                            PVOID data,
680                            DWORD reserved,
681                            LPOVERLAPPED overlapped) {
682   EXPECT_EQ(kFakeHandle, handle);
683   EXPECT_EQ(QOSSetOutgoingDSCPValue, op);
684   EXPECT_EQ(sizeof(DWORD), size);
685   EXPECT_EQ(g_expected_dscp, *reinterpret_cast<DWORD*>(data));
686   EXPECT_EQ(kFakeFlowId, flow_id);
687   EXPECT_EQ(0, reserved);
688   EXPECT_EQ(NULL, overlapped);
689   return true;
690 }
691 
692 }  // namespace
693 
694 // Mock out the Qwave functions and make sure they are
695 // called correctly. Must be in net namespace for friendship
696 // reasons.
697 TEST_F(UDPSocketTest, SetDSCPFake) {
698   // Setup the server to listen.
699   IPEndPoint bind_address;
700   // We need a real IP, but we won't actually send anything to it.
701   CreateUDPAddress("8.8.8.8", 9999, &bind_address);
702   UDPSocket client(DatagramSocket::DEFAULT_BIND,
703                    RandIntCallback(),
704                    NULL,
705                    NetLog::Source());
706   int rv = client.SetDiffServCodePoint(DSCP_AF41);
707   EXPECT_EQ(ERR_SOCKET_NOT_CONNECTED, rv);
708   rv = client.Connect(bind_address);
709   EXPECT_EQ(OK, rv);
710 
711   QwaveAPI& qos(QwaveAPI::Get());
712   qos.create_handle_func_ = FakeQOSCreateHandleFAIL;
713   qos.close_handle_func_ = FakeQOSCloseHandle;
714   qos.add_socket_to_flow_func_ = FakeQOSAddSocketToFlow;
715   qos.remove_socket_from_flow_func_ = FakeQOSRemoveSocketFromFlow;
716   qos.set_flow_func_ = FakeQOSSetFlow;
717   qos.qwave_supported_ = true;
718 
719   EXPECT_EQ(OK, client.SetDiffServCodePoint(DSCP_NO_CHANGE));
720   EXPECT_EQ(ERROR_NOT_SUPPORTED, client.SetDiffServCodePoint(DSCP_AF41));
721   qos.create_handle_func_ = FakeQOSCreateHandle;
722   g_expected_dscp = DSCP_AF41;
723   g_expected_traffic_type = QOSTrafficTypeAudioVideo;
724   EXPECT_EQ(OK, client.SetDiffServCodePoint(DSCP_AF41));
725   g_expected_dscp = DSCP_DEFAULT;
726   g_expected_traffic_type = QOSTrafficTypeBestEffort;
727   EXPECT_EQ(OK, client.SetDiffServCodePoint(DSCP_DEFAULT));
728   g_expected_dscp = DSCP_CS2;
729   g_expected_traffic_type = QOSTrafficTypeExcellentEffort;
730   EXPECT_EQ(OK, client.SetDiffServCodePoint(DSCP_CS2));
731   g_expected_dscp = DSCP_CS3;
732   g_expected_traffic_type = QOSTrafficTypeExcellentEffort;
733   EXPECT_EQ(OK, client.SetDiffServCodePoint(DSCP_NO_CHANGE));
734   g_expected_dscp = DSCP_DEFAULT;
735   g_expected_traffic_type = QOSTrafficTypeBestEffort;
736   EXPECT_EQ(OK, client.SetDiffServCodePoint(DSCP_DEFAULT));
737   client.Close();
738 }
739 #endif
740 
741 }  // namespace net
742