| 709 | } |
| 710 | |
| 711 | bool SocketCore::isReadable(time_t timeout) |
| 712 | { |
| 713 | #ifdef HAVE_POLL |
| 714 | struct pollfd p; |
| 715 | p.fd = sockfd_; |
| 716 | p.events = POLLIN; |
| 717 | int r; |
| 718 | while ((r = poll(&p, 1, timeout * 1000)) == -1 && errno == EINTR) |
| 719 | ; |
| 720 | int errNum = SOCKET_ERRNO; |
| 721 | if (r > 0) { |
| 722 | return p.revents & (POLLIN | POLLHUP | POLLERR); |
| 723 | } |
| 724 | if (r == 0) { |
| 725 | return false; |
| 726 | } |
| 727 | throw DL_RETRY_EX(fmt(EX_SOCKET_CHECK_READABLE, errorMsg(errNum).c_str())); |
| 728 | #else // !HAVE_POLL |
| 729 | # ifndef __MINGW32__ |
| 730 | CHECK_FD(sockfd_); |
| 731 | # endif // !__MINGW32__ |
| 732 | fd_set fds; |
| 733 | FD_ZERO(&fds); |
| 734 | FD_SET(sockfd_, &fds); |
| 735 | |
| 736 | struct timeval tv; |
| 737 | tv.tv_sec = timeout; |
| 738 | tv.tv_usec = 0; |
| 739 | |
| 740 | int r = select(sockfd_ + 1, &fds, nullptr, nullptr, &tv); |
| 741 | int errNum = SOCKET_ERRNO; |
| 742 | if (r == 1) { |
| 743 | return true; |
| 744 | } |
| 745 | if (r == 0) { |
| 746 | // time out |
| 747 | return false; |
| 748 | } |
| 749 | if (errNum == A2_EINPROGRESS || errNum == A2_EINTR) { |
| 750 | return false; |
| 751 | } |
| 752 | throw DL_RETRY_EX(fmt(EX_SOCKET_CHECK_READABLE, errorMsg(errNum).c_str())); |
| 753 | #endif // !HAVE_POLL |
| 754 | } |
| 755 | |
| 756 | ssize_t SocketCore::writeVector(a2iovec* iov, size_t iovcnt) |
| 757 | { |