about summary refs log tree commit diff
path: root/src/libstd/rt/unwind
diff options
context:
space:
mode:
authorAlex Crichton <alex@alexcrichton.com>2015-09-08 15:53:46 -0700
committerAlex Crichton <alex@alexcrichton.com>2015-09-11 11:19:20 -0700
commitf4be2026dfb507e5db919cc5df8fd934e05fa0b8 (patch)
tree278d5b3916042e7232b7ba98a5ead399a52057eb /src/libstd/rt/unwind
parent192c37537bc6ffaee06e8b4099dd09ae43bcfee7 (diff)
downloadrust-f4be2026dfb507e5db919cc5df8fd934e05fa0b8.tar.gz
rust-f4be2026dfb507e5db919cc5df8fd934e05fa0b8.zip
std: Internalize almost all of `std::rt`
This commit does some refactoring to make almost all of the `std::rt` private.
Specifically, the following items are no longer part of its API:

* DEFAULT_ERROR_CODE
* backtrace
* unwind
* args
* at_exit
* cleanup
* heap (this is just alloc::heap)
* min_stack
* util

The module is now tagged as `#[doc(hidden)]` as the only purpose it's serve is
an entry point for the `panic!` macro via the `begin_unwind` and
`begin_unwind_fmt` reexports.
Diffstat (limited to 'src/libstd/rt/unwind')
-rw-r--r--src/libstd/rt/unwind/gcc.rs235
-rw-r--r--src/libstd/rt/unwind/mod.rs325
-rw-r--r--src/libstd/rt/unwind/seh.rs145
-rw-r--r--src/libstd/rt/unwind/seh64_gnu.rs226
4 files changed, 0 insertions, 931 deletions
diff --git a/src/libstd/rt/unwind/gcc.rs b/src/libstd/rt/unwind/gcc.rs
deleted file mode 100644
index 55deb048b7e..00000000000
--- a/src/libstd/rt/unwind/gcc.rs
+++ /dev/null
@@ -1,235 +0,0 @@
-// Copyright 2015 The Rust Project Developers. See the COPYRIGHT
-// file at the top-level directory of this distribution and at
-// http://rust-lang.org/COPYRIGHT.
-//
-// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
-// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
-// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
-// option. This file may not be copied, modified, or distributed
-// except according to those terms.
-
-#![allow(private_no_mangle_fns)]
-
-use prelude::v1::*;
-
-use any::Any;
-use rt::libunwind as uw;
-
-struct Exception {
-    uwe: uw::_Unwind_Exception,
-    cause: Option<Box<Any + Send + 'static>>,
-}
-
-pub unsafe fn panic(data: Box<Any + Send + 'static>) -> ! {
-    let exception: Box<_> = box Exception {
-        uwe: uw::_Unwind_Exception {
-            exception_class: rust_exception_class(),
-            exception_cleanup: exception_cleanup,
-            private: [0; uw::unwinder_private_data_size],
-        },
-        cause: Some(data),
-    };
-    let exception_param = Box::into_raw(exception) as *mut uw::_Unwind_Exception;
-    let error = uw::_Unwind_RaiseException(exception_param);
-    rtabort!("Could not unwind stack, error = {}", error as isize);
-
-    extern fn exception_cleanup(_unwind_code: uw::_Unwind_Reason_Code,
-                                exception: *mut uw::_Unwind_Exception) {
-        rtdebug!("exception_cleanup()");
-        unsafe {
-            let _: Box<Exception> = Box::from_raw(exception as *mut Exception);
-        }
-    }
-}
-
-pub unsafe fn cleanup(ptr: *mut u8) -> Box<Any + Send + 'static> {
-    let my_ep = ptr as *mut Exception;
-    rtdebug!("caught {}", (*my_ep).uwe.exception_class);
-    let cause = (*my_ep).cause.take();
-    uw::_Unwind_DeleteException(ptr as *mut _);
-    cause.unwrap()
-}
-
-// Rust's exception class identifier.  This is used by personality routines to
-// determine whether the exception was thrown by their own runtime.
-fn rust_exception_class() -> uw::_Unwind_Exception_Class {
-    // M O Z \0  R U S T -- vendor, language
-    0x4d4f5a_00_52555354
-}
-
-// We could implement our personality routine in pure Rust, however exception
-// info decoding is tedious.  More importantly, personality routines have to
-// handle various platform quirks, which are not fun to maintain.  For this
-// reason, we attempt to reuse personality routine of the C language:
-// __gcc_personality_v0.
-//
-// Since C does not support exception catching, __gcc_personality_v0 simply
-// always returns _URC_CONTINUE_UNWIND in search phase, and always returns
-// _URC_INSTALL_CONTEXT (i.e. "invoke cleanup code") in cleanup phase.
-//
-// 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 thread's stack.
-// So we have two versions of the personality routine:
-// - rust_eh_personality, used by all cleanup landing pads, which never catches,
-//   so the behavior of __gcc_personality_v0 is perfectly adequate there, and
-// - rust_eh_personality_catch, used only by rust_try(), which always catches.
-//
-// See also: rustc_trans::trans::intrinsic::trans_gnu_try
-
-#[cfg(all(not(target_arch = "arm"),
-          not(all(windows, target_arch = "x86_64")),
-          not(test)))]
-pub mod eabi {
-    use rt::libunwind as uw;
-    use libc::c_int;
-
-    extern {
-        fn __gcc_personality_v0(version: c_int,
-                                actions: uw::_Unwind_Action,
-                                exception_class: uw::_Unwind_Exception_Class,
-                                ue_header: *mut uw::_Unwind_Exception,
-                                context: *mut uw::_Unwind_Context)
-            -> uw::_Unwind_Reason_Code;
-    }
-
-    #[lang = "eh_personality"]
-    #[no_mangle]
-    extern fn rust_eh_personality(
-        version: c_int,
-        actions: uw::_Unwind_Action,
-        exception_class: uw::_Unwind_Exception_Class,
-        ue_header: *mut uw::_Unwind_Exception,
-        context: *mut uw::_Unwind_Context
-    ) -> uw::_Unwind_Reason_Code
-    {
-        unsafe {
-            __gcc_personality_v0(version, actions, exception_class, ue_header,
-                                 context)
-        }
-    }
-
-    #[lang = "eh_personality_catch"]
-    #[no_mangle]
-    pub extern fn rust_eh_personality_catch(
-        version: c_int,
-        actions: uw::_Unwind_Action,
-        exception_class: uw::_Unwind_Exception_Class,
-        ue_header: *mut uw::_Unwind_Exception,
-        context: *mut uw::_Unwind_Context
-    ) -> uw::_Unwind_Reason_Code
-    {
-
-        if (actions as c_int & uw::_UA_SEARCH_PHASE as c_int) != 0 { // search phase
-            uw::_URC_HANDLER_FOUND // catch!
-        }
-        else { // cleanup phase
-            unsafe {
-                __gcc_personality_v0(version, actions, exception_class, ue_header,
-                                     context)
-            }
-        }
-    }
-}
-
-// iOS on armv7 is using SjLj exceptions and therefore requires to use
-// a specialized personality routine: __gcc_personality_sj0
-
-#[cfg(all(target_os = "ios", target_arch = "arm", not(test)))]
-pub mod eabi {
-    use rt::libunwind as uw;
-    use libc::c_int;
-
-    extern {
-        fn __gcc_personality_sj0(version: c_int,
-                                actions: uw::_Unwind_Action,
-                                exception_class: uw::_Unwind_Exception_Class,
-                                ue_header: *mut uw::_Unwind_Exception,
-                                context: *mut uw::_Unwind_Context)
-            -> uw::_Unwind_Reason_Code;
-    }
-
-    #[lang = "eh_personality"]
-    #[no_mangle]
-    pub extern fn rust_eh_personality(
-        version: c_int,
-        actions: uw::_Unwind_Action,
-        exception_class: uw::_Unwind_Exception_Class,
-        ue_header: *mut uw::_Unwind_Exception,
-        context: *mut uw::_Unwind_Context
-    ) -> uw::_Unwind_Reason_Code
-    {
-        unsafe {
-            __gcc_personality_sj0(version, actions, exception_class, ue_header,
-                                  context)
-        }
-    }
-
-    #[lang = "eh_personality_catch"]
-    #[no_mangle]
-    pub extern fn rust_eh_personality_catch(
-        version: c_int,
-        actions: uw::_Unwind_Action,
-        exception_class: uw::_Unwind_Exception_Class,
-        ue_header: *mut uw::_Unwind_Exception,
-        context: *mut uw::_Unwind_Context
-    ) -> uw::_Unwind_Reason_Code
-    {
-        if (actions as c_int & uw::_UA_SEARCH_PHASE as c_int) != 0 { // search phase
-            uw::_URC_HANDLER_FOUND // catch!
-        }
-        else { // cleanup phase
-            unsafe {
-                __gcc_personality_sj0(version, actions, exception_class, ue_header,
-                                      context)
-            }
-        }
-    }
-}
-
-
-// ARM EHABI uses a slightly different personality routine signature,
-// but otherwise works the same.
-#[cfg(all(target_arch = "arm", not(target_os = "ios"), not(test)))]
-pub mod eabi {
-    use rt::libunwind as uw;
-    use libc::c_int;
-
-    extern {
-        fn __gcc_personality_v0(state: uw::_Unwind_State,
-                                ue_header: *mut uw::_Unwind_Exception,
-                                context: *mut uw::_Unwind_Context)
-            -> uw::_Unwind_Reason_Code;
-    }
-
-    #[lang = "eh_personality"]
-    #[no_mangle]
-    extern fn rust_eh_personality(
-        state: uw::_Unwind_State,
-        ue_header: *mut uw::_Unwind_Exception,
-        context: *mut uw::_Unwind_Context
-    ) -> uw::_Unwind_Reason_Code
-    {
-        unsafe {
-            __gcc_personality_v0(state, ue_header, context)
-        }
-    }
-
-    #[lang = "eh_personality_catch"]
-    #[no_mangle]
-    pub extern fn rust_eh_personality_catch(
-        state: uw::_Unwind_State,
-        ue_header: *mut uw::_Unwind_Exception,
-        context: *mut uw::_Unwind_Context
-    ) -> uw::_Unwind_Reason_Code
-    {
-        if (state as c_int & uw::_US_ACTION_MASK as c_int)
-                           == uw::_US_VIRTUAL_UNWIND_FRAME as c_int { // search phase
-            uw::_URC_HANDLER_FOUND // catch!
-        }
-        else { // cleanup phase
-            unsafe {
-                __gcc_personality_v0(state, ue_header, context)
-            }
-        }
-    }
-}
diff --git a/src/libstd/rt/unwind/mod.rs b/src/libstd/rt/unwind/mod.rs
deleted file mode 100644
index 4feb2d49a98..00000000000
--- a/src/libstd/rt/unwind/mod.rs
+++ /dev/null
@@ -1,325 +0,0 @@
-// Copyright 2013 The Rust Project Developers. See the COPYRIGHT
-// file at the top-level directory of this distribution and at
-// http://rust-lang.org/COPYRIGHT.
-//
-// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
-// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
-// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
-// option. This file may not be copied, modified, or distributed
-// except according to those terms.
-
-//! Implementation of Rust stack unwinding
-//!
-//! For background on exception handling and stack unwinding please see
-//! "Exception Handling in LLVM" (llvm.org/docs/ExceptionHandling.html) and
-//! documents linked from it.
-//! These are also good reads:
-//!     http://mentorembedded.github.io/cxx-abi/abi-eh.html
-//!     http://monoinfinito.wordpress.com/series/exception-handling-in-c/
-//!     http://www.airs.com/blog/index.php?s=exception+frames
-//!
-//! ## A brief summary
-//!
-//! Exception handling happens in two phases: a search phase and a cleanup phase.
-//!
-//! In both phases the unwinder walks stack frames from top to bottom using
-//! information from the stack frame unwind sections of the current process's
-//! modules ("module" here refers to an OS module, i.e. an executable or a
-//! dynamic library).
-//!
-//! For each stack frame, it invokes the associated "personality routine", whose
-//! address is also stored in the unwind info section.
-//!
-//! In the search phase, the job of a personality routine is to examine exception
-//! object being thrown, and to decide whether it should be caught at that stack
-//! frame.  Once the handler frame has been identified, cleanup phase begins.
-//!
-//! In the cleanup phase, personality routines invoke cleanup code associated
-//! with their stack frames (i.e. destructors).  Once stack has been unwound down
-//! to the handler frame level, unwinding stops and the last personality routine
-//! transfers control to its catch block.
-//!
-//! ## Frame unwind info registration
-//!
-//! Each module has its own frame unwind info section (usually ".eh_frame"), and
-//! unwinder needs to know about all of them in order for unwinding to be able to
-//! cross module boundaries.
-//!
-//! On some platforms, like Linux, this is achieved by dynamically enumerating
-//! currently loaded modules via the dl_iterate_phdr() API and finding all
-//! .eh_frame sections.
-//!
-//! Others, like Windows, require modules to actively register their unwind info
-//! sections by calling __register_frame_info() API at startup.  In the latter
-//! case it is essential that there is only one copy of the unwinder runtime in
-//! the process.  This is usually achieved by linking to the dynamic version of
-//! the unwind runtime.
-//!
-//! Currently Rust uses unwind runtime provided by libgcc.
-
-#![allow(dead_code)]
-#![allow(unused_imports)]
-
-use prelude::v1::*;
-
-use any::Any;
-use boxed;
-use cell::Cell;
-use cmp;
-use panicking;
-use fmt;
-use intrinsics;
-use mem;
-use sync::atomic::{self, Ordering};
-use sys_common::mutex::Mutex;
-
-// The actual unwinding implementation is cfg'd here, and we've got two current
-// implementations. One goes through SEH on Windows and the other goes through
-// libgcc via the libunwind-like API.
-
-// i686-pc-windows-msvc
-#[cfg(all(windows, target_arch = "x86", target_env = "msvc"))]
-#[path = "seh.rs"] #[doc(hidden)]
-pub mod imp;
-
-// x86_64-pc-windows-*
-#[cfg(all(windows, target_arch = "x86_64"))]
-#[path = "seh64_gnu.rs"] #[doc(hidden)]
-pub mod imp;
-
-// i686-pc-windows-gnu and all others
-#[cfg(any(unix, all(windows, target_arch = "x86", target_env = "gnu")))]
-#[path = "gcc.rs"] #[doc(hidden)]
-pub mod imp;
-
-pub type Callback = fn(msg: &(Any + Send), file: &'static str, line: u32);
-
-// Variables used for invoking callbacks when a thread starts to unwind.
-//
-// For more information, see below.
-const MAX_CALLBACKS: usize = 16;
-static CALLBACKS: [atomic::AtomicUsize; MAX_CALLBACKS] =
-        [atomic::AtomicUsize::new(0), atomic::AtomicUsize::new(0),
-         atomic::AtomicUsize::new(0), atomic::AtomicUsize::new(0),
-         atomic::AtomicUsize::new(0), atomic::AtomicUsize::new(0),
-         atomic::AtomicUsize::new(0), atomic::AtomicUsize::new(0),
-         atomic::AtomicUsize::new(0), atomic::AtomicUsize::new(0),
-         atomic::AtomicUsize::new(0), atomic::AtomicUsize::new(0),
-         atomic::AtomicUsize::new(0), atomic::AtomicUsize::new(0),
-         atomic::AtomicUsize::new(0), atomic::AtomicUsize::new(0)];
-static CALLBACK_CNT: atomic::AtomicUsize = atomic::AtomicUsize::new(0);
-
-thread_local! { static PANICKING: Cell<bool> = Cell::new(false) }
-
-/// Invoke a closure, capturing the cause of panic if one occurs.
-///
-/// This function will return `Ok(())` if the closure did not panic, and will
-/// return `Err(cause)` if the closure panics. The `cause` returned is the
-/// object with which panic was originally invoked.
-///
-/// This function also is unsafe for a variety of reasons:
-///
-/// * This is not safe to call in a nested fashion. The unwinding
-///   interface for Rust is designed to have at most one try/catch block per
-///   thread, not multiple. No runtime checking is currently performed to uphold
-///   this invariant, so this function is not safe. A nested try/catch block
-///   may result in corruption of the outer try/catch block's state, especially
-///   if this is used within a thread itself.
-///
-/// * It is not sound to trigger unwinding while already unwinding. Rust threads
-///   have runtime checks in place to ensure this invariant, but it is not
-///   guaranteed that a rust thread is in place when invoking this function.
-///   Unwinding twice can lead to resource leaks where some destructors are not
-///   run.
-pub unsafe fn try<F: FnOnce()>(f: F) -> Result<(), Box<Any + Send>> {
-    let mut f = Some(f);
-    return inner_try(try_fn::<F>, &mut f as *mut _ as *mut u8);
-
-    // If an inner function were not used here, then this generic function `try`
-    // uses the native symbol `rust_try`, for which the code is statically
-    // linked into the standard library. This means that the DLL for the
-    // standard library must have `rust_try` as an exposed symbol that
-    // downstream crates can link against (because monomorphizations of `try` in
-    // downstream crates will have a reference to the `rust_try` symbol).
-    //
-    // On MSVC this requires the symbol `rust_try` to be tagged with
-    // `dllexport`, but it's easier to not have conditional `src/rt/rust_try.ll`
-    // files and instead just have this non-generic shim the compiler can take
-    // care of exposing correctly.
-    unsafe fn inner_try(f: fn(*mut u8), data: *mut u8)
-                        -> Result<(), Box<Any + Send>> {
-        let prev = PANICKING.with(|s| s.get());
-        PANICKING.with(|s| s.set(false));
-        let ep = intrinsics::try(f, data);
-        PANICKING.with(|s| s.set(prev));
-        if ep.is_null() {
-            Ok(())
-        } else {
-            Err(imp::cleanup(ep))
-        }
-    }
-
-    fn try_fn<F: FnOnce()>(opt_closure: *mut u8) {
-        let opt_closure = opt_closure as *mut Option<F>;
-        unsafe { (*opt_closure).take().unwrap()(); }
-    }
-
-    extern {
-        // Rust's try-catch
-        // When f(...) returns normally, the return value is null.
-        // When f(...) throws, the return value is a pointer to the caught
-        // exception object.
-        fn rust_try(f: extern fn(*mut u8),
-                    data: *mut u8) -> *mut u8;
-    }
-}
-
-/// Determines whether the current thread is unwinding because of panic.
-pub fn panicking() -> bool {
-    PANICKING.with(|s| s.get())
-}
-
-// An uninlined, unmangled function upon which to slap yer breakpoints
-#[inline(never)]
-#[no_mangle]
-#[allow(private_no_mangle_fns)]
-fn rust_panic(cause: Box<Any + Send + 'static>) -> ! {
-    rtdebug!("begin_unwind()");
-    unsafe {
-        imp::panic(cause)
-    }
-}
-
-#[cfg(not(test))]
-/// Entry point of panic from the libcore crate.
-#[lang = "panic_fmt"]
-pub extern fn rust_begin_unwind(msg: fmt::Arguments,
-                                file: &'static str, line: u32) -> ! {
-    begin_unwind_fmt(msg, &(file, line))
-}
-
-/// The entry point for unwinding with a formatted message.
-///
-/// This is designed to reduce the amount of code required at the call
-/// site as much as possible (so that `panic!()` has as low an impact
-/// on (e.g.) the inlining of other functions as possible), by moving
-/// the actual formatting into this shared place.
-#[inline(never)] #[cold]
-pub fn begin_unwind_fmt(msg: fmt::Arguments, file_line: &(&'static str, u32)) -> ! {
-    use fmt::Write;
-
-    // We do two allocations here, unfortunately. But (a) they're
-    // required with the current scheme, and (b) we don't handle
-    // panic + OOM properly anyway (see comment in begin_unwind
-    // below).
-
-    let mut s = String::new();
-    let _ = s.write_fmt(msg);
-    begin_unwind_inner(Box::new(s), file_line)
-}
-
-/// This is the entry point of unwinding for panic!() and assert!().
-#[inline(never)] #[cold] // avoid code bloat at the call sites as much as possible
-pub fn begin_unwind<M: Any + Send>(msg: M, file_line: &(&'static str, u32)) -> ! {
-    // Note that this should be the only allocation performed in this code path.
-    // Currently this means that panic!() on OOM will invoke this code path,
-    // but then again we're not really ready for panic on OOM anyway. If
-    // we do start doing this, then we should propagate this allocation to
-    // be performed in the parent of this thread instead of the thread that's
-    // panicking.
-
-    // see below for why we do the `Any` coercion here.
-    begin_unwind_inner(Box::new(msg), file_line)
-}
-
-/// The core of the unwinding.
-///
-/// This is non-generic to avoid instantiation bloat in other crates
-/// (which makes compilation of small crates noticeably slower). (Note:
-/// we need the `Any` object anyway, we're not just creating it to
-/// avoid being generic.)
-///
-/// Doing this split took the LLVM IR line counts of `fn main() { panic!()
-/// }` from ~1900/3700 (-O/no opts) to 180/590.
-#[inline(never)] #[cold] // this is the slow path, please never inline this
-fn begin_unwind_inner(msg: Box<Any + Send>,
-                      file_line: &(&'static str, u32)) -> ! {
-    // Make sure the default failure handler is registered before we look at the
-    // callbacks. We also use a raw sys-based mutex here instead of a
-    // `std::sync` one as accessing TLS can cause weird recursive problems (and
-    // we don't need poison checking).
-    unsafe {
-        static LOCK: Mutex = Mutex::new();
-        static mut INIT: bool = false;
-        LOCK.lock();
-        if !INIT {
-            register(panicking::on_panic);
-            INIT = true;
-        }
-        LOCK.unlock();
-    }
-
-    // First, invoke call the user-defined callbacks triggered on thread panic.
-    //
-    // By the time that we see a callback has been registered (by reading
-    // MAX_CALLBACKS), the actual callback itself may have not been stored yet,
-    // so we just chalk it up to a race condition and move on to the next
-    // callback. Additionally, CALLBACK_CNT may briefly be higher than
-    // MAX_CALLBACKS, so we're sure to clamp it as necessary.
-    let callbacks = {
-        let amt = CALLBACK_CNT.load(Ordering::SeqCst);
-        &CALLBACKS[..cmp::min(amt, MAX_CALLBACKS)]
-    };
-    for cb in callbacks {
-        match cb.load(Ordering::SeqCst) {
-            0 => {}
-            n => {
-                let f: Callback = unsafe { mem::transmute(n) };
-                let (file, line) = *file_line;
-                f(&*msg, file, line);
-            }
-        }
-    };
-
-    // Now that we've run all the necessary unwind callbacks, we actually
-    // perform the unwinding.
-    if panicking() {
-        // If a thread panics while it's already unwinding then we
-        // have limited options. Currently our preference is to
-        // just abort. In the future we may consider resuming
-        // unwinding or otherwise exiting the thread cleanly.
-        rterrln!("thread panicked while panicking. aborting.");
-        unsafe { intrinsics::abort() }
-    }
-    PANICKING.with(|s| s.set(true));
-    rust_panic(msg);
-}
-
-/// Register a callback to be invoked when a thread unwinds.
-///
-/// This is an unsafe and experimental API which allows for an arbitrary
-/// callback to be invoked when a thread panics. This callback is invoked on both
-/// the initial unwinding and a double unwinding if one occurs. Additionally,
-/// the local `Thread` will be in place for the duration of the callback, and
-/// the callback must ensure that it remains in place once the callback returns.
-///
-/// Only a limited number of callbacks can be registered, and this function
-/// returns whether the callback was successfully registered or not. It is not
-/// currently possible to unregister a callback once it has been registered.
-pub unsafe fn register(f: Callback) -> bool {
-    match CALLBACK_CNT.fetch_add(1, Ordering::SeqCst) {
-        // The invocation code has knowledge of this window where the count has
-        // been incremented, but the callback has not been stored. We're
-        // guaranteed that the slot we're storing into is 0.
-        n if n < MAX_CALLBACKS => {
-            let prev = CALLBACKS[n].swap(mem::transmute(f), Ordering::SeqCst);
-            rtassert!(prev == 0);
-            true
-        }
-        // If we accidentally bumped the count too high, pull it back.
-        _ => {
-            CALLBACK_CNT.store(MAX_CALLBACKS, Ordering::SeqCst);
-            false
-        }
-    }
-}
diff --git a/src/libstd/rt/unwind/seh.rs b/src/libstd/rt/unwind/seh.rs
deleted file mode 100644
index 8c793758166..00000000000
--- a/src/libstd/rt/unwind/seh.rs
+++ /dev/null
@@ -1,145 +0,0 @@
-// Copyright 2015 The Rust Project Developers. See the COPYRIGHT
-// file at the top-level directory of this distribution and at
-// http://rust-lang.org/COPYRIGHT.
-//
-// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
-// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
-// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
-// option. This file may not be copied, modified, or distributed
-// except according to those terms.
-
-//! Win64 SEH (see http://msdn.microsoft.com/en-us/library/1eyas8tf.aspx)
-//!
-//! On Windows (currently only on MSVC), the default exception handling
-//! mechanism is Structured Exception Handling (SEH). This is quite different
-//! than Dwarf-based exception handling (e.g. what other unix platforms use) in
-//! terms of compiler internals, so LLVM is required to have a good deal of
-//! extra support for SEH. Currently this support is somewhat lacking, so what's
-//! here is the bare bones of SEH support.
-//!
-//! In a nutshell, what happens here is:
-//!
-//! 1. The `panic` function calls the standard Windows function `RaiseException`
-//!    with a Rust-specific code, triggering the unwinding process.
-//! 2. All landing pads generated by the compiler (just "cleanup" landing pads)
-//!    use the personality function `__C_specific_handler`, a function in the
-//!    CRT, and the unwinding code in Windows will use this personality function
-//!    to execute all cleanup code on the stack.
-//! 3. Eventually the "catch" code in `rust_try` (located in
-//!    src/rt/rust_try_msvc_64.ll) is executed, which will ensure that the
-//!    exception being caught is indeed a Rust exception, returning control back
-//!    into Rust.
-//!
-//! Some specific differences from the gcc-based exception handling are:
-//!
-//! * Rust has no custom personality function, it is instead *always*
-//!   __C_specific_handler, so the filtering is done in a C++-like manner
-//!   instead of in the personality function itself. Note that the specific
-//!   syntax for this (found in the rust_try_msvc_64.ll) is taken from an LLVM
-//!   test case for SEH.
-//! * We've got some data to transmit across the unwinding boundary,
-//!   specifically a `Box<Any + Send + 'static>`. In Dwarf-based unwinding this
-//!   data is part of the payload of the exception, but I have not currently
-//!   figured out how to do this with LLVM's bindings. Judging by some comments
-//!   in the LLVM test cases this may not even be possible currently with LLVM,
-//!   so this is just abandoned entirely. Instead the data is stored in a
-//!   thread-local in `panic` and retrieved during `cleanup`.
-//!
-//! So given all that, the bindings here are pretty small,
-
-#![allow(bad_style)]
-
-use prelude::v1::*;
-
-use any::Any;
-use libc::{c_ulong, DWORD, c_void};
-use ptr;
-use sys_common::thread_local::StaticKey;
-
-//                        0x R U S T
-const RUST_PANIC: DWORD = 0x52555354;
-static PANIC_DATA: StaticKey = StaticKey::new(None);
-
-// This function is provided by kernel32.dll
-extern "system" {
-    fn RaiseException(dwExceptionCode: DWORD,
-                      dwExceptionFlags: DWORD,
-                      nNumberOfArguments: DWORD,
-                      lpArguments: *const c_ulong);
-}
-
-#[repr(C)]
-pub struct EXCEPTION_POINTERS {
-    ExceptionRecord: *mut EXCEPTION_RECORD,
-    ContextRecord: *mut CONTEXT,
-}
-
-enum CONTEXT {}
-
-#[repr(C)]
-struct EXCEPTION_RECORD {
-    ExceptionCode: DWORD,
-    ExceptionFlags: DWORD,
-    ExceptionRecord: *mut _EXCEPTION_RECORD,
-    ExceptionAddress: *mut c_void,
-    NumberParameters: DWORD,
-    ExceptionInformation: [*mut c_ulong; EXCEPTION_MAXIMUM_PARAMETERS],
-}
-
-enum _EXCEPTION_RECORD {}
-
-const EXCEPTION_MAXIMUM_PARAMETERS: usize = 15;
-
-pub unsafe fn panic(data: Box<Any + Send + 'static>) -> ! {
-    // See module docs above for an explanation of why `data` is stored in a
-    // thread local instead of being passed as an argument to the
-    // `RaiseException` function (which can in theory carry along arbitrary
-    // data).
-    let exception = Box::new(data);
-    rtassert!(PANIC_DATA.get().is_null());
-    PANIC_DATA.set(Box::into_raw(exception) as *mut u8);
-
-    RaiseException(RUST_PANIC, 0, 0, ptr::null());
-    rtabort!("could not unwind stack");
-}
-
-pub unsafe fn cleanup(ptr: *mut u8) -> Box<Any + Send + 'static> {
-    // The `ptr` here actually corresponds to the code of the exception, and our
-    // real data is stored in our thread local.
-    rtassert!(ptr as DWORD == RUST_PANIC);
-
-    let data = PANIC_DATA.get() as *mut Box<Any + Send + 'static>;
-    PANIC_DATA.set(ptr::null_mut());
-    rtassert!(!data.is_null());
-
-    *Box::from_raw(data)
-}
-
-// This is required by the compiler to exist (e.g. it's a lang item), but it's
-// never actually called by the compiler because __C_specific_handler is the
-// personality function that is always used. Hence this is just an aborting
-// stub.
-#[lang = "eh_personality"]
-fn rust_eh_personality() {
-    unsafe { ::intrinsics::abort() }
-}
-
-// This is a function referenced from `rust_try_msvc_64.ll` which is used to
-// filter the exceptions being caught by that function.
-//
-// In theory local variables can be accessed through the `rbp` parameter of this
-// function, but a comment in an LLVM test case indicates that this is not
-// implemented in LLVM, so this is just an idempotent function which doesn't
-// ferry along any other information.
-//
-// This function just takes a look at the current EXCEPTION_RECORD being thrown
-// to ensure that it's code is RUST_PANIC, which was set by the call to
-// `RaiseException` above in the `panic` function.
-#[no_mangle]
-#[lang = "msvc_try_filter"]
-pub extern fn __rust_try_filter(eh_ptrs: *mut EXCEPTION_POINTERS,
-                                _rbp: *mut u8) -> i32 {
-    unsafe {
-        ((*(*eh_ptrs).ExceptionRecord).ExceptionCode == RUST_PANIC) as i32
-    }
-}
diff --git a/src/libstd/rt/unwind/seh64_gnu.rs b/src/libstd/rt/unwind/seh64_gnu.rs
deleted file mode 100644
index 78f969bfbeb..00000000000
--- a/src/libstd/rt/unwind/seh64_gnu.rs
+++ /dev/null
@@ -1,226 +0,0 @@
-// Copyright 2015 The Rust Project Developers. See the COPYRIGHT
-// file at the top-level directory of this distribution and at
-// http://rust-lang.org/COPYRIGHT.
-//
-// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
-// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
-// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
-// option. This file may not be copied, modified, or distributed
-// except according to those terms.
-
-//! Unwinding implementation of top of native Win64 SEH,
-//! however the unwind handler data (aka LSDA) uses GCC-compatible encoding.
-
-#![allow(bad_style)]
-#![allow(private_no_mangle_fns)]
-
-use prelude::v1::*;
-
-use any::Any;
-use self::EXCEPTION_DISPOSITION::*;
-use rt::dwarf::eh;
-use core::mem;
-use core::ptr;
-use libc::{c_void, c_ulonglong, DWORD, LPVOID};
-type ULONG_PTR = c_ulonglong;
-
-// Define our exception codes:
-// according to http://msdn.microsoft.com/en-us/library/het71c37(v=VS.80).aspx,
-//    [31:30] = 3 (error), 2 (warning), 1 (info), 0 (success)
-//    [29]    = 1 (user-defined)
-//    [28]    = 0 (reserved)
-// we define bits:
-//    [24:27] = type
-//    [0:23]  = magic
-const ETYPE: DWORD = 0b1110_u32 << 28;
-const MAGIC: DWORD = 0x525354; // "RST"
-
-const RUST_PANIC: DWORD  = ETYPE | (1 << 24) | MAGIC;
-
-const EXCEPTION_NONCONTINUABLE: DWORD = 0x1;   // Noncontinuable exception
-const EXCEPTION_UNWINDING: DWORD = 0x2;        // Unwind is in progress
-const EXCEPTION_EXIT_UNWIND: DWORD = 0x4;      // Exit unwind is in progress
-const EXCEPTION_STACK_INVALID: DWORD = 0x8;    // Stack out of limits or unaligned
-const EXCEPTION_NESTED_CALL: DWORD = 0x10;     // Nested exception handler call
-const EXCEPTION_TARGET_UNWIND: DWORD = 0x20;   // Target unwind in progress
-const EXCEPTION_COLLIDED_UNWIND: DWORD = 0x40; // Collided exception handler call
-const EXCEPTION_UNWIND: DWORD = EXCEPTION_UNWINDING |
-                                EXCEPTION_EXIT_UNWIND |
-                                EXCEPTION_TARGET_UNWIND |
-                                EXCEPTION_COLLIDED_UNWIND;
-
-#[repr(C)]
-pub struct EXCEPTION_RECORD {
-    ExceptionCode: DWORD,
-    ExceptionFlags: DWORD,
-    ExceptionRecord: *const EXCEPTION_RECORD,
-    ExceptionAddress: LPVOID,
-    NumberParameters: DWORD,
-    ExceptionInformation: [ULONG_PTR; 15],
-}
-
-pub enum CONTEXT {}
-pub enum UNWIND_HISTORY_TABLE {}
-
-#[repr(C)]
-pub struct RUNTIME_FUNCTION {
-    BeginAddress: DWORD,
-    EndAddress: DWORD,
-    UnwindData: DWORD,
-}
-
-#[repr(C)]
-pub struct DISPATCHER_CONTEXT {
-    ControlPc: LPVOID,
-    ImageBase: LPVOID,
-    FunctionEntry: *const RUNTIME_FUNCTION,
-    EstablisherFrame: LPVOID,
-    TargetIp: LPVOID,
-    ContextRecord: *const CONTEXT,
-    LanguageHandler: LPVOID,
-    HandlerData: *const u8,
-    HistoryTable: *const UNWIND_HISTORY_TABLE,
-}
-
-#[repr(C)]
-#[derive(Copy, Clone)]
-pub enum EXCEPTION_DISPOSITION {
-    ExceptionContinueExecution,
-    ExceptionContinueSearch,
-    ExceptionNestedException,
-    ExceptionCollidedUnwind
-}
-
-// From kernel32.dll
-extern "system" {
-    fn RaiseException(dwExceptionCode: DWORD,
-                      dwExceptionFlags: DWORD,
-                      nNumberOfArguments: DWORD,
-                      lpArguments: *const ULONG_PTR);
-
-    fn RtlUnwindEx(TargetFrame: LPVOID,
-                   TargetIp: LPVOID,
-                   ExceptionRecord: *const EXCEPTION_RECORD,
-                   ReturnValue: LPVOID,
-                   OriginalContext: *const CONTEXT,
-                   HistoryTable: *const UNWIND_HISTORY_TABLE);
-}
-
-#[repr(C)]
-struct PanicData {
-    data: Box<Any + Send + 'static>
-}
-
-pub unsafe fn panic(data: Box<Any + Send + 'static>) -> ! {
-    let panic_ctx = Box::new(PanicData { data: data });
-    let params = [Box::into_raw(panic_ctx) as ULONG_PTR];
-    rtdebug!("panic: ctx={:X}", params[0]);
-    RaiseException(RUST_PANIC,
-                   EXCEPTION_NONCONTINUABLE,
-                   params.len() as DWORD,
-                   &params as *const ULONG_PTR);
-    rtabort!("could not unwind stack");
-}
-
-pub unsafe fn cleanup(ptr: *mut u8) -> Box<Any + Send + 'static> {
-    rtdebug!("cleanup: ctx={:X}", ptr as usize);
-    let panic_ctx = Box::from_raw(ptr as *mut PanicData);
-    return panic_ctx.data;
-}
-
-// SEH doesn't support resuming unwinds after calling a landing pad like
-// libunwind does. For this reason, MSVC compiler outlines landing pads into
-// separate functions that can be called directly from the personality function
-// but are nevertheless able to find and modify stack frame of the "parent"
-// function.
-//
-// Since this cannot be done with libdwarf-style landing pads,
-// rust_eh_personality instead catches RUST_PANICs, runs the landing pad, then
-// reraises the exception.
-//
-// Note that it makes certain assumptions about the exception:
-//
-// 1. That RUST_PANIC is non-continuable, so no lower stack frame may choose to
-//    resume execution.
-// 2. That the first parameter of the exception is a pointer to an extra data
-//    area (PanicData).
-// Since these assumptions do not generally hold true for foreign exceptions
-// (system faults, C++ exceptions, etc), we make no attempt to invoke our
-// landing pads (and, thus, destructors!) for anything other than RUST_PANICs.
-// This is considered acceptable, because the behavior of throwing exceptions
-// through a C ABI boundary is undefined.
-
-#[lang = "eh_personality_catch"]
-#[cfg(not(test))]
-unsafe extern fn rust_eh_personality_catch(
-    exceptionRecord: *mut EXCEPTION_RECORD,
-    establisherFrame: LPVOID,
-    contextRecord: *mut CONTEXT,
-    dispatcherContext: *mut DISPATCHER_CONTEXT
-) -> EXCEPTION_DISPOSITION
-{
-    rust_eh_personality(exceptionRecord, establisherFrame,
-                        contextRecord, dispatcherContext)
-}
-
-#[lang = "eh_personality"]
-#[cfg(not(test))]
-unsafe extern fn rust_eh_personality(
-    exceptionRecord: *mut EXCEPTION_RECORD,
-    establisherFrame: LPVOID,
-    contextRecord: *mut CONTEXT,
-    dispatcherContext: *mut DISPATCHER_CONTEXT
-) -> EXCEPTION_DISPOSITION
-{
-    let er = &*exceptionRecord;
-    let dc = &*dispatcherContext;
-    rtdebug!("rust_eh_personality: code={:X}, flags={:X}, frame={:X}, ip={:X}",
-        er.ExceptionCode, er.ExceptionFlags,
-        establisherFrame as usize, dc.ControlPc as usize);
-
-    if er.ExceptionFlags & EXCEPTION_UNWIND == 0 { // we are in the dispatch phase
-        if er.ExceptionCode == RUST_PANIC {
-            if let Some(lpad) = find_landing_pad(dc) {
-                rtdebug!("unwinding to landing pad {:X}", lpad);
-
-                RtlUnwindEx(establisherFrame,
-                            lpad as LPVOID,
-                            exceptionRecord,
-                            er.ExceptionInformation[0] as LPVOID, // pointer to PanicData
-                            contextRecord,
-                            dc.HistoryTable);
-                rtabort!("could not unwind");
-            }
-        }
-    }
-    ExceptionContinueSearch
-}
-
-// The `resume` instruction, found at the end of the landing pads, and whose job
-// is to resume stack unwinding, is typically lowered by LLVM into a call to
-// `_Unwind_Resume` routine.  To avoid confusion with the same symbol exported
-// from libgcc, we redirect it to `rust_eh_unwind_resume`.
-// Since resolution of this symbol is done by the linker, `rust_eh_unwind_resume`
-// must be marked `pub` + `#[no_mangle]`.  (Can we make it a lang item?)
-
-#[lang = "eh_unwind_resume"]
-#[cfg(not(test))]
-unsafe extern fn rust_eh_unwind_resume(panic_ctx: LPVOID) {
-    rtdebug!("rust_eh_unwind_resume: ctx={:X}", panic_ctx as usize);
-    let params = [panic_ctx as ULONG_PTR];
-    RaiseException(RUST_PANIC,
-                   EXCEPTION_NONCONTINUABLE,
-                   params.len() as DWORD,
-                   &params as *const ULONG_PTR);
-    rtabort!("could not resume unwind");
-}
-
-unsafe fn find_landing_pad(dc: &DISPATCHER_CONTEXT) -> Option<usize> {
-    let eh_ctx = eh::EHContext {
-        ip: dc.ControlPc as usize,
-        func_start: dc.ImageBase as usize + (*dc.FunctionEntry).BeginAddress as usize,
-        text_start: dc.ImageBase as usize,
-        data_start: 0
-    };
-    eh::find_landing_pad(dc.HandlerData, &eh_ctx)
-}