コード例 #1
0
ファイル: tcpsocket.cpp プロジェクト: jouven/cxxtools
short TcpSocket::poll(short events) const
{
    struct pollfd fds;
    fds.fd = _impl->fd();
    fds.events = events;

    int timeout = getTimeout().ceil();

    log_debug("poll timeout " << timeout);
    #ifdef __MINGW32__
    int p = WSAPoll(&fds, 1, timeout);
    #else
    int p = ::poll(&fds, 1, timeout);
    #endif

    log_debug("poll returns " << p << " revents " << fds.revents);

    if (p < 0)
    {
      log_error("error in poll; errno=" << errno);
      throw SystemError("poll");
    }
    else if (p == 0)
    {
      log_debug("poll timeout (" << timeout << ')');
      throw IOTimeout();
    }

    return fds.revents;
}
コード例 #2
0
	int SocketImpl::Poll(PollSocket* fdarray, std::size_t nfds, int timeout, SocketError* error)
	{
		NazaraAssert(fdarray && nfds > 0, "Invalid fdarray");

		#if NAZARA_NETWORK_POLL_SUPPORT
		static_assert(sizeof(PollSocket) == sizeof(WSAPOLLFD), "PollSocket size must match WSAPOLLFD size");

		int result = WSAPoll(reinterpret_cast<WSAPOLLFD*>(fdarray), static_cast<ULONG>(nfds), timeout);
		if (result == SOCKET_ERROR)
		{
			int errorCode = WSAGetLastError();
			if (error)
				*error = TranslateWSAErrorToSocketError(errorCode);

			return 0;
		}

		if (error)
			*error = SocketError_NoError;

		return result;
		#else
		NazaraUnused(fdarray);
		NazaraUnused(nfds);
		NazaraUnused(timeout);

		if (error)
			*error = SocketError_NotSupported;

		return 0;
		#endif
	}
コード例 #3
0
ファイル: socket-util.c プロジェクト: AlexanderFroemmgen/ovs
int
check_connection_completion(int fd)
{
    static struct vlog_rate_limit rl = VLOG_RATE_LIMIT_INIT(5, 10);
    struct pollfd pfd;
    int retval;

    pfd.fd = fd;
    pfd.events = POLLOUT;

#ifndef _WIN32
    do {
        retval = poll(&pfd, 1, 0);
    } while (retval < 0 && errno == EINTR);
#else
    retval = WSAPoll(&pfd, 1, 0);
#endif
    if (retval == 1) {
        if (pfd.revents & POLLERR) {
            ssize_t n = send(fd, "", 1, 0);
            if (n < 0) {
                return sock_errno();
            } else {
                VLOG_ERR_RL(&rl, "poll return POLLERR but send succeeded");
                return EPROTO;
            }
        }
        return 0;
    } else if (retval < 0) {
        VLOG_ERR_RL(&rl, "poll: %s", sock_strerror(sock_errno()));
        return errno;
    } else {
        return EAGAIN;
    }
}
コード例 #4
0
bool us_reactor_poll(us_reactor_t *self, int timeout) {
    bool r = false;
    us_reactor_collect_finished(self);
    us_reactor_fill_poll(self);
    if (self->m_num_handlers > 0) {
        int n;
#ifdef WIN32
        n = WSAPoll(self->m_poll_handlers, self->m_num_handlers, timeout);
#else
        n = poll(self->m_poll_handlers, self->m_num_handlers, timeout);
#endif
        if (n < 0 && errno != EINTR) {
            /* error doing poll, stop loop */
            us_reactor_log_debug("error doing poll, errno=%d", errno);
            r = false;
        }
        if (n > 0) {
            /* some handlers to be handled */
            us_reactor_handler_t *item = self->m_handlers;
            int n;
            int num = self->m_num_handlers;
            for (n = 0; n < num; ++n, item = item->m_next) {
                struct pollfd *p = &self->m_poll_handlers[n];
                if (p->fd != item->m_fd) {
                    us_reactor_log_error("item %p fd %d != p->fd", (void *)item, item->m_fd, p->fd);
                    abort();
                }
                if (item->m_wake_on_readable && (p->revents & POLLIN)) {
                    us_reactor_log_debug("item %p fd %d is readable", item, item->m_fd);
                    item->readable(item);
                }
                if (item->m_wake_on_writable && (p->revents & POLLOUT)) {
                    us_reactor_log_debug("item %p fd %d is writable", item, item->m_fd);
                    item->writable(item);
                }
                if ((p->revents & POLLHUP)) {
                    us_reactor_log_debug("poll item %p fd %d got HUP: %d", (void *)item, item->m_fd, p->revents);
                    us_reactor_handler_finish(item);
                }
                if ((p->revents & POLLERR)) {
                    us_reactor_log_debug("poll item %p fd %d got ERR: %d", (void *)item, item->m_fd, p->revents);
                    us_reactor_handler_finish(item);
                }
                if ((p->revents & POLLNVAL)) {
                    us_reactor_log_error("poll item %p fd %d got NVAL: %d", (void *)item, item->m_fd, p->revents);
                    us_reactor_handler_finish(item);
                }
            }
            r = true;
        }
        if (n == 0) {
            /* there are handlers, nothing to do, timeout occurred */
            r = true;
        }
    }
    us_reactor_collect_finished(self);
    return r;
}
コード例 #5
0
ファイル: conn.c プロジェクト: kwolekr/chiisai-bnetd
_inline int PollSockets(LPCONNPOOL cp) {
	int num_fds, i;
	SOCKET fd_highest;
	LPSESS sess;

	#if defined(_USE_KQUEUE)
		num_fds = kevent(cp->smfd, NULL, 0, cp->events, cp->nconns, NULL);
		return num_fds;
		
	#elif defined(_USE_EPOLL)
		num_fds = epoll_wait(cp->smfd, cp->events, cp->nconns, -1);
		return num_fds;
		
	#elif defined(_USE_DEVPOLL)
		num_fds = ioctl(cp->smfd, DP_POLL, &pollstuff);
		return (num_fds >= 0) ? num_fds : -1;

	#elif defined(_USE_POLL)
		num_fds = poll(cp->fds, cp->nconns, -1);
		return num_fds;
		
	#elif defined(_USE_WSAPOLL)
		num_fds = WSAPoll(cp->fdarray, cp->nconns, -1);
		return num_fds;
		
	#elif defined(_USE_WSAEVENTS)
		num_fds = WSAWaitForMultipleEvents(cp->nconns, cp->events, FALSE, WSA_INFINITE, TRUE);
		if (num_fds == WSA_WAIT_FAILED)
			return -1;
		WSAResetEvent(cp->events[num_fds - WSA_WAIT_EVENT_0]);
		return num_fds;

	#elif defined(_USE_SELECT)
		FD_ZERO(&cp->rdfds);
		fd_highest = 0;
		for (i = 0; i != cp->nconns; i++) {
			sess = cp->sessions[i];
			FD_SET(sess->sck, &cp->rdfds);
			if (sess->sck > fd_highest)
				fd_highest = sess->sck;
		}
		//printf("#before select(): nfds %d\n", cp->rdfds.fd_count);
		num_fds = select(fd_highest + 1, &cp->rdfds, NULL, NULL, NULL);
		//printf("#after select(): nfds %d\n", cp->rdfds.fd_count);
		/*if (!num_fds) {
			printf("WARNING: fd_count being manually set!\n");
			cp->rdfds.fd_count = cp->nconns - cp->n_connupdates;
			return 0;
		}*/
		//return num_fds;
		return (num_fds != -1) ? cp->nconns : -1;
	#endif
}
コード例 #6
0
ファイル: poll.c プロジェクト: dtrebbien/apr
static apr_status_t impl_pollset_poll(apr_pollset_t *pollset,
                                      apr_interval_time_t timeout,
                                      apr_int32_t *num,
                                      const apr_pollfd_t **descriptors)
{
    int ret;
    apr_status_t rv = APR_SUCCESS;

    if (timeout > 0) {
        timeout /= 1000;
    }
#ifdef WIN32
    ret = WSAPoll(pollset->p->pollset, pollset->nelts, (int)timeout);
#else
    ret = poll(pollset->p->pollset, pollset->nelts, timeout);
#endif
    (*num) = ret;
    if (ret < 0) {
        return apr_get_netos_error();
    }
    else if (ret == 0) {
        return APR_TIMEUP;
    }
    else {
        apr_uint32_t i, j;

        for (i = 0, j = 0; i < pollset->nelts; i++) {
            if (pollset->p->pollset[i].revents != 0) {
                /* Check if the polled descriptor is our
                 * wakeup pipe. In that case do not put it result set.
                 */
                if ((pollset->flags & APR_POLLSET_WAKEABLE) &&
                    pollset->p->query_set[i].desc_type == APR_POLL_FILE &&
                    pollset->p->query_set[i].desc.f == pollset->wakeup_pipe[0]) {
                    apr_poll_drain_wakeup_pipe(pollset->wakeup_pipe);
                    rv = APR_EINTR;
                }
                else {
                    pollset->p->result_set[j] = pollset->p->query_set[i];
                    pollset->p->result_set[j].rtnevents =
                        get_revent(pollset->p->pollset[i].revents);
                    j++;
                }
            }
        }
        if (((*num) = j) > 0)
            rv = APR_SUCCESS;
    }
    if (descriptors && (*num))
        *descriptors = pollset->p->result_set;
    return rv;
}
コード例 #7
0
ファイル: ovs-benchmark.c プロジェクト: FI-Lab/ovs
static int
do_poll(struct pollfd *fds, int nfds, int timeout)
{
    int retval;
#ifndef _WIN32
    do {
        retval = poll(fds, nfds, timeout);
    } while (retval < 0 && errno == EINTR);
#else
    retval = WSAPoll(fds, nfds, timeout);
#endif
    return retval;
}
コード例 #8
0
ファイル: poll.c プロジェクト: Leon555/Library-src
static apr_status_t impl_pollcb_poll(apr_pollcb_t *pollcb,
                                     apr_interval_time_t timeout,
                                     apr_pollcb_cb_t func,
                                     void *baton)
{
    int ret;
    apr_status_t rv = APR_SUCCESS;
    apr_uint32_t i;

#ifdef WIN32
    /* WSAPoll() requires at least one socket. */
    if (pollcb->nelts == 0) {
        if (timeout > 0) {
            apr_sleep(timeout);
            return APR_TIMEUP;
        }
        return APR_SUCCESS;
    }
    if (timeout > 0) {
        timeout /= 1000;
    }
    ret = WSAPoll(pollcb->pollset.ps, pollcb->nelts, (int)timeout);
#else
    if (timeout > 0) {
        timeout /= 1000;
    }
    ret = poll(pollcb->pollset.ps, pollcb->nelts, timeout);
#endif
    if (ret < 0) {
        return apr_get_netos_error();
    }
    else if (ret == 0) {
        return APR_TIMEUP;
    }
    else {
        for (i = 0; i < pollcb->nelts; i++) {
            if (pollcb->pollset.ps[i].revents != 0) {
                apr_pollfd_t *pollfd = pollcb->copyset[i];
                pollfd->rtnevents = get_revent(pollcb->pollset.ps[i].revents);                    
                rv = func(baton, pollfd);
                if (rv) {
                    return rv;
                }
            }
        }
    }
    return rv;
}
コード例 #9
0
ファイル: poll.c プロジェクト: dtrebbien/apr
static apr_status_t impl_pollcb_poll(apr_pollcb_t *pollcb,
                                     apr_interval_time_t timeout,
                                     apr_pollcb_cb_t func,
                                     void *baton)
{
    int ret;
    apr_status_t rv = APR_SUCCESS;
    apr_uint32_t i;

    if (timeout > 0) {
        timeout /= 1000;
    }
#ifdef WIN32
    ret = WSAPoll(pollcb->pollset.ps, pollcb->nelts, (int)timeout);
#else
    ret = poll(pollcb->pollset.ps, pollcb->nelts, timeout);
#endif
    if (ret < 0) {
        return apr_get_netos_error();
    }
    else if (ret == 0) {
        return APR_TIMEUP;
    }
    else {
        for (i = 0; i < pollcb->nelts; i++) {
            if (pollcb->pollset.ps[i].revents != 0) {
                apr_pollfd_t *pollfd = pollcb->copyset[i];

                if ((pollcb->flags & APR_POLLSET_WAKEABLE) &&
                    pollfd->desc_type == APR_POLL_FILE &&
                    pollfd->desc.f == pollcb->wakeup_pipe[0]) {
                    apr_poll_drain_wakeup_pipe(pollcb->wakeup_pipe);
                    return APR_EINTR;
                }

                pollfd->rtnevents = get_revent(pollcb->pollset.ps[i].revents);                    
                rv = func(baton, pollfd);
                if (rv) {
                    return rv;
                }
            }
        }
    }
    return rv;
}
コード例 #10
0
int rd_kafka_transport_poll(rd_kafka_transport_t *rktrans, int tmout) {
#ifndef _MSC_VER
	int r;

	r = poll(&rktrans->rktrans_pfd, 1, tmout);
	if (r <= 0)
		return r;
	return rktrans->rktrans_pfd.revents;
#else
	int r;

	r = WSAPoll(&rktrans->rktrans_pfd, 1, tmout);
	if (r == 0) {
		/* Workaround for broken WSAPoll() while connecting:
		 * failed connection attempts are not indicated at all by WSAPoll()
		 * so we need to check the socket error when Poll returns 0.
		 * Issue #525 */
		r = ECONNRESET;
		if (unlikely(rktrans->rktrans_rkb->rkb_state ==
			     RD_KAFKA_BROKER_STATE_CONNECT &&
			     (rd_kafka_transport_get_socket_error(rktrans,
								  &r) == -1 ||
			      r != 0))) {
			char errstr[512];
			errno = r;
			rd_snprintf(errstr, sizeof(errstr),
				    "Connect to %s failed: %s",
				    rd_sockaddr2str(rktrans->rktrans_rkb->
						    rkb_addr_last,
						    RD_SOCKADDR2STR_F_PORT |
                                                    RD_SOCKADDR2STR_F_FAMILY),
                                    socket_strerror(r));
			rd_kafka_transport_connect_done(rktrans, errstr);
			return -1;
		} else
			return 0;
	} else if (r == SOCKET_ERROR)
		return -1;
	return rktrans->rktrans_pfd.revents;
#endif
}
コード例 #11
0
ファイル: VPoll.cpp プロジェクト: Jamol/kuma
KMError VPoll::wait(uint32_t wait_ms)
{
#ifdef KUMA_OS_WIN
    int num_revts = WSAPoll(&poll_fds_[0], poll_fds_.size(), wait_ms);
#else
    int num_revts = poll(&poll_fds_[0], (nfds_t)poll_fds_.size(), wait_ms);
#endif
    if (-1 == num_revts) {
        if(EINTR == errno) {
            errno = 0;
        } else {
            KUMA_ERRTRACE("VPoll::wait, err="<<getLastError());
        }
        return KMError::INVALID_STATE;
    }

    // copy poll fds since event handler may unregister fd
    PollFdVector poll_fds = poll_fds_;
    
    int idx = 0;
    int last_idx = int(poll_fds.size() - 1);
    while(num_revts > 0 && idx <= last_idx) {
        if(poll_fds[idx].revents) {
            --num_revts;
            if(poll_fds[idx].fd < poll_items_.size()) {
                auto &item = poll_items_[poll_fds[idx].fd];
                auto revents = get_kuma_events(poll_fds[idx].revents);
                revents &= item.events;
                if (revents && item.cb) {
                    item.cb(revents, nullptr, 0);
                }
            }
        }
        ++idx;
    }
    return KMError::NOERR;
}
コード例 #12
0
static inline int poll(struct pollfd *pfd, unsigned long nfds, int timeout) { return WSAPoll(pfd, nfds, timeout); }
コード例 #13
0
ファイル: pubnub-sync.c プロジェクト: Ashar786/c
void
pubnub_sync_wait(struct pubnub *p, void *ctx_data)
{
	struct pubnub_sync *sync = (struct pubnub_sync *)ctx_data;
	while (!sync->stop) {
		DBGMSG("=polling= for %d (timeout %p)\n", sync->n, sync->timeout_cb);

		long timeout;
		if (sync->timeout_cb) {
			struct timespec now;
			GET_CLOCK_NOW
			timeout = (sync->timeout_at.tv_sec - now.tv_sec) * 1000;
			timeout += (sync->timeout_at.tv_nsec - now.tv_nsec) / 1000000;
			DBGMSG("timeout in %ld ms\n", timeout);
			if (timeout < 0) {
				/* If we missed the timeout moment, just
				 * spin poll() quickly until we are clear
				 * to call the timeout handler. */
				timeout = 0;
			}
		} else {
			timeout = -1;
		}

#ifdef _MSC_VER
		int n = (sync->n ? WSAPoll(sync->fdset, sync->n, timeout) : 0);
#else
		int n = poll(sync->fdset, sync->n, timeout);
#endif

		if (n < 0) {
			/* poll() errors are ignored, it's not clear what
			 * we should do. Most likely, we have just received
			 * a signal and will spin around and restart poll(). */
#ifdef _MSC_VER
			DBGMSG("WSAPoll error: %d\n", WSAGetLastError());
#else
			DBGMSG("poll(): %s\n", strerror(errno));
#endif
			continue;
		}

		if (n == 0) {
			/* Time out, call the handler and reset
			 * timeout. */
			DBGMSG("Timeout, callback and reset\n");
			/* First, we reset sync->timeout_cb, then we
			 * call the timeout handler - likely, that will
			 * cause it to set timeout_cb again, so resetting
			 * timeout_cb only after the call is bad idea. */
			void (*timeout_cb)(struct pubnub *p, void *cb_data) = sync->timeout_cb;
			sync->timeout_cb = NULL;
			if (timeout_cb) {
				timeout_cb(p, sync->timeout_cb_data);
			}
			continue;
		}

		for (int i = 0; i < sync->n; i++) {
			short revents = sync->fdset[i].revents;
			if (!revents)
				continue;
			DBGMSG("event: fd %d ev %d rev %d\n", sync->fdset[i].fd, sync->fdset[i].events, sync->fdset[i].revents);
			int mode = (revents & POLLIN ? 1 : 0) | (revents & POLLOUT ? 2 : 0) | (revents & POLLERR ? 4 : 0);
			sync->cbset[i].cb(p, sync->fdset[i].fd, mode, sync->cbset[i].cb_data);
		}
	}
	sync->stop = false;
}
コード例 #14
0
void socket_watcher_thread(void *arg)
{
    FILETIME prev_time;
    GetSystemTimeAsFileTime(&prev_time);

    for (;;) {
        const DWORD ms = 100;

        EnterCriticalSection(&m_watcher.queue_lock);
        if (m_watcher.queue_head != m_watcher.queue_tail) {
            pubnub_t *pbp = m_watcher.queue_apb[m_watcher.queue_tail++];
            LeaveCriticalSection(&m_watcher.queue_lock);
            if (pbp != NULL) {
                pubnub_mutex_lock(pbp->monitor);
                pbnc_fsm(pbp);
                pubnub_mutex_unlock(pbp->monitor);
            }
            EnterCriticalSection(&m_watcher.queue_lock);
            if (m_watcher.queue_tail == m_watcher.queue_size) {
                m_watcher.queue_tail = 0;
            }
        }
        LeaveCriticalSection(&m_watcher.queue_lock);

        EnterCriticalSection(&m_watcher.mutw);
        if (0 == m_watcher.apoll_size) {
            LeaveCriticalSection(&m_watcher.mutw);
            continue;
        }
        {
            int rslt = WSAPoll(m_watcher.apoll, m_watcher.apoll_size, ms);
            if (SOCKET_ERROR == rslt) {
                /* error? what to do about it? */
                PUBNUB_LOG_WARNING("poll size = %d, error = %d\n", m_watcher.apoll_size, WSAGetLastError());
            }
            else if (rslt > 0) {
                size_t i;
                size_t apoll_size = m_watcher.apoll_size;
                for (i = 0; i < apoll_size; ++i) {
                    if (m_watcher.apoll[i].revents & (POLLIN | POLLOUT)) {
                        pubnub_t *pbp = m_watcher.apb[i];
                        pubnub_mutex_lock(pbp->monitor);
                        pbnc_fsm(pbp);
                        if (apoll_size == m_watcher.apoll_size) {
                            if (m_watcher.apoll[i].events == POLLOUT) {
                                if ((pbp->state == PBS_WAIT_DNS_RCV) ||
                                    (pbp->state >= PBS_RX_HTTP_VER)) {
                                    m_watcher.apoll[i].events = POLLIN;
                                }
                            }
                            else {
                                if ((pbp->state > PBS_WAIT_DNS_RCV) &&
                                    (pbp->state < PBS_RX_HTTP_VER)) {
                                    m_watcher.apoll[i].events = POLLOUT;
                                }
                            }
                        }
                        else {
                            PUBNUB_ASSERT_OPT(apoll_size == m_watcher.apoll_size + 1);
                            apoll_size = m_watcher.apoll_size;
                            --i;
                        }
                        pubnub_mutex_unlock(pbp->monitor);
                    }
                }
            }
        }
        if (PUBNUB_TIMERS_API) {
            FILETIME current_time;
            int elapsed;
            GetSystemTimeAsFileTime(&current_time);
            elapsed = elapsed_ms(prev_time, current_time);
            if (elapsed > 0) {
                pubnub_t *expired = pubnub_timer_list_as_time_goes_by(&m_watcher.timer_head, elapsed);
                while (expired != NULL) {
                    pubnub_t *next = expired->next;

                    pubnub_mutex_lock(expired->monitor);
                    pbnc_stop(expired, PNR_TIMEOUT);
                    pubnub_mutex_unlock(expired->monitor);

                    expired->next = NULL;
                    expired->previous = NULL;
                    expired = next;
                }
                prev_time = current_time;
            }
        }

        LeaveCriticalSection(&m_watcher.mutw);
    }
}
コード例 #15
0
ファイル: WinFunc.cpp プロジェクト: noelq/EpiHistory
int				_poll(T_POLLFD *fds, int nfds, int timeout)
{
	return (WSAPoll(fds, nfds, timeout));
}
コード例 #16
0
    void Socket::_handleSendError(int ret, const char* context) {
#ifdef MONGO_SSL
        if (_ssl) {
            LOG(_logLevel) << "SSL Error ret: " << ret
                           << " err: " << _sslManager->SSL_get_error(_ssl , ret)
                           << " "
                           << _sslManager->ERR_error_string(_sslManager->ERR_get_error(), NULL)
                           << endl;
            throw SocketException(SocketException::SEND_ERROR , remoteString());
        }
#endif

#if defined(_WIN32)
        const int mongo_errno = WSAGetLastError();
        if ( mongo_errno == WSAETIMEDOUT && _timeout != 0 ) {
#else
        const int mongo_errno = errno;
        if ( ( mongo_errno == EAGAIN || mongo_errno == EWOULDBLOCK ) && _timeout != 0 ) {
#endif
            LOG(_logLevel) << "Socket " << context << 
                " send() timed out " << remoteString() << endl;
            throw SocketException(SocketException::SEND_TIMEOUT , remoteString());
        }
        else {
            LOG(_logLevel) << "Socket " << context << " send() "
                           << errnoWithDescription(mongo_errno) << ' ' << remoteString() << endl;
            throw SocketException(SocketException::SEND_ERROR , remoteString());            
        }
    }

    void Socket::_handleRecvError(int ret, int len, int* retries) {
        if (ret == 0) {
            LOG(3) << "Socket recv() conn closed? " << remoteString() << endl;
            throw SocketException(SocketException::CLOSED , remoteString());
        }
     
        // ret < 0
#ifdef MONGO_SSL
        if (_ssl) {
            LOG(_logLevel) << "SSL Error ret: " << ret
                           << " err: " << _sslManager->SSL_get_error(_ssl , ret)
                           << " "
                           << _sslManager->ERR_error_string(_sslManager->ERR_get_error(), NULL)
                           << endl;
            throw SocketException(SocketException::RECV_ERROR, remoteString());
        }
#endif

#if defined(_WIN32)
        int e = WSAGetLastError();
#else
        int e = errno;
# if defined(EINTR)
        if (e == EINTR) {
            LOG(_logLevel) << "EINTR retry " << ++*retries << endl;
            return;
        }
# endif
#endif

#if defined(_WIN32)
        // Windows
        if ((e == EAGAIN || e == WSAETIMEDOUT) && _timeout > 0) { 
#else
        if (e == EAGAIN && _timeout > 0) { 
#endif
            // this is a timeout
            LOG(_logLevel) << "Socket recv() timeout  " << remoteString() <<endl;
            throw SocketException(SocketException::RECV_TIMEOUT, remoteString());
        }

        LOG(_logLevel) << "Socket recv() " << 
            errnoWithDescription(e) << " " << remoteString() <<endl;
        throw SocketException(SocketException::RECV_ERROR , remoteString());
    }

    void Socket::setTimeout( double secs ) {
        setSockTimeouts( _fd, secs );
    }

    // TODO: allow modification?
    //
    // <positive value> : secs to wait between stillConnected checks
    // 0 : always check
    // -1 : never check
    const int Socket::errorPollIntervalSecs( 5 );

#if defined(NTDDI_VERSION) && ( !defined(NTDDI_VISTA) || ( NTDDI_VERSION < NTDDI_VISTA ) )
    // Windows XP

    // pre-Vista windows doesn't have WSAPoll, so don't test connections
    bool Socket::isStillConnected() {
        return true;
    }

#else // Not Windows XP

    // Patch to allow better tolerance of flaky network connections that get broken
    // while we aren't looking.
    // TODO: Remove when better async changes come.
    //
    // isStillConnected() polls the socket at max every Socket::errorPollIntervalSecs to determine
    // if any disconnection-type events have happened on the socket.
    bool Socket::isStillConnected() {

        if ( errorPollIntervalSecs < 0 ) return true;

        time_t now = time( 0 );
        time_t idleTimeSecs = now - _lastValidityCheckAtSecs;

        // Only check once every 5 secs
        if ( idleTimeSecs < errorPollIntervalSecs ) return true;
        // Reset our timer, we're checking the connection
        _lastValidityCheckAtSecs = now;

        // It's been long enough, poll to see if our socket is still connected

        pollfd pollInfo;
        pollInfo.fd = _fd;
        // We only care about reading the EOF message on clean close (and errors)
        pollInfo.events = POLLIN;

        // Poll( info[], size, timeout ) - timeout == 0 => nonblocking
#if defined(_WIN32)
        int nEvents = WSAPoll( &pollInfo, 1, 0 );
#else
        int nEvents = ::poll( &pollInfo, 1, 0 );
#endif

        LOG( 2 ) << "polling for status of connection to " << remoteString()
                 << ", " << ( nEvents == 0 ? "no events" :
                              nEvents == -1 ? "error detected" :
                                               "event detected" ) << endl;

        if ( nEvents == 0 ) {
            // No events incoming, return still connected AFAWK
            return true;
        }
        else if ( nEvents < 0 ) {
            // Poll itself failed, this is weird, warn and log errno
            warning() << "Socket poll() failed during connectivity check"
                      << " (idle " << idleTimeSecs << " secs,"
                      << " remote host " << remoteString() << ")"
                      << causedBy(errnoWithDescription()) << endl;

            // Return true since it's not clear that we're disconnected.
            return true;
        }

        dassert( nEvents == 1 );
        dassert( pollInfo.revents > 0 );

        // Return false at this point, some event happened on the socket, but log what the
        // actual event was.

        if ( pollInfo.revents & POLLIN ) {

            // There shouldn't really be any data to recv here, so make sure this
            // is a clean hangup.

            // Used concurrently, but we never actually read this data
            static char testBuf[1];

            int recvd = ::recv( _fd, testBuf, 1, portRecvFlags );

            if ( recvd < 0 ) {
                // An error occurred during recv, warn and log errno
                warning() << "Socket recv() failed during connectivity check"
                          << " (idle " << idleTimeSecs << " secs,"
                          << " remote host " << remoteString() << ")"
                          << causedBy(errnoWithDescription()) << endl;
            }
            else if ( recvd > 0 ) {
                // We got nonzero data from this socket, very weird?
                // Log and warn at runtime, log and abort at devtime
                // TODO: Dump the data to the log somehow?
                error() << "Socket found pending data during connectivity check"
                        << " (idle " << idleTimeSecs << " secs,"
                        << " remote host " << remoteString() << ")" << endl;
                dassert( false );
            }
            else {
                // recvd == 0, socket closed remotely, just return false
                LOG( 0 ) << "Socket closed remotely, no longer connected"
                         << " (idle " << idleTimeSecs << " secs,"
                         << " remote host " << remoteString() << ")" << endl;
            }
        }
        else if ( pollInfo.revents & POLLHUP ) {
            // A hangup has occurred on this socket
            LOG( 0 ) << "Socket hangup detected, no longer connected" << " (idle "
                         << idleTimeSecs << " secs," << " remote host " << remoteString() << ")"
                         << endl;
        }
        else if ( pollInfo.revents & POLLERR ) {
            // An error has occurred on this socket
            LOG( 0 ) << "Socket error detected, no longer connected" << " (idle "
                         << idleTimeSecs << " secs," << " remote host " << remoteString() << ")"
                         << endl;
        }
        else if ( pollInfo.revents & POLLNVAL ) {
            // Socket descriptor itself is weird
            // Log and warn at runtime, log and abort at devtime
            error() << "Socket descriptor detected as invalid"
                    << " (idle " << idleTimeSecs << " secs,"
                    << " remote host " << remoteString() << ")" << endl;
            dassert( false );
        }
        else {
            // Don't know what poll is saying here
            // Log and warn at runtime, log and abort at devtime
            error() << "Socket had unknown event (" << static_cast<int>(pollInfo.revents) << ")"
                    << " (idle " << idleTimeSecs << " secs,"
                    << " remote host " << remoteString() << ")" << endl;
            dassert( false );
        }

        return false;
    }

#endif // End Not Windows XP

#if defined(_WIN32)
    struct WinsockInit {
        WinsockInit() {
            WSADATA d;
            if ( WSAStartup(MAKEWORD(2,2), &d) != 0 ) {
                out() << "ERROR: wsastartup failed " << errnoWithDescription() << endl;
                problem() << "ERROR: wsastartup failed " << errnoWithDescription() << endl;
                _exit(EXIT_NTSERVICE_ERROR);
            }
        }
    } winsock_init;
#endif

} // namespace mongo
コード例 #17
0
ファイル: loop.c プロジェクト: asbr90/EmbSysTesting-Tool
int mosquitto_main_loop(struct mosquitto_db *db, int *listensock, int listensock_count, int listener_max)
{
	time_t start_time = time(NULL);
	time_t last_backup = time(NULL);
	time_t last_store_clean = time(NULL);
	time_t now;
	int fdcount;
#ifndef WIN32
	sigset_t sigblock, origsig;
#endif
	int i;
	struct pollfd *pollfds = NULL;
	int pollfd_count = 0;
	int pollfd_index;

#ifndef WIN32
	sigemptyset(&sigblock);
	sigaddset(&sigblock, SIGINT);
#endif

	while(run){
		mqtt3_db_sys_update(db, db->config->sys_interval, start_time);

		if(listensock_count + db->context_count > pollfd_count){
			pollfd_count = listensock_count + db->context_count;
			pollfds = _mosquitto_realloc(pollfds, sizeof(struct pollfd)*pollfd_count);
			if(!pollfds){
				_mosquitto_log_printf(NULL, MOSQ_LOG_ERR, "Error: Out of memory.");
				return MOSQ_ERR_NOMEM;
			}
		}

		memset(pollfds, -1, sizeof(struct pollfd)*pollfd_count);

		pollfd_index = 0;
		for(i=0; i<listensock_count; i++){
			pollfds[pollfd_index].fd = listensock[i];
			pollfds[pollfd_index].events = POLLIN;
			pollfds[pollfd_index].revents = 0;
			pollfd_index++;
		}

		now = time(NULL);
		for(i=0; i<db->context_count; i++){
			if(db->contexts[i]){
				db->contexts[i]->pollfd_index = -1;

				if(db->contexts[i]->sock != INVALID_SOCKET){
#ifdef WITH_BRIDGE
					if(db->contexts[i]->bridge){
						_mosquitto_check_keepalive(db->contexts[i]);
					}
#endif

					/* Local bridges never time out in this fashion. */
					if(!(db->contexts[i]->keepalive) || db->contexts[i]->bridge || now - db->contexts[i]->last_msg_in < (time_t)(db->contexts[i]->keepalive)*3/2){
						if(mqtt3_db_message_write(db->contexts[i]) == MOSQ_ERR_SUCCESS){
							pollfds[pollfd_index].fd = db->contexts[i]->sock;
							pollfds[pollfd_index].events = POLLIN | POLLRDHUP;
							pollfds[pollfd_index].revents = 0;
							if(db->contexts[i]->out_packet){
								pollfds[pollfd_index].events |= POLLOUT;
							}
							db->contexts[i]->pollfd_index = pollfd_index;
							pollfd_index++;
						}else{
							mqtt3_context_disconnect(db, db->contexts[i]);
						}
					}else{
						if(db->config->connection_messages == true){
							_mosquitto_log_printf(NULL, MOSQ_LOG_NOTICE, "Client %s has exceeded timeout, disconnecting.", db->contexts[i]->id);
						}
						/* Client has exceeded keepalive*1.5 */
						mqtt3_context_disconnect(db, db->contexts[i]);
					}
				}else{
#ifdef WITH_BRIDGE
					if(db->contexts[i]->bridge){
						/* Want to try to restart the bridge connection */
						if(!db->contexts[i]->bridge->restart_t){
							db->contexts[i]->bridge->restart_t = time(NULL)+db->contexts[i]->bridge->restart_timeout;
						}else{
							if(db->contexts[i]->bridge->start_type == bst_automatic && time(NULL) > db->contexts[i]->bridge->restart_t){
								db->contexts[i]->bridge->restart_t = 0;
								if(mqtt3_bridge_connect(db, db->contexts[i]) == MOSQ_ERR_SUCCESS){
									pollfds[pollfd_index].fd = db->contexts[i]->sock;
									pollfds[pollfd_index].events = POLLIN | POLLRDHUP;
									pollfds[pollfd_index].revents = 0;
									if(db->contexts[i]->out_packet){
										pollfds[pollfd_index].events |= POLLOUT;
									}
									db->contexts[i]->pollfd_index = pollfd_index;
									pollfd_index++;
								}else{
									/* Retry later. */
									db->contexts[i]->bridge->restart_t = time(NULL)+db->contexts[i]->bridge->restart_timeout;
								}
							}
						}
					}else{
#endif
						if(db->contexts[i]->clean_session == true){
							mqtt3_context_cleanup(db, db->contexts[i], true);
							db->contexts[i] = NULL;
						}else if(db->config->persistent_client_expiration > 0){
							/* This is a persistent client, check to see if the
							 * last time it connected was longer than
							 * persistent_client_expiration seconds ago. If so,
							 * expire it and clean up.
							 */
							if(time(NULL) > db->contexts[i]->disconnect_t+db->config->persistent_client_expiration){
								_mosquitto_log_printf(NULL, MOSQ_LOG_NOTICE, "Expiring persistent client %s due to timeout.", db->contexts[i]->id);
								g_clients_expired++;
								db->contexts[i]->clean_session = true;
								mqtt3_context_cleanup(db, db->contexts[i], true);
								db->contexts[i] = NULL;
							}
						}
#ifdef WITH_BRIDGE
					}
#endif
				}
			}
		}

		mqtt3_db_message_timeout_check(db, db->config->retry_interval);

#ifndef WIN32
		sigprocmask(SIG_SETMASK, &sigblock, &origsig);
		fdcount = poll(pollfds, pollfd_index, 100);
		sigprocmask(SIG_SETMASK, &origsig, NULL);
#else
		fdcount = WSAPoll(pollfds, pollfd_index, 100);
#endif
		if(fdcount == -1){
			loop_handle_errors(db, pollfds);
		}else{
			loop_handle_reads_writes(db, pollfds);

			for(i=0; i<listensock_count; i++){
				if(pollfds[i].revents & (POLLIN | POLLPRI)){
					while(mqtt3_socket_accept(db, listensock[i]) != -1){
					}
				}
			}
		}
#ifdef WITH_PERSISTENCE
		if(db->config->persistence && db->config->autosave_interval){
			if(db->config->autosave_on_changes){
				if(db->persistence_changes > db->config->autosave_interval){
					mqtt3_db_backup(db, false, false);
					db->persistence_changes = 0;
				}
			}else{
				if(last_backup + db->config->autosave_interval < now){
					mqtt3_db_backup(db, false, false);
					last_backup = time(NULL);
				}
			}
		}
#endif
		if(!db->config->store_clean_interval || last_store_clean + db->config->store_clean_interval < now){
			mqtt3_db_store_clean(db);
			last_store_clean = time(NULL);
		}
#ifdef WITH_PERSISTENCE
		if(flag_db_backup){
			mqtt3_db_backup(db, false, false);
			flag_db_backup = false;
		}
#endif
		if(flag_reload){
			_mosquitto_log_printf(NULL, MOSQ_LOG_INFO, "Reloading config.");
			mqtt3_config_read(db->config, true);
			mosquitto_security_cleanup(db, true);
			mosquitto_security_init(db, true);
			mosquitto_security_apply(db);
			mqtt3_log_init(db->config->log_type, db->config->log_dest);
			flag_reload = false;
		}
		if(flag_tree_print){
			mqtt3_sub_tree_print(&db->subs, 0);
			flag_tree_print = false;
		}
	}

	if(pollfds) _mosquitto_free(pollfds);
	return MOSQ_ERR_SUCCESS;
}
コード例 #18
0
ファイル: sysutils.cpp プロジェクト: Bhushan1002/SFrame
bool
SocketPool::wait( UInt32 msTimeout, UInt32 msInterruptOnlyTimeout, SocketActions *socketActions )   
{
    dbgAssert( socketActions );
    socketActions->clear();

    if( m_pool->size() == 0 )
    {
        // We don't have any sockets to check activity, so wait for 
        // the interrupt event.

#ifdef PERF
        Stopwatch stopwatch( true );
#endif

        DWORD res = WaitForSingleObject( m_interrupt.m_handle, msInterruptOnlyTimeout );
        dbgAssert( res == WAIT_OBJECT_0 || res == WAIT_TIMEOUT );

#ifdef PERF
        LOG_TRACE( "SocketPoolSync:wait for interrupt, actual=%llu, result=%d", 
            stopwatch.elapsed(), res );
#endif

        m_interrupt.reset();
        return res == WAIT_OBJECT_0;  // true if interrupt.
    }
  
    // It would be great to be able to wait for all sockets and the interrupt event together.
    // But we cannot use WSAPoll for that (because it supports sockets only) and 
    // WSAEventSelect/WaitForMultipleObjects (because they are not usable with curl for
    // write events). 
    //
    // For the latter from MSDN (WSAEventSelect):
    //   The FD_WRITE network event is handled slightly differently. An FD_WRITE network event is recorded 
    //   when a socket is first connected with a call to the connect, ConnectEx, WSAConnect, 
    //   WSAConnectByList, or WSAConnectByName function or when a socket is accepted with accept, 
    //   AcceptEx, or WSAAccept function and then after a send fails with WSAEWOULDBLOCK and 
    //   buffer space becomes available. Therefore, an application can assume that sends are 
    //   possible starting from the first FD_WRITE network event setting and lasting until 
    //   a send returns WSAEWOULDBLOCK. After such a failure the application will find out 
    //   that sends are again possible when an FD_WRITE network event is recorded and the
    //   associated event object is set.
    //
    // We don't know if the curl (or whatever caller) got WSAEWOULDBLOCK or not. And if the event is signaled,
    // we don't know if we need to reset it.
    // If curl didn't get WSAEWOULDBLOCK and we reset the event now,
    // we may not (or will never depending on how we are sending) get another signal for a while. 
    // But if we don't reset, WaitForMultipleObjects(..)
    // call becomes useless because the event is always signaled and we just get a busy loop.
    //
    // Other options such as to invoke APC to interrupt WSAPoll don't work either, APC gets
    // delivered but WSAPoll continues running and not interrupted immediately.
    //
    // As workaround, let's spin with short WSAPoll calls and check the interrupt signal in between
    // them.
    //

    dbgAssert( msTimeout < INFINITE );
    const UInt32 spinTimeout = 15;

    while( msTimeout )
    {
        // Check the interrupt signal.

        if( m_interrupt.wait( 0 ) )
        {
            m_interrupt.reset();
            return true;  // true if interrupt.
        }

#ifdef PERF
        Stopwatch stopwatch( true );
#endif
        int res = WSAPoll( &( ( *m_pool )[ 0 ] ), m_pool->size(), spinTimeout );
#ifdef PERF
        LOG_TRACE( "SocketPoolSync:WSAPoll, timeout left=%d, spin=%d, actual=%llu, size=%llu, result=%d", 
            msTimeout, spinTimeout, stopwatch.elapsed(), static_cast< UInt64 >( m_pool->size() ), res );
#endif

        dbgAssert( res >= 0 );

        if( res == 0 )
        {
            if ( msTimeout <= spinTimeout )
            {
                // Overall timeout has expired.

                break;
            }

            // Reduce the overall timeout and repeat.

            msTimeout -= spinTimeout;
            continue;
        }

        if( res > 0 )
        {
            for( SocketPoolState::const_iterator it = m_pool->begin(); it != m_pool->end(); ++it )
            {
                if( it->revents != 0 )
                {
                    socketActions->push_back( SocketActions::value_type( sh( it->fd ), 
                        getActionMask( it->events, it->revents ) ) );
                }
            }
        }

        break;
    }

    return !socketActions->empty(); // true if activity has been detected.
}
コード例 #19
0
ファイル: poll_2.cpp プロジェクト: JackieXie168/connect
int __cdecl main()
{
	WSADATA wsd;
	INT nStartup = 0, nErr = 0, ret = 0;
	SOCKET lsock = INVALID_SOCKET, asock = INVALID_SOCKET;
	SOCKADDR_STORAGE    addr = {0};
	WSAPOLLFD           fdarray = {0};
	ULONG               uNonBlockingMode = 1;
	CHAR                buf[MAX_PATH] = {0};
	HANDLE              hThread = NULL;
	DWORD               dwThreadId = 0;
	
	nErr = WSAStartup(WS_VER,&wsd);
	if (nErr) {
		WSASetLastError(nErr);
		ERR("WSAStartup");
		exit(0);
	} else {
		nStartup++;
	}
	
	if (NULL == (hCloseSignal = CreateEvent(NULL, TRUE, FALSE, NULL))) {
		ERR("CreateEvent");
		exit(0);
	}
	
	/*
	if (NULL == (hThread = CreateThread(NULL, 0, ConnectThread, NULL, 0, &dwThreadId))) {
		ERR("CreateThread");
		//exit__leave;
	}
	*/
	
	addr.ss_family = AF_INET;
	INETADDR_SETANY((SOCKADDR*)&addr);
	SS_PORT((SOCKADDR*)&addr) = htons(DEFAULT_PORT);
	
	if (INVALID_SOCKET == (lsock = socket(AF_INET, SOCK_STREAM, 0))) {
		ERR("socket");
		exit(0);
	}
	/*
	if (SOCKET_ERROR == ioctlsocket(lsock, FIONBIO, &uNonBlockingMode)) {
		ERR("FIONBIO");
		exit(0);
	}
	*/
	
	if (SOCKET_ERROR == bind(lsock, (SOCKADDR*)&addr, sizeof (addr))) {
		ERR("bind");
		exit(0);
	}
	
	if (SOCKET_ERROR == listen(lsock, 100)) {
		ERR("listen");
		exit(0);
	}
	
	//Call WSAPoll for readability of listener (accepted)
	
	//fdarray.fd = lsock;
	//fdarray.events = POLLRDNORM | POLLWRNORM;

	/*
	if (SOCKET_ERROR == (ret = WSAPoll(&fdarray, 1, DEFAULT_WAIT))) {
		ERR("WSAPoll");
		exit(0);
	}
	*/

while (1) {
	//if (ret) {
		//if ((fdarray.revents & POLLRDNORM) || (fdarray.revents & POLLWRNORM)) {
		//	printf("Main: Connection established.\n");
			
			if (INVALID_SOCKET == (asock = accept(lsock, NULL, NULL))) {
				ERR("accept");
				//__leave;
			}
			
			/*
			if (SOCKET_ERROR == (ret = recv(asock, buf, sizeof(buf), 0))) {
				ERR("recv");
			} else {
				printf("Main: recvd %d bytes\n",ret);
			}
			*/
		//}
	//}
	
	//Call WSAPoll for writeability of accepted
	
	fdarray.fd = asock;
	fdarray.events = POLLWRNORM;
	
	if (SOCKET_ERROR == (ret = WSAPoll(&fdarray, 1, DEFAULT_WAIT))) {
		ERR("WSAPoll");
		// exit
	}
	
	if (ret) {
		if (fdarray.revents & POLLWRNORM) {
			if (SOCKET_ERROR == (ret = send(asock, TST_MSG, sizeof(TST_MSG), 0))) {
				ERR("send");
				// exit
			} else {
				printf("Main: sent %d bytes\n",ret);
				closesocket(asock);
			}
		}
	}

}

	//SetEvent(hCloseSignal);
	
	//WaitForSingleObject(hThread,DEFAULT_WAIT);
	
	/* clean up before exit */
	
	CloseHandle(hCloseSignal);
	CloseHandle(hThread);
	CLOSESOCK(asock);
	CLOSESOCK(lsock);
	
	if (nStartup) {
		WSACleanup();
	}
	
	return 0;
	
}
コード例 #20
0
ファイル: WinFcntl.cpp プロジェクト: Dhalwani/airavata
int thrift_poll(THRIFT_POLLFD *fdArray, ULONG nfds, INT timeout)
{
    return WSAPoll(fdArray, nfds, timeout);
}
コード例 #21
0
int main_0040_io_event (int argc, char **argv) {
	rd_kafka_conf_t *conf;
	rd_kafka_topic_conf_t *tconf;
	rd_kafka_t *rk_p, *rk_c;
	const char *topic;
	rd_kafka_topic_t *rkt_p;
	rd_kafka_queue_t *queue;
	uint64_t testid;
	int msgcnt = 100;
	int recvd = 0;
	int fds[2];
	int wait_multiplier = 1;
	struct pollfd pfd;
        int r;
	enum {
		_NOPE,
		_YEP,
		_REBALANCE
	} expecting_io = _REBALANCE;

	testid = test_id_generate();
	topic = test_mk_topic_name(__FUNCTION__, 1);

	rk_p = test_create_producer();
	rkt_p = test_create_producer_topic(rk_p, topic, NULL);
	test_auto_create_topic_rkt(rk_p, rkt_p);

	test_conf_init(&conf, &tconf, 0);
	rd_kafka_conf_set_events(conf, RD_KAFKA_EVENT_REBALANCE);
	test_conf_set(conf, "session.timeout.ms", "6000");
	test_conf_set(conf, "enable.partition.eof", "false");
	/* Speed up propagation of new topics */
	test_conf_set(conf, "metadata.max.age.ms", "5000");
	test_topic_conf_set(tconf, "auto.offset.reset", "earliest");
	rk_c = test_create_consumer(topic, NULL, conf, tconf);

	queue = rd_kafka_queue_get_consumer(rk_c);

	test_consumer_subscribe(rk_c, topic);

#ifndef _MSC_VER
        r = pipe(fds);
#else
        r = _pipe(fds, 2, _O_BINARY);
#endif
        if (r == -1)
		TEST_FAIL("pipe() failed: %s\n", strerror(errno));
	
	rd_kafka_queue_io_event_enable(queue, fds[1], "1", 1);

	pfd.fd = fds[0];
	pfd.events = POLLIN;
	pfd.revents = 0;

	/**
	 * 1) Wait for rebalance event
	 * 2) Wait 1 interval (1s) expecting no IO (nothing produced).
	 * 3) Produce half the messages
	 * 4) Expect IO
	 * 5) Consume the available messages
	 * 6) Wait 1 interval expecting no IO.
	 * 7) Produce remaing half
	 * 8) Expect IO
	 * 9) Done.
	 */
	while (recvd < msgcnt) {
		int r;

#ifndef _MSC_VER
		r = poll(&pfd, 1, 1000 * wait_multiplier);
#else
                r = WSAPoll(&pfd, 1, 1000 * wait_multiplier);
#endif
		if (r == -1) {
			TEST_FAIL("poll() failed: %s", strerror(errno));
			
		} else if (r == 1) {
			rd_kafka_event_t *rkev;
			char b;
			int eventcnt = 0;

			if (pfd.events & POLLERR)
				TEST_FAIL("Poll error\n");
			if (!(pfd.events & POLLIN)) {
				TEST_SAY("Stray event 0x%x\n", (int)pfd.events);
				continue;
			}

			TEST_SAY("POLLIN\n");
                        /* Read signaling token to purge socket queue and
                         * eventually silence POLLIN */
#ifndef _MSC_VER
			r = read(pfd.fd, &b, 1);
#else
			r = _read((int)pfd.fd, &b, 1);
#endif
			if (r == -1)
				TEST_FAIL("read failed: %s\n", strerror(errno));

			if (!expecting_io)
				TEST_WARN("Got unexpected IO after %d/%d msgs\n",
					  recvd, msgcnt);

			while ((rkev = rd_kafka_queue_poll(queue, 0))) {
				eventcnt++;
				switch (rd_kafka_event_type(rkev))
				{
				case RD_KAFKA_EVENT_REBALANCE:
					TEST_SAY("Got %s: %s\n", rd_kafka_event_name(rkev),
						 rd_kafka_err2str(rd_kafka_event_error(rkev)));
					if (expecting_io != _REBALANCE)
						TEST_FAIL("Got Rebalance when expecting message\n");
					if (rd_kafka_event_error(rkev) == RD_KAFKA_RESP_ERR__ASSIGN_PARTITIONS) {
						rd_kafka_assign(rk_c, rd_kafka_event_topic_partition_list(rkev));
						expecting_io = _NOPE;
					} else
						rd_kafka_assign(rk_c, NULL);
					break;
					
				case RD_KAFKA_EVENT_FETCH:
					if (expecting_io != _YEP)
						TEST_FAIL("Did not expect more messages at %d/%d\n",
							  recvd, msgcnt);
					recvd++;
					if (recvd == (msgcnt / 2) || recvd == msgcnt)
						expecting_io = _NOPE;
					break;

				case RD_KAFKA_EVENT_ERROR:
					TEST_FAIL("Error: %s\n", rd_kafka_event_error_string(rkev));
					break;

				default:
					TEST_SAY("Ignoring event %s\n", rd_kafka_event_name(rkev));
				}
					
				rd_kafka_event_destroy(rkev);
			}
			TEST_SAY("%d events, Consumed %d/%d messages\n", eventcnt, recvd, msgcnt);

			wait_multiplier = 1;

		} else {
			if (expecting_io == _REBALANCE) {
				continue;
			} else if (expecting_io == _YEP) {
				TEST_FAIL("Did not see expected IO after %d/%d msgs\n",
					  recvd, msgcnt);
			}

			TEST_SAY("IO poll timeout (good)\n");

			TEST_SAY("Got idle period, producing\n");
			test_produce_msgs(rk_p, rkt_p, testid, 0, recvd, msgcnt/2,
					  NULL, 10);

			expecting_io = _YEP;
			/* When running slowly (e.g., valgrind) it might take
			 * some time before the first message is received
			 * after producing. */
			wait_multiplier = 3;
		}
	}
	TEST_SAY("Done\n");

	rd_kafka_topic_destroy(rkt_p);
	rd_kafka_destroy(rk_p);

	rd_kafka_queue_destroy(queue);
	rd_kafka_consumer_close(rk_c);
	rd_kafka_destroy(rk_c);

#ifndef _MSC_VER
	close(fds[0]);
	close(fds[1]);
#else
        _close(fds[0]);
        _close(fds[1]);
#endif

	return 0;
}
コード例 #22
0
ファイル: select.c プロジェクト: LuaDist/cmake
/*
 * This is an internal function used for waiting for read or write
 * events on single file descriptors.  It attempts to replace select()
 * in order to avoid limits with FD_SETSIZE.
 *
 * Return values:
 *   -1 = system call error
 *    0 = timeout
 *    CSELECT_IN | CSELECT_OUT | CSELECT_ERR
 */
int Curl_select(curl_socket_t readfd, curl_socket_t writefd, int timeout_ms)
{
#if defined(HAVE_POLL_FINE) || defined(CURL_HAVE_WSAPOLL)
  struct pollfd pfd[2];
  int num;
  int r;
  int ret;

  num = 0;
  if (readfd != CURL_SOCKET_BAD) {
    pfd[num].fd = readfd;
    pfd[num].events = POLLIN;
    num++;
  }
  if (writefd != CURL_SOCKET_BAD) {
    pfd[num].fd = writefd;
    pfd[num].events = POLLOUT;
    num++;
  }

#ifdef HAVE_POLL_FINE
  do {
    r = poll(pfd, num, timeout_ms);
  } while((r == -1) && (errno == EINTR));
#else
  r = WSAPoll(pfd, num, timeout_ms);
#endif

  if (r < 0)
    return -1;
  if (r == 0)
    return 0;

  ret = 0;
  num = 0;
  if (readfd != CURL_SOCKET_BAD) {
    if (pfd[num].revents & (POLLIN|POLLHUP))
      ret |= CSELECT_IN;
    if (pfd[num].revents & POLLERR) {
#ifdef __CYGWIN__
      /* Cygwin 1.5.21 needs this hack to pass test 160 */
      if (errno == EINPROGRESS)
        ret |= CSELECT_IN;
      else
#endif
        ret |= CSELECT_ERR;
    }
    num++;
  }
  if (writefd != CURL_SOCKET_BAD) {
    if (pfd[num].revents & POLLOUT)
      ret |= CSELECT_OUT;
    if (pfd[num].revents & (POLLERR|POLLHUP))
      ret |= CSELECT_ERR;
  }

  return ret;
#else
  struct timeval timeout;
  fd_set fds_read;
  fd_set fds_write;
  fd_set fds_err;
  curl_socket_t maxfd;
  int r;
  int ret;

  timeout.tv_sec = timeout_ms / 1000;
  timeout.tv_usec = (timeout_ms % 1000) * 1000;

  if((readfd == CURL_SOCKET_BAD) && (writefd == CURL_SOCKET_BAD)) {
    /* According to POSIX we should pass in NULL pointers if we don't want to
       wait for anything in particular but just use the timeout function.
       Windows however returns immediately if done so. I copied the MSDOS
       delay() use from src/main.c that already had this work-around. */
#ifdef WIN32
    Sleep(timeout_ms);
#elif defined(__MSDOS__)
    delay(timeout_ms);
#else
    select(0, NULL, NULL, NULL, &timeout);
#endif
    return 0;
  }

  FD_ZERO(&fds_err);
  maxfd = (curl_socket_t)-1;

  FD_ZERO(&fds_read);
  if (readfd != CURL_SOCKET_BAD) {
    VERIFY_SOCK(readfd);
    FD_SET(readfd, &fds_read);
    FD_SET(readfd, &fds_err);
    maxfd = readfd;
  }

  FD_ZERO(&fds_write);
  if (writefd != CURL_SOCKET_BAD) {
    VERIFY_SOCK(writefd);
    FD_SET(writefd, &fds_write);
    FD_SET(writefd, &fds_err);
    if (writefd > maxfd)
      maxfd = writefd;
  }

  do {
    r = select((int)maxfd + 1, &fds_read, &fds_write, &fds_err, &timeout);
  } while((r == -1) && (Curl_sockerrno() == EINTR));

  if (r < 0)
    return -1;
  if (r == 0)
    return 0;

  ret = 0;
  if (readfd != CURL_SOCKET_BAD) {
    if (FD_ISSET(readfd, &fds_read))
      ret |= CSELECT_IN;
    if (FD_ISSET(readfd, &fds_err))
      ret |= CSELECT_ERR;
  }
  if (writefd != CURL_SOCKET_BAD) {
    if (FD_ISSET(writefd, &fds_write))
      ret |= CSELECT_OUT;
    if (FD_ISSET(writefd, &fds_err))
      ret |= CSELECT_ERR;
  }

  return ret;
#endif
}
コード例 #23
0
ファイル: select.c プロジェクト: LuaDist/cmake
/*
 * This is a wrapper around poll().  If poll() does not exist, then
 * select() is used instead.  An error is returned if select() is
 * being used and a file descriptor too large for FD_SETSIZE.
 *
 * Return values:
 *   -1 = system call error or fd >= FD_SETSIZE
 *    0 = timeout
 *    1 = number of structures with non zero revent fields
 */
int Curl_poll(struct pollfd ufds[], unsigned int nfds, int timeout_ms)
{
  int r;
#ifdef HAVE_POLL_FINE
  do {
    r = poll(ufds, nfds, timeout_ms);
  } while((r == -1) && (errno == EINTR));
#elif defined(CURL_HAVE_WSAPOLL)
  r = WSAPoll(ufds, nfds, timeout_ms);
#else
  struct timeval timeout;
  struct timeval *ptimeout;
  fd_set fds_read;
  fd_set fds_write;
  fd_set fds_err;
  curl_socket_t maxfd;
  unsigned int i;

  FD_ZERO(&fds_read);
  FD_ZERO(&fds_write);
  FD_ZERO(&fds_err);
  maxfd = (curl_socket_t)-1;

  for (i = 0; i < nfds; i++) {
    if (ufds[i].fd == CURL_SOCKET_BAD)
      continue;
#ifndef USE_WINSOCK  /* winsock sockets are not in range [0..FD_SETSIZE] */
    if (ufds[i].fd >= FD_SETSIZE) {
      errno = EINVAL;
      return -1;
    }
#endif
    if (ufds[i].fd > maxfd)
      maxfd = ufds[i].fd;
    if (ufds[i].events & POLLIN)
      FD_SET(ufds[i].fd, &fds_read);
    if (ufds[i].events & POLLOUT)
      FD_SET(ufds[i].fd, &fds_write);
    if (ufds[i].events & POLLERR)
      FD_SET(ufds[i].fd, &fds_err);
  }

  if (timeout_ms < 0) {
    ptimeout = NULL;      /* wait forever */
  } else {
    timeout.tv_sec = timeout_ms / 1000;
    timeout.tv_usec = (timeout_ms % 1000) * 1000;
    ptimeout = &timeout;
  }

  do {
    r = select((int)maxfd + 1, &fds_read, &fds_write, &fds_err, ptimeout);
  } while((r == -1) && (Curl_sockerrno() == EINTR));

  if (r < 0)
    return -1;
  if (r == 0)
    return 0;

  r = 0;
  for (i = 0; i < nfds; i++) {
    ufds[i].revents = 0;
    if (ufds[i].fd == CURL_SOCKET_BAD)
      continue;
    if (FD_ISSET(ufds[i].fd, &fds_read))
      ufds[i].revents |= POLLIN;
    if (FD_ISSET(ufds[i].fd, &fds_write))
      ufds[i].revents |= POLLOUT;
    if (FD_ISSET(ufds[i].fd, &fds_err))
      ufds[i].revents |= POLLERR;
    if (ufds[i].revents != 0)
      r++;
  }
#endif
  return r;
}
コード例 #24
0
		int pollFunc(socketHandle *ufds, size_t nfds, int timeout){ return WSAPoll(ufds, nfds, timeout); }
コード例 #25
0
/**
 * See header
 */
int poll(struct pollfd *fds, int nfds, int timeout)
{
	return wserr(WSAPoll(fds, nfds, timeout));
}
コード例 #26
0
ファイル: connection.c プロジェクト: blakawk/Aio4c
Connection* ConnectionInit(Connection* connection) {
    ErrorCode code = AIO4C_ERROR_CODE_INITIALIZER;

#ifndef AIO4C_WIN32
    if ((connection->socket = socket(PF_INET, SOCK_STREAM, 0)) == -1) {
        code.error = errno;
#else /* AIO4C_WIN32 */
    if ((connection->socket = socket(PF_INET, SOCK_STREAM, 0)) == SOCKET_ERROR) {
        code.source = AIO4C_ERRNO_SOURCE_WSA;
#endif /* AIO4C_WIN32 */
        return _ConnectionHandleError(connection, AIO4C_LOG_LEVEL_ERROR, AIO4C_SOCKET_ERROR, &code);
    }

#ifndef AIO4C_WIN32
    if (fcntl(connection->socket, F_SETFL, O_NONBLOCK) == -1) {
        code.error = errno;
#else /* AIO4C_WIN32 */
    unsigned long ioctl = 1;
    if (ioctlsocket(connection->socket, FIONBIO, &ioctl) == SOCKET_ERROR) {
        code.source = AIO4C_ERRNO_SOURCE_WSA;
#endif /* AIO4C_WIN32 */
        return _ConnectionHandleError(connection, AIO4C_LOG_LEVEL_ERROR, AIO4C_FCNTL_ERROR, &code);
    }

    ConnectionState(connection, AIO4C_CONNECTION_STATE_INITIALIZED);

    return connection;
}

Connection* ConnectionConnect(Connection* connection) {
    ErrorCode code = AIO4C_ERROR_CODE_INITIALIZER;
    ConnectionState newState = AIO4C_CONNECTION_STATE_CONNECTING;

    if (connection->state != AIO4C_CONNECTION_STATE_INITIALIZED) {
        code.expected = AIO4C_CONNECTION_STATE_INITIALIZED;
        return _ConnectionHandleError(connection, AIO4C_LOG_LEVEL_DEBUG, AIO4C_CONNECTION_STATE_ERROR, &code);
    }

    if (connect(connection->socket, AddressGetAddr(connection->address), AddressGetAddrSize(connection->address)) == -1) {
#ifndef AIO4C_WIN32
        code.error = errno;
        if (errno == EINPROGRESS) {
#else /* AIO4C_WIN32 */
        int error = WSAGetLastError();
        code.source = AIO4C_ERRNO_SOURCE_WSA;
        if (error == WSAEINPROGRESS || error == WSAEALREADY || error == WSAEWOULDBLOCK) {
#endif /* AIO4C_WIN32 */
            newState = AIO4C_CONNECTION_STATE_CONNECTING;
        } else {
            return _ConnectionHandleError(connection, AIO4C_LOG_LEVEL_ERROR, AIO4C_CONNECT_ERROR, &code);
        }
    } else {
        newState = AIO4C_CONNECTION_STATE_CONNECTED;
    }

    ConnectionState(connection, newState);

    return connection;
}

Connection* ConnectionFinishConnect(Connection* connection) {
    ErrorCode code = AIO4C_ERROR_CODE_INITIALIZER;
    int soError = 0;
    socklen_t soSize = sizeof(int);

#ifdef AIO4C_HAVE_POLL
    aio4c_poll_t polls[1] = { { .fd = connection->socket, .events = POLLOUT, .revents = 0 } };

#ifndef AIO4C_WIN32
    if (poll(polls, 1, -1) == -1) {
        code.error = errno;
#else /* AIO4C_WIN32 */
    if (WSAPoll(polls, 1, -1) == SOCKET_ERROR) {
        code.source = AIO4C_ERRNO_SOURCE_WSA;
#endif /* AIO4C_WIN32 */
        return _ConnectionHandleError(connection, AIO4C_LOG_LEVEL_ERROR, AIO4C_POLL_ERROR, &code);
    }

    if (polls[0].revents > 0) {
#else /* AIO4C_HAVE_POLL */
    fd_set writeSet;
    fd_set errorSet;

    FD_ZERO(&writeSet);
    FD_ZERO(&errorSet);
    FD_SET(connection->socket, &writeSet);
    FD_SET(connection->socket, &errorSet);

#ifndef AIO4C_WIN32
    if (select(connection->socket + 1, NULL, &writeSet, &errorSet, NULL) == -1) {
        code.error = errno;
#else /* AIO4C_WIN32 */
    if (select(connection->socket + 1, NULL, &writeSet, &errorSet, NULL) == SOCKET_ERROR) {
        code.source = AIO4C_ERRNO_SOURCE_WSA;
#endif /* AIO4C_WIN32 */
        return _ConnectionHandleError(connection, AIO4C_LOG_LEVEL_ERROR, AIO4C_SELECT_ERROR, &code);
    }

    if (FD_ISSET(connection->socket, &writeSet) || FD_ISSET(connection->socket, &errorSet)) {
#endif /* AIO4C_HAVE_POLL */

#ifndef AIO4C_WIN32
        if (getsockopt(connection->socket, SOL_SOCKET, SO_ERROR, &soError, &soSize) != 0) {
            code.error = errno;
#else /* AI4OC_WIN32 */
        if (getsockopt(connection->socket, SOL_SOCKET, SO_ERROR, (char*)&soError, &soSize) == SOCKET_ERROR) {
            code.source = AIO4C_ERRNO_SOURCE_WSA;
#endif /* AIO4C_WIN32 */
            return _ConnectionHandleError(connection, AIO4C_LOG_LEVEL_ERROR, AIO4C_GETSOCKOPT_ERROR, &code);
        }

        if (soError != 0) {
#ifndef AIO4C_WIN32
            code.error = soError;
#else /* AIO4C_WIN32 */
            code.source = AIO4C_ERRNO_SOURCE_SOE;
            code.soError = soError;
#endif /* AIO4C_WIN32 */
            return _ConnectionHandleError(connection, AIO4C_LOG_LEVEL_ERROR, AIO4C_FINISH_CONNECT_ERROR, &code);
        }
    }

    return connection;
}

Connection* ConnectionRead(Connection* connection) {
    Buffer* buffer = NULL;
    ssize_t nbRead = 0;
    ErrorCode code = AIO4C_ERROR_CODE_INITIALIZER;
    aio4c_byte_t* data = NULL;

    buffer = connection->readBuffer;

    if (!BufferHasRemaining(buffer)) {
        code.buffer = buffer;
        return _ConnectionHandleError(connection, AIO4C_LOG_LEVEL_ERROR, AIO4C_BUFFER_OVERFLOW_ERROR, &code);
    }

    data = BufferGetBytes(buffer);
    if ((nbRead = recv(connection->socket, (void*)&data[BufferGetPosition(buffer)], BufferRemaining(buffer), 0)) < 0) {
#ifndef AIO4C_WIN32
        code.error = errno;
#else /* AIO4C_WIN32 */
        code.source = AIO4C_ERRNO_SOURCE_WSA;
#endif /* AIO4C_WIN32 */
        return _ConnectionHandleError(connection, AIO4C_LOG_LEVEL_ERROR, AIO4C_READ_ERROR, &code);
    }

    ProbeSize(AIO4C_PROBE_NETWORK_READ_SIZE, nbRead);

    if (nbRead == 0) {
        if (connection->state == AIO4C_CONNECTION_STATE_PENDING_CLOSE) {
            ConnectionState(connection, AIO4C_CONNECTION_STATE_CLOSED);
            return connection;
        } else {
            return _ConnectionHandleError(connection, AIO4C_LOG_LEVEL_INFO, AIO4C_CONNECTION_DISCONNECTED, &code);
        }
    }

    if (!connection->canRead) {
        Log(AIO4C_LOG_LEVEL_WARN, "received data on connection %s when reading is not allowed", connection->string);
        BufferReset(buffer);
        return connection;
    }

    BufferPosition(buffer, BufferGetPosition(buffer) + nbRead);

    _ConnectionEventHandle(connection, AIO4C_INBOUND_DATA_EVENT);

    return connection;
}