diff options
| author | Eduard Burtescu <edy.burt@gmail.com> | 2016-05-05 08:11:28 +0300 |
|---|---|---|
| committer | Eduard Burtescu <edy.burt@gmail.com> | 2016-05-07 19:14:33 +0300 |
| commit | ed66fe48e94df2cd0dee5af4afa44d7fb50cb0cf (patch) | |
| tree | 0a875e37191033361b5c3a04aa8494551157922a /src | |
| parent | 4f5900aefac42cec488a68c041ecd538c04b84fd (diff) | |
| download | rust-ed66fe48e94df2cd0dee5af4afa44d7fb50cb0cf.tar.gz rust-ed66fe48e94df2cd0dee5af4afa44d7fb50cb0cf.zip | |
Implement RFC 1440 "Allow Drop types in statics/const functions".
Diffstat (limited to 'src')
| -rw-r--r-- | src/librustc_mir/diagnostics.rs | 2 | ||||
| -rw-r--r-- | src/librustc_mir/transform/qualify_consts.rs | 37 | ||||
| -rw-r--r-- | src/libsyntax/feature_gate.rs | 5 | ||||
| -rw-r--r-- | src/test/compile-fail/check-static-values-constraints.rs | 26 | ||||
| -rw-r--r-- | src/test/compile-fail/issue-9243.rs | 5 | ||||
| -rw-r--r-- | src/test/compile-fail/static-mut-not-constant.rs | 2 |
6 files changed, 54 insertions, 23 deletions
diff --git a/src/librustc_mir/diagnostics.rs b/src/librustc_mir/diagnostics.rs index 30d3a39e473..65d51d20528 100644 --- a/src/librustc_mir/diagnostics.rs +++ b/src/librustc_mir/diagnostics.rs @@ -345,7 +345,7 @@ impl Drop for Foo { const F : Foo = Foo { a : 0 }; // error: constants are not allowed to have destructors static S : Foo = Foo { a : 0 }; -// error: statics are not allowed to have destructors +// error: destructors in statics are an unstable feature ``` To solve this issue, please use a type which does allow the usage of type with diff --git a/src/librustc_mir/transform/qualify_consts.rs b/src/librustc_mir/transform/qualify_consts.rs index 7728d43774f..90823528973 100644 --- a/src/librustc_mir/transform/qualify_consts.rs +++ b/src/librustc_mir/transform/qualify_consts.rs @@ -222,13 +222,40 @@ impl<'a, 'tcx> Qualifier<'a, 'tcx> { } /// Check for NEEDS_DROP (from an ADT or const fn call) and - /// error, unless we're in a function. + /// error, unless we're in a function, or the feature-gate + /// for globals with destructors is enabled. fn deny_drop(&self) { - if self.mode != Mode::Fn && self.qualif.intersects(Qualif::NEEDS_DROP) { - span_err!(self.tcx.sess, self.span, E0493, - "{}s are not allowed to have destructors", - self.mode); + if self.mode == Mode::Fn || !self.qualif.intersects(Qualif::NEEDS_DROP) { + return; + } + + // Static and const fn's allow destructors, but they're feature-gated. + let msg = if self.mode != Mode::Const { + // Feature-gate for globals with destructors is enabled. + if self.tcx.sess.features.borrow().drop_types_in_const { + return; + } + + // This comes from a macro that has #[allow_internal_unstable]. + if self.tcx.sess.codemap().span_allows_unstable(self.span) { + return; + } + + format!("destructors in {}s are an unstable feature", + self.mode) + } else { + format!("{}s are not allowed to have destructors", + self.mode) + }; + + let mut err = + struct_span_err!(self.tcx.sess, self.span, E0493, "{}", msg); + if self.mode != Mode::Const { + help!(&mut err, + "in Nightly builds, add `#![feature(drop_types_in_const)]` \ + to the crate attributes to enable"); } + err.emit(); } /// Check if an Lvalue with the current qualifications could diff --git a/src/libsyntax/feature_gate.rs b/src/libsyntax/feature_gate.rs index e269475d1e2..7f01821b004 100644 --- a/src/libsyntax/feature_gate.rs +++ b/src/libsyntax/feature_gate.rs @@ -266,7 +266,10 @@ declare_features! ( (active, specialization, "1.7.0", Some(31844)), // pub(restricted) visibilities (RFC 1422) - (active, pub_restricted, "1.9.0", Some(32409)) + (active, pub_restricted, "1.9.0", Some(32409)), + + // Allow Drop types in statics/const functions (RFC 1440) + (active, drop_types_in_const, "1.9.0", Some(33156)) ); declare_features! ( diff --git a/src/test/compile-fail/check-static-values-constraints.rs b/src/test/compile-fail/check-static-values-constraints.rs index ded0d07d737..df22e2ea4de 100644 --- a/src/test/compile-fail/check-static-values-constraints.rs +++ b/src/test/compile-fail/check-static-values-constraints.rs @@ -37,7 +37,7 @@ static STATIC2: SafeEnum = SafeEnum::Variant2(0); // This one should fail static STATIC3: SafeEnum = SafeEnum::Variant3(WithDtor); -//~^ ERROR statics are not allowed to have destructors +//~^ ERROR destructors in statics are an unstable feature // This enum will be used to test that variants @@ -54,9 +54,9 @@ impl Drop for UnsafeEnum { static STATIC4: UnsafeEnum = UnsafeEnum::Variant5; -//~^ ERROR statics are not allowed to have destructors +//~^ ERROR destructors in statics are an unstable feature static STATIC5: UnsafeEnum = UnsafeEnum::Variant6(0); -//~^ ERROR statics are not allowed to have destructors +//~^ ERROR destructors in statics are an unstable feature struct SafeStruct { @@ -71,7 +71,7 @@ static STATIC6: SafeStruct = SafeStruct{field1: SafeEnum::Variant1, field2: Safe // field2 has an unsafe value, hence this should fail static STATIC7: SafeStruct = SafeStruct{field1: SafeEnum::Variant1, field2: SafeEnum::Variant3(WithDtor)}; -//~^ ERROR statics are not allowed to have destructors +//~^ ERROR destructors in statics are an unstable feature // Test variadic constructor for structs. The base struct should be examined // as well as every field present in the constructor. @@ -84,7 +84,7 @@ static STATIC8: SafeStruct = SafeStruct{field1: SafeEnum::Variant1, static STATIC9: SafeStruct = SafeStruct{field1: SafeEnum::Variant1, ..SafeStruct{field1: SafeEnum::Variant3(WithDtor), field2: SafeEnum::Variant1}}; -//~^^ ERROR statics are not allowed to have destructors +//~^^ ERROR destructors in statics are an unstable feature struct UnsafeStruct; @@ -94,7 +94,7 @@ impl Drop for UnsafeStruct { // Types with destructors are not allowed for statics static STATIC10: UnsafeStruct = UnsafeStruct; -//~^ ERROR statics are not allowed to have destructor +//~^ ERROR destructors in statics are an unstable feature struct MyOwned; @@ -105,19 +105,19 @@ static STATIC11: Box<MyOwned> = box MyOwned; // to have types with destructors // These should fail static mut STATIC12: UnsafeStruct = UnsafeStruct; -//~^ ERROR mutable statics are not allowed to have destructors -//~^^ ERROR statics are not allowed to have destructors +//~^ ERROR destructors in statics are an unstable feature +//~^^ ERROR destructors in statics are an unstable feature static mut STATIC13: SafeStruct = SafeStruct{field1: SafeEnum::Variant1, -//~^ ERROR mutable statics are not allowed to have destructors +//~^ ERROR destructors in statics are an unstable feature field2: SafeEnum::Variant3(WithDtor)}; -//~^ ERROR: statics are not allowed to have destructors +//~^ ERROR: destructors in statics are an unstable feature static mut STATIC14: SafeStruct = SafeStruct { -//~^ ERROR mutable statics are not allowed to have destructors +//~^ ERROR destructors in statics are an unstable feature field1: SafeEnum::Variant1, field2: SafeEnum::Variant4("str".to_string()) -//~^ ERROR method calls in statics are limited to constant inherent methods +//~^ ERROR calls in statics are limited to constant functions }; static STATIC15: &'static [Box<MyOwned>] = &[ @@ -131,7 +131,7 @@ static STATIC16: (&'static Box<MyOwned>, &'static Box<MyOwned>) = ( ); static mut STATIC17: SafeEnum = SafeEnum::Variant1; -//~^ ERROR mutable statics are not allowed to have destructors +//~^ ERROR destructors in statics are an unstable feature static STATIC19: Box<isize> = box 3; diff --git a/src/test/compile-fail/issue-9243.rs b/src/test/compile-fail/issue-9243.rs index 7424a45d044..58bdff6c041 100644 --- a/src/test/compile-fail/issue-9243.rs +++ b/src/test/compile-fail/issue-9243.rs @@ -10,11 +10,12 @@ // Regression test for issue 9243 -struct Test { +pub struct Test { mem: isize, } -pub static g_test: Test = Test {mem: 0}; //~ ERROR statics are not allowed to have destructors +pub static g_test: Test = Test {mem: 0}; +//~^ ERROR destructors in statics are an unstable feature impl Drop for Test { fn drop(&mut self) {} diff --git a/src/test/compile-fail/static-mut-not-constant.rs b/src/test/compile-fail/static-mut-not-constant.rs index e3bb01e6970..9b83c42609a 100644 --- a/src/test/compile-fail/static-mut-not-constant.rs +++ b/src/test/compile-fail/static-mut-not-constant.rs @@ -12,6 +12,6 @@ static mut a: Box<isize> = box 3; //~^ ERROR allocations are not allowed in statics -//~^^ ERROR mutable statics are not allowed to have boxes +//~^^ ERROR destructors in statics are an unstable feature fn main() {} |
