void mtev_hash_merge_as_dict(mtev_hash_table *dst, mtev_hash_table *src) { mtev_hash_iter iter = MTEV_HASH_ITER_ZERO; if(src == NULL || dst == NULL) return; while(mtev_hash_adv(src, &iter)) { mtev_hash_replace(dst, strdup(iter.key.str), iter.klen, strdup(iter.value.str), free, free); } }
int eventer_name_callback_ext(const char *name, eventer_func_t f, void (*fn)(char *,int,eventer_t,void *), void *cl) { void **fptr = malloc(sizeof(*fptr)); *fptr = (void *)f; mtev_hash_replace(&__name_to_func, strdup(name), strlen(name), (void *)f, free, NULL); struct callback_details *cd; cd = calloc(1, sizeof(*cd)); cd->simple_name = strdup(name); cd->functional_name = fn; cd->closure = cl; mtev_hash_replace(&__func_to_name, (char *)fptr, sizeof(*fptr), cd, free, free_callback_details); return 0; }
void mysql_parse_dsn(const char *dsn, mtev_hash_table *h) { const char *a=dsn, *b=NULL, *c=NULL; while (a && (NULL != (b = strchr(a, '=')))) { char *key, *val=NULL; key = __noit__strndup(a, b-a); b++; if (b) { if (NULL != (c = strchr(b, ' '))) { val = __noit__strndup(b, c-b); } else { val = strdup(b); } } mtev_hash_replace(h, key, key?strlen(key):0, val, free, free); a = c; if (a) a++; } }
static void noit_fq_set_filters(mq_command_t *commands, int count) { int i, j; if (!global_fq_ctx.filtered_exchange[0]) { mtevL(mtev_error, "ERROR: trying to set check for filtered exchange when no such exchange exists\n"); return; } for (i=0; i<count; i++) { if (commands[i].action == MQ_ACTION_SET) { mtev_hash_table *metric_table = calloc(1, sizeof(mtev_hash_table)); mtev_hash_init(metric_table); for (j=0; j<commands[i].check.metric_count; j++) { mtev_hash_store(metric_table, strdup(commands[i].check.metrics[j]), strlen(commands[i].check.metrics[j]), NULL); filtered_metrics_exist = true; } mtev_hash_replace(&filtered_checks_hash, strdup(commands[i].check.uuid), strlen(commands[i].check.uuid), metric_table, free, noit_fq_free_metric_hash); } else { if (commands[i].check.metric_count == 0) { /* Forget the whole check */ if (!mtev_hash_delete(&filtered_checks_hash, commands[i].check.uuid, strlen(commands[i].check.uuid), free, noit_fq_free_metric_hash)) { mtevL(mtev_error, "failed forgetting check %s - check does not exist\n", commands[i].check.uuid); } } else { mtev_hash_table *filtered_metrics; if(mtev_hash_retrieve(&filtered_checks_hash, commands[i].check.uuid, strlen(commands[i].check.uuid), (void**)&filtered_metrics)) { for (j=0; j<commands[i].check.metric_count; j++) { if (!mtev_hash_delete(filtered_metrics, commands[i].check.metrics[j], strlen(commands[i].check.metrics[j]), free, noit_fq_free_metric_hash)) { mtevL(mtev_error, "failed forgetting metric '%s' for check %s - metric does not exist\n", commands[i].check.metrics[j], commands[i].check.uuid); } } } else { mtevL(mtev_error, "failed forgetting metrics for check %s - check does not exist\n", commands[i].check.uuid); } } } } }
noit_check_t * noit_fire_check(xmlNodePtr attr, xmlNodePtr config, const char **error) { char *target = NULL, *name = NULL, *module = NULL, *filterset = NULL; char *resolve_rtype = NULL; int timeout = 0, flags = NP_TRANSIENT, i, mod_cnt; noit_module_t *m = NULL; noit_check_t *c = NULL; xmlNodePtr a, co; mtev_hash_table *conf_hash = NULL; mtev_hash_table **moptions = NULL; for(a = attr->children; a; a = a->next) { if(!strcmp((char *)a->name, "target")) target = (char *)xmlNodeGetContent(a); else if(!strcmp((char *)a->name, "name")) name = (char *)xmlNodeGetContent(a); else if(!strcmp((char *)a->name, "module")) module = (char *)xmlNodeGetContent(a); else if(!strcmp((char *)a->name, "filterset")) filterset = (char *)xmlNodeGetContent(a); else if(!strcmp((char *)a->name, "timeout")) { char *timeout_str = (char *)xmlNodeGetContent(a); timeout = atoi(timeout_str); free(timeout_str); } else if(!strcmp((char *)a->name, "resolve_rtype")) resolve_rtype = (char *)xmlNodeGetContent(a); } if(!noit_check_validate_target(target)) { *error = "malformed target"; goto error; } if(!noit_check_validate_name(name)) { *error = "malformed name"; goto error; } if(module) m = noit_module_lookup(module); if(!m) { *error = "cannot find requested module"; goto error; } conf_hash = calloc(1, sizeof(*conf_hash)); if(config) { for(co = config->children; co; co = co->next) { char *name, *val; xmlChar *tmp_val; name = strdup((char *)co->name); tmp_val = xmlNodeGetContent(co); val = strdup(tmp_val ? (char *)tmp_val : ""); mtev_hash_replace(conf_hash, name, strlen(name), val, free, free); xmlFree(tmp_val); } } mod_cnt = noit_check_registered_module_cnt(); if(mod_cnt > 0) { moptions = alloca(mod_cnt * sizeof(*moptions)); memset(moptions, 0, mod_cnt * sizeof(*moptions)); for(i=0; i<mod_cnt; i++) { const char *name; mtev_conf_section_t checks; name = noit_check_registered_module(i); checks = mtev_conf_get_section(NULL, "/noit/checks"); if(name) moptions[i] = mtev_conf_get_namespaced_hash(checks, "config", name); } } if(!m->initiate_check) { *error = "that module cannot run checks"; goto error; } flags |= noit_calc_rtype_flag(resolve_rtype); c = mtev_memory_safe_calloc(1, sizeof(*c)); c->module = strdup(module); c->flags = NP_TRANSIENT; noit_check_update(c, target, name, filterset, conf_hash, moptions, 0, timeout, NULL, 0, flags); uuid_generate(c->checkid); c->flags |= NP_DISABLED; /* this is hack to know we haven't run it yet */ if(NOIT_CHECK_SHOULD_RESOLVE(c)) noit_check_resolve(c); error: if(conf_hash) { mtev_hash_destroy(conf_hash, free, free); free(conf_hash); } if(moptions) { for(i=0; i<mod_cnt; i++) { if(moptions[i]) { mtev_hash_destroy(moptions[i], free, free); free(moptions[i]); } } } if(target) xmlFree(target); if(name) xmlFree(name); if(module) xmlFree(module); if(filterset) xmlFree(filterset); if(resolve_rtype) xmlFree(resolve_rtype); return c; }
int noit_filtersets_cull_unused() { mtev_hash_table active = MTEV_HASH_EMPTY; char *buffer = NULL; mtev_conf_section_t *declares; int i, n_uses = 0, n_declares = 0, removed = 0; const char *declare_xpath = "//filterset[@name and not (@cull='false')]"; declares = mtev_conf_get_sections(NULL, declare_xpath, &n_declares); if(declares) { /* store all unit filtersets used */ for(i=0;i<n_declares;i++) { if(!buffer) buffer = malloc(128); if(mtev_conf_get_stringbuf(declares[i], "@name", buffer, 128)) { if(mtev_hash_store(&active, buffer, strlen(buffer), declares[i])) { buffer = NULL; } else { void *vnode = NULL; /* We've just hit a duplicate.... check to see if there's an existing * entry and if there is, load the latest one and delete the old * one. */ mtev_hash_retrieve(&active, buffer, strlen(buffer), &vnode); if (vnode) { noit_filter_compile_add(declares[i]); CONF_REMOVE(vnode); xmlUnlinkNode(vnode); xmlFreeNode(vnode); removed++; if(mtev_hash_replace(&active, buffer, strlen(buffer), declares[i], free, NULL)) { buffer = NULL; } } } } } if(buffer) free(buffer); free(declares); } n_uses = noit_poller_do(filterset_accum, &active); if(n_uses > 0 && mtev_hash_size(&active) > 0) { mtev_hash_iter iter = MTEV_HASH_ITER_ZERO; const char *filter_name; int filter_name_len; void *vnode; while(mtev_hash_next(&active, &iter, &filter_name, &filter_name_len, &vnode)) { if(noit_filter_remove(vnode)) { CONF_REMOVE(vnode); xmlUnlinkNode(vnode); xmlFreeNode(vnode); removed++; } } } mtev_hash_destroy(&active, free, NULL); return removed; }
void noit_filter_compile_add(mtev_conf_section_t setinfo) { mtev_conf_section_t *rules; int j, fcnt; char filterset_name[256]; filterset_t *set; if(!mtev_conf_get_stringbuf(setinfo, "@name", filterset_name, sizeof(filterset_name))) { mtevL(noit_error, "filterset with no name, skipping as it cannot be referenced.\n"); return; } set = calloc(1, sizeof(*set)); set->ref_cnt = 1; set->name = strdup(filterset_name); rules = mtev_conf_get_sections(setinfo, "rule", &fcnt); /* Here we will work through the list backwards pushing the rules on * the front of the list. That way we can simply walk them in order * for the application process. */ mtevL(noit_debug, "Compiling filterset '%s'\n", set->name); for(j=fcnt-1; j>=0; j--) { filterrule_t *rule; char buffer[256]; if(!mtev_conf_get_stringbuf(rules[j], "@type", buffer, sizeof(buffer)) || (strcmp(buffer, "accept") && strcmp(buffer, "allow") && strcmp(buffer, "deny") && strncmp(buffer, "skipto:", strlen("skipto:")))) { mtevL(noit_error, "rule must have type 'accept' or 'allow' or 'deny' or 'skipto:'\n"); continue; } mtevL(noit_debug, "Prepending %s into %s\n", buffer, set->name); rule = calloc(1, sizeof(*rule)); if(!strncasecmp(buffer, "skipto:", strlen("skipto:"))) { rule->type = NOIT_FILTER_SKIPTO; rule->skipto = strdup(buffer+strlen("skipto:")); } else { rule->type = (!strcmp(buffer, "accept") || !strcmp(buffer, "allow")) ? NOIT_FILTER_ACCEPT : NOIT_FILTER_DENY; } if(mtev_conf_get_stringbuf(rules[j], "@id", buffer, sizeof(buffer))) { rule->ruleid = strdup(buffer); } /* Compile any hash tables, should they exist */ #define HT_COMPILE(rname) do { \ mtev_conf_section_t *htentries; \ int hte_cnt, hti, tablesize = 2, auto_max = 0; \ char *htstr; \ htentries = mtev_conf_get_sections(rules[j], #rname, &hte_cnt); \ mtev_conf_get_int(rules[j], "@" #rname "_auto_add", &auto_max); \ if(hte_cnt || auto_max > 0) { \ rule->rname##_auto_hash_max = auto_max; \ rule->rname##_ht = calloc(1, sizeof(*(rule->rname##_ht))); \ while(tablesize < hte_cnt) tablesize <<= 1; \ mtev_hash_init_size(rule->rname##_ht, tablesize); \ for(hti=0; hti<hte_cnt; hti++) { \ if(!mtev_conf_get_string(htentries[hti], "self::node()", &htstr)) \ mtevL(noit_error, "Error fetching text content from filter match.\n"); \ else \ mtev_hash_replace(rule->rname##_ht, htstr, strlen(htstr), NULL, free, NULL); \ } \ } \ free(htentries); \ } while(0); HT_COMPILE(target); HT_COMPILE(module); HT_COMPILE(name); HT_COMPILE(metric); /* Compile our rules */ #define RULE_COMPILE(rname) do { \ char *longre = NULL; \ if(mtev_conf_get_string(rules[j], "@" #rname, &longre)) { \ const char *error; \ int erroffset; \ rule->rname = pcre_compile(longre, 0, &error, &erroffset, NULL); \ if(!rule->rname) { \ mtevL(noit_debug, "set '%s' rule '%s: %s' compile failed: %s\n", \ set->name, #rname, longre, error ? error : "???"); \ rule->rname##_override = fallback_no_match; \ } \ else { \ rule->rname##_e = pcre_study(rule->rname, 0, &error); \ } \ free(longre); \ } \ } while(0) if(rule->target_ht == NULL) RULE_COMPILE(target); if(rule->module_ht == NULL) RULE_COMPILE(module); if(rule->name_ht == NULL) RULE_COMPILE(name); if(rule->metric_ht == NULL) RULE_COMPILE(metric); rule->next = set->rules; set->rules = rule; } filterrule_t *cursor; for(cursor = set->rules; cursor->next; cursor = cursor->next) { if(cursor->skipto) { filterrule_t *target; for(target = cursor->next; target; target = target->next) { if(target->ruleid && !strcmp(cursor->skipto, target->ruleid)) { cursor->skipto_rule = target; break; } } if(!cursor->skipto_rule) mtevL(noit_error, "filterset %s skipto:%s not found\n", set->name, cursor->skipto); } } free(rules); LOCKFS(); mtev_hash_replace(filtersets, set->name, strlen(set->name), (void *)set, NULL, filterset_free); UNLOCKFS(); }