diff options
author | Craig Tiller <ctiller@google.com> | 2015-05-13 12:48:36 -0700 |
---|---|---|
committer | Craig Tiller <ctiller@google.com> | 2015-05-13 12:48:36 -0700 |
commit | 6e51180b984c42f0b00516a6609d1d90e183b9b9 (patch) | |
tree | 16cf3f5eb3e0a3e98a0cc79b403d01374c0d3e82 /src/core | |
parent | 6f05140a2680130e32220f3bf47b61f9b4760b11 (diff) |
Properly manage interest set for waiting calls
Diffstat (limited to 'src/core')
-rw-r--r-- | src/core/channel/client_channel.c | 6 | ||||
-rw-r--r-- | src/core/channel/client_setup.c | 15 | ||||
-rw-r--r-- | src/core/transport/transport.c | 4 | ||||
-rw-r--r-- | src/core/transport/transport.h | 2 |
4 files changed, 25 insertions, 2 deletions
diff --git a/src/core/channel/client_channel.c b/src/core/channel/client_channel.c index 26b6841f24..9f23ed3d71 100644 --- a/src/core/channel/client_channel.c +++ b/src/core/channel/client_channel.c @@ -132,9 +132,11 @@ static void remove_waiting_child(channel_data *chand, call_data *calld) { size_t new_count; size_t i; for (i = 0, new_count = 0; i < chand->waiting_child_count; i++) { - if (chand->waiting_children[i] == calld) continue; + if (chand->waiting_children[i] == calld) { + grpc_transport_setup_del_interested_party(chand->transport_setup, calld->s.waiting_op.bind_pollset); + continue; + } chand->waiting_children[new_count++] = chand->waiting_children[i]; - abort(); /* what to do about waiting_pollsets */ } GPR_ASSERT(new_count == chand->waiting_child_count - 1 || new_count == chand->waiting_child_count); diff --git a/src/core/channel/client_setup.c b/src/core/channel/client_setup.c index d3d31a9ffb..e2bd7ef52e 100644 --- a/src/core/channel/client_setup.c +++ b/src/core/channel/client_setup.c @@ -134,6 +134,20 @@ static void setup_add_interested_party(grpc_transport_setup *sp, grpc_pollset *p gpr_mu_unlock(&s->mu); } +static void setup_del_interested_party(grpc_transport_setup *sp, grpc_pollset *pollset) { + grpc_client_setup *s = (grpc_client_setup *)sp; + + gpr_mu_lock(&s->mu); + if (!s->active_request) { + gpr_mu_unlock(&s->mu); + return; + } + + grpc_pollset_set_del_pollset(&s->active_request->interested_parties, pollset); + + gpr_mu_unlock(&s->mu); +} + /* cancel handshaking: cancel all requests, and shutdown (the caller promises not to initiate again) */ static void setup_cancel(grpc_transport_setup *sp) { @@ -184,6 +198,7 @@ void grpc_client_setup_cb_end(grpc_client_setup_request *r) { /* vtable for transport setup */ static const grpc_transport_setup_vtable setup_vtable = {setup_initiate, setup_add_interested_party, + setup_del_interested_party, setup_cancel}; void grpc_client_setup_create_and_attach( diff --git a/src/core/transport/transport.c b/src/core/transport/transport.c index 0bceeabcc3..b81950d303 100644 --- a/src/core/transport/transport.c +++ b/src/core/transport/transport.c @@ -90,6 +90,10 @@ void grpc_transport_setup_add_interested_party(grpc_transport_setup *setup, grpc setup->vtable->add_interested_party(setup, pollset); } +void grpc_transport_setup_del_interested_party(grpc_transport_setup *setup, grpc_pollset *pollset) { + setup->vtable->del_interested_party(setup, pollset); +} + void grpc_transport_op_finish_with_failure(grpc_transport_op *op) { if (op->send_ops) { op->on_done_send(op->send_user_data, 0); diff --git a/src/core/transport/transport.h b/src/core/transport/transport.h index 5303cbee7d..4dcd4467e3 100644 --- a/src/core/transport/transport.h +++ b/src/core/transport/transport.h @@ -196,6 +196,7 @@ typedef struct grpc_transport_setup_vtable grpc_transport_setup_vtable; struct grpc_transport_setup_vtable { void (*initiate)(grpc_transport_setup *setup); void (*add_interested_party)(grpc_transport_setup *setup, grpc_pollset *pollset); + void (*del_interested_party)(grpc_transport_setup *setup, grpc_pollset *pollset); void (*cancel)(grpc_transport_setup *setup); }; @@ -214,6 +215,7 @@ struct grpc_transport_setup { void grpc_transport_setup_initiate(grpc_transport_setup *setup); void grpc_transport_setup_add_interested_party(grpc_transport_setup *setup, grpc_pollset *pollset); +void grpc_transport_setup_del_interested_party(grpc_transport_setup *setup, grpc_pollset *pollset); /* Cancel transport setup. After this returns, no new transports should be created, and all pending transport setup callbacks should be completed. |