Skip to content

Commit 9a30cb2

Browse files
mrobinsonservo-wpt-sync
authored andcommitted
dom: Always replace unpaired surrogates when handling page text
Background: > JavaScript strings are potentially ill-formed UTF-16 (arbitrary > Vec<u16>) and can contain unpaired surrogates. Rust’s String type is > well-formed UTF-8 and can not contain any surrogate. Surrogates are > never emitted when decoding bytes from the network, but they can sneak > in through document.write, the Element.innerHtml setter, or other DOM > APIs. In 2015, Servo launched an experiment to see if unpaired surrogates cropped up in page content. That experiment caused Servo to panic if unpaired surrogates were encountered with a request to report the page to bug #6564. During that time several pages were reported with unpaired surrogates, causing Servo to panic. In addition, when running the WPT tests Servo will never panic due to the `-Z replace-surrogates` option being passed by the test driver. Motivation: After this 10 year experiment, it's clear that unpaired surrogates are a real concern in page content. Several reports were filed of Servo panicking after encountering them in real world pages. A complete fix for this issue would be to somehow maintain unpaired surrogates in the DOM, but that is a much larger task than simply emitting U+FFD instead of an unpaired surrogate. Since it is clear that this kind of content exists, it is better for Servo to try its best to handle the content rather than crash as production browsers should not crash due to user content when possible. In this change, I modify Servo to always replace unpaired surrogates. It would have been ideal to only crash when debug assertions are enabled, but debug assertions are enabled by default in release mode -- so this wouldn't be effective for WPT tests. Signed-off-by: Martin Robinson <[email protected]>
1 parent 1d4c71a commit 9a30cb2

File tree

2 files changed

+2
-6
lines changed

2 files changed

+2
-6
lines changed

tools/wptrunner/wptrunner/browsers/servodriver.py

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -99,7 +99,6 @@ def __init__(self, logger, binary, debug_info=None, webdriver_host="127.0.0.1",
9999
# For some reason rustls does not like the certificate generated by the WPT tooling.
100100
"--ignore-certificate-errors",
101101
"--window-size", "800x600",
102-
"-Z", "replace-surrogates",
103102
"data:,",
104103
]
105104

tools/wptrunner/wptrunner/executors/executorservo.py

Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -80,16 +80,14 @@ def find_wpt_prefs(self):
8080
self.logger.error("Unable to find wpt-prefs.json")
8181
return default_path
8282

83-
def build_servo_command(self, test, extra_args=None, debug_opts="replace-surrogates"):
83+
def build_servo_command(self, test, extra_args=None):
8484
args = [
8585
"--hard-fail", "-u", "Servo/wptrunner",
8686
# See https://github.com/servo/servo/issues/30080.
8787
# For some reason rustls does not like the certificate generated by the WPT tooling.
8888
"--ignore-certificate-errors",
8989
"-z", self.test_url(test),
9090
]
91-
if debug_opts:
92-
args += ["-Z", debug_opts]
9391
for stylesheet in self.browser.user_stylesheets:
9492
args += ["--user-stylesheet", stylesheet]
9593
for pref, value in self.environment.get('prefs', {}).items():
@@ -231,12 +229,11 @@ def screenshot(self, test, viewport_size, dpi, page_ranges):
231229
extra_args = ["--exit",
232230
"--output=%s" % output_path,
233231
"--window-size", viewport_size or "800x600"]
234-
debug_opts = "replace-surrogates"
235232

236233
if dpi:
237234
extra_args += ["--device-pixel-ratio", dpi]
238235

239-
self.command = self.build_servo_command(test, extra_args, debug_opts)
236+
self.command = self.build_servo_command(test, extra_args)
240237

241238
if not self.interactive:
242239
self.proc = ProcessHandler(self.command,

0 commit comments

Comments
 (0)