Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

rustc_infer: remove InferCtxt::closure_sig as the FnSig is always shallowly known. #70089

Merged
merged 1 commit into from
Mar 21, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions src/librustc/ty/print/pretty.rs
Original file line number Diff line number Diff line change
Expand Up @@ -681,9 +681,9 @@ pub trait PrettyPrinter<'tcx>:

if self.tcx().sess.verbose() {
p!(write(
" closure_kind_ty={:?} closure_sig_ty={:?}",
" closure_kind_ty={:?} closure_sig_as_fn_ptr_ty={:?}",
substs.as_closure().kind_ty(did, self.tcx()),
substs.as_closure().sig_ty(did, self.tcx())
substs.as_closure().sig_as_fn_ptr_ty(did, self.tcx())
));
}

Expand Down
30 changes: 12 additions & 18 deletions src/librustc/ty/sty.rs
Original file line number Diff line number Diff line change
Expand Up @@ -371,7 +371,7 @@ pub struct ClosureSubsts<'tcx> {
/// parent slice and not canonical substs themselves.
struct SplitClosureSubsts<'tcx> {
closure_kind_ty: Ty<'tcx>,
closure_sig_ty: Ty<'tcx>,
closure_sig_as_fn_ptr_ty: Ty<'tcx>,
upvar_kinds: &'tcx [GenericArg<'tcx>],
}

Expand All @@ -384,7 +384,7 @@ impl<'tcx> ClosureSubsts<'tcx> {
let parent_len = generics.parent_count;
SplitClosureSubsts {
closure_kind_ty: self.substs.type_at(parent_len),
closure_sig_ty: self.substs.type_at(parent_len + 1),
closure_sig_as_fn_ptr_ty: self.substs.type_at(parent_len + 1),
upvar_kinds: &self.substs[parent_len + 2..],
}
}
Expand Down Expand Up @@ -412,12 +412,10 @@ impl<'tcx> ClosureSubsts<'tcx> {
self.split(def_id, tcx).closure_kind_ty
}

/// Returns the type representing the closure signature for this
/// closure; may contain type variables during inference. To get
/// the closure signature during inference, use
/// `infcx.fn_sig(def_id)`.
pub fn sig_ty(self, def_id: DefId, tcx: TyCtxt<'_>) -> Ty<'tcx> {
self.split(def_id, tcx).closure_sig_ty
/// Returns the `fn` pointer type representing the closure signature for this
/// closure.
pub fn sig_as_fn_ptr_ty(self, def_id: DefId, tcx: TyCtxt<'_>) -> Ty<'tcx> {
self.split(def_id, tcx).closure_sig_as_fn_ptr_ty
}

/// Returns the closure kind for this closure; only usable outside
Expand All @@ -429,16 +427,12 @@ impl<'tcx> ClosureSubsts<'tcx> {
self.split(def_id, tcx).closure_kind_ty.to_opt_closure_kind().unwrap()
}

/// Extracts the signature from the closure; only usable outside
/// of an inference context, because in that context we know that
/// there are no type variables.
///
/// If you have an inference context, use `infcx.closure_sig()`.
/// Extracts the signature from the closure.
pub fn sig(&self, def_id: DefId, tcx: TyCtxt<'tcx>) -> ty::PolyFnSig<'tcx> {
let ty = self.sig_ty(def_id, tcx);
let ty = self.sig_as_fn_ptr_ty(def_id, tcx);
match ty.kind {
ty::FnPtr(sig) => sig,
_ => bug!("closure_sig_ty is not a fn-ptr: {:?}", ty.kind),
_ => bug!("closure_sig_as_fn_ptr_ty is not a fn-ptr: {:?}", ty.kind),
}
}
}
Expand Down Expand Up @@ -2200,9 +2194,9 @@ impl<'tcx> TyS<'tcx> {
// ignore errors (#54954)
ty::Binder::dummy(FnSig::fake())
}
Closure(..) => {
bug!("to get the signature of a closure, use `closure_sig()` not `fn_sig()`",)
}
Closure(..) => bug!(
"to get the signature of a closure, use `substs.as_closure().sig()` not `fn_sig()`",
),
_ => bug!("Ty::fn_sig() called on non-fn type: {:?}", self),
}
}
Expand Down
10 changes: 0 additions & 10 deletions src/librustc_infer/infer/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1486,16 +1486,6 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
closure_kind_ty.to_opt_closure_kind()
}

/// Obtains the signature of a closure. For closures, unlike
/// `tcx.fn_sig(def_id)`, this method will work during the
/// type-checking of the enclosing function and return the closure
/// signature in its partially inferred state.
pub fn closure_sig(&self, def_id: DefId, substs: SubstsRef<'tcx>) -> ty::PolyFnSig<'tcx> {
let closure_sig_ty = substs.as_closure().sig_ty(def_id, self.tcx);
let closure_sig_ty = self.shallow_resolve(closure_sig_ty);
closure_sig_ty.fn_sig(self.tcx)
}

/// Clears the selection, evaluation, and projection caches. This is useful when
/// repeatedly attempting to select an `Obligation` while changing only
/// its `ParamEnv`, since `FulfillmentContext` doesn't use probing.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1684,7 +1684,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
// case it ends up being assigned into the return place.
annotated_closure = self.annotate_fn_sig(
*def_id,
self.infcx.closure_sig(*def_id, *substs),
substs.as_closure().sig(*def_id, self.infcx.tcx),
);
debug!(
"annotate_argument_and_return_for_borrow: \
Expand Down
4 changes: 1 addition & 3 deletions src/librustc_mir/borrow_check/type_check/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2083,9 +2083,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {

CastKind::Pointer(PointerCast::ClosureFnPointer(unsafety)) => {
let sig = match op.ty(*body, tcx).kind {
ty::Closure(def_id, substs) => {
substs.as_closure().sig_ty(def_id, tcx).fn_sig(tcx)
}
ty::Closure(def_id, substs) => substs.as_closure().sig(def_id, tcx),
_ => bug!(),
};
let ty_fn_ptr_from = tcx.coerce_closure_fn_ty(sig, *unsafety);
Expand Down
2 changes: 1 addition & 1 deletion src/librustc_mir/borrow_check/universal_regions.rs
Original file line number Diff line number Diff line change
Expand Up @@ -580,7 +580,7 @@ impl<'cx, 'tcx> UniversalRegionsBuilder<'cx, 'tcx> {
match defining_ty {
DefiningTy::Closure(def_id, substs) => {
assert_eq!(self.mir_def_id, def_id);
let closure_sig = substs.as_closure().sig_ty(def_id, tcx).fn_sig(tcx);
let closure_sig = substs.as_closure().sig(def_id, tcx);
let inputs_and_output = closure_sig.inputs_and_output();
let closure_ty = tcx.closure_env_ty(def_id, substs).unwrap();
ty::Binder::fuse(closure_ty, inputs_and_output, |closure_ty, inputs_and_output| {
Expand Down
2 changes: 1 addition & 1 deletion src/librustc_trait_selection/opaque_types.rs
Original file line number Diff line number Diff line change
Expand Up @@ -724,7 +724,7 @@ where
upvar_ty.visit_with(self);
}

substs.as_closure().sig_ty(def_id, self.tcx).visit_with(self);
substs.as_closure().sig_as_fn_ptr_ty(def_id, self.tcx).visit_with(self);
}

ty::Generator(def_id, ref substs, _) => {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -368,7 +368,7 @@ impl<'a, 'tcx> InferCtxtExt<'tcx> for InferCtxt<'a, 'tcx> {
let self_ty = trait_ref.self_ty();
let (def_id, output_ty, callable) = match self_ty.kind {
ty::Closure(def_id, substs) => {
(def_id, self.closure_sig(def_id, substs).output(), "closure")
(def_id, substs.as_closure().sig(def_id, self.tcx).output(), "closure")
}
ty::FnDef(def_id, _) => (def_id, self_ty.fn_sig(self.tcx).output(), "function"),
_ => return,
Expand Down
4 changes: 1 addition & 3 deletions src/librustc_trait_selection/traits/project.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1311,9 +1311,7 @@ fn confirm_closure_candidate<'cx, 'tcx>(
vtable: VtableClosureData<'tcx, PredicateObligation<'tcx>>,
) -> Progress<'tcx> {
let tcx = selcx.tcx();
let infcx = selcx.infcx();
let closure_sig_ty = vtable.substs.as_closure().sig_ty(vtable.closure_def_id, tcx);
let closure_sig = infcx.shallow_resolve(closure_sig_ty).fn_sig(tcx);
let closure_sig = vtable.substs.as_closure().sig(vtable.closure_def_id, tcx);
let Normalized { value: closure_sig, obligations } = normalize_with_depth(
selcx,
obligation.param_env,
Expand Down
6 changes: 3 additions & 3 deletions src/librustc_trait_selection/traits/select.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3349,9 +3349,9 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
"closure_trait_ref_unnormalized(obligation={:?}, closure_def_id={:?}, substs={:?})",
obligation, closure_def_id, substs,
);
let closure_type = self.infcx.closure_sig(closure_def_id, substs);
let closure_sig = substs.as_closure().sig(closure_def_id, self.tcx());

debug!("closure_trait_ref_unnormalized: closure_type = {:?}", closure_type);
debug!("closure_trait_ref_unnormalized: closure_sig = {:?}", closure_sig);

// (1) Feels icky to skip the binder here, but OTOH we know
// that the self-type is an unboxed closure type and hence is
Expand All @@ -3362,7 +3362,7 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
self.tcx(),
obligation.predicate.def_id(),
obligation.predicate.skip_binder().self_ty(), // (1)
closure_type,
closure_sig,
util::TupleArgumentsFlag::No,
)
.map_bound(|(trait_ref, _)| trait_ref)
Expand Down
10 changes: 5 additions & 5 deletions src/librustc_typeck/check/callee.rs
Original file line number Diff line number Diff line change
Expand Up @@ -105,12 +105,12 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
// haven't yet decided on whether the closure is fn vs
// fnmut vs fnonce. If so, we have to defer further processing.
if self.closure_kind(def_id, substs).is_none() {
let closure_ty = self.closure_sig(def_id, substs);
let fn_sig = self
let closure_sig = substs.as_closure().sig(def_id, self.tcx);
let closure_sig = self
.replace_bound_vars_with_fresh_vars(
call_expr.span,
infer::FnCall,
&closure_ty,
&closure_sig,
)
.0;
let adjustments = autoderef.adjust_steps(self, Needs::None);
Expand All @@ -121,12 +121,12 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
callee_expr,
adjusted_ty,
adjustments,
fn_sig,
fn_sig: closure_sig,
closure_def_id: def_id,
closure_substs: substs,
},
);
return Some(CallStep::DeferredClosure(fn_sig));
return Some(CallStep::DeferredClosure(closure_sig));
}
}

Expand Down
19 changes: 14 additions & 5 deletions src/librustc_typeck/check/closure.rs
Original file line number Diff line number Diff line change
Expand Up @@ -116,12 +116,13 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
interior,
generator_substs.witness(expr_def_id, self.tcx),
);
return self.tcx.mk_generator(expr_def_id, substs, movability);
}

let closure_type = self.tcx.mk_closure(expr_def_id, substs);
// HACK(eddyb) this forces the types equated above into `substs` but
// it should rely on `GeneratorSubsts` providing a constructor, instead.
let substs = self.resolve_vars_if_possible(&substs);

debug!("check_closure: expr.hir_id={:?} closure_type={:?}", expr.hir_id, closure_type);
return self.tcx.mk_generator(expr_def_id, substs, movability);
}

// Tuple up the arguments and insert the resulting function type into
// the `closures` table.
Expand All @@ -144,7 +145,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
self.demand_eqtype(
expr.span,
sig_fn_ptr_ty,
substs.as_closure().sig_ty(expr_def_id, self.tcx),
substs.as_closure().sig_as_fn_ptr_ty(expr_def_id, self.tcx),
);

if let Some(kind) = opt_kind {
Expand All @@ -155,6 +156,14 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
);
}

// HACK(eddyb) this forces the types equated above into `substs` but
// it should rely on `ClosureSubsts` providing a constructor, instead.
let substs = self.resolve_vars_if_possible(&substs);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

the purpose of this code is to ensure that have a fn type, and not an inference variable that's been equated with a fn type?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yupp, pretty much.


let closure_type = self.tcx.mk_closure(expr_def_id, substs);

debug!("check_closure: expr.hir_id={:?} closure_type={:?}", expr.hir_id, closure_type);

closure_type
}

Expand Down
4 changes: 2 additions & 2 deletions src/librustc_typeck/check/coercion.rs
Original file line number Diff line number Diff line change
Expand Up @@ -749,9 +749,9 @@ impl<'f, 'tcx> Coerce<'f, 'tcx> {
// `fn(arg0,arg1,...) -> _`
// or
// `unsafe fn(arg0,arg1,...) -> _`
let sig = self.closure_sig(def_id_a, substs_a);
let closure_sig = substs_a.as_closure().sig(def_id_a, self.tcx);
let unsafety = fn_ty.unsafety();
let pointer_ty = self.tcx.coerce_closure_fn_ty(sig, unsafety);
let pointer_ty = self.tcx.coerce_closure_fn_ty(closure_sig, unsafety);
debug!("coerce_closure_to_fn(a={:?}, b={:?}, pty={:?})", a, b, pointer_ty);
self.unify_and(
pointer_ty,
Expand Down
13 changes: 1 addition & 12 deletions src/librustc_typeck/check/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4839,18 +4839,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
let hir = self.tcx.hir();
let (def_id, sig) = match found.kind {
ty::FnDef(def_id, _) => (def_id, found.fn_sig(self.tcx)),
ty::Closure(def_id, substs) => {
// We don't use `closure_sig` to account for malformed closures like
// `|_: [_; continue]| {}` and instead we don't suggest anything.
let closure_sig_ty = substs.as_closure().sig_ty(def_id, self.tcx);
(
def_id,
match closure_sig_ty.kind {
ty::FnPtr(sig) => sig,
_ => return false,
},
)
}
ty::Closure(def_id, substs) => (def_id, substs.as_closure().sig(def_id, self.tcx)),
_ => return false,
};

Expand Down
15 changes: 6 additions & 9 deletions src/librustc_typeck/collect.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1527,16 +1527,13 @@ fn fn_sig(tcx: TyCtxt<'_>, def_id: DefId) -> ty::PolyFnSig<'_> {
// argument. In any case they are embedded within the
// closure type as part of the `ClosureSubsts`.
//
// To get
// the signature of a closure, you should use the
// `closure_sig` method on the `ClosureSubsts`:
// To get the signature of a closure, you should use the
// `sig` method on the `ClosureSubsts`:
//
// closure_substs.sig(def_id, tcx)
//
// or, inside of an inference context, you can use
//
// infcx.closure_sig(def_id, closure_substs)
bug!("to get the signature of a closure, use `closure_sig()` not `fn_sig()`");
// substs.as_closure().sig(def_id, tcx)
bug!(
"to get the signature of a closure, use `substs.as_closure().sig()` not `fn_sig()`",
);
}

x => {
Expand Down