LLVM_VERSION=$($LLVM_CONFIG --version)
case $LLVM_VERSION in
- (3.[7-8]*)
+ (3.[7-9]*)
msg "found ok version of LLVM: $LLVM_VERSION"
;;
(*)
.TP
\fBRUST_TEST_THREADS\fR
The test framework Rust provides executes tests in parallel. This variable sets
-the maximum number of threads used for this purpose.
+the maximum number of threads used for this purpose. This setting is overridden
+by the --test-threads option.
.TP
\fBRUST_TEST_NOCAPTURE\fR
CFG_STATIC_LIB_NAME_i586-unknown-linux-gnu=lib$(1).a
CFG_LIB_GLOB_i586-unknown-linux-gnu=lib$(1)-*.so
CFG_LIB_DSYM_GLOB_i586-unknown-linux-gnu=lib$(1)-*.dylib.dSYM
-CFG_JEMALLOC_CFLAGS_i586-unknown-linux-gnu := -m32 $(CFLAGS) -march=pentium
-CFG_GCCISH_CFLAGS_i586-unknown-linux-gnu := -g -fPIC -m32 $(CFLAGS) -march=pentium
+CFG_JEMALLOC_CFLAGS_i586-unknown-linux-gnu := -m32 $(CFLAGS) -march=pentium -Wa,-mrelax-relocations=no
+CFG_GCCISH_CFLAGS_i586-unknown-linux-gnu := -g -fPIC -m32 $(CFLAGS) -march=pentium -Wa,-mrelax-relocations=no
CFG_GCCISH_CXXFLAGS_i586-unknown-linux-gnu := -fno-rtti $(CXXFLAGS) -march=pentium
CFG_GCCISH_LINK_FLAGS_i586-unknown-linux-gnu := -shared -fPIC -ldl -pthread -lrt -g -m32
CFG_GCCISH_DEF_FLAG_i586-unknown-linux-gnu := -Wl,--export-dynamic,--dynamic-list=
CFG_LIB_NAME_i686-unknown-linux-musl=lib$(1).so
CFG_STATIC_LIB_NAME_i686-unknown-linux-musl=lib$(1).a
CFG_LIB_GLOB_i686-unknown-linux-musl=lib$(1)-*.so
-CFG_JEMALLOC_CFLAGS_i686-unknown-linux-musl := -m32 -Wl,-melf_i386
-CFG_GCCISH_CFLAGS_i686-unknown-linux-musl := -g -fPIC -m32 -Wl,-melf_i386
+CFG_JEMALLOC_CFLAGS_i686-unknown-linux-musl := -m32 -Wl,-melf_i386 -Wa,-mrelax-relocations=no
+CFG_GCCISH_CFLAGS_i686-unknown-linux-musl := -g -fPIC -m32 -Wl,-melf_i386 -Wa,-mrelax-relocations=no
CFG_GCCISH_CXXFLAGS_i686-unknown-linux-musl :=
CFG_GCCISH_LINK_FLAGS_i686-unknown-linux-musl :=
CFG_GCCISH_DEF_FLAG_i686-unknown-linux-musl :=
// This is a hack, because newer binutils broke things on some vms/distros
// (i.e., linking against unknown relocs disabled by the following flag)
// See: https://github.com/rust-lang/rust/issues/34978
- if target == "x86_64-unknown-linux-musl" {
- base.push("-Wa,-mrelax-relocations=no".into());
+ match target {
+ "i586-unknown-linux-gnu" |
+ "i686-unknown-linux-musl" |
+ "x86_64-unknown-linux-musl" => {
+ base.push("-Wa,-mrelax-relocations=no".into());
+ },
+ _ => {},
}
return base
}
if target.contains("rumprun") ||
target.contains("bitrig") ||
target.contains("openbsd") ||
- target.contains("msvc") {
+ target.contains("msvc") ||
+ target.contains("emscripten") {
build.config.use_jemalloc = false;
}
to use it to find the extension in a file name.
```rust
-# fn find(_: &str, _: char) -> Option<usize> { None }
+# fn find(haystack: &str, needle: char) -> Option<usize> { haystack.find(needle) }
fn main() {
let file_name = "foobar.rs";
match find(file_name, '.') {
sense to put it into a function:
```rust
-# fn find(_: &str, _: char) -> Option<usize> { None }
+# fn find(haystack: &str, needle: char) -> Option<usize> { haystack.find(needle) }
// Returns the extension of the given file name, where the extension is defined
// as all characters following the first `.`.
// If `file_name` has no `.`, then `None` is returned.
to get rid of the case analysis:
```rust
-# fn find(_: &str, _: char) -> Option<usize> { None }
+# fn find(haystack: &str, needle: char) -> Option<usize> { haystack.find(needle) }
// Returns the extension of the given file name, where the extension is defined
// as all characters following the first `.`.
// If `file_name` has no `.`, then `None` is returned.
self.vec.set_len(len + amt);
}
- /// Inserts a string into this `String` at a byte position.
+ /// Inserts a string slice into this `String` at a byte position.
///
/// This is an `O(n)` operation as it requires copying every element in the
/// buffer.
reason = "recent addition",
issue = "35553")]
pub fn insert_str(&mut self, idx: usize, string: &str) {
- let len = self.len();
- assert!(idx <= len);
+ assert!(idx <= self.len());
assert!(self.is_char_boundary(idx));
unsafe {
#[inline]
fn into_iter(mut self) -> IntoIter<T> {
unsafe {
- let ptr = self.as_mut_ptr();
- assume(!ptr.is_null());
- let begin = ptr as *const T;
+ let begin = self.as_mut_ptr();
+ assume(!begin.is_null());
let end = if mem::size_of::<T>() == 0 {
- arith_offset(ptr as *const i8, self.len() as isize) as *const T
+ arith_offset(begin as *const i8, self.len() as isize) as *const T
} else {
- ptr.offset(self.len() as isize) as *const T
+ begin.offset(self.len() as isize) as *const T
};
let buf = ptr::read(&self.buf);
mem::forget(self);
#[stable(feature = "rust1", since = "1.0.0")]
pub struct IntoIter<T> {
_buf: RawVec<T>,
- ptr: *const T,
+ ptr: *mut T,
end: *const T,
}
+impl<T> IntoIter<T> {
+ /// Returns the remaining items of this iterator as a slice.
+ ///
+ /// # Examples
+ ///
+ /// ```rust
+ /// # #![feature(vec_into_iter_as_slice)]
+ /// let vec = vec!['a', 'b', 'c'];
+ /// let mut into_iter = vec.into_iter();
+ /// assert_eq!(into_iter.as_slice(), &['a', 'b', 'c']);
+ /// let _ = into_iter.next().unwrap();
+ /// assert_eq!(into_iter.as_slice(), &['b', 'c']);
+ /// ```
+ #[unstable(feature = "vec_into_iter_as_slice", issue = "35601")]
+ pub fn as_slice(&self) -> &[T] {
+ unsafe {
+ slice::from_raw_parts(self.ptr, self.len())
+ }
+ }
+
+ /// Returns the remaining items of this iterator as a mutable slice.
+ ///
+ /// # Examples
+ ///
+ /// ```rust
+ /// # #![feature(vec_into_iter_as_slice)]
+ /// let vec = vec!['a', 'b', 'c'];
+ /// let mut into_iter = vec.into_iter();
+ /// assert_eq!(into_iter.as_slice(), &['a', 'b', 'c']);
+ /// into_iter.as_mut_slice()[2] = 'z';
+ /// assert_eq!(into_iter.next().unwrap(), 'a');
+ /// assert_eq!(into_iter.next().unwrap(), 'b');
+ /// assert_eq!(into_iter.next().unwrap(), 'z');
+ /// ```
+ #[unstable(feature = "vec_into_iter_as_slice", issue = "35601")]
+ pub fn as_mut_slice(&self) -> &mut [T] {
+ unsafe {
+ slice::from_raw_parts_mut(self.ptr, self.len())
+ }
+ }
+}
+
#[stable(feature = "rust1", since = "1.0.0")]
unsafe impl<T: Send> Send for IntoIter<T> {}
#[stable(feature = "rust1", since = "1.0.0")]
#[inline]
fn next(&mut self) -> Option<T> {
unsafe {
- if self.ptr == self.end {
+ if self.ptr as *const _ == self.end {
None
} else {
if mem::size_of::<T>() == 0 {
// purposefully don't use 'ptr.offset' because for
// vectors with 0-size elements this would return the
// same pointer.
- self.ptr = arith_offset(self.ptr as *const i8, 1) as *const T;
+ self.ptr = arith_offset(self.ptr as *const i8, 1) as *mut T;
// Use a non-null pointer value
Some(ptr::read(EMPTY as *mut T))
} else {
if mem::size_of::<T>() == 0 {
// See above for why 'ptr.offset' isn't used
- self.end = arith_offset(self.end as *const i8, -1) as *const T;
+ self.end = arith_offset(self.end as *const i8, -1) as *mut T;
// Use a non-null pointer value
Some(ptr::read(EMPTY as *mut T))
#[stable(feature = "vec_into_iter_clone", since = "1.8.0")]
impl<T: Clone> Clone for IntoIter<T> {
fn clone(&self) -> IntoIter<T> {
- unsafe {
- slice::from_raw_parts(self.ptr, self.len()).to_owned().into_iter()
- }
+ self.as_slice().to_owned().into_iter()
}
}
#![feature(unboxed_closures)]
#![feature(unicode)]
#![feature(vec_deque_contains)]
+#![feature(vec_into_iter_as_slice)]
extern crate collections;
extern crate test;
assert_eq!(vec2, [5, 6]);
}
+#[test]
+fn test_into_iter_as_slice() {
+ let vec = vec!['a', 'b', 'c'];
+ let mut into_iter = vec.into_iter();
+ assert_eq!(into_iter.as_slice(), &['a', 'b', 'c']);
+ let _ = into_iter.next().unwrap();
+ assert_eq!(into_iter.as_slice(), &['b', 'c']);
+ let _ = into_iter.next().unwrap();
+ let _ = into_iter.next().unwrap();
+ assert_eq!(into_iter.as_slice(), &[]);
+}
+
+#[test]
+fn test_into_iter_as_mut_slice() {
+ let vec = vec!['a', 'b', 'c'];
+ let mut into_iter = vec.into_iter();
+ assert_eq!(into_iter.as_slice(), &['a', 'b', 'c']);
+ into_iter.as_mut_slice()[0] = 'x';
+ into_iter.as_mut_slice()[1] = 'y';
+ assert_eq!(into_iter.next().unwrap(), 'x');
+ assert_eq!(into_iter.as_slice(), &['y', 'c']);
+}
+
#[test]
fn test_into_iter_count() {
assert_eq!(vec![1, 2, 3].into_iter().count(), 3);
use clone::Clone;
use cmp::{PartialEq, Eq, PartialOrd, Ord, Ordering};
+use convert::From;
use default::Default;
use fmt::{self, Debug, Display};
use marker::{Copy, PhantomData, Send, Sync, Sized, Unsize};
}
}
+#[stable(feature = "cell_from", since = "1.12.0")]
+impl<T: Copy> From<T> for Cell<T> {
+ fn from(t: T) -> Cell<T> {
+ Cell::new(t)
+ }
+}
+
/// A mutable memory location with dynamically checked borrow rules
///
/// See the [module-level documentation](index.html) for more.
}
}
+#[stable(feature = "cell_from", since = "1.12.0")]
+impl<T> From<T> for RefCell<T> {
+ fn from(t: T) -> RefCell<T> {
+ RefCell::new(t)
+ }
+}
+
struct BorrowRef<'b> {
borrow: &'b Cell<BorrowFlag>,
}
UnsafeCell::new(Default::default())
}
}
+
+#[stable(feature = "cell_from", since = "1.12.0")]
+impl<T> From<T> for UnsafeCell<T> {
+ fn from(t: T) -> UnsafeCell<T> {
+ UnsafeCell::new(t)
+ }
+}
///
/// # Generic Impls
///
-/// - `AsRef` auto-dereference if the inner type is a reference or a mutable
-/// reference (eg: `foo.as_ref()` will work the same if `foo` has type `&mut Foo` or `&&mut Foo`)
+/// - `AsRef` auto-dereferences if the inner type is a reference or a mutable
+/// reference (e.g.: `foo.as_ref()` will work the same if `foo` has type `&mut Foo` or `&&mut Foo`)
///
#[stable(feature = "rust1", since = "1.0.0")]
pub trait AsRef<T: ?Sized> {
///
/// # Generic Impls
///
-/// - `AsMut` auto-dereference if the inner type is a reference or a mutable
-/// reference (eg: `foo.as_ref()` will work the same if `foo` has type `&mut Foo` or `&&mut Foo`)
+/// - `AsMut` auto-dereferences if the inner type is a reference or a mutable
+/// reference (e.g.: `foo.as_ref()` will work the same if `foo` has type `&mut Foo` or `&&mut Foo`)
///
#[stable(feature = "rust1", since = "1.0.0")]
pub trait AsMut<T: ?Sized> {
//! atomically-reference-counted shared pointer).
//!
//! Most atomic types may be stored in static variables, initialized using
-//! the provided static initializers like `INIT_ATOMIC_BOOL`. Atomic statics
+//! the provided static initializers like `ATOMIC_BOOL_INIT`. Atomic statics
//! are often used for lazy global initialization.
//!
//!
```
"##,
+E0312: r##"
+A lifetime of reference outlives lifetime of borrowed content.
+
+Erroneous code example:
+
+```compile_fail,E0312
+fn make_child<'human, 'elve>(x: &mut &'human isize, y: &mut &'elve isize) {
+ *x = *y;
+ // error: lifetime of reference outlives lifetime of borrowed content
+}
+```
+
+The compiler cannot determine if the `human` lifetime will live long enough
+to keep up on the elve one. To solve this error, you have to give an
+explicit lifetime hierarchy:
+
+```
+fn make_child<'human, 'elve: 'human>(x: &mut &'human isize,
+ y: &mut &'elve isize) {
+ *x = *y; // ok!
+}
+```
+
+Or use the same lifetime for every variable:
+
+```
+fn make_child<'elve>(x: &mut &'elve isize, y: &mut &'elve isize) {
+ *x = *y; // ok!
+}
+```
+"##,
+
E0398: r##"
In Rust 1.3, the default object lifetime bounds are expected to change, as
described in RFC #1156 [1]. You are getting a warning because the compiler
// E0304, // expected signed integer constant
// E0305, // expected constant
E0311, // thing may not live long enough
- E0312, // lifetime of reference outlives lifetime of borrowed content
E0313, // lifetime of borrowed pointer outlives lifetime of captured variable
E0314, // closure outlives stack frame
E0315, // cannot invoke closure outside of its lifetime
declare_lint! {
pub PRIVATE_IN_PUBLIC,
- Warn,
+ Deny,
"detect private items in public interfaces not caught by the old implementation"
}
if ctxt.start_fn.is_none() {
ctxt.start_fn = Some((item.id, item.span));
} else {
- span_err!(ctxt.session, item.span, E0138,
- "multiple 'start' functions");
+ struct_span_err!(
+ ctxt.session, item.span, E0138,
+ "multiple 'start' functions")
+ .span_label(ctxt.start_fn.unwrap().1,
+ &format!("previous `start` function here"))
+ .span_label(item.span, &format!("multiple `start` functions"))
+ .emit();
}
},
EntryPointType::None => ()
#[derive(Clone, Debug, RustcEncodable, RustcDecodable)]
pub enum StatementKind<'tcx> {
Assign(Lvalue<'tcx>, Rvalue<'tcx>),
+ SetDiscriminant{ lvalue: Lvalue<'tcx>, variant_index: usize },
}
impl<'tcx> Debug for Statement<'tcx> {
fn fmt(&self, fmt: &mut Formatter) -> fmt::Result {
use self::StatementKind::*;
match self.kind {
- Assign(ref lv, ref rv) => write!(fmt, "{:?} = {:?}", lv, rv)
+ Assign(ref lv, ref rv) => write!(fmt, "{:?} = {:?}", lv, rv),
+ SetDiscriminant{lvalue: ref lv, variant_index: index} => {
+ write!(fmt, "discriminant({:?}) = {:?}", lv, index)
+ }
}
}
}
ref $($mutability)* rvalue) => {
self.visit_assign(block, lvalue, rvalue);
}
+ StatementKind::SetDiscriminant{ ref $($mutability)* lvalue, .. } => {
+ self.visit_lvalue(lvalue, LvalueContext::Store);
+ }
}
}
ty::TyArray(_, n) => format!("array of {} elements", n),
ty::TySlice(_) => "slice".to_string(),
ty::TyRawPtr(_) => "*-ptr".to_string(),
- ty::TyRef(_, _) => "&-ptr".to_string(),
+ ty::TyRef(region, tymut) => {
+ let tymut_string = tymut.to_string();
+ if tymut_string == "_" || //unknown type name,
+ tymut_string.len() > 10 || //name longer than saying "reference",
+ region.to_string() != "" //... or a complex type
+ {
+ match tymut {
+ ty::TypeAndMut{mutbl, ..} => {
+ format!("{}reference", match mutbl {
+ hir::Mutability::MutMutable => "mutable ",
+ _ => ""
+ })
+ }
+ }
+ } else {
+ format!("&{}", tymut_string)
+ }
+ }
ty::TyFnDef(..) => format!("fn item"),
ty::TyFnPtr(_) => "fn pointer".to_string(),
ty::TyTrait(ref inner) => {
}
let bits_per_block = self.bits_per_block(ctxt);
match stmt.kind {
+ repr::StatementKind::SetDiscriminant { .. } => {
+ span_bug!(stmt.source_info.span, "SetDiscriminant should not exist in borrowck");
+ }
repr::StatementKind::Assign(ref lvalue, _) => {
// assigning into this `lvalue` kills all
// MoveOuts from it, and *also* all MoveOuts
repr::StatementKind::Assign(ref lvalue, ref rvalue) => {
(lvalue, rvalue)
}
+ repr::StatementKind::SetDiscriminant{ .. } =>
+ span_bug!(stmt.source_info.span,
+ "sanity_check should run before Deaggregator inserts SetDiscriminant"),
};
if lvalue == peek_arg_lval {
Rvalue::InlineAsm { .. } => {}
}
}
+ StatementKind::SetDiscriminant{ .. } => {
+ span_bug!(stmt.source_info.span,
+ "SetDiscriminant should not exist during borrowck");
+ }
}
}
let block = &mir[loc.block];
match block.statements.get(loc.index) {
Some(stmt) => match stmt.kind {
+ repr::StatementKind::SetDiscriminant{ .. } => {
+ span_bug!(stmt.source_info.span, "SetDiscrimant should not exist during borrowck");
+ }
repr::StatementKind::Assign(ref lvalue, _) => {
debug!("drop_flag_effects: assignment {:?}", stmt);
on_all_children_bits(tcx, mir, move_data,
when that data may no longer exist. It's most commonly seen when attempting to
return a closure:
-```compile_fail
+```compile_fail,E0373
fn foo() -> Box<Fn(u32) -> u32> {
let x = 0u32;
Box::new(|y| x + y)
Another situation where this might be encountered is when spawning threads:
-```compile_fail
+```compile_fail,E0373
fn foo() {
let x = 0u32;
let y = 1u32;
E0381: r##"
It is not allowed to use or capture an uninitialized variable. For example:
-```compile_fail
+```compile_fail,E0381
fn main() {
let x: i32;
let y = x; // error, use of possibly uninitialized variable
This error occurs when an attempt is made to use a variable after its contents
have been moved elsewhere. For example:
-```compile_fail
+```compile_fail,E0382
struct MyStruct { s: u32 }
fn main() {
This error occurs when an attempt is made to reassign an immutable variable.
For example:
-```compile_fail
-fn main(){
+```compile_fail,E0384
+fn main() {
let x = 3;
x = 5; // error, reassignment of immutable variable
}
`mut` after the keyword `let` when declaring the variable. For example:
```
-fn main(){
+fn main() {
let mut x = 3;
x = 5;
}
For example, this can happen when storing a `&mut` inside an immutable `Box`:
-```compile_fail
+```compile_fail,E0386
let mut x: i64 = 1;
let y: Box<_> = Box::new(&mut x);
**y = 2; // error, cannot assign to data in an immutable container
This error occurs when an attempt is made to mutate or mutably reference data
that a closure has captured immutably. Examples of this error are shown below:
-```compile_fail
+```compile_fail,E0387
// Accepts a function or a closure that captures its environment immutably.
// Closures passed to foo will not be able to mutate their closed-over state.
fn foo<F: Fn()>(f: F) { }
https://doc.rust-lang.org/std/cell/
"##,
+E0388: r##"
+A mutable borrow was attempted in a static location.
+
+Erroneous code example:
+
+```compile_fail,E0388
+static X: i32 = 1;
+
+static STATIC_REF: &'static mut i32 = &mut X;
+// error: cannot borrow data mutably in a static location
+
+const CONST_REF: &'static mut i32 = &mut X;
+// error: cannot borrow data mutably in a static location
+```
+
+To fix this error, you have to use constant borrow:
+
+```
+static X: i32 = 1;
+
+static STATIC_REF: &'static i32 = &X;
+```
+"##,
+
E0389: r##"
An attempt was made to mutate data using a non-mutable reference. This
commonly occurs when attempting to assign to a non-mutable reference of a
Example of erroneous code:
-```compile_fail
+```compile_fail,E0389
struct FancyNum {
- num: u8
+ num: u8,
}
fn main() {
```
struct FancyNum {
- num: u8
+ num: u8,
}
fn main() {
E0499: r##"
A variable was borrowed as mutable more than once. Erroneous code example:
-```compile_fail
+```compile_fail,E0499
let mut i = 0;
let mut x = &mut i;
let mut a = &mut i;
Example of erroneous code:
-```compile_fail
+```compile_fail,E0501
fn inside_closure(x: &mut i32) {
// Actions which require unique access
}
Example of erroneous code:
-```compile_fail
+```compile_fail,E0502
fn bar(x: &mut i32) {}
fn foo(a: &mut i32) {
let ref y = a; // a is borrowed as immutable.
Example of erroneous code:
-```compile_fail
+```compile_fail,E0503
fn main() {
let mut value = 3;
// Create a mutable borrow of `value`. This borrow
Example of erroneous code:
-```compile_fail
+```compile_fail,E0504
struct FancyNum {
- num: u8
+ num: u8,
}
fn main() {
```
struct FancyNum {
- num: u8
+ num: u8,
}
fn main() {
```
struct FancyNum {
- num: u8
+ num: u8,
}
fn main() {
use std::thread;
struct FancyNum {
- num: u8
+ num: u8,
}
fn main() {
```
"##,
+E0505: r##"
+A value was moved out while it was still borrowed.
+
+Erroneous code example:
+
+```compile_fail,E0505
+struct Value {}
+
+fn eat(val: Value) {}
+
+fn main() {
+ let x = Value{};
+ {
+ let _ref_to_val: &Value = &x;
+ eat(x);
+ }
+}
+```
+
+Here, the function `eat` takes the ownership of `x`. However,
+`x` cannot be moved because it was borrowed to `_ref_to_val`.
+To fix that you can do few different things:
+
+* Try to avoid moving the variable.
+* Release borrow before move.
+* Implement the `Copy` trait on the type.
+
+Examples:
+
+```
+struct Value {}
+
+fn eat(val: &Value) {}
+
+fn main() {
+ let x = Value{};
+ {
+ let _ref_to_val: &Value = &x;
+ eat(&x); // pass by reference, if it's possible
+ }
+}
+```
+
+Or:
+
+```
+struct Value {}
+
+fn eat(val: Value) {}
+
+fn main() {
+ let x = Value{};
+ {
+ let _ref_to_val: &Value = &x;
+ }
+ eat(x); // release borrow and then move it.
+}
+```
+
+Or:
+
+```
+#[derive(Clone, Copy)] // implement Copy trait
+struct Value {}
+
+fn eat(val: Value) {}
+
+fn main() {
+ let x = Value{};
+ {
+ let _ref_to_val: &Value = &x;
+ eat(x); // it will be copied here.
+ }
+}
+```
+
+You can find more information about borrowing in the rust-book:
+http://doc.rust-lang.org/stable/book/references-and-borrowing.html
+"##,
+
E0506: r##"
This error occurs when an attempt is made to assign to a borrowed value.
Example of erroneous code:
-```compile_fail
+```compile_fail,E0506
struct FancyNum {
- num: u8
+ num: u8,
}
fn main() {
```
struct FancyNum {
- num: u8
+ num: u8,
}
fn main() {
```
struct FancyNum {
- num: u8
+ num: u8,
}
fn main() {
```
struct FancyNum {
- num: u8
+ num: u8,
}
fn main() {
```
"##,
-E0505: r##"
-A value was moved out while it was still borrowed.
-Erroneous code example:
-
-```compile_fail
-struct Value {}
-
-fn eat(val: Value) {}
-
-fn main() {
- let x = Value{};
- {
- let _ref_to_val: &Value = &x;
- eat(x);
- }
-}
-```
-
-Here, the function `eat` takes the ownership of `x`. However,
-`x` cannot be moved because it was borrowed to `_ref_to_val`.
-To fix that you can do few different things:
-
-* Try to avoid moving the variable.
-* Release borrow before move.
-* Implement the `Copy` trait on the type.
-
-Examples:
-
-```
-struct Value {}
-
-fn eat(val: &Value) {}
-
-fn main() {
- let x = Value{};
- {
- let _ref_to_val: &Value = &x;
- eat(&x); // pass by reference, if it's possible
- }
-}
-```
-
-Or:
-
-```
-struct Value {}
-
-fn eat(val: Value) {}
-
-fn main() {
- let x = Value{};
- {
- let _ref_to_val: &Value = &x;
- }
- eat(x); // release borrow and then move it.
-}
-```
-
-Or:
-
-```
-#[derive(Clone, Copy)] // implement Copy trait
-struct Value {}
-
-fn eat(val: Value) {}
-
-fn main() {
- let x = Value{};
- {
- let _ref_to_val: &Value = &x;
- eat(x); // it will be copied here.
- }
-}
-```
-
-You can find more information about borrowing in the rust-book:
-http://doc.rust-lang.org/stable/book/references-and-borrowing.html
-"##,
-
E0507: r##"
You tried to move out of a value which was borrowed. Erroneous code example:
-```compile_fail
+```compile_fail,E0507
use std::cell::RefCell;
struct TheDarkKnight;
Example of erroneous code:
-```compile_fail
+```compile_fail,E0508
struct NonCopy;
fn main() {
Example of erroneous code:
-```compile_fail
+```compile_fail,E0509
struct FancyNum {
num: usize
}
register_diagnostics! {
E0385, // {} in an aliasable location
- E0388, // {} in a static location
E0524, // two closures require unique access to `..` at the same time
}
store.register_future_incompatible(sess, vec![
FutureIncompatibleInfo {
id: LintId::of(PRIVATE_IN_PUBLIC),
- reference: "the explanation for E0446 (`--explain E0446`)",
+ reference: "issue #34537 <https://github.com/rust-lang/rust/issues/34537>",
},
FutureIncompatibleInfo {
id: LintId::of(INACCESSIBLE_EXTERN_CRATE),
let mut curr: usize = 0;
for bb in mir.basic_blocks_mut() {
- let idx = match get_aggregate_statement(curr, &bb.statements) {
+ let idx = match get_aggregate_statement_index(curr, &bb.statements) {
Some(idx) => idx,
None => continue,
};
let src_info = bb.statements[idx].source_info;
let suffix_stmts = bb.statements.split_off(idx+1);
let orig_stmt = bb.statements.pop().unwrap();
- let StatementKind::Assign(ref lhs, ref rhs) = orig_stmt.kind;
+ let (lhs, rhs) = match orig_stmt.kind {
+ StatementKind::Assign(ref lhs, ref rhs) => (lhs, rhs),
+ StatementKind::SetDiscriminant{ .. } =>
+ span_bug!(src_info.span, "expected aggregate, not {:?}", orig_stmt.kind),
+ };
let (agg_kind, operands) = match rhs {
&Rvalue::Aggregate(ref agg_kind, ref operands) => (agg_kind, operands),
_ => span_bug!(src_info.span, "expected aggregate, not {:?}", rhs),
let ty = variant_def.fields[i].ty(tcx, substs);
let rhs = Rvalue::Use(op.clone());
- // since we don't handle enums, we don't need a cast
- let lhs_cast = lhs.clone();
-
- // FIXME we cannot deaggregate enums issue: #35186
+ let lhs_cast = if adt_def.variants.len() > 1 {
+ Lvalue::Projection(Box::new(LvalueProjection {
+ base: lhs.clone(),
+ elem: ProjectionElem::Downcast(adt_def, variant),
+ }))
+ } else {
+ lhs.clone()
+ };
let lhs_proj = Lvalue::Projection(Box::new(LvalueProjection {
base: lhs_cast,
debug!("inserting: {:?} @ {:?}", new_statement, idx + i);
bb.statements.push(new_statement);
}
+
+ // if the aggregate was an enum, we need to set the discriminant
+ if adt_def.variants.len() > 1 {
+ let set_discriminant = Statement {
+ kind: StatementKind::SetDiscriminant {
+ lvalue: lhs.clone(),
+ variant_index: variant,
+ },
+ source_info: src_info,
+ };
+ bb.statements.push(set_discriminant);
+ };
+
curr = bb.statements.len();
bb.statements.extend(suffix_stmts);
}
}
}
-fn get_aggregate_statement<'a, 'tcx, 'b>(curr: usize,
+fn get_aggregate_statement_index<'a, 'tcx, 'b>(start: usize,
statements: &Vec<Statement<'tcx>>)
-> Option<usize> {
- for i in curr..statements.len() {
+ for i in start..statements.len() {
let ref statement = statements[i];
- let StatementKind::Assign(_, ref rhs) = statement.kind;
+ let rhs = match statement.kind {
+ StatementKind::Assign(_, ref rhs) => rhs,
+ StatementKind::SetDiscriminant{ .. } => continue,
+ };
let (kind, operands) = match rhs {
&Rvalue::Aggregate(ref kind, ref operands) => (kind, operands),
_ => continue,
&AggregateKind::Adt(adt_def, variant, _) => (adt_def, variant),
_ => continue,
};
- if operands.len() == 0 || adt_def.variants.len() > 1 {
+ if operands.len() == 0 {
// don't deaggregate ()
- // don't deaggregate enums ... for now
continue;
}
debug!("getting variant {:?}", variant);
let (mut rvalue, mut call) = (None, None);
let source_info = if stmt_idx < no_stmts {
let statement = &mut self.source[bb].statements[stmt_idx];
- let StatementKind::Assign(_, ref mut rhs) = statement.kind;
+ let mut rhs = match statement.kind {
+ StatementKind::Assign(_, ref mut rhs) => rhs,
+ StatementKind::SetDiscriminant{ .. } =>
+ span_bug!(statement.source_info.span,
+ "cannot promote SetDiscriminant {:?}",
+ statement),
+ };
if self.keep_original {
rvalue = Some(rhs.clone());
} else {
});
let mut rvalue = match candidate {
Candidate::Ref(Location { block: bb, statement_index: stmt_idx }) => {
- match self.source[bb].statements[stmt_idx].kind {
+ let ref mut statement = self.source[bb].statements[stmt_idx];
+ match statement.kind {
StatementKind::Assign(_, ref mut rvalue) => {
mem::replace(rvalue, Rvalue::Use(new_operand))
}
+ StatementKind::SetDiscriminant{ .. } => {
+ span_bug!(statement.source_info.span,
+ "cannot promote SetDiscriminant {:?}",
+ statement);
+ }
}
}
Candidate::ShuffleIndices(bb) => {
let (span, ty) = match candidate {
Candidate::Ref(Location { block: bb, statement_index: stmt_idx }) => {
let statement = &mir[bb].statements[stmt_idx];
- let StatementKind::Assign(ref dest, _) = statement.kind;
+ let dest = match statement.kind {
+ StatementKind::Assign(ref dest, _) => dest,
+ StatementKind::SetDiscriminant{ .. } =>
+ panic!("cannot promote SetDiscriminant"),
+ };
if let Lvalue::Temp(index) = *dest {
if temps[index] == TempState::PromotedOut {
// Already promoted.
use rustc::infer::{self, InferCtxt, InferOk};
use rustc::traits::{self, Reveal};
use rustc::ty::fold::TypeFoldable;
-use rustc::ty::{self, Ty, TyCtxt};
+use rustc::ty::{self, Ty, TyCtxt, TypeVariants};
use rustc::mir::repr::*;
use rustc::mir::tcx::LvalueTy;
use rustc::mir::transform::{MirPass, MirSource, Pass};
span_mirbug!(self, stmt, "bad assignment ({:?} = {:?}): {:?}",
lv_ty, rv_ty, terr);
}
- }
-
// FIXME: rvalue with undeterminable type - e.g. inline
// asm.
+ }
+ }
+ StatementKind::SetDiscriminant{ ref lvalue, variant_index } => {
+ let lvalue_type = lvalue.ty(mir, tcx).to_ty(tcx);
+ let adt = match lvalue_type.sty {
+ TypeVariants::TyEnum(adt, _) => adt,
+ _ => {
+ span_bug!(stmt.source_info.span,
+ "bad set discriminant ({:?} = {:?}): lhs is not an enum",
+ lvalue,
+ variant_index);
+ }
+ };
+ if variant_index >= adt.variants.len() {
+ span_bug!(stmt.source_info.span,
+ "bad set discriminant ({:?} = {:?}): value of of range",
+ lvalue,
+ variant_index);
+ };
}
}
}
visit::walk_foreign_item(self, fi)
}
- fn visit_variant_data(&mut self,
- vdata: &VariantData,
- _: Ident,
- _: &Generics,
- _: NodeId,
- span: Span) {
- if vdata.fields().is_empty() {
- if vdata.is_tuple() {
- self.err_handler()
- .struct_span_err(span,
- "empty tuple structs and enum variants are not allowed, use \
- unit structs and enum variants instead")
- .span_help(span,
- "remove trailing `()` to make a unit struct or unit enum variant")
- .emit();
- }
- }
-
- visit::walk_struct_def(self, vdata)
- }
-
fn visit_vis(&mut self, vis: &Visibility) {
match *vis {
Visibility::Restricted { ref path, .. } => {
match self.cx {
Loop => {}
Closure => {
- span_err!(self.sess, span, E0267, "`{}` inside of a closure", name);
+ struct_span_err!(self.sess, span, E0267, "`{}` inside of a closure", name)
+ .span_label(span, &format!("cannot break inside of a closure"))
+ .emit();
}
Normal => {
- span_err!(self.sess, span, E0268, "`{}` outside of loop", name);
+ struct_span_err!(self.sess, span, E0268, "`{}` outside of loop", name)
+ .span_label(span, &format!("cannot break outside of a loop"))
+ .emit();
}
}
}
examples:
```compile_fail,E0445
-#![deny(private_in_public)]
-
trait Foo {
fn dummy(&self) { }
}
A private type was used in a public type signature. Erroneous code example:
```compile_fail,E0446
-#![deny(private_in_public)]
-
mod Foo {
struct Bar(u32);
self.tcx.sess.add_lint(lint::builtin::PRIVATE_IN_PUBLIC,
node_id,
ty.span,
- format!("private type in public interface"));
+ format!("private type in public \
+ interface (error E0446)"));
}
}
}
let mut err = match (old_binding.is_extern_crate(), binding.is_extern_crate()) {
(true, true) => struct_span_err!(self.session, span, E0259, "{}", msg),
- (true, _) | (_, true) if binding.is_import() || old_binding.is_import() =>
- struct_span_err!(self.session, span, E0254, "{}", msg),
+ (true, _) | (_, true) if binding.is_import() || old_binding.is_import() => {
+ let mut e = struct_span_err!(self.session, span, E0254, "{}", msg);
+ e.span_label(span, &"already imported");
+ e
+ },
(true, _) | (_, true) => struct_span_err!(self.session, span, E0260, "{}", msg),
_ => match (old_binding.is_import(), binding.is_import()) {
(false, false) => struct_span_err!(self.session, span, E0428, "{}", msg),
}
Success(binding) if !binding.is_importable() => {
let msg = format!("`{}` is not directly importable", target);
- span_err!(self.session, directive.span, E0253, "{}", &msg);
+ struct_span_err!(self.session, directive.span, E0253, "{}", &msg)
+ .span_label(directive.span, &format!("cannot be imported directly"))
+ .emit();
// Do not import this illegal binding. Import a dummy binding and pretend
// everything is fine
self.import_dummy_binding(module, directive);
use rustc::mir::visit as mir_visit;
use rustc::mir::visit::Visitor as MirVisitor;
+use rustc_const_eval as const_eval;
+
use syntax::abi::Abi;
use errors;
use syntax_pos::DUMMY_SP;
-use syntax::ast::NodeId;
use base::custom_coerce_unsize_info;
use context::SharedCrateContext;
use common::{fulfill_obligation, normalize_and_test_predicates, type_is_sized};
debug!("visiting operand {:?}", *operand);
let callee = match *operand {
- mir::Operand::Constant(mir::Constant { ty: &ty::TyS {
- sty: ty::TyFnDef(def_id, substs, _), ..
- }, .. }) => Some((def_id, substs)),
+ mir::Operand::Constant(ref constant) => {
+ if let ty::TyFnDef(def_id, substs, _) = constant.ty.sty {
+ // This is something that can act as a callee, proceed
+ Some((def_id, substs))
+ } else {
+ // This is not a callee, but we still have to look for
+ // references to `const` items
+ if let mir::Literal::Item { def_id, substs } = constant.literal {
+ let tcx = self.scx.tcx();
+ let substs = monomorphize::apply_param_substs(tcx,
+ self.param_substs,
+ &substs);
+
+ // If the constant referred to here is an associated
+ // item of a trait, we need to resolve it to the actual
+ // constant in the corresponding impl. Luckily
+ // const_eval::lookup_const_by_id() does that for us.
+ if let Some((expr, _)) = const_eval::lookup_const_by_id(tcx,
+ def_id,
+ Some(substs)) {
+ // The hir::Expr we get here is the initializer of
+ // the constant, what we really want is the item
+ // DefId.
+ let const_node_id = tcx.map.get_parent(expr.id);
+ let def_id = if tcx.map.is_inlined_node_id(const_node_id) {
+ tcx.sess.cstore.defid_for_inlined_node(const_node_id).unwrap()
+ } else {
+ tcx.map.local_def_id(const_node_id)
+ };
+
+ collect_const_item_neighbours(self.scx,
+ def_id,
+ substs,
+ self.output);
+ }
+ }
+
+ None
+ }
+ }
_ => None
};
self.output.push(TransItem::Static(item.id));
}
hir::ItemConst(..) => {
- debug!("RootCollector: ItemConst({})",
- def_id_to_string(self.scx.tcx(),
- self.scx.tcx().map.local_def_id(item.id)));
- add_roots_for_const_item(self.scx, item.id, self.output);
+ // const items only generate translation items if they are
+ // actually used somewhere. Just declaring them is insufficient.
}
hir::ItemFn(_, _, _, _, ref generics, _) => {
if !generics.is_type_parameterized() {
// There are no translation items for constants themselves but their
// initializers might still contain something that produces translation items,
// such as cast that introduce a new vtable.
-fn add_roots_for_const_item<'a, 'tcx>(scx: &SharedCrateContext<'a, 'tcx>,
- const_item_node_id: NodeId,
- output: &mut Vec<TransItem<'tcx>>)
+fn collect_const_item_neighbours<'a, 'tcx>(scx: &SharedCrateContext<'a, 'tcx>,
+ def_id: DefId,
+ substs: &'tcx Substs<'tcx>,
+ output: &mut Vec<TransItem<'tcx>>)
{
- let def_id = scx.tcx().map.local_def_id(const_item_node_id);
-
// Scan the MIR in order to find function calls, closures, and
// drop-glue
let mir = errors::expect(scx.sess().diagnostic(), scx.get_mir(def_id),
|| format!("Could not find MIR for const: {:?}", def_id));
- let empty_substs = scx.empty_substs_for_def_id(def_id);
let visitor = MirNeighborCollector {
scx: scx,
mir: &mir,
output: output,
- param_substs: empty_substs
+ param_substs: substs
};
visit_mir_and_promoted(visitor, &mir);
Err(err) => if failure.is_ok() { failure = Err(err); }
}
}
+ mir::StatementKind::SetDiscriminant{ .. } => {
+ span_bug!(span, "SetDiscriminant should not appear in constants?");
+ }
}
}
use super::MirContext;
use super::LocalRef;
+use super::super::adt;
+use super::super::disr::Disr;
impl<'bcx, 'tcx> MirContext<'bcx, 'tcx> {
pub fn trans_statement(&mut self,
self.trans_rvalue(bcx, tr_dest, rvalue, debug_loc)
}
}
+ mir::StatementKind::SetDiscriminant{ref lvalue, variant_index} => {
+ let ty = self.monomorphized_lvalue_ty(lvalue);
+ let repr = adt::represent_type(bcx.ccx(), ty);
+ let lvalue_transed = self.trans_lvalue(&bcx, lvalue);
+ bcx.with_block(|bcx|
+ adt::trans_set_discr(bcx,
+ &repr,
+ lvalue_transed.llval,
+ Disr::from(variant_index))
+ );
+ bcx
+ }
}
}
}
use syntax::attr;
use syntax::attr::AttrMetaMethods;
use syntax::codemap::{self, Spanned};
+use syntax::feature_gate::{GateIssue, emit_feature_err};
use syntax::parse::token::{self, InternedString, keywords};
use syntax::ptr::P;
use syntax::util::lev_distance::find_best_match_for_name;
node_id: ast::NodeId)
-> Ty<'tcx> {
debug!("instantiate_type_path(did={:?}, path={:?})", did, path);
- let type_scheme = self.tcx.lookup_item_type(did);
+ let mut type_scheme = self.tcx.lookup_item_type(did);
+ if type_scheme.ty.is_fn() {
+ // Tuple variants have fn type even in type namespace, extract true variant type from it
+ let fn_ret = self.tcx.no_late_bound_regions(&type_scheme.ty.fn_ret()).unwrap().unwrap();
+ type_scheme = ty::TypeScheme { ty: fn_ret, generics: type_scheme.generics }
+ }
let type_predicates = self.tcx.lookup_predicates(did);
let substs = AstConv::ast_path_substs_for_ty(self, self,
path.span,
}
_ => None
};
- if variant.is_none() || variant.unwrap().kind == ty::VariantKind::Tuple {
- // Reject tuple structs for now, braced and unit structs are allowed.
+
+ if let Some(variant) = variant {
+ if variant.kind == ty::VariantKind::Tuple &&
+ !self.tcx.sess.features.borrow().relaxed_adts {
+ emit_feature_err(&self.tcx.sess.parse_sess.span_diagnostic,
+ "relaxed_adts", span, GateIssue::Language,
+ "tuple structs and variants in struct patterns are unstable");
+ }
+ let ty = self.instantiate_type_path(def.def_id(), path, node_id);
+ Some((variant, ty))
+ } else {
struct_span_err!(self.tcx.sess, path.span, E0071,
"`{}` does not name a struct or a struct variant",
pprust::path_to_string(path))
.span_label(path.span, &format!("not a struct"))
.emit();
-
- return None;
+ None
}
-
- let ty = self.instantiate_type_path(def.def_id(), path, node_id);
- Some((variant.unwrap(), ty))
}
fn check_expr_struct(&self,
let tcx = self.tcx;
if !tcx.expr_is_lval(&lhs) {
- span_err!(tcx.sess, expr.span, E0070,
- "invalid left-hand side expression");
+ struct_span_err!(
+ tcx.sess, expr.span, E0070,
+ "invalid left-hand side expression")
+ .span_label(
+ expr.span,
+ &format!("left-hand of expression not valid"))
+ .emit();
}
let lhs_ty = self.expr_ty(&lhs);
let tcx = self.tcx;
if !tcx.expr_is_lval(lhs_expr) {
- span_err!(tcx.sess, lhs_expr.span, E0067, "invalid left-hand side expression");
+ struct_span_err!(
+ tcx.sess, lhs_expr.span,
+ E0067, "invalid left-hand side expression")
+ .span_label(
+ lhs_expr.span,
+ &format!("invalid expression for left-hand side"))
+ .emit();
}
}
Matching with the wrong number of fields has no sensible interpretation:
-```compile_fail
+```compile_fail,E0023
enum Fruit {
Apple(String, String),
Pear(u32),
Each field of a struct can only be bound once in a pattern. Erroneous code
example:
-```compile_fail
+```compile_fail,E0025
struct Foo {
a: u8,
b: u8,
Change this:
-```compile_fail
+```compile_fail,E0026
struct Thing {
x: u32,
y: u32
For example:
-```compile_fail
+```compile_fail,E0027
struct Dog {
name: String,
age: u32,
want to capture values of an orderable type between two end-points, you can use
a guard.
-```compile_fail
+```compile_fail,E0029
+let string = "salutations !";
+
// The ordering relation for strings can't be evaluated at compile time,
// so this doesn't work:
match string {
The compiler doesn't know what method to call because more than one method
has the same prototype. Erroneous code example:
-```compile_fail
+```compile_fail,E0034
struct Test;
trait Trait1 {
You tried to give a type parameter where it wasn't needed. Erroneous code
example:
-```compile_fail
+```compile_fail,E0035
struct Test;
impl Test {
This error occurrs when you pass too many or not enough type parameters to
a method. Erroneous code example:
-```compile_fail
+```compile_fail,E0036
struct Test;
impl Test {
Here's an example of this error:
-```compile_fail
+```compile_fail,E0040
struct Foo {
x: i32,
}
E0044: r##"
You can't use type parameters on foreign items. Example of erroneous code:
-```compile_fail
+```compile_fail,E0044
extern { fn some_func<T>(x: T); }
```
FFI. As such, variadic parameters can only be used with functions which are
using the C ABI. Examples of erroneous code:
-```compile_fail
+```compile_fail,E0045
+#![feature(unboxed_closures)]
+
extern "rust-call" { fn foo(x: u8, ...); }
// or
To fix such code, put them in an extern "C" block:
-```ignore
-extern "C" fn foo(x: u8, ...);
-```
-
-Or:
-
```
extern "C" {
fn foo (x: u8, ...);
E0046: r##"
Items are missing in a trait implementation. Erroneous code example:
-```compile_fail
+```compile_fail,E0046
trait Foo {
fn foo();
}
For example, the trait below has a method `foo` with a type parameter `T`,
but the implementation of `foo` for the type `Bar` is missing this parameter:
-```compile_fail
+```compile_fail,E0049
trait Foo {
fn foo<T: Default>(x: T) -> Self;
}
(`&self` and `u8`), but the implementation of `foo` for the type `Bar` omits
the `u8` parameter:
-```compile_fail
+```compile_fail,E0050
trait Foo {
fn foo(&self, x: u8) -> bool;
}
Here are a couple examples of this error:
-```compile_fail
+```compile_fail,E0053
trait Foo {
fn foo(x: u16);
fn bar(&self);
It is not allowed to cast to a bool. If you are trying to cast a numeric type
to a bool, you can compare it with zero instead:
-```compile_fail
+```compile_fail,E0054
let x = 5;
// Not allowed, won't compile
For a somewhat artificial example:
-```compile_fail,ignore
+```compile_fail,E0055
#![recursion_limit="2"]
struct Foo;
An example using a closure:
-```compile_fail
+```compile_fail,E0057
let f = |x| x * 3;
let a = f(); // invalid, too few parameters
let b = f(4); // this works!
The most likely source of this error is using angle-bracket notation without
wrapping the function argument type into a tuple, for example:
-```compile_fail
+```compile_fail,E0059
+#![feature(unboxed_closures)]
+
fn foo<F: Fn<i32>>(f: F) -> F::Output { f(3) }
```
It can be fixed by adjusting the trait bound like this:
-```ignore
+```
+#![feature(unboxed_closures)]
+
fn foo<F: Fn<(i32,)>>(f: F) -> F::Output { f(3) }
```
enum variant, one of the fields was specified more than once. Erroneous code
example:
-```compile_fail
+```compile_fail,E0062
struct Foo {
- x: i32
+ x: i32,
}
fn main() {
```
struct Foo {
- x: i32
+ x: i32,
}
fn main() {
This error indicates that during an attempt to build a struct or struct-like
enum variant, one of the fields was not provided. Erroneous code example:
-```compile_fail
+```compile_fail,E0063
struct Foo {
x: i32,
- y: i32
+ y: i32,
}
fn main() {
```
struct Foo {
x: i32,
- y: i32
+ y: i32,
}
fn main() {
Let's start with some erroneous code examples:
-```compile_fail
+```compile_fail,E0067
use std::collections::LinkedList;
// Bad: assignment to non-lvalue expression
The compiler found a function whose body contains a `return;` statement but
whose return type is not `()`. An example of this is:
-```compile_fail
+```compile_fail,E0069
// error
fn foo() -> u8 {
return;
Now, we can go further. Here are some erroneous code examples:
-```compile_fail
+```compile_fail,E0070
struct SomeStruct {
x: i32,
y: i32
Example of erroneous code:
-```compile_fail
+```compile_fail,E0071
enum Foo { FirstValue(i32) };
let u = Foo::FirstValue { value: 0 }; // error: Foo::FirstValue
This will cause an error:
-```compile_fail
+```compile_fail,E0075
#![feature(repr_simd)]
#[repr(simd)]
This will cause an error:
-```compile_fail
+```compile_fail,E0076
#![feature(repr_simd)]
#[repr(simd)]
This will cause an error:
-```compile_fail
+```compile_fail,E0077
#![feature(repr_simd)]
#[repr(simd)]
For example, in the following code:
-```compile_fail
+```compile_fail,E0079
enum Foo {
- Q = "32"
+ Q = "32",
}
```
```
enum Foo {
- Q = 32
+ Q = 32,
}
```
This error indicates that the same value was used for two or more variants,
making them impossible to tell apart.
-```compile_fail
+```compile_fail,E0081
// Bad.
enum Enum {
P = 3,
X = 3,
- Y = 5
+ Y = 5,
}
```
enum Enum {
P,
X = 3,
- Y = 5
+ Y = 5,
}
```
top to bottom starting from 0, so clashes can occur with seemingly unrelated
variants.
-```compile_fail
+```compile_fail,E0081
enum Bad {
X,
Y = 0
#[repr(u8)]
enum Thing {
A = 1024,
- B = 5
+ B = 5,
}
```
```ignore
enum DependsOnPointerSize {
- A = 1 << 32
+ A = 1 << 32,
}
```
Erroneous code example:
-```compile_fail
+```compile_fail,E0084
#[repr(i32)]
enum NightsWatch {} // error: unsupported representation for zero-variant enum
```
E0087: r##"
Too many type parameters were supplied for a function. For example:
-```compile_fail
+```compile_fail,E0087
fn foo<T>() {}
fn main() {
E0088: r##"
You gave too many lifetime parameters. Erroneous code example:
-```compile_fail
+```compile_fail,E0088
fn f() {}
fn main() {
E0089: r##"
Not enough type parameters were supplied for a function. For example:
-```compile_fail
+```compile_fail,E0089
fn foo<T, U>() {}
fn main() {
Note that if a function takes multiple type parameters but you want the compiler
to infer some of them, you can use type placeholders:
-```compile_fail
+```compile_fail,E0089
fn foo<T, U>(x: T) {}
fn main() {
You gave an unnecessary type parameter in a type alias. Erroneous code
example:
-```compile_fail
+```compile_fail,E0091
type Foo<T> = u32; // error: type parameter `T` is unused
// or:
type Foo<A,B> = Box<A>; // error: type parameter `B` is unused
You tried to declare an undefined atomic operation function.
Erroneous code example:
-```compile_fail
+```compile_fail,E0092
#![feature(intrinsics)]
extern "rust-intrinsic" {
E0093: r##"
You declared an unknown intrinsic function. Erroneous code example:
-```compile_fail
+```compile_fail,E0093
#![feature(intrinsics)]
extern "rust-intrinsic" {
You gave an invalid number of type parameters to an intrinsic function.
Erroneous code example:
-```compile_fail
+```compile_fail,E0094
#![feature(intrinsics)]
extern "rust-intrinsic" {
You hit this error because the compiler lacks the information to
determine a type for this expression. Erroneous code example:
-```compile_fail
-fn main() {
- let x = |_| {}; // error: cannot determine a type for this expression
-}
+```compile_fail,E0101
+let x = |_| {}; // error: cannot determine a type for this expression
```
You have two possibilities to solve this situation:
Examples:
```
-fn main() {
- let x = |_ : u32| {}; // ok!
- // or:
- let x = |_| {};
- x(0u32);
-}
+let x = |_ : u32| {}; // ok!
+// or:
+let x = |_| {};
+x(0u32);
```
"##,
You hit this error because the compiler lacks the information to
determine the type of this variable. Erroneous code example:
-```compile_fail
-fn main() {
- // could be an array of anything
- let x = []; // error: cannot determine a type for this local variable
-}
+```compile_fail,E0102
+// could be an array of anything
+let x = []; // error: cannot determine a type for this local variable
```
To solve this situation, constrain the type of the variable.
Here are some simple examples of where you'll run into this error:
-```compile_fail
+```compile_fail,E0106
struct Foo { x: &bool } // error
struct Foo<'a> { x: &'a bool } // correct
Here are some examples of elision errors:
-```compile_fail
+```compile_fail,E0106
// error, no input lifetimes
fn foo() -> &str { }
Some basic examples include:
-```compile_fail
+```compile_fail,E0107
struct Foo<'a>(&'a str);
enum Bar { A, B, C }
Here's an example that is currently an error, but may work in a future version
of Rust:
-```compile_fail
+```compile_fail,E0107
struct Foo<'a>(&'a str);
trait Quux { }
where the type was defined. For example, an `impl` block as below is not allowed
since `Vec` is defined in the standard library:
-```compile_fail
+```compile_fail,E0116
impl Vec<u8> { } // error
```
Note that using the `type` keyword does not work here because `type` only
introduces a type alias:
-```compile_fail
+```compile_fail,E0116
type Bytes = Vec<u8>;
impl Bytes { } // error, same as above
Here's one example of this error:
-```compile_fail
+```compile_fail,E0117
impl Drop for u32 {}
```
You're trying to write an inherent implementation for something which isn't a
struct nor an enum. Erroneous code example:
-```compile_fail
+```compile_fail,E0118
impl (u8, u8) { // error: no base type found for inherent implementation
fn get_state(&self) -> String {
// ...
There are conflicting trait implementations for the same type.
Example of erroneous code:
-```compile_fail
+```compile_fail,E0119
trait MyTrait {
fn get(&self) -> usize;
}
An attempt was made to implement Drop on a trait, which is not allowed: only
structs and enums can implement Drop. An example causing this error:
-```compile_fail
+```compile_fail,E0120
trait MyTrait {}
impl Drop for MyTrait {
Examples of this error include:
-```compile_fail
+```compile_fail,E0121
fn foo() -> _ { 5 } // error, explicitly write out the return type instead
static BAR: _ = "test"; // error, explicitly write out the type instead
You declared two fields of a struct with the same name. Erroneous code
example:
-```compile_fail
+```compile_fail,E0124
struct Foo {
field1: i32,
field1: i32, // error: field is already declared
Type parameter defaults can only use parameters that occur before them.
Erroneous code example:
-```compile_fail
+```compile_fail,E0128
struct Foo<T=U, U=()> {
field1: T,
filed2: U,
parameters. When `main` is present, it must take no arguments and return `()`.
Erroneous code example:
-```compile_fail
+```compile_fail,E0131
fn main<T>() { // error: main function is not allowed to have type parameters
}
```
Erroneous code example:
-```compile_fail
+```compile_fail,E0132
#![feature(start)]
#[start]
This error means that an attempt was made to match a struct type enum
variant as a non-struct type:
-```compile_fail
+```compile_fail,E0164
enum Foo { B { i: u32 } }
fn bar(foo: Foo) -> u32 {
marked as diverging. A function diverges if it has `!` in the place of the
return type in its signature. For example:
-```compile_fail
+```compile_fail,E0166
fn foo() -> ! { return; } // error
```
This error means that an attempt was made to specify the type of a variable with
a combination of a concrete type and a trait. Consider the following example:
-```compile_fail
+```compile_fail,E0172
fn foo(bar: i32+std::fmt::Display) {}
```
For example:
-```compile_fail
+```compile_fail,E0178
trait Foo {}
struct Bar<'a> {
Here's an example of this error:
-```compile_fail
+```compile_fail,E0185
trait Foo {
fn foo();
}
Here's an example of this error:
-```compile_fail
+```compile_fail,E0186
trait Foo {
fn foo(&self);
}
Trait objects need to have all associated types specified. Erroneous code
example:
-```compile_fail
+```compile_fail,E0191
trait Trait {
type Bar;
}
A type parameter was declared which shadows an existing one. An example of this
error:
-```compile_fail
+```compile_fail,E0194
trait Foo<T> {
fn do_something(&self) -> T;
fn do_something_else<T: Clone>(&self, bar: T);
Your method's lifetime parameters do not match the trait declaration.
Erroneous code example:
-```compile_fail
+```compile_fail,E0195
trait Trait {
fn bar<'a,'b:'a>(x: &'a str, y: &'b str);
}
implementing an unsafe trait. Removing the `unsafe` keyword from the inherent
implementation will resolve this error.
-```compile_fail
+```compile_fail,E0197
struct Foo;
// this will cause this error
implementation for a safe trait unsafe will cause a compiler error. Removing
the unsafe marker on the trait noted in the error will resolve this problem.
-```compile_fail
+```compile_fail,E0199
struct Foo;
trait Bar { }
implementation for an unsafe trait isn't marked as unsafe. This may be resolved
by marking the unsafe implementation as unsafe.
-```compile_fail
+```compile_fail,E0200
struct Foo;
unsafe trait Bar { }
For example:
-```compile_fail
+```compile_fail,E0201
struct Foo(u8);
impl Foo {
fields does not implement `Copy`. To fix this, you must implement `Copy` for the
mentioned field. Note that this may not be possible, as in the example of
-```compile_fail
+```compile_fail,E0204
struct Foo {
foo : Vec<u32>,
}
Here's another example that will fail:
-```compile_fail
+```compile_fail,E0204
#[derive(Copy)]
struct Foo<'a> {
ty: &'a mut bool,
variants does not implement `Copy`. To fix this, you must implement `Copy` for
the mentioned variant. Note that this may not be possible, as in the example of
-```compile_fail
+```compile_fail,E0205
enum Foo {
Bar(Vec<u32>),
Baz,
Here's another example that will fail:
-```compile_fail
+```compile_fail,E0205
#[derive(Copy)]
enum Foo<'a> {
Bar(&'a mut bool),
- Baz
+ Baz,
}
```
examples will fail, because neither `i32` (primitive type) nor `&'static Bar`
(reference to `Bar`) is a struct or enum:
-```compile_fail
+```compile_fail,E0206
type Foo = i32;
impl Copy for Foo { } // error
Suppose we have a struct `Foo` and we would like to define some methods for it.
The following definition leads to a compiler error:
-```compile_fail
+```compile_fail,E0207
struct Foo;
impl<T: Default> Foo {
As another example, suppose we have a `Maker` trait and want to establish a
type `FooMaker` that makes `Foo`s:
-```compile_fail
+```compile_fail,E0207
trait Maker {
type Item;
fn make(&mut self) -> Self::Item;
If `ForeignTrait` is a trait defined in some external crate `foo`, then the
following trait `impl` is an error:
-```compile_fail
-extern crate foo;
-use foo::ForeignTrait;
+```compile_fail,E0210
+extern crate collections;
+use collections::range::RangeArgument;
+
+impl<T> RangeArgument<T> for T { } // error
-impl<T> ForeignTrait for T { } // error
+fn main() {}
```
To work around this, it can be covered with a local type, `MyType`:
A generic type was described using parentheses rather than angle brackets. For
example:
-```compile_fail
+```compile_fail,E0214
fn main() {
let v: Vec(&str) = vec!["foo"];
}
You used an associated type which isn't defined in the trait.
Erroneous code example:
-```compile_fail
+```compile_fail,E0220
trait T1 {
type Bar;
}
An attempt was made to retrieve an associated type, but the type was ambiguous.
For example:
-```compile_fail
+```compile_fail,E0221
trait T1 {}
trait T2 {}
An attempt was made to retrieve an associated type, but the type was ambiguous.
For example:
-```compile_fail
+```compile_fail,E0223
trait MyTrait {type X; }
fn main() {
You attempted to use multiple types as bounds for a closure or trait object.
Rust does not currently support this. A simple example that causes this error:
-```compile_fail
+```compile_fail,E0225
fn main() {
let _: Box<std::io::Read + std::io::Write>;
}
E0232: r##"
The attribute must have a value. Erroneous code example:
-```compile_fail
+```compile_fail,E0232
#![feature(on_unimplemented)]
#[rustc_on_unimplemented] // error: this attribute must have a value
For example, the `Foo` struct below is defined to be generic in `T`, but the
type parameter is missing in the definition of `Bar`:
-```compile_fail
+```compile_fail,E0243
struct Foo<T> { x: T }
struct Bar { x: Foo }
For example, the `Foo` struct below has no type parameters, but is supplied
with two in the definition of `Bar`:
-```compile_fail
+```compile_fail,E0244
struct Foo { x: bool }
struct Bar<S, T> { x: Foo<S, T> }
This error indicates an attempt to use a value where a type is expected. For
example:
-```compile_fail
+```compile_fail,E0248
enum Foo {
Bar(u32)
}
A cross-crate opt-out trait was implemented on something which wasn't a struct
or enum type. Erroneous code example:
-```compile_fail
+```compile_fail,E0321
#![feature(optin_builtin_traits)]
struct Foo;
impl !Sync for Foo {}
-unsafe impl Send for &'static Foo {
+unsafe impl Send for &'static Foo {}
// error: cross-crate traits with a default impl, like `core::marker::Send`,
// can only be implemented for a struct/enum type, not
// `&'static Foo`
An associated const was implemented when another trait item was expected.
Erroneous code example:
-```compile_fail
+```compile_fail,E0323
#![feature(associated_consts)]
trait Foo {
A method was implemented when another trait item was expected. Erroneous
code example:
-```compile_fail
+```compile_fail,E0324
+#![feature(associated_consts)]
+
struct Bar;
trait Foo {
An associated type was implemented when another trait item was expected.
Erroneous code example:
-```compile_fail
+```compile_fail,E0325
+#![feature(associated_consts)]
+
struct Bar;
trait Foo {
Here's an example of this error:
-```compile_fail
+```compile_fail,E0326
+#![feature(associated_consts)]
+
trait Foo {
const BAR: bool;
}
An attempt was made to implement `Drop` on a concrete specialization of a
generic type. An example is shown below:
-```compile_fail
+```compile_fail,E0366
struct Foo<T> {
t: T
}
An attempt was made to implement `Drop` on a specialization of a generic type.
An example is shown below:
-```compile_fail
+```compile_fail,E0367
trait Foo{}
struct MyStruct<T> {
This error indicates that a binary assignment operator like `+=` or `^=` was
applied to a type that doesn't support it. For example:
-```compile_fail
+```compile_fail,E0368
let mut x = 12f32; // error: binary operation `<<` cannot be applied to
// type `f32`
operator for some type `Foo` by implementing the `std::ops::Add` trait for
`Foo`, but you find that using `+=` does not work, as in this example:
-```compile_fail
+```compile_fail,E0368
use std::ops::Add;
struct Foo(u32);
A binary operation was attempted on a type which doesn't support it.
Erroneous code example:
-```compile_fail
+```compile_fail,E0369
let x = 12f32; // error: binary operation `<<` cannot be applied to
// type `f32`
Example:
-```compile_fail
+```compile_fail,E0371
trait Foo { fn foo(&self) { } }
trait Bar: Foo { }
trait Baz: Bar { }
Example of erroneous code:
-```compile_fail
+```compile_fail,E0374
#![feature(coerce_unsized)]
use std::ops::CoerceUnsized;
Example of erroneous code:
-```compile_fail
+```compile_fail,E0375
#![feature(coerce_unsized)]
use std::ops::CoerceUnsized;
Example of erroneous code:
-```compile_fail
+```compile_fail,E0376
#![feature(coerce_unsized)]
use std::ops::CoerceUnsized;
E0390: r##"
You tried to implement methods for a primitive type. Erroneous code example:
-```compile_fail
+```compile_fail,E0390
struct Foo {
x: i32
}
The following example contains a circular dependency between two traits:
-```compile_fail
+```compile_fail,E0391
trait FirstTrait : SecondTrait {
}
This error indicates that a type or lifetime parameter has been declared
but not actually used. Here is an example that demonstrates the error:
-```compile_fail
+```compile_fail,E0392
enum Foo<T> {
- Bar
+ Bar,
}
```
```
enum Foo {
- Bar
+ Bar,
}
```
```
enum Foo<T> {
- Bar(T)
+ Bar(T),
}
```
which the pointed-at data is valid. An initial attempt (below) causes this
error:
-```compile_fail
+```compile_fail,E0392
struct Foo<'a, T> {
- x: *const T
+ x: *const T,
}
```
A type parameter which references `Self` in its default value was not specified.
Example of erroneous code:
-```compile_fail
+```compile_fail,E0393
trait A<T=Self> {}
fn together_we_will_rule_the_galaxy(son: &A) {}
The length of the platform-intrinsic function `simd_shuffle`
wasn't specified. Erroneous code example:
-```compile_fail
+```compile_fail,E0439
#![feature(platform_intrinsics)]
extern "platform-intrinsic" {
A platform-specific intrinsic function has the wrong number of type
parameters. Erroneous code example:
-```compile_fail
+```compile_fail,E0440
#![feature(repr_simd)]
#![feature(platform_intrinsics)]
An unknown platform-specific intrinsic function was used. Erroneous
code example:
-```compile_fail
+```compile_fail,E0441
#![feature(repr_simd)]
#![feature(platform_intrinsics)]
Intrinsic argument(s) and/or return value have the wrong type.
Erroneous code example:
-```compile_fail
+```compile_fail,E0442
#![feature(repr_simd)]
#![feature(platform_intrinsics)]
Intrinsic argument(s) and/or return value have the wrong type.
Erroneous code example:
-```compile_fail
+```compile_fail,E0443
#![feature(repr_simd)]
#![feature(platform_intrinsics)]
A platform-specific intrinsic function has wrong number of arguments.
Erroneous code example:
-```compile_fail
+```compile_fail,E0444
#![feature(repr_simd)]
#![feature(platform_intrinsics)]
The `typeof` keyword is currently reserved but unimplemented.
Erroneous code example:
-```compile_fail
+```compile_fail,E0516
fn main() {
let x: typeof(92) = 92;
}
A non-default implementation was already made on this type so it cannot be
specialized further. Erroneous code example:
-```compile_fail
+```compile_fail,E0520
#![feature(specialization)]
trait SpaceLlama {
/// Ok("/home/alex/bar")
/// ```
///
-/// This sort of behavior has been known to [lead to privledge escalation] when
+/// This sort of behavior has been known to [lead to privilege escalation] when
/// used incorrectly, for example.
///
-/// [lead to privledge escalation]: http://securityvulns.com/Wdocument183.html
+/// [lead to privilege escalation]: http://securityvulns.com/Wdocument183.html
///
/// # Examples
///
use fmt;
use intrinsics;
use mem;
+use ptr;
use raw;
-use sys_common::rwlock::RWLock;
use sys::stdio::Stderr;
+use sys_common::rwlock::RWLock;
use sys_common::thread_info;
use sys_common::util;
use thread;
/// Invoke a closure, capturing the cause of an unwinding panic if one occurs.
pub unsafe fn try<R, F: FnOnce() -> R>(f: F) -> Result<R, Box<Any + Send>> {
- let mut slot = None;
- let mut f = Some(f);
- let ret;
-
- {
- let mut to_run = || {
- slot = Some(f.take().unwrap()());
- };
- let fnptr = get_call(&mut to_run);
- let dataptr = &mut to_run as *mut _ as *mut u8;
- let mut any_data = 0;
- let mut any_vtable = 0;
- let fnptr = mem::transmute::<fn(&mut _), fn(*mut u8)>(fnptr);
- let r = __rust_maybe_catch_panic(fnptr,
- dataptr,
- &mut any_data,
- &mut any_vtable);
- if r == 0 {
- ret = Ok(());
- } else {
- update_panic_count(-1);
- ret = Err(mem::transmute(raw::TraitObject {
- data: any_data as *mut _,
- vtable: any_vtable as *mut _,
- }));
- }
+ struct Data<F, R> {
+ f: F,
+ r: R,
}
- debug_assert!(update_panic_count(0) == 0);
- return ret.map(|()| {
- slot.take().unwrap()
- });
+ // We do some sketchy operations with ownership here for the sake of
+ // performance. The `Data` structure is never actually fully valid, but
+ // instead it always contains at least one uninitialized field. We can only
+ // pass pointers down to `__rust_maybe_catch_panic` (can't pass objects by
+ // value), so we do all the ownership tracking here manully.
+ //
+ // Note that this is all invalid if any of these functions unwind, but the
+ // whole point of this function is to prevent that! As a result we go
+ // through a transition where:
+ //
+ // * First, only the closure we're going to call is initialized. The return
+ // value is uninitialized.
+ // * When we make the function call, the `do_call` function below, we take
+ // ownership of the function pointer, replacing it with uninitialized
+ // data. At this point the `Data` structure is entirely uninitialized, but
+ // it won't drop due to an unwind because it's owned on the other side of
+ // the catch panic.
+ // * If the closure successfully returns, we write the return value into the
+ // data's return slot. Note that `ptr::write` is used as it's overwriting
+ // uninitialized data.
+ // * Finally, when we come back out of the `__rust_maybe_catch_panic` we're
+ // in one of two states:
+ //
+ // 1. The closure didn't panic, in which case the return value was
+ // filled in. We have to be careful to `forget` the closure,
+ // however, as ownership was passed to the `do_call` function.
+ // 2. The closure panicked, in which case the return value wasn't
+ // filled in. In this case the entire `data` structure is invalid,
+ // so we forget the entire thing.
+ //
+ // Once we stack all that together we should have the "most efficient'
+ // method of calling a catch panic whilst juggling ownership.
+ let mut any_data = 0;
+ let mut any_vtable = 0;
+ let mut data = Data {
+ f: f,
+ r: mem::uninitialized(),
+ };
- fn get_call<F: FnMut()>(_: &mut F) -> fn(&mut F) {
- call
- }
+ let r = __rust_maybe_catch_panic(do_call::<F, R>,
+ &mut data as *mut _ as *mut u8,
+ &mut any_data,
+ &mut any_vtable);
+
+ return if r == 0 {
+ let Data { f, r } = data;
+ mem::forget(f);
+ debug_assert!(update_panic_count(0) == 0);
+ Ok(r)
+ } else {
+ mem::forget(data);
+ update_panic_count(-1);
+ debug_assert!(update_panic_count(0) == 0);
+ Err(mem::transmute(raw::TraitObject {
+ data: any_data as *mut _,
+ vtable: any_vtable as *mut _,
+ }))
+ };
- fn call<F: FnMut()>(f: &mut F) {
- f()
+ fn do_call<F: FnOnce() -> R, R>(data: *mut u8) {
+ unsafe {
+ let data = data as *mut Data<F, R>;
+ let f = ptr::read(&mut (*data).f);
+ ptr::write(&mut (*data).r, f());
+ }
}
}
}
}
- #[cfg(not(target_os = "nacl"))]
+ #[cfg(not(any(target_os = "nacl", target_os = "emscripten")))]
unsafe fn reset_sigpipe() {
assert!(signal(libc::SIGPIPE, libc::SIG_IGN) != !0);
}
- #[cfg(target_os = "nacl")]
+ #[cfg(any(target_os = "nacl", target_os = "emscripten"))]
unsafe fn reset_sigpipe() {}
}
#[cfg(any(target_os = "android",
target_os = "ios",
- target_os = "nacl"))]
+ target_os = "nacl",
+ target_os = "emscripten"))]
unsafe fn fallback() -> Option<OsString> { None }
#[cfg(not(any(target_os = "android",
target_os = "ios",
- target_os = "nacl")))]
+ target_os = "nacl",
+ target_os = "emscripten")))]
unsafe fn fallback() -> Option<OsString> {
#[cfg(not(target_os = "solaris"))]
unsafe fn getpwduid_r(me: libc::uid_t, passwd: &mut libc::passwd,
}
#[cfg(any(target_os = "linux",
- target_os = "android",
- target_os = "emscripten"))]
+ target_os = "android"))]
pub fn set_name(name: &CStr) {
const PR_SET_NAME: libc::c_int = 15;
// pthread wrapper only appeared in glibc 2.12, so we use syscall
name.as_ptr() as *mut libc::c_void);
}
}
- #[cfg(any(target_env = "newlib", target_os = "solaris"))]
+ #[cfg(any(target_env = "newlib", target_os = "solaris", target_os = "emscripten"))]
pub fn set_name(_name: &CStr) {
- // Newlib and Illumos has no way to set a thread name.
+ // Newlib, Illumos and Emscripten have no way to set a thread name.
}
pub fn sleep(dur: Duration) {
use self::TokenTreeOrTokenTreeVec::*;
use ast;
-use ast::{Name, Ident};
+use ast::Ident;
use syntax_pos::{self, BytePos, mk_sp, Span};
use codemap::Spanned;
use errors::FatalError;
}
pub fn nameize(p_s: &ParseSess, ms: &[TokenTree], res: &[Rc<NamedMatch>])
- -> ParseResult<HashMap<Name, Rc<NamedMatch>>> {
+ -> ParseResult<HashMap<Ident, Rc<NamedMatch>>> {
fn n_rec(p_s: &ParseSess, m: &TokenTree, res: &[Rc<NamedMatch>],
- ret_val: &mut HashMap<Name, Rc<NamedMatch>>, idx: &mut usize)
+ ret_val: &mut HashMap<Ident, Rc<NamedMatch>>, idx: &mut usize)
-> Result<(), (syntax_pos::Span, String)> {
match *m {
TokenTree::Sequence(_, ref seq) => {
}
}
TokenTree::Token(sp, MatchNt(bind_name, _)) => {
- match ret_val.entry(bind_name.name) {
+ match ret_val.entry(bind_name) {
Vacant(spot) => {
spot.insert(res[*idx].clone());
*idx += 1;
Error(syntax_pos::Span, String)
}
-pub type NamedParseResult = ParseResult<HashMap<Name, Rc<NamedMatch>>>;
+pub type NamedParseResult = ParseResult<HashMap<Ident, Rc<NamedMatch>>>;
pub type PositionalParseResult = ParseResult<Vec<Rc<NamedMatch>>>;
/// Perform a token equality check, ignoring syntax context (that is, an
let mut valid = true;
// Extract the arguments:
- let lhses = match **argument_map.get(&lhs_nm.name).unwrap() {
+ let lhses = match **argument_map.get(&lhs_nm).unwrap() {
MatchedSeq(ref s, _) => {
s.iter().map(|m| match **m {
MatchedNonterminal(NtTT(ref tt)) => {
_ => cx.span_bug(def.span, "wrong-structured lhs")
};
- let rhses = match **argument_map.get(&rhs_nm.name).unwrap() {
+ let rhses = match **argument_map.get(&rhs_nm).unwrap() {
MatchedSeq(ref s, _) => {
s.iter().map(|m| match **m {
MatchedNonterminal(NtTT(ref tt)) => (**tt).clone(),
// except according to those terms.
use self::LockstepIterSize::*;
-use ast::{Ident, Name};
+use ast::Ident;
use syntax_pos::{Span, DUMMY_SP};
use errors::{Handler, DiagnosticBuilder};
use ext::tt::macro_parser::{NamedMatch, MatchedSeq, MatchedNonterminal};
/// the unzipped tree:
stack: Vec<TtFrame>,
/* for MBE-style macro transcription */
- interpolations: HashMap<Name, Rc<NamedMatch>>,
+ interpolations: HashMap<Ident, Rc<NamedMatch>>,
imported_from: Option<Ident>,
// Some => return imported_from as the next token
/// `src` contains no `TokenTree::Sequence`s, `MatchNt`s or `SubstNt`s, `interp` can
/// (and should) be None.
pub fn new_tt_reader(sp_diag: &Handler,
- interp: Option<HashMap<Name, Rc<NamedMatch>>>,
+ interp: Option<HashMap<Ident, Rc<NamedMatch>>>,
imported_from: Option<Ident>,
src: Vec<tokenstream::TokenTree>)
-> TtReader {
/// `src` contains no `TokenTree::Sequence`s, `MatchNt`s or `SubstNt`s, `interp` can
/// (and should) be None.
pub fn new_tt_reader_with_doc_flag(sp_diag: &Handler,
- interp: Option<HashMap<Name, Rc<NamedMatch>>>,
+ interp: Option<HashMap<Ident, Rc<NamedMatch>>>,
imported_from: Option<Ident>,
src: Vec<tokenstream::TokenTree>,
desugar_doc_comments: bool)
}
fn lookup_cur_matched(r: &TtReader, name: Ident) -> Option<Rc<NamedMatch>> {
- let matched_opt = r.interpolations.get(&name.name).cloned();
+ let matched_opt = r.interpolations.get(&name).cloned();
matched_opt.map(|s| lookup_cur_matched_by_matched(r, s))
}
(active, dotdot_in_tuple_patterns, "1.10.0", Some(33627)),
// Allows `impl Trait` in function return types.
- (active, conservative_impl_trait, "1.12.0", Some(34511))
+ (active, conservative_impl_trait, "1.12.0", Some(34511)),
+
+ // Allows tuple structs and variants in more contexts,
+ // Permits numeric fields in struct expressions and patterns.
+ (active, relaxed_adts, "1.12.0", Some(35626))
);
declare_features! (
(accepted, issue_5723_bootstrap, "1.0.0", None),
(accepted, macro_rules, "1.0.0", None),
// Allows using #![no_std]
- (accepted, no_std, "1.0.0", None),
+ (accepted, no_std, "1.6.0", None),
(accepted, slicing_syntax, "1.0.0", None),
(accepted, struct_variant, "1.0.0", None),
// These are used to test this portion of the compiler, they don't actually
}
PatKind::TupleStruct(_, ref fields, ddpos)
if ddpos.is_none() && fields.is_empty() => {
- self.context.span_handler.struct_span_err(pattern.span,
- "nullary enum variants are written with \
- no trailing `( )`").emit();
+ gate_feature_post!(&self, relaxed_adts, pattern.span,
+ "empty tuple structs patterns are unstable");
}
_ => {}
}
visit::walk_impl_item(self, ii);
}
+ fn visit_variant_data(&mut self, vdata: &ast::VariantData, _: ast::Ident,
+ _: &ast::Generics, _: NodeId, span: Span) {
+ if vdata.fields().is_empty() {
+ if vdata.is_tuple() {
+ gate_feature_post!(&self, relaxed_adts, span,
+ "empty tuple structs and enum variants are unstable, \
+ use unit structs and enum variants instead");
+ }
+ }
+
+ visit::walk_struct_def(self, vdata)
+ }
+
fn visit_vis(&mut self, vis: &ast::Visibility) {
let span = match *vis {
ast::Visibility::Crate(span) => span,
}
}
+ pub fn parse_field_name(&mut self) -> PResult<'a, Ident> {
+ if let token::Literal(token::Integer(name), None) = self.token {
+ self.bump();
+ Ok(Ident::with_empty_ctxt(name))
+ } else {
+ self.parse_ident()
+ }
+ }
+
/// Parse ident COLON expr
pub fn parse_field(&mut self) -> PResult<'a, Field> {
let lo = self.span.lo;
- let i = self.parse_ident()?;
+ let i = self.parse_field_name()?;
let hi = self.last_span.hi;
self.expect(&token::Colon)?;
let e = self.parse_expr()?;
// Check if a colon exists one ahead. This means we're parsing a fieldname.
let (subpat, fieldname, is_shorthand) = if self.look_ahead(1, |t| t == &token::Colon) {
// Parsing a pattern of the form "fieldname: pat"
- let fieldname = self.parse_ident()?;
+ let fieldname = self.parse_field_name()?;
self.bump();
let pat = self.parse_pat()?;
hi = pat.span.hi;
}
/// Parse a structure field
- fn parse_name_and_ty(&mut self, pr: Visibility,
- attrs: Vec<Attribute> ) -> PResult<'a, StructField> {
- let lo = match pr {
- Visibility::Inherited => self.span.lo,
- _ => self.last_span.lo,
- };
+ fn parse_name_and_ty(&mut self,
+ lo: BytePos,
+ vis: Visibility,
+ attrs: Vec<Attribute>)
+ -> PResult<'a, StructField> {
let name = self.parse_ident()?;
self.expect(&token::Colon)?;
let ty = self.parse_ty_sum()?;
Ok(StructField {
span: mk_sp(lo, self.last_span.hi),
ident: Some(name),
- vis: pr,
+ vis: vis,
id: ast::DUMMY_NODE_ID,
ty: ty,
attrs: attrs,
/// Parse a structure field declaration
pub fn parse_single_struct_field(&mut self,
+ lo: BytePos,
vis: Visibility,
attrs: Vec<Attribute> )
-> PResult<'a, StructField> {
- let a_var = self.parse_name_and_ty(vis, attrs)?;
+ let a_var = self.parse_name_and_ty(lo, vis, attrs)?;
match self.token {
token::Comma => {
self.bump();
/// Parse an element of a struct definition
fn parse_struct_decl_field(&mut self) -> PResult<'a, StructField> {
let attrs = self.parse_outer_attributes()?;
+ let lo = self.span.lo;
let vis = self.parse_visibility(true)?;
- self.parse_single_struct_field(vis, attrs)
+ self.parse_single_struct_field(lo, vis, attrs)
}
// If `allow_path` is false, just parse the `pub` in `pub(path)` (but still parse `pub(crate)`)
ts: InternalTS,
}
+// This indicates the maximum size for a leaf in the concatenation algorithm.
+// If two leafs will be collectively smaller than this, they will be merged.
+// If a leaf is larger than this, it will be concatenated at the top.
+const LEAF_SIZE : usize = 32;
+
// NB If Leaf access proves to be slow, inroducing a secondary Leaf without the bounds
// for unsliced Leafs may lead to some performance improvemenet.
#[derive(Clone, PartialEq, Eq, Hash, RustcEncodable, RustcDecodable)]
}
}
}
+
+ fn to_vec(&self) -> Vec<&TokenTree> {
+ let mut res = Vec::with_capacity(self.len());
+ fn traverse_and_append<'a>(res: &mut Vec<&'a TokenTree>, ts: &'a InternalTS) {
+ match *ts {
+ InternalTS::Empty(..) => {},
+ InternalTS::Leaf { ref tts, offset, len, .. } => {
+ let mut to_app = tts[offset..offset + len].iter().collect();
+ res.append(&mut to_app);
+ }
+ InternalTS::Node { ref left, ref right, .. } => {
+ traverse_and_append(res, left);
+ traverse_and_append(res, right);
+ }
+ }
+ }
+ traverse_and_append(&mut res, self);
+ res
+ }
+
+ fn to_tts(&self) -> Vec<TokenTree> {
+ self.to_vec().into_iter().cloned().collect::<Vec<TokenTree>>()
+ }
+
+ // Returns an internal node's children.
+ fn children(&self) -> Option<(Rc<InternalTS>, Rc<InternalTS>)> {
+ match *self {
+ InternalTS::Node { ref left, ref right, .. } => Some((left.clone(), right.clone())),
+ _ => None,
+ }
+ }
}
/// TokenStream operators include basic destructuring, boolean operations, `maybe_...`
///
/// `maybe_path_prefix("a::b::c(a,b,c).foo()") -> (a::b::c, "(a,b,c).foo()")`
impl TokenStream {
+ // Construct an empty node with a dummy span.
pub fn mk_empty() -> TokenStream {
TokenStream { ts: InternalTS::Empty(DUMMY_SP) }
}
+ // Construct an empty node with the provided span.
fn mk_spanned_empty(sp: Span) -> TokenStream {
TokenStream { ts: InternalTS::Empty(sp) }
}
+ // Construct a leaf node with a 0 offset and length equivalent to the input.
fn mk_leaf(tts: Rc<Vec<TokenTree>>, sp: Span) -> TokenStream {
let len = tts.len();
TokenStream {
}
}
+ // Construct a leaf node with the provided values.
fn mk_sub_leaf(tts: Rc<Vec<TokenTree>>, offset: usize, len: usize, sp: Span) -> TokenStream {
TokenStream {
ts: InternalTS::Leaf {
}
}
+ // Construct an internal node with the provided values.
fn mk_int_node(left: Rc<InternalTS>,
right: Rc<InternalTS>,
len: usize,
}
}
- /// Concatenates two TokenStreams into a new TokenStream
+ /// Concatenates two TokenStreams into a new TokenStream.
pub fn concat(left: TokenStream, right: TokenStream) -> TokenStream {
- let new_len = left.len() + right.len();
- let new_span = combine_spans(left.span(), right.span());
- TokenStream::mk_int_node(Rc::new(left.ts), Rc::new(right.ts), new_len, new_span)
+ // This internal procedure performs 'aggressive compacting' during concatenation as
+ // follows:
+ // - If the nodes' combined total total length is less than 32, we copy both of
+ // them into a new vector and build a new leaf node.
+ // - If one node is an internal node and the other is a 'small' leaf (length<32),
+ // we recur down the internal node on the appropriate side.
+ // - Otherwise, we construct a new internal node that points to them as left and
+ // right.
+ fn concat_internal(left: Rc<InternalTS>, right: Rc<InternalTS>) -> TokenStream {
+ let llen = left.len();
+ let rlen = right.len();
+ let len = llen + rlen;
+ let span = combine_spans(left.span(), right.span());
+ if len <= LEAF_SIZE {
+ let mut new_vec = left.to_tts();
+ let mut rvec = right.to_tts();
+ new_vec.append(&mut rvec);
+ return TokenStream::mk_leaf(Rc::new(new_vec), span);
+ }
+
+ match (left.children(), right.children()) {
+ (Some((lleft, lright)), None) => {
+ if rlen <= LEAF_SIZE {
+ let new_right = concat_internal(lright, right);
+ TokenStream::mk_int_node(lleft, Rc::new(new_right.ts), len, span)
+ } else {
+ TokenStream::mk_int_node(left, right, len, span)
+ }
+ }
+ (None, Some((rleft, rright))) => {
+ if rlen <= LEAF_SIZE {
+ let new_left = concat_internal(left, rleft);
+ TokenStream::mk_int_node(Rc::new(new_left.ts), rright, len, span)
+ } else {
+ TokenStream::mk_int_node(left, right, len, span)
+ }
+ }
+ (_, _) => TokenStream::mk_int_node(left, right, len, span),
+ }
+ }
+
+ if left.is_empty() {
+ right
+ } else if right.is_empty() {
+ left
+ } else {
+ concat_internal(Rc::new(left.ts), Rc::new(right.ts))
+ }
}
/// Indicate if the TokenStream is empty.
/// Convert a TokenStream into a vector of borrowed TokenTrees.
pub fn to_vec(&self) -> Vec<&TokenTree> {
- fn internal_to_vec(ts: &InternalTS) -> Vec<&TokenTree> {
- match *ts {
- InternalTS::Empty(..) => Vec::new(),
- InternalTS::Leaf { ref tts, offset, len, .. } => {
- tts[offset..offset + len].iter().collect()
- }
- InternalTS::Node { ref left, ref right, .. } => {
- let mut v1 = internal_to_vec(left);
- let mut v2 = internal_to_vec(right);
- v1.append(&mut v2);
- v1
- }
- }
- }
- internal_to_vec(&self.ts)
+ self.ts.to_vec()
}
/// Convert a TokenStream into a vector of TokenTrees (by cloning the TokenTrees).
/// (This operation is an O(n) deep copy of the underlying structure.)
pub fn to_tts(&self) -> Vec<TokenTree> {
- self.to_vec().into_iter().cloned().collect::<Vec<TokenTree>>()
+ self.ts.to_tts()
}
/// Return the TokenStream's span.
pub nocapture: bool,
pub color: ColorConfig,
pub quiet: bool,
+ pub test_threads: Option<usize>,
}
impl TestOpts {
nocapture: false,
color: AutoColor,
quiet: false,
+ test_threads: None,
}
}
}
of stdout", "PATH"),
getopts::optflag("", "nocapture", "don't capture stdout/stderr of each \
task, allow printing directly"),
+ getopts::optopt("", "test-threads", "Number of threads used for running tests \
+ in parallel", "n_threads"),
getopts::optflag("q", "quiet", "Display one character per test instead of one line"),
getopts::optopt("", "color", "Configure coloring of output:
auto = colorize if stdout is a tty and tests are run on serially (default);
tests whose names contain the filter are run.
By default, all tests are run in parallel. This can be altered with the
-RUST_TEST_THREADS environment variable when running tests (set it to 1).
+--test-threads flag or the RUST_TEST_THREADS environment variable when running
+tests (set it to 1).
All tests have their standard output and standard error captured by default.
This can be overridden with the --nocapture flag or setting RUST_TEST_NOCAPTURE
};
}
+ let test_threads = match matches.opt_str("test-threads") {
+ Some(n_str) =>
+ match n_str.parse::<usize>() {
+ Ok(n) => Some(n),
+ Err(e) =>
+ return Some(Err(format!("argument for --test-threads must be a number > 0 \
+ (error: {})", e)))
+ },
+ None =>
+ None,
+ };
+
let color = match matches.opt_str("color").as_ref().map(|s| &**s) {
Some("auto") | None => AutoColor,
Some("always") => AlwaysColor,
nocapture: nocapture,
color: color,
quiet: quiet,
+ test_threads: test_threads,
};
Some(Ok(test_opts))
}
});
- // It's tempting to just spawn all the tests at once, but since we have
- // many tests that run in other processes we would be making a big mess.
- let concurrency = get_concurrency();
+ let concurrency = match opts.test_threads {
+ Some(n) => n,
+ None => get_concurrency(),
+ };
let mut remaining = filtered_tests;
remaining.reverse();
pub const unwinder_private_data_size: usize = 2;
#[cfg(target_arch = "asmjs")]
-// FIXME: Copied from arm. Need to confirm.
pub const unwinder_private_data_size: usize = 20;
#[repr(C)]
--- /dev/null
+// Copyright 2016 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.
+
+// ignore-tidy-linelength
+
+// We specify -Z incremental here because we want to test the partitioning for
+// incremental compilation
+// compile-flags:-Zprint-trans-items=lazy -Zincremental=tmp/partitioning-tests/vtable-through-const
+
+// This test case makes sure, that references made through constants are
+// recorded properly in the InliningMap.
+
+mod mod1 {
+ pub trait Trait1 {
+ fn do_something(&self) {}
+ fn do_something_else(&self) {}
+ }
+
+ impl Trait1 for u32 {}
+
+ pub trait Trait1Gen<T> {
+ fn do_something(&self, x: T) -> T;
+ fn do_something_else(&self, x: T) -> T;
+ }
+
+ impl<T> Trait1Gen<T> for u32 {
+ fn do_something(&self, x: T) -> T { x }
+ fn do_something_else(&self, x: T) -> T { x }
+ }
+
+ fn id<T>(x: T) -> T { x }
+
+ // These are referenced, so they produce trans-items (see main())
+ pub const TRAIT1_REF: &'static Trait1 = &0u32 as &Trait1;
+ pub const TRAIT1_GEN_REF: &'static Trait1Gen<u8> = &0u32 as &Trait1Gen<u8>;
+ pub const ID_CHAR: fn(char) -> char = id::<char>;
+
+
+
+ pub trait Trait2 {
+ fn do_something(&self) {}
+ fn do_something_else(&self) {}
+ }
+
+ impl Trait2 for u32 {}
+
+ pub trait Trait2Gen<T> {
+ fn do_something(&self, x: T) -> T;
+ fn do_something_else(&self, x: T) -> T;
+ }
+
+ impl<T> Trait2Gen<T> for u32 {
+ fn do_something(&self, x: T) -> T { x }
+ fn do_something_else(&self, x: T) -> T { x }
+ }
+
+ // These are not referenced, so they do not produce trans-items
+ pub const TRAIT2_REF: &'static Trait2 = &0u32 as &Trait2;
+ pub const TRAIT2_GEN_REF: &'static Trait2Gen<u8> = &0u32 as &Trait2Gen<u8>;
+ pub const ID_I64: fn(i64) -> i64 = id::<i64>;
+}
+
+//~ TRANS_ITEM fn vtable_through_const::main[0] @@ vtable_through_const[External]
+fn main() {
+
+ // Since Trait1::do_something() is instantiated via its default implementation,
+ // it is considered a generic and is instantiated here only because it is
+ // referenced in this module.
+ //~ TRANS_ITEM fn vtable_through_const::mod1[0]::Trait1[0]::do_something_else[0]<u32> @@ vtable_through_const[Internal]
+
+ // Although it is never used, Trait1::do_something_else() has to be
+ // instantiated locally here too, otherwise the <&u32 as &Trait1> vtable
+ // could not be fully constructed.
+ //~ TRANS_ITEM fn vtable_through_const::mod1[0]::Trait1[0]::do_something[0]<u32> @@ vtable_through_const[Internal]
+ mod1::TRAIT1_REF.do_something();
+
+ // Same as above
+ //~ TRANS_ITEM fn vtable_through_const::mod1[0]::{{impl}}[1]::do_something[0]<u8> @@ vtable_through_const[Internal]
+ //~ TRANS_ITEM fn vtable_through_const::mod1[0]::{{impl}}[1]::do_something_else[0]<u8> @@ vtable_through_const[Internal]
+ mod1::TRAIT1_GEN_REF.do_something(0u8);
+
+ //~ TRANS_ITEM fn vtable_through_const::mod1[0]::id[0]<char> @@ vtable_through_const[Internal]
+ mod1::ID_CHAR('x');
+}
+
+//~ TRANS_ITEM drop-glue i8
fn main() {
LinkedList::new() += 1; //~ ERROR E0368
//~^ ERROR E0067
+ //~^^ NOTE invalid expression for left-hand side
+ //~| NOTE cannot use `+=` on type `std::collections::LinkedList<_>`
}
// option. This file may not be copied, modified, or distributed
// except according to those terms.
-enum Foo { FirstValue(i32) }
+enum Foo {}
fn main() {
- let u = Foo::FirstValue { value: 0 };
- //~^ ERROR `Foo::FirstValue` does not name a struct or a struct variant [E0071]
+ let u = Foo { value: 0 };
+ //~^ ERROR `Foo` does not name a struct or a struct variant [E0071]
//~| NOTE not a struct
let t = u32 { value: 4 };
#[start]
fn foo(argc: isize, argv: *const *const u8) -> isize {}
+//~^ NOTE previous `start` function here
#[start]
-fn f(argc: isize, argv: *const *const u8) -> isize {} //~ ERROR E0138
+fn f(argc: isize, argv: *const *const u8) -> isize {}
+//~^ ERROR E0138
+//~| NOTE multiple `start` functions
}
}
-use foo::MyTrait::do_something; //~ ERROR E0253
+use foo::MyTrait::do_something;
+ //~^ ERROR E0253
+ //~|NOTE cannot be imported directly
fn main() {}
// except according to those terms.
extern crate collections;
+//~^ NOTE previous import of `collections` here
mod foo {
pub trait collections {
}
}
-use foo::collections; //~ ERROR E0254
+use foo::collections;
+//~^ ERROR E0254
+//~| NOTE already imported
fn main() {}
fn main() {
let w = || { break; }; //~ ERROR E0267
+ //~| NOTE cannot break inside of a closure
}
fn main() {
break; //~ ERROR E0268
+ //~| NOTE cannot break outside of a loop
}
--- /dev/null
+// Copyright 2016 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.
+
+mod foo {
+ pub const X: u32 = 1;
+}
+
+pub use foo as foo2; //~ ERROR E0365
+
+fn main() {}
--- /dev/null
+// Copyright 2016 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(dead_code)]
+
+#[deny(overflowing_literals)]
+#[repr(i64)]
+enum Foo {
+ X = 0x7fffffffffffffff,
+ Y, //~ ERROR E0370
+}
+
+fn main() {}
--- /dev/null
+// Copyright 2016 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.
+
+#![feature(coerce_unsized)]
+use std::ops::CoerceUnsized;
+
+struct Foo<T: ?Sized> {
+ a: i32,
+}
+
+impl<T, U> CoerceUnsized<Foo<U>> for Foo<T> //~ ERROR E0374
+ where T: CoerceUnsized<U> {}
+
+fn main() {}
--- /dev/null
+// Copyright 2016 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.
+
+#![feature(coerce_unsized)]
+use std::ops::CoerceUnsized;
+
+struct Foo<T: ?Sized, U: ?Sized> {
+ a: i32,
+ b: T,
+ c: U,
+}
+
+impl<T, U> CoerceUnsized<Foo<U, T>> for Foo<T, U> {} //~ ERROR E0375
+
+fn main() {}
--- /dev/null
+// Copyright 2016 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.
+
+#![feature(coerce_unsized)]
+use std::ops::CoerceUnsized;
+
+struct Foo<T: ?Sized> {
+ a: T,
+}
+
+impl<T, U> CoerceUnsized<U> for Foo<T> {} //~ ERROR E0376
+
+fn main() {}
--- /dev/null
+// Copyright 2016 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.
+
+static X: i32 = 1;
+const C: i32 = 2;
+
+const CR: &'static mut i32 = &mut C; //~ ERROR E0017
+ //~| ERROR E0017
+static STATIC_REF: &'static mut i32 = &mut X; //~ ERROR E0017
+ //~| ERROR E0017
+ //~| ERROR E0388
+static CONST_REF: &'static mut i32 = &mut C; //~ ERROR E0017
+ //~| ERROR E0017
+
+fn main() {}
--- /dev/null
+// Copyright 2016 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.
+
+struct FancyNum {
+ num: u8,
+}
+
+fn main() {
+ let mut fancy = FancyNum{ num: 5 };
+ let fancy_ref = &(&mut fancy);
+ fancy_ref.num = 6; //~ ERROR E0389
+ println!("{}", fancy_ref.num);
+}
--- /dev/null
+// Copyright 2016 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.
+
+struct Foo {
+ x: i32
+}
+
+impl *mut Foo {} //~ ERROR E0390
+
+fn main() {
+}
--- /dev/null
+// Copyright 2016 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.
+
+enum Foo<T> { Bar } //~ ERROR E0392
+
+fn main() {
+}
--- /dev/null
+// Copyright 2016 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.
+
+trait A<T=Self> {}
+
+fn together_we_will_rule_the_galaxy(son: &A) {} //~ ERROR E0393
+
+fn main() {
+}
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+#![feature(relaxed_adts)]
+
pub struct XEmpty1 {}
pub struct XEmpty2;
+pub struct XEmpty6();
pub enum XE {
XEmpty3 {},
XEmpty4,
+ XEmpty5(),
}
//~^ ERROR mismatched types
//~| expected type `&[i32]`
//~| found type `[{integer}; 1]`
- //~| expected &-ptr, found array of 1 elements
+ //~| expected &[i32], found array of 1 elements
}
let _y: &Trait = x; //~ ERROR mismatched types
//~| expected type `&Trait`
//~| found type `Box<Trait>`
- //~| expected &-ptr, found box
+ //~| expected &Trait, found box
}
//~^ ERROR mismatched types
//~| expected type `T`
//~| found type `&_`
- //~| expected trait T, found &-ptr
+ //~| expected trait T, found reference
let &&&x = &(&1isize as &T);
//~^ ERROR mismatched types
//~| expected type `T`
//~| found type `&_`
- //~| expected trait T, found &-ptr
+ //~| expected trait T, found reference
let box box x = box 1isize as Box<T>;
//~^ ERROR mismatched types
//~| expected type `T`
}
pub fn main() {
- // Test that we cannot convert from *-ptr to &-ptr
+ // Test that we cannot convert from *-ptr to &S and &T
let x: *const S = &S;
let y: &S = x; //~ ERROR mismatched types
let y: &T = x; //~ ERROR mismatched types
- // Test that we cannot convert from *-ptr to &-ptr (mut version)
+ // Test that we cannot convert from *-ptr to &S and &T (mut version)
let x: *mut S = &mut S;
let y: &S = x; //~ ERROR mismatched types
let y: &T = x; //~ ERROR mismatched types
// aux-build:empty-struct.rs
+#![feature(relaxed_adts)]
+
extern crate empty_struct;
use empty_struct::*;
let e1 = Empty1 {};
let xe1 = XEmpty1 {};
- // Rejected by parser as yet
- // match e1 {
- // Empty1() => () // ERROR unresolved enum variant, struct or const `Empty1`
- // }
- // match xe1 {
- // XEmpty1() => () // ERROR unresolved enum variant, struct or const `XEmpty1`
- // }
+ match e1 {
+ Empty1() => () //~ ERROR unresolved variant or struct `Empty1`
+ }
+ match xe1 {
+ XEmpty1() => () //~ ERROR unresolved variant or struct `XEmpty1`
+ }
match e1 {
Empty1(..) => () //~ ERROR unresolved variant or struct `Empty1`
}
// aux-build:empty-struct.rs
+#![feature(relaxed_adts)]
+
extern crate empty_struct;
use empty_struct::*;
let e3 = E::Empty3 {};
let xe3 = XE::XEmpty3 {};
- // Rejected by parser as yet
- // match e3 {
- // E::Empty3() => () // ERROR `E::Empty3` does not name a tuple variant or a tuple struct
- // }
- // match xe3 {
- // E::Empty3() => () // ERROR `XE::XEmpty3` does not name a tuple variant or a tuple struct
- // }
+ match e3 {
+ E::Empty3() => () //~ ERROR `E::Empty3` does not name a tuple variant or a tuple struct
+ }
+ match xe3 {
+ XE::XEmpty3() => () //~ ERROR `XE::XEmpty3` does not name a tuple variant or a tuple struct
+ }
match e3 {
E::Empty3(..) => () //~ ERROR `E::Empty3` does not name a tuple variant or a tuple struct
}
--- /dev/null
+// 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.
+
+// Can't use unit struct as enum pattern
+
+// aux-build:empty-struct.rs
+
+#![feature(relaxed_adts)]
+
+extern crate empty_struct;
+use empty_struct::*;
+
+struct Empty2();
+
+enum E {
+ Empty4()
+}
+
+// remove attribute after warning cycle and promoting warnings to errors
+fn main() {
+ let e2 = Empty2();
+ let e4 = E::Empty4();
+ let xe6 = XEmpty6();
+ let xe5 = XE::XEmpty5();
+
+ match e2 {
+ Empty2 => () //~ ERROR `Empty2` does not name a unit variant, unit struct or a constant
+ }
+ match xe6 {
+ XEmpty6 => () //~ ERROR `XEmpty6` does not name a unit variant, unit struct or a constant
+ }
+
+ match e4 {
+ E::Empty4 => () //~ ERROR `E::Empty4` does not name a unit variant, unit struct or a
+ }
+ match xe5 {
+ XE::XEmpty5 => (), //~ ERROR `XE::XEmpty5` does not name a unit variant, unit struct or a
+ _ => {},
+ }
+}
--- /dev/null
+// 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.
+
+// Can't use unit struct as enum pattern
+
+// aux-build:empty-struct.rs
+
+#![feature(relaxed_adts)]
+
+extern crate empty_struct;
+use empty_struct::*;
+
+struct Empty2;
+
+enum E {
+ Empty4
+}
+
+// remove attribute after warning cycle and promoting warnings to errors
+fn main() {
+ let e2 = Empty2;
+ let e4 = E::Empty4;
+ let xe2 = XEmpty2;
+ let xe4 = XE::XEmpty4;
+
+ match e2 {
+ Empty2(..) => () //~ ERROR `Empty2` does not name a tuple variant or a tuple struct
+ //~^ WARNING hard error
+ }
+ match xe2 {
+ XEmpty2(..) => () //~ ERROR `XEmpty2` does not name a tuple variant or a tuple struct
+ //~^ WARNING hard error
+ }
+
+ match e4 {
+ E::Empty4(..) => () //~ ERROR `E::Empty4` does not name a tuple variant or a tuple struct
+ //~^ WARNING hard error
+ }
+ match xe4 {
+ XE::XEmpty4(..) => (), //~ ERROR `XE::XEmpty4` does not name a tuple variant or a tuple
+ //~^ WARNING hard error
+ _ => {},
+ }
+}
--- /dev/null
+// 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.
+
+// Can't use unit struct as enum pattern
+
+// aux-build:empty-struct.rs
+
+#![feature(relaxed_adts)]
+
+extern crate empty_struct;
+use empty_struct::*;
+
+struct Empty2;
+
+enum E {
+ Empty4
+}
+
+// remove attribute after warning cycle and promoting warnings to errors
+fn main() {
+ let e2 = Empty2;
+ let e4 = E::Empty4;
+ let xe2 = XEmpty2;
+ let xe4 = XE::XEmpty4;
+
+ match e2 {
+ Empty2() => () //~ ERROR `Empty2` does not name a tuple variant or a tuple struct
+ }
+ match xe2 {
+ XEmpty2() => () //~ ERROR `XEmpty2` does not name a tuple variant or a tuple struct
+ }
+
+ match e4 {
+ E::Empty4() => () //~ ERROR `E::Empty4` does not name a tuple variant or a tuple struct
+ }
+ match xe4 {
+ XE::XEmpty4() => (), //~ ERROR `XE::XEmpty4` does not name a tuple variant or a tuple
+ _ => {},
+ }
+}
+++ /dev/null
-// 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.
-
-// Can't use unit struct as enum pattern
-
-// aux-build:empty-struct.rs
-
-extern crate empty_struct;
-use empty_struct::*;
-
-struct Empty2;
-
-enum E {
- Empty4
-}
-
-// remove attribute after warning cycle and promoting warnings to errors
-fn main() {
- let e2 = Empty2;
- let e4 = E::Empty4;
- let xe2 = XEmpty2;
- let xe4 = XE::XEmpty4;
-
- // Rejected by parser as yet
- // match e2 {
- // Empty2() => () // ERROR `Empty2` does not name a tuple variant or a tuple struct
- // }
- // match xe2 {
- // XEmpty2() => () // ERROR `XEmpty2` does not name a tuple variant or a tuple struct
- // }
- match e2 {
- Empty2(..) => () //~ ERROR `Empty2` does not name a tuple variant or a tuple struct
- //~^ WARNING hard error
- }
- match xe2 {
- XEmpty2(..) => () //~ ERROR `XEmpty2` does not name a tuple variant or a tuple struct
- //~^ WARNING hard error
- }
- // Rejected by parser as yet
- // match e4 {
- // E::Empty4() => () // ERROR `E::Empty4` does not name a tuple variant or a tuple struct
- // }
- // match xe4 {
- // XE::XEmpty4() => (), // ERROR `XE::XEmpty4` does not name a tuple variant or a tuple
- // _ => {},
- // }
- match e4 {
- E::Empty4(..) => () //~ ERROR `E::Empty4` does not name a tuple variant or a tuple struct
- //~^ WARNING hard error
- }
- match xe4 {
- XE::XEmpty4(..) => (), //~ ERROR `XE::XEmpty4` does not name a tuple variant or a tuple
- //~^ WARNING hard error
- _ => {},
- }
-}
--- /dev/null
+// Copyright 2016 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.
+
+struct Z(u8, u8);
+
+enum E {
+ U(u8, u8),
+}
+
+fn main() {
+ match Z(0, 1) {
+ Z{..} => {} //~ ERROR tuple structs and variants in struct patterns are unstable
+ }
+ match E::U(0, 1) {
+ E::U{..} => {} //~ ERROR tuple structs and variants in struct patterns are unstable
+ }
+
+ let z1 = Z(0, 1);
+ let z2 = Z { ..z1 }; //~ ERROR tuple structs and variants in struct patterns are unstable
+}
--- /dev/null
+// Copyright 2016 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.
+
+struct S(); //~ ERROR empty tuple structs and enum variants are unstable
+struct Z(u8, u8);
+
+enum E {
+ V(), //~ ERROR empty tuple structs and enum variants are unstable
+ U(u8, u8),
+}
+
+fn main() {
+ match S() {
+ S() => {} //~ ERROR empty tuple structs patterns are unstable
+ }
+ match E::V() {
+ E::V() => {} //~ ERROR empty tuple structs patterns are unstable
+ }
+}
+++ /dev/null
-// Copyright 2014 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.
-
-// For style and consistency reasons, non-parametrized enum variants must
-// be used simply as `ident` instead of `ident ()`.
-// This test-case covers enum declaration.
-
-enum Foo {
- Bar(), //~ ERROR empty tuple structs and enum variants are not allowed
- //~^ HELP remove trailing `()` to make a unit struct or unit enum variant
- Baz(), //~ ERROR empty tuple structs and enum variants are not allowed
- //~^ HELP remove trailing `()` to make a unit struct or unit enum variant
- Bazar
-}
-
-fn main() {
- println!("{}", match Bar { Bar => 1, Baz => 2, Bazar => 3 }) //~ ERROR unresolved name `Bar`
-}
+++ /dev/null
-// Copyright 2014 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.
-
-// compile-flags: -Z continue-parse-after-error
-
-// For style and consistency reasons, non-parametrized enum variants must
-// be used simply as `ident` instead of `ident ()`.
-// This test-case covers enum matching.
-
-enum Foo {
- Bar,
- Baz,
- Bazar
-}
-
-fn main() {
- println!("{}", match Bar {
- Bar() => 1, //~ ERROR nullary enum variants are written with no trailing `( )`
- Baz() => 2, //~ ERROR nullary enum variants are written with no trailing `( )`
- Bazar => 3
- })
-}
//~^ ERROR mismatched types
//~| expected type `fn(&mut __test::test::Bencher)`
//~| found type `fn(isize) {bar}`
-//~| expected &-ptr, found isize
+//~| expected mutable reference, found isize
//~^ ERROR mismatched types
//~| expected type `&str`
//~| found type `Slice<_>`
- //~| expected &-ptr, found struct `Slice`
+ //~| expected &str, found struct `Slice`
}
// option. This file may not be copied, modified, or distributed
// except according to those terms.
-struct TS ( //~ ERROR empty tuple structs and enum variants are not allowed
+struct TS ( //~ ERROR empty tuple structs and enum variants are unstable
#[cfg(untrue)]
i32,
);
enum E {
- TV ( //~ ERROR empty tuple structs and enum variants are not allowed
+ TV ( //~ ERROR empty tuple structs and enum variants are unstable
#[cfg(untrue)]
i32,
)
(*p)(()) //~ ERROR mismatched types
//~| expected type `&mut ()`
//~| found type `()`
- //~| expected &-ptr, found ()
+ //~| expected &mut (), found ()
}
fn main() {}
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+#![feature(relaxed_adts)]
+
enum MyOption<T> {
MySome(T),
MyNone,
fn main() {
match MyOption::MySome(42) {
MyOption::MySome { x: 42 } => (),
- //~^ ERROR `MyOption::MySome` does not name a struct or a struct variant
+ //~^ ERROR struct `MyOption::MySome` does not have a field named `x`
+ //~| ERROR pattern does not mention field `0`
_ => (),
}
}
impl<'a, T> Fn<(&'a T,)> for Foo {
extern "rust-call" fn call(&self, (_,): (T,)) {}
//~^ ERROR: has an incompatible type for trait
- //~| expected &-ptr
+ //~| expected reference
}
impl<'a, T> FnMut<(&'a T,)> for Foo {
extern "rust-call" fn call_mut(&mut self, (_,): (T,)) {}
//~^ ERROR: has an incompatible type for trait
- //~| expected &-ptr
+ //~| expected reference
}
impl<'a, T> FnOnce<(&'a T,)> for Foo {
extern "rust-call" fn call_once(self, (_,): (T,)) {}
//~^ ERROR: has an incompatible type for trait
- //~| expected &-ptr
+ //~| expected reference
}
fn main() {}
($thing:expr) => {
$thing = 42;
//~^ ERROR invalid left-hand side expression
+ //~^^ NOTE left-hand of expression not valid
}
}
+++ /dev/null
-// 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.
-
-struct Foo(u32);
-struct Bar;
-
-enum Enum {
- Foo(u32),
- Bar
-}
-
-fn main() {
- let x = Foo(1);
- Foo { ..x }; //~ ERROR `Foo` does not name a struct or a struct variant
- let Foo { .. } = x; //~ ERROR `Foo` does not name a struct
-
- let x = Bar;
- Bar { ..x };
- let Bar { .. } = x;
-
- match Enum::Bar {
- Enum::Bar { .. }
- => {}
- Enum::Foo { .. } //~ ERROR `Enum::Foo` does not name a struct
- => {}
- }
-}
--- /dev/null
+// Copyright 2016 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.
+
+pub use inner::C;
+
+mod inner {
+ trait A {
+ fn a(&self) { }
+ }
+
+ pub trait B {
+ fn b(&self) { }
+ }
+
+ pub trait C: A + B { //~ ERROR private trait in public interface
+ //~^ WARN will become a hard error
+ fn c(&self) { }
+ }
+
+ impl A for i32 {}
+ impl B for i32 {}
+ impl C for i32 {}
+
+}
+
+fn main() {
+ // A is private
+ // B is pub, not reexported
+ // C : A + B is pub, reexported
+
+ // 0.a(); // can't call
+ // 0.b(); // can't call
+ 0.c(); // ok
+
+ C::a(&0); // can call
+ C::b(&0); // can call
+ C::c(&0); // ok
+}
fn bar(d: u8) { }
bar(&mut $d);
//~^ ERROR mismatched types
- //~| expected u8, found &-ptr
+ //~| expected u8, found &mut u8
//~| expected type `u8`
//~| found type `&mut u8`
}}
// option. This file may not be copied, modified, or distributed
// except according to those terms.
-#![feature(rustc_attrs)]
#![allow(unused)]
struct SemiPriv;
mod m1 {
struct Priv;
impl ::SemiPriv {
- pub fn f(_: Priv) {} //~ WARN private type in public interface
+ pub fn f(_: Priv) {} //~ ERROR private type in public interface
//~^ WARNING hard error
}
mod m2 {
struct Priv;
impl ::std::ops::Deref for ::SemiPriv {
- type Target = Priv; //~ WARN private type in public interface
+ type Target = Priv; //~ ERROR private type in public interface
//~^ WARNING hard error
fn deref(&self) -> &Self::Target { unimplemented!() }
}
mod m3 {
struct Priv;
impl ::SemiPrivTrait for () {
- type Assoc = Priv; //~ WARN private type in public interface
+ type Assoc = Priv; //~ ERROR private type in public interface
//~^ WARNING hard error
}
}
-#[rustc_error]
-fn main() {} //~ ERROR compilation successful
+fn main() {}
--- /dev/null
+// Copyright 2016 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.
+
+macro_rules! m { ($t:tt) => { $t } }
+
+fn main() {
+ m!($t); //~ ERROR unknown macro variable
+ //~| ERROR expected expression
+}
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+#![feature(relaxed_adts)]
+
struct NonCopyable(());
fn main() {
- let z = NonCopyable{ p: () }; //~ ERROR `NonCopyable` does not name a struct or a struct variant
+ let z = NonCopyable{ p: () }; //~ ERROR structure `NonCopyable` has no field named `p`
}
//~^ ERROR mismatched types
//~| expected type `(bool, bool)`
//~| found type `&_`
-//~| expected tuple, found &-ptr
+//~| expected tuple, found reference
}
//~^ ERROR mismatched types
//~| expected type `()`
//~| found type `&_`
- //~| expected (), found &-ptr
+ //~| expected (), found reference
}
//~^ ERROR mismatched types
//~| expected type `Box<BarStruct>`
//~| found type `&'a mut BarStruct`
- //~| expected box, found &-ptr
+ //~| expected box, found mutable reference
}
fn main() {}
//~^ ERROR mismatched types
//~| expected type `&std::option::Option<{integer}>`
//~| found type `std::option::Option<_>`
- //~| expected &-ptr, found enum `std::option::Option`
+ //~| expected reference, found enum `std::option::Option`
None => ()
//~^ ERROR mismatched types
//~| expected type `&std::option::Option<{integer}>`
//~| found type `std::option::Option<_>`
- //~| expected &-ptr, found enum `std::option::Option`
+ //~| expected reference, found enum `std::option::Option`
}
}
foo!(Box);
+macro_rules! bar {
+ ($x:tt) => {
+ macro_rules! baz {
+ ($x:tt, $y:tt) => { ($x, $y) }
+ }
+ }
+}
+
#[rustc_error]
-fn main() {} //~ ERROR compilation successful
+fn main() { //~ ERROR compilation successful
+ bar!($y);
+ let _: (i8, i16) = baz!(0i8, 0i16);
+}
Foo::bar(x); //~ ERROR mismatched types
//~| expected type `&Foo`
//~| found type `Foo`
- //~| expected &-ptr, found struct `Foo`
+ //~| expected &Foo, found struct `Foo`
Foo::bar(&42); //~ ERROR mismatched types
//~| expected type `&Foo`
//~| found type `&{integer}`
--- /dev/null
+// Copyright 2016 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.
+
+#![feature(relaxed_adts)]
+
+struct S(u8, u16);
+
+fn main() {
+ let s = S{0b1: 10, 0: 11}; //~ ERROR structure `S` has no field named `0b1`
+ match s {
+ S{0: a, 0x1: b, ..} => {} //~ ERROR does not have a field named `0x1`
+ }
+}
y: 3,
};
let ans = s("what"); //~ ERROR mismatched types
- //~^ NOTE expected isize, found &-ptr
+ //~^ NOTE expected isize, found reference
//~| NOTE expected type
//~| NOTE found type
let ans = s();
// except according to those terms.
mod m1 {
- #![deny(private_in_public)]
-
pub struct Pub;
struct Priv;
// Private types and traits are not allowed in public interfaces.
// This test also ensures that the checks are performed even inside private modules.
-#![feature(rustc_attrs)]
#![feature(associated_consts)]
#![feature(associated_type_defaults)]
#![allow(dead_code)]
type Alias;
}
- pub type Alias = Priv; //~ WARN private type in public interface
+ pub type Alias = Priv; //~ ERROR private type in public interface
//~^ WARNING hard error
pub enum E {
- V1(Priv), //~ WARN private type in public interface
+ V1(Priv), //~ ERROR private type in public interface
//~^ WARNING hard error
- V2 { field: Priv }, //~ WARN private type in public interface
+ V2 { field: Priv }, //~ ERROR private type in public interface
//~^ WARNING hard error
}
pub trait Tr {
- const C: Priv = Priv; //~ WARN private type in public interface
+ const C: Priv = Priv; //~ ERROR private type in public interface
//~^ WARNING hard error
- type Alias = Priv; //~ WARN private type in public interface
+ type Alias = Priv; //~ ERROR private type in public interface
//~^ WARNING hard error
- fn f1(arg: Priv) {} //~ WARN private type in public interface
+ fn f1(arg: Priv) {} //~ ERROR private type in public interface
//~^ WARNING hard error
- fn f2() -> Priv { panic!() } //~ WARN private type in public interface
+ fn f2() -> Priv { panic!() } //~ ERROR private type in public interface
//~^ WARNING hard error
}
extern {
- pub static ES: Priv; //~ WARN private type in public interface
+ pub static ES: Priv; //~ ERROR private type in public interface
//~^ WARNING hard error
- pub fn ef1(arg: Priv); //~ WARN private type in public interface
+ pub fn ef1(arg: Priv); //~ ERROR private type in public interface
//~^ WARNING hard error
- pub fn ef2() -> Priv; //~ WARN private type in public interface
+ pub fn ef2() -> Priv; //~ ERROR private type in public interface
//~^ WARNING hard error
}
impl PubTr for Pub {
- type Alias = Priv; //~ WARN private type in public interface
+ type Alias = Priv; //~ ERROR private type in public interface
//~^ WARNING hard error
}
}
pub struct Pub<T>(T);
pub trait PubTr {}
- pub type Alias<T: PrivTr> = T; //~ WARN private trait in public interface
+ pub type Alias<T: PrivTr> = T; //~ ERROR private trait in public interface
//~^ WARN trait bounds are not (yet) enforced in type definitions
//~| WARNING hard error
- pub trait Tr1: PrivTr {} //~ WARN private trait in public interface
+ pub trait Tr1: PrivTr {} //~ ERROR private trait in public interface
//~^ WARNING hard error
- pub trait Tr2<T: PrivTr> {} //~ WARN private trait in public interface
+ pub trait Tr2<T: PrivTr> {} //~ ERROR private trait in public interface
//~^ WARNING hard error
pub trait Tr3 {
- type Alias: PrivTr; //~ WARN private trait in public interface
+ type Alias: PrivTr; //~ ERROR private trait in public interface
//~^ WARNING hard error
- fn f<T: PrivTr>(arg: T) {} //~ WARN private trait in public interface
+ fn f<T: PrivTr>(arg: T) {} //~ ERROR private trait in public interface
//~^ WARNING hard error
}
- impl<T: PrivTr> Pub<T> {} //~ WARN private trait in public interface
+ impl<T: PrivTr> Pub<T> {} //~ ERROR private trait in public interface
//~^ WARNING hard error
- impl<T: PrivTr> PubTr for Pub<T> {} //~ WARN private trait in public interface
+ impl<T: PrivTr> PubTr for Pub<T> {} //~ ERROR private trait in public interface
//~^ WARNING hard error
}
pub struct Pub<T>(T);
pub trait PubTr {}
- pub type Alias<T> where T: PrivTr = T; //~ WARN private trait in public interface
+ pub type Alias<T> where T: PrivTr = T; //~ ERROR private trait in public interface
//~^ WARNING hard error
- pub trait Tr2<T> where T: PrivTr {} //~ WARN private trait in public interface
+ pub trait Tr2<T> where T: PrivTr {} //~ ERROR private trait in public interface
//~^ WARNING hard error
pub trait Tr3 {
- fn f<T>(arg: T) where T: PrivTr {} //~ WARN private trait in public interface
+ fn f<T>(arg: T) where T: PrivTr {} //~ ERROR private trait in public interface
//~^ WARNING hard error
}
- impl<T> Pub<T> where T: PrivTr {} //~ WARN private trait in public interface
+ impl<T> Pub<T> where T: PrivTr {} //~ ERROR private trait in public interface
//~^ WARNING hard error
- impl<T> PubTr for Pub<T> where T: PrivTr {} //~ WARN private trait in public interface
+ impl<T> PubTr for Pub<T> where T: PrivTr {} //~ ERROR private trait in public interface
//~^ WARNING hard error
}
trait PrivTr<T> {}
pub trait PubTr<T> {}
- pub trait Tr1: PrivTr<Pub> {} //~ WARN private trait in public interface
+ pub trait Tr1: PrivTr<Pub> {} //~ ERROR private trait in public interface
//~^ WARNING hard error
- pub trait Tr2: PubTr<Priv> {} //~ WARN private type in public interface
+ pub trait Tr2: PubTr<Priv> {} //~ ERROR private type in public interface
//~^ WARNING hard error
- pub trait Tr3: PubTr<[Priv; 1]> {} //~ WARN private type in public interface
+ pub trait Tr3: PubTr<[Priv; 1]> {} //~ ERROR private type in public interface
//~^ WARNING hard error
- pub trait Tr4: PubTr<Pub<Priv>> {} //~ WARN private type in public interface
+ pub trait Tr4: PubTr<Pub<Priv>> {} //~ ERROR private type in public interface
//~^ WARNING hard error
}
type Alias = Priv; // OK
}
impl PubTr for Pub {
- type Alias = Priv; //~ WARN private type in public interface
+ type Alias = Priv; //~ ERROR private type in public interface
//~^ WARNING hard error
}
}
pub trait Tr2: PrivUseAliasTr<PrivAlias> {} // OK
impl PrivAlias {
- pub fn f(arg: Priv) {} //~ WARN private type in public interface
+ pub fn f(arg: Priv) {} //~ ERROR private type in public interface
//~^ WARNING hard error
}
// This doesn't even parse
// impl <Priv as PrivTr>::AssocAlias {
- // pub fn f(arg: Priv) {} // WARN private type in public interface
+ // pub fn f(arg: Priv) {} // ERROR private type in public interface
// }
impl PrivUseAliasTr for PrivUseAlias {
- type Check = Priv; //~ WARN private type in public interface
+ type Check = Priv; //~ ERROR private type in public interface
//~^ WARNING hard error
}
impl PrivUseAliasTr for PrivAlias {
- type Check = Priv; //~ WARN private type in public interface
+ type Check = Priv; //~ ERROR private type in public interface
//~^ WARNING hard error
}
impl PrivUseAliasTr for <Priv as PrivTr>::AssocAlias {
- type Check = Priv; //~ WARN private type in public interface
+ type Check = Priv; //~ ERROR private type in public interface
//~^ WARNING hard error
}
}
type AssocAlias = Priv3;
}
- pub trait Tr1: PrivUseAliasTr {} //~ WARN private trait in public interface
+ pub trait Tr1: PrivUseAliasTr {} //~ ERROR private trait in public interface
//~^ WARNING hard error
- pub trait Tr2: PrivUseAliasTr<PrivAlias> {} //~ WARN private trait in public interface
- //~^ WARN private type in public interface
+ pub trait Tr2: PrivUseAliasTr<PrivAlias> {} //~ ERROR private trait in public interface
+ //~^ ERROR private type in public interface
//~| WARNING hard error
//~| WARNING hard error
pub fn f1(arg: PrivAliasGeneric<u8>) {} // OK, not an error
}
-#[rustc_error]
-fn main() {} //~ ERROR compilation successful
+fn main() {}
// option. This file may not be copied, modified, or distributed
// except according to those terms.
-#![feature(rustc_attrs)]
#![allow(dead_code)]
extern crate core;
-pub use core as reexported_core; //~ WARN extern crate `core` is private, and cannot be reexported
+pub use core as reexported_core; //~ ERROR extern crate `core` is private, and cannot be reexported
//~^ WARNING hard error
mod m1 {
- pub use ::E::V; //~ WARN variant `V` is private, and cannot be reexported
+ pub use ::E::V; //~ ERROR variant `V` is private, and cannot be reexported
//~^ WARNING hard error
}
mod m2 {
- pub use ::E::{V}; //~ WARN variant `V` is private, and cannot be reexported
+ pub use ::E::{V}; //~ ERROR variant `V` is private, and cannot be reexported
//~^ WARNING hard error
}
mod m3 {
- pub use ::E::V::{self}; //~ WARN variant `V` is private, and cannot be reexported
+ pub use ::E::V::{self}; //~ ERROR variant `V` is private, and cannot be reexported
//~^ WARNING hard error
}
mod m4 {
- pub use ::E::*; //~ WARN variant `V` is private, and cannot be reexported
+ pub use ::E::*; //~ ERROR variant `V` is private, and cannot be reexported
//~^ WARNING hard error
}
enum E { V }
-#[rustc_error]
-fn main() {} //~ ERROR compilation successful
+fn main() {}
+++ /dev/null
-// 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.
-
-// Regression test for issue #26083
-// Test that span for public struct fields start at `pub` instead of the identifier
-
-struct Foo {
- pub bar: u8,
-
- pub
- //~^ error: field `bar` is already declared [E0124]
- bar: u8,
-
- pub bar:
- //~^ error: field `bar` is already declared [E0124]
- u8,
-
- bar:
- //~^ error: field `bar` is already declared [E0124]
- u8,
-}
-
-fn main() { }
//~^ ERROR mismatched types
//~| expected type `usize`
//~| found type `&'static str`
- //~| expected usize, found &-ptr
+ //~| expected usize, found reference
//~| ERROR expected `usize` for repeat count, found string literal [E0306]
//~| expected `usize`
let f = [0; -4_isize];
+++ /dev/null
-// Copyright 2014 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.
-
-struct Foo(); //~ ERROR empty tuple structs and enum variants are not allowed
-
-fn main() {}
--- /dev/null
+// Copyright 2016 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.
+
+enum Baz {
+ Empty,
+ Foo { x: usize },
+}
+
+fn bar(a: usize) -> Baz {
+ Baz::Foo { x: a }
+}
+
+fn main() {
+ let x = bar(10);
+ match x {
+ Baz::Empty => println!("empty"),
+ Baz::Foo { x } => println!("{}", x),
+ };
+}
+
+// END RUST SOURCE
+// START rustc.node10.Deaggregator.before.mir
+// bb0: {
+// var0 = arg0; // scope 0 at main.rs:7:8: 7:9
+// tmp0 = var0; // scope 1 at main.rs:8:19: 8:20
+// return = Baz::Foo { x: tmp0 }; // scope 1 at main.rs:8:5: 8:21
+// goto -> bb1; // scope 1 at main.rs:7:1: 9:2
+// }
+// END rustc.node10.Deaggregator.before.mir
+// START rustc.node10.Deaggregator.after.mir
+// bb0: {
+// var0 = arg0; // scope 0 at main.rs:7:8: 7:9
+// tmp0 = var0; // scope 1 at main.rs:8:19: 8:20
+// ((return as Foo).0: usize) = tmp0; // scope 1 at main.rs:8:5: 8:21
+// discriminant(return) = 1; // scope 1 at main.rs:8:5: 8:21
+// goto -> bb1; // scope 1 at main.rs:7:1: 9:2
+// }
+// END rustc.node10.Deaggregator.after.mir
\ No newline at end of file
let mac_expr = match TokenTree::parse(cx, &mbe_matcher[..], args) {
Success(map) => {
- match (&*map[&str_to_ident("matched").name], &*map[&str_to_ident("pat").name]) {
+ match (&*map[&str_to_ident("matched")], &*map[&str_to_ident("pat")]) {
(&MatchedNonterminal(NtExpr(ref matched_expr)),
&MatchedSeq(ref pats, seq_sp)) => {
let pats: Vec<P<Pat>> = pats.iter().map(|pat_nt|
// ignore-android: FIXME(#10356)
// ignore-windows: std::dynamic_lib does not work on Windows well
// ignore-musl
+// ignore-emscripten no dynamic linking
extern crate linkage_visibility as foo;
// except according to those terms.
// exec-env:RUST_LOG=logging_enabled=info
+// ignore-emscripten: FIXME(#31622)
#![feature(rustc_private)]
// ignore-windows
// exec-env:RUST_LOG=debug
// compile-flags:-C debug-assertions=y
+// ignore-emscripten: FIXME(#31622)
#![feature(rustc_private)]
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+#![feature(relaxed_adts)]
+
pub struct XEmpty1 {}
pub struct XEmpty2;
+pub struct XEmpty7();
pub enum XE {
XEmpty3 {},
XEmpty4,
+ XEmpty6(),
}
// compile-flags:-g -Cllvm-args=-enable-tail-merge=0
// ignore-pretty as this critically relies on line numbers
+// ignore-emscripten spawning processes is not supported
use std::io;
use std::io::prelude::*;
// no-pretty-expanded FIXME #15189
// ignore-android FIXME #17520
+// ignore-emscripten spawning processes is not supported
// compile-flags:-g
use std::env;
// except according to those terms.
// ignore-windows - this is a unix-specific test
+// ignore-emscripten
#![feature(process_exec, libc)]
// except according to those terms.
// ignore-windows - this is a unix-specific test
+// ignore-emscripten
// ignore-pretty
#![feature(process_exec)]
// except according to those terms.
// compile-flags: -Z force-dropflag-checks=on
+// ignore-emscripten
// Quick-and-dirty test to ensure -Z force-dropflag-checks=on works as
// expected. Note that the inlined drop-flag is slated for removal
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten no threads support
+
#![allow(unknown_features)]
#![feature(box_syntax)]
+++ /dev/null
-// 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.
-
-// Feature gate test for empty struct with braces
-// Can't define an empty braced struct
-
-struct Empty1 {}
-struct Empty2;
-
-enum E {
- Empty4 {},
- Empty5,
-}
-
-fn main() {
-}
+++ /dev/null
-// 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.
-
-// Feature gate test for empty struct with braces
-// Can't use braced expressions and patterns with structs defined without braces
-
-struct Empty2;
-
-enum E {
- Empty5,
-}
-
-fn main() {
- let e2: Empty2 = Empty2 {};
- let e2: Empty2 = Empty2;
- let e5: E = E::Empty5 {};
- let e5: E = E::Empty5;
-
- match e2 {
- Empty2 {} => {}
- }
- match e2 {
- Empty2 => {}
- }
- match e2 {
- Empty2 { .. } => {}
- }
- match e5 {
- E::Empty5 {} => {}
- }
- match e5 {
- E::Empty5 => {}
- }
- match e5 {
- E::Empty5 { .. } => {}
- }
-
- let e22 = Empty2 { ..e2 };
-}
// aux-build:empty-struct.rs
+#![feature(relaxed_adts)]
+
extern crate empty_struct;
use empty_struct::*;
struct Empty1 {}
struct Empty2;
+struct Empty7();
#[derive(PartialEq, Eq)]
struct Empty3 {}
enum E {
Empty4 {},
Empty5,
+ Empty6(),
}
fn local() {
let e4: E = E::Empty4 {};
let e5: E = E::Empty5 {};
let e5: E = E::Empty5;
+ let e6: E = E::Empty6 {};
+ let e6: E = E::Empty6();
+ let ctor6: fn() -> E = E::Empty6;
+ let e7: Empty7 = Empty7 {};
+ let e7: Empty7 = Empty7();
+ let ctor7: fn() -> Empty7 = Empty7;
match e1 {
Empty1 {} => {}
E::Empty5 {} => {}
_ => {}
}
+ match e6 {
+ E::Empty6 {} => {}
+ _ => {}
+ }
+ match e7 {
+ Empty7 {} => {}
+ }
match e1 {
Empty1 { .. } => {}
E::Empty5 { .. } => {}
_ => {}
}
+ match e6 {
+ E::Empty6 { .. } => {}
+ _ => {}
+ }
+ match e7 {
+ Empty7 { .. } => {}
+ }
match e2 {
Empty2 => {}
E::Empty5 => {}
_ => {}
}
+ match e6 {
+ E::Empty6() => {}
+ _ => {}
+ }
+ match e6 {
+ E::Empty6(..) => {}
+ _ => {}
+ }
+ match e7 {
+ Empty7() => {}
+ }
+ match e7 {
+ Empty7(..) => {}
+ }
let e11: Empty1 = Empty1 { ..e1 };
let e22: Empty2 = Empty2 { ..e2 };
let e33: Empty3 = Empty3 { ..e3 };
+ let e77: Empty7 = Empty7 { ..e7 };
}
fn xcrate() {
let e3: XE = XE::XEmpty3 {};
let e4: XE = XE::XEmpty4 {};
let e4: XE = XE::XEmpty4;
+ let e6: XE = XE::XEmpty6 {};
+ let e6: XE = XE::XEmpty6();
+ let ctor6: fn() -> XE = XE::XEmpty6;
+ let e7: XEmpty7 = XEmpty7 {};
+ let e7: XEmpty7 = XEmpty7();
+ let ctor7: fn() -> XEmpty7 = XEmpty7;
match e1 {
XEmpty1 {} => {}
XE::XEmpty4 {} => {}
_ => {}
}
+ match e6 {
+ XE::XEmpty6 {} => {}
+ _ => {}
+ }
+ match e7 {
+ XEmpty7 {} => {}
+ }
match e1 {
XEmpty1 { .. } => {}
XE::XEmpty4 { .. } => {}
_ => {}
}
+ match e6 {
+ XE::XEmpty6 { .. } => {}
+ _ => {}
+ }
+ match e7 {
+ XEmpty7 { .. } => {}
+ }
match e2 {
XEmpty2 => {}
XE::XEmpty4 => {}
_ => {}
}
+ match e6 {
+ XE::XEmpty6() => {}
+ _ => {}
+ }
+ match e6 {
+ XE::XEmpty6(..) => {}
+ _ => {}
+ }
+ match e7 {
+ XEmpty7() => {}
+ }
+ match e7 {
+ XEmpty7(..) => {}
+ }
let e11: XEmpty1 = XEmpty1 { ..e1 };
let e22: XEmpty2 = XEmpty2 { ..e2 };
+ let e77: XEmpty7 = XEmpty7 { ..e7 };
}
fn main() {
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten
+
use std::env::args;
use std::process::Command;
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten
#![feature(path)]
// except according to those terms.
// exec-env:TEST_EXEC_ENV=22
-
+// ignore-emscripten FIXME: issue #31622
use std::env;
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten No support for threads
+
#![allow(unknown_features)]
#![feature(std_misc)]
target_os = "dragonfly",
target_os = "netbsd",
target_os = "openbsd",
- target_os = "solaris"))]
+ target_os = "solaris",
+ target_os = "emscripten"))]
mod m {
#[main]
#[cfg(target_arch = "x86")]
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten
// Make sure that if a process doesn't have its stdio/stderr descriptors set up
// that we don't die in a large ball of fire
// aux-build:issue-12133-dylib.rs
// aux-build:issue-12133-dylib2.rs
// ignore-musl
+// ignore-emscripten no dylib support
// pretty-expanded FIXME #23616
// except according to those terms.
// ignore-aarch64
+// ignore-emscripten
#![feature(io, process_capture)]
use std::env;
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten
#![feature(io, process_capture)]
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten
use std::env;
use std::process::Command;
// except according to those terms.
// ignore-aarch64
+// ignore-emscripten
use std::process::Command;
use std::env;
// except according to those terms.
// ignore-aarch64
+// ignore-emscripten
#![feature(std_misc, os)]
#[cfg(unix)]
// except according to those terms.
// pretty-expanded FIXME #23616
+// ignore-emscripten
use std::thread::Builder;
--- /dev/null
+// Copyright 2016 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(dead_code)]
+static X: &'static str = &*"";
+fn main() {}
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten
+
use std::thread;
use std::env;
use std::process::Command;
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten
// compile-flags: -Z orbit=off
// (blows the stack with MIR trans and no optimizations)
// except according to those terms.
// aux-build:issue-29485.rs
+// ignore-emscripten
#[feature(recover)]
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten
+
// Previously libstd would set stdio descriptors of a child process
// by `dup`ing the requested descriptors to inherit directly into the
// stdio descriptors. This, however, would incorrectly handle cases
mod m1 {
fn f() {
- struct Z {
+ pub struct Z {
pub field: u8
}
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten
+
use std::process::{Command, Stdio};
use std::env;
use std::sync::{Mutex, RwLock};
// ignore-windows
// ignore-macos
+// ignore-emscripten
// aux-build:linkage1.rs
#![feature(linkage)]
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten
+
fn check_for_no_backtrace(test: std::process::Output) {
assert!(!test.status.success());
let err = String::from_utf8_lossy(&test.stderr);
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten
+
#![feature(libc)]
extern crate libc;
--- /dev/null
+// Copyright 2016 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.
+
+#![feature(relaxed_adts)]
+
+struct S(u8, u16);
+
+fn main() {
+ let s = S{1: 10, 0: 11};
+ match s {
+ S{0: a, 1: b, ..} => {
+ assert_eq!(a, 11);
+ assert_eq!(b, 10);
+ }
+ }
+}
// <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.
+
+// ignore-emscripten no threads support
+
#![feature(panic_handler, const_fn, std_panic)]
use std::sync::atomic::{AtomicUsize, Ordering};
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten
+
use std::env;
use std::process::{self, Command, Stdio};
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten
use std::process::Command;
use std::env;
// intact.
// ignore-aarch64
+// ignore-emscripten
use std::io::prelude::*;
use std::io;
target_os = "dragonfly",
target_os = "netbsd",
target_os = "openbsd",
- target_os = "solaris"))]
+ target_os = "solaris",
+ target_os = "emscripten"))]
mod m {
#[cfg(target_arch = "x86")]
pub mod m {
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten
+
#![feature(start)]
use std::ffi::CStr;
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten can't run commands
+
#![feature(libc)]
extern crate libc;
// except according to those terms.
// ignore-windows
+// ignore-emscripten
use std::env;
use std::process::Command;
// doesn't die in a ball of fire, but rather it's gracefully handled.
// ignore-aarch64
+// ignore-emscripten
use std::env;
use std::io::prelude::*;
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten no threads support
+
use std::thread::{self, sleep};
use std::time::Duration;
use std::sync::{Arc, Mutex};
// option. This file may not be copied, modified, or distributed
// except according to those terms.
+// ignore-emscripten
#![feature(libc)]
// option. This file may not be copied, modified, or distributed
// except according to those terms.
-extern crate issue_28927_2 as inner2;
-pub use inner2 as bar;
+mod detail {
+ pub extern crate issue_28927_2 as inner2;
+}
+pub use detail::inner2 as bar;
--- /dev/null
+// Copyright 2016 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.
+
+// Regression test for issue #26083 and #35435
+// Test that span for public struct fields start at `pub`
+
+#![feature(pub_restricted)]
+
+struct Foo {
+ bar: u8,
+ pub bar: u8,
+ pub(crate) bar: u8,
+}
+
+fn main() {}
--- /dev/null
+error[E0124]: field `bar` is already declared
+ --> $DIR/pub-struct-field.rs:18:5
+ |
+17 | bar: u8,
+ | ------- `bar` first declared here
+18 | pub bar: u8,
+ | ^^^^^^^^^^^ field already declared
+
+error[E0124]: field `bar` is already declared
+ --> $DIR/pub-struct-field.rs:19:5
+ |
+17 | bar: u8,
+ | ------- `bar` first declared here
+18 | pub bar: u8,
+19 | pub(crate) bar: u8,
+ | ^^^^^^^^^^^^^^^^^^ field already declared
+
+error: aborting due to 2 previous errors
+
Err(_) => false
},
color: test::AutoColor,
+ test_threads: None,
}
}
self.check_correct_failure_status(&proc_res);
- if proc_res.status.success() {
- self.fatal("process did not return an error status");
- }
-
let output_to_check = self.get_output(&proc_res);
let expected_errors = errors::load_errors(&self.testpaths.file, self.revision);
if !expected_errors.is_empty() {