Remove unnecessary unwind messages
Now that the type_id intrinsic is working across crates, all of these unnecessary messages can be removed to have the failure type for a task truly be ~Any and only ~Any
This commit is contained in:
parent
61637439dc
commit
b00449380f
5 changed files with 41 additions and 76 deletions
|
@ -20,7 +20,6 @@ use util::Void;
|
|||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
// TypeId
|
||||
// FIXME: #9913 - Needs proper intrinsic support to work reliably cross crate
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
/// `TypeId` represents a globally unique identifier for a type
|
||||
|
@ -199,8 +198,10 @@ mod tests {
|
|||
|
||||
#[test]
|
||||
fn type_id() {
|
||||
let (a, b, c) = (TypeId::of::<uint>(), TypeId::of::<&str>(), TypeId::of::<Test>());
|
||||
let (d, e, f) = (TypeId::of::<uint>(), TypeId::of::<&str>(), TypeId::of::<Test>());
|
||||
let (a, b, c) = (TypeId::of::<uint>(), TypeId::of::<&'static str>(),
|
||||
TypeId::of::<Test>());
|
||||
let (d, e, f) = (TypeId::of::<uint>(), TypeId::of::<&'static str>(),
|
||||
TypeId::of::<Test>());
|
||||
|
||||
assert!(a != b);
|
||||
assert!(a != c);
|
||||
|
|
|
@ -155,9 +155,9 @@ use cell::Cell;
|
|||
use option::{Option, Some, None};
|
||||
use prelude::*;
|
||||
use rt::task::Task;
|
||||
use rt::task::UnwindMessageLinked;
|
||||
use rt::task::{UnwindResult, Failure};
|
||||
use task::spawn::Taskgroup;
|
||||
use task::LinkedFailure;
|
||||
use to_bytes::IterBytes;
|
||||
use unstable::atomics::{AtomicUint, Relaxed};
|
||||
use unstable::sync::{UnsafeArc, UnsafeArcSelf, UnsafeArcT, LittleLock};
|
||||
|
@ -597,7 +597,7 @@ impl Death {
|
|||
}
|
||||
|
||||
if !success {
|
||||
result = Cell::new(Failure(UnwindMessageLinked));
|
||||
result = Cell::new(Failure(~LinkedFailure as ~Any));
|
||||
}
|
||||
}
|
||||
on_exit(result.take());
|
||||
|
|
|
@ -36,6 +36,7 @@ use rt::logging::StdErrLogger;
|
|||
use rt::sched::{Scheduler, SchedHandle};
|
||||
use rt::stack::{StackSegment, StackPool};
|
||||
use send_str::SendStr;
|
||||
use task::LinkedFailure;
|
||||
use task::spawn::Taskgroup;
|
||||
use unstable::finally::Finally;
|
||||
|
||||
|
@ -95,8 +96,8 @@ pub enum UnwindResult {
|
|||
/// The task is ending successfully
|
||||
Success,
|
||||
|
||||
/// The Task is failing with reason `UnwindMessage`
|
||||
Failure(UnwindMessage),
|
||||
/// The Task is failing with reason `~Any`
|
||||
Failure(~Any),
|
||||
}
|
||||
|
||||
impl UnwindResult {
|
||||
|
@ -119,27 +120,9 @@ impl UnwindResult {
|
|||
}
|
||||
}
|
||||
|
||||
/// Represents the cause of a task failure
|
||||
#[deriving(ToStr)]
|
||||
pub enum UnwindMessage {
|
||||
// FIXME: #9913 - This variant is not neccessary once Any works properly
|
||||
/// Failed with a static string message
|
||||
UnwindMessageStrStatic(&'static str),
|
||||
|
||||
// FIXME: #9913 - This variant is not neccessary once Any works properly
|
||||
/// Failed with a owned string message
|
||||
UnwindMessageStrOwned(~str),
|
||||
|
||||
/// Failed with an `~Any`
|
||||
UnwindMessageAny(~Any),
|
||||
|
||||
/// Failed because of linked failure
|
||||
UnwindMessageLinked
|
||||
}
|
||||
|
||||
pub struct Unwinder {
|
||||
unwinding: bool,
|
||||
cause: Option<UnwindMessage>
|
||||
cause: Option<~Any>
|
||||
}
|
||||
|
||||
impl Unwinder {
|
||||
|
@ -532,7 +515,7 @@ impl Unwinder {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn begin_unwind(&mut self, cause: UnwindMessage) -> ! {
|
||||
pub fn begin_unwind(&mut self, cause: ~Any) -> ! {
|
||||
#[fixed_stack_segment]; #[inline(never)];
|
||||
|
||||
self.unwinding = true;
|
||||
|
@ -648,46 +631,34 @@ pub fn begin_unwind_raw(msg: *c_char, file: *c_char, line: size_t) -> ! {
|
|||
|
||||
/// This is the entry point of unwinding for fail!() and assert!().
|
||||
pub fn begin_unwind<M: Any + Send>(msg: M, file: &'static str, line: uint) -> ! {
|
||||
// Wrap the fail message in a `Any` box for uniform representation.
|
||||
let any = ~msg as ~Any;
|
||||
|
||||
// FIXME: #9913 - This can be changed to be internal to begin_unwind_internal
|
||||
// once Any works properly.
|
||||
// As a workaround, string types need to be special cased right now
|
||||
// because `Any` does not support dynamically querying whether the
|
||||
// type implements a trait yet, so without requiring that every `Any`
|
||||
// also implements `ToStr` there is no way to get a failure message
|
||||
// out of it again during unwinding.
|
||||
let msg = if any.is::<&'static str>() {
|
||||
UnwindMessageStrStatic(*any.move::<&'static str>().unwrap())
|
||||
} else if any.is::<~str>() {
|
||||
UnwindMessageStrOwned(*any.move::<~str>().unwrap())
|
||||
} else {
|
||||
UnwindMessageAny(any)
|
||||
};
|
||||
|
||||
begin_unwind_internal(msg, file, line)
|
||||
}
|
||||
|
||||
fn begin_unwind_internal(msg: UnwindMessage, file: &'static str, line: uint) -> ! {
|
||||
use any::AnyRefExt;
|
||||
use rt::in_green_task_context;
|
||||
use rt::task::Task;
|
||||
use rt::local::Local;
|
||||
use rt::task::Task;
|
||||
use str::Str;
|
||||
use unstable::intrinsics;
|
||||
|
||||
unsafe {
|
||||
// Be careful not to allocate in this block, if we're failing we may
|
||||
// have been failing due to a lack of memory in the first place...
|
||||
|
||||
let task: *mut Task;
|
||||
// Note that this should be the only allocation performed in this block.
|
||||
// Currently this means that fail!() on OOM will invoke this code path,
|
||||
// but then again we're not really ready for failing on OOM anyway. If
|
||||
// we do start doing this, then we should propagate this allocation to
|
||||
// be performed in the parent of this task instead of the task that's
|
||||
// failing.
|
||||
let msg = ~msg as ~Any;
|
||||
|
||||
{
|
||||
let msg_s = match msg {
|
||||
UnwindMessageAny(_) => "~Any",
|
||||
UnwindMessageLinked => "linked failure",
|
||||
UnwindMessageStrOwned(ref s) => s.as_slice(),
|
||||
UnwindMessageStrStatic(ref s) => s.as_slice(),
|
||||
//let msg: &Any = msg;
|
||||
let msg_s = match msg.as_ref::<&'static str>() {
|
||||
Some(s) => *s,
|
||||
None => match msg.as_ref::<~str>() {
|
||||
Some(s) => s.as_slice(),
|
||||
None => match msg.as_ref::<LinkedFailure>() {
|
||||
Some(*) => "linked failure",
|
||||
None => "~Any",
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
if !in_green_task_context() {
|
||||
|
|
|
@ -60,8 +60,6 @@ use comm::{stream, Chan, GenericChan, GenericPort, Port, Peekable};
|
|||
use result::{Result, Ok, Err};
|
||||
use rt::in_green_task_context;
|
||||
use rt::local::Local;
|
||||
use rt::task::{UnwindMessageAny, UnwindMessageLinked};
|
||||
use rt::task::{UnwindMessageStrStatic, UnwindMessageStrOwned};
|
||||
use rt::task::{UnwindResult, Success, Failure};
|
||||
use send_str::{SendStr, IntoSendStr};
|
||||
use unstable::finally::Finally;
|
||||
|
@ -90,30 +88,25 @@ pub type TaskResult = Result<(), ~Any>;
|
|||
|
||||
pub struct LinkedFailure;
|
||||
|
||||
#[inline]
|
||||
fn wrap_as_any(res: UnwindResult) -> TaskResult {
|
||||
match res {
|
||||
Success => Ok(()),
|
||||
Failure(UnwindMessageAny(a)) => Err(a),
|
||||
Failure(UnwindMessageLinked) => Err(~LinkedFailure as ~Any),
|
||||
Failure(UnwindMessageStrOwned(s)) => Err(~s as ~Any),
|
||||
Failure(UnwindMessageStrStatic(s)) => Err(~s as ~Any),
|
||||
}
|
||||
}
|
||||
|
||||
pub struct TaskResultPort {
|
||||
priv port: Port<UnwindResult>
|
||||
}
|
||||
|
||||
fn to_task_result(res: UnwindResult) -> TaskResult {
|
||||
match res {
|
||||
Success => Ok(()), Failure(a) => Err(a),
|
||||
}
|
||||
}
|
||||
|
||||
impl GenericPort<TaskResult> for TaskResultPort {
|
||||
#[inline]
|
||||
fn recv(&self) -> TaskResult {
|
||||
wrap_as_any(self.port.recv())
|
||||
to_task_result(self.port.recv())
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn try_recv(&self) -> Option<TaskResult> {
|
||||
self.port.try_recv().map(wrap_as_any)
|
||||
self.port.try_recv().map(to_task_result)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -83,11 +83,11 @@ use local_data;
|
|||
use rt::local::Local;
|
||||
use rt::sched::{Scheduler, Shutdown, TaskFromFriend};
|
||||
use rt::task::{Task, Sched};
|
||||
use rt::task::{UnwindMessageLinked, UnwindMessageStrStatic};
|
||||
use rt::task::{UnwindResult, Success, Failure};
|
||||
use rt::thread::Thread;
|
||||
use rt::work_queue::WorkQueue;
|
||||
use rt::{in_green_task_context, new_event_loop, KillHandle};
|
||||
use task::LinkedFailure;
|
||||
use task::SingleThreaded;
|
||||
use task::TaskOpts;
|
||||
use task::unkillable;
|
||||
|
@ -324,7 +324,7 @@ impl Drop for Taskgroup {
|
|||
do RuntimeGlue::with_task_handle_and_failing |me, failing| {
|
||||
if failing {
|
||||
for x in self.notifier.mut_iter() {
|
||||
x.task_result = Some(Failure(UnwindMessageLinked));
|
||||
x.task_result = Some(Failure(~LinkedFailure as ~Any));
|
||||
}
|
||||
// Take everybody down with us. After this point, every
|
||||
// other task in the group will see 'tg' as none, which
|
||||
|
@ -379,7 +379,7 @@ impl AutoNotify {
|
|||
notify_chan: chan,
|
||||
|
||||
// Un-set above when taskgroup successfully made.
|
||||
task_result: Some(Failure(UnwindMessageStrStatic("AutoNotify::new()")))
|
||||
task_result: Some(Failure(~("AutoNotify::new()") as ~Any))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue