Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix IndexDefect in httpclient and fix parsing of multiline headers #19262

Closed
wants to merge 5 commits into from
Closed

Fix IndexDefect in httpclient and fix parsing of multiline headers #19262

wants to merge 5 commits into from

Conversation

ghost
Copy link

@ghost ghost commented Dec 17, 2021

Follow the part of the HTTP spec regarding headers - this solves the actual issue in #19261 as well as makes httpclient follow the spec more closely. I've chosen not to enforce the spec to the level Firefox does (regarding disallowing spaces after the header name but before the value) as I've wanted to limit this change just to fix the bug that I encountered.

Also, I don't know how I should make the tests for this.

Danil Yarantsev (Yardanico) added 2 commits December 17, 2021 04:52
@ghost ghost linked an issue Dec 17, 2021 that may be closed by this pull request
@ghost ghost requested a review from dom96 December 17, 2021 01:58
@ghost
Copy link
Author

ghost commented Dec 17, 2021

Also, we might want to check that linei is actually less than line.len just to be safe, should I do it in this PR?

@ghost ghost marked this pull request as draft December 17, 2021 02:09
@ghost
Copy link
Author

ghost commented Dec 17, 2021

Okay, I forgot that httpclient saves headers in a different case than the default one, so my branch will error out in most cases. I'm thinking of a fix, but the problem is that toCaseInsensitive from httpcore is private, so I can either export it or copy it to httpclient.

Currently fixed by exporting toCaseInsensitive just to make a PoC, I don't know if there's a better way than this.

var leadingSpaces = skipWhitespace(line, linei)
if leadingSpaces == 0:
var le = parseUntil(line, name, ':', linei)
if le <= 0 or le >= line.len: httpError("invalid headers")
Copy link
Author

Choose a reason for hiding this comment

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

le >= line.len makes httpclient a little more stricter regarding random lines it finds in the response - basically, if the response is like:

Header-One: value
Header-Two: value
somerandomname

httpclient will error out on somerandomname. Chromium and Firefox don't error out on that and just skip the line - should we follow them or throw an error?

# that should be appended to the previous header, see bug #19261
# Also, if there was no header before this, we just ignore the line
elif prevHeader != "":
result.headers.table[result.headers.toCaseInsensitive(prevHeader)][^1].add line.strip()
Copy link
Author

Choose a reason for hiding this comment

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

We know that prevHeader is already in the table because we check if it's empty or not.

@ghost ghost changed the title Fix #19261 Fix IndexDefect in httpclient and fix parsing of multiline headers Dec 24, 2021
@stale
Copy link

stale bot commented Dec 26, 2022

This pull request has been automatically marked as stale because it has not had recent activity. If you think it is still a valid PR, please rebase it on the latest devel; otherwise it will be closed. Thank you for your contributions.

@ghost ghost marked this pull request as ready for review June 30, 2023 09:10
@ghost
Copy link
Author

ghost commented Jun 30, 2023

I'll see if I can either try to test this PR more properly to make it ready to merge, or make a smaller PR just to fix the IndexDefect without changing anything else. I hope we can get this into 2.0, sorry for not doing it before

@ghost
Copy link
Author

ghost commented Oct 30, 2023

Going to open a new PR instead

@ghost ghost closed this Oct 30, 2023
Araq added a commit that referenced this pull request Nov 1, 2023
Continuation of #19262

Fixes #19261

The parsing code is still too lenient (e.g. it will happily parse header
names with spaces in them, which is outright invalid by the spec), but I
didn't want to touch it beyond the simple changes to make sure that
`std/httpclient` won't throw `IndexDefect`s like it does now on those
cases:
- Multiline header values
- No colon after the header name
- No value after the header name + colon

One question remains - should I keep `toCaseInsensitive` exported in
`httpcore` or just copy-paste the implementation?

---------

Co-authored-by: Andreas Rumpf <[email protected]>
This pull request was closed.
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.

IndexDefect in httpclient because of a header spanning multiple lines
0 participants