-
Notifications
You must be signed in to change notification settings - Fork 434
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
improving url parsing: make it more strict #751
Comments
A temporary work around:
|
Wondering... do you guys have plans for patching this? |
wondering how one could open a CVE about "possible" security issue without even contacting the author first. I am tired of this behavior. Hackney doesn't giive 100% warranty a URL is syntactically correct. This is more a user and conveniencechoice . In the example linked above the host will be "127.0.0.2 " since all before @ will be shown as an auth string . The only "fix" i can see is to add an option to not use that feature and only ensure host and ports are passed there. |
It looks like this is sample code that showcases the vulnerability: https://gist.github.com/snoopysecurity/996de09ec0cfd0ebdcfdda8ff515deb1 |
That gist has been open for 11 months. |
@kevinkirkup It has. I'm afraid I don't understand what value this information adds to the conversation, can you help me see it? |
i will send a pr tomorrow to make url parsing stricter. I am debating it should be the default there though. But since mix.audit already flag it, there maybe no choice to make the default strict anyway. any feedback is welcome. |
Yeah, it must be very frustrating that this was known about for that long and a CVE was issued without (it seems) any attempt to communicate with you. Thank you for the effort to resolve it! With regards to the default implementation... I'm struggling to find the RFC(s) that covers the use of My personal opinion is that stricter would be preferred. If someone wants to use basic or digest auth with an |
This is the only sane method. |
Ok, from my reading of RFC3986 section 3.2, an authority = [ userinfo "@" ] host [ ":" port ]
userinfo = *( unreserved / pct-encoded / sub-delims / ":" )
unreserved = ALPHA / DIGIT / "-" / "." / "_" / "~"
sub-delims = "$" / "&" / "'" / "=" / other-delims
other-delims = "!" / "(" / ")" / "*" / "+" / "," / ";"
pct-encoded = "%" HEXDIG HEXDIG |
This won't mean much here but in Elixir it is parsed out as %URI{
scheme: "http",
authority: "127.0.0.1",
userinfo: nil,
host: "127.0.0.1",
port: 80,
path: nil,
query: "@127.2.2.2/",
fragment: nil
} = URI.parse("http://[email protected]/") The host is right, the request is supposed to go to Using EDIT: OTP 21 is when |
So the reason we parse the user auth from the uri is because hackney is an http client. Just like curl or your browser does it , it's useful for the user to have the same convenience. Since. It's an HTTP client and as such is not only used for the use case of a server to connect to an api. There is nothing I see really wrong in parsing the auth from the http line there per see. Removing this convenience as an http client lib will break a lot of code around. Also here I fail to see how it's a security issue, if 127.0.0.2 can be used, what stop the "attacker" to just pass this host? That would mean that no check is done on the uri at first? User can already fix this "security" issue by parsing the uri (using the hackney_url module) they receive or store and ensure that user part is stripped. Then remove it and check if the host is accepted. How lazy should be the validation? That said, this convenience will be kept around but will now be enabled using a global option. The patch add support of url validation (strict mode enabled) . This will land during the day. |
Worth noting though that both curl and available browsers (Firefox, Chrome) parse the URL
Considering Hackney is the backend for one of the most popular HTTP libraries for Elixir (HTTPoison), most developers who are using it are not even aware of I recently had a similar obscure problem in my (much smaller of course) project, where I needed to filter out certain protocols. While investigating a report, I learned that the URL standard or it's common implementation allows having a Point being that it's actually critical that all libraries do URL parsing exactly the same way, not deviating from each other, across all programming languages and frameworks — and the less bespoke code, the better — otherwise no one knows at which point it will break and for which case, due to URLs being such a fundamental concept. (A bit unrelated, btw, but |
Well I understand your frustration @benoitc that was indeed a shitty move by the CVE report, however @jewalky point is correct in my POV specifically this part:
As this is the common use today shouldn't this fix which address be implemented? |
@Xunjin Unless the author of HTTPoison specifically had a conversation with the author of hackney, I think the amount of responsibility that trickles down to @jewalky to this point:
I think this is what you meant, but I would correct this to say |
Sorry, wondering if this is really an issue since it's been know for 11 months. |
I don't think anyone is suggesting removing the feature to parse userinfo from URIs, or even making the feature optional (though according to multiple specifications it should be deprecated). From the RFCs that I read yesterday, though, an unescaped According to the README, hackney supports Erlang 22.3 and later. Since |
Ah! Thank you for clarifying, I did not understand that from your message. I think the question of whether it's really an issue is a really fair point but unfortunately this is not the place for the conversation - you should send that comment upstream to whoever decided to open this advisory - so maybe one of these two places: https://nvd.nist.gov/vuln/detail/CVE-2025-1211 or https://www.cve.org/CVERecord?id=CVE-2025-1211 [ Edit: in addition, something being known for a while is not the same thing as something not being an issue :) ] |
Sending good vibes to you @benoitc Thanks for allowing an entire community of developers to stand on your shoulders. 🥇 |
To add to this, I did find in RFC 2396 that US-ASCII control characters are not to be allowed in the URI syntax https://datatracker.ietf.org/doc/html/rfc2396#section-2.4.3, but I did not find anywhere in the new RFC 3986 that mentions anything about control characters in the URI. Maybe someone smarter than me might be able to comment on this find. |
The ABNF rules look to me like they do not include control characters, unless I'm missing something or there's a superseding RFC I can't find. |
Yep, you are right. To me it looks like if you pass a control character you should error but if you pass a percent-encoded control character it would be valid according to the ABNF rules. I tested this case on a few different libraries and it seems that some handle this case slightly differently. |
I am closing this issue since hackney 1.21.0 has been released and patch hackney_url to fix this vulnerability. Thanks all for the discussion and encouragements. I appreciate. Full changelog: https://github.com/benoitc/hackney/releases/tag/1.21.0 |
I have a number of projects that require hackney via transient dependencies. This morning my security audits started flagging hackney with a low severity error for CVE-2025-1211.
I don't see an existing issue for this, so thought I would bring it to your attention here.
I discovered this through the
mix_audit
library, which I run as a part of my CI pipelines.The text was updated successfully, but these errors were encountered: