Skip to content

perf: speed up URL parsing and IDNA ToASCII - #1142

Open
geeknoid wants to merge 1 commit into
servo:mainfrom
geeknoid:main
Open

perf: speed up URL parsing and IDNA ToASCII#1142
geeknoid wants to merge 1 commit into
servo:mainfrom
geeknoid:main

Conversation

@geeknoid

Copy link
Copy Markdown

Avoid redundant work on the URL parsing hot path:

  • host: only percent-decode when the input contains a %, and append domain hosts to the serialization with push_str instead of write!.
  • parser: skip the userinfo scan when the authority has no @, and advance the input iterator by the known byte length after scanning a host rather than re-iterating it character by character.
  • idna: pass ASCII labels with a leading digit through the fast path when the domain cannot be a bidi domain name.

Add Callgrind (gungraun) instruction-count benchmarks alongside the existing wall-clock ones.

benchmark instr orig instr new Δ% ns orig ns new ns Δ%
plain 2403 1823 -24.1% 209 168 -19.6%
short 2653 2074 -21.8% 243 186 -23.5%
long 3517 2935 -16.5% 306 253 -17.3%
fragment 3887 3306 -14.9% 344 285 -17.2%
port 2965 2318 -21.8% 321 264 -17.8%
hyphen 3573 2607 -27.0% 307 235 -23.5%
leading_digit 3674 2315 -37.0% 315 211 -33.0%
unicode_mixed 6791 6128 -9.8% 729 678 -7.0%
punycode_mixed 6105 5289 -13.4% 607 498 -18.0%
unicode_ltr 8379 7609 -9.2% 847 788 -7.0%
punycode_ltr 8265 7249 -12.3% 793 692 -12.7%
unicode_rtl 8547 7853 -8.1% 834 766 -8.2%
punycode_rtl 8336 7306 -12.4% 780 660 -15.4%
url_to_file_path 2736 2734 -0.1% 285 280 -1.8%

Avoid redundant work on the URL parsing hot path:

- host: only percent-decode when the input contains a `%`, and append
  domain hosts to the serialization with `push_str` instead of `write!`.
- parser: skip the userinfo scan when the authority has no `@`, and
  advance the input iterator by the known byte length after scanning a
  host rather than re-iterating it character by character.
- idna: pass ASCII labels with a leading digit through the fast path
  when the domain cannot be a bidi domain name.

Add Callgrind (gungraun) instruction-count benchmarks alongside the
existing wall-clock ones.

| benchmark       | instr orig | instr new |   Δ%    |  ns orig |   ns new |   ns Δ% |
|-----------------|-----------:|----------:|--------:|---------:|---------:|--------:|
| plain           |       2403 |      1823 |  -24.1% |      209 |      168 |  -19.6% |
| short           |       2653 |      2074 |  -21.8% |      243 |      186 |  -23.5% |
| long            |       3517 |      2935 |  -16.5% |      306 |      253 |  -17.3% |
| fragment        |       3887 |      3306 |  -14.9% |      344 |      285 |  -17.2% |
| port            |       2965 |      2318 |  -21.8% |      321 |      264 |  -17.8% |
| hyphen          |       3573 |      2607 |  -27.0% |      307 |      235 |  -23.5% |
| leading_digit   |       3674 |      2315 |  -37.0% |      315 |      211 |  -33.0% |
| unicode_mixed   |       6791 |      6128 |   -9.8% |      729 |      678 |   -7.0% |
| punycode_mixed  |       6105 |      5289 |  -13.4% |      607 |      498 |  -18.0% |
| unicode_ltr     |       8379 |      7609 |   -9.2% |      847 |      788 |   -7.0% |
| punycode_ltr    |       8265 |      7249 |  -12.3% |      793 |      692 |  -12.7% |
| unicode_rtl     |       8547 |      7853 |   -8.1% |      834 |      766 |   -8.2% |
| punycode_rtl    |       8336 |      7306 |  -12.4% |      780 |      660 |  -15.4% |
| url_to_file_path|       2736 |      2734 |   -0.1% |      285 |      280 |   -1.8% |
@hsivonen

Copy link
Copy Markdown
Collaborator

Thanks. The IDNA change here may become moot with the redesign required by #1135.

@geeknoid

Copy link
Copy Markdown
Author

@hsivonen Can we go ahead and merge this PR, it's no-regrets improvement across the board. If some of it is thrown out due to a change in the future, that won't be a problem, right?

@hsivonen

Copy link
Copy Markdown
Collaborator

I'm OK with landing the idna part. I defer to Manish or Valentin for the parts outside idna.

@codecov

codecov Bot commented Aug 10, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 82.69231% with 9 lines in your changes missing coverage. Please review.
⚠️ Please upload report for BASE (main@25137be). Learn more about missing BASE report.

Files with missing lines Patch % Lines
idna/src/uts46.rs 78.26% 5 Missing ⚠️
url/src/parser.rs 81.25% 3 Missing ⚠️
url/src/host.rs 92.30% 1 Missing ⚠️
Additional details and impacted files
@@           Coverage Diff           @@
##             main    #1142   +/-   ##
=======================================
  Coverage        ?   86.94%           
=======================================
  Files           ?       26           
  Lines           ?     5315           
  Branches        ?        0           
=======================================
  Hits            ?     4621           
  Misses          ?      694           
  Partials        ?        0           

☔ View full report in Codecov by Harness.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

@Manishearth Manishearth left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Rest also seems fine

Comment thread idna/Cargo.toml
bencher = "0.1"
tester = "0.9"
serde_json = "1.0"
gungraun = "0.19.4"

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Not overly happy about adding another benchmarking framework but it's fine.

@Manishearth

Copy link
Copy Markdown
Member

CI fails

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.

3 participants