[master] 689256a Isolate length manipulations of objects.

Poul-Henning Kamp phk at FreeBSD.org
Tue Aug 19 11:05:27 CEST 2014


commit 689256a2088ea301a16b5910590cfb79f116043a
Author: Poul-Henning Kamp <phk at FreeBSD.org>
Date:   Tue Aug 19 09:05:03 2014 +0000

    Isolate length manipulations of objects.

diff --git a/bin/varnishd/cache/cache.h b/bin/varnishd/cache/cache.h
index 4166f40..2026cd8 100644
--- a/bin/varnishd/cache/cache.h
+++ b/bin/varnishd/cache/cache.h
@@ -803,7 +803,7 @@ struct busyobj *VBO_GetBusyObj(struct worker *, const struct req *);
 void VBO_DerefBusyObj(struct worker *wrk, struct busyobj **busyobj);
 void VBO_Free(struct busyobj **vbo);
 void VBO_extend(struct busyobj *, ssize_t);
-ssize_t VBO_waitlen(struct busyobj *bo, ssize_t l);
+ssize_t VBO_waitlen(struct busyobj *, struct dstat *, ssize_t l);
 void VBO_setstate(struct busyobj *bo, enum busyobj_state_e next);
 void VBO_waitstate(struct busyobj *bo, enum busyobj_state_e want);
 
@@ -1061,6 +1061,7 @@ enum objiter_status {
 struct objiter *ObjIterBegin(struct worker *, struct objcore *);
 enum objiter_status ObjIter(struct objiter *, void **, ssize_t *);
 void ObjIterEnd(struct objiter **);
+void ObjExtend(struct objcore *, struct dstat *, ssize_t l);
 void ObjTrimStore(struct objcore *, struct dstat *);
 unsigned ObjGetXID(struct objcore *, struct dstat *);
 uint64_t ObjGetLen(struct objcore *oc, struct dstat *ds);
diff --git a/bin/varnishd/cache/cache_busyobj.c b/bin/varnishd/cache/cache_busyobj.c
index abbf03f..a3f4092 100644
--- a/bin/varnishd/cache/cache_busyobj.c
+++ b/bin/varnishd/cache/cache_busyobj.c
@@ -218,7 +218,6 @@ VBO_DerefBusyObj(struct worker *wrk, struct busyobj **pbo)
 void
 VBO_extend(struct busyobj *bo, ssize_t l)
 {
-	struct storage *st;
 
 	CHECK_OBJ_NOTNULL(bo, BUSYOBJ_MAGIC);
 	CHECK_OBJ_NOTNULL(bo->vfc, VFP_CTX_MAGIC);
@@ -226,27 +225,29 @@ VBO_extend(struct busyobj *bo, ssize_t l)
 		return;
 	assert(l > 0);
 	Lck_Lock(&bo->mtx);
-	st = VTAILQ_LAST(&bo->vfc->body->list, storagehead);
-	CHECK_OBJ_NOTNULL(st, STORAGE_MAGIC);
-	st->len += l;
-	bo->vfc->body->len += l;
+	ObjExtend(bo->vfc->oc, bo->stats, l);
 	AZ(pthread_cond_broadcast(&bo->cond));
 	Lck_Unlock(&bo->mtx);
 }
 
 ssize_t
-VBO_waitlen(struct busyobj *bo, ssize_t l)
+VBO_waitlen(struct busyobj *bo, struct dstat *ds, ssize_t l)
 {
+	ssize_t rv;
+
+	CHECK_OBJ_NOTNULL(bo, BUSYOBJ_MAGIC);
+	AN(ds);
 	Lck_Lock(&bo->mtx);
+	rv = ObjGetLen(bo->fetch_objcore, ds);
 	while (1) {
-		assert(l <= bo->vfc->body->len || bo->state == BOS_FAILED);
-		if (bo->vfc->body->len > l || bo->state >= BOS_FINISHED)
+		assert(l <= rv || bo->state == BOS_FAILED);
+		if (rv > l || bo->state >= BOS_FINISHED)
 			break;
 		(void)Lck_CondWait(&bo->cond, &bo->mtx, 0);
+		rv = ObjGetLen(bo->fetch_objcore, ds);
 	}
-	l = bo->vfc->body->len;
 	Lck_Unlock(&bo->mtx);
-	return (l);
+	return (rv);
 }
 
 void
diff --git a/bin/varnishd/cache/cache_http1_deliver.c b/bin/varnishd/cache/cache_http1_deliver.c
index 202ae12..e4d26b1 100644
--- a/bin/varnishd/cache/cache_http1_deliver.c
+++ b/bin/varnishd/cache/cache_http1_deliver.c
@@ -97,7 +97,7 @@ v1d_dorange(struct req *req, struct busyobj *bo, const char *r)
 
 	/* We must snapshot the length if we're streaming from the backend */
 	if (bo != NULL)
-		len = VBO_waitlen(bo, -1);
+		len = VBO_waitlen(bo, &req->wrk->stats, -1);
 	else
 		len = ObjGetLen(req->objcore, &req->wrk->stats);
 
@@ -340,7 +340,7 @@ V1D_Deliver(struct req *req, struct busyobj *bo)
 		l = -1;
 		while (req->objcore->busyobj) {
 			assert(bo != NULL);
-			l = VBO_waitlen(bo, l);
+			l = VBO_waitlen(bo, &req->wrk->stats, l);
 		}
 		ESI_DeliverChild(req);
 	} else if (req->res_mode & RES_GUNZIP ||
diff --git a/bin/varnishd/cache/cache_obj.c b/bin/varnishd/cache/cache_obj.c
index 04fd764..ed47b1e 100644
--- a/bin/varnishd/cache/cache_obj.c
+++ b/bin/varnishd/cache/cache_obj.c
@@ -117,7 +117,7 @@ ObjIter(struct objiter *oi, void **p, ssize_t *l)
 	} else {
 		ol = oi->len;
 		while (1) {
-			nl = VBO_waitlen(oi->bo, ol);
+			nl = VBO_waitlen(oi->bo, &oi->wrk->stats, ol);
 			if (nl != ol)
 				break;
 			if (oi->bo->state == BOS_FINISHED)
@@ -166,6 +166,29 @@ ObjIterEnd(struct objiter **oi)
 	*oi = NULL;
 }
 
+/*--------------------------------------------------------------------
+ */
+
+void
+ObjExtend(struct objcore *oc, struct dstat *ds, ssize_t l)
+{
+	struct object *o;
+	struct storage *st;
+
+	CHECK_OBJ_NOTNULL(oc, OBJCORE_MAGIC);
+
+	o = obj_getobj(oc, ds);
+	CHECK_OBJ_NOTNULL(o, OBJECT_MAGIC);
+	st = VTAILQ_LAST(&o->body->list, storagehead);
+	CHECK_OBJ_NOTNULL(st, STORAGE_MAGIC);
+	assert(st->len + l <= st->space);
+	st->len += l;
+	o->body->len += l;
+}
+
+/*--------------------------------------------------------------------
+ */
+
 void
 ObjTrimStore(struct objcore *oc, struct dstat *ds)
 {



More information about the varnish-commit mailing list