X-Git-Url: https://git.octo.it/?a=blobdiff_plain;f=src%2Frrd_rpncalc.c;h=8e64d8b200b58b61bde2402d94caa01e3d095ad3;hb=b9b92c21c1b517ca2d69e7baac4be7587aff5eb5;hp=c174370b284ccb48e65b890476aa30f6be74ea76;hpb=db5507e792921e2e6ea29ca0ed1710557acf340f;p=rrdtool.git diff --git a/src/rrd_rpncalc.c b/src/rrd_rpncalc.c index c174370..8e64d8b 100644 --- a/src/rrd_rpncalc.c +++ b/src/rrd_rpncalc.c @@ -6,6 +6,7 @@ #include "rrd_tool.h" #include "rrd_rpncalc.h" +#include "rrd_graph.h" #include short addop2str(enum op_en op, enum op_en op_type, char *op_str, @@ -40,7 +41,8 @@ short rpn_compact(rpnp_t *rpnp, rpn_cdefds_t **rpnc, short *count) return -1; } (*rpnc)[i].val = (short) temp; - } else if (rpnp[i].op == OP_VARIABLE) { + } else if (rpnp[i].op == OP_VARIABLE || + rpnp[i].op == OP_PREV_OTHER) { (*rpnc)[i].val = (short) rpnp[i].ptr; } } @@ -63,7 +65,8 @@ rpnp_t * rpn_expand(rpn_cdefds_t *rpnc) rpnp[i].op = (long) rpnc[i].op; if (rpnp[i].op == OP_NUMBER) { rpnp[i].val = (double) rpnc[i].val; - } else if (rpnp[i].op == OP_VARIABLE) { + } else if (rpnp[i].op == OP_VARIABLE || + rpnp[i].op == OP_PREV_OTHER) { rpnp[i].ptr = (long) rpnc[i].val; } } @@ -106,6 +109,12 @@ void rpn_compact2str(rpn_cdefds_t *rpnc,ds_def_t *ds_def,char **str) char *ds_name = ds_def[rpnc[i].val].ds_nam; add_op(OP_VARIABLE, ds_name) } + + if (rpnc[i].op == OP_PREV_OTHER) { + char *ds_name = ds_def[rpnc[i].val].ds_nam; + add_op(OP_VARIABLE, ds_name) + } + #undef add_op #define add_op(VV,VVV) \ @@ -261,6 +270,21 @@ rpn_parse(void *key_hash,char *expr,long (*lookup)(void *,char*)){ expr+=strlen(#VVV); \ } + +#define match_op_param(VV,VVV) \ + else if (sscanf(expr, #VVV "(" DEF_NAM_FMT ")",vname) == 1) { \ + int length = 0; \ + if ((length = strlen(#VVV)+strlen(vname)+2, \ + expr[length] == ',' || expr[length] == '\0') ) { \ + rpnp[steps].op = VV; \ + rpnp[steps].ptr = (*lookup)(key_hash,vname); \ + if (rpnp[steps].ptr < 0) { \ + free(rpnp); \ + return NULL; \ + } else expr+=length; \ + } \ + } + match_op(OP_ADD,+) match_op(OP_SUB,-) match_op(OP_MUL,*) @@ -289,6 +313,7 @@ rpn_parse(void *key_hash,char *expr,long (*lookup)(void *,char*)){ match_op(OP_UN,UN) match_op(OP_NEGINF,NEGINF) match_op(OP_NE,NE) + match_op_param(OP_PREV_OTHER,PREV) match_op(OP_PREV,PREV) match_op(OP_INF,INF) match_op(OP_ISINF,ISINF) @@ -299,7 +324,7 @@ rpn_parse(void *key_hash,char *expr,long (*lookup)(void *,char*)){ #undef match_op - else if ((sscanf(expr,"%29[_A-Za-z0-9]%n", + else if ((sscanf(expr, DEF_NAM_FMT "%n", vname,&pos) == 1) && ((rpnp[steps].ptr = (*lookup)(key_hash,vname)) != -1)){ rpnp[steps].op = OP_VARIABLE; @@ -397,10 +422,10 @@ rpn_calc(rpnp_t *rpnp, rpnstack_t *rpnstack, long data_idx, * row in the rra (skip over non-relevant * data sources) */ + rpnstack -> s[++stptr] = *(rpnp[rpi].data); if (data_idx % rpnp[rpi].step == 0){ rpnp[rpi].data += rpnp[rpi].ds_cnt; } - rpnstack -> s[++stptr] = *(rpnp[rpi].data); } break; case OP_PREV: @@ -410,6 +435,13 @@ rpn_calc(rpnp_t *rpnp, rpnstack_t *rpnstack, long data_idx, rpnstack -> s[++stptr] = output[output_idx-1]; } break; + case OP_PREV_OTHER: + if ((output_idx-1) <= 0) { + rpnstack -> s[++stptr] = DNAN; + } else { + rpnstack -> s[++stptr] = rpnp[rpnp[rpi].ptr].data[output_idx-1]; + } + break; case OP_UNKN: rpnstack -> s[++stptr] = DNAN; break;