// delete nodes depth-first void rbtDelete(NodeType **p, NodeType *sentinel) { if (*p == sentinel) return; rbtDelete(&(*p)->left, sentinel); rbtDelete(&(*p)->right, sentinel); free(*p); }
static int psmx2_domain_close(fid_t fid) { struct psmx2_fid_domain *domain; domain = container_of(fid, struct psmx2_fid_domain, util_domain.domain_fid.fid); FI_INFO(&psmx2_prov, FI_LOG_DOMAIN, "refcnt=%d\n", ofi_atomic_get32(&domain->util_domain.ref)); psmx2_domain_release(domain); if (ofi_domain_close(&domain->util_domain)) return 0; if (domain->progress_thread_enabled) psmx2_domain_stop_progress(domain); fastlock_destroy(&domain->sep_lock); fastlock_destroy(&domain->vl_lock); rbtDelete(domain->mr_map); fastlock_destroy(&domain->mr_lock); psmx2_trx_ctxt_free(domain->base_trx_ctxt); domain->fabric->active_domain = NULL; free(domain); psmx2_atomic_global_fini(); psmx2_am_global_fini(); return 0; }
static int psmx2_domain_close(fid_t fid) { struct psmx2_fid_domain *domain; domain = container_of(fid, struct psmx2_fid_domain, util_domain.domain_fid.fid); FI_INFO(&psmx2_prov, FI_LOG_DOMAIN, "refcnt=%d\n", ofi_atomic_get32(&domain->util_domain.ref)); if (ofi_domain_close(&domain->util_domain)) return 0; if (domain->progress_thread_enabled) psmx2_domain_stop_progress(domain); fastlock_destroy(&domain->sep_lock); fastlock_destroy(&domain->mr_lock); rbtDelete(domain->mr_map); psmx2_lock(&domain->fabric->domain_lock, 1); dlist_remove(&domain->entry); psmx2_unlock(&domain->fabric->domain_lock, 1); psmx2_fabric_release(domain->fabric); free(domain); return 0; }
void ofi_mr_close(struct ofi_util_mr *in_mr_h) { if (!in_mr_h) { FI_WARN(&core_prov, FI_LOG_MR, "util mr_close: received NULL input\n"); return; } rbtDelete(in_mr_h->map_handle); free(in_mr_h); }
static int psmx_domain_close(fid_t fid) { struct psmx_fid_domain *domain; int err; domain = container_of(fid, struct psmx_fid_domain, util_domain.domain_fid.fid); FI_INFO(&psmx_prov, FI_LOG_DOMAIN, "refcnt=%d\n", ofi_atomic_get32(&domain->util_domain.ref)); psmx_domain_release(domain); if (ofi_domain_close(&domain->util_domain)) return 0; if (domain->progress_thread_enabled) psmx_domain_stop_progress(domain); if (domain->am_initialized) psmx_am_fini(domain); fastlock_destroy(&domain->poll_lock); rbtDelete(domain->mr_map); fastlock_destroy(&domain->mr_lock); #if 0 /* AM messages could arrive after MQ is finalized, causing segfault * when trying to dereference the MQ pointer. There is no mechanism * to properly shutdown AM. The workaround is to keep MQ valid. */ psm_mq_finalize(domain->psm_mq); #endif /* workaround for: * Assertion failure at psm_ep.c:1059: ep->mctxt_master == ep */ sleep(psmx_env.delay); if (psmx_env.timeout) err = psm_ep_close(domain->psm_ep, PSM_EP_CLOSE_GRACEFUL, (int64_t) psmx_env.timeout * 1000000000LL); else err = PSM_EP_CLOSE_TIMEOUT; if (err != PSM_OK) psm_ep_close(domain->psm_ep, PSM_EP_CLOSE_FORCE, 0); domain->fabric->active_domain = NULL; free(domain); return 0; }
static void build_hosttree(void) { static int hosttree_exists = 0; namelist_t *walk; RbtStatus status; char *tstr; if (hosttree_exists) { rbtDelete(rbhosts); rbtDelete(rbclients); } rbhosts = rbtNew(name_compare); rbclients = rbtNew(name_compare); hosttree_exists = 1; for (walk = namehead; (walk); walk = walk->next) { status = rbtInsert(rbhosts, walk->bbhostname, walk); if (walk->clientname) rbtInsert(rbclients, walk->clientname, walk); switch (status) { case RBT_STATUS_OK: case RBT_STATUS_DUPLICATE_KEY: break; case RBT_STATUS_MEM_EXHAUSTED: errprintf("loadhosts:build_hosttree - insert into tree failed (out of memory)\n"); break; default: errprintf("loadhosts:build_hosttree - insert into tree failed code %d\n", status); break; } tstr = bbh_item(walk, BBH_NOTBEFORE); walk->notbefore = (tstr ? timestr2timet(tstr) : 0); if (walk->notbefore == -1) walk->notbefore = 0; tstr = bbh_item(walk, BBH_NOTAFTER); walk->notafter = (tstr ? timestr2timet(tstr) : INT_MAX); if (walk->notafter == -1) walk->notafter = INT_MAX; } }
static int sock_dom_close(struct fid *fid) { struct sock_domain *dom; dom = container_of(fid, struct sock_domain, dom_fid.fid); if (atomic_get(&dom->ref)) return -FI_EBUSY; sock_pe_finalize(dom->pe); fastlock_destroy(&dom->lock); rbtDelete(dom->mr_heap); sock_dom_remove_from_list(dom); free(dom); return 0; }
void psmx2_domain_release(struct psmx2_fid_domain *domain) { int err; FI_INFO(&psmx2_prov, FI_LOG_DOMAIN, "refcnt=%d\n", domain->refcnt); if (--domain->refcnt > 0) return; if (domain->progress_thread_enabled) psmx2_domain_stop_progress(domain); psmx2_am_fini(domain); fastlock_destroy(&domain->poll_lock); fastlock_destroy(&domain->vl_lock); rbtDelete(domain->mr_map); fastlock_destroy(&domain->mr_lock); #if 0 /* AM messages could arrive after MQ is finalized, causing segfault * when trying to dereference the MQ pointer. There is no mechanism * to properly shutdown AM. The workaround is to keep MQ valid. */ psm2_mq_finalize(domain->psm2_mq); #endif /* workaround for: * Assertion failure at psm2_ep.c:1059: ep->mctxt_master == ep */ sleep(psmx2_env.delay); if (psmx2_env.timeout) err = psm2_ep_close(domain->psm2_ep, PSM2_EP_CLOSE_GRACEFUL, (int64_t) psmx2_env.timeout * 1000000000LL); else err = PSM2_EP_CLOSE_TIMEOUT; if (err != PSM2_OK) psm2_ep_close(domain->psm2_ep, PSM2_EP_CLOSE_FORCE, 0); domain->fabric->active_domain = NULL; psmx2_fabric_release(domain->fabric); free(domain); }
void generate_critpage(FILE *output, char *hfprefix) { RbtIterator hhandle; int color = COL_GREEN; int maxprio = 0; /* Determine background color and max. priority */ for (hhandle = rbtBegin(rbstate); (hhandle != rbtEnd(rbstate)); hhandle = rbtNext(rbstate, hhandle)) { void *k1, *k2; hstatus_t *itm; rbtKeyValue(rbstate, hhandle, &k1, &k2); itm = (hstatus_t *)k2; if (itm->color > color) color = itm->color; if (itm->config->priority > maxprio) maxprio = itm->config->priority; } headfoot(output, hfprefix, "", "header", color); fprintf(output, "<center>\n"); if (color != COL_GREEN) { RbtHandle rbcolumns; int prio; rbcolumns = columnlist(rbstate); fprintf(output, "<TABLE BORDER=0 CELLPADDING=4 SUMMARY=\"Critical status display\">\n"); print_colheaders(output, rbcolumns); for (prio = 1; (prio <= maxprio); prio++) { print_oneprio(output, rbstate, rbcolumns, prio); } fprintf(output, "</TABLE>\n"); rbtDelete(rbcolumns); } else { /* "All Monitored Systems OK */ fprintf(output, "%s", xgetenv("XYMONALLOKTEXT")); } fprintf(output, "</center>\n"); headfoot(output, hfprefix, "", "footer", color); }
void ofi_mr_map_close(struct ofi_mr_map *map) { rbtDelete(map->rbtree); }
static int psmx2_domain_init(struct psmx2_fid_domain *domain, struct psmx2_src_name *src_addr) { int err; psmx2_am_global_init(); psmx2_atomic_global_init(); domain->base_trx_ctxt = psmx2_trx_ctxt_alloc(domain, src_addr, -1); if (!domain->base_trx_ctxt) return -FI_ENODEV; err = fastlock_init(&domain->mr_lock); if (err) { FI_WARN(&psmx2_prov, FI_LOG_CORE, "fastlock_init(mr_lock) returns %d\n", err); goto err_out_free_trx_ctxt; } domain->mr_map = rbtNew(&psmx2_key_compare); if (!domain->mr_map) { FI_WARN(&psmx2_prov, FI_LOG_CORE, "rbtNew failed\n"); goto err_out_destroy_mr_lock; } domain->mr_reserved_key = 1; err = fastlock_init(&domain->vl_lock); if (err) { FI_WARN(&psmx2_prov, FI_LOG_CORE, "fastlock_init(vl_lock) returns %d\n", err); goto err_out_delete_mr_map; } memset(domain->vl_map, 0, sizeof(domain->vl_map)); domain->vl_alloc = 0; ofi_atomic_initialize32(&domain->sep_cnt, 0); fastlock_init(&domain->sep_lock); dlist_init(&domain->sep_list); dlist_init(&domain->trx_ctxt_list); fastlock_init(&domain->trx_ctxt_lock); dlist_insert_before(&domain->base_trx_ctxt->entry, &domain->trx_ctxt_list); /* Set active domain before psmx2_domain_enable_ep() installs the * AM handlers to ensure that psmx2_active_fabric->active_domain * is always non-NULL inside the handlers. Notice that the vlaue * active_domain becomes NULL again only when the domain is closed. * At that time the AM handlers are gone with the PSM endpoint. */ domain->fabric->active_domain = domain; if (psmx2_domain_enable_ep(domain, NULL) < 0) goto err_out_reset_active_domain; if (domain->progress_thread_enabled) psmx2_domain_start_progress(domain); psmx2_am_init(domain->base_trx_ctxt); return 0; err_out_reset_active_domain: domain->fabric->active_domain = NULL; fastlock_destroy(&domain->vl_lock); err_out_delete_mr_map: rbtDelete(domain->mr_map); err_out_destroy_mr_lock: fastlock_destroy(&domain->mr_lock); err_out_free_trx_ctxt: psmx2_trx_ctxt_free(domain->base_trx_ctxt); return err; }
int load_nkconfig(char *fn) { static void *configfiles = NULL; static int firsttime = 1; FILE *fd; strbuffer_t *inbuf; /* Setup the default configuration filename */ if (!fn) { if (!defaultfn) { char *bbhome = xgetenv("BBHOME"); defaultfn = (char *)malloc(strlen(bbhome) + strlen(DEFAULTCONFIG) + 2); sprintf(defaultfn, "%s/%s", bbhome, DEFAULTCONFIG); } fn = defaultfn; } if (configfn) xfree(configfn); configfn = strdup(fn); /* First check if there were no modifications at all */ if (configfiles) { if (!stackfmodified(configfiles)){ dbgprintf("No files modified, skipping reload of %s\n", fn); return 0; } else { stackfclist(&configfiles); configfiles = NULL; } } if (!firsttime) { /* Clean up existing datatree */ RbtHandle handle; void *k1, *k2; for (handle = rbtBegin(rbconf); (handle != rbtEnd(rbconf)); handle = rbtNext(rbconf, handle)) { rbtKeyValue(rbconf, handle, &k1, &k2); flushrec(k1, k2); } rbtDelete(rbconf); } firsttime = 0; rbconf = rbtNew(name_compare); fd = stackfopen(fn, "r", &configfiles); if (fd == NULL) return 1; inbuf = newstrbuffer(0); while (stackfgets(inbuf, NULL)) { /* Full record : Host service START END TIMESPEC TTPrio TTGroup TTExtra */ /* Clone record: Host =HOST */ char *ehost, *eservice, *estart, *eend, *etime, *ttgroup, *ttextra, *updinfo; int ttprio = 0; nkconf_t *newitem; RbtStatus status; int idx = 0; ehost = gettok(STRBUF(inbuf), "|\n"); if (!ehost) continue; eservice = gettok(NULL, "|\n"); if (!eservice) continue; if (*eservice == '=') { char *key = (char *)malloc(strlen(ehost) + 2); char *pointsto = strdup(eservice+1); sprintf(key, "%s=", ehost); status = rbtInsert(rbconf, key, pointsto); } else { estart = gettok(NULL, "|\n"); if (!estart) continue; eend = gettok(NULL, "|\n"); if (!eend) continue; etime = gettok(NULL, "|\n"); if (!etime) continue; ttprio = atoi(gettok(NULL, "|\n")); if (ttprio == 0) continue; ttgroup = gettok(NULL, "|\n"); ttextra = gettok(NULL, "|\n"); updinfo = gettok(NULL, "|\n"); newitem = (nkconf_t *)malloc(sizeof(nkconf_t)); newitem->key = (char *)malloc(strlen(ehost) + strlen(eservice) + 15); sprintf(newitem->key, "%s|%s", ehost, eservice); newitem->starttime= ((estart && *estart) ? atoi(estart) : 0); newitem->endtime = ((eend && *eend) ? atoi(eend) : 0); newitem->nktime = ((etime && *etime) ? strdup(etime) : NULL); newitem->priority = ttprio; newitem->ttgroup = strdup(ttgroup); newitem->ttextra = strdup(ttextra); newitem->updinfo = strdup(updinfo); status = rbtInsert(rbconf, newitem->key, newitem); while (status == RBT_STATUS_DUPLICATE_KEY) { idx++; sprintf(newitem->key, "%s|%s|%d", ehost, eservice, idx); status = rbtInsert(rbconf, newitem->key, newitem); } } } stackfclose(fd); freestrbuffer(inbuf); if (debug) { RbtHandle handle; handle = rbtBegin(rbconf); while (handle != rbtEnd(rbconf)) { void *k1, *k2; rbtKeyValue(rbconf, handle, &k1, &k2); printf("%s\n", (char *)k1); handle = rbtNext(rbconf, handle); } } return 0; }
static void util_ns_map_fini(struct util_ns *ns) { rbtDelete(ns->ns_map); }
static void ofi_mr_rbt_storage_destroy(struct ofi_mr_storage *storage) { rbtDelete((RbtHandle)storage->storage); }
int psmx2_domain_open(struct fid_fabric *fabric, struct fi_info *info, struct fid_domain **domain, void *context) { struct psmx2_fid_fabric *fabric_priv; struct psmx2_fid_domain *domain_priv; struct psm2_ep_open_opts opts; int err; FI_INFO(&psmx2_prov, FI_LOG_DOMAIN, "\n"); fabric_priv = container_of(fabric, struct psmx2_fid_fabric, fabric); psmx2_fabric_acquire(fabric_priv); if (fabric_priv->active_domain) { psmx2_domain_acquire(fabric_priv->active_domain); *domain = &fabric_priv->active_domain->domain; return 0; } if (!info->domain_attr->name || strcmp(info->domain_attr->name, PSMX2_DOMAIN_NAME)) { err = -FI_EINVAL; goto err_out; } domain_priv = (struct psmx2_fid_domain *) calloc(1, sizeof *domain_priv); if (!domain_priv) { err = -FI_ENOMEM; goto err_out; } domain_priv->domain.fid.fclass = FI_CLASS_DOMAIN; domain_priv->domain.fid.context = context; domain_priv->domain.fid.ops = &psmx2_fi_ops; domain_priv->domain.ops = &psmx2_domain_ops; domain_priv->domain.mr = &psmx2_mr_ops; domain_priv->mr_mode = info->domain_attr->mr_mode; domain_priv->mode = info->mode; domain_priv->caps = info->caps; domain_priv->fabric = fabric_priv; domain_priv->progress_thread_enabled = (info->domain_attr->data_progress == FI_PROGRESS_AUTO); psm2_ep_open_opts_get_defaults(&opts); FI_INFO(&psmx2_prov, FI_LOG_CORE, "uuid: %s\n", psmx2_uuid_to_string(fabric_priv->uuid)); err = psm2_ep_open(fabric_priv->uuid, &opts, &domain_priv->psm2_ep, &domain_priv->psm2_epid); if (err != PSM2_OK) { FI_WARN(&psmx2_prov, FI_LOG_CORE, "psm2_ep_open returns %d, errno=%d\n", err, errno); err = psmx2_errno(err); goto err_out_free_domain; } FI_INFO(&psmx2_prov, FI_LOG_CORE, "epid: 0x%016lx\n", domain_priv->psm2_epid); err = psm2_mq_init(domain_priv->psm2_ep, PSM2_MQ_ORDERMASK_ALL, NULL, 0, &domain_priv->psm2_mq); if (err != PSM2_OK) { FI_WARN(&psmx2_prov, FI_LOG_CORE, "psm2_mq_init returns %d, errno=%d\n", err, errno); err = psmx2_errno(err); goto err_out_close_ep; } err = fastlock_init(&domain_priv->mr_lock); if (err) { FI_WARN(&psmx2_prov, FI_LOG_CORE, "fastlock_init(mr_lock) returns %d\n", err); goto err_out_finalize_mq; } domain_priv->mr_map = rbtNew(&psmx2_key_compare); if (!domain_priv->mr_map) { FI_WARN(&psmx2_prov, FI_LOG_CORE, "rbtNew failed\n"); goto err_out_destroy_mr_lock; } domain_priv->mr_reserved_key = 1; err = fastlock_init(&domain_priv->vl_lock); if (err) { FI_WARN(&psmx2_prov, FI_LOG_CORE, "fastlock_init(vl_lock) returns %d\n", err); goto err_out_delete_mr_map; } memset(domain_priv->vl_map, 0, sizeof(domain_priv->vl_map)); domain_priv->vl_alloc = 0; err = fastlock_init(&domain_priv->poll_lock); if (err) { FI_WARN(&psmx2_prov, FI_LOG_CORE, "fastlock_init(poll_lock) returns %d\n", err); goto err_out_destroy_vl_lock; } /* Set active domain before psmx2_domain_enable_ep() installs the * AM handlers to ensure that psmx2_active_fabric->active_domain * is always non-NULL inside the handlers. Notice that the vlaue * active_domain becomes NULL again only when the domain is closed. * At that time the AM handlers are gone with the PSM endpoint. */ fabric_priv->active_domain = domain_priv; if (psmx2_domain_enable_ep(domain_priv, NULL) < 0) goto err_out_reset_active_domain; if (domain_priv->progress_thread_enabled) psmx2_domain_start_progress(domain_priv); domain_priv->refcnt = 1; *domain = &domain_priv->domain; return 0; err_out_reset_active_domain: fabric_priv->active_domain = NULL; fastlock_destroy(&domain_priv->poll_lock); err_out_destroy_vl_lock: fastlock_destroy(&domain_priv->vl_lock); err_out_delete_mr_map: rbtDelete(domain_priv->mr_map); err_out_destroy_mr_lock: fastlock_destroy(&domain_priv->mr_lock); err_out_finalize_mq: psm2_mq_finalize(domain_priv->psm2_mq); err_out_close_ep: if (psm2_ep_close(domain_priv->psm2_ep, PSM2_EP_CLOSE_GRACEFUL, (int64_t) psmx2_env.timeout * 1000000000LL) != PSM2_OK) psm2_ep_close(domain_priv->psm2_ep, PSM2_EP_CLOSE_FORCE, 0); err_out_free_domain: free(domain_priv); err_out: psmx2_fabric_release(fabric_priv); return err; }
static int psmx_domain_init(struct psmx_fid_domain *domain, struct psmx_src_name *src_addr) { struct psmx_fid_fabric *fabric = domain->fabric; struct psm_ep_open_opts opts; int err; psm_ep_open_opts_get_defaults(&opts); FI_INFO(&psmx_prov, FI_LOG_CORE, "uuid: %s\n", psmx_uuid_to_string(fabric->uuid)); if (src_addr) { opts.unit = src_addr->unit; opts.port = src_addr->port; FI_INFO(&psmx_prov, FI_LOG_CORE, "ep_open_opts: unit=%d port=%u\n", opts.unit, opts.port); } err = psm_ep_open(fabric->uuid, &opts, &domain->psm_ep, &domain->psm_epid); if (err != PSM_OK) { FI_WARN(&psmx_prov, FI_LOG_CORE, "psm_ep_open returns %d, errno=%d\n", err, errno); err = psmx_errno(err); goto err_out; } FI_INFO(&psmx_prov, FI_LOG_CORE, "epid: 0x%016lx\n", domain->psm_epid); err = psm_mq_init(domain->psm_ep, PSM_MQ_ORDERMASK_ALL, NULL, 0, &domain->psm_mq); if (err != PSM_OK) { FI_WARN(&psmx_prov, FI_LOG_CORE, "psm_mq_init returns %d, errno=%d\n", err, errno); err = psmx_errno(err); goto err_out_close_ep; } err = fastlock_init(&domain->mr_lock); if (err) { FI_WARN(&psmx_prov, FI_LOG_CORE, "fastlock_init(mr_lock) returns %d\n", err); goto err_out_finalize_mq; } domain->mr_map = rbtNew(&psmx_key_compare); if (!domain->mr_map) { FI_WARN(&psmx_prov, FI_LOG_CORE, "rbtNew failed\n"); goto err_out_destroy_mr_lock; } domain->mr_reserved_key = 1; err = fastlock_init(&domain->poll_lock); if (err) { FI_WARN(&psmx_prov, FI_LOG_CORE, "fastlock_init(poll_lock) returns %d\n", err); goto err_out_delete_mr_map; } /* Set active domain before psmx_domain_enable_ep() installs the * AM handlers to ensure that psmx_active_fabric->active_domain * is always non-NULL inside the handlers. Notice that the vlaue * active_domain becomes NULL again only when the domain is closed. * At that time the AM handlers are gone with the PSM endpoint. */ fabric->active_domain = domain; if (psmx_domain_enable_ep(domain, NULL) < 0) goto err_out_reset_active_domain; if (domain->progress_thread_enabled) psmx_domain_start_progress(domain); return 0; err_out_reset_active_domain: fabric->active_domain = NULL; fastlock_destroy(&domain->poll_lock); err_out_delete_mr_map: rbtDelete(domain->mr_map); err_out_destroy_mr_lock: fastlock_destroy(&domain->mr_lock); err_out_finalize_mq: psm_mq_finalize(domain->psm_mq); err_out_close_ep: if (psm_ep_close(domain->psm_ep, PSM_EP_CLOSE_GRACEFUL, (int64_t) psmx_env.timeout * 1000000000LL) != PSM_OK) psm_ep_close(domain->psm_ep, PSM_EP_CLOSE_FORCE, 0); err_out: return err; }
int load_hostnames(char *bbhostsfn, char *extrainclude, int fqdn) { /* Return value: 0 for load OK, 1 for "No files changed since last load", -1 for error (file not found) */ static void *bbhfiles = NULL; FILE *bbhosts; int ip1, ip2, ip3, ip4, groupid, pageidx; char hostname[4096]; strbuffer_t *inbuf; pagelist_t *curtoppage, *curpage, *pgtail; namelist_t *nametail = NULL; RbtHandle htree; /* First check if there were no modifications at all */ if (bbhfiles) { if (!stackfmodified(bbhfiles)){ dbgprintf("No files modified, skipping reload of %s\n", bbhostsfn); return 1; } else { stackfclist(&bbhfiles); bbhfiles = NULL; } } MEMDEFINE(hostname); MEMDEFINE(l); configloaded = 1; initialize_hostlist(); curpage = curtoppage = pgtail = pghead; pageidx = groupid = 0; bbhosts = stackfopen(bbhostsfn, "r", &bbhfiles); if (bbhosts == NULL) return -1; inbuf = newstrbuffer(0); htree = rbtNew(name_compare); while (stackfgets(inbuf, extrainclude)) { sanitize_input(inbuf, 0, 0); if (strncmp(STRBUF(inbuf), "page", 4) == 0) { pagelist_t *newp; char *name, *title; pageidx = groupid = 0; if (get_page_name_title(STRBUF(inbuf), "page", &name, &title) == 0) { newp = (pagelist_t *)malloc(sizeof(pagelist_t)); newp->pagepath = strdup(name); newp->pagetitle = (title ? strdup(title) : NULL); newp->next = NULL; pgtail->next = newp; pgtail = newp; curpage = curtoppage = newp; } } else if (strncmp(STRBUF(inbuf), "subpage", 7) == 0) { pagelist_t *newp; char *name, *title; pageidx = groupid = 0; if (get_page_name_title(STRBUF(inbuf), "subpage", &name, &title) == 0) { newp = (pagelist_t *)malloc(sizeof(pagelist_t)); newp->pagepath = malloc(strlen(curtoppage->pagepath) + strlen(name) + 2); sprintf(newp->pagepath, "%s/%s", curtoppage->pagepath, name); newp->pagetitle = malloc(strlen(curtoppage->pagetitle) + strlen(title) + 2); sprintf(newp->pagetitle, "%s/%s", curtoppage->pagetitle, title); newp->next = NULL; pgtail->next = newp; pgtail = newp; curpage = newp; } } else if (strncmp(STRBUF(inbuf), "subparent", 9) == 0) { pagelist_t *newp, *parent; char *pname, *name, *title; pageidx = groupid = 0; parent = NULL; if (get_page_name_title(STRBUF(inbuf), "subparent", &pname, &title) == 0) { for (parent = pghead; (parent && !pagematch(parent, pname)); parent = parent->next); } if (parent && (get_page_name_title(title, "", &name, &title) == 0)) { newp = (pagelist_t *)malloc(sizeof(pagelist_t)); newp->pagepath = malloc(strlen(parent->pagepath) + strlen(name) + 2); sprintf(newp->pagepath, "%s/%s", parent->pagepath, name); newp->pagetitle = malloc(strlen(parent->pagetitle) + strlen(title) + 2); sprintf(newp->pagetitle, "%s/%s", parent->pagetitle, title); newp->next = NULL; pgtail->next = newp; pgtail = newp; curpage = newp; } } else if (strncmp(STRBUF(inbuf), "group", 5) == 0) { groupid++; } else if (sscanf(STRBUF(inbuf), "%d.%d.%d.%d %s", &ip1, &ip2, &ip3, &ip4, hostname) == 5) { char *startoftags, *tag, *delim; int elemidx, elemsize; char clientname[4096]; char downtime[4096]; char groupidstr[10]; RbtIterator handle; namelist_t *newitem = calloc(1, sizeof(namelist_t)); namelist_t *iwalk, *iprev; MEMDEFINE(clientname); MEMDEFINE(downtime); /* Hostname beginning with '@' are "no-display" hosts. But we still want them. */ if (*hostname == '@') memmove(hostname, hostname+1, strlen(hostname)); if (!fqdn) { /* Strip any domain from the hostname */ char *p = strchr(hostname, '.'); if (p) *p = '\0'; } sprintf(newitem->ip, "%d.%d.%d.%d", ip1, ip2, ip3, ip4); sprintf(groupidstr, "%d", groupid); newitem->groupid = strdup(groupidstr); newitem->pageindex = pageidx++; newitem->bbhostname = strdup(hostname); if (ip1 || ip2 || ip3 || ip4) newitem->preference = 1; else newitem->preference = 0; newitem->logname = strdup(newitem->bbhostname); { char *p = newitem->logname; while ((p = strchr(p, '.')) != NULL) { *p = '_'; } } newitem->page = curpage; newitem->defaulthost = defaulthost; clientname[0] = downtime[0] = '\0'; startoftags = strchr(STRBUF(inbuf), '#'); if (startoftags == NULL) startoftags = ""; else startoftags++; startoftags += strspn(startoftags, " \t\r\n"); newitem->allelems = strdup(startoftags); elemsize = 5; newitem->elems = (char **)malloc((elemsize+1)*sizeof(char *)); tag = newitem->allelems; elemidx = 0; while (tag && *tag) { if (elemidx == elemsize) { elemsize += 5; newitem->elems = (char **)realloc(newitem->elems, (elemsize+1)*sizeof(char *)); } newitem->elems[elemidx] = tag; /* Skip until we hit a whitespace or a quote */ tag += strcspn(tag, " \t\r\n\""); if (*tag == '"') { delim = tag; /* Hit a quote - skip until the next matching quote */ tag = strchr(tag+1, '"'); if (tag != NULL) { /* Found end-quote, NULL the item here and move on */ *tag = '\0'; tag++; } /* Now move quoted data one byte down (including the NUL) to kill quotechar */ memmove(delim, delim+1, strlen(delim)); } else if (*tag) { /* Normal end of item, NULL it and move on */ *tag = '\0'; tag++; } else { /* End of line - no more to do. */ tag = NULL; } /* * If we find a "noconn", drop preference value to 0. * If we find a "prefer", up reference value to 2. */ if ((newitem->preference == 1) && (strcmp(newitem->elems[elemidx], "noconn") == 0)) newitem->preference = 0; else if (strcmp(newitem->elems[elemidx], "prefer") == 0) newitem->preference = 2; /* Skip whitespace until start of next tag */ if (tag) tag += strspn(tag, " \t\r\n"); elemidx++; } newitem->elems[elemidx] = NULL; /* See if this host is defined before */ handle = rbtFind(htree, newitem->bbhostname); if (strcasecmp(newitem->bbhostname, ".default.") == 0) { /* The pseudo DEFAULT host */ newitem->next = NULL; defaulthost = newitem; } else if (handle == rbtEnd(htree)) { /* New item, so add to end of list */ newitem->next = NULL; if (namehead == NULL) namehead = nametail = newitem; else { nametail->next = newitem; nametail = newitem; } rbtInsert(htree, newitem->bbhostname, newitem); } else { /* Find the existing record - compare the record pointer instead of the name */ namelist_t *existingrec = (namelist_t *)gettreeitem(htree, handle); for (iwalk = namehead, iprev = NULL; ((iwalk != existingrec) && iwalk); iprev = iwalk, iwalk = iwalk->next) ; if (newitem->preference <= iwalk->preference) { /* Add after the existing (more preferred) entry */ newitem->next = iwalk->next; iwalk->next = newitem; } else { /* New item has higher preference, so add before the iwalk item (i.e. after iprev) */ if (iprev == NULL) { newitem->next = namehead; namehead = newitem; } else { newitem->next = iprev->next; iprev->next = newitem; } } } newitem->clientname = bbh_find_item(newitem, BBH_CLIENTALIAS); if (newitem->clientname == NULL) newitem->clientname = newitem->bbhostname; newitem->downtime = bbh_find_item(newitem, BBH_DOWNTIME); MEMUNDEFINE(clientname); MEMUNDEFINE(downtime); } } stackfclose(bbhosts); freestrbuffer(inbuf); rbtDelete(htree); MEMUNDEFINE(hostname); MEMUNDEFINE(l); build_hosttree(); return 0; }
void rbtDel(RBTreeType *tree) { if(tree == NULL) return; rbtDelete(&tree->root, SENTINEL); free(tree); }
static void psmx_ns_map_fini(void) { rbtDelete(psmx_ns_map); }