From 4ce20663f767c7d1610411b21ed31db3e9af21f4 Mon Sep 17 00:00:00 2001 From: bjorn3 Date: Sat, 3 Jul 2021 16:46:41 +0200 Subject: Don't use an allocator shim for `#[global_allocator]` This makes it possible to use liballoc/libstd in combination with `--emit obj` if you use `#[global_allocator]`. Making it work for the default libstd allocator would require weak functions, which are not well supported on all systems. --- compiler/rustc_codegen_llvm/src/allocator.rs | 136 ++++++++++++++------------- 1 file changed, 70 insertions(+), 66 deletions(-) (limited to 'compiler/rustc_codegen_llvm') diff --git a/compiler/rustc_codegen_llvm/src/allocator.rs b/compiler/rustc_codegen_llvm/src/allocator.rs index 668d9292705..acf44f3276d 100644 --- a/compiler/rustc_codegen_llvm/src/allocator.rs +++ b/compiler/rustc_codegen_llvm/src/allocator.rs @@ -1,10 +1,11 @@ use crate::attributes; use libc::c_uint; -use rustc_ast::expand::allocator::{AllocatorKind, AllocatorTy, ALLOCATOR_METHODS}; +use rustc_ast::expand::allocator::{ + alloc_error_handler_name, AllocatorKind, AllocatorTy, ALLOCATOR_METHODS, +}; use rustc_middle::bug; use rustc_middle::ty::TyCtxt; use rustc_session::config::{DebugInfo, OomStrategy}; -use rustc_span::symbol::sym; use crate::debuginfo; use crate::llvm::{self, False, True}; @@ -29,75 +30,78 @@ pub(crate) unsafe fn codegen( let i8p = llvm::LLVMPointerType(i8, 0); let void = llvm::LLVMVoidTypeInContext(llcx); - for method in ALLOCATOR_METHODS { - let mut args = Vec::with_capacity(method.inputs.len()); - for ty in method.inputs.iter() { - match *ty { - AllocatorTy::Layout => { - args.push(usize); // size - args.push(usize); // align + if kind == AllocatorKind::Default { + for method in ALLOCATOR_METHODS { + let mut args = Vec::with_capacity(method.inputs.len()); + for ty in method.inputs.iter() { + match *ty { + AllocatorTy::Layout => { + args.push(usize); // size + args.push(usize); // align + } + AllocatorTy::Ptr => args.push(i8p), + AllocatorTy::Usize => args.push(usize), + + AllocatorTy::ResultPtr | AllocatorTy::Unit => panic!("invalid allocator arg"), } - AllocatorTy::Ptr => args.push(i8p), - AllocatorTy::Usize => args.push(usize), - - AllocatorTy::ResultPtr | AllocatorTy::Unit => panic!("invalid allocator arg"), } - } - let output = match method.output { - AllocatorTy::ResultPtr => Some(i8p), - AllocatorTy::Unit => None, + let output = match method.output { + AllocatorTy::ResultPtr => Some(i8p), + AllocatorTy::Unit => None, - AllocatorTy::Layout | AllocatorTy::Usize | AllocatorTy::Ptr => { - panic!("invalid allocator output") + AllocatorTy::Layout | AllocatorTy::Usize | AllocatorTy::Ptr => { + panic!("invalid allocator output") + } + }; + let ty = llvm::LLVMFunctionType( + output.unwrap_or(void), + args.as_ptr(), + args.len() as c_uint, + False, + ); + let name = format!("__rust_{}", method.name); + let llfn = + llvm::LLVMRustGetOrInsertFunction(llmod, name.as_ptr().cast(), name.len(), ty); + + if tcx.sess.target.default_hidden_visibility { + llvm::LLVMRustSetVisibility(llfn, llvm::Visibility::Hidden); + } + if tcx.sess.must_emit_unwind_tables() { + let uwtable = attributes::uwtable_attr(llcx); + attributes::apply_to_llfn(llfn, llvm::AttributePlace::Function, &[uwtable]); } - }; - let ty = llvm::LLVMFunctionType( - output.unwrap_or(void), - args.as_ptr(), - args.len() as c_uint, - False, - ); - let name = format!("__rust_{}", method.name); - let llfn = llvm::LLVMRustGetOrInsertFunction(llmod, name.as_ptr().cast(), name.len(), ty); - - if tcx.sess.target.default_hidden_visibility { - llvm::LLVMRustSetVisibility(llfn, llvm::Visibility::Hidden); - } - if tcx.sess.must_emit_unwind_tables() { - let uwtable = attributes::uwtable_attr(llcx); - attributes::apply_to_llfn(llfn, llvm::AttributePlace::Function, &[uwtable]); - } - let callee = kind.fn_name(method.name); - let callee = - llvm::LLVMRustGetOrInsertFunction(llmod, callee.as_ptr().cast(), callee.len(), ty); - llvm::LLVMRustSetVisibility(callee, llvm::Visibility::Hidden); - - let llbb = llvm::LLVMAppendBasicBlockInContext(llcx, llfn, "entry\0".as_ptr().cast()); - - let llbuilder = llvm::LLVMCreateBuilderInContext(llcx); - llvm::LLVMPositionBuilderAtEnd(llbuilder, llbb); - let args = args - .iter() - .enumerate() - .map(|(i, _)| llvm::LLVMGetParam(llfn, i as c_uint)) - .collect::>(); - let ret = llvm::LLVMRustBuildCall( - llbuilder, - ty, - callee, - args.as_ptr(), - args.len() as c_uint, - [].as_ptr(), - 0 as c_uint, - ); - llvm::LLVMSetTailCall(ret, True); - if output.is_some() { - llvm::LLVMBuildRet(llbuilder, ret); - } else { - llvm::LLVMBuildRetVoid(llbuilder); + let callee = AllocatorKind::Default.fn_name(method.name); + let callee = + llvm::LLVMRustGetOrInsertFunction(llmod, callee.as_ptr().cast(), callee.len(), ty); + llvm::LLVMRustSetVisibility(callee, llvm::Visibility::Hidden); + + let llbb = llvm::LLVMAppendBasicBlockInContext(llcx, llfn, "entry\0".as_ptr().cast()); + + let llbuilder = llvm::LLVMCreateBuilderInContext(llcx); + llvm::LLVMPositionBuilderAtEnd(llbuilder, llbb); + let args = args + .iter() + .enumerate() + .map(|(i, _)| llvm::LLVMGetParam(llfn, i as c_uint)) + .collect::>(); + let ret = llvm::LLVMRustBuildCall( + llbuilder, + ty, + callee, + args.as_ptr(), + args.len() as c_uint, + [].as_ptr(), + 0 as c_uint, + ); + llvm::LLVMSetTailCall(ret, True); + if output.is_some() { + llvm::LLVMBuildRet(llbuilder, ret); + } else { + llvm::LLVMBuildRetVoid(llbuilder); + } + llvm::LLVMDisposeBuilder(llbuilder); } - llvm::LLVMDisposeBuilder(llbuilder); } // rust alloc error handler @@ -118,7 +122,7 @@ pub(crate) unsafe fn codegen( attributes::apply_to_llfn(llfn, llvm::AttributePlace::Function, &[uwtable]); } - let callee = alloc_error_handler_kind.fn_name(sym::oom); + let callee = alloc_error_handler_name(alloc_error_handler_kind); let callee = llvm::LLVMRustGetOrInsertFunction(llmod, callee.as_ptr().cast(), callee.len(), ty); // -> ! DIFlagNoReturn attributes::apply_to_llfn(callee, llvm::AttributePlace::Function, &[no_return]); -- cgit 1.4.1-3-g733a5 From 6ba7c5db079132b5d85112083691d4203a6b761c Mon Sep 17 00:00:00 2001 From: bjorn3 Date: Sat, 3 Jul 2021 17:50:53 +0200 Subject: Split AllocatorKind::fn_name in global_fn_name and default_fn_name --- compiler/rustc_ast/src/expand/allocator.rs | 13 ++++++------- compiler/rustc_builtin_macros/src/global_allocator.rs | 4 ++-- compiler/rustc_codegen_cranelift/src/allocator.rs | 4 ++-- compiler/rustc_codegen_gcc/src/allocator.rs | 4 ++-- compiler/rustc_codegen_llvm/src/allocator.rs | 4 ++-- compiler/rustc_metadata/src/creader.rs | 6 +++--- 6 files changed, 17 insertions(+), 18 deletions(-) (limited to 'compiler/rustc_codegen_llvm') diff --git a/compiler/rustc_ast/src/expand/allocator.rs b/compiler/rustc_ast/src/expand/allocator.rs index c7ca66bc841..73e79d4441c 100644 --- a/compiler/rustc_ast/src/expand/allocator.rs +++ b/compiler/rustc_ast/src/expand/allocator.rs @@ -6,13 +6,12 @@ pub enum AllocatorKind { Default, } -impl AllocatorKind { - pub fn fn_name(&self, base: Symbol) -> String { - match *self { - AllocatorKind::Global => format!("__rust_{base}"), - AllocatorKind::Default => format!("__rdl_{base}"), - } - } +pub fn global_fn_name(base: Symbol) -> String { + format!("__rust_{base}") +} + +pub fn default_fn_name(base: Symbol) -> String { + format!("__rdl_{base}") } pub fn alloc_error_handler_name(alloc_error_handler_kind: AllocatorKind) -> &'static str { diff --git a/compiler/rustc_builtin_macros/src/global_allocator.rs b/compiler/rustc_builtin_macros/src/global_allocator.rs index 1dd6a700e65..f0d378d12f7 100644 --- a/compiler/rustc_builtin_macros/src/global_allocator.rs +++ b/compiler/rustc_builtin_macros/src/global_allocator.rs @@ -1,7 +1,7 @@ use crate::util::check_builtin_macro_attribute; use rustc_ast::expand::allocator::{ - AllocatorKind, AllocatorMethod, AllocatorTy, ALLOCATOR_METHODS, + global_fn_name, AllocatorMethod, AllocatorTy, ALLOCATOR_METHODS, }; use rustc_ast::ptr::P; use rustc_ast::{self as ast, AttrVec, Expr, FnHeader, FnSig, Generics, Param, StmtKind}; @@ -90,7 +90,7 @@ impl AllocFnFactory<'_, '_> { })); let item = self.cx.item( self.span, - Ident::from_str_and_span(&AllocatorKind::Global.fn_name(method.name), self.span), + Ident::from_str_and_span(&global_fn_name(method.name), self.span), self.attrs(), kind, ); diff --git a/compiler/rustc_codegen_cranelift/src/allocator.rs b/compiler/rustc_codegen_cranelift/src/allocator.rs index ef69d3f7800..3b74050250b 100644 --- a/compiler/rustc_codegen_cranelift/src/allocator.rs +++ b/compiler/rustc_codegen_cranelift/src/allocator.rs @@ -4,7 +4,7 @@ use crate::prelude::*; use rustc_ast::expand::allocator::{ - alloc_error_handler_name, AllocatorKind, AllocatorTy, ALLOCATOR_METHODS, + alloc_error_handler_name, default_fn_name, AllocatorKind, AllocatorTy, ALLOCATOR_METHODS, }; use rustc_codegen_ssa::base::allocator_kind_for_codegen; use rustc_session::config::OomStrategy; @@ -69,7 +69,7 @@ fn codegen_inner( unwind_context, sig, &format!("__rust_{}", method.name), - &AllocatorKind::Default.fn_name(method.name), + &default_fn_name(method.name), ); } } diff --git a/compiler/rustc_codegen_gcc/src/allocator.rs b/compiler/rustc_codegen_gcc/src/allocator.rs index f4105b91e98..fe143aaad5f 100644 --- a/compiler/rustc_codegen_gcc/src/allocator.rs +++ b/compiler/rustc_codegen_gcc/src/allocator.rs @@ -2,7 +2,7 @@ use gccjit::FnAttribute; use gccjit::{FunctionType, GlobalKind, ToRValue}; use rustc_ast::expand::allocator::{ - alloc_error_handler_name, AllocatorKind, AllocatorTy, ALLOCATOR_METHODS, + alloc_error_handler_name, default_fn_name, AllocatorKind, AllocatorTy, ALLOCATOR_METHODS, }; use rustc_middle::bug; use rustc_middle::ty::TyCtxt; @@ -61,7 +61,7 @@ pub(crate) unsafe fn codegen(tcx: TyCtxt<'_>, mods: &mut GccContext, _module_nam // TODO(antoyo): emit unwind tables. } - let callee = AllocatorKind::Default.fn_name(method.name); + let callee = default_fn_name(method.name); let args: Vec<_> = types.iter().enumerate() .map(|(index, typ)| context.new_parameter(None, *typ, &format!("param{}", index))) .collect(); diff --git a/compiler/rustc_codegen_llvm/src/allocator.rs b/compiler/rustc_codegen_llvm/src/allocator.rs index acf44f3276d..c2484681072 100644 --- a/compiler/rustc_codegen_llvm/src/allocator.rs +++ b/compiler/rustc_codegen_llvm/src/allocator.rs @@ -1,7 +1,7 @@ use crate::attributes; use libc::c_uint; use rustc_ast::expand::allocator::{ - alloc_error_handler_name, AllocatorKind, AllocatorTy, ALLOCATOR_METHODS, + alloc_error_handler_name, default_fn_name, AllocatorKind, AllocatorTy, ALLOCATOR_METHODS, }; use rustc_middle::bug; use rustc_middle::ty::TyCtxt; @@ -71,7 +71,7 @@ pub(crate) unsafe fn codegen( attributes::apply_to_llfn(llfn, llvm::AttributePlace::Function, &[uwtable]); } - let callee = AllocatorKind::Default.fn_name(method.name); + let callee = default_fn_name(method.name); let callee = llvm::LLVMRustGetOrInsertFunction(llmod, callee.as_ptr().cast(), callee.len(), ty); llvm::LLVMRustSetVisibility(callee, llvm::Visibility::Hidden); diff --git a/compiler/rustc_metadata/src/creader.rs b/compiler/rustc_metadata/src/creader.rs index e6e7d25773e..07a9593fee8 100644 --- a/compiler/rustc_metadata/src/creader.rs +++ b/compiler/rustc_metadata/src/creader.rs @@ -4,7 +4,7 @@ use crate::errors; use crate::locator::{CrateError, CrateLocator, CratePaths}; use crate::rmeta::{CrateDep, CrateMetadata, CrateNumMap, CrateRoot, MetadataBlob}; -use rustc_ast::expand::allocator::AllocatorKind; +use rustc_ast::expand::allocator::{alloc_error_handler_name, global_fn_name, AllocatorKind}; use rustc_ast::{self as ast, *}; use rustc_data_structures::fx::FxHashSet; use rustc_data_structures::svh::Svh; @@ -1044,7 +1044,7 @@ fn global_allocator_spans(krate: &ast::Crate) -> Vec { } } - let name = Symbol::intern(&AllocatorKind::Global.fn_name(sym::alloc)); + let name = Symbol::intern(&global_fn_name(sym::alloc)); let mut f = Finder { name, spans: Vec::new() }; visit::walk_crate(&mut f, krate); f.spans @@ -1066,7 +1066,7 @@ fn alloc_error_handler_spans(krate: &ast::Crate) -> Vec { } } - let name = Symbol::intern(&AllocatorKind::Global.fn_name(sym::oom)); + let name = Symbol::intern(alloc_error_handler_name(AllocatorKind::Global)); let mut f = Finder { name, spans: Vec::new() }; visit::walk_crate(&mut f, krate); f.spans -- cgit 1.4.1-3-g733a5 From 145b0574efd63603f35beda4d6b69933c8a01c1f Mon Sep 17 00:00:00 2001 From: bjorn3 Date: Tue, 6 Jul 2021 18:56:01 +0200 Subject: Use global_fn_name instead of format! --- compiler/rustc_codegen_cranelift/src/allocator.rs | 5 +++-- compiler/rustc_codegen_gcc/src/allocator.rs | 5 +++-- compiler/rustc_codegen_llvm/src/allocator.rs | 5 +++-- 3 files changed, 9 insertions(+), 6 deletions(-) (limited to 'compiler/rustc_codegen_llvm') diff --git a/compiler/rustc_codegen_cranelift/src/allocator.rs b/compiler/rustc_codegen_cranelift/src/allocator.rs index 3b74050250b..c27971897a0 100644 --- a/compiler/rustc_codegen_cranelift/src/allocator.rs +++ b/compiler/rustc_codegen_cranelift/src/allocator.rs @@ -4,7 +4,8 @@ use crate::prelude::*; use rustc_ast::expand::allocator::{ - alloc_error_handler_name, default_fn_name, AllocatorKind, AllocatorTy, ALLOCATOR_METHODS, + alloc_error_handler_name, default_fn_name, global_fn_name, AllocatorKind, AllocatorTy, + ALLOCATOR_METHODS, }; use rustc_codegen_ssa::base::allocator_kind_for_codegen; use rustc_session::config::OomStrategy; @@ -68,7 +69,7 @@ fn codegen_inner( module, unwind_context, sig, - &format!("__rust_{}", method.name), + &global_fn_name(method.name), &default_fn_name(method.name), ); } diff --git a/compiler/rustc_codegen_gcc/src/allocator.rs b/compiler/rustc_codegen_gcc/src/allocator.rs index fe143aaad5f..ff68de8c8f1 100644 --- a/compiler/rustc_codegen_gcc/src/allocator.rs +++ b/compiler/rustc_codegen_gcc/src/allocator.rs @@ -2,7 +2,8 @@ use gccjit::FnAttribute; use gccjit::{FunctionType, GlobalKind, ToRValue}; use rustc_ast::expand::allocator::{ - alloc_error_handler_name, default_fn_name, AllocatorKind, AllocatorTy, ALLOCATOR_METHODS, + alloc_error_handler_name, default_fn_name, global_fn_name, AllocatorKind, AllocatorTy, + ALLOCATOR_METHODS, }; use rustc_middle::bug; use rustc_middle::ty::TyCtxt; @@ -46,7 +47,7 @@ pub(crate) unsafe fn codegen(tcx: TyCtxt<'_>, mods: &mut GccContext, _module_nam panic!("invalid allocator output") } }; - let name = format!("__rust_{}", method.name); + let name = global_fn_name(method.name); let args: Vec<_> = types.iter().enumerate() .map(|(index, typ)| context.new_parameter(None, *typ, &format!("param{}", index))) diff --git a/compiler/rustc_codegen_llvm/src/allocator.rs b/compiler/rustc_codegen_llvm/src/allocator.rs index c2484681072..564e996cdf3 100644 --- a/compiler/rustc_codegen_llvm/src/allocator.rs +++ b/compiler/rustc_codegen_llvm/src/allocator.rs @@ -1,7 +1,8 @@ use crate::attributes; use libc::c_uint; use rustc_ast::expand::allocator::{ - alloc_error_handler_name, default_fn_name, AllocatorKind, AllocatorTy, ALLOCATOR_METHODS, + alloc_error_handler_name, default_fn_name, global_fn_name, AllocatorKind, AllocatorTy, + ALLOCATOR_METHODS, }; use rustc_middle::bug; use rustc_middle::ty::TyCtxt; @@ -59,7 +60,7 @@ pub(crate) unsafe fn codegen( args.len() as c_uint, False, ); - let name = format!("__rust_{}", method.name); + let name = global_fn_name(method.name); let llfn = llvm::LLVMRustGetOrInsertFunction(llmod, name.as_ptr().cast(), name.len(), ty); -- cgit 1.4.1-3-g733a5 From 66982a383b6f7d3a933fc6896202632bee7161a4 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sat, 10 Sep 2022 11:33:44 +0000 Subject: Prevent insta-stable no alloc shim support You will need to add the following as replacement for the old __rust_* definitions when not using the alloc shim. #[no_mangle] static __rust_no_alloc_shim_is_unstable: u8 = 0; --- compiler/rustc_ast/src/expand/allocator.rs | 2 ++ compiler/rustc_codegen_cranelift/src/allocator.rs | 9 ++++++++- compiler/rustc_codegen_gcc/src/allocator.rs | 7 ++++++- compiler/rustc_codegen_llvm/src/allocator.rs | 10 +++++++++- compiler/rustc_codegen_ssa/src/back/symbol_export.rs | 13 ++++++++++++- library/alloc/src/alloc.rs | 12 +++++++++++- tests/codegen/alloc-optimisation.rs | 3 ++- tests/codegen/vec-optimizes-away.rs | 3 ++- 8 files changed, 52 insertions(+), 7 deletions(-) (limited to 'compiler/rustc_codegen_llvm') diff --git a/compiler/rustc_ast/src/expand/allocator.rs b/compiler/rustc_ast/src/expand/allocator.rs index 73e79d4441c..e87f6e820a1 100644 --- a/compiler/rustc_ast/src/expand/allocator.rs +++ b/compiler/rustc_ast/src/expand/allocator.rs @@ -21,6 +21,8 @@ pub fn alloc_error_handler_name(alloc_error_handler_kind: AllocatorKind) -> &'st } } +pub const NO_ALLOC_SHIM_IS_UNSTABLE: &str = "__rust_no_alloc_shim_is_unstable"; + pub enum AllocatorTy { Layout, Ptr, diff --git a/compiler/rustc_codegen_cranelift/src/allocator.rs b/compiler/rustc_codegen_cranelift/src/allocator.rs index c27971897a0..d4b1ae2b613 100644 --- a/compiler/rustc_codegen_cranelift/src/allocator.rs +++ b/compiler/rustc_codegen_cranelift/src/allocator.rs @@ -5,7 +5,7 @@ use crate::prelude::*; use rustc_ast::expand::allocator::{ alloc_error_handler_name, default_fn_name, global_fn_name, AllocatorKind, AllocatorTy, - ALLOCATOR_METHODS, + ALLOCATOR_METHODS, NO_ALLOC_SHIM_IS_UNSTABLE, }; use rustc_codegen_ssa::base::allocator_kind_for_codegen; use rustc_session::config::OomStrategy; @@ -94,4 +94,11 @@ fn codegen_inner( let val = oom_strategy.should_panic(); data_ctx.define(Box::new([val])); module.define_data(data_id, &data_ctx).unwrap(); + + let data_id = + module.declare_data(NO_ALLOC_SHIM_IS_UNSTABLE, Linkage::Export, false, false).unwrap(); + let mut data_ctx = DataContext::new(); + data_ctx.set_align(1); + data_ctx.define(Box::new([0])); + module.define_data(data_id, &data_ctx).unwrap(); } diff --git a/compiler/rustc_codegen_gcc/src/allocator.rs b/compiler/rustc_codegen_gcc/src/allocator.rs index ff68de8c8f1..13f88192bbc 100644 --- a/compiler/rustc_codegen_gcc/src/allocator.rs +++ b/compiler/rustc_codegen_gcc/src/allocator.rs @@ -3,7 +3,7 @@ use gccjit::FnAttribute; use gccjit::{FunctionType, GlobalKind, ToRValue}; use rustc_ast::expand::allocator::{ alloc_error_handler_name, default_fn_name, global_fn_name, AllocatorKind, AllocatorTy, - ALLOCATOR_METHODS, + ALLOCATOR_METHODS, NO_ALLOC_SHIM_IS_UNSTABLE, }; use rustc_middle::bug; use rustc_middle::ty::TyCtxt; @@ -127,4 +127,9 @@ pub(crate) unsafe fn codegen(tcx: TyCtxt<'_>, mods: &mut GccContext, _module_nam let value = tcx.sess.opts.unstable_opts.oom.should_panic(); let value = context.new_rvalue_from_int(i8, value as i32); global.global_set_initializer_rvalue(value); + + let name = NO_ALLOC_SHIM_IS_UNSTABLE.to_string(); + let global = context.new_global(None, GlobalKind::Exported, i8, name); + let value = context.new_rvalue_from_int(i8, 0); + global.global_set_initializer_rvalue(value); } diff --git a/compiler/rustc_codegen_llvm/src/allocator.rs b/compiler/rustc_codegen_llvm/src/allocator.rs index 564e996cdf3..a57508815d6 100644 --- a/compiler/rustc_codegen_llvm/src/allocator.rs +++ b/compiler/rustc_codegen_llvm/src/allocator.rs @@ -2,7 +2,7 @@ use crate::attributes; use libc::c_uint; use rustc_ast::expand::allocator::{ alloc_error_handler_name, default_fn_name, global_fn_name, AllocatorKind, AllocatorTy, - ALLOCATOR_METHODS, + ALLOCATOR_METHODS, NO_ALLOC_SHIM_IS_UNSTABLE, }; use rustc_middle::bug; use rustc_middle::ty::TyCtxt; @@ -161,6 +161,14 @@ pub(crate) unsafe fn codegen( let llval = llvm::LLVMConstInt(i8, val as u64, False); llvm::LLVMSetInitializer(ll_g, llval); + let name = NO_ALLOC_SHIM_IS_UNSTABLE; + let ll_g = llvm::LLVMRustGetOrInsertGlobal(llmod, name.as_ptr().cast(), name.len(), i8); + if tcx.sess.target.default_hidden_visibility { + llvm::LLVMRustSetVisibility(ll_g, llvm::Visibility::Hidden); + } + let llval = llvm::LLVMConstInt(i8, 0, False); + llvm::LLVMSetInitializer(ll_g, llval); + if tcx.sess.opts.debuginfo != DebugInfo::None { let dbg_cx = debuginfo::CodegenUnitDebugContext::new(llmod); debuginfo::metadata::build_compile_unit_di_node(tcx, module_name, &dbg_cx); diff --git a/compiler/rustc_codegen_ssa/src/back/symbol_export.rs b/compiler/rustc_codegen_ssa/src/back/symbol_export.rs index 8f2f829c17c..23c531a2266 100644 --- a/compiler/rustc_codegen_ssa/src/back/symbol_export.rs +++ b/compiler/rustc_codegen_ssa/src/back/symbol_export.rs @@ -2,7 +2,7 @@ use crate::base::allocator_kind_for_codegen; use std::collections::hash_map::Entry::*; -use rustc_ast::expand::allocator::ALLOCATOR_METHODS; +use rustc_ast::expand::allocator::{ALLOCATOR_METHODS, NO_ALLOC_SHIM_IS_UNSTABLE}; use rustc_data_structures::fx::FxHashMap; use rustc_hir::def::DefKind; use rustc_hir::def_id::{CrateNum, DefId, DefIdMap, LocalDefId, LOCAL_CRATE}; @@ -241,6 +241,17 @@ fn exported_symbols_provider_local( used: false, }, )); + + let exported_symbol = + ExportedSymbol::NoDefId(SymbolName::new(tcx, NO_ALLOC_SHIM_IS_UNSTABLE)); + symbols.push(( + exported_symbol, + SymbolExportInfo { + level: SymbolExportLevel::Rust, + kind: SymbolExportKind::Data, + used: false, + }, + )) } if tcx.sess.instrument_coverage() || tcx.sess.opts.cg.profile_generate.enabled() { diff --git a/library/alloc/src/alloc.rs b/library/alloc/src/alloc.rs index 6f2ba957bcd..01d1fdc9b2a 100644 --- a/library/alloc/src/alloc.rs +++ b/library/alloc/src/alloc.rs @@ -37,6 +37,9 @@ extern "Rust" { #[rustc_allocator_zeroed] #[rustc_nounwind] fn __rust_alloc_zeroed(size: usize, align: usize) -> *mut u8; + + #[cfg(not(bootstrap))] + static __rust_no_alloc_shim_is_unstable: u8; } /// The global memory allocator. @@ -90,7 +93,14 @@ pub use std::alloc::Global; #[must_use = "losing the pointer will leak memory"] #[inline] pub unsafe fn alloc(layout: Layout) -> *mut u8 { - unsafe { __rust_alloc(layout.size(), layout.align()) } + unsafe { + // Make sure we don't accidentally allow omitting the allocator shim in + // stable code until it is actually stabilized. + #[cfg(not(bootstrap))] + core::ptr::read_volatile(&__rust_no_alloc_shim_is_unstable); + + __rust_alloc(layout.size(), layout.align()) + } } /// Deallocate memory with the global allocator. diff --git a/tests/codegen/alloc-optimisation.rs b/tests/codegen/alloc-optimisation.rs index c3ffaeb9547..f88d695d87e 100644 --- a/tests/codegen/alloc-optimisation.rs +++ b/tests/codegen/alloc-optimisation.rs @@ -1,12 +1,13 @@ // // no-system-llvm // compile-flags: -O -#![crate_type="lib"] +#![crate_type = "lib"] #[no_mangle] pub fn alloc_test(data: u32) { // CHECK-LABEL: @alloc_test // CHECK-NEXT: start: + // CHECK-NEXT: {{.*}} load volatile i8, ptr @__rust_no_alloc_shim_is_unstable, align 1 // CHECK-NEXT: ret void let x = Box::new(data); drop(x); diff --git a/tests/codegen/vec-optimizes-away.rs b/tests/codegen/vec-optimizes-away.rs index 9143fad2340..6f477a796b6 100644 --- a/tests/codegen/vec-optimizes-away.rs +++ b/tests/codegen/vec-optimizes-away.rs @@ -1,12 +1,13 @@ // ignore-debug: the debug assertions get in the way // no-system-llvm // compile-flags: -O -#![crate_type="lib"] +#![crate_type = "lib"] #[no_mangle] pub fn sum_me() -> i32 { // CHECK-LABEL: @sum_me // CHECK-NEXT: {{^.*:$}} + // CHECK-NEXT: {{.*}} load volatile i8, ptr @__rust_no_alloc_shim_is_unstable, align 1 // CHECK-NEXT: ret i32 6 vec![1, 2, 3].iter().sum::() } -- cgit 1.4.1-3-g733a5