Skip to content

Commit

Permalink
Merge pull request #1580 from kamailio/bench_branch_pull
Browse files Browse the repository at this point in the history
Bench branch pull
  • Loading branch information
miconda committed Jul 3, 2018
2 parents a8d4ca2 + 71d1c72 commit 4ccbb45
Show file tree
Hide file tree
Showing 3 changed files with 267 additions and 1 deletion.
185 changes: 184 additions & 1 deletion src/modules/benchmark/benchmark.c
Expand Up @@ -244,6 +244,9 @@ void bm_reset_timer(int i)
bm_mycfg->tindex[i]->last_sum = 0;
bm_mycfg->tindex[i]->global_max = 0;
bm_mycfg->tindex[i]->global_min = 0xffffffff;
bm_mycfg->tindex[i]->period_sum = 0;
bm_mycfg->tindex[i]->period_max = 0;
bm_mycfg->tindex[i]->period_min = 0xffffffff;
}

void reset_timers(void)
Expand Down Expand Up @@ -361,6 +364,11 @@ int _bm_log_timer(unsigned int id)
bm_mycfg->tindex[id]->global_max,
((double)bm_mycfg->tindex[id]->sum)/bm_mycfg->tindex[id]->calls);

/* Fill data for last period. */
bm_mycfg->tindex[id]->period_sum = bm_mycfg->tindex[id]->last_sum;
bm_mycfg->tindex[id]->period_max = bm_mycfg->tindex[id]->last_max;
bm_mycfg->tindex[id]->period_min = bm_mycfg->tindex[id]->last_min;

bm_mycfg->tindex[id]->last_sum = 0;
bm_mycfg->tindex[id]->last_max = 0;
bm_mycfg->tindex[id]->last_min = 0xffffffff;
Expand Down Expand Up @@ -610,6 +618,167 @@ void bm_rpc_loglevel(rpc_t* rpc, void* ctx)
bm_mycfg->loglevel = v1;
}

/**
* Internal buffer to convert llu numbers into strings.
*/
#define BUFFER_S_LEN 100
static char buffer_s[BUFFER_S_LEN];

/**
* Create a RPC structure for a timer.
*
* /return 0 on success.
*/
int bm_rpc_timer_struct(rpc_t* rpc, void* ctx, int id)
{
void *handle; /* Handle for RPC structure. */

/* Create empty structure and obtain its handle */
if (rpc->add(ctx, "{", &handle) < 0) {
return -1;
}

int enabled = timer_active(id);

if (rpc->struct_add(handle, "s", "name", bm_mycfg->tindex[id]->name) < 0) {
return -1;
}

if (rpc->struct_add(handle, "s", "state", (enabled==0)?"disabled":"enabled") < 0) {
return -1;
}

if (rpc->struct_add(handle, "d", "id", id) < 0) {
return -1;
}

if (rpc->struct_add(handle, "d", "granularity", bm_mycfg->granularity) < 0) {
return -1;
}

/* We use a string to represent long long unsigned integers. */
int len;
len = snprintf(buffer_s, BUFFER_S_LEN, "%llu", bm_mycfg->tindex[id]->period_sum);
if (len <= 0 || len >= BUFFER_S_LEN) {
LM_ERR("Buffer overflow\n");
return -1;
}
if (rpc->struct_add(handle, "s", "period_sum", buffer_s) < 0) {
return -1;
}

len = snprintf(buffer_s, BUFFER_S_LEN, "%llu", bm_mycfg->tindex[id]->period_min);
if (len <= 0 || len >= BUFFER_S_LEN) {
LM_ERR("Buffer overflow\n");
return -1;
}
if (rpc->struct_add(handle, "s", "period_min", buffer_s) < 0) {
return -1;
}

len = snprintf(buffer_s, BUFFER_S_LEN, "%llu", bm_mycfg->tindex[id]->period_max);
if (len <= 0 || len >= BUFFER_S_LEN) {
LM_ERR("Buffer overflow\n");
return -1;
}
if (rpc->struct_add(handle, "s", "period_max", buffer_s) < 0) {
return -1;
}

if (bm_mycfg->granularity > 0) {
double media = ((double)bm_mycfg->tindex[id]->period_sum)/bm_mycfg->granularity;

if (rpc->struct_add(handle, "f", "period_media", media) < 0) {
return -1;
}
}

len = snprintf(buffer_s, BUFFER_S_LEN, "%llu", bm_mycfg->tindex[id]->calls);
if (len <= 0 || len >= BUFFER_S_LEN) {
LM_ERR("Buffer overflow\n");
return -1;
}
if (rpc->struct_add(handle, "s", "calls", buffer_s) < 0) {
return -1;
}

len = snprintf(buffer_s, BUFFER_S_LEN, "%llu", bm_mycfg->tindex[id]->sum);
if (len <= 0 || len >= BUFFER_S_LEN) {
LM_ERR("Buffer overflow\n");
return -1;
}
if (rpc->struct_add(handle, "s", "sum", buffer_s) < 0) {
return -1;
}

len = snprintf(buffer_s, BUFFER_S_LEN, "%llu", bm_mycfg->tindex[id]->global_min);
if (len <= 0 || len >= BUFFER_S_LEN) {
LM_ERR("Buffer overflow\n");
return -1;
}
if (rpc->struct_add(handle, "s", "global_min", buffer_s) < 0) {
return -1;
}

len = snprintf(buffer_s, BUFFER_S_LEN, "%llu", bm_mycfg->tindex[id]->global_max);
if (len <= 0 || len >= BUFFER_S_LEN) {
LM_ERR("Buffer overflow\n");
return -1;
}
if (rpc->struct_add(handle, "s", "global_max", buffer_s) < 0) {
return -1;
}

if (bm_mycfg->tindex[id]->calls > 0) {
double media = ((double)bm_mycfg->tindex[id]->sum)/bm_mycfg->tindex[id]->calls;

if (rpc->struct_add(handle, "f", "global_media", media) < 0) {
return -1;
}
}

return 0;
}

void bm_rpc_timer_list(rpc_t* rpc, void* ctx)
{
int id;

for (id = 0; id < bm_mycfg->nrtimers; id++) {

if (bm_rpc_timer_struct(rpc, ctx, id)) {
LM_ERR("Failure writing RPC structure for timer: %d\n", id);
return;
}

} /* for (id = 0; id < bm_mycfg->nrtimers; id++) */

return;
}

void bm_rpc_timer_name_list(rpc_t* rpc, void* ctx)
{
char *name = NULL;
unsigned int id = 0;

if(rpc->scan(ctx, "s", &name) < 1) {
LM_WARN("invalid timer name\n");
rpc->fault(ctx, 400, "Invalid timer name");
return;
}
if(_bm_register_timer(name, 0, &id)!=0) {
rpc->fault(ctx, 500, "Register timer failure");
return;
}

if (bm_rpc_timer_struct(rpc, ctx, id)) {
LM_ERR("Failure writing RPC structure for timer: %d\n", id);
return;
}

return;
}

static const char* bm_rpc_enable_global_doc[2] = {
"Enable/disable benchmarking",
0
Expand All @@ -630,6 +799,16 @@ static const char* bm_rpc_loglevel_doc[2] = {
0
};

static const char* bm_rpc_timer_list_doc[2] = {
"List all timers",
0
};

static const char* bm_rpc_timer_name_list_doc[2] = {
"List a timer based on its name",
0
};

rpc_export_t bm_rpc_cmds[] = {
{"benchmark.enable_global", bm_rpc_enable_global,
bm_rpc_enable_global_doc, 0},
Expand All @@ -639,6 +818,10 @@ rpc_export_t bm_rpc_cmds[] = {
bm_rpc_granularity_doc, 0},
{"benchmark.loglevel", bm_rpc_loglevel,
bm_rpc_loglevel_doc, 0},
{"benchmark.timer_list", bm_rpc_timer_list,
bm_rpc_timer_list_doc, 0},
{"benchmark.timer_name_list", bm_rpc_timer_name_list,
bm_rpc_timer_name_list_doc, 0},
{0, 0, 0, 0}
};

Expand Down Expand Up @@ -683,4 +866,4 @@ int mod_register(char *path, int *dlflags, void *p1, void *p2)

/*@} */

/* End of file */
/* End of file */
3 changes: 3 additions & 0 deletions src/modules/benchmark/benchmark.h
Expand Up @@ -66,6 +66,9 @@ typedef struct benchmark_timer
unsigned long long last_min; /* Maximum ... */
unsigned long long global_max; /* Global minimum, since start */
unsigned long long global_min; /* ... maximum ... */
unsigned long long period_sum; /* Sum for last completed period (between granularity) */
unsigned long long period_max; /* Maximum for last completed period ... */
unsigned long long period_min; /* Minimum for last completed period ... */
struct benchmark_timer *next;
} benchmark_timer_t;

Expand Down
80 changes: 80 additions & 0 deletions src/modules/benchmark/doc/benchmark_admin.xml
Expand Up @@ -332,6 +332,86 @@ bm_log_timer("test");
Modifies the module log level. See "loglevel" variable.
</para>
</section>
<section id="benchmark.rpc.timer_list">
<title><function moreinfo="none">benchmark.timer_list</function></title>
<para>
List data for all timers (Last complete period and global data)
Displays info close to the one output in the log by using a RPC structure.
period_sum, period_min and period_media show data for last granularity
period already completed.
</para>
<example>
<title>List all timers</title>
<programlisting format="linespecific">
...
&kamcmd; benchmark.timer_list
{
name: test
state: enabled
id: 0
granularity: 2
period_sum: 69
period_min: 22
period_max: 47
period_media: 34.500000
calls: 4
sum: 217
global_min: 22
global_max: 88
global_media: 54.250000
}
{
name: test2
state: enabled
id: 1
granularity: 2
period_sum: 122
period_min: 25
period_max: 97
period_media: 61.000000
calls: 4
sum: 349
global_min: 25
global_max: 151
global_media: 87.250000
}
...
</programlisting>
</example>
</section>
<section id="benchmark.rpc.timer_name_list">
<title><function moreinfo="none">benchmark.timer_name_list</function></title>
<para>
List data for one timer based on its name (Last complete period and global data)
It displays info close to the one output in the log by using a RPC structure.
period_sum, period_min and period_media show data for last granularity
period already completed.
</para>
<example>
<title>List one timer</title>
<programlisting format="linespecific">
...
&kamcmd; benchmark.timer_name_list test
{
name: test
state: enabled
id: 0
granularity: 2
period_sum: 69
period_min: 22
period_max: 47
period_media: 34.500000
calls: 4
sum: 217
global_min: 22
global_max: 88
global_media: 54.250000
}
...
</programlisting>
</example>
</section>

</section>

<section>
Expand Down

0 comments on commit 4ccbb45

Please sign in to comment.