aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/core/iomgr
diff options
context:
space:
mode:
authorGravatar Craig Tiller <craig.tiller@gmail.com>2015-06-18 08:13:05 -0700
committerGravatar Craig Tiller <craig.tiller@gmail.com>2015-06-18 08:13:05 -0700
commit6174b9a4d092c145d6cd3c90ab59bf5a0939329e (patch)
tree6a7a4ccfb3a628a36e5aa623e5b32d72843e683e /src/core/iomgr
parent42b239f13f2b07b65d5aa1440ccb91ec19ef9c7c (diff)
Docs
Diffstat (limited to 'src/core/iomgr')
-rw-r--r--src/core/iomgr/pollset.h2
-rw-r--r--src/core/iomgr/pollset_kick_posix.h8
-rw-r--r--src/core/iomgr/pollset_multipoller_with_epoll.c10
-rw-r--r--src/core/iomgr/pollset_multipoller_with_poll_posix.c10
-rw-r--r--src/core/iomgr/pollset_posix.c26
-rw-r--r--src/core/iomgr/pollset_posix.h9
-rw-r--r--src/core/iomgr/pollset_set.h2
-rw-r--r--src/core/iomgr/tcp_client.h4
-rw-r--r--src/core/iomgr/tcp_server_posix.c6
9 files changed, 46 insertions, 31 deletions
diff --git a/src/core/iomgr/pollset.h b/src/core/iomgr/pollset.h
index da3c94ec11..7472b6144f 100644
--- a/src/core/iomgr/pollset.h
+++ b/src/core/iomgr/pollset.h
@@ -65,7 +65,7 @@ void grpc_pollset_destroy(grpc_pollset *pollset);
May unlock GRPC_POLLSET_MU(pollset) during its execution. */
int grpc_pollset_work(grpc_pollset *pollset, gpr_timespec deadline);
-/* Break a pollset out of polling work
+/* Break one polling thread out of polling work for this pollset.
Requires GRPC_POLLSET_MU(pollset) locked. */
void grpc_pollset_kick(grpc_pollset *pollset);
diff --git a/src/core/iomgr/pollset_kick_posix.h b/src/core/iomgr/pollset_kick_posix.h
index 0a404b601b..77e32a8d51 100644
--- a/src/core/iomgr/pollset_kick_posix.h
+++ b/src/core/iomgr/pollset_kick_posix.h
@@ -37,6 +37,11 @@
#include "src/core/iomgr/wakeup_fd_posix.h"
#include <grpc/support/sync.h>
+/* pollset kicking allows breaking a thread out of polling work for
+ a given pollset.
+ writing a byte to a pipe is used as a posix-ly portable base
+ mechanism, and eventfds are utilized on Linux for better performance. */
+
typedef struct grpc_kick_fd_info {
grpc_wakeup_fd_info wakeup_fd;
/* used for polling list and free list */
@@ -67,7 +72,7 @@ void grpc_pollset_kick_destroy(grpc_pollset_kick_state *kick_state);
* applicable. Intended for testing. */
void grpc_pollset_kick_global_init_fallback_fd(void);
-/* Must be called before entering poll(). If return value is -1, this consumed
+/* Must be called before entering poll(). If return value is NULL, this consumed
an existing kick. Otherwise the return value is an FD to add to the poll set.
*/
grpc_kick_fd_info *grpc_pollset_kick_pre_poll(
@@ -82,6 +87,7 @@ void grpc_pollset_kick_consume(grpc_pollset_kick_state *kick_state,
void grpc_pollset_kick_post_poll(grpc_pollset_kick_state *kick_state,
grpc_kick_fd_info *fd_info);
+/* Actually kick */
void grpc_pollset_kick_kick(grpc_pollset_kick_state *kick_state);
#endif /* GRPC_INTERNAL_CORE_IOMGR_POLLSET_KICK_POSIX_H */
diff --git a/src/core/iomgr/pollset_multipoller_with_epoll.c b/src/core/iomgr/pollset_multipoller_with_epoll.c
index e5e3435feb..b4a526b9e7 100644
--- a/src/core/iomgr/pollset_multipoller_with_epoll.c
+++ b/src/core/iomgr/pollset_multipoller_with_epoll.c
@@ -97,15 +97,7 @@ static int multipoll_with_epoll_pollset_maybe_work(
* here.
*/
- if (gpr_time_cmp(deadline, gpr_inf_future) == 0) {
- timeout_ms = -1;
- } else {
- timeout_ms = gpr_time_to_millis(
- gpr_time_add(gpr_time_sub(deadline, now), gpr_time_from_micros(500)));
- if (timeout_ms < 0) {
- return 1;
- }
- }
+ timeout_ms = grpc_poll_deadline_to_millis_timeout(deadline, now);
pollset->counter += 1;
gpr_mu_unlock(&pollset->mu);
diff --git a/src/core/iomgr/pollset_multipoller_with_poll_posix.c b/src/core/iomgr/pollset_multipoller_with_poll_posix.c
index d21c52c0f0..2f108da66a 100644
--- a/src/core/iomgr/pollset_multipoller_with_poll_posix.c
+++ b/src/core/iomgr/pollset_multipoller_with_poll_posix.c
@@ -113,15 +113,7 @@ static int multipoll_with_poll_pollset_maybe_work(
grpc_kick_fd_info *kfd;
h = pollset->data.ptr;
- if (gpr_time_cmp(deadline, gpr_inf_future) == 0) {
- timeout = -1;
- } else {
- timeout = gpr_time_to_millis(
- gpr_time_add(gpr_time_sub(deadline, now), gpr_time_from_micros(500)));
- if (timeout < 0) {
- return 1;
- }
- }
+ timeout = grpc_poll_deadline_to_millis_timeout(deadline, now);
if (h->pfd_capacity < h->fd_count + 1) {
h->pfd_capacity = GPR_MAX(h->pfd_capacity * 3 / 2, h->fd_count + 1);
gpr_free(h->pfds);
diff --git a/src/core/iomgr/pollset_posix.c b/src/core/iomgr/pollset_posix.c
index 83ff1f26a5..46d3d132ce 100644
--- a/src/core/iomgr/pollset_posix.c
+++ b/src/core/iomgr/pollset_posix.c
@@ -188,6 +188,22 @@ void grpc_pollset_destroy(grpc_pollset *pollset) {
gpr_mu_destroy(&pollset->mu);
}
+int grpc_poll_deadline_to_millis_timeout(gpr_timespec deadline, gpr_timespec now) {
+ gpr_timespec timeout;
+ static const int max_spin_polling_us = 10;
+ if (gpr_time_cmp(deadline, gpr_inf_future) == 0) {
+ return -1;
+ }
+ if (gpr_time_cmp(
+ deadline,
+ gpr_time_add(now, gpr_time_from_micros(max_spin_polling_us))) <= 0) {
+ return 0;
+ }
+ timeout = gpr_time_sub(deadline, now);
+ return gpr_time_to_millis(
+ gpr_time_add(timeout, gpr_time_from_nanos(GPR_NS_PER_SEC - 1)));
+}
+
/*
* basic_pollset - a vtable that provides polling for zero or one file
* descriptor via poll()
@@ -344,15 +360,7 @@ static int basic_pollset_maybe_work(grpc_pollset *pollset,
GRPC_FD_UNREF(fd, "basicpoll");
fd = pollset->data.ptr = NULL;
}
- if (gpr_time_cmp(deadline, gpr_inf_future) == 0) {
- timeout = -1;
- } else {
- timeout = gpr_time_to_millis(
- gpr_time_add(gpr_time_sub(deadline, now), gpr_time_from_micros(500)));
- if (timeout < 0) {
- return 1;
- }
- }
+ timeout = grpc_poll_deadline_to_millis_timeout(deadline, now);
kfd = grpc_pollset_kick_pre_poll(&pollset->kick_state);
if (kfd == NULL) {
/* Already kicked */
diff --git a/src/core/iomgr/pollset_posix.h b/src/core/iomgr/pollset_posix.h
index 92c258e0cd..ba3d638d41 100644
--- a/src/core/iomgr/pollset_posix.h
+++ b/src/core/iomgr/pollset_posix.h
@@ -94,6 +94,15 @@ int grpc_kick_read_fd(grpc_pollset *p);
/* Call after polling has been kicked to leave the kicked state */
void grpc_kick_drain(grpc_pollset *p);
+/* Convert a timespec to milliseconds:
+ - very small or negative poll times are clamped to zero to do a
+ non-blocking poll (which becomes spin polling)
+ - other small values are rounded up to one millisecond
+ - longer than a millisecond polls are rounded up to the next nearest
+ millisecond to avoid spinning
+ - infinite timeouts are converted to -1 */
+int grpc_poll_deadline_to_millis_timeout(gpr_timespec deadline, gpr_timespec now);
+
/* turn a pollset into a multipoller: platform specific */
typedef void (*grpc_platform_become_multipoller_type)(grpc_pollset *pollset,
struct grpc_fd **fds,
diff --git a/src/core/iomgr/pollset_set.h b/src/core/iomgr/pollset_set.h
index 335ffb21b9..98e3b552a7 100644
--- a/src/core/iomgr/pollset_set.h
+++ b/src/core/iomgr/pollset_set.h
@@ -39,7 +39,7 @@
/* A grpc_pollset_set is a set of pollsets that are interested in an
action. Adding a pollset to a pollset_set automatically adds any
fd's (etc) that have been registered with the set_set with that pollset.
- Registering fd's automatically iterates all current pollsets. */
+ Registering fd's automatically adds them to all current pollsets. */
#ifdef GPR_POSIX_SOCKET
#include "src/core/iomgr/pollset_set_posix.h"
diff --git a/src/core/iomgr/tcp_client.h b/src/core/iomgr/tcp_client.h
index f40a5043c8..0fa08b52b0 100644
--- a/src/core/iomgr/tcp_client.h
+++ b/src/core/iomgr/tcp_client.h
@@ -41,7 +41,9 @@
/* Asynchronously connect to an address (specified as (addr, len)), and call
cb with arg and the completed connection when done (or call cb with arg and
- NULL on failure) */
+ NULL on failure).
+ interested_parties points to a set of pollsets that would be interested
+ in this connection being established (in order to continue their work) */
void grpc_tcp_client_connect(void (*cb)(void *arg, grpc_endpoint *tcp),
void *arg, grpc_pollset_set *interested_parties,
const struct sockaddr *addr, int addr_len,
diff --git a/src/core/iomgr/tcp_server_posix.c b/src/core/iomgr/tcp_server_posix.c
index 2ac35f863a..5854031c9b 100644
--- a/src/core/iomgr/tcp_server_posix.c
+++ b/src/core/iomgr/tcp_server_posix.c
@@ -108,6 +108,7 @@ struct grpc_tcp_server {
/* destroyed port count: how many ports are completely destroyed */
size_t destroyed_ports;
+ /* is this server shutting down? (boolean) */
int shutdown;
/* all listening ports */
@@ -119,7 +120,9 @@ struct grpc_tcp_server {
void (*shutdown_complete)(void *);
void *shutdown_complete_arg;
+ /* all pollsets interested in new connections */
grpc_pollset **pollsets;
+ /* number of pollsets in the pollsets array */
size_t pollset_count;
};
@@ -160,6 +163,9 @@ static void destroyed_port(void *server, int success) {
static void dont_care_about_shutdown_completion(void *ignored) {}
+/* called when all listening endpoints have been shutdown, so no further
+ events will be received on them - at this point it's safe to destroy
+ things */
static void deactivated_all_ports(grpc_tcp_server *s) {
size_t i;