Uh oh!
There was an error while loading. Please reload this page.
Get piece unchecked in write - #83302
Conversation
rust-highfive
commented
Mar 19, 2021
r? @sfackler (rust-highfive has picked a reviewer for you, use r? to override) |
joshtriplett
commented
Mar 19, 2021
This seems a little surprising. Iterators like |
camsteffen
commented
Mar 19, 2021
This does not remove a bounds check within the loop. Only a length check of |
sfackler
commented
Mar 20, 2021
|
camsteffen
commented
Mar 20, 2021
I added assertions. I think that shouldn't be an issue, unless someone is using |
Uh oh!
There was an error while loading. Please reload this page.
1e04a07 to
dfb16efComparebors
commented
Mar 27, 2021
☔ The latest upstream changes (presumably #83580) made this pull request unmergeable. Please resolve the merge conflicts. |
dfb16ef to
a24ced6CompareUh oh!
There was an error while loading. Please reload this page.
5eab7b6 to
e8ec0bbCompare
This comment has been minimized.
This comment has been minimized.
e8ec0bb to
18d508cCompare
This comment has been minimized.
This comment has been minimized.
Now any unsafe block like // format_args!("hello {}", world)matchmatch(&world,){(arg0,) => [::core::fmt::ArgumentV1::new(
arg0,::core::fmt::Display::fmt,)],}{ref args => unsafe{::core::fmt::Arguments::new_v1(&["hello "], args)},};Thoughts? |
crlf0710
commented
Apr 23, 2021
@camsteffen Ping from triage, CI is still red here. Maybe you can use any change necessary to get CI green, so we can pass this on to the reviewer? |
18d508c to
6a1fa08Compare
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
JohnCSimon
commented
May 17, 2021
@rustbot label: +S-waiting-on-review -S-waiting-on-author |
camsteffen
commented
Aug 23, 2021
Error seems unrelated and I couldn't reproduce locally. @bors retry |
bors
commented
Aug 23, 2021
bors
commented
Aug 24, 2021
☀️ Test successful - checks-actions |
rylev
commented
Sep 1, 2021
This caused a large regression in instruction counts when testing the compiler. This is a largely a change in std lib code, and we don't really have a good process for dealing with how std lib changes effect performance. This seems to be primarily affecting debug and check builds, but there doesn't seem to be a query that is clearly to blame here. Given the motivation of this PR is primarily performance, I think it deserves a closer look. As part of the performance triage process, I'm marking this as a performance regression. If you believe this performance regression to be justifiable or once you have an issue or PR that addresses this regression, please mark this PR with the label perf-regression-triaged. @rustbot label +perf-regression |
…tolnay Get piece unchecked in `write` We already use specialized `zip`, but it seems like we can do a little better by not checking `pieces` length at all. `Arguments` constructors are now unsafe. So the `format_args!` expansion now includes an `unsafe` block. <details> <summary>Local Bench Diff</summary> ```text name before ns/iter after ns/iter diff ns/iter diff % speedup fmt::write_str_macro1 22,967 19,718 -3,249 -14.15% x 1.16 fmt::write_str_macro2 35,527 32,654 -2,873 -8.09% x 1.09 fmt::write_str_macro_debug 571,953 575,973 4,020 0.70% x 0.99 fmt::write_str_ref 9,579 9,459 -120 -1.25% x 1.01 fmt::write_str_value 9,573 9,572 -1 -0.01% x 1.00 fmt::write_u128_max 176 173 -3 -1.70% x 1.02 fmt::write_u128_min 138 134 -4 -2.90% x 1.03 fmt::write_u64_max 139 136 -3 -2.16% x 1.02 fmt::write_u64_min 129 135 6 4.65% x 0.96 fmt::write_vec_macro1 24,401 22,273 -2,128 -8.72% x 1.10 fmt::write_vec_macro2 37,096 35,602 -1,494 -4.03% x 1.04 fmt::write_vec_macro_debug 588,291 589,575 1,284 0.22% x 1.00 fmt::write_vec_ref 9,568 9,732 164 1.71% x 0.98 fmt::write_vec_value 9,516 9,625 109 1.15% x 0.99 ``` </details>
The regression seems to be caused by the change in the format_args! expansion which is now more complex in order to have an unsafe block that surrounds |
Mark-Simulacrum
commented
Sep 20, 2021
Hm. So #88571 does look to fix the majority of the regression here, but I suppose we cannot land it as-is due to the unsafe nesting causing some problems with spurious lints. I would lean towards reverting this PR; the small wins in runtime performance do not seem worth it given that fmt isn't optimized for performance anyway (indirect calls, can't get inlined, etc.). The compile time regressions are not insignificant. |
camsteffen
commented
Sep 20, 2021
My only reservation with reverting is that the internal fmt API was already unsafe before this PR added the unsafe modifiers. |
Mark-Simulacrum
commented
Sep 21, 2021
I.. sort of doubt that the get_unchecked there matters that much either, so I'd at least be fine with dropping it too (in favor of safety) as part of a pseudo-revert. |
Mark-Simulacrum
commented
Sep 21, 2021
Looks like the justification is noted in the commit (so nice!) -- d80f127. I think that makes sense, but we could likely get away with something "not wrong" as a result without invoking the full panic machinery. e.g., We could also move the unsafety as an assertion into a ZST that the caller must construct via an unsafe method, which would get compiled out but also allow us to put the unsafe block in a more local place, rather than wrapping the whole function call. |
camsteffen
commented
Oct 4, 2021
@Mark-Simulacrum I'm thinking the next step here for perf triage is to do a perf run reverting this and the follow-up PRs? |
Mark-Simulacrum
commented
Oct 4, 2021
I think #89139 definitely helped with some of the regressions caused by this PR. I think a trial revert would still be good, though, to estimate how much of a performance hit this is with the mitigations in place (like ZST-based unsafe). |
camsteffen
commented
Oct 4, 2021
The revert perf run looks good! #89521 (comment) |
Mark-Simulacrum
commented
Oct 4, 2021
Hm, the revert results feel a little unexpected. Unless there's been unrelated performance optimization that mitigates much of the regression seen in this PR, we would expect the revert to look equivalent, right? But instead we see barely any improvement. |
We already use specialized
zip, but it seems like we can do a little better by not checkingpieceslength at all.Argumentsconstructors are now unsafe. So theformat_args!expansion now includes anunsafeblock.Local Bench Diff