[AMF metrics] Initial histogram support

Version of histogram support without ogs_metrics_spec_new_ex().
Buckets are now, just like labels, passed to ogs_metrics_spec_new() as a pointer.
This commit is contained in:
Gaber Stare 2023-03-06 11:44:30 +00:00 committed by Sukchan Lee
parent 7e1848f5de
commit 6f593432a4
9 changed files with 104 additions and 8 deletions

View File

@ -33,6 +33,7 @@ typedef struct ogs_metrics_server_s ogs_metrics_server_t;
typedef enum ogs_metrics_metric_type_s {
OGS_METRICS_METRIC_TYPE_COUNTER,
OGS_METRICS_METRIC_TYPE_GAUGE,
OGS_METRICS_METRIC_TYPE_HISTOGRAM,
} ogs_metrics_metric_type_t;
typedef struct ogs_metrics_context_s {
@ -42,6 +43,31 @@ typedef struct ogs_metrics_context_s {
uint16_t metrics_port;
} ogs_metrics_context_t;
typedef enum ogs_metrics_histogram_bucket_type_s {
OGS_METRICS_HISTOGRAM_BUCKET_TYPE_VARIABLE,
OGS_METRICS_HISTOGRAM_BUCKET_TYPE_LINEAR,
OGS_METRICS_HISTOGRAM_BUCKET_TYPE_EXPONENTIAL,
} ogs_metrics_histogram_bucket_type_t;
typedef struct ogs_metrics_histogram_bucket_params_s {
ogs_metrics_histogram_bucket_type_t type;
unsigned int count;
#define OGS_METRICS_HIST_VAR_BUCKETS_MAX 10
union {
struct {
float start;
float width;
} lin;
struct {
float start;
float factor;
} exp;
struct {
float buckets[OGS_METRICS_HIST_VAR_BUCKETS_MAX];
} var;
};
} ogs_metrics_histogram_params_t;
typedef struct ogs_metrics_context_s ogs_metrics_context_t;
void ogs_metrics_context_init(void);
void ogs_metrics_context_open(ogs_metrics_context_t *ctx);
@ -65,7 +91,8 @@ void ogs_metrics_spec_final(ogs_metrics_context_t *ctx);
ogs_metrics_spec_t *ogs_metrics_spec_new(
ogs_metrics_context_t *ctx, ogs_metrics_metric_type_t type,
const char *name, const char *description,
int initial_val, unsigned int num_labels, const char **labels);
int initial_val, unsigned int num_labels, const char ** labels,
ogs_metrics_histogram_params_t *histogram_params);
void ogs_metrics_spec_free(ogs_metrics_spec_t *spec);
typedef struct ogs_metrics_inst_s ogs_metrics_inst_t;

View File

@ -339,7 +339,8 @@ void ogs_metrics_spec_final(ogs_metrics_context_t *ctx)
ogs_metrics_spec_t *ogs_metrics_spec_new(
ogs_metrics_context_t *ctx, ogs_metrics_metric_type_t type,
const char *name, const char *description,
int initial_val, unsigned int num_labels, const char ** labels)
int initial_val, unsigned int num_labels, const char ** labels,
ogs_metrics_histogram_params_t *histogram_params)
{
ogs_metrics_spec_t *spec;
unsigned int i;
@ -372,6 +373,49 @@ ogs_metrics_spec_t *ogs_metrics_spec_new(
spec->prom = prom_gauge_new(spec->name, spec->description,
spec->num_labels, (const char **)spec->labels);
break;
case OGS_METRICS_METRIC_TYPE_HISTOGRAM: {
prom_histogram_buckets_t *buckets;
switch (histogram_params->type) {
case OGS_METRICS_HISTOGRAM_BUCKET_TYPE_EXPONENTIAL:
buckets = prom_histogram_buckets_exponential(histogram_params->exp.start,
histogram_params->exp.factor, histogram_params->count);
ogs_assert(buckets);
break;
case OGS_METRICS_HISTOGRAM_BUCKET_TYPE_LINEAR:
buckets = prom_histogram_buckets_linear(histogram_params->lin.start,
histogram_params->lin.width, histogram_params->count);
ogs_assert(buckets);
break;
case OGS_METRICS_HISTOGRAM_BUCKET_TYPE_VARIABLE:
{
double *upper_bounds;
buckets = (prom_histogram_buckets_t *)prom_malloc(sizeof(prom_histogram_buckets_t));
ogs_assert(buckets);
ogs_assert(histogram_params->count <= OGS_METRICS_HIST_VAR_BUCKETS_MAX);
buckets->count = histogram_params->count;
upper_bounds = (double *)prom_malloc(
sizeof(double) * histogram_params->count);
ogs_assert(upper_bounds);
for (i = 0; i < histogram_params->count; i++) {
upper_bounds[i] = histogram_params->var.buckets[i];
if (i > 0)
ogs_assert(upper_bounds[i] > upper_bounds[i - 1]);
}
buckets->upper_bounds = upper_bounds;
break;
}
default:
ogs_assert_if_reached();
break;
}
spec->prom = prom_histogram_new(spec->name, spec->description,
buckets, spec->num_labels, (const char **)spec->labels);
ogs_assert(spec->prom);
break;
}
default:
ogs_assert_if_reached();
break;
@ -477,6 +521,10 @@ void ogs_metrics_inst_add(ogs_metrics_inst_t *inst, int val)
else
prom_gauge_sub(inst->spec->prom, (double)-1.0*(double)val, (const char **)inst->label_values);
break;
case OGS_METRICS_METRIC_TYPE_HISTOGRAM:
ogs_assert(val >= 0);
prom_histogram_observe(inst->spec->prom, (double)val, (const char **)inst->label_values);
break;
default:
ogs_assert_if_reached();
break;

View File

@ -70,7 +70,8 @@ void ogs_metrics_spec_final(ogs_metrics_context_t *ctx)
ogs_metrics_spec_t *ogs_metrics_spec_new(
ogs_metrics_context_t *ctx, ogs_metrics_metric_type_t type,
const char *name, const char *description,
int initial_val, unsigned int num_labels, const char ** labels)
int initial_val, unsigned int num_labels, const char ** labels,
ogs_metrics_histogram_params_t *histogram_params)
{
return (ogs_metrics_spec_t *)1;
}

View File

@ -10,6 +10,7 @@ typedef struct amf_metrics_spec_def_s {
int initial_val;
unsigned int num_labels;
const char **labels;
ogs_metrics_histogram_params_t histogram_params;
} amf_metrics_spec_def_t;
/* Helper generic functions: */
@ -39,8 +40,10 @@ static int amf_metrics_init_spec(ogs_metrics_context_t *ctx,
for (i = 0; i < len; i++) {
dst[i] = ogs_metrics_spec_new(ctx, src[i].type,
src[i].name, src[i].description,
src[i].initial_val, src[i].num_labels, src[i].labels);
src[i].initial_val, src[i].num_labels, src[i].labels,
&src[i].histogram_params);
}
return OGS_OK;
}
@ -135,6 +138,18 @@ amf_metrics_spec_def_t amf_metrics_spec_def_global[_AMF_METR_GLOB_MAX] = {
.name = "fivegs_amffunction_mm_confupdatesucc",
.description = "Number of UE Configuration Update complete messages received by the AMF",
},
/* Global Histograms: */
[AMF_METR_GLOB_HIST_REG_TIME] = {
.type = OGS_METRICS_METRIC_TYPE_HISTOGRAM,
.name = "fivegs_amffunction_rm_regtime",
.description = "Time of registration procedure",
.histogram_params = {
.type = OGS_METRICS_HISTOGRAM_BUCKET_TYPE_EXPONENTIAL,
.count = 8,
.exp.start = 20,
.exp.factor = 2,
},
},
};
int amf_metrics_init_inst_global(void)
{

View File

@ -25,6 +25,7 @@ typedef enum amf_metric_type_global_s {
AMF_METR_GLOB_CTR_AMF_AUTH_REJECT,
AMF_METR_GLOB_CTR_MM_CONF_UPDATE,
AMF_METR_GLOB_CTR_MM_CONF_UPDATE_SUCC,
AMF_METR_GLOB_HIST_REG_TIME,
_AMF_METR_GLOB_MAX,
} amf_metric_type_global_t;
extern ogs_metrics_inst_t *amf_metrics_inst_global[_AMF_METR_GLOB_MAX];

View File

@ -39,7 +39,8 @@ static int mme_metrics_init_spec(ogs_metrics_context_t *ctx,
for (i = 0; i < len; i++) {
dst[i] = ogs_metrics_spec_new(ctx, src[i].type,
src[i].name, src[i].description,
src[i].initial_val, src[i].num_labels, src[i].labels);
src[i].initial_val, src[i].num_labels, src[i].labels,
NULL);
}
return OGS_OK;
}

View File

@ -40,7 +40,8 @@ static int pcf_metrics_init_spec(ogs_metrics_context_t *ctx,
for (i = 0; i < len; i++) {
dst[i] = ogs_metrics_spec_new(ctx, src[i].type,
src[i].name, src[i].description,
src[i].initial_val, src[i].num_labels, src[i].labels);
src[i].initial_val, src[i].num_labels, src[i].labels,
NULL);
}
return OGS_OK;
}

View File

@ -39,7 +39,8 @@ static int smf_metrics_init_spec(ogs_metrics_context_t *ctx,
for (i = 0; i < len; i++) {
dst[i] = ogs_metrics_spec_new(ctx, src[i].type,
src[i].name, src[i].description,
src[i].initial_val, src[i].num_labels, src[i].labels);
src[i].initial_val, src[i].num_labels, src[i].labels,
NULL);
}
return OGS_OK;
}

View File

@ -40,7 +40,8 @@ static int upf_metrics_init_spec(ogs_metrics_context_t *ctx,
for (i = 0; i < len; i++) {
dst[i] = ogs_metrics_spec_new(ctx, src[i].type,
src[i].name, src[i].description,
src[i].initial_val, src[i].num_labels, src[i].labels);
src[i].initial_val, src[i].num_labels, src[i].labels,
NULL);
}
return OGS_OK;
}