Skip to content

Commit

Permalink
core: pv - new parameters to control the size of pv cache
Browse files Browse the repository at this point in the history
- pv_cache_limit - the limit how many pv declarations in the cache
  after which an action is taken. Default value is 2048
- pv_cache_action - specify what action to be done when the size
  of pv cache is exceeded. If 0, print an warning log message when
  the limit is exceeded. If 1, warning log messages is printed and
  the cache systems tries to drop a $sht(...) declaration. Default is 0

This tries to cope better with the situation of declaring too many
variables when using kemi scripts

(cherry picked from commit 6dc9ee1)
  • Loading branch information
miconda committed Nov 21, 2017
1 parent b26e95d commit efe8504
Show file tree
Hide file tree
Showing 5 changed files with 97 additions and 4 deletions.
6 changes: 6 additions & 0 deletions src/core/cfg.lex
Expand Up @@ -437,6 +437,8 @@ KILL_TIMEOUT "exit_timeout"|"ser_kill_timeout"
MAX_WLOOPS "max_while_loops"
PVBUFSIZE "pv_buffer_size"
PVBUFSLOTS "pv_buffer_slots"
PVCACHELIMIT "pv_cache_limit"
PVCACHEACTION "pv_cache_action"
HTTP_REPLY_PARSE "http_reply_hack"|"http_reply_parse"
VERSION_TABLE_CFG "version_table"
VERBOSE_STARTUP "verbose_startup"
Expand Down Expand Up @@ -917,6 +919,10 @@ IMPORTFILE "import_file"
return PVBUFSIZE; }
<INITIAL>{PVBUFSLOTS} { count(); yylval.strval=yytext;
return PVBUFSLOTS; }
<INITIAL>{PVCACHELIMIT} { count(); yylval.strval=yytext;
return PVCACHELIMIT; }
<INITIAL>{PVCACHEACTION} { count(); yylval.strval=yytext;
return PVCACHEACTION; }
<INITIAL>{HTTP_REPLY_PARSE} { count(); yylval.strval=yytext;
return HTTP_REPLY_PARSE; }
<INITIAL>{VERSION_TABLE_CFG} { count(); yylval.strval=yytext; return VERSION_TABLE_CFG;}
Expand Down
8 changes: 7 additions & 1 deletion src/core/cfg.y
Expand Up @@ -475,6 +475,8 @@ extern char *default_routename;
%token MAX_WLOOPS
%token PVBUFSIZE
%token PVBUFSLOTS
%token PVCACHELIMIT
%token PVCACHEACTION
%token HTTP_REPLY_PARSE
%token VERSION_TABLE_CFG
%token VERBOSE_STARTUP
Expand Down Expand Up @@ -1554,8 +1556,12 @@ assign_stm:
| MAX_WLOOPS EQUAL error { yyerror("number expected"); }
| PVBUFSIZE EQUAL NUMBER { pv_set_buffer_size($3); }
| PVBUFSIZE EQUAL error { yyerror("number expected"); }
| PVBUFSLOTS EQUAL NUMBER { pv_set_buffer_slots($3); }
| PVBUFSLOTS EQUAL NUMBER { default_core_cfg.pv_cache_limit=$3; }
| PVBUFSLOTS EQUAL error { yyerror("number expected"); }
| PVCACHELIMIT EQUAL NUMBER { default_core_cfg.pv_cache_action=$3; }
| PVCACHELIMIT EQUAL error { yyerror("number expected"); }
| PVCACHEACTION EQUAL NUMBER { pv_set_buffer_slots($3); }
| PVCACHEACTION EQUAL error { yyerror("number expected"); }
| HTTP_REPLY_PARSE EQUAL NUMBER { http_reply_parse=$3; }
| HTTP_REPLY_PARSE EQUAL error { yyerror("boolean value expected"); }
| VERBOSE_STARTUP EQUAL NUMBER { ksr_verbose_startup=$3; }
Expand Down
12 changes: 9 additions & 3 deletions src/core/cfg_core.c
Expand Up @@ -120,7 +120,9 @@ struct cfg_group_core default_core_cfg = {
L_DBG, /*!< latency cfg log */
L_ERR, /*!< latency log */
0, /*!< latency limit db */
0 /*!< latency limit action */
0, /*!< latency limit action */
2048, /*!< pv_cache_limit */
0 /*!< pv_cache_action */
};

void *core_cfg = &default_core_cfg;
Expand Down Expand Up @@ -323,8 +325,12 @@ cfg_def_t core_cfg_def[] = {
{"latency_log", CFG_VAR_INT|CFG_ATOMIC, 0, 0, 0, 0,
"log level for latency limits alert messages"},
{"latency_limit_db", CFG_VAR_INT|CFG_ATOMIC, 0, 0, 0, 0,
"limit is ms for alerting on time consuming db commands"},
"limit in ms for alerting on time consuming db commands"},
{"latency_limit_action", CFG_VAR_INT|CFG_ATOMIC, 0, 0, 0, 0,
"limit is ms for alerting on time consuming config actions"},
"limit in ms for alerting on time consuming config actions"},
{"pv_cache_limit", CFG_VAR_INT|CFG_ATOMIC, 0, 0, 0, 0,
"limit to alert if too many vars in pv cache"},
{"pv_cache_action", CFG_VAR_INT|CFG_ATOMIC, 0, 0, 0, 0,
"action to do if too many vars in pv cache"},
{0, 0, 0, 0, 0, 0}
};
2 changes: 2 additions & 0 deletions src/core/cfg_core.h
Expand Up @@ -109,6 +109,8 @@ struct cfg_group_core {
int latency_log; /*!< log level for latency limits messages */
int latency_limit_db; /*!< alert limit of running db commands */
int latency_limit_action; /*!< alert limit of running cfg actions */
int pv_cache_limit; /*!< alert limit of having too many vars in pv cache */
int pv_cache_action; /*!< action to be taken on pv cache limit */
};

extern struct cfg_group_core default_core_cfg;
Expand Down
73 changes: 73 additions & 0 deletions src/core/pvapi.c
Expand Up @@ -59,6 +59,8 @@ static int _pv_table_set = 0;

static pv_cache_t* _pv_cache[PV_CACHE_SIZE];
static int _pv_cache_set = 0;
static int _pv_cache_counter = 0;
static int _pv_cache_drop_index = 0;

/**
*
Expand Down Expand Up @@ -254,6 +256,67 @@ int pv_table_add(pv_export_t *e)
return 0;
}

/**
*
*/
int pv_cache_drop(void)
{
int i;
pv_cache_t *pvp;
pv_cache_t *pvi;

if(_pv_cache_set==0) {
LM_DBG("PV cache not initialized\n");
return 0;
}
/* round-robin on slots to find a $sht(...) to drop */
_pv_cache_drop_index = (_pv_cache_drop_index + 1) % PV_CACHE_SIZE;
for(i=_pv_cache_drop_index; i<PV_CACHE_SIZE; i++) {
pvi = _pv_cache[i];
pvp = NULL;
while(pvi) {
if(pvi->pvname.len>5 && strncmp(pvi->pvname.s, "$sht(", 5)==0) {
LM_DBG("dropping from pv cache [%d]: %.*s\n", i,
pvi->pvname.len, pvi->pvname.s);
if(pvp) {
pvp->next = pvi->next;
} else {
_pv_cache[i] = pvi->next;
}
if(pvi->spec.pvp.pvn.nfree) {
pvi->spec.pvp.pvn.nfree((void*)(&pvi->spec.pvp.pvn));
}
pkg_free(pvi);
return 1;
}
pvi = pvi->next;
}
}
for(i=0; i<_pv_cache_drop_index; i++) {
pvi = _pv_cache[i];
pvp = NULL;
while(pvi) {
if(pvi->pvname.len>5 && strncmp(pvi->pvname.s, "$sht(", 5)==0) {
LM_DBG("dropping from pv cache [%d]: %.*s\n", i,
pvi->pvname.len, pvi->pvname.s);
if(pvp) {
pvp->next = pvi->next;
} else {
_pv_cache[i] = pvi->next;
}
if(pvi->spec.pvp.pvn.nfree) {
pvi->spec.pvp.pvn.nfree((void*)(&pvi->spec.pvp.pvn));
}
pkg_free(pvi);
return 1;
}
pvi = pvi->next;
}
}
LM_WARN("no suitable variable found to drop from pv cache\n");
return 0;
}

/**
*
*/
Expand All @@ -268,6 +331,16 @@ pv_spec_t* pv_cache_add(str *name)
LM_DBG("PV cache not initialized, doing it now\n");
pv_init_cache();
}
if(_pv_cache_counter+1>=cfg_get(core, core_cfg, pv_cache_limit)) {
if(_pv_cache_counter+1==cfg_get(core, core_cfg, pv_cache_limit)) {
LM_WARN("pv cache limit is going to be exceeded"
" - pkg memory may get filled with pv declarations\n");
} else {
if(cfg_get(core, core_cfg, pv_cache_action)==1) {
pv_cache_drop();
}
}
}
pvid = get_hash1_raw(name->s, name->len);
pvn = (pv_cache_t*)pkg_malloc(sizeof(pv_cache_t) + name->len + 1);
if(pvn==0)
Expand Down

0 comments on commit efe8504

Please sign in to comment.