commit - cc2ec1f7a082a95f019ba80d9be7f628ebafcc6a
commit + 05a099a8f45a2d2132479e114f734065e2e12f45
blob - d6960e83eb7a11678a5e4211687e018a2e127c2c
blob + 2570940fbbab47edc60a7dc9d72bf35ff61b4e0a
--- relay_http.c
+++ relay_http.c
-/* $OpenBSD: relay_http.c,v 1.96 2026/04/02 13:35:36 tb Exp $ */
+/* $OpenBSD: relay_http.c,v 1.97 2026/05/16 15:25:28 kirill Exp $ */
/*
* Copyright (c) 2006 - 2016 Reyk Floeter <reyk@openbsd.org>
struct kv *upgrade = NULL, *upgrade_ws = NULL;
struct kv *connection_close = NULL;
int ws_response = 0;
+ int headers_only = 0;
enum httpmethod request_method = HTTP_METHOD_NONE;
getmonotime(&con->se_tv_last);
connection_close = kv_find_value(&desc->http_headers,
"Connection", "close", ",");
+ /*
+ * RFC 9112 section 6.3: these responses end at the empty
+ * line after the header section. 101 upgrades become streams.
+ */
+ headers_only = cre->dir == RELAY_DIR_RESPONSE && !ws_response &&
+ (request_method == HTTP_METHOD_HEAD ||
+ (desc->http_status >= 100 && desc->http_status < 200) ||
+ desc->http_status == 204 || desc->http_status == 304);
+ if (headers_only)
+ cre->toread = 0;
switch (desc->http_method) {
case HTTP_METHOD_CONNECT:
bev->readcb = relay_read_http;
break;
}
- if (desc->http_chunked) {
+ if (desc->http_chunked && !headers_only) {
/* Chunked transfer encoding */
cre->toread = TOREAD_HTTP_CHUNK_LENGTH;
bev->readcb = relay_read_httpchunks;