[master] ac2e067 Remove the old sessmem allocator/freelist stuff, and replace with a run of the mill mempool.

Poul-Henning Kamp phk at varnish-cache.org
Sun Dec 25 11:29:28 CET 2011


commit ac2e067b0daced3cc24b16b0b14b7be10c5ceb27
Author: Poul-Henning Kamp <phk at FreeBSD.org>
Date:   Sun Dec 25 10:28:52 2011 +0000

    Remove the old sessmem allocator/freelist stuff, and replace with
    a run of the mill mempool.

diff --git a/bin/varnishd/cache/cache.h b/bin/varnishd/cache/cache.h
index d1dc4fb..9743398 100644
--- a/bin/varnishd/cache/cache.h
+++ b/bin/varnishd/cache/cache.h
@@ -634,9 +634,9 @@ struct sess {
 
 	/* Cross references ------------------------------------------*/
 
+	struct sesspool		*sesspool;
 	struct worker		*wrk;
 	struct req		*req;
-	struct sessmem		*mem;
 
 	/* Session related fields ------------------------------------*/
 
diff --git a/bin/varnishd/cache/cache_session.c b/bin/varnishd/cache/cache_session.c
index 92a7357..552c078 100644
--- a/bin/varnishd/cache/cache_session.c
+++ b/bin/varnishd/cache/cache_session.c
@@ -44,31 +44,16 @@
 #include "waiter/waiter.h"
 #include "vtim.h"
 
-/*--------------------------------------------------------------------*/
-
-struct sessmem {
-	unsigned		magic;
-#define SESSMEM_MAGIC		0x555859c5
-
-	struct sesspool		*pool;
-
-	unsigned		workspace;
-	uint16_t		nhttp;
-	void			*wsp;
-	VTAILQ_ENTRY(sessmem)	list;
+static unsigned ses_size = sizeof (struct sess);
 
-	struct sess		sess;
-};
+/*--------------------------------------------------------------------*/
 
 struct sesspool {
 	unsigned		magic;
 #define SESSPOOL_MAGIC		0xd916e202
 	struct pool		*pool;
-	VTAILQ_HEAD(,sessmem)	freelist;
-	struct lock		mtx;
-	unsigned		nsess;
-	unsigned		dly_free_cnt;
 	struct mempool		*mpl_req;
+	struct mempool		*mpl_sess;
 };
 
 /*--------------------------------------------------------------------
@@ -92,77 +77,14 @@ SES_Charge(struct sess *sp)
 }
 
 /*--------------------------------------------------------------------
- * This function allocates a session + assorted peripheral data
- * structures in one single malloc operation.
- */
-
-static struct sessmem *
-ses_sm_alloc(void)
-{
-	struct sessmem *sm;
-	unsigned char *p, *q;
-	unsigned nws;
-	uint16_t nhttp;
-	unsigned l, hl;
-
-	/*
-	 * It is not necessary to lock these, but we need to
-	 * cache them locally, to make sure we get a consistent
-	 * view of the value.
-	 */
-	nws = cache_param->sess_workspace;
-	nhttp = (uint16_t)cache_param->http_max_hdr;
-
-	hl = HTTP_estimate(nhttp);
-	l = sizeof *sm + nws + 2 * hl;
-	VSC_C_main->sessmem_size = l;
-	p = malloc(l);
-	if (p == NULL)
-		return (NULL);
-	q = p + l;
-
-	/* Don't waste time zeroing the workspace */
-	memset(p, 0, l - nws);
-
-	sm = (void*)p;
-	p += sizeof *sm;
-
-	sm->magic = SESSMEM_MAGIC;
-	sm->workspace = nws;
-	sm->nhttp = nhttp;
-
-	sm->http[0] = HTTP_create(p, nhttp);
-	p += hl;
-
-	sm->http[1] = HTTP_create(p, nhttp);
-	p += hl;
-
-	sm->wsp = p;
-	p += nws;
-
-	assert(p == q);
-
-	return (sm);
-}
-
-/*--------------------------------------------------------------------
  * This prepares a session for use, based on its sessmem structure.
  */
 
 static void
-ses_setup(struct sessmem *sm)
+ses_setup(struct sess *sp)
 {
-	struct sess *sp;
-
-	CHECK_OBJ_NOTNULL(sm, SESSMEM_MAGIC);
-	sp = &sm->sess;
-	memset(sp, 0, sizeof *sp);
 
-	/* We assume that the sess has been zeroed by the time we get here */
-	AZ(sp->magic);
-
-	sp->magic = SESS_MAGIC;
-	sp->mem = sm;
+	CHECK_OBJ_NOTNULL(sp, SESS_MAGIC);
 	sp->sockaddrlen = sizeof(sp->sockaddr);
 	sp->mysockaddrlen = sizeof(sp->mysockaddr);
 	sp->sockaddr.ss_family = sp->mysockaddr.ss_family = PF_UNSPEC;
@@ -178,39 +100,14 @@ ses_setup(struct sessmem *sm)
 struct sess *
 SES_New(struct worker *wrk, struct sesspool *pp)
 {
-	struct sessmem *sm;
 	struct sess *sp;
-	int do_alloc;
 
+	(void)wrk;					// XXX
 	CHECK_OBJ_NOTNULL(pp, SESSPOOL_MAGIC);
-
-	do_alloc = 0;
-	Lck_Lock(&pp->mtx);
-	sm = VTAILQ_FIRST(&pp->freelist);
-	if (sm != NULL) {
-		VTAILQ_REMOVE(&pp->freelist, sm, list);
-	} else if (pp->nsess < cache_param->max_sess) {
-		pp->nsess++;
-		do_alloc = 1;
-	}
-	wrk->stats.sessmem_free += pp->dly_free_cnt;
-	pp->dly_free_cnt = 0;
-	Lck_Unlock(&pp->mtx);
-	if (do_alloc) {
-		sm = ses_sm_alloc();
-		if (sm != NULL) {
-			wrk->stats.sessmem_alloc++;
-			sm->pool = pp;
-			ses_setup(sm);
-		} else {
-			wrk->stats.sessmem_fail++;
-		}
-	} else if (sm == NULL) {
-		wrk->stats.sessmem_limit++;
-	}
-	if (sm == NULL)
-		return (NULL);
-	sp = &sm->sess;
+	sp = MPL_Get(pp->mpl_sess, NULL);
+	sp->magic = SESS_MAGIC;
+	sp->sesspool = pp;
+	ses_setup(sp);
 	CHECK_OBJ_NOTNULL(sp, SESS_MAGIC);
 	return (sp);
 }
@@ -223,35 +120,15 @@ struct sess *
 SES_Alloc(void)
 {
 	struct sess *sp;
-	struct sessmem *sm;
 
-	sm = ses_sm_alloc();
-	AN(sm);
-	ses_setup(sm);
-	sp = &sm->sess;
-	sp->sockaddrlen = 0;
+	ALLOC_OBJ(sp, SESS_MAGIC);
+	AN(sp);
+	ses_setup(sp);
 	/* XXX: sp->req ? */
 	return (sp);
 }
 
 /*--------------------------------------------------------------------
- */
-
-static struct sesspool *
-ses_getpool(const struct sess *sp)
-{
-	struct sessmem *sm;
-	struct sesspool *pp;
-
-	CHECK_OBJ_NOTNULL(sp, SESS_MAGIC);
-	sm = sp->mem;
-	CHECK_OBJ_NOTNULL(sm, SESSMEM_MAGIC);
-	pp = sm->pool;
-	CHECK_OBJ_NOTNULL(pp, SESSPOOL_MAGIC);
-	return (pp);
-}
-
-/*--------------------------------------------------------------------
  * Schedule a session back on a work-thread from its pool
  */
 
@@ -260,9 +137,10 @@ SES_Schedule(struct sess *sp)
 {
 	struct sesspool *pp;
 
-	pp = ses_getpool(sp);
+	CHECK_OBJ_NOTNULL(sp, SESS_MAGIC);
 	AZ(sp->wrk);
-
+	pp = sp->sesspool;
+	CHECK_OBJ_NOTNULL(pp, SESSPOOL_MAGIC);
 	AN(pp->pool);
 
 	if (Pool_Schedule(pp->pool, sp)) {
@@ -325,14 +203,14 @@ void
 SES_Delete(struct sess *sp, const char *reason, double now)
 {
 	struct acct *b;
-	struct sessmem *sm;
 	struct worker *wrk;
 	struct sesspool *pp;
 
-	pp = ses_getpool(sp);
+	CHECK_OBJ_NOTNULL(sp, SESS_MAGIC);
+	pp = sp->sesspool;
+	CHECK_OBJ_NOTNULL(pp, SESSPOOL_MAGIC);
+	AN(pp->pool);
 
-	sm = sp->mem;
-	CHECK_OBJ_NOTNULL(sm, SESSMEM_MAGIC);
 	wrk = sp->wrk;
 	CHECK_OBJ_ORNULL(wrk, WORKER_MAGIC);
 
@@ -361,28 +239,8 @@ SES_Delete(struct sess *sp, const char *reason, double now)
 	    b->sess, b->req, b->pipe, b->pass,
 	    b->fetch, b->hdrbytes, b->bodybytes);
 
-	if (sm->workspace != cache_param->sess_workspace ||
-	    sm->nhttp != (uint16_t)cache_param->http_max_hdr ||
-	    pp->nsess > cache_param->max_sess) {
-		free(sm);
-		Lck_Lock(&pp->mtx);
-		if (wrk != NULL)
-			wrk->stats.sessmem_free++;
-		else
-			pp->dly_free_cnt++;
-		pp->nsess--;
-		Lck_Unlock(&pp->mtx);
-	} else {
-		/* Clean and prepare for reuse */
-		ses_setup(sm);
-		Lck_Lock(&pp->mtx);
-		if (wrk != NULL) {
-			wrk->stats.sessmem_free += pp->dly_free_cnt;
-			pp->dly_free_cnt = 0;
-		}
-		VTAILQ_INSERT_HEAD(&pp->freelist, sm, list);
-		Lck_Unlock(&pp->mtx);
-	}
+	MPL_Free(pp->mpl_sess, sp);
+
 }
 
 /*--------------------------------------------------------------------
@@ -397,7 +255,11 @@ SES_GetReq(struct sess *sp)
 	unsigned sz, hl;
 	char *p;
 
-	pp = ses_getpool(sp);
+	CHECK_OBJ_NOTNULL(sp, SESS_MAGIC);
+	pp = sp->sesspool;
+	CHECK_OBJ_NOTNULL(pp, SESSPOOL_MAGIC);
+	AN(pp->pool);
+
 	AZ(sp->req);
 	sp->req = MPL_Get(pp->mpl_req, &sz);
 	AN(sp->req);
@@ -427,7 +289,10 @@ SES_ReleaseReq(struct sess *sp)
 {
 	struct sesspool *pp;
 
-	pp = ses_getpool(sp);
+	CHECK_OBJ_NOTNULL(sp, SESS_MAGIC);
+	pp = sp->sesspool;
+	CHECK_OBJ_NOTNULL(pp, SESSPOOL_MAGIC);
+	AN(pp->pool);
 	CHECK_OBJ_NOTNULL(sp->req, REQ_MAGIC);
 	MPL_AssertSane(sp->req);
 	MPL_Free(pp->mpl_req, sp->req);
@@ -447,33 +312,20 @@ SES_NewPool(struct pool *wp, unsigned pool_no)
 	ALLOC_OBJ(pp, SESSPOOL_MAGIC);
 	AN(pp);
 	pp->pool = wp;
-	VTAILQ_INIT(&pp->freelist);
-	Lck_New(&pp->mtx, lck_sessmem);
 	bprintf(nb, "req%u", pool_no);
 	pp->mpl_req = MPL_New(nb, &cache_param->req_pool,
 	    &cache_param->sess_workspace);
+	pp->mpl_sess = MPL_New(nb, &cache_param->sess_pool, &ses_size);
 	return (pp);
 }
 
 void
 SES_DeletePool(struct sesspool *pp, struct worker *wrk)
 {
-	struct sessmem *sm;
 
 	CHECK_OBJ_NOTNULL(pp, SESSPOOL_MAGIC);
 	CHECK_OBJ_NOTNULL(wrk, WORKER_MAGIC);
-	Lck_Lock(&pp->mtx);
-	while (!VTAILQ_EMPTY(&pp->freelist)) {
-		sm = VTAILQ_FIRST(&pp->freelist);
-		CHECK_OBJ_NOTNULL(sm, SESSMEM_MAGIC);
-		VTAILQ_REMOVE(&pp->freelist, sm, list);
-		FREE_OBJ(sm);
-		wrk->stats.sessmem_free++;
-		pp->nsess--;
-	}
-	AZ(pp->nsess);
-	Lck_Unlock(&pp->mtx);
-	Lck_Delete(&pp->mtx);
+	MPL_Destroy(&pp->mpl_sess);
 	MPL_Destroy(&pp->mpl_req);
 	FREE_OBJ(pp);
 }
diff --git a/bin/varnishd/common/params.h b/bin/varnishd/common/params.h
index 0a476d4..ca39ff7 100644
--- a/bin/varnishd/common/params.h
+++ b/bin/varnishd/common/params.h
@@ -201,4 +201,5 @@ struct params {
 
 	struct poolparam	vbc_pool;
 	struct poolparam	req_pool;
+	struct poolparam	sess_pool;
 };
diff --git a/bin/varnishd/mgt/mgt_param.c b/bin/varnishd/mgt/mgt_param.c
index 81aaf0d..36f96cd 100644
--- a/bin/varnishd/mgt/mgt_param.c
+++ b/bin/varnishd/mgt/mgt_param.c
@@ -1221,6 +1221,14 @@ static const struct parspec input_parspec[] = {
 		"   max_age -- max age of free element.\n",
 		0,
 		"10,100,10", ""},
+	{ "pool_sess", tweak_poolparam, &mgt_param.sess_pool, 0, 10000,
+		"Parameters for per worker pool session memory pool.\n"
+		"The three numbers are:\n"
+		"   min_pool -- minimum size of free pool.\n"
+		"   max_pool -- maximum size of free pool.\n"
+		"   max_age -- max age of free element.\n",
+		0,
+		"10,100,10", ""},
 
 	{ NULL, NULL, NULL }
 };



More information about the varnish-commit mailing list