Commit 12085db8 authored by Poul-Henning Kamp's avatar Poul-Henning Kamp

Pulling in the request body, is a protocol specific operation,

so move the guts of it from cache_fetch.c to cache_http1_fsm.c.
parent fcd46ae3
......@@ -582,6 +582,14 @@ struct object {
/*--------------------------------------------------------------------*/
enum req_body_state_e {
REQ_BODY_INIT = 0,
REQ_BODY_CL,
// REQ_BODY_CHUNKED,
REQ_BODY_DONE,
REQ_BODY_NONE
};
struct req {
unsigned magic;
#define REQ_MAGIC 0x2751aaa1
......@@ -612,8 +620,12 @@ struct req {
struct exp exp;
unsigned cur_method;
unsigned handling;
unsigned char reqbodydone;
unsigned char wantbody;
enum req_body_state_e req_body_status;
uint64_t req_bodybytes;
uint64_t resp_bodybytes;
uint16_t err_code;
const char *err_reason;
......@@ -621,7 +633,6 @@ struct req {
struct director *director;
struct VCL_conf *vcl;
uint64_t req_bodybytes;
char *ws_req; /* WS above request data */
double t_req;
......@@ -766,6 +777,7 @@ void VBO_DerefBusyObj(struct worker *wrk, struct busyobj **busyobj);
void VBO_Free(struct busyobj **vbo);
/* cache_http1_fsm.c [HTTP1] */
ssize_t HTTP1_GetReqBody(struct req *, void *buf, ssize_t len);
void HTTP1_Session(struct worker *, struct req *);
/* cache_req_fsm.c [CNT] */
......
......@@ -380,43 +380,31 @@ fetch_eof(struct busyobj *bo, struct http_conn *htc)
int
FetchReqBody(struct req *req, int sendbody)
{
unsigned long content_length;
char buf[8192];
char *ptr, *endp;
int rdcnt;
ssize_t l = 1234;
if (req->reqbodydone) {
if (req->req_body_status == REQ_BODY_DONE) {
AZ(sendbody);
return (0);
}
if (http_GetHdr(req->http, H_Content_Length, &ptr)) {
req->reqbodydone = 1;
content_length = strtoul(ptr, &endp, 10);
/* XXX should check result of conversion */
while (content_length) {
if (content_length > sizeof buf)
rdcnt = sizeof buf;
else
rdcnt = content_length;
rdcnt = HTC_Read(req->htc, buf, rdcnt);
if (rdcnt <= 0)
return (1);
content_length -= rdcnt;
if (sendbody) {
/* XXX: stats ? */
(void)WRW_Write(req->wrk, buf, rdcnt);
if (WRW_Flush(req->wrk))
return (2);
while (req->req_body_status != REQ_BODY_DONE &&
req->req_body_status != REQ_BODY_NONE) {
l = HTTP1_GetReqBody(req, buf, sizeof buf);
if (l < 0) {
return (1);
} else if (l == 0) {
assert(req->req_body_status == REQ_BODY_DONE ||
req->req_body_status == REQ_BODY_NONE);
} else if (sendbody) {
/* XXX: stats ? */
(void)WRW_Write(req->wrk, buf, l);
if (WRW_Flush(req->wrk)) {
/* XXX: Try to salvage client-conn ? */
req->req_body_status = REQ_BODY_DONE;
return (2);
}
}
}
if (http_GetHdr(req->http, H_Transfer_Encoding, NULL)) {
/* XXX: Handle chunked encoding. */
VSLb(req->vsl, SLT_Debug, "Transfer-Encoding in request");
return (1);
}
return (0);
}
......@@ -480,7 +468,7 @@ FetchHdr(struct req *req, int need_host_hdr, int sendbody)
/* Deal with any message-body the request might have */
i = FetchReqBody(req, sendbody);
if (sendbody && req->reqbodydone)
if (sendbody && req->req_body_status == REQ_BODY_DONE)
retry = -1;
if (WRW_FlushRelease(wrk) || i > 0) {
VSLb(req->vsl, SLT_FetchError,
......
......@@ -76,6 +76,7 @@
#include "cache.h"
#include "vcl.h"
#include "vct.h"
#include "vtcp.h"
#include "vtim.h"
......@@ -200,7 +201,8 @@ http1_cleanup(struct sess *sp, struct worker *wrk, struct req *req)
req->t_req = NAN;
req->t_resp = NAN;
req->req_bodybytes = 0;
// req->req_bodybytes = 0;
req->resp_bodybytes = 0;
req->hash_always_miss = 0;
req->hash_ignore_busy = 0;
......@@ -287,7 +289,7 @@ http1_dissect(struct worker *wrk, struct req *req)
http_Unset(req->http, H_Expect);
/* XXX: pull in req-body and make it available instead. */
req->reqbodydone = 0;
req->req_body_status = REQ_BODY_INIT;
HTTP_Copy(req->http0, req->http); // For ESI & restart
......@@ -372,3 +374,55 @@ HTTP1_Session(struct worker *wrk, struct req *req)
}
}
}
ssize_t
HTTP1_GetReqBody(struct req *req, void *buf, ssize_t len)
{
char *ptr, *endp;
CHECK_OBJ_NOTNULL(req, REQ_MAGIC);
if (req->req_body_status == REQ_BODY_INIT) {
if (http_GetHdr(req->http, H_Content_Length, &ptr)) {
AN(ptr);
if (*ptr == '\0') {
req->req_body_status = REQ_BODY_DONE;
return (-1);
}
req->req_bodybytes = strtoul(ptr, &endp, 10);
if (*endp != '\0' && !vct_islws(*endp)) {
req->req_body_status = REQ_BODY_DONE;
return (-1);
}
if (req->req_bodybytes == 0) {
req->req_body_status = REQ_BODY_DONE;
return (0);
}
req->req_body_status = REQ_BODY_CL;
} else if (http_GetHdr(req->http, H_Transfer_Encoding, NULL)) {
VSLb(req->vsl, SLT_Debug,
"Transfer-Encoding in request");
req->req_body_status = REQ_BODY_DONE;
return (-1);
} else {
req->req_body_status = REQ_BODY_NONE;
return (0);
}
}
if (req->req_body_status == REQ_BODY_CL) {
if (req->req_bodybytes == 0) {
req->req_body_status = REQ_BODY_DONE;
return (0);
}
if (len > req->req_bodybytes)
len = req->req_bodybytes;
len = HTC_Read(req->htc, buf, len);
if (len <= 0) {
req->req_body_status = REQ_BODY_DONE;
return (-1);
}
req->req_bodybytes -= len;
return (len);
}
return (0);
}
......@@ -1233,7 +1233,7 @@ CNT_Request(struct worker *wrk, struct req *req)
/* XXX: Workaround for pipe */
if (req->sp->fd >= 0) {
VSLb(req->vsl, SLT_Length, "%ju",
(uintmax_t)req->req_bodybytes);
(uintmax_t)req->resp_bodybytes);
}
VSLb(req->vsl, SLT_ReqEnd, "%.9f %.9f %.9f %.9f %.9f",
req->t_req,
......
......@@ -78,7 +78,7 @@ SES_Charge(struct worker *wrk, struct req *req)
CHECK_OBJ_NOTNULL(sp, SESS_MAGIC);
a = &req->acct_req;
req->req_bodybytes += a->bodybytes;
req->resp_bodybytes += a->bodybytes;
#define ACCT(foo) \
wrk->stats.s_##foo += a->foo; \
......
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