static void listener_handler (struct instance *o) { ASSERT(!o->dying) BReactor *reactor = o->i->params->iparams->reactor; BPendingGroup *pg = BReactor_PendingGroup(reactor); struct connection *c = malloc(sizeof(*c)); if (!c) { ModuleLog(o->i, BLOG_ERROR, "malloc failed"); goto fail0; } c->inst = o; LinkedList0_Prepend(&o->connections_list, &c->connections_list_node); if (!BConnection_Init(&c->con, BConnection_source_listener(&o->listener, &c->addr), reactor, c, (BConnection_handler)connection_con_handler)) { ModuleLog(o->i, BLOG_ERROR, "BConnection_Init failed"); goto fail1; } BConnection_SendAsync_Init(&c->con); BConnection_RecvAsync_Init(&c->con); StreamPassInterface *con_send_if = BConnection_SendAsync_GetIf(&c->con); StreamRecvInterface *con_recv_if = BConnection_RecvAsync_GetIf(&c->con); PacketPassInterface_Init(&c->recv_if, RECV_MTU, (PacketPassInterface_handler_send)connection_recv_if_handler_send, c, pg); if (!PacketProtoDecoder_Init(&c->recv_decoder, con_recv_if, &c->recv_if, pg, c, (PacketProtoDecoder_handler_error)connection_recv_decoder_handler_error)) { ModuleLog(o->i, BLOG_ERROR, "PacketProtoDecoder_Init failed"); goto fail2; } PacketStreamSender_Init(&c->send_pss, con_send_if, PACKETPROTO_ENCLEN(SEND_MTU), pg); PacketPassFifoQueue_Init(&c->send_queue, PacketStreamSender_GetInput(&c->send_pss), pg); LinkedList0_Init(&c->requests_list); LinkedList0_Init(&c->replies_list); c->state = CONNECTION_STATE_RUNNING; ModuleLog(o->i, BLOG_INFO, "connection initialized"); return; fail2: PacketPassInterface_Free(&c->recv_if); BConnection_RecvAsync_Free(&c->con); BConnection_SendAsync_Free(&c->con); BConnection_Free(&c->con); fail1: LinkedList0_Remove(&o->connections_list, &c->connections_list_node); free(c); fail0: return; }
static void connection_free (struct connection *c) { struct instance *o = c->inst; ASSERT(c->state == CONNECTION_STATE_TERMINATING) ASSERT(LinkedList0_IsEmpty(&c->requests_list)) ASSERT(LinkedList0_IsEmpty(&c->replies_list)) LinkedList0_Remove(&o->connections_list, &c->connections_list_node); free(c); }
static void instance_free (struct instance *o) { ASSERT(LinkedList1_IsEmpty(&o->users)) // break any rdownups LinkedList0Node *ln; while (ln = LinkedList0_GetFirst(&o->rdownups_list)) { struct rdownup_instance *rdu = UPPER_OBJECT(ln, struct rdownup_instance, rdownups_list_node); ASSERT(rdu->blocker == o) LinkedList0_Remove(&o->rdownups_list, &rdu->rdownups_list_node); rdu->blocker = NULL; } NCDModuleInst_Backend_Dead(o->i); }
static void value_delete (struct value *v) { if (v->parent) { switch (v->parent->type) { case NCDVALUE_LIST: { value_list_remove(v->parent, v); } break; case NCDVALUE_MAP: { value_map_remove(v->parent, v); } break; default: ASSERT(0); } } LinkedList0Node *ln; while (ln = LinkedList0_GetFirst(&v->refs_list)) { struct instance *inst = UPPER_OBJECT(ln, struct instance, refs_list_node); ASSERT(inst->v == v) LinkedList0_Remove(&v->refs_list, &inst->refs_list_node); inst->v = NULL; } switch (v->type) { case NCDVALUE_STRING: { free(v->string.string); } break; case NCDVALUE_LIST: { while (value_list_len(v) > 0) { struct value *ev = value_list_at(v, 0); value_delete(ev); } } break; case NCDVALUE_MAP: { while (value_map_len(v) > 0) { struct value *ev = value_map_at(v, 0); value_delete(ev); } } break; default: ASSERT(0); } free(v); }
static void callrefhere_func_die (void *vo) { struct callrefhere_instance *o = vo; NCDModuleInst *i = o->i; // disconnect calls while (!LinkedList0_IsEmpty(&o->calls_list)) { struct instance *inst = UPPER_OBJECT(LinkedList0_GetFirst(&o->calls_list), struct instance, calls_list_node); ASSERT(inst->crh == o) LinkedList0_Remove(&o->calls_list, &inst->calls_list_node); inst->crh = NULL; } // free instance free(o); NCDModuleInst_Backend_Dead(i); }
void instance_free (struct instance *o) { NCDModuleInst *i = o->i; if (o->state != STATE_NONE) { // remove from callrefhere's calls list if (o->crh) { LinkedList0_Remove(&o->crh->calls_list, &o->calls_list_node); } // free process NCDModuleProcess_Free(&o->process); } // free instance free(o); NCDModuleInst_Backend_Dead(i); }