r5565 - trunk/varnish-cache/bin/varnishd
phk at varnish-cache.org
phk at varnish-cache.org
Sun Nov 21 00:59:48 CET 2010
Author: phk
Date: 2010-11-21 00:59:48 +0100 (Sun, 21 Nov 2010)
New Revision: 5565
Modified:
trunk/varnish-cache/bin/varnishd/storage_persistent.c
Log:
The -spersistemt objcore->obj translation must use the object index
rather than the pointer, otherwise a number of nasty issues appear.
Modified: trunk/varnish-cache/bin/varnishd/storage_persistent.c
===================================================================
--- trunk/varnish-cache/bin/varnishd/storage_persistent.c 2010-11-20 23:58:43 UTC (rev 5564)
+++ trunk/varnish-cache/bin/varnishd/storage_persistent.c 2010-11-20 23:59:48 UTC (rev 5565)
@@ -645,7 +645,7 @@
}
/*---------------------------------------------------------------------
- * objcore methods for zombie objects
+ * objcore methods for persistent objects
*/
static struct object *
@@ -653,38 +653,42 @@
{
struct object *o;
struct smp_seg *sg;
- struct smp_object *so;
+ unsigned smp_index;
- CAST_OBJ_NOTNULL(sg, oc->priv2, SMP_SEG_MAGIC);
+ /* Some calls are direct, but they should match anyway */
+ assert(oc->methods->getobj == smp_oc_getobj);
- /*
- * XXX: failed checks here should fail gracefully and not assert
- */
- so = oc->priv;
- xxxassert(so >= sg->objs && so <= sg->objs + sg->nalloc2);
+ CHECK_OBJ_NOTNULL(oc, OBJCORE_MAGIC);
+ if (wrk == NULL)
+ AZ(oc->flags & OC_F_NEEDFIXUP);
- o = so->ptr;
+ CAST_OBJ_NOTNULL(sg, oc->priv2, SMP_SEG_MAGIC);
+ smp_index = (uintptr_t) oc->priv;
+ assert(smp_index < sg->nalloc2);
+ o = sg->objs[smp_index].ptr;
CHECK_OBJ_NOTNULL(o, OBJECT_MAGIC);
- if (wrk == NULL)
- AZ(oc->flags & OC_F_NEEDFIXUP);
+ /*
+ * If this flag is not set, it will not be, and the lock is not
+ * needed to test it.
+ */
+ if (!(oc->flags & OC_F_NEEDFIXUP))
+ return (o);
+ AN(wrk);
+ Lck_Lock(&sg->sc->mtx);
+ /* Check again, we might have raced. */
if (oc->flags & OC_F_NEEDFIXUP) {
- AN(wrk);
- Lck_Lock(&sg->sc->mtx);
- if (oc->flags & OC_F_NEEDFIXUP) {
- oc->flags &= ~OC_F_NEEDFIXUP;
+ /* refcnt is >=1 because the object is in the hash */
+ o->objcore = oc;
- /* refcnt is one because the object is in the hash */
- o->objcore = oc;
-
- sg->nfixed++;
- wrk->stats.n_object++;
- wrk->stats.n_vampireobject--;
- }
- Lck_Unlock(&sg->sc->mtx);
+ sg->nfixed++;
+ wrk->stats.n_object++;
+ wrk->stats.n_vampireobject--;
+ oc->flags &= ~OC_F_NEEDFIXUP;
}
+ Lck_Unlock(&sg->sc->mtx);
return (o);
}
@@ -880,7 +884,7 @@
{
struct smp_object *so;
struct objcore *oc;
- uint32_t no;
+ uint32_t no, n;
double t_now = TIM_real();
struct smp_signctx ctx[1];
@@ -902,14 +906,15 @@
no = sg->p.nalloc;
/* Clear the bogus "hold" count */
sg->nobj = 0;
- for (;no > 0; so++,no--) {
+ n = 0;
+ for (;no > 0; so++,no--,n++) {
if (so->ttl < t_now)
continue;
HSH_Prealloc(sp);
oc = sp->wrk->nobjcore;
oc->flags |= OC_F_NEEDFIXUP | OC_F_LRUDONTMOVE;
oc->flags &= ~OC_F_BUSY;
- oc->priv = so;
+ oc->priv = (void*)(uintptr_t)n;
oc->priv2 = sg;
oc->methods = &smp_oc_methods;
oc->ban = BAN_RefBan(oc, so->ban, sc->tailban);
@@ -1373,14 +1378,6 @@
sg->nalloc1++;
sc->objreserv += sizeof (struct smp_object);
assert(sc->objreserv <= smp_spaceleft(sg));
- /*
- * NB: Tricky.
- * We can not use the smp_getobj() method yet, because the
- * smp_object's position is not finalized until the segment
- * closes. Fortunately we don't need to either, because newly
- * created objects will never regress into NEEDFIXUP state,
- * so the default oc->methods, will do just fine.
- */
*sgp = sg;
}
@@ -1453,6 +1450,10 @@
so->ptr = o;
so->ban = o->ban_t;
+ oc->priv = (void*)(uintptr_t)(o->smp_index);
+ oc->priv2 = sg;
+ oc->methods = &smp_oc_methods;
+
Lck_Unlock(&sc->mtx);
return (o);
}
More information about the varnish-commit
mailing list