diff options
| author | Alex Crichton <alex@alexcrichton.com> | 2016-03-07 09:20:25 -0800 |
|---|---|---|
| committer | Alex Crichton <alex@alexcrichton.com> | 2016-03-07 11:02:43 -0800 |
| commit | ec58f40463e3c12208376c89459975974633382c (patch) | |
| tree | 88f82c1cc80ac25352ea61d904092d3d3614614c /src/libstd | |
| parent | 72d588a62044b9fae0e5baaba21aa9166b6db9c5 (diff) | |
| download | rust-ec58f40463e3c12208376c89459975974633382c.tar.gz rust-ec58f40463e3c12208376c89459975974633382c.zip | |
std: Add impl of FnOnce to AssertRecoverSafe
This was originally intended, but forgot to land by accident! cc #27719
Diffstat (limited to 'src/libstd')
| -rw-r--r-- | src/libstd/lib.rs | 1 | ||||
| -rw-r--r-- | src/libstd/panic.rs | 36 |
2 files changed, 36 insertions, 1 deletions
diff --git a/src/libstd/lib.rs b/src/libstd/lib.rs index fa07b0f761b..e97b015283b 100644 --- a/src/libstd/lib.rs +++ b/src/libstd/lib.rs @@ -230,6 +230,7 @@ #![feature(float_extras)] #![feature(float_from_str_radix)] #![feature(fnbox)] +#![feature(fn_traits)] #![feature(heap_api)] #![feature(hashmap_hasher)] #![feature(inclusive_range)] diff --git a/src/libstd/panic.rs b/src/libstd/panic.rs index 69a1b57a0c5..5c2e36623cb 100644 --- a/src/libstd/panic.rs +++ b/src/libstd/panic.rs @@ -129,6 +129,9 @@ pub trait RefRecoverSafe {} /// /// # Examples /// +/// One way to use `AssertRecoverSafe` is to assert that the entire closure +/// itself is recover safe, bypassing all checks for all variables: +/// /// ``` /// #![feature(recover, std_panic)] /// @@ -144,10 +147,33 @@ pub trait RefRecoverSafe {} /// // }); /// /// // This, however, will compile due to the `AssertRecoverSafe` wrapper +/// let result = panic::recover(AssertRecoverSafe::new(|| { +/// variable += 3; +/// })); +/// // ... +/// ``` +/// +/// Wrapping the entire closure amounts to a blanket assertion that all captured +/// variables are recover safe. This has the downside that if new captures are +/// added in the future, they will also be considered recover safe. Therefore, +/// you may prefer to just wrap individual captures, as shown below. This is +/// more annotation, but it ensures that if a new capture is added which is not +/// recover safe, you will get a compilation error at that time, which will +/// allow you to consider whether that new capture in fact represent a bug or +/// not. +/// +/// ``` +/// #![feature(recover, std_panic)] +/// +/// use std::panic::{self, AssertRecoverSafe}; +/// +/// let mut variable = 4; +/// let other_capture = 3; +/// /// let result = { /// let mut wrapper = AssertRecoverSafe::new(&mut variable); /// panic::recover(move || { -/// **wrapper += 3; +/// **wrapper += other_capture; /// }) /// }; /// // ... @@ -215,6 +241,14 @@ impl<T> DerefMut for AssertRecoverSafe<T> { } } +impl<R, F: FnOnce() -> R> FnOnce<()> for AssertRecoverSafe<F> { + type Output = R; + + extern "rust-call" fn call_once(self, _args: ()) -> R { + (self.0)() + } +} + /// Invokes a closure, capturing the cause of panic if one occurs. /// /// This function will return `Ok` with the closure's result if the closure |
