static int parse_tag_rra_cdp_prep( xmlTextReaderPtr reader, rrd_t *rrd, cdp_prep_t *cdp_prep) { int status; unsigned int ds_count; status = 0; for ( ds_count = 0; ds_count < rrd->stat_head->ds_cnt;ds_count++){ if (expect_element(reader,"ds") == 0) { status = parse_tag_rra_cdp_prep_ds(reader, rrd, cdp_prep + ds_count); if (status != 0) break; } else { status = -1; break; } } if (status == 0) status = expect_element(reader,"/cdp_prep"); return (status); } /* int parse_tag_rra_cdp_prep */
static int parse_tag_rra_database_row( xmlTextReaderPtr reader, rrd_t *rrd, rrd_value_t *rrd_value) { unsigned int values_count = 0; int status; status = 0; for (values_count = 0;values_count < rrd->stat_head->ds_cnt;values_count++){ if (expect_element(reader,"v") == 0){ status = get_xml_double(reader,rrd_value + values_count); if (status == 0) value_check_range(rrd_value + values_count, rrd->ds_def + values_count); else break; } else return -1; if (expect_element(reader,"/v") == -1){ return -1; } } return status; } /* int parse_tag_rra_database_row */
/* * Parse the <params> block within an RRA definition */ static int parse_tag_rra_params( xmlTextReaderPtr reader, rra_def_t *rra_def) { xmlChar *element; int status; status = -1; while ((element = get_xml_element(reader)) != NULL){ /* * Parameters for CF_HWPREDICT */ if (xmlStrcasecmp(element, (const xmlChar *) "hw_alpha") == 0) status = get_xml_double(reader, &rra_def->par[RRA_hw_alpha].u_val); else if (xmlStrcasecmp(element, (const xmlChar *) "hw_beta") == 0) status = get_xml_double(reader, &rra_def->par[RRA_hw_beta].u_val); else if (xmlStrcasecmp(element, (const xmlChar *) "dependent_rra_idx") == 0) status = get_xml_ulong(reader, &rra_def-> par[RRA_dependent_rra_idx].u_cnt); /* * Parameters for CF_SEASONAL and CF_DEVSEASONAL */ else if (xmlStrcasecmp(element, (const xmlChar *) "seasonal_gamma") == 0) status = get_xml_double(reader, &rra_def->par[RRA_seasonal_gamma].u_val); else if (xmlStrcasecmp (element, (const xmlChar *) "seasonal_smooth_idx") == 0) status = get_xml_ulong(reader, &rra_def-> par[RRA_seasonal_smooth_idx].u_cnt); else if (xmlStrcasecmp(element, (const xmlChar *) "smoothing_window") == 0) status = get_xml_double(reader, &rra_def-> par[RRA_seasonal_smoothing_window]. u_val); /* else if (dependent_rra_idx) ...; */ /* * Parameters for CF_FAILURES */ else if (xmlStrcasecmp(element, (const xmlChar *) "delta_pos") == 0) status = get_xml_double(reader, &rra_def->par[RRA_delta_pos].u_val); else if (xmlStrcasecmp(element, (const xmlChar *) "delta_neg") == 0) status = get_xml_double(reader, &rra_def->par[RRA_delta_neg].u_val); else if (xmlStrcasecmp(element, (const xmlChar *) "window_len") == 0) status = get_xml_ulong(reader, &rra_def->par[RRA_window_len]. u_cnt); else if (xmlStrcasecmp(element, (const xmlChar *) "failure_threshold") == 0) status = get_xml_ulong(reader, &rra_def-> par[RRA_failure_threshold].u_cnt); /* * Parameters for CF_AVERAGE, CF_MAXIMUM, CF_MINIMUM, and CF_LAST */ else if (xmlStrcasecmp(element, (const xmlChar *) "xff") == 0) status = get_xml_double(reader, &rra_def->par[RRA_cdp_xff_val]. u_val); /* * Compatibility code for 1.0.49 */ else if (xmlStrcasecmp(element, (const xmlChar *) "value") == 0) { /* {{{ */ unsigned int i = 0; for (i=0;i<ARRAY_LENGTH(rra_def->par);i++){ if ((i == RRA_dependent_rra_idx) || (i == RRA_seasonal_smooth_idx) || (i == RRA_failure_threshold)) status = get_xml_ulong(reader, &rra_def->par[i]. u_cnt); else status = get_xml_double(reader, &rra_def->par[i].u_val); if (status != 0) break; if ( i-1 < ARRAY_LENGTH(rra_def->par)){ status = expect_element(reader,"/value"); if (status == 0){ status = expect_element(reader,"value"); } } if (status != 0){ break; } } } /* }}} */ else if (xmlStrcasecmp(element,(const xmlChar *) "/params") == 0){ xmlFree(element); return status; } /* }}} */ else { rrd_set_error("line %d: parse_tag_rra_params: Unknown tag: %s", xmlTextReaderGetParserLineNumber(reader),element); status = -1; } status = expect_element_end(reader,(char *)element); xmlFree(element); if (status != 0) break; } return (status); } /* int parse_tag_rra_params */
static int parse_tag_rra_database( xmlTextReaderPtr reader, rrd_t *rrd ) { rra_def_t *cur_rra_def; rra_ptr_t *cur_rra_ptr; unsigned int total_row_cnt; int status; int i; xmlChar *element; unsigned int start_row_cnt; int ds_cnt; ds_cnt = rrd->stat_head->ds_cnt; total_row_cnt = 0; for (i = 0; i < (((int) rrd->stat_head->rra_cnt) - 1); i++) total_row_cnt += rrd->rra_def[i].row_cnt; cur_rra_def = rrd->rra_def + i; cur_rra_ptr = rrd->rra_ptr + i; start_row_cnt = total_row_cnt; status = 0; while ((element = get_xml_element(reader)) != NULL){ if (xmlStrcasecmp(element,(const xmlChar *)"row") == 0){ rrd_value_t *temp; rrd_value_t *cur_rrd_value; unsigned int total_values_count = rrd->stat_head->ds_cnt * (total_row_cnt + 1); /* Allocate space for the new values.. */ temp = (rrd_value_t *) realloc(rrd->rrd_value, sizeof(rrd_value_t) * total_values_count); if (temp == NULL) { rrd_set_error("parse_tag_rra_database: realloc failed."); status = -1; break; } rrd->rrd_value = temp; cur_rrd_value = rrd->rrd_value + (rrd->stat_head->ds_cnt * total_row_cnt); memset(cur_rrd_value, '\0', sizeof(rrd_value_t) * rrd->stat_head->ds_cnt); total_row_cnt++; cur_rra_def->row_cnt++; status = parse_tag_rra_database_row(reader, rrd, cur_rrd_value); if (status == 0) status = expect_element(reader,"/row"); } /* if (xmlStrcasecmp(element,"row")) */ else { if ( xmlStrcasecmp(element,(const xmlChar *)"/database") == 0){ xmlFree(element); break; } else { rrd_set_error("line %d: found unexpected tag: %s", xmlTextReaderGetParserLineNumber(reader),element); status = -1; } } xmlFree(element); if (status != 0) break; } /* Set the RRA pointer to a random location */ cur_rra_ptr->cur_row = rrd_random() % cur_rra_def->row_cnt; /* * rotate rows to match cur_row... * * this will require some extra temp. memory. We can do this rather * brainlessly, because we have done all kinds of realloc before, * so we messed around with memory a lot already. */ /* What we want: +-start_row_cnt | +-cur_rra_def->row_cnt | | |a---------n012-------------------------| (cur_rra_def->row_cnt slots of ds_cnt width) What we have | |012-------------------------a---------n| Do this by: copy away 0..(a-1) to a temp buffer move a..n to start of buffer copy temp buffer to position after where we moved n to */ int a = cur_rra_def->row_cnt - cur_rra_ptr->cur_row - 1; rrd_value_t *temp = malloc(ds_cnt * sizeof(rrd_value_t) * a); if (temp == NULL) { rrd_set_error("parse_tag_rra: malloc failed."); return -1; } rrd_value_t *start = rrd->rrd_value + start_row_cnt * ds_cnt; /* */ memcpy(temp, start, a * ds_cnt * sizeof(rrd_value_t)); memmove(start, start + a * ds_cnt, (cur_rra_ptr->cur_row + 1) * ds_cnt * sizeof(rrd_value_t)); memcpy(start + (cur_rra_ptr->cur_row + 1) * ds_cnt, temp, a * ds_cnt * sizeof(rrd_value_t)); free(temp); return (status); } /* int parse_tag_rra_database */
static rrd_t *parse_file( const char *filename) { xmlTextReaderPtr reader; int status; rrd_t *rrd; stdioXmlReaderContext *sctx = NULL; /* special handling for XML on stdin (like it is the case when using the pipe interface) */ if (strcmp(filename, "-") == 0) { sctx = (stdioXmlReaderContext *) malloc(sizeof(*sctx)); if (sctx == NULL) { rrd_set_error("parse_file: malloc failed."); return (NULL); } sctx->stream = stdin; sctx->freeOnClose = 1; sctx->closed = 0; sctx->eofchar = 0x1A; /* ctrl-Z */ xmlSetGenericErrorFunc(NULL, ignoringErrorFunc); reader = xmlReaderForIO(stdioXmlInputReadCallback, stdioXmlInputCloseCallback, sctx, filename, NULL, 0); } else { reader = xmlNewTextReaderFilename(filename); } if (reader == NULL) { if (sctx != NULL) free(sctx); rrd_set_error("Could not create xml reader for: %s",filename); return (NULL); } /* NOTE: from now on, sctx will get freed implicitly through * xmlFreeTextReader and its call to * stdioXmlInputCloseCallback. */ if (expect_element(reader,"rrd") != 0) { xmlFreeTextReader(reader); return (NULL); } rrd = (rrd_t *) malloc(sizeof(rrd_t)); if (rrd == NULL) { rrd_set_error("parse_file: malloc failed."); xmlFreeTextReader(reader); return (NULL); } memset(rrd, '\0', sizeof(rrd_t)); rrd->stat_head = (stat_head_t *) malloc(sizeof(stat_head_t)); if (rrd->stat_head == NULL) { rrd_set_error("parse_tag_rrd: malloc failed."); xmlFreeTextReader(reader); free(rrd); return (NULL); } memset(rrd->stat_head, '\0', sizeof(stat_head_t)); strncpy(rrd->stat_head->cookie, "RRD", sizeof(rrd->stat_head->cookie)); rrd->stat_head->float_cookie = FLOAT_COOKIE; rrd->live_head = (live_head_t *) malloc(sizeof(live_head_t)); if (rrd->live_head == NULL) { rrd_set_error("parse_tag_rrd: malloc failed."); xmlFreeTextReader(reader); free(rrd->stat_head); free(rrd); return (NULL); } memset(rrd->live_head, '\0', sizeof(live_head_t)); status = parse_tag_rrd(reader, rrd); xmlFreeTextReader(reader); if (status != 0) { local_rrd_free(rrd); rrd = NULL; } return (rrd); } /* rrd_t *parse_file */
static int parse_tag_rra_database( xmlTextReaderPtr reader, rrd_t *rrd ) { rra_def_t *cur_rra_def; unsigned int total_row_cnt; int status; int i; xmlChar *element; total_row_cnt = 0; for (i = 0; i < (((int) rrd->stat_head->rra_cnt) - 1); i++) total_row_cnt += rrd->rra_def[i].row_cnt; cur_rra_def = rrd->rra_def + i; status = 0; while ((element = get_xml_element(reader)) != NULL){ if (xmlStrcasecmp(element,(const xmlChar *)"row") == 0){ rrd_value_t *temp; rrd_value_t *cur_rrd_value; unsigned int total_values_count = rrd->stat_head->ds_cnt * (total_row_cnt + 1); /* Allocate space for the new values.. */ temp = (rrd_value_t *) realloc(rrd->rrd_value, sizeof(rrd_value_t) * total_values_count); if (temp == NULL) { rrd_set_error("parse_tag_rra_database: realloc failed."); status = -1; break; } rrd->rrd_value = temp; cur_rrd_value = rrd->rrd_value + (rrd->stat_head->ds_cnt * total_row_cnt); memset(cur_rrd_value, '\0', sizeof(rrd_value_t) * rrd->stat_head->ds_cnt); total_row_cnt++; cur_rra_def->row_cnt++; status = parse_tag_rra_database_row(reader, rrd, cur_rrd_value); if (status == 0) status = expect_element(reader,"/row"); } /* if (xmlStrcasecmp(element,"row")) */ else { if ( xmlStrcasecmp(element,(const xmlChar *)"/database") == 0){ xmlFree(element); break; } else { rrd_set_error("line %d: found unexpected tag: %s", xmlTextReaderGetParserLineNumber(reader),element); status = -1; } } xmlFree(element); if (status != 0) break; } return (status); } /* int parse_tag_rra_database */