Skip to content

RFC 9112: reject signed chunk sizes and Content-Length values - #729

Merged
arturobernalg merged 1 commit into
apache:masterfrom
arturobernalg:chunk-size-digits
Nov 1, 2026
Merged

arturobernalg merged 1 commit into
apache:masterfrom
arturobernalg:chunk-size-digits

Conversation

@arturobernalg

Copy link
Copy Markdown
Member

Long#parseLong accepts a leading + or -, which the grammar does not allow (chunk-size is 1*HEXDIG, Content-Length is 1*DIGIT).

On master:

  • ChunkedInputStream accepts +5
  • ChunkDecoder accepts +5, silently skips a -1 chunk head (it equals the internal "no chunk head" marker) and fails with IllegalArgumentException on other negative values
  • MessageSupport#getContentLength accepts +5

All three now reject such values with MalformedChunkCodingException / ProtocolException. Leading zeros are still accepted. Tests added for the blocking and non-blocking paths.

@arturobernalg
arturobernalg requested a review from ok2c November 1, 2026 09:15
@ok2c

ok2c commented Nov 1, 2026

Copy link
Copy Markdown
Member

@arturobernalg I am strongly not in favor of this change. It adds an extra full scan over chunk length element. Either be pragmatic and test for leading char not being - or + or blank, or consider implementing a better #parseLong method

@arturobernalg

Copy link
Copy Markdown
Member Author

@arturobernalg I am strongly not in favor of this change. It adds an extra full scan over chunk length element. Either be pragmatic and test for leading char not being - or + or blank, or consider implementing a better #parseLong method

@ok2c agreed. Updated. Removed the extra scan and added a leading-character check as suggested. The existing parsing and overflow handling remain unchanged. Please do another pass

final Header contentLengthHeader = message.getFirstHeader(HttpHeaders.CONTENT_LENGTH);
if (contentLengthHeader != null) {
final String s = contentLengthHeader.getValue();
if (s != null && !s.isEmpty() && (s.charAt(0) == '+' || s.charAt(0) == '-')) {

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

s != null && !s.isEmpty() && (s.charAt(0) == '+' || s.charAt(0) == '-')

@arturobernalg Should we move this predicate to a support method in MessageSupport?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@ok2c Agree. Changed

Long#parseLong accepts a leading '+' or '-'. The NIO chunk decoder also
treated '-1' as 'no chunk head yet' and skipped the line, and failed with
IllegalArgumentException on other negative values. Chunk sizes must be
1*HEXDIG and Content-Length 1*DIGIT. Reject an empty value and a leading
sign before parsing, in both the blocking and non-blocking code paths.
@arturobernalg
arturobernalg merged commit 450ef92 into apache:master Nov 1, 2026
12 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants