Skip to content

Commit 2454a68

Browse files
committed
Auto merge of rust-lang#71879 - Dylan-DPC:rollup-n05awny, r=Dylan-DPC
Rollup of 5 pull requests Successful merges: - rust-lang#71038 (forbid `dyn Trait` in patterns) - rust-lang#71697 (Added MIR constant propagation of Scalars into function call arguments) - rust-lang#71773 (doc: misc rustdoc things) - rust-lang#71810 (Do not try to find binop method on RHS `TyErr`) - rust-lang#71877 (Use f64 in f64 examples) Failed merges: r? @ghost
2 parents 649b632 + fc2837b commit 2454a68

File tree

15 files changed

+185
-31
lines changed

15 files changed

+185
-31
lines changed

src/libcore/num/f64.rs

+2-2
Original file line numberDiff line numberDiff line change
@@ -474,11 +474,11 @@ impl f64 {
474474
/// assuming that the value is finite and fits in that type.
475475
///
476476
/// ```
477-
/// let value = 4.6_f32;
477+
/// let value = 4.6_f64;
478478
/// let rounded = unsafe { value.to_int_unchecked::<u16>() };
479479
/// assert_eq!(rounded, 4);
480480
///
481-
/// let value = -128.9_f32;
481+
/// let value = -128.9_f64;
482482
/// let rounded = unsafe { value.to_int_unchecked::<i8>() };
483483
/// assert_eq!(rounded, i8::MIN);
484484
/// ```

src/librustc_builtin_macros/test_harness.rs

+2-2
Original file line numberDiff line numberDiff line change
@@ -255,8 +255,8 @@ fn generate_test_harness(
255255
///
256256
/// The expansion here can be controlled by two attributes:
257257
///
258-
/// `reexport_test_harness_main` provides a different name for the `main`
259-
/// function and `test_runner` provides a path that replaces
258+
/// [`TestCtxt::reexport_test_harness_main`] provides a different name for the `main`
259+
/// function and [`TestCtxt::test_runner`] provides a path that replaces
260260
/// `test::test_main_static`.
261261
fn mk_main(cx: &mut TestCtxt<'_>) -> P<ast::Item> {
262262
let sp = cx.def_site;

src/librustc_lint/lib.rs

+3-3
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,9 @@
66
//! other phases of the compiler, which are generally required to hold in order
77
//! to compile the program at all.
88
//!
9-
//! Most lints can be written as `LintPass` instances. These run after
9+
//! Most lints can be written as [LintPass] instances. These run after
1010
//! all other analyses. The `LintPass`es built into rustc are defined
11-
//! within `rustc_session::lint::builtin`,
11+
//! within [rustc_session::lint::builtin],
1212
//! which has further comments on how to add such a lint.
1313
//! rustc can also load user-defined lint plugins via the plugin mechanism.
1414
//!
@@ -19,7 +19,7 @@
1919
//! example) requires more effort. See `emit_lint` and `GatherNodeLevels`
2020
//! in `context.rs`.
2121
//!
22-
//! Some code also exists in `rustc_session::lint`, `rustc_middle::lint`.
22+
//! Some code also exists in [rustc_session::lint], [rustc_middle::lint].
2323
//!
2424
//! ## Note
2525
//!

src/librustc_mir/transform/const_prop.rs

+51-5
Original file line numberDiff line numberDiff line change
@@ -787,6 +787,7 @@ impl<'tcx> Visitor<'tcx> for CanConstProp {
787787
| NonMutatingUse(NonMutatingUseContext::Inspect)
788788
| NonMutatingUse(NonMutatingUseContext::Projection)
789789
| NonUse(_) => {}
790+
// FIXME(felix91gr): explain the reasoning behind this
790791
MutatingUse(MutatingUseContext::Projection) => {
791792
if self.local_kinds[local] != LocalKind::Temp {
792793
self.can_const_prop[local] = ConstPropMode::NoPropagation;
@@ -969,13 +970,58 @@ impl<'mir, 'tcx> MutVisitor<'tcx> for ConstPropagator<'mir, 'tcx> {
969970
| TerminatorKind::GeneratorDrop
970971
| TerminatorKind::FalseEdges { .. }
971972
| TerminatorKind::FalseUnwind { .. } => {}
972-
//FIXME(wesleywiser) Call does have Operands that could be const-propagated
973-
TerminatorKind::Call { .. } => {}
973+
// Every argument in our function calls can be const propagated.
974+
TerminatorKind::Call { ref mut args, .. } => {
975+
let mir_opt_level = self.tcx.sess.opts.debugging_opts.mir_opt_level;
976+
// Constant Propagation into function call arguments is gated
977+
// under mir-opt-level 2, because LLVM codegen gives performance
978+
// regressions with it.
979+
if mir_opt_level >= 2 {
980+
for opr in args {
981+
/*
982+
The following code would appear to be incomplete, because
983+
the function `Operand::place()` returns `None` if the
984+
`Operand` is of the variant `Operand::Constant`. In this
985+
context however, that variant will never appear. This is why:
986+
987+
When constructing the MIR, all function call arguments are
988+
copied into `Locals` of `LocalKind::Temp`. At least, all arguments
989+
that are not unsized (Less than 0.1% are unsized. See #71170
990+
to learn more about those).
991+
992+
This means that, conversely, all `Operands` found as function call
993+
arguments are of the variant `Operand::Copy`. This allows us to
994+
simplify our handling of `Operands` in this case.
995+
*/
996+
if let Some(l) = opr.place().and_then(|p| p.as_local()) {
997+
if let Some(value) = self.get_const(l) {
998+
if self.should_const_prop(value) {
999+
// FIXME(felix91gr): this code only handles `Scalar` cases.
1000+
// For now, we're not handling `ScalarPair` cases because
1001+
// doing so here would require a lot of code duplication.
1002+
// We should hopefully generalize `Operand` handling into a fn,
1003+
// and use it to do const-prop here and everywhere else
1004+
// where it makes sense.
1005+
if let interpret::Operand::Immediate(
1006+
interpret::Immediate::Scalar(
1007+
interpret::ScalarMaybeUndef::Scalar(scalar),
1008+
),
1009+
) = *value
1010+
{
1011+
*opr = self.operand_from_scalar(
1012+
scalar,
1013+
value.layout.ty,
1014+
source_info.span,
1015+
);
1016+
}
1017+
}
1018+
}
1019+
}
1020+
}
1021+
}
1022+
}
9741023
}
9751024
// We remove all Locals which are restricted in propagation to their containing blocks.
976-
// We wouldn't need to clone, but the borrow checker can't see that we're not aliasing
977-
// the locals_of_current_block field, so we need to clone it first.
978-
// let ecx = &mut self.ecx;
9791025
for local in self.locals_of_current_block.iter() {
9801026
Self::remove_const(&mut self.ecx, local);
9811027
}

src/librustc_mir_build/hair/pattern/const_to_pat.rs

+14-13
Original file line numberDiff line numberDiff line change
@@ -111,21 +111,22 @@ impl<'a, 'tcx> ConstToPat<'a, 'tcx> {
111111
}
112112

113113
if let Some(non_sm_ty) = structural {
114-
let adt_def = match non_sm_ty {
115-
traits::NonStructuralMatchTy::Adt(adt_def) => adt_def,
114+
let msg = match non_sm_ty {
115+
traits::NonStructuralMatchTy::Adt(adt_def) => {
116+
let path = self.tcx().def_path_str(adt_def.did);
117+
format!(
118+
"to use a constant of type `{}` in a pattern, \
119+
`{}` must be annotated with `#[derive(PartialEq, Eq)]`",
120+
path, path,
121+
)
122+
}
123+
traits::NonStructuralMatchTy::Dynamic => {
124+
format!("trait objects cannot be used in patterns")
125+
}
116126
traits::NonStructuralMatchTy::Param => {
117127
bug!("use of constant whose type is a parameter inside a pattern")
118128
}
119129
};
120-
let path = self.tcx().def_path_str(adt_def.did);
121-
122-
let make_msg = || -> String {
123-
format!(
124-
"to use a constant of type `{}` in a pattern, \
125-
`{}` must be annotated with `#[derive(PartialEq, Eq)]`",
126-
path, path,
127-
)
128-
};
129130

130131
// double-check there even *is* a semantic `PartialEq` to dispatch to.
131132
//
@@ -155,13 +156,13 @@ impl<'a, 'tcx> ConstToPat<'a, 'tcx> {
155156

156157
if !ty_is_partial_eq {
157158
// span_fatal avoids ICE from resolution of non-existent method (rare case).
158-
self.tcx().sess.span_fatal(self.span, &make_msg());
159+
self.tcx().sess.span_fatal(self.span, &msg);
159160
} else if mir_structural_match_violation {
160161
self.tcx().struct_span_lint_hir(
161162
lint::builtin::INDIRECT_STRUCTURAL_MATCH,
162163
self.id,
163164
self.span,
164-
|lint| lint.build(&make_msg()).emit(),
165+
|lint| lint.build(&msg).emit(),
165166
);
166167
} else {
167168
debug!(

src/librustc_trait_selection/traits/structural_match.rs

+5
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ use rustc_span::Span;
1111
pub enum NonStructuralMatchTy<'tcx> {
1212
Adt(&'tcx AdtDef),
1313
Param,
14+
Dynamic,
1415
}
1516

1617
/// This method traverses the structure of `ty`, trying to find an
@@ -137,6 +138,10 @@ impl<'a, 'tcx> TypeVisitor<'tcx> for Search<'a, 'tcx> {
137138
self.found = Some(NonStructuralMatchTy::Param);
138139
return true; // Stop visiting.
139140
}
141+
ty::Dynamic(..) => {
142+
self.found = Some(NonStructuralMatchTy::Dynamic);
143+
return true; // Stop visiting.
144+
}
140145
ty::RawPtr(..) => {
141146
// structural-match ignores substructure of
142147
// `*const _`/`*mut _`, so skip `super_visit_with`.

src/librustc_typeck/check/op.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -251,7 +251,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
251251
}
252252
Err(()) => {
253253
// error types are considered "builtin"
254-
if !lhs_ty.references_error() {
254+
if !lhs_ty.references_error() && !rhs_ty.references_error() {
255255
let source_map = self.tcx.sess.source_map();
256256
match is_assign {
257257
IsAssign::Yes => {

src/test/mir-opt/const_prop/scalar_literal_propagation/rustc.main.ConstProp.diff

+10-3
Original file line numberDiff line numberDiff line change
@@ -22,20 +22,27 @@
2222
StorageLive(_2); // scope 1 at $DIR/scalar_literal_propagation.rs:4:5: 4:15
2323
StorageLive(_3); // scope 1 at $DIR/scalar_literal_propagation.rs:4:13: 4:14
2424
- _3 = _1; // scope 1 at $DIR/scalar_literal_propagation.rs:4:13: 4:14
25+
- _2 = const consume(move _3) -> bb1; // scope 1 at $DIR/scalar_literal_propagation.rs:4:5: 4:15
2526
+ _3 = const 1u32; // scope 1 at $DIR/scalar_literal_propagation.rs:4:13: 4:14
26-
+ // ty::Const
27+
// ty::Const
2728
+ // + ty: u32
2829
+ // + val: Value(Scalar(0x00000001))
2930
+ // mir::Constant
3031
+ // + span: $DIR/scalar_literal_propagation.rs:4:13: 4:14
3132
+ // + literal: Const { ty: u32, val: Value(Scalar(0x00000001)) }
32-
_2 = const consume(move _3) -> bb1; // scope 1 at $DIR/scalar_literal_propagation.rs:4:5: 4:15
33-
// ty::Const
33+
+ _2 = const consume(const 1u32) -> bb1; // scope 1 at $DIR/scalar_literal_propagation.rs:4:5: 4:15
34+
+ // ty::Const
3435
// + ty: fn(u32) {consume}
3536
// + val: Value(Scalar(<ZST>))
3637
// mir::Constant
3738
// + span: $DIR/scalar_literal_propagation.rs:4:5: 4:12
3839
// + literal: Const { ty: fn(u32) {consume}, val: Value(Scalar(<ZST>)) }
40+
+ // ty::Const
41+
+ // + ty: u32
42+
+ // + val: Value(Scalar(0x00000001))
43+
+ // mir::Constant
44+
+ // + span: $DIR/scalar_literal_propagation.rs:4:5: 4:15
45+
+ // + literal: Const { ty: u32, val: Value(Scalar(0x00000001)) }
3946
}
4047

4148
bb1: {

src/test/mir-opt/simplify-locals-removes-unused-consts/rustc.main.SimplifyLocals.diff

+20-2
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,7 @@
5050
- StorageDead(_2); // scope 0 at $DIR/simplify-locals-removes-unused-consts.rs:13:27: 13:28
5151
- StorageDead(_1); // scope 0 at $DIR/simplify-locals-removes-unused-consts.rs:13:28: 13:29
5252
- StorageLive(_4); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:14:5: 14:22
53+
- StorageLive(_5); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:14:13: 14:21
5354
- StorageLive(_6); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:14:14: 14:16
5455
- _6 = const (); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:14:14: 14:16
5556
- // ty::Const
@@ -66,6 +67,13 @@
6667
- // mir::Constant
6768
- // + span: $DIR/simplify-locals-removes-unused-consts.rs:14:18: 14:20
6869
- // + literal: Const { ty: (), val: Value(Scalar(<ZST>)) }
70+
- _5 = const ((), ()); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:14:13: 14:21
71+
- // ty::Const
72+
- // + ty: ((), ())
73+
- // + val: Value(Scalar(<ZST>))
74+
- // mir::Constant
75+
- // + span: $DIR/simplify-locals-removes-unused-consts.rs:14:13: 14:21
76+
- // + literal: Const { ty: ((), ()), val: Value(Scalar(<ZST>)) }
6977
- StorageDead(_7); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:14:20: 14:21
7078
- StorageDead(_6); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:14:20: 14:21
7179
- _4 = const use_zst(const ((), ())) -> bb1; // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:14:5: 14:22
@@ -79,13 +87,15 @@
7987
// + ty: ((), ())
8088
// + val: Value(Scalar(<ZST>))
8189
// mir::Constant
82-
// + span: $DIR/simplify-locals-removes-unused-consts.rs:14:13: 14:21
90+
// + span: $DIR/simplify-locals-removes-unused-consts.rs:14:5: 14:22
8391
// + literal: Const { ty: ((), ()), val: Value(Scalar(<ZST>)) }
8492
}
8593

8694
bb1: {
95+
- StorageDead(_5); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:14:21: 14:22
8796
- StorageDead(_4); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:14:22: 14:23
8897
- StorageLive(_8); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:16:5: 16:35
98+
- StorageLive(_9); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:16:12: 16:34
8999
- StorageLive(_10); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:16:12: 16:30
90100
- StorageLive(_11); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:16:12: 16:28
91101
- _11 = const Temp { x: 40u8 }; // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:16:12: 16:28
@@ -105,6 +115,13 @@
105115
- // mir::Constant
106116
- // + span: $DIR/simplify-locals-removes-unused-consts.rs:16:12: 16:30
107117
- // + literal: Const { ty: u8, val: Value(Scalar(0x28)) }
118+
- _9 = const 42u8; // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:16:12: 16:34
119+
- // ty::Const
120+
- // + ty: u8
121+
- // + val: Value(Scalar(0x2a))
122+
- // mir::Constant
123+
- // + span: $DIR/simplify-locals-removes-unused-consts.rs:16:12: 16:34
124+
- // + literal: Const { ty: u8, val: Value(Scalar(0x2a)) }
108125
- StorageDead(_10); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:16:33: 16:34
109126
- _8 = const use_u8(const 42u8) -> bb2; // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:16:5: 16:35
110127
- // ty::Const
@@ -117,11 +134,12 @@
117134
// + ty: u8
118135
// + val: Value(Scalar(0x2a))
119136
// mir::Constant
120-
// + span: $DIR/simplify-locals-removes-unused-consts.rs:16:12: 16:34
137+
// + span: $DIR/simplify-locals-removes-unused-consts.rs:16:5: 16:35
121138
// + literal: Const { ty: u8, val: Value(Scalar(0x2a)) }
122139
}
123140

124141
bb2: {
142+
- StorageDead(_9); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:16:34: 16:35
125143
- StorageDead(_11); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:16:35: 16:36
126144
- StorageDead(_8); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:16:35: 16:36
127145
+ StorageDead(_2); // scope 1 at $DIR/simplify-locals-removes-unused-consts.rs:16:35: 16:36
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
#![feature(const_generics)]
2+
//~^ WARN the feature `const_generics` is incomplete and may cause the compiler to crash
3+
4+
trait A {}
5+
struct B;
6+
impl A for B {}
7+
8+
fn test<const T: &'static dyn A>() {
9+
//~^ ERROR must be annotated with `#[derive(PartialEq, Eq)]` to be used
10+
unimplemented!()
11+
}
12+
13+
fn main() {
14+
test::<{ &B }>();
15+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
warning: the feature `const_generics` is incomplete and may cause the compiler to crash
2+
--> $DIR/issue-63322-forbid-dyn.rs:1:12
3+
|
4+
LL | #![feature(const_generics)]
5+
| ^^^^^^^^^^^^^^
6+
|
7+
= note: `#[warn(incomplete_features)]` on by default
8+
9+
error[E0741]: `&'static (dyn A + 'static)` must be annotated with `#[derive(PartialEq, Eq)]` to be used as the type of a const parameter
10+
--> $DIR/issue-63322-forbid-dyn.rs:8:18
11+
|
12+
LL | fn test<const T: &'static dyn A>() {
13+
| ^^^^^^^^^^^^^^ `&'static (dyn A + 'static)` doesn't derive both `PartialEq` and `Eq`
14+
15+
error: aborting due to previous error; 1 warning emitted
16+
17+
For more information about this error, try `rustc --explain E0741`.

src/test/ui/issues-71798.rs

+7
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
fn test_ref(x: &u32) -> impl std::future::Future<Output = u32> + '_ {
2+
*x //~^ ERROR the trait bound `u32: std::future::Future` is not satisfied
3+
}
4+
5+
fn main() {
6+
let _ = test_ref & u; //~ ERROR cannot find value `u` in this scope
7+
}

src/test/ui/issues-71798.stderr

+20
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
error[E0425]: cannot find value `u` in this scope
2+
--> $DIR/issues-71798.rs:6:24
3+
|
4+
LL | let _ = test_ref & u;
5+
| ^ not found in this scope
6+
7+
error[E0277]: the trait bound `u32: std::future::Future` is not satisfied
8+
--> $DIR/issues-71798.rs:1:25
9+
|
10+
LL | fn test_ref(x: &u32) -> impl std::future::Future<Output = u32> + '_ {
11+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `std::future::Future` is not implemented for `u32`
12+
LL | *x
13+
| -- this returned value is of type `u32`
14+
|
15+
= note: the return type of a function must have a statically known size
16+
17+
error: aborting due to 2 previous errors
18+
19+
Some errors have detailed explanations: E0277, E0425.
20+
For more information about an error, try `rustc --explain E0277`.
+10
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
const F: &'static dyn Send = &7u32;
2+
3+
fn main() {
4+
let a: &dyn Send = &7u32;
5+
match a {
6+
F => panic!(),
7+
//~^ ERROR trait objects cannot be used in patterns
8+
_ => {}
9+
}
10+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
error: trait objects cannot be used in patterns
2+
--> $DIR/issue-70972-dyn-trait.rs:6:9
3+
|
4+
LL | F => panic!(),
5+
| ^
6+
7+
error: aborting due to previous error
8+

0 commit comments

Comments
 (0)