diff options
| author | bors <bors@rust-lang.org> | 2021-06-23 21:35:46 +0000 |
|---|---|---|
| committer | bors <bors@rust-lang.org> | 2021-06-23 21:35:46 +0000 |
| commit | f1e691da2e640bb45fe18f8a5bd8f7afa65ce21d (patch) | |
| tree | 4bc0031e6e3e98f5fb85a57793857a294d5fe2f8 /compiler | |
| parent | 5a7834050f3a0ebcd117b4ddf0bc1e8459594309 (diff) | |
| parent | 433c1aec2195eb8864e46bf24f50f74123bbb284 (diff) | |
| download | rust-f1e691da2e640bb45fe18f8a5bd8f7afa65ce21d.tar.gz rust-f1e691da2e640bb45fe18f8a5bd8f7afa65ce21d.zip | |
Auto merge of #86138 - FabianWolff:issue-85871, r=nikomatsakis
Check whether the closure's owner is an ADT in thir-unsafeck
This pull request fixes #85871. The code in `rustc_mir_build/src/check_unsafety.rs` incorrectly assumes that a closure's owner always has a body, but only functions, closures, and constants have bodies, whereas a closure can also appear inside a struct or enum:
```rust
struct S {
arr: [(); match || 1 { _ => 42 }]
}
enum E {
A([(); { || 1; 42 }])
}
```
This pull request fixes the resulting ICE by checking whether the closure's owner is an ADT and only deferring to `thir_check_unsafety(owner)` if it isn't.
Diffstat (limited to 'compiler')
| -rw-r--r-- | compiler/rustc_mir_build/src/check_unsafety.rs | 11 |
1 files changed, 8 insertions, 3 deletions
diff --git a/compiler/rustc_mir_build/src/check_unsafety.rs b/compiler/rustc_mir_build/src/check_unsafety.rs index 4e80931ec03..9bef8ac2413 100644 --- a/compiler/rustc_mir_build/src/check_unsafety.rs +++ b/compiler/rustc_mir_build/src/check_unsafety.rs @@ -375,10 +375,15 @@ pub fn check_unsafety<'tcx>(tcx: TyCtxt<'tcx>, def: ty::WithOptConstParam<LocalD return; } - // Closures are handled by their parent function + // Closures are handled by their owner, if it has a body if tcx.is_closure(def.did.to_def_id()) { - tcx.ensure().thir_check_unsafety(tcx.hir().local_def_id_to_hir_id(def.did).owner); - return; + let owner = tcx.hir().local_def_id_to_hir_id(def.did).owner; + let owner_hir_id = tcx.hir().local_def_id_to_hir_id(owner); + + if tcx.hir().maybe_body_owned_by(owner_hir_id).is_some() { + tcx.ensure().thir_check_unsafety(owner); + return; + } } let (thir, expr) = tcx.thir_body(def); |
