Skip to content
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

Use ControlFlow in more places #12830

Open
wants to merge 4 commits into
base: master
Choose a base branch
from

Conversation

blyxyas
Copy link
Member

@blyxyas blyxyas commented May 21, 2024

Now, instead of manually using variables in visitors to signify that a visit is "done" and that the visitor should stop traversing. We use the trait type "Result" to signify this (in relevant places).

I'll schedule a perf run, I don't think it will be much of a difference, but every bit of performance is welcomed :)

Fixes #12829
r? @y21

@rustbot rustbot added the S-waiting-on-review Status: Awaiting review from the assignee but also interested parties label May 21, 2024
@y21
Copy link
Member

y21 commented May 22, 2024

Looks like this broke some tests 😅

@blyxyas
Copy link
Member Author

blyxyas commented May 26, 2024

I've done some changes, it doesn't break any test files but it seems to not run .fixed rustfix tests.

EDIT: On CI it seems like there aren't any issues, could you test the patch on your PC to check? Maybe it's just my workflow

@blyxyas
Copy link
Member Author

blyxyas commented May 29, 2024

I've had this commit already finished for the last... 3 days? I'm not sure why I didn't commit it 😅

@y21
Copy link
Member

y21 commented May 29, 2024

EDIT: On CI it seems like there aren't any issues, could you test the patch on your PC to check? Maybe it's just my workflow

Oh sorry, didn't see this edit. Huh... yeah, I'm seeing something similar.
image

I don't think this is something caused by this PR though. It also seems to happen on master for me.

Anyway, I'll try taking a closer look at the changes in a bit

@blyxyas
Copy link
Member Author

blyxyas commented May 29, 2024

@oli-obk do you have some commentary on this weird behaviour

Copy link
Member

@y21 y21 left a comment

Choose a reason for hiding this comment

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

some possible improvements :)

Comment on lines 100 to 101
visit::walk_expr(self, expr);
ControlFlow::Continue(())
Copy link
Member

Choose a reason for hiding this comment

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

Suggested change
visit::walk_expr(self, expr);
ControlFlow::Continue(())
visit::walk_expr(self, expr)

This is currently ignoring Breaks that happen in nested visits. We should propagate them here.

This is in a bunch of places in this PR, can you fix the other instances of walk_*(); Continue(()) also?

}

type Result = ControlFlow<()>;
fn visit_expr(&mut self, expr: &'tcx Expr<'_>) -> ControlFlow<()> {
match expr.kind {
ExprKind::Ret(_) | ExprKind::Break(_, _) => {
self.has_break_or_return = true;
Copy link
Member

Choose a reason for hiding this comment

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

I think we can even remove this bool from the struct, by using .is_break() on the visit result

Copy link
Member

Choose a reason for hiding this comment

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

same in option_map_unwrap_or.rs and lifetimes.rs

@@ -90,12 +91,14 @@ pub struct OppVisitor<'a, 'tcx> {
}

impl<'tcx> Visitor<'tcx> for OppVisitor<'_, 'tcx> {
fn visit_expr(&mut self, expr: &'tcx Expr<'_>) {
type Result = ControlFlow<()>;
Copy link
Member

Choose a reason for hiding this comment

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

This could be ControlFlow<&'tcx Expr<'tcx>> with Break(mutex). (Also gets rid of the found_mutex field)

if self.found_default_call {
return;
}
fn visit_expr(&mut self, expr: &'tcx Expr<'tcx>) -> ControlFlow<()> {
walk_expr(self, expr);
Copy link
Member

Choose a reason for hiding this comment

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

Suggested change
walk_expr(self, expr);
walk_expr(self, expr)?;

propagating any Breaks

Copy link
Member

Choose a reason for hiding this comment

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

pls also double check that the Breaks from the other walk_* calls are propagated too in case I missed one :3

Copy link
Member Author

Choose a reason for hiding this comment

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

I'm having some problems with this suggestion. I'm having this problem with other walk_exprs:

error[E0308]: `?` operator has incompatible types
   --> clippy_lints/src/if_let_mutex.rs:100:9
    |
96  | ...n visit_expr(&mut self, expr: &'tcx Expr<'_>) -> ControlFlow<&'tcx Expr<'tcx>...
    |                                                     ----------------------------- expected `ControlFlow<&'tcx rustc_hir::Expr<'tcx>>` because of return type
...
100 | ...   visit::walk_expr(self, expr)?
    |       ^^^^^^^^^^^^^^^^^^^^^^^^^^^^-
    |       |                           |
    |       |                           help: try removing this `?`
    |       expected `ControlFlow<&Expr<'_>>`, found `()`
    |
    = note: `?` operator cannot convert from `()` to `ControlFlow<&'tcx rustc_hir::Expr<'tcx>>`
    = note:   expected enum `ControlFlow<&'tcx rustc_hir::Expr<'tcx>>`
            found unit type `()`

Copy link
Member

@y21 y21 Jun 2, 2024

Choose a reason for hiding this comment

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

Ah, my second comment might've been confusing. It was unrelated to the ? (just meant that we should make sure all ControlFlow::Breaks are properly handled, didn't mean to imply that we should use ? everywhere).
Looks like the ? is only needed in unconditional_recursion specifically, since it would otherwise be ignored.

In the if_let_mutex case (and all other cases where walk_expr is the last expression in the function) just walk_expr(self, expr) without the ? should be enough since its immediately returned.

@y21
Copy link
Member

y21 commented May 29, 2024

btw didn't this also change for_each_expr? I could swear I looked at this PR for a very short time before and saw a change there

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
S-waiting-on-review Status: Awaiting review from the assignee but also interested parties
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Use ControlFlow in more visitors
3 participants