fixed the problem of no percent-encoding of decoded query path in proxying

This commit is contained in:
hyung-hwan 2014-09-17 13:26:21 +00:00
parent 94f015ea98
commit f84b27c1de
12 changed files with 174 additions and 93 deletions

View File

@ -92,16 +92,19 @@ struct qse_htre_t
} s;
} u;
/* special attributes derived from the header */
struct
{
#define QSE_HTRE_ATTR_CHUNKED (1 << 0)
#define QSE_HTRE_ATTR_LENGTH (1 << 1)
#define QSE_HTRE_ATTR_KEEPALIVE (1 << 2)
#define QSE_HTRE_ATTR_EXPECT (1 << 3)
#define QSE_HTRE_ATTR_EXPECT100 (1 << 4)
#define QSE_HTRE_ATTR_PROXIED (1 << 5)
int flags;
#define QSE_HTRE_QPATH_PERDEC (1 << 6) /* the qpath has been percent-decoded */
int flags;
/* special attributes derived from the header */
struct
{
qse_size_t content_length;
const qse_mchar_t* status; /* for cgi */
} attr;
@ -231,6 +234,10 @@ QSE_EXPORT void qse_htre_setconcb (
void* ctx
);
QSE_EXPORT int qse_htre_perdecqpath (
qse_htre_t* req
);
#ifdef __cplusplus
}
#endif

View File

@ -154,6 +154,13 @@ struct qse_http_range_t
};
typedef struct qse_http_range_t qse_http_range_t;
enum qse_perenchttpstr_opt_t
{
QSE_PERENCHTTPSTR_KEEP_SLASH = (1 << 0)
};
typedef enum qse_perenchttpstr_opt_t qse_perenchttpstr_opt_t;
#ifdef __cplusplus
extern "C" {
#endif
@ -195,20 +202,26 @@ QSE_EXPORT qse_mchar_t* qse_fmthttptime (
qse_size_t bufsz
);
/* percent-decode a string */
/* percent-decode a string.
* returns the number of affected characters.
* for example, 0 means that no characters in the input required decoding. */
QSE_EXPORT qse_size_t qse_perdechttpstr (
const qse_mchar_t* str,
qse_mchar_t* buf
);
/* percent-encode a string */
/* percent-encode a string.
* returns the number of affected characters.
* for example, 0 means that no characters in the input required encoding. */
QSE_EXPORT qse_size_t qse_perenchttpstr (
int opt, /**< 0 or bitwise-OR'ed of #qse_perenchttpstr_opt_t */
const qse_mchar_t* str,
qse_mchar_t* buf
);
QSE_EXPORT qse_mchar_t* qse_perenchttpstrdup (
int opt, /**< 0 or bitwise-OR'ed of #qse_perenchttpstr_opt_t */
const qse_mchar_t* str,
qse_mmgr_t* mmgr
);

View File

@ -444,7 +444,7 @@ static qse_mchar_t* parse_initial_line (qse_htrd_t* htrd, qse_mchar_t* line)
if (htrd->re.version.major > 1 ||
(htrd->re.version.major == 1 && htrd->re.version.minor >= 1))
{
htrd->re.attr.flags |= QSE_HTRE_ATTR_KEEPALIVE;
htrd->re.flags |= QSE_HTRE_ATTR_KEEPALIVE;
}
return ++p;
@ -500,14 +500,14 @@ static int capture_connection (qse_htrd_t* htrd, qse_htb_pair_t* pair)
n = qse_mbscmp (val->ptr, QSE_MT("close"));
if (n == 0)
{
htrd->re.attr.flags &= ~QSE_HTRE_ATTR_KEEPALIVE;
htrd->re.flags &= ~QSE_HTRE_ATTR_KEEPALIVE;
return 0;
}
n = qse_mbscmp (val->ptr, QSE_MT("keep-alive"));
if (n == 0)
{
htrd->re.attr.flags |= QSE_HTRE_ATTR_KEEPALIVE;
htrd->re.flags |= QSE_HTRE_ATTR_KEEPALIVE;
return 0;
}
@ -523,7 +523,7 @@ static int capture_connection (qse_htrd_t* htrd, qse_htb_pair_t* pair)
if (htrd->re.version.major < 1 ||
(htrd->re.version.major == 1 && htrd->re.version.minor <= 0))
{
htrd->re.attr.flags &= ~QSE_HTRE_ATTR_KEEPALIVE;
htrd->re.flags &= ~QSE_HTRE_ATTR_KEEPALIVE;
}
return 0;
}
@ -568,7 +568,7 @@ static int capture_content_length (qse_htrd_t* htrd, qse_htb_pair_t* pair)
return -1;
}
if ((htrd->re.attr.flags & QSE_HTRE_ATTR_CHUNKED) && len > 0)
if ((htrd->re.flags & QSE_HTRE_ATTR_CHUNKED) && len > 0)
{
/* content-length is greater than 0
* while transfer-encoding: chunked is specified. */
@ -576,7 +576,7 @@ static int capture_content_length (qse_htrd_t* htrd, qse_htb_pair_t* pair)
return -1;
}
htrd->re.attr.flags |= QSE_HTRE_ATTR_LENGTH;
htrd->re.flags |= QSE_HTRE_ATTR_LENGTH;
htrd->re.attr.content_length = len;
return 0;
}
@ -586,14 +586,14 @@ static int capture_expect (qse_htrd_t* htrd, qse_htb_pair_t* pair)
qse_htre_hdrval_t* val;
/* Expect is included */
htrd->re.attr.flags |= QSE_HTRE_ATTR_EXPECT;
htrd->re.flags |= QSE_HTRE_ATTR_EXPECT;
val = QSE_HTB_VPTR(pair);
while (val)
{
/* Expect: 100-continue is included */
if (qse_mbscasecmp (val->ptr, QSE_MT("100-continue")) == 0)
htrd->re.attr.flags |= QSE_HTRE_ATTR_EXPECT100;
htrd->re.flags |= QSE_HTRE_ATTR_EXPECT100;
val = val->next;
}
@ -623,13 +623,13 @@ static int capture_transfer_encoding (qse_htrd_t* htrd, qse_htb_pair_t* pair)
if (n == 0)
{
/* if (htrd->re.attr.content_length > 0) */
if (htrd->re.attr.flags & QSE_HTRE_ATTR_LENGTH)
if (htrd->re.flags & QSE_HTRE_ATTR_LENGTH)
{
/* both content-length and 'transfer-encoding: chunked' are specified. */
goto badre;
}
htrd->re.attr.flags |= QSE_HTRE_ATTR_CHUNKED;
htrd->re.flags |= QSE_HTRE_ATTR_CHUNKED;
return 0;
}
@ -1232,10 +1232,10 @@ int qse_htrd_feed (qse_htrd_t* htrd, const qse_mchar_t* req, qse_size_t len)
}
/* carry on processing content body fed together with the header */
if (htrd->re.attr.flags & QSE_HTRE_ATTR_CHUNKED)
if (htrd->re.flags & QSE_HTRE_ATTR_CHUNKED)
{
/* transfer-encoding: chunked */
QSE_ASSERT (!(htrd->re.attr.flags & QSE_HTRE_ATTR_LENGTH));
QSE_ASSERT (!(htrd->re.flags & QSE_HTRE_ATTR_LENGTH));
dechunk_start:
htrd->fed.s.chunk.phase = GET_CHUNK_LEN;
@ -1279,8 +1279,8 @@ int qse_htrd_feed (qse_htrd_t* htrd, const qse_mchar_t* req, qse_size_t len)
/* we need to read as many octets as
* Content-Length */
if ((htrd->option & QSE_HTRD_RESPONSE) &&
!(htrd->re.attr.flags & QSE_HTRE_ATTR_LENGTH) &&
!(htrd->re.attr.flags & QSE_HTRE_ATTR_KEEPALIVE))
!(htrd->re.flags & QSE_HTRE_ATTR_LENGTH) &&
!(htrd->re.flags & QSE_HTRE_ATTR_KEEPALIVE))
{
/* for a response, no content-length and
* no chunk are specified and 'connection'

View File

@ -39,22 +39,22 @@ int qse_htre_init (qse_htre_t* re, qse_mmgr_t* mmgr)
{
static qse_htb_style_t style =
{
{
QSE_HTB_COPIER_DEFAULT,
QSE_HTB_COPIER_DEFAULT
},
{
QSE_HTB_FREEER_DEFAULT,
free_hdrval
},
QSE_HTB_COMPER_DEFAULT,
QSE_HTB_KEEPER_DEFAULT,
QSE_HTB_SIZER_DEFAULT,
QSE_HTB_HASHER_DEFAULT
{
QSE_HTB_COPIER_DEFAULT,
QSE_HTB_COPIER_DEFAULT
},
{
QSE_HTB_FREEER_DEFAULT,
free_hdrval
},
QSE_HTB_COMPER_DEFAULT,
QSE_HTB_KEEPER_DEFAULT,
QSE_HTB_SIZER_DEFAULT,
QSE_HTB_HASHER_DEFAULT
};
QSE_MEMSET (re, 0, QSE_SIZEOF(*re));
re->mmgr = mmgr;
re->mmgr = mmgr;
if (qse_htb_init (&re->hdrtab, mmgr, 60, 70, 1, 1) <= -1) return -1;
if (qse_htb_init (&re->trailers, mmgr, 20, 70, 1, 1) <= -1) return -1;
@ -264,3 +264,11 @@ void qse_htre_setconcb (qse_htre_t* re, qse_htre_concb_t concb, void* ctx)
re->concb_ctx = ctx;
}
int qse_htre_perdecqpath (qse_htre_t* re)
{
/* percent decode the query path */
if (re->type != QSE_HTRE_Q || (re->flags & QSE_HTRE_QPATH_PERDEC)) return -1;
if (qse_perdechttpstr ((re)->u.q.path, (re)->u.q.path) > 0)
re->flags |= QSE_HTRE_QPATH_PERDEC;
return 0;
}

View File

@ -390,12 +390,13 @@ qse_size_t qse_perdechttpstr (const qse_mchar_t* str, qse_mchar_t* buf)
{
const qse_mchar_t* p = str;
qse_mchar_t* out = buf;
qse_size_t dec_count = 0;
while (*p != QSE_T('\0'))
{
if (*p == QSE_MT('%') && *(p+1) != QSE_MT('\0') && *(p+2) != QSE_MT('\0'))
{
int q = QSE_MXDIGITTONUM (*(p+1));
int q = QSE_MXDIGITTONUM (*(p+1));
if (q >= 0)
{
int w = QSE_MXDIGITTONUM (*(p+2));
@ -405,57 +406,89 @@ qse_size_t qse_perdechttpstr (const qse_mchar_t* str, qse_mchar_t* buf)
* contains a null character */
*out++ = ((q << 4) + w);
p += 3;
dec_count++;
continue;
}
}
}
*out++ = *p++;
}
*out = QSE_MT('\0');
return out - buf;
/*return out - buf;*/
return dec_count;
}
#define IS_UNRESERVED(c) \
(((c) >= QSE_MT('A') && (c) <= QSE_MT('Z')) || \
((c) >= QSE_MT('a') && (c) <= QSE_MT('z')) || \
((c) >= QSE_MT('0') && (c) <= QSE_MT('9')) || \
(c) == QSE_MT('-') || (c) == QSE_T('_') || \
(c) == QSE_MT('.') || (c) == QSE_T('~'))
#define TO_HEX(v) (QSE_MT("0123456789ABCDEF")[(v) & 15])
qse_size_t qse_perenchttpstr (const qse_mchar_t* str, qse_mchar_t* buf)
qse_size_t qse_perenchttpstr (int opt, const qse_mchar_t* str, qse_mchar_t* buf)
{
const qse_mchar_t* p = str;
qse_mchar_t* out = buf;
while (*p != QSE_T('\0'))
{
if (IS_UNRESERVED(*p)) *out++ = *p;
else
{
*out++ = QSE_MT('%');
*out++ = TO_HEX (*p >> 4);
*out++ = TO_HEX (*p & 15);
}
p++;
}
qse_size_t enc_count = 0;
if (opt & QSE_PERENCHTTPSTR_KEEP_SLASH)
{
while (*p != QSE_T('\0'))
{
if (IS_UNRESERVED(*p) || *p == QSE_MT('/')) *out++ = *p;
else
{
*out++ = QSE_MT('%');
*out++ = TO_HEX (*p >> 4);
*out++ = TO_HEX (*p & 15);
enc_count++;
}
p++;
}
}
else
{
while (*p != QSE_T('\0'))
{
if (IS_UNRESERVED(*p)) *out++ = *p;
else
{
*out++ = QSE_MT('%');
*out++ = TO_HEX (*p >> 4);
*out++ = TO_HEX (*p & 15);
enc_count++;
}
p++;
}
}
*out = QSE_MT('\0');
return out - buf;
/*return out - buf;*/
return enc_count;
}
qse_mchar_t* qse_perenchttpstrdup (const qse_mchar_t* str, qse_mmgr_t* mmgr)
qse_mchar_t* qse_perenchttpstrdup (int opt, const qse_mchar_t* str, qse_mmgr_t* mmgr)
{
qse_mchar_t* buf;
qse_size_t len = 0;
qse_size_t count = 0;
/* count the number of characters that should be encoded */
for (len = 0; str[len] != QSE_T('\0'); len++)
if (opt & QSE_PERENCHTTPSTR_KEEP_SLASH)
{
if (!IS_UNRESERVED(str[len])) count++;
for (len = 0; str[len] != QSE_T('\0'); len++)
{
if (!IS_UNRESERVED(str[len]) && str[len] != QSE_MT('/')) count++;
}
}
else
{
for (len = 0; str[len] != QSE_T('\0'); len++)
{
if (!IS_UNRESERVED(str[len])) count++;
}
}
/* if there are no characters to escape, just return the original string */
@ -466,7 +499,7 @@ qse_mchar_t* qse_perenchttpstrdup (const qse_mchar_t* str, qse_mmgr_t* mmgr)
if (buf == QSE_NULL) return QSE_NULL;
/* perform actual escaping */
qse_perenchttpstr (str, buf);
qse_perenchttpstr (opt, str, buf);
return buf;
}

View File

@ -304,7 +304,7 @@ static int cgi_htrd_peek_script_output (qse_htrd_t* htrd, qse_htre_t* req)
}
keepalive = cgi->keepalive;
if (req->attr.flags & QSE_HTRE_ATTR_LENGTH)
if (req->flags & QSE_HTRE_ATTR_LENGTH)
{
cgi->resflags |= CGI_RES_SCRIPT_LENGTH;
cgi->script_output_length = req->attr.content_length;
@ -730,7 +730,7 @@ static int task_init_cgi (
cgi->method = qse_htre_getqmethodtype(arg->req);
cgi->version = *qse_htre_getversion(arg->req);
cgi->keepalive = (arg->req->attr.flags & QSE_HTRE_ATTR_KEEPALIVE);
cgi->keepalive = (arg->req->flags & QSE_HTRE_ATTR_KEEPALIVE);
cgi->nph = arg->nph;
cgi->req = QSE_NULL;
@ -747,7 +747,7 @@ static int task_init_cgi (
}
if (!(arg->req->state & QSE_HTRE_COMPLETED) &&
!(arg->req->attr.flags & QSE_HTRE_ATTR_LENGTH))
!(arg->req->flags & QSE_HTRE_ATTR_LENGTH))
{
/* if the request is not completed and doesn't have
* content-length set, it's not really possible to
@ -821,8 +821,8 @@ static int task_init_cgi (
* should reach here. if content-length is set
* the length should match len. */
QSE_ASSERT (len > 0);
QSE_ASSERT (!(arg->req->attr.flags & QSE_HTRE_ATTR_LENGTH) ||
((arg->req->attr.flags & QSE_HTRE_ATTR_LENGTH) &&
QSE_ASSERT (!(arg->req->flags & QSE_HTRE_ATTR_LENGTH) ||
((arg->req->flags & QSE_HTRE_ATTR_LENGTH) &&
arg->req->attr.content_length == len));
cgi->reqflags |= CGI_REQ_GOTALL;
content_length = len;
@ -848,7 +848,7 @@ static int task_init_cgi (
cgi->req = arg->req;
qse_htre_setconcb (cgi->req, cgi_snatch_client_input, task);
QSE_ASSERT (arg->req->attr.flags & QSE_HTRE_ATTR_LENGTH);
QSE_ASSERT (arg->req->flags & QSE_HTRE_ATTR_LENGTH);
content_length = arg->req->attr.content_length;
}
}

View File

@ -155,7 +155,7 @@ static qse_size_t format_dirent (
* a lot of file names to escape. */
/* perform percent-encoding for the anchor */
encname = qse_perenchttpstrdup (dirent->name, httpd->mmgr);
encname = qse_perenchttpstrdup (0, dirent->name, httpd->mmgr);
if (encname == QSE_NULL)
{
httpd->errnum = QSE_HTTPD_ENOMEM;
@ -602,7 +602,7 @@ qse_httpd_task_t* qse_httpd_entaskdir (
data.foot.ptr = dir->foot? dir->foot: qse_httpd_getname(httpd);
data.foot.len = qse_mbslen(data.foot.ptr);
data.version = *qse_htre_getversion(req);
data.keepalive = (req->attr.flags & QSE_HTRE_ATTR_KEEPALIVE);
data.keepalive = (req->flags & QSE_HTRE_ATTR_KEEPALIVE);
data.method = method;
QSE_MEMSET (&task, 0, QSE_SIZEOF(task));

View File

@ -541,7 +541,7 @@ qse_httpd_task_t* qse_httpd_entaskfile (
data.path.ptr = (qse_mchar_t*)path;
data.path.len = qse_mbslen(path);
data.version = *qse_htre_getversion(req);
data.keepalive = (req->attr.flags & QSE_HTRE_ATTR_KEEPALIVE);
data.keepalive = (req->flags & QSE_HTRE_ATTR_KEEPALIVE);
data.method = qse_htre_getqmethodtype(req);
xtnsize = QSE_SIZEOF(task_file_t) + data.path.len + 1;

View File

@ -575,7 +575,7 @@ static int proxy_htrd_peek_peer_output (qse_htrd_t* htrd, qse_htre_t* res)
proxy->resflags |= PROXY_RES_RECEIVED_RESHDR;
keepalive = proxy->keepalive;
if (res->attr.flags & QSE_HTRE_ATTR_LENGTH)
if (res->flags & QSE_HTRE_ATTR_LENGTH)
{
/* the response from the peer is length based */
proxy->resflags |= PROXY_RES_PEER_LENGTH;
@ -601,7 +601,7 @@ static int proxy_htrd_peek_peer_output (qse_htrd_t* htrd, qse_htre_t* res)
/* chunk response when writing back to client */
proxy->resflags |= PROXY_RES_CLIENT_CHUNK;
if (res->attr.flags & QSE_HTRE_ATTR_CHUNKED)
if (res->flags & QSE_HTRE_ATTR_CHUNKED)
{
/* mark the peer output is chunked */
proxy->resflags |= PROXY_RES_PEER_CHUNK;
@ -623,7 +623,7 @@ static int proxy_htrd_peek_peer_output (qse_htrd_t* htrd, qse_htre_t* res)
/* and push the actual disconnection task */
if (qse_httpd_entaskdisconnect (httpd, xtn->client, xtn->task) == QSE_NULL) return -1;
if (res->attr.flags & QSE_HTRE_ATTR_CHUNKED)
if (res->flags & QSE_HTRE_ATTR_CHUNKED)
proxy->resflags |= PROXY_RES_PEER_CHUNK;
else
proxy->resflags |= PROXY_RES_PEER_CLOSE;
@ -925,7 +925,7 @@ static int task_init_proxy (
proxy->method = qse_htre_getqmethodtype(arg->req);
proxy->version = *qse_htre_getversion(arg->req);
proxy->keepalive = (arg->req->attr.flags & QSE_HTRE_ATTR_KEEPALIVE);
proxy->keepalive = (arg->req->flags & QSE_HTRE_ATTR_KEEPALIVE);
proxy->task = task; /* needed for url rewriting */
@ -1030,6 +1030,7 @@ printf (">>>>>>>>>>>>>>>>>>>>>>>> [%s] <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<\n", proxy
else
{
int snatch_needed = 0;
/* compose a request to send to the peer using the request
* received from the client */
@ -1038,7 +1039,26 @@ printf (">>>>>>>>>>>>>>>>>>>>>>>> [%s] <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<\n", proxy
qse_mbs_cat (proxy->reqfwdbuf, QSE_MT(" ")) == (qse_size_t)-1) goto nomem_oops;
proxy->qpath_pos_in_reqfwdbuf = QSE_STR_LEN(proxy->reqfwdbuf);
if (qse_mbs_cat (proxy->reqfwdbuf, qse_htre_getqpath(arg->req)) == (qse_size_t)-1) goto nomem_oops;
if (arg->req->flags & QSE_HTRE_QPATH_PERDEC)
{
/* the query path has been percent-decoded. so encode it back */
qse_mchar_t* qpath, * qpath_enc;
qse_size_t x;
qpath = qse_htre_getqpath(arg->req);
qpath_enc = qse_perenchttpstrdup (QSE_PERENCHTTPSTR_KEEP_SLASH, qpath, httpd->mmgr);
if (qpath_enc == QSE_NULL) goto nomem_oops;
x = qse_mbs_cat (proxy->reqfwdbuf, qpath_enc);
QSE_MMGR_FREE (httpd->mmgr, qpath_enc);
if (x == (qse_size_t)-1) goto nomem_oops;
}
else
{
/* the query path doesn't require encoding or it's never decoded */
if (qse_mbs_cat (proxy->reqfwdbuf, qse_htre_getqpath(arg->req)) == (qse_size_t)-1) goto nomem_oops;
}
if (qse_htre_getqparam(arg->req))
{
@ -1081,7 +1101,7 @@ qse_mbs_ncat (proxy->reqfwdbuf, spc, QSE_COUNTOF(spc));
}
proxy->resflags |= PROXY_RES_AWAIT_RESHDR;
if ((arg->req->attr.flags & QSE_HTRE_ATTR_EXPECT100) &&
if ((arg->req->flags & QSE_HTRE_ATTR_EXPECT100) &&
(arg->req->version.major > 1 || (arg->req->version.major == 1 && arg->req->version.minor >= 1)))
{
proxy->resflags |= PROXY_RES_AWAIT_100;
@ -1115,8 +1135,8 @@ qse_mbs_ncat (proxy->reqfwdbuf, spc, QSE_COUNTOF(spc));
if (arg->req->state & QSE_HTRE_DISCARDED)
{
/* no content to add */
if ((arg->req->attr.flags & QSE_HTRE_ATTR_LENGTH) ||
(arg->req->attr.flags & QSE_HTRE_ATTR_CHUNKED))
if ((arg->req->flags & QSE_HTRE_ATTR_LENGTH) ||
(arg->req->flags & QSE_HTRE_ATTR_CHUNKED))
{
/* i don't add chunk traiers if the
* request content has been discarded */
@ -1129,15 +1149,15 @@ qse_mbs_ncat (proxy->reqfwdbuf, spc, QSE_COUNTOF(spc));
}
else if (arg->req->state & QSE_HTRE_COMPLETED)
{
if (arg->req->attr.flags & QSE_HTRE_ATTR_CHUNKED)
if (arg->req->flags & QSE_HTRE_ATTR_CHUNKED)
{
/* add trailers if any */
if (qse_htre_walktrailers (arg->req, proxy_capture_client_trailer, proxy) <= -1) goto nomem_oops;
}
len = qse_htre_getcontentlen(arg->req);
if (len > 0 || (arg->req->attr.flags & QSE_HTRE_ATTR_LENGTH) ||
(arg->req->attr.flags & QSE_HTRE_ATTR_CHUNKED))
if (len > 0 || (arg->req->flags & QSE_HTRE_ATTR_LENGTH) ||
(arg->req->flags & QSE_HTRE_ATTR_CHUNKED))
{
qse_mchar_t buf[64];
@ -1163,7 +1183,7 @@ qse_mbs_ncat (proxy->reqfwdbuf, spc, QSE_COUNTOF(spc));
if (qse_mbs_cat (proxy->reqfwdbuf, QSE_MT("\r\n")) == (qse_size_t)-1) goto nomem_oops;
}
}
else if (arg->req->attr.flags & QSE_HTRE_ATTR_LENGTH)
else if (arg->req->flags & QSE_HTRE_ATTR_LENGTH)
{
/* the Content-Length header field is contained in the request. */
qse_mchar_t buf[64];
@ -1191,7 +1211,7 @@ qse_mbs_ncat (proxy->reqfwdbuf, spc, QSE_COUNTOF(spc));
/* if this request is not chunked nor not length based,
* the state should be QSE_HTRE_COMPLETED. so only a
* chunked request should reach here */
QSE_ASSERT (arg->req->attr.flags & QSE_HTRE_ATTR_CHUNKED);
QSE_ASSERT (arg->req->flags & QSE_HTRE_ATTR_CHUNKED);
proxy->reqflags |= PROXY_REQ_FWDCHUNKED;
if (qse_mbs_cat (proxy->reqfwdbuf, QSE_MT("Transfer-Encoding: chunked\r\n")) == (qse_size_t)-1 ||

View File

@ -2087,7 +2087,7 @@ static int process_request (
* any more. once it's decoded in the peek mode,
* the decoded query path is made available in the
* non-peek mode as well */
if (peek) qse_perdechttpstr (qse_htre_getqpath(req), qse_htre_getqpath(req));
if (peek) qse_htre_perdecqpath(req);
if (peek && (httpd->opt.trait & QSE_HTTPD_LOGACT))
{
@ -2154,11 +2154,11 @@ if (qse_htre_getcontentlen(req) > 0)
else
{
if (mth == QSE_HTTP_POST &&
!(req->attr.flags & QSE_HTRE_ATTR_LENGTH) &&
!(req->attr.flags & QSE_HTRE_ATTR_CHUNKED))
!(req->flags & QSE_HTRE_ATTR_LENGTH) &&
!(req->flags & QSE_HTRE_ATTR_CHUNKED))
{
/* POST without Content-Length nor not chunked */
req->attr.flags &= ~QSE_HTRE_ATTR_KEEPALIVE;
req->flags &= ~QSE_HTRE_ATTR_KEEPALIVE;
qse_httpd_discardcontent (httpd, req);
task = qse_httpd_entaskerr (httpd, client, QSE_NULL, 411, req);
if (task)
@ -2234,7 +2234,7 @@ printf ("CANOT MAKE RESOURCE.... %s\n", qse_htre_getqpath(req));
if (task == QSE_NULL) goto oops;
}
else if (req->attr.flags & QSE_HTRE_ATTR_PROXIED)
else if (req->flags & QSE_HTRE_ATTR_PROXIED)
{
/* the contents should be proxied.
* do nothing locally */
@ -2246,7 +2246,7 @@ printf ("CANOT MAKE RESOURCE.... %s\n", qse_htre_getqpath(req));
}
}
if (!(req->attr.flags & QSE_HTRE_ATTR_KEEPALIVE) || mth == QSE_HTTP_CONNECT)
if (!(req->flags & QSE_HTRE_ATTR_KEEPALIVE) || mth == QSE_HTTP_CONNECT)
{
if (!peek)
{
@ -2727,7 +2727,7 @@ static int make_resource (
case QSE_HTTPD_SERVERSTD_ROOT_PROXY:
target->type = QSE_HTTPD_RSRC_PROXY;
target->u.proxy = tmp.root.u.proxy;
req->attr.flags |= QSE_HTRE_ATTR_PROXIED;
req->flags |= QSE_HTRE_ATTR_PROXIED;
return 0;
case QSE_HTTPD_SERVERSTD_ROOT_ERROR:
@ -2797,7 +2797,7 @@ auth_ok:
/* if authentication is ok or no authentication is required,
* handle 'Expect: 100-continue' if it is contained in the header */
if ((req->attr.flags & QSE_HTRE_ATTR_EXPECT) &&
if ((req->flags & QSE_HTRE_ATTR_EXPECT) &&
(req->version.major > 1 || (req->version.major == 1 && req->version.minor >= 1)) &&
qse_htre_getcontentlen(req) <= 0)
{
@ -2807,7 +2807,7 @@ auth_ok:
* if the partial or complete content is already received,
* we don't need to send '100 continue'. */
if (req->attr.flags & QSE_HTRE_ATTR_EXPECT100)
if (req->flags & QSE_HTRE_ATTR_EXPECT100)
{
/* "Expect: 100-continue" in the header.
* mark to return "100 continue" */

View File

@ -242,7 +242,7 @@ qse_httpd_task_t* qse_httpd_entaskerr (
httpd, client, pred, code, QSE_NULL,
qse_htre_getqmethodtype(req),
qse_htre_getversion(req),
(req->attr.flags & QSE_HTRE_ATTR_KEEPALIVE)
(req->flags & QSE_HTRE_ATTR_KEEPALIVE)
);
}
@ -268,7 +268,7 @@ qse_httpd_task_t* qse_httpd_entaskauth (
httpd, client, pred, 401, (void*)realm,
qse_htre_getqmethodtype(req),
qse_htre_getversion(req),
(req->attr.flags & QSE_HTRE_ATTR_KEEPALIVE));
(req->flags & QSE_HTRE_ATTR_KEEPALIVE));
}
@ -287,7 +287,7 @@ qse_httpd_task_t* qse_httpd_entaskreloc (
httpd, client, pred, 301, (void*)&reloc,
qse_htre_getqmethodtype(req),
qse_htre_getversion(req),
(req->attr.flags & QSE_HTRE_ATTR_KEEPALIVE));
(req->flags & QSE_HTRE_ATTR_KEEPALIVE));
}
qse_httpd_task_t* qse_httpd_entaskredir (
@ -303,7 +303,7 @@ qse_httpd_task_t* qse_httpd_entaskredir (
httpd, client, pred, 301, (void*)&reloc,
qse_htre_getqmethodtype(req),
qse_htre_getversion(req),
(req->attr.flags & QSE_HTRE_ATTR_KEEPALIVE));
(req->flags & QSE_HTRE_ATTR_KEEPALIVE));
}
/*------------------------------------------------------------------------*/
@ -324,7 +324,7 @@ qse_httpd_task_t* qse_httpd_entasknomod (
httpd, client, pred, 304, QSE_NULL,
qse_htre_getqmethodtype(req),
qse_htre_getversion(req),
(req->attr.flags & QSE_HTRE_ATTR_KEEPALIVE));
(req->flags & QSE_HTRE_ATTR_KEEPALIVE));
}
/*------------------------------------------------------------------------*/
@ -340,7 +340,7 @@ qse_httpd_task_t* qse_httpd_entaskallow (
msg = qse_httpstatustombs (code);
version = qse_htre_getversion(req);
keepalive = (req->attr.flags & QSE_HTRE_ATTR_KEEPALIVE);
keepalive = (req->flags & QSE_HTRE_ATTR_KEEPALIVE);
return qse_httpd_entaskformat (
httpd, client, pred,
QSE_MT("HTTP/%d.%d %d %s\r\nServer: %s\r\nDate: %s\r\nConnection: %s\r\nAllow: %s\r\nContent-Length: 0\r\n\r\n"),

View File

@ -112,7 +112,7 @@ qse_httpd_task_t* qse_httpd_entasktext (
version->major, version->minor,
qse_httpd_getname (httpd),
qse_httpd_fmtgmtimetobb (httpd, QSE_NULL, 0),
((req->attr.flags & QSE_HTRE_ATTR_KEEPALIVE)? QSE_MT("keep-alive"): QSE_MT("close")),
((req->flags & QSE_HTRE_ATTR_KEEPALIVE)? QSE_MT("keep-alive"): QSE_MT("close")),
mime, b_tlen
);
if (pred == QSE_NULL) return QSE_NULL;