Commit 1c8e6642 authored by Poul-Henning Kamp's avatar Poul-Henning Kamp

Add the first stab at a "restart" mechanism.

The intent is to be able to do things like:

	backend b1 {
		set backend.host = "fs.freebsd.dk";
		set backend.port = "82";
	}
	backend b2 {
		set backend.host = "fs.freebsd.dk";
		set backend.port = "81";
	}
	backend b3 {
		set backend.host = "fs.freebsd.dk";
		set backend.port = "80";
	}

	sub vcl_recv {
		remove req.http.cookie;
		if (req.restarts == 0) {
			set req.backend = b1;
		} else if (req.restarts == 1) {
			set req.backend = b2;
		} else {
			set req.backend = b3;
		}
	}

	sub vcl_fetch {
		if (obj.status != 200) {
			restart;
		}
	}




git-svn-id: http://www.varnish-cache.org/svn/trunk/varnish-cache@2067 d4fa192b-c00b-0410-8231-f00ffab90ce4
parent 6d9bf8b0
......@@ -278,6 +278,8 @@ struct sess {
int id;
unsigned xid;
int restarts;
struct worker *wrk;
socklen_t sockaddrlen;
......
......@@ -303,21 +303,30 @@ cnt_fetch(struct sess *sp)
VBE_free_bereq(sp->bereq);
sp->bereq = NULL;
if (i) {
if (0 && i) {
SYN_ErrorPage(sp, 503, "Error talking to backend", 30);
} else {
RFC2616_cache_policy(sp, &sp->obj->http); /* XXX -> VCL */
if (!i)
RFC2616_cache_policy(sp, &sp->obj->http); /* XXX -> VCL */
else
sp->obj->http.status = 503;
VCL_fetch_method(sp);
switch (sp->handling) {
case VCL_RET_ERROR:
case VCL_RET_RESTART:
sp->obj->ttl = 0;
sp->obj->cacheable = 0;
HSH_Unbusy(sp->obj);
HSH_Deref(sp->obj);
sp->obj = NULL;
sp->step = STP_ERROR;
if (sp->handling == VCL_RET_ERROR)
sp->step = STP_ERROR;
else {
sp->restarts++;
sp->step = STP_RECV;
}
return (0);
case VCL_RET_PASS:
sp->obj->pass = 1;
......@@ -696,40 +705,42 @@ cnt_recv(struct sess *sp)
{
int done;
AZ(sp->vcl);
AZ(sp->obj);
/* Update stats of various sorts */
VSL_stats->client_req++; /* XXX not locked */
sp->t_req = TIM_real();
sp->wrk->used = sp->t_req;
sp->wrk->acct.req++;
if (sp->restarts == 0) {
AZ(sp->vcl);
/* Update stats of various sorts */
VSL_stats->client_req++; /* XXX not locked */
sp->t_req = TIM_real();
sp->wrk->used = sp->t_req;
sp->wrk->acct.req++;
/* Assign XID and log */
sp->xid = ++xids; /* XXX not locked */
WSP(sp, SLT_ReqStart, "%s %s %u", sp->addr, sp->port, sp->xid);
/* Borrow VCL reference from worker thread */
VCL_Refresh(&sp->wrk->vcl);
sp->vcl = sp->wrk->vcl;
sp->wrk->vcl = NULL;
done = http_DissectRequest(sp);
if (done != 0) {
RES_Error(sp, done, NULL); /* XXX: STP_ERROR ? */
sp->step = STP_DONE;
return (0);
}
/* Assign XID and log */
sp->xid = ++xids; /* XXX not locked */
WSP(sp, SLT_ReqStart, "%s %s %u", sp->addr, sp->port, sp->xid);
sp->doclose = http_DoConnection(sp->http);
/* Borrow VCL reference from worker thread */
VCL_Refresh(&sp->wrk->vcl);
sp->vcl = sp->wrk->vcl;
sp->wrk->vcl = NULL;
/* By default we use the first backend */
AZ(sp->backend);
sp->backend = sp->vcl->backend[0];
CHECK_OBJ_NOTNULL(sp->backend, BACKEND_MAGIC);
done = http_DissectRequest(sp);
if (done != 0) {
RES_Error(sp, done, NULL); /* XXX: STP_ERROR ? */
sp->step = STP_DONE;
return (0);
/* XXX: Handle TRACE & OPTIONS of Max-Forwards = 0 */
}
sp->doclose = http_DoConnection(sp->http);
/* By default we use the first backend */
AZ(sp->backend);
sp->backend = sp->vcl->backend[0];
CHECK_OBJ_NOTNULL(sp->backend, BACKEND_MAGIC);
/* XXX: Handle TRACE & OPTIONS of Max-Forwards = 0 */
VCL_recv_method(sp);
sp->wantbody = (strcmp(sp->http->hd[HTTP_HDR_REQ].b, "HEAD") != 0);
......
......@@ -304,7 +304,7 @@ HSH_Deref(struct object *o)
if (r != 0)
return;
if (o->http.ws->s != NULL)
if (o->http.ws != NULL && o->http.ws->s != NULL)
free(o->http.ws->s);
if (o->vary != NULL)
......
......@@ -239,6 +239,9 @@ VRT_r_obj_status(const struct sess *sp)
{
CHECK_OBJ_NOTNULL(sp, SESS_MAGIC);
CHECK_OBJ_NOTNULL(sp->obj, OBJECT_MAGIC);
/* XXX: use http_GetStatus() */
if (sp->obj->http.status)
return (sp->obj->http.status);
return (atoi(sp->obj->http.hd[HTTP_HDR_STATUS].b));
}
......@@ -356,6 +359,16 @@ VREQ(proto, HTTP_HDR_PROTO)
/*--------------------------------------------------------------------*/
int
VRT_r_req_restarts(const struct sess *sp)
{
CHECK_OBJ_NOTNULL(sp, SESS_MAGIC);
return (sp->restarts);
}
/*--------------------------------------------------------------------*/
const char *
VRT_r_resp_proto(const struct sess *sp)
{
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment