about summary refs log tree commit diff
path: root/src
diff options
context:
space:
mode:
authorOliver Scherer <github35764891676564198441@oli-obk.de>2019-11-26 12:55:11 +0100
committerOliver Scherer <github35764891676564198441@oli-obk.de>2019-12-03 10:20:15 +0100
commit46c00a21e1e89ebbf7757dcbee35f89332575134 (patch)
treecddd9cc140b18c51a4d5c8c7c976e655178f0b23 /src
parent52be0b07ae4ff025e40e04d7fe8d2a530980b637 (diff)
downloadrust-46c00a21e1e89ebbf7757dcbee35f89332575134.tar.gz
rust-46c00a21e1e89ebbf7757dcbee35f89332575134.zip
Move all intrinsic whitelists into the constness check file
Diffstat (limited to 'src')
-rw-r--r--src/librustc/ty/constness.rs35
-rw-r--r--src/librustc_mir/transform/qualify_min_const_fn.rs55
-rw-r--r--src/test/ui/consts/const-extern-fn/const-extern-fn-call-extern-fn.rs4
-rw-r--r--src/test/ui/consts/const-extern-fn/const-extern-fn-call-extern-fn.stderr4
4 files changed, 42 insertions, 56 deletions
diff --git a/src/librustc/ty/constness.rs b/src/librustc/ty/constness.rs
index 0fb3f575b52..8ec5120d6b3 100644
--- a/src/librustc/ty/constness.rs
+++ b/src/librustc/ty/constness.rs
@@ -36,12 +36,47 @@ impl<'tcx> TyCtxt<'tcx> {
         }
     }
 
+    /// Returns `true` if the `def_id` refers to an intrisic which we've whitelisted
+    /// for being called from stable `const fn`s (`min_const_fn`).
+    ///
+    /// Adding more intrinsics requires sign-off from @rust-lang/lang.
+    fn is_intrinsic_min_const_fn(self, def_id: DefId) -> bool {
+        match self.item_name(def_id) {
+            | sym::size_of
+            | sym::min_align_of
+            | sym::needs_drop
+            // Arithmetic:
+            | sym::add_with_overflow // ~> .overflowing_add
+            | sym::sub_with_overflow // ~> .overflowing_sub
+            | sym::mul_with_overflow // ~> .overflowing_mul
+            | sym::wrapping_add // ~> .wrapping_add
+            | sym::wrapping_sub // ~> .wrapping_sub
+            | sym::wrapping_mul // ~> .wrapping_mul
+            | sym::saturating_add // ~> .saturating_add
+            | sym::saturating_sub // ~> .saturating_sub
+            | sym::unchecked_shl // ~> .wrapping_shl
+            | sym::unchecked_shr // ~> .wrapping_shr
+            | sym::rotate_left // ~> .rotate_left
+            | sym::rotate_right // ~> .rotate_right
+            | sym::ctpop // ~> .count_ones
+            | sym::ctlz // ~> .leading_zeros
+            | sym::cttz // ~> .trailing_zeros
+            | sym::bswap // ~> .swap_bytes
+            | sym::bitreverse // ~> .reverse_bits
+            => true,
+            _ => false,
+        }
+    }
+
     /// Returns `true` if this function must conform to `min_const_fn`
     pub fn is_min_const_fn(self, def_id: DefId) -> bool {
         // Bail out if the signature doesn't contain `const`
         if !self.is_const_fn_raw(def_id) {
             return false;
         }
+        if let Abi::RustIntrinsic = self.fn_sig(def_id).abi() {
+            return self.is_intrinsic_min_const_fn(def_id);
+        }
 
         if self.features().staged_api {
             // in order for a libstd function to be considered min_const_fn
diff --git a/src/librustc_mir/transform/qualify_min_const_fn.rs b/src/librustc_mir/transform/qualify_min_const_fn.rs
index b7e1b83ee05..cf04d3e975b 100644
--- a/src/librustc_mir/transform/qualify_min_const_fn.rs
+++ b/src/librustc_mir/transform/qualify_min_const_fn.rs
@@ -2,7 +2,6 @@ use rustc::hir::def_id::DefId;
 use rustc::hir;
 use rustc::mir::*;
 use rustc::ty::{self, Predicate, Ty, TyCtxt, adjustment::{PointerCast}};
-use rustc_target::spec::abi;
 use std::borrow::Cow;
 use syntax_pos::Span;
 use syntax::symbol::{sym, Symbol};
@@ -356,18 +355,8 @@ fn check_terminator(
         } => {
             let fn_ty = func.ty(body, tcx);
             if let ty::FnDef(def_id, _) = fn_ty.kind {
-
-                // some intrinsics are waved through if called inside the
-                // standard library. Users never need to call them directly
-                match tcx.fn_sig(def_id).abi() {
-                    abi::Abi::RustIntrinsic => if !is_intrinsic_whitelisted(tcx, def_id) {
-                        return Err((
-                            span,
-                            "can only call a curated list of intrinsics in `min_const_fn`".into(),
-                        ))
-                    },
-                    abi::Abi::Rust if tcx.is_min_const_fn(def_id) => {},
-                    abi::Abi::Rust => return Err((
+                if !tcx.is_min_const_fn(def_id) {
+                    return Err((
                         span,
                         format!(
                             "can only call other `const fn` within a `const fn`, \
@@ -375,14 +364,7 @@ fn check_terminator(
                             func,
                         )
                         .into(),
-                    )),
-                    abi => return Err((
-                        span,
-                        format!(
-                            "cannot call functions with `{}` abi in `min_const_fn`",
-                            abi,
-                        ).into(),
-                    )),
+                    ));
                 }
 
                 check_operand(tcx, func, span, def_id, body)?;
@@ -410,34 +392,3 @@ fn check_terminator(
     }
 }
 
-/// Returns `true` if the `def_id` refers to an intrisic which we've whitelisted
-/// for being called from stable `const fn`s (`min_const_fn`).
-///
-/// Adding more intrinsics requires sign-off from @rust-lang/lang.
-fn is_intrinsic_whitelisted(tcx: TyCtxt<'tcx>, def_id: DefId) -> bool {
-    match tcx.item_name(def_id) {
-        | sym::size_of
-        | sym::min_align_of
-        | sym::needs_drop
-        // Arithmetic:
-        | sym::add_with_overflow // ~> .overflowing_add
-        | sym::sub_with_overflow // ~> .overflowing_sub
-        | sym::mul_with_overflow // ~> .overflowing_mul
-        | sym::wrapping_add // ~> .wrapping_add
-        | sym::wrapping_sub // ~> .wrapping_sub
-        | sym::wrapping_mul // ~> .wrapping_mul
-        | sym::saturating_add // ~> .saturating_add
-        | sym::saturating_sub // ~> .saturating_sub
-        | sym::unchecked_shl // ~> .wrapping_shl
-        | sym::unchecked_shr // ~> .wrapping_shr
-        | sym::rotate_left // ~> .rotate_left
-        | sym::rotate_right // ~> .rotate_right
-        | sym::ctpop // ~> .count_ones
-        | sym::ctlz // ~> .leading_zeros
-        | sym::cttz // ~> .trailing_zeros
-        | sym::bswap // ~> .swap_bytes
-        | sym::bitreverse // ~> .reverse_bits
-        => true,
-        _ => false,
-    }
-}
diff --git a/src/test/ui/consts/const-extern-fn/const-extern-fn-call-extern-fn.rs b/src/test/ui/consts/const-extern-fn/const-extern-fn-call-extern-fn.rs
index 7c6a574a211..6469a65700d 100644
--- a/src/test/ui/consts/const-extern-fn/const-extern-fn-call-extern-fn.rs
+++ b/src/test/ui/consts/const-extern-fn/const-extern-fn-call-extern-fn.rs
@@ -7,7 +7,7 @@ extern "C" {
 const extern fn bar() {
     unsafe {
         regular_in_block();
-        //~^ ERROR: cannot call functions with `"C"` abi in `min_const_fn`
+        //~^ ERROR: can only call other `const fn` within a `const fn`
     }
 }
 
@@ -16,7 +16,7 @@ extern fn regular() {}
 const extern fn foo() {
     unsafe {
         regular();
-        //~^ ERROR: cannot call functions with `"C"` abi in `min_const_fn`
+        //~^ ERROR: can only call other `const fn` within a `const fn`
     }
 }
 
diff --git a/src/test/ui/consts/const-extern-fn/const-extern-fn-call-extern-fn.stderr b/src/test/ui/consts/const-extern-fn/const-extern-fn-call-extern-fn.stderr
index d8bdf0a57cf..eed279ecf75 100644
--- a/src/test/ui/consts/const-extern-fn/const-extern-fn-call-extern-fn.stderr
+++ b/src/test/ui/consts/const-extern-fn/const-extern-fn-call-extern-fn.stderr
@@ -1,4 +1,4 @@
-error[E0723]: cannot call functions with `"C"` abi in `min_const_fn`
+error[E0723]: can only call other `const fn` within a `const fn`, but `const regular_in_block` is not stable as `const fn`
   --> $DIR/const-extern-fn-call-extern-fn.rs:9:9
    |
 LL |         regular_in_block();
@@ -7,7 +7,7 @@ LL |         regular_in_block();
    = note: for more information, see issue https://github.com/rust-lang/rust/issues/57563
    = help: add `#![feature(const_fn)]` to the crate attributes to enable
 
-error[E0723]: cannot call functions with `"C"` abi in `min_const_fn`
+error[E0723]: can only call other `const fn` within a `const fn`, but `const regular` is not stable as `const fn`
   --> $DIR/const-extern-fn-call-extern-fn.rs:18:9
    |
 LL |         regular();