[experimental-ims] 0dd1ee2 Complete the busyobj management code by adding a (default-on) per worker cache and a wrapper structure (needed for $param sized elements) and two new stats counters.
Geoff Simmons
geoff at varnish-cache.org
Mon Jan 9 21:52:49 CET 2012
commit 0dd1ee21b69f043ad55219c592454d17dd8739db
Author: Poul-Henning Kamp <phk at FreeBSD.org>
Date: Thu Dec 8 07:12:33 2011 +0000
Complete the busyobj management code by adding a (default-on) per
worker cache and a wrapper structure (needed for $param sized elements)
and two new stats counters.
diff --git a/bin/varnishd/cache/cache.h b/bin/varnishd/cache/cache.h
index 0ee855b..4435c32 100644
--- a/bin/varnishd/cache/cache.h
+++ b/bin/varnishd/cache/cache.h
@@ -106,6 +106,7 @@ struct pool;
struct sess;
struct sesspool;
struct vbc;
+struct vbo;
struct vef_priv;
struct vrt_backend;
struct vsb;
@@ -293,7 +294,7 @@ struct worker {
struct objhead *nobjhead;
struct objcore *nobjcore;
struct waitinglist *nwaitinglist;
- /* struct busyobj *nbusyobj; */
+ struct vbo *nvbo;
void *nhashpriv;
struct dstat stats;
@@ -496,9 +497,7 @@ oc_getlru(const struct objcore *oc)
struct busyobj {
unsigned magic;
#define BUSYOBJ_MAGIC 0x23b95567
- struct lock mtx;
- /* Members passed this line are cleared on reuse */
- unsigned refcount;
+ struct vbo *vbo;
uint8_t *vary;
unsigned is_gzip;
@@ -700,8 +699,9 @@ double BAN_Time(const struct ban *ban);
/* cache_busyobj.c */
void VBO_Init(void);
struct busyobj *VBO_GetBusyObj(struct worker *wrk);
-struct busyobj *VBO_RefBusyObj(struct busyobj *busyobj);
+void VBO_RefBusyObj(const struct busyobj *busyobj);
void VBO_DerefBusyObj(struct worker *wrk, struct busyobj **busyobj);
+void VBO_Free(struct vbo **vbo);
/* cache_center.c [CNT] */
void CNT_Session(struct sess *sp);
diff --git a/bin/varnishd/cache/cache_busyobj.c b/bin/varnishd/cache/cache_busyobj.c
index 32bad7e..4272725 100644
--- a/bin/varnishd/cache/cache_busyobj.c
+++ b/bin/varnishd/cache/cache_busyobj.c
@@ -1,8 +1,8 @@
/*-
- * Copyright (c) 2006 Verdens Gang AS
- * Copyright (c) 2006-2011 Varnish Software AS
+ * Copyright (c) 2011 Varnish Software AS
* All rights reserved.
*
+ * Author: Martin Blix Grydeland <martin at varnish-software.com>
* Author: Poul-Henning Kamp <phk at phk.freebsd.dk>
*
* Redistribution and use in source and binary forms, with or without
@@ -38,101 +38,141 @@
#include "cache.h"
-static struct lock nbusyobj_mtx;
-static struct busyobj *nbusyobj;
+struct vbo {
+ unsigned magic;
+#define VBO_MAGIC 0xde3d8223
+ struct lock mtx;
+ unsigned refcount;
+ struct busyobj bo;
+};
+
+static struct lock vbo_mtx;
+static struct vbo *nvbo;
void
VBO_Init(void)
{
- Lck_New(&nbusyobj_mtx, lck_nbusyobj);
- nbusyobj = NULL;
+ Lck_New(&vbo_mtx, lck_busyobj);
+ nvbo = NULL;
}
/*--------------------------------------------------------------------
* BusyObj handling
*/
-static struct busyobj *
-vbo_NewBusyObj(void)
+static struct vbo *
+vbo_New(void)
{
- struct busyobj *busyobj;
+ struct vbo *vbo;
- ALLOC_OBJ(busyobj, BUSYOBJ_MAGIC);
- AN(busyobj);
- Lck_New(&busyobj->mtx, lck_busyobj);
- return (busyobj);
+ ALLOC_OBJ(vbo, VBO_MAGIC);
+ AN(vbo);
+ Lck_New(&vbo->mtx, lck_busyobj);
+ return (vbo);
}
-static void
-vbe_FreeBusyObj(struct busyobj *busyobj)
+void
+VBO_Free(struct vbo **vbop)
{
- CHECK_OBJ_NOTNULL(busyobj, BUSYOBJ_MAGIC);
- AZ(busyobj->refcount);
- Lck_Delete(&busyobj->mtx);
- FREE_OBJ(busyobj);
+ struct vbo *vbo;
+
+ AN(vbop);
+ vbo = *vbop;
+ *vbop = NULL;
+ CHECK_OBJ_NOTNULL(vbo, VBO_MAGIC);
+ AZ(vbo->refcount);
+ Lck_Delete(&vbo->mtx);
+ FREE_OBJ(vbo);
}
struct busyobj *
VBO_GetBusyObj(struct worker *wrk)
{
- struct busyobj *busyobj = NULL;
-
- (void)wrk;
- Lck_Lock(&nbusyobj_mtx);
- if (nbusyobj != NULL) {
- CHECK_OBJ_NOTNULL(nbusyobj, BUSYOBJ_MAGIC);
- busyobj = nbusyobj;
- nbusyobj = NULL;
- memset((char *)busyobj + offsetof(struct busyobj, refcount), 0,
- sizeof *busyobj - offsetof(struct busyobj, refcount));
+ struct vbo *vbo = NULL;
+
+ CHECK_OBJ_NOTNULL(wrk, WORKER_MAGIC);
+
+ if (wrk->nvbo != NULL) {
+ vbo = wrk->nvbo;
+ wrk->nvbo = NULL;
+ }
+
+ if (vbo == NULL) {
+ Lck_Lock(&vbo_mtx);
+
+ vbo = nvbo;
+ nvbo = NULL;
+
+ if (vbo == NULL)
+ VSC_C_main->busyobj_alloc++;
+
+ Lck_Unlock(&vbo_mtx);
}
- Lck_Unlock(&nbusyobj_mtx);
- if (busyobj == NULL)
- busyobj = vbo_NewBusyObj();
- AN(busyobj);
- busyobj->refcount = 1;
- busyobj->beresp = wrk->x_beresp;
- busyobj->bereq = wrk->x_bereq;
- return (busyobj);
+
+ if (vbo == NULL)
+ vbo = vbo_New();
+
+ CHECK_OBJ_NOTNULL(vbo, VBO_MAGIC);
+ AZ(vbo->refcount);
+ AZ(vbo->bo.magic);
+ vbo->refcount = 1;
+ vbo->bo.magic = BUSYOBJ_MAGIC;
+ vbo->bo.vbo = vbo;
+ vbo->bo.beresp = wrk->x_beresp;
+ vbo->bo.bereq = wrk->x_bereq;
+ return (&vbo->bo);
}
-struct busyobj *
-VBO_RefBusyObj(struct busyobj *busyobj)
+void
+VBO_RefBusyObj(const struct busyobj *busyobj)
{
+ struct vbo *vbo;
+
CHECK_OBJ_NOTNULL(busyobj, BUSYOBJ_MAGIC);
- Lck_Lock(&busyobj->mtx);
- assert(busyobj->refcount > 0);
- busyobj->refcount++;
- Lck_Unlock(&busyobj->mtx);
- return (busyobj);
+ vbo = busyobj->vbo;
+ CHECK_OBJ_NOTNULL(vbo, VBO_MAGIC);
+ Lck_Lock(&vbo->mtx);
+ assert(vbo->refcount > 0);
+ vbo->refcount++;
+ Lck_Unlock(&vbo->mtx);
}
void
VBO_DerefBusyObj(struct worker *wrk, struct busyobj **pbo)
{
- struct busyobj *busyobj;
+ struct busyobj *bo;
+ struct vbo *vbo;
+ unsigned r;
- (void)wrk;
- busyobj = *pbo;
- CHECK_OBJ_NOTNULL(busyobj, BUSYOBJ_MAGIC);
- Lck_Lock(&busyobj->mtx);
- assert(busyobj->refcount > 0);
- busyobj->refcount--;
+ CHECK_OBJ_NOTNULL(wrk, WORKER_MAGIC);
+ AN(pbo);
+ bo = *pbo;
*pbo = NULL;
- if (busyobj->refcount > 0) {
- Lck_Unlock(&busyobj->mtx);
- return;
- }
- Lck_Unlock(&busyobj->mtx);
-
- /* XXX Sanity checks e.g. AZ(busyobj->vbc) */
-
- Lck_Lock(&nbusyobj_mtx);
- if (nbusyobj == NULL) {
- nbusyobj = busyobj;
- busyobj = NULL;
+ CHECK_OBJ_NOTNULL(bo, BUSYOBJ_MAGIC);
+ vbo = bo->vbo;
+ CHECK_OBJ_NOTNULL(vbo, VBO_MAGIC);
+ Lck_Lock(&vbo->mtx);
+ assert(vbo->refcount > 0);
+ r = --vbo->refcount;
+ Lck_Unlock(&vbo->mtx);
+
+ if (r == 0) {
+ /* XXX: Sanity checks & cleanup */
+ memset(&vbo->bo, 0, sizeof vbo->bo);
+
+ if (cache_param->bo_cache && wrk->nvbo == NULL) {
+ wrk->nvbo = vbo;
+ } else {
+ Lck_Lock(&vbo_mtx);
+ if (nvbo == NULL) {
+ nvbo = vbo;
+ vbo = NULL;
+ } else
+ VSC_C_main->busyobj_free++;
+ Lck_Unlock(&vbo_mtx);
+
+ if (vbo != NULL)
+ VBO_Free(&vbo);
+ }
}
- Lck_Unlock(&nbusyobj_mtx);
- if (busyobj != NULL)
- vbe_FreeBusyObj(busyobj);
}
diff --git a/bin/varnishd/cache/cache_hash.c b/bin/varnishd/cache/cache_hash.c
index 675afea..6f6a85f 100644
--- a/bin/varnishd/cache/cache_hash.c
+++ b/bin/varnishd/cache/cache_hash.c
@@ -134,10 +134,8 @@ HSH_Cleanup(struct worker *wrk)
free(wrk->nhashpriv);
wrk->nhashpriv = NULL;
}
- /* if (wrk->nbusyobj != NULL) { */
- /* FREE_OBJ(wrk->nbusyobj); */
- /* wrk->nbusyobj = NULL; */
- /* } */
+ if (wrk->nvbo != NULL)
+ VBO_Free(&wrk->nvbo);
}
void
diff --git a/bin/varnishd/common/params.h b/bin/varnishd/common/params.h
index b9b758f..8fd777f 100644
--- a/bin/varnishd/common/params.h
+++ b/bin/varnishd/common/params.h
@@ -189,6 +189,8 @@ struct params {
struct vre_limits vre_limits;
+ unsigned bo_cache;
+
/* VSM dimensions */
ssize_t vsm_space;
ssize_t vsl_space;
diff --git a/bin/varnishd/mgt/mgt_param.c b/bin/varnishd/mgt/mgt_param.c
index e4be5d8..cc14e41 100644
--- a/bin/varnishd/mgt/mgt_param.c
+++ b/bin/varnishd/mgt/mgt_param.c
@@ -1105,6 +1105,14 @@ static const struct parspec input_parspec[] = {
MUST_RESTART,
"1M", "bytes"},
+ { "busyobj_worker_cache", tweak_bool,
+ &mgt_param.bo_cache, 0, 0,
+ "Cache free busyobj per worker thread."
+ "Disable this if you have very high hitrates and want"
+ "to save the memory of one busyobj per worker thread.",
+ 0,
+ "true", ""},
+
{ NULL, NULL, NULL }
};
diff --git a/include/tbl/vsc_f_main.h b/include/tbl/vsc_f_main.h
index a04767d..ab8415c 100644
--- a/include/tbl/vsc_f_main.h
+++ b/include/tbl/vsc_f_main.h
@@ -235,6 +235,20 @@ VSC_F(sess_dropped, uint64_t, 1, 'c',
" See also param queue_max."
)
+/*---------------------------------------------------------------------
+ * BusyObj
+ */
+
+VSC_F(busyobj_alloc, uint64_t, 1, 'c',
+ "Busyobj allocations",
+ "Number of busyobj structures allocated."
+)
+
+VSC_F(busyobj_free, uint64_t, 1, 'c',
+ "Busyobj freed",
+ "Number of busyobj structures freed."
+)
+
/*---------------------------------------------------------------------*/
VSC_F(n_sess_mem, uint64_t, 0, 'i', "N struct sess_mem", "")
More information about the varnish-commit
mailing list