From 77ca4cbeda3e26576a9e02fedcbf85bafa22a1d5 Mon Sep 17 00:00:00 2001 From: =?utf8?q?Ji=C5=99=C3=AD=20Filipovi=C4=8D?= Date: Fri, 23 Jul 2010 13:23:22 +0000 Subject: [PATCH] create larger hash table instead of switching to linear search when some hash table is full --- org.glite.lb.server/src/stats.c | 57 +++++++++++++++++++++++++++++++---------- org.glite.lb.server/src/stats.h | 5 +++- 2 files changed, 48 insertions(+), 14 deletions(-) diff --git a/org.glite.lb.server/src/stats.c b/org.glite.lb.server/src/stats.c index 7cf1bbe..aaee282 100644 --- a/org.glite.lb.server/src/stats.c +++ b/org.glite.lb.server/src/stats.c @@ -37,7 +37,7 @@ limitations under the License. #include "stats.h" -#define GROUPS_HASHTABLE_SIZE 8192 +#define GROUPS_HASHTABLE_SIZE 1024 static int stats_inc_counter(edg_wll_Context,const edg_wll_JobStat *,edg_wll_Stats *); static int stats_record_duration(edg_wll_Context,const edg_wll_JobStat *,const edg_wll_JobStat *,edg_wll_Stats *); @@ -106,7 +106,8 @@ int edg_wll_InitStatistics(edg_wll_Context ctx) stats[i].htab = (struct hsearch_data*)malloc(sizeof(*(stats[i].htab))); memset(stats[i].htab, 0, sizeof(*(stats[i].htab))); - if (!hcreate_r(GROUPS_HASHTABLE_SIZE, stats[i].htab)){ + stats[i].htab_size = GROUPS_HASHTABLE_SIZE; + if (!hcreate_r(stats[i].htab_size, stats[i].htab)){ glite_common_log(LOG_CATEGORY_CONTROL, LOG_PRIORITY_WARN, "Cannot create hash table for stats!"); @@ -165,6 +166,43 @@ int edg_wll_UpdateStatistics( return 0; } +static int stats_double_htable(edg_wll_Stats *stats){ + struct edg_wll_stats_group *g; + ENTRY search, *found; + int i; + + glite_common_log(LOG_CATEGORY_LB_SERVER, LOG_PRIORITY_INFO, + "Hash table full, refilling."); + hdestroy_r(stats->htab); + memset(stats->htab, 0, sizeof(*(stats->htab))); + stats->htab_size *= 2; + if (!hcreate_r(stats->htab_size, stats->htab)){ + glite_common_log(LOG_CATEGORY_CONTROL, + LOG_PRIORITY_WARN, + "Cannot enlarge hash table for stats! Using linear search instead."); + free(stats->htab); + stats->htab = NULL; + return -1; + } + for (i=0; igrpno; i++) { + g = (struct edg_wll_stats_group *) ( + ((char *) stats->map) + stats->grpsize * i + ); + search.key = strdup(g->sig); + search.data = (void*)g; + if (! hsearch_r(search, ENTER, &found, stats->htab)){ + glite_common_log(LOG_CATEGORY_LB_SERVER, + LOG_PRIORITY_WARN, + "Unexpected error in hsearch_r, switching to linear search!"); + hdestroy_r(stats->htab); + free(stats->htab); + stats->htab = NULL; + return -1; + } + } + return 0; +} + static struct edg_wll_stats_archive *archive_skip( const struct edg_wll_stats_archive *a, int len) @@ -202,11 +240,7 @@ static int stats_remap(edg_wll_Stats *stats) search.key = strdup(g->sig); search.data = (void*)g; if (!hsearch_r(search, ENTER, &found, stats->htab)){ - glite_common_log(LOG_CATEGORY_LB_SERVER, - LOG_PRIORITY_WARN, - "Hash table full, using linear search instead!"); - hdestroy_r(stats->htab); - stats->htab = NULL; + stats_double_htable(stats); // all is filled now, can break break; } } @@ -248,6 +282,7 @@ static int stats_search_group(edg_wll_Context ctx, const edg_wll_JobStat *jobsta struct edg_wll_stats_archive *a; ENTRY search, *found; + asprintf(&jobstat->destination, "fake dest %i", rand()%10); sig = str2md5base64(jobstat->destination); stats_search_existing_group(stats, g, sig); @@ -287,18 +322,14 @@ static int stats_search_group(edg_wll_Context ctx, const edg_wll_JobStat *jobsta } strcpy((*g)->sig,sig); - strncpy((*g)->destination, jobstat->destination, 256); + strncpy((*g)->destination, jobstat->destination, STATS_DEST_SIZE); (*g)->last_update = jobstat->stateEnterTime.tv_sec; //now; if (stats->htab){ search.key = strdup(sig); search.data = (void*)(*g); if (!hsearch_r(search, ENTER, &found, stats->htab)){ - glite_common_log(LOG_CATEGORY_LB_SERVER, - LOG_PRIORITY_WARN, - "Hash table full, using linear search instead!"); - hdestroy_r(stats->htab); - stats->htab = NULL; + stats_double_htable(stats); } } } diff --git a/org.glite.lb.server/src/stats.h b/org.glite.lb.server/src/stats.h index df3d49e..30963d5 100644 --- a/org.glite.lb.server/src/stats.h +++ b/org.glite.lb.server/src/stats.h @@ -29,6 +29,8 @@ limitations under the License. #include "glite/lb/jobstat.h" #include "glite/lb/query_rec.h" +#define STATS_DEST_SIZE 256 + int edg_wll_InitStatistics(edg_wll_Context); int edg_wll_UpdateStatistics( @@ -52,7 +54,7 @@ struct edg_wll_stats_archive { struct edg_wll_stats_group { int grpno; char sig[33]; - char destination[256]; + char destination[STATS_DEST_SIZE]; time_t last_update; struct edg_wll_stats_archive archive[1]; }; @@ -71,6 +73,7 @@ typedef struct { int fd; struct edg_wll_stats_group *map; int grpno,grpsize; + unsigned htab_size; struct hsearch_data *htab; } edg_wll_Stats; -- 1.8.2.3