static void cc_start_transport_op(grpc_exec_ctx *exec_ctx, grpc_channel_element *elem, grpc_transport_op *op) { channel_data *chand = elem->channel_data; grpc_exec_ctx_sched(exec_ctx, op->on_consumed, GRPC_ERROR_NONE, NULL); GPR_ASSERT(op->set_accept_stream == false); if (op->bind_pollset != NULL) { grpc_pollset_set_add_pollset(exec_ctx, chand->interested_parties, op->bind_pollset); } gpr_mu_lock(&chand->mu); if (op->on_connectivity_state_change != NULL) { grpc_connectivity_state_notify_on_state_change( exec_ctx, &chand->state_tracker, op->connectivity_state, op->on_connectivity_state_change); op->on_connectivity_state_change = NULL; op->connectivity_state = NULL; } if (op->send_ping != NULL) { if (chand->lb_policy == NULL) { grpc_exec_ctx_sched(exec_ctx, op->send_ping, GRPC_ERROR_CREATE("Ping with no load balancing"), NULL); } else { grpc_lb_policy_ping_one(exec_ctx, chand->lb_policy, op->send_ping); op->bind_pollset = NULL; } op->send_ping = NULL; } if (op->disconnect_with_error != GRPC_ERROR_NONE) { if (chand->resolver != NULL) { set_channel_connectivity_state_locked( exec_ctx, chand, GRPC_CHANNEL_SHUTDOWN, GRPC_ERROR_REF(op->disconnect_with_error), "disconnect"); grpc_resolver_shutdown(exec_ctx, chand->resolver); GRPC_RESOLVER_UNREF(exec_ctx, chand->resolver, "channel"); chand->resolver = NULL; if (!chand->started_resolving) { grpc_closure_list_fail_all(&chand->waiting_for_config_closures, GRPC_ERROR_REF(op->disconnect_with_error)); grpc_exec_ctx_enqueue_list(exec_ctx, &chand->waiting_for_config_closures, NULL); } if (chand->lb_policy != NULL) { grpc_pollset_set_del_pollset_set(exec_ctx, chand->lb_policy->interested_parties, chand->interested_parties); GRPC_LB_POLICY_UNREF(exec_ctx, chand->lb_policy, "channel"); chand->lb_policy = NULL; } } GRPC_ERROR_UNREF(op->disconnect_with_error); } gpr_mu_unlock(&chand->mu); }
static void perform_transport_op(grpc_exec_ctx *exec_ctx, grpc_transport *gt, grpc_transport_op *op) { inproc_transport *t = (inproc_transport *)gt; INPROC_LOG(GPR_DEBUG, "perform_transport_op %p %p", t, op); gpr_mu_lock(&t->mu->mu); if (op->on_connectivity_state_change) { grpc_connectivity_state_notify_on_state_change( exec_ctx, &t->connectivity, op->connectivity_state, op->on_connectivity_state_change); } if (op->set_accept_stream) { t->accept_stream_cb = op->set_accept_stream_fn; t->accept_stream_data = op->set_accept_stream_user_data; } if (op->on_consumed) { GRPC_CLOSURE_SCHED(exec_ctx, op->on_consumed, GRPC_ERROR_NONE); } bool do_close = false; if (op->goaway_error != GRPC_ERROR_NONE) { do_close = true; GRPC_ERROR_UNREF(op->goaway_error); } if (op->disconnect_with_error != GRPC_ERROR_NONE) { do_close = true; GRPC_ERROR_UNREF(op->disconnect_with_error); } if (do_close) { close_transport_locked(exec_ctx, t); } gpr_mu_unlock(&t->mu->mu); }
void pf_notify_on_state_change(grpc_exec_ctx *exec_ctx, grpc_lb_policy *pol, grpc_connectivity_state *current, grpc_closure *notify) { pick_first_lb_policy *p = (pick_first_lb_policy *)pol; gpr_mu_lock(&p->mu); grpc_connectivity_state_notify_on_state_change(exec_ctx, &p->state_tracker, current, notify); gpr_mu_unlock(&p->mu); }
void grpc_client_uchannel_watch_connectivity_state( grpc_exec_ctx *exec_ctx, grpc_channel_element *elem, grpc_pollset *pollset, grpc_connectivity_state *state, grpc_closure *on_complete) { channel_data *chand = elem->channel_data; gpr_mu_lock(&chand->mu_state); grpc_connectivity_state_notify_on_state_change( exec_ctx, &chand->state_tracker, state, on_complete); gpr_mu_unlock(&chand->mu_state); }
static void rr_notify_on_state_change(grpc_exec_ctx *exec_ctx, grpc_lb_policy *pol, grpc_connectivity_state *current, grpc_closure *notify) { round_robin_lb_policy *p = (round_robin_lb_policy *)pol; gpr_mu_lock(&p->mu); grpc_connectivity_state_notify_on_state_change(exec_ctx, &p->state_tracker, current, notify); gpr_mu_unlock(&p->mu); }
static void perform_transport_op(grpc_transport *gt, grpc_transport_op *op) { grpc_chttp2_transport *t = (grpc_chttp2_transport *)gt; int close_transport = 0; lock(t); if (op->on_consumed) { grpc_chttp2_schedule_closure(&t->global, op->on_consumed, 1); } if (op->on_connectivity_state_change) { grpc_connectivity_state_notify_on_state_change( &t->channel_callback.state_tracker, op->connectivity_state, op->on_connectivity_state_change); } if (op->send_goaway) { t->global.sent_goaway = 1; grpc_chttp2_goaway_append( t->global.last_incoming_stream_id, grpc_chttp2_grpc_status_to_http2_error(op->goaway_status), gpr_slice_ref(*op->goaway_message), &t->global.qbuf); close_transport = !grpc_chttp2_has_streams(t); } if (op->set_accept_stream != NULL) { t->channel_callback.accept_stream = op->set_accept_stream; t->channel_callback.accept_stream_user_data = op->set_accept_stream_user_data; } if (op->bind_pollset) { add_to_pollset_locked(t, op->bind_pollset); } if (op->bind_pollset_set) { add_to_pollset_set_locked(t, op->bind_pollset_set); } if (op->send_ping) { send_ping_locked(t, op->send_ping); } if (op->disconnect) { close_transport_locked(t); } unlock(t); if (close_transport) { lock(t); close_transport_locked(t); unlock(t); } }
static void cc_start_transport_op(grpc_exec_ctx *exec_ctx, grpc_channel_element *elem, grpc_transport_op *op) { channel_data *chand = elem->channel_data; grpc_resolver *destroy_resolver = NULL; grpc_exec_ctx_enqueue(exec_ctx, op->on_consumed, true, NULL); GPR_ASSERT(op->set_accept_stream == NULL); if (op->bind_pollset != NULL) { grpc_pollset_set_add_pollset(exec_ctx, &chand->interested_parties, op->bind_pollset); } gpr_mu_lock(&chand->mu_config); if (op->on_connectivity_state_change != NULL) { grpc_connectivity_state_notify_on_state_change( exec_ctx, &chand->state_tracker, op->connectivity_state, op->on_connectivity_state_change); op->on_connectivity_state_change = NULL; op->connectivity_state = NULL; } if (op->send_ping != NULL) { if (chand->lb_policy == NULL) { grpc_exec_ctx_enqueue(exec_ctx, op->send_ping, false, NULL); } else { grpc_lb_policy_ping_one(exec_ctx, chand->lb_policy, op->send_ping); op->bind_pollset = NULL; } op->send_ping = NULL; } if (op->disconnect && chand->resolver != NULL) { grpc_connectivity_state_set(exec_ctx, &chand->state_tracker, GRPC_CHANNEL_FATAL_FAILURE, "disconnect"); destroy_resolver = chand->resolver; chand->resolver = NULL; if (chand->lb_policy != NULL) { grpc_pollset_set_del_pollset_set(exec_ctx, &chand->lb_policy->interested_parties, &chand->interested_parties); GRPC_LB_POLICY_UNREF(exec_ctx, chand->lb_policy, "channel"); chand->lb_policy = NULL; } } gpr_mu_unlock(&chand->mu_config); if (destroy_resolver) { grpc_resolver_shutdown(exec_ctx, destroy_resolver); GRPC_RESOLVER_UNREF(exec_ctx, destroy_resolver, "channel"); } }
static void test_subscribe_then_unsubscribe(void) { grpc_connectivity_state_tracker tracker; grpc_closure *closure = grpc_closure_create(must_fail, THE_ARG); grpc_connectivity_state state = GRPC_CHANNEL_IDLE; grpc_exec_ctx exec_ctx = GRPC_EXEC_CTX_INIT; gpr_log(GPR_DEBUG, "test_subscribe_then_unsubscribe"); g_counter = 0; grpc_connectivity_state_init(&tracker, GRPC_CHANNEL_IDLE, "xxx"); GPR_ASSERT(grpc_connectivity_state_notify_on_state_change(&exec_ctx, &tracker, &state, closure)); grpc_exec_ctx_flush(&exec_ctx); GPR_ASSERT(state == GRPC_CHANNEL_IDLE); GPR_ASSERT(g_counter == 0); grpc_connectivity_state_notify_on_state_change(&exec_ctx, &tracker, NULL, closure); grpc_exec_ctx_flush(&exec_ctx); GPR_ASSERT(state == GRPC_CHANNEL_IDLE); GPR_ASSERT(g_counter == 1); grpc_connectivity_state_destroy(&exec_ctx, &tracker); grpc_exec_ctx_finish(&exec_ctx); }
void grpc_client_channel_watch_connectivity_state( grpc_exec_ctx *exec_ctx, grpc_channel_element *elem, grpc_pollset *pollset, grpc_connectivity_state *state, grpc_closure *on_complete) { channel_data *chand = elem->channel_data; external_connectivity_watcher *w = gpr_malloc(sizeof(*w)); w->chand = chand; w->pollset = pollset; w->on_complete = on_complete; grpc_pollset_set_add_pollset(exec_ctx, chand->interested_parties, pollset); grpc_closure_init(&w->my_closure, on_external_watch_complete, w); GRPC_CHANNEL_STACK_REF(w->chand->owning_stack, "external_connectivity_watcher"); gpr_mu_lock(&chand->mu); grpc_connectivity_state_notify_on_state_change( exec_ctx, &chand->state_tracker, state, &w->my_closure); gpr_mu_unlock(&chand->mu); }
static void cuc_start_transport_op(grpc_exec_ctx *exec_ctx, grpc_channel_element *elem, grpc_transport_op *op) { channel_data *chand = elem->channel_data; grpc_exec_ctx_enqueue(exec_ctx, op->on_consumed, true, NULL); GPR_ASSERT(op->set_accept_stream == false); GPR_ASSERT(op->bind_pollset == NULL); if (op->on_connectivity_state_change != NULL) { grpc_connectivity_state_notify_on_state_change( exec_ctx, &chand->state_tracker, op->connectivity_state, op->on_connectivity_state_change); op->on_connectivity_state_change = NULL; op->connectivity_state = NULL; } if (op->disconnect) { grpc_connectivity_state_set(exec_ctx, &chand->state_tracker, GRPC_CHANNEL_FATAL_FAILURE, "disconnect"); } }