Example #1
0
static void
bev_async_consider_reading(struct bufferevent_async *beva)
{
	size_t cur_size;
	size_t read_high;
	size_t at_most;
	int limit;
	struct bufferevent *bev = &beva->bev.bev;

	/* Don't read if there is a read in progress, or we do not
	 * want to read. */
	if (beva->read_in_progress || beva->bev.connecting)
		return;
	if (!beva->ok || !(bev->enabled&EV_READ)) {
		bev_async_del_read(beva);
		return;
	}

	/* Don't read if we're full */
	cur_size = evbuffer_get_length(bev->input);
	read_high = bev->wm_read.high;
	if (read_high) {
		if (cur_size >= read_high) {
			bev_async_del_read(beva);
			return;
		}
		at_most = read_high - cur_size;
	} else {
		at_most = 16384; /* FIXME totally magic. */
	}

	/* XXXX This over-commits. */
	/* XXXX see also not above on cast on _bufferevent_get_write_max() */
	limit = (int)_bufferevent_get_read_max(&beva->bev);
	if (at_most >= (size_t)limit && limit >= 0)
		at_most = limit;

	if (beva->bev.read_suspended) {
		bev_async_del_read(beva);
		return;
	}

	bufferevent_incref(bev);
	if (evbuffer_launch_read(bev->input, at_most, &beva->read_overlapped)) {
		beva->ok = 0;
		_bufferevent_run_eventcb(bev, BEV_EVENT_ERROR);
		bufferevent_decref(bev);
	} else {
		beva->read_in_progress = at_most;
		_bufferevent_decrement_read_buckets(&beva->bev, at_most);
		bev_async_add_read(beva);
	}

	return;
}
Example #2
0
static int
be_async_disable(struct bufferevent *bev, short what)
{
	struct bufferevent_async *bev_async = upcast(bev);
	/* XXXX If we disable reading or writing, we may want to consider
	 * canceling any in-progress read or write operation, though it might
	 * not work. */

	if (what & EV_READ) {
		BEV_DEL_GENERIC_READ_TIMEOUT(bev);
		bev_async_del_read(bev_async);
	}
	if (what & EV_WRITE) {
		BEV_DEL_GENERIC_WRITE_TIMEOUT(bev);
		bev_async_del_write(bev_async);
	}

	return 0;
}
static void
be_async_destruct(struct bufferevent *bev)
{
	struct bufferevent_async *bev_async = upcast(bev);
	struct bufferevent_private *bev_p = BEV_UPCAST(bev);
	evutil_socket_t fd;

	EVUTIL_ASSERT(!upcast(bev)->write_in_progress &&
			!upcast(bev)->read_in_progress);

	bev_async_del_read(bev_async);
	bev_async_del_write(bev_async);

	fd = evbuffer_overlapped_get_fd_(bev->input);
	if (bev_p->options & BEV_OPT_CLOSE_ON_FREE) {
		/* XXXX possible double-close */
		ld_evutil_closesocket(fd);
	}
}
Example #4
0
static void
be_async_destruct(struct bufferevent *bev)
{
	struct bufferevent_async *bev_async = upcast(bev);
	struct bufferevent_private *bev_p = BEV_UPCAST(bev);
	evutil_socket_t fd;

	EVUTIL_ASSERT(!upcast(bev)->write_in_progress &&
			!upcast(bev)->read_in_progress);

	bev_async_del_read(bev_async);
	bev_async_del_write(bev_async);

	fd = evbuffer_overlapped_get_fd_(bev->input);
	if (fd != (evutil_socket_t)INVALID_SOCKET &&
		(bev_p->options & BEV_OPT_CLOSE_ON_FREE)) {
		evutil_closesocket(fd);
		evbuffer_overlapped_set_fd_(bev->input, INVALID_SOCKET);
	}
}
Example #5
0
static void
be_async_destruct(struct bufferevent *bev)
{
	struct bufferevent_async *bev_async = upcast(bev);
	struct bufferevent_private *bev_p = BEV_UPCAST(bev);
	evutil_socket_t fd;

	EVUTIL_ASSERT(!upcast(bev)->write_in_progress &&
			!upcast(bev)->read_in_progress);

	bev_async_del_read(bev_async);
	bev_async_del_write(bev_async);

	fd = _evbuffer_overlapped_get_fd(bev->input);
	if (bev_p->options & BEV_OPT_CLOSE_ON_FREE) {
		/* XXXX possible double-close */
		evutil_closesocket(fd);
	}
	/* delete this in case non-blocking connect was used */
	if (event_initialized(&bev->ev_write)) {
		event_del(&bev->ev_write);
		_bufferevent_del_generic_timeout_cbs(bev);
	}
}