[core] lowercase response hdr field names for h2

This commit is contained in:
Glenn Strauss 2020-07-26 09:37:54 -04:00
parent e089facf84
commit 77057a7c02
2 changed files with 38 additions and 13 deletions

View File

@ -180,7 +180,14 @@ void http_header_response_insert(request_st * const r, enum http_header_e id, co
buffer * const vb = array_get_buf_ptr(&r->resp_headers, k, klen);
if (!buffer_string_is_empty(vb)) { /* append value */
buffer_append_string_len(vb, CONST_STR_LEN("\r\n"));
buffer_append_string_len(vb, k, klen);
if (r->http_version >= HTTP_VERSION_2) {
char * const h = buffer_string_prepare_append(vb, klen + vlen + 2);
for (uint32_t i = 0; i < klen; ++i)
h[i] = (k[i] < 'A' || k[i] > 'Z') ? k[i] : (k[i] | 0x20);
buffer_commit(vb, klen);
}
else
buffer_append_string_len(vb, k, klen);
buffer_append_string_len(vb, CONST_STR_LEN(": "));
}
buffer_append_string_len(vb, v, vlen);

View File

@ -3,7 +3,6 @@
#include "response.h"
#include "request.h"
#include "base.h"
#include "burl.h"
#include "fdevent.h"
#include "http_header.h"
#include "http_kv.h"
@ -50,12 +49,21 @@ int http_response_write_header(request_st * const r) {
chunkqueue * const cq = r->write_queue;
buffer * const b = chunkqueue_prepend_buffer_open(cq);
if (r->http_version == HTTP_VERSION_1_1) {
buffer_copy_string_len(b, CONST_STR_LEN("HTTP/1.1 "));
} else {
buffer_copy_string_len(b, CONST_STR_LEN("HTTP/1.0 "));
/* future: might fork this routine and send headers directly to
* the HPACK encoder, rather than double-buffering in chunkqueue */
const int h1 = (r->http_version <= HTTP_VERSION_1_1);
if (!h1) {
buffer_append_string_len(b, CONST_STR_LEN(":status: "));
buffer_append_int(b, r->http_status);
}
else {
if (r->http_version == HTTP_VERSION_1_1) {
buffer_copy_string_len(b, CONST_STR_LEN("HTTP/1.1 "));
} else {
buffer_copy_string_len(b, CONST_STR_LEN("HTTP/1.0 "));
}
http_status_append(b, r->http_status);
}
http_status_append(b, r->http_status);
/* disable keep-alive if requested */
@ -75,7 +83,7 @@ int http_response_write_header(request_st * const r) {
if ((r->resp_htags & HTTP_HEADER_UPGRADE) && r->http_version == HTTP_VERSION_1_1) {
http_header_response_set(r, HTTP_HEADER_CONNECTION, CONST_STR_LEN("Connection"), CONST_STR_LEN("upgrade"));
} else if (0 == r->keep_alive) {
if (r->http_version <= HTTP_VERSION_1_1) /*(e.g. not HTTP_VERSION_2)*/
if (h1) /*(e.g. not HTTP_VERSION_2)*/
http_header_response_set(r, HTTP_HEADER_CONNECTION, CONST_STR_LEN("Connection"), CONST_STR_LEN("close"));
} else if (r->http_version == HTTP_VERSION_1_0) {/*(&& r->keep_alive != 0)*/
http_header_response_set(r, HTTP_HEADER_CONNECTION, CONST_STR_LEN("Connection"), CONST_STR_LEN("keep-alive"));
@ -95,7 +103,16 @@ int http_response_write_header(request_st * const r) {
continue;
buffer_append_string_len(b, CONST_STR_LEN("\r\n"));
buffer_append_string_buffer(b, &ds->key);
if (!h1) { /* HTTP/2 requires lowercase keys */
const size_t klen = buffer_string_length(&ds->key);
char * const h = buffer_string_prepare_append(b, klen);
const char * const k = ds->key.ptr;
for (uint32_t j = 0; j < klen; ++j)
h[j] = (k[j] < 'A' || k[j] > 'Z') ? k[j] : (k[j] | 0x20);
buffer_commit(b, klen);
}
else
buffer_append_string_buffer(b, &ds->key);
buffer_append_string_len(b, CONST_STR_LEN(": "));
buffer_append_string_buffer(b, &ds->value);
}
@ -105,9 +122,6 @@ int http_response_write_header(request_st * const r) {
static char tstr[32]; /* 30-chars for "%a, %d %b %Y %H:%M:%S GMT" */
static size_t tlen;
/* HTTP/1.1 requires a Date: header */
buffer_append_string_len(b, CONST_STR_LEN("\r\nDate: "));
/* cache the generated timestamp */
const time_t cur_ts = log_epoch_secs;
if (tlast != cur_ts) {
@ -116,12 +130,16 @@ int http_response_write_header(request_st * const r) {
"%a, %d %b %Y %H:%M:%S GMT", gmtime(&tlast));
}
/* HTTP/1.1 and later requires a Date: header */
buffer_append_string_len(b, !h1 ? "\r\ndate: " : "\r\nDate: ",
sizeof("\r\ndate: ")-1);
buffer_append_string_len(b, tstr, tlen);
}
if (!(r->resp_htags & HTTP_HEADER_SERVER)) {
if (!buffer_string_is_empty(r->conf.server_tag)) {
buffer_append_string_len(b, CONST_STR_LEN("\r\nServer: "));
buffer_append_string_len(b, !h1 ? "\r\nserver: " : "\r\nServer: ",
sizeof("\r\nserver: ")-1);
buffer_append_string_len(b, CONST_BUF_LEN(r->conf.server_tag));
}
}