Skip to content

Commit 2009b58

Browse files
committed
Auto merge of rust-lang#11452 - y21:issue11165, r=Centri3
[`len_without_is_empty`]: follow type alias to find inherent `is_empty` method Fixes rust-lang#11165 When we see an `impl B` and `B` is a type alias to some type `A`, then we need to follow the type alias to look for an `is_empty` method on the aliased type `A`. Before this PR, it'd get the inherent impls of `B`, which there aren't any and so it would warn that there isn't an `is_empty` method even if there was one. Passing the type alias `DefId` to `TyCtxt::type_of` gives us the aliased `DefId` (or simply return the type itself if it wasn't a type alias) so we can just use that changelog: [`len_without_is_empty`]: follow type alias to find inherent `is_empty` method
2 parents b788add + 26c0f97 commit 2009b58

File tree

3 files changed

+38
-1
lines changed

3 files changed

+38
-1
lines changed

clippy_lints/src/len_zero.rs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -424,6 +424,14 @@ fn check_for_is_empty(
424424
item_name: Symbol,
425425
item_kind: &str,
426426
) {
427+
// Implementor may be a type alias, in which case we need to get the `DefId` of the aliased type to
428+
// find the correct inherent impls.
429+
let impl_ty = if let Some(adt) = cx.tcx.type_of(impl_ty).skip_binder().ty_adt_def() {
430+
adt.did()
431+
} else {
432+
return;
433+
};
434+
427435
let is_empty = Symbol::intern("is_empty");
428436
let is_empty = cx
429437
.tcx

tests/ui/len_without_is_empty.rs

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -436,4 +436,27 @@ impl DifferingErrors {
436436
}
437437
}
438438

439+
// Issue #11165
440+
pub struct Aliased1;
441+
pub type Alias1 = Aliased1;
442+
443+
impl Alias1 {
444+
pub fn len(&self) -> usize {
445+
todo!()
446+
}
447+
448+
pub fn is_empty(&self) -> bool {
449+
todo!()
450+
}
451+
}
452+
453+
pub struct Aliased2;
454+
pub type Alias2 = Aliased2;
455+
impl Alias2 {
456+
pub fn len(&self) -> usize {
457+
//~^ ERROR: type `Alias2` has a public `len` method, but no `is_empty` method
458+
todo!()
459+
}
460+
}
461+
439462
fn main() {}

tests/ui/len_without_is_empty.stderr

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -141,5 +141,11 @@ error: struct `AsyncResultLenWithoutIsEmpty` has a public `len` method, but no `
141141
LL | pub async fn len(&self) -> Result<usize, ()> {
142142
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
143143

144-
error: aborting due to 15 previous errors
144+
error: type `Alias2` has a public `len` method, but no `is_empty` method
145+
--> $DIR/len_without_is_empty.rs:456:5
146+
|
147+
LL | pub fn len(&self) -> usize {
148+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^
149+
150+
error: aborting due to 16 previous errors
145151

0 commit comments

Comments
 (0)