int noit_poller_schedule(const char *target, const char *module, const char *name, const char *filterset, noit_hash_table *config, u_int32_t period, u_int32_t timeout, const char *oncheck, int flags, uuid_t in, uuid_t out) { noit_check_t *new_check; new_check = calloc(1, sizeof(*new_check)); if(!new_check) return -1; /* The module and the UUID can never be changed */ new_check->module = strdup(module); if(uuid_is_null(in)) uuid_generate(new_check->checkid); else uuid_copy(new_check->checkid, in); noit_check_update(new_check, target, name, filterset, config, period, timeout, oncheck, flags); assert(noit_hash_store(&polls, (char *)new_check->checkid, UUID_SIZE, new_check)); uuid_copy(out, new_check->checkid); return 0; }
noit_check_t * noit_fire_check(xmlNodePtr attr, xmlNodePtr config, const char **error) { char *target = NULL, *name = NULL, *module = NULL, *filterset = NULL; int timeout = 0; noit_module_t *m; noit_check_t *c = NULL; xmlNodePtr a, co; noit_hash_table *conf_hash = 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); } } m = noit_module_lookup(module); if(!m) { *error = "cannot find requested module"; goto error; } conf_hash = calloc(1, sizeof(*conf_hash)); 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 : ""); noit_hash_replace(conf_hash, name, strlen(name), val, free, free); xmlFree(tmp_val); } if(!m->initiate_check) { *error = "that module cannot run checks"; goto error; } c = calloc(1, sizeof(*c)); noit_check_update(c, target, name, filterset, conf_hash, 0, timeout, NULL, NP_TRANSIENT); c->module = strdup(module); 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) { noit_hash_destroy(conf_hash, free, free); free(conf_hash); } if(target) xmlFree(target); if(name) xmlFree(name); if(module) xmlFree(module); if(filterset) xmlFree(filterset); return c; }
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; noit_check_t *c = NULL; xmlNodePtr a, co; noit_hash_table *conf_hash = NULL; noit_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); } 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 : ""); noit_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; noit_conf_section_t checks; name = noit_check_registered_module(i); checks = noit_conf_get_section(NULL, "/noit/checks"); if(name) moptions[i] = noit_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 = calloc(1, sizeof(*c)); noit_check_update(c, target, name, filterset, conf_hash, moptions, 0, timeout, NULL, flags); c->module = strdup(module); 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) { noit_hash_destroy(conf_hash, free, free); free(conf_hash); } if(moptions) { for(i=0; i<mod_cnt; i++) { if(moptions[i]) { noit_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; }
void noit_poller_process_checks(const char *xpath) { int i, flags, cnt = 0; noit_conf_section_t *sec; __config_load_generation++; sec = noit_conf_get_sections(NULL, xpath, &cnt); for(i=0; i<cnt; i++) { void *vcheck; char uuid_str[37]; char target[256] = ""; char module[256] = ""; char name[256] = ""; char filterset[256] = ""; char oncheck[1024] = ""; int no_period = 0; int no_oncheck = 0; int period = 0, timeout = 0; noit_boolean disabled = noit_false, busted = noit_false; uuid_t uuid, out_uuid; noit_hash_table *options; #define NEXT(...) noitL(noit_stderr, __VA_ARGS__); continue #define MYATTR(type,a,...) noit_conf_get_##type(sec[i], "@" #a, __VA_ARGS__) #define INHERIT(type,a,...) \ noit_conf_get_##type(sec[i], "ancestor-or-self::node()/@" #a, __VA_ARGS__) if(!MYATTR(stringbuf, uuid, uuid_str, sizeof(uuid_str))) { noitL(noit_stderr, "check %d has no uuid\n", i+1); continue; } if(uuid_parse(uuid_str, uuid)) { noitL(noit_stderr, "check uuid: '%s' is invalid\n", uuid_str); continue; } if(!INHERIT(stringbuf, target, target, sizeof(target))) { noitL(noit_stderr, "check uuid: '%s' has no target\n", uuid_str); busted = noit_true; } if(!INHERIT(stringbuf, module, module, sizeof(module))) { noitL(noit_stderr, "check uuid: '%s' has no module\n", uuid_str); busted = noit_true; } if(!INHERIT(stringbuf, filterset, filterset, sizeof(filterset))) filterset[0] = '\0'; if(!MYATTR(stringbuf, name, name, sizeof(name))) strlcpy(name, module, sizeof(name)); if(!INHERIT(int, period, &period) || period == 0) no_period = 1; if(!INHERIT(stringbuf, oncheck, oncheck, sizeof(oncheck)) || !oncheck[0]) no_oncheck = 1; if(no_period && no_oncheck) { noitL(noit_stderr, "check uuid: '%s' has neither period nor oncheck\n", uuid_str); busted = noit_true; } if(!(no_period || no_oncheck)) { noitL(noit_stderr, "check uuid: '%s' has oncheck and period.\n", uuid_str); busted = noit_true; } if(!INHERIT(int, timeout, &timeout)) { noitL(noit_stderr, "check uuid: '%s' has no timeout\n", uuid_str); busted = noit_true; } if(!no_period && timeout >= period) { noitL(noit_stderr, "check uuid: '%s' timeout > period\n", uuid_str); timeout = period/2; } options = noit_conf_get_hash(sec[i], "config"); INHERIT(boolean, disable, &disabled); flags = 0; if(busted) flags |= (NP_UNCONFIG|NP_DISABLED); else if(disabled) flags |= NP_DISABLED; if(noit_hash_retrieve(&polls, (char *)uuid, UUID_SIZE, &vcheck)) { noit_check_t *existing_check = (noit_check_t *)vcheck; /* Once set, we can never change it. */ assert(!existing_check->module || !existing_check->module[0] || !strcmp(existing_check->module, module)); /* Only set it if it is not yet set */ if(!existing_check->module || !existing_check->module[0]) { if(existing_check->module) free(existing_check->module); existing_check->module = strdup(module); } noit_check_update(existing_check, target, name, filterset, options, period, timeout, oncheck[0] ? oncheck : NULL, flags); noitL(noit_debug, "reloaded uuid: %s\n", uuid_str); } else { noit_poller_schedule(target, module, name, filterset, options, period, timeout, oncheck[0] ? oncheck : NULL, flags, uuid, out_uuid); noitL(noit_debug, "loaded uuid: %s\n", uuid_str); } noit_hash_destroy(options, free, free); free(options); } if(sec) free(sec); }