Rollup merge of #98705 - WaffleLapkin:closure_binder, r=cjgillot
Implement `for<>` lifetime binder for closures This PR implements RFC 3216 ([TI](https://github.com/rust-lang/rust/issues/97362)) and allows code like the following: ```rust let _f = for<'a, 'b> |a: &'a A, b: &'b B| -> &'b C { b.c(a) }; // ^^^^^^^^^^^--- new! ``` cc ``@Aaron1011`` ``@cjgillot``
This commit is contained in:
commit
e5a86d7358
91 changed files with 843 additions and 208 deletions
|
@ -6,6 +6,7 @@ use rustc_ast_pretty::pp::Breaks::{Consistent, Inconsistent};
|
|||
use rustc_ast_pretty::pp::{self, Breaks};
|
||||
use rustc_ast_pretty::pprust::{Comments, PrintState};
|
||||
use rustc_hir as hir;
|
||||
use rustc_hir::LifetimeParamKind;
|
||||
use rustc_hir::{GenericArg, GenericParam, GenericParamKind, Node, Term};
|
||||
use rustc_hir::{GenericBound, PatKind, RangeEnd, TraitBoundModifier};
|
||||
use rustc_span::source_map::SourceMap;
|
||||
|
@ -1452,15 +1453,16 @@ impl<'a> State<'a> {
|
|||
}
|
||||
self.bclose(expr.span);
|
||||
}
|
||||
hir::ExprKind::Closure {
|
||||
hir::ExprKind::Closure(&hir::Closure {
|
||||
binder,
|
||||
capture_clause,
|
||||
bound_generic_params,
|
||||
fn_decl,
|
||||
body,
|
||||
fn_decl_span: _,
|
||||
movability: _,
|
||||
} => {
|
||||
self.print_formal_generic_params(bound_generic_params);
|
||||
}) => {
|
||||
self.print_closure_binder(binder, bound_generic_params);
|
||||
self.print_capture_clause(capture_clause);
|
||||
|
||||
self.print_closure_params(fn_decl, body);
|
||||
|
@ -2045,6 +2047,42 @@ impl<'a> State<'a> {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn print_closure_binder(
|
||||
&mut self,
|
||||
binder: hir::ClosureBinder,
|
||||
generic_params: &[GenericParam<'_>],
|
||||
) {
|
||||
let generic_params = generic_params
|
||||
.iter()
|
||||
.filter(|p| {
|
||||
matches!(
|
||||
p,
|
||||
GenericParam {
|
||||
kind: GenericParamKind::Lifetime { kind: LifetimeParamKind::Explicit },
|
||||
..
|
||||
}
|
||||
)
|
||||
})
|
||||
.collect::<Vec<_>>();
|
||||
|
||||
match binder {
|
||||
hir::ClosureBinder::Default => {}
|
||||
// we need to distinguish `|...| {}` from `for<> |...| {}` as `for<>` adds additional restrictions
|
||||
hir::ClosureBinder::For { .. } if generic_params.is_empty() => self.word("for<>"),
|
||||
hir::ClosureBinder::For { .. } => {
|
||||
self.word("for");
|
||||
self.word("<");
|
||||
|
||||
self.commasep(Inconsistent, &generic_params, |s, param| {
|
||||
s.print_generic_param(param)
|
||||
});
|
||||
|
||||
self.word(">");
|
||||
self.nbsp();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn print_bounds<'b>(
|
||||
&mut self,
|
||||
prefix: &'static str,
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue