[master] 4be6020 Split beresp.body status determination into transport protocol dependent (is there a C-L header ?), and semantic (ie: HEAD request doesn't have body, even if the response has C-L etc.)
Poul-Henning Kamp
phk at FreeBSD.org
Thu Sep 11 15:56:37 CEST 2014
commit 4be6020bd72be0f90d904f1bf5ccb56454015dcd
Author: Poul-Henning Kamp <phk at FreeBSD.org>
Date: Thu Sep 11 13:18:10 2014 +0000
Split beresp.body status determination into transport protocol
dependent (is there a C-L header ?), and semantic (ie: HEAD request
doesn't have body, even if the response has C-L etc.)
diff --git a/bin/varnishd/cache/cache.h b/bin/varnishd/cache/cache.h
index 8080082..b7591c8 100644
--- a/bin/varnishd/cache/cache.h
+++ b/bin/varnishd/cache/cache.h
@@ -1228,7 +1228,6 @@ void *WS_Printf(struct ws *ws, const char *fmt, ...) __printflike(2, 3);
/* cache_rfc2616.c */
void RFC2616_Ttl(struct busyobj *, double now);
-enum body_status RFC2616_Body(struct busyobj *, struct dstat *);
unsigned RFC2616_Req_Gzip(const struct http *);
int RFC2616_Do_Cond(const struct req *sp);
void RFC2616_Weaken_Etag(struct http *hp);
diff --git a/bin/varnishd/cache/cache_fetch.c b/bin/varnishd/cache/cache_fetch.c
index 7e0bcb1..3d48293 100644
--- a/bin/varnishd/cache/cache_fetch.c
+++ b/bin/varnishd/cache/cache_fetch.c
@@ -314,9 +314,52 @@ vbf_stp_startfetch(struct worker *wrk, struct busyobj *bo)
/*
* Figure out how the fetch is supposed to happen, before the
* headers are adultered by VCL
- * NB: Also sets other wrk variables
*/
- bo->htc->body_status = RFC2616_Body(bo, &wrk->stats);
+ if (!strcasecmp(http_GetMethod(bo->bereq), "head")) {
+ /*
+ * A HEAD request can never have a body in the reply,
+ * no matter what the headers might say.
+ * [RFC2516 4.3 p33]
+ */
+ wrk->stats.fetch_head++;
+ bo->htc->body_status = BS_NONE;
+ } else if (http_GetStatus(bo->beresp) <= 199) {
+ /*
+ * 1xx responses never have a body.
+ * [RFC2616 4.3 p33]
+ * ... but we should never see them.
+ */
+ wrk->stats.fetch_1xx++;
+ bo->htc->body_status = BS_ERROR;
+ } else if (http_IsStatus(bo->beresp, 204)) {
+ /*
+ * 204 is "No Content", obviously don't expect a body.
+ * [RFC2616 10.2.5 p60]
+ */
+ wrk->stats.fetch_204++;
+ bo->htc->body_status = BS_NONE;
+ } else if (http_IsStatus(bo->beresp, 304)) {
+ /*
+ * 304 is "Not Modified" it has no body.
+ * [RFC2616 10.3.5 p63]
+ */
+ wrk->stats.fetch_304++;
+ bo->htc->body_status = BS_NONE;
+ } else if (bo->htc->body_status == BS_CHUNKED) {
+ wrk->stats.fetch_chunked++;
+ } else if (bo->htc->body_status == BS_LENGTH) {
+ assert(bo->htc->content_length > 0);
+ bo->content_length = bo->htc->content_length;
+ wrk->stats.fetch_length++;
+ } else if (bo->htc->body_status == BS_EOF) {
+ wrk->stats.fetch_eof++;
+ } else if (bo->htc->body_status == BS_ERROR) {
+ wrk->stats.fetch_bad++;
+ } else if (bo->htc->body_status == BS_NONE) {
+ wrk->stats.fetch_none++;
+ } else {
+ WRONG("wrong bodystatus");
+ }
if (bo->htc->body_status == BS_ERROR) {
AN (bo->vbc);
diff --git a/bin/varnishd/cache/cache_rfc2616.c b/bin/varnishd/cache/cache_rfc2616.c
index dcd5102..51ba2c4 100644
--- a/bin/varnishd/cache/cache_rfc2616.c
+++ b/bin/varnishd/cache/cache_rfc2616.c
@@ -181,116 +181,6 @@ RFC2616_Ttl(struct busyobj *bo, double now)
}
/*--------------------------------------------------------------------
- * Body existence, fetch method and close policy.
- */
-
-enum body_status
-RFC2616_Body(struct busyobj *bo, struct dstat *stats)
-{
- struct http *hp;
- char *b;
- ssize_t cl;
-
- hp = bo->beresp;
-
- if (!strcasecmp(http_GetMethod(bo->bereq), "head")) {
- /*
- * A HEAD request can never have a body in the reply,
- * no matter what the headers might say.
- * [RFC2516 4.3 p33]
- */
- stats->fetch_head++;
- return (BS_NONE);
- }
-
- if (http_GetStatus(hp) <= 199) {
- /*
- * 1xx responses never have a body.
- * [RFC2616 4.3 p33]
- * ... but we should never see them.
- */
- stats->fetch_1xx++;
- return (BS_ERROR);
- }
-
- if (http_IsStatus(hp, 204)) {
- /*
- * 204 is "No Content", obviously don't expect a body.
- * [RFC2616 10.2.5 p60]
- */
- stats->fetch_204++;
- return (BS_NONE);
- }
-
- if (http_IsStatus(hp, 304)) {
- /*
- * 304 is "Not Modified" it has no body.
- * [RFC2616 10.3.5 p63]
- */
- stats->fetch_304++;
- return (BS_NONE);
- }
-
- if (http_HdrIs(hp, H_Transfer_Encoding, "chunked")) {
- stats->fetch_chunked++;
- return (BS_CHUNKED);
- }
-
- if (http_GetHdr(hp, H_Transfer_Encoding, &b)) {
- VSLb(bo->vsl, SLT_Error, "Illegal Transfer-Encoding:");
- stats->fetch_bad++;
- return (BS_ERROR);
- }
-
- cl = http_GetContentLength(hp);
- if (cl == -2) {
- VSLb(bo->vsl, SLT_Error, "Bad Content-Length:");
- stats->fetch_bad++;
- return (BS_ERROR);
- }
- if (cl > 0) {
- stats->fetch_length++;
- bo->content_length = cl;
- return (BS_LENGTH);
- }
- if (cl == 0) {
- stats->fetch_length++;
- return (BS_NONE);
- }
-
- if (http_HdrIs(hp, H_Connection, "keep-alive")) {
- /*
- * Keep alive with neither TE=Chunked or C-Len is impossible.
- * We assume a zero length body.
- */
- stats->fetch_zero++;
- return (BS_NONE);
- }
-
- if (http_HdrIs(hp, H_Connection, "close")) {
- /*
- * In this case, it is safe to just read what comes.
- */
- stats->fetch_close++;
- return (BS_EOF);
- }
-
- if (hp->protover < 11) {
- /*
- * With no Connection header, assume EOF.
- */
- stats->fetch_oldhttp++;
- return (BS_EOF);
- }
-
- /*
- * Fall back to EOF transfer.
- */
- stats->fetch_eof++;
- return (BS_EOF);
-}
-
-/*--------------------------------------------------------------------
* Find out if the request can receive a gzip'ed response
*/
diff --git a/include/tbl/vsc_f_main.h b/include/tbl/vsc_f_main.h
index 845fbcb..72c2568 100644
--- a/include/tbl/vsc_f_main.h
+++ b/include/tbl/vsc_f_main.h
@@ -197,31 +197,23 @@ VSC_F(fetch_head, uint64_t, 1, 'c', info,
)
VSC_F(fetch_length, uint64_t, 1, 'c', info,
"Fetch with Length",
- "beresp with Content-Length."
+ "beresp.body with Content-Length."
)
VSC_F(fetch_chunked, uint64_t, 1, 'c', info,
"Fetch chunked",
- "beresp with Chunked."
+ "beresp.body with Chunked."
)
VSC_F(fetch_eof, uint64_t, 1, 'c', info,
"Fetch EOF",
- "beresp with EOF from lack of other info."
+ "beresp.body with EOF."
)
VSC_F(fetch_bad, uint64_t, 1, 'c', info,
"Fetch bad T-E",
- "beresp failed due to unknown Transfer-Encoding."
+ "beresp.body length/fetch could not be determined."
)
-VSC_F(fetch_close, uint64_t, 1, 'c', info,
- "Fetch wanted close",
- "beresp with EOF due to Connection: Close."
-)
-VSC_F(fetch_oldhttp, uint64_t, 1, 'c', info,
- "Fetch pre HTTP/1.1 closed",
- "beresp with EOF due to HTTP < 1.1"
-)
-VSC_F(fetch_zero, uint64_t, 1, 'c', info,
- "Fetch zero len body",
- "beresp with EOF due to keep-live but neither Chunked or Len."
+VSC_F(fetch_none, uint64_t, 1, 'c', info,
+ "Fetch no body",
+ "beresp.body empty"
)
VSC_F(fetch_1xx, uint64_t, 1, 'c', info,
"Fetch no body (1xx)",
More information about the varnish-commit
mailing list