GHSA-wwv5-g3v4-889x: Pip/tornado vulnerability
Summary The CVE-2026-35536 fix added a validation loop that rejects [\x00-\x20\x3b\x7f], but only for the hardcoded lowercase keys name/domain/path/samesite. The still-live deprecated kwargs path writes attacker-supplied attribute values straight into the Morsel with no validation, and because Morsel.setitem is case-insensitive, a capitalized kwarg (Domain=, Path=, SameSite=, Max-Age=) routes to the same reserved attribute while bypassing the loop — re-opening ;-delimited attribute injection.
python self.setcookie("sid", "abc", Domain="evil.com; Secure; SameSite=None") -> Set-Cookie: sid=abc; Domain=evil.com; Secure; SameSite=None; Path=/ Sanity (the canonical lowercase named arg IS blocked): self.setcookie("sid", "abc", domain="evil.com; Secure") # -> http.cookies.CookieError
The patch's regression test (SetCookieForbiddenCharHandler) only exercises the four named params, never the kwargs path, so the gap is not regression-covered.
Affected code - tornado/web.py → RequestHandler.setcookie: the validation loop covers only the lowercase named args; the trailing if kwargs: loop does morsel[k] = v with no character validation.
Steps to reproduce GET /upper (uses Domain= kwarg) emits Set-Cookie: cupper=v; Domain=evil.com; Secure; SameSite=None; Path=/; GET /lower (uses lowercase domain=) returns a CookieError.
Impact Injection of independent cookie attributes (force/drop Secure/HttpOnly/SameSite, rebind Domain/Path) — the same impact CVE-2026-35536 closed, via the sibling path the patch missed. Conditional on the app using a capitalized/legacy keyword.
Suggested remediation Apply the same [\x00-\x20\x3b\x7f] validation to every entry in the kwargs loop (after normalizing the key case), or remove the deprecated kwargs path; add a regression test for capitalized kwargs.
Credit Reported as part of an incomplete-patch measurement study (responsible disclosure).
Affected Software
Event History
Frequently Asked Questions
Which applications are realistically exposed to this issue?
Applications are exposed when they pass attacker-controlled cookie attribute values through the deprecated **kwargs path to RequestHandler.set_cookie, particularly using capitalized reserved keys such as Domain, Path, SameSite, or Max-Age. The lowercase named arguments name, domain, path, and samesite are covered by the validation loop.
What does an attacker need to exploit it?
An attacker needs control over a value assigned through the unvalidated **kwargs cookie-attribute path. Supplying a semicolon in a capitalized attribute value can inject additional Set-Cookie attributes, such as Secure or SameSite=None.
What can be done before a patch is available?
Avoid passing untrusted values through **kwargs to set_cookie. Use the lowercase named parameters where applicable, since the described validation rejects semicolons and the other listed forbidden characters for those parameters.
How can I identify potentially affected code?
Review RequestHandler.set_cookie calls for use of **kwargs or capitalized cookie attribute keys, including Domain, Path, SameSite, and Max-Age. Prioritize cases where those values can be influenced by a request, user input, or another untrusted source.