]> err.no Git - varnish/commitdiff
On a cache-miss, insert only the (busy) objcore, leave the actual
authorphk <phk@d4fa192b-c00b-0410-8231-f00ffab90ce4>
Sat, 28 Feb 2009 18:18:23 +0000 (18:18 +0000)
committerphk <phk@d4fa192b-c00b-0410-8231-f00ffab90ce4>
Sat, 28 Feb 2009 18:18:23 +0000 (18:18 +0000)
object allocation and insertion for later in cache_center.c

For now, do it right away in cache_center, before going to STP_MISS.

git-svn-id: svn+ssh://projects.linpro.no/svn/varnish/trunk@3841 d4fa192b-c00b-0410-8231-f00ffab90ce4

varnish-cache/bin/varnishd/cache_center.c
varnish-cache/bin/varnishd/cache_hash.c
varnish-cache/bin/varnishd/hash_slinger.h

index 2e23fc8a8d1e284b7db4a4ac72041daa41a0deae..216099b2856ddff17625b5c3f2ca1e76ea0211e2 100644 (file)
@@ -652,7 +652,9 @@ DOT lookup -> miss [label="no",style=bold,color=blue,weight=2]
 static int
 cnt_lookup(struct sess *sp)
 {
+       struct objcore *oc;
        struct object *o;
+       struct objhead *oh;
 
        CHECK_OBJ_NOTNULL(sp, SESS_MAGIC);
        CHECK_OBJ_NOTNULL(sp->vcl, VCL_CONF_MAGIC);
@@ -663,9 +665,9 @@ cnt_lookup(struct sess *sp)
                assert(sp->handling == VCL_RET_HASH);
        }
 
-       o = HSH_Lookup(sp);
+       oc = HSH_Lookup(sp, &oh);
 
-       if (o == NULL) {
+       if (oc == NULL) {
                /*
                 * We lost the session to a busy object, disembark the
                 * worker thread.   The hash code to restart the session,
@@ -674,16 +676,31 @@ cnt_lookup(struct sess *sp)
                return (1);
        }
 
-       sp->obj = o;
+       CHECK_OBJ_NOTNULL(oh, OBJHEAD_MAGIC);
 
        /* If we inserted a new object it's a miss */
-       if (ObjIsBusy(sp->obj)) {
+       if (oc->flags & OC_F_BUSY) {
                VSL_stats->cache_miss++;
+
+               AZ(oc->obj);
+               o = sp->wrk->nobj;
+               sp->wrk->nobj = NULL;
+
+               o->objhead = oh;
+               o->objcore = oc;
+               oc->obj = o;
+               sp->obj = o;
+
+               BAN_NewObj(o);
                sp->step = STP_MISS;
                return (0);
        }
 
-       if (sp->obj->objcore->flags & OC_F_PASS) {
+       o = oc->obj;
+       CHECK_OBJ_NOTNULL(o, OBJECT_MAGIC);
+       sp->obj = o;
+
+       if (oc->flags & OC_F_PASS) {
                VSL_stats->cache_hitpass++;
                WSP(sp, SLT_HitPass, "%u", sp->obj->xid);
                HSH_Deref(sp->wrk, &sp->obj);
index b35f2d8e3cbf62cd0a3844982fcf147600809aba..599f8e732fc1b0377e6f185d3e8a3b8cd0850007 100644 (file)
@@ -264,13 +264,14 @@ HSH_AddString(struct sess *sp, const char *str)
        sp->lhashptr += l + 1;
 }
 
-struct object *
-HSH_Lookup(struct sess *sp)
+struct objcore *
+HSH_Lookup(struct sess *sp, struct objhead **poh)
 {
        struct worker *w;
        struct objhead *oh;
        struct objcore *oc;
-       struct object *o, *busy_o, *grace_o;
+       struct objcore *busy_oc, *grace_oc;
+       struct object *o;
 
        CHECK_OBJ_NOTNULL(sp, SESS_MAGIC);
        CHECK_OBJ_NOTNULL(sp->wrk, WORKER_MAGIC);
@@ -296,17 +297,19 @@ HSH_Lookup(struct sess *sp)
                Lck_Lock(&oh->mtx);
        }
 
-       busy_o = NULL;
-       grace_o = NULL;
-       o = NULL;
+       busy_oc = NULL;
+       grace_oc = NULL;
        VTAILQ_FOREACH(oc, &oh->objcs, list) {
+               CHECK_OBJ_NOTNULL(oc, OBJCORE_MAGIC);
+
+               if (oc->flags & OC_F_BUSY) {
+                       busy_oc = oc;
+                       continue;
+               }
+
                o = oc->obj;
                CHECK_OBJ_NOTNULL(o, OBJECT_MAGIC);
                
-               if (ObjIsBusy(o)) {
-                       busy_o = o;
-                       continue;
-               }
                if (!o->cacheable)
                        continue;
                if (o->ttl == 0)
@@ -322,33 +325,39 @@ HSH_Lookup(struct sess *sp)
 
                /* Remember any matching objects inside their grace period */
                if (o->ttl + HSH_Grace(o->grace) >= sp->t_req)
-                       grace_o = o;
+                       grace_oc = oc;
        }
-       if (oc == NULL)
-               o = NULL;
-       else
-               AN(o);
 
        /*
         * If we have seen a busy object, and have an object in grace,
         * use it, if req.grace is also satisified.
+        * XXX: Interesting footnote:  The busy object might be for a
+        * XXX: different "Vary:" than we sought.  We have no way of knowing
+        * XXX: this until the object is unbusy'ed, so in practice we
+        * XXX: serialize fetch of all Vary's if grace is possible.
         */
-       if (o == NULL && grace_o != NULL &&
-           busy_o != NULL &&
-           grace_o->ttl + HSH_Grace(sp->grace) >= sp->t_req)
-               o = grace_o;
+       if (oc == NULL && grace_oc != NULL && busy_oc != NULL) {
+               o = grace_oc->obj;
+               CHECK_OBJ_NOTNULL(o, OBJECT_MAGIC);
+               if (o->ttl + HSH_Grace(sp->grace) >= sp->t_req)
+                       oc = grace_oc;
+       }
+
+       if (oc != NULL) {
+               o = oc->obj;
+               CHECK_OBJ_NOTNULL(o, OBJECT_MAGIC);
 
-       if (o != NULL) {
                /* We found an object we like */
                o->refcnt++;
                if (o->hits < INT_MAX)
                        o->hits++;
                Lck_Unlock(&oh->mtx);
                assert(hash->deref(oh));
-               return (o);
+               *poh = oh;
+               return (oc);
        }
 
-       if (busy_o != NULL) {
+       if (busy_oc != NULL) {
                /* There are one or more busy objects, wait for them */
                if (sp->esis == 0)
                        VTAILQ_INSERT_TAIL(&oh->waitinglist, sp, list);
@@ -361,26 +370,17 @@ HSH_Lookup(struct sess *sp)
                return (NULL);
        }
 
-       /* Insert (precreated) object in objecthead */
-       o = w->nobj;
-       w->nobj = NULL;
-
+       /* Insert (precreated) objcore in objecthead */
        oc = w->nobjcore;
        w->nobjcore = NULL;
+       AN(oc->flags & OC_F_BUSY);
 
-       o->objhead = oh;
-       o->objcore = oc;
-       oc->obj = o;
        /* XXX: Should this not be ..._HEAD now ? */
        VTAILQ_INSERT_TAIL(&oh->objcs, oc, list);
        /* NB: do not deref objhead the new object inherits our reference */
        Lck_Unlock(&oh->mtx);
-       /*
-        * XXX: This may be too early, relative to pass objects.
-        * XXX: possibly move to when we commit to have it in the cache.
-        */
-       BAN_NewObj(o);
-       return (o);
+       *poh = oh;
+       return (oc);
 }
 
 static void
@@ -432,6 +432,7 @@ HSH_Unbusy(const struct sess *sp)
        o = sp->obj;
        CHECK_OBJ_NOTNULL(o, OBJECT_MAGIC);
        AN(ObjIsBusy(o));
+       assert(o->objcore->obj == o);
        assert(o->refcnt > 0);
        if (o->ws_o->overflow)
                VSL_stats->n_objoverflow++;
index e37297fc39fd1a7bb0fb9a6d53eefd415cd457f1..1e764613412ab662fde236a4abca3bf52e0d5fe1 100644 (file)
@@ -54,7 +54,7 @@ void HSH_Prealloc(struct sess *sp);
 void HSH_Cleanup(struct worker *w);
 void HSH_Freestore(struct object *o);
 void HSH_Copy(const struct sess *sp, struct objhead *o);
-struct object *HSH_Lookup(struct sess *sp);
+struct objcore *HSH_Lookup(struct sess *sp, struct objhead **poh);
 void HSH_Unbusy(const struct sess *sp);
 void HSH_Ref(struct object *o);
 void HSH_Drop(struct sess *sp);