Repository navigation
Escape "<" and ">" when serializing attribute values - #6362
Conversation
7dfae8b to
ac056b2
Compare
|
@zcorpan Thank you for nudging this along! Did you spend any time thinking about compat analysis? Mostly curious, I've never done any compat analysis.. |
|
@mozfreddyb I did think about it. I think static analysis is unlikely to find anything. What is possible is to add a use counter in Chromium (or equivalent in other engines) when the HTML serializer serializes an attribute value that contains "<" or ">". When the use counter reaches stable, the next HTTP Archive crawl will collect URLs from its data set of around 7 million pages, which can be queried with BigQuery. If there is an experimental implementation of this change, one can manually test those URLs and see if anything is obviously broken. If this quickly finds multiple things that are broken, then it likely is not a web compatible change. If nothing broken is found, then it might be web compatible, but obviously this wouldn't be a guarantee. The lack of complaints during the dev and beta period is probably a more convincing signal that it is web compatible. |
…in attribute values, a=testonly Automatic update from web-platform-tests HTML: tentative test for serializing <> in attribute values See whatwg/html#6362 -- wpt-commits: c5d4ba83796ad90ea175682d9e4477656fc5ddb5 wpt-pr: 51827
…in attribute values, a=testonly Automatic update from web-platform-tests HTML: tentative test for serializing <> in attribute values See whatwg/html#6362 -- wpt-commits: c5d4ba83796ad90ea175682d9e4477656fc5ddb5 wpt-pr: 51827
|
The Firefox/Gecko implementation was/is: https://bugzilla.mozilla.org/show_bug.cgi?id=1941347 |
annevk
left a comment
There was a problem hiding this comment.
We should probably hold off until Chromium has actually deployed this?
https://bugs.webkit.org/show_bug.cgi?id=292432 rdar://150520333 Reviewed by Ryosuke Niwa and Sam Weinig. Implement whatwg/html#6362 and add a preference in case we find out we have to disable it in certain cases. The preference does not impact the recently added getHTML() method on Element and ShadowRoot as that should be new enough to not matter. Add new test from: web-platform-tests/wpt#27501 Canonical link: https://commits.webkit.org/295149@main
|
Given that everyone is moving ahead with this and we still haven't seen breakage, let's flip the switch now. It's also rather awkward to keep the tests and such in limbo that long. |
ac056b2 to
1896a6a
Compare
…lues when serializing, Automatic update from web-platform-tests HTML: Escape "<" and ">" in attribute values when serializing See whatwg/html#6362. -- wpt-commits: 3fad71d22b6681a3430ff498add3ea8c31660401 wpt-pr: 27501 Differential Revision: https://phabricator.services.mozilla.com/D250932
…lues when serializing, Automatic update from web-platform-tests HTML: Escape "<" and ">" in attribute values when serializing See whatwg/html#6362. -- wpt-commits: 3fad71d22b6681a3430ff498add3ea8c31660401 wpt-pr: 27501 Differential Revision: https://phabricator.services.mozilla.com/D250932
…lues when serializing, Automatic update from web-platform-tests HTML: Escape "<" and ">" in attribute values when serializing See whatwg/html#6362. -- wpt-commits: 3fad71d22b6681a3430ff498add3ea8c31660401 wpt-pr: 27501 Differential Revision: https://phabricator.services.mozilla.com/D250932 UltraBlame original commit: b534c633b2ea53fe10c965fc83f8a795b7f7e2a8
…lues when serializing, Automatic update from web-platform-tests HTML: Escape "<" and ">" in attribute values when serializing See whatwg/html#6362. -- wpt-commits: 3fad71d22b6681a3430ff498add3ea8c31660401 wpt-pr: 27501 Differential Revision: https://phabricator.services.mozilla.com/D250932 UltraBlame original commit: b534c633b2ea53fe10c965fc83f8a795b7f7e2a8
…lues when serializing, Automatic update from web-platform-tests HTML: Escape "<" and ">" in attribute values when serializing See whatwg/html#6362. -- wpt-commits: 3fad71d22b6681a3430ff498add3ea8c31660401 wpt-pr: 27501 Differential Revision: https://phabricator.services.mozilla.com/D250932 UltraBlame original commit: b534c633b2ea53fe10c965fc83f8a795b7f7e2a8
The experiment to escape "<" and ">" in attributes has been successful and after https://crrev.com/c/6597054 it's been launched to everyone (in M138) and is a part of the spec (see whatwg/html#6362). This CL does a cleanup changes the following: 1) Removes the use counter which is no longer necessary. 2) Updates markup_formatter.{cc,h} so that "<>" are always escaped. 3) Removes EscapeLtGtInAttributes as a runtime enabled feature Note that removing the usecounter forced change to the signature of `AppendAttributeValue` method -- it no longer needs to accept `Document`. So this CL changes more files so all call sites are changed accordingly. Because this has been launched in M138, it's now safe to remove in M140. Bug: 40747109 Change-Id: If14151908eb74643fcbd2fa1d461f6002da3ccd7 Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6714366 Reviewed-by: Mason Freed <masonf@chromium.org> Reviewed-by: Mike West <mkwst@chromium.org> Commit-Queue: Michał Bentkowski <securitymb@google.com> Cr-Commit-Position: refs/heads/main@{#1484826}
This reverts commit 8d717b4. Reason for revert: Because I failed to merge the original change in M138, it actually landed in M139. So I'm reverting this one to make sure that the cleanup will happen at M141 at the earliest. Bug: 40747109 Original change's description: > Cleanup after EscapeLtGtInAttributes experiment > > The experiment to escape "<" and ">" in attributes has been successful > and after https://crrev.com/c/6597054 it's been launched to everyone (in > M138) and is a part of the spec (see > whatwg/html#6362). > > This CL does a cleanup changes the following: 1) Removes the use > counter which is no longer necessary. 2) Updates markup_formatter.{cc,h} > so that "<>" are always escaped. 3) Removes EscapeLtGtInAttributes as a > runtime enabled feature > > Note that removing the usecounter forced change to the signature of > `AppendAttributeValue` method -- it no longer needs to accept > `Document`. So this CL changes more files so all call sites are changed > accordingly. > > Because this has been launched in M138, it's now safe to remove in M140. > > Bug: 40747109 > Change-Id: If14151908eb74643fcbd2fa1d461f6002da3ccd7 > Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6714366 > Reviewed-by: Mason Freed <masonf@chromium.org> > Reviewed-by: Mike West <mkwst@chromium.org> > Commit-Queue: Michał Bentkowski <securitymb@google.com> > Cr-Commit-Position: refs/heads/main@{#1484826} Bug: 40747109 Change-Id: I617c4a1159c33f4d30d52eea11eca52b58e64d26 Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6769766 Reviewed-by: Mason Freed <masonf@chromium.org> Commit-Queue: Michał Bentkowski <securitymb@google.com> Reviewed-by: Mike West <mkwst@chromium.org> Cr-Commit-Position: refs/heads/main@{#1489988}
https://bugs.webkit.org/show_bug.cgi?id=292432 rdar://150520333 Reviewed by Ryosuke Niwa and Sam Weinig. Implement whatwg/html#6362 and add a preference in case we find out we have to disable it in certain cases. The preference does not impact the recently added getHTML() method on Element and ShadowRoot as that should be new enough to not matter. Add new test from: web-platform-tests/wpt#27501 Canonical link: https://commits.webkit.org/295149@main
This reverts commit 548fe0c. Reason for reland: Enough time has passed, we didn't get any new complaints. Bug: 40747109 Original change's description: > Revert "Cleanup after EscapeLtGtInAttributes experiment" > > This reverts commit 8d717b4. > > Reason for revert: Because I failed to merge the original change in M138, it actually landed in M139. So I'm reverting this one to make sure that the cleanup will happen at M141 at the earliest. > > Bug: 40747109 > Original change's description: > > Cleanup after EscapeLtGtInAttributes experiment > > > > The experiment to escape "<" and ">" in attributes has been successful > > and after https://crrev.com/c/6597054 it's been launched to everyone (in > > M138) and is a part of the spec (see > > whatwg/html#6362). > > > > This CL does a cleanup changes the following: 1) Removes the use > > counter which is no longer necessary. 2) Updates markup_formatter.{cc,h} > > so that "<>" are always escaped. 3) Removes EscapeLtGtInAttributes as a > > runtime enabled feature > > > > Note that removing the usecounter forced change to the signature of > > `AppendAttributeValue` method -- it no longer needs to accept > > `Document`. So this CL changes more files so all call sites are changed > > accordingly. > > > > Because this has been launched in M138, it's now safe to remove in M140. > > > > Bug: 40747109 > > Change-Id: If14151908eb74643fcbd2fa1d461f6002da3ccd7 > > Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6714366 > > Reviewed-by: Mason Freed <masonf@chromium.org> > > Reviewed-by: Mike West <mkwst@chromium.org> > > Commit-Queue: Michał Bentkowski <securitymb@google.com> > > Cr-Commit-Position: refs/heads/main@{#1484826} > > Bug: 40747109 > Change-Id: I617c4a1159c33f4d30d52eea11eca52b58e64d26 > Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6769766 > Reviewed-by: Mason Freed <masonf@chromium.org> > Commit-Queue: Michał Bentkowski <securitymb@google.com> > Reviewed-by: Mike West <mkwst@chromium.org> > Cr-Commit-Position: refs/heads/main@{#1489988} Bug: 40747109 Change-Id: I5995b31c1f82dc48fb44e289b9d0d6444b294dbe Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6905283 Reviewed-by: Daniel Vogelheim <vogelheim@chromium.org> Reviewed-by: Mason Freed <masonf@chromium.org> Commit-Queue: Michał Bentkowski <securitymb@google.com> Cr-Commit-Position: refs/heads/main@{#1512746}
Since the HTML standard's change of 2025-05-20 (whatwg/html#6362), the fragment serialization escapes < and > in attribute values, and browsers ship it. The fork's own escaper replaces entities' escapeAttribute: text escapes &, <, > and U+00A0; attribute values also escape ". Elements write their attributes through one serializeAttribute, and the fork no longer depends on entities directly. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01JCrHZsvZnDmQpSnRDjP1Jb
… does Since whatwg/html#6362 (2025-05-20), the fragment serialization escapes `<` and `>` in attribute values as well as in text, against mutation XSS; Chrome 138, Firefox 140 and Safari 26 ship it, and html5ever's own serializer does it. `escape_attribute` now escapes `&`, `"`, `<`, `>` and U+00A0. The fork makes the same change. Until its fixtures are recorded again, seven recorded outputs of the pinned fork differ, each only by `<`/`>` in an attribute: the trees of two parse inputs, as a template and as a document; two serialized documents; and one rendered spec. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01JCrHZsvZnDmQpSnRDjP1Jb
The serializer and the start tags rewrite() rebuilds for edited elements left < and > literal inside attribute values. A value that holds markup stays inert after one parse, but a serialize and reparse through foreign content or <noscript> can move it into a raw-text element, where its </style> or </noscript> ends the element and the rest becomes live markup. whatwg/html#6362 added < and > to the attribute mode of "escaping a string" for this reason. Escape < and > in attribute values under every formatter and layout and in rewrite() start tags, and drop the angle-bracket switch from the serializer's escape scan.
packages/tea-dom/src/render.dawn adds to_html and to_document, a third reader of the Node[M] that diff/apply and wire already read. No existing module changes. Two escapes. Text escapes & < >. Attribute values are always double-quoted and escape & < > ". The < > in attributes follows the WHATWG serialisation change of May 2025 (whatwg/html#6362, shipped in Chrome 138, Firefox 140 and Safari 26), which closes a mutation XSS route. elm-html-string escaping only the quote, and leptos 0.6 streaming SSR skipping text escapes (leptos#4885), are the two failures the tests are written against. The promise is that the string parses to the DOM the bridge builds from the same tree on its first frame, so two rules copy js/dom.mjs rather than plain serialisation. checked on a form control prints nothing for "" and "false" and a bare checked otherwise, which is writeProperty; printing checked="false" would check the box the bridge leaves unchecked. A repeated prop prints once, at its first position with its last value, which is what new Map(node.props) keeps; a parser keeps the first of two attributes, so printing both would make the two readers disagree on one tree. Each of four mutations reds the suite: dropping the quote from the attribute escape, a void test that is always false, deleting the checked rule, and printing text unescaped. tea_dom goes from 0.1.0 to 0.2.0. The version had never moved since the package was created, through on_value, foreign and the serve variants; nothing polices it, but a new public module is the addition 0.x minor versions are for, and this ends the habit of never bumping it.
Avoid a class of XSS attacks where markup goes through
a lossy parse-serialize-parse roundtrip and the original
attribute value is parsed in the data state.
This reverts 4eeb8a1.
Fixes #6235.
(See WHATWG Working Mode: Changes for more details.)
/parsing.html ( diff )
/parsing.html ( diff )