read once
diff --git a/src/core/lib/iomgr/udp_server.cc b/src/core/lib/iomgr/udp_server.cc
index 1bff4ae..61add3b 100644
--- a/src/core/lib/iomgr/udp_server.cc
+++ b/src/core/lib/iomgr/udp_server.cc
@@ -353,20 +353,23 @@
static void do_read(grpc_exec_ctx* exec_ctx, void* arg, grpc_error* error) {
grpc_udp_listener* sp = reinterpret_cast<grpc_udp_listener*>(arg);
GPR_ASSERT(sp->read_cb && error == GRPC_ERROR_NONE);
- // TODO(danzh): the reason we hold server->mu here is merely to prevent fd
- // shutdown while we are reading. However, it blocks do_write(). Switch to
- // read lock if available.
+ /* TODO: the reason we hold server->mu here is merely to prevent fd
+ * shutdown while we are reading. However, it blocks do_write(). Switch to
+ * read lock if available.
+ * */
gpr_mu_lock(&sp->server->mu);
/* Tell the registered callback that data is available to read. */
if (!sp->already_shutdown &&
sp->read_cb(exec_ctx, sp->emfd, sp->server->user_data)) {
- // There maybe more packets to read. Schedule
- // read_more_cb_ closure to run after finishing this event loop.
+ /* There maybe more packets to read. Schedule read_more_cb_ closure to run
+ * after finishing this event loop.
+ * */
GRPC_CLOSURE_SCHED(exec_ctx, &sp->do_read_closure, GRPC_ERROR_NONE);
} else {
- // Finish reading all the packets, re-arm the notification event so we can
- // get another chance to read.
- // Or fd already shutdown, re-arm to get a notification with shutdown error.
+ /* Finish reading all the packets, re-arm the notification event so we can
+ * get another chance to read. Or fd already shutdown, re-arm to get a
+ * notification with shutdown error.
+ * */
grpc_fd_notify_on_read(exec_ctx, sp->emfd, &sp->read_closure);
}
gpr_mu_unlock(&sp->server->mu);
@@ -376,8 +379,8 @@
static void on_read(grpc_exec_ctx* exec_ctx, void* arg, grpc_error* error) {
grpc_udp_listener* sp = (grpc_udp_listener*)arg;
- gpr_mu_lock(&sp->server->mu);
if (error != GRPC_ERROR_NONE) {
+ gpr_mu_lock(&sp->server->mu);
if (0 == --sp->server->active_ports && sp->server->shutdown) {
gpr_mu_unlock(&sp->server->mu);
deactivated_all_ports(exec_ctx, sp->server);
@@ -386,12 +389,24 @@
}
return;
}
-
- // Schedule actual read in another thread.
- GRPC_CLOSURE_INIT(&sp->do_read_closure, do_read, arg,
- grpc_executor_scheduler(GRPC_EXECUTOR_LONG));
- GRPC_CLOSURE_SCHED(exec_ctx, &sp->do_read_closure, GRPC_ERROR_NONE);
- gpr_mu_unlock(&sp->server->mu);
+ /* Read once. If there is more data to read, off load the work to another
+ * thread to finish.
+ * */
+ GPR_ASSERT(sp->read_cb);
+ if (sp->read_cb(exec_ctx, sp->emfd, sp->server->user_data)) {
+ /* There maybe more packets to read. Schedule read_more_cb_ closure to run
+ * after finishing this event loop.
+ * */
+ GRPC_CLOSURE_INIT(&sp->do_read_closure, do_read, arg,
+ grpc_executor_scheduler(GRPC_EXECUTOR_LONG));
+ GRPC_CLOSURE_SCHED(exec_ctx, &sp->do_read_closure, GRPC_ERROR_NONE);
+ } else {
+ /* Finish reading all the packets, re-arm the notification event so we can
+ * get another chance to read. Or fd already shutdown, re-arm to get a
+ * notification with shutdown error.
+ * */
+ grpc_fd_notify_on_read(exec_ctx, sp->emfd, &sp->read_closure);
+ }
}
// Wrapper of grpc_fd_notify_on_write() with a grpc_closure callback interface.