X-Git-Url: https://git.lizzy.rs/?a=blobdiff_plain;f=compiler%2Frustc_hir_typeck%2Fsrc%2Fcallee.rs;h=b09ddf80e2a52577292e3d602fca7e3cff198dc2;hb=552b63c1619498f1a17fd482f4bb87815d8fdc48;hp=1c14c1d35f7997ef026f08ed22134a100f6ae75f;hpb=5c2592cd4324973b48011a8a93908612bec9cebf;p=rust.git diff --git a/compiler/rustc_hir_typeck/src/callee.rs b/compiler/rustc_hir_typeck/src/callee.rs index 1c14c1d35f7..b09ddf80e2a 100644 --- a/compiler/rustc_hir_typeck/src/callee.rs +++ b/compiler/rustc_hir_typeck/src/callee.rs @@ -179,12 +179,16 @@ fn try_overloaded_call_step( // Hack: we know that there are traits implementing Fn for &F // where F:Fn and so forth. In the particular case of types - // like `x: &mut FnMut()`, if there is a call `x()`, we would - // normally translate to `FnMut::call_mut(&mut x, ())`, but - // that winds up requiring `mut x: &mut FnMut()`. A little - // over the top. The simplest fix by far is to just ignore - // this case and deref again, so we wind up with - // `FnMut::call_mut(&mut *x, ())`. + // like `f: &mut FnMut()`, if there is a call `f()`, we would + // normally translate to `FnMut::call_mut(&mut f, ())`, but + // that winds up potentially requiring the user to mark their + // variable as `mut` which feels unnecessary and unexpected. + // + // fn foo(f: &mut impl FnMut()) { f() } + // ^ without this hack `f` would have to be declared as mutable + // + // The simplest fix by far is to just ignore this case and deref again, + // so we wind up with `FnMut::call_mut(&mut *f, ())`. ty::Ref(..) if autoderef.step_count() == 0 => { return None; } @@ -444,7 +448,7 @@ fn confirm_builtin_call( // previously appeared within a `Binder<>` and hence would not // have been normalized before. let fn_sig = self.replace_bound_vars_with_fresh_vars(call_expr.span, infer::FnCall, fn_sig); - let fn_sig = self.normalize_associated_types_in(call_expr.span, fn_sig); + let fn_sig = self.normalize(call_expr.span, fn_sig); // Call the generic checker. let expected_arg_tys = self.expected_inputs_for_expected_output(