Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Replace OptimizedInboxTextEncoder vectorization with SearchValues #114494

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

Merged
merged 1 commit into from
Apr 16, 2025

Conversation

MihaZupan
Copy link
Member

Closes #114437

I only replaced the existing ASCII-only fast path.

If we wanted to later, we could add a SearchValues implementation that handles the large character sets that STEW uses, in which case the .NET core implementation would just directly forward to SearchValues.

@MihaZupan MihaZupan added this to the 10.0.0 milestone Apr 10, 2025
@MihaZupan MihaZupan self-assigned this Apr 10, 2025
@Copilot Copilot AI review requested due to automatic review settings April 10, 2025 16:24
Copy link
Contributor

@Copilot Copilot AI left a comment

Choose a reason for hiding this comment

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

Copilot reviewed 5 out of 7 changed files in this pull request and generated 1 comment.

Files not reviewed (2)
  • src/libraries/System.Text.Encodings.Web/src/System.Text.Encodings.Web.csproj: Language not supported
  • src/libraries/System.Text.Encodings.Web/tests/System.Text.Encodings.Web.Tests.csproj: Language not supported
Comments suppressed due to low confidence (2)

src/libraries/System.Text.Encodings.Web/tests/AllowedAsciiCodePointsTests.cs:1

  • Removal of AllowedAsciiCodePointsTests.cs may reduce test coverage for the fast path. Consider adding new tests to validate the SearchValues-based approach.
// Entire test file removed

src/libraries/System.Text.Encodings.Web/src/System/Text/Encodings/Web/OptimizedInboxTextEncoder.cs:406

  • Double-check that the combination of IndexOfAnyExcept with the char.IsAscii check correctly identifies the first disallowed character in all edge cases, especially when the span consists entirely of allowed characters.
if ((uint)asciiCharsSkipped >= (uint)data.Length || char.IsAscii(data[asciiCharsSkipped]))

Copy link
Contributor

Tagging subscribers to this area: @dotnet/area-system-text-encodings-web
See info in area-owners.md if you want to be subscribed.

@MihaZupan
Copy link
Member Author

@MihuBot benchmark System.Text.Json

@MihaZupan
Copy link
Member Author

@MihuBot benchmark System.Text.Json -arm

@tarekgh
Copy link
Member

tarekgh commented Apr 10, 2025

Just wondering, does the optimization using SearchValues will still work fine on previous .NET versions like .NET 8?

Copy link
Member

@tarekgh tarekgh left a comment

Choose a reason for hiding this comment

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

LGTM as long as the benchmark numbers at least not showing any regressions. Thanks!

@MihaZupan
Copy link
Member Author

on previous .NET versions like .NET 8?

I'd expect it to be very similar in this case since we're limiting usage to ASCII-only sets.

I'll see what the numbers show for short inputs.
For longer inputs this should be an improvement on X64 since SearchValues also has Avx2 paths, and handles trailing elements more efficiently.

@MihaZupan
Copy link
Member Author

Numbers for Utf8JsonWriter/Perf.Strings.cs look good (MihuBot/runtime-utils#1062, MihuBot/runtime-utils#1063).
@eiriktsarpalis Is that a reasonable benchmark to look at for Json when changing JsonWriterHelper.NeedsEscaping perf?

X64 System.Text.Json.Tests.Perf_Strings
BenchmarkDotNet v0.14.1-nightly.20250107.205, Linux Ubuntu 22.04.5 LTS (Jammy Jellyfish)
AMD EPYC 9V74, 1 CPU, 8 logical and 4 physical cores
MediumRun : .NET 10.0.0 (42.42.42.42424), X64 RyuJIT AVX-512F+CD+BW+DQ+VL+VBMI
Job=MediumRun  OutlierMode=DontRemove  IterationCount=15
LaunchCount=2  MemoryRandomization=True  WarmupCount=10
Method Toolchain Formatted SkipValidation Escaped Mean Error Ratio Allocated Alloc Ratio
WriteStringsUtf8 Main False False AllEscaped 31.090 ms 0.2648 ms 1.00 2176.06 KB 1.00
WriteStringsUtf8 PR False False AllEscaped 30.537 ms 0.3616 ms 0.98 4351.99 KB 2.00
WriteStringsUtf16 Main False False AllEscaped 30.887 ms 0.3925 ms 1.00 4351.93 KB 1.00
WriteStringsUtf16 PR False False AllEscaped 30.856 ms 0.3415 ms 1.00 4351.93 KB 1.00
WriteStringsUtf8 Main False False OneEscaped 5.959 ms 0.2084 ms 1.00 136.11 KB 1.00
WriteStringsUtf8 PR False False OneEscaped 5.649 ms 0.0877 ms 0.95 136.11 KB 1.00
WriteStringsUtf16 Main False False OneEscaped 7.910 ms 0.0518 ms 1.00 272.08 KB 1.00
WriteStringsUtf16 PR False False OneEscaped 7.588 ms 0.0237 ms 0.96 136.11 KB 0.50
WriteStringsUtf8 Main False False NoneEscaped 2.913 ms 0.0221 ms 1.00 68.12 KB 1.00
WriteStringsUtf8 PR False False NoneEscaped 2.120 ms 0.0156 ms 0.73 68.12 KB 1.00
WriteStringsUtf16 Main False False NoneEscaped 4.611 ms 0.0193 ms 1.00 136.11 KB 1.00
WriteStringsUtf16 PR False False NoneEscaped 3.981 ms 0.0233 ms 0.86 136.1 KB 1.00
WriteStringsUtf8 Main False True AllEscaped 30.814 ms 0.3473 ms 1.00 4351.99 KB 1.00
WriteStringsUtf8 PR False True AllEscaped 30.849 ms 0.3239 ms 1.00 2176.06 KB 0.50
WriteStringsUtf16 Main False True AllEscaped 30.530 ms 0.3316 ms 1.00 4351.95 KB 1.00
WriteStringsUtf16 PR False True AllEscaped 30.842 ms 0.3172 ms 1.01 4351.95 KB 1.00
WriteStringsUtf8 Main False True OneEscaped 5.746 ms 0.0287 ms 1.00 136.11 KB 1.00
WriteStringsUtf8 PR False True OneEscaped 5.561 ms 0.0432 ms 0.97 136.11 KB 1.00
WriteStringsUtf16 Main False True OneEscaped 7.821 ms 0.0341 ms 1.00 272.08 KB 1.00
WriteStringsUtf16 PR False True OneEscaped 7.561 ms 0.0287 ms 0.97 136.1 KB 0.50
WriteStringsUtf8 Main False True NoneEscaped 2.879 ms 0.0291 ms 1.00 68.12 KB 1.00
WriteStringsUtf8 PR False True NoneEscaped 2.091 ms 0.0197 ms 0.73 68.12 KB 1.00
WriteStringsUtf16 Main False True NoneEscaped 4.550 ms 0.0177 ms 1.00 136.1 KB 1.00
WriteStringsUtf16 PR False True NoneEscaped 3.886 ms 0.0080 ms 0.85 68.12 KB 0.50
WriteStringsUtf8 Main True False AllEscaped 30.932 ms 0.3364 ms 1.00 2176.06 KB 1.00
WriteStringsUtf8 PR True False AllEscaped 31.011 ms 0.2931 ms 1.00 2176.06 KB 1.00
WriteStringsUtf16 Main True False AllEscaped 30.902 ms 0.3211 ms 1.00 2176.03 KB 1.00
WriteStringsUtf16 PR True False AllEscaped 30.790 ms 0.3336 ms 1.00 4351.93 KB 2.00
WriteStringsUtf8 Main True False OneEscaped 6.031 ms 0.0290 ms 1.00 136.11 KB 1.00
WriteStringsUtf8 PR True False OneEscaped 5.814 ms 0.0119 ms 0.96 136.11 KB 1.00
WriteStringsUtf16 Main True False OneEscaped 8.115 ms 0.0143 ms 1.00 272.08 KB 1.00
WriteStringsUtf16 PR True False OneEscaped 7.799 ms 0.0095 ms 0.96 136.1 KB 0.50
WriteStringsUtf8 Main True False NoneEscaped 3.186 ms 0.0123 ms 1.00 68.12 KB 1.00
WriteStringsUtf8 PR True False NoneEscaped 2.397 ms 0.0061 ms 0.75 68.12 KB 1.00
WriteStringsUtf16 Main True False NoneEscaped 4.794 ms 0.0144 ms 1.00 136.11 KB 1.00
WriteStringsUtf16 PR True False NoneEscaped 4.154 ms 0.0046 ms 0.87 136.11 KB 1.00
WriteStringsUtf8 Main True True AllEscaped 31.222 ms 0.3781 ms 1.00 4351.99 KB 1.00
WriteStringsUtf8 PR True True AllEscaped 30.947 ms 0.3336 ms 0.99 4351.97 KB 1.00
WriteStringsUtf16 Main True True AllEscaped 30.825 ms 0.3191 ms 1.00 4351.95 KB 1.00
WriteStringsUtf16 PR True True AllEscaped 31.059 ms 0.4522 ms 1.01 2176.04 KB 0.50
WriteStringsUtf8 Main True True OneEscaped 5.986 ms 0.0173 ms 1.00 136.11 KB 1.00
WriteStringsUtf8 PR True True OneEscaped 5.779 ms 0.0283 ms 0.97 136.11 KB 1.00
WriteStringsUtf16 Main True True OneEscaped 8.080 ms 0.0146 ms 1.00 272.08 KB 1.00
WriteStringsUtf16 PR True True OneEscaped 7.766 ms 0.0271 ms 0.96 136.11 KB 0.50
WriteStringsUtf8 Main True True NoneEscaped 3.150 ms 0.0329 ms 1.00 68.12 KB 1.00
WriteStringsUtf8 PR True True NoneEscaped 2.378 ms 0.0075 ms 0.75 68.12 KB 1.00
WriteStringsUtf16 Main True True NoneEscaped 4.818 ms 0.0223 ms 1.00 136.1 KB 1.00
WriteStringsUtf16 PR True True NoneEscaped 4.135 ms 0.0074 ms 0.86 136.1 KB 1.00
ARM64 System.Text.Json.Tests.Perf_Strings
BenchmarkDotNet v0.14.1-nightly.20250107.205, Linux Ubuntu 22.04.5 LTS (Jammy Jellyfish)
Unknown processor, 8 physical cores
MediumRun : .NET 10.0.0 (42.42.42.42424), Arm64 RyuJIT AdvSIMD
Job=MediumRun  OutlierMode=DontRemove  IterationCount=15
LaunchCount=2  MemoryRandomization=True  WarmupCount=10
Method Toolchain Formatted SkipValidation Escaped Mean Error Ratio Allocated Alloc Ratio
WriteStringsUtf8 Main False False AllEscaped 65.456 ms 0.5885 ms 1.00 8704.08 KB 1.00
WriteStringsUtf8 PR False False AllEscaped 65.883 ms 0.5980 ms 1.01 8704.2 KB 1.00
WriteStringsUtf16 Main False False AllEscaped 64.839 ms 0.1328 ms 1.00 8704.53 KB 1.00
WriteStringsUtf16 PR False False AllEscaped 64.784 ms 0.1060 ms 1.00 8704.49 KB 1.00
WriteStringsUtf8 Main False False OneEscaped 7.103 ms 0.0290 ms 1.00 136.1 KB 1.00
WriteStringsUtf8 PR False False OneEscaped 6.738 ms 0.0418 ms 0.95 136.11 KB 1.00
WriteStringsUtf16 Main False False OneEscaped 9.319 ms 0.0455 ms 1.00 272.08 KB 1.00
WriteStringsUtf16 PR False False OneEscaped 9.017 ms 0.0435 ms 0.97 272.08 KB 1.00
WriteStringsUtf8 Main False False NoneEscaped 3.217 ms 0.0089 ms 1.00 68.12 KB 1.00
WriteStringsUtf8 PR False False NoneEscaped 2.539 ms 0.0164 ms 0.79 68.12 KB 1.00
WriteStringsUtf16 Main False False NoneEscaped 4.785 ms 0.0718 ms 1.00 136.1 KB 1.00
WriteStringsUtf16 PR False False NoneEscaped 4.336 ms 0.0059 ms 0.91 136.1 KB 1.00
WriteStringsUtf8 Main False True AllEscaped 66.573 ms 0.6872 ms 1.00 8703.76 KB 1.00
WriteStringsUtf8 PR False True AllEscaped 65.994 ms 0.5760 ms 0.99 8703.76 KB 1.00
WriteStringsUtf16 Main False True AllEscaped 64.941 ms 0.1118 ms 1.00 8703.72 KB 1.00
WriteStringsUtf16 PR False True AllEscaped 64.841 ms 0.1180 ms 1.00 8703.72 KB 1.00
WriteStringsUtf8 Main False True OneEscaped 7.067 ms 0.0226 ms 1.00 136.1 KB 1.00
WriteStringsUtf8 PR False True OneEscaped 6.719 ms 0.0234 ms 0.95 136.1 KB 1.00
WriteStringsUtf16 Main False True OneEscaped 9.262 ms 0.0428 ms 1.00 272.08 KB 1.00
WriteStringsUtf16 PR False True OneEscaped 9.022 ms 0.0407 ms 0.97 272.08 KB 1.00
WriteStringsUtf8 Main False True NoneEscaped 3.335 ms 0.1156 ms 1.00 68.12 KB 1.00
WriteStringsUtf8 PR False True NoneEscaped 2.475 ms 0.0049 ms 0.74 68.12 KB 1.00
WriteStringsUtf16 Main False True NoneEscaped 4.689 ms 0.0033 ms 1.00 136.1 KB 1.00
WriteStringsUtf16 PR False True NoneEscaped 4.286 ms 0.0096 ms 0.91 136.1 KB 1.00
WriteStringsUtf8 Main True False AllEscaped 67.163 ms 0.6017 ms 1.00 8703.81 KB 1.00
WriteStringsUtf8 PR True False AllEscaped 66.579 ms 0.5252 ms 0.99 8703.76 KB 1.00
WriteStringsUtf16 Main True False AllEscaped 65.064 ms 0.0905 ms 1.00 8703.72 KB 1.00
WriteStringsUtf16 PR True False AllEscaped 65.027 ms 0.0718 ms 1.00 8703.72 KB 1.00
WriteStringsUtf8 Main True False OneEscaped 7.420 ms 0.0154 ms 1.00 136.1 KB 1.00
WriteStringsUtf8 PR True False OneEscaped 7.172 ms 0.0569 ms 0.97 136.1 KB 1.00
WriteStringsUtf16 Main True False OneEscaped 9.721 ms 0.0108 ms 1.00 272.08 KB 1.00
WriteStringsUtf16 PR True False OneEscaped 9.325 ms 0.0115 ms 0.96 272.08 KB 1.00
WriteStringsUtf8 Main True False NoneEscaped 3.518 ms 0.0107 ms 1.00 68.12 KB 1.00
WriteStringsUtf8 PR True False NoneEscaped 2.869 ms 0.0036 ms 0.82 68.12 KB 1.00
WriteStringsUtf16 Main True False NoneEscaped 5.202 ms 0.0359 ms 1.00 136.1 KB 1.00
WriteStringsUtf16 PR True False NoneEscaped 4.650 ms 0.0344 ms 0.89 136.1 KB 1.00
WriteStringsUtf8 Main True True AllEscaped 66.755 ms 0.7020 ms 1.00 8703.76 KB 1.00
WriteStringsUtf8 PR True True AllEscaped 65.929 ms 0.8973 ms 0.99 8703.76 KB 1.00
WriteStringsUtf16 Main True True AllEscaped 65.076 ms 0.0751 ms 1.00 8703.72 KB 1.00
WriteStringsUtf16 PR True True AllEscaped 65.038 ms 0.0845 ms 1.00 8703.72 KB 1.00
WriteStringsUtf8 Main True True OneEscaped 7.542 ms 0.1200 ms 1.00 136.1 KB 1.00
WriteStringsUtf8 PR True True OneEscaped 7.062 ms 0.0189 ms 0.94 136.1 KB 1.00
WriteStringsUtf16 Main True True OneEscaped 9.816 ms 0.0194 ms 1.00 272.08 KB 1.00
WriteStringsUtf16 PR True True OneEscaped 9.341 ms 0.0225 ms 0.95 272.08 KB 1.00
WriteStringsUtf8 Main True True NoneEscaped 3.504 ms 0.0160 ms 1.00 68.12 KB 1.00
WriteStringsUtf8 PR True True NoneEscaped 2.823 ms 0.0031 ms 0.81 68.12 KB 1.00
WriteStringsUtf16 Main True True NoneEscaped 5.047 ms 0.0048 ms 1.00 136.1 KB 1.00
WriteStringsUtf16 PR True True NoneEscaped 4.589 ms 0.0142 ms 0.91 136.1 KB 1.00

@MihaZupan
Copy link
Member Author

@EgorBot -mono --envvars MONO_ENV_OPTIONS:--interp --filter "Perf_Strings"

@lewing
Copy link
Member

lewing commented Apr 23, 2025

Some impressive improvements here for Wasm both interpreter and aot. Nice work!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Use SearchValues in System.Text.Encodings.Web
3 participants