Auto merge of #74461 - Manishearth:rollup-xadbh00, r=Manishearth

Rollup of 18 pull requests

Successful merges:

 - #71670 (Enforce even more the code blocks attributes check through rustdoc)
 - #73930 (Make some Option methods const)
 - #74009 (Fix MinGW `run-make-fulldeps` tests)
 - #74056 (Add Arguments::as_str().)
 - #74169 (Stop processing unreachable blocks when solving dataflow)
 - #74251 (Teach bootstrap about target files vs target triples)
 - #74288 (Fix src/test/run-make/static-pie/test-aslr.rs)
 - #74300 (Use intra-doc links in core::iter module)
 - #74364 (add lazy normalization regression tests)
 - #74368 (Add CSS tidy check)
 - #74394 (Remove leftover from emscripten fastcomp support)
 - #74411 (Don't assign `()` to `!` MIR locals)
 - #74416 (Use an UTF-8 locale for the linker.)
 - #74424 (Move hir::Place to librustc_middle/hir)
 - #74428 (docs: better demonstrate that None values are skipped as many times a…)
 - #74438 (warn about uninitialized multi-variant enums)
 - #74440 (Fix Arc::as_ptr docs)
 - #74452 (intra-doc links: resolve modules in the type namespace)

Failed merges:

r? @ghost
This commit is contained in:
bors 2020-07-17 21:10:14 +00:00
commit d3df8512d2
75 changed files with 1315 additions and 1057 deletions

View file

@ -16,6 +16,7 @@ use build_helper::{output, t};
use crate::cache::{Cache, Interned, INTERNER};
use crate::check;
use crate::compile;
use crate::config::TargetSelection;
use crate::dist;
use crate::doc;
use crate::flags::Subcommand;
@ -86,8 +87,8 @@ pub trait Step: 'static + Clone + Debug + PartialEq + Eq + Hash {
pub struct RunConfig<'a> {
pub builder: &'a Builder<'a>,
pub host: Interned<String>,
pub target: Interned<String>,
pub host: TargetSelection,
pub target: TargetSelection,
pub path: PathBuf,
}
@ -576,7 +577,7 @@ impl<'a> Builder<'a> {
/// not take `Compiler` since all `Compiler` instances are meant to be
/// obtained through this function, since it ensures that they are valid
/// (i.e., built and assembled).
pub fn compiler(&self, stage: u32, host: Interned<String>) -> Compiler {
pub fn compiler(&self, stage: u32, host: TargetSelection) -> Compiler {
self.ensure(compile::Assemble { target_compiler: Compiler { stage, host } })
}
@ -594,8 +595,8 @@ impl<'a> Builder<'a> {
pub fn compiler_for(
&self,
stage: u32,
host: Interned<String>,
target: Interned<String>,
host: TargetSelection,
target: TargetSelection,
) -> Compiler {
if self.build.force_use_stage1(Compiler { stage, host }, target) {
self.compiler(1, self.config.build)
@ -610,15 +611,11 @@ impl<'a> Builder<'a> {
/// Returns the libdir where the standard library and other artifacts are
/// found for a compiler's sysroot.
pub fn sysroot_libdir(
&self,
compiler: Compiler,
target: Interned<String>,
) -> Interned<PathBuf> {
pub fn sysroot_libdir(&self, compiler: Compiler, target: TargetSelection) -> Interned<PathBuf> {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
struct Libdir {
compiler: Compiler,
target: Interned<String>,
target: TargetSelection,
}
impl Step for Libdir {
type Output = Interned<PathBuf>;
@ -633,7 +630,7 @@ impl<'a> Builder<'a> {
.sysroot(self.compiler)
.join(lib)
.join("rustlib")
.join(self.target)
.join(self.target.triple)
.join("lib");
let _ = fs::remove_dir_all(&sysroot);
t!(fs::create_dir_all(&sysroot));
@ -656,7 +653,7 @@ impl<'a> Builder<'a> {
Some(relative_libdir) if compiler.stage >= 1 => {
self.sysroot(compiler).join(relative_libdir)
}
_ => self.sysroot(compiler).join(libdir(&compiler.host)),
_ => self.sysroot(compiler).join(libdir(compiler.host)),
}
}
}
@ -668,11 +665,11 @@ impl<'a> Builder<'a> {
/// Windows.
pub fn libdir_relative(&self, compiler: Compiler) -> &Path {
if compiler.is_snapshot(self) {
libdir(&self.config.build).as_ref()
libdir(self.config.build).as_ref()
} else {
match self.config.libdir_relative() {
Some(relative_libdir) if compiler.stage >= 1 => relative_libdir,
_ => libdir(&compiler.host).as_ref(),
_ => libdir(compiler.host).as_ref(),
}
}
}
@ -707,7 +704,7 @@ impl<'a> Builder<'a> {
if compiler.is_snapshot(self) {
self.initial_rustc.clone()
} else {
self.sysroot(compiler).join("bin").join(exe("rustc", &compiler.host))
self.sysroot(compiler).join("bin").join(exe("rustc", compiler.host))
}
}
@ -725,7 +722,11 @@ impl<'a> Builder<'a> {
.env("CFG_RELEASE_CHANNEL", &self.config.channel)
.env("RUSTDOC_REAL", self.rustdoc(compiler))
.env("RUSTDOC_CRATE_VERSION", self.rust_version())
.env("RUSTC_BOOTSTRAP", "1");
.env("RUSTC_BOOTSTRAP", "1")
.arg("-Winvalid_codeblock_attributes");
if self.config.deny_warnings {
cmd.arg("-Dwarnings");
}
// Remove make-related flags that can cause jobserver problems.
cmd.env_remove("MAKEFLAGS");
@ -741,7 +742,7 @@ impl<'a> Builder<'a> {
///
/// Note that this returns `None` if LLVM is disabled, or if we're in a
/// check build or dry-run, where there's no need to build all of LLVM.
fn llvm_config(&self, target: Interned<String>) -> Option<PathBuf> {
fn llvm_config(&self, target: TargetSelection) -> Option<PathBuf> {
if self.config.llvm_enabled() && self.kind != Kind::Check && !self.config.dry_run {
let llvm_config = self.ensure(native::Llvm { target });
if llvm_config.is_file() {
@ -763,7 +764,7 @@ impl<'a> Builder<'a> {
compiler: Compiler,
mode: Mode,
source_type: SourceType,
target: Interned<String>,
target: TargetSelection,
cmd: &str,
) -> Cargo {
let mut cargo = Command::new(&self.initial_cargo);
@ -773,7 +774,7 @@ impl<'a> Builder<'a> {
let my_out = match mode {
// This is the intended out directory for compiler documentation.
Mode::Rustc | Mode::ToolRustc | Mode::Codegen => self.compiler_doc_out(target),
Mode::Std => out_dir.join(target).join("doc"),
Mode::Std => out_dir.join(target.triple).join("doc"),
_ => panic!("doc mode {:?} not expected", mode),
};
let rustdoc = self.rustdoc(compiler);
@ -795,7 +796,7 @@ impl<'a> Builder<'a> {
}
if cmd != "install" {
cargo.arg("--target").arg(target);
cargo.arg("--target").arg(target.rustc_target_arg());
} else {
assert_eq!(target, compiler.host);
}
@ -821,7 +822,7 @@ impl<'a> Builder<'a> {
compiler.stage
};
let mut rustflags = Rustflags::new(&target);
let mut rustflags = Rustflags::new(target);
if stage != 0 {
if let Ok(s) = env::var("CARGOFLAGS_NOT_BOOTSTRAP") {
cargo.args(s.split_whitespace());
@ -838,7 +839,7 @@ impl<'a> Builder<'a> {
// FIXME: It might be better to use the same value for both `RUSTFLAGS` and `RUSTDOCFLAGS`,
// but this breaks CI. At the very least, stage0 `rustdoc` needs `--cfg bootstrap`. See
// #71458.
let rustdocflags = rustflags.clone();
let mut rustdocflags = rustflags.clone();
if let Ok(s) = env::var("CARGOFLAGS") {
cargo.args(s.split_whitespace());
@ -994,7 +995,7 @@ impl<'a> Builder<'a> {
// argument manually via `-C link-args=-Wl,-rpath,...`. Plus isn't it
// fun to pass a flag to a tool to pass a flag to pass a flag to a tool
// to change a flag in a binary?
if self.config.rust_rpath && util::use_host_linker(&target) {
if self.config.rust_rpath && util::use_host_linker(target) {
let rpath = if target.contains("apple") {
// Note that we need to take one extra step on macOS to also pass
// `-Wl,-instal_name,@rpath/...` to get things to work right. To
@ -1022,7 +1023,7 @@ impl<'a> Builder<'a> {
}
if let Some(target_linker) = self.linker(target, can_use_lld) {
let target = crate::envify(&target);
let target = crate::envify(&target.triple);
cargo.env(&format!("CARGO_TARGET_{}_LINKER", target), target_linker);
}
if !(["build", "check", "clippy", "fix", "rustc"].contains(&cmd)) && want_rustdoc {
@ -1140,6 +1141,7 @@ impl<'a> Builder<'a> {
if self.config.deny_warnings {
lint_flags.push("-Dwarnings");
rustdocflags.arg("-Dwarnings");
}
// FIXME(#58633) hide "unused attribute" errors in incremental
@ -1157,6 +1159,8 @@ impl<'a> Builder<'a> {
// are always ignored in dependencies. Eventually this should be
// fixed via better support from Cargo.
cargo.env("RUSTC_LINT_FLAGS", lint_flags.join(" "));
rustdocflags.arg("-Winvalid_codeblock_attributes");
}
if let Mode::Rustc | Mode::Codegen = mode {
@ -1193,21 +1197,23 @@ impl<'a> Builder<'a> {
}
};
let cc = ccacheify(&self.cc(target));
cargo.env(format!("CC_{}", target), &cc);
cargo.env(format!("CC_{}", target.triple), &cc);
let cflags = self.cflags(target, GitRepo::Rustc).join(" ");
cargo.env(format!("CFLAGS_{}", target), cflags.clone());
cargo.env(format!("CFLAGS_{}", target.triple), cflags.clone());
if let Some(ar) = self.ar(target) {
let ranlib = format!("{} s", ar.display());
cargo.env(format!("AR_{}", target), ar).env(format!("RANLIB_{}", target), ranlib);
cargo
.env(format!("AR_{}", target.triple), ar)
.env(format!("RANLIB_{}", target.triple), ranlib);
}
if let Ok(cxx) = self.cxx(target) {
let cxx = ccacheify(&cxx);
cargo
.env(format!("CXX_{}", target), &cxx)
.env(format!("CXXFLAGS_{}", target), cflags);
.env(format!("CXX_{}", target.triple), &cxx)
.env(format!("CXXFLAGS_{}", target.triple), cflags);
}
}
@ -1241,7 +1247,7 @@ impl<'a> Builder<'a> {
// Environment variables *required* throughout the build
//
// FIXME: should update code to not require this env var
cargo.env("CFG_COMPILER_HOST_TRIPLE", target);
cargo.env("CFG_COMPILER_HOST_TRIPLE", target.triple);
// Set this for all builds to make sure doc builds also get it.
cargo.env("CFG_RELEASE_CHANNEL", &self.config.channel);
@ -1397,7 +1403,7 @@ mod tests;
struct Rustflags(String);
impl Rustflags {
fn new(target: &str) -> Rustflags {
fn new(target: TargetSelection) -> Rustflags {
let mut ret = Rustflags(String::new());
// Inherit `RUSTFLAGS` by default ...
@ -1405,7 +1411,7 @@ impl Rustflags {
// ... and also handle target-specific env RUSTFLAGS if they're
// configured.
let target_specific = format!("CARGO_TARGET_{}_RUSTFLAGS", crate::envify(target));
let target_specific = format!("CARGO_TARGET_{}_RUSTFLAGS", crate::envify(&target.triple));
ret.env(&target_specific);
ret

View file

@ -1,5 +1,5 @@
use super::*;
use crate::config::Config;
use crate::config::{Config, TargetSelection};
use std::thread;
use pretty_assertions::assert_eq;
@ -17,16 +17,16 @@ fn configure(host: &[&str], target: &[&str]) -> Config {
.join(&thread::current().name().unwrap_or("unknown").replace(":", "-"));
t!(fs::create_dir_all(&dir));
config.out = dir;
config.build = INTERNER.intern_str("A");
config.build = TargetSelection::from_user("A");
config.hosts = vec![config.build]
.into_iter()
.chain(host.iter().map(|s| INTERNER.intern_str(s)))
.chain(host.iter().map(|s| TargetSelection::from_user(s)))
.collect::<Vec<_>>();
config.targets = config
.hosts
.clone()
.into_iter()
.chain(target.iter().map(|s| INTERNER.intern_str(s)))
.chain(target.iter().map(|s| TargetSelection::from_user(s)))
.collect::<Vec<_>>();
config
}
@ -41,7 +41,7 @@ fn dist_baseline() {
let mut builder = Builder::new(&build);
builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Dist), &[]);
let a = INTERNER.intern_str("A");
let a = TargetSelection::from_user("A");
assert_eq!(first(builder.cache.all::<dist::Docs>()), &[dist::Docs { host: a },]);
assert_eq!(first(builder.cache.all::<dist::Mingw>()), &[dist::Mingw { host: a },]);
@ -67,8 +67,8 @@ fn dist_with_targets() {
let mut builder = Builder::new(&build);
builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Dist), &[]);
let a = INTERNER.intern_str("A");
let b = INTERNER.intern_str("B");
let a = TargetSelection::from_user("A");
let b = TargetSelection::from_user("B");
assert_eq!(
first(builder.cache.all::<dist::Docs>()),
@ -98,8 +98,8 @@ fn dist_with_hosts() {
let mut builder = Builder::new(&build);
builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Dist), &[]);
let a = INTERNER.intern_str("A");
let b = INTERNER.intern_str("B");
let a = TargetSelection::from_user("A");
let b = TargetSelection::from_user("B");
assert_eq!(
first(builder.cache.all::<dist::Docs>()),
@ -128,8 +128,8 @@ fn dist_with_hosts() {
#[test]
fn dist_only_cross_host() {
let a = INTERNER.intern_str("A");
let b = INTERNER.intern_str("B");
let a = TargetSelection::from_user("A");
let b = TargetSelection::from_user("B");
let mut build = Build::new(configure(&["B"], &[]));
build.config.docs = false;
build.config.extended = true;
@ -156,9 +156,9 @@ fn dist_with_targets_and_hosts() {
let mut builder = Builder::new(&build);
builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Dist), &[]);
let a = INTERNER.intern_str("A");
let b = INTERNER.intern_str("B");
let c = INTERNER.intern_str("C");
let a = TargetSelection::from_user("A");
let b = TargetSelection::from_user("B");
let c = TargetSelection::from_user("C");
assert_eq!(
first(builder.cache.all::<dist::Docs>()),
@ -194,9 +194,9 @@ fn dist_with_target_flag() {
let mut builder = Builder::new(&build);
builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Dist), &[]);
let a = INTERNER.intern_str("A");
let b = INTERNER.intern_str("B");
let c = INTERNER.intern_str("C");
let a = TargetSelection::from_user("A");
let b = TargetSelection::from_user("B");
let c = TargetSelection::from_user("C");
assert_eq!(
first(builder.cache.all::<dist::Docs>()),
@ -224,8 +224,8 @@ fn dist_with_same_targets_and_hosts() {
let mut builder = Builder::new(&build);
builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Dist), &[]);
let a = INTERNER.intern_str("A");
let b = INTERNER.intern_str("B");
let a = TargetSelection::from_user("A");
let b = TargetSelection::from_user("B");
assert_eq!(
first(builder.cache.all::<dist::Docs>()),
@ -277,9 +277,9 @@ fn build_default() {
let mut builder = Builder::new(&build);
builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Build), &[]);
let a = INTERNER.intern_str("A");
let b = INTERNER.intern_str("B");
let c = INTERNER.intern_str("C");
let a = TargetSelection::from_user("A");
let b = TargetSelection::from_user("B");
let c = TargetSelection::from_user("C");
assert_eq!(
first(builder.cache.all::<compile::Std>()),
@ -318,9 +318,9 @@ fn build_with_target_flag() {
let mut builder = Builder::new(&build);
builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Build), &[]);
let a = INTERNER.intern_str("A");
let b = INTERNER.intern_str("B");
let c = INTERNER.intern_str("C");
let a = TargetSelection::from_user("A");
let b = TargetSelection::from_user("B");
let c = TargetSelection::from_user("C");
assert_eq!(
first(builder.cache.all::<compile::Std>()),
@ -374,7 +374,7 @@ fn test_with_no_doc_stage0() {
let build = Build::new(config);
let mut builder = Builder::new(&build);
let host = INTERNER.intern_str("A");
let host = TargetSelection::from_user("A");
builder
.run_step_descriptions(&[StepDescription::from::<test::Crate>()], &["src/libstd".into()]);
@ -428,7 +428,7 @@ fn doc_default() {
let build = Build::new(config);
let mut builder = Builder::new(&build);
builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Doc), &[]);
let a = INTERNER.intern_str("A");
let a = TargetSelection::from_user("A");
// error_index_generator uses stage 1 to share rustdoc artifacts with the
// rustdoc tool.
@ -466,7 +466,7 @@ fn test_docs() {
let build = Build::new(config);
let mut builder = Builder::new(&build);
builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Test), &[]);
let a = INTERNER.intern_str("A");
let a = TargetSelection::from_user("A");
// error_index_generator uses stage 1 to share rustdoc artifacts with the
// rustdoc tool.

View file

@ -28,16 +28,15 @@ use std::{env, iter};
use build_helper::output;
use crate::cache::Interned;
use crate::config::Target;
use crate::config::{Target, TargetSelection};
use crate::{Build, GitRepo};
// The `cc` crate doesn't provide a way to obtain a path to the detected archiver,
// so use some simplified logic here. First we respect the environment variable `AR`, then
// try to infer the archiver path from the C compiler path.
// In the future this logic should be replaced by calling into the `cc` crate.
fn cc2ar(cc: &Path, target: &str) -> Option<PathBuf> {
if let Some(ar) = env::var_os(format!("AR_{}", target.replace("-", "_"))) {
fn cc2ar(cc: &Path, target: TargetSelection) -> Option<PathBuf> {
if let Some(ar) = env::var_os(format!("AR_{}", target.triple.replace("-", "_"))) {
Some(PathBuf::from(ar))
} else if let Some(ar) = env::var_os("AR") {
Some(PathBuf::from(ar))
@ -79,8 +78,8 @@ pub fn find(build: &mut Build) {
.opt_level(2)
.warnings(false)
.debug(false)
.target(&target)
.host(&build.build);
.target(&target.triple)
.host(&build.build.triple);
match build.crt_static(target) {
Some(a) => {
cfg.static_crt(a);
@ -106,10 +105,10 @@ pub fn find(build: &mut Build) {
let ar = if let ar @ Some(..) = config.and_then(|c| c.ar.clone()) {
ar
} else {
cc2ar(compiler.path(), &target)
cc2ar(compiler.path(), target)
};
build.cc.insert(target, compiler);
build.cc.insert(target, compiler.clone());
let cflags = build.cflags(target, GitRepo::Rustc);
// If we use llvm-libunwind, we will need a C++ compiler as well for all targets
@ -120,8 +119,8 @@ pub fn find(build: &mut Build) {
.warnings(false)
.debug(false)
.cpp(true)
.target(&target)
.host(&build.build);
.target(&target.triple)
.host(&build.build.triple);
let cxx_configured = if let Some(cxx) = config.and_then(|c| c.cxx.as_ref()) {
cfg.compiler(cxx);
@ -138,14 +137,14 @@ pub fn find(build: &mut Build) {
build.cxx.insert(target, compiler);
}
build.verbose(&format!("CC_{} = {:?}", &target, build.cc(target)));
build.verbose(&format!("CFLAGS_{} = {:?}", &target, cflags));
build.verbose(&format!("CC_{} = {:?}", &target.triple, build.cc(target)));
build.verbose(&format!("CFLAGS_{} = {:?}", &target.triple, cflags));
if let Ok(cxx) = build.cxx(target) {
build.verbose(&format!("CXX_{} = {:?}", &target, cxx));
build.verbose(&format!("CXXFLAGS_{} = {:?}", &target, cflags));
build.verbose(&format!("CXX_{} = {:?}", &target.triple, cxx));
build.verbose(&format!("CXXFLAGS_{} = {:?}", &target.triple, cflags));
}
if let Some(ar) = ar {
build.verbose(&format!("AR_{} = {:?}", &target, ar));
build.verbose(&format!("AR_{} = {:?}", &target.triple, ar));
build.ar.insert(target, ar);
}
}
@ -154,17 +153,18 @@ pub fn find(build: &mut Build) {
fn set_compiler(
cfg: &mut cc::Build,
compiler: Language,
target: Interned<String>,
target: TargetSelection,
config: Option<&Target>,
build: &Build,
) {
match &*target {
match &*target.triple {
// When compiling for android we may have the NDK configured in the
// config.toml in which case we look there. Otherwise the default
// compiler already takes into account the triple in question.
t if t.contains("android") => {
if let Some(ndk) = config.and_then(|c| c.ndk.as_ref()) {
let target = target
.triple
.replace("armv7neon", "arm")
.replace("armv7", "arm")
.replace("thumbv7neon", "arm")

View file

@ -1,15 +1,15 @@
//! Implementation of compiling the compiler and standard library, in "check"-based modes.
use crate::builder::{Builder, Kind, RunConfig, ShouldRun, Step};
use crate::cache::Interned;
use crate::compile::{add_to_sysroot, run_cargo, rustc_cargo, std_cargo};
use crate::config::TargetSelection;
use crate::tool::{prepare_tool_cargo, SourceType};
use crate::{Compiler, Mode};
use std::path::PathBuf;
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct Std {
pub target: Interned<String>,
pub target: TargetSelection,
}
fn args(kind: Kind) -> Vec<String> {
@ -71,7 +71,7 @@ impl Step for Std {
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct Rustc {
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for Rustc {
@ -127,7 +127,7 @@ macro_rules! tool_check_step {
($name:ident, $path:expr, $source_type:expr) => {
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct $name {
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for $name {
@ -163,8 +163,8 @@ macro_rules! tool_check_step {
println!(
"Checking {} artifacts ({} -> {})",
stringify!($name).to_lowercase(),
&compiler.host,
target
&compiler.host.triple,
target.triple
);
run_cargo(
builder,
@ -184,7 +184,7 @@ macro_rules! tool_check_step {
fn stamp(
builder: &Builder<'_>,
compiler: Compiler,
target: Interned<String>,
target: TargetSelection,
) -> PathBuf {
builder
.cargo_out(compiler, Mode::ToolRustc, target)
@ -204,12 +204,12 @@ tool_check_step!(Clippy, "src/tools/clippy", SourceType::InTree);
/// Cargo's output path for the standard library in a given stage, compiled
/// by a particular compiler for the specified target.
fn libstd_stamp(builder: &Builder<'_>, compiler: Compiler, target: Interned<String>) -> PathBuf {
fn libstd_stamp(builder: &Builder<'_>, compiler: Compiler, target: TargetSelection) -> PathBuf {
builder.cargo_out(compiler, Mode::Std, target).join(".libstd-check.stamp")
}
/// Cargo's output path for librustc in a given stage, compiled by a particular
/// compiler for the specified target.
fn librustc_stamp(builder: &Builder<'_>, compiler: Compiler, target: Interned<String>) -> PathBuf {
fn librustc_stamp(builder: &Builder<'_>, compiler: Compiler, target: TargetSelection) -> PathBuf {
builder.cargo_out(compiler, Mode::Rustc, target).join(".librustc-check.stamp")
}

View file

@ -23,7 +23,7 @@ pub fn clean(build: &Build, all: bool) {
rm_rf(&build.out.join("dist"));
for host in &build.hosts {
let entries = match build.out.join(host).read_dir() {
let entries = match build.out.join(host.triple).read_dir() {
Ok(iter) => iter,
Err(_) => continue,
};

View file

@ -22,6 +22,7 @@ use serde::Deserialize;
use crate::builder::Cargo;
use crate::builder::{Builder, Kind, RunConfig, ShouldRun, Step};
use crate::cache::{Interned, INTERNER};
use crate::config::TargetSelection;
use crate::dist;
use crate::native;
use crate::tool::SourceType;
@ -30,7 +31,7 @@ use crate::{Compiler, DependencyType, GitRepo, Mode};
#[derive(Debug, PartialOrd, Ord, Copy, Clone, PartialEq, Eq, Hash)]
pub struct Std {
pub target: Interned<String>,
pub target: TargetSelection,
pub compiler: Compiler,
}
@ -129,7 +130,7 @@ fn copy_and_stamp(
fn copy_third_party_objects(
builder: &Builder<'_>,
compiler: &Compiler,
target: Interned<String>,
target: TargetSelection,
) -> Vec<(PathBuf, DependencyType)> {
let mut target_deps = vec![];
@ -157,7 +158,7 @@ fn copy_third_party_objects(
fn copy_self_contained_objects(
builder: &Builder<'_>,
compiler: &Compiler,
target: Interned<String>,
target: TargetSelection,
) -> Vec<(PathBuf, DependencyType)> {
let libdir_self_contained = builder.sysroot_libdir(*compiler, target).join("self-contained");
t!(fs::create_dir_all(&libdir_self_contained));
@ -206,7 +207,7 @@ fn copy_self_contained_objects(
/// Configure cargo to compile the standard library, adding appropriate env vars
/// and such.
pub fn std_cargo(builder: &Builder<'_>, target: Interned<String>, stage: u32, cargo: &mut Cargo) {
pub fn std_cargo(builder: &Builder<'_>, target: TargetSelection, stage: u32, cargo: &mut Cargo) {
if let Some(target) = env::var_os("MACOSX_STD_DEPLOYMENT_TARGET") {
cargo.env("MACOSX_DEPLOYMENT_TARGET", target);
}
@ -301,7 +302,7 @@ pub fn std_cargo(builder: &Builder<'_>, target: Interned<String>, stage: u32, ca
struct StdLink {
pub compiler: Compiler,
pub target_compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for StdLink {
@ -337,7 +338,7 @@ impl Step for StdLink {
fn copy_sanitizers(
builder: &Builder<'_>,
compiler: &Compiler,
target: Interned<String>,
target: TargetSelection,
) -> Vec<PathBuf> {
let runtimes: Vec<native::SanitizerRuntime> = builder.ensure(native::Sanitizers { target });
@ -372,7 +373,7 @@ fn copy_sanitizers(
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct StartupObjects {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for StartupObjects {
@ -419,7 +420,7 @@ impl Step for StartupObjects {
.arg("--cfg")
.arg("bootstrap")
.arg("--target")
.arg(target)
.arg(target.rustc_target_arg())
.arg("--emit=obj")
.arg("-o")
.arg(dst_file)
@ -438,7 +439,7 @@ impl Step for StartupObjects {
#[derive(Debug, PartialOrd, Ord, Copy, Clone, PartialEq, Eq, Hash)]
pub struct Rustc {
pub target: Interned<String>,
pub target: TargetSelection,
pub compiler: Compiler,
}
@ -518,7 +519,7 @@ impl Step for Rustc {
}
}
pub fn rustc_cargo(builder: &Builder<'_>, cargo: &mut Cargo, target: Interned<String>) {
pub fn rustc_cargo(builder: &Builder<'_>, cargo: &mut Cargo, target: TargetSelection) {
cargo
.arg("--features")
.arg(builder.rustc_features())
@ -527,7 +528,7 @@ pub fn rustc_cargo(builder: &Builder<'_>, cargo: &mut Cargo, target: Interned<St
rustc_cargo_env(builder, cargo, target);
}
pub fn rustc_cargo_env(builder: &Builder<'_>, cargo: &mut Cargo, target: Interned<String>) {
pub fn rustc_cargo_env(builder: &Builder<'_>, cargo: &mut Cargo, target: TargetSelection) {
// Set some configuration variables picked up by build scripts and
// the compiler alike
cargo
@ -608,7 +609,7 @@ pub fn rustc_cargo_env(builder: &Builder<'_>, cargo: &mut Cargo, target: Interne
struct RustcLink {
pub compiler: Compiler,
pub target_compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for RustcLink {
@ -638,11 +639,7 @@ impl Step for RustcLink {
/// Cargo's output path for the standard library in a given stage, compiled
/// by a particular compiler for the specified target.
pub fn libstd_stamp(
builder: &Builder<'_>,
compiler: Compiler,
target: Interned<String>,
) -> PathBuf {
pub fn libstd_stamp(builder: &Builder<'_>, compiler: Compiler, target: TargetSelection) -> PathBuf {
builder.cargo_out(compiler, Mode::Std, target).join(".libstd.stamp")
}
@ -651,7 +648,7 @@ pub fn libstd_stamp(
pub fn librustc_stamp(
builder: &Builder<'_>,
compiler: Compiler,
target: Interned<String>,
target: TargetSelection,
) -> PathBuf {
builder.cargo_out(compiler, Mode::Rustc, target).join(".librustc.stamp")
}
@ -659,7 +656,7 @@ pub fn librustc_stamp(
pub fn compiler_file(
builder: &Builder<'_>,
compiler: &Path,
target: Interned<String>,
target: TargetSelection,
file: &str,
) -> PathBuf {
let mut cmd = Command::new(compiler);
@ -690,9 +687,9 @@ impl Step for Sysroot {
fn run(self, builder: &Builder<'_>) -> Interned<PathBuf> {
let compiler = self.compiler;
let sysroot = if compiler.stage == 0 {
builder.out.join(&compiler.host).join("stage0-sysroot")
builder.out.join(&compiler.host.triple).join("stage0-sysroot")
} else {
builder.out.join(&compiler.host).join(format!("stage{}", compiler.stage))
builder.out.join(&compiler.host.triple).join(format!("stage{}", compiler.stage))
};
let _ = fs::remove_dir_all(&sysroot);
t!(fs::create_dir_all(&sysroot));
@ -806,8 +803,8 @@ impl Step for Assemble {
let libdir = builder.sysroot_libdir(target_compiler, target_compiler.host);
if let Some(lld_install) = lld_install {
let src_exe = exe("lld", &target_compiler.host);
let dst_exe = exe("rust-lld", &target_compiler.host);
let src_exe = exe("lld", target_compiler.host);
let dst_exe = exe("rust-lld", target_compiler.host);
// we prepend this bin directory to the user PATH when linking Rust binaries. To
// avoid shadowing the system LLD we rename the LLD we provide to `rust-lld`.
let dst = libdir.parent().unwrap().join("bin");
@ -822,7 +819,7 @@ impl Step for Assemble {
// Link the compiler binary itself into place
let out_dir = builder.cargo_out(build_compiler, Mode::Rustc, host);
let rustc = out_dir.join(exe("rustc_binary", &*host));
let rustc = out_dir.join(exe("rustc_binary", host));
let bindir = sysroot.join("bin");
t!(fs::create_dir_all(&bindir));
let compiler = builder.rustc(target_compiler);

View file

@ -7,6 +7,7 @@ use std::cmp;
use std::collections::{HashMap, HashSet};
use std::env;
use std::ffi::OsString;
use std::fmt;
use std::fs;
use std::path::{Path, PathBuf};
use std::process;
@ -39,7 +40,7 @@ pub struct Config {
pub docs: bool,
pub locked_deps: bool,
pub vendor: bool,
pub target_config: HashMap<Interned<String>, Target>,
pub target_config: HashMap<TargetSelection, Target>,
pub full_bootstrap: bool,
pub extended: bool,
pub tools: Option<HashSet<String>>,
@ -112,9 +113,9 @@ pub struct Config {
pub rust_thin_lto_import_instr_limit: Option<u32>,
pub rust_remap_debuginfo: bool,
pub build: Interned<String>,
pub hosts: Vec<Interned<String>>,
pub targets: Vec<Interned<String>>,
pub build: TargetSelection,
pub hosts: Vec<TargetSelection>,
pub targets: Vec<TargetSelection>,
pub local_rebuild: bool,
pub jemalloc: bool,
pub control_flow_guard: bool,
@ -158,6 +159,67 @@ pub struct Config {
pub out: PathBuf,
}
#[derive(Debug, Copy, Clone, Default, PartialEq, Eq, PartialOrd, Ord, Hash)]
pub struct TargetSelection {
pub triple: Interned<String>,
file: Option<Interned<String>>,
}
impl TargetSelection {
pub fn from_user(selection: &str) -> Self {
let path = Path::new(selection);
let (triple, file) = if path.exists() {
let triple = path
.file_stem()
.expect("Target specification file has no file stem")
.to_str()
.expect("Target specification file stem is not UTF-8");
(triple, Some(selection))
} else {
(selection, None)
};
let triple = INTERNER.intern_str(triple);
let file = file.map(|f| INTERNER.intern_str(f));
Self { triple, file }
}
pub fn rustc_target_arg(&self) -> &str {
self.file.as_ref().unwrap_or(&self.triple)
}
pub fn contains(&self, needle: &str) -> bool {
self.triple.contains(needle)
}
pub fn starts_with(&self, needle: &str) -> bool {
self.triple.starts_with(needle)
}
pub fn ends_with(&self, needle: &str) -> bool {
self.triple.ends_with(needle)
}
}
impl fmt::Display for TargetSelection {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "{}", self.triple)?;
if let Some(file) = self.file {
write!(f, "({})", file)?;
}
Ok(())
}
}
impl PartialEq<&str> for TargetSelection {
fn eq(&self, other: &&str) -> bool {
self.triple == *other
}
}
/// Per-target configuration stored in the global configuration structure.
#[derive(Default)]
pub struct Target {
@ -403,7 +465,7 @@ impl Config {
config.missing_tools = false;
// set by bootstrap.py
config.build = INTERNER.intern_str(&env::var("BUILD").expect("'BUILD' to be set"));
config.build = TargetSelection::from_user(&env::var("BUILD").expect("'BUILD' to be set"));
config.src = Config::path_from_python("SRC");
config.out = Config::path_from_python("BUILD_DIR");
@ -464,14 +526,16 @@ impl Config {
let build = toml.build.clone().unwrap_or_default();
// set by bootstrap.py
config.hosts.push(config.build.clone());
for host in build.host.iter() {
let host = INTERNER.intern_str(host);
for host in build.host.iter().map(|h| TargetSelection::from_user(h)) {
if !config.hosts.contains(&host) {
config.hosts.push(host);
}
}
for target in
config.hosts.iter().cloned().chain(build.target.iter().map(|s| INTERNER.intern_str(s)))
for target in config
.hosts
.iter()
.copied()
.chain(build.target.iter().map(|h| TargetSelection::from_user(h)))
{
if !config.targets.contains(&target) {
config.targets.push(target);
@ -637,7 +701,7 @@ impl Config {
target.wasi_root = cfg.wasi_root.clone().map(PathBuf::from);
target.qemu_rootfs = cfg.qemu_rootfs.clone().map(PathBuf::from);
config.target_config.insert(INTERNER.intern_string(triple.clone()), target);
config.target_config.insert(TargetSelection::from_user(triple), target);
}
}

View file

@ -20,6 +20,7 @@ use crate::builder::{Builder, RunConfig, ShouldRun, Step};
use crate::cache::{Interned, INTERNER};
use crate::channel;
use crate::compile;
use crate::config::TargetSelection;
use crate::tool::{self, Tool};
use crate::util::{exe, is_dylib, timeit};
use crate::{Compiler, DependencyType, Mode, LLVM_TOOLS};
@ -68,7 +69,7 @@ fn missing_tool(tool_name: &str, skip: bool) {
#[derive(Debug, PartialOrd, Ord, Copy, Clone, Hash, PartialEq, Eq)]
pub struct Docs {
pub host: Interned<String>,
pub host: TargetSelection,
}
impl Step for Docs {
@ -131,7 +132,7 @@ impl Step for Docs {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct RustcDocs {
pub host: Interned<String>,
pub host: TargetSelection,
}
impl Step for RustcDocs {
@ -210,11 +211,11 @@ fn find_files(files: &[&str], path: &[PathBuf]) -> Vec<PathBuf> {
fn make_win_dist(
rust_root: &Path,
plat_root: &Path,
target_triple: Interned<String>,
target: TargetSelection,
builder: &Builder<'_>,
) {
//Ask gcc where it keeps its stuff
let mut cmd = Command::new(builder.cc(target_triple));
let mut cmd = Command::new(builder.cc(target));
cmd.arg("-print-search-dirs");
let gcc_out = output(&mut cmd);
@ -234,16 +235,16 @@ fn make_win_dist(
}
}
let compiler = if target_triple == "i686-pc-windows-gnu" {
let compiler = if target == "i686-pc-windows-gnu" {
"i686-w64-mingw32-gcc.exe"
} else if target_triple == "x86_64-pc-windows-gnu" {
} else if target == "x86_64-pc-windows-gnu" {
"x86_64-w64-mingw32-gcc.exe"
} else {
"gcc.exe"
};
let target_tools = [compiler, "ld.exe", "dlltool.exe", "libwinpthread-1.dll"];
let mut rustc_dlls = vec!["libwinpthread-1.dll"];
if target_triple.starts_with("i686-") {
if target.starts_with("i686-") {
rustc_dlls.push("libgcc_s_dw2-1.dll");
} else {
rustc_dlls.push("libgcc_s_seh-1.dll");
@ -311,7 +312,7 @@ fn make_win_dist(
let target_bin_dir = plat_root
.join("lib")
.join("rustlib")
.join(target_triple)
.join(target.triple)
.join("bin")
.join("self-contained");
fs::create_dir_all(&target_bin_dir).expect("creating target_bin_dir failed");
@ -331,7 +332,7 @@ fn make_win_dist(
let target_lib_dir = plat_root
.join("lib")
.join("rustlib")
.join(target_triple)
.join(target.triple)
.join("lib")
.join("self-contained");
fs::create_dir_all(&target_lib_dir).expect("creating target_lib_dir failed");
@ -342,7 +343,7 @@ fn make_win_dist(
#[derive(Debug, PartialOrd, Ord, Copy, Clone, Hash, PartialEq, Eq)]
pub struct Mingw {
pub host: Interned<String>,
pub host: TargetSelection,
}
impl Step for Mingw {
@ -530,11 +531,11 @@ impl Step for Rustc {
// Copy over lld if it's there
if builder.config.lld_enabled {
let exe = exe("rust-lld", &compiler.host);
let exe = exe("rust-lld", compiler.host);
let src =
builder.sysroot_libdir(compiler, host).parent().unwrap().join("bin").join(&exe);
// for the rationale about this rename check `compile::copy_lld_to_sysroot`
let dst = image.join("lib/rustlib").join(&*host).join("bin").join(&exe);
let dst = image.join("lib/rustlib").join(&*host.triple).join("bin").join(&exe);
t!(fs::create_dir_all(&dst.parent().unwrap()));
builder.copy(&src, &dst);
}
@ -592,7 +593,7 @@ impl Step for Rustc {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct DebuggerScripts {
pub sysroot: Interned<PathBuf>,
pub host: Interned<String>,
pub host: TargetSelection,
}
impl Step for DebuggerScripts {
@ -662,8 +663,8 @@ fn skip_host_target_lib(builder: &Builder<'_>, compiler: Compiler) -> bool {
}
/// Copy stamped files into an image's `target/lib` directory.
fn copy_target_libs(builder: &Builder<'_>, target: &str, image: &Path, stamp: &Path) {
let dst = image.join("lib/rustlib").join(target).join("lib");
fn copy_target_libs(builder: &Builder<'_>, target: TargetSelection, image: &Path, stamp: &Path) {
let dst = image.join("lib/rustlib").join(target.triple).join("lib");
let self_contained_dst = dst.join("self-contained");
t!(fs::create_dir_all(&dst));
t!(fs::create_dir_all(&self_contained_dst));
@ -679,7 +680,7 @@ fn copy_target_libs(builder: &Builder<'_>, target: &str, image: &Path, stamp: &P
#[derive(Debug, PartialOrd, Ord, Copy, Clone, Hash, PartialEq, Eq)]
pub struct Std {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for Std {
@ -718,7 +719,7 @@ impl Step for Std {
let compiler_to_use = builder.compiler_for(compiler.stage, compiler.host, target);
let stamp = compile::libstd_stamp(builder, compiler_to_use, target);
copy_target_libs(builder, &target, &image, &stamp);
copy_target_libs(builder, target, &image, &stamp);
let mut cmd = rust_installer(builder);
cmd.arg("generate")
@ -747,7 +748,7 @@ impl Step for Std {
#[derive(Debug, PartialOrd, Ord, Copy, Clone, Hash, PartialEq, Eq)]
pub struct RustcDev {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for RustcDev {
@ -787,7 +788,7 @@ impl Step for RustcDev {
let compiler_to_use = builder.compiler_for(compiler.stage, compiler.host, target);
let stamp = compile::librustc_stamp(builder, compiler_to_use, target);
copy_target_libs(builder, &target, &image, &stamp);
copy_target_libs(builder, target, &image, &stamp);
let mut cmd = rust_installer(builder);
cmd.arg("generate")
@ -818,7 +819,7 @@ impl Step for RustcDev {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct Analysis {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for Analysis {
@ -861,12 +862,12 @@ impl Step for Analysis {
let src = builder
.stage_out(compiler, Mode::Std)
.join(target)
.join(target.triple)
.join(builder.cargo_dir())
.join("deps");
let image_src = src.join("save-analysis");
let dst = image.join("lib/rustlib").join(target).join("analysis");
let dst = image.join("lib/rustlib").join(target.triple).join("analysis");
t!(fs::create_dir_all(&dst));
builder.info(&format!("image_src: {:?}, dst: {:?}", image_src, dst));
builder.cp_r(&image_src, &dst);
@ -1163,7 +1164,7 @@ pub fn sanitize_sh(path: &Path) -> String {
#[derive(Debug, PartialOrd, Ord, Copy, Clone, Hash, PartialEq, Eq)]
pub struct Cargo {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for Cargo {
@ -1255,7 +1256,7 @@ impl Step for Cargo {
#[derive(Debug, PartialOrd, Ord, Copy, Clone, Hash, PartialEq, Eq)]
pub struct Rls {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for Rls {
@ -1345,7 +1346,7 @@ impl Step for Rls {
#[derive(Debug, PartialOrd, Ord, Copy, Clone, Hash, PartialEq, Eq)]
pub struct RustAnalyzer {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for RustAnalyzer {
@ -1432,7 +1433,7 @@ impl Step for RustAnalyzer {
#[derive(Debug, PartialOrd, Ord, Copy, Clone, Hash, PartialEq, Eq)]
pub struct Clippy {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for Clippy {
@ -1523,7 +1524,7 @@ impl Step for Clippy {
#[derive(Debug, PartialOrd, Ord, Copy, Clone, Hash, PartialEq, Eq)]
pub struct Miri {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for Miri {
@ -1620,7 +1621,7 @@ impl Step for Miri {
#[derive(Debug, PartialOrd, Ord, Copy, Clone, Hash, PartialEq, Eq)]
pub struct Rustfmt {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for Rustfmt {
@ -1714,8 +1715,8 @@ impl Step for Rustfmt {
#[derive(Debug, PartialOrd, Ord, Copy, Clone, Hash, PartialEq, Eq)]
pub struct Extended {
stage: u32,
host: Interned<String>,
target: Interned<String>,
host: TargetSelection,
target: TargetSelection,
}
impl Step for Extended {
@ -2255,7 +2256,7 @@ impl Step for Extended {
}
}
fn add_env(builder: &Builder<'_>, cmd: &mut Command, target: Interned<String>) {
fn add_env(builder: &Builder<'_>, cmd: &mut Command, target: TargetSelection) {
let mut parts = channel::CFG_RELEASE_NUM.split('.');
cmd.env("CFG_RELEASE_INFO", builder.rust_version())
.env("CFG_RELEASE_NUM", channel::CFG_RELEASE_NUM)
@ -2266,7 +2267,7 @@ fn add_env(builder: &Builder<'_>, cmd: &mut Command, target: Interned<String>) {
.env("CFG_VER_BUILD", "0") // just needed to build
.env("CFG_PACKAGE_VERS", builder.rust_package_vers())
.env("CFG_PACKAGE_NAME", pkgname(builder, "rust"))
.env("CFG_BUILD", target)
.env("CFG_BUILD", target.triple)
.env("CFG_CHANNEL", &builder.config.channel);
if target.contains("windows-gnu") {
@ -2348,7 +2349,7 @@ impl Step for HashSign {
///
/// Note: This function does not yet support Windows, but we also don't support
/// linking LLVM tools dynamically on Windows yet.
fn maybe_install_llvm(builder: &Builder<'_>, target: Interned<String>, dst_libdir: &Path) {
fn maybe_install_llvm(builder: &Builder<'_>, target: TargetSelection, dst_libdir: &Path) {
let src_libdir = builder.llvm_out(target).join("lib");
if target.contains("apple-darwin") {
@ -2373,13 +2374,13 @@ fn maybe_install_llvm(builder: &Builder<'_>, target: Interned<String>, dst_libdi
}
/// Maybe add libLLVM.so to the target lib-dir for linking.
pub fn maybe_install_llvm_target(builder: &Builder<'_>, target: Interned<String>, sysroot: &Path) {
let dst_libdir = sysroot.join("lib/rustlib").join(&*target).join("lib");
pub fn maybe_install_llvm_target(builder: &Builder<'_>, target: TargetSelection, sysroot: &Path) {
let dst_libdir = sysroot.join("lib/rustlib").join(&*target.triple).join("lib");
maybe_install_llvm(builder, target, &dst_libdir);
}
/// Maybe add libLLVM.so to the runtime lib-dir for rustc itself.
pub fn maybe_install_llvm_runtime(builder: &Builder<'_>, target: Interned<String>, sysroot: &Path) {
pub fn maybe_install_llvm_runtime(builder: &Builder<'_>, target: TargetSelection, sysroot: &Path) {
let dst_libdir =
sysroot.join(builder.sysroot_libdir_relative(Compiler { stage: 1, host: target }));
maybe_install_llvm(builder, target, &dst_libdir);
@ -2387,7 +2388,7 @@ pub fn maybe_install_llvm_runtime(builder: &Builder<'_>, target: Interned<String
#[derive(Clone, Debug, Eq, Hash, PartialEq)]
pub struct LlvmTools {
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for LlvmTools {
@ -2425,10 +2426,10 @@ impl Step for LlvmTools {
// Prepare the image directory
let src_bindir = builder.llvm_out(target).join("bin");
let dst_bindir = image.join("lib/rustlib").join(&*target).join("bin");
let dst_bindir = image.join("lib/rustlib").join(&*target.triple).join("bin");
t!(fs::create_dir_all(&dst_bindir));
for tool in LLVM_TOOLS {
let exe = src_bindir.join(exe(tool, &target));
let exe = src_bindir.join(exe(tool, target));
builder.install(&exe, &dst_bindir, 0o755);
}

View file

@ -18,7 +18,7 @@ use build_helper::{t, up_to_date};
use crate::builder::{Builder, Compiler, RunConfig, ShouldRun, Step};
use crate::cache::{Interned, INTERNER};
use crate::compile;
use crate::config::Config;
use crate::config::{Config, TargetSelection};
use crate::tool::{self, prepare_tool_cargo, SourceType, Tool};
use crate::util::symlink_dir;
@ -27,7 +27,7 @@ macro_rules! book {
$(
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct $name {
target: Interned<String>,
target: TargetSelection,
}
impl Step for $name {
@ -101,7 +101,7 @@ fn is_explicit_request(builder: &Builder<'_>, path: &str) -> bool {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct UnstableBook {
target: Interned<String>,
target: TargetSelection,
}
impl Step for UnstableBook {
@ -129,7 +129,7 @@ impl Step for UnstableBook {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
struct RustbookSrc {
target: Interned<String>,
target: TargetSelection,
name: Interned<String>,
src: Interned<PathBuf>,
}
@ -169,7 +169,7 @@ impl Step for RustbookSrc {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct TheBook {
compiler: Compiler,
target: Interned<String>,
target: TargetSelection,
}
impl Step for TheBook {
@ -241,7 +241,7 @@ impl Step for TheBook {
fn invoke_rustdoc(
builder: &Builder<'_>,
compiler: Compiler,
target: Interned<String>,
target: TargetSelection,
markdown: &str,
) {
let out = builder.doc_out(target);
@ -277,7 +277,7 @@ fn invoke_rustdoc(
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct Standalone {
compiler: Compiler,
target: Interned<String>,
target: TargetSelection,
}
impl Step for Standalone {
@ -386,7 +386,7 @@ impl Step for Standalone {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct Std {
pub stage: u32,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for Std {
@ -415,7 +415,7 @@ impl Step for Std {
let compiler = builder.compiler(stage, builder.config.build);
builder.ensure(compile::Std { compiler, target });
let out_dir = builder.stage_out(compiler, Mode::Std).join(target).join("doc");
let out_dir = builder.stage_out(compiler, Mode::Std).join(target.triple).join("doc");
t!(fs::copy(builder.src.join("src/doc/rust.css"), out.join("rust.css")));
@ -475,7 +475,7 @@ impl Step for Std {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct Rustc {
stage: u32,
target: Interned<String>,
target: TargetSelection,
}
impl Step for Rustc {
@ -522,7 +522,7 @@ impl Step for Rustc {
// needed because rustdoc is built in a different directory from
// rustc. rustdoc needs to be able to see everything, for example when
// merging the search index, or generating local (relative) links.
let out_dir = builder.stage_out(compiler, Mode::Rustc).join(target).join("doc");
let out_dir = builder.stage_out(compiler, Mode::Rustc).join(target.triple).join("doc");
t!(symlink_dir_force(&builder.config, &out, &out_dir));
// Build cargo command.
@ -559,7 +559,7 @@ impl Step for Rustc {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct Rustdoc {
stage: u32,
target: Interned<String>,
target: TargetSelection,
}
impl Step for Rustdoc {
@ -604,7 +604,7 @@ impl Step for Rustdoc {
builder.ensure(tool::Rustdoc { compiler });
// Symlink compiler docs to the output directory of rustdoc documentation.
let out_dir = builder.stage_out(compiler, Mode::ToolRustc).join(target).join("doc");
let out_dir = builder.stage_out(compiler, Mode::ToolRustc).join(target.triple).join("doc");
t!(fs::create_dir_all(&out_dir));
t!(symlink_dir_force(&builder.config, &out, &out_dir));
@ -632,7 +632,7 @@ impl Step for Rustdoc {
#[derive(Ord, PartialOrd, Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct ErrorIndex {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for ErrorIndex {
@ -672,7 +672,7 @@ impl Step for ErrorIndex {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct UnstableBookGen {
target: Interned<String>,
target: TargetSelection,
}
impl Step for UnstableBookGen {

View file

@ -10,8 +10,7 @@ use std::process;
use getopts::Options;
use crate::builder::Builder;
use crate::cache::{Interned, INTERNER};
use crate::config::Config;
use crate::config::{Config, TargetSelection};
use crate::{Build, DocTests};
/// Deserialized version of all flags for this compile.
@ -21,8 +20,8 @@ pub struct Flags {
pub stage: Option<u32>,
pub keep_stage: Vec<u32>,
pub host: Vec<Interned<String>>,
pub target: Vec<Interned<String>>,
pub host: Vec<TargetSelection>,
pub target: Vec<TargetSelection>,
pub config: Option<PathBuf>,
pub jobs: Option<u32>,
pub cmd: Subcommand,
@ -532,11 +531,11 @@ Arguments:
.collect(),
host: split(&matches.opt_strs("host"))
.into_iter()
.map(|x| INTERNER.intern_string(x))
.map(|x| TargetSelection::from_user(&x))
.collect::<Vec<_>>(),
target: split(&matches.opt_strs("target"))
.into_iter()
.map(|x| INTERNER.intern_string(x))
.map(|x| TargetSelection::from_user(&x))
.collect::<Vec<_>>(),
config: cfg_file,
jobs: matches.opt_str("jobs").map(|j| j.parse().expect("`jobs` should be a number")),

View file

@ -14,46 +14,47 @@ use crate::dist::{self, pkgname, sanitize_sh, tmpdir};
use crate::Compiler;
use crate::builder::{Builder, RunConfig, ShouldRun, Step};
use crate::cache::Interned;
use crate::config::Config;
use crate::config::{Config, TargetSelection};
pub fn install_docs(builder: &Builder<'_>, stage: u32, host: Interned<String>) {
pub fn install_docs(builder: &Builder<'_>, stage: u32, host: TargetSelection) {
install_sh(builder, "docs", "rust-docs", stage, Some(host));
}
pub fn install_std(builder: &Builder<'_>, stage: u32, target: Interned<String>) {
pub fn install_std(builder: &Builder<'_>, stage: u32, target: TargetSelection) {
install_sh(builder, "std", "rust-std", stage, Some(target));
}
pub fn install_cargo(builder: &Builder<'_>, stage: u32, host: Interned<String>) {
pub fn install_cargo(builder: &Builder<'_>, stage: u32, host: TargetSelection) {
install_sh(builder, "cargo", "cargo", stage, Some(host));
}
pub fn install_rls(builder: &Builder<'_>, stage: u32, host: Interned<String>) {
pub fn install_rls(builder: &Builder<'_>, stage: u32, host: TargetSelection) {
install_sh(builder, "rls", "rls", stage, Some(host));
}
pub fn install_rust_analyzer(builder: &Builder<'_>, stage: u32, host: Interned<String>) {
pub fn install_rust_analyzer(builder: &Builder<'_>, stage: u32, host: TargetSelection) {
install_sh(builder, "rust-analyzer", "rust-analyzer", stage, Some(host));
}
pub fn install_clippy(builder: &Builder<'_>, stage: u32, host: Interned<String>) {
pub fn install_clippy(builder: &Builder<'_>, stage: u32, host: TargetSelection) {
install_sh(builder, "clippy", "clippy", stage, Some(host));
}
pub fn install_miri(builder: &Builder<'_>, stage: u32, host: Interned<String>) {
pub fn install_miri(builder: &Builder<'_>, stage: u32, host: TargetSelection) {
install_sh(builder, "miri", "miri", stage, Some(host));
}
pub fn install_rustfmt(builder: &Builder<'_>, stage: u32, host: Interned<String>) {
pub fn install_rustfmt(builder: &Builder<'_>, stage: u32, host: TargetSelection) {
install_sh(builder, "rustfmt", "rustfmt", stage, Some(host));
}
pub fn install_analysis(builder: &Builder<'_>, stage: u32, host: Interned<String>) {
pub fn install_analysis(builder: &Builder<'_>, stage: u32, host: TargetSelection) {
install_sh(builder, "analysis", "rust-analysis", stage, Some(host));
}
pub fn install_src(builder: &Builder<'_>, stage: u32) {
install_sh(builder, "src", "rust-src", stage, None);
}
pub fn install_rustc(builder: &Builder<'_>, stage: u32, host: Interned<String>) {
pub fn install_rustc(builder: &Builder<'_>, stage: u32, host: TargetSelection) {
install_sh(builder, "rustc", "rustc", stage, Some(host));
}
@ -62,7 +63,7 @@ fn install_sh(
package: &str,
name: &str,
stage: u32,
host: Option<Interned<String>>,
host: Option<TargetSelection>,
) {
builder.info(&format!("Install {} stage{} ({:?})", package, stage, host));
@ -150,7 +151,7 @@ macro_rules! install {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct $name {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl $name {

View file

@ -123,6 +123,7 @@ use std::os::windows::fs::symlink_file;
use build_helper::{mtime, output, run, run_suppressed, t, try_run, try_run_suppressed};
use filetime::FileTime;
use crate::config::TargetSelection;
use crate::util::{exe, libdir, CiEnv};
mod builder;
@ -187,7 +188,7 @@ const LLVM_TOOLS: &[&str] = &[
#[derive(Eq, PartialOrd, Ord, PartialEq, Clone, Copy, Hash, Debug)]
pub struct Compiler {
stage: u32,
host: Interned<String>,
host: TargetSelection,
}
#[derive(PartialEq, Eq, Copy, Clone, Debug)]
@ -236,9 +237,9 @@ pub struct Build {
verbosity: usize,
// Targets for which to build
build: Interned<String>,
hosts: Vec<Interned<String>>,
targets: Vec<Interned<String>>,
build: TargetSelection,
hosts: Vec<TargetSelection>,
targets: Vec<TargetSelection>,
// Stage 0 (downloaded) compiler, lld and cargo or their local rust equivalents
initial_rustc: PathBuf,
@ -248,10 +249,10 @@ pub struct Build {
// Runtime state filled in later on
// C/C++ compilers and archiver for all targets
cc: HashMap<Interned<String>, cc::Tool>,
cxx: HashMap<Interned<String>, cc::Tool>,
ar: HashMap<Interned<String>, PathBuf>,
ranlib: HashMap<Interned<String>, PathBuf>,
cc: HashMap<TargetSelection, cc::Tool>,
cxx: HashMap<TargetSelection, cc::Tool>,
ar: HashMap<TargetSelection, PathBuf>,
ranlib: HashMap<TargetSelection, PathBuf>,
// Miscellaneous
crates: HashMap<Interned<String>, Crate>,
is_sudo: bool,
@ -259,7 +260,7 @@ pub struct Build {
delayed_failures: RefCell<Vec<String>>,
prerelease_version: Cell<Option<u32>>,
tool_artifacts:
RefCell<HashMap<Interned<String>, HashMap<String, (&'static str, PathBuf, Vec<String>)>>>,
RefCell<HashMap<TargetSelection, HashMap<String, (&'static str, PathBuf, Vec<String>)>>>,
}
#[derive(Debug)]
@ -365,7 +366,7 @@ impl Build {
output(
Command::new(&config.initial_rustc)
.arg("--target")
.arg(config.build)
.arg(config.build.rustc_target_arg())
.arg("--print")
.arg("target-libdir"),
)
@ -453,7 +454,7 @@ impl Build {
}
pub fn build_triple(&self) -> &[Interned<String>] {
unsafe { slice::from_raw_parts(&self.build, 1) }
slice::from_ref(&self.build.triple)
}
/// Executes the entire build, as configured by the flags and configuration.
@ -558,7 +559,10 @@ impl Build {
}
fn tools_dir(&self, compiler: Compiler) -> PathBuf {
let out = self.out.join(&*compiler.host).join(format!("stage{}-tools-bin", compiler.stage));
let out = self
.out
.join(&*compiler.host.triple)
.join(format!("stage{}-tools-bin", compiler.stage));
t!(fs::create_dir_all(&out));
out
}
@ -575,47 +579,47 @@ impl Build {
Mode::ToolBootstrap => "-bootstrap-tools",
Mode::ToolStd | Mode::ToolRustc => "-tools",
};
self.out.join(&*compiler.host).join(format!("stage{}{}", compiler.stage, suffix))
self.out.join(&*compiler.host.triple).join(format!("stage{}{}", compiler.stage, suffix))
}
/// Returns the root output directory for all Cargo output in a given stage,
/// running a particular compiler, whether or not we're building the
/// standard library, and targeting the specified architecture.
fn cargo_out(&self, compiler: Compiler, mode: Mode, target: Interned<String>) -> PathBuf {
self.stage_out(compiler, mode).join(&*target).join(self.cargo_dir())
fn cargo_out(&self, compiler: Compiler, mode: Mode, target: TargetSelection) -> PathBuf {
self.stage_out(compiler, mode).join(&*target.triple).join(self.cargo_dir())
}
/// Root output directory for LLVM compiled for `target`
///
/// Note that if LLVM is configured externally then the directory returned
/// will likely be empty.
fn llvm_out(&self, target: Interned<String>) -> PathBuf {
self.out.join(&*target).join("llvm")
fn llvm_out(&self, target: TargetSelection) -> PathBuf {
self.out.join(&*target.triple).join("llvm")
}
fn lld_out(&self, target: Interned<String>) -> PathBuf {
self.out.join(&*target).join("lld")
fn lld_out(&self, target: TargetSelection) -> PathBuf {
self.out.join(&*target.triple).join("lld")
}
/// Output directory for all documentation for a target
fn doc_out(&self, target: Interned<String>) -> PathBuf {
self.out.join(&*target).join("doc")
fn doc_out(&self, target: TargetSelection) -> PathBuf {
self.out.join(&*target.triple).join("doc")
}
/// Output directory for all documentation for a target
fn compiler_doc_out(&self, target: Interned<String>) -> PathBuf {
self.out.join(&*target).join("compiler-doc")
fn compiler_doc_out(&self, target: TargetSelection) -> PathBuf {
self.out.join(&*target.triple).join("compiler-doc")
}
/// Output directory for some generated md crate documentation for a target (temporary)
fn md_doc_out(&self, target: Interned<String>) -> Interned<PathBuf> {
INTERNER.intern_path(self.out.join(&*target).join("md-doc"))
fn md_doc_out(&self, target: TargetSelection) -> Interned<PathBuf> {
INTERNER.intern_path(self.out.join(&*target.triple).join("md-doc"))
}
/// Returns `true` if no custom `llvm-config` is set for the specified target.
///
/// If no custom `llvm-config` was specified then Rust's llvm will be used.
fn is_rust_llvm(&self, target: Interned<String>) -> bool {
fn is_rust_llvm(&self, target: TargetSelection) -> bool {
match self.config.target_config.get(&target) {
Some(ref c) => c.llvm_config.is_none(),
None => true,
@ -623,13 +627,13 @@ impl Build {
}
/// Returns the path to `FileCheck` binary for the specified target
fn llvm_filecheck(&self, target: Interned<String>) -> PathBuf {
fn llvm_filecheck(&self, target: TargetSelection) -> PathBuf {
let target_config = self.config.target_config.get(&target);
if let Some(s) = target_config.and_then(|c| c.llvm_filecheck.as_ref()) {
s.to_path_buf()
} else if let Some(s) = target_config.and_then(|c| c.llvm_config.as_ref()) {
let llvm_bindir = output(Command::new(s).arg("--bindir"));
let filecheck = Path::new(llvm_bindir.trim()).join(exe("FileCheck", &*target));
let filecheck = Path::new(llvm_bindir.trim()).join(exe("FileCheck", target));
if filecheck.exists() {
filecheck
} else {
@ -637,7 +641,7 @@ impl Build {
// llvm subdirectory of the libdir.
let llvm_libdir = output(Command::new(s).arg("--libdir"));
let lib_filecheck =
Path::new(llvm_libdir.trim()).join("llvm").join(exe("FileCheck", &*target));
Path::new(llvm_libdir.trim()).join("llvm").join(exe("FileCheck", target));
if lib_filecheck.exists() {
lib_filecheck
} else {
@ -662,18 +666,18 @@ impl Build {
} else {
base
};
base.join("bin").join(exe("FileCheck", &*target))
base.join("bin").join(exe("FileCheck", target))
}
}
/// Directory for libraries built from C/C++ code and shared between stages.
fn native_dir(&self, target: Interned<String>) -> PathBuf {
self.out.join(&*target).join("native")
fn native_dir(&self, target: TargetSelection) -> PathBuf {
self.out.join(&*target.triple).join("native")
}
/// Root output directory for rust_test_helpers library compiled for
/// `target`
fn test_helpers_out(&self, target: Interned<String>) -> PathBuf {
fn test_helpers_out(&self, target: TargetSelection) -> PathBuf {
self.native_dir(target).join("rust-test-helpers")
}
@ -686,7 +690,7 @@ impl Build {
/// Returns the libdir of the snapshot compiler.
fn rustc_snapshot_libdir(&self) -> PathBuf {
self.rustc_snapshot_sysroot().join(libdir(&self.config.build))
self.rustc_snapshot_sysroot().join(libdir(self.config.build))
}
/// Returns the sysroot of the snapshot compiler.
@ -784,13 +788,13 @@ impl Build {
}
/// Returns the path to the C compiler for the target specified.
fn cc(&self, target: Interned<String>) -> &Path {
fn cc(&self, target: TargetSelection) -> &Path {
self.cc[&target].path()
}
/// Returns a list of flags to pass to the C compiler for the target
/// specified.
fn cflags(&self, target: Interned<String>, which: GitRepo) -> Vec<String> {
fn cflags(&self, target: TargetSelection, which: GitRepo) -> Vec<String> {
// Filter out -O and /O (the optimization flags) that we picked up from
// cc-rs because the build scripts will determine that for themselves.
let mut base = self.cc[&target]
@ -811,7 +815,7 @@ impl Build {
// Work around an apparently bad MinGW / GCC optimization,
// See: http://lists.llvm.org/pipermail/cfe-dev/2016-December/051980.html
// See: https://gcc.gnu.org/bugzilla/show_bug.cgi?id=78936
if &*target == "i686-pc-windows-gnu" {
if &*target.triple == "i686-pc-windows-gnu" {
base.push("-fno-omit-frame-pointer".into());
}
@ -829,17 +833,17 @@ impl Build {
}
/// Returns the path to the `ar` archive utility for the target specified.
fn ar(&self, target: Interned<String>) -> Option<&Path> {
fn ar(&self, target: TargetSelection) -> Option<&Path> {
self.ar.get(&target).map(|p| &**p)
}
/// Returns the path to the `ranlib` utility for the target specified.
fn ranlib(&self, target: Interned<String>) -> Option<&Path> {
fn ranlib(&self, target: TargetSelection) -> Option<&Path> {
self.ranlib.get(&target).map(|p| &**p)
}
/// Returns the path to the C++ compiler for the target specified.
fn cxx(&self, target: Interned<String>) -> Result<&Path, String> {
fn cxx(&self, target: TargetSelection) -> Result<&Path, String> {
match self.cxx.get(&target) {
Some(p) => Ok(p.path()),
None => {
@ -849,12 +853,12 @@ impl Build {
}
/// Returns the path to the linker for the given target if it needs to be overridden.
fn linker(&self, target: Interned<String>, can_use_lld: bool) -> Option<&Path> {
fn linker(&self, target: TargetSelection, can_use_lld: bool) -> Option<&Path> {
if let Some(linker) = self.config.target_config.get(&target).and_then(|c| c.linker.as_ref())
{
Some(linker)
} else if target != self.config.build
&& util::use_host_linker(&target)
&& util::use_host_linker(target)
&& !target.contains("msvc")
{
Some(self.cc(target))
@ -866,7 +870,7 @@ impl Build {
}
/// Returns if this target should statically link the C runtime, if specified
fn crt_static(&self, target: Interned<String>) -> Option<bool> {
fn crt_static(&self, target: TargetSelection) -> Option<bool> {
if target.contains("pc-windows-msvc") {
Some(true)
} else {
@ -875,7 +879,7 @@ impl Build {
}
/// Returns the "musl root" for this `target`, if defined
fn musl_root(&self, target: Interned<String>) -> Option<&Path> {
fn musl_root(&self, target: TargetSelection) -> Option<&Path> {
self.config
.target_config
.get(&target)
@ -885,7 +889,7 @@ impl Build {
}
/// Returns the "musl libdir" for this `target`.
fn musl_libdir(&self, target: Interned<String>) -> Option<PathBuf> {
fn musl_libdir(&self, target: TargetSelection) -> Option<PathBuf> {
let t = self.config.target_config.get(&target)?;
if let libdir @ Some(_) = &t.musl_libdir {
return libdir.clone();
@ -894,18 +898,18 @@ impl Build {
}
/// Returns the sysroot for the wasi target, if defined
fn wasi_root(&self, target: Interned<String>) -> Option<&Path> {
fn wasi_root(&self, target: TargetSelection) -> Option<&Path> {
self.config.target_config.get(&target).and_then(|t| t.wasi_root.as_ref()).map(|p| &**p)
}
/// Returns `true` if this is a no-std `target`, if defined
fn no_std(&self, target: Interned<String>) -> Option<bool> {
fn no_std(&self, target: TargetSelection) -> Option<bool> {
self.config.target_config.get(&target).map(|t| t.no_std)
}
/// Returns `true` if the target will be tested using the `remote-test-client`
/// and `remote-test-server` binaries.
fn remote_tested(&self, target: Interned<String>) -> bool {
fn remote_tested(&self, target: TargetSelection) -> bool {
self.qemu_rootfs(target).is_some()
|| target.contains("android")
|| env::var_os("TEST_DEVICE_ADDR").is_some()
@ -916,7 +920,7 @@ impl Build {
///
/// If `Some` is returned then that means that tests for this target are
/// emulated with QEMU and binaries will need to be shipped to the emulator.
fn qemu_rootfs(&self, target: Interned<String>) -> Option<&Path> {
fn qemu_rootfs(&self, target: TargetSelection) -> Option<&Path> {
self.config.target_config.get(&target).and_then(|t| t.qemu_rootfs.as_ref()).map(|p| &**p)
}
@ -948,7 +952,7 @@ impl Build {
///
/// When all of these conditions are met the build will lift artifacts from
/// the previous stage forward.
fn force_use_stage1(&self, compiler: Compiler, target: Interned<String>) -> bool {
fn force_use_stage1(&self, compiler: Compiler, target: TargetSelection) -> bool {
!self.config.full_bootstrap
&& compiler.stage >= 2
&& (self.hosts.iter().any(|h| *h == target) || target == self.build)
@ -1058,7 +1062,7 @@ impl Build {
self.rust_version()
}
fn llvm_link_tools_dynamically(&self, target: Interned<String>) -> bool {
fn llvm_link_tools_dynamically(&self, target: TargetSelection) -> bool {
target.contains("linux-gnu") || target.contains("apple-darwin")
}

View file

@ -19,8 +19,8 @@ use std::process::Command;
use build_helper::{output, t};
use crate::builder::{Builder, RunConfig, ShouldRun, Step};
use crate::cache::Interned;
use crate::channel;
use crate::config::TargetSelection;
use crate::util::{self, exe};
use crate::GitRepo;
use build_helper::up_to_date;
@ -41,7 +41,7 @@ pub struct Meta {
// if not).
pub fn prebuilt_llvm_config(
builder: &Builder<'_>,
target: Interned<String>,
target: TargetSelection,
) -> Result<PathBuf, Meta> {
// If we're using a custom LLVM bail out here, but we can only use a
// custom LLVM for the build triple.
@ -54,13 +54,14 @@ pub fn prebuilt_llvm_config(
let root = "src/llvm-project/llvm";
let out_dir = builder.llvm_out(target);
let mut llvm_config_ret_dir = builder.llvm_out(builder.config.build);
if !builder.config.build.contains("msvc") || builder.config.ninja {
llvm_config_ret_dir.push("build");
}
llvm_config_ret_dir.push("bin");
let build_llvm_config = llvm_config_ret_dir.join(exe("llvm-config", &*builder.config.build));
let build_llvm_config = llvm_config_ret_dir.join(exe("llvm-config", builder.config.build));
let stamp = out_dir.join("llvm-finished-building");
let stamp = HashStamp::new(stamp, builder.in_tree_llvm_info.sha());
@ -93,7 +94,7 @@ pub fn prebuilt_llvm_config(
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct Llvm {
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for Llvm {
@ -115,9 +116,9 @@ impl Step for Llvm {
let target_native = if self.target.starts_with("riscv") {
// RISC-V target triples in Rust is not named the same as C compiler target triples.
// This converts Rust RISC-V target triples to C compiler triples.
let idx = target.find('-').unwrap();
let idx = target.triple.find('-').unwrap();
format!("riscv{}{}", &target[5..7], &target[idx..])
format!("riscv{}{}", &target.triple[5..7], &target.triple[idx..])
} else {
target.to_string()
};
@ -359,7 +360,7 @@ fn check_llvm_version(builder: &Builder<'_>, llvm_config: &Path) {
fn configure_cmake(
builder: &Builder<'_>,
target: Interned<String>,
target: TargetSelection,
cfg: &mut cmake::Config,
use_compiler_launcher: bool,
) {
@ -375,7 +376,7 @@ fn configure_cmake(
if builder.config.ninja {
cfg.generator("Ninja");
}
cfg.target(&target).host(&builder.config.build);
cfg.target(&target.triple).host(&builder.config.build.triple);
let sanitize_cc = |cc: &Path| {
if target.contains("msvc") {
@ -405,7 +406,7 @@ fn configure_cmake(
cfg.define("CMAKE_C_COMPILER", sanitize_cc(&wrap_cc))
.define("CMAKE_CXX_COMPILER", sanitize_cc(&wrap_cc));
cfg.env("SCCACHE_PATH", builder.config.ccache.as_ref().unwrap())
.env("SCCACHE_TARGET", target)
.env("SCCACHE_TARGET", target.triple)
.env("SCCACHE_CC", &cc)
.env("SCCACHE_CXX", &cxx);
@ -505,7 +506,7 @@ fn configure_cmake(
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct Lld {
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for Lld {
@ -578,8 +579,8 @@ impl Step for Lld {
// brittle and will break over time. If anyone knows better how to
// cross-compile LLD it would be much appreciated to fix this!
if target != builder.config.build {
cfg.env("LLVM_CONFIG_SHIM_REPLACE", &builder.config.build)
.env("LLVM_CONFIG_SHIM_REPLACE_WITH", &target)
cfg.env("LLVM_CONFIG_SHIM_REPLACE", &builder.config.build.triple)
.env("LLVM_CONFIG_SHIM_REPLACE_WITH", &target.triple)
.define(
"LLVM_TABLEGEN_EXE",
llvm_config.with_file_name("llvm-tblgen").with_extension(EXE_EXTENSION),
@ -599,7 +600,7 @@ impl Step for Lld {
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct TestHelpers {
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for TestHelpers {
@ -646,8 +647,8 @@ impl Step for TestHelpers {
cfg.cargo_metadata(false)
.out_dir(&dst)
.target(&target)
.host(&builder.config.build)
.target(&target.triple)
.host(&builder.config.build.triple)
.opt_level(0)
.warnings(false)
.debug(false)
@ -658,7 +659,7 @@ impl Step for TestHelpers {
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct Sanitizers {
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for Sanitizers {
@ -709,7 +710,7 @@ impl Step for Sanitizers {
let mut cfg = cmake::Config::new(&compiler_rt_dir);
cfg.profile("Release");
cfg.define("CMAKE_C_COMPILER_TARGET", self.target);
cfg.define("CMAKE_C_COMPILER_TARGET", self.target.triple);
cfg.define("COMPILER_RT_BUILD_BUILTINS", "OFF");
cfg.define("COMPILER_RT_BUILD_CRT", "OFF");
cfg.define("COMPILER_RT_BUILD_LIBFUZZER", "OFF");
@ -752,7 +753,7 @@ pub struct SanitizerRuntime {
/// Returns sanitizers available on a given target.
fn supported_sanitizers(
out_dir: &Path,
target: Interned<String>,
target: TargetSelection,
channel: &str,
) -> Vec<SanitizerRuntime> {
let darwin_libs = |os: &str, components: &[&str]| -> Vec<SanitizerRuntime> {
@ -778,7 +779,7 @@ fn supported_sanitizers(
.collect()
};
match &*target {
match &*target.triple {
"aarch64-fuchsia" => common_libs("fuchsia", "aarch64", &["asan"]),
"aarch64-unknown-linux-gnu" => {
common_libs("linux", "aarch64", &["asan", "lsan", "msan", "tsan"])

View file

@ -183,7 +183,11 @@ pub fn check(build: &mut Build) {
panic!("the iOS target is only supported on macOS");
}
build.config.target_config.entry(target.clone()).or_insert(Target::from_triple(target));
build
.config
.target_config
.entry(target.clone())
.or_insert(Target::from_triple(&target.triple));
if target.contains("-none-") || target.contains("nvptx") {
if build.no_std(*target) == Some(false) {

View file

@ -16,6 +16,7 @@ use build_helper::{self, output, t};
use crate::builder::{Builder, Compiler, Kind, RunConfig, ShouldRun, Step};
use crate::cache::{Interned, INTERNER};
use crate::compile;
use crate::config::TargetSelection;
use crate::dist;
use crate::flags::Subcommand;
use crate::native;
@ -93,7 +94,7 @@ fn try_run_quiet(builder: &Builder<'_>, cmd: &mut Command) -> bool {
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct Linkcheck {
host: Interned<String>,
host: TargetSelection,
}
impl Step for Linkcheck {
@ -115,7 +116,7 @@ impl Step for Linkcheck {
let _time = util::timeit(&builder);
try_run(
builder,
builder.tool_cmd(Tool::Linkchecker).arg(builder.out.join(host).join("doc")),
builder.tool_cmd(Tool::Linkchecker).arg(builder.out.join(host.triple).join("doc")),
);
}
@ -132,7 +133,7 @@ impl Step for Linkcheck {
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct Cargotest {
stage: u32,
host: Interned<String>,
host: TargetSelection,
}
impl Step for Cargotest {
@ -177,7 +178,7 @@ impl Step for Cargotest {
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct Cargo {
stage: u32,
host: Interned<String>,
host: TargetSelection,
}
impl Step for Cargo {
@ -230,7 +231,7 @@ impl Step for Cargo {
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct Rls {
stage: u32,
host: Interned<String>,
host: TargetSelection,
}
impl Step for Rls {
@ -281,7 +282,7 @@ impl Step for Rls {
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct Rustfmt {
stage: u32,
host: Interned<String>,
host: TargetSelection,
}
impl Step for Rustfmt {
@ -338,7 +339,7 @@ impl Step for Rustfmt {
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct Miri {
stage: u32,
host: Interned<String>,
host: TargetSelection,
}
impl Step for Miri {
@ -464,7 +465,7 @@ impl Step for Miri {
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct CompiletestTest {
host: Interned<String>,
host: TargetSelection,
}
impl Step for CompiletestTest {
@ -501,7 +502,7 @@ impl Step for CompiletestTest {
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct Clippy {
stage: u32,
host: Interned<String>,
host: TargetSelection,
}
impl Step for Clippy {
@ -542,8 +543,10 @@ impl Step for Clippy {
cargo.env("RUSTC_TEST_SUITE", builder.rustc(compiler));
cargo.env("RUSTC_LIB_PATH", builder.rustc_libdir(compiler));
let host_libs = builder.stage_out(compiler, Mode::ToolRustc).join(builder.cargo_dir());
let target_libs =
builder.stage_out(compiler, Mode::ToolRustc).join(&self.host).join(builder.cargo_dir());
let target_libs = builder
.stage_out(compiler, Mode::ToolRustc)
.join(&self.host.triple)
.join(builder.cargo_dir());
cargo.env("HOST_LIBS", host_libs);
cargo.env("TARGET_LIBS", target_libs);
// clippy tests need to find the driver
@ -607,7 +610,7 @@ impl Step for RustdocTheme {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct RustdocJSStd {
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for RustdocJSStd {
@ -646,8 +649,8 @@ impl Step for RustdocJSStd {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct RustdocJSNotStd {
pub host: Interned<String>,
pub target: Interned<String>,
pub host: TargetSelection,
pub target: TargetSelection,
pub compiler: Compiler,
}
@ -683,8 +686,8 @@ impl Step for RustdocJSNotStd {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct RustdocUi {
pub host: Interned<String>,
pub target: Interned<String>,
pub host: TargetSelection,
pub target: TargetSelection,
pub compiler: Compiler,
}
@ -785,8 +788,8 @@ impl Step for ExpandYamlAnchors {
}
}
fn testdir(builder: &Builder<'_>, host: Interned<String>) -> PathBuf {
builder.out.join(host).join("test")
fn testdir(builder: &Builder<'_>, host: TargetSelection) -> PathBuf {
builder.out.join(host.triple).join("test")
}
macro_rules! default_test {
@ -855,7 +858,7 @@ macro_rules! test_definitions {
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct $name {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for $name {
@ -943,7 +946,7 @@ default_test!(Assembly { path: "src/test/assembly", mode: "assembly", suite: "as
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
struct Compiletest {
compiler: Compiler,
target: Interned<String>,
target: TargetSelection,
mode: &'static str,
suite: &'static str,
path: &'static str,
@ -1023,8 +1026,8 @@ impl Step for Compiletest {
cmd.arg("--build-base").arg(testdir(builder, compiler.host).join(suite));
cmd.arg("--stage-id").arg(format!("stage{}-{}", compiler.stage, target));
cmd.arg("--mode").arg(mode);
cmd.arg("--target").arg(target);
cmd.arg("--host").arg(&*compiler.host);
cmd.arg("--target").arg(target.rustc_target_arg());
cmd.arg("--host").arg(&*compiler.host.triple);
cmd.arg("--llvm-filecheck").arg(builder.llvm_filecheck(builder.config.build));
if builder.config.cmd.bless() {
@ -1543,7 +1546,7 @@ impl Step for RustcGuide {
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct CrateLibrustc {
compiler: Compiler,
target: Interned<String>,
target: TargetSelection,
test_kind: TestKind,
krate: Interned<String>,
}
@ -1589,7 +1592,7 @@ impl Step for CrateLibrustc {
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct CrateNotDefault {
compiler: Compiler,
target: Interned<String>,
target: TargetSelection,
test_kind: TestKind,
krate: &'static str,
}
@ -1638,7 +1641,7 @@ impl Step for CrateNotDefault {
#[derive(Debug, Copy, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
pub struct Crate {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
pub mode: Mode,
pub test_kind: TestKind,
pub krate: Interned<String>,
@ -1750,17 +1753,17 @@ impl Step for Crate {
if target.contains("emscripten") {
cargo.env(
format!("CARGO_TARGET_{}_RUNNER", envify(&target)),
format!("CARGO_TARGET_{}_RUNNER", envify(&target.triple)),
builder.config.nodejs.as_ref().expect("nodejs not configured"),
);
} else if target.starts_with("wasm32") {
let node = builder.config.nodejs.as_ref().expect("nodejs not configured");
let runner =
format!("{} {}/src/etc/wasm32-shim.js", node.display(), builder.src.display());
cargo.env(format!("CARGO_TARGET_{}_RUNNER", envify(&target)), &runner);
cargo.env(format!("CARGO_TARGET_{}_RUNNER", envify(&target.triple)), &runner);
} else if builder.remote_tested(target) {
cargo.env(
format!("CARGO_TARGET_{}_RUNNER", envify(&target)),
format!("CARGO_TARGET_{}_RUNNER", envify(&target.triple)),
format!("{} run 0", builder.tool_exe(Tool::RemoteTestClient).display()),
);
}
@ -1776,7 +1779,7 @@ impl Step for Crate {
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct CrateRustdoc {
host: Interned<String>,
host: TargetSelection,
test_kind: TestKind,
}
@ -1883,7 +1886,7 @@ impl Step for CrateRustdoc {
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub struct RemoteCopyLibs {
compiler: Compiler,
target: Interned<String>,
target: TargetSelection,
}
impl Step for RemoteCopyLibs {
@ -1911,7 +1914,7 @@ impl Step for RemoteCopyLibs {
// Spawn the emulator and wait for it to come online
let tool = builder.tool_exe(Tool::RemoteTestClient);
let mut cmd = Command::new(&tool);
cmd.arg("spawn-emulator").arg(target).arg(&server).arg(builder.out.join("tmp"));
cmd.arg("spawn-emulator").arg(target.triple).arg(&server).arg(builder.out.join("tmp"));
if let Some(rootfs) = builder.qemu_rootfs(target) {
cmd.arg(rootfs);
}
@ -1966,7 +1969,9 @@ impl Step for Distcheck {
.current_dir(&dir),
);
builder.run(
Command::new(build_helper::make(&builder.config.build)).arg("check").current_dir(&dir),
Command::new(build_helper::make(&builder.config.build.triple))
.arg("check")
.current_dir(&dir),
);
// Now make sure that rust-src has all of libstd's dependencies

View file

@ -7,10 +7,10 @@ use std::process::{exit, Command};
use build_helper::t;
use crate::builder::{Builder, Cargo as CargoCommand, RunConfig, ShouldRun, Step};
use crate::cache::Interned;
use crate::channel;
use crate::channel::GitInfo;
use crate::compile;
use crate::config::TargetSelection;
use crate::toolstate::ToolState;
use crate::util::{add_dylib_path, exe};
use crate::Compiler;
@ -25,7 +25,7 @@ pub enum SourceType {
#[derive(Debug, Clone, Hash, PartialEq, Eq)]
struct ToolBuild {
compiler: Compiler,
target: Interned<String>,
target: TargetSelection,
tool: &'static str,
path: &'static str,
mode: Mode,
@ -111,7 +111,7 @@ impl Step for ToolBuild {
.and_then(|p| p.file_name())
.and_then(|p| p.to_str())
.unwrap();
if maybe_target != &*target {
if maybe_target != &*target.triple {
continue;
}
}
@ -208,8 +208,8 @@ impl Step for ToolBuild {
}
} else {
let cargo_out =
builder.cargo_out(compiler, self.mode, target).join(exe(tool, &compiler.host));
let bin = builder.tools_dir(compiler).join(exe(tool, &compiler.host));
builder.cargo_out(compiler, self.mode, target).join(exe(tool, compiler.host));
let bin = builder.tools_dir(compiler).join(exe(tool, compiler.host));
builder.copy(&cargo_out, &bin);
Some(bin)
}
@ -220,7 +220,7 @@ pub fn prepare_tool_cargo(
builder: &Builder<'_>,
compiler: Compiler,
mode: Mode,
target: Interned<String>,
target: TargetSelection,
command: &'static str,
path: &'static str,
source_type: SourceType,
@ -303,7 +303,7 @@ macro_rules! bootstrap_tool {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct $name {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for $name {
@ -416,7 +416,7 @@ impl Step for ErrorIndex {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct RemoteTestServer {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for RemoteTestServer {
@ -476,7 +476,7 @@ impl Step for Rustdoc {
if !target_compiler.is_snapshot(builder) {
panic!("rustdoc in stage 0 must be snapshot rustdoc");
}
return builder.initial_rustc.with_file_name(exe("rustdoc", &target_compiler.host));
return builder.initial_rustc.with_file_name(exe("rustdoc", target_compiler.host));
}
let target = target_compiler.host;
// Similar to `compile::Assemble`, build with the previous stage's compiler. Otherwise
@ -514,14 +514,14 @@ impl Step for Rustdoc {
// rustdoc a different name.
let tool_rustdoc = builder
.cargo_out(build_compiler, Mode::ToolRustc, target)
.join(exe("rustdoc_tool_binary", &target_compiler.host));
.join(exe("rustdoc_tool_binary", target_compiler.host));
// don't create a stage0-sysroot/bin directory.
if target_compiler.stage > 0 {
let sysroot = builder.sysroot(target_compiler);
let bindir = sysroot.join("bin");
t!(fs::create_dir_all(&bindir));
let bin_rustdoc = bindir.join(exe("rustdoc", &*target_compiler.host));
let bin_rustdoc = bindir.join(exe("rustdoc", target_compiler.host));
let _ = fs::remove_file(&bin_rustdoc);
builder.copy(&tool_rustdoc, &bin_rustdoc);
bin_rustdoc
@ -534,7 +534,7 @@ impl Step for Rustdoc {
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
pub struct Cargo {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
}
impl Step for Cargo {
@ -583,7 +583,7 @@ macro_rules! tool_extended {
#[derive(Debug, Clone, Hash, PartialEq, Eq)]
pub struct $name {
pub compiler: Compiler,
pub target: Interned<String>,
pub target: TargetSelection,
pub extra_features: Vec<String>,
}

View file

@ -14,17 +14,16 @@ use std::time::Instant;
use build_helper::t;
use crate::builder::Builder;
use crate::cache::Interned;
use crate::config::Config;
use crate::config::{Config, TargetSelection};
/// Returns the `name` as the filename of a static library for `target`.
pub fn staticlib(name: &str, target: &str) -> String {
pub fn staticlib(name: &str, target: TargetSelection) -> String {
if target.contains("windows") { format!("{}.lib", name) } else { format!("lib{}.a", name) }
}
/// Given an executable called `name`, return the filename for the
/// executable for a particular target.
pub fn exe(name: &str, target: &str) -> String {
pub fn exe(name: &str, target: TargetSelection) -> String {
if target.contains("windows") { format!("{}.exe", name) } else { name.to_string() }
}
@ -35,7 +34,7 @@ pub fn is_dylib(name: &str) -> bool {
/// Returns the corresponding relative library directory that the compiler's
/// dylibs will be found in.
pub fn libdir(target: &str) -> &'static str {
pub fn libdir(target: TargetSelection) -> &'static str {
if target.contains("windows") { "bin" } else { "lib" }
}
@ -294,7 +293,7 @@ pub fn forcing_clang_based_tests() -> bool {
}
}
pub fn use_host_linker(target: &Interned<String>) -> bool {
pub fn use_host_linker(target: TargetSelection) -> bool {
// FIXME: this information should be gotten by checking the linker flavor
// of the rustc target
!(target.contains("emscripten")

View file

@ -573,7 +573,7 @@ impl<T: ?Sized> Arc<T> {
/// Provides a raw pointer to the data.
///
/// The counts are not affected in way and the `Arc` is not consumed. The pointer is valid for
/// The counts are not affected in any way and the `Arc` is not consumed. The pointer is valid for
/// as long as there are strong counts in the `Arc`.
///
/// # Examples

View file

@ -324,7 +324,7 @@ impl<'a> Arguments<'a> {
#[doc(hidden)]
#[inline]
#[unstable(feature = "fmt_internals", reason = "internal to format_args!", issue = "none")]
pub fn new_v1(pieces: &'a [&'a str], args: &'a [ArgumentV1<'a>]) -> Arguments<'a> {
pub fn new_v1(pieces: &'a [&'static str], args: &'a [ArgumentV1<'a>]) -> Arguments<'a> {
Arguments { pieces, fmt: None, args }
}
@ -338,7 +338,7 @@ impl<'a> Arguments<'a> {
#[inline]
#[unstable(feature = "fmt_internals", reason = "internal to format_args!", issue = "none")]
pub fn new_v1_formatted(
pieces: &'a [&'a str],
pieces: &'a [&'static str],
args: &'a [ArgumentV1<'a>],
fmt: &'a [rt::v1::Argument],
) -> Arguments<'a> {
@ -399,7 +399,7 @@ impl<'a> Arguments<'a> {
#[derive(Copy, Clone)]
pub struct Arguments<'a> {
// Format string pieces to print.
pieces: &'a [&'a str],
pieces: &'a [&'static str],
// Placeholder specs, or `None` if all specs are default (as in "{}{}").
fmt: Option<&'a [rt::v1::Argument]>,
@ -409,6 +409,47 @@ pub struct Arguments<'a> {
args: &'a [ArgumentV1<'a>],
}
impl<'a> Arguments<'a> {
/// Get the formatted string, if it has no arguments to be formatted.
///
/// This can be used to avoid allocations in the most trivial case.
///
/// # Examples
///
/// ```rust
/// #![feature(fmt_as_str)]
///
/// use core::fmt::Arguments;
///
/// fn write_str(_: &str) { /* ... */ }
///
/// fn write_fmt(args: &Arguments) {
/// if let Some(s) = args.as_str() {
/// write_str(s)
/// } else {
/// write_str(&args.to_string());
/// }
/// }
/// ```
///
/// ```rust
/// #![feature(fmt_as_str)]
///
/// assert_eq!(format_args!("hello").as_str(), Some("hello"));
/// assert_eq!(format_args!("").as_str(), Some(""));
/// assert_eq!(format_args!("{}", 1).as_str(), None);
/// ```
#[unstable(feature = "fmt_as_str", issue = "74442")]
#[inline]
pub fn as_str(&self) -> Option<&'static str> {
match (self.pieces, self.args) {
([], []) => Some(""),
([s], []) => Some(s),
_ => None,
}
}
}
#[stable(feature = "rust1", since = "1.0.0")]
impl Debug for Arguments<'_> {
fn fmt(&self, fmt: &mut Formatter<'_>) -> Result {

View file

@ -39,11 +39,11 @@
//! ```
//!
//! An iterator has a method, [`next`], which when called, returns an
//! [`Option`]`<Item>`. [`next`] will return `Some(Item)` as long as there
//! [`Option`]`<Item>`. [`next`] will return [`Some(Item)`] as long as there
//! are elements, and once they've all been exhausted, will return `None` to
//! indicate that iteration is finished. Individual iterators may choose to
//! resume iteration, and so calling [`next`] again may or may not eventually
//! start returning `Some(Item)` again at some point (for example, see [`TryIter`]).
//! start returning [`Some(Item)`] again at some point (for example, see [`TryIter`]).
//!
//! [`Iterator`]'s full definition includes a number of other methods as well,
//! but they are default methods, built on top of [`next`], and so you get
@ -53,9 +53,9 @@
//! more complex forms of processing. See the [Adapters](#adapters) section
//! below for more details.
//!
//! [`Some(Item)`]: Some
//! [`Iterator`]: trait.Iterator.html
//! [`next`]: trait.Iterator.html#tymethod.next
//! [`Option`]: ../../std/option/enum.Option.html
//! [`TryIter`]: ../../std/sync/mpsc/struct.TryIter.html
//!
//! # The three forms of iteration
@ -72,9 +72,9 @@
//! # Implementing Iterator
//!
//! Creating an iterator of your own involves two steps: creating a `struct` to
//! hold the iterator's state, and then `impl`ementing [`Iterator`] for that
//! `struct`. This is why there are so many `struct`s in this module: there is
//! one for each iterator and iterator adapter.
//! hold the iterator's state, and then implementing [`Iterator`] for that `struct`.
//! This is why there are so many `struct`s in this module: there is one for
//! each iterator and iterator adapter.
//!
//! Let's make an iterator named `Counter` which counts from `1` to `5`:
//!

View file

@ -9,9 +9,9 @@ use crate::ops::{Add, Mul};
/// [`FromIterator`] this trait should rarely be called directly and instead
/// interacted with through [`Iterator::sum`].
///
/// [`sum`]: ../../std/iter/trait.Sum.html#tymethod.sum
/// [`FromIterator`]: ../../std/iter/trait.FromIterator.html
/// [`Iterator::sum`]: ../../std/iter/trait.Iterator.html#method.sum
/// [`sum`]: #tymethod.sum
/// [`FromIterator`]: crate::iter::FromIterator
/// [`Iterator::sum`]: crate::iter::Iterator::sum
#[stable(feature = "iter_arith_traits", since = "1.12.0")]
pub trait Sum<A = Self>: Sized {
/// Method which takes an iterator and generates `Self` from the elements by
@ -28,9 +28,9 @@ pub trait Sum<A = Self>: Sized {
/// [`FromIterator`] this trait should rarely be called directly and instead
/// interacted with through [`Iterator::product`].
///
/// [`product`]: ../../std/iter/trait.Product.html#tymethod.product
/// [`FromIterator`]: ../../std/iter/trait.FromIterator.html
/// [`Iterator::product`]: ../../std/iter/trait.Iterator.html#method.product
/// [`product`]: #tymethod.product
/// [`FromIterator`]: crate::iter::FromIterator
/// [`Iterator::product`]: crate::iter::Iterator::product
#[stable(feature = "iter_arith_traits", since = "1.12.0")]
pub trait Product<A = Self>: Sized {
/// Method which takes an iterator and generates `Self` from the elements by

View file

@ -106,8 +106,7 @@ pub trait DoubleEndedIterator: Iterator {
/// `nth_back()` will return [`None`] if `n` is greater than or equal to the length of the
/// iterator.
///
/// [`None`]: ../../std/option/enum.Option.html#variant.None
/// [`nth`]: ../../std/iter/trait.Iterator.html#method.nth
/// [`nth`]: crate::iter::Iterator::nth
///
/// # Examples
///
@ -274,8 +273,7 @@ pub trait DoubleEndedIterator: Iterator {
/// argument is a double reference. You can see this effect in the
/// examples below, with `&&x`.
///
/// [`Some(element)`]: ../../std/option/enum.Option.html#variant.Some
/// [`None`]: ../../std/option/enum.Option.html#variant.None
/// [`Some(element)`]: Some
///
/// # Examples
///

View file

@ -106,8 +106,7 @@ pub trait Iterator {
/// again may or may not eventually start returning [`Some(Item)`] again at some
/// point.
///
/// [`None`]: ../../std/option/enum.Option.html#variant.None
/// [`Some(Item)`]: ../../std/option/enum.Option.html#variant.Some
/// [`Some(Item)`]: Some
///
/// # Examples
///
@ -160,9 +159,7 @@ pub trait Iterator {
/// The default implementation returns `(0, `[`None`]`)` which is correct for any
/// iterator.
///
/// [`usize`]: ../../std/primitive.usize.html
/// [`Option`]: ../../std/option/enum.Option.html
/// [`None`]: ../../std/option/enum.Option.html#variant.None
/// [`usize`]: type@usize
///
/// # Examples
///
@ -214,8 +211,6 @@ pub trait Iterator {
/// called at least once even if the iterator does not have any elements.
///
/// [`next`]: #tymethod.next
/// [`None`]: ../../std/option/enum.Option.html#variant.None
/// [`Some`]: ../../std/option/enum.Option.html#variant.Some
///
/// # Overflow Behavior
///
@ -229,7 +224,7 @@ pub trait Iterator {
/// This function might panic if the iterator has more than [`usize::MAX`]
/// elements.
///
/// [`usize::MAX`]: ../../std/usize/constant.MAX.html
/// [`usize::MAX`]: crate::usize::MAX
///
/// # Examples
///
@ -263,8 +258,6 @@ pub trait Iterator {
/// doing so, it keeps track of the current element. After [`None`] is
/// returned, `last()` will then return the last element it saw.
///
/// [`None`]: ../../std/option/enum.Option.html#variant.None
///
/// # Examples
///
/// Basic usage:
@ -303,8 +296,6 @@ pub trait Iterator {
/// `nth()` will return [`None`] if `n` is greater than or equal to the length of the
/// iterator.
///
/// [`None`]: ../../std/option/enum.Option.html#variant.None
///
/// # Examples
///
/// Basic usage:
@ -537,9 +528,8 @@ pub trait Iterator {
/// assert_eq!((2, 'o'), zipper[2]);
/// ```
///
/// [`enumerate`]: trait.Iterator.html#method.enumerate
/// [`next`]: ../../std/iter/trait.Iterator.html#tymethod.next
/// [`None`]: ../../std/option/enum.Option.html#variant.None
/// [`enumerate`]: #method.enumerate
/// [`next`]: #tymethod.next
#[inline]
#[stable(feature = "rust1", since = "1.0.0")]
fn zip<U>(self, other: U) -> Zip<Self, U::IntoIter>
@ -568,7 +558,7 @@ pub trait Iterator {
/// more idiomatic to use [`for`] than `map()`.
///
/// [`for`]: ../../book/ch03-05-control-flow.html#looping-through-a-collection-with-for
/// [`FnMut`]: ../../std/ops/trait.FnMut.html
/// [`FnMut`]: crate::ops::FnMut
///
/// # Examples
///
@ -756,12 +746,11 @@ pub trait Iterator {
/// Basic usage:
///
/// ```
/// let a = ["1", "lol", "3", "NaN", "5"];
/// let a = ["1", "two", "NaN", "four", "5"];
///
/// let mut iter = a.iter().filter_map(|s| s.parse().ok());
///
/// assert_eq!(iter.next(), Some(1));
/// assert_eq!(iter.next(), Some(3));
/// assert_eq!(iter.next(), Some(5));
/// assert_eq!(iter.next(), None);
/// ```
@ -769,17 +758,14 @@ pub trait Iterator {
/// Here's the same example, but with [`filter`] and [`map`]:
///
/// ```
/// let a = ["1", "lol", "3", "NaN", "5"];
/// let a = ["1", "two", "NaN", "four", "5"];
/// let mut iter = a.iter().map(|s| s.parse()).filter(|s| s.is_ok()).map(|s| s.unwrap());
/// assert_eq!(iter.next(), Some(1));
/// assert_eq!(iter.next(), Some(3));
/// assert_eq!(iter.next(), Some(5));
/// assert_eq!(iter.next(), None);
/// ```
///
/// [`Option<T>`]: ../../std/option/enum.Option.html
/// [`Some`]: ../../std/option/enum.Option.html#variant.Some
/// [`None`]: ../../std/option/enum.Option.html#variant.None
/// [`Option<T>`]: Option
#[inline]
#[stable(feature = "rust1", since = "1.0.0")]
fn filter_map<B, F>(self, f: F) -> FilterMap<Self, F>
@ -812,8 +798,8 @@ pub trait Iterator {
/// The returned iterator might panic if the to-be-returned index would
/// overflow a [`usize`].
///
/// [`usize::MAX`]: ../../std/usize/constant.MAX.html
/// [`usize`]: ../../std/primitive.usize.html
/// [`usize`]: type@usize
/// [`usize::MAX`]: crate::usize::MAX
/// [`zip`]: #method.zip
///
/// # Examples
@ -849,8 +835,8 @@ pub trait Iterator {
/// anything other than fetching the next value) of the [`next`] method
/// will occur.
///
/// [`peek`]: struct.Peekable.html#method.peek
/// [`next`]: ../../std/iter/trait.Iterator.html#tymethod.next
/// [`peek`]: crate::iter::Peekable::peek
/// [`next`]: #tymethod.next
///
/// # Examples
///
@ -1116,8 +1102,6 @@ pub trait Iterator {
/// It is also not specified what this iterator returns after the first` None` is returned.
/// If you need fused iterator, use [`fuse`].
///
/// [`Some`]: ../../std/option/enum.Option.html#variant.Some
/// [`None`]: ../../std/option/enum.Option.html#variant.None
/// [`fuse`]: #method.fuse
#[inline]
#[unstable(feature = "iter_map_while", reason = "recently added", issue = "68537")]
@ -1216,8 +1200,6 @@ pub trait Iterator {
/// iterator and the return value from the closure, an [`Option`], is
/// yielded by the iterator.
///
/// [`Option`]: ../../std/option/enum.Option.html
///
/// # Examples
///
/// Basic usage:
@ -1366,8 +1348,7 @@ pub trait Iterator {
/// [`Some(T)`] again. `fuse()` adapts an iterator, ensuring that after a
/// [`None`] is given, it will always return [`None`] forever.
///
/// [`None`]: ../../std/option/enum.Option.html#variant.None
/// [`Some(T)`]: ../../std/option/enum.Option.html#variant.Some
/// [`Some(T)`]: Some
///
/// # Examples
///
@ -1658,10 +1639,9 @@ pub trait Iterator {
/// assert_eq!(Ok(vec![1, 3]), result);
/// ```
///
/// [`iter`]: ../../std/iter/trait.Iterator.html#tymethod.next
/// [`iter`]: #tymethod.next
/// [`String`]: ../../std/string/struct.String.html
/// [`char`]: ../../std/primitive.char.html
/// [`Result`]: ../../std/result/enum.Result.html
/// [`char`]: type@char
#[inline]
#[stable(feature = "rust1", since = "1.0.0")]
#[must_use = "if you really need to exhaust the iterator, consider `.for_each(drop)` instead"]
@ -2184,8 +2164,7 @@ pub trait Iterator {
/// argument is a double reference. You can see this effect in the
/// examples below, with `&&x`.
///
/// [`Some(element)`]: ../../std/option/enum.Option.html#variant.Some
/// [`None`]: ../../std/option/enum.Option.html#variant.None
/// [`Some(element)`]: Some
///
/// # Examples
///
@ -2331,9 +2310,8 @@ pub trait Iterator {
/// This function might panic if the iterator has more than `usize::MAX`
/// non-matching elements.
///
/// [`Some(index)`]: ../../std/option/enum.Option.html#variant.Some
/// [`None`]: ../../std/option/enum.Option.html#variant.None
/// [`usize::MAX`]: ../../std/usize/constant.MAX.html
/// [`Some(index)`]: Some
/// [`usize::MAX`]: crate::usize::MAX
///
/// # Examples
///
@ -2394,8 +2372,7 @@ pub trait Iterator {
/// `rposition()` is short-circuiting; in other words, it will stop
/// processing as soon as it finds a `true`.
///
/// [`Some(index)`]: ../../std/option/enum.Option.html#variant.Some
/// [`None`]: ../../std/option/enum.Option.html#variant.None
/// [`Some(index)`]: Some
///
/// # Examples
///
@ -2449,8 +2426,6 @@ pub trait Iterator {
/// If several elements are equally maximum, the last element is
/// returned. If the iterator is empty, [`None`] is returned.
///
/// [`None`]: ../../std/option/enum.Option.html#variant.None
///
/// # Examples
///
/// Basic usage:
@ -2477,8 +2452,6 @@ pub trait Iterator {
/// If several elements are equally minimum, the first element is
/// returned. If the iterator is empty, [`None`] is returned.
///
/// [`None`]: ../../std/option/enum.Option.html#variant.None
///
/// # Examples
///
/// Basic usage:
@ -2506,8 +2479,6 @@ pub trait Iterator {
/// If several elements are equally maximum, the last element is
/// returned. If the iterator is empty, [`None`] is returned.
///
/// [`None`]: ../../std/option/enum.Option.html#variant.None
///
/// # Examples
///
/// ```
@ -2541,8 +2512,6 @@ pub trait Iterator {
/// If several elements are equally maximum, the last element is
/// returned. If the iterator is empty, [`None`] is returned.
///
/// [`None`]: ../../std/option/enum.Option.html#variant.None
///
/// # Examples
///
/// ```
@ -2570,8 +2539,6 @@ pub trait Iterator {
/// If several elements are equally minimum, the first element is
/// returned. If the iterator is empty, [`None`] is returned.
///
/// [`None`]: ../../std/option/enum.Option.html#variant.None
///
/// # Examples
///
/// ```
@ -2605,8 +2572,6 @@ pub trait Iterator {
/// If several elements are equally minimum, the first element is
/// returned. If the iterator is empty, [`None`] is returned.
///
/// [`None`]: ../../std/option/enum.Option.html#variant.None
///
/// # Examples
///
/// ```
@ -2747,7 +2712,7 @@ pub trait Iterator {
/// This is useful when you have an iterator over `&T`, but you need an
/// iterator over `T`.
///
/// [`clone`]: ../../std/clone/trait.Clone.html#tymethod.clone
/// [`clone`]: crate::clone::Clone::clone
///
/// # Examples
///
@ -2779,8 +2744,6 @@ pub trait Iterator {
/// from the beginning. After iterating again, it will start at the
/// beginning again. And again. And again. Forever.
///
/// [`None`]: ../../std/option/enum.Option.html#variant.None
///
/// # Examples
///
/// Basic usage:
@ -3233,7 +3196,7 @@ pub trait Iterator {
/// assert!(![0.0, 1.0, f32::NAN].iter().is_sorted_by(|a, b| a.partial_cmp(b)));
/// ```
///
/// [`is_sorted`]: trait.Iterator.html#method.is_sorted
/// [`is_sorted`]: #method.is_sorted
#[unstable(feature = "is_sorted", reason = "new API", issue = "53485")]
fn is_sorted_by<F>(mut self, mut compare: F) -> bool
where
@ -3262,7 +3225,7 @@ pub trait Iterator {
/// the elements, as determined by `f`. Apart from that, it's equivalent to [`is_sorted`]; see
/// its documentation for more information.
///
/// [`is_sorted`]: trait.Iterator.html#method.is_sorted
/// [`is_sorted`]: #method.is_sorted
///
/// # Examples
///

View file

@ -9,9 +9,8 @@
/// on the iterator. If the iterator is already fused, the additional [`Fuse`]
/// wrapper will be a no-op with no performance penalty.
///
/// [`None`]: ../../std/option/enum.Option.html#variant.None
/// [`Iterator::fuse`]: ../../std/iter/trait.Iterator.html#method.fuse
/// [`Fuse`]: ../../std/iter/struct.Fuse.html
/// [`Iterator::fuse`]: crate::iter::Iterator::fuse
/// [`Fuse`]: crate::iter::Fuse
#[stable(feature = "fused", since = "1.26.0")]
#[rustc_unsafe_specialization_marker]
pub trait FusedIterator: Iterator {}
@ -35,9 +34,8 @@ impl<I: FusedIterator + ?Sized> FusedIterator for &mut I {}
/// This trait must only be implemented when the contract is upheld.
/// Consumers of this trait must inspect [`.size_hint`]s upper bound.
///
/// [`None`]: ../../std/option/enum.Option.html#variant.None
/// [`usize::MAX`]: ../../std/usize/constant.MAX.html
/// [`.size_hint`]: ../../std/iter/trait.Iterator.html#method.size_hint
/// [`usize::MAX`]: crate::usize::MAX
/// [`.size_hint`]: crate::iter::Iterator::size_hint
#[unstable(feature = "trusted_len", issue = "37572")]
#[rustc_unsafe_specialization_marker]
pub unsafe trait TrustedLen: Iterator {}

View file

@ -83,6 +83,7 @@
#![feature(const_panic)]
#![feature(const_fn_union)]
#![feature(const_generics)]
#![feature(const_option)]
#![feature(const_ptr_offset)]
#![feature(const_ptr_offset_from)]
#![feature(const_raw_ptr_comparison)]
@ -150,6 +151,7 @@
#![feature(slice_ptr_get)]
#![feature(no_niche)] // rust-lang/rust#68303
#![feature(unsafe_block_in_unsafe_fn)]
#![deny(intra_doc_link_resolution_failure)]
#![deny(unsafe_op_in_unsafe_fn)]
#[prelude_import]

View file

@ -6,9 +6,12 @@ macro_rules! panic {
() => (
$crate::panic!("explicit panic")
);
($msg:expr) => (
($msg:literal) => (
$crate::panicking::panic($msg)
);
($msg:expr) => (
$crate::panic!("{}", $crate::convert::identity::<&str>($msg))
);
($msg:expr,) => (
$crate::panic!($msg)
);

View file

@ -179,8 +179,9 @@ impl<T> Option<T> {
/// [`Some`]: #variant.Some
#[must_use = "if you intended to assert that this has a value, consider `.unwrap()` instead"]
#[inline]
#[rustc_const_unstable(feature = "const_option", issue = "67441")]
#[stable(feature = "rust1", since = "1.0.0")]
pub fn is_some(&self) -> bool {
pub const fn is_some(&self) -> bool {
matches!(*self, Some(_))
}
@ -200,8 +201,9 @@ impl<T> Option<T> {
#[must_use = "if you intended to assert that this doesn't have a value, consider \
`.and_then(|| panic!(\"`Option` had a value when expected `None`\"))` instead"]
#[inline]
#[rustc_const_unstable(feature = "const_option", issue = "67441")]
#[stable(feature = "rust1", since = "1.0.0")]
pub fn is_none(&self) -> bool {
pub const fn is_none(&self) -> bool {
!self.is_some()
}
@ -259,8 +261,9 @@ impl<T> Option<T> {
/// println!("still can print text: {:?}", text);
/// ```
#[inline]
#[rustc_const_unstable(feature = "const_option", issue = "67441")]
#[stable(feature = "rust1", since = "1.0.0")]
pub fn as_ref(&self) -> Option<&T> {
pub const fn as_ref(&self) -> Option<&T> {
match *self {
Some(ref x) => Some(x),
None => None,
@ -580,8 +583,9 @@ impl<T> Option<T> {
/// assert_eq!(x.iter().next(), None);
/// ```
#[inline]
#[rustc_const_unstable(feature = "const_option", issue = "67441")]
#[stable(feature = "rust1", since = "1.0.0")]
pub fn iter(&self) -> Iter<'_, T> {
pub const fn iter(&self) -> Iter<'_, T> {
Iter { inner: Item { opt: self.as_ref() } }
}

View file

@ -36,7 +36,7 @@ use crate::panic::{Location, PanicInfo};
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never))]
#[track_caller]
#[lang = "panic"] // needed by codegen for panic on overflow and other `Assert` MIR terminators
pub fn panic(expr: &str) -> ! {
pub fn panic(expr: &'static str) -> ! {
if cfg!(feature = "panic_immediate_abort") {
super::intrinsics::abort()
}

View file

@ -28,7 +28,9 @@ use rustc_target::spec::{LinkOutputKind, LinkerFlavor, LldFlavor};
pub fn disable_localization(linker: &mut Command) {
// No harm in setting both env vars simultaneously.
// Unix-style linkers.
linker.env("LC_ALL", "C");
// We use an UTF-8 locale, as the generic C locale disables support for non-ASCII
// bytes in filenames on some platforms.
linker.env("LC_ALL", "en_US.UTF-8");
// MSVC's `link.exe`.
linker.env("VSLANG", "1033");
}

View file

@ -235,13 +235,8 @@ pub fn get_codegen_backend(sess: &Session) -> Box<dyn CodegenBackend> {
static mut LOAD: fn() -> Box<dyn CodegenBackend> = || unreachable!();
INIT.call_once(|| {
let codegen_name = sess
.opts
.debugging_opts
.codegen_backend
.as_ref()
.unwrap_or(&sess.target.target.options.codegen_backend);
let backend = match &codegen_name[..] {
let codegen_name = sess.opts.debugging_opts.codegen_backend.as_deref().unwrap_or("llvm");
let backend = match codegen_name {
filename if filename.contains('.') => load_backend_from_dylib(filename.as_ref()),
codegen_name => get_builtin_codegen_backend(codegen_name),
};

View file

@ -1922,6 +1922,14 @@ impl<'tcx> LateLintPass<'tcx> for InvalidValue {
None
}
/// Test if this enum has several actually "existing" variants.
/// Zero-sized uninhabited variants do not always have a tag assigned and thus do not "exist".
fn is_multi_variant(adt: &ty::AdtDef) -> bool {
// As an approximation, we only count dataless variants. Those are definitely inhabited.
let existing_variants = adt.variants.iter().filter(|v| v.fields.is_empty()).count();
existing_variants > 1
}
/// Return `Some` only if we are sure this type does *not*
/// allow zero initialization.
fn ty_find_init_error<'tcx>(
@ -1950,7 +1958,7 @@ impl<'tcx> LateLintPass<'tcx> for InvalidValue {
}
// Recurse and checks for some compound types.
Adt(adt_def, substs) if !adt_def.is_union() => {
// First check f this ADT has a layout attribute (like `NonNull` and friends).
// First check if this ADT has a layout attribute (like `NonNull` and friends).
use std::ops::Bound;
match tcx.layout_scalar_valid_range(adt_def.did) {
// We exploit here that `layout_scalar_valid_range` will never
@ -2001,10 +2009,20 @@ impl<'tcx> LateLintPass<'tcx> for InvalidValue {
)
})
}
// Multi-variant enums are tricky: if all but one variant are
// uninhabited, we might actually do layout like for a single-variant
// enum, and then even leaving them uninitialized could be okay.
_ => None, // Conservative fallback for multi-variant enum.
// Multi-variant enum.
_ => {
if init == InitKind::Uninit && is_multi_variant(adt_def) {
let span = tcx.def_span(adt_def.did);
Some((
"enums have to be initialized to a variant".to_string(),
Some(span),
))
} else {
// In principle, for zero-initialization we could figure out which variant corresponds
// to tag 0, and check that... but for now we just accept all zero-initializations.
None
}
}
}
}
Tuple(..) => {

View file

@ -4,6 +4,7 @@
pub mod exports;
pub mod map;
pub mod place;
use crate::ich::StableHashingContext;
use crate::ty::query::Providers;

View file

@ -0,0 +1,115 @@
use crate::ty;
use crate::ty::Ty;
use rustc_hir::HirId;
use rustc_target::abi::VariantIdx;
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, RustcEncodable, RustcDecodable, HashStable)]
pub enum PlaceBase {
/// A temporary variable
Rvalue,
/// A named `static` item
StaticItem,
/// A named local variable
Local(HirId),
/// An upvar referenced by closure env
Upvar(ty::UpvarId),
}
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, RustcEncodable, RustcDecodable, HashStable)]
pub enum ProjectionKind {
/// A dereference of a pointer, reference or `Box<T>` of the given type
Deref,
/// `B.F` where `B` is the base expression and `F` is
/// the field. The field is identified by which variant
/// it appears in along with a field index. The variant
/// is used for enums.
Field(u32, VariantIdx),
/// Some index like `B[x]`, where `B` is the base
/// expression. We don't preserve the index `x` because
/// we won't need it.
Index,
/// A subslice covering a range of values like `B[x..y]`.
Subslice,
}
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, RustcEncodable, RustcDecodable, HashStable)]
pub struct Projection<'tcx> {
/// Type after the projection is being applied.
pub ty: Ty<'tcx>,
/// Defines the type of access
pub kind: ProjectionKind,
}
/// A `Place` represents how a value is located in memory.
///
/// This is an HIR version of `mir::Place`
#[derive(Clone, Debug, PartialEq, Eq, Hash, RustcEncodable, RustcDecodable, HashStable)]
pub struct Place<'tcx> {
/// The type of the `PlaceBase`
pub base_ty: Ty<'tcx>,
/// The "outermost" place that holds this value.
pub base: PlaceBase,
/// How this place is derived from the base place.
pub projections: Vec<Projection<'tcx>>,
}
/// A `PlaceWithHirId` represents how a value is located in memory.
///
/// This is an HIR version of `mir::Place`
#[derive(Clone, Debug, PartialEq, Eq, Hash, RustcEncodable, RustcDecodable, HashStable)]
pub struct PlaceWithHirId<'tcx> {
/// `HirId` of the expression or pattern producing this value.
pub hir_id: HirId,
/// Information about the `Place`
pub place: Place<'tcx>,
}
impl<'tcx> PlaceWithHirId<'tcx> {
pub fn new(
hir_id: HirId,
base_ty: Ty<'tcx>,
base: PlaceBase,
projections: Vec<Projection<'tcx>>,
) -> PlaceWithHirId<'tcx> {
PlaceWithHirId {
hir_id: hir_id,
place: Place { base_ty: base_ty, base: base, projections: projections },
}
}
}
impl<'tcx> Place<'tcx> {
/// Returns an iterator of the types that have to be dereferenced to access
/// the `Place`.
///
/// The types are in the reverse order that they are applied. So if
/// `x: &*const u32` and the `Place` is `**x`, then the types returned are
///`*const u32` then `&*const u32`.
pub fn deref_tys(&self) -> impl Iterator<Item = Ty<'tcx>> + '_ {
self.projections.iter().enumerate().rev().filter_map(move |(index, proj)| {
if ProjectionKind::Deref == proj.kind {
Some(self.ty_before_projection(index))
} else {
None
}
})
}
/// Returns the type of this `Place` after all projections have been applied.
pub fn ty(&self) -> Ty<'tcx> {
self.projections.last().map_or_else(|| self.base_ty, |proj| proj.ty)
}
/// Returns the type of this `Place` immediately before `projection_index`th projection
/// is applied.
pub fn ty_before_projection(&self, projection_index: usize) -> Ty<'tcx> {
assert!(projection_index < self.projections.len());
if projection_index == 0 { self.base_ty } else { self.projections[projection_index - 1].ty }
}
}

View file

@ -292,3 +292,20 @@ impl<'a, 'tcx> Iterator for ReversePostorder<'a, 'tcx> {
}
impl<'a, 'tcx> ExactSizeIterator for ReversePostorder<'a, 'tcx> {}
/// Returns an iterator over all basic blocks reachable from the `START_BLOCK` in no particular
/// order.
///
/// This is clearer than writing `preorder` in cases where the order doesn't matter.
pub fn reachable<'a, 'tcx>(
body: &'a Body<'tcx>,
) -> impl 'a + Iterator<Item = (BasicBlock, &'a BasicBlockData<'tcx>)> {
preorder(body)
}
/// Returns a `BitSet` containing all basic blocks reachable from the `START_BLOCK`.
pub fn reachable_as_bitset(body: &Body<'tcx>) -> BitSet<BasicBlock> {
let mut iter = preorder(body);
(&mut iter).for_each(drop);
iter.visited
}

View file

@ -34,6 +34,9 @@ where
///
/// When this flag is set, we need to reset to an entry set before doing a seek.
state_needs_reset: bool,
#[cfg(debug_assertions)]
reachable_blocks: BitSet<BasicBlock>,
}
impl<'mir, 'tcx, A, R> ResultsCursor<'mir, 'tcx, A, R>
@ -55,6 +58,9 @@ where
state_needs_reset: true,
state: BitSet::new_empty(bits_per_block),
pos: CursorPosition::block_entry(mir::START_BLOCK),
#[cfg(debug_assertions)]
reachable_blocks: mir::traversal::reachable_as_bitset(body),
}
}
@ -85,6 +91,9 @@ where
///
/// For backward dataflow analyses, this is the dataflow state after the terminator.
pub(super) fn seek_to_block_entry(&mut self, block: BasicBlock) {
#[cfg(debug_assertions)]
assert!(self.reachable_blocks.contains(block));
self.state.overwrite(&self.results.borrow().entry_set_for_block(block));
self.pos = CursorPosition::block_entry(block);
self.state_needs_reset = false;

View file

@ -52,6 +52,15 @@ where
visit_results(body, blocks, self, vis)
}
pub fn visit_reachable_with(
&self,
body: &'mir mir::Body<'tcx>,
vis: &mut impl ResultsVisitor<'mir, 'tcx, FlowState = BitSet<A::Idx>>,
) {
let blocks = mir::traversal::reachable(body);
visit_results(body, blocks.map(|(bb, _)| bb), self, vis)
}
pub fn visit_in_rpo_with(
&self,
body: &'mir mir::Body<'tcx>,
@ -204,15 +213,6 @@ where
}
}
// Add blocks that are not reachable from START_BLOCK to the work queue. These blocks will
// be processed after the ones added above.
//
// FIXME(ecstaticmorse): Is this actually necessary? In principle, we shouldn't need to
// know the dataflow state in unreachable basic blocks.
for bb in body.basic_blocks().indices() {
dirty_queue.insert(bb);
}
let mut state = BitSet::new_empty(bits_per_block);
while let Some(bb) = dirty_queue.pop() {
let bb_data = &body[bb];

View file

@ -16,7 +16,13 @@ pub fn visit_results<F, V>(
{
let mut state = results.new_flow_state(body);
#[cfg(debug_assertions)]
let reachable_blocks = mir::traversal::reachable_as_bitset(body);
for block in blocks {
#[cfg(debug_assertions)]
assert!(reachable_blocks.contains(block));
let block_data = &body[block];
V::Direction::visit_results_in_block(&mut state, block, block_data, results, vis);
}

View file

@ -624,9 +624,7 @@ fn compute_storage_conflicts(
local_conflicts: BitMatrix::from_row_n(&ineligible_locals, body.local_decls.len()),
};
// Visit only reachable basic blocks. The exact order is not important.
let reachable_blocks = traversal::preorder(body).map(|(bb, _)| bb);
requires_storage.visit_with(body, reachable_blocks, &mut visitor);
requires_storage.visit_reachable_with(body, &mut visitor);
let local_conflicts = visitor.local_conflicts;

View file

@ -188,10 +188,9 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
let ptr_ty = ptr.ty;
// Create an *internal* temp for the pointer, so that unsafety
// checking won't complain about the raw pointer assignment.
let ptr_temp = this.local_decls.push(LocalDecl::with_source_info(
ptr_ty,
source_info,
).internal());
let ptr_temp = this
.local_decls
.push(LocalDecl::with_source_info(ptr_ty, source_info).internal());
let ptr_temp = Place::from(ptr_temp);
let block = unpack!(this.into(ptr_temp, block, ptr));
this.into(this.hir.tcx().mk_place_deref(ptr_temp), block, val)
@ -224,7 +223,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
Some((destination, success))
},
from_hir_call,
fn_span
fn_span,
},
);
success.unit()
@ -387,15 +386,18 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
// These cases don't actually need a destination
ExprKind::Assign { .. }
| ExprKind::AssignOp { .. }
| ExprKind::Continue { .. }
| ExprKind::Break { .. }
| ExprKind::LlvmInlineAsm { .. }
| ExprKind::Return { .. } => {
| ExprKind::LlvmInlineAsm { .. } => {
unpack!(block = this.stmt_expr(block, expr, None));
this.cfg.push_assign_unit(block, source_info, destination, this.hir.tcx());
block.unit()
}
ExprKind::Continue { .. } | ExprKind::Break { .. } | ExprKind::Return { .. } => {
unpack!(block = this.stmt_expr(block, expr, None));
// No assign, as these have type `!`.
block.unit()
}
// Avoid creating a temporary
ExprKind::VarRef { .. }
| ExprKind::SelfRef

View file

@ -938,9 +938,6 @@ pub struct TargetOptions {
/// for this target unconditionally.
pub no_builtins: bool,
/// The codegen backend to use for this target, typically "llvm"
pub codegen_backend: String,
/// The default visibility for symbols in this target should be "hidden"
/// rather than "default"
pub default_hidden_visibility: bool,
@ -1068,7 +1065,6 @@ impl Default for TargetOptions {
requires_lto: false,
singlethread: false,
no_builtins: false,
codegen_backend: "llvm".to_string(),
default_hidden_visibility: false,
emit_debug_gdb_scripts: true,
requires_uwtable: false,
@ -1461,7 +1457,6 @@ impl Target {
key!(requires_lto, bool);
key!(singlethread, bool);
key!(no_builtins, bool);
key!(codegen_backend);
key!(default_hidden_visibility, bool);
key!(emit_debug_gdb_scripts, bool);
key!(requires_uwtable, bool);
@ -1699,7 +1694,6 @@ impl ToJson for Target {
target_option_val!(requires_lto);
target_option_val!(singlethread);
target_option_val!(no_builtins);
target_option_val!(codegen_backend);
target_option_val!(default_hidden_visibility);
target_option_val!(emit_debug_gdb_scripts);
target_option_val!(requires_uwtable);

View file

@ -82,6 +82,7 @@ use rustc_hir::intravisit::{self, NestedVisitorMap, Visitor};
use rustc_hir::PatKind;
use rustc_infer::infer::outlives::env::OutlivesEnvironment;
use rustc_infer::infer::{self, RegionObligation, RegionckMode};
use rustc_middle::hir::place::{PlaceBase, PlaceWithHirId};
use rustc_middle::ty::adjustment;
use rustc_middle::ty::{self, Ty};
use rustc_span::Span;
@ -442,7 +443,7 @@ impl<'a, 'tcx> RegionCtxt<'a, 'tcx> {
fn constrain_adjustments(
&mut self,
expr: &hir::Expr<'_>,
) -> mc::McResult<mc::PlaceWithHirId<'tcx>> {
) -> mc::McResult<PlaceWithHirId<'tcx>> {
debug!("constrain_adjustments(expr={:?})", expr);
let mut place = self.with_mc(|mc| mc.cat_expr_unadjusted(expr))?;
@ -483,10 +484,10 @@ impl<'a, 'tcx> RegionCtxt<'a, 'tcx> {
fn check_safety_of_rvalue_destructor_if_necessary(
&mut self,
place_with_id: &mc::PlaceWithHirId<'tcx>,
place_with_id: &PlaceWithHirId<'tcx>,
span: Span,
) {
if let mc::PlaceBase::Rvalue = place_with_id.place.base {
if let PlaceBase::Rvalue = place_with_id.place.base {
if place_with_id.place.projections.is_empty() {
let typ = self.resolve_type(place_with_id.place.ty());
let body_id = self.body_id;
@ -573,7 +574,7 @@ impl<'a, 'tcx> RegionCtxt<'a, 'tcx> {
/// Link lifetimes of any ref bindings in `root_pat` to the pointers found
/// in the discriminant, if needed.
fn link_pattern(&self, discr_cmt: mc::PlaceWithHirId<'tcx>, root_pat: &hir::Pat<'_>) {
fn link_pattern(&self, discr_cmt: PlaceWithHirId<'tcx>, root_pat: &hir::Pat<'_>) {
debug!("link_pattern(discr_cmt={:?}, root_pat={:?})", discr_cmt, root_pat);
ignore_err!(self.with_mc(|mc| {
mc.cat_pattern(discr_cmt, root_pat, |sub_cmt, hir::Pat { kind, span, hir_id }| {
@ -594,7 +595,7 @@ impl<'a, 'tcx> RegionCtxt<'a, 'tcx> {
fn link_autoref(
&self,
expr: &hir::Expr<'_>,
expr_cmt: &mc::PlaceWithHirId<'tcx>,
expr_cmt: &PlaceWithHirId<'tcx>,
autoref: &adjustment::AutoBorrow<'tcx>,
) {
debug!("link_autoref(autoref={:?}, expr_cmt={:?})", autoref, expr_cmt);
@ -615,7 +616,7 @@ impl<'a, 'tcx> RegionCtxt<'a, 'tcx> {
span: Span,
id: hir::HirId,
mutbl: hir::Mutability,
cmt_borrowed: &mc::PlaceWithHirId<'tcx>,
cmt_borrowed: &PlaceWithHirId<'tcx>,
) {
debug!(
"link_region_from_node_type(id={:?}, mutbl={:?}, cmt_borrowed={:?})",
@ -638,7 +639,7 @@ impl<'a, 'tcx> RegionCtxt<'a, 'tcx> {
span: Span,
borrow_region: ty::Region<'tcx>,
borrow_kind: ty::BorrowKind,
borrow_place: &mc::PlaceWithHirId<'tcx>,
borrow_place: &PlaceWithHirId<'tcx>,
) {
let origin = infer::DataBorrowed(borrow_place.place.ty(), span);
self.type_must_outlive(origin, borrow_place.place.ty(), borrow_region);
@ -659,7 +660,7 @@ impl<'a, 'tcx> RegionCtxt<'a, 'tcx> {
_ => assert!(pointer_ty.is_box(), "unexpected built-in deref type {}", pointer_ty),
}
}
if let mc::PlaceBase::Upvar(upvar_id) = borrow_place.place.base {
if let PlaceBase::Upvar(upvar_id) = borrow_place.place.base {
self.link_upvar_region(span, borrow_region, upvar_id);
}
}

View file

@ -33,14 +33,13 @@
use super::FnCtxt;
use crate::expr_use_visitor as euv;
use crate::mem_categorization as mc;
use crate::mem_categorization::PlaceBase;
use rustc_data_structures::fx::FxIndexMap;
use rustc_hir as hir;
use rustc_hir::def_id::DefId;
use rustc_hir::def_id::LocalDefId;
use rustc_hir::intravisit::{self, NestedVisitorMap, Visitor};
use rustc_infer::infer::UpvarRegion;
use rustc_middle::hir::place::{PlaceBase, PlaceWithHirId};
use rustc_middle::ty::{self, Ty, TyCtxt, UpvarSubsts};
use rustc_span::{Span, Symbol};
@ -276,7 +275,7 @@ struct InferBorrowKind<'a, 'tcx> {
impl<'a, 'tcx> InferBorrowKind<'a, 'tcx> {
fn adjust_upvar_borrow_kind_for_consume(
&mut self,
place_with_id: &mc::PlaceWithHirId<'tcx>,
place_with_id: &PlaceWithHirId<'tcx>,
mode: euv::ConsumeMode,
) {
debug!(
@ -315,7 +314,7 @@ impl<'a, 'tcx> InferBorrowKind<'a, 'tcx> {
/// Indicates that `place_with_id` is being directly mutated (e.g., assigned
/// to). If the place is based on a by-ref upvar, this implies that
/// the upvar must be borrowed using an `&mut` borrow.
fn adjust_upvar_borrow_kind_for_mut(&mut self, place_with_id: &mc::PlaceWithHirId<'tcx>) {
fn adjust_upvar_borrow_kind_for_mut(&mut self, place_with_id: &PlaceWithHirId<'tcx>) {
debug!("adjust_upvar_borrow_kind_for_mut(place_with_id={:?})", place_with_id);
if let PlaceBase::Upvar(upvar_id) = place_with_id.place.base {
@ -340,7 +339,7 @@ impl<'a, 'tcx> InferBorrowKind<'a, 'tcx> {
}
}
fn adjust_upvar_borrow_kind_for_unique(&mut self, place_with_id: &mc::PlaceWithHirId<'tcx>) {
fn adjust_upvar_borrow_kind_for_unique(&mut self, place_with_id: &PlaceWithHirId<'tcx>) {
debug!("adjust_upvar_borrow_kind_for_unique(place_with_id={:?})", place_with_id);
if let PlaceBase::Upvar(upvar_id) = place_with_id.place.base {
@ -470,12 +469,12 @@ impl<'a, 'tcx> InferBorrowKind<'a, 'tcx> {
}
impl<'a, 'tcx> euv::Delegate<'tcx> for InferBorrowKind<'a, 'tcx> {
fn consume(&mut self, place_with_id: &mc::PlaceWithHirId<'tcx>, mode: euv::ConsumeMode) {
fn consume(&mut self, place_with_id: &PlaceWithHirId<'tcx>, mode: euv::ConsumeMode) {
debug!("consume(place_with_id={:?},mode={:?})", place_with_id, mode);
self.adjust_upvar_borrow_kind_for_consume(place_with_id, mode);
}
fn borrow(&mut self, place_with_id: &mc::PlaceWithHirId<'tcx>, bk: ty::BorrowKind) {
fn borrow(&mut self, place_with_id: &PlaceWithHirId<'tcx>, bk: ty::BorrowKind) {
debug!("borrow(place_with_id={:?}, bk={:?})", place_with_id, bk);
match bk {
@ -489,7 +488,7 @@ impl<'a, 'tcx> euv::Delegate<'tcx> for InferBorrowKind<'a, 'tcx> {
}
}
fn mutate(&mut self, assignee_place: &mc::PlaceWithHirId<'tcx>) {
fn mutate(&mut self, assignee_place: &PlaceWithHirId<'tcx>) {
debug!("mutate(assignee_place={:?})", assignee_place);
self.adjust_upvar_borrow_kind_for_mut(assignee_place);

View file

@ -5,7 +5,7 @@
pub use self::ConsumeMode::*;
// Export these here so that Clippy can use them.
pub use mc::{PlaceBase, PlaceWithHirId, Projection};
pub use rustc_middle::hir::place::{PlaceBase, PlaceWithHirId, Projection};
use rustc_hir as hir;
use rustc_hir::def::Res;
@ -13,6 +13,7 @@ use rustc_hir::def_id::LocalDefId;
use rustc_hir::PatKind;
use rustc_index::vec::Idx;
use rustc_infer::infer::InferCtxt;
use rustc_middle::hir::place::ProjectionKind;
use rustc_middle::ty::{self, adjustment, TyCtxt};
use rustc_target::abi::VariantIdx;
@ -27,13 +28,13 @@ use rustc_span::Span;
pub trait Delegate<'tcx> {
// The value found at `place` is either copied or moved, depending
// on mode.
fn consume(&mut self, place_with_id: &mc::PlaceWithHirId<'tcx>, mode: ConsumeMode);
fn consume(&mut self, place_with_id: &PlaceWithHirId<'tcx>, mode: ConsumeMode);
// The value found at `place` is being borrowed with kind `bk`.
fn borrow(&mut self, place_with_id: &mc::PlaceWithHirId<'tcx>, bk: ty::BorrowKind);
fn borrow(&mut self, place_with_id: &PlaceWithHirId<'tcx>, bk: ty::BorrowKind);
// The path at `place_with_id` is being assigned to.
fn mutate(&mut self, assignee_place: &mc::PlaceWithHirId<'tcx>);
fn mutate(&mut self, assignee_place: &PlaceWithHirId<'tcx>);
}
#[derive(Copy, Clone, PartialEq, Debug)]
@ -398,7 +399,7 @@ impl<'a, 'tcx> ExprUseVisitor<'a, 'tcx> {
&*with_expr,
with_place.clone(),
with_field.ty(self.tcx(), substs),
mc::ProjectionKind::Field(f_index as u32, VariantIdx::new(0)),
ProjectionKind::Field(f_index as u32, VariantIdx::new(0)),
);
self.delegate_consume(&field_place);
}
@ -462,7 +463,7 @@ impl<'a, 'tcx> ExprUseVisitor<'a, 'tcx> {
fn walk_autoref(
&mut self,
expr: &hir::Expr<'_>,
base_place: &mc::PlaceWithHirId<'tcx>,
base_place: &PlaceWithHirId<'tcx>,
autoref: &adjustment::AutoBorrow<'tcx>,
) {
debug!(
@ -575,7 +576,7 @@ impl<'a, 'tcx> ExprUseVisitor<'a, 'tcx> {
closure_hir_id: hir::HirId,
closure_span: Span,
var_id: hir::HirId,
) -> mc::McResult<mc::PlaceWithHirId<'tcx>> {
) -> mc::McResult<PlaceWithHirId<'tcx>> {
// Create the place for the variable being borrowed, from the
// perspective of the creator (parent) of the closure.
let var_ty = self.mc.node_ty(var_id)?;

View file

@ -48,6 +48,7 @@
//! result of `*x'`, effectively, where `x'` is a `Categorization::Upvar` reference
//! tied to `x`. The type of `x'` will be a borrowed pointer.
use rustc_middle::hir::place::*;
use rustc_middle::ty::adjustment;
use rustc_middle::ty::fold::TypeFoldable;
use rustc_middle::ty::{self, Ty, TyCtxt};
@ -64,116 +65,6 @@ use rustc_span::Span;
use rustc_target::abi::VariantIdx;
use rustc_trait_selection::infer::InferCtxtExt;
#[derive(Clone, Debug)]
pub enum PlaceBase {
/// A temporary variable
Rvalue,
/// A named `static` item
StaticItem,
/// A named local variable
Local(hir::HirId),
/// An upvar referenced by closure env
Upvar(ty::UpvarId),
}
#[derive(Clone, Debug, Eq, PartialEq)]
pub enum ProjectionKind {
/// A dereference of a pointer, reference or `Box<T>` of the given type
Deref,
/// `B.F` where `B` is the base expression and `F` is
/// the field. The field is identified by which variant
/// it appears in along with a field index. The variant
/// is used for enums.
Field(u32, VariantIdx),
/// Some index like `B[x]`, where `B` is the base
/// expression. We don't preserve the index `x` because
/// we won't need it.
Index,
/// A subslice covering a range of values like `B[x..y]`.
Subslice,
}
#[derive(Clone, Debug)]
pub struct Projection<'tcx> {
// Type after the projection is being applied.
ty: Ty<'tcx>,
/// Defines the type of access
kind: ProjectionKind,
}
/// A `Place` represents how a value is located in memory.
///
/// This is an HIR version of `mir::Place`
#[derive(Clone, Debug)]
pub struct Place<'tcx> {
/// The type of the `PlaceBase`
pub base_ty: Ty<'tcx>,
/// The "outermost" place that holds this value.
pub base: PlaceBase,
/// How this place is derived from the base place.
pub projections: Vec<Projection<'tcx>>,
}
/// A `PlaceWithHirId` represents how a value is located in memory.
///
/// This is an HIR version of `mir::Place`
#[derive(Clone, Debug)]
pub struct PlaceWithHirId<'tcx> {
/// `HirId` of the expression or pattern producing this value.
pub hir_id: hir::HirId,
/// Information about the `Place`
pub place: Place<'tcx>,
}
impl<'tcx> PlaceWithHirId<'tcx> {
crate fn new(
hir_id: hir::HirId,
base_ty: Ty<'tcx>,
base: PlaceBase,
projections: Vec<Projection<'tcx>>,
) -> PlaceWithHirId<'tcx> {
PlaceWithHirId {
hir_id: hir_id,
place: Place { base_ty: base_ty, base: base, projections: projections },
}
}
}
impl<'tcx> Place<'tcx> {
/// Returns an iterator of the types that have to be dereferenced to access
/// the `Place`.
///
/// The types are in the reverse order that they are applied. So if
/// `x: &*const u32` and the `Place` is `**x`, then the types returned are
///`*const u32` then `&*const u32`.
crate fn deref_tys(&self) -> impl Iterator<Item = Ty<'tcx>> + '_ {
self.projections.iter().enumerate().rev().filter_map(move |(index, proj)| {
if ProjectionKind::Deref == proj.kind {
Some(self.ty_before_projection(index))
} else {
None
}
})
}
// Returns the type of this `Place` after all projections have been applied.
pub fn ty(&self) -> Ty<'tcx> {
self.projections.last().map_or_else(|| self.base_ty, |proj| proj.ty)
}
// Returns the type of this `Place` immediately before `projection_index`th projection
// is applied.
crate fn ty_before_projection(&self, projection_index: usize) -> Ty<'tcx> {
assert!(projection_index < self.projections.len());
if projection_index == 0 { self.base_ty } else { self.projections[projection_index - 1].ty }
}
}
crate trait HirNode {
fn hir_id(&self) -> hir::HirId;
fn span(&self) -> Span;

View file

@ -320,7 +320,7 @@ pub fn run_core(options: RustdocOptions) -> (clean::Crate, RenderInfo, RenderOpt
let missing_doc_example = rustc_lint::builtin::MISSING_DOC_CODE_EXAMPLES.name;
let private_doc_tests = rustc_lint::builtin::PRIVATE_DOC_TESTS.name;
let no_crate_level_docs = rustc_lint::builtin::MISSING_CRATE_LEVEL_DOCS.name;
let invalid_codeblock_attribute_name = rustc_lint::builtin::INVALID_CODEBLOCK_ATTRIBUTES.name;
let invalid_codeblock_attributes_name = rustc_lint::builtin::INVALID_CODEBLOCK_ATTRIBUTES.name;
// In addition to those specific lints, we also need to allow those given through
// command line, otherwise they'll get ignored and we don't want that.
@ -330,12 +330,12 @@ pub fn run_core(options: RustdocOptions) -> (clean::Crate, RenderInfo, RenderOpt
missing_doc_example.to_owned(),
private_doc_tests.to_owned(),
no_crate_level_docs.to_owned(),
invalid_codeblock_attribute_name.to_owned(),
invalid_codeblock_attributes_name.to_owned(),
];
let (lint_opts, lint_caps) = init_lints(allowed_lints, lint_opts, |lint| {
if lint.name == intra_link_resolution_failure_name
|| lint.name == invalid_codeblock_attribute_name
|| lint.name == invalid_codeblock_attributes_name
{
None
} else {

View file

@ -1 +1,2 @@
/* ignore-tidy-linelength */
/*! normalize.css v3.0.0 | MIT License | git.io/normalize */html{font-family:sans-serif;-ms-text-size-adjust:100%;-webkit-text-size-adjust:100%}body{margin:0}article,aside,details,figcaption,figure,footer,header,hgroup,main,nav,section,summary{display:block}audio,canvas,progress,video{display:inline-block;vertical-align:baseline}audio:not([controls]){display:none;height:0}[hidden],template{display:none}a{background:transparent}a:active,a:hover{outline:0}abbr[title]{border-bottom:1px dotted}b,strong{font-weight:bold}dfn{font-style:italic}h1{font-size:2em;margin:.67em 0}mark{background:#ff0;color:#000}small{font-size:80%}sub,sup{font-size:75%;line-height:0;position:relative;vertical-align:baseline}sup{top:-0.5em}sub{bottom:-0.25em}img{border:0}svg:not(:root){overflow:hidden}figure{margin:1em 40px}hr{-moz-box-sizing:content-box;box-sizing:content-box;height:0}pre{overflow:auto}code,kbd,pre,samp{font-family:monospace,monospace;font-size:1em}button,input,optgroup,select,textarea{color:inherit;font:inherit;margin:0}button{overflow:visible}button,select{text-transform:none}button,html input[type="button"],input[type="reset"],input[type="submit"]{-webkit-appearance:button;cursor:pointer}button[disabled],html input[disabled]{cursor:default}button::-moz-focus-inner,input::-moz-focus-inner{border:0;padding:0}input{line-height:normal}input[type="checkbox"],input[type="radio"]{box-sizing:border-box;padding:0}input[type="number"]::-webkit-inner-spin-button,input[type="number"]::-webkit-outer-spin-button{height:auto}input[type="search"]{-webkit-appearance:textfield;-moz-box-sizing:content-box;-webkit-box-sizing:content-box;box-sizing:content-box}input[type="search"]::-webkit-search-cancel-button,input[type="search"]::-webkit-search-decoration{-webkit-appearance:none}fieldset{border:1px solid silver;margin:0 2px;padding:.35em .625em .75em}legend{border:0;padding:0}textarea{overflow:auto}optgroup{font-weight:bold}table{border-collapse:collapse;border-spacing:0}td,th{padding:0}

View file

@ -49,9 +49,9 @@
}
* {
-webkit-box-sizing: border-box;
-moz-box-sizing: border-box;
box-sizing: border-box;
-webkit-box-sizing: border-box;
-moz-box-sizing: border-box;
box-sizing: border-box;
}
/* This part handles the "default" theme being used depending on the system one. */
@ -91,7 +91,8 @@ h2 {
h3 {
font-size: 1.3em;
}
h1, h2, h3:not(.impl):not(.method):not(.type):not(.tymethod):not(.important), h4:not(.method):not(.type):not(.tymethod):not(.associatedconstant) {
h1, h2, h3:not(.impl):not(.method):not(.type):not(.tymethod):not(.important),
h4:not(.method):not(.type):not(.tymethod):not(.associatedconstant) {
font-weight: 500;
margin: 20px 0 15px 0;
padding-bottom: 6px;
@ -103,7 +104,8 @@ h1.fqn {
h1.fqn > .in-band > a:hover {
text-decoration: underline;
}
h2, h3:not(.impl):not(.method):not(.type):not(.tymethod), h4:not(.method):not(.type):not(.tymethod):not(.associatedconstant) {
h2, h3:not(.impl):not(.method):not(.type):not(.tymethod),
h4:not(.method):not(.type):not(.tymethod):not(.associatedconstant) {
border-bottom: 1px solid;
}
h3.impl, h3.method, h4.method, h3.type, h4.type, h4.associatedconstant {
@ -1123,7 +1125,7 @@ h3 > .collapse-toggle, h4 > .collapse-toggle {
/* The margin on the tooltip does not capture hover events,
this extends the area of hover enough so that mouse hover is not
lost when moving the mouse to the tooltip */
content: "\00a0\00a0\00a0";
content: "\00a0\00a0\00a0";
}
.important-traits .important, .important-traits .docblock {
@ -1131,13 +1133,12 @@ h3 > .collapse-toggle, h4 > .collapse-toggle {
}
.important-traits .docblock code.content{
margin: 0;
padding: 0;
font-size: 20px;
margin: 0;
padding: 0;
font-size: 20px;
}
/* Example code has the "Run" button that
needs to be positioned relative to the pre */
/* Example code has the "Run" button that needs to be positioned relative to the pre */
pre.rust.rust-example-rendered {
position: relative;
}

View file

@ -10,7 +10,8 @@ body {
color: #c5c5c5;
}
h1, h2, h3:not(.impl):not(.method):not(.type):not(.tymethod), h4:not(.method):not(.type):not(.tymethod) {
h1, h2, h3:not(.impl):not(.method):not(.type):not(.tymethod),
h4:not(.method):not(.type):not(.tymethod) {
color: white;
}
h1.fqn {
@ -41,13 +42,13 @@ h3 > code, h4 > code, h5 > code {
color: #e6e1cf;
}
pre > code {
color: #e6e1cf;
color: #e6e1cf;
}
span code {
color: #e6e1cf;
color: #e6e1cf;
}
.docblock a > code {
color: #39AFD7 !important;
color: #39AFD7 !important;
}
.docblock code, .docblock-short code {
background-color: #191f26;
@ -100,11 +101,11 @@ pre {
}
.sidebar-elems .location {
color: #ff7733;
color: #ff7733;
}
.sidebar-elems .location a {
color: #fff;
color: #fff;
}
.sidebar .version {
@ -123,9 +124,9 @@ pre {
.line-numbers span { color: #5c6773ab; }
.line-numbers .line-highlighted {
background-color: rgba(255, 236, 164, 0.06) !important;
padding-right: 4px;
border-right: 1px solid #ffb44c;
background-color: rgba(255, 236, 164, 0.06) !important;
padding-right: 4px;
border-right: 1px solid #ffb44c;
}
.docblock h1, .docblock h2, .docblock h3, .docblock h4, .docblock h5 {
@ -168,31 +169,31 @@ pre {
.content span.keyword, .content a.keyword { color: #de5249; }
.content span.externcrate, .content span.mod, .content a.mod {
color: #acccf9;
color: #acccf9;
}
.content span.struct, .content a.struct {
color: #ffa0a5;
color: #ffa0a5;
}
.content span.enum, .content a.enum {
color: #99e0c9;
color: #99e0c9;
}
.content span.trait, .content a.trait {
color: #39AFD7;
color: #39AFD7;
}
.content span.type, .content a.type {
color: #cfbcf5;
color: #cfbcf5;
}
.content span.fn, .content a.fn, .content span.method,
.content a.method, .content span.tymethod,
.content a.tymethod, .content .fnname {
color: #fdd687;
color: #fdd687;
}
.content span.attr, .content a.attr, .content span.derive,
.content a.derive, .content span.macro, .content a.macro {
color: #a37acc;
color: #a37acc;
}
pre.rust .comment, pre.rust .doccomment {
pre.rust .comment, pre.rust .doccomment {
color: #788797;
font-style: italic;
}
@ -228,14 +229,24 @@ a {
}
.search-input {
color: #ffffff;
background-color: #141920;
box-shadow: 0 0 0 1px #424c57,0 0 0 2px transparent;
transition: box-shadow 150ms ease-in-out;
color: #ffffff;
background-color: #141920;
box-shadow: 0 0 0 1px #424c57,0 0 0 2px transparent;
transition: box-shadow 150ms ease-in-out;
}
#crate-search+.search-input:focus {
box-shadow: 0 0 0 1px #148099,0 0 0 2px transparent;
box-shadow: 0 0 0 1px #148099,0 0 0 2px transparent;
color: #ffffff;
background-color: #141920;
box-shadow: none;
transition: box-shadow 150ms ease-in-out;
border-radius: 4px;
margin-left: 8px;
}
#crate-search+.search-input:focus {
box-shadow: 0px 6px 20px 0px black;
}
.search-focus:disabled {
@ -249,7 +260,7 @@ a {
.stab.unstable,
.stab.deprecated,
.stab.portability {
color: #c5c5c5;
color: #c5c5c5;
background: #314559 !important;
border-style: none !important;
border-radius: 4px;
@ -262,10 +273,10 @@ a {
}
#help > div {
background: #14191f;
box-shadow: 0px 6px 20px 0px black;
border: none;
border-radius: 4px;
background: #14191f;
box-shadow: 0px 6px 20px 0px black;
border: none;
border-radius: 4px;
}
.since {
@ -288,14 +299,14 @@ pre.rust .question-mark {
color: #ff9011;
}
pre.rust .self {
color: #36a3d9;
font-style: italic;
color: #36a3d9;
font-style: italic;
}
pre.rust .attribute {
color: #e6e1cf;
color: #e6e1cf;
}
pre.rust .attribute .ident, pre.rust .attribute .op {
color: #e6e1cf;
color: #e6e1cf;
}
.example-wrap > pre.line-number {
@ -304,15 +315,15 @@ pre.rust .attribute .ident, pre.rust .attribute .op {
}
a.test-arrow {
font-size: 100%;
color: #788797;
border-radius: 4px;
background-color: rgba(255, 255, 255, 0);
font-size: 100%;
color: #788797;
border-radius: 4px;
background-color: rgba(255, 255, 255, 0);
}
a.test-arrow:hover {
background-color: rgba(242, 151, 24, 0.05);
color: #ffb44c;
background-color: rgba(242, 151, 24, 0.05);
color: #ffb44c;
}
.toggle-label {
@ -377,9 +388,9 @@ pre.ignore:hover, .information:hover + pre.ignore {
}
.tooltip .tooltiptext {
background-color: #314559;
color: #c5c5c5;
border: 1px solid #5c6773;
background-color: #314559;
color: #c5c5c5;
border: 1px solid #5c6773;
}
.tooltip .tooltiptext::after {
@ -387,12 +398,12 @@ pre.ignore:hover, .information:hover + pre.ignore {
}
.important-traits-tooltiptext {
background-color: #314559;
border-color: #5c6773;
background-color: #314559;
border-color: #5c6773;
}
#titles > div.selected {
background-color: #141920 !important;
background-color: #141920 !important;
border-bottom: 1px solid #ffb44c !important;
border-top: none;
}
@ -403,7 +414,7 @@ pre.ignore:hover, .information:hover + pre.ignore {
}
#titles > div:hover {
border-bottom: 1px solid rgba(242, 151, 24, 0.3);
border-bottom: 1px solid rgba(242, 151, 24, 0.3);
}
#titles > div > div.count {
@ -413,12 +424,13 @@ pre.ignore:hover, .information:hover + pre.ignore {
/* rules that this theme does not need to set, here to satisfy the rule checker */
/* note that a lot of these are partially set in some way (meaning they are set
individually rather than as a group) */
/* TODO: these rules should be at the bottom of the file but currently must be
/* FIXME: these rules should be at the bottom of the file but currently must be
above the `@media (max-width: 700px)` rules due to a bug in the css checker */
/* see https://github.com/rust-lang/rust/pull/71237#issuecomment-618170143 */
.content .highlighted.mod, .content .highlighted.externcrate {}
.search-input:focus {}
.content span.attr,.content a.attr,.block a.current.attr,.content span.derive,.content a.derive,.block a.current.derive,.content span.macro,.content a.macro,.block a.current.macro {}
.content span.attr,.content a.attr,.block a.current.attr,.content span.derive,.content a.derive,
.block a.current.derive,.content span.macro,.content a.macro,.block a.current.macro {}
.content .highlighted.trait {}
.content span.struct,.content a.struct,.block a.current.struct {}
#titles>div:hover,#titles>div.selected {}
@ -433,16 +445,20 @@ pre.rust .lifetime {}
.content .highlighted.fn,.content .highlighted.method,.content .highlighted.tymethod {}
h2,h3:not(.impl):not(.method):not(.type):not(.tymethod),h4:not(.method):not(.type):not(.tymethod) {}
.content span.enum,.content a.enum,.block a.current.enum {}
.content span.constant,.content a.constant,.block a.current.constant,.content span.static,.content a.static,.block a.current.static {}
.content span.constant,.content a.constant,.block a.current.constant,.content span.static,
.content a.static,.block a.current.static {}
.content span.keyword,.content a.keyword,.block a.current.keyword {}
pre.rust .comment {}
.content .highlighted.enum {}
.content .highlighted.struct {}
.content .highlighted.keyword {}
.content span.traitalias,.content a.traitalias,.block a.current.traitalias {}
.content span.fn,.content a.fn,.block a.current.fn,.content span.method,.content a.method,.block a.current.method,.content span.tymethod,.content a.tymethod,.block a.current.tymethod,.content .fnname {}
.content span.fn,.content a.fn,.block a.current.fn,.content span.method,.content a.method,
.block a.current.method,.content span.tymethod,.content a.tymethod,.block a.current.tymethod,
.content .fnname {}
pre.rust .kw {}
pre.rust .self,pre.rust .bool-val,pre.rust .prelude-val,pre.rust .attribute,pre.rust .attribute .ident {}
pre.rust .self,pre.rust .bool-val,pre.rust .prelude-val,pre.rust .attribute,
pre.rust .attribute .ident {}
.content span.foreigntype,.content a.foreigntype,.block a.current.foreigntype {}
pre.rust .doccomment {}
.stab.deprecated {}
@ -483,11 +499,11 @@ kbd {
#theme-picker, #settings-menu {
border-color: #5c6773;
background-color: #0f1419;
background-color: #0f1419;
}
#theme-picker > img, #settings-menu > img {
filter: invert(100);
filter: invert(100);
}
#theme-picker:hover, #theme-picker:focus,

View file

@ -3,13 +3,15 @@ body {
color: #ddd;
}
h1, h2, h3:not(.impl):not(.method):not(.type):not(.tymethod), h4:not(.method):not(.type):not(.tymethod) {
h1, h2, h3:not(.impl):not(.method):not(.type):not(.tymethod),
h4:not(.method):not(.type):not(.tymethod) {
color: #ddd;
}
h1.fqn {
border-bottom-color: #d2d2d2;
}
h2, h3:not(.impl):not(.method):not(.type):not(.tymethod), h4:not(.method):not(.type):not(.tymethod) {
h2, h3:not(.impl):not(.method):not(.type):not(.tymethod),
h4:not(.method):not(.type):not(.tymethod) {
border-bottom-color: #d2d2d2;
}

View file

@ -5,13 +5,15 @@ body {
color: black;
}
h1, h2, h3:not(.impl):not(.method):not(.type):not(.tymethod), h4:not(.method):not(.type):not(.tymethod) {
h1, h2, h3:not(.impl):not(.method):not(.type):not(.tymethod),
h4:not(.method):not(.type):not(.tymethod) {
color: black;
}
h1.fqn {
border-bottom-color: #D5D5D5;
}
h2, h3:not(.impl):not(.method):not(.type):not(.tymethod), h4:not(.method):not(.type):not(.tymethod) {
h2, h3:not(.impl):not(.method):not(.type):not(.tymethod),
h4:not(.method):not(.type):not(.tymethod) {
border-bottom-color: #DDDDDD;
}

View file

@ -584,25 +584,18 @@ impl<'a, 'tcx> DocFolder for LinkCollector<'a, 'tcx> {
let (res, fragment) = {
let mut kind = None;
let mut disambiguator = None;
path_str = if let Some(prefix) = ["struct@", "enum@", "type@", "trait@", "union@"]
.iter()
.find(|p| link.starts_with(**p))
path_str = if let Some(prefix) =
["struct@", "enum@", "type@", "trait@", "union@", "module@", "mod@"]
.iter()
.find(|p| link.starts_with(**p))
{
kind = Some(TypeNS);
disambiguator = Some(&prefix[..prefix.len() - 1]);
link.trim_start_matches(prefix)
} else if let Some(prefix) = [
"const@",
"static@",
"value@",
"function@",
"mod@",
"fn@",
"module@",
"method@",
]
.iter()
.find(|p| link.starts_with(**p))
} else if let Some(prefix) =
["const@", "static@", "value@", "function@", "fn@", "method@"]
.iter()
.find(|p| link.starts_with(**p))
{
kind = Some(ValueNS);
disambiguator = Some(&prefix[..prefix.len() - 1]);

View file

@ -45,14 +45,14 @@ pub struct TestOptions {
pub fn run(options: Options) -> Result<(), String> {
let input = config::Input::File(options.input.clone());
let invalid_codeblock_attribute_name = rustc_lint::builtin::INVALID_CODEBLOCK_ATTRIBUTES.name;
let invalid_codeblock_attributes_name = rustc_lint::builtin::INVALID_CODEBLOCK_ATTRIBUTES.name;
// In addition to those specific lints, we also need to allow those given through
// command line, otherwise they'll get ignored and we don't want that.
let allowed_lints = vec![invalid_codeblock_attribute_name.to_owned()];
let allowed_lints = vec![invalid_codeblock_attributes_name.to_owned()];
let (lint_opts, lint_caps) = init_lints(allowed_lints, options.lint_opts.clone(), |lint| {
if lint.name == invalid_codeblock_attribute_name {
if lint.name == invalid_codeblock_attributes_name {
None
} else {
Some((lint.name_lower(), lint::Allow))

View file

@ -79,13 +79,6 @@ fn main() -> () {
}
bb10: {
_4 = const (); // scope 0 at $DIR/issue-49232.rs:10:25: 10:30
// ty::Const
// + ty: ()
// + val: Value(Scalar(<ZST>))
// mir::Constant
// + span: $DIR/issue-49232.rs:10:25: 10:30
// + literal: Const { ty: (), val: Value(Scalar(<ZST>)) }
unreachable; // scope 0 at $DIR/issue-49232.rs:10:25: 10:30
}

View file

@ -26,27 +26,21 @@
let mut _24: &[&str; 3]; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _25: &[&str; 3]; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _26: [&str; 3]; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _27: &str; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _28: &str; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _29: &str; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _30: &str; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _31: &str; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _32: &str; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _33: &[std::fmt::ArgumentV1]; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _34: &[std::fmt::ArgumentV1; 2]; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let _35: &[std::fmt::ArgumentV1; 2]; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let _36: [std::fmt::ArgumentV1; 2]; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _37: (&&i32, &&i32); // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _38: &&i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _39: &i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _40: &&i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _41: &i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _44: std::fmt::ArgumentV1; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _45: &&i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _46: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _47: std::fmt::ArgumentV1; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _48: &&i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _49: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _27: &[std::fmt::ArgumentV1]; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _28: &[std::fmt::ArgumentV1; 2]; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let _29: &[std::fmt::ArgumentV1; 2]; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let _30: [std::fmt::ArgumentV1; 2]; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _31: (&&i32, &&i32); // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _32: &&i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _33: &i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _34: &&i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _35: &i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _38: std::fmt::ArgumentV1; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _39: &&i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _40: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _41: std::fmt::ArgumentV1; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _42: &&i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _43: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
scope 1 {
debug split => _1; // in scope 1 at $DIR/issue-73223.rs:2:9: 2:14
let _6: std::option::Option<i32>; // in scope 1 at $DIR/issue-73223.rs:7:9: 7:14
@ -54,39 +48,39 @@
debug _prev => _6; // in scope 3 at $DIR/issue-73223.rs:7:9: 7:14
let _13: &i32; // in scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _14: &i32; // in scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _51: &i32; // in scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _45: &i32; // in scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
scope 4 {
debug left_val => _13; // in scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
debug right_val => _14; // in scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _42: &&i32; // in scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _43: &&i32; // in scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _50: &[&str; 3]; // in scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _36: &&i32; // in scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _37: &&i32; // in scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _44: &[&str; 3]; // in scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
scope 5 {
debug arg0 => _42; // in scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
debug arg1 => _43; // in scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
debug arg0 => _36; // in scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
debug arg1 => _37; // in scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
scope 6 {
debug x => _45; // in scope 6 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
debug f => _46; // in scope 6 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
let mut _52: for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 6 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _53: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 6 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _54: &core::fmt::Opaque; // in scope 6 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _55: &&i32; // in scope 6 at $SRC_DIR/libstd/macros.rs:LL:COL
debug x => _39; // in scope 6 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
debug f => _40; // in scope 6 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
let mut _46: for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 6 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _47: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 6 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _48: &core::fmt::Opaque; // in scope 6 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _49: &&i32; // in scope 6 at $SRC_DIR/libstd/macros.rs:LL:COL
}
scope 8 {
debug x => _48; // in scope 8 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
debug f => _49; // in scope 8 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
let mut _56: for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 8 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _57: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 8 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _58: &core::fmt::Opaque; // in scope 8 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _59: &&i32; // in scope 8 at $SRC_DIR/libstd/macros.rs:LL:COL
debug x => _42; // in scope 8 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
debug f => _43; // in scope 8 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
let mut _50: for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 8 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _51: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 8 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _52: &core::fmt::Opaque; // in scope 8 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _53: &&i32; // in scope 8 at $SRC_DIR/libstd/macros.rs:LL:COL
}
}
scope 10 {
debug pieces => _23; // in scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
debug args => _33; // in scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
let mut _60: &[&str]; // in scope 10 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _61: std::option::Option<&[std::fmt::rt::v1::Argument]>; // in scope 10 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _62: &[std::fmt::ArgumentV1]; // in scope 10 at $SRC_DIR/libstd/macros.rs:LL:COL
debug args => _27; // in scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
let mut _54: &[&str]; // in scope 10 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _55: std::option::Option<&[std::fmt::rt::v1::Argument]>; // in scope 10 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _56: &[std::fmt::ArgumentV1]; // in scope 10 at $SRC_DIR/libstd/macros.rs:LL:COL
}
}
}
@ -150,14 +144,14 @@
StorageLive(_10); // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_10 = &_1; // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_11); // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_51 = const main::promoted[1]; // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_45 = const main::promoted[1]; // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
// ty::Const
// + ty: &i32
// + val: Unevaluated(WithOptConstParam { did: DefId(0:3 ~ issue_73223[317d]::main[0]), const_param_did: None }, [], Some(promoted[1]))
// mir::Constant
// + span: $SRC_DIR/libcore/macros/mod.rs:LL:COL
// + literal: Const { ty: &i32, val: Unevaluated(WithOptConstParam { did: DefId(0:3 ~ issue_73223[317d]::main[0]), const_param_did: None }, [], Some(promoted[1])) }
_11 = _51; // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_11 = _45; // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
(_9.0: &i32) = move _10; // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
(_9.1: &i32) = move _11; // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageDead(_11); // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
@ -217,53 +211,53 @@
StorageLive(_23); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_24); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_25); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_50 = const main::promoted[0]; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_44 = const main::promoted[0]; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
// ty::Const
// + ty: &[&str; 3]
// + val: Unevaluated(WithOptConstParam { did: DefId(0:3 ~ issue_73223[317d]::main[0]), const_param_did: None }, [], Some(promoted[0]))
// mir::Constant
// + span: $SRC_DIR/libcore/macros/mod.rs:LL:COL
// + literal: Const { ty: &[&str; 3], val: Unevaluated(WithOptConstParam { did: DefId(0:3 ~ issue_73223[317d]::main[0]), const_param_did: None }, [], Some(promoted[0])) }
_25 = _50; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_25 = _44; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_24 = _25; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_23 = move _24 as &[&str] (Pointer(Unsize)); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageDead(_24); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_33); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_34); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_35); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_36); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_37); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_38); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_39); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_39 = _13; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_38 = &_39; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_40); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_41); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_41 = _14; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_40 = &_41; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
(_37.0: &&i32) = move _38; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
(_37.1: &&i32) = move _40; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_40); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_38); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_42); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_42 = (_37.0: &&i32); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_43); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_43 = (_37.1: &&i32); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_44); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_45); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_45 = _42; // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_46); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_46 = const <&i32 as std::fmt::Debug>::fmt as for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> (Pointer(ReifyFnPointer)); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_27); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_28); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_29); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_30); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_31); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_32); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_33); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_33 = _13; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_32 = &_33; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_34); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_35); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_35 = _14; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_34 = &_35; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
(_31.0: &&i32) = move _32; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
(_31.1: &&i32) = move _34; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_34); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_32); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_36); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_36 = (_31.0: &&i32); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_37); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_37 = (_31.1: &&i32); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_38); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_39); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_39 = _36; // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_40); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_40 = const <&i32 as std::fmt::Debug>::fmt as for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> (Pointer(ReifyFnPointer)); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
// ty::Const
// + ty: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> {<&i32 as std::fmt::Debug>::fmt}
// + val: Value(Scalar(<ZST>))
// mir::Constant
// + span: $SRC_DIR/libcore/macros/mod.rs:LL:COL
// + literal: Const { ty: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> {<&i32 as std::fmt::Debug>::fmt}, val: Value(Scalar(<ZST>)) }
StorageLive(_52); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_53); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_53 = _46; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_52 = const std::intrinsics::transmute::<for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>, for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>>(move _53) -> bb6; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_46); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_47); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_47 = _40; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_46 = const std::intrinsics::transmute::<for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>, for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>>(move _47) -> bb6; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
// ty::Const
// + ty: unsafe extern "rust-intrinsic" fn(for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>) -> for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> {std::intrinsics::transmute::<for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>, for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>>}
// + val: Value(Scalar(<ZST>))
@ -273,11 +267,11 @@
}
bb6: {
StorageDead(_53); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_54); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_55); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_55 = _45; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_54 = const std::intrinsics::transmute::<&&i32, &core::fmt::Opaque>(move _55) -> bb7; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_47); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_48); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_49); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_49 = _39; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_48 = const std::intrinsics::transmute::<&&i32, &core::fmt::Opaque>(move _49) -> bb7; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
// ty::Const
// + ty: unsafe extern "rust-intrinsic" fn(&&i32) -> &core::fmt::Opaque {std::intrinsics::transmute::<&&i32, &core::fmt::Opaque>}
// + val: Value(Scalar(<ZST>))
@ -287,28 +281,28 @@
}
bb7: {
StorageDead(_55); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_44.0: &core::fmt::Opaque) = move _54; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_44.1: for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>) = move _52; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_54); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_52); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_46); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_45); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_47); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_48); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_48 = _43; // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_49); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_49 = const <&i32 as std::fmt::Debug>::fmt as for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> (Pointer(ReifyFnPointer)); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageDead(_49); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_38.0: &core::fmt::Opaque) = move _48; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_38.1: for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>) = move _46; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_48); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_46); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_40); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_39); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_41); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_42); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_42 = _37; // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_43); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_43 = const <&i32 as std::fmt::Debug>::fmt as for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> (Pointer(ReifyFnPointer)); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
// ty::Const
// + ty: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> {<&i32 as std::fmt::Debug>::fmt}
// + val: Value(Scalar(<ZST>))
// mir::Constant
// + span: $SRC_DIR/libcore/macros/mod.rs:LL:COL
// + literal: Const { ty: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> {<&i32 as std::fmt::Debug>::fmt}, val: Value(Scalar(<ZST>)) }
StorageLive(_56); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_57); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_57 = _49; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_56 = const std::intrinsics::transmute::<for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>, for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>>(move _57) -> bb8; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_50); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_51); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_51 = _43; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_50 = const std::intrinsics::transmute::<for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>, for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>>(move _51) -> bb8; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
// ty::Const
// + ty: unsafe extern "rust-intrinsic" fn(for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>) -> for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> {std::intrinsics::transmute::<for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>, for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>>}
// + val: Value(Scalar(<ZST>))
@ -318,11 +312,11 @@
}
bb8: {
StorageDead(_57); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_58); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_59); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_59 = _48; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_58 = const std::intrinsics::transmute::<&&i32, &core::fmt::Opaque>(move _59) -> bb9; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_51); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_52); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_53); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_53 = _42; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_52 = const std::intrinsics::transmute::<&&i32, &core::fmt::Opaque>(move _53) -> bb9; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
// ty::Const
// + ty: unsafe extern "rust-intrinsic" fn(&&i32) -> &core::fmt::Opaque {std::intrinsics::transmute::<&&i32, &core::fmt::Opaque>}
// + val: Value(Scalar(<ZST>))
@ -332,35 +326,35 @@
}
bb9: {
StorageDead(_59); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_47.0: &core::fmt::Opaque) = move _58; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_47.1: for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>) = move _56; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_58); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_56); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_49); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_48); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
_36 = [move _44, move _47]; // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_47); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_44); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_43); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_42); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
_35 = &_36; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
_34 = _35; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
_33 = move _34 as &[std::fmt::ArgumentV1] (Pointer(Unsize)); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_34); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_60); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_60 = _23; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_61); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
discriminant(_61) = 0; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_62); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_62 = _33; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_22.0: &[&str]) = move _60; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_22.1: std::option::Option<&[std::fmt::rt::v1::Argument]>) = move _61; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_22.2: &[std::fmt::ArgumentV1]) = move _62; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_62); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_61); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_60); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_33); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_53); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_41.0: &core::fmt::Opaque) = move _52; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_41.1: for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>) = move _50; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_52); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_50); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_43); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_42); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
_30 = [move _38, move _41]; // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_41); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_38); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_37); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_36); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
_29 = &_30; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
_28 = _29; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
_27 = move _28 as &[std::fmt::ArgumentV1] (Pointer(Unsize)); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_28); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_54); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_54 = _23; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_55); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
discriminant(_55) = 0; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_56); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_56 = _27; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_22.0: &[&str]) = move _54; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_22.1: std::option::Option<&[std::fmt::rt::v1::Argument]>) = move _55; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_22.2: &[std::fmt::ArgumentV1]) = move _56; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_56); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_55); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_54); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_27); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_23); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
_21 = &_22; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
_20 = _21; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL

View file

@ -26,27 +26,21 @@
let mut _24: &[&str; 3]; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _25: &[&str; 3]; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _26: [&str; 3]; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _27: &str; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _28: &str; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _29: &str; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _30: &str; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _31: &str; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _32: &str; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _33: &[std::fmt::ArgumentV1]; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _34: &[std::fmt::ArgumentV1; 2]; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let _35: &[std::fmt::ArgumentV1; 2]; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let _36: [std::fmt::ArgumentV1; 2]; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _37: (&&i32, &&i32); // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _38: &&i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _39: &i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _40: &&i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _41: &i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _44: std::fmt::ArgumentV1; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _45: &&i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _46: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _47: std::fmt::ArgumentV1; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _48: &&i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _49: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _27: &[std::fmt::ArgumentV1]; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _28: &[std::fmt::ArgumentV1; 2]; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let _29: &[std::fmt::ArgumentV1; 2]; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let _30: [std::fmt::ArgumentV1; 2]; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _31: (&&i32, &&i32); // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _32: &&i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _33: &i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _34: &&i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _35: &i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _38: std::fmt::ArgumentV1; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _39: &&i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _40: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _41: std::fmt::ArgumentV1; // in scope 0 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _42: &&i32; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _43: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 0 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
scope 1 {
debug split => _1; // in scope 1 at $DIR/issue-73223.rs:2:9: 2:14
let _6: std::option::Option<i32>; // in scope 1 at $DIR/issue-73223.rs:7:9: 7:14
@ -54,39 +48,39 @@
debug _prev => _6; // in scope 3 at $DIR/issue-73223.rs:7:9: 7:14
let _13: &i32; // in scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _14: &i32; // in scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _51: &i32; // in scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _45: &i32; // in scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
scope 4 {
debug left_val => _13; // in scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
debug right_val => _14; // in scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _42: &&i32; // in scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _43: &&i32; // in scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _50: &[&str; 3]; // in scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _36: &&i32; // in scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let _37: &&i32; // in scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
let mut _44: &[&str; 3]; // in scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
scope 5 {
debug arg0 => _42; // in scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
debug arg1 => _43; // in scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
debug arg0 => _36; // in scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
debug arg1 => _37; // in scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
scope 6 {
debug x => _45; // in scope 6 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
debug f => _46; // in scope 6 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
let mut _52: for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 6 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _53: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 6 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _54: &core::fmt::Opaque; // in scope 6 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _55: &&i32; // in scope 6 at $SRC_DIR/libstd/macros.rs:LL:COL
debug x => _39; // in scope 6 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
debug f => _40; // in scope 6 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
let mut _46: for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 6 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _47: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 6 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _48: &core::fmt::Opaque; // in scope 6 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _49: &&i32; // in scope 6 at $SRC_DIR/libstd/macros.rs:LL:COL
}
scope 8 {
debug x => _48; // in scope 8 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
debug f => _49; // in scope 8 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
let mut _56: for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 8 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _57: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 8 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _58: &core::fmt::Opaque; // in scope 8 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _59: &&i32; // in scope 8 at $SRC_DIR/libstd/macros.rs:LL:COL
debug x => _42; // in scope 8 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
debug f => _43; // in scope 8 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
let mut _50: for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 8 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _51: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>; // in scope 8 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _52: &core::fmt::Opaque; // in scope 8 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _53: &&i32; // in scope 8 at $SRC_DIR/libstd/macros.rs:LL:COL
}
}
scope 10 {
debug pieces => _23; // in scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
debug args => _33; // in scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
let mut _60: &[&str]; // in scope 10 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _61: std::option::Option<&[std::fmt::rt::v1::Argument]>; // in scope 10 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _62: &[std::fmt::ArgumentV1]; // in scope 10 at $SRC_DIR/libstd/macros.rs:LL:COL
debug args => _27; // in scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
let mut _54: &[&str]; // in scope 10 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _55: std::option::Option<&[std::fmt::rt::v1::Argument]>; // in scope 10 at $SRC_DIR/libstd/macros.rs:LL:COL
let mut _56: &[std::fmt::ArgumentV1]; // in scope 10 at $SRC_DIR/libstd/macros.rs:LL:COL
}
}
}
@ -150,14 +144,14 @@
StorageLive(_10); // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_10 = &_1; // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_11); // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_51 = const main::promoted[1]; // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_45 = const main::promoted[1]; // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
// ty::Const
// + ty: &i32
// + val: Unevaluated(WithOptConstParam { did: DefId(0:3 ~ issue_73223[317d]::main[0]), const_param_did: None }, [], Some(promoted[1]))
// mir::Constant
// + span: $SRC_DIR/libcore/macros/mod.rs:LL:COL
// + literal: Const { ty: &i32, val: Unevaluated(WithOptConstParam { did: DefId(0:3 ~ issue_73223[317d]::main[0]), const_param_did: None }, [], Some(promoted[1])) }
_11 = _51; // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_11 = _45; // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
(_9.0: &i32) = move _10; // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
(_9.1: &i32) = move _11; // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageDead(_11); // scope 3 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
@ -217,53 +211,53 @@
StorageLive(_23); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_24); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_25); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_50 = const main::promoted[0]; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_44 = const main::promoted[0]; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
// ty::Const
// + ty: &[&str; 3]
// + val: Unevaluated(WithOptConstParam { did: DefId(0:3 ~ issue_73223[317d]::main[0]), const_param_did: None }, [], Some(promoted[0]))
// mir::Constant
// + span: $SRC_DIR/libcore/macros/mod.rs:LL:COL
// + literal: Const { ty: &[&str; 3], val: Unevaluated(WithOptConstParam { did: DefId(0:3 ~ issue_73223[317d]::main[0]), const_param_did: None }, [], Some(promoted[0])) }
_25 = _50; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_25 = _44; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_24 = _25; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_23 = move _24 as &[&str] (Pointer(Unsize)); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageDead(_24); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_33); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_34); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_35); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_36); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_37); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_38); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_39); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_39 = _13; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_38 = &_39; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_40); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_41); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_41 = _14; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_40 = &_41; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
(_37.0: &&i32) = move _38; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
(_37.1: &&i32) = move _40; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_40); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_38); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_42); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_42 = (_37.0: &&i32); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_43); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_43 = (_37.1: &&i32); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_44); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_45); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_45 = _42; // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_46); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_46 = const <&i32 as std::fmt::Debug>::fmt as for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> (Pointer(ReifyFnPointer)); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_27); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_28); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_29); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_30); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_31); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_32); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_33); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_33 = _13; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_32 = &_33; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_34); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_35); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_35 = _14; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_34 = &_35; // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
(_31.0: &&i32) = move _32; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
(_31.1: &&i32) = move _34; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_34); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_32); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_36); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_36 = (_31.0: &&i32); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_37); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_37 = (_31.1: &&i32); // scope 4 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_38); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_39); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_39 = _36; // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_40); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_40 = const <&i32 as std::fmt::Debug>::fmt as for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> (Pointer(ReifyFnPointer)); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
// ty::Const
// + ty: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> {<&i32 as std::fmt::Debug>::fmt}
// + val: Value(Scalar(<ZST>))
// mir::Constant
// + span: $SRC_DIR/libcore/macros/mod.rs:LL:COL
// + literal: Const { ty: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> {<&i32 as std::fmt::Debug>::fmt}, val: Value(Scalar(<ZST>)) }
StorageLive(_52); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_53); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_53 = _46; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_52 = const std::intrinsics::transmute::<for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>, for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>>(move _53) -> bb6; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_46); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_47); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_47 = _40; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_46 = const std::intrinsics::transmute::<for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>, for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>>(move _47) -> bb6; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
// ty::Const
// + ty: unsafe extern "rust-intrinsic" fn(for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>) -> for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> {std::intrinsics::transmute::<for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>, for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>>}
// + val: Value(Scalar(<ZST>))
@ -273,11 +267,11 @@
}
bb6: {
StorageDead(_53); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_54); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_55); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_55 = _45; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_54 = const std::intrinsics::transmute::<&&i32, &core::fmt::Opaque>(move _55) -> bb7; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_47); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_48); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_49); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_49 = _39; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_48 = const std::intrinsics::transmute::<&&i32, &core::fmt::Opaque>(move _49) -> bb7; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
// ty::Const
// + ty: unsafe extern "rust-intrinsic" fn(&&i32) -> &core::fmt::Opaque {std::intrinsics::transmute::<&&i32, &core::fmt::Opaque>}
// + val: Value(Scalar(<ZST>))
@ -287,28 +281,28 @@
}
bb7: {
StorageDead(_55); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_44.0: &core::fmt::Opaque) = move _54; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_44.1: for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>) = move _52; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_54); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_52); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_46); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_45); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_47); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_48); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_48 = _43; // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_49); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_49 = const <&i32 as std::fmt::Debug>::fmt as for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> (Pointer(ReifyFnPointer)); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageDead(_49); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_38.0: &core::fmt::Opaque) = move _48; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_38.1: for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>) = move _46; // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_48); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_46); // scope 7 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_40); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_39); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_41); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_42); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_42 = _37; // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
StorageLive(_43); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
_43 = const <&i32 as std::fmt::Debug>::fmt as for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> (Pointer(ReifyFnPointer)); // scope 5 at $SRC_DIR/libcore/macros/mod.rs:LL:COL
// ty::Const
// + ty: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> {<&i32 as std::fmt::Debug>::fmt}
// + val: Value(Scalar(<ZST>))
// mir::Constant
// + span: $SRC_DIR/libcore/macros/mod.rs:LL:COL
// + literal: Const { ty: for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> {<&i32 as std::fmt::Debug>::fmt}, val: Value(Scalar(<ZST>)) }
StorageLive(_56); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_57); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_57 = _49; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_56 = const std::intrinsics::transmute::<for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>, for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>>(move _57) -> bb8; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_50); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_51); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_51 = _43; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_50 = const std::intrinsics::transmute::<for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>, for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>>(move _51) -> bb8; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
// ty::Const
// + ty: unsafe extern "rust-intrinsic" fn(for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>) -> for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error> {std::intrinsics::transmute::<for<'r, 's, 't0> fn(&'r &i32, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>, for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>>}
// + val: Value(Scalar(<ZST>))
@ -318,11 +312,11 @@
}
bb8: {
StorageDead(_57); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_58); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_59); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_59 = _48; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_58 = const std::intrinsics::transmute::<&&i32, &core::fmt::Opaque>(move _59) -> bb9; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_51); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_52); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_53); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_53 = _42; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_52 = const std::intrinsics::transmute::<&&i32, &core::fmt::Opaque>(move _53) -> bb9; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
// ty::Const
// + ty: unsafe extern "rust-intrinsic" fn(&&i32) -> &core::fmt::Opaque {std::intrinsics::transmute::<&&i32, &core::fmt::Opaque>}
// + val: Value(Scalar(<ZST>))
@ -332,35 +326,35 @@
}
bb9: {
StorageDead(_59); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_47.0: &core::fmt::Opaque) = move _58; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_47.1: for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>) = move _56; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_58); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_56); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_49); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_48); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
_36 = [move _44, move _47]; // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_47); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_44); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_43); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_42); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
_35 = &_36; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
_34 = _35; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
_33 = move _34 as &[std::fmt::ArgumentV1] (Pointer(Unsize)); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_34); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_60); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_60 = _23; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_61); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
discriminant(_61) = 0; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_62); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_62 = _33; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_22.0: &[&str]) = move _60; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_22.1: std::option::Option<&[std::fmt::rt::v1::Argument]>) = move _61; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_22.2: &[std::fmt::ArgumentV1]) = move _62; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_62); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_61); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_60); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_33); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_53); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_41.0: &core::fmt::Opaque) = move _52; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_41.1: for<'r, 's, 't0> fn(&'r core::fmt::Opaque, &'s mut std::fmt::Formatter<'t0>) -> std::result::Result<(), std::fmt::Error>) = move _50; // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_52); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_50); // scope 9 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_43); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_42); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
_30 = [move _38, move _41]; // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_41); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_38); // scope 5 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_37); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_36); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
_29 = &_30; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
_28 = _29; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
_27 = move _28 as &[std::fmt::ArgumentV1] (Pointer(Unsize)); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_28); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageLive(_54); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_54 = _23; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_55); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
discriminant(_55) = 0; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageLive(_56); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
_56 = _27; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_22.0: &[&str]) = move _54; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_22.1: std::option::Option<&[std::fmt::rt::v1::Argument]>) = move _55; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
(_22.2: &[std::fmt::ArgumentV1]) = move _56; // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_56); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_55); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_54); // scope 10 at $SRC_DIR/libcore/fmt/mod.rs:LL:COL
StorageDead(_27); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
StorageDead(_23); // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
_21 = &_22; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL
_20 = _21; // scope 4 at $SRC_DIR/libstd/macros.rs:LL:COL

View file

@ -34,27 +34,27 @@ pub fn bar() ({
((::alloc::fmt::format as
for<'r> fn(std::fmt::Arguments<'r>) -> std::string::String {std::fmt::format})(((::core::fmt::Arguments::new_v1
as
fn(&[&str], &[std::fmt::ArgumentV1]) -> std::fmt::Arguments {std::fmt::Arguments::new_v1})((&([("test"
as
&str)]
as
[&str; 1])
as
&[&str; 1]),
(&(match (()
as
())
{
()
=>
([]
as
[std::fmt::ArgumentV1; 0]),
}
as
[std::fmt::ArgumentV1; 0])
as
&[std::fmt::ArgumentV1; 0]))
fn(&[&'static str], &[std::fmt::ArgumentV1]) -> std::fmt::Arguments {std::fmt::Arguments::new_v1})((&([("test"
as
&str)]
as
[&str; 1])
as
&[&str; 1]),
(&(match (()
as
())
{
()
=>
([]
as
[std::fmt::ArgumentV1; 0]),
}
as
[std::fmt::ArgumentV1; 0])
as
&[std::fmt::ArgumentV1; 0]))
as
std::fmt::Arguments))
as std::string::String);

View file

@ -1,6 +1,6 @@
-include ../tools.mk
# only-mingw
# only-windows-gnu
all:
$(CXX) foo.cpp -c -o $(TMPDIR)/foo.o

View file

@ -1,10 +1,6 @@
-include ../tools.mk
# ignore-windows
# ignore-freebsd
# FIXME: on windows `rustc --dep-info` produces Makefile dependency with
# windows native paths (e.g. `c:\path\to\libfoo.a`)
# but msys make seems to fail to recognize such paths, so test fails.
all:
$(RUSTC) --emit dep-info main.rs

View file

@ -1,6 +1,6 @@
-include ../tools.mk
# ignore-windows
# ignore-windows-msvc
#
# Because of Windows exception handling, the code is not necessarily any shorter.
# https://github.com/llvm-mirror/llvm/commit/64b2297786f7fd6f5fa24cdd4db0298fbf211466

View file

@ -1,6 +1,6 @@
-include ../tools.mk
# ignore-windows
# ignore-windows-msvc
all:
$(RUSTC) --emit=obj app.rs

View file

@ -1,10 +0,0 @@
-include ../tools.mk
# only-mingw
all: empty.rs
cp -r $(shell cygpath -u $(shell $(RUSTC) --print sysroot)) $(TMPDIR)/sysroot
$(RUSTC) --target $(TARGET) --sysroot $(TMPDIR)/sysroot -L$(TMPDIR)/obj -Z print-link-args empty.rs | $(CGREP) 'lib\\crt2.o'
mkdir -p $(TMPDIR)/obj
mv $(TMPDIR)/sysroot/lib/rustlib/$(TARGET)/lib/crt2.o $(TMPDIR)/obj/crt2.o
$(RUSTC) --target $(TARGET) --sysroot $(TMPDIR)/sysroot -L$(TMPDIR)/obj -Z print-link-args empty.rs | $(CGREP) 'obj\\crt2.o'

View file

@ -1 +0,0 @@
fn main() {}

View file

@ -1,8 +1,6 @@
-include ../tools.mk
ifdef IS_WINDOWS
all:
else
# ignore-windows-msvc
# rustc will remove one of the two redundant references to foo below. Depending
# on which one gets removed, we'll get a linker error on SOME platforms (like
@ -23,5 +21,3 @@ RUSTC_FLAGS = \
all: $(call DYLIB,foo) $(call STATICLIB,bar) $(call STATICLIB,baz)
$(RUSTC) $(RUSTC_FLAGS) main.rs
$(call RUN,main)
endif

View file

@ -1,9 +1,6 @@
include ../tools.mk
# ignore-windows
#
# On MINGW the --version-script, --dynamic-list, and --retain-symbol args don't
# seem to work reliably.
# ignore-windows-msvc
NM=nm -D
CDYLIB_NAME=liba_cdylib.so
@ -19,6 +16,14 @@ EXE_NAME=an_executable
COMBINED_CDYLIB_NAME=libcombined_rlib_dylib.dylib
endif
ifdef IS_WINDOWS
NM=nm -g
CDYLIB_NAME=liba_cdylib.dll.a
RDYLIB_NAME=liba_rust_dylib.dll.a
EXE_NAME=an_executable.exe
COMBINED_CDYLIB_NAME=libcombined_rlib_dylib.dll.a
endif
# `grep` regex for symbols produced by either `legacy` or `v0` mangling
RE_ANY_RUST_SYMBOL="_ZN.*h.*E\|_R[a-zA-Z0-9_]+"
@ -30,38 +35,38 @@ all:
$(RUSTC) -Zshare-generics=no a_cdylib.rs --crate-name combined_rlib_dylib --crate-type=rlib,cdylib
# Check that a cdylib exports its public #[no_mangle] functions
[ "$$($(NM) $(TMPDIR)/$(CDYLIB_NAME) | grep -c public_c_function_from_cdylib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(CDYLIB_NAME) | grep -v __imp_ | grep -c public_c_function_from_cdylib)" -eq "1" ]
# Check that a cdylib exports the public #[no_mangle] functions of dependencies
[ "$$($(NM) $(TMPDIR)/$(CDYLIB_NAME) | grep -c public_c_function_from_rlib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(CDYLIB_NAME) | grep -v __imp_ | grep -c public_c_function_from_rlib)" -eq "1" ]
# Check that a cdylib DOES NOT export any public Rust functions
[ "$$($(NM) $(TMPDIR)/$(CDYLIB_NAME) | grep -c $(RE_ANY_RUST_SYMBOL))" -eq "0" ]
[ "$$($(NM) $(TMPDIR)/$(CDYLIB_NAME) | grep -v __imp_ | grep -c $(RE_ANY_RUST_SYMBOL))" -eq "0" ]
# Check that a Rust dylib exports its monomorphic functions
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -c public_c_function_from_rust_dylib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -c public_rust_function_from_rust_dylib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -v __imp_ | grep -c public_c_function_from_rust_dylib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -v __imp_ | grep -c public_rust_function_from_rust_dylib)" -eq "1" ]
# Check that a Rust dylib does not export generics if -Zshare-generics=no
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -c public_generic_function_from_rust_dylib)" -eq "0" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -v __imp_ | grep -c public_generic_function_from_rust_dylib)" -eq "0" ]
# Check that a Rust dylib exports the monomorphic functions from its dependencies
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -c public_c_function_from_rlib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -c public_rust_function_from_rlib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -v __imp_ | grep -c public_c_function_from_rlib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -v __imp_ | grep -c public_rust_function_from_rlib)" -eq "1" ]
# Check that a Rust dylib does not export generics if -Zshare-generics=no
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -c public_generic_function_from_rlib)" -eq "0" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -v __imp_ | grep -c public_generic_function_from_rlib)" -eq "0" ]
# Check that an executable does not export any dynamic symbols
[ "$$($(NM) $(TMPDIR)/$(EXE_NAME) | grep -c public_c_function_from_rlib)" -eq "0" ]
[ "$$($(NM) $(TMPDIR)/$(EXE_NAME) | grep -c public_rust_function_from_exe)" -eq "0" ]
[ "$$($(NM) $(TMPDIR)/$(EXE_NAME) | grep -v __imp_ | grep -c public_c_function_from_rlib)" -eq "0" ]
[ "$$($(NM) $(TMPDIR)/$(EXE_NAME) | grep -v __imp_ | grep -c public_rust_function_from_exe)" -eq "0" ]
# Check the combined case, where we generate a cdylib and an rlib in the same
# compilation session:
# Check that a cdylib exports its public #[no_mangle] functions
[ "$$($(NM) $(TMPDIR)/$(COMBINED_CDYLIB_NAME) | grep -c public_c_function_from_cdylib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(COMBINED_CDYLIB_NAME) | grep -v __imp_ | grep -c public_c_function_from_cdylib)" -eq "1" ]
# Check that a cdylib exports the public #[no_mangle] functions of dependencies
[ "$$($(NM) $(TMPDIR)/$(COMBINED_CDYLIB_NAME) | grep -c public_c_function_from_rlib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(COMBINED_CDYLIB_NAME) | grep -v __imp_ | grep -c public_c_function_from_rlib)" -eq "1" ]
# Check that a cdylib DOES NOT export any public Rust functions
[ "$$($(NM) $(TMPDIR)/$(COMBINED_CDYLIB_NAME) | grep -c $(RE_ANY_RUST_SYMBOL))" -eq "0" ]
[ "$$($(NM) $(TMPDIR)/$(COMBINED_CDYLIB_NAME) | grep -v __imp_ | grep -c $(RE_ANY_RUST_SYMBOL))" -eq "0" ]
$(RUSTC) -Zshare-generics=yes an_rlib.rs
@ -70,22 +75,22 @@ all:
$(RUSTC) -Zshare-generics=yes an_executable.rs
# Check that a cdylib exports its public #[no_mangle] functions
[ "$$($(NM) $(TMPDIR)/$(CDYLIB_NAME) | grep -c public_c_function_from_cdylib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(CDYLIB_NAME) | grep -v __imp_ | grep -c public_c_function_from_cdylib)" -eq "1" ]
# Check that a cdylib exports the public #[no_mangle] functions of dependencies
[ "$$($(NM) $(TMPDIR)/$(CDYLIB_NAME) | grep -c public_c_function_from_rlib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(CDYLIB_NAME) | grep -v __imp_ | grep -c public_c_function_from_rlib)" -eq "1" ]
# Check that a cdylib DOES NOT export any public Rust functions
[ "$$($(NM) $(TMPDIR)/$(CDYLIB_NAME) | grep -c $(RE_ANY_RUST_SYMBOL))" -eq "0" ]
[ "$$($(NM) $(TMPDIR)/$(CDYLIB_NAME) | grep -v __imp_ | grep -c $(RE_ANY_RUST_SYMBOL))" -eq "0" ]
# Check that a Rust dylib exports its monomorphic functions, including generics this time
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -c public_c_function_from_rust_dylib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -c public_rust_function_from_rust_dylib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -c public_generic_function_from_rust_dylib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -v __imp_ | grep -c public_c_function_from_rust_dylib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -v __imp_ | grep -c public_rust_function_from_rust_dylib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -v __imp_ | grep -c public_generic_function_from_rust_dylib)" -eq "1" ]
# Check that a Rust dylib exports the monomorphic functions from its dependencies
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -c public_c_function_from_rlib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -c public_rust_function_from_rlib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -c public_generic_function_from_rlib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -v __imp_ | grep -c public_c_function_from_rlib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -v __imp_ | grep -c public_rust_function_from_rlib)" -eq "1" ]
[ "$$($(NM) $(TMPDIR)/$(RDYLIB_NAME) | grep -v __imp_ | grep -c public_generic_function_from_rlib)" -eq "1" ]
# Check that an executable does not export any dynamic symbols
[ "$$($(NM) $(TMPDIR)/$(EXE_NAME) | grep -c public_c_function_from_rlib)" -eq "0" ]
[ "$$($(NM) $(TMPDIR)/$(EXE_NAME) | grep -c public_rust_function_from_exe)" -eq "0" ]
[ "$$($(NM) $(TMPDIR)/$(EXE_NAME) | grep -v __imp_ | grep -c public_c_function_from_rlib)" -eq "0" ]
[ "$$($(NM) $(TMPDIR)/$(EXE_NAME) | grep -v __imp_ | grep -c public_rust_function_from_exe)" -eq "0" ]

View file

@ -150,7 +150,7 @@ ifdef IS_MSVC
$(CC) $< -link -dll -out:`cygpath -w $@`
else
%.dll: lib%.o
$(CC) -o $@ $< -shared
$(CC) -o $@ $< -shared -Wl,--out-implib=$@.a
endif
$(TMPDIR)/lib%.o: %.c

View file

@ -1,6 +1,6 @@
-include ../tools.mk
# ignore-windows
# ignore-windows-msvc
all:
$(RUSTC) -C opt-level=3 --emit=obj used.rs

View file

@ -29,7 +29,7 @@ fn main() {
}
Some(s) if s.eq("--test-aslr") => {
let cnt = run_self(&arg0);
if cnt != NUM_RUNS {
if cnt == 1 {
eprintln!("FAIL: {} most likely no ASLR", arg0);
std::process::exit(1);
}

View file

@ -0,0 +1,18 @@
// ignore-tidy-linelength
#![deny(intra_doc_link_resolution_failure)]
pub fn foo() {
}
pub mod foo {}
// @has intra_doc_link_mod_ambiguity/struct.A.html '//a/@href' '../intra_doc_link_mod_ambiguity/foo/index.html'
/// Module is [`module@foo`]
pub struct A;
// @has intra_doc_link_mod_ambiguity/struct.B.html '//a/@href' '../intra_doc_link_mod_ambiguity/fn.foo.html'
/// Function is [`fn@foo`]
pub struct B;

View file

@ -0,0 +1,14 @@
// run-pass
#![feature(const_option)]
const X: Option<i32> = Some(32);
const Y: Option<&i32> = X.as_ref();
const IS_SOME: bool = X.is_some();
const IS_NONE: bool = Y.is_none();
fn main() {
assert!(IS_SOME);
assert!(!IS_NONE)
}

View file

@ -0,0 +1,18 @@
// check-pass
trait Trait<T> {
const ASSOC_CONST: usize = 0;
}
impl Trait<()> for u8 {}
// `u8::ASSOC_CONST` is resolved today, but will be ambiguous
// under lazy normalization.
fn foo<T, U>() -> [(T, U); u8::ASSOC_CONST]
where
u8: Trait<T> + Trait<U>,
{
todo!()
}
fn main() {}

View file

@ -0,0 +1,18 @@
// check-pass
// If we allow the parent generics here without using lazy normalization
// this results in a cycle error.
struct Foo<T, U>(T, U);
impl<T> From<[u8; 1 + 1]> for Foo<T, [u8; 1 + 1]> {
fn from(value: [u8; 1 + 1]) -> Foo<T, [u8; 1 + 1]> {
todo!();
}
}
fn break_me<T>()
where
[u8; 1 + 1]: From<[u8; 1 + 1]>
{}
fn main() {}

View file

@ -23,6 +23,18 @@ enum WrapEnum<T> { Wrapped(T) }
#[repr(transparent)]
pub(crate) struct NonBig(u64);
/// A two-variant enum, thus needs a tag and may not remain uninitialized.
enum Fruit {
Apple,
Banana,
}
/// Looks like two variants but really only has one.
enum OneFruit {
Apple(!),
Banana,
}
#[allow(unused)]
fn generic<T: 'static>() {
unsafe {
@ -80,6 +92,9 @@ fn main() {
let _val: NonBig = mem::zeroed();
let _val: NonBig = mem::uninitialized(); //~ ERROR: does not permit being left uninitialized
let _val: Fruit = mem::zeroed();
let _val: Fruit = mem::uninitialized(); //~ ERROR: does not permit being left uninitialized
// Transmute-from-0
let _val: &'static i32 = mem::transmute(0usize); //~ ERROR: does not permit zero-initialization
let _val: &'static [i32] = mem::transmute((0usize, 0usize)); //~ ERROR: does not permit zero-initialization
@ -96,5 +111,9 @@ fn main() {
let _val: MaybeUninit<&'static i32> = mem::zeroed();
let _val: i32 = mem::zeroed();
let _val: bool = MaybeUninit::zeroed().assume_init();
// Some things that happen to work due to rustc implementation details,
// but are not guaranteed to keep working.
let _val: i32 = mem::uninitialized();
let _val: OneFruit = mem::uninitialized();
}
}

View file

@ -1,5 +1,5 @@
error: the type `&T` does not permit zero-initialization
--> $DIR/uninitialized-zeroed.rs:29:32
--> $DIR/uninitialized-zeroed.rs:41:32
|
LL | let _val: &'static T = mem::zeroed();
| ^^^^^^^^^^^^^
@ -15,7 +15,7 @@ LL | #![deny(invalid_value)]
= note: references must be non-null
error: the type `&T` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:30:32
--> $DIR/uninitialized-zeroed.rs:42:32
|
LL | let _val: &'static T = mem::uninitialized();
| ^^^^^^^^^^^^^^^^^^^^
@ -26,7 +26,7 @@ LL | let _val: &'static T = mem::uninitialized();
= note: references must be non-null
error: the type `Wrap<&T>` does not permit zero-initialization
--> $DIR/uninitialized-zeroed.rs:32:38
--> $DIR/uninitialized-zeroed.rs:44:38
|
LL | let _val: Wrap<&'static T> = mem::zeroed();
| ^^^^^^^^^^^^^
@ -41,7 +41,7 @@ LL | struct Wrap<T> { wrapped: T }
| ^^^^^^^^^^
error: the type `Wrap<&T>` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:33:38
--> $DIR/uninitialized-zeroed.rs:45:38
|
LL | let _val: Wrap<&'static T> = mem::uninitialized();
| ^^^^^^^^^^^^^^^^^^^^
@ -56,7 +56,7 @@ LL | struct Wrap<T> { wrapped: T }
| ^^^^^^^^^^
error: the type `!` does not permit zero-initialization
--> $DIR/uninitialized-zeroed.rs:40:23
--> $DIR/uninitialized-zeroed.rs:52:23
|
LL | let _val: ! = mem::zeroed();
| ^^^^^^^^^^^^^
@ -67,7 +67,7 @@ LL | let _val: ! = mem::zeroed();
= note: the `!` type has no valid value
error: the type `!` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:41:23
--> $DIR/uninitialized-zeroed.rs:53:23
|
LL | let _val: ! = mem::uninitialized();
| ^^^^^^^^^^^^^^^^^^^^
@ -78,7 +78,7 @@ LL | let _val: ! = mem::uninitialized();
= note: the `!` type has no valid value
error: the type `(i32, !)` does not permit zero-initialization
--> $DIR/uninitialized-zeroed.rs:43:30
--> $DIR/uninitialized-zeroed.rs:55:30
|
LL | let _val: (i32, !) = mem::zeroed();
| ^^^^^^^^^^^^^
@ -89,7 +89,7 @@ LL | let _val: (i32, !) = mem::zeroed();
= note: the `!` type has no valid value
error: the type `(i32, !)` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:44:30
--> $DIR/uninitialized-zeroed.rs:56:30
|
LL | let _val: (i32, !) = mem::uninitialized();
| ^^^^^^^^^^^^^^^^^^^^
@ -100,7 +100,7 @@ LL | let _val: (i32, !) = mem::uninitialized();
= note: the `!` type has no valid value
error: the type `Void` does not permit zero-initialization
--> $DIR/uninitialized-zeroed.rs:46:26
--> $DIR/uninitialized-zeroed.rs:58:26
|
LL | let _val: Void = mem::zeroed();
| ^^^^^^^^^^^^^
@ -111,7 +111,7 @@ LL | let _val: Void = mem::zeroed();
= note: enums with no variants have no valid value
error: the type `Void` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:47:26
--> $DIR/uninitialized-zeroed.rs:59:26
|
LL | let _val: Void = mem::uninitialized();
| ^^^^^^^^^^^^^^^^^^^^
@ -122,7 +122,7 @@ LL | let _val: Void = mem::uninitialized();
= note: enums with no variants have no valid value
error: the type `&i32` does not permit zero-initialization
--> $DIR/uninitialized-zeroed.rs:49:34
--> $DIR/uninitialized-zeroed.rs:61:34
|
LL | let _val: &'static i32 = mem::zeroed();
| ^^^^^^^^^^^^^
@ -133,7 +133,7 @@ LL | let _val: &'static i32 = mem::zeroed();
= note: references must be non-null
error: the type `&i32` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:50:34
--> $DIR/uninitialized-zeroed.rs:62:34
|
LL | let _val: &'static i32 = mem::uninitialized();
| ^^^^^^^^^^^^^^^^^^^^
@ -144,7 +144,7 @@ LL | let _val: &'static i32 = mem::uninitialized();
= note: references must be non-null
error: the type `Ref` does not permit zero-initialization
--> $DIR/uninitialized-zeroed.rs:52:25
--> $DIR/uninitialized-zeroed.rs:64:25
|
LL | let _val: Ref = mem::zeroed();
| ^^^^^^^^^^^^^
@ -159,7 +159,7 @@ LL | struct Ref(&'static i32);
| ^^^^^^^^^^^^
error: the type `Ref` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:53:25
--> $DIR/uninitialized-zeroed.rs:65:25
|
LL | let _val: Ref = mem::uninitialized();
| ^^^^^^^^^^^^^^^^^^^^
@ -174,7 +174,7 @@ LL | struct Ref(&'static i32);
| ^^^^^^^^^^^^
error: the type `fn()` does not permit zero-initialization
--> $DIR/uninitialized-zeroed.rs:55:26
--> $DIR/uninitialized-zeroed.rs:67:26
|
LL | let _val: fn() = mem::zeroed();
| ^^^^^^^^^^^^^
@ -185,7 +185,7 @@ LL | let _val: fn() = mem::zeroed();
= note: function pointers must be non-null
error: the type `fn()` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:56:26
--> $DIR/uninitialized-zeroed.rs:68:26
|
LL | let _val: fn() = mem::uninitialized();
| ^^^^^^^^^^^^^^^^^^^^
@ -196,7 +196,7 @@ LL | let _val: fn() = mem::uninitialized();
= note: function pointers must be non-null
error: the type `Wrap<fn()>` does not permit zero-initialization
--> $DIR/uninitialized-zeroed.rs:58:32
--> $DIR/uninitialized-zeroed.rs:70:32
|
LL | let _val: Wrap<fn()> = mem::zeroed();
| ^^^^^^^^^^^^^
@ -211,7 +211,7 @@ LL | struct Wrap<T> { wrapped: T }
| ^^^^^^^^^^
error: the type `Wrap<fn()>` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:59:32
--> $DIR/uninitialized-zeroed.rs:71:32
|
LL | let _val: Wrap<fn()> = mem::uninitialized();
| ^^^^^^^^^^^^^^^^^^^^
@ -226,7 +226,7 @@ LL | struct Wrap<T> { wrapped: T }
| ^^^^^^^^^^
error: the type `WrapEnum<fn()>` does not permit zero-initialization
--> $DIR/uninitialized-zeroed.rs:61:36
--> $DIR/uninitialized-zeroed.rs:73:36
|
LL | let _val: WrapEnum<fn()> = mem::zeroed();
| ^^^^^^^^^^^^^
@ -241,7 +241,7 @@ LL | enum WrapEnum<T> { Wrapped(T) }
| ^
error: the type `WrapEnum<fn()>` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:62:36
--> $DIR/uninitialized-zeroed.rs:74:36
|
LL | let _val: WrapEnum<fn()> = mem::uninitialized();
| ^^^^^^^^^^^^^^^^^^^^
@ -256,7 +256,7 @@ LL | enum WrapEnum<T> { Wrapped(T) }
| ^
error: the type `Wrap<(RefPair, i32)>` does not permit zero-initialization
--> $DIR/uninitialized-zeroed.rs:64:42
--> $DIR/uninitialized-zeroed.rs:76:42
|
LL | let _val: Wrap<(RefPair, i32)> = mem::zeroed();
| ^^^^^^^^^^^^^
@ -271,7 +271,7 @@ LL | struct RefPair((&'static i32, i32));
| ^^^^^^^^^^^^^^^^^^^
error: the type `Wrap<(RefPair, i32)>` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:65:42
--> $DIR/uninitialized-zeroed.rs:77:42
|
LL | let _val: Wrap<(RefPair, i32)> = mem::uninitialized();
| ^^^^^^^^^^^^^^^^^^^^
@ -286,7 +286,7 @@ LL | struct RefPair((&'static i32, i32));
| ^^^^^^^^^^^^^^^^^^^
error: the type `std::ptr::NonNull<i32>` does not permit zero-initialization
--> $DIR/uninitialized-zeroed.rs:67:34
--> $DIR/uninitialized-zeroed.rs:79:34
|
LL | let _val: NonNull<i32> = mem::zeroed();
| ^^^^^^^^^^^^^
@ -297,7 +297,7 @@ LL | let _val: NonNull<i32> = mem::zeroed();
= note: `std::ptr::NonNull<i32>` must be non-null
error: the type `std::ptr::NonNull<i32>` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:68:34
--> $DIR/uninitialized-zeroed.rs:80:34
|
LL | let _val: NonNull<i32> = mem::uninitialized();
| ^^^^^^^^^^^^^^^^^^^^
@ -308,7 +308,7 @@ LL | let _val: NonNull<i32> = mem::uninitialized();
= note: `std::ptr::NonNull<i32>` must be non-null
error: the type `*const dyn std::marker::Send` does not permit zero-initialization
--> $DIR/uninitialized-zeroed.rs:70:37
--> $DIR/uninitialized-zeroed.rs:82:37
|
LL | let _val: *const dyn Send = mem::zeroed();
| ^^^^^^^^^^^^^
@ -319,7 +319,7 @@ LL | let _val: *const dyn Send = mem::zeroed();
= note: the vtable of a wide raw pointer must be non-null
error: the type `*const dyn std::marker::Send` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:71:37
--> $DIR/uninitialized-zeroed.rs:83:37
|
LL | let _val: *const dyn Send = mem::uninitialized();
| ^^^^^^^^^^^^^^^^^^^^
@ -330,7 +330,7 @@ LL | let _val: *const dyn Send = mem::uninitialized();
= note: the vtable of a wide raw pointer must be non-null
error: the type `bool` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:75:26
--> $DIR/uninitialized-zeroed.rs:87:26
|
LL | let _val: bool = mem::uninitialized();
| ^^^^^^^^^^^^^^^^^^^^
@ -341,7 +341,7 @@ LL | let _val: bool = mem::uninitialized();
= note: booleans must be either `true` or `false`
error: the type `Wrap<char>` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:78:32
--> $DIR/uninitialized-zeroed.rs:90:32
|
LL | let _val: Wrap<char> = mem::uninitialized();
| ^^^^^^^^^^^^^^^^^^^^
@ -356,7 +356,7 @@ LL | struct Wrap<T> { wrapped: T }
| ^^^^^^^^^^
error: the type `NonBig` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:81:28
--> $DIR/uninitialized-zeroed.rs:93:28
|
LL | let _val: NonBig = mem::uninitialized();
| ^^^^^^^^^^^^^^^^^^^^
@ -366,8 +366,26 @@ LL | let _val: NonBig = mem::uninitialized();
|
= note: `NonBig` must be initialized inside its custom valid range
error: the type `Fruit` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:96:27
|
LL | let _val: Fruit = mem::uninitialized();
| ^^^^^^^^^^^^^^^^^^^^
| |
| this code causes undefined behavior when executed
| help: use `MaybeUninit<T>` instead, and only call `assume_init` after initialization is done
|
note: enums have to be initialized to a variant
--> $DIR/uninitialized-zeroed.rs:27:1
|
LL | / enum Fruit {
LL | | Apple,
LL | | Banana,
LL | | }
| |_^
error: the type `&i32` does not permit zero-initialization
--> $DIR/uninitialized-zeroed.rs:84:34
--> $DIR/uninitialized-zeroed.rs:99:34
|
LL | let _val: &'static i32 = mem::transmute(0usize);
| ^^^^^^^^^^^^^^^^^^^^^^
@ -378,7 +396,7 @@ LL | let _val: &'static i32 = mem::transmute(0usize);
= note: references must be non-null
error: the type `&[i32]` does not permit zero-initialization
--> $DIR/uninitialized-zeroed.rs:85:36
--> $DIR/uninitialized-zeroed.rs:100:36
|
LL | let _val: &'static [i32] = mem::transmute((0usize, 0usize));
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@ -389,7 +407,7 @@ LL | let _val: &'static [i32] = mem::transmute((0usize, 0usize));
= note: references must be non-null
error: the type `std::num::NonZeroU32` does not permit zero-initialization
--> $DIR/uninitialized-zeroed.rs:86:32
--> $DIR/uninitialized-zeroed.rs:101:32
|
LL | let _val: NonZeroU32 = mem::transmute(0);
| ^^^^^^^^^^^^^^^^^
@ -400,7 +418,7 @@ LL | let _val: NonZeroU32 = mem::transmute(0);
= note: `std::num::NonZeroU32` must be non-null
error: the type `std::ptr::NonNull<i32>` does not permit zero-initialization
--> $DIR/uninitialized-zeroed.rs:89:34
--> $DIR/uninitialized-zeroed.rs:104:34
|
LL | let _val: NonNull<i32> = MaybeUninit::zeroed().assume_init();
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@ -411,7 +429,7 @@ LL | let _val: NonNull<i32> = MaybeUninit::zeroed().assume_init();
= note: `std::ptr::NonNull<i32>` must be non-null
error: the type `std::ptr::NonNull<i32>` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:90:34
--> $DIR/uninitialized-zeroed.rs:105:34
|
LL | let _val: NonNull<i32> = MaybeUninit::uninit().assume_init();
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@ -422,7 +440,7 @@ LL | let _val: NonNull<i32> = MaybeUninit::uninit().assume_init();
= note: `std::ptr::NonNull<i32>` must be non-null
error: the type `bool` does not permit being left uninitialized
--> $DIR/uninitialized-zeroed.rs:91:26
--> $DIR/uninitialized-zeroed.rs:106:26
|
LL | let _val: bool = MaybeUninit::uninit().assume_init();
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@ -432,5 +450,5 @@ LL | let _val: bool = MaybeUninit::uninit().assume_init();
|
= note: booleans must be either `true` or `false`
error: aborting due to 35 previous errors
error: aborting due to 36 previous errors

View file

@ -867,6 +867,7 @@ impl Config {
&self.target == name || // triple
util::matches_os(&self.target, name) || // target
util::matches_env(&self.target, name) || // env
self.target.ends_with(name) || // target and env
name == util::get_arch(&self.target) || // architecture
name == util::get_pointer_width(&self.target) || // pointer width
name == self.stage_id.split('-').next().unwrap() || // stage

View file

@ -119,6 +119,7 @@ fn contains_ignore_directive(can_contain: bool, contents: &str, check: &str) ->
// Update `can_contain` when changing this
if contents.contains(&format!("// ignore-tidy-{}", check))
|| contents.contains(&format!("# ignore-tidy-{}", check))
|| contents.contains(&format!("/* ignore-tidy-{} */", check))
{
Directive::Ignore(false)
} else {
@ -136,15 +137,37 @@ macro_rules! suppressible_tidy_err {
};
}
pub fn is_in(full_path: &Path, parent_folder_to_find: &str, folder_to_find: &str) -> bool {
if let Some(parent) = full_path.parent() {
if parent.file_name().map_or_else(
|| false,
|f| {
f.to_string_lossy() == folder_to_find
&& parent
.parent()
.and_then(|f| f.file_name())
.map_or_else(|| false, |f| f == parent_folder_to_find)
},
) {
true
} else {
is_in(parent, parent_folder_to_find, folder_to_find)
}
} else {
false
}
}
pub fn check(path: &Path, bad: &mut bool) {
super::walk(path, &mut super::filter_dirs, &mut |entry, contents| {
let file = entry.path();
let filename = file.file_name().unwrap().to_string_lossy();
let extensions = [".rs", ".py", ".js", ".sh", ".c", ".cpp", ".h", ".md"];
let extensions = [".rs", ".py", ".js", ".sh", ".c", ".cpp", ".h", ".md", ".css"];
if extensions.iter().all(|e| !filename.ends_with(e)) || filename.starts_with(".#") {
return;
}
let is_style_file = filename.ends_with(".css");
let under_rustfmt = filename.ends_with(".rs") &&
// This list should ideally be sourced from rustfmt.toml but we don't want to add a toml
// parser to tidy.
@ -161,6 +184,10 @@ pub fn check(path: &Path, bad: &mut bool) {
// currently), just the long error code explanation ones.
return;
}
if is_style_file && !is_in(file, "src", "librustdoc") {
// We only check CSS files in rustdoc.
return;
}
if contents.is_empty() {
tidy_error!(bad, "{}: empty file", file.display());
@ -172,8 +199,9 @@ pub fn check(path: &Path, bad: &mut bool) {
COLS
};
let can_contain =
contents.contains("// ignore-tidy-") || contents.contains("# ignore-tidy-");
let can_contain = contents.contains("// ignore-tidy-")
|| contents.contains("# ignore-tidy-")
|| contents.contains("/* ignore-tidy-");
// Enable testing ICE's that require specific (untidy)
// file formats easily eg. `issue-1234-ignore-tidy.rs`
if filename.contains("ignore-tidy") {
@ -208,12 +236,15 @@ pub fn check(path: &Path, bad: &mut bool) {
&format!("line longer than {} chars", max_columns)
);
}
if line.contains('\t') {
if !is_style_file && line.contains('\t') {
suppressible_tidy_err!(err, skip_tab, "tab character");
}
if line.ends_with(' ') || line.ends_with('\t') {
suppressible_tidy_err!(err, skip_end_whitespace, "trailing whitespace");
}
if is_style_file && line.starts_with(' ') {
err("CSS files use tabs for indent");
}
if line.contains('\r') {
suppressible_tidy_err!(err, skip_cr, "CR character");
}