Restructure trans_crate() so that codegen unit partitioning happens before creating LocalCrateContexts.
This commit is contained in:
parent
bb8c8c58d3
commit
bebcb285ad
4 changed files with 45 additions and 23 deletions
|
|
@ -639,7 +639,8 @@ pub fn run_passes(sess: &Session,
|
|||
}
|
||||
|
||||
// Sanity check
|
||||
assert!(trans.modules.len() == sess.opts.cg.codegen_units);
|
||||
assert!(trans.modules.len() == sess.opts.cg.codegen_units ||
|
||||
sess.opts.debugging_opts.incremental.is_some());
|
||||
|
||||
let tm = create_target_machine(sess);
|
||||
|
||||
|
|
|
|||
|
|
@ -81,7 +81,7 @@ use machine::{llalign_of_min, llsize_of, llsize_of_real};
|
|||
use meth;
|
||||
use mir;
|
||||
use monomorphize::{self, Instance};
|
||||
use partitioning::{self, PartitioningStrategy, InstantiationMode};
|
||||
use partitioning::{self, PartitioningStrategy, InstantiationMode, CodegenUnit};
|
||||
use symbol_names_test;
|
||||
use tvec;
|
||||
use type_::Type;
|
||||
|
|
@ -2186,7 +2186,8 @@ pub fn update_linkage(ccx: &CrateContext,
|
|||
// `llval` is a translation of an item defined in a separate
|
||||
// compilation unit. This only makes sense if there are at least
|
||||
// two compilation units.
|
||||
assert!(ccx.sess().opts.cg.codegen_units > 1);
|
||||
assert!(ccx.sess().opts.cg.codegen_units > 1 ||
|
||||
ccx.sess().opts.debugging_opts.incremental.is_some());
|
||||
// `llval` is a copy of something defined elsewhere, so use
|
||||
// `AvailableExternallyLinkage` to avoid duplicating code in the
|
||||
// output.
|
||||
|
|
@ -2723,12 +2724,15 @@ pub fn trans_crate<'tcx>(tcx: &TyCtxt<'tcx>,
|
|||
check_overflow,
|
||||
check_dropflag);
|
||||
|
||||
let codegen_units = tcx.sess.opts.cg.codegen_units;
|
||||
let codegen_units = collect_and_partition_translation_items(&shared_ccx);
|
||||
let codegen_unit_count = codegen_units.len();
|
||||
assert!(tcx.sess.opts.cg.codegen_units == codegen_unit_count ||
|
||||
tcx.sess.opts.debugging_opts.incremental.is_some());
|
||||
|
||||
let crate_context_list = CrateContextList::new(&shared_ccx, codegen_units);
|
||||
|
||||
{
|
||||
let ccx = crate_context_list.get_ccx(0);
|
||||
collect_translation_items(&ccx);
|
||||
|
||||
// Translate all items. See `TransModVisitor` for
|
||||
// details on why we walk in this particular way.
|
||||
|
|
@ -2818,7 +2822,7 @@ pub fn trans_crate<'tcx>(tcx: &TyCtxt<'tcx>,
|
|||
}
|
||||
}
|
||||
|
||||
if codegen_units > 1 {
|
||||
if codegen_unit_count > 1 {
|
||||
internalize_symbols(&crate_context_list,
|
||||
&reachable_symbols.iter().map(|x| &x[..]).collect());
|
||||
}
|
||||
|
|
@ -2910,10 +2914,11 @@ impl<'a, 'tcx, 'v> Visitor<'v> for TransItemsWithinModVisitor<'a, 'tcx> {
|
|||
}
|
||||
}
|
||||
|
||||
fn collect_translation_items<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>) {
|
||||
let time_passes = ccx.sess().time_passes();
|
||||
fn collect_and_partition_translation_items<'a, 'tcx>(scx: &SharedCrateContext<'a, 'tcx>)
|
||||
-> Vec<CodegenUnit<'tcx>> {
|
||||
let time_passes = scx.sess().time_passes();
|
||||
|
||||
let collection_mode = match ccx.sess().opts.debugging_opts.print_trans_items {
|
||||
let collection_mode = match scx.sess().opts.debugging_opts.print_trans_items {
|
||||
Some(ref s) => {
|
||||
let mode_string = s.to_lowercase();
|
||||
let mode_string = mode_string.trim();
|
||||
|
|
@ -2924,7 +2929,7 @@ fn collect_translation_items<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>) {
|
|||
let message = format!("Unknown codegen-item collection mode '{}'. \
|
||||
Falling back to 'lazy' mode.",
|
||||
mode_string);
|
||||
ccx.sess().warn(&message);
|
||||
scx.sess().warn(&message);
|
||||
}
|
||||
|
||||
TransItemCollectionMode::Lazy
|
||||
|
|
@ -2934,27 +2939,27 @@ fn collect_translation_items<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>) {
|
|||
};
|
||||
|
||||
let (items, reference_map) = time(time_passes, "translation item collection", || {
|
||||
collector::collect_crate_translation_items(ccx.shared(), collection_mode)
|
||||
collector::collect_crate_translation_items(scx, collection_mode)
|
||||
});
|
||||
|
||||
let strategy = if ccx.sess().opts.debugging_opts.incremental.is_some() {
|
||||
let strategy = if scx.sess().opts.debugging_opts.incremental.is_some() {
|
||||
PartitioningStrategy::PerModule
|
||||
} else {
|
||||
PartitioningStrategy::FixedUnitCount(ccx.sess().opts.cg.codegen_units)
|
||||
PartitioningStrategy::FixedUnitCount(scx.sess().opts.cg.codegen_units)
|
||||
};
|
||||
|
||||
let codegen_units = time(time_passes, "codegen unit partitioning", || {
|
||||
partitioning::partition(ccx.tcx(),
|
||||
partitioning::partition(scx.tcx(),
|
||||
items.iter().cloned(),
|
||||
strategy,
|
||||
&reference_map)
|
||||
});
|
||||
|
||||
if ccx.sess().opts.debugging_opts.print_trans_items.is_some() {
|
||||
if scx.sess().opts.debugging_opts.print_trans_items.is_some() {
|
||||
let mut item_to_cgus = HashMap::new();
|
||||
|
||||
for cgu in codegen_units {
|
||||
for (trans_item, linkage) in cgu.items {
|
||||
for cgu in &codegen_units {
|
||||
for (&trans_item, &linkage) in &cgu.items {
|
||||
item_to_cgus.entry(trans_item)
|
||||
.or_insert(Vec::new())
|
||||
.push((cgu.name.clone(), linkage));
|
||||
|
|
@ -2964,7 +2969,7 @@ fn collect_translation_items<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>) {
|
|||
let mut item_keys: Vec<_> = items
|
||||
.iter()
|
||||
.map(|i| {
|
||||
let mut output = i.to_string(ccx.tcx());
|
||||
let mut output = i.to_string(scx.tcx());
|
||||
output.push_str(" @@");
|
||||
let mut empty = Vec::new();
|
||||
let mut cgus = item_to_cgus.get_mut(i).unwrap_or(&mut empty);
|
||||
|
|
@ -3003,10 +3008,12 @@ fn collect_translation_items<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>) {
|
|||
println!("TRANS_ITEM {}", item);
|
||||
}
|
||||
|
||||
let mut ccx_map = ccx.translation_items().borrow_mut();
|
||||
let mut ccx_map = scx.translation_items().borrow_mut();
|
||||
|
||||
for cgi in items {
|
||||
ccx_map.insert(cgi, TransItemState::PredictedButNotGenerated);
|
||||
}
|
||||
}
|
||||
|
||||
codegen_units
|
||||
}
|
||||
|
|
|
|||
|
|
@ -28,6 +28,7 @@ use mir::CachedMir;
|
|||
use monomorphize::Instance;
|
||||
|
||||
use collector::{TransItem, TransItemState};
|
||||
use partitioning::CodegenUnit;
|
||||
use type_::{Type, TypeNames};
|
||||
use rustc::ty::subst::{Substs, VecPerParamSpace};
|
||||
use rustc::ty::{self, Ty, TyCtxt};
|
||||
|
|
@ -196,11 +197,12 @@ pub struct CrateContextList<'a, 'tcx: 'a> {
|
|||
impl<'a, 'tcx: 'a> CrateContextList<'a, 'tcx> {
|
||||
|
||||
pub fn new(shared_ccx: &'a SharedCrateContext<'a, 'tcx>,
|
||||
local_count: usize)
|
||||
codegen_units: Vec<CodegenUnit<'tcx>>)
|
||||
-> CrateContextList<'a, 'tcx> {
|
||||
CrateContextList {
|
||||
shared: shared_ccx,
|
||||
local_ccxs: (0..local_count).map(|index| {
|
||||
// FIXME: We don't actually use the codegen unit partitioning yet.
|
||||
local_ccxs: codegen_units.iter().map(|cgu| {
|
||||
// Append ".rs" to crate name as LLVM module identifier.
|
||||
//
|
||||
// LLVM code generator emits a ".file filename" directive
|
||||
|
|
@ -209,7 +211,7 @@ impl<'a, 'tcx: 'a> CrateContextList<'a, 'tcx> {
|
|||
// crashes if the module identifier is same as other symbols
|
||||
// such as a function name in the module.
|
||||
// 1. http://llvm.org/bugs/show_bug.cgi?id=11479
|
||||
let llmod_id = format!("{}.{}.rs", shared_ccx.link_meta.crate_name, index);
|
||||
let llmod_id = format!("{}.rs", cgu.name);
|
||||
LocalCrateContext::new(shared_ccx, &llmod_id[..])
|
||||
}).collect()
|
||||
}
|
||||
|
|
|
|||
|
|
@ -182,7 +182,19 @@ pub fn partition<'tcx, I>(tcx: &TyCtxt<'tcx>,
|
|||
// easily determine which declarations need to be placed within each one.
|
||||
let post_declarations = place_declarations(post_inlining, reference_map);
|
||||
|
||||
post_declarations.0
|
||||
let mut final_partitioning = post_declarations.0;
|
||||
|
||||
if final_partitioning.len() == 0 {
|
||||
// Some crates don't contain anything that will result in a translation
|
||||
// item. We still want to have at least one (empty) codegen unit in that
|
||||
// case.
|
||||
final_partitioning.push(CodegenUnit {
|
||||
name: token::intern_and_get_ident(&format!("{}.0", tcx.crate_name)[..]),
|
||||
items: FnvHashMap()
|
||||
});
|
||||
}
|
||||
|
||||
final_partitioning
|
||||
}
|
||||
|
||||
struct PreInliningPartitioning<'tcx> {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue