0

I am attempting to inject a carriage-return + newline in a HTTP request header value. My understanding is that this is possible with HTTP/2 and HTTP/3. However, when I send a request with Burp I get this error:

RST_STREAM received with error code: 0x1 (Protocol error detected)

Does HTTP/2 support newlines in header values? Why do I get this error? Does Apache2 or PHP validate the header contents?

1

1 Answer 1

1

RFC 9113 HTTP/2 says that headers are a type of field:

HTTP fields (Section 5 of [HTTP]) are conveyed by HTTP/2 in the HEADERS ...

And that newlines can be dangerous:

Failure to validate fields can be exploited for request smuggling attacks.

And the following validation must be performed:

A field name MUST NOT contain characters in the ranges 0x00-0x20, 0x41-0x5a, or 0x7f-0xff (all ranges inclusive). This specifically excludes all non-visible ASCII characters, ASCII SP (0x20), and uppercase characters ('A' to 'Z', ASCII 0x41 to 0x5a).

Apache uses the nghttp2 library, and that indeed validates the header value and does not allow carriage return or linefeed characters.

static const int VALID_HD_VALUE_CHARS[] = {
    ...
    0 /* BS   */, 1 /* HT   */, 0 /* LF   */, 0 /* VT   */,
    0 /* FF   */, 0 /* CR   */, 0 /* SO   */, 0 /* SI   */,
    ...
};

int nghttp2_check_header_value(const uint8_t *value, size_t len) {
  const uint8_t *last;
  for (last = value + len; value != last; ++value) {
    if (!VALID_HD_VALUE_CHARS[*value]) {
      return 0;
    }
  }
  return 1;
}

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .