]> git.proxmox.com Git - rustc.git/blobdiff - src/librustc_trans/attributes.rs
New upstream version 1.12.0+dfsg1
[rustc.git] / src / librustc_trans / attributes.rs
index 01e9970dc76c349d5b499a85056f9a3d4c4d9d72..62eac35e0abd9766d64b7b471c6cf2022e15e182 100644 (file)
@@ -9,8 +9,8 @@
 // except according to those terms.
 //! Set and unset common attributes on LLVM values.
 
-use libc::c_uint;
-use llvm::{self, ValueRef};
+use llvm::{self, Attribute, ValueRef};
+use llvm::AttributePlace::Function;
 pub use syntax::attr::InlineAttr;
 use syntax::ast;
 use context::CrateContext;
@@ -20,14 +20,14 @@ use context::CrateContext;
 pub fn inline(val: ValueRef, inline: InlineAttr) {
     use self::InlineAttr::*;
     match inline {
-        Hint   => llvm::SetFunctionAttribute(val, llvm::Attribute::InlineHint),
-        Always => llvm::SetFunctionAttribute(val, llvm::Attribute::AlwaysInline),
-        Never  => llvm::SetFunctionAttribute(val, llvm::Attribute::NoInline),
+        Hint   => Attribute::InlineHint.apply_llfn(Function, val),
+        Always => Attribute::AlwaysInline.apply_llfn(Function, val),
+        Never  => Attribute::NoInline.apply_llfn(Function, val),
         None   => {
-            let attr = llvm::Attribute::InlineHint |
-                       llvm::Attribute::AlwaysInline |
-                       llvm::Attribute::NoInline;
-            llvm::RemoveFunctionAttributes(val, attr)
+            let attr = Attribute::InlineHint |
+                       Attribute::AlwaysInline |
+                       Attribute::NoInline;
+            attr.unapply_llfn(Function, val)
         },
     };
 }
@@ -35,56 +35,37 @@ pub fn inline(val: ValueRef, inline: InlineAttr) {
 /// Tell LLVM to emit or not emit the information necessary to unwind the stack for the function.
 #[inline]
 pub fn emit_uwtable(val: ValueRef, emit: bool) {
-    if emit {
-        llvm::SetFunctionAttribute(val, llvm::Attribute::UWTable);
-    } else {
-        llvm::RemoveFunctionAttributes(val, llvm::Attribute::UWTable);
-    }
+    Attribute::UWTable.toggle_llfn(Function, val, emit);
 }
 
 /// Tell LLVM whether the function can or cannot unwind.
 #[inline]
 pub fn unwind(val: ValueRef, can_unwind: bool) {
-    if can_unwind {
-        llvm::RemoveFunctionAttributes(val, llvm::Attribute::NoUnwind);
-    } else {
-        llvm::SetFunctionAttribute(val, llvm::Attribute::NoUnwind);
-    }
+    Attribute::NoUnwind.toggle_llfn(Function, val, !can_unwind);
 }
 
 /// Tell LLVM whether it should optimise function for size.
 #[inline]
 #[allow(dead_code)] // possibly useful function
 pub fn set_optimize_for_size(val: ValueRef, optimize: bool) {
-    if optimize {
-        llvm::SetFunctionAttribute(val, llvm::Attribute::OptimizeForSize);
-    } else {
-        llvm::RemoveFunctionAttributes(val, llvm::Attribute::OptimizeForSize);
-    }
+    Attribute::OptimizeForSize.toggle_llfn(Function, val, optimize);
 }
 
 /// Tell LLVM if this function should be 'naked', i.e. skip the epilogue and prologue.
 #[inline]
 pub fn naked(val: ValueRef, is_naked: bool) {
-    if is_naked {
-        llvm::SetFunctionAttribute(val, llvm::Attribute::Naked);
-    } else {
-        llvm::RemoveFunctionAttributes(val, llvm::Attribute::Naked);
-    }
+    Attribute::Naked.toggle_llfn(Function, val, is_naked);
 }
 
 pub fn set_frame_pointer_elimination(ccx: &CrateContext, llfn: ValueRef) {
     // FIXME: #11906: Omitting frame pointers breaks retrieving the value of a
     // parameter.
     if ccx.sess().must_not_eliminate_frame_pointers() {
-        unsafe {
-            let attr = "no-frame-pointer-elim\0".as_ptr() as *const _;
-            let val = "true\0".as_ptr() as *const _;
-            llvm::LLVMAddFunctionAttrStringValue(llfn,
-                                                 llvm::FunctionIndex as c_uint,
-                                                 attr,
-                                                 val);
-        }
+        llvm::AddFunctionAttrStringValue(
+            llfn,
+            llvm::AttributePlace::Function,
+            "no-frame-pointer-elim\0",
+            "true\0")
     }
 }
 
@@ -98,13 +79,12 @@ pub fn from_fn_attrs(ccx: &CrateContext, attrs: &[ast::Attribute], llfn: ValueRe
 
     for attr in attrs {
         if attr.check_name("cold") {
-            llvm::Attributes::default().set(llvm::Attribute::Cold)
-                .apply_llfn(llvm::FunctionIndex as usize, llfn)
+            Attribute::Cold.apply_llfn(Function, llfn);
         } else if attr.check_name("naked") {
             naked(llfn, true);
         } else if attr.check_name("allocator") {
-            llvm::Attributes::default().set(llvm::Attribute::NoAlias)
-                .apply_llfn(llvm::ReturnIndex as usize, llfn)
+            Attribute::NoAlias.apply_llfn(
+                llvm::AttributePlace::ReturnValue(), llfn);
         } else if attr.check_name("unwind") {
             unwind(llfn, true);
         }