about summary refs log tree commit diff
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2015-12-11 02:44:21 +0000
committerbors <bors@rust-lang.org>2015-12-11 02:44:21 +0000
commitae5d09551e8a0777999aadb1aa804e43aeab0ff2 (patch)
treed85b21c824df99c7129b64e3b829f51acbd497de
parent7ce713961cb7c36bb66db70a276973eb78cf9e6e (diff)
parent58c099770f091c221b5a04919f2e719d4d7d5f1a (diff)
downloadrust-ae5d09551e8a0777999aadb1aa804e43aeab0ff2.tar.gz
rust-ae5d09551e8a0777999aadb1aa804e43aeab0ff2.zip
Auto merge of #30307 - pnkfelix:fix-issue-26656, r=alexcrichton
Long awaited regression test for dropck on trait object method.

Fix #26656.
-rw-r--r--src/test/compile-fail/issue-26656.rs52
1 files changed, 52 insertions, 0 deletions
diff --git a/src/test/compile-fail/issue-26656.rs b/src/test/compile-fail/issue-26656.rs
new file mode 100644
index 00000000000..e5fa65498de
--- /dev/null
+++ b/src/test/compile-fail/issue-26656.rs
@@ -0,0 +1,52 @@
+// 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.
+
+// Issue #26656: Verify that trait objects cannot bypass dropck.
+
+// Using this instead of Fn etc. to take HRTB out of the equation.
+trait Trigger<B> { fn fire(&self, b: &mut B); }
+impl<B: Button> Trigger<B> for () {
+    fn fire(&self, b: &mut B) {
+        b.push();
+    }
+}
+
+// Still unsound Zook
+trait Button { fn push(&self); }
+struct Zook<B> { button: B, trigger: Box<Trigger<B>+'static> }
+
+impl<B> Drop for Zook<B> {
+    fn drop(&mut self) {
+        self.trigger.fire(&mut self.button);
+    }
+}
+
+// AND
+struct Bomb { usable: bool }
+impl Drop for Bomb { fn drop(&mut self) { self.usable = false; } }
+impl Bomb { fn activate(&self) { assert!(self.usable) } }
+
+enum B<'a> { HarmlessButton, BigRedButton(&'a Bomb) }
+impl<'a> Button for B<'a> {
+    fn push(&self) {
+        if let B::BigRedButton(borrowed) = *self {
+            borrowed.activate();
+        }
+    }
+}
+
+fn main() {
+    let (mut zook, ticking);
+    zook = Zook { button: B::HarmlessButton,
+                  trigger: Box::new(()) };
+    ticking = Bomb { usable: true };
+    zook.button = B::BigRedButton(&ticking);
+    //~^ ERROR `ticking` does not live long enough
+}