Skip to content
Permalink
Browse files

rustc_codegen_ssa: use FnAbi::of_instance wherever possible.

  • Loading branch information
eddyb committed Oct 29, 2019
1 parent 5b7d0f3 commit 4b68afe257603a61aa2eb8b8eaa394c5e7a246fe
@@ -4,15 +4,15 @@
//! and methods are represented as just a fn ptr and not a full
//! closure.

use crate::abi::FnAbi;
use crate::abi::{FnAbi, FnAbiLlvmExt};
use crate::attributes;
use crate::llvm;
use crate::context::CodegenCx;
use crate::value::Value;
use rustc_codegen_ssa::traits::*;

use rustc::ty::{self, TypeFoldable, Instance};
use rustc::ty::layout::{FnAbiExt, LayoutOf, HasTyCtxt};
use rustc::ty::{TypeFoldable, Instance};
use rustc::ty::layout::{FnAbiExt, HasTyCtxt};

/// Codegens a reference to a fn/method item, monomorphizing and
/// inlining as it goes.
@@ -37,14 +37,14 @@ pub fn get_fn(
return llfn;
}

let sig = instance.fn_sig(cx.tcx());
let sym = tcx.symbol_name(instance).name.as_str();
debug!("get_fn({:?}: {:?}) => {}", instance, sig, sym);
debug!("get_fn({:?}: {:?}) => {}", instance, instance.ty(cx.tcx()), sym);

let fn_abi = FnAbi::of_instance(cx, instance);

let llfn = if let Some(llfn) = cx.get_declared_value(&sym) {
// Create a fn pointer with the substituted signature.
let fn_ptr_ty = tcx.mk_fn_ptr(sig);
let llptrty = cx.backend_type(cx.layout_of(fn_ptr_ty));
// Create a fn pointer with the new signature.
let llptrty = fn_abi.ptr_to_llvm_type(cx);

// This is subtle and surprising, but sometimes we have to bitcast
// the resulting fn pointer. The reason has to do with external
@@ -77,15 +77,16 @@ pub fn get_fn(
llfn
}
} else {
let sig = tcx.normalize_erasing_late_bound_regions(ty::ParamEnv::reveal_all(), &sig);
let fn_abi = FnAbi::new(cx, sig, &[]);
let llfn = cx.declare_fn(&sym, &fn_abi);
debug!("get_fn: not casting pointer!");

if instance.def.is_inline(tcx) {
attributes::inline(cx, llfn, attributes::InlineAttr::Hint);
}
attributes::from_fn_attrs(cx, llfn, Some(instance.def.def_id()), sig.abi);
// FIXME(eddyb) avoid this `Instance::fn_sig` call.
// Perhaps store the relevant information in `FnAbi`?
let sig_abi = instance.fn_sig(cx.tcx()).abi();
attributes::from_fn_attrs(cx, llfn, Some(instance.def.def_id()), sig_abi);

let instance_def_id = instance.def_id();

@@ -16,7 +16,7 @@ use rustc::hir::CodegenFnAttrFlags;
use rustc::hir::def_id::{DefId, CrateNum, LOCAL_CRATE};
use rustc::ty::subst::{SubstsRef, GenericArgKind};

use crate::abi::Abi;
use crate::abi::{Abi, FnAbi};
use crate::common::CodegenCx;
use crate::builder::Builder;
use crate::value::Value;
@@ -280,7 +280,7 @@ impl DebugInfoMethods<'tcx> for CodegenCx<'ll, 'tcx> {
fn create_function_debug_context(
&self,
instance: Instance<'tcx>,
sig: ty::FnSig<'tcx>,
fn_abi: &FnAbi<'tcx, Ty<'tcx>>,
llfn: &'ll Value,
mir: &mir::Body<'_>,
) -> Option<FunctionDebugContext<&'ll DIScope>> {
@@ -308,6 +308,12 @@ impl DebugInfoMethods<'tcx> for CodegenCx<'ll, 'tcx> {
let file_metadata = file_metadata(self, &loc.file.name, def_id.krate);

let function_type_metadata = unsafe {
// FIXME(eddyb) avoid this `Instance::fn_sig` call, by
// rewriting `get_function_signature` to use `fn_abi` instead.
let sig = self.tcx().normalize_erasing_late_bound_regions(
ty::ParamEnv::reveal_all(),
&instance.fn_sig(self.tcx()),
);
let fn_signature = get_function_signature(self, sig);
llvm::LLVMRustDIBuilderCreateSubroutineType(DIB(self), file_metadata, fn_signature)
};
@@ -338,7 +344,7 @@ impl DebugInfoMethods<'tcx> for CodegenCx<'ll, 'tcx> {

let mut flags = DIFlags::FlagPrototyped;

if self.layout_of(sig.output()).abi.is_uninhabited() {
if fn_abi.ret.layout.abi.is_uninhabited() {
flags |= DIFlags::FlagNoReturn;
}

@@ -390,6 +396,7 @@ impl DebugInfoMethods<'tcx> for CodegenCx<'ll, 'tcx> {

return Some(fn_debug_context);

// FIXME(eddyb) rewrite this to be based on `FnAbi` instead of `FnSig`.
fn get_function_signature<'ll, 'tcx>(
cx: &CodegenCx<'ll, 'tcx>,
sig: ty::FnSig<'tcx>,
@@ -6,7 +6,7 @@ use crate::llvm;
use crate::type_of::LayoutLlvmExt;
use rustc::hir::def_id::{DefId, LOCAL_CRATE};
use rustc::mir::mono::{Linkage, Visibility};
use rustc::ty::{self, TypeFoldable, Instance};
use rustc::ty::{TypeFoldable, Instance};
use rustc::ty::layout::{FnAbiExt, LayoutOf, HasTyCtxt};
use rustc_codegen_ssa::traits::*;

@@ -43,12 +43,7 @@ impl PreDefineMethods<'tcx> for CodegenCx<'ll, 'tcx> {
assert!(!instance.substs.needs_infer() &&
!instance.substs.has_param_types());

let mono_sig = instance.fn_sig(self.tcx());
let mono_sig = self.tcx().normalize_erasing_late_bound_regions(
ty::ParamEnv::reveal_all(),
&mono_sig,
);
let fn_abi = FnAbi::new(self, mono_sig, &[]);
let fn_abi = FnAbi::of_instance(self, instance);
let lldecl = self.declare_fn(symbol_name, &fn_abi);
unsafe { llvm::LLVMRustSetLinkage(lldecl, base::linkage_to_llvm(linkage)) };
let attrs = self.tcx.codegen_fn_attrs(instance.def_id());
@@ -73,15 +68,18 @@ impl PreDefineMethods<'tcx> for CodegenCx<'ll, 'tcx> {
}
}

debug!("predefine_fn: mono_sig = {:?} instance = {:?}", mono_sig, instance);
debug!("predefine_fn: instance = {:?}", instance);
if instance.def.is_inline(self.tcx) {
attributes::inline(self, lldecl, attributes::InlineAttr::Hint);
}
// FIXME(eddyb) avoid this `Instance::fn_sig` call.
// Perhaps store the relevant information in `FnAbi`?
let mono_sig_abi = instance.fn_sig(self.tcx()).abi();
attributes::from_fn_attrs(
self,
lldecl,
Some(instance.def.def_id()),
mono_sig.abi,
mono_sig_abi,
);

self.instances.borrow_mut().insert(instance, lldecl);
@@ -129,13 +129,10 @@ pub fn codegen_mir<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>>(

let mir = cx.tcx().instance_mir(instance.def);

let sig = instance.fn_sig(cx.tcx());
let sig = cx.tcx().normalize_erasing_late_bound_regions(ty::ParamEnv::reveal_all(), &sig);
let fn_abi = FnAbi::new(cx, sig, &[]);
let fn_abi = FnAbi::of_instance(cx, instance);
debug!("fn_abi: {:?}", fn_abi);

let debug_context =
cx.create_function_debug_context(instance, sig, llfn, &mir);
let debug_context = cx.create_function_debug_context(instance, &fn_abi, llfn, &mir);

let mut bx = Bx::new_block(cx, llfn, "start");

@@ -2,8 +2,9 @@ use super::BackendTypes;
use crate::mir::debuginfo::{FunctionDebugContext, VariableKind};
use rustc::hir::def_id::CrateNum;
use rustc::mir;
use rustc::ty::{self, Ty, Instance};
use rustc::ty::{Ty, Instance};
use rustc::ty::layout::Size;
use rustc_target::abi::call::FnAbi;
use syntax::ast::Name;
use syntax_pos::{SourceFile, Span};

@@ -17,7 +18,7 @@ pub trait DebugInfoMethods<'tcx>: BackendTypes {
fn create_function_debug_context(
&self,
instance: Instance<'tcx>,
sig: ty::FnSig<'tcx>,
fn_abi: &FnAbi<'tcx, Ty<'tcx>>,
llfn: Self::Function,
mir: &mir::Body<'_>,
) -> Option<FunctionDebugContext<Self::DIScope>>;

0 comments on commit 4b68afe

Please sign in to comment.
You can’t perform that action at this time.