aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPhilip Herron <herron.philip@googlemail.com>2025-04-03 15:37:40 +0100
committerPhilip Herron <philip.herron@embecosm.com>2025-04-03 16:40:33 +0000
commit002c349b6d0f8c12d26beaff178785524f155583 (patch)
tree66f3006c26577fda51424dee288fffda24e88462
parent67017c92b8cb51064243c9c76b0fafe3c80e17b2 (diff)
downloadgcc-002c349b6d0f8c12d26beaff178785524f155583.zip
gcc-002c349b6d0f8c12d26beaff178785524f155583.tar.gz
gcc-002c349b6d0f8c12d26beaff178785524f155583.tar.bz2
gccrs: Fix ICE on invalid match arms
We hit assertions on empty enum or unknown variant, this catches the error and emits a new diagnostic. Fixes Rust-GCC#3656 gcc/rust/ChangeLog: * typecheck/rust-hir-type-check-pattern.cc (TypeCheckPattern::visit): emit error gcc/testsuite/ChangeLog: * rust/compile/issue-3656.rs: New test. Signed-off-by: Philip Herron <herron.philip@googlemail.com>
-rw-r--r--gcc/rust/typecheck/rust-hir-type-check-pattern.cc21
-rw-r--r--gcc/testsuite/rust/compile/issue-3656.rs10
2 files changed, 29 insertions, 2 deletions
diff --git a/gcc/rust/typecheck/rust-hir-type-check-pattern.cc b/gcc/rust/typecheck/rust-hir-type-check-pattern.cc
index eb3c416..1543d62 100644
--- a/gcc/rust/typecheck/rust-hir-type-check-pattern.cc
+++ b/gcc/rust/typecheck/rust-hir-type-check-pattern.cc
@@ -277,7 +277,15 @@ TypeCheckPattern::visit (HIR::StructPattern &pattern)
infered = pattern_ty;
TyTy::ADTType *adt = static_cast<TyTy::ADTType *> (infered);
- rust_assert (adt->number_of_variants () > 0);
+ if (adt->number_of_variants () == 0)
+ {
+ HIR::PathInExpression &path = pattern.get_path ();
+ const AST::SimplePath &sp = path.as_simple_path ();
+ rust_error_at (pattern.get_locus (), ErrorCode::E0574,
+ "expected struct, variant or union type, found enum %qs",
+ sp.as_string ().c_str ());
+ return;
+ }
TyTy::VariantDef *variant = adt->get_variants ().at (0);
if (adt->is_enum ())
@@ -285,7 +293,16 @@ TypeCheckPattern::visit (HIR::StructPattern &pattern)
HirId variant_id = UNKNOWN_HIRID;
bool ok = context->lookup_variant_definition (
pattern.get_path ().get_mappings ().get_hirid (), &variant_id);
- rust_assert (ok);
+ if (!ok)
+ {
+ HIR::PathInExpression &path = pattern.get_path ();
+ const AST::SimplePath &sp = path.as_simple_path ();
+ rust_error_at (
+ pattern.get_locus (), ErrorCode::E0574,
+ "expected struct, variant or union type, found enum %qs",
+ sp.as_string ().c_str ());
+ return;
+ }
ok = adt->lookup_variant_by_id (variant_id, &variant);
rust_assert (ok);
diff --git a/gcc/testsuite/rust/compile/issue-3656.rs b/gcc/testsuite/rust/compile/issue-3656.rs
new file mode 100644
index 0000000..e0bec2f
--- /dev/null
+++ b/gcc/testsuite/rust/compile/issue-3656.rs
@@ -0,0 +1,10 @@
+enum Foo {
+ Bar(isize),
+}
+
+fn main() {
+ match Foo::Bar(205) {
+ Foo { i } => (),
+ // { dg-error "expected struct, variant or union type, found enum .Foo. .E0574." "" { target *-*-* } .-1 }
+ }
+}