| 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 "tools/android/forwarder2/socket.h" | 5 #include "tools/android/forwarder2/socket.h" |
| 6 | 6 |
| 7 #include <arpa/inet.h> | 7 #include <arpa/inet.h> |
| 8 #include <fcntl.h> | 8 #include <fcntl.h> |
| 9 #include <netdb.h> | 9 #include <netdb.h> |
| 10 #include <netinet/in.h> | 10 #include <netinet/in.h> |
| 11 #include <stdio.h> | 11 #include <stdio.h> |
| 12 #include <string.h> | 12 #include <string.h> |
| 13 #include <sys/socket.h> | 13 #include <sys/socket.h> |
| 14 #include <sys/types.h> | 14 #include <sys/types.h> |
| 15 #include <unistd.h> | 15 #include <unistd.h> |
| 16 | 16 |
| 17 #include <algorithm> |
| 18 |
| 17 #include "base/logging.h" | 19 #include "base/logging.h" |
| 18 #include "base/posix/eintr_wrapper.h" | 20 #include "base/posix/eintr_wrapper.h" |
| 19 #include "base/safe_strerror_posix.h" | 21 #include "base/safe_strerror_posix.h" |
| 20 #include "tools/android/common/net.h" | 22 #include "tools/android/common/net.h" |
| 21 #include "tools/android/forwarder2/common.h" | 23 #include "tools/android/forwarder2/common.h" |
| 22 | 24 |
| 23 namespace { | 25 namespace { |
| 24 const int kNoTimeout = -1; | 26 const int kNoTimeout = -1; |
| 25 const int kConnectTimeOut = 10; // Seconds. | 27 const int kConnectTimeOut = 10; // Seconds. |
| 26 | 28 |
| (...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 66 } | 68 } |
| 67 return true; | 69 return true; |
| 68 } | 70 } |
| 69 | 71 |
| 70 Socket::Socket() | 72 Socket::Socket() |
| 71 : socket_(-1), | 73 : socket_(-1), |
| 72 port_(0), | 74 port_(0), |
| 73 socket_error_(false), | 75 socket_error_(false), |
| 74 family_(AF_INET), | 76 family_(AF_INET), |
| 75 addr_ptr_(reinterpret_cast<sockaddr*>(&addr_.addr4)), | 77 addr_ptr_(reinterpret_cast<sockaddr*>(&addr_.addr4)), |
| 76 addr_len_(sizeof(sockaddr)), | 78 addr_len_(sizeof(sockaddr)) { |
| 77 exit_notifier_fd_(-1), | |
| 78 exited_(false) { | |
| 79 memset(&addr_, 0, sizeof(addr_)); | 79 memset(&addr_, 0, sizeof(addr_)); |
| 80 } | 80 } |
| 81 | 81 |
| 82 Socket::~Socket() { | 82 Socket::~Socket() { |
| 83 Close(); | 83 Close(); |
| 84 } | 84 } |
| 85 | 85 |
| 86 void Socket::Shutdown() { | 86 void Socket::Shutdown() { |
| 87 if (!IsClosed()) { | 87 if (!IsClosed()) { |
| 88 PRESERVE_ERRNO_HANDLE_EINTR(shutdown(socket_, SHUT_RDWR)); | 88 PRESERVE_ERRNO_HANDLE_EINTR(shutdown(socket_, SHUT_RDWR)); |
| (...skipping 234 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 323 int ret = HANDLE_EINTR(send(socket_, buffer, count, MSG_NOSIGNAL)); | 323 int ret = HANDLE_EINTR(send(socket_, buffer, count, MSG_NOSIGNAL)); |
| 324 if (ret < 0) | 324 if (ret < 0) |
| 325 SetSocketError(); | 325 SetSocketError(); |
| 326 return ret; | 326 return ret; |
| 327 } | 327 } |
| 328 | 328 |
| 329 int Socket::WriteString(const std::string& buffer) { | 329 int Socket::WriteString(const std::string& buffer) { |
| 330 return WriteNumBytes(buffer.c_str(), buffer.size()); | 330 return WriteNumBytes(buffer.c_str(), buffer.size()); |
| 331 } | 331 } |
| 332 | 332 |
| 333 void Socket::AddEventFd(int event_fd) { |
| 334 event_fds_.push_back(event_fd); |
| 335 std::sort(event_fds_.begin(), event_fds_.end()); |
| 336 } |
| 337 |
| 338 bool Socket::DidReceiveEventOnFd(int fd) const { |
| 339 return std::find( |
| 340 fired_events_.begin(), fired_events_.end(), fd) != fired_events_.end(); |
| 341 } |
| 342 |
| 333 int Socket::WriteNumBytes(const void* buffer, size_t num_bytes) { | 343 int Socket::WriteNumBytes(const void* buffer, size_t num_bytes) { |
| 334 int bytes_written = 0; | 344 int bytes_written = 0; |
| 335 int ret = 1; | 345 int ret = 1; |
| 336 while (bytes_written < num_bytes && ret > 0) { | 346 while (bytes_written < num_bytes && ret > 0) { |
| 337 ret = Write(static_cast<const char*>(buffer) + bytes_written, | 347 ret = Write(static_cast<const char*>(buffer) + bytes_written, |
| 338 num_bytes - bytes_written); | 348 num_bytes - bytes_written); |
| 339 if (ret >= 0) | 349 if (ret >= 0) |
| 340 bytes_written += ret; | 350 bytes_written += ret; |
| 341 } | 351 } |
| 342 return bytes_written; | 352 return bytes_written; |
| 343 } | 353 } |
| 344 | 354 |
| 345 bool Socket::WaitForEvent(EventType type, int timeout_secs) { | 355 bool Socket::WaitForEvent(EventType type, int timeout_secs) { |
| 346 if (exit_notifier_fd_ == -1 || socket_ == -1) | 356 if (event_fds_.empty() || socket_ == -1) |
| 347 return true; | 357 return true; |
| 348 const int nfds = std::max(socket_, exit_notifier_fd_) + 1; | 358 const int nfds = std::max(socket_, event_fds_.back()) + 1; |
| 349 fd_set read_fds; | 359 fd_set read_fds; |
| 350 fd_set write_fds; | 360 fd_set write_fds; |
| 351 FD_ZERO(&read_fds); | 361 FD_ZERO(&read_fds); |
| 352 FD_ZERO(&write_fds); | 362 FD_ZERO(&write_fds); |
| 353 if (type == READ) | 363 if (type == READ) |
| 354 FD_SET(socket_, &read_fds); | 364 FD_SET(socket_, &read_fds); |
| 355 else | 365 else |
| 356 FD_SET(socket_, &write_fds); | 366 FD_SET(socket_, &write_fds); |
| 357 FD_SET(exit_notifier_fd_, &read_fds); | 367 for (std::vector<int>::const_iterator it = event_fds_.begin(); |
| 358 | 368 it != event_fds_.end(); ++it) { |
| 369 FD_SET(*it, &read_fds); |
| 370 } |
| 359 timeval tv = {}; | 371 timeval tv = {}; |
| 360 timeval* tv_ptr = NULL; | 372 timeval* tv_ptr = NULL; |
| 361 if (timeout_secs > 0) { | 373 if (timeout_secs > 0) { |
| 362 tv.tv_sec = timeout_secs; | 374 tv.tv_sec = timeout_secs; |
| 363 tv.tv_usec = 0; | 375 tv.tv_usec = 0; |
| 364 tv_ptr = &tv; | 376 tv_ptr = &tv; |
| 365 } | 377 } |
| 366 if (HANDLE_EINTR(select(nfds, &read_fds, &write_fds, NULL, tv_ptr)) <= 0) | 378 if (HANDLE_EINTR(select(nfds, &read_fds, &write_fds, NULL, tv_ptr)) <= 0) |
| 367 return false; | 379 return false; |
| 368 if (FD_ISSET(exit_notifier_fd_, &read_fds)) { | 380 for (std::vector<int>::const_iterator it = event_fds_.begin(); |
| 369 exited_ = true; | 381 it != event_fds_.end(); ++it) { |
| 370 return false; | 382 if (FD_ISSET(*it, &read_fds)) |
| 383 fired_events_.push_back(*it); |
| 371 } | 384 } |
| 372 return true; | 385 return fired_events_.empty(); |
| 373 } | 386 } |
| 374 | 387 |
| 375 // static | 388 // static |
| 376 int Socket::GetHighestFileDescriptor(const Socket& s1, const Socket& s2) { | 389 int Socket::GetHighestFileDescriptor(const Socket& s1, const Socket& s2) { |
| 377 return std::max(s1.socket_, s2.socket_); | 390 return std::max(s1.socket_, s2.socket_); |
| 378 } | 391 } |
| 379 | 392 |
| 380 // static | 393 // static |
| 381 pid_t Socket::GetUnixDomainSocketProcessOwner(const std::string& path) { | 394 pid_t Socket::GetUnixDomainSocketProcessOwner(const std::string& path) { |
| 382 Socket socket; | 395 Socket socket; |
| 383 if (!socket.ConnectUnix(path)) | 396 if (!socket.ConnectUnix(path)) |
| 384 return -1; | 397 return -1; |
| 385 ucred ucred; | 398 ucred ucred; |
| 386 socklen_t len = sizeof(ucred); | 399 socklen_t len = sizeof(ucred); |
| 387 if (getsockopt(socket.socket_, SOL_SOCKET, SO_PEERCRED, &ucred, &len) == -1) { | 400 if (getsockopt(socket.socket_, SOL_SOCKET, SO_PEERCRED, &ucred, &len) == -1) { |
| 388 CHECK_NE(ENOPROTOOPT, errno); | 401 CHECK_NE(ENOPROTOOPT, errno); |
| 389 return -1; | 402 return -1; |
| 390 } | 403 } |
| 391 return ucred.pid; | 404 return ucred.pid; |
| 392 } | 405 } |
| 393 | 406 |
| 394 } // namespace forwarder2 | 407 } // namespace forwarder2 |
| OLD | NEW |