Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2013 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/socket/tcp_socket.h" | 5 #include "net/socket/tcp_socket.h" |
| 6 #include "net/socket/tcp_socket_win.h" | 6 #include "net/socket/tcp_socket_win.h" |
| 7 | 7 |
| 8 #include <errno.h> | 8 #include <errno.h> |
| 9 #include <mstcpip.h> | 9 #include <mstcpip.h> |
| 10 | 10 |
| (...skipping 22 matching lines...) Expand all Loading... | |
| 33 | 33 |
| 34 namespace net { | 34 namespace net { |
| 35 | 35 |
| 36 namespace { | 36 namespace { |
| 37 | 37 |
| 38 const int kTCPKeepAliveSeconds = 45; | 38 const int kTCPKeepAliveSeconds = 45; |
| 39 | 39 |
| 40 int SetSocketReceiveBufferSize(SOCKET socket, int32_t size) { | 40 int SetSocketReceiveBufferSize(SOCKET socket, int32_t size) { |
| 41 int rv = setsockopt(socket, SOL_SOCKET, SO_RCVBUF, | 41 int rv = setsockopt(socket, SOL_SOCKET, SO_RCVBUF, |
| 42 reinterpret_cast<const char*>(&size), sizeof(size)); | 42 reinterpret_cast<const char*>(&size), sizeof(size)); |
| 43 int net_error = (rv == 0) ? OK : MapSystemError(WSAGetLastError()); | 43 int os_error = WSAGetLastError(); |
| 44 int net_error = (rv == 0) ? OK : MapSystemError(os_error); | |
| 44 DCHECK(!rv) << "Could not set socket receive buffer size: " << net_error; | 45 DCHECK(!rv) << "Could not set socket receive buffer size: " << net_error; |
| 45 return net_error; | 46 return net_error; |
| 46 } | 47 } |
| 47 | 48 |
| 48 int SetSocketSendBufferSize(SOCKET socket, int32_t size) { | 49 int SetSocketSendBufferSize(SOCKET socket, int32_t size) { |
| 49 int rv = setsockopt(socket, SOL_SOCKET, SO_SNDBUF, | 50 int rv = setsockopt(socket, SOL_SOCKET, SO_SNDBUF, |
| 50 reinterpret_cast<const char*>(&size), sizeof(size)); | 51 reinterpret_cast<const char*>(&size), sizeof(size)); |
| 51 int net_error = (rv == 0) ? OK : MapSystemError(WSAGetLastError()); | 52 int os_error = WSAGetLastError(); |
|
eroman
2016/11/29 19:51:00
For these two cases, does the re-ordering make a d
Sigurður Ásgeirsson
2016/11/29 20:27:55
This is purely for consistency. Note that C++ can
| |
| 53 int net_error = (rv == 0) ? OK : MapSystemError(os_error); | |
| 52 DCHECK(!rv) << "Could not set socket send buffer size: " << net_error; | 54 DCHECK(!rv) << "Could not set socket send buffer size: " << net_error; |
| 53 return net_error; | 55 return net_error; |
| 54 } | 56 } |
| 55 | 57 |
| 56 // Disable Nagle. | 58 // Disable Nagle. |
| 57 // Enable TCP Keep-Alive to prevent NAT routers from timing out TCP | 59 // Enable TCP Keep-Alive to prevent NAT routers from timing out TCP |
| 58 // connections. See http://crbug.com/27400 for details. | 60 // connections. See http://crbug.com/27400 for details. |
| 59 bool SetTCPKeepAlive(SOCKET socket, BOOL enable, int delay_secs) { | 61 bool SetTCPKeepAlive(SOCKET socket, BOOL enable, int delay_secs) { |
| 60 unsigned delay = delay_secs * 1000; | 62 unsigned delay = delay_secs * 1000; |
| 61 struct tcp_keepalive keepalive_vals = { | 63 struct tcp_keepalive keepalive_vals = { |
| 62 enable ? 1u : 0u, // TCP keep-alive on. | 64 enable ? 1u : 0u, // TCP keep-alive on. |
| 63 delay, // Delay seconds before sending first TCP keep-alive packet. | 65 delay, // Delay seconds before sending first TCP keep-alive packet. |
| 64 delay, // Delay seconds between sending TCP keep-alive packets. | 66 delay, // Delay seconds between sending TCP keep-alive packets. |
| 65 }; | 67 }; |
| 66 DWORD bytes_returned = 0xABAB; | 68 DWORD bytes_returned = 0xABAB; |
| 67 int rv = WSAIoctl(socket, SIO_KEEPALIVE_VALS, &keepalive_vals, | 69 int rv = WSAIoctl(socket, SIO_KEEPALIVE_VALS, &keepalive_vals, |
| 68 sizeof(keepalive_vals), NULL, 0, | 70 sizeof(keepalive_vals), NULL, 0, |
| 69 &bytes_returned, NULL, NULL); | 71 &bytes_returned, NULL, NULL); |
| 72 int os_error = WSAGetLastError(); | |
| 70 DCHECK(!rv) << "Could not enable TCP Keep-Alive for socket: " << socket | 73 DCHECK(!rv) << "Could not enable TCP Keep-Alive for socket: " << socket |
| 71 << " [error: " << WSAGetLastError() << "]."; | 74 << " [error: " << os_error << "]."; |
| 72 | 75 |
| 73 // Disregard any failure in disabling nagle or enabling TCP Keep-Alive. | 76 // Disregard any failure in disabling nagle or enabling TCP Keep-Alive. |
| 74 return rv == 0; | 77 return rv == 0; |
| 75 } | 78 } |
| 76 | 79 |
| 77 int MapConnectError(int os_error) { | 80 int MapConnectError(int os_error) { |
| 78 switch (os_error) { | 81 switch (os_error) { |
| 79 // connect fails with WSAEACCES when Windows Firewall blocks the | 82 // connect fails with WSAEACCES when Windows Firewall blocks the |
| 80 // connection. | 83 // connection. |
| 81 case WSAEACCES: | 84 case WSAEACCES: |
| (...skipping 187 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 269 Close(); | 272 Close(); |
| 270 net_log_.EndEvent(NetLogEventType::SOCKET_ALIVE); | 273 net_log_.EndEvent(NetLogEventType::SOCKET_ALIVE); |
| 271 } | 274 } |
| 272 | 275 |
| 273 int TCPSocketWin::Open(AddressFamily family) { | 276 int TCPSocketWin::Open(AddressFamily family) { |
| 274 DCHECK(CalledOnValidThread()); | 277 DCHECK(CalledOnValidThread()); |
| 275 DCHECK_EQ(socket_, INVALID_SOCKET); | 278 DCHECK_EQ(socket_, INVALID_SOCKET); |
| 276 | 279 |
| 277 socket_ = CreatePlatformSocket(ConvertAddressFamily(family), SOCK_STREAM, | 280 socket_ = CreatePlatformSocket(ConvertAddressFamily(family), SOCK_STREAM, |
| 278 IPPROTO_TCP); | 281 IPPROTO_TCP); |
| 282 int os_error = WSAGetLastError(); | |
|
eroman
2016/11/29 19:51:00
Same issue as for base::SetNonBlocking() -- relies
Sigurður Ásgeirsson
2016/11/29 20:27:55
I don't know whether this works the same on other
| |
| 279 if (socket_ == INVALID_SOCKET) { | 283 if (socket_ == INVALID_SOCKET) { |
| 280 PLOG(ERROR) << "CreatePlatformSocket() returned an error"; | 284 PLOG(ERROR) << "CreatePlatformSocket() returned an error"; |
| 281 return MapSystemError(WSAGetLastError()); | 285 return MapSystemError(os_error); |
| 282 } | 286 } |
| 283 | 287 |
| 284 if (!base::SetNonBlocking(socket_)) { | 288 if (!base::SetNonBlocking(socket_)) { |
| 285 int result = MapSystemError(WSAGetLastError()); | 289 os_error = WSAGetLastError(); |
| 290 int result = MapSystemError(os_error); | |
| 286 Close(); | 291 Close(); |
| 287 return result; | 292 return result; |
| 288 } | 293 } |
| 289 | 294 |
| 290 return OK; | 295 return OK; |
| 291 } | 296 } |
| 292 | 297 |
| 293 int TCPSocketWin::AdoptConnectedSocket(SOCKET socket, | 298 int TCPSocketWin::AdoptConnectedSocket(SOCKET socket, |
| 294 const IPEndPoint& peer_address) { | 299 const IPEndPoint& peer_address) { |
| 295 DCHECK(CalledOnValidThread()); | 300 DCHECK(CalledOnValidThread()); |
| 296 DCHECK_EQ(socket_, INVALID_SOCKET); | 301 DCHECK_EQ(socket_, INVALID_SOCKET); |
| 297 DCHECK(!core_.get()); | 302 DCHECK(!core_.get()); |
| 298 | 303 |
| 299 socket_ = socket; | 304 socket_ = socket; |
| 300 | 305 |
| 301 if (!base::SetNonBlocking(socket_)) { | 306 if (!base::SetNonBlocking(socket_)) { |
| 302 int result = MapSystemError(WSAGetLastError()); | 307 int os_error = WSAGetLastError(); |
|
eroman
2016/11/29 19:51:00
Given this is called 3 times, I would suggest addi
Sigurður Ásgeirsson
2016/11/29 20:27:55
Done.
| |
| 308 int result = MapSystemError(os_error); | |
| 303 Close(); | 309 Close(); |
| 304 return result; | 310 return result; |
| 305 } | 311 } |
| 306 | 312 |
| 307 core_ = new Core(this); | 313 core_ = new Core(this); |
| 308 peer_address_.reset(new IPEndPoint(peer_address)); | 314 peer_address_.reset(new IPEndPoint(peer_address)); |
| 309 | 315 |
| 310 return OK; | 316 return OK; |
| 311 } | 317 } |
| 312 | 318 |
| 313 int TCPSocketWin::AdoptListenSocket(SOCKET socket) { | 319 int TCPSocketWin::AdoptListenSocket(SOCKET socket) { |
| 314 DCHECK(CalledOnValidThread()); | 320 DCHECK(CalledOnValidThread()); |
| 315 DCHECK_EQ(socket_, INVALID_SOCKET); | 321 DCHECK_EQ(socket_, INVALID_SOCKET); |
| 316 | 322 |
| 317 socket_ = socket; | 323 socket_ = socket; |
| 318 | 324 |
| 319 if (!base::SetNonBlocking(socket_)) { | 325 if (!base::SetNonBlocking(socket_)) { |
| 320 int result = MapSystemError(WSAGetLastError()); | 326 int os_error = WSAGetLastError(); |
| 327 int result = MapSystemError(os_error); | |
| 321 Close(); | 328 Close(); |
| 322 return result; | 329 return result; |
| 323 } | 330 } |
| 324 | 331 |
| 325 // |core_| is not needed for sockets that are used to accept connections. | 332 // |core_| is not needed for sockets that are used to accept connections. |
| 326 // The operation here is more like Open but with an existing socket. | 333 // The operation here is more like Open but with an existing socket. |
| 327 | 334 |
| 328 return OK; | 335 return OK; |
| 329 } | 336 } |
| 330 | 337 |
| 331 int TCPSocketWin::Bind(const IPEndPoint& address) { | 338 int TCPSocketWin::Bind(const IPEndPoint& address) { |
| 332 DCHECK(CalledOnValidThread()); | 339 DCHECK(CalledOnValidThread()); |
| 333 DCHECK_NE(socket_, INVALID_SOCKET); | 340 DCHECK_NE(socket_, INVALID_SOCKET); |
| 334 | 341 |
| 335 SockaddrStorage storage; | 342 SockaddrStorage storage; |
| 336 if (!address.ToSockAddr(storage.addr, &storage.addr_len)) | 343 if (!address.ToSockAddr(storage.addr, &storage.addr_len)) |
| 337 return ERR_ADDRESS_INVALID; | 344 return ERR_ADDRESS_INVALID; |
| 338 | 345 |
| 339 int result = bind(socket_, storage.addr, storage.addr_len); | 346 int result = bind(socket_, storage.addr, storage.addr_len); |
| 347 int os_error = WSAGetLastError(); | |
| 340 if (result < 0) { | 348 if (result < 0) { |
| 341 PLOG(ERROR) << "bind() returned an error"; | 349 PLOG(ERROR) << "bind() returned an error"; |
| 342 return MapSystemError(WSAGetLastError()); | 350 return MapSystemError(os_error); |
| 343 } | 351 } |
| 344 | 352 |
| 345 return OK; | 353 return OK; |
| 346 } | 354 } |
| 347 | 355 |
| 348 int TCPSocketWin::Listen(int backlog) { | 356 int TCPSocketWin::Listen(int backlog) { |
| 349 DCHECK(CalledOnValidThread()); | 357 DCHECK(CalledOnValidThread()); |
| 350 DCHECK_GT(backlog, 0); | 358 DCHECK_GT(backlog, 0); |
| 351 DCHECK_NE(socket_, INVALID_SOCKET); | 359 DCHECK_NE(socket_, INVALID_SOCKET); |
| 352 DCHECK_EQ(accept_event_, WSA_INVALID_EVENT); | 360 DCHECK_EQ(accept_event_, WSA_INVALID_EVENT); |
| 353 | 361 |
| 354 accept_event_ = WSACreateEvent(); | 362 accept_event_ = WSACreateEvent(); |
| 363 int os_error = WSAGetLastError(); | |
| 355 if (accept_event_ == WSA_INVALID_EVENT) { | 364 if (accept_event_ == WSA_INVALID_EVENT) { |
| 356 PLOG(ERROR) << "WSACreateEvent()"; | 365 PLOG(ERROR) << "WSACreateEvent()"; |
| 357 return MapSystemError(WSAGetLastError()); | 366 return MapSystemError(os_error); |
| 358 } | 367 } |
| 359 | 368 |
| 360 int result = listen(socket_, backlog); | 369 int result = listen(socket_, backlog); |
| 370 os_error = WSAGetLastError(); | |
| 361 if (result < 0) { | 371 if (result < 0) { |
| 362 PLOG(ERROR) << "listen() returned an error"; | 372 PLOG(ERROR) << "listen() returned an error"; |
| 363 return MapSystemError(WSAGetLastError()); | 373 return MapSystemError(os_error); |
| 364 } | 374 } |
| 365 | 375 |
| 366 return OK; | 376 return OK; |
| 367 } | 377 } |
| 368 | 378 |
| 369 int TCPSocketWin::Accept(std::unique_ptr<TCPSocketWin>* socket, | 379 int TCPSocketWin::Accept(std::unique_ptr<TCPSocketWin>* socket, |
| 370 IPEndPoint* address, | 380 IPEndPoint* address, |
| 371 const CompletionCallback& callback) { | 381 const CompletionCallback& callback) { |
| 372 DCHECK(CalledOnValidThread()); | 382 DCHECK(CalledOnValidThread()); |
| 373 DCHECK(socket); | 383 DCHECK(socket); |
| (...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 431 | 441 |
| 432 if (socket_ == INVALID_SOCKET || waiting_connect_) | 442 if (socket_ == INVALID_SOCKET || waiting_connect_) |
| 433 return false; | 443 return false; |
| 434 | 444 |
| 435 if (waiting_read_) | 445 if (waiting_read_) |
| 436 return true; | 446 return true; |
| 437 | 447 |
| 438 // Check if connection is alive. | 448 // Check if connection is alive. |
| 439 char c; | 449 char c; |
| 440 int rv = recv(socket_, &c, 1, MSG_PEEK); | 450 int rv = recv(socket_, &c, 1, MSG_PEEK); |
| 451 int os_error = WSAGetLastError(); | |
| 441 if (rv == 0) | 452 if (rv == 0) |
| 442 return false; | 453 return false; |
| 443 if (rv == SOCKET_ERROR && WSAGetLastError() != WSAEWOULDBLOCK) | 454 if (rv == SOCKET_ERROR && os_error != WSAEWOULDBLOCK) |
| 444 return false; | 455 return false; |
| 445 | 456 |
| 446 return true; | 457 return true; |
| 447 } | 458 } |
| 448 | 459 |
| 449 bool TCPSocketWin::IsConnectedAndIdle() const { | 460 bool TCPSocketWin::IsConnectedAndIdle() const { |
| 450 DCHECK(CalledOnValidThread()); | 461 DCHECK(CalledOnValidThread()); |
| 451 | 462 |
| 452 if (socket_ == INVALID_SOCKET || waiting_connect_) | 463 if (socket_ == INVALID_SOCKET || waiting_connect_) |
| 453 return false; | 464 return false; |
| 454 | 465 |
| 455 if (waiting_read_) | 466 if (waiting_read_) |
| 456 return true; | 467 return true; |
| 457 | 468 |
| 458 // Check if connection is alive and we haven't received any data | 469 // Check if connection is alive and we haven't received any data |
| 459 // unexpectedly. | 470 // unexpectedly. |
| 460 char c; | 471 char c; |
| 461 int rv = recv(socket_, &c, 1, MSG_PEEK); | 472 int rv = recv(socket_, &c, 1, MSG_PEEK); |
| 473 int os_error = WSAGetLastError(); | |
| 462 if (rv >= 0) | 474 if (rv >= 0) |
| 463 return false; | 475 return false; |
| 464 if (WSAGetLastError() != WSAEWOULDBLOCK) | 476 if (os_error != WSAEWOULDBLOCK) |
| 465 return false; | 477 return false; |
| 466 | 478 |
| 467 return true; | 479 return true; |
| 468 } | 480 } |
| 469 | 481 |
| 470 int TCPSocketWin::Read(IOBuffer* buf, | 482 int TCPSocketWin::Read(IOBuffer* buf, |
| 471 int buf_len, | 483 int buf_len, |
| 472 const CompletionCallback& callback) { | 484 const CompletionCallback& callback) { |
| 473 DCHECK(CalledOnValidThread()); | 485 DCHECK(CalledOnValidThread()); |
| 474 DCHECK_NE(socket_, INVALID_SOCKET); | 486 DCHECK_NE(socket_, INVALID_SOCKET); |
| (...skipping 16 matching lines...) Expand all Loading... | |
| 491 | 503 |
| 492 WSABUF write_buffer; | 504 WSABUF write_buffer; |
| 493 write_buffer.len = buf_len; | 505 write_buffer.len = buf_len; |
| 494 write_buffer.buf = buf->data(); | 506 write_buffer.buf = buf->data(); |
| 495 | 507 |
| 496 // TODO(wtc): Remove the assertion after enough testing. | 508 // TODO(wtc): Remove the assertion after enough testing. |
| 497 AssertEventNotSignaled(core_->write_overlapped_.hEvent); | 509 AssertEventNotSignaled(core_->write_overlapped_.hEvent); |
| 498 DWORD num; | 510 DWORD num; |
| 499 int rv = WSASend(socket_, &write_buffer, 1, &num, 0, | 511 int rv = WSASend(socket_, &write_buffer, 1, &num, 0, |
| 500 &core_->write_overlapped_, NULL); | 512 &core_->write_overlapped_, NULL); |
| 513 int os_error = WSAGetLastError(); | |
| 501 if (rv == 0) { | 514 if (rv == 0) { |
| 502 if (ResetEventIfSignaled(core_->write_overlapped_.hEvent)) { | 515 if (ResetEventIfSignaled(core_->write_overlapped_.hEvent)) { |
| 503 rv = static_cast<int>(num); | 516 rv = static_cast<int>(num); |
| 504 if (rv > buf_len || rv < 0) { | 517 if (rv > buf_len || rv < 0) { |
| 505 // It seems that some winsock interceptors report that more was written | 518 // It seems that some winsock interceptors report that more was written |
| 506 // than was available. Treat this as an error. http://crbug.com/27870 | 519 // than was available. Treat this as an error. http://crbug.com/27870 |
| 507 LOG(ERROR) << "Detected broken LSP: Asked to write " << buf_len | 520 LOG(ERROR) << "Detected broken LSP: Asked to write " << buf_len |
| 508 << " bytes, but " << rv << " bytes reported."; | 521 << " bytes, but " << rv << " bytes reported."; |
| 509 return ERR_WINSOCK_UNEXPECTED_WRITTEN_BYTES; | 522 return ERR_WINSOCK_UNEXPECTED_WRITTEN_BYTES; |
| 510 } | 523 } |
| 511 net_log_.AddByteTransferEvent(NetLogEventType::SOCKET_BYTES_SENT, rv, | 524 net_log_.AddByteTransferEvent(NetLogEventType::SOCKET_BYTES_SENT, rv, |
| 512 buf->data()); | 525 buf->data()); |
| 513 NetworkActivityMonitor::GetInstance()->IncrementBytesSent(rv); | 526 NetworkActivityMonitor::GetInstance()->IncrementBytesSent(rv); |
| 514 return rv; | 527 return rv; |
| 515 } | 528 } |
| 516 } else { | 529 } else { |
| 517 int os_error = WSAGetLastError(); | |
| 518 if (os_error != WSA_IO_PENDING) { | 530 if (os_error != WSA_IO_PENDING) { |
| 519 int net_error = MapSystemError(os_error); | 531 int net_error = MapSystemError(os_error); |
| 520 net_log_.AddEvent(NetLogEventType::SOCKET_WRITE_ERROR, | 532 net_log_.AddEvent(NetLogEventType::SOCKET_WRITE_ERROR, |
| 521 CreateNetLogSocketErrorCallback(net_error, os_error)); | 533 CreateNetLogSocketErrorCallback(net_error, os_error)); |
| 522 return net_error; | 534 return net_error; |
| 523 } | 535 } |
| 524 } | 536 } |
| 525 waiting_write_ = true; | 537 waiting_write_ = true; |
| 526 write_callback_ = callback; | 538 write_callback_ = callback; |
| 527 core_->write_iobuffer_ = buf; | 539 core_->write_iobuffer_ = buf; |
| 528 core_->write_buffer_length_ = buf_len; | 540 core_->write_buffer_length_ = buf_len; |
| 529 core_->WatchForWrite(); | 541 core_->WatchForWrite(); |
| 530 return ERR_IO_PENDING; | 542 return ERR_IO_PENDING; |
| 531 } | 543 } |
| 532 | 544 |
| 533 int TCPSocketWin::GetLocalAddress(IPEndPoint* address) const { | 545 int TCPSocketWin::GetLocalAddress(IPEndPoint* address) const { |
| 534 DCHECK(CalledOnValidThread()); | 546 DCHECK(CalledOnValidThread()); |
| 535 DCHECK(address); | 547 DCHECK(address); |
| 536 | 548 |
| 537 SockaddrStorage storage; | 549 SockaddrStorage storage; |
| 538 if (getsockname(socket_, storage.addr, &storage.addr_len)) | 550 if (getsockname(socket_, storage.addr, &storage.addr_len)) { |
| 539 return MapSystemError(WSAGetLastError()); | 551 int os_error = WSAGetLastError(); |
| 552 return MapSystemError(os_error); | |
| 553 } | |
| 540 if (!address->FromSockAddr(storage.addr, storage.addr_len)) | 554 if (!address->FromSockAddr(storage.addr, storage.addr_len)) |
| 541 return ERR_ADDRESS_INVALID; | 555 return ERR_ADDRESS_INVALID; |
| 542 | 556 |
| 543 return OK; | 557 return OK; |
| 544 } | 558 } |
| 545 | 559 |
| 546 int TCPSocketWin::GetPeerAddress(IPEndPoint* address) const { | 560 int TCPSocketWin::GetPeerAddress(IPEndPoint* address) const { |
| 547 DCHECK(CalledOnValidThread()); | 561 DCHECK(CalledOnValidThread()); |
| 548 DCHECK(address); | 562 DCHECK(address); |
| 549 if (!IsConnected()) | 563 if (!IsConnected()) |
| (...skipping 132 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 682 logging_multiple_connect_attempts_ = false; | 696 logging_multiple_connect_attempts_ = false; |
| 683 } else { | 697 } else { |
| 684 NOTREACHED(); | 698 NOTREACHED(); |
| 685 } | 699 } |
| 686 } | 700 } |
| 687 | 701 |
| 688 int TCPSocketWin::AcceptInternal(std::unique_ptr<TCPSocketWin>* socket, | 702 int TCPSocketWin::AcceptInternal(std::unique_ptr<TCPSocketWin>* socket, |
| 689 IPEndPoint* address) { | 703 IPEndPoint* address) { |
| 690 SockaddrStorage storage; | 704 SockaddrStorage storage; |
| 691 int new_socket = accept(socket_, storage.addr, &storage.addr_len); | 705 int new_socket = accept(socket_, storage.addr, &storage.addr_len); |
| 706 int os_error = WSAGetLastError(); | |
| 692 if (new_socket < 0) { | 707 if (new_socket < 0) { |
| 693 int net_error = MapSystemError(WSAGetLastError()); | 708 int net_error = MapSystemError(os_error); |
| 694 if (net_error != ERR_IO_PENDING) | 709 if (net_error != ERR_IO_PENDING) |
| 695 net_log_.EndEventWithNetErrorCode(NetLogEventType::TCP_ACCEPT, net_error); | 710 net_log_.EndEventWithNetErrorCode(NetLogEventType::TCP_ACCEPT, net_error); |
| 696 return net_error; | 711 return net_error; |
| 697 } | 712 } |
| 698 | 713 |
| 699 IPEndPoint ip_end_point; | 714 IPEndPoint ip_end_point; |
| 700 if (!ip_end_point.FromSockAddr(storage.addr, storage.addr_len)) { | 715 if (!ip_end_point.FromSockAddr(storage.addr, storage.addr_len)) { |
| 701 NOTREACHED(); | 716 NOTREACHED(); |
| 702 if (closesocket(new_socket) < 0) | 717 if (closesocket(new_socket) < 0) |
| 703 PLOG(ERROR) << "closesocket"; | 718 PLOG(ERROR) << "closesocket"; |
| (...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 756 | 771 |
| 757 // WSAEventSelect sets the socket to non-blocking mode as a side effect. | 772 // WSAEventSelect sets the socket to non-blocking mode as a side effect. |
| 758 // Our connect() and recv() calls require that the socket be non-blocking. | 773 // Our connect() and recv() calls require that the socket be non-blocking. |
| 759 WSAEventSelect(socket_, core_->read_overlapped_.hEvent, FD_CONNECT); | 774 WSAEventSelect(socket_, core_->read_overlapped_.hEvent, FD_CONNECT); |
| 760 | 775 |
| 761 SockaddrStorage storage; | 776 SockaddrStorage storage; |
| 762 if (!peer_address_->ToSockAddr(storage.addr, &storage.addr_len)) | 777 if (!peer_address_->ToSockAddr(storage.addr, &storage.addr_len)) |
| 763 return ERR_ADDRESS_INVALID; | 778 return ERR_ADDRESS_INVALID; |
| 764 | 779 |
| 765 int result; | 780 int result; |
| 781 int os_error; | |
| 766 { | 782 { |
| 767 // TODO(ricea): Remove ScopedTracker below once crbug.com/436634 is fixed. | 783 // TODO(ricea): Remove ScopedTracker below once crbug.com/436634 is fixed. |
| 768 tracked_objects::ScopedTracker tracking_profile( | 784 tracked_objects::ScopedTracker tracking_profile( |
| 769 FROM_HERE_WITH_EXPLICIT_FUNCTION("436634 connect()")); | 785 FROM_HERE_WITH_EXPLICIT_FUNCTION("436634 connect()")); |
| 770 result = connect(socket_, storage.addr, storage.addr_len); | 786 result = connect(socket_, storage.addr, storage.addr_len); |
| 787 os_error = WSAGetLastError(); | |
| 771 } | 788 } |
| 772 | 789 |
| 773 if (!result) { | 790 if (!result) { |
| 774 // Connected without waiting! | 791 // Connected without waiting! |
| 775 // | 792 // |
| 776 // The MSDN page for connect says: | 793 // The MSDN page for connect says: |
| 777 // With a nonblocking socket, the connection attempt cannot be completed | 794 // With a nonblocking socket, the connection attempt cannot be completed |
| 778 // immediately. In this case, connect will return SOCKET_ERROR, and | 795 // immediately. In this case, connect will return SOCKET_ERROR, and |
| 779 // WSAGetLastError will return WSAEWOULDBLOCK. | 796 // WSAGetLastError will return WSAEWOULDBLOCK. |
| 780 // which implies that for a nonblocking socket, connect never returns 0. | 797 // which implies that for a nonblocking socket, connect never returns 0. |
| 781 // It's not documented whether the event object will be signaled or not | 798 // It's not documented whether the event object will be signaled or not |
| 782 // if connect does return 0. So the code below is essentially dead code | 799 // if connect does return 0. So the code below is essentially dead code |
| 783 // and we don't know if it's correct. | 800 // and we don't know if it's correct. |
| 784 NOTREACHED(); | 801 NOTREACHED(); |
| 785 | 802 |
| 786 if (ResetEventIfSignaled(core_->read_overlapped_.hEvent)) | 803 if (ResetEventIfSignaled(core_->read_overlapped_.hEvent)) |
| 787 return OK; | 804 return OK; |
| 788 } else { | 805 } else { |
| 789 int os_error = WSAGetLastError(); | |
| 790 if (os_error != WSAEWOULDBLOCK) { | 806 if (os_error != WSAEWOULDBLOCK) { |
| 791 LOG(ERROR) << "connect failed: " << os_error; | 807 LOG(ERROR) << "connect failed: " << os_error; |
| 792 connect_os_error_ = os_error; | 808 connect_os_error_ = os_error; |
| 793 int rv = MapConnectError(os_error); | 809 int rv = MapConnectError(os_error); |
| 794 CHECK_NE(ERR_IO_PENDING, rv); | 810 CHECK_NE(ERR_IO_PENDING, rv); |
| 795 return rv; | 811 return rv; |
| 796 } | 812 } |
| 797 } | 813 } |
| 798 | 814 |
| 799 // TODO(ricea): Remove ScopedTracker below once crbug.com/436634 is fixed. | 815 // TODO(ricea): Remove ScopedTracker below once crbug.com/436634 is fixed. |
| (...skipping 27 matching lines...) Expand all Loading... | |
| 827 void TCPSocketWin::LogConnectEnd(int net_error) { | 843 void TCPSocketWin::LogConnectEnd(int net_error) { |
| 828 if (net_error != OK) { | 844 if (net_error != OK) { |
| 829 net_log_.EndEventWithNetErrorCode(NetLogEventType::TCP_CONNECT, net_error); | 845 net_log_.EndEventWithNetErrorCode(NetLogEventType::TCP_CONNECT, net_error); |
| 830 return; | 846 return; |
| 831 } | 847 } |
| 832 | 848 |
| 833 struct sockaddr_storage source_address; | 849 struct sockaddr_storage source_address; |
| 834 socklen_t addrlen = sizeof(source_address); | 850 socklen_t addrlen = sizeof(source_address); |
| 835 int rv = getsockname( | 851 int rv = getsockname( |
| 836 socket_, reinterpret_cast<struct sockaddr*>(&source_address), &addrlen); | 852 socket_, reinterpret_cast<struct sockaddr*>(&source_address), &addrlen); |
| 853 int os_error = WSAGetLastError(); | |
| 837 if (rv != 0) { | 854 if (rv != 0) { |
| 838 LOG(ERROR) << "getsockname() [rv: " << rv | 855 LOG(ERROR) << "getsockname() [rv: " << rv << "] error: " << os_error; |
| 839 << "] error: " << WSAGetLastError(); | |
| 840 NOTREACHED(); | 856 NOTREACHED(); |
| 841 net_log_.EndEventWithNetErrorCode(NetLogEventType::TCP_CONNECT, rv); | 857 net_log_.EndEventWithNetErrorCode(NetLogEventType::TCP_CONNECT, rv); |
| 842 return; | 858 return; |
| 843 } | 859 } |
| 844 | 860 |
| 845 net_log_.EndEvent( | 861 net_log_.EndEvent( |
| 846 NetLogEventType::TCP_CONNECT, | 862 NetLogEventType::TCP_CONNECT, |
| 847 CreateNetLogSourceAddressCallback( | 863 CreateNetLogSourceAddressCallback( |
| 848 reinterpret_cast<const struct sockaddr*>(&source_address), | 864 reinterpret_cast<const struct sockaddr*>(&source_address), |
| 849 sizeof(source_address))); | 865 sizeof(source_address))); |
| 850 } | 866 } |
| 851 | 867 |
| 852 int TCPSocketWin::DoRead(IOBuffer* buf, int buf_len, | 868 int TCPSocketWin::DoRead(IOBuffer* buf, int buf_len, |
| 853 const CompletionCallback& callback) { | 869 const CompletionCallback& callback) { |
| 854 if (!core_->non_blocking_reads_initialized_) { | 870 if (!core_->non_blocking_reads_initialized_) { |
| 855 WSAEventSelect(socket_, core_->read_overlapped_.hEvent, | 871 WSAEventSelect(socket_, core_->read_overlapped_.hEvent, |
| 856 FD_READ | FD_CLOSE); | 872 FD_READ | FD_CLOSE); |
| 857 core_->non_blocking_reads_initialized_ = true; | 873 core_->non_blocking_reads_initialized_ = true; |
| 858 } | 874 } |
| 859 int rv = recv(socket_, buf->data(), buf_len, 0); | 875 int rv = recv(socket_, buf->data(), buf_len, 0); |
| 876 int os_error = WSAGetLastError(); | |
| 860 if (rv == SOCKET_ERROR) { | 877 if (rv == SOCKET_ERROR) { |
| 861 int os_error = WSAGetLastError(); | |
| 862 if (os_error != WSAEWOULDBLOCK) { | 878 if (os_error != WSAEWOULDBLOCK) { |
| 863 int net_error = MapSystemError(os_error); | 879 int net_error = MapSystemError(os_error); |
| 864 net_log_.AddEvent(NetLogEventType::SOCKET_READ_ERROR, | 880 net_log_.AddEvent(NetLogEventType::SOCKET_READ_ERROR, |
| 865 CreateNetLogSocketErrorCallback(net_error, os_error)); | 881 CreateNetLogSocketErrorCallback(net_error, os_error)); |
| 866 return net_error; | 882 return net_error; |
| 867 } | 883 } |
| 868 } else { | 884 } else { |
| 869 net_log_.AddByteTransferEvent(NetLogEventType::SOCKET_BYTES_RECEIVED, rv, | 885 net_log_.AddByteTransferEvent(NetLogEventType::SOCKET_BYTES_RECEIVED, rv, |
| 870 buf->data()); | 886 buf->data()); |
| 871 NetworkActivityMonitor::GetInstance()->IncrementBytesReceived(rv); | 887 NetworkActivityMonitor::GetInstance()->IncrementBytesReceived(rv); |
| 872 return rv; | 888 return rv; |
| 873 } | 889 } |
| 874 | 890 |
| 875 waiting_read_ = true; | 891 waiting_read_ = true; |
| 876 read_callback_ = callback; | 892 read_callback_ = callback; |
| 877 core_->read_iobuffer_ = buf; | 893 core_->read_iobuffer_ = buf; |
| 878 core_->read_buffer_length_ = buf_len; | 894 core_->read_buffer_length_ = buf_len; |
| 879 core_->WatchForRead(); | 895 core_->WatchForRead(); |
| 880 return ERR_IO_PENDING; | 896 return ERR_IO_PENDING; |
| 881 } | 897 } |
| 882 | 898 |
| 883 void TCPSocketWin::DidCompleteConnect() { | 899 void TCPSocketWin::DidCompleteConnect() { |
| 884 DCHECK(waiting_connect_); | 900 DCHECK(waiting_connect_); |
| 885 DCHECK(!read_callback_.is_null()); | 901 DCHECK(!read_callback_.is_null()); |
| 886 int result; | 902 int result; |
| 887 | 903 |
| 888 WSANETWORKEVENTS events; | 904 WSANETWORKEVENTS events; |
| 889 int rv; | 905 int rv; |
| 906 int os_error = 0; | |
| 890 { | 907 { |
| 891 // TODO(pkasting): Remove ScopedTracker below once crbug.com/462784 is | 908 // TODO(pkasting): Remove ScopedTracker below once crbug.com/462784 is |
| 892 // fixed. | 909 // fixed. |
| 893 tracked_objects::ScopedTracker tracking_profile1( | 910 tracked_objects::ScopedTracker tracking_profile1( |
| 894 FROM_HERE_WITH_EXPLICIT_FUNCTION( | 911 FROM_HERE_WITH_EXPLICIT_FUNCTION( |
| 895 "462784 TCPSocketWin::DidCompleteConnect -> WSAEnumNetworkEvents")); | 912 "462784 TCPSocketWin::DidCompleteConnect -> WSAEnumNetworkEvents")); |
| 896 rv = WSAEnumNetworkEvents(socket_, core_->read_overlapped_.hEvent, &events); | 913 rv = WSAEnumNetworkEvents(socket_, core_->read_overlapped_.hEvent, &events); |
| 914 os_error = WSAGetLastError(); | |
| 897 } | 915 } |
| 898 int os_error = 0; | |
| 899 if (rv == SOCKET_ERROR) { | 916 if (rv == SOCKET_ERROR) { |
| 900 NOTREACHED(); | 917 NOTREACHED(); |
| 901 os_error = WSAGetLastError(); | |
| 902 result = MapSystemError(os_error); | 918 result = MapSystemError(os_error); |
| 903 } else if (events.lNetworkEvents & FD_CONNECT) { | 919 } else if (events.lNetworkEvents & FD_CONNECT) { |
| 904 os_error = events.iErrorCode[FD_CONNECT_BIT]; | 920 os_error = events.iErrorCode[FD_CONNECT_BIT]; |
| 905 result = MapConnectError(os_error); | 921 result = MapConnectError(os_error); |
| 906 } else { | 922 } else { |
| 907 NOTREACHED(); | 923 NOTREACHED(); |
| 908 result = ERR_UNEXPECTED; | 924 result = ERR_UNEXPECTED; |
| 909 } | 925 } |
| 910 | 926 |
| 911 connect_os_error_ = os_error; | 927 connect_os_error_ = os_error; |
| 912 DoConnectComplete(result); | 928 DoConnectComplete(result); |
| 913 waiting_connect_ = false; | 929 waiting_connect_ = false; |
| 914 | 930 |
| 915 // TODO(pkasting): Remove ScopedTracker below once crbug.com/462784 is fixed. | 931 // TODO(pkasting): Remove ScopedTracker below once crbug.com/462784 is fixed. |
| 916 tracked_objects::ScopedTracker tracking_profile4( | 932 tracked_objects::ScopedTracker tracking_profile4( |
| 917 FROM_HERE_WITH_EXPLICIT_FUNCTION( | 933 FROM_HERE_WITH_EXPLICIT_FUNCTION( |
| 918 "462784 TCPSocketWin::DidCompleteConnect -> read_callback_")); | 934 "462784 TCPSocketWin::DidCompleteConnect -> read_callback_")); |
| 919 DCHECK_NE(result, ERR_IO_PENDING); | 935 DCHECK_NE(result, ERR_IO_PENDING); |
| 920 base::ResetAndReturn(&read_callback_).Run(result); | 936 base::ResetAndReturn(&read_callback_).Run(result); |
| 921 } | 937 } |
| 922 | 938 |
| 923 void TCPSocketWin::DidCompleteWrite() { | 939 void TCPSocketWin::DidCompleteWrite() { |
| 924 DCHECK(waiting_write_); | 940 DCHECK(waiting_write_); |
| 925 DCHECK(!write_callback_.is_null()); | 941 DCHECK(!write_callback_.is_null()); |
| 926 | 942 |
| 927 DWORD num_bytes, flags; | 943 DWORD num_bytes, flags; |
| 928 BOOL ok = WSAGetOverlappedResult(socket_, &core_->write_overlapped_, | 944 BOOL ok = WSAGetOverlappedResult(socket_, &core_->write_overlapped_, |
| 929 &num_bytes, FALSE, &flags); | 945 &num_bytes, FALSE, &flags); |
| 930 WSAResetEvent(core_->write_overlapped_.hEvent); | 946 WSAResetEvent(core_->write_overlapped_.hEvent); |
| 947 int os_error = WSAGetLastError(); | |
|
eroman
2016/11/29 19:51:00
Based on the conditional where this is used, I thi
Sigurður Ásgeirsson
2016/11/29 20:27:55
Done, though this probably does change semantics i
| |
| 931 waiting_write_ = false; | 948 waiting_write_ = false; |
| 932 int rv; | 949 int rv; |
| 933 if (!ok) { | 950 if (!ok) { |
| 934 int os_error = WSAGetLastError(); | |
| 935 rv = MapSystemError(os_error); | 951 rv = MapSystemError(os_error); |
| 936 net_log_.AddEvent(NetLogEventType::SOCKET_WRITE_ERROR, | 952 net_log_.AddEvent(NetLogEventType::SOCKET_WRITE_ERROR, |
| 937 CreateNetLogSocketErrorCallback(rv, os_error)); | 953 CreateNetLogSocketErrorCallback(rv, os_error)); |
| 938 } else { | 954 } else { |
| 939 rv = static_cast<int>(num_bytes); | 955 rv = static_cast<int>(num_bytes); |
| 940 if (rv > core_->write_buffer_length_ || rv < 0) { | 956 if (rv > core_->write_buffer_length_ || rv < 0) { |
| 941 // It seems that some winsock interceptors report that more was written | 957 // It seems that some winsock interceptors report that more was written |
| 942 // than was available. Treat this as an error. http://crbug.com/27870 | 958 // than was available. Treat this as an error. http://crbug.com/27870 |
| 943 LOG(ERROR) << "Detected broken LSP: Asked to write " | 959 LOG(ERROR) << "Detected broken LSP: Asked to write " |
| 944 << core_->write_buffer_length_ << " bytes, but " << rv | 960 << core_->write_buffer_length_ << " bytes, but " << rv |
| (...skipping 13 matching lines...) Expand all Loading... | |
| 958 } | 974 } |
| 959 | 975 |
| 960 void TCPSocketWin::DidSignalRead() { | 976 void TCPSocketWin::DidSignalRead() { |
| 961 DCHECK(waiting_read_); | 977 DCHECK(waiting_read_); |
| 962 DCHECK(!read_callback_.is_null()); | 978 DCHECK(!read_callback_.is_null()); |
| 963 | 979 |
| 964 int os_error = 0; | 980 int os_error = 0; |
| 965 WSANETWORKEVENTS network_events; | 981 WSANETWORKEVENTS network_events; |
| 966 int rv = WSAEnumNetworkEvents(socket_, core_->read_overlapped_.hEvent, | 982 int rv = WSAEnumNetworkEvents(socket_, core_->read_overlapped_.hEvent, |
| 967 &network_events); | 983 &network_events); |
| 984 os_error = WSAGetLastError(); | |
| 985 | |
| 968 if (rv == SOCKET_ERROR) { | 986 if (rv == SOCKET_ERROR) { |
| 969 os_error = WSAGetLastError(); | |
| 970 rv = MapSystemError(os_error); | 987 rv = MapSystemError(os_error); |
| 971 } else if (network_events.lNetworkEvents) { | 988 } else if (network_events.lNetworkEvents) { |
| 972 // TODO(pkasting): Remove ScopedTracker below once crbug.com/462778 is | 989 // TODO(pkasting): Remove ScopedTracker below once crbug.com/462778 is |
| 973 // fixed. | 990 // fixed. |
| 974 tracked_objects::ScopedTracker tracking_profile2( | 991 tracked_objects::ScopedTracker tracking_profile2( |
| 975 FROM_HERE_WITH_EXPLICIT_FUNCTION( | 992 FROM_HERE_WITH_EXPLICIT_FUNCTION( |
| 976 "462778 TCPSocketWin::DidSignalRead -> DoRead")); | 993 "462778 TCPSocketWin::DidSignalRead -> DoRead")); |
| 977 DCHECK_EQ(network_events.lNetworkEvents & ~(FD_READ | FD_CLOSE), 0); | 994 DCHECK_EQ(network_events.lNetworkEvents & ~(FD_READ | FD_CLOSE), 0); |
| 978 // If network_events.lNetworkEvents is FD_CLOSE and | 995 // If network_events.lNetworkEvents is FD_CLOSE and |
| 979 // network_events.iErrorCode[FD_CLOSE_BIT] is 0, it is a graceful | 996 // network_events.iErrorCode[FD_CLOSE_BIT] is 0, it is a graceful |
| (...skipping 29 matching lines...) Expand all Loading... | |
| 1009 } | 1026 } |
| 1010 | 1027 |
| 1011 bool TCPSocketWin::GetEstimatedRoundTripTime(base::TimeDelta* out_rtt) const { | 1028 bool TCPSocketWin::GetEstimatedRoundTripTime(base::TimeDelta* out_rtt) const { |
| 1012 DCHECK(out_rtt); | 1029 DCHECK(out_rtt); |
| 1013 // TODO(bmcquade): Consider implementing using | 1030 // TODO(bmcquade): Consider implementing using |
| 1014 // GetPerTcpConnectionEStats/GetPerTcp6ConnectionEStats. | 1031 // GetPerTcpConnectionEStats/GetPerTcp6ConnectionEStats. |
| 1015 return false; | 1032 return false; |
| 1016 } | 1033 } |
| 1017 | 1034 |
| 1018 } // namespace net | 1035 } // namespace net |
| OLD | NEW |