OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "net/udp/udp_socket_win.h" | 5 #include "net/udp/udp_socket_win.h" |
6 | 6 |
7 #include <mstcpip.h> | 7 #include <mstcpip.h> |
8 | 8 |
9 #include "base/callback.h" | 9 #include "base/callback.h" |
10 #include "base/logging.h" | 10 #include "base/logging.h" |
(...skipping 370 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
381 | 381 |
382 int UDPSocketWin::CreateSocket(int addr_family) { | 382 int UDPSocketWin::CreateSocket(int addr_family) { |
383 addr_family_ = addr_family; | 383 addr_family_ = addr_family; |
384 socket_ = CreatePlatformSocket(addr_family_, SOCK_DGRAM, IPPROTO_UDP); | 384 socket_ = CreatePlatformSocket(addr_family_, SOCK_DGRAM, IPPROTO_UDP); |
385 if (socket_ == INVALID_SOCKET) | 385 if (socket_ == INVALID_SOCKET) |
386 return MapSystemError(WSAGetLastError()); | 386 return MapSystemError(WSAGetLastError()); |
387 core_ = new Core(this); | 387 core_ = new Core(this); |
388 return OK; | 388 return OK; |
389 } | 389 } |
390 | 390 |
391 int UDPSocketWin::SetReceiveBufferSize(int32 size) { | 391 bool UDPSocketWin::SetReceiveBufferSize(int32 size) { |
392 DCHECK(CalledOnValidThread()); | 392 DCHECK(CalledOnValidThread()); |
393 int rv = setsockopt(socket_, SOL_SOCKET, SO_RCVBUF, | 393 setsockopt(socket_, SOL_SOCKET, SO_RCVBUF, |
394 reinterpret_cast<const char*>(&size), sizeof(size)); | 394 reinterpret_cast<const char*>(&size), sizeof(size)); |
395 if (rv != 0) | 395 // If the setsockopt fails, but the buffer is big enough, we will return |
396 return MapSystemError(WSAGetLastError()); | 396 // success. It is not worth testing the return value as we still need to check |
397 | 397 // via getsockopt anyway according to Windows documentation. |
398 // According to documentation, setsockopt may succeed, but we need to check | |
399 // the results via getsockopt to be sure it works on Windows. | |
400 int32 actual_size = 0; | 398 int32 actual_size = 0; |
401 int option_size = sizeof(actual_size); | 399 int option_size = sizeof(actual_size); |
402 rv = getsockopt(socket_, SOL_SOCKET, SO_RCVBUF, | 400 int rv = getsockopt(socket_, SOL_SOCKET, SO_RCVBUF, |
403 reinterpret_cast<char*>(&actual_size), &option_size); | 401 reinterpret_cast<char*>(&actual_size), &option_size); |
404 if (rv != 0) | 402 if (rv != 0) |
405 return MapSystemError(WSAGetLastError()); | 403 return false; |
406 if (actual_size >= size) | 404 if (actual_size < size) { |
407 return OK; | 405 UMA_HISTOGRAM_CUSTOM_COUNTS("Net.SocketReceiveBufferUnchangeable", |
408 UMA_HISTOGRAM_CUSTOM_COUNTS("Net.SocketUnchangeableReceiveBuffer", | 406 actual_size, 1000, 1000000, 50); |
409 actual_size, 1000, 1000000, 50); | 407 } |
410 return ERR_SOCKET_RECEIVE_BUFFER_SIZE_UNCHANGEABLE; | 408 return actual_size >= size; |
411 } | 409 } |
412 | 410 |
413 int UDPSocketWin::SetSendBufferSize(int32 size) { | 411 bool UDPSocketWin::SetSendBufferSize(int32 size) { |
414 DCHECK(CalledOnValidThread()); | 412 DCHECK(CalledOnValidThread()); |
415 int rv = setsockopt(socket_, SOL_SOCKET, SO_SNDBUF, | 413 setsockopt(socket_, SOL_SOCKET, SO_SNDBUF, |
416 reinterpret_cast<const char*>(&size), sizeof(size)); | 414 reinterpret_cast<const char*>(&size), sizeof(size)); |
417 if (rv != 0) | 415 // If the setsockopt fails, but the buffer is big enough, we will return |
418 return MapSystemError(WSAGetLastError()); | 416 // success. It is not worth testing the return value as we still need to check |
419 // According to documentation, setsockopt may succeed, but we need to check | 417 // via getsockopt anyway according to Windows documentation. |
420 // the results via getsockopt to be sure it works on Windows. | |
421 int32 actual_size = 0; | 418 int32 actual_size = 0; |
422 int option_size = sizeof(actual_size); | 419 int option_size = sizeof(actual_size); |
423 rv = getsockopt(socket_, SOL_SOCKET, SO_SNDBUF, | 420 int rv = getsockopt(socket_, SOL_SOCKET, SO_SNDBUF, |
424 reinterpret_cast<char*>(&actual_size), &option_size); | 421 reinterpret_cast<char*>(&actual_size), &option_size); |
425 if (rv != 0) | 422 if (rv != 0) |
426 return MapSystemError(WSAGetLastError()); | 423 return false; |
427 if (actual_size >= size) | 424 if (actual_size < size) { |
428 return OK; | 425 UMA_HISTOGRAM_CUSTOM_COUNTS("Net.SocketUnchangeableSendBuffer", |
429 UMA_HISTOGRAM_CUSTOM_COUNTS("Net.SocketUnchangeableSendBuffer", | 426 actual_size, 1000, 1000000, 50); |
430 actual_size, 1000, 1000000, 50); | 427 } |
431 return ERR_SOCKET_SEND_BUFFER_SIZE_UNCHANGEABLE; | 428 return actual_size >= size; |
432 } | 429 } |
433 | 430 |
434 void UDPSocketWin::AllowAddressReuse() { | 431 void UDPSocketWin::AllowAddressReuse() { |
435 DCHECK(CalledOnValidThread()); | 432 DCHECK(CalledOnValidThread()); |
436 DCHECK(!is_connected()); | 433 DCHECK(!is_connected()); |
437 | 434 |
438 socket_options_ |= SOCKET_OPTION_REUSE_ADDRESS; | 435 socket_options_ |= SOCKET_OPTION_REUSE_ADDRESS; |
439 } | 436 } |
440 | 437 |
441 void UDPSocketWin::AllowBroadcast() { | 438 void UDPSocketWin::AllowBroadcast() { |
(...skipping 393 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
835 // Note: setsockopt(IP_TOS) does not work on windows XP and later. | 832 // Note: setsockopt(IP_TOS) does not work on windows XP and later. |
836 int UDPSocketWin::SetDiffServCodePoint(DiffServCodePoint dscp) { | 833 int UDPSocketWin::SetDiffServCodePoint(DiffServCodePoint dscp) { |
837 return ERR_NOT_IMPLEMENTED; | 834 return ERR_NOT_IMPLEMENTED; |
838 } | 835 } |
839 | 836 |
840 void UDPSocketWin::DetachFromThread() { | 837 void UDPSocketWin::DetachFromThread() { |
841 base::NonThreadSafe::DetachFromThread(); | 838 base::NonThreadSafe::DetachFromThread(); |
842 } | 839 } |
843 | 840 |
844 } // namespace net | 841 } // namespace net |
OLD | NEW |