Skip to content

Commit 52a5abd

Browse files
committed
Add not-null pointer patterns to pattern types
1 parent f6092f2 commit 52a5abd

File tree

28 files changed

+289
-22
lines changed

28 files changed

+289
-22
lines changed

compiler/rustc_ast/src/ast.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2580,6 +2580,9 @@ pub enum TyPatKind {
25802580
/// A range pattern (e.g., `1...2`, `1..2`, `1..`, `..2`, `1..=2`, `..=2`).
25812581
Range(Option<Box<AnonConst>>, Option<Box<AnonConst>>, Spanned<RangeEnd>),
25822582

2583+
/// A `!null` pattern for raw pointers.
2584+
NotNull,
2585+
25832586
Or(ThinVec<Box<TyPat>>),
25842587

25852588
/// Placeholder for a pattern that wasn't syntactically well formed in some way.

compiler/rustc_ast_lowering/src/pat.rs

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -143,7 +143,9 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
143143
}
144144
// return inner to be processed in next loop
145145
PatKind::Paren(inner) => pattern = inner,
146-
PatKind::MacCall(_) => panic!("{:?} shouldn't exist here", pattern.span),
146+
PatKind::MacCall(_) => {
147+
panic!("{pattern:#?} shouldn't exist here")
148+
}
147149
PatKind::Err(guar) => break hir::PatKind::Err(*guar),
148150
}
149151
};
@@ -460,6 +462,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
460462
)
461463
}),
462464
),
465+
TyPatKind::NotNull => hir::TyPatKind::NotNull,
463466
TyPatKind::Or(variants) => {
464467
hir::TyPatKind::Or(self.arena.alloc_from_iter(
465468
variants.iter().map(|pat| self.lower_ty_pat_mut(pat, base_type)),

compiler/rustc_ast_pretty/src/pprust/state.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1232,6 +1232,7 @@ impl<'a> State<'a> {
12321232
self.print_expr_anon_const(end, &[]);
12331233
}
12341234
}
1235+
rustc_ast::TyPatKind::NotNull => self.word("!null"),
12351236
rustc_ast::TyPatKind::Or(variants) => {
12361237
let mut first = true;
12371238
for pat in variants {

compiler/rustc_builtin_macros/src/pattern_type.rs

Lines changed: 15 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -30,15 +30,21 @@ fn parse_pat_ty<'a>(
3030
let ty = parser.parse_ty()?;
3131
parser.expect_keyword(exp!(Is))?;
3232

33-
let pat = pat_to_ty_pat(
34-
cx,
35-
*parser.parse_pat_no_top_guard(
36-
None,
37-
RecoverComma::No,
38-
RecoverColon::No,
39-
CommaRecoveryMode::EitherTupleOrPipe,
40-
)?,
41-
);
33+
let start = parser.token.span;
34+
let pat = if parser.eat(exp!(Bang)) {
35+
parser.expect_keyword(exp!(Null))?;
36+
ty_pat(TyPatKind::NotNull, start.to(parser.token.span))
37+
} else {
38+
pat_to_ty_pat(
39+
cx,
40+
*parser.parse_pat_no_top_guard(
41+
None,
42+
RecoverComma::No,
43+
RecoverColon::No,
44+
CommaRecoveryMode::EitherTupleOrPipe,
45+
)?,
46+
)
47+
};
4248

4349
if parser.token != token::Eof {
4450
parser.unexpected()?;

compiler/rustc_const_eval/src/interpret/validity.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1259,9 +1259,10 @@ impl<'rt, 'tcx, M: Machine<'tcx>> ValueVisitor<'tcx, M> for ValidityVisitor<'rt,
12591259
// When you extend this match, make sure to also add tests to
12601260
// tests/ui/type/pattern_types/validity.rs((
12611261
match **pat {
1262-
// Range patterns are precisely reflected into `valid_range` and thus
1262+
// Range and non-null patterns are precisely reflected into `valid_range` and thus
12631263
// handled fully by `visit_scalar` (called below).
12641264
ty::PatternKind::Range { .. } => {},
1265+
ty::PatternKind::NotNull => {},
12651266

12661267
// FIXME(pattern_types): check that the value is covered by one of the variants.
12671268
// For now, we rely on layout computation setting the scalar's `valid_range` to

compiler/rustc_hir/src/hir.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1855,6 +1855,9 @@ pub enum TyPatKind<'hir> {
18551855
/// A range pattern (e.g., `1..=2` or `1..2`).
18561856
Range(&'hir ConstArg<'hir>, &'hir ConstArg<'hir>),
18571857

1858+
/// A pattern that excludes null pointers
1859+
NotNull,
1860+
18581861
/// A list of patterns where only one needs to be satisfied
18591862
Or(&'hir [TyPat<'hir>]),
18601863

compiler/rustc_hir/src/intravisit.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -725,7 +725,7 @@ pub fn walk_ty_pat<'v, V: Visitor<'v>>(visitor: &mut V, pattern: &'v TyPat<'v>)
725725
try_visit!(visitor.visit_const_arg_unambig(upper_bound));
726726
}
727727
TyPatKind::Or(patterns) => walk_list!(visitor, visit_pattern_type_pattern, patterns),
728-
TyPatKind::Err(_) => (),
728+
TyPatKind::NotNull | TyPatKind::Err(_) => (),
729729
}
730730
V::Result::output()
731731
}

compiler/rustc_hir_analysis/src/hir_ty_lowering/mod.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2583,6 +2583,7 @@ impl<'tcx> dyn HirTyLowerer<'tcx> + '_ {
25832583
.span_delayed_bug(ty_span, "invalid base type for range pattern")),
25842584
}
25852585
}
2586+
hir::TyPatKind::NotNull => Ok(ty::PatternKind::NotNull),
25862587
hir::TyPatKind::Or(patterns) => {
25872588
self.tcx()
25882589
.mk_patterns_from_iter(patterns.iter().map(|pat| {

compiler/rustc_hir_analysis/src/variance/constraints.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -340,6 +340,7 @@ impl<'a, 'tcx> ConstraintContext<'a, 'tcx> {
340340
self.add_constraints_from_const(current, start, variance);
341341
self.add_constraints_from_const(current, end, variance);
342342
}
343+
ty::PatternKind::NotNull => {}
343344
ty::PatternKind::Or(patterns) => {
344345
for pat in patterns {
345346
self.add_constraints_from_pat(current, variance, pat)

compiler/rustc_hir_pretty/src/lib.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1888,6 +1888,10 @@ impl<'a> State<'a> {
18881888
self.word("..=");
18891889
self.print_const_arg(end);
18901890
}
1891+
TyPatKind::NotNull => {
1892+
self.word_space("not");
1893+
self.word("null");
1894+
}
18911895
TyPatKind::Or(patterns) => {
18921896
self.popen();
18931897
let mut first = true;

0 commit comments

Comments
 (0)