diff --git a/.travis.yml b/.travis.yml index 7251a46cc5878..2a5f755ebff3d 100644 --- a/.travis.yml +++ b/.travis.yml @@ -218,10 +218,6 @@ before_install: echo '{"ipv6":true,"fixed-cidr-v6":"fd9a:8454:6789:13f7::/64"}' | sudo tee /etc/docker/daemon.json; sudo service docker restart; fi - - date - - sudo atq || true - - sudo grep -rE 'shutdown|poweroff|halt' /var/spool/cron || true - - sudo grep -E 'google-clock-skew|ntpd|startup-script' /var/log/syslog || true install: - case "$TRAVIS_OS_NAME" in @@ -278,8 +274,6 @@ after_success: du . | sort -nr | head -n100 after_failure: - # Requested by travis to debug "shutting down NOW" errors - - sudo tail -n 500 /var/log/syslog - > echo "#### Build failed; Disk usage after running script:"; df -h; diff --git a/src/Cargo.lock b/src/Cargo.lock index a8308eb403896..99b768ab1a92e 100644 --- a/src/Cargo.lock +++ b/src/Cargo.lock @@ -100,7 +100,7 @@ name = "backtrace" version = "0.3.9" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ - "backtrace-sys 0.1.23 (registry+https://github.com/rust-lang/crates.io-index)", + "backtrace-sys 0.1.24 (registry+https://github.com/rust-lang/crates.io-index)", "cfg-if 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", "libc 0.2.43 (registry+https://github.com/rust-lang/crates.io-index)", "rustc-demangle 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)", @@ -109,7 +109,7 @@ dependencies = [ [[package]] name = "backtrace-sys" -version = "0.1.23" +version = "0.1.24" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ "cc 1.0.18 (registry+https://github.com/rust-lang/crates.io-index)", @@ -3125,7 +3125,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" "checksum assert_cli 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)" = "98589b0e465a6c510d95fceebd365bb79bedece7f6e18a480897f2015f85ec51" "checksum atty 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)" = "9a7d5b8723950951411ee34d271d99dddcc2035a16ab25310ea2c8cfd4369652" "checksum backtrace 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)" = "89a47830402e9981c5c41223151efcced65a0510c13097c769cede7efb34782a" -"checksum backtrace-sys 0.1.23 (registry+https://github.com/rust-lang/crates.io-index)" = "bff67d0c06556c0b8e6b5f090f0eac52d950d9dfd1d35ba04e4ca3543eaf6a7e" +"checksum backtrace-sys 0.1.24 (registry+https://github.com/rust-lang/crates.io-index)" = "c66d56ac8dabd07f6aacdaf633f4b8262f5b3601a810a0dcddffd5c22c69daa0" "checksum bitflags 0.9.1 (registry+https://github.com/rust-lang/crates.io-index)" = "4efd02e230a02e18f92fc2735f44597385ed02ad8f831e7c1c1156ee5e1ab3a5" "checksum bitflags 1.0.3 (registry+https://github.com/rust-lang/crates.io-index)" = "d0c54bb8f454c567f21197eefcdbf5679d0bd99f2ddbe52e84c77061952e6789" "checksum bufstream 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "f2f382711e76b9de6c744cc00d0497baba02fb00a787f088c879f01d09468e32" diff --git a/src/ci/docker/run.sh b/src/ci/docker/run.sh index b1ee636644ec7..3a7714d32fa17 100755 --- a/src/ci/docker/run.sh +++ b/src/ci/docker/run.sh @@ -119,10 +119,6 @@ fi # goes ahead and sets it for all builders. args="$args --privileged" -if [ "$CI" != "" ]; then - args="$args --dns 8.8.8.8 --dns 8.8.4.4 --dns 1.1.1.1 --dns 1.0.0.1" -fi - exec docker \ run \ --volume "$root_dir:/checkout:ro" \ diff --git a/src/doc/unstable-book/src/library-features/future-atomic-orderings.md b/src/doc/unstable-book/src/library-features/future-atomic-orderings.md deleted file mode 100644 index 40c2ef2db0551..0000000000000 --- a/src/doc/unstable-book/src/library-features/future-atomic-orderings.md +++ /dev/null @@ -1,5 +0,0 @@ -# `future_atomic_orderings` - -This feature is internal to the Rust compiler and is not intended for general use. - ------------------------- diff --git a/src/doc/unstable-book/src/library-features/io-error-internals.md b/src/doc/unstable-book/src/library-features/io-error-internals.md deleted file mode 100644 index 5bee18d33d61b..0000000000000 --- a/src/doc/unstable-book/src/library-features/io-error-internals.md +++ /dev/null @@ -1,5 +0,0 @@ -# `io_error_internals` - -This feature is internal to the Rust compiler and is not intended for general use. - ------------------------- diff --git a/src/libcore/lib.rs b/src/libcore/lib.rs index 178ae62dd3dfa..e85bf1dfcad23 100644 --- a/src/libcore/lib.rs +++ b/src/libcore/lib.rs @@ -120,6 +120,7 @@ #![feature(const_slice_len)] #![feature(const_str_as_bytes)] #![feature(const_str_len)] +#![feature(non_exhaustive)] #[prelude_import] #[allow(unused)] diff --git a/src/libcore/macros.rs b/src/libcore/macros.rs index 83f9dfea8f267..5b3b2d1635688 100644 --- a/src/libcore/macros.rs +++ b/src/libcore/macros.rs @@ -396,6 +396,7 @@ macro_rules! write { /// ``` #[macro_export] #[stable(feature = "rust1", since = "1.0.0")] +#[allow_internal_unstable] macro_rules! writeln { ($dst:expr) => ( write!($dst, "\n") @@ -403,11 +404,8 @@ macro_rules! writeln { ($dst:expr,) => ( writeln!($dst) ); - ($dst:expr, $fmt:expr) => ( - write!($dst, concat!($fmt, "\n")) - ); - ($dst:expr, $fmt:expr, $($arg:tt)*) => ( - write!($dst, concat!($fmt, "\n"), $($arg)*) + ($dst:expr, $($arg:tt)*) => ( + $dst.write_fmt(format_args_nl!($($arg)*)) ); } diff --git a/src/libcore/sync/atomic.rs b/src/libcore/sync/atomic.rs index 5bb713f576741..617e067e0787e 100644 --- a/src/libcore/sync/atomic.rs +++ b/src/libcore/sync/atomic.rs @@ -185,6 +185,7 @@ unsafe impl Sync for AtomicPtr {} /// [nomicon]: ../../../nomicon/atomics.html #[stable(feature = "rust1", since = "1.0.0")] #[derive(Copy, Clone, Debug)] +#[non_exhaustive] pub enum Ordering { /// No ordering constraints, only atomic operations. /// @@ -256,10 +257,6 @@ pub enum Ordering { /// [`AcqRel`]: https://llvm.org/docs/Atomics.html#acquirerelease #[stable(feature = "rust1", since = "1.0.0")] SeqCst, - // Prevent exhaustive matching to allow for future extension - #[doc(hidden)] - #[unstable(feature = "future_atomic_orderings", issue = "0")] - __Nonexhaustive, } /// An [`AtomicBool`] initialized to `false`. @@ -1954,7 +1951,6 @@ fn strongest_failure_ordering(order: Ordering) -> Ordering { SeqCst => SeqCst, Acquire => Acquire, AcqRel => Acquire, - __Nonexhaustive => __Nonexhaustive, } } @@ -1966,7 +1962,6 @@ unsafe fn atomic_store(dst: *mut T, val: T, order: Ordering) { SeqCst => intrinsics::atomic_store(dst, val), Acquire => panic!("there is no such thing as an acquire store"), AcqRel => panic!("there is no such thing as an acquire/release store"), - __Nonexhaustive => panic!("invalid memory ordering"), } } @@ -1978,7 +1973,6 @@ unsafe fn atomic_load(dst: *const T, order: Ordering) -> T { SeqCst => intrinsics::atomic_load(dst), Release => panic!("there is no such thing as a release load"), AcqRel => panic!("there is no such thing as an acquire/release load"), - __Nonexhaustive => panic!("invalid memory ordering"), } } @@ -1991,7 +1985,6 @@ unsafe fn atomic_swap(dst: *mut T, val: T, order: Ordering) -> T { AcqRel => intrinsics::atomic_xchg_acqrel(dst, val), Relaxed => intrinsics::atomic_xchg_relaxed(dst, val), SeqCst => intrinsics::atomic_xchg(dst, val), - __Nonexhaustive => panic!("invalid memory ordering"), } } @@ -2004,7 +1997,6 @@ unsafe fn atomic_add(dst: *mut T, val: T, order: Ordering) -> T { AcqRel => intrinsics::atomic_xadd_acqrel(dst, val), Relaxed => intrinsics::atomic_xadd_relaxed(dst, val), SeqCst => intrinsics::atomic_xadd(dst, val), - __Nonexhaustive => panic!("invalid memory ordering"), } } @@ -2017,7 +2009,6 @@ unsafe fn atomic_sub(dst: *mut T, val: T, order: Ordering) -> T { AcqRel => intrinsics::atomic_xsub_acqrel(dst, val), Relaxed => intrinsics::atomic_xsub_relaxed(dst, val), SeqCst => intrinsics::atomic_xsub(dst, val), - __Nonexhaustive => panic!("invalid memory ordering"), } } @@ -2039,8 +2030,6 @@ unsafe fn atomic_compare_exchange(dst: *mut T, (AcqRel, Relaxed) => intrinsics::atomic_cxchg_acqrel_failrelaxed(dst, old, new), (SeqCst, Relaxed) => intrinsics::atomic_cxchg_failrelaxed(dst, old, new), (SeqCst, Acquire) => intrinsics::atomic_cxchg_failacq(dst, old, new), - (__Nonexhaustive, _) => panic!("invalid memory ordering"), - (_, __Nonexhaustive) => panic!("invalid memory ordering"), (_, AcqRel) => panic!("there is no such thing as an acquire/release failure ordering"), (_, Release) => panic!("there is no such thing as a release failure ordering"), _ => panic!("a failure ordering can't be stronger than a success ordering"), @@ -2065,8 +2054,6 @@ unsafe fn atomic_compare_exchange_weak(dst: *mut T, (AcqRel, Relaxed) => intrinsics::atomic_cxchgweak_acqrel_failrelaxed(dst, old, new), (SeqCst, Relaxed) => intrinsics::atomic_cxchgweak_failrelaxed(dst, old, new), (SeqCst, Acquire) => intrinsics::atomic_cxchgweak_failacq(dst, old, new), - (__Nonexhaustive, _) => panic!("invalid memory ordering"), - (_, __Nonexhaustive) => panic!("invalid memory ordering"), (_, AcqRel) => panic!("there is no such thing as an acquire/release failure ordering"), (_, Release) => panic!("there is no such thing as a release failure ordering"), _ => panic!("a failure ordering can't be stronger than a success ordering"), @@ -2082,7 +2069,6 @@ unsafe fn atomic_and(dst: *mut T, val: T, order: Ordering) -> T { AcqRel => intrinsics::atomic_and_acqrel(dst, val), Relaxed => intrinsics::atomic_and_relaxed(dst, val), SeqCst => intrinsics::atomic_and(dst, val), - __Nonexhaustive => panic!("invalid memory ordering"), } } @@ -2094,7 +2080,6 @@ unsafe fn atomic_nand(dst: *mut T, val: T, order: Ordering) -> T { AcqRel => intrinsics::atomic_nand_acqrel(dst, val), Relaxed => intrinsics::atomic_nand_relaxed(dst, val), SeqCst => intrinsics::atomic_nand(dst, val), - __Nonexhaustive => panic!("invalid memory ordering"), } } @@ -2106,7 +2091,6 @@ unsafe fn atomic_or(dst: *mut T, val: T, order: Ordering) -> T { AcqRel => intrinsics::atomic_or_acqrel(dst, val), Relaxed => intrinsics::atomic_or_relaxed(dst, val), SeqCst => intrinsics::atomic_or(dst, val), - __Nonexhaustive => panic!("invalid memory ordering"), } } @@ -2118,7 +2102,6 @@ unsafe fn atomic_xor(dst: *mut T, val: T, order: Ordering) -> T { AcqRel => intrinsics::atomic_xor_acqrel(dst, val), Relaxed => intrinsics::atomic_xor_relaxed(dst, val), SeqCst => intrinsics::atomic_xor(dst, val), - __Nonexhaustive => panic!("invalid memory ordering"), } } @@ -2131,7 +2114,6 @@ unsafe fn atomic_max(dst: *mut T, val: T, order: Ordering) -> T { AcqRel => intrinsics::atomic_max_acqrel(dst, val), Relaxed => intrinsics::atomic_max_relaxed(dst, val), SeqCst => intrinsics::atomic_max(dst, val), - __Nonexhaustive => panic!("invalid memory ordering"), } } @@ -2144,7 +2126,6 @@ unsafe fn atomic_min(dst: *mut T, val: T, order: Ordering) -> T { AcqRel => intrinsics::atomic_min_acqrel(dst, val), Relaxed => intrinsics::atomic_min_relaxed(dst, val), SeqCst => intrinsics::atomic_min(dst, val), - __Nonexhaustive => panic!("invalid memory ordering"), } } @@ -2157,7 +2138,6 @@ unsafe fn atomic_umax(dst: *mut T, val: T, order: Ordering) -> T { AcqRel => intrinsics::atomic_umax_acqrel(dst, val), Relaxed => intrinsics::atomic_umax_relaxed(dst, val), SeqCst => intrinsics::atomic_umax(dst, val), - __Nonexhaustive => panic!("invalid memory ordering"), } } @@ -2170,7 +2150,6 @@ unsafe fn atomic_umin(dst: *mut T, val: T, order: Ordering) -> T { AcqRel => intrinsics::atomic_umin_acqrel(dst, val), Relaxed => intrinsics::atomic_umin_relaxed(dst, val), SeqCst => intrinsics::atomic_umin(dst, val), - __Nonexhaustive => panic!("invalid memory ordering"), } } @@ -2260,7 +2239,6 @@ pub fn fence(order: Ordering) { AcqRel => intrinsics::atomic_fence_acqrel(), SeqCst => intrinsics::atomic_fence(), Relaxed => panic!("there is no such thing as a relaxed fence"), - __Nonexhaustive => panic!("invalid memory ordering"), } } } @@ -2350,7 +2328,6 @@ pub fn compiler_fence(order: Ordering) { AcqRel => intrinsics::atomic_singlethreadfence_acqrel(), SeqCst => intrinsics::atomic_singlethreadfence(), Relaxed => panic!("there is no such thing as a relaxed compiler fence"), - __Nonexhaustive => panic!("invalid memory ordering"), } } } diff --git a/src/libpanic_unwind/wasm32.rs b/src/libpanic_unwind/dummy.rs similarity index 100% rename from src/libpanic_unwind/wasm32.rs rename to src/libpanic_unwind/dummy.rs diff --git a/src/libpanic_unwind/lib.rs b/src/libpanic_unwind/lib.rs index a61b2c1f06394..9c3fc76c307a6 100644 --- a/src/libpanic_unwind/lib.rs +++ b/src/libpanic_unwind/lib.rs @@ -55,36 +55,33 @@ use core::mem; use core::raw; use core::panic::BoxMeUp; -// Rust runtime's startup objects depend on these symbols, so make them public. -#[cfg(all(target_os="windows", target_arch = "x86", target_env="gnu"))] -pub use imp::eh_frame_registry::*; +#[macro_use] +mod macros; -// *-pc-windows-msvc -#[cfg(target_env = "msvc")] -#[path = "seh.rs"] -mod imp; - -// x86_64-pc-windows-gnu -#[cfg(all(windows, target_arch = "x86_64", target_env = "gnu"))] -#[path = "seh64_gnu.rs"] -mod imp; - -// i686-pc-windows-gnu and all others -#[cfg(any(all(unix, not(target_os = "emscripten")), - target_os = "cloudabi", - target_os = "redox", - all(windows, target_arch = "x86", target_env = "gnu")))] -#[path = "gcc.rs"] -mod imp; - -// emscripten -#[cfg(target_os = "emscripten")] -#[path = "emcc.rs"] -mod imp; - -#[cfg(all(target_arch = "wasm32", not(target_os = "emscripten")))] -#[path = "wasm32.rs"] -mod imp; +cfg_if! { + if #[cfg(target_os = "emscripten")] { + #[path = "emcc.rs"] + mod imp; + } else if #[cfg(target_arch = "wasm32")] { + #[path = "dummy.rs"] + mod imp; + } else if #[cfg(all(target_env = "msvc", target_arch = "aarch64"))] { + #[path = "dummy.rs"] + mod imp; + } else if #[cfg(target_env = "msvc")] { + #[path = "seh.rs"] + mod imp; + } else if #[cfg(all(windows, target_arch = "x86_64", target_env = "gnu"))] { + #[path = "seh64_gnu.rs"] + mod imp; + } else { + // Rust runtime's startup objects depend on these symbols, so make them public. + #[cfg(all(target_os="windows", target_arch = "x86", target_env="gnu"))] + pub use imp::eh_frame_registry::*; + #[path = "gcc.rs"] + mod imp; + } +} mod dwarf; mod windows; diff --git a/src/libpanic_unwind/macros.rs b/src/libpanic_unwind/macros.rs new file mode 100644 index 0000000000000..6ea79dc862bda --- /dev/null +++ b/src/libpanic_unwind/macros.rs @@ -0,0 +1,45 @@ +// Copyright 2018 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 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +/// A macro for defining `#[cfg]` if-else statements. +/// +/// This is similar to the `if/elif` C preprocessor macro by allowing definition +/// of a cascade of `#[cfg]` cases, emitting the implementation which matches +/// first. +/// +/// This allows you to conveniently provide a long list `#[cfg]`'d blocks of code +/// without having to rewrite each clause multiple times. +macro_rules! cfg_if { + ($( + if #[cfg($($meta:meta),*)] { $($it:item)* } + ) else * else { + $($it2:item)* + }) => { + __cfg_if_items! { + () ; + $( ( ($($meta),*) ($($it)*) ), )* + ( () ($($it2)*) ), + } + } +} + +macro_rules! __cfg_if_items { + (($($not:meta,)*) ; ) => {}; + (($($not:meta,)*) ; ( ($($m:meta),*) ($($it:item)*) ), $($rest:tt)*) => { + __cfg_if_apply! { cfg(all(not(any($($not),*)), $($m,)*)), $($it)* } + __cfg_if_items! { ($($not,)* $($m,)*) ; $($rest)* } + } +} + +macro_rules! __cfg_if_apply { + ($m:meta, $($it:item)*) => { + $(#[$m] $it)* + } +} diff --git a/src/libproc_macro/diagnostic.rs b/src/libproc_macro/diagnostic.rs index 51e7647f36cc2..af7790164183c 100644 --- a/src/libproc_macro/diagnostic.rs +++ b/src/libproc_macro/diagnostic.rs @@ -16,6 +16,7 @@ use syntax_pos::MultiSpan; /// An enum representing a diagnostic level. #[unstable(feature = "proc_macro_diagnostic", issue = "38356")] #[derive(Copy, Clone, Debug)] +#[non_exhaustive] pub enum Level { /// An error. Error, @@ -25,8 +26,6 @@ pub enum Level { Note, /// A help message. Help, - #[doc(hidden)] - __Nonexhaustive, } /// A structure representing a diagnostic message and associated children diff --git a/src/libproc_macro/lib.rs b/src/libproc_macro/lib.rs index fec90008c6701..b54054752eaf1 100644 --- a/src/libproc_macro/lib.rs +++ b/src/libproc_macro/lib.rs @@ -36,6 +36,7 @@ #![feature(staged_api)] #![feature(lang_items)] #![feature(optin_builtin_traits)] +#![feature(non_exhaustive)] #![recursion_limit="256"] @@ -180,6 +181,20 @@ impl iter::FromIterator for TokenStream { } } +#[stable(feature = "token_stream_extend", since = "1.30.0")] +impl Extend for TokenStream { + fn extend>(&mut self, trees: I) { + self.extend(trees.into_iter().map(TokenStream::from)); + } +} + +#[stable(feature = "token_stream_extend", since = "1.30.0")] +impl Extend for TokenStream { + fn extend>(&mut self, streams: I) { + self.0.extend(streams.into_iter().map(|stream| stream.0)); + } +} + /// Public implementation details for the `TokenStream` type, such as iterators. #[stable(feature = "proc_macro_lib2", since = "1.29.0")] pub mod token_stream { diff --git a/src/libproc_macro/rustc.rs b/src/libproc_macro/rustc.rs index a54c695f6376f..21229d3299d7e 100644 --- a/src/libproc_macro/rustc.rs +++ b/src/libproc_macro/rustc.rs @@ -278,7 +278,6 @@ impl Level { Level::Warning => errors::Level::Warning, Level::Note => errors::Level::Note, Level::Help => errors::Level::Help, - Level::__Nonexhaustive => unreachable!("Level::__Nonexhaustive"), } } } diff --git a/src/librustc/mir/mod.rs b/src/librustc/mir/mod.rs index dae5709ba114a..8ceff303774b5 100644 --- a/src/librustc/mir/mod.rs +++ b/src/librustc/mir/mod.rs @@ -429,8 +429,8 @@ pub enum BorrowKind { /// Data must be immutable but not aliasable. This kind of borrow /// cannot currently be expressed by the user and is used only in - /// implicit closure bindings. It is needed when you the closure - /// is borrowing or mutating a mutable referent, e.g.: + /// implicit closure bindings. It is needed when the closure is + /// borrowing or mutating a mutable referent, e.g.: /// /// let x: &mut isize = ...; /// let y = || *x += 5; @@ -443,7 +443,7 @@ pub enum BorrowKind { /// let y = (&mut Env { &x }, fn_ptr); // Closure is pair of env and fn /// fn fn_ptr(env: &mut Env) { **env.x += 5; } /// - /// This is then illegal because you cannot mutate a `&mut` found + /// This is then illegal because you cannot mutate an `&mut` found /// in an aliasable location. To solve, you'd have to translate with /// an `&mut` borrow: /// @@ -523,6 +523,8 @@ pub struct VarBindingForm<'tcx> { /// (b) it gives a way to separate this case from the remaining cases /// for diagnostics. pub opt_match_place: Option<(Option>, Span)>, + /// Span of the pattern in which this variable was bound. + pub pat_span: Span, } #[derive(Clone, PartialEq, Eq, Hash, Debug, RustcEncodable, RustcDecodable)] @@ -540,7 +542,8 @@ CloneTypeFoldableAndLiftImpls! { BindingForm<'tcx>, } impl_stable_hash_for!(struct self::VarBindingForm<'tcx> { binding_mode, opt_ty_info, - opt_match_place + opt_match_place, + pat_span }); mod binding_form_impl { @@ -673,7 +676,7 @@ pub struct LocalDecl<'tcx> { /// ROOT SCOPE /// │{ argument x: &str } /// │ - /// │ │{ #[allow(unused_mut] } // this is actually split into 2 scopes + /// │ │{ #[allow(unused_mut)] } // this is actually split into 2 scopes /// │ │ // in practice because I'm lazy. /// │ │ /// │ │← x.source_info.scope @@ -710,6 +713,7 @@ impl<'tcx> LocalDecl<'tcx> { binding_mode: ty::BindingMode::BindByValue(_), opt_ty_info: _, opt_match_place: _, + pat_span: _, }))) => true, // FIXME: might be able to thread the distinction between @@ -729,6 +733,7 @@ impl<'tcx> LocalDecl<'tcx> { binding_mode: ty::BindingMode::BindByValue(_), opt_ty_info: _, opt_match_place: _, + pat_span: _, }))) => true, Some(ClearCrossCrate::Set(BindingForm::ImplicitSelf)) => true, @@ -906,7 +911,7 @@ pub enum TerminatorKind<'tcx> { /// Drop the Place and assign the new value over it. This ensures /// that the assignment to `P` occurs *even if* the destructor for - /// place unwinds. Its semantics are best explained by by the + /// place unwinds. Its semantics are best explained by the /// elaboration: /// /// ``` diff --git a/src/librustc/traits/on_unimplemented.rs b/src/librustc/traits/on_unimplemented.rs index e1395c3fa4427..280ce75720bcf 100644 --- a/src/librustc/traits/on_unimplemented.rs +++ b/src/librustc/traits/on_unimplemented.rs @@ -131,7 +131,7 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedDirective { parse_error(tcx, item.span, "this attribute must have a valid value", "expected value here", - Some(r#"eg `#[rustc_on_unimplemented = "foo"]`"#)); + Some(r#"eg `#[rustc_on_unimplemented(message="foo")]`"#)); } if errored { @@ -170,7 +170,7 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedDirective { return Err(parse_error(tcx, attr.span, "`#[rustc_on_unimplemented]` requires a value", "value required here", - Some(r#"eg `#[rustc_on_unimplemented = "foo"]`"#))); + Some(r#"eg `#[rustc_on_unimplemented(message="foo")]`"#))); }; debug!("of_item({:?}/{:?}) = {:?}", trait_def_id, impl_def_id, result); result @@ -213,10 +213,13 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedDirective { } } + let options: FxHashMap = options.into_iter() + .filter_map(|(k, v)| v.as_ref().map(|v| (k.to_owned(), v.to_owned()))) + .collect(); OnUnimplementedNote { - label: label.map(|l| l.format(tcx, trait_ref)), - message: message.map(|m| m.format(tcx, trait_ref)), - note: note.map(|n| n.format(tcx, trait_ref)), + label: label.map(|l| l.format(tcx, trait_ref, &options)), + message: message.map(|m| m.format(tcx, trait_ref, &options)), + note: note.map(|n| n.format(tcx, trait_ref, &options)), } } } @@ -251,6 +254,10 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { Position::ArgumentNamed(s) if s == "Self" => (), // `{ThisTraitsName}` is allowed Position::ArgumentNamed(s) if s == name => (), + // `{from_method}` is allowed + Position::ArgumentNamed(s) if s == "from_method" => (), + // `{from_desugaring}` is allowed + Position::ArgumentNamed(s) if s == "from_desugaring" => (), // So is `{A}` if A is a type parameter Position::ArgumentNamed(s) => match generics.params.iter().find(|param| { param.name == s @@ -258,17 +265,14 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { Some(_) => (), None => { span_err!(tcx.sess, span, E0230, - "there is no parameter \ - {} on trait {}", - s, name); + "there is no parameter `{}` on trait `{}`", s, name); result = Err(ErrorReported); } }, // `{:1}` and `{}` are not to be used Position::ArgumentIs(_) | Position::ArgumentImplicitlyIs(_) => { span_err!(tcx.sess, span, E0231, - "only named substitution \ - parameters are allowed"); + "only named substitution parameters are allowed"); result = Err(ErrorReported); } } @@ -280,7 +284,8 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { pub fn format(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>, - trait_ref: ty::TraitRef<'tcx>) + trait_ref: ty::TraitRef<'tcx>, + options: &FxHashMap) -> String { let name = tcx.item_name(trait_ref.def_id); @@ -296,6 +301,7 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { let name = param.name.to_string(); Some((name, value)) }).collect::>(); + let empty_string = String::new(); let parser = Parser::new(&self.0, None); parser.map(|p| { @@ -308,14 +314,20 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { &trait_str } None => { - bug!("broken on_unimplemented {:?} for {:?}: \ - no argument matching {:?}", - self.0, trait_ref, s) + if let Some(val) = options.get(s) { + val + } else if s == "from_desugaring" || s == "from_method" { + // don't break messages using these two arguments incorrectly + &empty_string + } else { + bug!("broken on_unimplemented {:?} for {:?}: \ + no argument matching {:?}", + self.0, trait_ref, s) + } } }, _ => { - bug!("broken on_unimplemented {:?} - bad \ - format arg", self.0) + bug!("broken on_unimplemented {:?} - bad format arg", self.0) } } } diff --git a/src/librustc_apfloat/ieee.rs b/src/librustc_apfloat/ieee.rs index 45279f18117c1..87d59d2e763cb 100644 --- a/src/librustc_apfloat/ieee.rs +++ b/src/librustc_apfloat/ieee.rs @@ -2306,24 +2306,14 @@ mod sig { /// One, not zero, based LSB. That is, returns 0 for a zeroed significand. pub(super) fn olsb(limbs: &[Limb]) -> usize { - for (i, &limb) in limbs.iter().enumerate() { - if limb != 0 { - return i * LIMB_BITS + limb.trailing_zeros() as usize + 1; - } - } - - 0 + limbs.iter().enumerate().find(|(_, &limb)| limb != 0).map_or(0, + |(i, limb)| i * LIMB_BITS + limb.trailing_zeros() as usize + 1) } /// One, not zero, based MSB. That is, returns 0 for a zeroed significand. pub(super) fn omsb(limbs: &[Limb]) -> usize { - for (i, &limb) in limbs.iter().enumerate().rev() { - if limb != 0 { - return (i + 1) * LIMB_BITS - limb.leading_zeros() as usize; - } - } - - 0 + limbs.iter().enumerate().rfind(|(_, &limb)| limb != 0).map_or(0, + |(i, limb)| (i + 1) * LIMB_BITS - limb.leading_zeros() as usize) } /// Comparison (unsigned) of two significands. diff --git a/src/librustc_borrowck/borrowck/mod.rs b/src/librustc_borrowck/borrowck/mod.rs index 098149c36ce43..5b08400eb112d 100644 --- a/src/librustc_borrowck/borrowck/mod.rs +++ b/src/librustc_borrowck/borrowck/mod.rs @@ -1235,7 +1235,7 @@ impl<'a, 'tcx> BorrowckCtxt<'a, 'tcx> { ty::BindByReference(..) => { let let_span = self.tcx.hir.span(node_id); let suggestion = suggest_ref_mut(self.tcx, let_span); - if let Some((let_span, replace_str)) = suggestion { + if let Some(replace_str) = suggestion { db.span_suggestion( let_span, "use a mutable reference instead", diff --git a/src/librustc_mir/borrow_check/move_errors.rs b/src/librustc_mir/borrow_check/move_errors.rs index d3524e841b223..56ca4db098f87 100644 --- a/src/librustc_mir/borrow_check/move_errors.rs +++ b/src/librustc_mir/borrow_check/move_errors.rs @@ -8,7 +8,7 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use rustc::hir; +use core::unicode::property::Pattern_White_Space; use rustc::mir::*; use rustc::ty; use rustc_errors::DiagnosticBuilder; @@ -36,18 +36,18 @@ use util::borrowck_errors::{BorrowckErrors, Origin}; // let (&x, &y) = (&String::new(), &String::new()); #[derive(Debug)] enum GroupedMoveError<'tcx> { - // Match place can't be moved from + // Place expression can't be moved from, // e.g. match x[0] { s => (), } where x: &[String] - MovesFromMatchPlace { + MovesFromPlace { original_path: Place<'tcx>, span: Span, move_from: Place<'tcx>, kind: IllegalMoveOriginKind<'tcx>, binds_to: Vec, }, - // Part of a pattern can't be moved from, + // Part of a value expression can't be moved from, // e.g. match &String::new() { &x => (), } - MovesFromPattern { + MovesFromValue { original_path: Place<'tcx>, span: Span, move_from: MovePathIndex, @@ -119,6 +119,7 @@ impl<'a, 'gcx, 'tcx> MirBorrowckCtxt<'a, 'gcx, 'tcx> { opt_match_place: Some((ref opt_match_place, match_span)), binding_mode: _, opt_ty_info: _, + pat_span: _, }))) = local_decl.is_user_variable { self.append_binding_error( @@ -155,7 +156,7 @@ impl<'a, 'gcx, 'tcx> MirBorrowckCtxt<'a, 'gcx, 'tcx> { statement_span: Span, ) { debug!( - "append_to_grouped_errors(match_place={:?}, match_span={:?})", + "append_binding_error(match_place={:?}, match_span={:?})", match_place, match_span ); @@ -166,7 +167,7 @@ impl<'a, 'gcx, 'tcx> MirBorrowckCtxt<'a, 'gcx, 'tcx> { // Error with the match place LookupResult::Parent(_) => { for ge in &mut *grouped_errors { - if let GroupedMoveError::MovesFromMatchPlace { span, binds_to, .. } = ge { + if let GroupedMoveError::MovesFromPlace { span, binds_to, .. } = ge { if match_span == *span { debug!("appending local({:?}) to list", bind_to); if !binds_to.is_empty() { @@ -184,7 +185,7 @@ impl<'a, 'gcx, 'tcx> MirBorrowckCtxt<'a, 'gcx, 'tcx> { } else { (vec![bind_to], match_span) }; - grouped_errors.push(GroupedMoveError::MovesFromMatchPlace { + grouped_errors.push(GroupedMoveError::MovesFromPlace { span, move_from: match_place.clone(), original_path, @@ -200,7 +201,7 @@ impl<'a, 'gcx, 'tcx> MirBorrowckCtxt<'a, 'gcx, 'tcx> { _ => unreachable!("Probably not unreachable..."), }; for ge in &mut *grouped_errors { - if let GroupedMoveError::MovesFromPattern { + if let GroupedMoveError::MovesFromValue { span, move_from: other_mpi, binds_to, @@ -215,7 +216,7 @@ impl<'a, 'gcx, 'tcx> MirBorrowckCtxt<'a, 'gcx, 'tcx> { } } debug!("found a new move error location"); - grouped_errors.push(GroupedMoveError::MovesFromPattern { + grouped_errors.push(GroupedMoveError::MovesFromValue { span: match_span, move_from: mpi, original_path, @@ -230,13 +231,13 @@ impl<'a, 'gcx, 'tcx> MirBorrowckCtxt<'a, 'gcx, 'tcx> { let (mut err, err_span) = { let (span, original_path, kind): (Span, &Place<'tcx>, &IllegalMoveOriginKind) = match error { - GroupedMoveError::MovesFromMatchPlace { + GroupedMoveError::MovesFromPlace { span, ref original_path, ref kind, .. } | - GroupedMoveError::MovesFromPattern { span, ref original_path, ref kind, .. } | + GroupedMoveError::MovesFromValue { span, ref original_path, ref kind, .. } | GroupedMoveError::OtherIllegalMove { span, ref original_path, ref kind } => { (span, original_path, kind) }, @@ -331,111 +332,140 @@ impl<'a, 'gcx, 'tcx> MirBorrowckCtxt<'a, 'gcx, 'tcx> { err: &mut DiagnosticBuilder<'a>, span: Span, ) { + let snippet = self.tcx.sess.codemap().span_to_snippet(span).unwrap(); match error { - GroupedMoveError::MovesFromMatchPlace { + GroupedMoveError::MovesFromPlace { mut binds_to, move_from, .. } => { - // Ok to suggest a borrow, since the target can't be moved from - // anyway. - if let Ok(snippet) = self.tcx.sess.codemap().span_to_snippet(span) { - match move_from { - Place::Projection(ref proj) - if self.suitable_to_remove_deref(proj, &snippet) => - { - err.span_suggestion( - span, - "consider removing this dereference operator", - (&snippet[1..]).to_owned(), - ); - } - _ => { - err.span_suggestion( - span, - "consider using a reference instead", - format!("&{}", snippet), - ); - } - } - - binds_to.sort(); - binds_to.dedup(); - for local in binds_to { - let bind_to = &self.mir.local_decls[local]; - let binding_span = bind_to.source_info.span; - err.span_label( - binding_span, - format!( - "move occurs because {} has type `{}`, \ - which does not implement the `Copy` trait", - bind_to.name.unwrap(), - bind_to.ty - ), - ); - } + let try_remove_deref = match move_from { + Place::Projection(box PlaceProjection { + elem: ProjectionElem::Deref, + .. + }) => true, + _ => false, + }; + if try_remove_deref && snippet.starts_with('*') { + // The snippet doesn't start with `*` in (e.g.) index + // expressions `a[b]`, which roughly desugar to + // `*Index::index(&a, b)` or + // `*IndexMut::index_mut(&mut a, b)`. + err.span_suggestion( + span, + "consider removing the `*`", + snippet[1..].to_owned(), + ); + } else { + err.span_suggestion( + span, + "consider borrowing here", + format!("&{}", snippet), + ); } + + binds_to.sort(); + binds_to.dedup(); + self.add_move_error_details(err, &binds_to); } - GroupedMoveError::MovesFromPattern { mut binds_to, .. } => { - // Suggest ref, since there might be a move in - // another match arm + GroupedMoveError::MovesFromValue { mut binds_to, .. } => { binds_to.sort(); binds_to.dedup(); - let mut multipart_suggestion = Vec::with_capacity(binds_to.len()); - for (j, local) in binds_to.into_iter().enumerate() { - let bind_to = &self.mir.local_decls[local]; - let binding_span = bind_to.source_info.span; + self.add_move_error_suggestions(err, &binds_to); + self.add_move_error_details(err, &binds_to); + } + // No binding. Nothing to suggest. + GroupedMoveError::OtherIllegalMove { .. } => (), + } + } - // Suggest ref mut when the user has already written mut. - let ref_kind = match bind_to.mutability { - Mutability::Not => "ref", - Mutability::Mut => "ref mut", - }; - if j == 0 { - err.span_label(binding_span, format!("data moved here")); + fn add_move_error_suggestions( + &self, + err: &mut DiagnosticBuilder<'a>, + binds_to: &[Local], + ) { + let mut suggestions: Vec<(Span, &str, String)> = Vec::new(); + for local in binds_to { + let bind_to = &self.mir.local_decls[*local]; + if let Some( + ClearCrossCrate::Set(BindingForm::Var(VarBindingForm { + pat_span, + .. + })) + ) = bind_to.is_user_variable { + let pat_snippet = self + .tcx.sess.codemap() + .span_to_snippet(pat_span) + .unwrap(); + if pat_snippet.starts_with('&') { + let pat_snippet = pat_snippet[1..].trim_left(); + let suggestion; + let to_remove; + if pat_snippet.starts_with("mut") + && pat_snippet["mut".len()..].starts_with(Pattern_White_Space) + { + suggestion = pat_snippet["mut".len()..].trim_left(); + to_remove = "&mut"; } else { - err.span_label(binding_span, format!("... and here")); - } - match bind_to.name { - Some(name) => { - multipart_suggestion.push((binding_span, - format!("{} {}", ref_kind, name))); - } - None => { - err.span_label( - span, - format!("Local {:?} is not suitable for ref", bind_to), - ); - } + suggestion = pat_snippet; + to_remove = "&"; } + suggestions.push(( + pat_span, + to_remove, + suggestion.to_owned(), + )); } - err.multipart_suggestion("to prevent move, use ref or ref mut", - multipart_suggestion); } - // Nothing to suggest. - GroupedMoveError::OtherIllegalMove { .. } => (), + } + suggestions.sort_unstable_by_key(|&(span, _, _)| span); + suggestions.dedup_by_key(|&mut (span, _, _)| span); + for (span, to_remove, suggestion) in suggestions { + err.span_suggestion( + span, + &format!("consider removing the `{}`", to_remove), + suggestion + ); } } - fn suitable_to_remove_deref(&self, proj: &PlaceProjection<'tcx>, snippet: &str) -> bool { - let is_shared_ref = |ty: ty::Ty| match ty.sty { - ty::TypeVariants::TyRef(.., hir::Mutability::MutImmutable) => true, - _ => false, - }; + fn add_move_error_details( + &self, + err: &mut DiagnosticBuilder<'a>, + binds_to: &[Local], + ) { + let mut noncopy_var_spans = Vec::new(); + for (j, local) in binds_to.into_iter().enumerate() { + let bind_to = &self.mir.local_decls[*local]; + let binding_span = bind_to.source_info.span; - proj.elem == ProjectionElem::Deref && snippet.starts_with('*') && match proj.base { - Place::Local(local) => { - let local_decl = &self.mir.local_decls[local]; - // If this is a temporary, then this could be from an - // overloaded * operator. - local_decl.is_user_variable.is_some() && is_shared_ref(local_decl.ty) + if j == 0 { + err.span_label(binding_span, format!("data moved here")); + } else { + err.span_label(binding_span, format!("...and here")); } - Place::Promoted(_) => true, - Place::Static(ref st) => is_shared_ref(st.ty), - Place::Projection(ref proj) => match proj.elem { - ProjectionElem::Field(_, ty) => is_shared_ref(ty), - _ => false, - }, + + if binds_to.len() == 1 { + err.span_note( + binding_span, + &format!( + "move occurs because `{}` has type `{}`, \ + which does not implement the `Copy` trait", + bind_to.name.unwrap(), + bind_to.ty + ), + ); + } else { + noncopy_var_spans.push(binding_span); + } + } + + if binds_to.len() > 1 { + err.span_note( + noncopy_var_spans, + "move occurs because these variables have types that \ + don't implement the `Copy` trait", + ); } } } diff --git a/src/librustc_mir/borrow_check/mutability_errors.rs b/src/librustc_mir/borrow_check/mutability_errors.rs index 283cccd51174a..f11135fc026f5 100644 --- a/src/librustc_mir/borrow_check/mutability_errors.rs +++ b/src/librustc_mir/borrow_check/mutability_errors.rs @@ -329,7 +329,11 @@ impl<'a, 'gcx, 'tcx> MirBorrowckCtxt<'a, 'gcx, 'tcx> { ClearCrossCrate::Set(mir::BindingForm::Var(mir::VarBindingForm { binding_mode: ty::BindingMode::BindByReference(_), .. - })) => suggest_ref_mut(self.tcx, local_decl.source_info.span), + })) => { + let pattern_span = local_decl.source_info.span; + suggest_ref_mut(self.tcx, pattern_span) + .map(|replacement| (pattern_span, replacement)) + } // ClearCrossCrate::Set(mir::BindingForm::RefForGuard) => unreachable!(), diff --git a/src/librustc_mir/build/matches/mod.rs b/src/librustc_mir/build/matches/mod.rs index 6b6ec749bcbe6..b317bb7cff0e3 100644 --- a/src/librustc_mir/build/matches/mod.rs +++ b/src/librustc_mir/build/matches/mod.rs @@ -321,9 +321,10 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> { block.unit() } - /// Declares the bindings of the given pattern and returns the visibility scope - /// for the bindings in this patterns, if such a scope had to be created. - /// NOTE: Declaring the bindings should always be done in their drop scope. + /// Declares the bindings of the given patterns and returns the visibility + /// scope for the bindings in these patterns, if such a scope had to be + /// created. NOTE: Declaring the bindings should always be done in their + /// drop scope. pub fn declare_bindings(&mut self, mut visibility_scope: Option, scope_span: Span, @@ -356,7 +357,8 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> { let visibility_scope = visibility_scope.unwrap(); this.declare_binding(source_info, visibility_scope, mutability, name, mode, num_patterns, var, ty, has_guard, - opt_match_place.map(|(x, y)| (x.cloned(), y))); + opt_match_place.map(|(x, y)| (x.cloned(), y)), + patterns[0].span); }); visibility_scope } @@ -1181,7 +1183,8 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> { var_id: NodeId, var_ty: Ty<'tcx>, has_guard: ArmHasGuard, - opt_match_place: Option<(Option>, Span)>) + opt_match_place: Option<(Option>, Span)>, + pat_span: Span) { debug!("declare_binding(var_id={:?}, name={:?}, mode={:?}, var_ty={:?}, \ visibility_scope={:?}, source_info={:?})", @@ -1207,6 +1210,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> { // Instead, just abandon providing diagnostic info. opt_ty_info: None, opt_match_place, + pat_span, }))), }; let for_arm_body = self.local_decls.push(local.clone()); diff --git a/src/librustc_mir/build/mod.rs b/src/librustc_mir/build/mod.rs index 054bd69c361b9..c0c431804d8c1 100644 --- a/src/librustc_mir/build/mod.rs +++ b/src/librustc_mir/build/mod.rs @@ -763,6 +763,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> { binding_mode, opt_ty_info, opt_match_place: Some((Some(place.clone()), span)), + pat_span: span, }))) }; self.var_indices.insert(var, LocalsForNode::One(local)); diff --git a/src/librustc_mir/lib.rs b/src/librustc_mir/lib.rs index 42682c34407ca..bda80ff562c75 100644 --- a/src/librustc_mir/lib.rs +++ b/src/librustc_mir/lib.rs @@ -35,6 +35,7 @@ Rust MIR: a lowered representation of Rust. Also: an experiment! #![feature(try_trait)] #![feature(unicode_internals)] #![feature(step_trait)] +#![feature(slice_concat_ext)] #![recursion_limit="256"] diff --git a/src/librustc_mir/util/mod.rs b/src/librustc_mir/util/mod.rs index 78e9dd23e83ae..fe6fefe89fd66 100644 --- a/src/librustc_mir/util/mod.rs +++ b/src/librustc_mir/util/mod.rs @@ -31,14 +31,14 @@ pub use self::graphviz::write_node_label as write_graphviz_node_label; /// If possible, suggest replacing `ref` with `ref mut`. pub fn suggest_ref_mut<'cx, 'gcx, 'tcx>( tcx: ty::TyCtxt<'cx, 'gcx, 'tcx>, - pattern_span: Span, -) -> Option<(Span, String)> { - let hi_src = tcx.sess.codemap().span_to_snippet(pattern_span).unwrap(); + binding_span: Span, +) -> Option<(String)> { + let hi_src = tcx.sess.codemap().span_to_snippet(binding_span).unwrap(); if hi_src.starts_with("ref") && hi_src["ref".len()..].starts_with(Pattern_White_Space) { let replacement = format!("ref mut{}", &hi_src["ref".len()..]); - Some((pattern_span, replacement)) + Some(replacement) } else { None } diff --git a/src/librustc_target/spec/aarch64_pc_windows_msvc.rs b/src/librustc_target/spec/aarch64_pc_windows_msvc.rs new file mode 100644 index 0000000000000..8747f239d3418 --- /dev/null +++ b/src/librustc_target/spec/aarch64_pc_windows_msvc.rs @@ -0,0 +1,35 @@ +// Copyright 2018 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 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +use spec::{LinkerFlavor, Target, TargetResult, PanicStrategy, LldFlavor}; + +pub fn target() -> TargetResult { + let mut base = super::windows_msvc_base::opts(); + base.max_atomic_width = Some(64); + base.has_elf_tls = true; + + // FIXME: this shouldn't be panic=abort, it should be panic=unwind + base.panic_strategy = PanicStrategy::Abort; + base.linker = Some("rust-lld".to_owned()); + + Ok(Target { + llvm_target: "aarch64-pc-windows-msvc".to_string(), + target_endian: "little".to_string(), + target_pointer_width: "64".to_string(), + target_c_int_width: "32".to_string(), + data_layout: "e-m:w-p:64:64-i32:32-i64:64-i128:128-n32:64-S128".to_string(), + arch: "aarch64".to_string(), + target_os: "windows".to_string(), + target_env: "msvc".to_string(), + target_vendor: "pc".to_string(), + linker_flavor: LinkerFlavor::Lld(LldFlavor::Link), + options: base, + }) +} diff --git a/src/librustc_target/spec/mod.rs b/src/librustc_target/spec/mod.rs index d55762e03eee3..3a18c56f4fc59 100644 --- a/src/librustc_target/spec/mod.rs +++ b/src/librustc_target/spec/mod.rs @@ -355,6 +355,7 @@ supported_targets! { ("x86_64-pc-windows-gnu", x86_64_pc_windows_gnu), ("i686-pc-windows-gnu", i686_pc_windows_gnu), + ("aarch64-pc-windows-msvc", aarch64_pc_windows_msvc), ("x86_64-pc-windows-msvc", x86_64_pc_windows_msvc), ("i686-pc-windows-msvc", i686_pc_windows_msvc), ("i586-pc-windows-msvc", i586_pc_windows_msvc), diff --git a/src/libserialize/json.rs b/src/libserialize/json.rs index 0361718eb7337..35ef6327de5fd 100644 --- a/src/libserialize/json.rs +++ b/src/libserialize/json.rs @@ -365,6 +365,9 @@ impl std::error::Error for EncoderError { } impl From for EncoderError { + /// Converts a [`fmt::Error`] into `EncoderError` + /// + /// This conversion does not allocate memory. fn from(err: fmt::Error) -> EncoderError { EncoderError::FmtError(err) } } @@ -1387,10 +1390,9 @@ impl Stack { // Used by Parser to test whether the top-most element is an index. fn last_is_index(&self) -> bool { - if let Some(InternalIndex(_)) = self.stack.last() { - true - } else { - false + match self.stack.last() { + Some(InternalIndex(_)) => true, + _ => false, } } diff --git a/src/libstd/build.rs b/src/libstd/build.rs index 26d93f97e69f3..016e7adb4c914 100644 --- a/src/libstd/build.rs +++ b/src/libstd/build.rs @@ -104,7 +104,8 @@ fn build_libbacktrace(target: &str) -> Result<(), ()> { } else { build.file("../libbacktrace/elf.c"); - if target.contains("64") { + let pointer_width = env::var("CARGO_CFG_TARGET_POINTER_WIDTH").unwrap(); + if pointer_width == "64" { build.define("BACKTRACE_ELF_SIZE", "64"); } else { build.define("BACKTRACE_ELF_SIZE", "32"); diff --git a/src/libstd/io/error.rs b/src/libstd/io/error.rs index 02a3ce8b9c4d4..3e50988a68ba2 100644 --- a/src/libstd/io/error.rs +++ b/src/libstd/io/error.rs @@ -97,6 +97,7 @@ struct Custom { #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] #[stable(feature = "rust1", since = "1.0.0")] #[allow(deprecated)] +#[non_exhaustive] pub enum ErrorKind { /// An entity was not found, often a file. #[stable(feature = "rust1", since = "1.0.0")] @@ -180,15 +181,6 @@ pub enum ErrorKind { /// read. #[stable(feature = "read_exact", since = "1.6.0")] UnexpectedEof, - - /// A marker variant that tells the compiler that users of this enum cannot - /// match it exhaustively. - #[unstable(feature = "io_error_internals", - reason = "better expressed through extensible enums that this \ - enum cannot be exhaustively matched against", - issue = "0")] - #[doc(hidden)] - __Nonexhaustive, } impl ErrorKind { @@ -212,7 +204,6 @@ impl ErrorKind { ErrorKind::Interrupted => "operation interrupted", ErrorKind::Other => "other os error", ErrorKind::UnexpectedEof => "unexpected end of file", - ErrorKind::__Nonexhaustive => unreachable!() } } } diff --git a/src/libstd/lib.rs b/src/libstd/lib.rs index 5d463225ae93b..60ad330bb9b72 100644 --- a/src/libstd/lib.rs +++ b/src/libstd/lib.rs @@ -311,6 +311,7 @@ #![feature(doc_keyword)] #![feature(panic_info_message)] #![feature(panic_implementation)] +#![feature(non_exhaustive)] #![default_lib_allocator] diff --git a/src/libstd/sys/cloudabi/abi/cloudabi.rs b/src/libstd/sys/cloudabi/abi/cloudabi.rs index 2909db5098e58..cd9a5ad448f58 100644 --- a/src/libstd/sys/cloudabi/abi/cloudabi.rs +++ b/src/libstd/sys/cloudabi/abi/cloudabi.rs @@ -121,6 +121,7 @@ include!("bitflags.rs"); /// File or memory access pattern advisory information. #[repr(u8)] #[derive(Copy, Clone, Eq, PartialEq, Hash, Debug)] +#[non_exhaustive] pub enum advice { /// The application expects that it will not access the /// specified data in the near future. @@ -140,12 +141,12 @@ pub enum advice { /// The application expects to access the specified data /// in the near future. WILLNEED = 6, - #[doc(hidden)] _NonExhaustive = -1 as isize as u8, } /// Enumeration describing the kind of value stored in [`auxv`](struct.auxv.html). #[repr(u32)] #[derive(Copy, Clone, Eq, PartialEq, Hash, Debug)] +#[non_exhaustive] pub enum auxtype { /// Base address of the binary argument data provided to /// [`proc_exec()`](fn.proc_exec.html). @@ -210,12 +211,12 @@ pub enum auxtype { SYSINFO_EHDR = 262, /// Thread ID of the initial thread of the process. TID = 261, - #[doc(hidden)] _NonExhaustive = -1 as isize as u32, } /// Identifiers for clocks. #[repr(u32)] #[derive(Copy, Clone, Eq, PartialEq, Hash, Debug)] +#[non_exhaustive] pub enum clockid { /// The system-wide monotonic clock, which is defined as a /// clock measuring real time, whose value cannot be @@ -232,7 +233,6 @@ pub enum clockid { REALTIME = 3, /// The CPU-time clock associated with the current thread. THREAD_CPUTIME_ID = 4, - #[doc(hidden)] _NonExhaustive = -1 as isize as u32, } /// A userspace condition variable. @@ -267,6 +267,7 @@ pub const DIRCOOKIE_START: dircookie = dircookie(0); /// exclusively or merely provided for alignment with POSIX. #[repr(u16)] #[derive(Copy, Clone, Eq, PartialEq, Hash, Debug)] +#[non_exhaustive] pub enum errno { /// No error occurred. System call completed successfully. SUCCESS = 0, @@ -422,7 +423,6 @@ pub enum errno { XDEV = 75, /// Extension: Capabilities insufficient. NOTCAPABLE = 76, - #[doc(hidden)] _NonExhaustive = -1 as isize as u16, } bitflags! { @@ -438,6 +438,7 @@ bitflags! { /// Type of a subscription to an event or its occurrence. #[repr(u8)] #[derive(Copy, Clone, Eq, PartialEq, Hash, Debug)] +#[non_exhaustive] pub enum eventtype { /// The time value of clock [`subscription.union.clock.clock_id`](struct.subscription_clock.html#structfield.clock_id) /// has reached timestamp [`subscription.union.clock.timeout`](struct.subscription_clock.html#structfield.timeout). @@ -463,7 +464,6 @@ pub enum eventtype { /// The process associated with process descriptor /// [`subscription.union.proc_terminate.fd`](struct.subscription_proc_terminate.html#structfield.fd) has terminated. PROC_TERMINATE = 7, - #[doc(hidden)] _NonExhaustive = -1 as isize as u8, } /// Exit code generated by a process when exiting. @@ -530,6 +530,7 @@ pub type filesize = u64; /// The type of a file descriptor or file. #[repr(u8)] #[derive(Copy, Clone, Eq, PartialEq, Hash, Debug)] +#[non_exhaustive] pub enum filetype { /// The type of the file descriptor or file is unknown or /// is different from any of the other types specified. @@ -558,7 +559,6 @@ pub enum filetype { SOCKET_STREAM = 130, /// The file refers to a symbolic link inode. SYMBOLIC_LINK = 144, - #[doc(hidden)] _NonExhaustive = -1 as isize as u8, } bitflags! { @@ -847,12 +847,12 @@ bitflags! { /// memory. #[repr(u8)] #[derive(Copy, Clone, Eq, PartialEq, Hash, Debug)] +#[non_exhaustive] pub enum scope { /// The object is stored in private memory. PRIVATE = 4, /// The object is stored in shared memory. SHARED = 8, - #[doc(hidden)] _NonExhaustive = -1 as isize as u8, } bitflags! { @@ -878,6 +878,7 @@ bitflags! { /// Signal condition. #[repr(u8)] #[derive(Copy, Clone, Eq, PartialEq, Hash, Debug)] +#[non_exhaustive] pub enum signal { /// Process abort signal. /// @@ -983,7 +984,6 @@ pub enum signal { /// /// Action: Terminates the process. XFSZ = 26, - #[doc(hidden)] _NonExhaustive = -1 as isize as u8, } bitflags! { @@ -1049,6 +1049,7 @@ pub type userdata = u64; /// should be set. #[repr(u8)] #[derive(Copy, Clone, Eq, PartialEq, Hash, Debug)] +#[non_exhaustive] pub enum whence { /// Seek relative to current position. CUR = 1, @@ -1056,7 +1057,6 @@ pub enum whence { END = 2, /// Seek relative to start-of-file. SET = 3, - #[doc(hidden)] _NonExhaustive = -1 as isize as u8, } /// Auxiliary vector entry. diff --git a/src/libstd/sys/windows/backtrace/mod.rs b/src/libstd/sys/windows/backtrace/mod.rs index 7ef4e203571b2..f64cae810b9ac 100644 --- a/src/libstd/sys/windows/backtrace/mod.rs +++ b/src/libstd/sys/windows/backtrace/mod.rs @@ -229,6 +229,7 @@ impl StackFrame for c::STACKFRAME_EX { self.AddrFrame.Mode = c::ADDRESS_MODE::AddrModeFlat; c::IMAGE_FILE_MACHINE_I386 } + #[cfg(target_arch = "x86_64")] fn init(&mut self, ctx: &c::CONTEXT) -> c::DWORD { self.AddrPC.Offset = ctx.Rip as u64; @@ -240,6 +241,17 @@ impl StackFrame for c::STACKFRAME_EX { c::IMAGE_FILE_MACHINE_AMD64 } + #[cfg(target_arch = "aarch64")] + fn init(&mut self, ctx: &c::CONTEXT) -> c::DWORD { + self.AddrPC.Offset = ctx.Pc as u64; + self.AddrPC.Mode = c::ADDRESS_MODE::AddrModeFlat; + self.AddrStack.Offset = ctx.Sp as u64; + self.AddrStack.Mode = c::ADDRESS_MODE::AddrModeFlat; + self.AddrFrame.Offset = ctx.Fp as u64; + self.AddrFrame.Mode = c::ADDRESS_MODE::AddrModeFlat; + c::IMAGE_FILE_MACHINE_ARM64 + } + fn get_addr(&self) -> *const u8 { (self.AddrPC.Offset - 1) as *const u8 } @@ -260,6 +272,7 @@ impl StackFrame for c::STACKFRAME64 { self.AddrFrame.Mode = c::ADDRESS_MODE::AddrModeFlat; c::IMAGE_FILE_MACHINE_I386 } + #[cfg(target_arch = "x86_64")] fn init(&mut self, ctx: &c::CONTEXT) -> c::DWORD { self.AddrPC.Offset = ctx.Rip as u64; @@ -271,6 +284,17 @@ impl StackFrame for c::STACKFRAME64 { c::IMAGE_FILE_MACHINE_AMD64 } + #[cfg(target_arch = "aarch64")] + fn init(&mut self, ctx: &c::CONTEXT) -> c::DWORD { + self.AddrPC.Offset = ctx.Pc as u64; + self.AddrPC.Mode = c::ADDRESS_MODE::AddrModeFlat; + self.AddrStack.Offset = ctx.Sp as u64; + self.AddrStack.Mode = c::ADDRESS_MODE::AddrModeFlat; + self.AddrFrame.Offset = ctx.Fp as u64; + self.AddrFrame.Mode = c::ADDRESS_MODE::AddrModeFlat; + c::IMAGE_FILE_MACHINE_ARM64 + } + fn get_addr(&self) -> *const u8 { (self.AddrPC.Offset - 1) as *const u8 } diff --git a/src/libstd/sys/windows/c.rs b/src/libstd/sys/windows/c.rs index 6f81afe66f95b..e514a56dcc436 100644 --- a/src/libstd/sys/windows/c.rs +++ b/src/libstd/sys/windows/c.rs @@ -280,6 +280,9 @@ pub const IMAGE_FILE_MACHINE_I386: DWORD = 0x014c; #[cfg(target_arch = "x86_64")] #[cfg(feature = "backtrace")] pub const IMAGE_FILE_MACHINE_AMD64: DWORD = 0x8664; +#[cfg(target_arch = "aarch64")] +#[cfg(feature = "backtrace")] +pub const IMAGE_FILE_MACHINE_ARM64: DWORD = 0xAA64; pub const EXCEPTION_CONTINUE_SEARCH: LONG = 0; pub const EXCEPTION_STACK_OVERFLOW: DWORD = 0xc00000fd; @@ -791,9 +794,68 @@ pub struct FLOATING_SAVE_AREA { // will not appear in the final documentation. This should be also defined for // other architectures supported by Windows such as ARM, and for historical // interest, maybe MIPS and PowerPC as well. -#[cfg(all(dox, not(any(target_arch = "x86_64", target_arch = "x86"))))] +#[cfg(all(dox, not(any(target_arch = "x86_64", target_arch = "x86", target_arch = "aarch64"))))] pub enum CONTEXT {} +#[cfg(target_arch = "aarch64")] +pub const ARM64_MAX_BREAKPOINTS: usize = 8; + +#[cfg(target_arch = "aarch64")] +pub const ARM64_MAX_WATCHPOINTS: usize = 2; + +#[cfg(target_arch = "aarch64")] +#[repr(C)] +pub struct ARM64_NT_NEON128 { + pub D: [f64; 2], +} + +#[cfg(target_arch = "aarch64")] +#[repr(C, align(16))] +pub struct CONTEXT { + pub ContextFlags: DWORD, + pub Cpsr: DWORD, + pub X0: u64, + pub X1: u64, + pub X2: u64, + pub X3: u64, + pub X4: u64, + pub X5: u64, + pub X6: u64, + pub X7: u64, + pub X8: u64, + pub X9: u64, + pub X10: u64, + pub X11: u64, + pub X12: u64, + pub X13: u64, + pub X14: u64, + pub X15: u64, + pub X16: u64, + pub X17: u64, + pub X18: u64, + pub X19: u64, + pub X20: u64, + pub X21: u64, + pub X22: u64, + pub X23: u64, + pub X24: u64, + pub X25: u64, + pub X26: u64, + pub X27: u64, + pub X28: u64, + pub Fp: u64, + pub Lr: u64, + pub Sp: u64, + pub Pc: u64, + pub V: [ARM64_NT_NEON128; 32], + pub Fpcr: DWORD, + pub Fpsr: DWORD, + pub Bcr: [DWORD; ARM64_MAX_BREAKPOINTS], + pub Bvr: [DWORD; ARM64_MAX_BREAKPOINTS], + pub Wcr: [DWORD; ARM64_MAX_WATCHPOINTS], + pub Wvr: [DWORD; ARM64_MAX_WATCHPOINTS], +} + #[repr(C)] pub struct SOCKADDR_STORAGE_LH { pub ss_family: ADDRESS_FAMILY, diff --git a/src/libstd/sys/windows/mod.rs b/src/libstd/sys/windows/mod.rs index 0d12ecf8fe3a1..ccf79de909fa9 100644 --- a/src/libstd/sys/windows/mod.rs +++ b/src/libstd/sys/windows/mod.rs @@ -266,8 +266,12 @@ pub fn dur2timeout(dur: Duration) -> c::DWORD { // handlers. // // https://msdn.microsoft.com/en-us/library/dn774154.aspx -#[cfg(any(target_arch = "x86", target_arch = "x86_64"))] +#[allow(unreachable_code)] pub unsafe fn abort_internal() -> ! { - asm!("int $$0x29" :: "{ecx}"(7) ::: volatile); // 7 is FAST_FAIL_FATAL_APP_EXIT - ::intrinsics::unreachable(); + #[cfg(any(target_arch = "x86", target_arch = "x86_64"))] + { + asm!("int $$0x29" :: "{ecx}"(7) ::: volatile); // 7 is FAST_FAIL_FATAL_APP_EXIT + ::intrinsics::unreachable(); + } + ::intrinsics::abort(); } diff --git a/src/libsyntax/attr/mod.rs b/src/libsyntax/attr/mod.rs index 879f555ba03ee..5857bd282f0bc 100644 --- a/src/libsyntax/attr/mod.rs +++ b/src/libsyntax/attr/mod.rs @@ -607,7 +607,7 @@ impl NestedMetaItemKind { } impl Lit { - fn tokens(&self) -> TokenStream { + crate fn tokens(&self) -> TokenStream { TokenTree::Token(self.span, self.node.token()).into() } } @@ -794,7 +794,7 @@ pub fn inject(mut krate: ast::Crate, parse_sess: &ParseSess, attrs: &[String]) - ); let start_span = parser.span; - let (path, tokens) = panictry!(parser.parse_path_and_tokens()); + let (path, tokens) = panictry!(parser.parse_meta_item_unrestricted()); let end_span = parser.span; if parser.token != token::Eof { parse_sess.span_diagnostic diff --git a/src/libsyntax/config.rs b/src/libsyntax/config.rs index 4fe78bf829a1c..b4e35a9d56496 100644 --- a/src/libsyntax/config.rs +++ b/src/libsyntax/config.rs @@ -90,7 +90,7 @@ impl<'a> StripUnconfigured<'a> { let cfg = parser.parse_meta_item()?; parser.expect(&token::Comma)?; let lo = parser.span.lo(); - let (path, tokens) = parser.parse_path_and_tokens()?; + let (path, tokens) = parser.parse_meta_item_unrestricted()?; parser.expect(&token::CloseDelim(token::Paren))?; Ok((cfg, path, tokens, parser.prev_span.with_lo(lo))) }) { diff --git a/src/libsyntax/feature_gate.rs b/src/libsyntax/feature_gate.rs index 56e69b9df9e04..395e5c9865232 100644 --- a/src/libsyntax/feature_gate.rs +++ b/src/libsyntax/feature_gate.rs @@ -1526,27 +1526,29 @@ impl<'a> Visitor<'a> for PostExpansionVisitor<'a> { } } - match attr.parse_meta(self.context.parse_sess) { - Ok(meta) => { - // allow attr_literals in #[repr(align(x))] and #[repr(packed(n))] - let mut allow_attr_literal = false; - if attr.path == "repr" { - if let Some(content) = meta.meta_item_list() { - allow_attr_literal = content.iter().any( - |c| c.check_name("align") || c.check_name("packed")); + if !self.context.features.unrestricted_attribute_tokens { + // Unfortunately, `parse_meta` cannot be called speculatively because it can report + // errors by itself, so we have to call it only if the feature is disabled. + match attr.parse_meta(self.context.parse_sess) { + Ok(meta) => { + // allow attr_literals in #[repr(align(x))] and #[repr(packed(n))] + let mut allow_attr_literal = false; + if attr.path == "repr" { + if let Some(content) = meta.meta_item_list() { + allow_attr_literal = content.iter().any( + |c| c.check_name("align") || c.check_name("packed")); + } } - } - if !allow_attr_literal && contains_novel_literal(&meta) { - gate_feature_post!(&self, attr_literals, attr.span, - "non-string literals in attributes, or string \ - literals in top-level positions, are experimental"); + if !allow_attr_literal && contains_novel_literal(&meta) { + gate_feature_post!(&self, attr_literals, attr.span, + "non-string literals in attributes, or string \ + literals in top-level positions, are experimental"); + } + } + Err(mut err) => { + err.help("try enabling `#![feature(unrestricted_attribute_tokens)]`").emit() } - } - Err(mut err) => { - err.cancel(); - gate_feature_post!(&self, unrestricted_attribute_tokens, attr.span, - "arbitrary tokens in non-macro attributes are unstable"); } } } @@ -1920,6 +1922,11 @@ pub fn get_features(span_handler: &Handler, krate_attrs: &[ast::Attribute], err.emit(); } + // Some features are known to be incomplete and using them is likely to have + // unanticipated results, such as compiler crashes. We warn the user about these + // to alert them. + let incomplete_features = ["generic_associated_types"]; + let mut features = Features::new(); let mut edition_enabled_features = FxHashMap(); @@ -1955,6 +1962,16 @@ pub fn get_features(span_handler: &Handler, krate_attrs: &[ast::Attribute], continue }; + if incomplete_features.iter().any(|f| *f == name.as_str()) { + span_handler.struct_span_warn( + mi.span, + &format!( + "the feature `{}` is incomplete and may cause the compiler to crash", + name + ) + ).emit(); + } + if let Some(edition) = ALL_EDITIONS.iter().find(|e| name == e.feature_name()) { if *edition <= crate_edition { continue diff --git a/src/libsyntax/lib.rs b/src/libsyntax/lib.rs index c48ad0a802cb0..0a42325d2b6ff 100644 --- a/src/libsyntax/lib.rs +++ b/src/libsyntax/lib.rs @@ -130,6 +130,9 @@ pub mod util { mod rc_slice; pub use self::rc_slice::RcSlice; + + mod rc_vec; + pub use self::rc_vec::RcVec; } pub mod json; diff --git a/src/libsyntax/parse/attr.rs b/src/libsyntax/parse/attr.rs index 4d59f64bb6b57..b0136c3e18b46 100644 --- a/src/libsyntax/parse/attr.rs +++ b/src/libsyntax/parse/attr.rs @@ -12,9 +12,9 @@ use attr; use ast; use codemap::respan; use parse::{SeqSep, PResult}; -use parse::token::{self, Nonterminal}; +use parse::token::{self, Nonterminal, DelimToken}; use parse::parser::{Parser, TokenType, PathStyle}; -use tokenstream::TokenStream; +use tokenstream::{TokenStream, TokenTree}; #[derive(Debug)] enum InnerAttributeParsePolicy<'a> { @@ -116,7 +116,7 @@ impl<'a> Parser<'a> { }; self.expect(&token::OpenDelim(token::Bracket))?; - let (path, tokens) = self.parse_path_and_tokens()?; + let (path, tokens) = self.parse_meta_item_unrestricted()?; self.expect(&token::CloseDelim(token::Bracket))?; let hi = self.prev_span; @@ -138,7 +138,16 @@ impl<'a> Parser<'a> { }) } - crate fn parse_path_and_tokens(&mut self) -> PResult<'a, (ast::Path, TokenStream)> { + /// Parse an inner part of attribute - path and following tokens. + /// The tokens must be either a delimited token stream, or empty token stream, + /// or the "legacy" key-value form. + /// PATH `(` TOKEN_STREAM `)` + /// PATH `[` TOKEN_STREAM `]` + /// PATH `{` TOKEN_STREAM `}` + /// PATH + /// PATH `=` TOKEN_TREE + /// The delimiters or `=` are still put into the resulting token stream. + crate fn parse_meta_item_unrestricted(&mut self) -> PResult<'a, (ast::Path, TokenStream)> { let meta = match self.token { token::Interpolated(ref nt) => match nt.0 { Nonterminal::NtMeta(ref meta) => Some(meta.clone()), @@ -150,7 +159,22 @@ impl<'a> Parser<'a> { self.bump(); (meta.ident, meta.node.tokens(meta.span)) } else { - (self.parse_path(PathStyle::Mod)?, self.parse_tokens()) + let path = self.parse_path(PathStyle::Mod)?; + let tokens = if self.check(&token::OpenDelim(DelimToken::Paren)) || + self.check(&token::OpenDelim(DelimToken::Bracket)) || + self.check(&token::OpenDelim(DelimToken::Brace)) { + self.parse_token_tree().into() + } else if self.eat(&token::Eq) { + let eq = TokenTree::Token(self.prev_span, token::Eq); + let tree = match self.token { + token::CloseDelim(_) | token::Eof => self.unexpected()?, + _ => self.parse_token_tree(), + }; + TokenStream::concat(vec![eq.into(), tree.into()]) + } else { + TokenStream::empty() + }; + (path, tokens) }) } diff --git a/src/libsyntax/parse/lexer/comments.rs b/src/libsyntax/parse/lexer/comments.rs index 20a585b6601a5..2c53dbdc402a5 100644 --- a/src/libsyntax/parse/lexer/comments.rs +++ b/src/libsyntax/parse/lexer/comments.rs @@ -63,6 +63,7 @@ pub fn strip_doc_comment_decoration(comment: &str) -> String { if !lines.is_empty() && lines[0].chars().all(|c| c == '*') { i += 1; } + while i < j && lines[i].trim().is_empty() { i += 1; } @@ -74,9 +75,11 @@ pub fn strip_doc_comment_decoration(comment: &str) -> String { .all(|c| c == '*') { j -= 1; } + while j > i && lines[j - 1].trim().is_empty() { j -= 1; } + lines[i..j].to_vec() } @@ -85,6 +88,7 @@ pub fn strip_doc_comment_decoration(comment: &str) -> String { let mut i = usize::MAX; let mut can_trim = true; let mut first = true; + for line in &lines { for (j, c) in line.chars().enumerate() { if j > i || !"* \t".contains(c) { @@ -119,7 +123,8 @@ pub fn strip_doc_comment_decoration(comment: &str) -> String { } // one-line comments lose their prefix - const ONELINERS: &'static [&'static str] = &["///!", "///", "//!", "//"]; + const ONELINERS: &[&str] = &["///!", "///", "//!", "//"]; + for prefix in ONELINERS { if comment.starts_with(*prefix) { return (&comment[prefix.len()..]).to_string(); @@ -205,6 +210,7 @@ fn all_whitespace(s: &str, col: CharPos) -> Option { let len = s.len(); let mut col = col.to_usize(); let mut cursor: usize = 0; + while col > 0 && cursor < len { let ch = char_at(s, cursor); if !ch.is_whitespace() { @@ -213,7 +219,8 @@ fn all_whitespace(s: &str, col: CharPos) -> Option { cursor += ch.len_utf8(); col -= 1; } - return Some(cursor); + + Some(cursor) } fn trim_whitespace_prefix_and_push_line(lines: &mut Vec, s: String, col: CharPos) { @@ -246,11 +253,13 @@ fn read_block_comment(rdr: &mut StringReader, "src_index={}, end_src_index={}, line_begin_pos={}", src_index, end_src_index, rdr.filemap.line_begin_pos(rdr.pos).to_u32()); let mut n = 0; + while src_index < end_src_index { let c = char_at(&rdr.src, src_index); src_index += c.len_utf8(); n += 1; } + let col = CharPos(n); rdr.bump(); @@ -358,10 +367,10 @@ pub struct Literal { // it appears this function is called only from pprust... that's // probably not a good thing. pub fn gather_comments_and_literals(sess: &ParseSess, path: FileName, srdr: &mut dyn Read) - -> (Vec, Vec) { - let mut src = Vec::new(); - srdr.read_to_end(&mut src).unwrap(); - let src = String::from_utf8(src).unwrap(); + -> (Vec, Vec) +{ + let mut src = String::new(); + srdr.read_to_string(&mut src).unwrap(); let cm = CodeMap::new(sess.codemap().path_mapping().clone()); let filemap = cm.new_filemap(path, src); let mut rdr = lexer::StringReader::new_raw(sess, filemap, None); @@ -370,6 +379,7 @@ pub fn gather_comments_and_literals(sess: &ParseSess, path: FileName, srdr: &mut let mut literals: Vec = Vec::new(); let mut code_to_the_left = false; // Only code let mut anything_to_the_left = false; // Code or comments + while !rdr.is_eof() { loop { // Eat all the whitespace and count blank lines. diff --git a/src/libsyntax/parse/lexer/mod.rs b/src/libsyntax/parse/lexer/mod.rs index f9b9e95ead1b6..bdf25618f474e 100644 --- a/src/libsyntax/parse/lexer/mod.rs +++ b/src/libsyntax/parse/lexer/mod.rs @@ -67,29 +67,30 @@ pub struct StringReader<'a> { span_src_raw: Span, open_braces: Vec<(token::DelimToken, Span)>, crate override_span: Option, + last_unclosed_found_span: Option, } impl<'a> StringReader<'a> { fn mk_sp(&self, lo: BytePos, hi: BytePos) -> Span { self.mk_sp_and_raw(lo, hi).0 } + fn mk_sp_and_raw(&self, lo: BytePos, hi: BytePos) -> (Span, Span) { let raw = Span::new(lo, hi, NO_EXPANSION); - let real = unwrap_or!(self.override_span, raw); + let real = self.override_span.unwrap_or(raw); + (real, raw) } + fn mk_ident(&self, string: &str) -> Ident { let mut ident = Ident::from_str(string); if let Some(span) = self.override_span { ident.span = span; } + ident } - fn next_token(&mut self) -> TokenAndSpan where Self: Sized { - let res = self.try_next_token(); - self.unwrap_or_abort(res) - } fn unwrap_or_abort(&mut self, res: Result) -> TokenAndSpan { match res { Ok(tok) => tok, @@ -99,6 +100,25 @@ impl<'a> StringReader<'a> { } } } + + fn next_token(&mut self) -> TokenAndSpan where Self: Sized { + let res = self.try_next_token(); + self.unwrap_or_abort(res) + } + + /// Return the next token. EFFECT: advances the string_reader. + pub fn try_next_token(&mut self) -> Result { + assert!(self.fatal_errs.is_empty()); + let ret_val = TokenAndSpan { + tok: replace(&mut self.peek_tok, token::Whitespace), + sp: self.peek_span, + }; + self.advance_token()?; + self.span_src_raw = self.peek_span_src_raw; + + Ok(ret_val) + } + fn try_real_token(&mut self) -> Result { let mut t = self.try_next_token()?; loop { @@ -109,36 +129,32 @@ impl<'a> StringReader<'a> { _ => break, } } + self.token = t.tok.clone(); self.span = t.sp; + Ok(t) } + pub fn real_token(&mut self) -> TokenAndSpan { let res = self.try_real_token(); self.unwrap_or_abort(res) } + + #[inline] fn is_eof(&self) -> bool { self.ch.is_none() } - /// Return the next token. EFFECT: advances the string_reader. - pub fn try_next_token(&mut self) -> Result { - assert!(self.fatal_errs.is_empty()); - let ret_val = TokenAndSpan { - tok: replace(&mut self.peek_tok, token::Whitespace), - sp: self.peek_span, - }; - self.advance_token()?; - self.span_src_raw = self.peek_span_src_raw; - Ok(ret_val) - } fn fail_unterminated_raw_string(&self, pos: BytePos, hash_count: u16) { let mut err = self.struct_span_fatal(pos, pos, "unterminated raw string"); err.span_label(self.mk_sp(pos, pos), "unterminated raw string"); + if hash_count > 0 { err.note(&format!("this raw string should be terminated with `\"{}`", "#".repeat(hash_count as usize))); } + err.emit(); FatalError.raise(); } @@ -146,12 +162,15 @@ impl<'a> StringReader<'a> { fn fatal(&self, m: &str) -> FatalError { self.fatal_span(self.peek_span, m) } + pub fn emit_fatal_errors(&mut self) { for err in &mut self.fatal_errs { err.emit(); } + self.fatal_errs.clear(); } + pub fn peek(&self) -> TokenAndSpan { // FIXME(pcwalton): Bad copy! TokenAndSpan { @@ -161,15 +180,18 @@ impl<'a> StringReader<'a> { } /// For comments.rs, which hackily pokes into next_pos and ch - fn new_raw(sess: &'a ParseSess, filemap: Lrc, - override_span: Option) -> Self { + fn new_raw(sess: &'a ParseSess, filemap: Lrc, override_span: Option) + -> Self + { let mut sr = StringReader::new_raw_internal(sess, filemap, override_span); sr.bump(); + sr } fn new_raw_internal(sess: &'a ParseSess, filemap: Lrc, - override_span: Option) -> Self { + override_span: Option) -> Self + { if filemap.src.is_none() { sess.span_diagnostic.bug(&format!("Cannot lex filemap without source: {}", filemap.name)); @@ -195,16 +217,19 @@ impl<'a> StringReader<'a> { span_src_raw: syntax_pos::DUMMY_SP, open_braces: Vec::new(), override_span, + last_unclosed_found_span: None, } } pub fn new(sess: &'a ParseSess, filemap: Lrc, override_span: Option) - -> Self { + -> Self + { let mut sr = StringReader::new_raw(sess, filemap, override_span); if sr.advance_token().is_err() { sr.emit_fatal_errors(); FatalError.raise(); } + sr } @@ -229,9 +254,11 @@ impl<'a> StringReader<'a> { sr.emit_fatal_errors(); FatalError.raise(); } + sr } + #[inline] fn ch_is(&self, c: char) -> bool { self.ch == Some(c) } @@ -276,26 +303,23 @@ impl<'a> StringReader<'a> { let mut m = m.to_string(); m.push_str(": "); Self::push_escaped_char_for_msg(&mut m, c); + self.fatal_span_(from_pos, to_pos, &m[..]) } - fn struct_span_fatal(&self, - from_pos: BytePos, - to_pos: BytePos, - m: &str) - -> DiagnosticBuilder<'a> { + fn struct_span_fatal(&self, from_pos: BytePos, to_pos: BytePos, m: &str) + -> DiagnosticBuilder<'a> + { self.sess.span_diagnostic.struct_span_fatal(self.mk_sp(from_pos, to_pos), m) } - fn struct_fatal_span_char(&self, - from_pos: BytePos, - to_pos: BytePos, - m: &str, - c: char) - -> DiagnosticBuilder<'a> { + fn struct_fatal_span_char(&self, from_pos: BytePos, to_pos: BytePos, m: &str, c: char) + -> DiagnosticBuilder<'a> + { let mut m = m.to_string(); m.push_str(": "); Self::push_escaped_char_for_msg(&mut m, c); + self.sess.span_diagnostic.struct_span_fatal(self.mk_sp(from_pos, to_pos), &m[..]) } @@ -307,15 +331,14 @@ impl<'a> StringReader<'a> { Self::push_escaped_char_for_msg(&mut m, c); self.err_span_(from_pos, to_pos, &m[..]); } - fn struct_err_span_char(&self, - from_pos: BytePos, - to_pos: BytePos, - m: &str, - c: char) - -> DiagnosticBuilder<'a> { + + fn struct_err_span_char(&self, from_pos: BytePos, to_pos: BytePos, m: &str, c: char) + -> DiagnosticBuilder<'a> + { let mut m = m.to_string(); m.push_str(": "); Self::push_escaped_char_for_msg(&mut m, c); + self.sess.span_diagnostic.struct_span_err(self.mk_sp(from_pos, to_pos), &m[..]) } @@ -324,6 +347,7 @@ impl<'a> StringReader<'a> { fn fatal_span_verbose(&self, from_pos: BytePos, to_pos: BytePos, mut m: String) -> FatalError { m.push_str(": "); m.push_str(&self.src[self.src_index(from_pos)..self.src_index(to_pos)]); + self.fatal_span_(from_pos, to_pos, &m[..]) } @@ -354,6 +378,7 @@ impl<'a> StringReader<'a> { }; } } + Ok(()) } @@ -468,6 +493,7 @@ impl<'a> StringReader<'a> { } } + #[inline] fn nextch_is(&self, c: char) -> bool { self.nextch() == Some(c) } @@ -484,6 +510,7 @@ impl<'a> StringReader<'a> { None } + #[inline] fn nextnextch_is(&self, c: char) -> bool { self.nextnextch() == Some(c) } @@ -493,8 +520,10 @@ impl<'a> StringReader<'a> { if !ident_start(self.ch) { return None; } + let start = self.pos; self.bump(); + while ident_continue(self.ch) { self.bump(); } @@ -709,6 +738,7 @@ impl<'a> StringReader<'a> { fn scan_digits(&mut self, real_radix: u32, scan_radix: u32) -> usize { assert!(real_radix <= scan_radix); let mut len = 0; + loop { let c = self.ch; if c == Some('_') { @@ -736,31 +766,29 @@ impl<'a> StringReader<'a> { /// Lex a LIT_INTEGER or a LIT_FLOAT fn scan_number(&mut self, c: char) -> token::Lit { - let num_digits; let mut base = 10; let start_bpos = self.pos; - self.bump(); - if c == '0' { + let num_digits = if c == '0' { match self.ch.unwrap_or('\0') { 'b' => { self.bump(); base = 2; - num_digits = self.scan_digits(2, 10); + self.scan_digits(2, 10) } 'o' => { self.bump(); base = 8; - num_digits = self.scan_digits(8, 10); + self.scan_digits(8, 10) } 'x' => { self.bump(); base = 16; - num_digits = self.scan_digits(16, 16); + self.scan_digits(16, 16) } '0'..='9' | '_' | '.' | 'e' | 'E' => { - num_digits = self.scan_digits(10, 10) + 1; + self.scan_digits(10, 10) + 1 } _ => { // just a 0 @@ -768,15 +796,14 @@ impl<'a> StringReader<'a> { } } } else if c.is_digit(10) { - num_digits = self.scan_digits(10, 10) + 1; + self.scan_digits(10, 10) + 1 } else { - num_digits = 0; - } + 0 + }; if num_digits == 0 { - self.err_span_(start_bpos, - self.pos, - "no valid digits found for number"); + self.err_span_(start_bpos, self.pos, "no valid digits found for number"); + return token::Integer(Symbol::intern("0")); } @@ -794,6 +821,7 @@ impl<'a> StringReader<'a> { } let pos = self.pos; self.check_float_base(start_bpos, pos, base); + token::Float(self.name_from(start_bpos)) } else { // it might be a float if it has an exponent @@ -873,7 +901,8 @@ impl<'a> StringReader<'a> { first_source_char: char, ascii_only: bool, delim: char) - -> bool { + -> bool + { match first_source_char { '\\' => { // '\X' for some X must be a character constant: @@ -1008,6 +1037,7 @@ impl<'a> StringReader<'a> { "overlong unicode escape (must have at most 6 hex digits)"); valid = false; } + loop { match self.ch { Some('}') => { @@ -1043,6 +1073,7 @@ impl<'a> StringReader<'a> { } self.bump(); } + valid } @@ -1050,9 +1081,11 @@ impl<'a> StringReader<'a> { fn scan_float_exponent(&mut self) { if self.ch_is('e') || self.ch_is('E') { self.bump(); + if self.ch_is('-') || self.ch_is('+') { self.bump(); } + if self.scan_digits(10, 10) == 0 { let mut err = self.struct_span_fatal( self.pos, self.next_pos, @@ -1125,6 +1158,7 @@ impl<'a> StringReader<'a> { ('b', Some('r'), Some('#')) => (false, false), _ => (true, false), }; + if is_ident_start { let raw_start = self.pos; if is_raw_ident { @@ -1135,6 +1169,7 @@ impl<'a> StringReader<'a> { let start = self.pos; self.bump(); + while ident_continue(self.ch) { self.bump(); } @@ -1142,16 +1177,19 @@ impl<'a> StringReader<'a> { return Ok(self.with_str_from(start, |string| { // FIXME: perform NFKC normalization here. (Issue #2253) let ident = self.mk_ident(string); + if is_raw_ident && (ident.is_path_segment_keyword() || ident.name == keywords::Underscore.name()) { self.fatal_span_(raw_start, self.pos, &format!("`r#{}` is not currently supported.", ident.name) ).raise(); } + if is_raw_ident { let span = self.mk_sp(raw_start, self.pos); self.sess.raw_identifier_spans.borrow_mut().push(span); } + token::Ident(ident, is_raw_ident) })); } @@ -1337,14 +1375,11 @@ impl<'a> StringReader<'a> { return Ok(token::Lifetime(ident)); } - let valid = self.scan_char_or_byte(start, - c2, - // ascii_only = - false, - '\''); + let valid = self.scan_char_or_byte(start, c2, /* ascii_only */ false, '\''); if !self.ch_is('\'') { let pos = self.pos; + loop { self.bump(); if self.ch_is('\'') { @@ -1370,6 +1405,7 @@ impl<'a> StringReader<'a> { break; } } + self.fatal_span_verbose(start_with_quote, pos, String::from("character literal may only contain one codepoint")).raise(); } @@ -1379,8 +1415,10 @@ impl<'a> StringReader<'a> { } else { Symbol::intern("0") }; + self.bump(); // advance ch past token let suffix = self.scan_optional_raw_name(); + Ok(token::Literal(token::Char(id), suffix)) } 'b' => { @@ -1392,12 +1430,14 @@ impl<'a> StringReader<'a> { _ => unreachable!(), // Should have been a token::Ident above. }; let suffix = self.scan_optional_raw_name(); + Ok(token::Literal(lit, suffix)) } '"' => { let start_bpos = self.pos; let mut valid = true; self.bump(); + while !self.ch_is('"') { if self.is_eof() { let last_bpos = self.pos; @@ -1409,11 +1449,7 @@ impl<'a> StringReader<'a> { let ch_start = self.pos; let ch = self.ch.unwrap(); self.bump(); - valid &= self.scan_char_or_byte(ch_start, - ch, - // ascii_only = - false, - '"'); + valid &= self.scan_char_or_byte(ch_start, ch, /* ascii_only */ false, '"'); } // adjust for the ASCII " at the start of the literal let id = if valid { @@ -1423,6 +1459,7 @@ impl<'a> StringReader<'a> { }; self.bump(); let suffix = self.scan_optional_raw_name(); + Ok(token::Literal(token::Str_(id), suffix)) } 'r' => { @@ -1492,6 +1529,7 @@ impl<'a> StringReader<'a> { } self.bump(); } + self.bump(); let id = if valid { self.name_from_to(content_start_bpos, content_end_bpos) @@ -1499,6 +1537,7 @@ impl<'a> StringReader<'a> { Symbol::intern("??") }; let suffix = self.scan_optional_raw_name(); + Ok(token::Literal(token::StrRaw(id, hash_count), suffix)) } '-' => { @@ -1555,6 +1594,7 @@ impl<'a> StringReader<'a> { c); unicode_chars::check_for_substitution(self, c, &mut err); self.fatal_errs.push(err); + Err(()) } } @@ -1572,9 +1612,11 @@ impl<'a> StringReader<'a> { val.push(self.ch.unwrap()); self.bump(); } + if self.ch_is('\n') { self.bump(); } + val } @@ -1626,9 +1668,11 @@ impl<'a> StringReader<'a> { Symbol::intern("?") }; self.bump(); // advance ch past token + token::Byte(id) } + #[inline] fn scan_byte_escape(&mut self, delim: char, below_0x7f_only: bool) -> bool { self.scan_hex_digits(2, delim, below_0x7f_only) } @@ -1653,12 +1697,14 @@ impl<'a> StringReader<'a> { true, '"'); } + let id = if valid { self.name_from(start) } else { Symbol::intern("??") }; self.bump(); + token::ByteStr(id) } @@ -1716,25 +1762,26 @@ impl<'a> StringReader<'a> { } self.bump(); } + self.bump(); - token::ByteStrRaw(self.name_from_to(content_start_bpos, content_end_bpos), - hash_count) + + token::ByteStrRaw(self.name_from_to(content_start_bpos, content_end_bpos), hash_count) } } // This tests the character for the unicode property 'PATTERN_WHITE_SPACE' which // is guaranteed to be forward compatible. http://unicode.org/reports/tr31/#R3 +#[inline] crate fn is_pattern_whitespace(c: Option) -> bool { c.map_or(false, Pattern_White_Space) } +#[inline] fn in_range(c: Option, lo: char, hi: char) -> bool { - match c { - Some(c) => lo <= c && c <= hi, - _ => false, - } + c.map_or(false, |c| lo <= c && c <= hi) } +#[inline] fn is_dec_digit(c: Option) -> bool { in_range(c, '0', '9') } diff --git a/src/libsyntax/parse/lexer/tokentrees.rs b/src/libsyntax/parse/lexer/tokentrees.rs index 36c220fa0d943..e2fd7faf90387 100644 --- a/src/libsyntax/parse/lexer/tokentrees.rs +++ b/src/libsyntax/parse/lexer/tokentrees.rs @@ -17,9 +17,11 @@ impl<'a> StringReader<'a> { // Parse a stream of tokens into a list of `TokenTree`s, up to an `Eof`. crate fn parse_all_token_trees(&mut self) -> PResult<'a, TokenStream> { let mut tts = Vec::new(); + while self.token != token::Eof { tts.push(self.parse_token_tree()?); } + Ok(TokenStream::concat(tts)) } @@ -30,6 +32,7 @@ impl<'a> StringReader<'a> { if let token::CloseDelim(..) = self.token { return TokenStream::concat(tts); } + match self.parse_token_tree() { Ok(tree) => tts.push(tree), Err(mut e) => { @@ -48,6 +51,7 @@ impl<'a> StringReader<'a> { for &(_, sp) in &self.open_braces { err.span_help(sp, "did you mean to close this delimiter?"); } + Err(err) }, token::OpenDelim(delim) => { @@ -77,16 +81,23 @@ impl<'a> StringReader<'a> { // Incorrect delimiter. token::CloseDelim(other) => { let token_str = token_to_string(&self.token); - let msg = format!("incorrect close delimiter: `{}`", token_str); - let mut err = self.sess.span_diagnostic.struct_span_err(self.span, &msg); - // This is a conservative error: only report the last unclosed delimiter. - // The previous unclosed delimiters could actually be closed! The parser - // just hasn't gotten to them yet. - if let Some(&(_, sp)) = self.open_braces.last() { - err.span_note(sp, "unclosed delimiter"); - }; - err.emit(); - + if self.last_unclosed_found_span != Some(self.span) { + // do not complain about the same unclosed delimiter multiple times + self.last_unclosed_found_span = Some(self.span); + let msg = format!("incorrect close delimiter: `{}`", token_str); + let mut err = self.sess.span_diagnostic.struct_span_err( + self.span, + &msg, + ); + err.span_label(self.span, "incorrect close delimiter"); + // This is a conservative error: only report the last unclosed + // delimiter. The previous unclosed delimiters could actually be + // closed! The parser just hasn't gotten to them yet. + if let Some(&(_, sp)) = self.open_braces.last() { + err.span_label(sp, "unclosed delimiter"); + }; + err.emit(); + } self.open_braces.pop().unwrap(); // If the incorrect delimiter matches an earlier opening @@ -118,7 +129,8 @@ impl<'a> StringReader<'a> { // matching opening delimiter). let token_str = token_to_string(&self.token); let msg = format!("unexpected close delimiter: `{}`", token_str); - let err = self.sess.span_diagnostic.struct_span_err(self.span, &msg); + let mut err = self.sess.span_diagnostic.struct_span_err(self.span, &msg); + err.span_label(self.span, "unexpected close delimiter"); Err(err) }, _ => { @@ -129,6 +141,7 @@ impl<'a> StringReader<'a> { let raw = self.span_src_raw; self.real_token(); let is_joint = raw.hi() == self.span_src_raw.lo() && token::is_op(&self.token); + Ok(if is_joint { tt.joint() } else { tt.into() }) } } diff --git a/src/libsyntax/parse/lexer/unicode_chars.rs b/src/libsyntax/parse/lexer/unicode_chars.rs index a32b515672eca..88ff8582da801 100644 --- a/src/libsyntax/parse/lexer/unicode_chars.rs +++ b/src/libsyntax/parse/lexer/unicode_chars.rs @@ -15,7 +15,7 @@ use syntax_pos::{Span, NO_EXPANSION}; use errors::DiagnosticBuilder; use super::StringReader; -const UNICODE_ARRAY: &'static [(char, &'static str, char)] = &[ +const UNICODE_ARRAY: &[(char, &str, char)] = &[ ('
', "Line Separator", ' '), ('
', "Paragraph Separator", ' '), (' ', "Ogham Space mark", ' '), diff --git a/src/libsyntax/parse/parser.rs b/src/libsyntax/parse/parser.rs index 0e45cacaf38c9..345464c666425 100644 --- a/src/libsyntax/parse/parser.rs +++ b/src/libsyntax/parse/parser.rs @@ -825,7 +825,7 @@ impl<'a> Parser<'a> { /// /// This method will automatically add `tok` to `expected_tokens` if `tok` is not /// encountered. - fn check(&mut self, tok: &token::Token) -> bool { + crate fn check(&mut self, tok: &token::Token) -> bool { let is_present = self.token == *tok; if !is_present { self.expected_tokens.push(TokenType::Token(tok.clone())); } is_present @@ -4719,7 +4719,12 @@ impl<'a> Parser<'a> { if !self.eat(&token::OpenDelim(token::Brace)) { let sp = self.span; let tok = self.this_token_to_string(); + let mut do_not_suggest_help = false; let mut e = self.span_fatal(sp, &format!("expected `{{`, found `{}`", tok)); + if self.token.is_keyword(keywords::In) || self.token == token::Colon { + do_not_suggest_help = true; + e.span_label(sp, "expected `{`"); + } // Check to see if the user has written something like // @@ -4729,7 +4734,8 @@ impl<'a> Parser<'a> { // Which is valid in other languages, but not Rust. match self.parse_stmt_without_recovery(false) { Ok(Some(stmt)) => { - if self.look_ahead(1, |t| t == &token::OpenDelim(token::Brace)) { + if self.look_ahead(1, |t| t == &token::OpenDelim(token::Brace)) + || do_not_suggest_help { // if the next token is an open brace (e.g., `if a b {`), the place- // inside-a-block suggestion would be more likely wrong than right return Err(e); diff --git a/src/libsyntax/tokenstream.rs b/src/libsyntax/tokenstream.rs index fda975e6c456b..840ee299bf338 100644 --- a/src/libsyntax/tokenstream.rs +++ b/src/libsyntax/tokenstream.rs @@ -29,7 +29,7 @@ use parse::Directory; use parse::token::{self, Token}; use print::pprust; use serialize::{Decoder, Decodable, Encoder, Encodable}; -use util::RcSlice; +use util::RcVec; use std::borrow::Cow; use std::{fmt, iter, mem}; @@ -221,7 +221,7 @@ impl TokenStream { new_slice.extend_from_slice(parts.0); new_slice.push(comma); new_slice.extend_from_slice(parts.1); - let slice = RcSlice::new(new_slice); + let slice = RcVec::new(new_slice); return Some((TokenStream { kind: TokenStreamKind::Stream(slice) }, sp)); } } @@ -234,7 +234,7 @@ enum TokenStreamKind { Empty, Tree(TokenTree), JointTree(TokenTree), - Stream(RcSlice), + Stream(RcVec), } impl From for TokenStream { @@ -255,6 +255,60 @@ impl> iter::FromIterator for TokenStream { } } +impl Extend for TokenStream { + fn extend>(&mut self, iter: I) { + let iter = iter.into_iter(); + let kind = mem::replace(&mut self.kind, TokenStreamKind::Empty); + + // Vector of token streams originally in self. + let tts: Vec = match kind { + TokenStreamKind::Empty => { + let mut vec = Vec::new(); + vec.reserve(iter.size_hint().0); + vec + } + TokenStreamKind::Tree(_) | TokenStreamKind::JointTree(_) => { + let mut vec = Vec::new(); + vec.reserve(1 + iter.size_hint().0); + vec.push(TokenStream { kind }); + vec + } + TokenStreamKind::Stream(rc_vec) => match RcVec::try_unwrap(rc_vec) { + Ok(mut vec) => { + // Extend in place using the existing capacity if possible. + // This is the fast path for libraries like `quote` that + // build a token stream. + vec.reserve(iter.size_hint().0); + vec + } + Err(rc_vec) => { + // Self is shared so we need to copy and extend that. + let mut vec = Vec::new(); + vec.reserve(rc_vec.len() + iter.size_hint().0); + vec.extend_from_slice(&rc_vec); + vec + } + } + }; + + // Perform the extend, joining tokens as needed along the way. + let mut builder = TokenStreamBuilder(tts); + for stream in iter { + builder.push(stream); + } + + // Build the resulting token stream. If it contains more than one token, + // preserve capacity in the vector in anticipation of the caller + // performing additional calls to extend. + let mut tts = builder.0; + *self = match tts.len() { + 0 => TokenStream::empty(), + 1 => tts.pop().unwrap(), + _ => TokenStream::concat_rc_vec(RcVec::new_preserving_capacity(tts)), + }; + } +} + impl Eq for TokenStream {} impl PartialEq for TokenStream { @@ -287,11 +341,11 @@ impl TokenStream { match streams.len() { 0 => TokenStream::empty(), 1 => streams.pop().unwrap(), - _ => TokenStream::concat_rc_slice(RcSlice::new(streams)), + _ => TokenStream::concat_rc_vec(RcVec::new(streams)), } } - fn concat_rc_slice(streams: RcSlice) -> TokenStream { + fn concat_rc_vec(streams: RcVec) -> TokenStream { TokenStream { kind: TokenStreamKind::Stream(streams) } } @@ -434,7 +488,7 @@ impl TokenStreamBuilder { match len { 1 => {} 2 => self.0.push(streams[0].clone().into()), - _ => self.0.push(TokenStream::concat_rc_slice(streams.sub_slice(0 .. len - 1))), + _ => self.0.push(TokenStream::concat_rc_vec(streams.sub_slice(0 .. len - 1))), } self.push_all_but_last_tree(&streams[len - 1]) } @@ -446,7 +500,7 @@ impl TokenStreamBuilder { match len { 1 => {} 2 => self.0.push(streams[1].clone().into()), - _ => self.0.push(TokenStream::concat_rc_slice(streams.sub_slice(1 .. len))), + _ => self.0.push(TokenStream::concat_rc_vec(streams.sub_slice(1 .. len))), } self.push_all_but_first_tree(&streams[0]) } @@ -466,13 +520,13 @@ enum CursorKind { #[derive(Clone)] struct StreamCursor { - stream: RcSlice, + stream: RcVec, index: usize, - stack: Vec<(RcSlice, usize)>, + stack: Vec<(RcVec, usize)>, } impl StreamCursor { - fn new(stream: RcSlice) -> Self { + fn new(stream: RcVec) -> Self { StreamCursor { stream: stream, index: 0, stack: Vec::new() } } @@ -495,7 +549,7 @@ impl StreamCursor { } } - fn insert(&mut self, stream: RcSlice) { + fn insert(&mut self, stream: RcVec) { self.stack.push((mem::replace(&mut self.stream, stream), mem::replace(&mut self.index, 0))); } @@ -557,7 +611,7 @@ impl Cursor { CursorKind::Empty => TokenStream::empty(), CursorKind::Tree(ref tree, _) => tree.clone().into(), CursorKind::JointTree(ref tree, _) => tree.clone().joint(), - CursorKind::Stream(ref cursor) => TokenStream::concat_rc_slice({ + CursorKind::Stream(ref cursor) => TokenStream::concat_rc_vec({ cursor.stack.get(0).cloned().map(|(stream, _)| stream) .unwrap_or(cursor.stream.clone()) }), @@ -607,14 +661,14 @@ impl Cursor { /// `ThinTokenStream` is smaller, but needs to allocate to represent a single `TokenTree`. /// We must use `ThinTokenStream` in `TokenTree::Delimited` to avoid infinite size due to recursion. #[derive(Debug, Clone)] -pub struct ThinTokenStream(Option>); +pub struct ThinTokenStream(Option>); impl From for ThinTokenStream { fn from(stream: TokenStream) -> ThinTokenStream { ThinTokenStream(match stream.kind { TokenStreamKind::Empty => None, - TokenStreamKind::Tree(tree) => Some(RcSlice::new(vec![tree.into()])), - TokenStreamKind::JointTree(tree) => Some(RcSlice::new(vec![tree.joint()])), + TokenStreamKind::Tree(tree) => Some(RcVec::new(vec![tree.into()])), + TokenStreamKind::JointTree(tree) => Some(RcVec::new(vec![tree.joint()])), TokenStreamKind::Stream(stream) => Some(stream), }) } @@ -622,7 +676,7 @@ impl From for ThinTokenStream { impl From for TokenStream { fn from(stream: ThinTokenStream) -> TokenStream { - stream.0.map(TokenStream::concat_rc_slice).unwrap_or_else(TokenStream::empty) + stream.0.map(TokenStream::concat_rc_vec).unwrap_or_else(TokenStream::empty) } } @@ -773,4 +827,106 @@ mod tests { assert_eq!(stream.trees().count(), 1); } + #[test] + fn test_extend_empty() { + with_globals(|| { + // Append a token onto an empty token stream. + let mut stream = TokenStream::empty(); + stream.extend(vec![string_to_ts("t")]); + + let expected = string_to_ts("t"); + assert!(stream.eq_unspanned(&expected)); + }); + } + + #[test] + fn test_extend_nothing() { + with_globals(|| { + // Append nothing onto a token stream containing one token. + let mut stream = string_to_ts("t"); + stream.extend(vec![]); + + let expected = string_to_ts("t"); + assert!(stream.eq_unspanned(&expected)); + }); + } + + #[test] + fn test_extend_single() { + with_globals(|| { + // Append a token onto token stream containing a single token. + let mut stream = string_to_ts("t1"); + stream.extend(vec![string_to_ts("t2")]); + + let expected = string_to_ts("t1 t2"); + assert!(stream.eq_unspanned(&expected)); + }); + } + + #[test] + fn test_extend_in_place() { + with_globals(|| { + // Append a token onto token stream containing a reference counted + // vec of tokens. The token stream has a reference count of 1 so + // this can happen in place. + let mut stream = string_to_ts("t1 t2"); + stream.extend(vec![string_to_ts("t3")]); + + let expected = string_to_ts("t1 t2 t3"); + assert!(stream.eq_unspanned(&expected)); + }); + } + + #[test] + fn test_extend_copy() { + with_globals(|| { + // Append a token onto token stream containing a reference counted + // vec of tokens. The token stream is shared so the extend takes + // place on a copy. + let mut stream = string_to_ts("t1 t2"); + let _incref = stream.clone(); + stream.extend(vec![string_to_ts("t3")]); + + let expected = string_to_ts("t1 t2 t3"); + assert!(stream.eq_unspanned(&expected)); + }); + } + + #[test] + fn test_extend_no_join() { + with_globals(|| { + let first = TokenTree::Token(DUMMY_SP, Token::Dot); + let second = TokenTree::Token(DUMMY_SP, Token::Dot); + + // Append a dot onto a token stream containing a dot, but do not + // join them. + let mut stream = TokenStream::from(first); + stream.extend(vec![TokenStream::from(second)]); + + let expected = string_to_ts(". ."); + assert!(stream.eq_unspanned(&expected)); + + let unexpected = string_to_ts(".."); + assert!(!stream.eq_unspanned(&unexpected)); + }); + } + + #[test] + fn test_extend_join() { + with_globals(|| { + let first = TokenTree::Token(DUMMY_SP, Token::Dot).joint(); + let second = TokenTree::Token(DUMMY_SP, Token::Dot); + + // Append a dot onto a token stream containing a dot, forming a + // dotdot. + let mut stream = first; + stream.extend(vec![TokenStream::from(second)]); + + let expected = string_to_ts(".."); + assert!(stream.eq_unspanned(&expected)); + + let unexpected = string_to_ts(". ."); + assert!(!stream.eq_unspanned(&unexpected)); + }); + } } diff --git a/src/libsyntax/util/rc_vec.rs b/src/libsyntax/util/rc_vec.rs new file mode 100644 index 0000000000000..99fbce1ad91e1 --- /dev/null +++ b/src/libsyntax/util/rc_vec.rs @@ -0,0 +1,90 @@ +// Copyright 2017 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 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +use std::fmt; +use std::ops::{Deref, Range}; + +use rustc_data_structures::stable_hasher::{HashStable, StableHasher, StableHasherResult}; +use rustc_data_structures::sync::Lrc; + +#[derive(Clone)] +pub struct RcVec { + data: Lrc>, + offset: u32, + len: u32, +} + +impl RcVec { + pub fn new(mut vec: Vec) -> Self { + // By default, constructing RcVec from Vec gives it just enough capacity + // to hold the initial elements. Callers that anticipate needing to + // extend the vector may prefer RcVec::new_preserving_capacity. + vec.shrink_to_fit(); + Self::new_preserving_capacity(vec) + } + + pub fn new_preserving_capacity(vec: Vec) -> Self { + RcVec { + offset: 0, + len: vec.len() as u32, + data: Lrc::new(vec), + } + } + + pub fn sub_slice(&self, range: Range) -> Self { + RcVec { + data: self.data.clone(), + offset: self.offset + range.start as u32, + len: (range.end - range.start) as u32, + } + } + + /// If this RcVec has exactly one strong reference, returns ownership of the + /// underlying vector. Otherwise returns self unmodified. + pub fn try_unwrap(self) -> Result, Self> { + match Lrc::try_unwrap(self.data) { + // If no other RcVec shares ownership of this data. + Ok(mut vec) => { + // Drop any elements after our view of the data. + vec.truncate(self.offset as usize + self.len as usize); + // Drop any elements before our view of the data. Do this after + // the `truncate` so that elements past the end of our view do + // not need to be copied around. + vec.drain(..self.offset as usize); + Ok(vec) + } + + // If the data is shared. + Err(data) => Err(RcVec { data, ..self }), + } + } +} + +impl Deref for RcVec { + type Target = [T]; + fn deref(&self) -> &[T] { + &self.data[self.offset as usize..(self.offset + self.len) as usize] + } +} + +impl fmt::Debug for RcVec { + fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { + fmt::Debug::fmt(self.deref(), f) + } +} + +impl HashStable for RcVec +where + T: HashStable, +{ + fn hash_stable(&self, hcx: &mut CTX, hasher: &mut StableHasher) { + (**self).hash_stable(hcx, hasher); + } +} diff --git a/src/libsyntax_ext/deriving/default.rs b/src/libsyntax_ext/deriving/default.rs index 958116f7809bb..adbc5828b8fb8 100644 --- a/src/libsyntax_ext/deriving/default.rs +++ b/src/libsyntax_ext/deriving/default.rs @@ -76,8 +76,8 @@ fn default_substructure(cx: &mut ExtCtxt, trait_span: Span, substr: &Substructur } } StaticEnum(..) => { - span_err_if_not_stage0!(cx, trait_span, E0665, - "`Default` cannot be derived for enums, only structs"); + span_err!(cx, trait_span, E0665, + "`Default` cannot be derived for enums, only structs"); // let compilation continue cx.expr_usize(trait_span, 0) } diff --git a/src/libsyntax_ext/deriving/mod.rs b/src/libsyntax_ext/deriving/mod.rs index 2f5e42d2f7b17..ae47a028bc386 100644 --- a/src/libsyntax_ext/deriving/mod.rs +++ b/src/libsyntax_ext/deriving/mod.rs @@ -19,17 +19,6 @@ use syntax::ptr::P; use syntax::symbol::Symbol; use syntax_pos::Span; -macro_rules! span_err_if_not_stage0 { - ($cx:expr, $sp:expr, $code:ident, $text:tt) => { - #[cfg(not(stage0))] { - span_err!($cx, $sp, $code, $text) - } - #[cfg(stage0)] { - $cx.span_err($sp, $text) - } - } -} - macro path_local($x:ident) { generic::ty::Path::new_local(stringify!($x)) } diff --git a/src/test/compile-fail-fulldeps/issue-48941.rs b/src/test/compile-fail-fulldeps/issue-48941.rs index 4be2874ed4ff6..baeb019df1ca0 100644 --- a/src/test/compile-fail-fulldeps/issue-48941.rs +++ b/src/test/compile-fail-fulldeps/issue-48941.rs @@ -17,10 +17,7 @@ #![feature(plugin)] #![plugin(macro_crate_test)] -#[noop_attribute"x"] //~ ERROR expected one of -fn night() { } - -#[noop_attribute("hi"), rank = 2] //~ ERROR unexpected token +#[noop_attribute("hi", rank = a)] //~ ERROR expected unsuffixed literal or identifier, found a fn knight() { } #[noop_attribute("/user", data= = " or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +#[path =] //~ ERROR unexpected token: `]` +mod m {} diff --git a/src/test/parse-fail/attr-bad-meta-3.rs b/src/test/parse-fail/attr-bad-meta-3.rs new file mode 100644 index 0000000000000..92e2a59d25d87 --- /dev/null +++ b/src/test/parse-fail/attr-bad-meta-3.rs @@ -0,0 +1,12 @@ +// Copyright 2018 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 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +#[path() token] //~ ERROR expected `]`, found `token` +mod m {} diff --git a/src/test/parse-fail/attr-bad-meta.rs b/src/test/parse-fail/attr-bad-meta.rs index 41db88121cb52..6f9d794dc2dc3 100644 --- a/src/test/parse-fail/attr-bad-meta.rs +++ b/src/test/parse-fail/attr-bad-meta.rs @@ -8,6 +8,7 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -// asterisk is bogus -#[path*] //~ ERROR arbitrary tokens in non-macro attributes are unstable +#![feature(unrestricted_attribute_tokens)] + +#[path*] //~ ERROR expected one of `(`, `::`, `=`, `[`, `]`, or `{`, found `*` mod m {} diff --git a/src/test/run-pass-fulldeps/proc-macro/auxiliary/derive-b.rs b/src/test/run-pass-fulldeps/proc-macro/auxiliary/derive-b.rs index 7b521f2b9138a..e1aabad4142f9 100644 --- a/src/test/run-pass-fulldeps/proc-macro/auxiliary/derive-b.rs +++ b/src/test/run-pass-fulldeps/proc-macro/auxiliary/derive-b.rs @@ -19,7 +19,7 @@ use proc_macro::TokenStream; #[proc_macro_derive(B, attributes(B, C))] pub fn derive(input: TokenStream) -> TokenStream { let input = input.to_string(); - assert!(input.contains("#[B arbitrary tokens]")); + assert!(input.contains("#[B [ arbitrary tokens ]]")); assert!(input.contains("struct B {")); assert!(input.contains("#[C]")); "".parse().unwrap() diff --git a/src/test/run-pass-fulldeps/proc-macro/derive-b.rs b/src/test/run-pass-fulldeps/proc-macro/derive-b.rs index 918d2c17123e8..1de6496e29f8b 100644 --- a/src/test/run-pass-fulldeps/proc-macro/derive-b.rs +++ b/src/test/run-pass-fulldeps/proc-macro/derive-b.rs @@ -16,7 +16,7 @@ extern crate derive_b; #[derive(Debug, PartialEq, derive_b::B, Eq, Copy, Clone)] -#[cfg_attr(all(), B arbitrary tokens)] +#[cfg_attr(all(), B[arbitrary tokens])] struct B { #[C] a: u64 diff --git a/src/test/ui-fulldeps/invalid-punct-ident-4.stderr b/src/test/ui-fulldeps/invalid-punct-ident-4.stderr index 4493e37eeb273..669a1eb583921 100644 --- a/src/test/ui-fulldeps/invalid-punct-ident-4.stderr +++ b/src/test/ui-fulldeps/invalid-punct-ident-4.stderr @@ -2,7 +2,7 @@ error: unexpected close delimiter: `)` --> $DIR/invalid-punct-ident-4.rs:16:1 | LL | lexer_failure!(); //~ ERROR proc macro panicked - | ^^^^^^^^^^^^^^^^^ + | ^^^^^^^^^^^^^^^^^ unexpected close delimiter error: proc macro panicked --> $DIR/invalid-punct-ident-4.rs:16:1 diff --git a/src/test/ui-fulldeps/proc-macro/attribute-spans-preserved.rs b/src/test/ui-fulldeps/proc-macro/attribute-spans-preserved.rs index e1401653ba356..18ca34b117db7 100644 --- a/src/test/ui-fulldeps/proc-macro/attribute-spans-preserved.rs +++ b/src/test/ui-fulldeps/proc-macro/attribute-spans-preserved.rs @@ -17,6 +17,6 @@ extern crate attribute_spans_preserved as foo; use foo::foo; #[ foo ( let y: u32 = "z"; ) ] //~ ERROR: mismatched types -#[ bar let x: u32 = "y"; ] //~ ERROR: mismatched types +#[ bar { let x: u32 = "y"; } ] //~ ERROR: mismatched types fn main() { } diff --git a/src/test/ui-fulldeps/proc-macro/attribute-spans-preserved.stderr b/src/test/ui-fulldeps/proc-macro/attribute-spans-preserved.stderr index fe62bd23b87c9..a6cbf79209e2e 100644 --- a/src/test/ui-fulldeps/proc-macro/attribute-spans-preserved.stderr +++ b/src/test/ui-fulldeps/proc-macro/attribute-spans-preserved.stderr @@ -8,10 +8,10 @@ LL | #[ foo ( let y: u32 = "z"; ) ] //~ ERROR: mismatched types found type `&'static str` error[E0308]: mismatched types - --> $DIR/attribute-spans-preserved.rs:20:21 + --> $DIR/attribute-spans-preserved.rs:20:23 | -LL | #[ bar let x: u32 = "y"; ] //~ ERROR: mismatched types - | ^^^ expected u32, found reference +LL | #[ bar { let x: u32 = "y"; } ] //~ ERROR: mismatched types + | ^^^ expected u32, found reference | = note: expected type `u32` found type `&'static str` diff --git a/src/test/ui-fulldeps/proc-macro/attribute-spans-preserved.stdout b/src/test/ui-fulldeps/proc-macro/attribute-spans-preserved.stdout index 33dc064ef680f..b1487fcd5edbd 100644 --- a/src/test/ui-fulldeps/proc-macro/attribute-spans-preserved.stdout +++ b/src/test/ui-fulldeps/proc-macro/attribute-spans-preserved.stdout @@ -1 +1 @@ -fn main ( ) { let y : u32 = "z" ; let x : u32 = "y" ; } +fn main ( ) { let y : u32 = "z" ; { let x : u32 = "y" ; } } diff --git a/src/test/ui/E0508-fail.ast.nll.stderr b/src/test/ui/E0508-fail.ast.nll.stderr new file mode 100644 index 0000000000000..fda6c24dc8710 --- /dev/null +++ b/src/test/ui/E0508-fail.ast.nll.stderr @@ -0,0 +1,12 @@ +error[E0508]: cannot move out of type `[NonCopy; 1]`, a non-copy array + --> $DIR/E0508-fail.rs:18:18 + | +LL | let _value = array[0]; //[ast]~ ERROR [E0508] + | ^^^^^^^^ + | | + | cannot move out of here + | help: consider borrowing here: `&array[0]` + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0508`. diff --git a/src/test/ui/E0508-fail.mir.stderr b/src/test/ui/E0508-fail.mir.stderr index faf7411af317b..fda6c24dc8710 100644 --- a/src/test/ui/E0508-fail.mir.stderr +++ b/src/test/ui/E0508-fail.mir.stderr @@ -5,7 +5,7 @@ LL | let _value = array[0]; //[ast]~ ERROR [E0508] | ^^^^^^^^ | | | cannot move out of here - | help: consider using a reference instead: `&array[0]` + | help: consider borrowing here: `&array[0]` error: aborting due to previous error diff --git a/src/test/ui/E0508.nll.stderr b/src/test/ui/E0508.nll.stderr new file mode 100644 index 0000000000000..025ff874bced4 --- /dev/null +++ b/src/test/ui/E0508.nll.stderr @@ -0,0 +1,12 @@ +error[E0508]: cannot move out of type `[NonCopy; 1]`, a non-copy array + --> $DIR/E0508.rs:15:18 + | +LL | let _value = array[0]; //~ ERROR [E0508] + | ^^^^^^^^ + | | + | cannot move out of here + | help: consider borrowing here: `&array[0]` + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0508`. diff --git a/src/test/ui/E0660.rs b/src/test/ui/E0660.rs index 82ef38e96cded..2981e4ea8b3a3 100644 --- a/src/test/ui/E0660.rs +++ b/src/test/ui/E0660.rs @@ -8,8 +8,6 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -// ignore-stage1 - #![feature(asm)] fn main() { diff --git a/src/test/ui/E0660.stderr b/src/test/ui/E0660.stderr index fcf3e9a255273..e8acb282be94d 100644 --- a/src/test/ui/E0660.stderr +++ b/src/test/ui/E0660.stderr @@ -1,11 +1,11 @@ error[E0660]: malformed inline assembly - --> $DIR/E0660.rs:17:5 + --> $DIR/E0660.rs:15:5 | LL | asm!("nop" "nop"); | ^^^^^^^^^^^^^^^^^^ error[E0660]: malformed inline assembly - --> $DIR/E0660.rs:19:5 + --> $DIR/E0660.rs:17:5 | LL | asm!("nop" "nop" : "=r"(a)); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ diff --git a/src/test/ui/E0661.rs b/src/test/ui/E0661.rs index 7f8a0d8b57420..2410eba02451f 100644 --- a/src/test/ui/E0661.rs +++ b/src/test/ui/E0661.rs @@ -8,8 +8,6 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -// ignore-stage1 - #![feature(asm)] fn main() { diff --git a/src/test/ui/E0661.stderr b/src/test/ui/E0661.stderr index d8b974d424074..90aeca5612ae4 100644 --- a/src/test/ui/E0661.stderr +++ b/src/test/ui/E0661.stderr @@ -1,5 +1,5 @@ error[E0661]: output operand constraint lacks '=' or '+' - --> $DIR/E0661.rs:17:18 + --> $DIR/E0661.rs:15:18 | LL | asm!("nop" : "r"(a)); | ^^^ diff --git a/src/test/ui/E0662.rs b/src/test/ui/E0662.rs index 6adb11c56169c..700540fd1e0c0 100644 --- a/src/test/ui/E0662.rs +++ b/src/test/ui/E0662.rs @@ -8,8 +8,6 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -// ignore-stage1 - #![feature(asm)] fn main() { diff --git a/src/test/ui/E0662.stderr b/src/test/ui/E0662.stderr index 215e3a6d2f023..31655ca198794 100644 --- a/src/test/ui/E0662.stderr +++ b/src/test/ui/E0662.stderr @@ -1,5 +1,5 @@ error[E0662]: input operand constraint contains '=' - --> $DIR/E0662.rs:18:12 + --> $DIR/E0662.rs:16:12 | LL | : "=test"("a") //~ ERROR E0662 | ^^^^^^^ diff --git a/src/test/ui/E0663.rs b/src/test/ui/E0663.rs index 9eb05ada4a82a..dea2b9156b7e9 100644 --- a/src/test/ui/E0663.rs +++ b/src/test/ui/E0663.rs @@ -8,8 +8,6 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -// ignore-stage1 - #![feature(asm)] fn main() { diff --git a/src/test/ui/E0663.stderr b/src/test/ui/E0663.stderr index 123aa73eccc5e..0a287620f20e1 100644 --- a/src/test/ui/E0663.stderr +++ b/src/test/ui/E0663.stderr @@ -1,5 +1,5 @@ error[E0663]: input operand constraint contains '+' - --> $DIR/E0663.rs:18:12 + --> $DIR/E0663.rs:16:12 | LL | : "+test"("a") //~ ERROR E0663 | ^^^^^^^ diff --git a/src/test/ui/E0664.rs b/src/test/ui/E0664.rs index 738ffc18e3827..9773f604c468b 100644 --- a/src/test/ui/E0664.rs +++ b/src/test/ui/E0664.rs @@ -8,8 +8,6 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -// ignore-stage1 - #![feature(asm)] fn main() { diff --git a/src/test/ui/E0664.stderr b/src/test/ui/E0664.stderr index 570811729be85..1e79c84cbc8c4 100644 --- a/src/test/ui/E0664.stderr +++ b/src/test/ui/E0664.stderr @@ -1,5 +1,5 @@ error[E0664]: clobber should not be surrounded by braces - --> $DIR/E0664.rs:19:12 + --> $DIR/E0664.rs:17:12 | LL | : "{eax}" //~ ERROR E0664 | ^^^^^^^ diff --git a/src/test/ui/E0665.rs b/src/test/ui/E0665.rs index 8888bedf01687..0a0bd3f59052c 100644 --- a/src/test/ui/E0665.rs +++ b/src/test/ui/E0665.rs @@ -8,8 +8,6 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -// ignore-stage1 - #[derive(Default)] //~ ERROR E0665 enum Food { Sweet, diff --git a/src/test/ui/E0665.stderr b/src/test/ui/E0665.stderr index c97e9e5ea89d0..268224cac3826 100644 --- a/src/test/ui/E0665.stderr +++ b/src/test/ui/E0665.stderr @@ -1,5 +1,5 @@ error[E0665]: `Default` cannot be derived for enums, only structs - --> $DIR/E0665.rs:13:10 + --> $DIR/E0665.rs:11:10 | LL | #[derive(Default)] //~ ERROR E0665 | ^^^^^^^ diff --git a/src/test/ui/access-mode-in-closures.nll.stderr b/src/test/ui/access-mode-in-closures.nll.stderr index 2aa8f1c381309..b9de60f43f703 100644 --- a/src/test/ui/access-mode-in-closures.nll.stderr +++ b/src/test/ui/access-mode-in-closures.nll.stderr @@ -2,10 +2,16 @@ error[E0507]: cannot move out of borrowed content --> $DIR/access-mode-in-closures.rs:19:15 | LL | match *s { sty(v) => v } //~ ERROR cannot move out - | ^^ - move occurs because v has type `std::vec::Vec`, which does not implement the `Copy` trait + | ^^ - data moved here | | | cannot move out of borrowed content - | help: consider removing this dereference operator: `s` + | help: consider removing the `*`: `s` + | +note: move occurs because `v` has type `std::vec::Vec`, which does not implement the `Copy` trait + --> $DIR/access-mode-in-closures.rs:19:24 + | +LL | match *s { sty(v) => v } //~ ERROR cannot move out + | ^ error: aborting due to previous error diff --git a/src/test/ui/attr-eq-token-tree.rs b/src/test/ui/attr-eq-token-tree.rs new file mode 100644 index 0000000000000..c759e62dba0b5 --- /dev/null +++ b/src/test/ui/attr-eq-token-tree.rs @@ -0,0 +1,16 @@ +// Copyright 2018 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 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +// compile-pass + +#![feature(custom_attribute, unrestricted_attribute_tokens)] + +#[my_attr = !] // OK under feature gate +fn main() {} diff --git a/src/test/ui/borrowck/borrowck-for-loop-correct-cmt-for-pattern.nll.stderr b/src/test/ui/borrowck/borrowck-for-loop-correct-cmt-for-pattern.nll.stderr index f9e517def1406..25eb69ad9377d 100644 --- a/src/test/ui/borrowck/borrowck-for-loop-correct-cmt-for-pattern.nll.stderr +++ b/src/test/ui/borrowck/borrowck-for-loop-correct-cmt-for-pattern.nll.stderr @@ -2,28 +2,46 @@ error[E0507]: cannot move out of borrowed content --> $DIR/borrowck-for-loop-correct-cmt-for-pattern.rs:22:15 | LL | for &a in x.iter() { //~ ERROR cannot move out - | - ^^^^^^^^ cannot move out of borrowed content - | | - | data moved here - | help: to prevent move, use ref or ref mut: `ref a` + | -- ^^^^^^^^ cannot move out of borrowed content + | || + | |data moved here + | help: consider removing the `&`: `a` + | +note: move occurs because `a` has type `&mut i32`, which does not implement the `Copy` trait + --> $DIR/borrowck-for-loop-correct-cmt-for-pattern.rs:22:10 + | +LL | for &a in x.iter() { //~ ERROR cannot move out + | ^ error[E0507]: cannot move out of borrowed content --> $DIR/borrowck-for-loop-correct-cmt-for-pattern.rs:28:15 | LL | for &a in &f.a { //~ ERROR cannot move out - | - ^^^^ cannot move out of borrowed content - | | - | data moved here - | help: to prevent move, use ref or ref mut: `ref a` + | -- ^^^^ cannot move out of borrowed content + | || + | |data moved here + | help: consider removing the `&`: `a` + | +note: move occurs because `a` has type `std::boxed::Box`, which does not implement the `Copy` trait + --> $DIR/borrowck-for-loop-correct-cmt-for-pattern.rs:28:10 + | +LL | for &a in &f.a { //~ ERROR cannot move out + | ^ error[E0507]: cannot move out of borrowed content --> $DIR/borrowck-for-loop-correct-cmt-for-pattern.rs:32:15 | LL | for &a in x.iter() { //~ ERROR cannot move out - | - ^^^^^^^^ cannot move out of borrowed content - | | - | data moved here - | help: to prevent move, use ref or ref mut: `ref a` + | -- ^^^^^^^^ cannot move out of borrowed content + | || + | |data moved here + | help: consider removing the `&`: `a` + | +note: move occurs because `a` has type `std::boxed::Box`, which does not implement the `Copy` trait + --> $DIR/borrowck-for-loop-correct-cmt-for-pattern.rs:32:10 + | +LL | for &a in x.iter() { //~ ERROR cannot move out + | ^ error: aborting due to 3 previous errors diff --git a/src/test/ui/borrowck/borrowck-issue-2657-2.nll.stderr b/src/test/ui/borrowck/borrowck-issue-2657-2.nll.stderr index 55c6a40d281bc..cdbfab8bd054a 100644 --- a/src/test/ui/borrowck/borrowck-issue-2657-2.nll.stderr +++ b/src/test/ui/borrowck/borrowck-issue-2657-2.nll.stderr @@ -5,7 +5,7 @@ LL | let _b = *y; //~ ERROR cannot move out | ^^ | | | cannot move out of borrowed content - | help: consider removing this dereference operator: `y` + | help: consider removing the `*`: `y` error: aborting due to previous error diff --git a/src/test/ui/borrowck/borrowck-move-error-with-note.nll.stderr b/src/test/ui/borrowck/borrowck-move-error-with-note.nll.stderr index 1b913471924b7..2df520a936c9d 100644 --- a/src/test/ui/borrowck/borrowck-move-error-with-note.nll.stderr +++ b/src/test/ui/borrowck/borrowck-move-error-with-note.nll.stderr @@ -5,14 +5,24 @@ LL | match *f { //~ ERROR cannot move out of | ^^ | | | cannot move out of borrowed content - | help: consider removing this dereference operator: `f` + | help: consider removing the `*`: `f` LL | //~| cannot move out LL | Foo::Foo1(num1, - | ---- move occurs because num1 has type `std::boxed::Box`, which does not implement the `Copy` trait + | ---- data moved here LL | num2) => (), - | ---- move occurs because num2 has type `std::boxed::Box`, which does not implement the `Copy` trait + | ---- ...and here LL | Foo::Foo2(num) => (), - | --- move occurs because num has type `std::boxed::Box`, which does not implement the `Copy` trait + | --- ...and here + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/borrowck-move-error-with-note.rs:23:19 + | +LL | Foo::Foo1(num1, + | ^^^^ +LL | num2) => (), + | ^^^^ +LL | Foo::Foo2(num) => (), + | ^^^ error[E0509]: cannot move out of type `S`, which implements the `Drop` trait --> $DIR/borrowck-move-error-with-note.rs:39:11 @@ -23,12 +33,15 @@ LL | match (S {f: "foo".to_string(), g: "bar".to_string()}) { LL | f: _s, | -- data moved here LL | g: _t - | -- ... and here -help: to prevent move, use ref or ref mut + | -- ...and here | -LL | f: ref _s, -LL | g: ref _t +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/borrowck-move-error-with-note.rs:42:16 | +LL | f: _s, + | ^^ +LL | g: _t + | ^^ error[E0507]: cannot move out of borrowed content --> $DIR/borrowck-move-error-with-note.rs:57:11 @@ -37,10 +50,16 @@ LL | match a.a { //~ ERROR cannot move out of | ^^^ | | | cannot move out of borrowed content - | help: consider using a reference instead: `&a.a` + | help: consider borrowing here: `&a.a` LL | //~| cannot move out LL | n => { - | - move occurs because n has type `std::boxed::Box`, which does not implement the `Copy` trait + | - data moved here + | +note: move occurs because `n` has type `std::boxed::Box`, which does not implement the `Copy` trait + --> $DIR/borrowck-move-error-with-note.rs:59:9 + | +LL | n => { + | ^ error: aborting due to 3 previous errors diff --git a/src/test/ui/borrowck/borrowck-move-from-unsafe-ptr.nll.stderr b/src/test/ui/borrowck/borrowck-move-from-unsafe-ptr.nll.stderr index 4f692bfc55e42..f823a6f08d789 100644 --- a/src/test/ui/borrowck/borrowck-move-from-unsafe-ptr.nll.stderr +++ b/src/test/ui/borrowck/borrowck-move-from-unsafe-ptr.nll.stderr @@ -5,7 +5,7 @@ LL | let y = *x; //~ ERROR cannot move out of dereference of raw pointer | ^^ | | | cannot move out of borrowed content - | help: consider using a reference instead: `&*x` + | help: consider removing the `*`: `x` error: aborting due to previous error diff --git a/src/test/ui/borrowck/borrowck-move-in-irrefut-pat.ast.nll.stderr b/src/test/ui/borrowck/borrowck-move-in-irrefut-pat.ast.nll.stderr index f670936dbac17..49c2ec0dcf4e7 100644 --- a/src/test/ui/borrowck/borrowck-move-in-irrefut-pat.ast.nll.stderr +++ b/src/test/ui/borrowck/borrowck-move-in-irrefut-pat.ast.nll.stderr @@ -5,8 +5,14 @@ LL | fn arg_item(&_x: &String) {} | ^-- | || | |data moved here - | |help: to prevent move, use ref or ref mut: `ref _x` | cannot move out of borrowed content + | help: consider removing the `&`: `_x` + | +note: move occurs because `_x` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/borrowck-move-in-irrefut-pat.rs:16:14 + | +LL | fn arg_item(&_x: &String) {} + | ^^ error[E0507]: cannot move out of borrowed content --> $DIR/borrowck-move-in-irrefut-pat.rs:21:11 @@ -15,17 +21,29 @@ LL | with(|&_x| ()) | ^-- | || | |data moved here - | |help: to prevent move, use ref or ref mut: `ref _x` | cannot move out of borrowed content + | help: consider removing the `&`: `_x` + | +note: move occurs because `_x` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/borrowck-move-in-irrefut-pat.rs:21:12 + | +LL | with(|&_x| ()) + | ^^ error[E0507]: cannot move out of borrowed content --> $DIR/borrowck-move-in-irrefut-pat.rs:27:15 | LL | let &_x = &"hi".to_string(); - | -- ^^^^^^^^^^^^^^^^^ cannot move out of borrowed content - | | - | data moved here - | help: to prevent move, use ref or ref mut: `ref _x` + | --- ^^^^^^^^^^^^^^^^^ cannot move out of borrowed content + | || + | |data moved here + | help: consider removing the `&`: `_x` + | +note: move occurs because `_x` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/borrowck-move-in-irrefut-pat.rs:27:10 + | +LL | let &_x = &"hi".to_string(); + | ^^ error: aborting due to 3 previous errors diff --git a/src/test/ui/borrowck/borrowck-move-in-irrefut-pat.mir.stderr b/src/test/ui/borrowck/borrowck-move-in-irrefut-pat.mir.stderr index f670936dbac17..49c2ec0dcf4e7 100644 --- a/src/test/ui/borrowck/borrowck-move-in-irrefut-pat.mir.stderr +++ b/src/test/ui/borrowck/borrowck-move-in-irrefut-pat.mir.stderr @@ -5,8 +5,14 @@ LL | fn arg_item(&_x: &String) {} | ^-- | || | |data moved here - | |help: to prevent move, use ref or ref mut: `ref _x` | cannot move out of borrowed content + | help: consider removing the `&`: `_x` + | +note: move occurs because `_x` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/borrowck-move-in-irrefut-pat.rs:16:14 + | +LL | fn arg_item(&_x: &String) {} + | ^^ error[E0507]: cannot move out of borrowed content --> $DIR/borrowck-move-in-irrefut-pat.rs:21:11 @@ -15,17 +21,29 @@ LL | with(|&_x| ()) | ^-- | || | |data moved here - | |help: to prevent move, use ref or ref mut: `ref _x` | cannot move out of borrowed content + | help: consider removing the `&`: `_x` + | +note: move occurs because `_x` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/borrowck-move-in-irrefut-pat.rs:21:12 + | +LL | with(|&_x| ()) + | ^^ error[E0507]: cannot move out of borrowed content --> $DIR/borrowck-move-in-irrefut-pat.rs:27:15 | LL | let &_x = &"hi".to_string(); - | -- ^^^^^^^^^^^^^^^^^ cannot move out of borrowed content - | | - | data moved here - | help: to prevent move, use ref or ref mut: `ref _x` + | --- ^^^^^^^^^^^^^^^^^ cannot move out of borrowed content + | || + | |data moved here + | help: consider removing the `&`: `_x` + | +note: move occurs because `_x` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/borrowck-move-in-irrefut-pat.rs:27:10 + | +LL | let &_x = &"hi".to_string(); + | ^^ error: aborting due to 3 previous errors diff --git a/src/test/ui/borrowck/borrowck-move-out-of-overloaded-deref.nll.stderr b/src/test/ui/borrowck/borrowck-move-out-of-overloaded-deref.nll.stderr new file mode 100644 index 0000000000000..b9c47e6e8cfe9 --- /dev/null +++ b/src/test/ui/borrowck/borrowck-move-out-of-overloaded-deref.nll.stderr @@ -0,0 +1,12 @@ +error[E0507]: cannot move out of borrowed content + --> $DIR/borrowck-move-out-of-overloaded-deref.rs:14:14 + | +LL | let _x = *Rc::new("hi".to_string()); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^ + | | + | cannot move out of borrowed content + | help: consider removing the `*`: `Rc::new("hi".to_string())` + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0507`. diff --git a/src/test/ui/borrowck/borrowck-move-out-of-struct-with-dtor.ast.nll.stderr b/src/test/ui/borrowck/borrowck-move-out-of-struct-with-dtor.ast.nll.stderr index 15c7011d71671..34f9f035188b8 100644 --- a/src/test/ui/borrowck/borrowck-move-out-of-struct-with-dtor.ast.nll.stderr +++ b/src/test/ui/borrowck/borrowck-move-out-of-struct-with-dtor.ast.nll.stderr @@ -5,10 +5,13 @@ LL | match (S {f:"foo".to_string()}) { | ^^^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of here LL | //[mir]~^ ERROR [E0509] LL | S {f:_s} => {} - | -- - | | - | data moved here - | help: to prevent move, use ref or ref mut: `ref _s` + | -- data moved here + | +note: move occurs because `_s` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/borrowck-move-out-of-struct-with-dtor.rs:22:14 + | +LL | S {f:_s} => {} + | ^^ error[E0509]: cannot move out of type `S`, which implements the `Drop` trait --> $DIR/borrowck-move-out-of-struct-with-dtor.rs:28:20 @@ -17,7 +20,12 @@ LL | let S {f:_s} = S {f:"foo".to_string()}; | -- ^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of here | | | data moved here - | help: to prevent move, use ref or ref mut: `ref _s` + | +note: move occurs because `_s` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/borrowck-move-out-of-struct-with-dtor.rs:28:14 + | +LL | let S {f:_s} = S {f:"foo".to_string()}; + | ^^ error[E0509]: cannot move out of type `S`, which implements the `Drop` trait --> $DIR/borrowck-move-out-of-struct-with-dtor.rs:33:19 @@ -26,8 +34,13 @@ LL | fn move_in_fn_arg(S {f:_s}: S) { | ^^^^^--^ | | | | | data moved here - | | help: to prevent move, use ref or ref mut: `ref _s` | cannot move out of here + | +note: move occurs because `_s` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/borrowck-move-out-of-struct-with-dtor.rs:33:24 + | +LL | fn move_in_fn_arg(S {f:_s}: S) { + | ^^ error: aborting due to 3 previous errors diff --git a/src/test/ui/borrowck/borrowck-move-out-of-struct-with-dtor.mir.stderr b/src/test/ui/borrowck/borrowck-move-out-of-struct-with-dtor.mir.stderr index 15c7011d71671..34f9f035188b8 100644 --- a/src/test/ui/borrowck/borrowck-move-out-of-struct-with-dtor.mir.stderr +++ b/src/test/ui/borrowck/borrowck-move-out-of-struct-with-dtor.mir.stderr @@ -5,10 +5,13 @@ LL | match (S {f:"foo".to_string()}) { | ^^^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of here LL | //[mir]~^ ERROR [E0509] LL | S {f:_s} => {} - | -- - | | - | data moved here - | help: to prevent move, use ref or ref mut: `ref _s` + | -- data moved here + | +note: move occurs because `_s` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/borrowck-move-out-of-struct-with-dtor.rs:22:14 + | +LL | S {f:_s} => {} + | ^^ error[E0509]: cannot move out of type `S`, which implements the `Drop` trait --> $DIR/borrowck-move-out-of-struct-with-dtor.rs:28:20 @@ -17,7 +20,12 @@ LL | let S {f:_s} = S {f:"foo".to_string()}; | -- ^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of here | | | data moved here - | help: to prevent move, use ref or ref mut: `ref _s` + | +note: move occurs because `_s` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/borrowck-move-out-of-struct-with-dtor.rs:28:14 + | +LL | let S {f:_s} = S {f:"foo".to_string()}; + | ^^ error[E0509]: cannot move out of type `S`, which implements the `Drop` trait --> $DIR/borrowck-move-out-of-struct-with-dtor.rs:33:19 @@ -26,8 +34,13 @@ LL | fn move_in_fn_arg(S {f:_s}: S) { | ^^^^^--^ | | | | | data moved here - | | help: to prevent move, use ref or ref mut: `ref _s` | cannot move out of here + | +note: move occurs because `_s` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/borrowck-move-out-of-struct-with-dtor.rs:33:24 + | +LL | fn move_in_fn_arg(S {f:_s}: S) { + | ^^ error: aborting due to 3 previous errors diff --git a/src/test/ui/borrowck/borrowck-move-out-of-tuple-struct-with-dtor.nll.stderr b/src/test/ui/borrowck/borrowck-move-out-of-tuple-struct-with-dtor.nll.stderr index c69ae8755a957..278c33c71e245 100644 --- a/src/test/ui/borrowck/borrowck-move-out-of-tuple-struct-with-dtor.nll.stderr +++ b/src/test/ui/borrowck/borrowck-move-out-of-tuple-struct-with-dtor.nll.stderr @@ -4,10 +4,13 @@ error[E0509]: cannot move out of type `S`, which implements the `Drop` trait LL | match S("foo".to_string()) { | ^^^^^^^^^^^^^^^^^^^^ cannot move out of here LL | S(_s) => {} - | -- - | | - | data moved here - | help: to prevent move, use ref or ref mut: `ref _s` + | -- data moved here + | +note: move occurs because `_s` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/borrowck-move-out-of-tuple-struct-with-dtor.rs:18:11 + | +LL | S(_s) => {} + | ^^ error[E0509]: cannot move out of type `S`, which implements the `Drop` trait --> $DIR/borrowck-move-out-of-tuple-struct-with-dtor.rs:24:17 @@ -16,7 +19,12 @@ LL | let S(_s) = S("foo".to_string()); | -- ^^^^^^^^^^^^^^^^^^^^ cannot move out of here | | | data moved here - | help: to prevent move, use ref or ref mut: `ref _s` + | +note: move occurs because `_s` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/borrowck-move-out-of-tuple-struct-with-dtor.rs:24:11 + | +LL | let S(_s) = S("foo".to_string()); + | ^^ error[E0509]: cannot move out of type `S`, which implements the `Drop` trait --> $DIR/borrowck-move-out-of-tuple-struct-with-dtor.rs:28:19 @@ -25,8 +33,13 @@ LL | fn move_in_fn_arg(S(_s): S) { | ^^--^ | | | | | data moved here - | | help: to prevent move, use ref or ref mut: `ref _s` | cannot move out of here + | +note: move occurs because `_s` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/borrowck-move-out-of-tuple-struct-with-dtor.rs:28:21 + | +LL | fn move_in_fn_arg(S(_s): S) { + | ^^ error: aborting due to 3 previous errors diff --git a/src/test/ui/borrowck/borrowck-move-out-of-vec-tail.nll.stderr b/src/test/ui/borrowck/borrowck-move-out-of-vec-tail.nll.stderr index 95a7894d53254..f3430ba4e06c9 100644 --- a/src/test/ui/borrowck/borrowck-move-out-of-vec-tail.nll.stderr +++ b/src/test/ui/borrowck/borrowck-move-out-of-vec-tail.nll.stderr @@ -7,14 +7,23 @@ LL | &[Foo { string: a }, | - data moved here ... LL | Foo { string: b }] => { - | - ... and here -help: to prevent move, use ref or ref mut + | - ...and here | -LL | &[Foo { string: ref a }, +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/borrowck-move-out-of-vec-tail.rs:30:33 + | +LL | &[Foo { string: a }, + | ^ +... +LL | Foo { string: b }] => { + | ^ +help: consider removing the `&` + | +LL | [Foo { string: a }, LL | //~^ ERROR cannot move out of type `[Foo]` LL | //~| cannot move out LL | //~| to prevent move -LL | Foo { string: ref b }] => { +LL | Foo { string: b }] => { | error: aborting due to previous error diff --git a/src/test/ui/borrowck/borrowck-overloaded-index-move-from-vec.nll.stderr b/src/test/ui/borrowck/borrowck-overloaded-index-move-from-vec.nll.stderr index 4a72d7f330266..92e10c258c269 100644 --- a/src/test/ui/borrowck/borrowck-overloaded-index-move-from-vec.nll.stderr +++ b/src/test/ui/borrowck/borrowck-overloaded-index-move-from-vec.nll.stderr @@ -5,7 +5,7 @@ LL | let bad = v[0]; | ^^^^ | | | cannot move out of borrowed content - | help: consider using a reference instead: `&v[0]` + | help: consider borrowing here: `&v[0]` error: aborting due to previous error diff --git a/src/test/ui/borrowck/borrowck-vec-pattern-nesting.nll.stderr b/src/test/ui/borrowck/borrowck-vec-pattern-nesting.nll.stderr index 2779132590e2c..d5b17119d85f5 100644 --- a/src/test/ui/borrowck/borrowck-vec-pattern-nesting.nll.stderr +++ b/src/test/ui/borrowck/borrowck-vec-pattern-nesting.nll.stderr @@ -28,10 +28,21 @@ error[E0508]: cannot move out of type `[std::boxed::Box]`, a non-copy sli LL | match vec { | ^^^ cannot move out of here LL | &mut [_a, //~ ERROR cannot move out - | -- - | | - | data moved here - | help: to prevent move, use ref or ref mut: `ref _a` + | -- data moved here + | +note: move occurs because `_a` has type `std::boxed::Box`, which does not implement the `Copy` trait + --> $DIR/borrowck-vec-pattern-nesting.rs:44:15 + | +LL | &mut [_a, //~ ERROR cannot move out + | ^^ +help: consider removing the `&mut` + | +LL | [_a, //~ ERROR cannot move out +LL | //~| cannot move out +LL | //~| to prevent move +LL | .. +LL | ] => { + | error[E0508]: cannot move out of type `[std::boxed::Box]`, a non-copy slice --> $DIR/borrowck-vec-pattern-nesting.rs:57:13 @@ -40,7 +51,7 @@ LL | let a = vec[0]; //~ ERROR cannot move out | ^^^^^^ | | | cannot move out of here - | help: consider using a reference instead: `&vec[0]` + | help: consider borrowing here: `&vec[0]` error[E0508]: cannot move out of type `[std::boxed::Box]`, a non-copy slice --> $DIR/borrowck-vec-pattern-nesting.rs:64:11 @@ -49,10 +60,19 @@ LL | match vec { | ^^^ cannot move out of here ... LL | _b] => {} - | -- - | | - | data moved here - | help: to prevent move, use ref or ref mut: `ref _b` + | -- data moved here + | +note: move occurs because `_b` has type `std::boxed::Box`, which does not implement the `Copy` trait + --> $DIR/borrowck-vec-pattern-nesting.rs:67:10 + | +LL | _b] => {} + | ^^ +help: consider removing the `&mut` + | +LL | [ //~ ERROR cannot move out +LL | //~^ cannot move out +LL | _b] => {} + | error[E0508]: cannot move out of type `[std::boxed::Box]`, a non-copy slice --> $DIR/borrowck-vec-pattern-nesting.rs:70:13 @@ -61,7 +81,7 @@ LL | let a = vec[0]; //~ ERROR cannot move out | ^^^^^^ | | | cannot move out of here - | help: consider using a reference instead: `&vec[0]` + | help: consider borrowing here: `&vec[0]` error[E0508]: cannot move out of type `[std::boxed::Box]`, a non-copy slice --> $DIR/borrowck-vec-pattern-nesting.rs:77:11 @@ -69,14 +89,18 @@ error[E0508]: cannot move out of type `[std::boxed::Box]`, a non-copy sli LL | match vec { | ^^^ cannot move out of here LL | &mut [_a, _b, _c] => {} //~ ERROR cannot move out - | -- -- -- ... and here - | | | - | | ... and here - | data moved here -help: to prevent move, use ref or ref mut - | -LL | &mut [ref _a, ref _b, ref _c] => {} //~ ERROR cannot move out - | ^^^^^^ ^^^^^^ ^^^^^^ + | ----------------- + | | | | | + | | | | ...and here + | | | ...and here + | | data moved here + | help: consider removing the `&mut`: `[_a, _b, _c]` + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/borrowck-vec-pattern-nesting.rs:78:15 + | +LL | &mut [_a, _b, _c] => {} //~ ERROR cannot move out + | ^^ ^^ ^^ error[E0508]: cannot move out of type `[std::boxed::Box]`, a non-copy slice --> $DIR/borrowck-vec-pattern-nesting.rs:82:13 @@ -85,7 +109,7 @@ LL | let a = vec[0]; //~ ERROR cannot move out | ^^^^^^ | | | cannot move out of here - | help: consider using a reference instead: `&vec[0]` + | help: consider borrowing here: `&vec[0]` error: aborting due to 8 previous errors diff --git a/src/test/ui/borrowck/issue-51415.nll.stderr b/src/test/ui/borrowck/issue-51415.nll.stderr index 20713c3392e8e..d4340938eebc1 100644 --- a/src/test/ui/borrowck/issue-51415.nll.stderr +++ b/src/test/ui/borrowck/issue-51415.nll.stderr @@ -5,8 +5,13 @@ LL | let opt = a.iter().enumerate().find(|(_, &s)| { | ^^^^^-^ | | | | | data moved here - | | help: to prevent move, use ref or ref mut: `ref s` | cannot move out of borrowed content + | +note: move occurs because `s` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/issue-51415.rs:16:47 + | +LL | let opt = a.iter().enumerate().find(|(_, &s)| { + | ^ error: aborting due to previous error diff --git a/src/test/ui/by-move-pattern-binding.nll.stderr b/src/test/ui/by-move-pattern-binding.nll.stderr index 4ba9b3aeb5d5d..491b5b5bd74ab 100644 --- a/src/test/ui/by-move-pattern-binding.nll.stderr +++ b/src/test/ui/by-move-pattern-binding.nll.stderr @@ -5,10 +5,16 @@ LL | match &s.x { | ^^^^ cannot move out of borrowed content LL | &E::Foo => {} LL | &E::Bar(identifier) => f(identifier.clone()) //~ ERROR cannot move - | ---------- - | | - | data moved here - | help: to prevent move, use ref or ref mut: `ref identifier` + | ------------------- + | | | + | | data moved here + | help: consider removing the `&`: `E::Bar(identifier)` + | +note: move occurs because `identifier` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/by-move-pattern-binding.rs:26:17 + | +LL | &E::Bar(identifier) => f(identifier.clone()) //~ ERROR cannot move + | ^^^^^^^^^^ error: aborting due to previous error diff --git a/src/test/ui/check-static-values-constraints.nll.stderr b/src/test/ui/check-static-values-constraints.nll.stderr index b265ec8bddac6..5522e22fb1fa2 100644 --- a/src/test/ui/check-static-values-constraints.nll.stderr +++ b/src/test/ui/check-static-values-constraints.nll.stderr @@ -56,7 +56,7 @@ LL | let y = { static x: Box = box 3; x }; | ^ | | | cannot move out of static item - | help: consider using a reference instead: `&x` + | help: consider borrowing here: `&x` error[E0010]: allocations are not allowed in statics --> $DIR/check-static-values-constraints.rs:120:38 diff --git a/src/test/ui/codemap_tests/overlapping_spans.nll.stderr b/src/test/ui/codemap_tests/overlapping_spans.nll.stderr index a1fbcf1430db9..e334472f9d6e1 100644 --- a/src/test/ui/codemap_tests/overlapping_spans.nll.stderr +++ b/src/test/ui/codemap_tests/overlapping_spans.nll.stderr @@ -4,10 +4,13 @@ error[E0509]: cannot move out of type `S`, which implements the `Drop` trait LL | match (S {f:"foo".to_string()}) { | ^^^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of here LL | S {f:_s} => {} //~ ERROR cannot move out - | -- - | | - | data moved here - | help: to prevent move, use ref or ref mut: `ref _s` + | -- data moved here + | +note: move occurs because `_s` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/overlapping_spans.rs:21:14 + | +LL | S {f:_s} => {} //~ ERROR cannot move out + | ^^ error: aborting due to previous error diff --git a/src/test/ui/disallowed-deconstructing/disallowed-deconstructing-destructing-struct-let.nll.stderr b/src/test/ui/disallowed-deconstructing/disallowed-deconstructing-destructing-struct-let.nll.stderr index a8be048d7df6c..8e0599370287f 100644 --- a/src/test/ui/disallowed-deconstructing/disallowed-deconstructing-destructing-struct-let.nll.stderr +++ b/src/test/ui/disallowed-deconstructing/disallowed-deconstructing-destructing-struct-let.nll.stderr @@ -5,7 +5,12 @@ LL | let X { x: y } = x; //~ ERROR cannot move out of type | - ^ cannot move out of here | | | data moved here - | help: to prevent move, use ref or ref mut: `ref y` + | +note: move occurs because `y` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/disallowed-deconstructing-destructing-struct-let.rs:22:16 + | +LL | let X { x: y } = x; //~ ERROR cannot move out of type + | ^ error: aborting due to previous error diff --git a/src/test/ui/disallowed-deconstructing/disallowed-deconstructing-destructing-struct-match.nll.stderr b/src/test/ui/disallowed-deconstructing/disallowed-deconstructing-destructing-struct-match.nll.stderr index 9f0d2d5f0e189..dd1a3ef2a2b98 100644 --- a/src/test/ui/disallowed-deconstructing/disallowed-deconstructing-destructing-struct-match.nll.stderr +++ b/src/test/ui/disallowed-deconstructing/disallowed-deconstructing-destructing-struct-match.nll.stderr @@ -4,10 +4,13 @@ error[E0509]: cannot move out of type `X`, which implements the `Drop` trait LL | match x { | ^ cannot move out of here LL | X { x: y } => println!("contents: {}", y) - | - - | | - | data moved here - | help: to prevent move, use ref or ref mut: `ref y` + | - data moved here + | +note: move occurs because `y` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/disallowed-deconstructing-destructing-struct-match.rs:25:16 + | +LL | X { x: y } => println!("contents: {}", y) + | ^ error: aborting due to previous error diff --git a/src/test/ui/error-codes/E0232.stderr b/src/test/ui/error-codes/E0232.stderr index cb6cc44a73597..613b359c299b8 100644 --- a/src/test/ui/error-codes/E0232.stderr +++ b/src/test/ui/error-codes/E0232.stderr @@ -4,7 +4,7 @@ error[E0232]: `#[rustc_on_unimplemented]` requires a value LL | #[rustc_on_unimplemented] | ^^^^^^^^^^^^^^^^^^^^^^^^^ value required here | - = note: eg `#[rustc_on_unimplemented = "foo"]` + = note: eg `#[rustc_on_unimplemented(message="foo")]` error: aborting due to previous error diff --git a/src/test/ui/error-codes/E0509.nll.stderr b/src/test/ui/error-codes/E0509.nll.stderr new file mode 100644 index 0000000000000..723b083b90442 --- /dev/null +++ b/src/test/ui/error-codes/E0509.nll.stderr @@ -0,0 +1,12 @@ +error[E0509]: cannot move out of type `DropStruct`, which implements the `Drop` trait + --> $DIR/E0509.rs:26:23 + | +LL | let fancy_field = drop_struct.fancy; //~ ERROR E0509 + | ^^^^^^^^^^^^^^^^^ + | | + | cannot move out of here + | help: consider borrowing here: `&drop_struct.fancy` + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0509`. diff --git a/src/test/parse-fail/issue-10636-1.rs b/src/test/ui/issue-10636-1.rs similarity index 86% rename from src/test/parse-fail/issue-10636-1.rs rename to src/test/ui/issue-10636-1.rs index 398fe8c5b8cf3..fdd50773593a8 100644 --- a/src/test/parse-fail/issue-10636-1.rs +++ b/src/test/ui/issue-10636-1.rs @@ -12,4 +12,8 @@ struct Obj { //~ NOTE: unclosed delimiter member: usize -) //~ ERROR: incorrect close delimiter +) +//~^ ERROR incorrect close delimiter +//~| NOTE incorrect close delimiter + +fn main() {} diff --git a/src/test/ui/issue-10636-1.stderr b/src/test/ui/issue-10636-1.stderr new file mode 100644 index 0000000000000..af80e259fbd25 --- /dev/null +++ b/src/test/ui/issue-10636-1.stderr @@ -0,0 +1,11 @@ +error: incorrect close delimiter: `)` + --> $DIR/issue-10636-1.rs:15:1 + | +LL | struct Obj { //~ NOTE: unclosed delimiter + | - unclosed delimiter +LL | member: usize +LL | ) + | ^ incorrect close delimiter + +error: aborting due to previous error + diff --git a/src/test/ui/issue-51602.rs b/src/test/ui/issue-51602.rs new file mode 100644 index 0000000000000..a3edecb94f7c5 --- /dev/null +++ b/src/test/ui/issue-51602.rs @@ -0,0 +1,15 @@ +// Copyright 2018 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 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +fn main(){ + if i in 1..10 { + break; + } +} diff --git a/src/test/ui/issue-51602.stderr b/src/test/ui/issue-51602.stderr new file mode 100644 index 0000000000000..ac079b452c5eb --- /dev/null +++ b/src/test/ui/issue-51602.stderr @@ -0,0 +1,10 @@ +error: expected `{`, found `in` + --> $DIR/issue-51602.rs:12:10 + | +LL | if i in 1..10 { + | -- ^^ expected `{` + | | + | this `if` statement has a condition, but no block + +error: aborting due to previous error + diff --git a/src/test/ui/issues/issue-12567.nll.stderr b/src/test/ui/issues/issue-12567.nll.stderr index 29bda252b9115..72d21d47d86fa 100644 --- a/src/test/ui/issues/issue-12567.nll.stderr +++ b/src/test/ui/issues/issue-12567.nll.stderr @@ -8,15 +8,16 @@ LL | (&[], &[hd, ..]) | (&[hd, ..], &[]) | -- data moved here ... LL | (&[hd1, ..], &[hd2, ..]) - | --- ... and here -help: to prevent move, use ref or ref mut + | --- ...and here | -LL | (&[], &[ref hd, ..]) | (&[hd, ..], &[]) -LL | => println!("one empty"), -LL | //~^^ ERROR: cannot move out of type `[T]`, a non-copy slice -LL | //~^^^ ERROR: cannot move out of type `[T]`, a non-copy slice -LL | (&[hd1, ..], &[ref hd2, ..]) +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/issue-12567.rs:16:17 | +LL | (&[], &[hd, ..]) | (&[hd, ..], &[]) + | ^^ +... +LL | (&[hd1, ..], &[hd2, ..]) + | ^^^ error[E0508]: cannot move out of type `[T]`, a non-copy slice --> $DIR/issue-12567.rs:14:11 @@ -28,15 +29,16 @@ LL | (&[], &[hd, ..]) | (&[hd, ..], &[]) | -- data moved here ... LL | (&[hd1, ..], &[hd2, ..]) - | --- ... and here -help: to prevent move, use ref or ref mut + | --- ...and here | -LL | (&[], &[ref hd, ..]) | (&[hd, ..], &[]) -LL | => println!("one empty"), -LL | //~^^ ERROR: cannot move out of type `[T]`, a non-copy slice -LL | //~^^^ ERROR: cannot move out of type `[T]`, a non-copy slice -LL | (&[ref hd1, ..], &[hd2, ..]) +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/issue-12567.rs:16:17 | +LL | (&[], &[hd, ..]) | (&[hd, ..], &[]) + | ^^ +... +LL | (&[hd1, ..], &[hd2, ..]) + | ^^^ error: aborting due to 2 previous errors diff --git a/src/test/ui/issues/issue-17718-static-move.nll.stderr b/src/test/ui/issues/issue-17718-static-move.nll.stderr new file mode 100644 index 0000000000000..f8da3c3d5989e --- /dev/null +++ b/src/test/ui/issues/issue-17718-static-move.nll.stderr @@ -0,0 +1,12 @@ +error[E0507]: cannot move out of static item + --> $DIR/issue-17718-static-move.rs:16:14 + | +LL | let _a = FOO; //~ ERROR: cannot move out of static item + | ^^^ + | | + | cannot move out of static item + | help: consider borrowing here: `&FOO` + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0507`. diff --git a/src/test/ui/issues/issue-20801.nll.stderr b/src/test/ui/issues/issue-20801.nll.stderr index fc94cc423c531..3a6784eed67dd 100644 --- a/src/test/ui/issues/issue-20801.nll.stderr +++ b/src/test/ui/issues/issue-20801.nll.stderr @@ -5,7 +5,7 @@ LL | let a = unsafe { *mut_ref() }; | ^^^^^^^^^^ | | | cannot move out of borrowed content - | help: consider using a reference instead: `&*mut_ref()` + | help: consider removing the `*`: `mut_ref()` error[E0507]: cannot move out of borrowed content --> $DIR/issue-20801.rs:39:22 @@ -14,7 +14,7 @@ LL | let b = unsafe { *imm_ref() }; | ^^^^^^^^^^ | | | cannot move out of borrowed content - | help: consider using a reference instead: `&*imm_ref()` + | help: consider removing the `*`: `imm_ref()` error[E0507]: cannot move out of borrowed content --> $DIR/issue-20801.rs:42:22 @@ -23,7 +23,7 @@ LL | let c = unsafe { *mut_ptr() }; | ^^^^^^^^^^ | | | cannot move out of borrowed content - | help: consider using a reference instead: `&*mut_ptr()` + | help: consider removing the `*`: `mut_ptr()` error[E0507]: cannot move out of borrowed content --> $DIR/issue-20801.rs:45:22 @@ -32,7 +32,7 @@ LL | let d = unsafe { *const_ptr() }; | ^^^^^^^^^^^^ | | | cannot move out of borrowed content - | help: consider using a reference instead: `&*const_ptr()` + | help: consider removing the `*`: `const_ptr()` error: aborting due to 4 previous errors diff --git a/src/test/ui/issues/issue-40402-ref-hints/issue-40402-1.nll.stderr b/src/test/ui/issues/issue-40402-ref-hints/issue-40402-1.nll.stderr index 162e43abc0ac4..9020d3778c373 100644 --- a/src/test/ui/issues/issue-40402-ref-hints/issue-40402-1.nll.stderr +++ b/src/test/ui/issues/issue-40402-ref-hints/issue-40402-1.nll.stderr @@ -5,7 +5,7 @@ LL | let e = f.v[0]; //~ ERROR cannot move out of indexed content | ^^^^^^ | | | cannot move out of borrowed content - | help: consider using a reference instead: `&f.v[0]` + | help: consider borrowing here: `&f.v[0]` error: aborting due to previous error diff --git a/src/test/ui/issues/issue-40402-ref-hints/issue-40402-2.nll.stderr b/src/test/ui/issues/issue-40402-ref-hints/issue-40402-2.nll.stderr index cd75be24589df..a80e9a5fe091f 100644 --- a/src/test/ui/issues/issue-40402-ref-hints/issue-40402-2.nll.stderr +++ b/src/test/ui/issues/issue-40402-ref-hints/issue-40402-2.nll.stderr @@ -5,9 +5,15 @@ LL | let (a, b) = x[0]; //~ ERROR cannot move out of indexed content | - - ^^^^ | | | | | | | cannot move out of borrowed content - | | | help: consider using a reference instead: `&x[0]` - | | move occurs because b has type `std::string::String`, which does not implement the `Copy` trait - | move occurs because a has type `std::string::String`, which does not implement the `Copy` trait + | | | help: consider borrowing here: `&x[0]` + | | ...and here + | data moved here + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/issue-40402-2.rs:15:10 + | +LL | let (a, b) = x[0]; //~ ERROR cannot move out of indexed content + | ^ ^ error: aborting due to previous error diff --git a/src/test/ui/macros/issue-30143.rs b/src/test/ui/macros/issue-30143.rs new file mode 100644 index 0000000000000..b7fb5b3af999a --- /dev/null +++ b/src/test/ui/macros/issue-30143.rs @@ -0,0 +1,21 @@ +// Copyright 2018 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 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +use std::fmt::Write; + +fn main() { + println!(0); + //~^ ERROR format argument must be a string literal + eprintln!('a'); + //~^ ERROR format argument must be a string literal + let mut s = String::new(); + writeln!(s, true).unwrap(); + //~^ ERROR format argument must be a string literal +} diff --git a/src/test/ui/macros/issue-30143.stderr b/src/test/ui/macros/issue-30143.stderr new file mode 100644 index 0000000000000..56834f68f847c --- /dev/null +++ b/src/test/ui/macros/issue-30143.stderr @@ -0,0 +1,32 @@ +error: format argument must be a string literal + --> $DIR/issue-30143.rs:14:14 + | +LL | println!(0); + | ^ +help: you might be missing a string literal to format with + | +LL | println!("{}", 0); + | ^^^^^ + +error: format argument must be a string literal + --> $DIR/issue-30143.rs:16:15 + | +LL | eprintln!('a'); + | ^^^ +help: you might be missing a string literal to format with + | +LL | eprintln!("{}", 'a'); + | ^^^^^ + +error: format argument must be a string literal + --> $DIR/issue-30143.rs:19:17 + | +LL | writeln!(s, true).unwrap(); + | ^^^^ +help: you might be missing a string literal to format with + | +LL | writeln!(s, "{}", true).unwrap(); + | ^^^^^ + +error: aborting due to 3 previous errors + diff --git a/src/test/ui/macros/macro-attribute.rs b/src/test/ui/macros/macro-attribute.rs index a77b172487600..111375b369363 100644 --- a/src/test/ui/macros/macro-attribute.rs +++ b/src/test/ui/macros/macro-attribute.rs @@ -8,5 +8,7 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -#[doc = $not_there] //~ ERROR arbitrary tokens in non-macro attributes are unstable +#![feature(unrestricted_attribute_tokens)] + +#[doc = $not_there] //~ ERROR expected `]`, found `not_there` fn main() { } diff --git a/src/test/ui/macros/macro-attribute.stderr b/src/test/ui/macros/macro-attribute.stderr index 48132dddf1a42..c403872ecb385 100644 --- a/src/test/ui/macros/macro-attribute.stderr +++ b/src/test/ui/macros/macro-attribute.stderr @@ -1,11 +1,8 @@ -error[E0658]: arbitrary tokens in non-macro attributes are unstable (see issue #44690) - --> $DIR/macro-attribute.rs:11:1 +error: expected `]`, found `not_there` + --> $DIR/macro-attribute.rs:13:10 | -LL | #[doc = $not_there] //~ ERROR arbitrary tokens in non-macro attributes are unstable - | ^^^^^^^^^^^^^^^^^^^ - | - = help: add #![feature(unrestricted_attribute_tokens)] to the crate attributes to enable +LL | #[doc = $not_there] //~ ERROR expected `]`, found `not_there` + | ^^^^^^^^^ expected `]` error: aborting due to previous error -For more information about this error, try `rustc --explain E0658`. diff --git a/src/test/ui/macros/macros-nonfatal-errors.rs b/src/test/ui/macros/macros-nonfatal-errors.rs index 7290d18beb74e..2815e1be70983 100644 --- a/src/test/ui/macros/macros-nonfatal-errors.rs +++ b/src/test/ui/macros/macros-nonfatal-errors.rs @@ -10,7 +10,6 @@ // normalize-stderr-test: "The system cannot find the file specified\." -> "No such file or directory" // ignore-tidy-linelength -// ignore-stage1 // test that errors in a (selection) of macros don't kill compilation // immediately, so that we get more errors listed at a time. diff --git a/src/test/ui/macros/macros-nonfatal-errors.stderr b/src/test/ui/macros/macros-nonfatal-errors.stderr index efb2c248813d7..084042acc974d 100644 --- a/src/test/ui/macros/macros-nonfatal-errors.stderr +++ b/src/test/ui/macros/macros-nonfatal-errors.stderr @@ -1,47 +1,47 @@ error[E0665]: `Default` cannot be derived for enums, only structs - --> $DIR/macros-nonfatal-errors.rs:21:10 + --> $DIR/macros-nonfatal-errors.rs:20:10 | LL | #[derive(Default)] //~ ERROR | ^^^^^^^ error: inline assembly must be a string literal - --> $DIR/macros-nonfatal-errors.rs:25:10 + --> $DIR/macros-nonfatal-errors.rs:24:10 | LL | asm!(invalid); //~ ERROR | ^^^^^^^ error: concat_idents! requires ident args. - --> $DIR/macros-nonfatal-errors.rs:27:5 + --> $DIR/macros-nonfatal-errors.rs:26:5 | LL | concat_idents!("not", "idents"); //~ ERROR | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: argument must be a string literal - --> $DIR/macros-nonfatal-errors.rs:29:17 + --> $DIR/macros-nonfatal-errors.rs:28:17 | LL | option_env!(invalid); //~ ERROR | ^^^^^^^ error: expected string literal - --> $DIR/macros-nonfatal-errors.rs:30:10 + --> $DIR/macros-nonfatal-errors.rs:29:10 | LL | env!(invalid); //~ ERROR | ^^^^^^^ error: expected string literal - --> $DIR/macros-nonfatal-errors.rs:31:10 + --> $DIR/macros-nonfatal-errors.rs:30:10 | LL | env!(foo, abr, baz); //~ ERROR | ^^^ error: environment variable `RUST_HOPEFULLY_THIS_DOESNT_EXIST` not defined - --> $DIR/macros-nonfatal-errors.rs:32:5 + --> $DIR/macros-nonfatal-errors.rs:31:5 | LL | env!("RUST_HOPEFULLY_THIS_DOESNT_EXIST"); //~ ERROR | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error[E0658]: non-ident macro paths are experimental (see issue #35896) - --> $DIR/macros-nonfatal-errors.rs:34:5 + --> $DIR/macros-nonfatal-errors.rs:33:5 | LL | foo::blah!(); //~ ERROR | ^^^^^^^^^ @@ -49,7 +49,7 @@ LL | foo::blah!(); //~ ERROR = help: add #![feature(use_extern_macros)] to the crate attributes to enable error: format argument must be a string literal - --> $DIR/macros-nonfatal-errors.rs:36:13 + --> $DIR/macros-nonfatal-errors.rs:35:13 | LL | format!(invalid); //~ ERROR | ^^^^^^^ @@ -59,37 +59,37 @@ LL | format!("{}", invalid); //~ ERROR | ^^^^^ error: argument must be a string literal - --> $DIR/macros-nonfatal-errors.rs:38:14 + --> $DIR/macros-nonfatal-errors.rs:37:14 | LL | include!(invalid); //~ ERROR | ^^^^^^^ error: argument must be a string literal - --> $DIR/macros-nonfatal-errors.rs:40:18 + --> $DIR/macros-nonfatal-errors.rs:39:18 | LL | include_str!(invalid); //~ ERROR | ^^^^^^^ error: couldn't read $DIR/i'd be quite surprised if a file with this name existed: No such file or directory (os error 2) - --> $DIR/macros-nonfatal-errors.rs:41:5 + --> $DIR/macros-nonfatal-errors.rs:40:5 | LL | include_str!("i'd be quite surprised if a file with this name existed"); //~ ERROR | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: argument must be a string literal - --> $DIR/macros-nonfatal-errors.rs:42:20 + --> $DIR/macros-nonfatal-errors.rs:41:20 | LL | include_bytes!(invalid); //~ ERROR | ^^^^^^^ error: couldn't read $DIR/i'd be quite surprised if a file with this name existed: No such file or directory (os error 2) - --> $DIR/macros-nonfatal-errors.rs:43:5 + --> $DIR/macros-nonfatal-errors.rs:42:5 | LL | include_bytes!("i'd be quite surprised if a file with this name existed"); //~ ERROR | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: trace_macros! accepts only `true` or `false` - --> $DIR/macros-nonfatal-errors.rs:45:5 + --> $DIR/macros-nonfatal-errors.rs:44:5 | LL | trace_macros!(invalid); //~ ERROR | ^^^^^^^^^^^^^^^^^^^^^^^ diff --git a/src/test/ui/moves/move-out-of-slice-1.nll.stderr b/src/test/ui/moves/move-out-of-slice-1.nll.stderr index b061b6a796385..aa62b457ecdf3 100644 --- a/src/test/ui/moves/move-out-of-slice-1.nll.stderr +++ b/src/test/ui/moves/move-out-of-slice-1.nll.stderr @@ -4,10 +4,13 @@ error[E0508]: cannot move out of type `[A]`, a non-copy slice LL | match a { | ^ cannot move out of here LL | box [a] => {}, //~ ERROR cannot move out of type `[A]`, a non-copy slice - | - - | | - | data moved here - | help: to prevent move, use ref or ref mut: `ref a` + | - data moved here + | +note: move occurs because `a` has type `A`, which does not implement the `Copy` trait + --> $DIR/move-out-of-slice-1.rs:18:14 + | +LL | box [a] => {}, //~ ERROR cannot move out of type `[A]`, a non-copy slice + | ^ error: aborting due to previous error diff --git a/src/test/ui/moves/moves-based-on-type-block-bad.nll.stderr b/src/test/ui/moves/moves-based-on-type-block-bad.nll.stderr index 94f2074b45d4c..1f22ab1481852 100644 --- a/src/test/ui/moves/moves-based-on-type-block-bad.nll.stderr +++ b/src/test/ui/moves/moves-based-on-type-block-bad.nll.stderr @@ -5,10 +5,16 @@ LL | match hellothere.x { //~ ERROR cannot move out | ^^^^^^^^^^^^ | | | cannot move out of borrowed content - | help: consider using a reference instead: `&hellothere.x` + | help: consider borrowing here: `&hellothere.x` ... LL | box E::Bar(x) => println!("{}", x.to_string()), - | - move occurs because x has type `std::boxed::Box`, which does not implement the `Copy` trait + | - data moved here + | +note: move occurs because `x` has type `std::boxed::Box`, which does not implement the `Copy` trait + --> $DIR/moves-based-on-type-block-bad.rs:37:28 + | +LL | box E::Bar(x) => println!("{}", x.to_string()), + | ^ error: aborting due to previous error diff --git a/src/test/ui/nll/cannot-move-block-spans.nll.stderr b/src/test/ui/nll/cannot-move-block-spans.nll.stderr index 814e11b6f0682..6a4c8f2e8d815 100644 --- a/src/test/ui/nll/cannot-move-block-spans.nll.stderr +++ b/src/test/ui/nll/cannot-move-block-spans.nll.stderr @@ -5,7 +5,7 @@ LL | let x = { *r }; //~ ERROR | ^^ | | | cannot move out of borrowed content - | help: consider removing this dereference operator: `r` + | help: consider removing the `*`: `r` error[E0507]: cannot move out of borrowed content --> $DIR/cannot-move-block-spans.rs:16:22 @@ -14,7 +14,7 @@ LL | let y = unsafe { *r }; //~ ERROR | ^^ | | | cannot move out of borrowed content - | help: consider removing this dereference operator: `r` + | help: consider removing the `*`: `r` error[E0507]: cannot move out of borrowed content --> $DIR/cannot-move-block-spans.rs:17:26 @@ -23,7 +23,7 @@ LL | let z = loop { break *r; }; //~ ERROR | ^^ | | | cannot move out of borrowed content - | help: consider removing this dereference operator: `r` + | help: consider removing the `*`: `r` error[E0508]: cannot move out of type `[std::string::String; 2]`, a non-copy array --> $DIR/cannot-move-block-spans.rs:21:15 @@ -32,7 +32,7 @@ LL | let x = { arr[0] }; //~ ERROR | ^^^^^^ | | | cannot move out of here - | help: consider using a reference instead: `&arr[0]` + | help: consider borrowing here: `&arr[0]` error[E0508]: cannot move out of type `[std::string::String; 2]`, a non-copy array --> $DIR/cannot-move-block-spans.rs:22:22 @@ -41,7 +41,7 @@ LL | let y = unsafe { arr[0] }; //~ ERROR | ^^^^^^ | | | cannot move out of here - | help: consider using a reference instead: `&arr[0]` + | help: consider borrowing here: `&arr[0]` error[E0508]: cannot move out of type `[std::string::String; 2]`, a non-copy array --> $DIR/cannot-move-block-spans.rs:23:26 @@ -50,7 +50,7 @@ LL | let z = loop { break arr[0]; }; //~ ERROR | ^^^^^^ | | | cannot move out of here - | help: consider using a reference instead: `&arr[0]` + | help: consider borrowing here: `&arr[0]` error[E0507]: cannot move out of borrowed content --> $DIR/cannot-move-block-spans.rs:27:38 @@ -59,7 +59,7 @@ LL | let x = { let mut u = 0; u += 1; *r }; //~ ERROR | ^^ | | | cannot move out of borrowed content - | help: consider removing this dereference operator: `r` + | help: consider removing the `*`: `r` error[E0507]: cannot move out of borrowed content --> $DIR/cannot-move-block-spans.rs:28:45 @@ -68,7 +68,7 @@ LL | let y = unsafe { let mut u = 0; u += 1; *r }; //~ ERROR | ^^ | | | cannot move out of borrowed content - | help: consider removing this dereference operator: `r` + | help: consider removing the `*`: `r` error[E0507]: cannot move out of borrowed content --> $DIR/cannot-move-block-spans.rs:29:49 @@ -77,7 +77,7 @@ LL | let z = loop { let mut u = 0; u += 1; break *r; u += 2; }; //~ ERROR | ^^ | | | cannot move out of borrowed content - | help: consider removing this dereference operator: `r` + | help: consider removing the `*`: `r` error: aborting due to 9 previous errors diff --git a/src/test/ui/nll/move-errors.stderr b/src/test/ui/nll/move-errors.stderr index 53d60d3f6d649..592768363096c 100644 --- a/src/test/ui/nll/move-errors.stderr +++ b/src/test/ui/nll/move-errors.stderr @@ -5,7 +5,7 @@ LL | let b = *a; | ^^ | | | cannot move out of borrowed content - | help: consider removing this dereference operator: `a` + | help: consider removing the `*`: `a` error[E0508]: cannot move out of type `[A; 1]`, a non-copy array --> $DIR/move-errors.rs:25:13 @@ -14,7 +14,7 @@ LL | let b = a[0]; | ^^^^ | | | cannot move out of here - | help: consider using a reference instead: `&a[0]` + | help: consider borrowing here: `&a[0]` error[E0507]: cannot move out of borrowed content --> $DIR/move-errors.rs:32:13 @@ -23,7 +23,7 @@ LL | let s = **r; | ^^^ | | | cannot move out of borrowed content - | help: consider using a reference instead: `&**r` + | help: consider removing the `*`: `*r` error[E0507]: cannot move out of borrowed content --> $DIR/move-errors.rs:40:13 @@ -32,7 +32,7 @@ LL | let s = *r; | ^^ | | | cannot move out of borrowed content - | help: consider using a reference instead: `&*r` + | help: consider removing the `*`: `r` error[E0508]: cannot move out of type `[A; 1]`, a non-copy array --> $DIR/move-errors.rs:45:13 @@ -41,7 +41,7 @@ LL | let a = [A("".to_string())][0]; | ^^^^^^^^^^^^^^^^^^^^^^ | | | cannot move out of here - | help: consider using a reference instead: `&[A("".to_string())][0]` + | help: consider borrowing here: `&[A("".to_string())][0]` error[E0507]: cannot move out of borrowed content --> $DIR/move-errors.rs:51:16 @@ -50,8 +50,14 @@ LL | let A(s) = *a; | - ^^ | | | | | cannot move out of borrowed content - | | help: consider removing this dereference operator: `a` - | move occurs because s has type `std::string::String`, which does not implement the `Copy` trait + | | help: consider removing the `*`: `a` + | data moved here + | +note: move occurs because `s` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/move-errors.rs:51:11 + | +LL | let A(s) = *a; + | ^ error[E0509]: cannot move out of type `D`, which implements the `Drop` trait --> $DIR/move-errors.rs:57:19 @@ -60,7 +66,12 @@ LL | let C(D(s)) = c; | - ^ cannot move out of here | | | data moved here - | help: to prevent move, use ref or ref mut: `ref s` + | +note: move occurs because `s` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/move-errors.rs:57:13 + | +LL | let C(D(s)) = c; + | ^ error[E0507]: cannot move out of borrowed content --> $DIR/move-errors.rs:64:9 @@ -75,12 +86,20 @@ LL | match x[0] { | ^^^^ | | | cannot move out of here - | help: consider using a reference instead: `&x[0]` + | help: consider borrowing here: `&x[0]` LL | //~^ ERROR LL | B::U(d) => (), - | - move occurs because d has type `D`, which does not implement the `Copy` trait + | - data moved here LL | B::V(s) => (), - | - move occurs because s has type `std::string::String`, which does not implement the `Copy` trait + | - ...and here + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/move-errors.rs:89:14 + | +LL | B::U(d) => (), + | ^ +LL | B::V(s) => (), + | ^ error[E0509]: cannot move out of type `D`, which implements the `Drop` trait --> $DIR/move-errors.rs:96:11 @@ -89,10 +108,13 @@ LL | match x { | ^ cannot move out of here ... LL | B::U(D(s)) => (), - | - - | | - | data moved here - | help: to prevent move, use ref or ref mut: `ref s` + | - data moved here + | +note: move occurs because `s` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/move-errors.rs:99:16 + | +LL | B::U(D(s)) => (), + | ^ error[E0509]: cannot move out of type `D`, which implements the `Drop` trait --> $DIR/move-errors.rs:105:11 @@ -101,10 +123,13 @@ LL | match x { | ^ cannot move out of here ... LL | (D(s), &t) => (), - | - - | | - | data moved here - | help: to prevent move, use ref or ref mut: `ref s` + | - data moved here + | +note: move occurs because `s` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/move-errors.rs:108:12 + | +LL | (D(s), &t) => (), + | ^ error[E0507]: cannot move out of borrowed content --> $DIR/move-errors.rs:105:11 @@ -113,10 +138,13 @@ LL | match x { | ^ cannot move out of borrowed content ... LL | (D(s), &t) => (), - | - - | | - | data moved here - | help: to prevent move, use ref or ref mut: `ref t` + | - data moved here + | +note: move occurs because `t` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/move-errors.rs:108:17 + | +LL | (D(s), &t) => (), + | ^ error[E0509]: cannot move out of type `F`, which implements the `Drop` trait --> $DIR/move-errors.rs:115:11 @@ -125,13 +153,15 @@ LL | match x { | ^ cannot move out of here LL | //~^ ERROR LL | F(s, mut t) => (), - | - ----- ... and here + | - ----- ...and here | | | data moved here -help: to prevent move, use ref or ref mut | -LL | F(ref s, ref mut t) => (), - | ^^^^^ ^^^^^^^^^ +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/move-errors.rs:117:11 + | +LL | F(s, mut t) => (), + | ^ ^^^^^ error[E0507]: cannot move out of borrowed content --> $DIR/move-errors.rs:123:11 @@ -140,10 +170,16 @@ LL | match *x { | ^^ | | | cannot move out of borrowed content - | help: consider removing this dereference operator: `x` + | help: consider removing the `*`: `x` LL | //~^ ERROR LL | Ok(s) | Err(s) => (), - | - move occurs because s has type `std::string::String`, which does not implement the `Copy` trait + | - data moved here + | +note: move occurs because `s` has type `std::string::String`, which does not implement the `Copy` trait + --> $DIR/move-errors.rs:125:12 + | +LL | Ok(s) | Err(s) => (), + | ^ error: aborting due to 14 previous errors diff --git a/src/test/ui/on-unimplemented/bad-annotation.rs b/src/test/ui/on-unimplemented/bad-annotation.rs index 7ef155e5f2ebe..286c71bb29908 100644 --- a/src/test/ui/on-unimplemented/bad-annotation.rs +++ b/src/test/ui/on-unimplemented/bad-annotation.rs @@ -28,7 +28,7 @@ trait BadAnnotation1 {} #[rustc_on_unimplemented = "Unimplemented trait error on `{Self}` with params `<{A},{B},{C}>`"] -//~^ ERROR there is no parameter C on trait BadAnnotation2 +//~^ ERROR there is no parameter `C` on trait `BadAnnotation2` trait BadAnnotation2 {} diff --git a/src/test/ui/on-unimplemented/bad-annotation.stderr b/src/test/ui/on-unimplemented/bad-annotation.stderr index 1c5d4d603afc6..212eb125f85b3 100644 --- a/src/test/ui/on-unimplemented/bad-annotation.stderr +++ b/src/test/ui/on-unimplemented/bad-annotation.stderr @@ -4,9 +4,9 @@ error[E0232]: `#[rustc_on_unimplemented]` requires a value LL | #[rustc_on_unimplemented] //~ ERROR `#[rustc_on_unimplemented]` requires a value | ^^^^^^^^^^^^^^^^^^^^^^^^^ value required here | - = note: eg `#[rustc_on_unimplemented = "foo"]` + = note: eg `#[rustc_on_unimplemented(message="foo")]` -error[E0230]: there is no parameter C on trait BadAnnotation2 +error[E0230]: there is no parameter `C` on trait `BadAnnotation2` --> $DIR/bad-annotation.rs:30:1 | LL | #[rustc_on_unimplemented = "Unimplemented trait error on `{Self}` with params `<{A},{B},{C}>`"] @@ -24,7 +24,7 @@ error[E0232]: this attribute must have a valid value LL | #[rustc_on_unimplemented(lorem="")] | ^^^^^^^^ expected value here | - = note: eg `#[rustc_on_unimplemented = "foo"]` + = note: eg `#[rustc_on_unimplemented(message="foo")]` error[E0232]: this attribute must have a valid value --> $DIR/bad-annotation.rs:44:26 @@ -32,7 +32,7 @@ error[E0232]: this attribute must have a valid value LL | #[rustc_on_unimplemented(lorem(ipsum(dolor)))] | ^^^^^^^^^^^^^^^^^^^ expected value here | - = note: eg `#[rustc_on_unimplemented = "foo"]` + = note: eg `#[rustc_on_unimplemented(message="foo")]` error[E0232]: this attribute must have a valid value --> $DIR/bad-annotation.rs:48:39 @@ -40,7 +40,7 @@ error[E0232]: this attribute must have a valid value LL | #[rustc_on_unimplemented(message="x", message="y")] | ^^^^^^^^^^^ expected value here | - = note: eg `#[rustc_on_unimplemented = "foo"]` + = note: eg `#[rustc_on_unimplemented(message="foo")]` error[E0232]: this attribute must have a valid value --> $DIR/bad-annotation.rs:52:39 @@ -48,7 +48,7 @@ error[E0232]: this attribute must have a valid value LL | #[rustc_on_unimplemented(message="x", on(desugared, message="y"))] | ^^^^^^^^^^^^^^^^^^^^^^^^^^ expected value here | - = note: eg `#[rustc_on_unimplemented = "foo"]` + = note: eg `#[rustc_on_unimplemented(message="foo")]` error[E0232]: empty `on`-clause in `#[rustc_on_unimplemented]` --> $DIR/bad-annotation.rs:56:26 @@ -62,7 +62,7 @@ error[E0232]: this attribute must have a valid value LL | #[rustc_on_unimplemented(on="x", message="y")] | ^^^^^^ expected value here | - = note: eg `#[rustc_on_unimplemented = "foo"]` + = note: eg `#[rustc_on_unimplemented(message="foo")]` error[E0232]: this attribute must have a valid value --> $DIR/bad-annotation.rs:67:40 @@ -70,7 +70,7 @@ error[E0232]: this attribute must have a valid value LL | #[rustc_on_unimplemented(on(desugared, on(desugared, message="x")), message="y")] | ^^^^^^^^^^^^^^^^^^^^^^^^^^ expected value here | - = note: eg `#[rustc_on_unimplemented = "foo"]` + = note: eg `#[rustc_on_unimplemented(message="foo")]` error: aborting due to 10 previous errors diff --git a/src/test/ui/parser-recovery-2.stderr b/src/test/ui/parser-recovery-2.stderr index 7b5206073522f..1025dad3af773 100644 --- a/src/test/ui/parser-recovery-2.stderr +++ b/src/test/ui/parser-recovery-2.stderr @@ -1,14 +1,11 @@ error: incorrect close delimiter: `)` --> $DIR/parser-recovery-2.rs:18:5 | -LL | ) //~ ERROR incorrect close delimiter: `)` - | ^ - | -note: unclosed delimiter - --> $DIR/parser-recovery-2.rs:16:14 - | LL | fn bar() { - | ^ + | - unclosed delimiter +LL | let x = foo(); //~ ERROR cannot find function `foo` in this scope +LL | ) //~ ERROR incorrect close delimiter: `)` + | ^ incorrect close delimiter error: unexpected token: `;` --> $DIR/parser-recovery-2.rs:22:15 diff --git a/src/test/ui/resolve/token-error-correct-2.stderr b/src/test/ui/resolve/token-error-correct-2.stderr index 7abc1ba47810b..fcd4b4888b0ad 100644 --- a/src/test/ui/resolve/token-error-correct-2.stderr +++ b/src/test/ui/resolve/token-error-correct-2.stderr @@ -1,14 +1,11 @@ error: incorrect close delimiter: `)` --> $DIR/token-error-correct-2.rs:16:5 | -LL | ) //~ ERROR: incorrect close delimiter: `)` - | ^ - | -note: unclosed delimiter - --> $DIR/token-error-correct-2.rs:14:12 - | LL | if foo { - | ^ + | - unclosed delimiter +LL | //~^ ERROR: cannot find value `foo` +LL | ) //~ ERROR: incorrect close delimiter: `)` + | ^ incorrect close delimiter error[E0425]: cannot find value `foo` in this scope --> $DIR/token-error-correct-2.rs:14:8 diff --git a/src/test/ui/resolve/token-error-correct-3.stderr b/src/test/ui/resolve/token-error-correct-3.stderr index 24186d94acce9..a546c2704d915 100644 --- a/src/test/ui/resolve/token-error-correct-3.stderr +++ b/src/test/ui/resolve/token-error-correct-3.stderr @@ -1,14 +1,11 @@ error: incorrect close delimiter: `}` --> $DIR/token-error-correct-3.rs:30:9 | -LL | } else { //~ ERROR: incorrect close delimiter: `}` - | ^ - | -note: unclosed delimiter - --> $DIR/token-error-correct-3.rs:24:21 - | LL | callback(path.as_ref(); //~ ERROR expected one of - | ^ + | - unclosed delimiter +... +LL | } else { //~ ERROR: incorrect close delimiter: `}` + | ^ incorrect close delimiter error: expected one of `)`, `,`, `.`, `?`, or an operator, found `;` --> $DIR/token-error-correct-3.rs:24:35 diff --git a/src/test/ui/resolve/token-error-correct.rs b/src/test/ui/resolve/token-error-correct.rs index c88f823839dad..39c664e270c45 100644 --- a/src/test/ui/resolve/token-error-correct.rs +++ b/src/test/ui/resolve/token-error-correct.rs @@ -15,4 +15,3 @@ fn main() { //~^ ERROR: expected expression, found `;` } //~^ ERROR: incorrect close delimiter: `}` -//~| ERROR: incorrect close delimiter: `}` diff --git a/src/test/ui/resolve/token-error-correct.stderr b/src/test/ui/resolve/token-error-correct.stderr index c6d32c6726ea5..1e246b6f085bd 100644 --- a/src/test/ui/resolve/token-error-correct.stderr +++ b/src/test/ui/resolve/token-error-correct.stderr @@ -1,26 +1,11 @@ error: incorrect close delimiter: `}` --> $DIR/token-error-correct.rs:16:1 | -LL | } - | ^ - | -note: unclosed delimiter - --> $DIR/token-error-correct.rs:14:12 - | LL | foo(bar(; - | ^ - -error: incorrect close delimiter: `}` - --> $DIR/token-error-correct.rs:16:1 - | + | - unclosed delimiter +LL | //~^ ERROR: expected expression, found `;` LL | } - | ^ - | -note: unclosed delimiter - --> $DIR/token-error-correct.rs:14:8 - | -LL | foo(bar(; - | ^ + | ^ incorrect close delimiter error: expected expression, found `;` --> $DIR/token-error-correct.rs:14:13 @@ -28,5 +13,5 @@ error: expected expression, found `;` LL | foo(bar(; | ^ expected expression -error: aborting due to 3 previous errors +error: aborting due to 2 previous errors diff --git a/src/test/ui/rfc1598-generic-associated-types/collections.rs b/src/test/ui/rfc1598-generic-associated-types/collections.rs index e71166ed65bba..a6dbb03d379db 100644 --- a/src/test/ui/rfc1598-generic-associated-types/collections.rs +++ b/src/test/ui/rfc1598-generic-associated-types/collections.rs @@ -9,10 +9,11 @@ // except according to those terms. #![feature(generic_associated_types)] +//~^ WARNING the feature `generic_associated_types` is incomplete #![feature(associated_type_defaults)] -//FIXME(#44265): "lifetime parameters are not allowed on this type" errors will be addressed in a -//follow-up PR +// FIXME(#44265): "lifetime parameters are not allowed on this type" errors will be addressed in a +// follow-up PR. // A Collection trait and collection families. Based on // http://smallcultfollowing.com/babysteps/blog/2016/11/03/ diff --git a/src/test/ui/rfc1598-generic-associated-types/collections.stderr b/src/test/ui/rfc1598-generic-associated-types/collections.stderr index 8c31ab2ca88e4..0e7d6ace1bb1d 100644 --- a/src/test/ui/rfc1598-generic-associated-types/collections.stderr +++ b/src/test/ui/rfc1598-generic-associated-types/collections.stderr @@ -1,29 +1,35 @@ +warning: the feature `generic_associated_types` is incomplete and may cause the compiler to crash + --> $DIR/collections.rs:11:12 + | +LL | #![feature(generic_associated_types)] + | ^^^^^^^^^^^^^^^^^^^^^^^^ + error[E0109]: type parameters are not allowed on this type - --> $DIR/collections.rs:65:90 + --> $DIR/collections.rs:66:90 | LL | fn floatify(ints: &C) -> <>::Family as CollectionFamily>::Member | ^^^ type parameter not allowed error[E0109]: type parameters are not allowed on this type - --> $DIR/collections.rs:77:69 + --> $DIR/collections.rs:78:69 | LL | fn floatify_sibling(ints: &C) -> >::Sibling | ^^^ type parameter not allowed error[E0109]: type parameters are not allowed on this type - --> $DIR/collections.rs:26:71 + --> $DIR/collections.rs:27:71 | LL | <>::Family as CollectionFamily>::Member; | ^ type parameter not allowed error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/collections.rs:33:50 + --> $DIR/collections.rs:34:50 | LL | fn iterate<'iter>(&'iter self) -> Self::Iter<'iter>; | ^^^^^ lifetime parameter not allowed error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/collections.rs:59:50 + --> $DIR/collections.rs:60:50 | LL | fn iterate<'iter>(&'iter self) -> Self::Iter<'iter> { | ^^^^^ lifetime parameter not allowed diff --git a/src/test/ui/rfc1598-generic-associated-types/construct_with_other_type.rs b/src/test/ui/rfc1598-generic-associated-types/construct_with_other_type.rs index 0429410031526..88a660b3a5afe 100644 --- a/src/test/ui/rfc1598-generic-associated-types/construct_with_other_type.rs +++ b/src/test/ui/rfc1598-generic-associated-types/construct_with_other_type.rs @@ -9,11 +9,12 @@ // except according to those terms. #![feature(generic_associated_types)] +//~^ WARNING the feature `generic_associated_types` is incomplete use std::ops::Deref; -//FIXME(#44265): "lifetime parameters are not allowed on this type" errors will be addressed in a -//follow-up PR +// FIXME(#44265): "lifetime parameters are not allowed on this type" errors will be addressed in a +// follow-up PR. trait Foo { type Bar<'a, 'b>; diff --git a/src/test/ui/rfc1598-generic-associated-types/construct_with_other_type.stderr b/src/test/ui/rfc1598-generic-associated-types/construct_with_other_type.stderr index 1746122eb49f4..5c85698fa55c7 100644 --- a/src/test/ui/rfc1598-generic-associated-types/construct_with_other_type.stderr +++ b/src/test/ui/rfc1598-generic-associated-types/construct_with_other_type.stderr @@ -1,17 +1,23 @@ +warning: the feature `generic_associated_types` is incomplete and may cause the compiler to crash + --> $DIR/construct_with_other_type.rs:11:12 + | +LL | #![feature(generic_associated_types)] + | ^^^^^^^^^^^^^^^^^^^^^^^^ + error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/construct_with_other_type.rs:26:46 + --> $DIR/construct_with_other_type.rs:27:46 | LL | type Baa<'a>: Deref as Foo>::Bar<'a, 'static>>; | ^^ lifetime parameter not allowed error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/construct_with_other_type.rs:26:63 + --> $DIR/construct_with_other_type.rs:27:63 | LL | type Baa<'a>: Deref as Foo>::Bar<'a, 'static>>; | ^^ lifetime parameter not allowed error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/construct_with_other_type.rs:34:40 + --> $DIR/construct_with_other_type.rs:35:40 | LL | type Baa<'a> = &'a ::Bar<'a, 'static>; | ^^ lifetime parameter not allowed diff --git a/src/test/ui/rfc1598-generic-associated-types/empty_generics.rs b/src/test/ui/rfc1598-generic-associated-types/empty_generics.rs index b12c075d13291..d8a2a1b73f7ef 100644 --- a/src/test/ui/rfc1598-generic-associated-types/empty_generics.rs +++ b/src/test/ui/rfc1598-generic-associated-types/empty_generics.rs @@ -9,6 +9,7 @@ // except according to those terms. #![feature(generic_associated_types)] +//~^ WARNING the feature `generic_associated_types` is incomplete trait Foo { type Bar<,>; diff --git a/src/test/ui/rfc1598-generic-associated-types/empty_generics.stderr b/src/test/ui/rfc1598-generic-associated-types/empty_generics.stderr index aff3044e9a14d..2670c3aa142b2 100644 --- a/src/test/ui/rfc1598-generic-associated-types/empty_generics.stderr +++ b/src/test/ui/rfc1598-generic-associated-types/empty_generics.stderr @@ -1,8 +1,14 @@ error: expected one of `>`, identifier, or lifetime, found `,` - --> $DIR/empty_generics.rs:14:14 + --> $DIR/empty_generics.rs:15:14 | LL | type Bar<,>; | ^ expected one of `>`, identifier, or lifetime here +warning: the feature `generic_associated_types` is incomplete and may cause the compiler to crash + --> $DIR/empty_generics.rs:11:12 + | +LL | #![feature(generic_associated_types)] + | ^^^^^^^^^^^^^^^^^^^^^^^^ + error: aborting due to previous error diff --git a/src/test/ui/rfc1598-generic-associated-types/gat-incomplete-warning.rs b/src/test/ui/rfc1598-generic-associated-types/gat-incomplete-warning.rs new file mode 100644 index 0000000000000..7f48408b369fd --- /dev/null +++ b/src/test/ui/rfc1598-generic-associated-types/gat-incomplete-warning.rs @@ -0,0 +1,16 @@ +// Copyright 2018 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 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +// run-pass + +#![feature(generic_associated_types)] +//~^ WARNING the feature `generic_associated_types` is incomplete + +fn main() {} diff --git a/src/test/ui/rfc1598-generic-associated-types/gat-incomplete-warning.stderr b/src/test/ui/rfc1598-generic-associated-types/gat-incomplete-warning.stderr new file mode 100644 index 0000000000000..67682dcb8fb1b --- /dev/null +++ b/src/test/ui/rfc1598-generic-associated-types/gat-incomplete-warning.stderr @@ -0,0 +1,6 @@ +warning: the feature `generic_associated_types` is incomplete and may cause the compiler to crash + --> $DIR/gat-incomplete-warning.rs:13:12 + | +LL | #![feature(generic_associated_types)] + | ^^^^^^^^^^^^^^^^^^^^^^^^ + diff --git a/src/test/ui/rfc1598-generic-associated-types/generic-associated-types-where.stderr b/src/test/ui/rfc1598-generic-associated-types/generic-associated-types-where.stderr new file mode 100644 index 0000000000000..97d5482735f86 --- /dev/null +++ b/src/test/ui/rfc1598-generic-associated-types/generic-associated-types-where.stderr @@ -0,0 +1,6 @@ +warning: the feature `generic_associated_types` is incomplete and may cause the compiler to crash + --> $DIR/generic-associated-types-where.rs:11:12 + | +LL | #![feature(generic_associated_types)] + | ^^^^^^^^^^^^^^^^^^^^^^^^ + diff --git a/src/test/ui/rfc1598-generic-associated-types/generic_associated_type_undeclared_lifetimes.rs b/src/test/ui/rfc1598-generic-associated-types/generic_associated_type_undeclared_lifetimes.rs index 263b3cb42eb4f..267272ded8c06 100644 --- a/src/test/ui/rfc1598-generic-associated-types/generic_associated_type_undeclared_lifetimes.rs +++ b/src/test/ui/rfc1598-generic-associated-types/generic_associated_type_undeclared_lifetimes.rs @@ -9,11 +9,12 @@ // except according to those terms. #![feature(generic_associated_types)] +//~^ WARNING the feature `generic_associated_types` is incomplete use std::ops::Deref; -//FIXME(#44265): "lifetime parameters are not allowed on this type" errors will be addressed in a -//follow-up PR +// FIXME(#44265): "lifetime parameters are not allowed on this type" errors will be addressed in a +// follow-up PR. trait Iterable { type Item<'a>; diff --git a/src/test/ui/rfc1598-generic-associated-types/generic_associated_type_undeclared_lifetimes.stderr b/src/test/ui/rfc1598-generic-associated-types/generic_associated_type_undeclared_lifetimes.stderr index d48c21477b310..79b29902ccdf0 100644 --- a/src/test/ui/rfc1598-generic-associated-types/generic_associated_type_undeclared_lifetimes.stderr +++ b/src/test/ui/rfc1598-generic-associated-types/generic_associated_type_undeclared_lifetimes.stderr @@ -1,29 +1,35 @@ +warning: the feature `generic_associated_types` is incomplete and may cause the compiler to crash + --> $DIR/generic_associated_type_undeclared_lifetimes.rs:11:12 + | +LL | #![feature(generic_associated_types)] + | ^^^^^^^^^^^^^^^^^^^^^^^^ + error[E0261]: use of undeclared lifetime name `'b` - --> $DIR/generic_associated_type_undeclared_lifetimes.rs:22:37 + --> $DIR/generic_associated_type_undeclared_lifetimes.rs:23:37 | LL | + Deref>; | ^^ undeclared lifetime error[E0261]: use of undeclared lifetime name `'undeclared` - --> $DIR/generic_associated_type_undeclared_lifetimes.rs:26:41 + --> $DIR/generic_associated_type_undeclared_lifetimes.rs:27:41 | LL | fn iter<'a>(&'a self) -> Self::Iter<'undeclared>; | ^^^^^^^^^^^ undeclared lifetime error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/generic_associated_type_undeclared_lifetimes.rs:20:47 + --> $DIR/generic_associated_type_undeclared_lifetimes.rs:21:47 | LL | type Iter<'a>: Iterator> | ^^ lifetime parameter not allowed error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/generic_associated_type_undeclared_lifetimes.rs:22:37 + --> $DIR/generic_associated_type_undeclared_lifetimes.rs:23:37 | LL | + Deref>; | ^^ lifetime parameter not allowed error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/generic_associated_type_undeclared_lifetimes.rs:26:41 + --> $DIR/generic_associated_type_undeclared_lifetimes.rs:27:41 | LL | fn iter<'a>(&'a self) -> Self::Iter<'undeclared>; | ^^^^^^^^^^^ lifetime parameter not allowed diff --git a/src/test/ui/rfc1598-generic-associated-types/iterable.rs b/src/test/ui/rfc1598-generic-associated-types/iterable.rs index 38967dbbe4530..b52b6e024219a 100644 --- a/src/test/ui/rfc1598-generic-associated-types/iterable.rs +++ b/src/test/ui/rfc1598-generic-associated-types/iterable.rs @@ -9,11 +9,12 @@ // except according to those terms. #![feature(generic_associated_types)] +//~^ WARNING the feature `generic_associated_types` is incomplete use std::ops::Deref; -//FIXME(#44265): "lifetime parameters are not allowed on this type" errors will be addressed in a -//follow-up PR +// FIXME(#44265): "lifetime parameters are not allowed on this type" errors will be addressed in a +// follow-up PR. trait Iterable { type Item<'a>; diff --git a/src/test/ui/rfc1598-generic-associated-types/iterable.stderr b/src/test/ui/rfc1598-generic-associated-types/iterable.stderr index 737a29ec2c8be..de3563c14eb7c 100644 --- a/src/test/ui/rfc1598-generic-associated-types/iterable.stderr +++ b/src/test/ui/rfc1598-generic-associated-types/iterable.stderr @@ -1,35 +1,41 @@ +warning: the feature `generic_associated_types` is incomplete and may cause the compiler to crash + --> $DIR/iterable.rs:11:12 + | +LL | #![feature(generic_associated_types)] + | ^^^^^^^^^^^^^^^^^^^^^^^^ + error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/iterable.rs:20:47 + --> $DIR/iterable.rs:21:47 | LL | type Iter<'a>: Iterator>; | ^^ lifetime parameter not allowed error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/iterable.rs:49:53 + --> $DIR/iterable.rs:50:53 | LL | fn make_iter<'a, I: Iterable>(it: &'a I) -> I::Iter<'a> { | ^^ lifetime parameter not allowed error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/iterable.rs:54:60 + --> $DIR/iterable.rs:55:60 | LL | fn get_first<'a, I: Iterable>(it: &'a I) -> Option> { | ^^ lifetime parameter not allowed error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/iterable.rs:23:41 + --> $DIR/iterable.rs:24:41 | LL | fn iter<'a>(&'a self) -> Self::Iter<'a>; | ^^ lifetime parameter not allowed error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/iterable.rs:32:41 + --> $DIR/iterable.rs:33:41 | LL | fn iter<'a>(&'a self) -> Self::Iter<'a> { | ^^ lifetime parameter not allowed error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/iterable.rs:43:41 + --> $DIR/iterable.rs:44:41 | LL | fn iter<'a>(&'a self) -> Self::Iter<'a> { | ^^ lifetime parameter not allowed diff --git a/src/test/ui/rfc1598-generic-associated-types/parameter_number_and_kind.rs b/src/test/ui/rfc1598-generic-associated-types/parameter_number_and_kind.rs index 51527d4117c2c..82e82e6dbccaf 100644 --- a/src/test/ui/rfc1598-generic-associated-types/parameter_number_and_kind.rs +++ b/src/test/ui/rfc1598-generic-associated-types/parameter_number_and_kind.rs @@ -9,12 +9,13 @@ // except according to those terms. #![feature(generic_associated_types)] +//~^ WARNING the feature `generic_associated_types` is incomplete #![feature(associated_type_defaults)] -//FIXME(#44265): "lifetime parameters are not allowed on this type" errors will be addressed in a -//follow-up PR +// FIXME(#44265): "lifetime parameters are not allowed on this type" errors will be addressed in a +// follow-up PR. -//FIXME(#44265): Update expected errors once E110 is resolved, now does not get past `trait Foo` +// FIXME(#44265): Update expected errors once E110 is resolved, now does not get past `trait Foo`. trait Foo { type A<'a>; diff --git a/src/test/ui/rfc1598-generic-associated-types/parameter_number_and_kind.stderr b/src/test/ui/rfc1598-generic-associated-types/parameter_number_and_kind.stderr index c8d37a51fa96b..e47daf2ae1bba 100644 --- a/src/test/ui/rfc1598-generic-associated-types/parameter_number_and_kind.stderr +++ b/src/test/ui/rfc1598-generic-associated-types/parameter_number_and_kind.stderr @@ -1,29 +1,35 @@ +warning: the feature `generic_associated_types` is incomplete and may cause the compiler to crash + --> $DIR/parameter_number_and_kind.rs:11:12 + | +LL | #![feature(generic_associated_types)] + | ^^^^^^^^^^^^^^^^^^^^^^^^ + error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/parameter_number_and_kind.rs:26:27 + --> $DIR/parameter_number_and_kind.rs:27:27 | LL | type FOk = Self::E<'static, T>; | ^^^^^^^ lifetime parameter not allowed error[E0109]: type parameters are not allowed on this type - --> $DIR/parameter_number_and_kind.rs:26:36 + --> $DIR/parameter_number_and_kind.rs:27:36 | LL | type FOk = Self::E<'static, T>; | ^ type parameter not allowed error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/parameter_number_and_kind.rs:29:26 + --> $DIR/parameter_number_and_kind.rs:30:26 | LL | type FErr1 = Self::E<'static, 'static>; // Error | ^^^^^^^ lifetime parameter not allowed error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/parameter_number_and_kind.rs:31:29 + --> $DIR/parameter_number_and_kind.rs:32:29 | LL | type FErr2 = Self::E<'static, T, u32>; // Error | ^^^^^^^ lifetime parameter not allowed error[E0109]: type parameters are not allowed on this type - --> $DIR/parameter_number_and_kind.rs:31:38 + --> $DIR/parameter_number_and_kind.rs:32:38 | LL | type FErr2 = Self::E<'static, T, u32>; // Error | ^ type parameter not allowed diff --git a/src/test/ui/rfc1598-generic-associated-types/pointer_family.rs b/src/test/ui/rfc1598-generic-associated-types/pointer_family.rs index cbeeb1d6ca7b2..0300ad06194e7 100644 --- a/src/test/ui/rfc1598-generic-associated-types/pointer_family.rs +++ b/src/test/ui/rfc1598-generic-associated-types/pointer_family.rs @@ -9,8 +9,9 @@ // except according to those terms. #![feature(generic_associated_types)] +//~^ WARNING the feature `generic_associated_types` is incomplete -//FIXME(#44265): "type parameter not allowed" errors will be addressed in a follow-up PR +// FIXME(#44265): "type parameter not allowed" errors will be addressed in a follow-up PR. use std::rc::Rc; use std::sync::Arc; diff --git a/src/test/ui/rfc1598-generic-associated-types/pointer_family.stderr b/src/test/ui/rfc1598-generic-associated-types/pointer_family.stderr index 3e772eee4f492..3be0481dc67e8 100644 --- a/src/test/ui/rfc1598-generic-associated-types/pointer_family.stderr +++ b/src/test/ui/rfc1598-generic-associated-types/pointer_family.stderr @@ -1,23 +1,29 @@ +warning: the feature `generic_associated_types` is incomplete and may cause the compiler to crash + --> $DIR/pointer_family.rs:11:12 + | +LL | #![feature(generic_associated_types)] + | ^^^^^^^^^^^^^^^^^^^^^^^^ + error[E0109]: type parameters are not allowed on this type - --> $DIR/pointer_family.rs:46:21 + --> $DIR/pointer_family.rs:47:21 | LL | bar: P::Pointer, | ^^^^^^ type parameter not allowed error[E0109]: type parameters are not allowed on this type - --> $DIR/pointer_family.rs:21:42 + --> $DIR/pointer_family.rs:22:42 | LL | fn new(value: T) -> Self::Pointer; | ^ type parameter not allowed error[E0109]: type parameters are not allowed on this type - --> $DIR/pointer_family.rs:29:42 + --> $DIR/pointer_family.rs:30:42 | LL | fn new(value: T) -> Self::Pointer { | ^ type parameter not allowed error[E0109]: type parameters are not allowed on this type - --> $DIR/pointer_family.rs:39:42 + --> $DIR/pointer_family.rs:40:42 | LL | fn new(value: T) -> Self::Pointer { | ^ type parameter not allowed diff --git a/src/test/ui/rfc1598-generic-associated-types/shadowing.stderr b/src/test/ui/rfc1598-generic-associated-types/shadowing.stderr new file mode 100644 index 0000000000000..f2d626f921c89 --- /dev/null +++ b/src/test/ui/rfc1598-generic-associated-types/shadowing.stderr @@ -0,0 +1,6 @@ +warning: the feature `generic_associated_types` is incomplete and may cause the compiler to crash + --> $DIR/shadowing.rs:11:12 + | +LL | #![feature(generic_associated_types)] + | ^^^^^^^^^^^^^^^^^^^^^^^^ + diff --git a/src/test/ui/rfc1598-generic-associated-types/streaming_iterator.rs b/src/test/ui/rfc1598-generic-associated-types/streaming_iterator.rs index 522ddb5dc135e..aa90886fdfd65 100644 --- a/src/test/ui/rfc1598-generic-associated-types/streaming_iterator.rs +++ b/src/test/ui/rfc1598-generic-associated-types/streaming_iterator.rs @@ -9,8 +9,9 @@ // except according to those terms. #![feature(generic_associated_types)] +//~^ WARNING the feature `generic_associated_types` is incomplete -//FIXME(#44265): "lifetime parameter not allowed on this type" errors will be addressed in a +// FIXME(#44265): "lifetime parameter not allowed on this type" errors will be addressed in a // follow-up PR use std::fmt::Display; diff --git a/src/test/ui/rfc1598-generic-associated-types/streaming_iterator.stderr b/src/test/ui/rfc1598-generic-associated-types/streaming_iterator.stderr index 12e206cbd476a..4aca8d476877b 100644 --- a/src/test/ui/rfc1598-generic-associated-types/streaming_iterator.stderr +++ b/src/test/ui/rfc1598-generic-associated-types/streaming_iterator.stderr @@ -1,29 +1,35 @@ +warning: the feature `generic_associated_types` is incomplete and may cause the compiler to crash + --> $DIR/streaming_iterator.rs:11:12 + | +LL | #![feature(generic_associated_types)] + | ^^^^^^^^^^^^^^^^^^^^^^^^ + error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/streaming_iterator.rs:27:41 + --> $DIR/streaming_iterator.rs:28:41 | LL | bar: ::Item<'static>, | ^^^^^^^ lifetime parameter not allowed error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/streaming_iterator.rs:35:64 + --> $DIR/streaming_iterator.rs:36:64 | LL | fn foo(iter: T) where T: StreamingIterator, for<'a> T::Item<'a>: Display { /* ... */ } | ^^ lifetime parameter not allowed error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/streaming_iterator.rs:21:48 + --> $DIR/streaming_iterator.rs:22:48 | LL | fn next<'a>(&'a self) -> Option>; | ^^ lifetime parameter not allowed error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/streaming_iterator.rs:47:37 + --> $DIR/streaming_iterator.rs:48:37 | LL | type Item<'a> = (usize, I::Item<'a>); | ^^ lifetime parameter not allowed error[E0110]: lifetime parameters are not allowed on this type - --> $DIR/streaming_iterator.rs:49:48 + --> $DIR/streaming_iterator.rs:50:48 | LL | fn next<'a>(&'a self) -> Option> { | ^^ lifetime parameter not allowed diff --git a/src/test/ui/std-uncopyable-atomics.nll.stderr b/src/test/ui/std-uncopyable-atomics.nll.stderr new file mode 100644 index 0000000000000..e6b612fed8588 --- /dev/null +++ b/src/test/ui/std-uncopyable-atomics.nll.stderr @@ -0,0 +1,39 @@ +error[E0507]: cannot move out of borrowed content + --> $DIR/std-uncopyable-atomics.rs:19:13 + | +LL | let x = *&x; //~ ERROR: cannot move out of borrowed content + | ^^^ + | | + | cannot move out of borrowed content + | help: consider removing the `*`: `&x` + +error[E0507]: cannot move out of borrowed content + --> $DIR/std-uncopyable-atomics.rs:21:13 + | +LL | let x = *&x; //~ ERROR: cannot move out of borrowed content + | ^^^ + | | + | cannot move out of borrowed content + | help: consider removing the `*`: `&x` + +error[E0507]: cannot move out of borrowed content + --> $DIR/std-uncopyable-atomics.rs:23:13 + | +LL | let x = *&x; //~ ERROR: cannot move out of borrowed content + | ^^^ + | | + | cannot move out of borrowed content + | help: consider removing the `*`: `&x` + +error[E0507]: cannot move out of borrowed content + --> $DIR/std-uncopyable-atomics.rs:25:13 + | +LL | let x = *&x; //~ ERROR: cannot move out of borrowed content + | ^^^ + | | + | cannot move out of borrowed content + | help: consider removing the `*`: `&x` + +error: aborting due to 4 previous errors + +For more information about this error, try `rustc --explain E0507`. diff --git a/src/test/ui/suggestions/dont-suggest-ref/duplicate-suggestions.rs b/src/test/ui/suggestions/dont-suggest-ref/duplicate-suggestions.rs new file mode 100644 index 0000000000000..dc0186e3f26bf --- /dev/null +++ b/src/test/ui/suggestions/dont-suggest-ref/duplicate-suggestions.rs @@ -0,0 +1,162 @@ +// Copyright 2018 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 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +#![feature(nll)] + +#[derive(Clone)] +enum Either { + One(X), + Two(X), +} + +#[derive(Clone)] +struct X(Y); + +#[derive(Clone)] +struct Y; + + +pub fn main() { + let e = Either::One(X(Y)); + let mut em = Either::One(X(Y)); + + let r = &e; + let rm = &mut Either::One(X(Y)); + + let x = X(Y); + let mut xm = X(Y); + + let s = &x; + let sm = &mut X(Y); + + let ve = vec![Either::One(X(Y))]; + + let vr = &ve; + let vrm = &mut vec![Either::One(X(Y))]; + + let vx = vec![X(Y)]; + + let vs = &vx; + let vsm = &mut vec![X(Y)]; + + // -------- test for duplicate suggestions -------- + + let &(X(_t), X(_u)) = &(x.clone(), x.clone()); + //~^ ERROR cannot move + //~| HELP consider removing the `&` + //~| SUGGESTION (X(_t), X(_u)) + if let &(Either::One(_t), Either::Two(_u)) = &(e.clone(), e.clone()) { } + //~^ ERROR cannot move + //~| HELP consider removing the `&` + //~| SUGGESTION (Either::One(_t), Either::Two(_u)) + while let &(Either::One(_t), Either::Two(_u)) = &(e.clone(), e.clone()) { } + //~^ ERROR cannot move + //~| HELP consider removing the `&` + //~| SUGGESTION (Either::One(_t), Either::Two(_u)) + match &(e.clone(), e.clone()) { + //~^ ERROR cannot move + &(Either::One(_t), Either::Two(_u)) => (), + //~^ HELP consider removing the `&` + //~| SUGGESTION (Either::One(_t), Either::Two(_u)) + &(Either::Two(_t), Either::One(_u)) => (), + //~^ HELP consider removing the `&` + //~| SUGGESTION (Either::Two(_t), Either::One(_u)) + _ => (), + } + match &(e.clone(), e.clone()) { + //~^ ERROR cannot move + &(Either::One(_t), Either::Two(_u)) + //~^ HELP consider removing the `&` + //~| SUGGESTION (Either::One(_t), Either::Two(_u)) + | &(Either::Two(_t), Either::One(_u)) => (), + // FIXME: would really like a suggestion here too + _ => (), + } + match &(e.clone(), e.clone()) { + //~^ ERROR cannot move + &(Either::One(_t), Either::Two(_u)) => (), + //~^ HELP consider removing the `&` + //~| SUGGESTION (Either::One(_t), Either::Two(_u)) + &(Either::Two(ref _t), Either::One(ref _u)) => (), + _ => (), + } + match &(e.clone(), e.clone()) { + //~^ ERROR cannot move + &(Either::One(_t), Either::Two(_u)) => (), + //~^ HELP consider removing the `&` + //~| SUGGESTION (Either::One(_t), Either::Two(_u)) + (Either::Two(_t), Either::One(_u)) => (), + _ => (), + } + fn f5(&(X(_t), X(_u)): &(X, X)) { } + //~^ ERROR cannot move + //~| HELP consider removing the `&` + //~| SUGGESTION (X(_t), X(_u)) + + let &mut (X(_t), X(_u)) = &mut (xm.clone(), xm.clone()); + //~^ ERROR cannot move + //~| HELP consider removing the `&mut` + //~| SUGGESTION (X(_t), X(_u)) + if let &mut (Either::One(_t), Either::Two(_u)) = &mut (em.clone(), em.clone()) { } + //~^ ERROR cannot move + //~| HELP consider removing the `&mut` + //~| SUGGESTION (Either::One(_t), Either::Two(_u)) + while let &mut (Either::One(_t), Either::Two(_u)) = &mut (em.clone(), em.clone()) { } + //~^ ERROR cannot move + //~| HELP consider removing the `&mut` + //~| SUGGESTION (Either::One(_t), Either::Two(_u)) + match &mut (em.clone(), em.clone()) { + //~^ ERROR cannot move + &mut (Either::One(_t), Either::Two(_u)) => (), + //~^ HELP consider removing the `&mut` + //~| SUGGESTION (Either::One(_t), Either::Two(_u)) + &mut (Either::Two(_t), Either::One(_u)) => (), + //~^ HELP consider removing the `&mut` + //~| SUGGESTION (Either::Two(_t), Either::One(_u)) + _ => (), + } + match &mut (em.clone(), em.clone()) { + //~^ ERROR cannot move + &mut (Either::One(_t), Either::Two(_u)) + //~^ HELP consider removing the `&mut` + //~| SUGGESTION (Either::One(_t), Either::Two(_u)) + | &mut (Either::Two(_t), Either::One(_u)) => (), + // FIXME: would really like a suggestion here too + _ => (), + } + match &mut (em.clone(), em.clone()) { + //~^ ERROR cannot move + &mut (Either::One(_t), Either::Two(_u)) => (), + //~^ HELP consider removing the `&mut` + //~| SUGGESTION (Either::One(_t), Either::Two(_u)) + &mut (Either::Two(ref _t), Either::One(ref _u)) => (), + _ => (), + } + match &mut (em.clone(), em.clone()) { + //~^ ERROR cannot move + &mut (Either::One(_t), Either::Two(_u)) => (), + //~^ HELP consider removing the `&mut` + //~| SUGGESTION (Either::One(_t), Either::Two(_u)) + &mut (Either::Two(ref mut _t), Either::One(ref mut _u)) => (), + _ => (), + } + match &mut (em.clone(), em.clone()) { + //~^ ERROR cannot move + &mut (Either::One(_t), Either::Two(_u)) => (), + //~^ HELP consider removing the `&mut` + //~| SUGGESTION (Either::One(_t), Either::Two(_u)) + (Either::Two(_t), Either::One(_u)) => (), + _ => (), + } + fn f6(&mut (X(_t), X(_u)): &mut (X, X)) { } + //~^ ERROR cannot move + //~| HELP consider removing the `&mut` + //~| SUGGESTION (X(_t), X(_u)) +} diff --git a/src/test/ui/suggestions/dont-suggest-ref/duplicate-suggestions.stderr b/src/test/ui/suggestions/dont-suggest-ref/duplicate-suggestions.stderr new file mode 100644 index 0000000000000..bb3688411f718 --- /dev/null +++ b/src/test/ui/suggestions/dont-suggest-ref/duplicate-suggestions.stderr @@ -0,0 +1,328 @@ +error[E0507]: cannot move out of borrowed content + --> $DIR/duplicate-suggestions.rs:51:27 + | +LL | let &(X(_t), X(_u)) = &(x.clone(), x.clone()); + | --------------- ^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content + | | | | + | | | ...and here + | | data moved here + | help: consider removing the `&`: `(X(_t), X(_u))` + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/duplicate-suggestions.rs:51:13 + | +LL | let &(X(_t), X(_u)) = &(x.clone(), x.clone()); + | ^^ ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/duplicate-suggestions.rs:55:50 + | +LL | if let &(Either::One(_t), Either::Two(_u)) = &(e.clone(), e.clone()) { } + | ----------------------------------- ^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content + | | | | + | | | ...and here + | | data moved here + | help: consider removing the `&`: `(Either::One(_t), Either::Two(_u))` + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/duplicate-suggestions.rs:55:26 + | +LL | if let &(Either::One(_t), Either::Two(_u)) = &(e.clone(), e.clone()) { } + | ^^ ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/duplicate-suggestions.rs:59:53 + | +LL | while let &(Either::One(_t), Either::Two(_u)) = &(e.clone(), e.clone()) { } + | ----------------------------------- ^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content + | | | | + | | | ...and here + | | data moved here + | help: consider removing the `&`: `(Either::One(_t), Either::Two(_u))` + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/duplicate-suggestions.rs:59:29 + | +LL | while let &(Either::One(_t), Either::Two(_u)) = &(e.clone(), e.clone()) { } + | ^^ ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/duplicate-suggestions.rs:63:11 + | +LL | match &(e.clone(), e.clone()) { + | ^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &(Either::One(_t), Either::Two(_u)) => (), + | -- -- ...and here + | | + | data moved here +... +LL | &(Either::Two(_t), Either::One(_u)) => (), + | -- ...and here -- ...and here + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/duplicate-suggestions.rs:65:23 + | +LL | &(Either::One(_t), Either::Two(_u)) => (), + | ^^ ^^ +... +LL | &(Either::Two(_t), Either::One(_u)) => (), + | ^^ ^^ +help: consider removing the `&` + | +LL | (Either::One(_t), Either::Two(_u)) => (), + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +help: consider removing the `&` + | +LL | (Either::Two(_t), Either::One(_u)) => (), + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/duplicate-suggestions.rs:73:11 + | +LL | match &(e.clone(), e.clone()) { + | ^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &(Either::One(_t), Either::Two(_u)) + | ----------------------------------- + | | | | + | | | ...and here + | | data moved here + | help: consider removing the `&`: `(Either::One(_t), Either::Two(_u))` + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/duplicate-suggestions.rs:75:23 + | +LL | &(Either::One(_t), Either::Two(_u)) + | ^^ ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/duplicate-suggestions.rs:82:11 + | +LL | match &(e.clone(), e.clone()) { + | ^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &(Either::One(_t), Either::Two(_u)) => (), + | ----------------------------------- + | | | | + | | | ...and here + | | data moved here + | help: consider removing the `&`: `(Either::One(_t), Either::Two(_u))` + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/duplicate-suggestions.rs:84:23 + | +LL | &(Either::One(_t), Either::Two(_u)) => (), + | ^^ ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/duplicate-suggestions.rs:90:11 + | +LL | match &(e.clone(), e.clone()) { + | ^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &(Either::One(_t), Either::Two(_u)) => (), + | ----------------------------------- + | | | | + | | | ...and here + | | data moved here + | help: consider removing the `&`: `(Either::One(_t), Either::Two(_u))` + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/duplicate-suggestions.rs:92:23 + | +LL | &(Either::One(_t), Either::Two(_u)) => (), + | ^^ ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/duplicate-suggestions.rs:103:31 + | +LL | let &mut (X(_t), X(_u)) = &mut (xm.clone(), xm.clone()); + | ------------------- ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content + | | | | + | | | ...and here + | | data moved here + | help: consider removing the `&mut`: `(X(_t), X(_u))` + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/duplicate-suggestions.rs:103:17 + | +LL | let &mut (X(_t), X(_u)) = &mut (xm.clone(), xm.clone()); + | ^^ ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/duplicate-suggestions.rs:107:54 + | +LL | if let &mut (Either::One(_t), Either::Two(_u)) = &mut (em.clone(), em.clone()) { } + | --------------------------------------- ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content + | | | | + | | | ...and here + | | data moved here + | help: consider removing the `&mut`: `(Either::One(_t), Either::Two(_u))` + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/duplicate-suggestions.rs:107:30 + | +LL | if let &mut (Either::One(_t), Either::Two(_u)) = &mut (em.clone(), em.clone()) { } + | ^^ ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/duplicate-suggestions.rs:111:57 + | +LL | while let &mut (Either::One(_t), Either::Two(_u)) = &mut (em.clone(), em.clone()) { } + | --------------------------------------- ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content + | | | | + | | | ...and here + | | data moved here + | help: consider removing the `&mut`: `(Either::One(_t), Either::Two(_u))` + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/duplicate-suggestions.rs:111:33 + | +LL | while let &mut (Either::One(_t), Either::Two(_u)) = &mut (em.clone(), em.clone()) { } + | ^^ ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/duplicate-suggestions.rs:115:11 + | +LL | match &mut (em.clone(), em.clone()) { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &mut (Either::One(_t), Either::Two(_u)) => (), + | -- -- ...and here + | | + | data moved here +... +LL | &mut (Either::Two(_t), Either::One(_u)) => (), + | -- ...and here -- ...and here + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/duplicate-suggestions.rs:117:27 + | +LL | &mut (Either::One(_t), Either::Two(_u)) => (), + | ^^ ^^ +... +LL | &mut (Either::Two(_t), Either::One(_u)) => (), + | ^^ ^^ +help: consider removing the `&mut` + | +LL | (Either::One(_t), Either::Two(_u)) => (), + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +help: consider removing the `&mut` + | +LL | (Either::Two(_t), Either::One(_u)) => (), + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/duplicate-suggestions.rs:125:11 + | +LL | match &mut (em.clone(), em.clone()) { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &mut (Either::One(_t), Either::Two(_u)) + | --------------------------------------- + | | | | + | | | ...and here + | | data moved here + | help: consider removing the `&mut`: `(Either::One(_t), Either::Two(_u))` + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/duplicate-suggestions.rs:127:27 + | +LL | &mut (Either::One(_t), Either::Two(_u)) + | ^^ ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/duplicate-suggestions.rs:134:11 + | +LL | match &mut (em.clone(), em.clone()) { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &mut (Either::One(_t), Either::Two(_u)) => (), + | --------------------------------------- + | | | | + | | | ...and here + | | data moved here + | help: consider removing the `&mut`: `(Either::One(_t), Either::Two(_u))` + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/duplicate-suggestions.rs:136:27 + | +LL | &mut (Either::One(_t), Either::Two(_u)) => (), + | ^^ ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/duplicate-suggestions.rs:142:11 + | +LL | match &mut (em.clone(), em.clone()) { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &mut (Either::One(_t), Either::Two(_u)) => (), + | --------------------------------------- + | | | | + | | | ...and here + | | data moved here + | help: consider removing the `&mut`: `(Either::One(_t), Either::Two(_u))` + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/duplicate-suggestions.rs:144:27 + | +LL | &mut (Either::One(_t), Either::Two(_u)) => (), + | ^^ ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/duplicate-suggestions.rs:150:11 + | +LL | match &mut (em.clone(), em.clone()) { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &mut (Either::One(_t), Either::Two(_u)) => (), + | --------------------------------------- + | | | | + | | | ...and here + | | data moved here + | help: consider removing the `&mut`: `(Either::One(_t), Either::Two(_u))` + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/duplicate-suggestions.rs:152:27 + | +LL | &mut (Either::One(_t), Either::Two(_u)) => (), + | ^^ ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/duplicate-suggestions.rs:98:11 + | +LL | fn f5(&(X(_t), X(_u)): &(X, X)) { } + | ^^^^--^^^^^--^^ + | | | | + | | | ...and here + | | data moved here + | cannot move out of borrowed content + | help: consider removing the `&`: `(X(_t), X(_u))` + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/duplicate-suggestions.rs:98:15 + | +LL | fn f5(&(X(_t), X(_u)): &(X, X)) { } + | ^^ ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/duplicate-suggestions.rs:158:11 + | +LL | fn f6(&mut (X(_t), X(_u)): &mut (X, X)) { } + | ^^^^^^^^--^^^^^--^^ + | | | | + | | | ...and here + | | data moved here + | cannot move out of borrowed content + | help: consider removing the `&mut`: `(X(_t), X(_u))` + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/duplicate-suggestions.rs:158:19 + | +LL | fn f6(&mut (X(_t), X(_u)): &mut (X, X)) { } + | ^^ ^^ + +error: aborting due to 17 previous errors + +For more information about this error, try `rustc --explain E0507`. diff --git a/src/test/ui/suggestions/dont-suggest-ref/move-into-closure.rs b/src/test/ui/suggestions/dont-suggest-ref/move-into-closure.rs new file mode 100644 index 0000000000000..8cc847e693fa7 --- /dev/null +++ b/src/test/ui/suggestions/dont-suggest-ref/move-into-closure.rs @@ -0,0 +1,171 @@ +// Copyright 2018 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 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +#![feature(nll)] + +#[derive(Clone)] +enum Either { + One(X), + Two(X), +} + +#[derive(Clone)] +struct X(Y); + +#[derive(Clone)] +struct Y; + +fn consume_fn(_f: F) { } + +fn consume_fnmut(_f: F) { } + +pub fn main() { } + +fn move_into_fn() { + let e = Either::One(X(Y)); + let mut em = Either::One(X(Y)); + + let x = X(Y); + + // -------- move into Fn -------- + + consume_fn(|| { + let X(_t) = x; + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &x + if let Either::One(_t) = e { } + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &e + while let Either::One(_t) = e { } + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &e + match e { + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &e + Either::One(_t) + | Either::Two(_t) => (), + } + match e { + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &e + Either::One(_t) => (), + Either::Two(ref _t) => (), + // FIXME: should suggest removing `ref` too + } + + let X(mut _t) = x; + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &x + if let Either::One(mut _t) = em { } + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &em + while let Either::One(mut _t) = em { } + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &em + match em { + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &em + Either::One(mut _t) + | Either::Two(mut _t) => (), + } + match em { + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &em + Either::One(mut _t) => (), + Either::Two(ref _t) => (), + // FIXME: should suggest removing `ref` too + } + }); +} + +fn move_into_fnmut() { + let e = Either::One(X(Y)); + let mut em = Either::One(X(Y)); + + let x = X(Y); + + // -------- move into FnMut -------- + + consume_fnmut(|| { + let X(_t) = x; + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &x + if let Either::One(_t) = e { } + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &e + while let Either::One(_t) = e { } + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &e + match e { + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &e + Either::One(_t) + | Either::Two(_t) => (), + } + match e { + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &e + Either::One(_t) => (), + Either::Two(ref _t) => (), + // FIXME: should suggest removing `ref` too + } + + let X(mut _t) = x; + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &x + if let Either::One(mut _t) = em { } + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &em + while let Either::One(mut _t) = em { } + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &em + match em { + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &em + Either::One(mut _t) + | Either::Two(mut _t) => (), + } + match em { + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &em + Either::One(mut _t) => (), + Either::Two(ref _t) => (), + // FIXME: should suggest removing `ref` too + } + match em { + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &em + Either::One(mut _t) => (), + Either::Two(ref mut _t) => (), + // FIXME: should suggest removing `ref` too + } + }); +} diff --git a/src/test/ui/suggestions/dont-suggest-ref/move-into-closure.stderr b/src/test/ui/suggestions/dont-suggest-ref/move-into-closure.stderr new file mode 100644 index 0000000000000..228ec5afce635 --- /dev/null +++ b/src/test/ui/suggestions/dont-suggest-ref/move-into-closure.stderr @@ -0,0 +1,420 @@ +error[E0507]: cannot move out of captured variable in an `Fn` closure + --> $DIR/move-into-closure.rs:40:21 + | +LL | let x = X(Y); + | - captured outer variable +... +LL | let X(_t) = x; + | -- ^ + | | | + | | cannot move out of captured variable in an `Fn` closure + | | help: consider borrowing here: `&x` + | data moved here + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:40:15 + | +LL | let X(_t) = x; + | ^^ + +error[E0507]: cannot move out of captured variable in an `Fn` closure + --> $DIR/move-into-closure.rs:44:34 + | +LL | let e = Either::One(X(Y)); + | - captured outer variable +... +LL | if let Either::One(_t) = e { } + | -- ^ + | | | + | | cannot move out of captured variable in an `Fn` closure + | | help: consider borrowing here: `&e` + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:44:28 + | +LL | if let Either::One(_t) = e { } + | ^^ + +error[E0507]: cannot move out of captured variable in an `Fn` closure + --> $DIR/move-into-closure.rs:48:37 + | +LL | let e = Either::One(X(Y)); + | - captured outer variable +... +LL | while let Either::One(_t) = e { } + | -- ^ + | | | + | | cannot move out of captured variable in an `Fn` closure + | | help: consider borrowing here: `&e` + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:48:31 + | +LL | while let Either::One(_t) = e { } + | ^^ + +error[E0507]: cannot move out of captured variable in an `Fn` closure + --> $DIR/move-into-closure.rs:52:15 + | +LL | let e = Either::One(X(Y)); + | - captured outer variable +... +LL | match e { + | ^ + | | + | cannot move out of captured variable in an `Fn` closure + | help: consider borrowing here: `&e` +... +LL | Either::One(_t) + | -- data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:56:25 + | +LL | Either::One(_t) + | ^^ + +error[E0507]: cannot move out of captured variable in an `Fn` closure + --> $DIR/move-into-closure.rs:59:15 + | +LL | let e = Either::One(X(Y)); + | - captured outer variable +... +LL | match e { + | ^ + | | + | cannot move out of captured variable in an `Fn` closure + | help: consider borrowing here: `&e` +... +LL | Either::One(_t) => (), + | -- data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:63:25 + | +LL | Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of captured variable in an `Fn` closure + --> $DIR/move-into-closure.rs:68:25 + | +LL | let x = X(Y); + | - captured outer variable +... +LL | let X(mut _t) = x; + | ------ ^ + | | | + | | cannot move out of captured variable in an `Fn` closure + | | help: consider borrowing here: `&x` + | data moved here + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:68:15 + | +LL | let X(mut _t) = x; + | ^^^^^^ + +error[E0507]: cannot move out of captured variable in an `Fn` closure + --> $DIR/move-into-closure.rs:72:38 + | +LL | let mut em = Either::One(X(Y)); + | ------ captured outer variable +... +LL | if let Either::One(mut _t) = em { } + | ------ ^^ + | | | + | | cannot move out of captured variable in an `Fn` closure + | | help: consider borrowing here: `&em` + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:72:28 + | +LL | if let Either::One(mut _t) = em { } + | ^^^^^^ + +error[E0507]: cannot move out of captured variable in an `Fn` closure + --> $DIR/move-into-closure.rs:76:41 + | +LL | let mut em = Either::One(X(Y)); + | ------ captured outer variable +... +LL | while let Either::One(mut _t) = em { } + | ------ ^^ + | | | + | | cannot move out of captured variable in an `Fn` closure + | | help: consider borrowing here: `&em` + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:76:31 + | +LL | while let Either::One(mut _t) = em { } + | ^^^^^^ + +error[E0507]: cannot move out of captured variable in an `Fn` closure + --> $DIR/move-into-closure.rs:80:15 + | +LL | let mut em = Either::One(X(Y)); + | ------ captured outer variable +... +LL | match em { + | ^^ + | | + | cannot move out of captured variable in an `Fn` closure + | help: consider borrowing here: `&em` +... +LL | Either::One(mut _t) + | ------ data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:84:25 + | +LL | Either::One(mut _t) + | ^^^^^^ + +error[E0507]: cannot move out of captured variable in an `Fn` closure + --> $DIR/move-into-closure.rs:87:15 + | +LL | let mut em = Either::One(X(Y)); + | ------ captured outer variable +... +LL | match em { + | ^^ + | | + | cannot move out of captured variable in an `Fn` closure + | help: consider borrowing here: `&em` +... +LL | Either::One(mut _t) => (), + | ------ data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:91:25 + | +LL | Either::One(mut _t) => (), + | ^^^^^^ + +error[E0507]: cannot move out of captured variable in an `FnMut` closure + --> $DIR/move-into-closure.rs:107:21 + | +LL | let x = X(Y); + | - captured outer variable +... +LL | let X(_t) = x; + | -- ^ + | | | + | | cannot move out of captured variable in an `FnMut` closure + | | help: consider borrowing here: `&x` + | data moved here + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:107:15 + | +LL | let X(_t) = x; + | ^^ + +error[E0507]: cannot move out of captured variable in an `FnMut` closure + --> $DIR/move-into-closure.rs:111:34 + | +LL | let e = Either::One(X(Y)); + | - captured outer variable +... +LL | if let Either::One(_t) = e { } + | -- ^ + | | | + | | cannot move out of captured variable in an `FnMut` closure + | | help: consider borrowing here: `&e` + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:111:28 + | +LL | if let Either::One(_t) = e { } + | ^^ + +error[E0507]: cannot move out of captured variable in an `FnMut` closure + --> $DIR/move-into-closure.rs:115:37 + | +LL | let e = Either::One(X(Y)); + | - captured outer variable +... +LL | while let Either::One(_t) = e { } + | -- ^ + | | | + | | cannot move out of captured variable in an `FnMut` closure + | | help: consider borrowing here: `&e` + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:115:31 + | +LL | while let Either::One(_t) = e { } + | ^^ + +error[E0507]: cannot move out of captured variable in an `FnMut` closure + --> $DIR/move-into-closure.rs:119:15 + | +LL | let e = Either::One(X(Y)); + | - captured outer variable +... +LL | match e { + | ^ + | | + | cannot move out of captured variable in an `FnMut` closure + | help: consider borrowing here: `&e` +... +LL | Either::One(_t) + | -- data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:123:25 + | +LL | Either::One(_t) + | ^^ + +error[E0507]: cannot move out of captured variable in an `FnMut` closure + --> $DIR/move-into-closure.rs:126:15 + | +LL | let e = Either::One(X(Y)); + | - captured outer variable +... +LL | match e { + | ^ + | | + | cannot move out of captured variable in an `FnMut` closure + | help: consider borrowing here: `&e` +... +LL | Either::One(_t) => (), + | -- data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:130:25 + | +LL | Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of captured variable in an `FnMut` closure + --> $DIR/move-into-closure.rs:135:25 + | +LL | let x = X(Y); + | - captured outer variable +... +LL | let X(mut _t) = x; + | ------ ^ + | | | + | | cannot move out of captured variable in an `FnMut` closure + | | help: consider borrowing here: `&x` + | data moved here + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:135:15 + | +LL | let X(mut _t) = x; + | ^^^^^^ + +error[E0507]: cannot move out of captured variable in an `FnMut` closure + --> $DIR/move-into-closure.rs:139:38 + | +LL | let mut em = Either::One(X(Y)); + | ------ captured outer variable +... +LL | if let Either::One(mut _t) = em { } + | ------ ^^ + | | | + | | cannot move out of captured variable in an `FnMut` closure + | | help: consider borrowing here: `&em` + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:139:28 + | +LL | if let Either::One(mut _t) = em { } + | ^^^^^^ + +error[E0507]: cannot move out of captured variable in an `FnMut` closure + --> $DIR/move-into-closure.rs:143:41 + | +LL | let mut em = Either::One(X(Y)); + | ------ captured outer variable +... +LL | while let Either::One(mut _t) = em { } + | ------ ^^ + | | | + | | cannot move out of captured variable in an `FnMut` closure + | | help: consider borrowing here: `&em` + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:143:31 + | +LL | while let Either::One(mut _t) = em { } + | ^^^^^^ + +error[E0507]: cannot move out of captured variable in an `FnMut` closure + --> $DIR/move-into-closure.rs:147:15 + | +LL | let mut em = Either::One(X(Y)); + | ------ captured outer variable +... +LL | match em { + | ^^ + | | + | cannot move out of captured variable in an `FnMut` closure + | help: consider borrowing here: `&em` +... +LL | Either::One(mut _t) + | ------ data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:151:25 + | +LL | Either::One(mut _t) + | ^^^^^^ + +error[E0507]: cannot move out of captured variable in an `FnMut` closure + --> $DIR/move-into-closure.rs:154:15 + | +LL | let mut em = Either::One(X(Y)); + | ------ captured outer variable +... +LL | match em { + | ^^ + | | + | cannot move out of captured variable in an `FnMut` closure + | help: consider borrowing here: `&em` +... +LL | Either::One(mut _t) => (), + | ------ data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:158:25 + | +LL | Either::One(mut _t) => (), + | ^^^^^^ + +error[E0507]: cannot move out of captured variable in an `FnMut` closure + --> $DIR/move-into-closure.rs:162:15 + | +LL | let mut em = Either::One(X(Y)); + | ------ captured outer variable +... +LL | match em { + | ^^ + | | + | cannot move out of captured variable in an `FnMut` closure + | help: consider borrowing here: `&em` +... +LL | Either::One(mut _t) => (), + | ------ data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/move-into-closure.rs:166:25 + | +LL | Either::One(mut _t) => (), + | ^^^^^^ + +error: aborting due to 21 previous errors + +For more information about this error, try `rustc --explain E0507`. diff --git a/src/test/ui/suggestions/dont-suggest-ref/simple.rs b/src/test/ui/suggestions/dont-suggest-ref/simple.rs new file mode 100644 index 0000000000000..474e88c4d5395 --- /dev/null +++ b/src/test/ui/suggestions/dont-suggest-ref/simple.rs @@ -0,0 +1,376 @@ +// Copyright 2018 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 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +#![feature(nll)] + +#[derive(Clone)] +enum Either { + One(X), + Two(X), +} + +#[derive(Clone)] +struct X(Y); + +#[derive(Clone)] +struct Y; + +pub fn main() { + let e = Either::One(X(Y)); + let mut em = Either::One(X(Y)); + + let r = &e; + let rm = &mut Either::One(X(Y)); + + let x = X(Y); + let mut xm = X(Y); + + let s = &x; + let sm = &mut X(Y); + + let ve = vec![Either::One(X(Y))]; + + let vr = &ve; + let vrm = &mut vec![Either::One(X(Y))]; + + let vx = vec![X(Y)]; + + let vs = &vx; + let vsm = &mut vec![X(Y)]; + + // -------- move from Either/X place -------- + + let X(_t) = *s; + //~^ ERROR cannot move + //~| HELP consider removing the `*` + //~| SUGGESTION s + if let Either::One(_t) = *r { } + //~^ ERROR cannot move + //~| HELP consider removing the `*` + //~| SUGGESTION r + while let Either::One(_t) = *r { } + //~^ ERROR cannot move + //~| HELP consider removing the `*` + //~| SUGGESTION r + match *r { + //~^ ERROR cannot move + //~| HELP consider removing the `*` + //~| SUGGESTION r + Either::One(_t) + | Either::Two(_t) => (), + } + match *r { + //~^ ERROR cannot move + //~| HELP consider removing the `*` + //~| SUGGESTION r + Either::One(_t) => (), + Either::Two(ref _t) => (), + // FIXME: should suggest removing `ref` too + } + + let X(_t) = *sm; + //~^ ERROR cannot move + //~| HELP consider removing the `*` + //~| SUGGESTION sm + if let Either::One(_t) = *rm { } + //~^ ERROR cannot move + //~| HELP consider removing the `*` + //~| SUGGESTION rm + while let Either::One(_t) = *rm { } + //~^ ERROR cannot move + //~| HELP consider removing the `*` + //~| SUGGESTION rm + match *rm { + //~^ ERROR cannot move + //~| HELP consider removing the `*` + //~| SUGGESTION rm + Either::One(_t) + | Either::Two(_t) => (), + } + match *rm { + //~^ ERROR cannot move + //~| HELP consider removing the `*` + //~| SUGGESTION rm + Either::One(_t) => (), + Either::Two(ref _t) => (), + // FIXME: should suggest removing `ref` too + } + match *rm { + //~^ ERROR cannot move + //~| HELP consider removing the `*` + //~| SUGGESTION rm + Either::One(_t) => (), + Either::Two(ref mut _t) => (), + // FIXME: should suggest removing `ref` too + } + + let X(_t) = vs[0]; + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &vs[0] + if let Either::One(_t) = vr[0] { } + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &vr[0] + while let Either::One(_t) = vr[0] { } + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &vr[0] + match vr[0] { + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &vr[0] + Either::One(_t) + | Either::Two(_t) => (), + } + match vr[0] { + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &vr[0] + Either::One(_t) => (), + Either::Two(ref _t) => (), + // FIXME: should suggest removing `ref` too + } + + let X(_t) = vsm[0]; + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &vsm[0] + if let Either::One(_t) = vrm[0] { } + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &vrm[0] + while let Either::One(_t) = vrm[0] { } + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &vrm[0] + match vrm[0] { + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &vrm[0] + Either::One(_t) + | Either::Two(_t) => (), + } + match vrm[0] { + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &vrm[0] + Either::One(_t) => (), + Either::Two(ref _t) => (), + // FIXME: should suggest removing `ref` too + } + match vrm[0] { + //~^ ERROR cannot move + //~| HELP consider borrowing here + //~| SUGGESTION &vrm[0] + Either::One(_t) => (), + Either::Two(ref mut _t) => (), + // FIXME: should suggest removing `ref` too + } + + // -------- move from &Either/&X place -------- + + let &X(_t) = s; + //~^ ERROR cannot move + //~| HELP consider removing the `&` + //~| SUGGESTION X(_t) + if let &Either::One(_t) = r { } + //~^ ERROR cannot move + //~| HELP consider removing the `&` + //~| SUGGESTION Either::One(_t) + while let &Either::One(_t) = r { } + //~^ ERROR cannot move + //~| HELP consider removing the `&` + //~| SUGGESTION Either::One(_t) + match r { + //~^ ERROR cannot move + &Either::One(_t) + //~^ HELP consider removing the `&` + //~| SUGGESTION Either::One(_t) + | &Either::Two(_t) => (), + // FIXME: would really like a suggestion here too + } + match r { + //~^ ERROR cannot move + &Either::One(_t) => (), + //~^ HELP consider removing the `&` + //~| SUGGESTION Either::One(_t) + &Either::Two(ref _t) => (), + } + match r { + //~^ ERROR cannot move + &Either::One(_t) => (), + //~^ HELP consider removing the `&` + //~| SUGGESTION Either::One(_t) + Either::Two(_t) => (), + } + fn f1(&X(_t): &X) { } + //~^ ERROR cannot move + //~| HELP consider removing the `&` + //~| SUGGESTION X(_t) + + let &mut X(_t) = sm; + //~^ ERROR cannot move + //~| HELP consider removing the `&mut` + //~| SUGGESTION X(_t) + if let &mut Either::One(_t) = rm { } + //~^ ERROR cannot move + //~| HELP consider removing the `&mut` + //~| SUGGESTION Either::One(_t) + while let &mut Either::One(_t) = rm { } + //~^ ERROR cannot move + //~| HELP consider removing the `&mut` + //~| SUGGESTION Either::One(_t) + match rm { + //~^ ERROR cannot move + &mut Either::One(_t) => (), + //~^ HELP consider removing the `&mut` + //~| SUGGESTION Either::One(_t) + &mut Either::Two(_t) => (), + //~^ HELP consider removing the `&mut` + //~| SUGGESTION Either::Two(_t) + } + match rm { + //~^ ERROR cannot move + &mut Either::One(_t) => (), + //~^ HELP consider removing the `&mut` + //~| SUGGESTION Either::One(_t) + &mut Either::Two(ref _t) => (), + } + match rm { + //~^ ERROR cannot move + &mut Either::One(_t) => (), + //~^ HELP consider removing the `&mut` + //~| SUGGESTION Either::One(_t) + &mut Either::Two(ref mut _t) => (), + } + match rm { + //~^ ERROR cannot move + &mut Either::One(_t) => (), + //~^ HELP consider removing the `&mut` + //~| SUGGESTION Either::One(_t) + Either::Two(_t) => (), + } + fn f2(&mut X(_t): &mut X) { } + //~^ ERROR cannot move + //~| HELP consider removing the `&mut` + //~| SUGGESTION X(_t) + + // -------- move from tuple of &Either/&X -------- + + // FIXME: These should have suggestions. + + let (&X(_t),) = (&x.clone(),); + //~^ ERROR cannot move + if let (&Either::One(_t),) = (&e.clone(),) { } + //~^ ERROR cannot move + while let (&Either::One(_t),) = (&e.clone(),) { } + //~^ ERROR cannot move + match (&e.clone(),) { + //~^ ERROR cannot move + (&Either::One(_t),) + | (&Either::Two(_t),) => (), + } + fn f3((&X(_t),): (&X,)) { } + //~^ ERROR cannot move + + let (&mut X(_t),) = (&mut xm.clone(),); + //~^ ERROR cannot move + if let (&mut Either::One(_t),) = (&mut em.clone(),) { } + //~^ ERROR cannot move + while let (&mut Either::One(_t),) = (&mut em.clone(),) { } + //~^ ERROR cannot move + match (&mut em.clone(),) { + //~^ ERROR cannot move + (&mut Either::One(_t),) => (), + (&mut Either::Two(_t),) => (), + } + fn f4((&mut X(_t),): (&mut X,)) { } + //~^ ERROR cannot move + + // -------- move from &Either/&X value -------- + + let &X(_t) = &x; + //~^ ERROR cannot move + //~| HELP consider removing the `&` + //~| SUGGESTION X(_t) + if let &Either::One(_t) = &e { } + //~^ ERROR cannot move + //~| HELP consider removing the `&` + //~| SUGGESTION Either::One(_t) + while let &Either::One(_t) = &e { } + //~^ ERROR cannot move + //~| HELP consider removing the `&` + //~| SUGGESTION Either::One(_t) + match &e { + //~^ ERROR cannot move + &Either::One(_t) + //~^ HELP consider removing the `&` + //~| SUGGESTION Either::One(_t) + | &Either::Two(_t) => (), + // FIXME: would really like a suggestion here too + } + match &e { + //~^ ERROR cannot move + &Either::One(_t) => (), + //~^ HELP consider removing the `&` + //~| SUGGESTION Either::One(_t) + &Either::Two(ref _t) => (), + } + match &e { + //~^ ERROR cannot move + &Either::One(_t) => (), + //~^ HELP consider removing the `&` + //~| SUGGESTION Either::One(_t) + Either::Two(_t) => (), + } + + let &mut X(_t) = &mut xm; + //~^ ERROR cannot move + //~| HELP consider removing the `&mut` + //~| SUGGESTION X(_t) + if let &mut Either::One(_t) = &mut em { } + //~^ ERROR cannot move + //~| HELP consider removing the `&mut` + //~| SUGGESTION Either::One(_t) + while let &mut Either::One(_t) = &mut em { } + //~^ ERROR cannot move + //~| HELP consider removing the `&mut` + //~| SUGGESTION Either::One(_t) + match &mut em { + //~^ ERROR cannot move + &mut Either::One(_t) + //~^ HELP consider removing the `&mut` + //~| SUGGESTION Either::One(_t) + | &mut Either::Two(_t) => (), + // FIXME: would really like a suggestion here too + } + match &mut em { + //~^ ERROR cannot move + &mut Either::One(_t) => (), + //~^ HELP consider removing the `&mut` + //~| SUGGESTION Either::One(_t) + &mut Either::Two(ref _t) => (), + } + match &mut em { + //~^ ERROR cannot move + &mut Either::One(_t) => (), + //~^ HELP consider removing the `&mut` + //~| SUGGESTION Either::One(_t) + &mut Either::Two(ref mut _t) => (), + } + match &mut em { + //~^ ERROR cannot move + &mut Either::One(_t) => (), + //~^ HELP consider removing the `&mut` + //~| SUGGESTION Either::One(_t) + Either::Two(_t) => (), + } +} diff --git a/src/test/ui/suggestions/dont-suggest-ref/simple.stderr b/src/test/ui/suggestions/dont-suggest-ref/simple.stderr new file mode 100644 index 0000000000000..d7a32dbfcc643 --- /dev/null +++ b/src/test/ui/suggestions/dont-suggest-ref/simple.stderr @@ -0,0 +1,998 @@ +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:50:17 + | +LL | let X(_t) = *s; + | -- ^^ + | | | + | | cannot move out of borrowed content + | | help: consider removing the `*`: `s` + | data moved here + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/simple.rs:50:11 + | +LL | let X(_t) = *s; + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:54:30 + | +LL | if let Either::One(_t) = *r { } + | -- ^^ + | | | + | | cannot move out of borrowed content + | | help: consider removing the `*`: `r` + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:54:24 + | +LL | if let Either::One(_t) = *r { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:58:33 + | +LL | while let Either::One(_t) = *r { } + | -- ^^ + | | | + | | cannot move out of borrowed content + | | help: consider removing the `*`: `r` + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:58:27 + | +LL | while let Either::One(_t) = *r { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:62:11 + | +LL | match *r { + | ^^ + | | + | cannot move out of borrowed content + | help: consider removing the `*`: `r` +... +LL | Either::One(_t) + | -- data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:66:21 + | +LL | Either::One(_t) + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:69:11 + | +LL | match *r { + | ^^ + | | + | cannot move out of borrowed content + | help: consider removing the `*`: `r` +... +LL | Either::One(_t) => (), + | -- data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:73:21 + | +LL | Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:78:17 + | +LL | let X(_t) = *sm; + | -- ^^^ + | | | + | | cannot move out of borrowed content + | | help: consider removing the `*`: `sm` + | data moved here + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/simple.rs:78:11 + | +LL | let X(_t) = *sm; + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:82:30 + | +LL | if let Either::One(_t) = *rm { } + | -- ^^^ + | | | + | | cannot move out of borrowed content + | | help: consider removing the `*`: `rm` + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:82:24 + | +LL | if let Either::One(_t) = *rm { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:86:33 + | +LL | while let Either::One(_t) = *rm { } + | -- ^^^ + | | | + | | cannot move out of borrowed content + | | help: consider removing the `*`: `rm` + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:86:27 + | +LL | while let Either::One(_t) = *rm { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:90:11 + | +LL | match *rm { + | ^^^ + | | + | cannot move out of borrowed content + | help: consider removing the `*`: `rm` +... +LL | Either::One(_t) + | -- data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:94:21 + | +LL | Either::One(_t) + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:97:11 + | +LL | match *rm { + | ^^^ + | | + | cannot move out of borrowed content + | help: consider removing the `*`: `rm` +... +LL | Either::One(_t) => (), + | -- data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:101:21 + | +LL | Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:105:11 + | +LL | match *rm { + | ^^^ + | | + | cannot move out of borrowed content + | help: consider removing the `*`: `rm` +... +LL | Either::One(_t) => (), + | -- data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:109:21 + | +LL | Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:114:17 + | +LL | let X(_t) = vs[0]; + | -- ^^^^^ + | | | + | | cannot move out of borrowed content + | | help: consider borrowing here: `&vs[0]` + | data moved here + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/simple.rs:114:11 + | +LL | let X(_t) = vs[0]; + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:118:30 + | +LL | if let Either::One(_t) = vr[0] { } + | -- ^^^^^ + | | | + | | cannot move out of borrowed content + | | help: consider borrowing here: `&vr[0]` + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:118:24 + | +LL | if let Either::One(_t) = vr[0] { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:122:33 + | +LL | while let Either::One(_t) = vr[0] { } + | -- ^^^^^ + | | | + | | cannot move out of borrowed content + | | help: consider borrowing here: `&vr[0]` + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:122:27 + | +LL | while let Either::One(_t) = vr[0] { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:126:11 + | +LL | match vr[0] { + | ^^^^^ + | | + | cannot move out of borrowed content + | help: consider borrowing here: `&vr[0]` +... +LL | Either::One(_t) + | -- data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:130:21 + | +LL | Either::One(_t) + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:133:11 + | +LL | match vr[0] { + | ^^^^^ + | | + | cannot move out of borrowed content + | help: consider borrowing here: `&vr[0]` +... +LL | Either::One(_t) => (), + | -- data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:137:21 + | +LL | Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:142:17 + | +LL | let X(_t) = vsm[0]; + | -- ^^^^^^ + | | | + | | cannot move out of borrowed content + | | help: consider borrowing here: `&vsm[0]` + | data moved here + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/simple.rs:142:11 + | +LL | let X(_t) = vsm[0]; + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:146:30 + | +LL | if let Either::One(_t) = vrm[0] { } + | -- ^^^^^^ + | | | + | | cannot move out of borrowed content + | | help: consider borrowing here: `&vrm[0]` + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:146:24 + | +LL | if let Either::One(_t) = vrm[0] { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:150:33 + | +LL | while let Either::One(_t) = vrm[0] { } + | -- ^^^^^^ + | | | + | | cannot move out of borrowed content + | | help: consider borrowing here: `&vrm[0]` + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:150:27 + | +LL | while let Either::One(_t) = vrm[0] { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:154:11 + | +LL | match vrm[0] { + | ^^^^^^ + | | + | cannot move out of borrowed content + | help: consider borrowing here: `&vrm[0]` +... +LL | Either::One(_t) + | -- data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:158:21 + | +LL | Either::One(_t) + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:161:11 + | +LL | match vrm[0] { + | ^^^^^^ + | | + | cannot move out of borrowed content + | help: consider borrowing here: `&vrm[0]` +... +LL | Either::One(_t) => (), + | -- data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:165:21 + | +LL | Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:169:11 + | +LL | match vrm[0] { + | ^^^^^^ + | | + | cannot move out of borrowed content + | help: consider borrowing here: `&vrm[0]` +... +LL | Either::One(_t) => (), + | -- data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:173:21 + | +LL | Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:180:18 + | +LL | let &X(_t) = s; + | ------ ^ cannot move out of borrowed content + | | | + | | data moved here + | help: consider removing the `&`: `X(_t)` + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/simple.rs:180:12 + | +LL | let &X(_t) = s; + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:184:31 + | +LL | if let &Either::One(_t) = r { } + | ---------------- ^ cannot move out of borrowed content + | | | + | | data moved here + | help: consider removing the `&`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:184:25 + | +LL | if let &Either::One(_t) = r { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:188:34 + | +LL | while let &Either::One(_t) = r { } + | ---------------- ^ cannot move out of borrowed content + | | | + | | data moved here + | help: consider removing the `&`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:188:28 + | +LL | while let &Either::One(_t) = r { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:192:11 + | +LL | match r { + | ^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &Either::One(_t) + | ---------------- + | | | + | | data moved here + | help: consider removing the `&`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:194:22 + | +LL | &Either::One(_t) + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:200:11 + | +LL | match r { + | ^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &Either::One(_t) => (), + | ---------------- + | | | + | | data moved here + | help: consider removing the `&`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:202:22 + | +LL | &Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:207:11 + | +LL | match r { + | ^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &Either::One(_t) => (), + | ---------------- + | | | + | | data moved here + | help: consider removing the `&`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:209:22 + | +LL | &Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:219:22 + | +LL | let &mut X(_t) = sm; + | ---------- ^^ cannot move out of borrowed content + | | | + | | data moved here + | help: consider removing the `&mut`: `X(_t)` + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/simple.rs:219:16 + | +LL | let &mut X(_t) = sm; + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:223:35 + | +LL | if let &mut Either::One(_t) = rm { } + | -------------------- ^^ cannot move out of borrowed content + | | | + | | data moved here + | help: consider removing the `&mut`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:223:29 + | +LL | if let &mut Either::One(_t) = rm { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:227:38 + | +LL | while let &mut Either::One(_t) = rm { } + | -------------------- ^^ cannot move out of borrowed content + | | | + | | data moved here + | help: consider removing the `&mut`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:227:32 + | +LL | while let &mut Either::One(_t) = rm { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:231:11 + | +LL | match rm { + | ^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &mut Either::One(_t) => (), + | -- data moved here +... +LL | &mut Either::Two(_t) => (), + | -- ...and here + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/simple.rs:233:26 + | +LL | &mut Either::One(_t) => (), + | ^^ +... +LL | &mut Either::Two(_t) => (), + | ^^ +help: consider removing the `&mut` + | +LL | Either::One(_t) => (), + | ^^^^^^^^^^^^^^^ +help: consider removing the `&mut` + | +LL | Either::Two(_t) => (), + | ^^^^^^^^^^^^^^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:240:11 + | +LL | match rm { + | ^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &mut Either::One(_t) => (), + | -------------------- + | | | + | | data moved here + | help: consider removing the `&mut`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:242:26 + | +LL | &mut Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:247:11 + | +LL | match rm { + | ^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &mut Either::One(_t) => (), + | -------------------- + | | | + | | data moved here + | help: consider removing the `&mut`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:249:26 + | +LL | &mut Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:254:11 + | +LL | match rm { + | ^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &mut Either::One(_t) => (), + | -------------------- + | | | + | | data moved here + | help: consider removing the `&mut`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:256:26 + | +LL | &mut Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:270:21 + | +LL | let (&X(_t),) = (&x.clone(),); + | -- ^^^^^^^^^^^^^ cannot move out of borrowed content + | | + | data moved here + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/simple.rs:270:13 + | +LL | let (&X(_t),) = (&x.clone(),); + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:272:34 + | +LL | if let (&Either::One(_t),) = (&e.clone(),) { } + | -- ^^^^^^^^^^^^^ cannot move out of borrowed content + | | + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:272:26 + | +LL | if let (&Either::One(_t),) = (&e.clone(),) { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:274:37 + | +LL | while let (&Either::One(_t),) = (&e.clone(),) { } + | -- ^^^^^^^^^^^^^ cannot move out of borrowed content + | | + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:274:29 + | +LL | while let (&Either::One(_t),) = (&e.clone(),) { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:276:11 + | +LL | match (&e.clone(),) { + | ^^^^^^^^^^^^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | (&Either::One(_t),) + | -- data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:278:23 + | +LL | (&Either::One(_t),) + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:284:25 + | +LL | let (&mut X(_t),) = (&mut xm.clone(),); + | -- ^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content + | | + | data moved here + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/simple.rs:284:17 + | +LL | let (&mut X(_t),) = (&mut xm.clone(),); + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:286:38 + | +LL | if let (&mut Either::One(_t),) = (&mut em.clone(),) { } + | -- ^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content + | | + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:286:30 + | +LL | if let (&mut Either::One(_t),) = (&mut em.clone(),) { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:288:41 + | +LL | while let (&mut Either::One(_t),) = (&mut em.clone(),) { } + | -- ^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content + | | + | data moved here + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:288:33 + | +LL | while let (&mut Either::One(_t),) = (&mut em.clone(),) { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:290:11 + | +LL | match (&mut em.clone(),) { + | ^^^^^^^^^^^^^^^^^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | (&mut Either::One(_t),) => (), + | -- data moved here +LL | (&mut Either::Two(_t),) => (), + | -- ...and here + | +note: move occurs because these variables have types that don't implement the `Copy` trait + --> $DIR/simple.rs:292:27 + | +LL | (&mut Either::One(_t),) => (), + | ^^ +LL | (&mut Either::Two(_t),) => (), + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:300:18 + | +LL | let &X(_t) = &x; + | ------ ^^ cannot move out of borrowed content + | | | + | | data moved here + | help: consider removing the `&`: `X(_t)` + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/simple.rs:300:12 + | +LL | let &X(_t) = &x; + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:304:31 + | +LL | if let &Either::One(_t) = &e { } + | ---------------- ^^ cannot move out of borrowed content + | | | + | | data moved here + | help: consider removing the `&`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:304:25 + | +LL | if let &Either::One(_t) = &e { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:308:34 + | +LL | while let &Either::One(_t) = &e { } + | ---------------- ^^ cannot move out of borrowed content + | | | + | | data moved here + | help: consider removing the `&`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:308:28 + | +LL | while let &Either::One(_t) = &e { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:312:11 + | +LL | match &e { + | ^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &Either::One(_t) + | ---------------- + | | | + | | data moved here + | help: consider removing the `&`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:314:22 + | +LL | &Either::One(_t) + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:320:11 + | +LL | match &e { + | ^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &Either::One(_t) => (), + | ---------------- + | | | + | | data moved here + | help: consider removing the `&`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:322:22 + | +LL | &Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:327:11 + | +LL | match &e { + | ^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &Either::One(_t) => (), + | ---------------- + | | | + | | data moved here + | help: consider removing the `&`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:329:22 + | +LL | &Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:335:22 + | +LL | let &mut X(_t) = &mut xm; + | ---------- ^^^^^^^ cannot move out of borrowed content + | | | + | | data moved here + | help: consider removing the `&mut`: `X(_t)` + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/simple.rs:335:16 + | +LL | let &mut X(_t) = &mut xm; + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:339:35 + | +LL | if let &mut Either::One(_t) = &mut em { } + | -------------------- ^^^^^^^ cannot move out of borrowed content + | | | + | | data moved here + | help: consider removing the `&mut`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:339:29 + | +LL | if let &mut Either::One(_t) = &mut em { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:343:38 + | +LL | while let &mut Either::One(_t) = &mut em { } + | -------------------- ^^^^^^^ cannot move out of borrowed content + | | | + | | data moved here + | help: consider removing the `&mut`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:343:32 + | +LL | while let &mut Either::One(_t) = &mut em { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:347:11 + | +LL | match &mut em { + | ^^^^^^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &mut Either::One(_t) + | -------------------- + | | | + | | data moved here + | help: consider removing the `&mut`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:349:26 + | +LL | &mut Either::One(_t) + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:355:11 + | +LL | match &mut em { + | ^^^^^^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &mut Either::One(_t) => (), + | -------------------- + | | | + | | data moved here + | help: consider removing the `&mut`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:357:26 + | +LL | &mut Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:362:11 + | +LL | match &mut em { + | ^^^^^^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &mut Either::One(_t) => (), + | -------------------- + | | | + | | data moved here + | help: consider removing the `&mut`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:364:26 + | +LL | &mut Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:369:11 + | +LL | match &mut em { + | ^^^^^^^ cannot move out of borrowed content +LL | //~^ ERROR cannot move +LL | &mut Either::One(_t) => (), + | -------------------- + | | | + | | data moved here + | help: consider removing the `&mut`: `Either::One(_t)` + | +note: move occurs because `_t` has type `X`, which does not implement the `Copy` trait + --> $DIR/simple.rs:371:26 + | +LL | &mut Either::One(_t) => (), + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:214:11 + | +LL | fn f1(&X(_t): &X) { } + | ^^^--^ + | | | + | | data moved here + | cannot move out of borrowed content + | help: consider removing the `&`: `X(_t)` + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/simple.rs:214:14 + | +LL | fn f1(&X(_t): &X) { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:261:11 + | +LL | fn f2(&mut X(_t): &mut X) { } + | ^^^^^^^--^ + | | | + | | data moved here + | cannot move out of borrowed content + | help: consider removing the `&mut`: `X(_t)` + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/simple.rs:261:18 + | +LL | fn f2(&mut X(_t): &mut X) { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:281:11 + | +LL | fn f3((&X(_t),): (&X,)) { } + | ^^^^--^^^ + | | | + | | data moved here + | cannot move out of borrowed content + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/simple.rs:281:15 + | +LL | fn f3((&X(_t),): (&X,)) { } + | ^^ + +error[E0507]: cannot move out of borrowed content + --> $DIR/simple.rs:295:11 + | +LL | fn f4((&mut X(_t),): (&mut X,)) { } + | ^^^^^^^^--^^^ + | | | + | | data moved here + | cannot move out of borrowed content + | +note: move occurs because `_t` has type `Y`, which does not implement the `Copy` trait + --> $DIR/simple.rs:295:19 + | +LL | fn f4((&mut X(_t),): (&mut X,)) { } + | ^^ + +error: aborting due to 60 previous errors + +For more information about this error, try `rustc --explain E0507`. diff --git a/src/test/ui/token/issue-10636-2.stderr b/src/test/ui/token/issue-10636-2.stderr index 6c0053f2f8597..634191bb5ef4e 100644 --- a/src/test/ui/token/issue-10636-2.stderr +++ b/src/test/ui/token/issue-10636-2.stderr @@ -1,14 +1,11 @@ error: incorrect close delimiter: `}` --> $DIR/issue-10636-2.rs:18:1 | -LL | } //~ ERROR: incorrect close delimiter - | ^ - | -note: unclosed delimiter - --> $DIR/issue-10636-2.rs:15:15 - | LL | option.map(|some| 42; - | ^ + | - unclosed delimiter +... +LL | } //~ ERROR: incorrect close delimiter + | ^ incorrect close delimiter error: expected one of `)`, `,`, `.`, `?`, or an operator, found `;` --> $DIR/issue-10636-2.rs:15:25 diff --git a/src/test/ui/unrestricted-attribute-tokens.rs b/src/test/ui/unrestricted-attribute-tokens.rs new file mode 100644 index 0000000000000..2971b504369b3 --- /dev/null +++ b/src/test/ui/unrestricted-attribute-tokens.rs @@ -0,0 +1,16 @@ +// Copyright 2018 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 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +// compile-pass + +#![feature(custom_attribute, unrestricted_attribute_tokens)] + +#[my_attr(a b c d)] +fn main() {} diff --git a/src/tools/compiletest/src/json.rs b/src/tools/compiletest/src/json.rs index 201a661726e91..58220ba992c7a 100644 --- a/src/tools/compiletest/src/json.rs +++ b/src/tools/compiletest/src/json.rs @@ -82,7 +82,7 @@ pub fn extract_rendered(output: &str, proc_res: &ProcRes) -> String { Err(error) => { proc_res.fatal(Some(&format!( "failed to decode compiler output as json: \ - `{}`\noutput: {}\nline: {}", + `{}`\nline: {}\noutput: {}", error, line, output ))); } @@ -114,7 +114,7 @@ fn parse_line(file_name: &str, line: &str, output: &str, proc_res: &ProcRes) -> Err(error) => { proc_res.fatal(Some(&format!( "failed to decode compiler output as json: \ - `{}`\noutput: {}\nline: {}", + `{}`\nline: {}\noutput: {}", error, line, output ))); } diff --git a/src/tools/tidy/src/unstable_book.rs b/src/tools/tidy/src/unstable_book.rs index 6b573908de902..62296f73f016b 100644 --- a/src/tools/tidy/src/unstable_book.rs +++ b/src/tools/tidy/src/unstable_book.rs @@ -60,6 +60,7 @@ pub fn collect_unstable_book_section_file_names(dir: &path::Path) -> BTreeSet