Skip to content

Commit 270c94e

Browse files
committed
Auto merge of #106215 - matthiaskrgr:rollup-53r89ww, r=matthiaskrgr
Rollup of 6 pull requests Successful merges: - #106028 (docs/test: add UI test and long-form error docs for `E0461`) - #106172 (Suggest `impl Iterator` when possible for `_` return type) - #106173 (Deduplicate `op` methods) - #106176 (Recover `fn` keyword as `Fn` trait in bounds) - #106194 (rustdoc: combine common sidebar background color CSS rules) - #106199 (Silence knock-down errors on `[type error]` bindings) Failed merges: r? `@ghost` `@rustbot` modify labels: rollup
2 parents 83a28ef + d37cb3f commit 270c94e

36 files changed

+500
-395
lines changed

compiler/rustc_error_codes/src/error_codes.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -244,6 +244,7 @@ E0457: include_str!("./error_codes/E0457.md"),
244244
E0458: include_str!("./error_codes/E0458.md"),
245245
E0459: include_str!("./error_codes/E0459.md"),
246246
E0460: include_str!("./error_codes/E0460.md"),
247+
E0461: include_str!("./error_codes/E0461.md"),
247248
E0462: include_str!("./error_codes/E0462.md"),
248249
E0463: include_str!("./error_codes/E0463.md"),
249250
E0464: include_str!("./error_codes/E0464.md"),
@@ -595,7 +596,6 @@ E0791: include_str!("./error_codes/E0791.md"),
595596
// E0421, // merged into 531
596597
// E0427, // merged into 530
597598
// E0456, // plugin `..` is not available for triple `..`
598-
E0461, // couldn't find crate `..` with expected target triple ..
599599
E0465, // multiple .. candidates for `..` found
600600
// E0467, // removed
601601
// E0470, // removed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
Couldn't find crate `..` with expected target triple `..`.
2+
3+
Example of erroneous code:
4+
5+
`a.rs`
6+
```ignore (cannot-link-with-other-tests)
7+
#![crate_type = "lib"]
8+
9+
fn foo() {}
10+
```
11+
12+
`main.rs`
13+
```ignore (cannot-link-with-other-tests)
14+
extern crate a;
15+
16+
fn main() {
17+
a::foo();
18+
}
19+
```
20+
21+
`a.rs` is then compiled with `--target powerpc-unknown-linux-gnu` and `b.rs`
22+
with `--target x86_64-unknown-linux-gnu`. `a.rs` is compiled into a binary
23+
format incompatible with `b.rs`; PowerPC and x86 are totally different
24+
architectures. This issue also extends to any difference in target triples, as
25+
`std` is operating-system specific.
26+
27+
This error can be fixed by:
28+
* Using [Cargo](../cargo/index.html), the Rust package manager, automatically
29+
fixing this issue.
30+
* Recompiling either crate so that they target a consistent target triple.

compiler/rustc_error_messages/locales/en-US/parse.ftl

+3
Original file line numberDiff line numberDiff line change
@@ -365,3 +365,6 @@ parse_invalid_identifier_with_leading_number = expected identifier, found number
365365
366366
parse_maybe_fn_typo_with_impl = you might have meant to write `impl` instead of `fn`
367367
.suggestion = replace `fn` with `impl` here
368+
369+
parse_expected_fn_path_found_fn_keyword = expected identifier, found keyword `fn`
370+
.suggestion = use `Fn` to refer to the trait

compiler/rustc_expand/src/build.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -626,7 +626,7 @@ impl<'a> ExtCtxt<'a> {
626626

627627
// Builds `#[name = val]`.
628628
//
629-
// Note: `span` is used for both the identifer and the value.
629+
// Note: `span` is used for both the identifier and the value.
630630
pub fn attr_name_value_str(&self, name: Symbol, val: Symbol, span: Span) -> ast::Attribute {
631631
let g = &self.sess.parse_sess.attr_id_generator;
632632
attr::mk_attr_name_value_str(g, ast::AttrStyle::Outer, name, val, span)

compiler/rustc_hir_analysis/src/collect.rs

+60-1
Original file line numberDiff line numberDiff line change
@@ -24,14 +24,18 @@ use rustc_hir as hir;
2424
use rustc_hir::def_id::{DefId, LocalDefId};
2525
use rustc_hir::intravisit::{self, Visitor};
2626
use rustc_hir::{GenericParamKind, Node};
27+
use rustc_infer::infer::type_variable::{TypeVariableOrigin, TypeVariableOriginKind};
28+
use rustc_infer::infer::TyCtxtInferExt;
2729
use rustc_middle::hir::nested_filter;
2830
use rustc_middle::ty::query::Providers;
2931
use rustc_middle::ty::util::{Discr, IntTypeExt};
3032
use rustc_middle::ty::{self, AdtKind, Const, IsSuggestable, ToPredicate, Ty, TyCtxt};
3133
use rustc_span::symbol::{kw, sym, Ident, Symbol};
3234
use rustc_span::Span;
3335
use rustc_target::spec::abi;
36+
use rustc_trait_selection::infer::InferCtxtExt;
3437
use rustc_trait_selection::traits::error_reporting::suggestions::NextTypeParamName;
38+
use rustc_trait_selection::traits::ObligationCtxt;
3539
use std::iter;
3640

3741
mod generics_of;
@@ -1224,7 +1228,17 @@ fn infer_return_ty_for_fn_sig<'tcx>(
12241228
// to prevent the user from getting a papercut while trying to use the unique closure
12251229
// syntax (e.g. `[closure@src/lib.rs:2:5: 2:9]`).
12261230
diag.help("consider using an `Fn`, `FnMut`, or `FnOnce` trait bound");
1227-
diag.note("for more information on `Fn` traits and closure types, see https://doc.rust-lang.org/book/ch13-01-closures.html");
1231+
diag.note(
1232+
"for more information on `Fn` traits and closure types, see \
1233+
https://doc.rust-lang.org/book/ch13-01-closures.html",
1234+
);
1235+
} else if let Some(i_ty) = suggest_impl_iterator(tcx, ret_ty, ty.span, hir_id, def_id) {
1236+
diag.span_suggestion(
1237+
ty.span,
1238+
"replace with an appropriate return type",
1239+
format!("impl Iterator<Item = {}>", i_ty),
1240+
Applicability::MachineApplicable,
1241+
);
12281242
}
12291243
diag.emit();
12301244

@@ -1242,6 +1256,51 @@ fn infer_return_ty_for_fn_sig<'tcx>(
12421256
}
12431257
}
12441258

1259+
fn suggest_impl_iterator<'tcx>(
1260+
tcx: TyCtxt<'tcx>,
1261+
ret_ty: Ty<'tcx>,
1262+
span: Span,
1263+
hir_id: hir::HirId,
1264+
def_id: LocalDefId,
1265+
) -> Option<Ty<'tcx>> {
1266+
let Some(iter_trait) = tcx.get_diagnostic_item(sym::Iterator) else { return None; };
1267+
let Some(iterator_item) = tcx.get_diagnostic_item(sym::IteratorItem) else { return None; };
1268+
if !tcx
1269+
.infer_ctxt()
1270+
.build()
1271+
.type_implements_trait(iter_trait, [ret_ty], tcx.param_env(def_id))
1272+
.must_apply_modulo_regions()
1273+
{
1274+
return None;
1275+
}
1276+
let infcx = tcx.infer_ctxt().build();
1277+
let ocx = ObligationCtxt::new_in_snapshot(&infcx);
1278+
// Find the type of `Iterator::Item`.
1279+
let origin = TypeVariableOrigin { kind: TypeVariableOriginKind::TypeInference, span };
1280+
let ty_var = infcx.next_ty_var(origin);
1281+
let projection = ty::Binder::dummy(ty::PredicateKind::Clause(ty::Clause::Projection(
1282+
ty::ProjectionPredicate {
1283+
projection_ty: tcx.mk_alias_ty(iterator_item, tcx.mk_substs([ret_ty.into()].iter())),
1284+
term: ty_var.into(),
1285+
},
1286+
)));
1287+
// Add `<ret_ty as Iterator>::Item = _` obligation.
1288+
ocx.register_obligation(crate::traits::Obligation::misc(
1289+
tcx,
1290+
span,
1291+
hir_id,
1292+
tcx.param_env(def_id),
1293+
projection,
1294+
));
1295+
if ocx.select_where_possible().is_empty()
1296+
&& let item_ty = infcx.resolve_vars_if_possible(ty_var)
1297+
&& item_ty.is_suggestable(tcx, false)
1298+
{
1299+
return Some(item_ty);
1300+
}
1301+
None
1302+
}
1303+
12451304
fn impl_trait_ref(tcx: TyCtxt<'_>, def_id: DefId) -> Option<ty::TraitRef<'_>> {
12461305
let icx = ItemCtxt::new(tcx, def_id);
12471306
let item = tcx.hir().expect_item(def_id.expect_local());

compiler/rustc_hir_analysis/src/collect/type_of.rs

+7-6
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ use rustc_hir::intravisit;
55
use rustc_hir::intravisit::Visitor;
66
use rustc_hir::{HirId, Node};
77
use rustc_middle::hir::nested_filter;
8+
use rustc_middle::ty::print::with_forced_trimmed_paths;
89
use rustc_middle::ty::subst::InternalSubsts;
910
use rustc_middle::ty::util::IntTypeExt;
1011
use rustc_middle::ty::{self, DefIdTree, Ty, TyCtxt, TypeFolder, TypeSuperFoldable, TypeVisitable};
@@ -907,10 +908,10 @@ fn infer_placeholder_type<'a>(
907908
Applicability::MachineApplicable,
908909
);
909910
} else {
910-
err.span_note(
911+
with_forced_trimmed_paths!(err.span_note(
911912
tcx.hir().body(body_id).value.span,
912-
&format!("however, the inferred type `{}` cannot be named", ty),
913-
);
913+
&format!("however, the inferred type `{ty}` cannot be named"),
914+
));
914915
}
915916
}
916917

@@ -931,10 +932,10 @@ fn infer_placeholder_type<'a>(
931932
Applicability::MaybeIncorrect,
932933
);
933934
} else {
934-
diag.span_note(
935+
with_forced_trimmed_paths!(diag.span_note(
935936
tcx.hir().body(body_id).value.span,
936-
&format!("however, the inferred type `{}` cannot be named", ty),
937-
);
937+
&format!("however, the inferred type `{ty}` cannot be named"),
938+
));
938939
}
939940
}
940941

compiler/rustc_hir_typeck/src/callee.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -241,7 +241,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
241241
});
242242

243243
if let Some(ok) = self.lookup_method_in_trait(
244-
call_expr.span,
244+
self.misc(call_expr.span),
245245
method_name,
246246
trait_def_id,
247247
adjusted_ty,

compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs

+6-6
Original file line numberDiff line numberDiff line change
@@ -1307,7 +1307,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
13071307
// Type check the initializer.
13081308
if let Some(ref init) = decl.init {
13091309
let init_ty = self.check_decl_initializer(decl.hir_id, decl.pat, &init);
1310-
self.overwrite_local_ty_if_err(decl.hir_id, decl.pat, decl_ty, init_ty);
1310+
self.overwrite_local_ty_if_err(decl.hir_id, decl.pat, init_ty);
13111311
}
13121312

13131313
// Does the expected pattern type originate from an expression and what is the span?
@@ -1322,7 +1322,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
13221322
// Type check the pattern. Override if necessary to avoid knock-on errors.
13231323
self.check_pat_top(&decl.pat, decl_ty, ty_span, origin_expr);
13241324
let pat_ty = self.node_ty(decl.pat.hir_id);
1325-
self.overwrite_local_ty_if_err(decl.hir_id, decl.pat, decl_ty, pat_ty);
1325+
self.overwrite_local_ty_if_err(decl.hir_id, decl.pat, pat_ty);
13261326

13271327
if let Some(blk) = decl.els {
13281328
let previous_diverges = self.diverges.get();
@@ -1627,14 +1627,14 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
16271627
&self,
16281628
hir_id: hir::HirId,
16291629
pat: &'tcx hir::Pat<'tcx>,
1630-
decl_ty: Ty<'tcx>,
16311630
ty: Ty<'tcx>,
16321631
) {
16331632
if ty.references_error() {
16341633
// Override the types everywhere with `err()` to avoid knock on errors.
1635-
self.write_ty(hir_id, ty);
1636-
self.write_ty(pat.hir_id, ty);
1637-
let local_ty = LocalTy { decl_ty, revealed_ty: ty };
1634+
let err = self.tcx.ty_error();
1635+
self.write_ty(hir_id, err);
1636+
self.write_ty(pat.hir_id, err);
1637+
let local_ty = LocalTy { decl_ty: err, revealed_ty: err };
16381638
self.locals.borrow_mut().insert(hir_id, local_ty);
16391639
self.locals.borrow_mut().insert(pat.hir_id, local_ty);
16401640
}

0 commit comments

Comments
 (0)