Skip to content

Commit dca74e7

Browse files
danielsntedinski
authored andcommitted
use codegen_unimplemented() for the try intrinsic (rust-lang#275)
* use codegen_unimplemented() for the try intrinsic * Additional unit test
1 parent 5e9ddf8 commit dca74e7

File tree

4 files changed

+63
-9
lines changed

4 files changed

+63
-9
lines changed

compiler/rustc_codegen_llvm/src/gotoc/intrinsic.rs

Lines changed: 18 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,14 @@ impl<'tcx> GotocCtx<'tcx> {
4242
let intrinsic = self.symbol_name(instance);
4343
let intrinsic = intrinsic.as_str();
4444
let loc = self.codegen_span_option2(span);
45+
debug!(
46+
"codegen_intrinsic:\n\tinstance {:?}\n\tfargs {:?}\n\tp {:?}\n\tspan {:?}",
47+
instance, fargs, p, span
48+
);
49+
let sig = instance.ty(self.tcx, ty::ParamEnv::reveal_all()).fn_sig(self.tcx);
50+
let sig = self.tcx.normalize_erasing_late_bound_regions(ty::ParamEnv::reveal_all(), sig);
51+
let ret_ty = self.monomorphize(sig.output());
52+
let cbmc_ret_ty = self.codegen_ty(ret_ty);
4553

4654
/// https://doc.rust-lang.org/core/intrinsics/fn.copy.html
4755
/// https://doc.rust-lang.org/core/intrinsics/fn.copy_nonoverlapping.html
@@ -171,6 +179,13 @@ impl<'tcx> GotocCtx<'tcx> {
171179
}};
172180
}
173181

182+
macro_rules! codegen_unimplemented_intrinsic {
183+
($url: expr) => {{
184+
let e = self.codegen_unimplemented(intrinsic, cbmc_ret_ty, loc, $url);
185+
self.codegen_expr_to_place(p, e)
186+
}};
187+
}
188+
174189
// Most atomic intrinsics do:
175190
// 1. Perform an operation on a primary argument (e.g., addition)
176191
// 2. Return the previous value of the primary argument
@@ -202,14 +217,6 @@ impl<'tcx> GotocCtx<'tcx> {
202217
}};
203218
}
204219

205-
debug!(
206-
"codegen_intrinsic:\n\tinstance {:?}\n\tfargs {:?}\n\tp {:?}\n\tspan {:?}",
207-
instance, fargs, p, span
208-
);
209-
let sig = instance.ty(self.tcx, ty::ParamEnv::reveal_all()).fn_sig(self.tcx);
210-
let sig = self.tcx.normalize_erasing_late_bound_regions(ty::ParamEnv::reveal_all(), sig);
211-
let ret_ty = self.monomorphize(sig.output());
212-
213220
match intrinsic {
214221
"abort" => Stmt::assert_false("abort intrinsic", loc),
215222
"add_with_overflow" => codegen_op_with_overflow!(add_overflow),
@@ -394,6 +401,9 @@ impl<'tcx> GotocCtx<'tcx> {
394401
"transmute" => self.codegen_intrinsic_transmute(fargs, ret_ty, p),
395402
"truncf32" => codegen_simple_intrinsic!(Truncf),
396403
"truncf64" => codegen_simple_intrinsic!(Trunc),
404+
"try" => {
405+
codegen_unimplemented_intrinsic!("https://github.com/model-checking/rmc/issues/267")
406+
}
397407
"type_id" => codegen_intrinsic_const!(),
398408
"type_name" => codegen_intrinsic_const!(),
399409
"unaligned_volatile_load" => {

compiler/rustc_codegen_llvm/src/gotoc/rvalue.rs

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -628,7 +628,15 @@ impl<'tcx> GotocCtx<'tcx> {
628628
match k {
629629
PointerCast::ReifyFnPointer => self.codegen_operand(o).address_of(),
630630
PointerCast::UnsafeFnPointer => self.codegen_operand(o),
631-
PointerCast::ClosureFnPointer(_) => unimplemented!(),
631+
PointerCast::ClosureFnPointer(_) => {
632+
let dest_typ = self.codegen_ty(t);
633+
self.codegen_unimplemented(
634+
"PointerCast::ClosureFnPointer",
635+
dest_typ,
636+
Location::none(),
637+
"https://github.com/model-checking/rmc/issues/274",
638+
)
639+
}
632640
PointerCast::MutToConstPointer => self.codegen_operand(o),
633641
PointerCast::ArrayToPointer => {
634642
// TODO: I am not sure whether it is correct or not.
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
// Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
2+
// SPDX-License-Identifier: Apache-2.0 OR MIT
3+
4+
// https://doc.rust-lang.org/std/panic/fn.catch_unwind.html
5+
// Stable way of calling the `try` intrinsic.
6+
use std::panic;
7+
8+
fn main() {
9+
let result = panic::catch_unwind(|| {
10+
println!("hello!");
11+
});
12+
assert!(result.is_ok());
13+
14+
let result = panic::catch_unwind(|| {
15+
panic!("oh no!");
16+
});
17+
assert!(result.is_err());
18+
}

src/test/cbmc/Intrinsics/fixme_try.rs

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
// Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
2+
// SPDX-License-Identifier: Apache-2.0 OR MIT
3+
4+
// See discussion on https://github.com/model-checking/rmc/issues/267
5+
#![feature(core_intrinsics)]
6+
use std::intrinsics::r#try;
7+
8+
fn main() {
9+
unsafe {
10+
// Rust will make a best-effort to swallow the panic, and then execute the cleanup function.
11+
// However, my understanding is that failure is still possible, since its just a best-effort
12+
r#try(
13+
|_a: *mut u8| panic!("foo"),
14+
std::ptr::null_mut(),
15+
|_a: *mut u8, _b: *mut u8| println!("bar"),
16+
);
17+
}
18+
}

0 commit comments

Comments
 (0)