diff --git a/src/bootstrap/bin/rustdoc.rs b/src/bootstrap/bin/rustdoc.rs index 798d5c3eb67..a54e58665cc 100644 --- a/src/bootstrap/bin/rustdoc.rs +++ b/src/bootstrap/bin/rustdoc.rs @@ -35,7 +35,7 @@ fn main() { }; let mut dylib_path = bootstrap::util::dylib_path(); - dylib_path.insert(0, PathBuf::from(libdir)); + dylib_path.insert(0, PathBuf::from(libdir.clone())); let mut cmd = Command::new(rustdoc); cmd.args(&args) @@ -69,6 +69,7 @@ fn main() { if verbose > 1 { eprintln!("rustdoc command: {:?}", cmd); + eprintln!("libdir: {:?}", libdir); } std::process::exit(match cmd.status() { diff --git a/src/bootstrap/builder.rs b/src/bootstrap/builder.rs index 79167b1fd5e..c67787b5b0a 100644 --- a/src/bootstrap/builder.rs +++ b/src/bootstrap/builder.rs @@ -459,6 +459,7 @@ impl<'a> Builder<'a> { dist::Cargo, dist::Rls, dist::Rustfmt, + dist::Clippy, dist::LlvmTools, dist::Extended, dist::HashSign @@ -469,6 +470,7 @@ impl<'a> Builder<'a> { install::Cargo, install::Rls, install::Rustfmt, + install::Clippy, install::Analysis, install::Src, install::Rustc @@ -825,7 +827,7 @@ impl<'a> Builder<'a> { cargo.env("RUSTC_ERROR_FORMAT", error_format); } if cmd != "build" && cmd != "check" && want_rustdoc { - cargo.env("RUSTDOC_LIBDIR", &libdir); + cargo.env("RUSTDOC_LIBDIR", self.sysroot_libdir(compiler, self.config.build)); } if mode.is_tool() { diff --git a/src/build_helper/lib.rs b/src/build_helper/lib.rs index 4d767f09689..00e5dee256e 100644 --- a/src/build_helper/lib.rs +++ b/src/build_helper/lib.rs @@ -15,6 +15,7 @@ use std::path::{Path, PathBuf}; use std::process::{Command, Stdio}; use std::time::{SystemTime, UNIX_EPOCH}; use std::{env, fs}; +use std::thread; /// A helper macro to `unwrap` a result except also print out details like: /// @@ -181,7 +182,9 @@ pub struct NativeLibBoilerplate { impl Drop for NativeLibBoilerplate { fn drop(&mut self) { - t!(File::create(self.out_dir.join("rustbuild.timestamp"))); + if !thread::panicking() { + t!(File::create(self.out_dir.join("rustbuild.timestamp"))); + } } } @@ -225,24 +228,34 @@ pub fn native_lib_boilerplate( } } -pub fn sanitizer_lib_boilerplate(sanitizer_name: &str) -> Result { - let (link_name, search_path) = match &*env::var("TARGET").unwrap() { +pub fn sanitizer_lib_boilerplate(sanitizer_name: &str) + -> Result<(NativeLibBoilerplate, String), ()> +{ + let (link_name, search_path, dynamic) = match &*env::var("TARGET").unwrap() { "x86_64-unknown-linux-gnu" => ( format!("clang_rt.{}-x86_64", sanitizer_name), "build/lib/linux", + false, ), "x86_64-apple-darwin" => ( - format!("dylib=clang_rt.{}_osx_dynamic", sanitizer_name), + format!("clang_rt.{}_osx_dynamic", sanitizer_name), "build/lib/darwin", + true, ), _ => return Err(()), }; - native_lib_boilerplate( + let to_link = if dynamic { + format!("dylib={}", link_name) + } else { + format!("static={}", link_name) + }; + let lib = native_lib_boilerplate( "libcompiler_builtins/compiler-rt", sanitizer_name, - &link_name, + &to_link, search_path, - ) + )?; + Ok((lib, link_name)) } fn dir_up_to_date(src: &Path, threshold: SystemTime) -> bool { diff --git a/src/liballoc/str.rs b/src/liballoc/str.rs index bb99d0401d3..4d6434c378e 100644 --- a/src/liballoc/str.rs +++ b/src/liballoc/str.rs @@ -45,6 +45,7 @@ use core::str::pattern::{Searcher, ReverseSearcher, DoubleEndedSearcher}; use core::mem; use core::ptr; use core::iter::FusedIterator; +use core::unicode::conversions; use borrow::{Borrow, ToOwned}; use boxed::Box; @@ -369,7 +370,18 @@ impl str { // See https://github.com/rust-lang/rust/issues/26035 map_uppercase_sigma(self, i, &mut s) } else { - s.extend(c.to_lowercase()); + match conversions::to_lower(c) { + [a, '\0', _] => s.push(a), + [a, b, '\0'] => { + s.push(a); + s.push(b); + } + [a, b, c] => { + s.push(a); + s.push(b); + s.push(c); + } + } } } return s; @@ -423,7 +435,20 @@ impl str { #[stable(feature = "unicode_case_mapping", since = "1.2.0")] pub fn to_uppercase(&self) -> String { let mut s = String::with_capacity(self.len()); - s.extend(self.chars().flat_map(|c| c.to_uppercase())); + for c in self[..].chars() { + match conversions::to_upper(c) { + [a, '\0', _] => s.push(a), + [a, b, '\0'] => { + s.push(a); + s.push(b); + } + [a, b, c] => { + s.push(a); + s.push(b); + s.push(c); + } + } + } return s; } diff --git a/src/libcore/iter/iterator.rs b/src/libcore/iter/iterator.rs index c0681619bf8..afc273d265b 100644 --- a/src/libcore/iter/iterator.rs +++ b/src/libcore/iter/iterator.rs @@ -384,7 +384,9 @@ pub trait Iterator { /// /// In other words, it zips two iterators together, into a single one. /// - /// If either iterator returns [`None`], [`next`] will return [`None`]. + /// If either iterator returns [`None`], [`next`] from the zipped iterator + /// will return [`None`]. If the first iterator returns [`None`], `zip` will + /// short-circuit and `next` will not be called on the second iterator. /// /// # Examples /// diff --git a/src/libcore/option.rs b/src/libcore/option.rs index f3e823670aa..9f9dbd0777a 100644 --- a/src/libcore/option.rs +++ b/src/libcore/option.rs @@ -833,12 +833,14 @@ impl Option { /// /// ``` /// let mut x = Some(2); - /// x.take(); + /// let y = x.take(); /// assert_eq!(x, None); + /// assert_eq!(y, Some(2)); /// /// let mut x: Option = None; - /// x.take(); + /// let y = x.take(); /// assert_eq!(x, None); + /// assert_eq!(y, None); /// ``` #[inline] #[stable(feature = "rust1", since = "1.0.0")] diff --git a/src/libcore/unicode/mod.rs b/src/libcore/unicode/mod.rs index b6b033adc04..e5cda880f88 100644 --- a/src/libcore/unicode/mod.rs +++ b/src/libcore/unicode/mod.rs @@ -20,6 +20,9 @@ pub(crate) mod version; pub mod derived_property { pub use unicode::tables::derived_property::{Case_Ignorable, Cased}; } +pub mod conversions { + pub use unicode::tables::conversions::{to_lower, to_upper}; +} // For use in libsyntax pub mod property { diff --git a/src/librustc/hir/lowering.rs b/src/librustc/hir/lowering.rs index 722934ac39a..93fb282546b 100644 --- a/src/librustc/hir/lowering.rs +++ b/src/librustc/hir/lowering.rs @@ -4011,8 +4011,12 @@ impl<'a> LoweringContext<'a> { let iter = self.str_to_ident("iter"); let next_ident = self.str_to_ident("__next"); + let next_sp = self.allow_internal_unstable( + CompilerDesugaringKind::ForLoop, + head_sp, + ); let next_pat = self.pat_ident_binding_mode( - pat.span, + next_sp, next_ident, hir::BindingAnnotation::Mutable, ); diff --git a/src/librustc/ich/impls_syntax.rs b/src/librustc/ich/impls_syntax.rs index fa9c5cefdf3..c9ac6cdedbb 100644 --- a/src/librustc/ich/impls_syntax.rs +++ b/src/librustc/ich/impls_syntax.rs @@ -412,6 +412,7 @@ impl_stable_hash_for!(enum ::syntax_pos::hygiene::CompilerDesugaringKind { DotFill, QuestionMark, ExistentialReturnType, + ForLoop, Catch }); diff --git a/src/librustc/infer/error_reporting/need_type_info.rs b/src/librustc/infer/error_reporting/need_type_info.rs index 773de8912ce..04d14f40b85 100644 --- a/src/librustc/infer/error_reporting/need_type_info.rs +++ b/src/librustc/infer/error_reporting/need_type_info.rs @@ -13,6 +13,7 @@ use hir::intravisit::{self, Visitor, NestedVisitorMap}; use infer::InferCtxt; use infer::type_variable::TypeVariableOrigin; use ty::{self, Ty, TyInfer, TyVar}; +use syntax::codemap::CompilerDesugaringKind; use syntax_pos::Span; use errors::DiagnosticBuilder; @@ -132,7 +133,15 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { labels.push((pattern.span, format!("consider giving this closure parameter a type"))); } else if let Some(pattern) = local_visitor.found_local_pattern { if let Some(simple_ident) = pattern.simple_ident() { - labels.push((pattern.span, format!("consider giving `{}` a type", simple_ident))); + match pattern.span.compiler_desugaring_kind() { + None => labels.push((pattern.span, + format!("consider giving `{}` a type", simple_ident))), + Some(CompilerDesugaringKind::ForLoop) => labels.push(( + pattern.span, + "the element type for this iterator is not specified".to_string(), + )), + _ => {} + } } else { labels.push((pattern.span, format!("consider giving the pattern a type"))); } diff --git a/src/librustc_asan/build.rs b/src/librustc_asan/build.rs index cb7721affe7..b8614c520e7 100644 --- a/src/librustc_asan/build.rs +++ b/src/librustc_asan/build.rs @@ -18,7 +18,7 @@ use cmake::Config; fn main() { if let Some(llvm_config) = env::var_os("LLVM_CONFIG") { - let native = match sanitizer_lib_boilerplate("asan") { + let (native, target) = match sanitizer_lib_boilerplate("asan") { Ok(native) => native, _ => return, }; @@ -29,7 +29,7 @@ fn main() { .define("COMPILER_RT_BUILD_XRAY", "OFF") .define("LLVM_CONFIG_PATH", llvm_config) .out_dir(&native.out_dir) - .build_target("asan") + .build_target(&target) .build(); } println!("cargo:rerun-if-env-changed=LLVM_CONFIG"); diff --git a/src/librustc_lsan/build.rs b/src/librustc_lsan/build.rs index 3d2ae480de6..05e40cdcedd 100644 --- a/src/librustc_lsan/build.rs +++ b/src/librustc_lsan/build.rs @@ -18,7 +18,7 @@ use cmake::Config; fn main() { if let Some(llvm_config) = env::var_os("LLVM_CONFIG") { - let native = match sanitizer_lib_boilerplate("lsan") { + let (native, target) = match sanitizer_lib_boilerplate("lsan") { Ok(native) => native, _ => return, }; @@ -29,7 +29,7 @@ fn main() { .define("COMPILER_RT_BUILD_XRAY", "OFF") .define("LLVM_CONFIG_PATH", llvm_config) .out_dir(&native.out_dir) - .build_target("lsan") + .build_target(&target) .build(); } println!("cargo:rerun-if-env-changed=LLVM_CONFIG"); diff --git a/src/librustc_msan/build.rs b/src/librustc_msan/build.rs index 7e2a82dd0ab..4abfc358560 100644 --- a/src/librustc_msan/build.rs +++ b/src/librustc_msan/build.rs @@ -18,7 +18,7 @@ use cmake::Config; fn main() { if let Some(llvm_config) = env::var_os("LLVM_CONFIG") { - let native = match sanitizer_lib_boilerplate("msan") { + let (native, target) = match sanitizer_lib_boilerplate("msan") { Ok(native) => native, _ => return, }; @@ -29,7 +29,7 @@ fn main() { .define("COMPILER_RT_BUILD_XRAY", "OFF") .define("LLVM_CONFIG_PATH", llvm_config) .out_dir(&native.out_dir) - .build_target("msan") + .build_target(&target) .build(); } println!("cargo:rerun-if-env-changed=LLVM_CONFIG"); diff --git a/src/librustc_resolve/lib.rs b/src/librustc_resolve/lib.rs index f388b911feb..177e4ed8cf3 100644 --- a/src/librustc_resolve/lib.rs +++ b/src/librustc_resolve/lib.rs @@ -4521,7 +4521,7 @@ impl<'a> Resolver<'a> { attr::mark_known(attr); let msg = "attribute procedural macros are experimental"; - let feature = "proc_macro"; + let feature = "use_extern_macros"; feature_err(&self.session.parse_sess, feature, attr.span, GateIssue::Language, msg) diff --git a/src/librustc_tsan/build.rs b/src/librustc_tsan/build.rs index 641d9c3647d..38595478c74 100644 --- a/src/librustc_tsan/build.rs +++ b/src/librustc_tsan/build.rs @@ -18,7 +18,7 @@ use cmake::Config; fn main() { if let Some(llvm_config) = env::var_os("LLVM_CONFIG") { - let native = match sanitizer_lib_boilerplate("tsan") { + let (native, target) = match sanitizer_lib_boilerplate("tsan") { Ok(native) => native, _ => return, }; @@ -29,7 +29,7 @@ fn main() { .define("COMPILER_RT_BUILD_XRAY", "OFF") .define("LLVM_CONFIG_PATH", llvm_config) .out_dir(&native.out_dir) - .build_target("tsan") + .build_target(&target) .build(); } println!("cargo:rerun-if-env-changed=LLVM_CONFIG"); diff --git a/src/librustdoc/html/render.rs b/src/librustdoc/html/render.rs index 41c08dbf4ab..3070458d0be 100644 --- a/src/librustdoc/html/render.rs +++ b/src/librustdoc/html/render.rs @@ -1968,7 +1968,6 @@ impl Context { // If the item is a macro, redirect from the old macro URL (with !) // to the new one (without). - // FIXME(#35705) remove this redirect. if item_type == ItemType::Macro { let redir_name = format!("{}.{}!.html", item_type, name); let redir_dst = self.dst.join(redir_name); diff --git a/src/libstd/io/buffered.rs b/src/libstd/io/buffered.rs index ee297d3783e..189569683a9 100644 --- a/src/libstd/io/buffered.rs +++ b/src/libstd/io/buffered.rs @@ -738,7 +738,7 @@ impl fmt::Display for IntoInnerError { /// reducing the number of actual writes to the file. /// /// ```no_run -/// use std::fs::File; +/// use std::fs::{self, File}; /// use std::io::prelude::*; /// use std::io::LineWriter; /// @@ -752,17 +752,30 @@ impl fmt::Display for IntoInnerError { /// let file = File::create("poem.txt")?; /// let mut file = LineWriter::new(file); /// -/// for &byte in road_not_taken.iter() { -/// file.write(&[byte]).unwrap(); -/// } +/// file.write_all(b"I shall be telling this with a sigh")?; /// -/// // let's check we did the right thing. -/// let mut file = File::open("poem.txt")?; -/// let mut contents = String::new(); +/// // No bytes are written until a newline is encountered (or +/// // the internal buffer is filled). +/// assert_eq!(fs::read_to_string("poem.txt")?, ""); +/// file.write_all(b"\n")?; +/// assert_eq!( +/// fs::read_to_string("poem.txt")?, +/// "I shall be telling this with a sigh\n", +/// ); /// -/// file.read_to_string(&mut contents)?; +/// // Write the rest of the poem. +/// file.write_all(b"Somewhere ages and ages hence: +/// Two roads diverged in a wood, and I - +/// I took the one less traveled by, +/// And that has made all the difference.")?; /// -/// assert_eq!(contents.as_bytes(), &road_not_taken[..]); +/// // The last line of the poem doesn't end in a newline, so +/// // we have to flush or drop the `LineWriter` to finish +/// // writing. +/// file.flush()?; +/// +/// // Confirm the whole poem was written. +/// assert_eq!(fs::read("poem.txt")?, &road_not_taken[..]); /// Ok(()) /// } /// ``` @@ -862,7 +875,7 @@ impl LineWriter { /// /// The internal buffer is written out before returning the writer. /// - // # Errors + /// # Errors /// /// An `Err` will be returned if an error occurs while flushing the buffer. /// diff --git a/src/libstd/net/tcp.rs b/src/libstd/net/tcp.rs index 0f60b5b3ee4..6b4bbdddf32 100644 --- a/src/libstd/net/tcp.rs +++ b/src/libstd/net/tcp.rs @@ -81,7 +81,7 @@ pub struct TcpStream(net_imp::TcpStream); /// } /// /// fn main() -> io::Result<()> { -/// let listener = TcpListener::bind("127.0.0.1:80").unwrap(); +/// let listener = TcpListener::bind("127.0.0.1:80")?; /// /// // accept connections and process them serially /// for stream in listener.incoming() { diff --git a/src/libsyntax/feature_gate.rs b/src/libsyntax/feature_gate.rs index 2ef90e3ec47..84b5f9659b5 100644 --- a/src/libsyntax/feature_gate.rs +++ b/src/libsyntax/feature_gate.rs @@ -284,7 +284,7 @@ declare_features! ( // Allows #[link(..., cfg(..))] (active, link_cfg, "1.14.0", Some(37406), None), - (active, use_extern_macros, "1.15.0", Some(35896), None), + (active, use_extern_macros, "1.15.0", Some(35896), Some(Edition::Edition2018)), // `extern "ptx-*" fn()` (active, abi_ptx, "1.15.0", Some(38788), None), diff --git a/src/libsyntax_pos/hygiene.rs b/src/libsyntax_pos/hygiene.rs index c7076478332..1531f030127 100644 --- a/src/libsyntax_pos/hygiene.rs +++ b/src/libsyntax_pos/hygiene.rs @@ -602,6 +602,7 @@ pub enum CompilerDesugaringKind { /// `impl Trait` with `Foo`. ExistentialReturnType, Async, + ForLoop, } impl CompilerDesugaringKind { @@ -612,6 +613,7 @@ impl CompilerDesugaringKind { CompilerDesugaringKind::QuestionMark => "?", CompilerDesugaringKind::Catch => "do catch", CompilerDesugaringKind::ExistentialReturnType => "existential type", + CompilerDesugaringKind::ForLoop => "for loop", }) } } diff --git a/src/test/debuginfo/type-names.rs b/src/test/debuginfo/type-names.rs index c89c0e4e758..3ec8b048b12 100644 --- a/src/test/debuginfo/type-names.rs +++ b/src/test/debuginfo/type-names.rs @@ -11,9 +11,6 @@ // ignore-tidy-linelength // ignore-lldb // ignore-gdb // Test temporarily ignored due to debuginfo tests being disabled, see PR 47155 -// ignore-android: FIXME(#24958) -// ignore-arm: FIXME(#24958) -// ignore-aarch64: FIXME(#24958) // compile-flags:-g diff --git a/src/test/ui/issue-20261.stderr b/src/test/ui/issue-20261.stderr index a4a2aec8969..a7a7ea7c69b 100644 --- a/src/test/ui/issue-20261.stderr +++ b/src/test/ui/issue-20261.stderr @@ -2,7 +2,7 @@ error[E0282]: type annotations needed --> $DIR/issue-20261.rs:14:11 | LL | for (ref i,) in [].iter() { - | -------- consider giving `__next` a type + | --------- the element type for this iterator is not specified LL | i.clone(); | ^^^^^ cannot infer type for `_` | diff --git a/src/test/ui/issue-51116.rs b/src/test/ui/issue-51116.rs new file mode 100644 index 00000000000..34217c6236c --- /dev/null +++ b/src/test/ui/issue-51116.rs @@ -0,0 +1,24 @@ +// 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() { + let tiles = Default::default(); + for row in &mut tiles { + for tile in row { + //~^ NOTE the element type for this iterator is not specified + *tile = 0; + //~^ ERROR type annotations needed + //~| NOTE cannot infer type for `_` + //~| NOTE type must be known at this point + } + } + + let tiles: [[usize; 3]; 3] = tiles; +} diff --git a/src/test/ui/issue-51116.stderr b/src/test/ui/issue-51116.stderr new file mode 100644 index 00000000000..0c38688340b --- /dev/null +++ b/src/test/ui/issue-51116.stderr @@ -0,0 +1,14 @@ +error[E0282]: type annotations needed + --> $DIR/issue-51116.rs:16:13 + | +LL | for tile in row { + | --- the element type for this iterator is not specified +LL | //~^ NOTE the element type for this iterator is not specified +LL | *tile = 0; + | ^^^^^ cannot infer type for `_` + | + = note: type must be known at this point + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0282`.