Use less fragile error handling
This commit is contained in:
parent
77fe9f0a72
commit
126dcc618d
2 changed files with 16 additions and 18 deletions
|
@ -98,14 +98,16 @@ fn eval_body_using_ecx<'mir, 'tcx, R: InterpretationResult<'tcx>>(
|
||||||
// Only report this after validation, as validaiton produces much better diagnostics.
|
// Only report this after validation, as validaiton produces much better diagnostics.
|
||||||
// FIXME: ensure validation always reports this and stop making interning care about it.
|
// FIXME: ensure validation always reports this and stop making interning care about it.
|
||||||
|
|
||||||
if let Err(InternResult { found_bad_mutable_pointer, found_dangling_pointer }) = intern_result {
|
match intern_result {
|
||||||
if found_dangling_pointer {
|
Ok(()) => {}
|
||||||
|
Err(InternResult::FoundDanglingPointer) => {
|
||||||
return Err(ecx
|
return Err(ecx
|
||||||
.tcx
|
.tcx
|
||||||
.dcx()
|
.dcx()
|
||||||
.emit_err(DanglingPtrInFinal { span: ecx.tcx.span, kind: intern_kind })
|
.emit_err(DanglingPtrInFinal { span: ecx.tcx.span, kind: intern_kind })
|
||||||
.into());
|
.into());
|
||||||
} else if found_bad_mutable_pointer {
|
}
|
||||||
|
Err(InternResult::FoundBadMutablePointer) => {
|
||||||
// only report mutable pointers if there were no dangling pointers
|
// only report mutable pointers if there were no dangling pointers
|
||||||
let err_diag = errors::MutablePtrInFinal { span: ecx.tcx.span, kind: intern_kind };
|
let err_diag = errors::MutablePtrInFinal { span: ecx.tcx.span, kind: intern_kind };
|
||||||
ecx.tcx.emit_node_span_lint(
|
ecx.tcx.emit_node_span_lint(
|
||||||
|
|
|
@ -132,17 +132,10 @@ pub enum InternKind {
|
||||||
Promoted,
|
Promoted,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Default, Debug)]
|
#[derive(Debug)]
|
||||||
pub struct InternResult {
|
pub enum InternResult {
|
||||||
pub found_bad_mutable_pointer: bool,
|
FoundBadMutablePointer,
|
||||||
pub found_dangling_pointer: bool,
|
FoundDanglingPointer,
|
||||||
}
|
|
||||||
|
|
||||||
impl InternResult {
|
|
||||||
fn has_errors(&self) -> bool {
|
|
||||||
let Self { found_bad_mutable_pointer, found_dangling_pointer } = *self;
|
|
||||||
found_bad_mutable_pointer || found_dangling_pointer
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Intern `ret` and everything it references.
|
/// Intern `ret` and everything it references.
|
||||||
|
@ -212,7 +205,7 @@ pub fn intern_const_alloc_recursive<
|
||||||
// Whether we encountered a bad mutable pointer.
|
// Whether we encountered a bad mutable pointer.
|
||||||
// We want to first report "dangling" and then "mutable", so we need to delay reporting these
|
// We want to first report "dangling" and then "mutable", so we need to delay reporting these
|
||||||
// errors.
|
// errors.
|
||||||
let mut result = InternResult::default();
|
let mut result = Ok(());
|
||||||
|
|
||||||
// Keep interning as long as there are things to intern.
|
// Keep interning as long as there are things to intern.
|
||||||
// We show errors if there are dangling pointers, or mutable pointers in immutable contexts
|
// We show errors if there are dangling pointers, or mutable pointers in immutable contexts
|
||||||
|
@ -262,7 +255,10 @@ pub fn intern_const_alloc_recursive<
|
||||||
// on the promotion analysis not screwing up to ensure that it is sound to intern
|
// on the promotion analysis not screwing up to ensure that it is sound to intern
|
||||||
// promoteds as immutable.
|
// promoteds as immutable.
|
||||||
trace!("found bad mutable pointer");
|
trace!("found bad mutable pointer");
|
||||||
result.found_bad_mutable_pointer = true;
|
// Prefer dangling pointer errors over mutable pointer errors
|
||||||
|
if result.is_ok() {
|
||||||
|
result = Err(InternResult::FoundBadMutablePointer);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if ecx.tcx.try_get_global_alloc(alloc_id).is_some() {
|
if ecx.tcx.try_get_global_alloc(alloc_id).is_some() {
|
||||||
// Already interned.
|
// Already interned.
|
||||||
|
@ -284,11 +280,11 @@ pub fn intern_const_alloc_recursive<
|
||||||
Ok(nested) => todo.extend(nested),
|
Ok(nested) => todo.extend(nested),
|
||||||
Err(()) => {
|
Err(()) => {
|
||||||
ecx.tcx.dcx().delayed_bug("found dangling pointer during const interning");
|
ecx.tcx.dcx().delayed_bug("found dangling pointer during const interning");
|
||||||
result.found_dangling_pointer = true
|
result = Err(InternResult::FoundDanglingPointer);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if result.has_errors() { Err(result) } else { Ok(()) }
|
result
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Intern `ret`. This function assumes that `ret` references no other allocation.
|
/// Intern `ret`. This function assumes that `ret` references no other allocation.
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue