Generalized mono_item.rs and base.rs:codegen_instance
This commit is contained in:
parent
6a993fe353
commit
441a7c1092
@ -39,7 +39,7 @@ use rustc::middle::weak_lang_items;
|
|||||||
use rustc::mir::mono::{Linkage, Visibility, Stats, CodegenUnitNameBuilder};
|
use rustc::mir::mono::{Linkage, Visibility, Stats, CodegenUnitNameBuilder};
|
||||||
use rustc::middle::cstore::{EncodedMetadata};
|
use rustc::middle::cstore::{EncodedMetadata};
|
||||||
use rustc::ty::{self, Ty, TyCtxt};
|
use rustc::ty::{self, Ty, TyCtxt};
|
||||||
use rustc::ty::layout::{self, Align, TyLayout, LayoutOf, VariantIdx};
|
use rustc::ty::layout::{self, Align, TyLayout, LayoutOf, VariantIdx, HasTyCtxt};
|
||||||
use rustc::ty::query::Providers;
|
use rustc::ty::query::Providers;
|
||||||
use rustc::middle::cstore::{self, LinkagePreference};
|
use rustc::middle::cstore::{self, LinkagePreference};
|
||||||
use rustc::middle::exported_symbols;
|
use rustc::middle::exported_symbols;
|
||||||
@ -76,6 +76,7 @@ use interfaces::*;
|
|||||||
use std::any::Any;
|
use std::any::Any;
|
||||||
use std::cmp;
|
use std::cmp;
|
||||||
use std::ffi::CString;
|
use std::ffi::CString;
|
||||||
|
use std::marker;
|
||||||
use std::ops::{Deref, DerefMut};
|
use std::ops::{Deref, DerefMut};
|
||||||
use std::sync::mpsc;
|
use std::sync::mpsc;
|
||||||
use std::time::{Instant, Duration};
|
use std::time::{Instant, Duration};
|
||||||
@ -90,27 +91,29 @@ use mir::operand::OperandValue;
|
|||||||
|
|
||||||
use rustc_codegen_utils::check_for_rustc_errors_attr;
|
use rustc_codegen_utils::check_for_rustc_errors_attr;
|
||||||
|
|
||||||
pub struct StatRecorder<'a, 'll: 'a, 'tcx: 'll> {
|
pub struct StatRecorder<'a, 'tcx, Cx: 'a + CodegenMethods<'tcx>> {
|
||||||
cx: &'a CodegenCx<'ll, 'tcx>,
|
cx: &'a Cx,
|
||||||
name: Option<String>,
|
name: Option<String>,
|
||||||
istart: usize,
|
istart: usize,
|
||||||
|
_marker: marker::PhantomData<&'tcx ()>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl StatRecorder<'a, 'll, 'tcx> {
|
impl<'a, 'tcx, Cx: CodegenMethods<'tcx>> StatRecorder<'a, 'tcx, Cx> {
|
||||||
pub fn new(cx: &'a CodegenCx<'ll, 'tcx>, name: String) -> Self {
|
pub fn new(cx: &'a Cx, name: String) -> Self {
|
||||||
let istart = cx.stats.borrow().n_llvm_insns;
|
let istart = cx.stats().borrow().n_llvm_insns;
|
||||||
StatRecorder {
|
StatRecorder {
|
||||||
cx,
|
cx,
|
||||||
name: Some(name),
|
name: Some(name),
|
||||||
istart,
|
istart,
|
||||||
|
_marker: marker::PhantomData,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Drop for StatRecorder<'a, 'll, 'tcx> {
|
impl<'a, 'tcx, Cx: CodegenMethods<'tcx>> Drop for StatRecorder<'a, 'tcx, Cx> {
|
||||||
fn drop(&mut self) {
|
fn drop(&mut self) {
|
||||||
if self.cx.sess().codegen_stats() {
|
if self.cx.sess().codegen_stats() {
|
||||||
let mut stats = self.cx.stats.borrow_mut();
|
let mut stats = self.cx.stats().borrow_mut();
|
||||||
let iend = stats.n_llvm_insns;
|
let iend = stats.n_llvm_insns;
|
||||||
stats.fn_stats.push((self.name.take().unwrap(), iend - self.istart));
|
stats.fn_stats.push((self.name.take().unwrap(), iend - self.istart));
|
||||||
stats.n_fns += 1;
|
stats.n_fns += 1;
|
||||||
@ -449,10 +452,13 @@ pub fn memcpy_ty<'a, 'tcx: 'a, Builder: BuilderMethods<'a, 'tcx>>(
|
|||||||
bx.memcpy(dst, dst_align, src, src_align, bx.cx().const_usize(size), flags);
|
bx.memcpy(dst, dst_align, src, src_align, bx.cx().const_usize(size), flags);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn codegen_instance(cx: &CodegenCx<'_, 'tcx>, instance: Instance<'tcx>) {
|
pub fn codegen_instance<'a, 'tcx: 'a, Bx: BuilderMethods<'a, 'tcx>>(
|
||||||
|
cx: &'a Bx::CodegenCx,
|
||||||
|
instance: Instance<'tcx>,
|
||||||
|
) {
|
||||||
let _s = if cx.sess().codegen_stats() {
|
let _s = if cx.sess().codegen_stats() {
|
||||||
let mut instance_name = String::new();
|
let mut instance_name = String::new();
|
||||||
DefPathBasedNames::new(cx.tcx, true, true)
|
DefPathBasedNames::new(cx.tcx(), true, true)
|
||||||
.push_def_path(instance.def_id(), &mut instance_name);
|
.push_def_path(instance.def_id(), &mut instance_name);
|
||||||
Some(StatRecorder::new(cx, instance_name))
|
Some(StatRecorder::new(cx, instance_name))
|
||||||
} else {
|
} else {
|
||||||
@ -464,16 +470,16 @@ pub fn codegen_instance(cx: &CodegenCx<'_, 'tcx>, instance: Instance<'tcx>) {
|
|||||||
// release builds.
|
// release builds.
|
||||||
info!("codegen_instance({})", instance);
|
info!("codegen_instance({})", instance);
|
||||||
|
|
||||||
let sig = instance.fn_sig(cx.tcx);
|
let sig = instance.fn_sig(cx.tcx());
|
||||||
let sig = cx.tcx.normalize_erasing_late_bound_regions(ty::ParamEnv::reveal_all(), &sig);
|
let sig = cx.tcx().normalize_erasing_late_bound_regions(ty::ParamEnv::reveal_all(), &sig);
|
||||||
|
|
||||||
let lldecl = cx.instances.borrow().get(&instance).cloned().unwrap_or_else(||
|
let lldecl = cx.instances().borrow().get(&instance).cloned().unwrap_or_else(||
|
||||||
bug!("Instance `{:?}` not already declared", instance));
|
bug!("Instance `{:?}` not already declared", instance));
|
||||||
|
|
||||||
cx.stats.borrow_mut().n_closures += 1;
|
cx.stats().borrow_mut().n_closures += 1;
|
||||||
|
|
||||||
let mir = cx.tcx.instance_mir(instance.def);
|
let mir = cx.tcx().instance_mir(instance.def);
|
||||||
mir::codegen_mir::<Builder>(cx, lldecl, &mir, instance, sig);
|
mir::codegen_mir::<Bx>(cx, lldecl, &mir, instance, sig);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn set_link_section(llval: &Value, attrs: &CodegenFnAttrs) {
|
pub fn set_link_section(llval: &Value, attrs: &CodegenFnAttrs) {
|
||||||
|
@ -417,6 +417,14 @@ impl MiscMethods<'tcx> for CodegenCx<'ll, 'tcx> {
|
|||||||
fn check_overflow(&self) -> bool {
|
fn check_overflow(&self) -> bool {
|
||||||
self.check_overflow
|
self.check_overflow
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn stats(&self) -> &RefCell<Stats> {
|
||||||
|
&self.stats
|
||||||
|
}
|
||||||
|
|
||||||
|
fn codegen_unit(&self) -> &Arc<CodegenUnit<'tcx>> {
|
||||||
|
&self.codegen_unit
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl IntrinsicDeclarationMethods<'tcx> for CodegenCx<'b, 'tcx> {
|
impl IntrinsicDeclarationMethods<'tcx> for CodegenCx<'b, 'tcx> {
|
||||||
|
@ -9,6 +9,9 @@
|
|||||||
// except according to those terms.
|
// except according to those terms.
|
||||||
|
|
||||||
use super::backend::Backend;
|
use super::backend::Backend;
|
||||||
|
use monomorphize::Instance;
|
||||||
|
use rustc::hir::def_id::DefId;
|
||||||
|
use rustc::mir::mono::{Linkage, Visibility};
|
||||||
use rustc::ty;
|
use rustc::ty;
|
||||||
|
|
||||||
pub trait DeclareMethods<'tcx>: Backend<'tcx> {
|
pub trait DeclareMethods<'tcx>: Backend<'tcx> {
|
||||||
@ -22,3 +25,20 @@ pub trait DeclareMethods<'tcx>: Backend<'tcx> {
|
|||||||
fn get_declared_value(&self, name: &str) -> Option<Self::Value>;
|
fn get_declared_value(&self, name: &str) -> Option<Self::Value>;
|
||||||
fn get_defined_value(&self, name: &str) -> Option<Self::Value>;
|
fn get_defined_value(&self, name: &str) -> Option<Self::Value>;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub trait PreDefineMethods<'tcx>: Backend<'tcx> {
|
||||||
|
fn predefine_static(
|
||||||
|
&self,
|
||||||
|
def_id: DefId,
|
||||||
|
linkage: Linkage,
|
||||||
|
visibility: Visibility,
|
||||||
|
symbol_name: &str,
|
||||||
|
);
|
||||||
|
fn predefine_fn(
|
||||||
|
&self,
|
||||||
|
instance: Instance<'tcx>,
|
||||||
|
linkage: Linkage,
|
||||||
|
visibility: Visibility,
|
||||||
|
symbol_name: &str,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
@ -10,10 +10,13 @@
|
|||||||
|
|
||||||
use super::backend::Backend;
|
use super::backend::Backend;
|
||||||
use libc::c_uint;
|
use libc::c_uint;
|
||||||
|
use monomorphize::partitioning::CodegenUnit;
|
||||||
|
use rustc::mir::mono::Stats;
|
||||||
use rustc::session::Session;
|
use rustc::session::Session;
|
||||||
use rustc::ty::{self, Instance, Ty};
|
use rustc::ty::{self, Instance, Ty};
|
||||||
use rustc::util::nodemap::FxHashMap;
|
use rustc::util::nodemap::FxHashMap;
|
||||||
use std::cell::RefCell;
|
use std::cell::RefCell;
|
||||||
|
use std::sync::Arc;
|
||||||
|
|
||||||
pub trait MiscMethods<'tcx>: Backend<'tcx> {
|
pub trait MiscMethods<'tcx>: Backend<'tcx> {
|
||||||
fn vtables(
|
fn vtables(
|
||||||
@ -26,4 +29,6 @@ pub trait MiscMethods<'tcx>: Backend<'tcx> {
|
|||||||
fn eh_personality(&self) -> Self::Value;
|
fn eh_personality(&self) -> Self::Value;
|
||||||
fn eh_unwind_resume(&self) -> Self::Value;
|
fn eh_unwind_resume(&self) -> Self::Value;
|
||||||
fn sess(&self) -> &Session;
|
fn sess(&self) -> &Session;
|
||||||
|
fn stats(&self) -> &RefCell<Stats>;
|
||||||
|
fn codegen_unit(&self) -> &Arc<CodegenUnit<'tcx>>;
|
||||||
}
|
}
|
||||||
|
@ -26,7 +26,7 @@ pub use self::backend::{Backend, BackendTypes};
|
|||||||
pub use self::builder::BuilderMethods;
|
pub use self::builder::BuilderMethods;
|
||||||
pub use self::consts::ConstMethods;
|
pub use self::consts::ConstMethods;
|
||||||
pub use self::debuginfo::{DebugInfoBuilderMethods, DebugInfoMethods};
|
pub use self::debuginfo::{DebugInfoBuilderMethods, DebugInfoMethods};
|
||||||
pub use self::declare::DeclareMethods;
|
pub use self::declare::{DeclareMethods, PreDefineMethods};
|
||||||
pub use self::intrinsic::{IntrinsicCallMethods, IntrinsicDeclarationMethods};
|
pub use self::intrinsic::{IntrinsicCallMethods, IntrinsicDeclarationMethods};
|
||||||
pub use self::misc::MiscMethods;
|
pub use self::misc::MiscMethods;
|
||||||
pub use self::statics::StaticMethods;
|
pub use self::statics::StaticMethods;
|
||||||
@ -47,6 +47,7 @@ pub trait CodegenMethods<'tcx>:
|
|||||||
+ IntrinsicDeclarationMethods<'tcx>
|
+ IntrinsicDeclarationMethods<'tcx>
|
||||||
+ DeclareMethods<'tcx>
|
+ DeclareMethods<'tcx>
|
||||||
+ AsmMethods<'tcx>
|
+ AsmMethods<'tcx>
|
||||||
|
+ PreDefineMethods<'tcx>
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -61,6 +62,7 @@ impl<'tcx, T> CodegenMethods<'tcx> for T where
|
|||||||
+ IntrinsicDeclarationMethods<'tcx>
|
+ IntrinsicDeclarationMethods<'tcx>
|
||||||
+ DeclareMethods<'tcx>
|
+ DeclareMethods<'tcx>
|
||||||
+ AsmMethods<'tcx>
|
+ AsmMethods<'tcx>
|
||||||
|
+ PreDefineMethods<'tcx>
|
||||||
{}
|
{}
|
||||||
|
|
||||||
pub trait HasCodegen<'tcx>: Backend<'tcx> {
|
pub trait HasCodegen<'tcx>: Backend<'tcx> {
|
||||||
|
@ -25,24 +25,27 @@ use rustc::hir::def::Def;
|
|||||||
use rustc::hir::def_id::{DefId, LOCAL_CRATE};
|
use rustc::hir::def_id::{DefId, LOCAL_CRATE};
|
||||||
use rustc::mir::mono::{Linkage, Visibility};
|
use rustc::mir::mono::{Linkage, Visibility};
|
||||||
use rustc::ty::TypeFoldable;
|
use rustc::ty::TypeFoldable;
|
||||||
use rustc::ty::layout::LayoutOf;
|
use rustc::ty::layout::{LayoutOf, HasTyCtxt};
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
|
use builder::Builder;
|
||||||
use interfaces::*;
|
use interfaces::*;
|
||||||
|
|
||||||
pub use rustc::mir::mono::MonoItem;
|
pub use rustc::mir::mono::MonoItem;
|
||||||
|
|
||||||
pub use rustc_mir::monomorphize::item::MonoItemExt as BaseMonoItemExt;
|
pub use rustc_mir::monomorphize::item::MonoItemExt as BaseMonoItemExt;
|
||||||
|
|
||||||
pub trait MonoItemExt<'a, 'tcx>: fmt::Debug + BaseMonoItemExt<'a, 'tcx> {
|
pub trait MonoItemExt<'a, 'tcx: 'a, Bx: BuilderMethods<'a, 'tcx>> :
|
||||||
fn define(&self, cx: &CodegenCx<'a, 'tcx>) {
|
fmt::Debug + BaseMonoItemExt<'a, 'tcx>
|
||||||
|
{
|
||||||
|
fn define(&self, cx: &'a Bx::CodegenCx) {
|
||||||
debug!("BEGIN IMPLEMENTING '{} ({})' in cgu {}",
|
debug!("BEGIN IMPLEMENTING '{} ({})' in cgu {}",
|
||||||
self.to_string(cx.tcx),
|
self.to_string(cx.tcx()),
|
||||||
self.to_raw_string(),
|
self.to_raw_string(),
|
||||||
cx.codegen_unit.name());
|
cx.codegen_unit().name());
|
||||||
|
|
||||||
match *self.as_mono_item() {
|
match *self.as_mono_item() {
|
||||||
MonoItem::Static(def_id) => {
|
MonoItem::Static(def_id) => {
|
||||||
let tcx = cx.tcx;
|
let tcx = cx.tcx();
|
||||||
let is_mutable = match tcx.describe_def(def_id) {
|
let is_mutable = match tcx.describe_def(def_id) {
|
||||||
Some(Def::Static(_, is_mutable)) => is_mutable,
|
Some(Def::Static(_, is_mutable)) => is_mutable,
|
||||||
Some(other) => {
|
Some(other) => {
|
||||||
@ -55,7 +58,7 @@ pub trait MonoItemExt<'a, 'tcx>: fmt::Debug + BaseMonoItemExt<'a, 'tcx> {
|
|||||||
cx.codegen_static(def_id, is_mutable);
|
cx.codegen_static(def_id, is_mutable);
|
||||||
}
|
}
|
||||||
MonoItem::GlobalAsm(node_id) => {
|
MonoItem::GlobalAsm(node_id) => {
|
||||||
let item = cx.tcx.hir.expect_item(node_id);
|
let item = cx.tcx().hir.expect_item(node_id);
|
||||||
if let hir::ItemKind::GlobalAsm(ref ga) = item.node {
|
if let hir::ItemKind::GlobalAsm(ref ga) = item.node {
|
||||||
cx.codegen_global_asm(ga);
|
cx.codegen_global_asm(ga);
|
||||||
} else {
|
} else {
|
||||||
@ -63,43 +66,43 @@ pub trait MonoItemExt<'a, 'tcx>: fmt::Debug + BaseMonoItemExt<'a, 'tcx> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
MonoItem::Fn(instance) => {
|
MonoItem::Fn(instance) => {
|
||||||
base::codegen_instance(&cx, instance);
|
base::codegen_instance::<Bx>(&cx, instance);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
debug!("END IMPLEMENTING '{} ({})' in cgu {}",
|
debug!("END IMPLEMENTING '{} ({})' in cgu {}",
|
||||||
self.to_string(cx.tcx),
|
self.to_string(cx.tcx()),
|
||||||
self.to_raw_string(),
|
self.to_raw_string(),
|
||||||
cx.codegen_unit.name());
|
cx.codegen_unit().name());
|
||||||
}
|
}
|
||||||
|
|
||||||
fn predefine(&self,
|
fn predefine(&self,
|
||||||
cx: &CodegenCx<'a, 'tcx>,
|
cx: &'a Bx::CodegenCx,
|
||||||
linkage: Linkage,
|
linkage: Linkage,
|
||||||
visibility: Visibility) {
|
visibility: Visibility) {
|
||||||
debug!("BEGIN PREDEFINING '{} ({})' in cgu {}",
|
debug!("BEGIN PREDEFINING '{} ({})' in cgu {}",
|
||||||
self.to_string(cx.tcx),
|
self.to_string(cx.tcx()),
|
||||||
self.to_raw_string(),
|
self.to_raw_string(),
|
||||||
cx.codegen_unit.name());
|
cx.codegen_unit().name());
|
||||||
|
|
||||||
let symbol_name = self.symbol_name(cx.tcx).as_str();
|
let symbol_name = self.symbol_name(cx.tcx()).as_str();
|
||||||
|
|
||||||
debug!("symbol {}", &symbol_name);
|
debug!("symbol {}", &symbol_name);
|
||||||
|
|
||||||
match *self.as_mono_item() {
|
match *self.as_mono_item() {
|
||||||
MonoItem::Static(def_id) => {
|
MonoItem::Static(def_id) => {
|
||||||
predefine_static(cx, def_id, linkage, visibility, &symbol_name);
|
cx.predefine_static(def_id, linkage, visibility, &symbol_name);
|
||||||
}
|
}
|
||||||
MonoItem::Fn(instance) => {
|
MonoItem::Fn(instance) => {
|
||||||
predefine_fn(cx, instance, linkage, visibility, &symbol_name);
|
cx.predefine_fn(instance, linkage, visibility, &symbol_name);
|
||||||
}
|
}
|
||||||
MonoItem::GlobalAsm(..) => {}
|
MonoItem::GlobalAsm(..) => {}
|
||||||
}
|
}
|
||||||
|
|
||||||
debug!("END PREDEFINING '{} ({})' in cgu {}",
|
debug!("END PREDEFINING '{} ({})' in cgu {}",
|
||||||
self.to_string(cx.tcx),
|
self.to_string(cx.tcx()),
|
||||||
self.to_raw_string(),
|
self.to_raw_string(),
|
||||||
cx.codegen_unit.name());
|
cx.codegen_unit().name());
|
||||||
}
|
}
|
||||||
|
|
||||||
fn to_raw_string(&self) -> String {
|
fn to_raw_string(&self) -> String {
|
||||||
@ -119,68 +122,70 @@ pub trait MonoItemExt<'a, 'tcx>: fmt::Debug + BaseMonoItemExt<'a, 'tcx> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, 'tcx> MonoItemExt<'a, 'tcx> for MonoItem<'tcx> {}
|
impl MonoItemExt<'a, 'tcx, Builder<'a, 'll, 'tcx>> for MonoItem<'tcx> {}
|
||||||
|
|
||||||
fn predefine_static<'a, 'tcx>(cx: &CodegenCx<'a, 'tcx>,
|
impl PreDefineMethods<'tcx> for CodegenCx<'ll, 'tcx> {
|
||||||
def_id: DefId,
|
fn predefine_static(&self,
|
||||||
|
def_id: DefId,
|
||||||
|
linkage: Linkage,
|
||||||
|
visibility: Visibility,
|
||||||
|
symbol_name: &str) {
|
||||||
|
let instance = Instance::mono(self.tcx, def_id);
|
||||||
|
let ty = instance.ty(self.tcx);
|
||||||
|
let llty = self.layout_of(ty).llvm_type(self);
|
||||||
|
|
||||||
|
let g = self.define_global(symbol_name, llty).unwrap_or_else(|| {
|
||||||
|
self.sess().span_fatal(self.tcx.def_span(def_id),
|
||||||
|
&format!("symbol `{}` is already defined", symbol_name))
|
||||||
|
});
|
||||||
|
|
||||||
|
unsafe {
|
||||||
|
llvm::LLVMRustSetLinkage(g, base::linkage_to_llvm(linkage));
|
||||||
|
llvm::LLVMRustSetVisibility(g, base::visibility_to_llvm(visibility));
|
||||||
|
}
|
||||||
|
|
||||||
|
self.instances.borrow_mut().insert(instance, g);
|
||||||
|
}
|
||||||
|
|
||||||
|
fn predefine_fn(&self,
|
||||||
|
instance: Instance<'tcx>,
|
||||||
linkage: Linkage,
|
linkage: Linkage,
|
||||||
visibility: Visibility,
|
visibility: Visibility,
|
||||||
symbol_name: &str) {
|
symbol_name: &str) {
|
||||||
let instance = Instance::mono(cx.tcx, def_id);
|
assert!(!instance.substs.needs_infer() &&
|
||||||
let ty = instance.ty(cx.tcx);
|
!instance.substs.has_param_types());
|
||||||
let llty = cx.layout_of(ty).llvm_type(cx);
|
|
||||||
|
|
||||||
let g = cx.define_global(symbol_name, llty).unwrap_or_else(|| {
|
let mono_sig = instance.fn_sig(self.tcx());
|
||||||
cx.sess().span_fatal(cx.tcx.def_span(def_id),
|
let attrs = self.tcx.codegen_fn_attrs(instance.def_id());
|
||||||
&format!("symbol `{}` is already defined", symbol_name))
|
let lldecl = self.declare_fn(symbol_name, mono_sig);
|
||||||
});
|
unsafe { llvm::LLVMRustSetLinkage(lldecl, base::linkage_to_llvm(linkage)) };
|
||||||
|
base::set_link_section(lldecl, &attrs);
|
||||||
unsafe {
|
if linkage == Linkage::LinkOnceODR ||
|
||||||
llvm::LLVMRustSetLinkage(g, base::linkage_to_llvm(linkage));
|
linkage == Linkage::WeakODR {
|
||||||
llvm::LLVMRustSetVisibility(g, base::visibility_to_llvm(visibility));
|
llvm::SetUniqueComdat(self.llmod, lldecl);
|
||||||
}
|
|
||||||
|
|
||||||
cx.instances.borrow_mut().insert(instance, g);
|
|
||||||
}
|
|
||||||
|
|
||||||
fn predefine_fn<'a, 'tcx>(cx: &CodegenCx<'a, 'tcx>,
|
|
||||||
instance: Instance<'tcx>,
|
|
||||||
linkage: Linkage,
|
|
||||||
visibility: Visibility,
|
|
||||||
symbol_name: &str) {
|
|
||||||
assert!(!instance.substs.needs_infer() &&
|
|
||||||
!instance.substs.has_param_types());
|
|
||||||
|
|
||||||
let mono_sig = instance.fn_sig(cx.tcx);
|
|
||||||
let attrs = cx.tcx.codegen_fn_attrs(instance.def_id());
|
|
||||||
let lldecl = cx.declare_fn(symbol_name, mono_sig);
|
|
||||||
unsafe { llvm::LLVMRustSetLinkage(lldecl, base::linkage_to_llvm(linkage)) };
|
|
||||||
base::set_link_section(lldecl, &attrs);
|
|
||||||
if linkage == Linkage::LinkOnceODR ||
|
|
||||||
linkage == Linkage::WeakODR {
|
|
||||||
llvm::SetUniqueComdat(cx.llmod, lldecl);
|
|
||||||
}
|
|
||||||
|
|
||||||
// If we're compiling the compiler-builtins crate, e.g. the equivalent of
|
|
||||||
// compiler-rt, then we want to implicitly compile everything with hidden
|
|
||||||
// visibility as we're going to link this object all over the place but
|
|
||||||
// don't want the symbols to get exported.
|
|
||||||
if linkage != Linkage::Internal && linkage != Linkage::Private &&
|
|
||||||
cx.tcx.is_compiler_builtins(LOCAL_CRATE) {
|
|
||||||
unsafe {
|
|
||||||
llvm::LLVMRustSetVisibility(lldecl, llvm::Visibility::Hidden);
|
|
||||||
}
|
}
|
||||||
} else {
|
|
||||||
unsafe {
|
// If we're compiling the compiler-builtins crate, e.g. the equivalent of
|
||||||
llvm::LLVMRustSetVisibility(lldecl, base::visibility_to_llvm(visibility));
|
// compiler-rt, then we want to implicitly compile everything with hidden
|
||||||
|
// visibility as we're going to link this object all over the place but
|
||||||
|
// don't want the symbols to get exported.
|
||||||
|
if linkage != Linkage::Internal && linkage != Linkage::Private &&
|
||||||
|
self.tcx.is_compiler_builtins(LOCAL_CRATE) {
|
||||||
|
unsafe {
|
||||||
|
llvm::LLVMRustSetVisibility(lldecl, llvm::Visibility::Hidden);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
unsafe {
|
||||||
|
llvm::LLVMRustSetVisibility(lldecl, base::visibility_to_llvm(visibility));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
debug!("predefine_fn: mono_sig = {:?} instance = {:?}", mono_sig, instance);
|
debug!("predefine_fn: mono_sig = {:?} instance = {:?}", mono_sig, instance);
|
||||||
if instance.def.is_inline(cx.tcx) {
|
if instance.def.is_inline(self.tcx) {
|
||||||
attributes::inline(cx, lldecl, attributes::InlineAttr::Hint);
|
attributes::inline(self, lldecl, attributes::InlineAttr::Hint);
|
||||||
}
|
}
|
||||||
attributes::from_fn_attrs(cx, lldecl, Some(instance.def.def_id()));
|
attributes::from_fn_attrs(self, lldecl, Some(instance.def.def_id()));
|
||||||
|
|
||||||
cx.instances.borrow_mut().insert(instance, lldecl);
|
self.instances.borrow_mut().insert(instance, lldecl);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user