Fix race in TCP connection

If the TCP client connection alarm triggers close to the connection
deadline (but succeeds), the alarm shuts down the endpoint underneath
the existing transport... which is very bad for its health.
pull/2353/head
Craig Tiller 10 years ago
parent b97b988052
commit 315feadd4a
  1. 7
      src/core/iomgr/tcp_client_posix.c

@ -114,6 +114,7 @@ static void on_writable(void *acp, int success) {
void (*cb)(void *arg, grpc_endpoint *tcp) = ac->cb; void (*cb)(void *arg, grpc_endpoint *tcp) = ac->cb;
void *cb_arg = ac->cb_arg; void *cb_arg = ac->cb_arg;
gpr_mu_lock(&ac->mu);
if (success) { if (success) {
do { do {
so_error_size = sizeof(so_error); so_error_size = sizeof(so_error);
@ -139,6 +140,7 @@ static void on_writable(void *acp, int success) {
opened too many network connections. The "easy" fix: opened too many network connections. The "easy" fix:
don't do that! */ don't do that! */
gpr_log(GPR_ERROR, "kernel out of buffers"); gpr_log(GPR_ERROR, "kernel out of buffers");
gpr_mu_unlock(&ac->mu);
grpc_fd_notify_on_write(ac->fd, &ac->write_closure); grpc_fd_notify_on_write(ac->fd, &ac->write_closure);
return; return;
} else { } else {
@ -165,10 +167,11 @@ static void on_writable(void *acp, int success) {
abort(); abort();
finish: finish:
gpr_mu_lock(&ac->mu); if (ep == NULL) {
if (!ep) {
grpc_pollset_set_del_fd(ac->interested_parties, ac->fd); grpc_pollset_set_del_fd(ac->interested_parties, ac->fd);
grpc_fd_orphan(ac->fd, NULL, "tcp_client_orphan"); grpc_fd_orphan(ac->fd, NULL, "tcp_client_orphan");
} else {
ac->fd = NULL;
} }
done = (--ac->refs == 0); done = (--ac->refs == 0);
gpr_mu_unlock(&ac->mu); gpr_mu_unlock(&ac->mu);

Loading…
Cancel
Save