From a4e5c91cb823526765574c6d18ea6b13f1cb7dab Mon Sep 17 00:00:00 2001 From: kennytm Date: Sat, 4 Nov 2017 02:44:54 +0800 Subject: [PATCH 01/15] libtest: Force a newline every 100 dots when testing in quiet mode. Rationale: We use --quiet mode when testing a PR in the CI. Also, we use `stamp` to prefix every line with a timestamp. Previously, when testing in --quiet mode, we will only print a dot for each test without any line breaks. Combined with `stamp`, this means we'd need to wait for all tests to complete before writing the output. On Travis CI, if we don't print anything within 30 minutes, the job will be forcefully canceled. This makes it very easy to spuriously-timeout when testing non-default images like arm-android using the CI. This commit tries to workaround the issue by printing a new line every 100 dots, forcing `stamp` to emit something to reset Travis's countdown. --- src/libtest/lib.rs | 17 ++++++++++++++--- 1 file changed, 14 insertions(+), 3 deletions(-) diff --git a/src/libtest/lib.rs b/src/libtest/lib.rs index e8a1242c8145f..76abcb83edc53 100644 --- a/src/libtest/lib.rs +++ b/src/libtest/lib.rs @@ -71,6 +71,7 @@ use std::thread; use std::time::{Instant, Duration}; const TEST_WARN_TIMEOUT_S: u64 = 60; +const QUIET_MODE_MAX_COLUMN: usize = 100; // insert a '\n' after 100 tests in quiet mode // to be used by rustc to compile tests in libtest pub mod test { @@ -614,7 +615,14 @@ impl ConsoleTestState { pub fn write_short_result(&mut self, verbose: &str, quiet: &str, color: term::color::Color) -> io::Result<()> { if self.quiet { - self.write_pretty(quiet, color) + self.write_pretty(quiet, color)?; + if self.current_test_count() % QUIET_MODE_MAX_COLUMN == QUIET_MODE_MAX_COLUMN - 1 { + // we insert a new line every 100 dots in order to flush the + // screen when dealing with line-buffered output (e.g. piping to + // `stamp` in the rust CI). + self.write_plain("\n")?; + } + Ok(()) } else { self.write_pretty(verbose, color)?; self.write_plain("\n") @@ -771,9 +779,12 @@ impl ConsoleTestState { Ok(()) } + fn current_test_count(&self) -> usize { + self.passed + self.failed + self.ignored + self.measured + self.allowed_fail + } + pub fn write_run_finish(&mut self) -> io::Result { - assert!(self.passed + self.failed + self.ignored + self.measured + - self.allowed_fail == self.total); + assert!(self.current_test_count() == self.total); if self.options.display_output { self.write_outputs()?; From 1b5aaf22e88cdca0583be5bacdbc196daafd8f3e Mon Sep 17 00:00:00 2001 From: kennytm Date: Sat, 4 Nov 2017 02:49:06 +0800 Subject: [PATCH 02/15] dist-powerpc64le-linux: Use links from vault.centos.org instead. This commit reverts #45734 and applies #45744. We expect the vault links to be more stable than mirror.centos.org. --- .../dist-powerpc64le-linux/build-powerpc64le-toolchain.sh | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/ci/docker/dist-powerpc64le-linux/build-powerpc64le-toolchain.sh b/src/ci/docker/dist-powerpc64le-linux/build-powerpc64le-toolchain.sh index f231d20b19753..5f556b67081a3 100755 --- a/src/ci/docker/dist-powerpc64le-linux/build-powerpc64le-toolchain.sh +++ b/src/ci/docker/dist-powerpc64le-linux/build-powerpc64le-toolchain.sh @@ -23,9 +23,9 @@ SYSROOT=/usr/local/$TARGET/sysroot mkdir -p $SYSROOT pushd $SYSROOT -centos_base=http://mirror.centos.org/altarch/7/os/ppc64le/Packages -glibc_v=2.17-196.el7 -kernel_v=3.10.0-693.el7 +centos_base=http://vault.centos.org/altarch/7.3.1611/os/ppc64le/Packages/ +glibc_v=2.17-157.el7 +kernel_v=3.10.0-514.el7 for package in glibc{,-devel,-headers}-$glibc_v kernel-headers-$kernel_v; do curl $centos_base/$package.ppc64le.rpm | \ rpm2cpio - | cpio -idm From 33400fbbcd26caf98fe316b4f2ab81efdc9c40f2 Mon Sep 17 00:00:00 2001 From: kennytm Date: Wed, 1 Nov 2017 01:39:47 +0800 Subject: [PATCH 03/15] Modify the script to allow for running docker images on Windows 7. --- src/ci/docker/README.md | 50 +++++++++++++++++++++++++++++++++++--- src/ci/docker/run.sh | 13 ++++++++-- src/tools/tidy/src/bins.rs | 6 ++--- 3 files changed, 60 insertions(+), 9 deletions(-) diff --git a/src/ci/docker/README.md b/src/ci/docker/README.md index adce6a00d4623..922deba7367e9 100644 --- a/src/ci/docker/README.md +++ b/src/ci/docker/README.md @@ -22,6 +22,48 @@ Images will output artifacts in an `obj` dir at the root of a repository. - `scripts` contains files shared by docker images - `disabled` contains images that are not built on travis +## Docker Toolbox on Windows + +For Windows before Windows 10, the docker images can be run on Windows via +[Docker Toolbox]. There are several preparation needs to be made before running +a Docker image. + +1. Stop the virtual machine from the terminal with `docker-machine stop` + +2. If your Rust source is placed outside of `C:\Users\**`, e.g. if you place the + repository in the `E:\rust` folder, please add a shared folder from + VirtualBox by: + + 1. Select the "default" virtual machine inside VirtualBox, then click + "Settings" + 2. Go to "Shared Folders", click "Add shared foldrer" (the folder icon with + a plus sign), fill in the following information, then click "OK": + + * Folder path: `E:\rust` + * Folder name: `e/rust` + * Read-only: ☐ *unchecked* + * Auto-mount: ☑ *checked* + * Make Permanant: ☑ *checked* + +3. VirtualBox might not support creating symbolic links inside a shared folder + by default. You can enable it manually by running these from `cmd.exe`: + + ```bat + cd "C:\Program Files\Oracle\VirtualBox" + VBoxManage setextradata default VBoxInternal2/SharedFoldersEnableSymlinksCreate/e/rust 1 + :: ^~~~~~ + :: folder name + ``` + +4. Restart the virtual machine from terminal with `docker-machine start`. + +To run the image, + +1. Launch the "Docker Quickstart Terminal". +2. Execute `./src/ci/docker/run.sh $image_name` as explained at the beginning. + +[Docker Toolbox]: https://www.docker.com/products/docker-toolbox + ## Cross toolchains A number of these images take quite a long time to compile as they're building @@ -137,7 +179,7 @@ For targets: `armv7-unknown-linux-gnueabihf` libraries like jemalloc. See the mk/cfg/arm(v7)-uknown-linux-gnueabi{,hf}.mk file in Rust's source code. -## `aarch64-linux-gnu.config` +### `aarch64-linux-gnu.config` For targets: `aarch64-unknown-linux-gnu` @@ -150,7 +192,7 @@ For targets: `aarch64-unknown-linux-gnu` - C compiler > gcc version = 5.2.0 - C compiler > C++ = ENABLE -- to cross compile LLVM -## `powerpc-linux-gnu.config` +### `powerpc-linux-gnu.config` For targets: `powerpc-unknown-linux-gnu` @@ -165,7 +207,7 @@ For targets: `powerpc-unknown-linux-gnu` - C compiler > gcc version = 4.9.3 - C compiler > C++ = ENABLE -- to cross compile LLVM -## `powerpc64-linux-gnu.config` +### `powerpc64-linux-gnu.config` For targets: `powerpc64-unknown-linux-gnu` @@ -184,7 +226,7 @@ For targets: `powerpc64-unknown-linux-gnu` (+) These CPU options match the configuration of the toolchains in RHEL6. -## `s390x-linux-gnu.config` +### `s390x-linux-gnu.config` For targets: `s390x-unknown-linux-gnu` diff --git a/src/ci/docker/run.sh b/src/ci/docker/run.sh index b2560c6b95b4c..dc02310b4f21f 100755 --- a/src/ci/docker/run.sh +++ b/src/ci/docker/run.sh @@ -11,6 +11,8 @@ set -e +export MSYS_NO_PATHCONV=1 + script=`cd $(dirname $0) && pwd`/`basename $0` image=$1 @@ -25,12 +27,19 @@ travis_fold start build_docker travis_time_start if [ -f "$docker_dir/$image/Dockerfile" ]; then + dockerfile="$docker_dir/$image/Dockerfile" + if [ -x /usr/bin/cygpath ]; then + context="`cygpath -w $docker_dir`" + dockerfile="`cygpath -w $dockerfile`" + else + context="$docker_dir" + fi retry docker \ build \ --rm \ -t rust-ci \ - -f "$docker_dir/$image/Dockerfile" \ - "$docker_dir" + -f "$dockerfile" \ + "$context" elif [ -f "$docker_dir/disabled/$image/Dockerfile" ]; then if [ -n "$TRAVIS_OS_NAME" ]; then echo Cannot run disabled images on travis! diff --git a/src/tools/tidy/src/bins.rs b/src/tools/tidy/src/bins.rs index 11d5dbe736e81..f6e42c8dc17b1 100644 --- a/src/tools/tidy/src/bins.rs +++ b/src/tools/tidy/src/bins.rs @@ -31,9 +31,9 @@ pub fn check(path: &Path, bad: &mut bool) { if let Ok(mut file) = fs::File::open("/proc/version") { let mut contents = String::new(); file.read_to_string(&mut contents).unwrap(); - // Probably on Windows Linux Subsystem, all files will be marked as - // executable, so skip checking. - if contents.contains("Microsoft") { + // Probably on Windows Linux Subsystem or Docker via VirtualBox, + // all files will be marked as executable, so skip checking. + if contents.contains("Microsoft") || contents.contains("boot2docker") { return; } } From d517668a088715e932c373fb18dfffdc58831829 Mon Sep 17 00:00:00 2001 From: kennytm Date: Sun, 5 Nov 2017 01:47:02 +0800 Subject: [PATCH 04/15] If the linker segfaulted, don't emit it as a warning. Prevent spuriously breaking UI tests. See https://github.com/rust-lang/rust/pull/45489#issuecomment-340134944. --- src/librustc_trans/back/link.rs | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/src/librustc_trans/back/link.rs b/src/librustc_trans/back/link.rs index 907693ea8a379..1961acf53a695 100644 --- a/src/librustc_trans/back/link.rs +++ b/src/librustc_trans/back/link.rs @@ -671,11 +671,12 @@ fn link_natively(sess: &Session, break } - sess.struct_warn("looks like the linker segfaulted when we tried to \ - call it, automatically retrying again") - .note(&format!("{:?}", cmd)) - .note(&out) - .emit(); + warn!( + "looks like the linker segfaulted when we tried to call it, \ + automatically retrying again. cmd = {:?}, out = {}.", + cmd, + out, + ); } match prog { From 51e22479485900d3d593547e8cf855bba9a03db8 Mon Sep 17 00:00:00 2001 From: kennytm Date: Sun, 5 Nov 2017 22:45:41 +0800 Subject: [PATCH 05/15] Abbreviate some stdout/stderr output in compiletest. This is intended to prevent the spurious OOM error from run-pass/rustc-rust-log.rs, by skipping the output in the middle when the size is over 416 KB, so that the log output will not be overwhelmed. --- src/Cargo.lock | 2 + src/tools/compiletest/Cargo.toml | 4 + src/tools/compiletest/src/main.rs | 4 +- src/tools/compiletest/src/read2.rs | 208 +++++++++++++++++++++++++++ src/tools/compiletest/src/runtest.rs | 91 +++++++++++- 5 files changed, 302 insertions(+), 7 deletions(-) create mode 100644 src/tools/compiletest/src/read2.rs diff --git a/src/Cargo.lock b/src/Cargo.lock index f8418b77f61a6..edd0ee8bd5ace 100644 --- a/src/Cargo.lock +++ b/src/Cargo.lock @@ -347,7 +347,9 @@ dependencies = [ "getopts 0.2.15 (registry+https://github.com/rust-lang/crates.io-index)", "libc 0.2.32 (registry+https://github.com/rust-lang/crates.io-index)", "log 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)", + "miow 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)", "rustc-serialize 0.3.24 (registry+https://github.com/rust-lang/crates.io-index)", + "winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", ] [[package]] diff --git a/src/tools/compiletest/Cargo.toml b/src/tools/compiletest/Cargo.toml index f8282cc5f8d9b..d4d567e63c017 100644 --- a/src/tools/compiletest/Cargo.toml +++ b/src/tools/compiletest/Cargo.toml @@ -11,3 +11,7 @@ getopts = "0.2" log = "0.3" rustc-serialize = "0.3" libc = "0.2" + +[target.'cfg(windows)'.dependencies] +miow = "0.2" +winapi = "0.2" diff --git a/src/tools/compiletest/src/main.rs b/src/tools/compiletest/src/main.rs index 1701c8a3e43ee..9fb6a3f5e0753 100644 --- a/src/tools/compiletest/src/main.rs +++ b/src/tools/compiletest/src/main.rs @@ -11,10 +11,11 @@ #![crate_name = "compiletest"] #![feature(test)] +#![feature(slice_rotate)] #![deny(warnings)] -#[cfg(any(target_os = "macos", target_os = "ios"))] +#[cfg(unix)] extern crate libc; extern crate test; extern crate getopts; @@ -47,6 +48,7 @@ pub mod runtest; pub mod common; pub mod errors; mod raise_fd_limit; +mod read2; fn main() { env_logger::init().unwrap(); diff --git a/src/tools/compiletest/src/read2.rs b/src/tools/compiletest/src/read2.rs new file mode 100644 index 0000000000000..1d8816c7db132 --- /dev/null +++ b/src/tools/compiletest/src/read2.rs @@ -0,0 +1,208 @@ +// 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. + +// FIXME: This is a complete copy of `cargo/src/cargo/util/read2.rs` +// Consider unify the read2() in libstd, cargo and this to prevent further code duplication. + +pub use self::imp::read2; + +#[cfg(not(any(unix, windows)))] +mod imp { + use std::io::{self, Read}; + use std::process::{ChildStdout, ChildStderr}; + + pub fn read2(out_pipe: ChildStdout, + err_pipe: ChildStderr, + data: &mut FnMut(bool, &mut Vec, bool)) -> io::Result<()> { + let mut buffer = Vec::new(); + out_pipe.read_to_end(&mut buffer)?; + data(true, &mut buffer, true); + buffer.clear(); + err_pipe.read_to_end(&mut buffer)?; + data(false, &mut buffer, true); + Ok(()) + } +} + +#[cfg(unix)] +mod imp { + use std::io::prelude::*; + use std::io; + use std::mem; + use std::os::unix::prelude::*; + use std::process::{ChildStdout, ChildStderr}; + use libc; + + pub fn read2(mut out_pipe: ChildStdout, + mut err_pipe: ChildStderr, + data: &mut FnMut(bool, &mut Vec, bool)) -> io::Result<()> { + unsafe { + libc::fcntl(out_pipe.as_raw_fd(), libc::F_SETFL, libc::O_NONBLOCK); + libc::fcntl(err_pipe.as_raw_fd(), libc::F_SETFL, libc::O_NONBLOCK); + } + + let mut out_done = false; + let mut err_done = false; + let mut out = Vec::new(); + let mut err = Vec::new(); + + let mut fds: [libc::pollfd; 2] = unsafe { mem::zeroed() }; + fds[0].fd = out_pipe.as_raw_fd(); + fds[0].events = libc::POLLIN; + fds[1].fd = err_pipe.as_raw_fd(); + fds[1].events = libc::POLLIN; + loop { + // wait for either pipe to become readable using `select` + let r = unsafe { libc::poll(fds.as_mut_ptr(), 2, -1) }; + if r == -1 { + let err = io::Error::last_os_error(); + if err.kind() == io::ErrorKind::Interrupted { + continue + } + return Err(err) + } + + // Read as much as we can from each pipe, ignoring EWOULDBLOCK or + // EAGAIN. If we hit EOF, then this will happen because the underlying + // reader will return Ok(0), in which case we'll see `Ok` ourselves. In + // this case we flip the other fd back into blocking mode and read + // whatever's leftover on that file descriptor. + let handle = |res: io::Result<_>| { + match res { + Ok(_) => Ok(true), + Err(e) => { + if e.kind() == io::ErrorKind::WouldBlock { + Ok(false) + } else { + Err(e) + } + } + } + }; + if !out_done && fds[0].revents != 0 && handle(out_pipe.read_to_end(&mut out))? { + out_done = true; + } + data(true, &mut out, out_done); + if !err_done && fds[1].revents != 0 && handle(err_pipe.read_to_end(&mut err))? { + err_done = true; + } + data(false, &mut err, err_done); + + if out_done && err_done { + return Ok(()) + } + } + } +} + +#[cfg(windows)] +mod imp { + extern crate miow; + extern crate winapi; + + use std::io; + use std::os::windows::prelude::*; + use std::process::{ChildStdout, ChildStderr}; + use std::slice; + + use self::miow::iocp::{CompletionPort, CompletionStatus}; + use self::miow::pipe::NamedPipe; + use self::miow::Overlapped; + use self::winapi::ERROR_BROKEN_PIPE; + + struct Pipe<'a> { + dst: &'a mut Vec, + overlapped: Overlapped, + pipe: NamedPipe, + done: bool, + } + + pub fn read2(out_pipe: ChildStdout, + err_pipe: ChildStderr, + data: &mut FnMut(bool, &mut Vec, bool)) -> io::Result<()> { + let mut out = Vec::new(); + let mut err = Vec::new(); + + let port = CompletionPort::new(1)?; + port.add_handle(0, &out_pipe)?; + port.add_handle(1, &err_pipe)?; + + unsafe { + let mut out_pipe = Pipe::new(out_pipe, &mut out); + let mut err_pipe = Pipe::new(err_pipe, &mut err); + + out_pipe.read()?; + err_pipe.read()?; + + let mut status = [CompletionStatus::zero(), CompletionStatus::zero()]; + + while !out_pipe.done || !err_pipe.done { + for status in port.get_many(&mut status, None)? { + if status.token() == 0 { + out_pipe.complete(status); + data(true, out_pipe.dst, out_pipe.done); + out_pipe.read()?; + } else { + err_pipe.complete(status); + data(false, err_pipe.dst, err_pipe.done); + err_pipe.read()?; + } + } + } + + Ok(()) + } + } + + impl<'a> Pipe<'a> { + unsafe fn new(p: P, dst: &'a mut Vec) -> Pipe<'a> { + Pipe { + dst: dst, + pipe: NamedPipe::from_raw_handle(p.into_raw_handle()), + overlapped: Overlapped::zero(), + done: false, + } + } + + unsafe fn read(&mut self) -> io::Result<()> { + let dst = slice_to_end(self.dst); + match self.pipe.read_overlapped(dst, self.overlapped.raw()) { + Ok(_) => Ok(()), + Err(e) => { + if e.raw_os_error() == Some(ERROR_BROKEN_PIPE as i32) { + self.done = true; + Ok(()) + } else { + Err(e) + } + } + } + } + + unsafe fn complete(&mut self, status: &CompletionStatus) { + let prev = self.dst.len(); + self.dst.set_len(prev + status.bytes_transferred() as usize); + if status.bytes_transferred() == 0 { + self.done = true; + } + } + } + + unsafe fn slice_to_end(v: &mut Vec) -> &mut [u8] { + if v.capacity() == 0 { + v.reserve(16); + } + if v.capacity() == v.len() { + v.reserve(1); + } + slice::from_raw_parts_mut(v.as_mut_ptr().offset(v.len() as isize), + v.capacity() - v.len()) + } +} diff --git a/src/tools/compiletest/src/runtest.rs b/src/tools/compiletest/src/runtest.rs index de96aa9cdeb7f..0983ce9d09a04 100644 --- a/src/tools/compiletest/src/runtest.rs +++ b/src/tools/compiletest/src/runtest.rs @@ -29,7 +29,7 @@ use std::fmt; use std::io::prelude::*; use std::io::{self, BufReader}; use std::path::{Path, PathBuf}; -use std::process::{Command, Output, ExitStatus, Stdio}; +use std::process::{Command, Output, ExitStatus, Stdio, Child}; use std::str; use extract_gdb_version; @@ -1344,12 +1344,14 @@ actual:\n\ if let Some(input) = input { child.stdin.as_mut().unwrap().write_all(input.as_bytes()).unwrap(); } - let Output { status, stdout, stderr } = child.wait_with_output().unwrap(); + + let Output { status, stdout, stderr } = read2_abbreviated(child) + .expect("failed to read output"); let result = ProcRes { status, - stdout: String::from_utf8(stdout).unwrap(), - stderr: String::from_utf8(stderr).unwrap(), + stdout: String::from_utf8_lossy(&stdout).into_owned(), + stderr: String::from_utf8_lossy(&stderr).into_owned(), cmdline, }; @@ -1634,7 +1636,9 @@ actual:\n\ cmd.arg("-a").arg("-u"); cmd.arg(filename); cmd.arg("-nobanner"); - let output = match cmd.output() { + cmd.stdout(Stdio::piped()); + cmd.stderr(Stdio::piped()); + let output = match cmd.spawn().and_then(read2_abbreviated) { Ok(output) => output, Err(_) => return, }; @@ -2094,6 +2098,8 @@ actual:\n\ let mut cmd = Command::new(make); cmd.current_dir(&self.testpaths.file) + .stdout(Stdio::piped()) + .stderr(Stdio::piped()) .env("TARGET", &self.config.target) .env("PYTHON", &self.config.docck_python) .env("S", src_root) @@ -2142,7 +2148,7 @@ actual:\n\ } } - let output = cmd.output().expect("failed to spawn `make`"); + let output = cmd.spawn().and_then(read2_abbreviated).expect("failed to spawn `make`"); if !output.status.success() { let res = ProcRes { status: output.status, @@ -2534,3 +2540,76 @@ fn nocomment_mir_line(line: &str) -> &str { line } } + +fn read2_abbreviated(mut child: Child) -> io::Result { + use std::mem::replace; + use read2::read2; + + const HEAD_LEN: usize = 160 * 1024; + const TAIL_LEN: usize = 256 * 1024; + + enum ProcOutput { + Full(Vec), + Abbreviated { + head: Vec, + skipped: usize, + tail: Box<[u8]>, + } + } + + impl ProcOutput { + fn extend(&mut self, data: &[u8]) { + let new_self = match *self { + ProcOutput::Full(ref mut bytes) => { + bytes.extend_from_slice(data); + let new_len = bytes.len(); + if new_len <= HEAD_LEN + TAIL_LEN { + return; + } + let tail = bytes.split_off(new_len - TAIL_LEN).into_boxed_slice(); + let head = replace(bytes, Vec::new()); + let skipped = new_len - HEAD_LEN - TAIL_LEN; + ProcOutput::Abbreviated { head, skipped, tail } + } + ProcOutput::Abbreviated { ref mut skipped, ref mut tail, .. } => { + *skipped += data.len(); + if data.len() <= TAIL_LEN { + tail[..data.len()].copy_from_slice(data); + tail.rotate(data.len()); + } else { + tail.copy_from_slice(&data[(data.len() - TAIL_LEN)..]); + } + return; + } + }; + *self = new_self; + } + + fn into_bytes(self) -> Vec { + match self { + ProcOutput::Full(bytes) => bytes, + ProcOutput::Abbreviated { mut head, skipped, tail } => { + write!(&mut head, "\n\n<<<<<< SKIPPED {} BYTES >>>>>>\n\n", skipped).unwrap(); + head.extend_from_slice(&tail); + head + } + } + } + } + + let mut stdout = ProcOutput::Full(Vec::new()); + let mut stderr = ProcOutput::Full(Vec::new()); + + drop(child.stdin.take()); + read2(child.stdout.take().unwrap(), child.stderr.take().unwrap(), &mut |is_stdout, data, _| { + if is_stdout { &mut stdout } else { &mut stderr }.extend(data); + data.clear(); + })?; + let status = child.wait()?; + + Ok(Output { + status, + stdout: stdout.into_bytes(), + stderr: stderr.into_bytes(), + }) +} \ No newline at end of file From 9cfdabaf3ca626685a3c6ff96f2b9306ee1412c2 Mon Sep 17 00:00:00 2001 From: kennytm Date: Sun, 5 Nov 2017 23:09:29 +0800 Subject: [PATCH 06/15] Force `gem update --system` before deployment. Try to prevent #44159. --- .travis.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.travis.yml b/.travis.yml index db34f1404481b..a59364e40de1d 100644 --- a/.travis.yml +++ b/.travis.yml @@ -286,6 +286,7 @@ before_deploy: rm -rf obj/build/dist/doc && cp -r obj/build/dist/* deploy/$TRAVIS_COMMIT; fi + - travis_retry gem update --system deploy: - provider: s3 From eee10cc48245be7b98bfec4c19aa558243e29f46 Mon Sep 17 00:00:00 2001 From: kennytm Date: Mon, 6 Nov 2017 01:10:09 +0800 Subject: [PATCH 07/15] Try to print the crash logs on macOS on failure. An attempt to debug #45230. --- .travis.yml | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index a59364e40de1d..33982838eae32 100644 --- a/.travis.yml +++ b/.travis.yml @@ -253,7 +253,14 @@ after_failure: # Random attempt at debugging currently. Just poking around in here to see if # anything shows up. - - ls $HOME/Library/Logs/DiagnosticReports/ + - ls -lat $HOME/Library/Logs/DiagnosticReports/ + - find $HOME/Library/Logs/DiagnosticReports/ ! \( + -name '*.stage2-*.crash' + -name 'com.apple.CoreSimulator.CoreSimulatorService-*.crash' + \) + -exec echo -e travis_fold":start:crashlog\n\033[31;1m" {} "\033[0m" \; + -exec head -750 {} \; + -exec echo travis_fold":"end:crashlog \; # attempt to debug anything killed by the oom killer on linux, just to see if # it happened From e65214441dd9b6ec4eff3821d988818ecb53abf6 Mon Sep 17 00:00:00 2001 From: Lukas Kalbertodt Date: Tue, 3 Oct 2017 12:27:42 +0200 Subject: [PATCH 08/15] Add `Option::filter()` according to RFC 2124 --- src/libcore/option.rs | 39 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 39 insertions(+) diff --git a/src/libcore/option.rs b/src/libcore/option.rs index 980ea551f0806..63c846b25eca5 100644 --- a/src/libcore/option.rs +++ b/src/libcore/option.rs @@ -607,6 +607,45 @@ impl Option { } } + /// Returns `None` if the option is `None`, otherwise calls `predicate` + /// with the wrapped value and returns: + /// + /// - `Some(t)` if `predicate` returns `true` (where `t` is the wrapped + /// value), and + /// - `None` if `predicate` returns `false`. + /// + /// This function works similar to `Iterator::filter()`. You can imagine + /// the `Option` being an iterator over one or zero elements. `filter()` + /// lets you decide which elements to keep. + /// + /// # Examples + /// + /// ```rust + /// #![feature(option_filter)] + /// + /// fn is_even(n: &i32) -> bool { + /// n % 2 == 0 + /// } + /// + /// assert_eq!(None.filter(is_even), None); + /// assert_eq!(Some(3).filter(is_even), None); + /// assert_eq!(Some(4).filter(is_even), Some(4)); + /// ``` + #[inline] + #[unstable(feature = "option_filter", issue = "45860")] + pub fn filter bool>(self, predicate: P) -> Self { + match self { + Some(x) => { + if predicate(&x) { + Some(x) + } else { + None + } + } + None => None, + } + } + /// Returns the option if it contains a value, otherwise returns `optb`. /// /// # Examples From 3d480b4138acb67d11767a046e92ff93ca9db72c Mon Sep 17 00:00:00 2001 From: Guillaume Gomez Date: Wed, 8 Nov 2017 14:11:27 +0100 Subject: [PATCH 09/15] Add missing example for Debug trait --- src/libcore/fmt/mod.rs | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+) diff --git a/src/libcore/fmt/mod.rs b/src/libcore/fmt/mod.rs index 1e45af5b105c9..e2d61890c3096 100644 --- a/src/libcore/fmt/mod.rs +++ b/src/libcore/fmt/mod.rs @@ -525,6 +525,26 @@ impl<'a> Display for Arguments<'a> { #[lang = "debug_trait"] pub trait Debug { /// Formats the value using the given formatter. + /// + /// # Examples + /// + /// ``` + /// use std::fmt; + /// + /// struct Position { + /// longitude: f32, + /// latitude: f32, + /// } + /// + /// impl fmt::Debug for Position { + /// fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { + /// write!(f, "({:?}, {:?})", self.longitude, self.latitude) + /// } + /// } + /// + /// assert_eq!("(1.987, 2.983)".to_owned(), + /// format!("{:?}", Position { longitude: 1.987, latitude: 2.983, })); + /// ``` #[stable(feature = "rust1", since = "1.0.0")] fn fmt(&self, f: &mut Formatter) -> Result; } From d0339c7e44ea145acdc779f0ecd078b11d212dc2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Esteban=20K=C3=BCber?= Date: Tue, 7 Nov 2017 18:01:35 -0800 Subject: [PATCH 10/15] Fix help for duplicated names: `extern crate (...) as (...)` On the case of duplicated names caused by an `extern crate` statement with a rename, don't include the inline suggestion, instead using a span label with only the text to avoid incorrect rust code output. --- src/librustc_resolve/build_reduced_graph.rs | 4 ++-- src/librustc_resolve/check_unused.rs | 2 +- src/librustc_resolve/lib.rs | 14 ++++++++++++-- src/librustc_resolve/resolve_imports.rs | 6 +++--- src/test/compile-fail/E0259.rs | 1 + src/test/ui/suggestions/auxiliary/m1.rs | 11 +++++++++++ src/test/ui/suggestions/auxiliary/m2.rs | 11 +++++++++++ src/test/ui/suggestions/extern-crate-rename.rs | 18 ++++++++++++++++++ .../ui/suggestions/extern-crate-rename.stderr | 15 +++++++++++++++ 9 files changed, 74 insertions(+), 8 deletions(-) create mode 100644 src/test/ui/suggestions/auxiliary/m1.rs create mode 100644 src/test/ui/suggestions/auxiliary/m2.rs create mode 100644 src/test/ui/suggestions/extern-crate-rename.rs create mode 100644 src/test/ui/suggestions/extern-crate-rename.stderr diff --git a/src/librustc_resolve/build_reduced_graph.rs b/src/librustc_resolve/build_reduced_graph.rs index a10bce2934226..b30fc38fcbcdf 100644 --- a/src/librustc_resolve/build_reduced_graph.rs +++ b/src/librustc_resolve/build_reduced_graph.rs @@ -250,7 +250,7 @@ impl<'a> Resolver<'a> { } } - ItemKind::ExternCrate(_) => { + ItemKind::ExternCrate(as_name) => { self.crate_loader.process_item(item, &self.definitions); // n.b. we don't need to look at the path option here, because cstore already did @@ -265,7 +265,7 @@ impl<'a> Resolver<'a> { id: item.id, parent, imported_module: Cell::new(Some(module)), - subclass: ImportDirectiveSubclass::ExternCrate, + subclass: ImportDirectiveSubclass::ExternCrate(as_name), span: item.span, module_path: Vec::new(), vis: Cell::new(vis), diff --git a/src/librustc_resolve/check_unused.rs b/src/librustc_resolve/check_unused.rs index a66d1ce0859b7..5820acf1b9006 100644 --- a/src/librustc_resolve/check_unused.rs +++ b/src/librustc_resolve/check_unused.rs @@ -120,7 +120,7 @@ pub fn check_crate(resolver: &mut Resolver, krate: &ast::Crate) { _ if directive.used.get() || directive.vis.get() == ty::Visibility::Public || directive.span.source_equal(&DUMMY_SP) => {} - ImportDirectiveSubclass::ExternCrate => { + ImportDirectiveSubclass::ExternCrate(_) => { resolver.maybe_unused_extern_crates.push((directive.id, directive.span)); } ImportDirectiveSubclass::MacroUse => { diff --git a/src/librustc_resolve/lib.rs b/src/librustc_resolve/lib.rs index bed9f37c5157f..c4185e9080127 100644 --- a/src/librustc_resolve/lib.rs +++ b/src/librustc_resolve/lib.rs @@ -1118,7 +1118,7 @@ impl<'a> NameBinding<'a> { match self.kind { NameBindingKind::Import { directive: &ImportDirective { - subclass: ImportDirectiveSubclass::ExternCrate, .. + subclass: ImportDirectiveSubclass::ExternCrate(_), .. }, .. } => true, _ => false, @@ -1132,6 +1132,15 @@ impl<'a> NameBinding<'a> { } } + fn is_renamed_extern_crate(&self) -> bool { + if let NameBindingKind::Import { directive, ..} = self.kind { + if let ImportDirectiveSubclass::ExternCrate(Some(_)) = directive.subclass { + return true; + } + } + false + } + fn is_glob_import(&self) -> bool { match self.kind { NameBindingKind::Import { directive, .. } => directive.is_glob(), @@ -3700,7 +3709,8 @@ impl<'a> Resolver<'a> { let cm = self.session.codemap(); let rename_msg = "You can use `as` to change the binding name of the import"; - if let Ok(snippet) = cm.span_to_snippet(binding.span) { + if let (Ok(snippet), false) = (cm.span_to_snippet(binding.span), + binding.is_renamed_extern_crate()) { err.span_suggestion(binding.span, rename_msg, format!("{} as Other{}", snippet, name)); diff --git a/src/librustc_resolve/resolve_imports.rs b/src/librustc_resolve/resolve_imports.rs index b85bf18ea800c..bcbabd700946a 100644 --- a/src/librustc_resolve/resolve_imports.rs +++ b/src/librustc_resolve/resolve_imports.rs @@ -23,7 +23,7 @@ use rustc::hir::def_id::DefId; use rustc::hir::def::*; use rustc::util::nodemap::{FxHashMap, FxHashSet}; -use syntax::ast::{Ident, SpannedIdent, NodeId}; +use syntax::ast::{Ident, Name, SpannedIdent, NodeId}; use syntax::ext::base::Determinacy::{self, Determined, Undetermined}; use syntax::ext::hygiene::Mark; use syntax::parse::token; @@ -48,7 +48,7 @@ pub enum ImportDirectiveSubclass<'a> { max_vis: Cell, // The visibility of the greatest reexport. // n.b. `max_vis` is only used in `finalize_import` to check for reexport errors. }, - ExternCrate, + ExternCrate(Option), MacroUse, } @@ -923,7 +923,7 @@ fn import_directive_subclass_to_string(subclass: &ImportDirectiveSubclass) -> St match *subclass { SingleImport { source, .. } => source.to_string(), GlobImport { .. } => "*".to_string(), - ExternCrate => "".to_string(), + ExternCrate(_) => "".to_string(), MacroUse => "#[macro_use]".to_string(), } } diff --git a/src/test/compile-fail/E0259.rs b/src/test/compile-fail/E0259.rs index c285c4d9e00c1..e125cc0c19c37 100644 --- a/src/test/compile-fail/E0259.rs +++ b/src/test/compile-fail/E0259.rs @@ -18,5 +18,6 @@ extern crate libc as alloc; //~^ ERROR E0259 //~| NOTE `alloc` reimported here //~| NOTE `alloc` must be defined only once in the type namespace of this module +//~| NOTE You can use `as` to change the binding name of the import fn main() {} diff --git a/src/test/ui/suggestions/auxiliary/m1.rs b/src/test/ui/suggestions/auxiliary/m1.rs new file mode 100644 index 0000000000000..b61667cfd882c --- /dev/null +++ b/src/test/ui/suggestions/auxiliary/m1.rs @@ -0,0 +1,11 @@ +// 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. + +pub fn foo() {} diff --git a/src/test/ui/suggestions/auxiliary/m2.rs b/src/test/ui/suggestions/auxiliary/m2.rs new file mode 100644 index 0000000000000..94ff5e4497fe9 --- /dev/null +++ b/src/test/ui/suggestions/auxiliary/m2.rs @@ -0,0 +1,11 @@ +// 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. + +pub fn bar() {} diff --git a/src/test/ui/suggestions/extern-crate-rename.rs b/src/test/ui/suggestions/extern-crate-rename.rs new file mode 100644 index 0000000000000..b3fa5871a82f5 --- /dev/null +++ b/src/test/ui/suggestions/extern-crate-rename.rs @@ -0,0 +1,18 @@ +// 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. + +// aux-build:m1.rs +// aux-build:m2.rs + + +extern crate m1; +extern crate m2 as m1; + +fn main() {} diff --git a/src/test/ui/suggestions/extern-crate-rename.stderr b/src/test/ui/suggestions/extern-crate-rename.stderr new file mode 100644 index 0000000000000..c15e238e8b0a3 --- /dev/null +++ b/src/test/ui/suggestions/extern-crate-rename.stderr @@ -0,0 +1,15 @@ +error[E0259]: the name `m1` is defined multiple times + --> $DIR/extern-crate-rename.rs:16:1 + | +15 | extern crate m1; + | ---------------- previous import of the extern crate `m1` here +16 | extern crate m2 as m1; + | ^^^^^^^^^^^^^^^^^^^^^^ + | | + | `m1` reimported here + | You can use `as` to change the binding name of the import + | + = note: `m1` must be defined only once in the type namespace of this module + +error: aborting due to previous error + From cd32aff3fcdea295ed147bc16eb9299fe9876c0f Mon Sep 17 00:00:00 2001 From: John Ford Date: Wed, 8 Nov 2017 22:40:35 +0100 Subject: [PATCH 11/15] get() example should use get() not get_mut() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit I'm really new to Rust, this is the first thing I've ever actually pushed to github in a rust project, so please double check that it's correct. I noticed that the in-doc example for the string's get() function was referring to get_mut(). Looks like a copy/paste issue. ```rust fn main() { let v = String::from("🗻∈🌏"); assert_eq!(Some("🗻"), v.get(0..4)); // indices not on UTF-8 sequence boundaries assert!(v.get(1..).is_none()); assert!(v.get(..8).is_none()); // out of bounds assert!(v.get(..42).is_none()); } ``` results in: ``` jhford-work:~/rust/redish $ cat get-example.rs fn main() { let v = String::from("🗻∈🌏"); assert_eq!(Some("🗻"), v.get(0..4)); // indices not on UTF-8 sequence boundaries assert!(v.get(1..).is_none()); assert!(v.get(..8).is_none()); // out of bounds assert!(v.get(..42).is_none()); } jhford-work:~/rust/redish $ rustc get-example.rs jhford-work:~/rust/redish $ ./get-example ; echo $? 0 ``` I did not build an entire rust toolchain as I'm not totally sure how to do that. --- src/liballoc/str.rs | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/liballoc/str.rs b/src/liballoc/str.rs index 5f0b4088fc07e..a167b2e57c078 100644 --- a/src/liballoc/str.rs +++ b/src/liballoc/str.rs @@ -363,16 +363,16 @@ impl str { /// # Examples /// /// ``` - /// let mut v = String::from("🗻∈🌏"); + /// let v = String::from("🗻∈🌏"); /// /// assert_eq!(Some("🗻"), v.get(0..4)); /// /// // indices not on UTF-8 sequence boundaries - /// assert!(v.get_mut(1..).is_none()); - /// assert!(v.get_mut(..8).is_none()); + /// assert!(v.get(1..).is_none()); + /// assert!(v.get(..8).is_none()); /// /// // out of bounds - /// assert!(v.get_mut(..42).is_none()); + /// assert!(v.get(..42).is_none()); /// ``` #[stable(feature = "str_checked_slicing", since = "1.20.0")] #[inline] From 47ed4738d927c5415956f5420e4d633917111398 Mon Sep 17 00:00:00 2001 From: Jorge Aparicio Date: Thu, 9 Nov 2017 00:20:55 +0100 Subject: [PATCH 12/15] fix core for targets with max-atomic-width = 0 closes #45802 --- src/libcore/sync/atomic.rs | 1 + 1 file changed, 1 insertion(+) diff --git a/src/libcore/sync/atomic.rs b/src/libcore/sync/atomic.rs index cd3dd9ce1399e..b7cf6d778a2f9 100644 --- a/src/libcore/sync/atomic.rs +++ b/src/libcore/sync/atomic.rs @@ -927,6 +927,7 @@ impl AtomicPtr { } } +#[cfg(target_has_atomic = "ptr")] #[stable(feature = "atomic_from", since = "1.23.0")] impl From<*mut T> for AtomicPtr { #[inline] From 6a92c0fdbddbda6fcb0c6215f64240d228e4b2f5 Mon Sep 17 00:00:00 2001 From: Konrad Borowski Date: Thu, 9 Nov 2017 12:36:38 +0100 Subject: [PATCH 13/15] Allow a trailing comma in assert_eq/ne macro --- src/libcore/macros.rs | 6 ++++++ .../assert-eq-trailing-comma.rs} | 0 .../assert-ne-trailing-comma.rs} | 0 src/test/ui/macros/assert_eq_trailing_comma.stderr | 8 -------- src/test/ui/macros/assert_ne_trailing_comma.stderr | 8 -------- 5 files changed, 6 insertions(+), 16 deletions(-) rename src/test/{ui/macros/assert_eq_trailing_comma.rs => run-pass/assert-eq-trailing-comma.rs} (100%) rename src/test/{ui/macros/assert_ne_trailing_comma.rs => run-pass/assert-ne-trailing-comma.rs} (100%) delete mode 100644 src/test/ui/macros/assert_eq_trailing_comma.stderr delete mode 100644 src/test/ui/macros/assert_ne_trailing_comma.stderr diff --git a/src/libcore/macros.rs b/src/libcore/macros.rs index 12667036444e6..c410c2d900470 100644 --- a/src/libcore/macros.rs +++ b/src/libcore/macros.rs @@ -120,6 +120,9 @@ macro_rules! assert_eq { } } }); + ($left:expr, $right:expr,) => ({ + assert_eq!($left, $right) + }); ($left:expr, $right:expr, $($arg:tt)+) => ({ match (&($left), &($right)) { (left_val, right_val) => { @@ -168,6 +171,9 @@ macro_rules! assert_ne { } } }); + ($left:expr, $right:expr,) => { + assert_ne!($left, $right) + }; ($left:expr, $right:expr, $($arg:tt)+) => ({ match (&($left), &($right)) { (left_val, right_val) => { diff --git a/src/test/ui/macros/assert_eq_trailing_comma.rs b/src/test/run-pass/assert-eq-trailing-comma.rs similarity index 100% rename from src/test/ui/macros/assert_eq_trailing_comma.rs rename to src/test/run-pass/assert-eq-trailing-comma.rs diff --git a/src/test/ui/macros/assert_ne_trailing_comma.rs b/src/test/run-pass/assert-ne-trailing-comma.rs similarity index 100% rename from src/test/ui/macros/assert_ne_trailing_comma.rs rename to src/test/run-pass/assert-ne-trailing-comma.rs diff --git a/src/test/ui/macros/assert_eq_trailing_comma.stderr b/src/test/ui/macros/assert_eq_trailing_comma.stderr deleted file mode 100644 index 1b46e94584e6b..0000000000000 --- a/src/test/ui/macros/assert_eq_trailing_comma.stderr +++ /dev/null @@ -1,8 +0,0 @@ -error: unexpected end of macro invocation - --> $DIR/assert_eq_trailing_comma.rs:12:20 - | -12 | assert_eq!(1, 1,); - | ^ - -error: aborting due to previous error - diff --git a/src/test/ui/macros/assert_ne_trailing_comma.stderr b/src/test/ui/macros/assert_ne_trailing_comma.stderr deleted file mode 100644 index 33d2cb0ed8242..0000000000000 --- a/src/test/ui/macros/assert_ne_trailing_comma.stderr +++ /dev/null @@ -1,8 +0,0 @@ -error: unexpected end of macro invocation - --> $DIR/assert_ne_trailing_comma.rs:12:20 - | -12 | assert_ne!(1, 2,); - | ^ - -error: aborting due to previous error - From 48655ea6610d1bdffacb4b8730c53e4803fc9cfd Mon Sep 17 00:00:00 2001 From: Ariel Ben-Yehuda Date: Thu, 9 Nov 2017 23:03:03 +0200 Subject: [PATCH 14/15] add a bunch of debug logging to transform::inline --- src/librustc_mir/transform/inline.rs | 29 ++++++++++++++++++++++------ 1 file changed, 23 insertions(+), 6 deletions(-) diff --git a/src/librustc_mir/transform/inline.rs b/src/librustc_mir/transform/inline.rs index f2453d3946172..95e9c8f6df882 100644 --- a/src/librustc_mir/transform/inline.rs +++ b/src/librustc_mir/transform/inline.rs @@ -37,7 +37,7 @@ const UNKNOWN_SIZE_COST: usize = 10; pub struct Inline; -#[derive(Copy, Clone)] +#[derive(Copy, Clone, Debug)] struct CallSite<'tcx> { callee: DefId, substs: &'tcx Substs<'tcx>, @@ -113,7 +113,9 @@ impl<'a, 'tcx> Inliner<'a, 'tcx> { loop { local_change = false; while let Some(callsite) = callsites.pop_front() { + debug!("checking whether to inline callsite {:?}", callsite); if !self.tcx.is_mir_available(callsite.callee) { + debug!("checking whether to inline callsite {:?} - MIR unavailable", callsite); continue; } @@ -133,10 +135,12 @@ impl<'a, 'tcx> Inliner<'a, 'tcx> { }; let start = caller_mir.basic_blocks().len(); - + debug!("attempting to inline callsite {:?} - mir={:?}", callsite, callee_mir); if !self.inline_call(callsite, caller_mir, callee_mir) { + debug!("attempting to inline callsite {:?} - failure", callsite); continue; } + debug!("attempting to inline callsite {:?} - success", callsite); // Add callsites from inlined function for (bb, bb_data) in caller_mir.basic_blocks().iter_enumerated().skip(start) { @@ -180,16 +184,19 @@ impl<'a, 'tcx> Inliner<'a, 'tcx> { callee_mir: &Mir<'tcx>) -> bool { + debug!("should_inline({:?})", callsite); let tcx = self.tcx; // Don't inline closures that have captures // FIXME: Handle closures better if callee_mir.upvar_decls.len() > 0 { + debug!(" upvar decls present - not inlining"); return false; } // Cannot inline generators which haven't been transformed yet if callee_mir.yield_ty.is_some() { + debug!(" yield ty present - not inlining"); return false; } @@ -201,7 +208,10 @@ impl<'a, 'tcx> Inliner<'a, 'tcx> { // there are cases that prevent inlining that we // need to check for first. attr::InlineAttr::Always => true, - attr::InlineAttr::Never => return false, + attr::InlineAttr::Never => { + debug!("#[inline(never)] present - not inlining"); + return false + } attr::InlineAttr::Hint => true, attr::InlineAttr::None => false, }; @@ -211,6 +221,7 @@ impl<'a, 'tcx> Inliner<'a, 'tcx> { // reference unexported symbols if callsite.callee.is_local() { if callsite.substs.types().count() == 0 && !hinted { + debug!(" callee is an exported function - not inlining"); return false; } } @@ -232,6 +243,7 @@ impl<'a, 'tcx> Inliner<'a, 'tcx> { if callee_mir.basic_blocks().len() <= 3 { threshold += threshold / 4; } + debug!(" final inline threshold = {}", threshold); // FIXME: Give a bonus to functions with only a single caller @@ -327,12 +339,17 @@ impl<'a, 'tcx> Inliner<'a, 'tcx> { } } - debug!("Inline cost for {:?} is {}", callsite.callee, cost); - if let attr::InlineAttr::Always = hint { + debug!("INLINING {:?} because inline(always) [cost={}]", callsite, cost); true } else { - cost <= threshold + if cost <= threshold { + debug!("INLINING {:?} [cost={} <= threshold={}]", callsite, cost, threshold); + true + } else { + debug!("NOT inlining {:?} [cost={} > threshold={}]", callsite, cost, threshold); + false + } } } From 0872cda34a6455c3304f7ede3e22dc769252f1aa Mon Sep 17 00:00:00 2001 From: Robin Kruppe Date: Fri, 10 Nov 2017 01:26:22 +0100 Subject: [PATCH 15/15] Fix typo in -Zsaturating-float-casts test --- src/test/run-pass/saturating-float-casts.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/test/run-pass/saturating-float-casts.rs b/src/test/run-pass/saturating-float-casts.rs index 6db4d7635f07f..010ecebb1bbe3 100644 --- a/src/test/run-pass/saturating-float-casts.rs +++ b/src/test/run-pass/saturating-float-casts.rs @@ -48,8 +48,8 @@ macro_rules! test_c { }); ($fval:expr, f* -> $ity:ident, $ival:expr) => ( - test!($fval, f32 -> $ity, $ival); - test!($fval, f64 -> $ity, $ival); + test_c!($fval, f32 -> $ity, $ival); + test_c!($fval, f64 -> $ity, $ival); ) }