summaryrefslogtreecommitdiff
path: root/src/perl/MMV/MMV.xs
diff options
context:
space:
mode:
authorIgor Pashev <pashev.igor@gmail.com>2014-10-26 12:33:50 +0400
committerIgor Pashev <pashev.igor@gmail.com>2014-10-26 12:33:50 +0400
commit47e6e7c84f008a53061e661f31ae96629bc694ef (patch)
tree648a07f3b5b9d67ce19b0fd72e8caa1175c98f1a /src/perl/MMV/MMV.xs
downloadpcp-debian.tar.gz
Debian 3.9.10debian/3.9.10debian
Diffstat (limited to 'src/perl/MMV/MMV.xs')
-rw-r--r--src/perl/MMV/MMV.xs381
1 files changed, 381 insertions, 0 deletions
diff --git a/src/perl/MMV/MMV.xs b/src/perl/MMV/MMV.xs
new file mode 100644
index 0000000..2ee6ff8
--- /dev/null
+++ b/src/perl/MMV/MMV.xs
@@ -0,0 +1,381 @@
+/*
+ * Copyright (c) 2009 Aconex. All Rights Reserved.
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+ * for more details.
+ */
+
+#include "pmapi.h"
+#include "mmv_stats.h"
+#include "EXTERN.h"
+#include "perl.h"
+#include "XSUB.h"
+
+static int
+list_to_metric(SV *list, mmv_metric_t *metric)
+{
+ int i, len;
+ SV **entry[8];
+ AV *mlist = (AV *) SvRV(list);
+
+ if (SvTYPE((SV *)mlist) != SVt_PVAV) {
+ warn("metric declaration is not an array reference");
+ return -1;
+ }
+ len = av_len(mlist) + 1;
+ if (len < 6) {
+ warn("too few entries in metric array reference");
+ return -1;
+ }
+ if (len > 8) {
+ warn("too many entries in metric array reference");
+ return -1;
+ }
+ for (i = 0; i < len; i++)
+ entry[i] = av_fetch(mlist, i, 0);
+
+ strncpy(metric->name, SvPV_nolen(*entry[0]), MMV_NAMEMAX);
+ metric->name[MMV_NAMEMAX-1] = '\0';
+ metric->item = SvIV(*entry[1]);
+ metric->type = SvIV(*entry[2]);
+ metric->indom = SvIV(*entry[3]);
+ i = SvIV(*entry[4]);
+ memcpy(&metric->dimension, &i, sizeof(pmUnits));
+ metric->semantics = SvIV(*entry[5]);
+ if (len > 6)
+ metric->shorttext = strdup(SvPV_nolen(*entry[6]));
+ else
+ metric->shorttext = NULL;
+ if (len > 7)
+ metric->helptext = strdup(SvPV_nolen(*entry[7]));
+ else
+ metric->helptext = NULL;
+ return 0;
+}
+
+static int
+list_to_instances(SV *list, mmv_instances_t **insts)
+{
+ mmv_instances_t *instances;
+ int i, len;
+ AV *inlist = (AV *) SvRV(list);
+
+ if (SvTYPE((SV *)inlist) != SVt_PVAV) {
+ warn("instances declaration is not an array reference");
+ return -1;
+ }
+ len = av_len(inlist) + 1;
+ if (len++ % 2) {
+ warn("odd number of entries in instance array reference");
+ return -1;
+ }
+
+ len /= 2;
+ instances = (mmv_instances_t *)calloc(len, sizeof(mmv_instances_t));
+ if (instances == NULL) {
+ warn("insufficient memory for instance array");
+ return -1;
+ }
+ for (i = 0; i < len; i++) {
+ SV **id = av_fetch(inlist, i*2, 0);
+ SV **name = av_fetch(inlist, i*2+1, 0);
+ instances[i].internal = SvIV(*id);
+ strncpy(instances[i].external, SvPV_nolen(*name), MMV_NAMEMAX);
+ instances[i].external[MMV_NAMEMAX-1] = '\0';
+ }
+ *insts = instances;
+ return len;
+}
+
+static int
+list_to_indom(SV *list, mmv_indom_t *indom)
+{
+ int i, len;
+ SV **entry[4];
+ AV *ilist = (AV *) SvRV(list);
+
+ if (SvTYPE((SV *)ilist) != SVt_PVAV) {
+ warn("indom declaration is not an array reference");
+ return -1;
+ }
+ len = av_len(ilist) + 1;
+ if (len < 2) {
+ warn("too few entries in indom array reference");
+ return -1;
+ }
+ if (len > 4) {
+ warn("too many entries in indom array reference");
+ return -1;
+ }
+ for (i = 0; i < len; i++)
+ entry[i] = av_fetch(ilist, i, 0);
+
+ indom->serial = SvIV(*entry[0]);
+ if ((i = list_to_instances(*entry[1], &indom->instances)) < 0)
+ return -1;
+ indom->count = i;
+ if (len > 2)
+ indom->shorttext = strdup(SvPV_nolen(*entry[2]));
+ else
+ indom->shorttext = NULL;
+ if (len > 3)
+ indom->helptext = strdup(SvPV_nolen(*entry[3]));
+ else
+ indom->helptext = NULL;
+ return 0;
+}
+
+static int
+list_to_metrics(SV *list, mmv_metric_t **metriclist, int *mcount)
+{
+ mmv_metric_t *metrics;
+ int i, len;
+ AV *mlist = (AV *) SvRV(list);
+
+ if (SvTYPE((SV *)mlist) != SVt_PVAV) {
+ warn("metrics list is not an array reference");
+ return -1;
+ }
+ len = av_len(mlist) + 1;
+ metrics = (mmv_metric_t *)calloc(len, sizeof(mmv_metric_t));
+ if (metrics == NULL) {
+ warn("insufficient memory for metrics array");
+ return -1;
+ }
+ for (i = 0; i < len; i++) {
+ SV **entry = av_fetch(mlist, i, 0);
+ if (list_to_metric(*entry, &metrics[i]) < 0)
+ break;
+ }
+ *metriclist = metrics;
+ *mcount = len;
+ return (i == len);
+}
+
+static int
+list_to_indoms(SV *list, mmv_indom_t **indomlist, int *icount)
+{
+ mmv_indom_t *indoms;
+ int i, len;
+ AV *ilist = (AV *) SvRV(list);
+
+ if (SvTYPE((SV *)ilist) != SVt_PVAV) {
+ warn("indoms list is not an array reference");
+ return -1;
+ }
+ len = av_len(ilist) + 1;
+ indoms = (mmv_indom_t *)calloc(len, sizeof(mmv_indom_t));
+ if (indoms == NULL) {
+ warn("insufficient memory for indoms array");
+ return -1;
+ }
+ for (i = 0; i < len; i++) {
+ SV **entry = av_fetch(ilist, i, 0);
+ if (list_to_indom(*entry, &indoms[i]) < 0)
+ break;
+ }
+ *indomlist = indoms;
+ *icount = len;
+ return (i == len);
+}
+
+
+MODULE = PCP::MMV PACKAGE = PCP::MMV
+
+void *
+mmv_stats_init(name,cl,fl,metrics,indoms)
+ char * name
+ int cl
+ int fl
+ SV * metrics
+ SV * indoms
+ PREINIT:
+ int i, j;
+ int mcount;
+ int icount;
+ mmv_metric_t * mlist;
+ mmv_indom_t * ilist;
+ CODE:
+ i = list_to_metrics(metrics, &mlist, &mcount);
+ j = list_to_indoms(indoms, &ilist, &icount);
+
+ if (i <= 0 || j <= 0) {
+ warn("mmv_stats_init: bad list conversion: metrics=%d indoms=%d\n", i, j);
+ RETVAL = NULL;
+ }
+ else {
+ RETVAL = mmv_stats_init(name, cl, fl, mlist, mcount, ilist, icount);
+ if (RETVAL == NULL)
+ warn("mmv_stats_init failed: %s\n", osstrerror());
+ }
+
+ for (i = 0; i < icount; i++) {
+ if (ilist[i].shorttext)
+ free(ilist[i].shorttext);
+ if (ilist[i].helptext)
+ free(ilist[i].helptext);
+ free(ilist[i].instances);
+ }
+ if (ilist)
+ free(ilist);
+ for (i = 0; i < mcount; i++) {
+ if (mlist[i].shorttext)
+ free(mlist[i].shorttext);
+ if (mlist[i].helptext)
+ free(mlist[i].helptext);
+ }
+ if (mlist)
+ free(mlist);
+
+ if (!RETVAL)
+ XSRETURN_UNDEF;
+ OUTPUT:
+ RETVAL
+
+void
+mmv_stats_stop(handle,name)
+ void * handle
+ char * name
+ CODE:
+ mmv_stats_stop(handle, name);
+
+int
+mmv_units(dim_space,dim_time,dim_count,scale_space,scale_time,scale_count)
+ unsigned int dim_space
+ unsigned int dim_time
+ unsigned int dim_count
+ unsigned int scale_space
+ unsigned int scale_time
+ unsigned int scale_count
+ PREINIT:
+ pmUnits units;
+ CODE:
+ units.pad = 0;
+ units.dimSpace = dim_space; units.scaleSpace = scale_space;
+ units.dimTime = dim_time; units.scaleTime = scale_time;
+ units.dimCount = dim_count; units.scaleCount = scale_count;
+ RETVAL = *(int *)(&units);
+ OUTPUT:
+ RETVAL
+
+pmAtomValue *
+mmv_lookup_value_desc(handle,metric,instance)
+ void * handle
+ char * metric
+ char * instance
+ CODE:
+ RETVAL = mmv_lookup_value_desc(handle, metric, instance);
+ OUTPUT:
+ RETVAL
+
+void
+mmv_inc_value(handle,atom,value)
+ void * handle
+ pmAtomValue * atom
+ double value
+ CODE:
+ mmv_inc_value(handle, atom, value);
+
+void
+mmv_set_value(handle,atom,value)
+ void * handle
+ pmAtomValue * atom
+ double value
+ CODE:
+ mmv_set_value(handle, atom, value);
+
+void
+mmv_set_string(handle,atom,string)
+ void * handle
+ pmAtomValue * atom
+ SV * string
+ PREINIT:
+ int length;
+ char * data;
+ CODE:
+ data = SvPV_nolen(string);
+ length = strlen(data);
+ mmv_set_string(handle, atom, data, length);
+
+void
+mmv_stats_add(handle,metric,instance,count)
+ void * handle
+ char * metric
+ char * instance
+ double count
+ CODE:
+ mmv_stats_add(handle, metric, instance, count);
+
+void
+mmv_stats_inc(handle,metric,instance)
+ void * handle
+ char * metric
+ char * instance
+ CODE:
+ mmv_stats_inc(handle, metric, instance);
+
+void
+mmv_stats_set(handle,metric,instance, value)
+ void * handle
+ char * metric
+ char * instance
+ double value
+ CODE:
+ mmv_stats_set(handle, metric, instance, value);
+
+void
+mmv_stats_add_fallback(handle,metric,instance,instance2,count)
+ void * handle
+ char * metric
+ char * instance
+ char * instance2
+ double count
+ CODE:
+ mmv_stats_add_fallback(handle, metric, instance, instance2, count);
+
+void
+mmv_stats_inc_fallback(handle,metric,instance,instance2)
+ void * handle
+ char * metric
+ char * instance
+ char * instance2
+ CODE:
+ mmv_stats_inc_fallback(handle, metric, instance, instance2);
+
+void
+mmv_stats_interval_start(handle,value,metric,instance)
+ void * handle
+ pmAtomValue * value
+ char * metric
+ char * instance
+ CODE:
+ mmv_stats_interval_start(handle, value, metric, instance);
+
+void
+mmv_stats_interval_end(handle, value)
+ void * handle
+ pmAtomValue * value
+ CODE:
+ mmv_stats_interval_end(handle, value);
+
+void
+mmv_stats_set_string(handle,metric,instance,string)
+ void * handle
+ char * metric
+ char * instance
+ SV * string
+ PREINIT:
+ int length;
+ char * data;
+ CODE:
+ data = SvPV_nolen(string);
+ length = strlen(data);
+ mmv_stats_set_strlen(handle, metric, instance, data, length);
+