Added clarification regarding rust_try_inner.
This commit is contained in:
@@ -220,12 +220,19 @@ fn rust_exception_class() -> uw::_Unwind_Exception_Class {
|
|||||||
//
|
//
|
||||||
// This is pretty close to Rust's exception handling approach, except that Rust
|
// This is pretty close to Rust's exception handling approach, except that Rust
|
||||||
// does have a single "catch-all" handler at the bottom of each task's stack.
|
// does have a single "catch-all" handler at the bottom of each task's stack.
|
||||||
// So we have two versions:
|
// So we have two versions of the personality routine:
|
||||||
// - rust_eh_personality, used by all cleanup landing pads, which never catches,
|
// - rust_eh_personality, used by all cleanup landing pads, which never catches,
|
||||||
// so the behavior of __gcc_personality_v0 is perfectly adequate there, and
|
// so the behavior of __gcc_personality_v0 is perfectly adequate there, and
|
||||||
// - rust_eh_personality_catch, used only by rust_try(), which always catches.
|
// - rust_eh_personality_catch, used only by rust_try(), which always catches.
|
||||||
// This is achieved by overriding the return value in search phase to always
|
//
|
||||||
// say "catch!".
|
// Note, however, that for implementation simplicity, rust_eh_personality_catch
|
||||||
|
// lacks code to install a landing pad, so in order to obtain exception object
|
||||||
|
// pointer (which it needs to return upstream), rust_try() employs another trick:
|
||||||
|
// it calls into the nested rust_try_inner(), whose landing pad does not resume
|
||||||
|
// unwinds. Instead, it extracts the exception pointer and performs a "normal"
|
||||||
|
// return.
|
||||||
|
//
|
||||||
|
// See also: rt/rust_try.ll
|
||||||
|
|
||||||
#[cfg(not(target_arch = "arm"), not(windows, target_arch = "x86_64"), not(test))]
|
#[cfg(not(target_arch = "arm"), not(windows, target_arch = "x86_64"), not(test))]
|
||||||
#[doc(hidden)]
|
#[doc(hidden)]
|
||||||
@@ -334,7 +341,8 @@ pub mod eabi {
|
|||||||
|
|
||||||
// ARM EHABI uses a slightly different personality routine signature,
|
// ARM EHABI uses a slightly different personality routine signature,
|
||||||
// but otherwise works the same.
|
// but otherwise works the same.
|
||||||
#[cfg(target_arch = "arm", not(target_os = "ios", not(test)))]
|
#[cfg(target_arch = "arm", not(target_os = "ios"), not(test))]
|
||||||
|
#[doc(hidden)]
|
||||||
#[allow(visible_private_types)]
|
#[allow(visible_private_types)]
|
||||||
pub mod eabi {
|
pub mod eabi {
|
||||||
use uw = libunwind;
|
use uw = libunwind;
|
||||||
@@ -384,10 +392,9 @@ pub mod eabi {
|
|||||||
// with an "API translator" layer (_GCC_specific_handler).
|
// with an "API translator" layer (_GCC_specific_handler).
|
||||||
|
|
||||||
#[cfg(windows, target_arch = "x86_64", not(test))]
|
#[cfg(windows, target_arch = "x86_64", not(test))]
|
||||||
|
#[doc(hidden)]
|
||||||
#[allow(visible_private_types)]
|
#[allow(visible_private_types)]
|
||||||
#[allow(non_camel_case_types)]
|
#[allow(non_camel_case_types)]
|
||||||
#[allow(unused_variable)]
|
|
||||||
#[allow(uppercase_variables)]
|
|
||||||
pub mod eabi {
|
pub mod eabi {
|
||||||
use uw = libunwind;
|
use uw = libunwind;
|
||||||
use libc::{c_void, c_int};
|
use libc::{c_void, c_int};
|
||||||
|
|||||||
@@ -11,6 +11,7 @@
|
|||||||
; Rust's try-catch
|
; Rust's try-catch
|
||||||
; When f(...) returns normally, the return value is null.
|
; When f(...) returns normally, the return value is null.
|
||||||
; When f(...) throws, the return value is a pointer to the caught exception object.
|
; When f(...) throws, the return value is a pointer to the caught exception object.
|
||||||
|
|
||||||
; See also: librustrt/unwind.rs
|
; See also: librustrt/unwind.rs
|
||||||
|
|
||||||
define i8* @rust_try(void (i8*,i8*)* %f, i8* %fptr, i8* %env) {
|
define i8* @rust_try(void (i8*,i8*)* %f, i8* %fptr, i8* %env) {
|
||||||
@@ -25,7 +26,7 @@ normal:
|
|||||||
catch:
|
catch:
|
||||||
landingpad { i8*, i32 } personality i8* bitcast (i32 (...)* @rust_eh_personality_catch to i8*)
|
landingpad { i8*, i32 } personality i8* bitcast (i32 (...)* @rust_eh_personality_catch to i8*)
|
||||||
catch i8* null
|
catch i8* null
|
||||||
; execution will never reach here because rust_try_inner's landing pad does not resume unwinds
|
; rust_try_inner's landing pad does not resume unwinds, so execution will never reach here
|
||||||
ret i8* null
|
ret i8* null
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
# If this file is modified, then llvm will be forcibly cleaned and then rebuilt.
|
# If this file is modified, then llvm will be forcibly cleaned and then rebuilt.
|
||||||
# The actual contents of this file do not matter, but to trigger a change on the
|
# The actual contents of this file do not matter, but to trigger a change on the
|
||||||
# build bots then the contents should be changed so git updates the mtime.
|
# build bots then the contents should be changed so git updates the mtime.
|
||||||
2014-08-24
|
2014-08-05
|
||||||
|
|||||||
Reference in New Issue
Block a user