Use enum to distinguish dependency type

This commit is contained in:
Mateusz Mikuła 2020-06-03 00:56:27 +02:00
parent 638ebbc585
commit 961974fe03
3 changed files with 54 additions and 26 deletions

View File

@ -23,7 +23,7 @@ use crate::builder::Cargo;
use crate::dist; use crate::dist;
use crate::native; use crate::native;
use crate::util::{exe, is_dylib, symlink_dir}; use crate::util::{exe, is_dylib, symlink_dir};
use crate::{Compiler, GitRepo, Mode}; use crate::{Compiler, DependencyType, GitRepo, Mode};
use crate::builder::{Builder, Kind, RunConfig, ShouldRun, Step}; use crate::builder::{Builder, Kind, RunConfig, ShouldRun, Step};
use crate::cache::{Interned, INTERNER}; use crate::cache::{Interned, INTERNER};
@ -84,7 +84,7 @@ impl Step for Std {
return; return;
} }
target_deps.extend(copy_third_party_objects(builder, &compiler, target).into_iter()); target_deps.extend(copy_third_party_objects(builder, &compiler, target));
target_deps.extend(copy_self_contained_objects(builder, &compiler, target)); target_deps.extend(copy_self_contained_objects(builder, &compiler, target));
let mut cargo = builder.cargo(compiler, Mode::Std, target, "build"); let mut cargo = builder.cargo(compiler, Mode::Std, target, "build");
@ -116,7 +116,8 @@ fn copy_and_stamp(
libdir: &Path, libdir: &Path,
sourcedir: &Path, sourcedir: &Path,
name: &str, name: &str,
target_deps: &mut Vec<PathBuf>, target_deps: &mut Vec<(PathBuf, DependencyType)>,
dependency_type: DependencyType,
) { ) {
let target = libdir.join(name); let target = libdir.join(name);
builder.copy(&sourcedir.join(name), &target); builder.copy(&sourcedir.join(name), &target);
@ -129,7 +130,7 @@ fn copy_third_party_objects(
builder: &Builder<'_>, builder: &Builder<'_>,
compiler: &Compiler, compiler: &Compiler,
target: Interned<String>, target: Interned<String>,
) -> Vec<PathBuf> { ) -> Vec<(PathBuf, DependencyType)> {
let libdir = builder.sysroot_libdir(*compiler, target); let libdir = builder.sysroot_libdir(*compiler, target);
let mut target_deps = vec![]; let mut target_deps = vec![];
@ -148,13 +149,18 @@ fn copy_third_party_objects(
Path::new(&src), Path::new(&src),
"libunwind.a", "libunwind.a",
&mut target_deps, &mut target_deps,
DependencyType::Target,
); );
} }
if builder.config.sanitizers && compiler.stage != 0 { if builder.config.sanitizers && compiler.stage != 0 {
// The sanitizers are only copied in stage1 or above, // The sanitizers are only copied in stage1 or above,
// to avoid creating dependency on LLVM. // to avoid creating dependency on LLVM.
target_deps.extend(copy_sanitizers(builder, &compiler, target)); target_deps.extend(
copy_sanitizers(builder, &compiler, target)
.into_iter()
.map(|d| (d, DependencyType::Target)),
);
} }
target_deps target_deps
@ -165,7 +171,7 @@ fn copy_self_contained_objects(
builder: &Builder<'_>, builder: &Builder<'_>,
compiler: &Compiler, compiler: &Compiler,
target: Interned<String>, target: Interned<String>,
) -> Vec<PathBuf> { ) -> Vec<(PathBuf, DependencyType)> {
let libdir = builder.sysroot_libdir(*compiler, target); let libdir = builder.sysroot_libdir(*compiler, target);
let mut target_deps = vec![]; let mut target_deps = vec![];
@ -185,6 +191,7 @@ fn copy_self_contained_objects(
&srcdir, &srcdir,
obj, obj,
&mut target_deps, &mut target_deps,
DependencyType::TargetSelfContained,
); );
} }
} else if target.ends_with("-wasi") { } else if target.ends_with("-wasi") {
@ -195,13 +202,14 @@ fn copy_self_contained_objects(
&srcdir, &srcdir,
"crt1.o", "crt1.o",
&mut target_deps, &mut target_deps,
DependencyType::TargetSelfContained,
); );
} else if target.contains("windows-gnu") { } else if target.contains("windows-gnu") {
for obj in ["crt2.o", "dllcrt2.o"].iter() { for obj in ["crt2.o", "dllcrt2.o"].iter() {
let src = compiler_file(builder, builder.cc(target), target, obj); let src = compiler_file(builder, builder.cc(target), target, obj);
let target = libdir.join(obj); let target = libdir.join(obj);
builder.copy(&src, &target); builder.copy(&src, &target);
target_deps.push(target); target_deps.push((target, DependencyType::TargetSelfContained));
} }
} }
@ -370,7 +378,7 @@ pub struct StartupObjects {
} }
impl Step for StartupObjects { impl Step for StartupObjects {
type Output = Vec<PathBuf>; type Output = Vec<(PathBuf, DependencyType)>;
fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> { fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> {
run.path("src/rtstartup") run.path("src/rtstartup")
@ -389,7 +397,7 @@ impl Step for StartupObjects {
/// They don't require any library support as they're just plain old object /// They don't require any library support as they're just plain old object
/// files, so we just use the nightly snapshot compiler to always build them (as /// files, so we just use the nightly snapshot compiler to always build them (as
/// no other compilers are guaranteed to be available). /// no other compilers are guaranteed to be available).
fn run(self, builder: &Builder<'_>) -> Vec<PathBuf> { fn run(self, builder: &Builder<'_>) -> Vec<(PathBuf, DependencyType)> {
let for_compiler = self.compiler; let for_compiler = self.compiler;
let target = self.target; let target = self.target;
if !target.contains("windows-gnu") { if !target.contains("windows-gnu") {
@ -423,7 +431,7 @@ impl Step for StartupObjects {
let target = sysroot_dir.join((*file).to_string() + ".o"); let target = sysroot_dir.join((*file).to_string() + ".o");
builder.copy(dst_file, &target); builder.copy(dst_file, &target);
target_deps.push(target); target_deps.push((target, DependencyType::Target));
} }
target_deps target_deps
@ -838,8 +846,8 @@ pub fn add_to_sysroot(
) { ) {
t!(fs::create_dir_all(&sysroot_dst)); t!(fs::create_dir_all(&sysroot_dst));
t!(fs::create_dir_all(&sysroot_host_dst)); t!(fs::create_dir_all(&sysroot_host_dst));
for (path, host) in builder.read_stamp_file(stamp) { for (path, dependency_type) in builder.read_stamp_file(stamp) {
if host { if dependency_type == DependencyType::Host {
builder.copy(&path, &sysroot_host_dst.join(path.file_name().unwrap())); builder.copy(&path, &sysroot_host_dst.join(path.file_name().unwrap()));
} else { } else {
builder.copy(&path, &sysroot_dst.join(path.file_name().unwrap())); builder.copy(&path, &sysroot_dst.join(path.file_name().unwrap()));
@ -852,7 +860,7 @@ pub fn run_cargo(
cargo: Cargo, cargo: Cargo,
tail_args: Vec<String>, tail_args: Vec<String>,
stamp: &Path, stamp: &Path,
additional_target_deps: Vec<PathBuf>, additional_target_deps: Vec<(PathBuf, DependencyType)>,
is_check: bool, is_check: bool,
) -> Vec<PathBuf> { ) -> Vec<PathBuf> {
if builder.config.dry_run { if builder.config.dry_run {
@ -903,7 +911,7 @@ pub fn run_cargo(
if filename.starts_with(&host_root_dir) { if filename.starts_with(&host_root_dir) {
// Unless it's a proc macro used in the compiler // Unless it's a proc macro used in the compiler
if crate_types.iter().any(|t| t == "proc-macro") { if crate_types.iter().any(|t| t == "proc-macro") {
deps.push((filename.to_path_buf(), true)); deps.push((filename.to_path_buf(), DependencyType::Host));
} }
continue; continue;
} }
@ -911,7 +919,7 @@ pub fn run_cargo(
// If this was output in the `deps` dir then this is a precise file // If this was output in the `deps` dir then this is a precise file
// name (hash included) so we start tracking it. // name (hash included) so we start tracking it.
if filename.starts_with(&target_deps_dir) { if filename.starts_with(&target_deps_dir) {
deps.push((filename.to_path_buf(), false)); deps.push((filename.to_path_buf(), DependencyType::Target));
continue; continue;
} }
@ -963,17 +971,21 @@ pub fn run_cargo(
let candidate = format!("{}.lib", path_to_add); let candidate = format!("{}.lib", path_to_add);
let candidate = PathBuf::from(candidate); let candidate = PathBuf::from(candidate);
if candidate.exists() { if candidate.exists() {
deps.push((candidate, false)); deps.push((candidate, DependencyType::Target));
} }
} }
deps.push((path_to_add.into(), false)); deps.push((path_to_add.into(), DependencyType::Target));
} }
deps.extend(additional_target_deps.into_iter().map(|d| (d, false))); deps.extend(additional_target_deps);
deps.sort(); deps.sort();
let mut new_contents = Vec::new(); let mut new_contents = Vec::new();
for (dep, proc_macro) in deps.iter() { for (dep, dependency_type) in deps.iter() {
new_contents.extend(if *proc_macro { b"h" } else { b"t" }); new_contents.extend(match *dependency_type {
DependencyType::Host => b"h",
DependencyType::Target => b"t",
DependencyType::TargetSelfContained => b"s",
});
new_contents.extend(dep.to_str().unwrap().as_bytes()); new_contents.extend(dep.to_str().unwrap().as_bytes());
new_contents.extend(b"\0"); new_contents.extend(b"\0");
} }

View File

@ -22,7 +22,7 @@ use crate::channel;
use crate::compile; use crate::compile;
use crate::tool::{self, Tool}; use crate::tool::{self, Tool};
use crate::util::{exe, is_dylib, timeit}; use crate::util::{exe, is_dylib, timeit};
use crate::{Compiler, Mode, LLVM_TOOLS}; use crate::{Compiler, DependencyType, Mode, LLVM_TOOLS};
use time::{self, Timespec}; use time::{self, Timespec};
pub fn pkgname(builder: &Builder<'_>, component: &str) -> String { pub fn pkgname(builder: &Builder<'_>, component: &str) -> String {
@ -651,8 +651,8 @@ fn skip_host_target_lib(builder: &Builder<'_>, compiler: Compiler) -> bool {
fn copy_target_libs(builder: &Builder<'_>, target: &str, image: &Path, stamp: &Path) { fn copy_target_libs(builder: &Builder<'_>, target: &str, image: &Path, stamp: &Path) {
let dst = image.join("lib/rustlib").join(target).join("lib"); let dst = image.join("lib/rustlib").join(target).join("lib");
t!(fs::create_dir_all(&dst)); t!(fs::create_dir_all(&dst));
for (path, host) in builder.read_stamp_file(stamp) { for (path, dependency_type) in builder.read_stamp_file(stamp) {
if !host || builder.config.build == target { if dependency_type != DependencyType::Host || builder.config.build == target {
builder.copy(&path, &dst.join(path.file_name().unwrap())); builder.copy(&path, &dst.join(path.file_name().unwrap()));
} }
} }

View File

@ -280,6 +280,17 @@ impl Crate {
} }
} }
/// When building Rust various objects are handled differently.
#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord)]
pub enum DependencyType {
/// Libraries originating from proc-macros.
Host,
/// Typical Rust libraries.
Target,
/// Non Rust libraries and objects shipped to ease usage of certain targets.
TargetSelfContained,
}
/// The various "modes" of invoking Cargo. /// The various "modes" of invoking Cargo.
/// ///
/// These entries currently correspond to the various output directories of the /// These entries currently correspond to the various output directories of the
@ -1097,7 +1108,7 @@ impl Build {
ret ret
} }
fn read_stamp_file(&self, stamp: &Path) -> Vec<(PathBuf, bool)> { fn read_stamp_file(&self, stamp: &Path) -> Vec<(PathBuf, DependencyType)> {
if self.config.dry_run { if self.config.dry_run {
return Vec::new(); return Vec::new();
} }
@ -1110,9 +1121,14 @@ impl Build {
if part.is_empty() { if part.is_empty() {
continue; continue;
} }
let host = part[0] as char == 'h'; let dependency_type = match part[0] as char {
'h' => DependencyType::Host,
's' => DependencyType::TargetSelfContained,
't' => DependencyType::Target,
_ => unreachable!(),
};
let path = PathBuf::from(t!(str::from_utf8(&part[1..]))); let path = PathBuf::from(t!(str::from_utf8(&part[1..])));
paths.push((path, host)); paths.push((path, dependency_type));
} }
paths paths
} }