Images will output artifacts in an `obj` dir at the root of a repository.
+## Filesystem layout
+
+- Each directory, excluding `scripts` and `disabled`, corresponds to a docker image
+- `scripts` contains files shared by docker images
+- `disabled` contains images that are not build travis
+
## Cross toolchains
A number of these images take quite a long time to compile as they're building
+++ /dev/null
-#!/bin/sh
-# 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 <LICENSE-APACHE or
-# http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
-# <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
-# option. This file may not be copied, modified, or distributed
-# except according to those terms.
-
-set -ex
-
-URL=https://dl.google.com/android/repository
-
-download_ndk() {
- mkdir -p /android/ndk
- cd /android/ndk
- curl -O $URL/$1
- unzip -q $1
- rm $1
- mv android-ndk-* ndk
-}
-
-make_standalone_toolchain() {
- # See https://developer.android.com/ndk/guides/standalone_toolchain.htm
- python2.7 /android/ndk/ndk/build/tools/make_standalone_toolchain.py \
- --install-dir /android/ndk/$1-$2 \
- --arch $1 \
- --api $2
-}
-
-remove_ndk() {
- rm -rf /android/ndk/ndk
-}
RUN apt-get update && \
apt-get install -y --no-install-recommends \
+ ca-certificates \
+ cmake \
+ curl \
+ file \
g++ \
+ git \
+ libssl-dev \
make \
- file \
- curl \
- ca-certificates \
+ pkg-config \
python2.7 \
- git \
- cmake \
- unzip \
sudo \
- xz-utils \
- libssl-dev \
- pkg-config
-
-RUN curl -OL https://github.com/Yelp/dumb-init/releases/download/v1.2.0/dumb-init_1.2.0_amd64.deb && \
- dpkg -i dumb-init_*.deb && \
- rm dumb-init_*.deb
+ unzip \
+ xz-utils
-RUN curl -o /usr/local/bin/sccache \
- https://s3.amazonaws.com/rust-lang-ci/rust-ci-mirror/2017-05-12-sccache-x86_64-unknown-linux-musl && \
- chmod +x /usr/local/bin/sccache
+# dumb-init
+COPY scripts/dumb-init.sh /scripts/
+RUN sh /scripts/dumb-init.sh
-# Install NDK
-COPY install-ndk.sh /tmp
-RUN . /tmp/install-ndk.sh && \
- download_ndk android-ndk-r13b-linux-x86_64.zip && \
- make_standalone_toolchain arm 9 && \
- remove_ndk
+# ndk
+COPY scripts/android-ndk.sh /scripts/
+RUN . /scripts/android-ndk.sh && \
+ download_and_make_toolchain android-ndk-r13b-linux-x86_64.zip arm 9
-# Install SDK
+# sdk
RUN dpkg --add-architecture i386 && \
apt-get update && \
apt-get install -y --no-install-recommends \
- openjdk-9-jre-headless \
- tzdata \
- libstdc++6:i386 \
libgl1-mesa-glx \
- libpulse0
+ libpulse0 \
+ libstdc++6:i386 \
+ openjdk-9-jre-headless \
+ tzdata
-COPY install-sdk.sh /tmp
-RUN . /tmp/install-sdk.sh && \
- download_sdk tools_r25.2.5-linux.zip && \
- download_sysimage armeabi-v7a 18 && \
- create_avd armeabi-v7a 18
+COPY scripts/android-sdk.sh /scripts/
+RUN . /scripts/android-sdk.sh && \
+ download_and_create_avd tools_r25.2.5-linux.zip armeabi-v7a 18
-# Setup env
+# env
ENV PATH=$PATH:/android/sdk/tools
ENV PATH=$PATH:/android/sdk/platform-tools
--target=$TARGETS \
--arm-linux-androideabi-ndk=/android/ndk/arm-9
-ENV SCRIPT python2.7 ../x.py test --target $TARGETS --verbose
+ENV SCRIPT python2.7 ../x.py test --target $TARGETS
+
+# sccache
+COPY scripts/sccache.sh /scripts/
+RUN sh /scripts/sccache.sh
-# Entrypoint
-COPY start-emulator.sh /android/
-ENTRYPOINT ["/usr/bin/dumb-init", "--", "/android/start-emulator.sh"]
+# init
+COPY scripts/android-start-emulator.sh /scripts/
+ENTRYPOINT ["/usr/bin/dumb-init", "--", "/scripts/android-start-emulator.sh"]
+++ /dev/null
-#!/bin/sh
-# Copyright 2016 The Rust Project Developers. See the COPYRIGHT
-# file at the top-level directory of this distribution and at
-# http://rust-lang.org/COPYRIGHT.
-#
-# Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
-# http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
-# <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
-# option. This file may not be copied, modified, or distributed
-# except according to those terms.
-
-set -ex
-
-URL=https://dl.google.com/android/repository
-
-download_ndk() {
- mkdir -p /android/ndk
- cd /android/ndk
- curl -O $URL/$1
- unzip -q $1
- rm $1
- mv android-ndk-* ndk
-}
-
-make_standalone_toolchain() {
- # See https://developer.android.com/ndk/guides/standalone_toolchain.html
- python2.7 /android/ndk/ndk/build/tools/make_standalone_toolchain.py \
- --install-dir /android/ndk/$1-$2 \
- --arch $1 \
- --api $2
-}
-
-remove_ndk() {
- rm -rf /android/ndk/ndk
-}
+++ /dev/null
-#!/bin/sh
-# 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 <LICENSE-APACHE or
-# http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
-# <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
-# option. This file may not be copied, modified, or distributed
-# except according to those terms.
-
-set -ex
-
-URL=https://dl.google.com/android/repository
-
-download_sdk() {
- mkdir -p /android/sdk
- cd /android/sdk
- curl -O $URL/$1
- unzip -q $1
- rm -rf $1
-}
-
-download_sysimage() {
- # See https://developer.android.com/studio/tools/help/android.html
- abi=$1
- api=$2
-
- filter="platform-tools,android-$api"
- filter="$filter,sys-img-$abi-android-$api"
-
- # Keep printing yes to accept the licenses
- while true; do echo yes; sleep 10; done | \
- /android/sdk/tools/android update sdk -a --no-ui \
- --filter "$filter"
-}
-
-create_avd() {
- # See https://developer.android.com/studio/tools/help/android.html
- abi=$1
- api=$2
-
- echo no | \
- /android/sdk/tools/android create avd \
- --name $abi-$api \
- --target android-$api \
- --abi $abi
-}
-
+++ /dev/null
-#!/bin/sh
-# Copyright 2016 The Rust Project Developers. See the COPYRIGHT
-# file at the top-level directory of this distribution and at
-# http://rust-lang.org/COPYRIGHT.
-#
-# Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
-# http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
-# <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
-# option. This file may not be copied, modified, or distributed
-# except according to those terms.
-
-set -ex
-
-# Setting SHELL to a file instead on a symlink helps android
-# emulator identify the system
-export SHELL=/bin/bash
-
-# Using the default qemu2 engine makes time::tests::since_epoch fails because
-# the emulator date is set to unix epoch (in armeabi-v7a-18 image). Using
-# classic engine the emulator starts with the current date and the tests run
-# fine. If another image is used, this need to be evaluated again.
-nohup nohup emulator @armeabi-v7a-18 \
- -engine classic -no-window -partition-size 2047 0<&- &>/dev/null &
-
-exec "$@"
# The `vexpress_config` config file was a previously generated config file for
# the kernel. This file was generated by running `make vexpress_defconfig`
# followed by `make menuconfig` and then enabling the IPv6 protocol page.
-COPY vexpress_config /build/.config
+COPY armhf-gnu/vexpress_config /build/.config
RUN curl https://cdn.kernel.org/pub/linux/kernel/v4.x/linux-4.4.42.tar.xz | \
tar xJf - && \
cd /build/linux-4.4.42 && \
# Copy over our init script, which starts up our test server and also a few
# other misc tasks.
-COPY rcS rootfs/etc/init.d/rcS
+COPY armhf-gnu/rcS rootfs/etc/init.d/rcS
RUN chmod +x rootfs/etc/init.d/rcS
# Helper to quickly fill the entropy pool in the kernel.
-COPY addentropy.c /tmp/
+COPY armhf-gnu/addentropy.c /tmp/
RUN arm-linux-gnueabihf-gcc addentropy.c -o rootfs/addentropy -static
# TODO: What is this?!
WORKDIR /tmp
-COPY build-rumprun.sh /tmp/
+COPY cross/build-rumprun.sh /tmp/
RUN ./build-rumprun.sh
-COPY build-arm-musl.sh /tmp/
+COPY cross/build-arm-musl.sh /tmp/
RUN ./build-arm-musl.sh
# originally from
RUN apt-get update && \
apt-get install -y --no-install-recommends \
+ ca-certificates \
+ cmake \
+ curl \
+ file \
g++ \
+ git \
+ libssl-dev \
make \
- file \
- curl \
- ca-certificates \
+ pkg-config \
python2.7 \
- git \
- cmake \
- unzip \
sudo \
- xz-utils \
- libssl-dev \
- pkg-config
-
-RUN curl -OL https://github.com/Yelp/dumb-init/releases/download/v1.2.0/dumb-init_1.2.0_amd64.deb && \
- dpkg -i dumb-init_*.deb && \
- rm dumb-init_*.deb
-
-RUN curl -o /usr/local/bin/sccache \
- https://s3.amazonaws.com/rust-lang-ci/rust-ci-mirror/2017-05-12-sccache-x86_64-unknown-linux-musl && \
- chmod +x /usr/local/bin/sccache
+ unzip \
+ xz-utils
-ENTRYPOINT ["/usr/bin/dumb-init", "--"]
+# dumb-init
+COPY scripts/dumb-init.sh /scripts/
+RUN sh /scripts/dumb-init.sh
-COPY android-ndk.sh /
-RUN . /android-ndk.sh && \
- download_ndk android-ndk-r13b-linux-x86_64.zip && \
- make_standalone_toolchain arm64 21 && \
- remove_ndk
+# ndk
+COPY scripts/android-ndk.sh /scripts/
+RUN . /scripts/android-ndk.sh && \
+ download_and_make_toolchain android-ndk-r13b-linux-x86_64.zip arm64 21
+# env
ENV PATH=$PATH:/android/ndk/arm64-21/bin
ENV DEP_Z_ROOT=/android/ndk/arm64-21/sysroot/usr/
--enable-cargo-openssl-static
ENV SCRIPT python2.7 ../x.py dist --target $HOSTS --host $HOSTS
+
+# sccache
+COPY scripts/sccache.sh /scripts/
+RUN sh /scripts/sccache.sh
+
+# init
+ENTRYPOINT ["/usr/bin/dumb-init", "--"]
RUN apt-get update && \
apt-get install -y --no-install-recommends \
+ ca-certificates \
+ cmake \
+ curl \
+ file \
g++ \
+ git \
+ libssl-dev \
make \
- file \
- curl \
- ca-certificates \
+ pkg-config \
python2.7 \
- git \
- cmake \
- unzip \
sudo \
- xz-utils \
- libssl-dev \
- pkg-config
-
-RUN curl -OL https://github.com/Yelp/dumb-init/releases/download/v1.2.0/dumb-init_1.2.0_amd64.deb && \
- dpkg -i dumb-init_*.deb && \
- rm dumb-init_*.deb
-
-RUN curl -o /usr/local/bin/sccache \
- https://s3.amazonaws.com/rust-lang-ci/rust-ci-mirror/2017-05-12-sccache-x86_64-unknown-linux-musl && \
- chmod +x /usr/local/bin/sccache
+ unzip \
+ xz-utils
-ENTRYPOINT ["/usr/bin/dumb-init", "--"]
+# dumb-init
+COPY scripts/dumb-init.sh /scripts/
+RUN sh /scripts/dumb-init.sh
-COPY android-ndk.sh /
-RUN . /android-ndk.sh && \
+# ndk
+COPY scripts/android-ndk.sh /scripts/
+RUN . /scripts/android-ndk.sh && \
download_ndk android-ndk-r13b-linux-x86_64.zip && \
make_standalone_toolchain arm 9 && \
make_standalone_toolchain arm 21 && \
remove_ndk
+RUN chmod 777 /android/ndk && \
+ ln -s /android/ndk/arm-21 /android/ndk/arm
+
+# env
ENV PATH=$PATH:/android/ndk/arm-9/bin
ENV DEP_Z_ROOT=/android/ndk/arm-9/sysroot/usr/
# level 9), the default linker behavior is to generate an error, to allow the
# build to finish we use --warn-unresolved-symbols. Note that the missing
# symbols does not affect std, only the compiler (llvm) and cargo (openssl).
-RUN chmod 777 /android/ndk && \
- ln -s /android/ndk/arm-21 /android/ndk/arm
-
ENV SCRIPT \
python2.7 ../x.py build src/llvm --host $HOSTS --target $HOSTS && \
(export RUSTFLAGS="\"-C link-arg=-Wl,--warn-unresolved-symbols\""; \
rm /android/ndk/arm && \
ln -s /android/ndk/arm-9 /android/ndk/arm && \
python2.7 ../x.py dist --host $HOSTS --target $HOSTS)
+
+# sccache
+COPY scripts/sccache.sh /scripts/
+RUN sh /scripts/sccache.sh
+
+# init
+ENTRYPOINT ["/usr/bin/dumb-init", "--"]
RUN apt-get update && \
apt-get install -y --no-install-recommends \
+ ca-certificates \
+ cmake \
+ curl \
+ file \
g++ \
+ git \
+ libssl-dev \
make \
- file \
- curl \
- ca-certificates \
+ pkg-config \
python2.7 \
- git \
- cmake \
- unzip \
sudo \
- xz-utils \
- libssl-dev \
- pkg-config
-
-RUN curl -OL https://github.com/Yelp/dumb-init/releases/download/v1.2.0/dumb-init_1.2.0_amd64.deb && \
- dpkg -i dumb-init_*.deb && \
- rm dumb-init_*.deb
-
-RUN curl -o /usr/local/bin/sccache \
- https://s3.amazonaws.com/rust-lang-ci/rust-ci-mirror/2017-05-12-sccache-x86_64-unknown-linux-musl && \
- chmod +x /usr/local/bin/sccache
+ unzip \
+ xz-utils
-ENTRYPOINT ["/usr/bin/dumb-init", "--"]
+# dumb-init
+COPY scripts/dumb-init.sh /scripts/
+RUN sh /scripts/dumb-init.sh
-COPY android-ndk.sh /
-RUN . /android-ndk.sh && \
+# ndk
+COPY scripts/android-ndk.sh /scripts/
+RUN . /scripts/android-ndk.sh && \
download_ndk android-ndk-r13b-linux-x86_64.zip && \
make_standalone_toolchain x86 9 && \
make_standalone_toolchain x86 21 && \
remove_ndk
+RUN chmod 777 /android/ndk && \
+ ln -s /android/ndk/x86-21 /android/ndk/x86
+
+# env
ENV PATH=$PATH:/android/ndk/x86-9/bin
ENV DEP_Z_ROOT=/android/ndk/x86-9/sysroot/usr/
# level 9), the default linker behavior is to generate an error, to allow the
# build to finish we use --warn-unresolved-symbols. Note that the missing
# symbols does not affect std, only the compiler (llvm) and cargo (openssl).
-RUN chmod 777 /android/ndk && \
- ln -s /android/ndk/x86-21 /android/ndk/x86
-
ENV SCRIPT \
python2.7 ../x.py build src/llvm --host $HOSTS --target $HOSTS && \
(export RUSTFLAGS="\"-C link-arg=-Wl,--warn-unresolved-symbols\""; \
rm /android/ndk/x86 && \
ln -s /android/ndk/x86-9 /android/ndk/x86 && \
python2.7 ../x.py dist --host $HOSTS --target $HOSTS)
+
+# sccache
+COPY scripts/sccache.sh /scripts/
+RUN sh /scripts/sccache.sh
+
+# init
+ENTRYPOINT ["/usr/bin/dumb-init", "--"]
RUN apt-get update && \
apt-get install -y --no-install-recommends \
+ ca-certificates \
+ cmake \
+ curl \
+ file \
g++ \
+ git \
+ libssl-dev \
make \
- file \
- curl \
- ca-certificates \
+ pkg-config \
python2.7 \
- git \
- cmake \
- unzip \
sudo \
- xz-utils \
- libssl-dev \
- pkg-config
-
-RUN curl -OL https://github.com/Yelp/dumb-init/releases/download/v1.2.0/dumb-init_1.2.0_amd64.deb && \
- dpkg -i dumb-init_*.deb && \
- rm dumb-init_*.deb
-
-RUN curl -o /usr/local/bin/sccache \
- https://s3.amazonaws.com/rust-lang-ci/rust-ci-mirror/2017-05-12-sccache-x86_64-unknown-linux-musl && \
- chmod +x /usr/local/bin/sccache
+ unzip \
+ xz-utils
-ENTRYPOINT ["/usr/bin/dumb-init", "--"]
+# dumb-init
+COPY scripts/dumb-init.sh /scripts/
+RUN sh /scripts/dumb-init.sh
-COPY android-ndk.sh /
-RUN . /android-ndk.sh && \
- download_ndk android-ndk-r13b-linux-x86_64.zip && \
- make_standalone_toolchain x86_64 21 && \
- remove_ndk
+# ndk
+COPY scripts/android-ndk.sh /scripts/
+RUN . /scripts/android-ndk.sh && \
+ download_and_make_toolchain android-ndk-r13b-linux-x86_64.zip x86_64 21
+# env
ENV PATH=$PATH:/android/ndk/x86_64-21/bin
ENV DEP_Z_ROOT=/android/ndk/x86_64-21/sysroot/usr/
--enable-cargo-openssl-static
ENV SCRIPT python2.7 ../x.py dist --target $HOSTS --host $HOSTS
+
+# sccache
+COPY scripts/sccache.sh /scripts/
+RUN sh /scripts/sccache.sh
+
+# init
+ENTRYPOINT ["/usr/bin/dumb-init", "--"]
USER rustbuild
WORKDIR /tmp
-COPY aarch64-linux-gnu.config build-toolchains.sh /tmp/
+COPY dist-aarch64-linux/aarch64-linux-gnu.config dist-aarch64-linux/build-toolchains.sh /tmp/
RUN ./build-toolchains.sh
USER root
RUN apt-get update && \
apt-get install -y --no-install-recommends \
+ ca-certificates \
+ cmake \
+ curl \
+ file \
g++ \
+ git \
+ libssl-dev \
make \
- file \
- curl \
- ca-certificates \
+ pkg-config \
python2.7 \
- git \
- cmake \
- unzip \
sudo \
- xz-utils \
- libssl-dev \
- pkg-config
-
-RUN curl -OL https://github.com/Yelp/dumb-init/releases/download/v1.2.0/dumb-init_1.2.0_amd64.deb && \
- dpkg -i dumb-init_*.deb && \
- rm dumb-init_*.deb
-
-RUN curl -o /usr/local/bin/sccache \
- https://s3.amazonaws.com/rust-lang-ci/rust-ci-mirror/2017-05-12-sccache-x86_64-unknown-linux-musl && \
- chmod +x /usr/local/bin/sccache
+ unzip \
+ xz-utils
-ENTRYPOINT ["/usr/bin/dumb-init", "--"]
+# dumb-init
+COPY scripts/dumb-init.sh /scripts/
+RUN sh /scripts/dumb-init.sh
-# Install NDK
-COPY install-ndk.sh /tmp
-RUN . /tmp/install-ndk.sh && \
+# ndk
+COPY scripts/android-ndk.sh /scripts/
+RUN . /scripts/android-ndk.sh && \
download_ndk android-ndk-r13b-linux-x86_64.zip && \
make_standalone_toolchain arm 9 && \
make_standalone_toolchain x86 9 && \
make_standalone_toolchain x86_64 21 && \
remove_ndk
+# env
ENV TARGETS=arm-linux-androideabi
ENV TARGETS=$TARGETS,armv7-linux-androideabi
ENV TARGETS=$TARGETS,i686-linux-android
--x86_64-linux-android-ndk=/android/ndk/x86_64-21
ENV SCRIPT python2.7 ../x.py dist --target $TARGETS
+
+# cache
+COPY scripts/sccache.sh /scripts/
+RUN sh /scripts/sccache.sh
+
+# init
+ENTRYPOINT ["/usr/bin/dumb-init", "--"]
+++ /dev/null
-#!/bin/sh
-# Copyright 2016 The Rust Project Developers. See the COPYRIGHT
-# file at the top-level directory of this distribution and at
-# http://rust-lang.org/COPYRIGHT.
-#
-# Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
-# http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
-# <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
-# option. This file may not be copied, modified, or distributed
-# except according to those terms.
-
-set -ex
-
-URL=https://dl.google.com/android/repository
-
-download_ndk() {
- mkdir -p /android/ndk
- cd /android/ndk
- curl -O $URL/$1
- unzip -q $1
- rm $1
- mv android-ndk-* ndk
-}
-
-make_standalone_toolchain() {
- # See https://developer.android.com/ndk/guides/standalone_toolchain.html
- python2.7 /android/ndk/ndk/build/tools/make_standalone_toolchain.py \
- --install-dir /android/ndk/$1-$2 \
- --arch $1 \
- --api $2
-}
-
-remove_ndk() {
- rm -rf /android/ndk/ndk
-}
USER rustbuild
WORKDIR /tmp
-COPY arm-linux-gnueabi.config build-toolchains.sh /tmp/
+COPY dist-arm-linux/arm-linux-gnueabi.config dist-arm-linux/build-toolchains.sh /tmp/
RUN ./build-toolchains.sh
USER root
USER rustbuild
WORKDIR /tmp
-COPY arm-linux-gnueabihf.config build-toolchains.sh /tmp/
+COPY dist-armhf-linux/arm-linux-gnueabihf.config dist-armhf-linux/build-toolchains.sh /tmp/
RUN ./build-toolchains.sh
USER root
USER rustbuild
WORKDIR /tmp
-COPY build-toolchains.sh armv7-linux-gnueabihf.config /tmp/
+COPY dist-armv7-linux/build-toolchains.sh dist-armv7-linux/armv7-linux-gnueabihf.config /tmp/
RUN ./build-toolchains.sh
USER root
tar xzf - -C /usr/local --strip-components=1
WORKDIR /tmp
-COPY shared.sh build-toolchain.sh compiler-rt-dso-handle.patch /tmp/
+COPY dist-fuchsia/shared.sh dist-fuchsia/build-toolchain.sh dist-fuchsia/compiler-rt-dso-handle.patch /tmp/
RUN /tmp/build-toolchain.sh
RUN curl -OL https://github.com/Yelp/dumb-init/releases/download/v1.2.0/dumb-init_1.2.0_amd64.deb && \
pkg-config
WORKDIR /build/
-COPY musl-libunwind-patch.patch build-musl.sh /build/
+COPY dist-i586-gnu-i686-musl/musl-libunwind-patch.patch dist-i586-gnu-i686-musl/build-musl.sh /build/
RUN sh /build/build-musl.sh && rm -rf /build
RUN curl -OL https://github.com/Yelp/dumb-init/releases/download/v1.2.0/dumb-init_1.2.0_amd64.deb && \
libssl-dev \
pkg-config
-COPY build-toolchain.sh /tmp/
+COPY dist-i686-freebsd/build-toolchain.sh /tmp/
RUN /tmp/build-toolchain.sh i686
RUN curl -OL https://github.com/Yelp/dumb-init/releases/download/v1.2.0/dumb-init_1.2.0_amd64.deb && \
ENV LD_LIBRARY_PATH=/rustroot/lib64:/rustroot/lib
ENV PKG_CONFIG_PATH=/rustroot/lib/pkgconfig
WORKDIR /tmp
-COPY shared.sh build-binutils.sh /tmp/
+COPY dist-i686-linux/shared.sh dist-i686-linux/build-binutils.sh /tmp/
# We need a build of openssl which supports SNI to download artifacts from
# static.rust-lang.org. This'll be used to link into libcurl below (and used
# later as well), so build a copy of OpenSSL with dynamic libraries into our
# generic root.
-COPY build-openssl.sh /tmp/
+COPY dist-i686-linux/build-openssl.sh /tmp/
RUN ./build-openssl.sh
# The `curl` binary on CentOS doesn't support SNI which is needed for fetching
#
# Note that we also disable a bunch of optional features of curl that we don't
# really need.
-COPY build-curl.sh /tmp/
+COPY dist-i686-linux/build-curl.sh /tmp/
RUN ./build-curl.sh
# binutils < 2.22 has a bug where the 32-bit executables it generates
RUN ./build-binutils.sh
# Need a newer version of gcc than centos has to compile LLVM nowadays
-COPY build-gcc.sh /tmp/
+COPY dist-i686-linux/build-gcc.sh /tmp/
RUN ./build-gcc.sh
# CentOS 5.5 has Python 2.4 by default, but LLVM needs 2.7+
-COPY build-python.sh /tmp/
+COPY dist-i686-linux/build-python.sh /tmp/
RUN ./build-python.sh
# Apparently CentOS 5.5 desn't have `git` in yum, but we're gonna need it for
# cloning, so download and build it here.
-COPY build-git.sh /tmp/
+COPY dist-i686-linux/build-git.sh /tmp/
RUN ./build-git.sh
# libssh2 (a dependency of Cargo) requires cmake 2.8.11 or higher but CentOS
# only has 2.6.4, so build our own
-COPY build-cmake.sh /tmp/
+COPY dist-i686-linux/build-cmake.sh /tmp/
RUN ./build-cmake.sh
# for sanitizers, we need kernel headers files newer than the ones CentOS ships
# with so we install newer ones here
-COPY build-headers.sh /tmp/
+COPY dist-i686-linux/build-headers.sh /tmp/
RUN ./build-headers.sh
RUN curl -Lo /rustroot/dumb-init \
USER rustbuild
WORKDIR /tmp
-COPY patches/ /tmp/patches/
-COPY powerpc-linux-gnu.config build-powerpc-toolchain.sh /tmp/
+COPY dist-powerpc-linux/patches/ /tmp/patches/
+COPY dist-powerpc-linux/powerpc-linux-gnu.config dist-powerpc-linux/build-powerpc-toolchain.sh /tmp/
RUN ./build-powerpc-toolchain.sh
USER root
USER rustbuild
WORKDIR /tmp
-COPY patches/ /tmp/patches/
-COPY shared.sh powerpc64-linux-gnu.config build-powerpc64-toolchain.sh /tmp/
+COPY dist-powerpc64-linux/patches/ /tmp/patches/
+COPY dist-powerpc64-linux/shared.sh dist-powerpc64-linux/powerpc64-linux-gnu.config dist-powerpc64-linux/build-powerpc64-toolchain.sh /tmp/
RUN ./build-powerpc64-toolchain.sh
USER root
USER root
RUN apt-get install -y --no-install-recommends rpm2cpio cpio
-COPY shared.sh build-powerpc64le-toolchain.sh /tmp/
+COPY dist-powerpc64le-linux/shared.sh dist-powerpc64le-linux/build-powerpc64le-toolchain.sh /tmp/
RUN ./build-powerpc64le-toolchain.sh
RUN curl -o /usr/local/bin/sccache \
USER rustbuild
WORKDIR /tmp
-COPY patches/ /tmp/patches/
-COPY s390x-linux-gnu.config build-s390x-toolchain.sh /tmp/
+COPY dist-s390x-linux/patches/ /tmp/patches/
+COPY dist-s390x-linux/s390x-linux-gnu.config dist-s390x-linux/build-s390x-toolchain.sh /tmp/
RUN ./build-s390x-toolchain.sh
USER root
libssl-dev \
pkg-config
-COPY build-toolchain.sh /tmp/
+COPY dist-x86_64-freebsd/build-toolchain.sh /tmp/
RUN /tmp/build-toolchain.sh x86_64
RUN curl -OL https://github.com/Yelp/dumb-init/releases/download/v1.2.0/dumb-init_1.2.0_amd64.deb && \
ENV LD_LIBRARY_PATH=/rustroot/lib64:/rustroot/lib
ENV PKG_CONFIG_PATH=/rustroot/lib/pkgconfig
WORKDIR /tmp
-COPY shared.sh build-binutils.sh /tmp/
+COPY dist-x86_64-linux/shared.sh dist-x86_64-linux/build-binutils.sh /tmp/
# We need a build of openssl which supports SNI to download artifacts from
# static.rust-lang.org. This'll be used to link into libcurl below (and used
# later as well), so build a copy of OpenSSL with dynamic libraries into our
# generic root.
-COPY build-openssl.sh /tmp/
+COPY dist-x86_64-linux/build-openssl.sh /tmp/
RUN ./build-openssl.sh
# The `curl` binary on CentOS doesn't support SNI which is needed for fetching
#
# Note that we also disable a bunch of optional features of curl that we don't
# really need.
-COPY build-curl.sh /tmp/
+COPY dist-x86_64-linux/build-curl.sh /tmp/
RUN ./build-curl.sh
# binutils < 2.22 has a bug where the 32-bit executables it generates
RUN ./build-binutils.sh
# Need a newer version of gcc than centos has to compile LLVM nowadays
-COPY build-gcc.sh /tmp/
+COPY dist-x86_64-linux/build-gcc.sh /tmp/
RUN ./build-gcc.sh
# CentOS 5.5 has Python 2.4 by default, but LLVM needs 2.7+
-COPY build-python.sh /tmp/
+COPY dist-x86_64-linux/build-python.sh /tmp/
RUN ./build-python.sh
# Apparently CentOS 5.5 desn't have `git` in yum, but we're gonna need it for
# cloning, so download and build it here.
-COPY build-git.sh /tmp/
+COPY dist-x86_64-linux/build-git.sh /tmp/
RUN ./build-git.sh
# libssh2 (a dependency of Cargo) requires cmake 2.8.11 or higher but CentOS
# only has 2.6.4, so build our own
-COPY build-cmake.sh /tmp/
+COPY dist-x86_64-linux/build-cmake.sh /tmp/
RUN ./build-cmake.sh
# for sanitizers, we need kernel headers files newer than the ones CentOS ships
# with so we install newer ones here
-COPY build-headers.sh /tmp/
+COPY dist-x86_64-linux/build-headers.sh /tmp/
RUN ./build-headers.sh
RUN curl -Lo /rustroot/dumb-init \
pkg-config
WORKDIR /build/
-COPY build-musl.sh /build/
+COPY dist-x86_64-musl/build-musl.sh /build/
RUN sh /build/build-musl.sh && rm -rf /build
RUN curl -OL https://github.com/Yelp/dumb-init/releases/download/v1.2.0/dumb-init_1.2.0_amd64.deb && \
USER rustbuild
WORKDIR /tmp
-COPY build-netbsd-toolchain.sh /tmp/
+COPY dist-x86_64-netbsd/build-netbsd-toolchain.sh /tmp/
RUN ./build-netbsd-toolchain.sh
USER root
ENTRYPOINT ["/usr/bin/dumb-init", "--"]
WORKDIR /tmp
-COPY build-emscripten.sh /tmp/
+COPY emscripten/build-emscripten.sh /tmp/
RUN ./build-emscripten.sh
ENV PATH=$PATH:/tmp/emsdk_portable
ENV PATH=$PATH:/tmp/emsdk_portable/clang/tag-e1.37.10/build_tag-e1.37.10_32/bin
build \
--rm \
-t rust-ci \
- "$docker_dir/$image"
+ -f "$docker_dir/$image/Dockerfile" \
+ "$docker_dir"
elif [ -f "$docker_dir/disabled/$image/Dockerfile" ]; then
if [ -n "$TRAVIS_OS_NAME" ]; then
echo Cannot run disabled images on travis!
--- /dev/null
+# 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 <LICENSE-APACHE or
+# http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+# <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
+# option. This file may not be copied, modified, or distributed
+# except according to those terms.
+
+set -ex
+
+URL=https://dl.google.com/android/repository
+
+download_ndk() {
+ mkdir -p /android/ndk
+ cd /android/ndk
+ curl -O $URL/$1
+ unzip -q $1
+ rm $1
+ mv android-ndk-* ndk
+}
+
+make_standalone_toolchain() {
+ # See https://developer.android.com/ndk/guides/standalone_toolchain.htm
+ python2.7 /android/ndk/ndk/build/tools/make_standalone_toolchain.py \
+ --install-dir /android/ndk/$1-$2 \
+ --arch $1 \
+ --api $2
+}
+
+remove_ndk() {
+ rm -rf /android/ndk/ndk
+}
+
+download_and_make_toolchain() {
+ download_ndk $1 && \
+ make_standalone_toolchain $2 $3 && \
+ remove_ndk
+}
--- /dev/null
+# 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 <LICENSE-APACHE or
+# http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+# <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
+# option. This file may not be copied, modified, or distributed
+# except according to those terms.
+
+set -ex
+
+URL=https://dl.google.com/android/repository
+
+download_sdk() {
+ mkdir -p /android/sdk
+ cd /android/sdk
+ curl -O $URL/$1
+ unzip -q $1
+ rm -rf $1
+}
+
+download_sysimage() {
+ # See https://developer.android.com/studio/tools/help/android.html
+ abi=$1
+ api=$2
+
+ filter="platform-tools,android-$api"
+ filter="$filter,sys-img-$abi-android-$api"
+
+ # Keep printing yes to accept the licenses
+ while true; do echo yes; sleep 10; done | \
+ /android/sdk/tools/android update sdk -a --no-ui \
+ --filter "$filter"
+}
+
+create_avd() {
+ # See https://developer.android.com/studio/tools/help/android.html
+ abi=$1
+ api=$2
+
+ echo no | \
+ /android/sdk/tools/android create avd \
+ --name $abi-$api \
+ --target android-$api \
+ --abi $abi
+}
+
+download_and_create_avd() {
+ download_sdk $1
+ download_sysimage $2 $3
+ create_avd $2 $3
+}
--- /dev/null
+#!/bin/sh
+# Copyright 2016 The Rust Project Developers. See the COPYRIGHT
+# file at the top-level directory of this distribution and at
+# http://rust-lang.org/COPYRIGHT.
+#
+# Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+# http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+# <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
+# option. This file may not be copied, modified, or distributed
+# except according to those terms.
+
+set -ex
+
+# Setting SHELL to a file instead on a symlink helps android
+# emulator identify the system
+export SHELL=/bin/bash
+
+# Using the default qemu2 engine makes time::tests::since_epoch fails because
+# the emulator date is set to unix epoch (in armeabi-v7a-18 image). Using
+# classic engine the emulator starts with the current date and the tests run
+# fine. If another image is used, this need to be evaluated again.
+nohup nohup emulator @armeabi-v7a-18 \
+ -engine classic -no-window -partition-size 2047 0<&- &>/dev/null &
+
+exec "$@"
--- /dev/null
+# 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 <LICENSE-APACHE or
+# http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+# <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
+# option. This file may not be copied, modified, or distributed
+# except according to those terms.
+
+set -ex
+
+curl -OL https://github.com/Yelp/dumb-init/releases/download/v1.2.0/dumb-init_1.2.0_amd64.deb
+dpkg -i dumb-init_*.deb
+rm dumb-init_*.deb
--- /dev/null
+# 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 <LICENSE-APACHE or
+# http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+# <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
+# option. This file may not be copied, modified, or distributed
+# except according to those terms.
+
+set -ex
+
+curl -o /usr/local/bin/sccache \
+ https://s3.amazonaws.com/rust-lang-ci/rust-ci-mirror/2017-05-12-sccache-x86_64-unknown-linux-musl
+
+chmod +x /usr/local/bin/sccache
})
}
+
macro_rules! make_test_inner {
- ($s:ident, $code:expr, $name:ident, $str:expr) => {
+ ($s:ident, $code:expr, $name:ident, $str:expr, $iters:expr) => {
#[bench]
fn $name(bencher: &mut Bencher) {
let mut $s = $str;
black_box(&mut $s);
- bencher.iter(|| $code);
+ bencher.iter(|| for _ in 0..$iters { black_box($code); });
}
}
}
macro_rules! make_test {
($name:ident, $s:ident, $code:expr) => {
+ make_test!($name, $s, $code, 1);
+ };
+ ($name:ident, $s:ident, $code:expr, $iters:expr) => {
mod $name {
use test::Bencher;
use test::black_box;
// Short strings: 65 bytes each
make_test_inner!($s, $code, short_ascii,
- "Mary had a little lamb, Little lamb Mary had a littl lamb, lamb!");
+ "Mary had a little lamb, Little lamb Mary had a littl lamb, lamb!", $iters);
make_test_inner!($s, $code, short_mixed,
- "ศไทย中华Việt Nam; Mary had a little lamb, Little lam!");
+ "ศไทย中华Việt Nam; Mary had a little lamb, Little lam!", $iters);
make_test_inner!($s, $code, short_pile_of_poo,
- "💩💩💩💩💩💩💩💩💩💩💩💩💩💩💩💩!");
+ "💩💩💩💩💩💩💩💩💩💩💩💩💩💩💩💩!", $iters);
make_test_inner!($s, $code, long_lorem_ipsum,"\
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Suspendisse quis lorem sit amet dolor \
ultricies condimentum. Praesent iaculis purus elit, ac malesuada quam malesuada in. Duis sed orci \
feugiat. Etiam quis mauris vel risus luctus mattis a a nunc. Nullam orci quam, imperdiet id \
vehicula in, porttitor ut nibh. Duis sagittis adipiscing nisl vitae congue. Donec mollis risus eu \
leo suscipit, varius porttitor nulla porta. Pellentesque ut sem nec nisi euismod vehicula. Nulla \
-malesuada sollicitudin quam eu fermentum!");
+malesuada sollicitudin quam eu fermentum!", $iters);
}
}
}
make_test!(rfind_zzz_char, s, s.rfind('\u{1F4A4}'));
make_test!(find_zzz_str, s, s.find("\u{1F4A4}"));
+make_test!(starts_with_ascii_char, s, s.starts_with('/'), 1024);
+make_test!(ends_with_ascii_char, s, s.ends_with('/'), 1024);
+make_test!(starts_with_unichar, s, s.starts_with('\u{1F4A4}'), 1024);
+make_test!(ends_with_unichar, s, s.ends_with('\u{1F4A4}'), 1024);
+make_test!(starts_with_str, s, s.starts_with("💩💩💩💩💩💩💩💩💩💩💩💩💩💩💩💩"), 1024);
+make_test!(ends_with_str, s, s.ends_with("💩💩💩💩💩💩💩💩💩💩💩💩💩💩💩💩"), 1024);
+
make_test!(split_space_char, s, s.split(' ').count());
make_test!(split_terminator_space_char, s, s.split_terminator(' ').count());
/// assert!(!bananas.contains("apples"));
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
+ #[inline]
pub fn contains<'a, P: Pattern<'a>>(&'a self, pat: P) -> bool {
core_str::StrExt::contains(self, pat)
}
/// assert_eq!(s.find(x), None);
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
+ #[inline]
pub fn find<'a, P: Pattern<'a>>(&'a self, pat: P) -> Option<usize> {
core_str::StrExt::find(self, pat)
}
/// assert_eq!(s.rfind(x), None);
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
+ #[inline]
pub fn rfind<'a, P: Pattern<'a>>(&'a self, pat: P) -> Option<usize>
where P::Searcher: ReverseSearcher<'a>
{
///
/// [`split_whitespace`]: #method.split_whitespace
#[stable(feature = "rust1", since = "1.0.0")]
+ #[inline]
pub fn split<'a, P: Pattern<'a>>(&'a self, pat: P) -> Split<'a, P> {
core_str::StrExt::split(self, pat)
}
/// assert_eq!(v, ["ghi", "def", "abc"]);
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
+ #[inline]
pub fn rsplit<'a, P: Pattern<'a>>(&'a self, pat: P) -> RSplit<'a, P>
where P::Searcher: ReverseSearcher<'a>
{
/// assert_eq!(v, ["A", "", "B", ""]);
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
+ #[inline]
pub fn split_terminator<'a, P: Pattern<'a>>(&'a self, pat: P) -> SplitTerminator<'a, P> {
core_str::StrExt::split_terminator(self, pat)
}
/// assert_eq!(v, ["", "B", "", "A"]);
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
+ #[inline]
pub fn rsplit_terminator<'a, P: Pattern<'a>>(&'a self, pat: P) -> RSplitTerminator<'a, P>
where P::Searcher: ReverseSearcher<'a>
{
/// assert_eq!(v, ["abc", "defXghi"]);
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
+ #[inline]
pub fn splitn<'a, P: Pattern<'a>>(&'a self, n: usize, pat: P) -> SplitN<'a, P> {
core_str::StrExt::splitn(self, n, pat)
}
/// assert_eq!(v, ["ghi", "abc1def"]);
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
+ #[inline]
pub fn rsplitn<'a, P: Pattern<'a>>(&'a self, n: usize, pat: P) -> RSplitN<'a, P>
where P::Searcher: ReverseSearcher<'a>
{
/// assert_eq!(v, ["1", "2", "3"]);
/// ```
#[stable(feature = "str_matches", since = "1.2.0")]
+ #[inline]
pub fn matches<'a, P: Pattern<'a>>(&'a self, pat: P) -> Matches<'a, P> {
core_str::StrExt::matches(self, pat)
}
/// assert_eq!(v, ["3", "2", "1"]);
/// ```
#[stable(feature = "str_matches", since = "1.2.0")]
+ #[inline]
pub fn rmatches<'a, P: Pattern<'a>>(&'a self, pat: P) -> RMatches<'a, P>
where P::Searcher: ReverseSearcher<'a>
{
/// assert_eq!(v, [(0, "aba")]); // only the first `aba`
/// ```
#[stable(feature = "str_match_indices", since = "1.5.0")]
+ #[inline]
pub fn match_indices<'a, P: Pattern<'a>>(&'a self, pat: P) -> MatchIndices<'a, P> {
core_str::StrExt::match_indices(self, pat)
}
/// assert_eq!(v, [(2, "aba")]); // only the last `aba`
/// ```
#[stable(feature = "str_match_indices", since = "1.5.0")]
+ #[inline]
pub fn rmatch_indices<'a, P: Pattern<'a>>(&'a self, pat: P) -> RMatchIndices<'a, P>
where P::Searcher: ReverseSearcher<'a>
{
/// assert_eq!(s, s.replace("cookie monster", "little lamb"));
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
+ #[inline]
pub fn replace<'a, P: Pattern<'a>>(&'a self, from: P, to: &str) -> String {
let mut result = String::new();
let mut last_end = 0;
/// Searches for chars that are equal to a given char
impl<'a> Pattern<'a> for char {
- pattern_methods!(CharSearcher<'a>, CharEqPattern, CharSearcher);
+ type Searcher = CharSearcher<'a>;
+
+ #[inline]
+ fn into_searcher(self, haystack: &'a str) -> Self::Searcher {
+ CharSearcher(CharEqPattern(self).into_searcher(haystack))
+ }
+
+ #[inline]
+ fn is_contained_in(self, haystack: &'a str) -> bool {
+ if (self as u32) < 128 {
+ haystack.as_bytes().contains(&(self as u8))
+ } else {
+ let mut buffer = [0u8; 4];
+ self.encode_utf8(&mut buffer).is_contained_in(haystack)
+ }
+ }
+
+ #[inline]
+ fn is_prefix_of(self, haystack: &'a str) -> bool {
+ CharEqPattern(self).is_prefix_of(haystack)
+ }
+
+ #[inline]
+ fn is_suffix_of(self, haystack: &'a str) -> bool where Self::Searcher: ReverseSearcher<'a>
+ {
+ CharEqPattern(self).is_suffix_of(haystack)
+ }
}
/////////////////////////////////////////////////////////////////////////////
linker: Option<String> = (None, parse_opt_string, [UNTRACKED],
"system linker to link outputs with"),
link_arg: Vec<String> = (vec![], parse_string_push, [UNTRACKED],
- "a single extra argument to pass to the linker (can be used several times)"),
+ "a single extra argument to append to the linker invocation (can be used several times)"),
link_args: Option<Vec<String>> = (None, parse_opt_list, [UNTRACKED],
- "extra arguments to pass to the linker (space separated)"),
+ "extra arguments to append to the linker invocation (space separated)"),
link_dead_code: bool = (false, parse_bool, [UNTRACKED],
"don't let linker strip dead code (turning it on can be used for code coverage)"),
lto: bool = (false, parse_bool, [TRACKED],
"add a mapping target to the file path remapping config"),
force_unstable_if_unmarked: bool = (false, parse_bool, [TRACKED],
"force all crates to be `rustc_private` unstable"),
+ pre_link_arg: Vec<String> = (vec![], parse_string_push, [UNTRACKED],
+ "a single extra argument to prepend the linker invocation (can be used several times)"),
+ pre_link_args: Option<Vec<String>> = (None, parse_opt_list, [UNTRACKED],
+ "extra arguments to prepend to the linker invocation (space separated)"),
}
pub fn default_lib_output() -> CrateType {
})
}
- match canonicalize(env::current_exe().ok()) {
- Some(mut p) => { p.pop(); p.pop(); p }
- None => bug!("can't determine value for sysroot")
+ match env::current_exe() {
+ Ok(exe) => {
+ match canonicalize(Some(exe)) {
+ Some(mut p) => { p.pop(); p.pop(); return p; },
+ None => bug!("can't determine value for sysroot")
+ }
+ }
+ Err(ref e) => panic!(format!("failed to get current_exe: {}", e))
}
}
if let Some(args) = sess.target.target.options.pre_link_args.get(&flavor) {
cmd.args(args);
}
+ if let Some(ref args) = sess.opts.debugging_opts.pre_link_args {
+ cmd.args(args);
+ }
+ cmd.args(&sess.opts.debugging_opts.pre_link_arg);
let pre_link_objects = if crate_type == config::CrateTypeExecutable {
&sess.target.target.options.pre_link_objects_exe
}
/// Describes the result of a process after it has terminated.
+///
+/// This `struct` is used to represent the exit status of a child process.
+/// Child processes are created via the [`Command`] struct and their exit
+/// status is exposed through the [`status`] method.
+///
+/// [`Command`]: struct.Command.html
+/// [`status`]: struct.Command.html#method.status
#[derive(PartialEq, Eq, Clone, Copy, Debug)]
#[stable(feature = "process", since = "1.0.0")]
pub struct ExitStatus(imp::ExitStatus);
/// On Unix, this will return `None` if the process was terminated
/// by a signal; `std::os::unix` provides an extension trait for
/// extracting the signal and other details from the `ExitStatus`.
+ ///
+ /// # Examples
+ ///
+ /// ```no_run
+ /// use std::process::Command;
+ ///
+ /// let status = Command::new("mkdir")
+ /// .arg("projects")
+ /// .status()
+ /// .expect("failed to execute mkdir");
+ ///
+ /// match status.code() {
+ /// Some(code) => println!("Exited with status code: {}", code),
+ /// None => println!("Process terminated by signal")
+ /// }
+ /// ```
#[stable(feature = "process", since = "1.0.0")]
pub fn code(&self) -> Option<i32> {
self.0.code()
#[cfg(any(target_os = "linux", target_os = "android", target_os = "emscripten"))]
pub fn current_exe() -> io::Result<PathBuf> {
- ::fs::read_link("/proc/self/exe")
+ let selfexe = PathBuf::from("/proc/self/exe");
+ if selfexe.exists() {
+ ::fs::read_link(selfexe)
+ } else {
+ Err(io::Error::new(io::ErrorKind::Other, "no /proc/self/exe available. Is /proc mounted?"))
+ }
}
#[cfg(any(target_os = "macos", target_os = "ios"))]
/// Creates an `OsString` from a potentially ill-formed UTF-16 slice of
/// 16-bit code units.
///
- /// This is lossless: calling `.encode_wide()` on the resulting string
+ /// This is lossless: calling [`encode_wide`] on the resulting string
/// will always return the original code units.
+ ///
+ /// # Examples
+ ///
+ /// ```
+ /// use std::ffi::OsString;
+ /// use std::os::windows::prelude::*;
+ ///
+ /// // UTF-16 encoding for "Unicode".
+ /// let source = [0x0055, 0x006E, 0x0069, 0x0063, 0x006F, 0x0064, 0x0065];
+ ///
+ /// let string = OsString::from_wide(&source[..]);
+ /// ```
+ ///
+ /// [`encode_wide`]: ./trait.OsStrExt.html#tymethod.encode_wide
#[stable(feature = "rust1", since = "1.0.0")]
fn from_wide(wide: &[u16]) -> Self;
}
/// Windows-specific extensions to `OsStr`.
#[stable(feature = "rust1", since = "1.0.0")]
pub trait OsStrExt {
- /// Re-encodes an `OsStr` as a wide character sequence,
- /// i.e. potentially ill-formed UTF-16.
+ /// Re-encodes an `OsStr` as a wide character sequence, i.e. potentially
+ /// ill-formed UTF-16.
+ ///
+ /// This is lossless: calling [`OsString::from_wide`] and then
+ /// `encode_wide` on the result will yield the original code units.
+ /// Note that the encoding does not add a final null terminator.
+ ///
+ /// # Examples
+ ///
+ /// ```
+ /// use std::ffi::OsString;
+ /// use std::os::windows::prelude::*;
+ ///
+ /// // UTF-16 encoding for "Unicode".
+ /// let source = [0x0055, 0x006E, 0x0069, 0x0063, 0x006F, 0x0064, 0x0065];
+ ///
+ /// let string = OsString::from_wide(&source[..]);
+ ///
+ /// let result: Vec<u16> = string.encode_wide().collect();
+ /// assert_eq!(&source[..], &result[..]);
+ /// ```
///
- /// This is lossless. Note that the encoding does not include a final
- /// null.
+ /// [`OsString::from_wide`]: ./trait.OsStringExt.html#tymethod.from_wide
#[stable(feature = "rust1", since = "1.0.0")]
fn encode_wide(&self) -> EncodeWide;
}
// option. This file may not be copied, modified, or distributed
// except according to those terms.
-//! Windows-specific extensions for the primitives in `std::fs`
+//! Windows-specific extensions for the primitives in the `std::fs` module.
#![stable(feature = "rust1", since = "1.0.0")]
use sys;
use sys_common::{AsInnerMut, AsInner};
-/// Windows-specific extensions to `File`
+/// Windows-specific extensions to [`File`].
+///
+/// [`File`]: ../../../fs/struct.File.html
#[stable(feature = "file_offset", since = "1.15.0")]
pub trait FileExt {
/// Seeks to a given position and reads a number of bytes.
/// Note that similar to `File::read`, it is not an error to return with a
/// short read. When returning from such a short read, the file pointer is
/// still updated.
+ ///
+ /// # Examples
+ ///
+ /// ```no_run
+ /// use std::io;
+ /// use std::fs::File;
+ /// use std::os::windows::prelude::*;
+ ///
+ /// # fn foo() -> io::Result<()> {
+ /// let mut file = File::open("foo.txt")?;
+ /// let mut buffer = [0; 10];
+ ///
+ /// // Read 10 bytes, starting 72 bytes from the
+ /// // start of the file.
+ /// file.seek_read(&mut buffer[..], 72)?;
+ /// # Ok(())
+ /// # }
+ /// ```
#[stable(feature = "file_offset", since = "1.15.0")]
fn seek_read(&self, buf: &mut [u8], offset: u64) -> io::Result<usize>;
/// Note that similar to `File::write`, it is not an error to return a
/// short write. When returning from such a short write, the file pointer
/// is still updated.
+ ///
+ /// # Examples
+ ///
+ /// ```no_run
+ /// use std::fs::File;
+ /// use std::os::windows::prelude::*;
+ ///
+ /// # fn foo() -> std::io::Result<()> {
+ /// let mut buffer = File::create("foo.txt")?;
+ ///
+ /// // Write a byte string starting 72 bytes from
+ /// // the start of the file.
+ /// buffer.seek_write(b"some bytes", 72)?;
+ /// # Ok(())
+ /// # }
+ /// ```
#[stable(feature = "file_offset", since = "1.15.0")]
fn seek_write(&self, buf: &[u8], offset: u64) -> io::Result<usize>;
}
}
}
-/// Windows-specific extensions to `OpenOptions`
+/// Windows-specific extensions to [`OpenOptions`].
+///
+/// [`OpenOptions`]: ../../../fs/struct.OpenOptions.html
#[stable(feature = "open_options_ext", since = "1.10.0")]
pub trait OpenOptionsExt {
- /// Overrides the `dwDesiredAccess` argument to the call to `CreateFile`
+ /// Overrides the `dwDesiredAccess` argument to the call to [`CreateFile`]
/// with the specified value.
///
/// This will override the `read`, `write`, and `append` flags on the
/// `OpenOptions` structure. This method provides fine-grained control over
/// the permissions to read, write and append data, attributes (like hidden
- /// and system) and extended attributes.
+ /// and system), and extended attributes.
///
/// # Examples
///
/// ```no_run
/// use std::fs::OpenOptions;
- /// use std::os::windows::fs::OpenOptionsExt;
+ /// use std::os::windows::prelude::*;
///
/// // Open without read and write permission, for example if you only need
- /// // to call `stat()` on the file
+ /// // to call `stat` on the file
/// let file = OpenOptions::new().access_mode(0).open("foo.txt");
/// ```
+ ///
+ /// [`CreateFile`]: https://msdn.microsoft.com/en-us/library/windows/desktop/aa363858.aspx
#[stable(feature = "open_options_ext", since = "1.10.0")]
fn access_mode(&mut self, access: u32) -> &mut Self;
- /// Overrides the `dwShareMode` argument to the call to `CreateFile` with
+ /// Overrides the `dwShareMode` argument to the call to [`CreateFile`] with
/// the specified value.
///
/// By default `share_mode` is set to
- /// `FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE`. Specifying
- /// less permissions denies others to read from, write to and/or delete the
- /// file while it is open.
+ /// `FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE`. This allows
+ /// other processes to to read, write, and delete/rename the same file
+ /// while it is open. Removing any of the flags will prevent other
+ /// processes from performing the corresponding operation until the file
+ /// handle is closed.
///
/// # Examples
///
/// ```no_run
/// use std::fs::OpenOptions;
- /// use std::os::windows::fs::OpenOptionsExt;
+ /// use std::os::windows::prelude::*;
///
/// // Do not allow others to read or modify this file while we have it open
- /// // for writing
- /// let file = OpenOptions::new().write(true)
- /// .share_mode(0)
- /// .open("foo.txt");
+ /// // for writing.
+ /// let file = OpenOptions::new()
+ /// .write(true)
+ /// .share_mode(0)
+ /// .open("foo.txt");
/// ```
+ ///
+ /// [`CreateFile`]: https://msdn.microsoft.com/en-us/library/windows/desktop/aa363858.aspx
#[stable(feature = "open_options_ext", since = "1.10.0")]
fn share_mode(&mut self, val: u32) -> &mut Self;
/// Sets extra flags for the `dwFileFlags` argument to the call to
- /// `CreateFile2` (or combines it with `attributes` and `security_qos_flags`
- /// to set the `dwFlagsAndAttributes` for `CreateFile`).
+ /// [`CreateFile2`] to the specified value (or combines it with
+ /// `attributes` and `security_qos_flags` to set the `dwFlagsAndAttributes`
+ /// for [`CreateFile`]).
///
- /// Custom flags can only set flags, not remove flags set by Rusts options.
- /// This options overwrites any previously set custom flags.
+ /// Custom flags can only set flags, not remove flags set by Rust's options.
+ /// This option overwrites any previously set custom flags.
///
/// # Examples
///
- /// ```rust,ignore
+ /// ```ignore
/// extern crate winapi;
+ ///
/// use std::fs::OpenOptions;
- /// use std::os::windows::fs::OpenOptionsExt;
- ///
- /// let mut options = OpenOptions::new();
- /// options.create(true).write(true);
- /// if cfg!(windows) {
- /// options.custom_flags(winapi::FILE_FLAG_DELETE_ON_CLOSE);
- /// }
- /// let file = options.open("foo.txt");
+ /// use std::os::windows::prelude::*;
+ ///
+ /// let file = OpenOptions::new()
+ /// .create(true)
+ /// .write(true)
+ /// .custom_flags(winapi::FILE_FLAG_DELETE_ON_CLOSE)
+ /// .open("foo.txt");
/// ```
+ ///
+ /// [`CreateFile`]: https://msdn.microsoft.com/en-us/library/windows/desktop/aa363858.aspx
+ /// [`CreateFile2`]: https://msdn.microsoft.com/en-us/library/windows/desktop/hh449422.aspx
#[stable(feature = "open_options_ext", since = "1.10.0")]
fn custom_flags(&mut self, flags: u32) -> &mut Self;
- /// Sets the `dwFileAttributes` argument to the call to `CreateFile2` to
+ /// Sets the `dwFileAttributes` argument to the call to [`CreateFile2`] to
/// the specified value (or combines it with `custom_flags` and
/// `security_qos_flags` to set the `dwFlagsAndAttributes` for
- /// `CreateFile`).
+ /// [`CreateFile`]).
///
/// If a _new_ file is created because it does not yet exist and
/// `.create(true)` or `.create_new(true)` are specified, the new file is
///
/// # Examples
///
- /// ```rust,ignore
+ /// ```ignore
/// extern crate winapi;
+ ///
/// use std::fs::OpenOptions;
- /// use std::os::windows::fs::OpenOptionsExt;
+ /// use std::os::windows::prelude::*;
///
- /// let file = OpenOptions::new().write(true).create(true)
- /// .attributes(winapi::FILE_ATTRIBUTE_HIDDEN)
- /// .open("foo.txt");
+ /// let file = OpenOptions::new()
+ /// .write(true)
+ /// .create(true)
+ /// .attributes(winapi::FILE_ATTRIBUTE_HIDDEN)
+ /// .open("foo.txt");
/// ```
+ ///
+ /// [`CreateFile`]: https://msdn.microsoft.com/en-us/library/windows/desktop/aa363858.aspx
+ /// [`CreateFile2`]: https://msdn.microsoft.com/en-us/library/windows/desktop/hh449422.aspx
#[stable(feature = "open_options_ext", since = "1.10.0")]
fn attributes(&mut self, val: u32) -> &mut Self;
- /// Sets the `dwSecurityQosFlags` argument to the call to `CreateFile2` to
+ /// Sets the `dwSecurityQosFlags` argument to the call to [`CreateFile2`] to
/// the specified value (or combines it with `custom_flags` and `attributes`
- /// to set the `dwFlagsAndAttributes` for `CreateFile`).
+ /// to set the `dwFlagsAndAttributes` for [`CreateFile`]).
+ ///
+ /// By default, `security_qos_flags` is set to `SECURITY_ANONYMOUS`. For
+ /// information about possible values, see [Impersonation Levels] on the
+ /// Windows Dev Center site.
+ ///
+ /// # Examples
+ ///
+ /// ```no_run
+ /// use std::fs::OpenOptions;
+ /// use std::os::windows::prelude::*;
+ ///
+ /// let file = OpenOptions::new()
+ /// .write(true)
+ /// .create(true)
+ ///
+ /// // Sets the flag value to `SecurityIdentification`.
+ /// .security_qos_flags(1)
+ ///
+ /// .open("foo.txt");
+ /// ```
+ ///
+ /// [`CreateFile`]: https://msdn.microsoft.com/en-us/library/windows/desktop/aa363858.aspx
+ /// [`CreateFile2`]: https://msdn.microsoft.com/en-us/library/windows/desktop/hh449422.aspx
+ /// [Impersonation Levels]:
+ /// https://msdn.microsoft.com/en-us/library/windows/desktop/aa379572.aspx
#[stable(feature = "open_options_ext", since = "1.10.0")]
fn security_qos_flags(&mut self, flags: u32) -> &mut OpenOptions;
}
}
}
-/// Extension methods for `fs::Metadata` to access the raw fields contained
+/// Extension methods for [`fs::Metadata`] to access the raw fields contained
/// within.
+///
+/// The data members that this trait exposes correspond to the members
+/// of the [`BY_HANDLE_FILE_INFORMATION`] structure.
+///
+/// [`fs::Metadata`]: ../../../fs/struct.Metadata.html
+/// [`BY_HANDLE_FILE_INFORMATION`]:
+/// https://msdn.microsoft.com/en-us/library/windows/desktop/aa363788.aspx
#[stable(feature = "metadata_ext", since = "1.1.0")]
pub trait MetadataExt {
/// Returns the value of the `dwFileAttributes` field of this metadata.
///
/// This field contains the file system attribute information for a file
- /// or directory.
+ /// or directory. For possible values and their descriptions, see
+ /// [File Attribute Constants] in the Windows Dev Center.
+ ///
+ /// # Examples
+ ///
+ /// ```no_run
+ /// use std::io;
+ /// use std::fs;
+ /// use std::os::windows::prelude::*;
+ ///
+ /// # fn foo() -> io::Result<()> {
+ /// let metadata = fs::metadata("foo.txt")?;
+ /// let attributes = metadata.file_attributes();
+ /// # Ok(())
+ /// # }
+ /// ```
+ ///
+ /// [File Attribute Constants]:
+ /// https://msdn.microsoft.com/en-us/library/windows/desktop/gg258117.aspx
#[stable(feature = "metadata_ext", since = "1.1.0")]
fn file_attributes(&self) -> u32;
/// Returns the value of the `ftCreationTime` field of this metadata.
///
- /// The returned 64-bit value represents the number of 100-nanosecond
- /// intervals since January 1, 1601 (UTC).
+ /// The returned 64-bit value is equivalent to a [`FILETIME`] struct,
+ /// which represents the number of 100-nanosecond intervals since
+ /// January 1, 1601 (UTC). The struct is automatically
+ /// converted to a `u64` value, as that is the recommended way
+ /// to use it.
+ ///
+ /// If the underlying filesystem does not support creation time, the
+ /// returned value is 0.
+ ///
+ /// # Examples
+ ///
+ /// ```no_run
+ /// use std::io;
+ /// use std::fs;
+ /// use std::os::windows::prelude::*;
+ ///
+ /// # fn foo() -> io::Result<()> {
+ /// let metadata = fs::metadata("foo.txt")?;
+ /// let creation_time = metadata.creation_time();
+ /// # Ok(())
+ /// # }
+ /// ```
+ ///
+ /// [`FILETIME`]: https://msdn.microsoft.com/en-us/library/windows/desktop/ms724284.aspx
#[stable(feature = "metadata_ext", since = "1.1.0")]
fn creation_time(&self) -> u64;
/// Returns the value of the `ftLastAccessTime` field of this metadata.
///
- /// The returned 64-bit value represents the number of 100-nanosecond
- /// intervals since January 1, 1601 (UTC).
+ /// The returned 64-bit value is equivalent to a [`FILETIME`] struct,
+ /// which represents the number of 100-nanosecond intervals since
+ /// January 1, 1601 (UTC). The struct is automatically
+ /// converted to a `u64` value, as that is the recommended way
+ /// to use it.
+ ///
+ /// For a file, the value specifies the last time that a file was read
+ /// from or written to. For a directory, the value specifies when
+ /// the directory was created. For both files and directories, the
+ /// specified date is correct, but the time of day is always set to
+ /// midnight.
+ ///
+ /// If the underlying filesystem does not support last access time, the
+ /// returned value is 0.
+ ///
+ /// # Examples
+ ///
+ /// ```no_run
+ /// use std::io;
+ /// use std::fs;
+ /// use std::os::windows::prelude::*;
+ ///
+ /// # fn foo() -> io::Result<()> {
+ /// let metadata = fs::metadata("foo.txt")?;
+ /// let last_access_time = metadata.last_access_time();
+ /// # Ok(())
+ /// # }
+ /// ```
+ ///
+ /// [`FILETIME`]: https://msdn.microsoft.com/en-us/library/windows/desktop/ms724284.aspx
#[stable(feature = "metadata_ext", since = "1.1.0")]
fn last_access_time(&self) -> u64;
/// Returns the value of the `ftLastWriteTime` field of this metadata.
///
- /// The returned 64-bit value represents the number of 100-nanosecond
- /// intervals since January 1, 1601 (UTC).
+ /// The returned 64-bit value is equivalent to a [`FILETIME`] struct,
+ /// which represents the number of 100-nanosecond intervals since
+ /// January 1, 1601 (UTC). The struct is automatically
+ /// converted to a `u64` value, as that is the recommended way
+ /// to use it.
+ ///
+ /// For a file, the value specifies the last time that a file was written
+ /// to. For a directory, the structure specifies when the directory was
+ /// created.
+ ///
+ /// If the underlying filesystem does not support the last write time
+ /// time, the returned value is 0.
+ ///
+ /// # Examples
+ ///
+ /// ```no_run
+ /// use std::io;
+ /// use std::fs;
+ /// use std::os::windows::prelude::*;
+ ///
+ /// # fn foo() -> io::Result<()> {
+ /// let metadata = fs::metadata("foo.txt")?;
+ /// let last_write_time = metadata.last_write_time();
+ /// # Ok(())
+ /// # }
+ /// ```
+ ///
+ /// [`FILETIME`]: https://msdn.microsoft.com/en-us/library/windows/desktop/ms724284.aspx
#[stable(feature = "metadata_ext", since = "1.1.0")]
fn last_write_time(&self) -> u64;
/// metadata.
///
/// The returned value does not have meaning for directories.
+ ///
+ /// # Examples
+ ///
+ /// ```no_run
+ /// use std::io;
+ /// use std::fs;
+ /// use std::os::windows::prelude::*;
+ ///
+ /// # fn foo() -> io::Result<()> {
+ /// let metadata = fs::metadata("foo.txt")?;
+ /// let file_size = metadata.file_size();
+ /// # Ok(())
+ /// # }
+ /// ```
#[stable(feature = "metadata_ext", since = "1.1.0")]
fn file_size(&self) -> u64;
}
///
/// # Examples
///
-/// ```ignore
+/// ```no_run
/// use std::os::windows::fs;
///
/// # fn foo() -> std::io::Result<()> {
///
/// # Examples
///
-/// ```ignore
+/// ```no_run
/// use std::os::windows::fs;
///
/// # fn foo() -> std::io::Result<()> {
// option. This file may not be copied, modified, or distributed
// except according to those terms.
-//! Experimental extensions to `std` for Windows.
+//! Platform-specific extensions to `std` for Windows.
//!
-//! For now, this module is limited to extracting handles, file
-//! descriptors, and sockets, but its functionality will grow over
-//! time.
+//! Provides access to platform-level information for Windows, and exposes
+//! Windows-specific idioms that would otherwise be inappropriate as part
+//! the core `std` library. These extensions allow developers to use
+//! `std` types and idioms with Windows in a way that the normal
+//! platform-agnostic idioms would not normally support.
#![stable(feature = "rust1", since = "1.0.0")]
}
}
+/// Generates a wide character sequence for potentially ill-formed UTF-16.
#[stable(feature = "rust1", since = "1.0.0")]
#[derive(Clone)]
pub struct EncodeWide<'a> {
/// Returns span for the macro which originally caused the current expansion to happen.
///
/// Stops backtracing at include! boundary.
- pub fn expansion_cause(&self) -> Span {
+ pub fn expansion_cause(&self) -> Option<Span> {
let mut ctxt = self.backtrace();
let mut last_macro = None;
loop {
break
}
}
- last_macro.expect("missing expansion backtrace")
+ last_macro
}
pub fn struct_span_warn(&self,
-> Box<base::MacResult+'static> {
base::check_zero_tts(cx, sp, tts, "line!");
- let topmost = cx.expansion_cause();
+ let topmost = cx.expansion_cause().unwrap_or(sp);
let loc = cx.codemap().lookup_char_pos(topmost.lo);
base::MacEager::expr(cx.expr_u32(topmost, loc.line as u32))
-> Box<base::MacResult+'static> {
base::check_zero_tts(cx, sp, tts, "column!");
- let topmost = cx.expansion_cause();
+ let topmost = cx.expansion_cause().unwrap_or(sp);
let loc = cx.codemap().lookup_char_pos(topmost.lo);
base::MacEager::expr(cx.expr_u32(topmost, loc.col.to_usize() as u32))
-> Box<base::MacResult+'static> {
base::check_zero_tts(cx, sp, tts, "file!");
- let topmost = cx.expansion_cause();
+ let topmost = cx.expansion_cause().unwrap_or(sp);
let loc = cx.codemap().lookup_char_pos(topmost.lo);
base::MacEager::expr(cx.expr_str(topmost, Symbol::intern(&loc.file.name)))
}
passed: usize,
failed: usize,
ignored: usize,
+ filtered_out: usize,
measured: usize,
metrics: MetricMap,
failures: Vec<(TestDesc, Vec<u8>)>,
passed: 0,
failed: 0,
ignored: 0,
+ filtered_out: 0,
measured: 0,
metrics: MetricMap::new(),
failures: Vec::new(),
} else {
self.write_pretty("FAILED", term::color::RED)?;
}
- let s = format!(". {} passed; {} failed; {} ignored; {} measured\n\n",
+ let s = format!(". {} passed; {} failed; {} ignored; {} measured; {} filtered out\n\n",
self.passed,
self.failed,
self.ignored,
- self.measured);
+ self.measured,
+ self.filtered_out);
self.write_plain(&s)?;
return Ok(success);
}
fn callback<T: Write>(event: &TestEvent, st: &mut ConsoleTestState<T>) -> io::Result<()> {
match (*event).clone() {
TeFiltered(ref filtered_tests) => st.write_run_start(filtered_tests.len()),
+ TeFilteredOut(filtered_out) => Ok(st.filtered_out = filtered_out),
TeWait(ref test, padding) => st.write_test_start(test, padding),
TeTimeout(ref test) => st.write_timeout(test),
TeResult(test, result, stdout) => {
passed: 0,
failed: 0,
ignored: 0,
+ filtered_out: 0,
measured: 0,
max_name_len: 10,
metrics: MetricMap::new(),
TeWait(TestDesc, NamePadding),
TeResult(TestDesc, TestResult, Vec<u8>),
TeTimeout(TestDesc),
+ TeFilteredOut(usize),
}
pub type MonitorMsg = (TestDesc, TestResult, Vec<u8>);
use std::collections::HashMap;
use std::sync::mpsc::RecvTimeoutError;
+ let tests_len = tests.len();
+
let mut filtered_tests = filter_tests(opts, tests);
if !opts.bench_benchmarks {
filtered_tests = convert_benchmarks_to_tests(filtered_tests);
}
+ let filtered_out = tests_len - filtered_tests.len();
+ callback(TeFilteredOut(filtered_out))?;
+
let filtered_descs = filtered_tests.iter()
.map(|t| t.desc.clone())
.collect();
--- /dev/null
+// 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 <LICENSE-APACHE or
+// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+fn main() {
+ include!(line!()); //~ ERROR argument must be a string literal
+}
-Subproject commit 41e490480b01ef8d15ef061b578fbf1e08d0faa9
+Subproject commit 397359840ecad02d5fe69b2a0cf328e98235ffea