Skip to content

Commit 716eadf

Browse files
authored
zombie_processes: do not complain about early early returns (#14912)
If an early return is found under the HIR local declaration node but before the child process is created, it should not trigger the lint because the child process has not yet been created. changelog: [`zombie_process`]: do not complain about early early returns Fixes rust-lang/rust-clippy#14911
2 parents 9b8c42c + 3c8bfd1 commit 716eadf

File tree

2 files changed

+21
-15
lines changed

2 files changed

+21
-15
lines changed

clippy_lints/src/zombie_processes.rs

Lines changed: 11 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ use rustc_ast::Mutability;
55
use rustc_ast::visit::visit_opt;
66
use rustc_errors::Applicability;
77
use rustc_hir::def_id::LocalDefId;
8-
use rustc_hir::intravisit::{Visitor, walk_block, walk_expr, walk_local};
8+
use rustc_hir::intravisit::{Visitor, walk_block, walk_expr};
99
use rustc_hir::{Expr, ExprKind, HirId, LetStmt, Node, PatKind, Stmt, StmtKind};
1010
use rustc_lint::{LateContext, LateLintPass};
1111
use rustc_middle::hir::nested_filter;
@@ -69,8 +69,9 @@ impl<'tcx> LateLintPass<'tcx> for ZombieProcesses {
6969
let mut vis = WaitFinder {
7070
cx,
7171
local_id,
72+
create_id: expr.hir_id,
7273
body_id: cx.tcx.hir_enclosing_body_owner(expr.hir_id),
73-
state: VisitorState::WalkUpToLocal,
74+
state: VisitorState::WalkUpToCreate,
7475
early_return: None,
7576
missing_wait_branch: None,
7677
};
@@ -131,6 +132,7 @@ struct MaybeWait(Span);
131132
struct WaitFinder<'a, 'tcx> {
132133
cx: &'a LateContext<'tcx>,
133134
local_id: HirId,
135+
create_id: HirId,
134136
body_id: LocalDefId,
135137
state: VisitorState,
136138
early_return: Option<Span>,
@@ -141,8 +143,8 @@ struct WaitFinder<'a, 'tcx> {
141143

142144
#[derive(PartialEq)]
143145
enum VisitorState {
144-
WalkUpToLocal,
145-
LocalFound,
146+
WalkUpToCreate,
147+
CreateFound,
146148
}
147149

148150
#[derive(Copy, Clone)]
@@ -155,19 +157,13 @@ impl<'tcx> Visitor<'tcx> for WaitFinder<'_, 'tcx> {
155157
type NestedFilter = nested_filter::OnlyBodies;
156158
type Result = ControlFlow<MaybeWait>;
157159

158-
fn visit_local(&mut self, l: &'tcx LetStmt<'tcx>) -> Self::Result {
159-
if self.state == VisitorState::WalkUpToLocal
160-
&& let PatKind::Binding(_, pat_id, ..) = l.pat.kind
161-
&& self.local_id == pat_id
162-
{
163-
self.state = VisitorState::LocalFound;
160+
fn visit_expr(&mut self, ex: &'tcx Expr<'tcx>) -> Self::Result {
161+
if ex.hir_id == self.create_id {
162+
self.state = VisitorState::CreateFound;
163+
return Continue(());
164164
}
165165

166-
walk_local(self, l)
167-
}
168-
169-
fn visit_expr(&mut self, ex: &'tcx Expr<'tcx>) -> Self::Result {
170-
if self.state != VisitorState::LocalFound {
166+
if self.state != VisitorState::CreateFound {
171167
return walk_expr(self, ex);
172168
}
173169

tests/ui/zombie_processes.rs

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -198,3 +198,13 @@ mod issue14677 {
198198
child.wait().unwrap();
199199
}
200200
}
201+
202+
fn issue14911() -> std::io::Result<String> {
203+
let (mut recv, send) = std::io::pipe()?;
204+
let mut command = Command::new("ls")
205+
.stdout(send.try_clone()?)
206+
.spawn()
207+
.expect("Could not spawn new process...");
208+
command.wait()?;
209+
Ok("".into())
210+
}

0 commit comments

Comments
 (0)