From c5a91418e1638943a24cb1a9c71fbddf4b23931f Mon Sep 17 00:00:00 2001 From: John Hodge Date: Thu, 2 Jul 2015 21:34:53 -0700 Subject: [PATCH 1/3] Add disable_float cfg target for #26449. This allows to compile libcore on architectures that lack floating point support or to use libcore in kernel code without worrying about saving and restoring the floating point register state inside the kernel. --- src/libcore/clone.rs | 2 ++ src/libcore/default.rs | 2 ++ src/libcore/fmt/mod.rs | 2 ++ src/libcore/intrinsics.rs | 5 +++++ src/libcore/lib.rs | 3 +++ src/libcore/num/flt2dec/decoder.rs | 3 +++ src/libcore/num/mod.rs | 3 +++ src/libcore/ops.rs | 24 +++++++++++++++++++----- 8 files changed, 39 insertions(+), 5 deletions(-) diff --git a/src/libcore/clone.rs b/src/libcore/clone.rs index a13160b3a19ee..bdc309449c32c 100644 --- a/src/libcore/clone.rs +++ b/src/libcore/clone.rs @@ -80,7 +80,9 @@ clone_impl! { u16 } clone_impl! { u32 } clone_impl! { u64 } +#[cfg(not(disable_float))] clone_impl! { f32 } +#[cfg(not(disable_float))] clone_impl! { f64 } clone_impl! { () } diff --git a/src/libcore/default.rs b/src/libcore/default.rs index f5103d394eef0..24f9d785f9429 100644 --- a/src/libcore/default.rs +++ b/src/libcore/default.rs @@ -153,5 +153,7 @@ default_impl! { i16, 0 } default_impl! { i32, 0 } default_impl! { i64, 0 } +#[cfg(not(disable_float))] default_impl! { f32, 0.0f32 } +#[cfg(not(disable_float))] default_impl! { f64, 0.0f64 } diff --git a/src/libcore/fmt/mod.rs b/src/libcore/fmt/mod.rs index f735ed7b78b17..c854b2761f612 100644 --- a/src/libcore/fmt/mod.rs +++ b/src/libcore/fmt/mod.rs @@ -1131,7 +1131,9 @@ macro_rules! floating { ($ty:ident) => { } } } } +#[cfg(not(disable_float))] floating! { f32 } +#[cfg(not(disable_float))] floating! { f64 } // Implementation of Display/Debug for various core types diff --git a/src/libcore/intrinsics.rs b/src/libcore/intrinsics.rs index 455928077da46..1a86835df366a 100644 --- a/src/libcore/intrinsics.rs +++ b/src/libcore/intrinsics.rs @@ -392,7 +392,10 @@ extern "rust-intrinsic" { pub fn volatile_load(src: *const T) -> T; /// Perform a volatile store to the `dst` pointer. pub fn volatile_store(dst: *mut T, val: T); +} +#[cfg(not(disable_float))] +extern "rust-intrinsic" { /// Returns the square root of an `f32` pub fn sqrtf32(x: f32) -> f32; /// Returns the square root of an `f64` @@ -489,7 +492,9 @@ extern "rust-intrinsic" { pub fn roundf32(x: f32) -> f32; /// Returns the nearest integer to an `f64`. Rounds half-way cases away from zero. pub fn roundf64(x: f64) -> f64; +} +extern "rust-intrinsic" { /// Returns the number of bits set in a `u8`. pub fn ctpop8(x: u8) -> u8; /// Returns the number of bits set in a `u16`. diff --git a/src/libcore/lib.rs b/src/libcore/lib.rs index 030d2a33f8f65..c0f94b1672ea5 100644 --- a/src/libcore/lib.rs +++ b/src/libcore/lib.rs @@ -110,7 +110,9 @@ mod uint_macros; #[path = "num/u32.rs"] pub mod u32; #[path = "num/u64.rs"] pub mod u64; +#[cfg(not(disable_float))] #[path = "num/f32.rs"] pub mod f32; +#[cfg(not(disable_float))] #[path = "num/f64.rs"] pub mod f64; #[macro_use] @@ -148,6 +150,7 @@ pub mod iter; pub mod option; pub mod raw; pub mod result; +#[cfg(not(disable_float))] pub mod simd; pub mod slice; pub mod str; diff --git a/src/libcore/num/flt2dec/decoder.rs b/src/libcore/num/flt2dec/decoder.rs index f98bc11a315f0..8d3c2f9a1e38d 100644 --- a/src/libcore/num/flt2dec/decoder.rs +++ b/src/libcore/num/flt2dec/decoder.rs @@ -12,6 +12,7 @@ use prelude::*; +#[cfg(not(disable_float))] use {f32, f64}; use num::{Float, FpCategory}; @@ -60,11 +61,13 @@ pub trait DecodableFloat: Float + Copy { fn min_pos_norm_value() -> Self; } +#[cfg(not(disable_float))] impl DecodableFloat for f32 { fn ldexpi(f: i64, exp: isize) -> Self { f as Self * (exp as Self).exp2() } fn min_pos_norm_value() -> Self { f32::MIN_POSITIVE } } +#[cfg(not(disable_float))] impl DecodableFloat for f64 { fn ldexpi(f: i64, exp: isize) -> Self { f as Self * (exp as Self).exp2() } fn min_pos_norm_value() -> Self { f64::MIN_POSITIVE } diff --git a/src/libcore/num/mod.rs b/src/libcore/num/mod.rs index 97b4f77675533..93dec996bcaa4 100644 --- a/src/libcore/num/mod.rs +++ b/src/libcore/num/mod.rs @@ -92,6 +92,7 @@ macro_rules! zero_one_impl_float { } )*) } +#[cfg(not(disable_float))] zero_one_impl_float! { f32 f64 } macro_rules! checked_op { @@ -1399,7 +1400,9 @@ macro_rules! from_str_float_impl { } } } +#[cfg(not(disable_float))] from_str_float_impl!(f32); +#[cfg(not(disable_float))] from_str_float_impl!(f64); macro_rules! from_str_radix_int_impl { diff --git a/src/libcore/ops.rs b/src/libcore/ops.rs index 9a22fe3a493f1..595664c9076f1 100644 --- a/src/libcore/ops.rs +++ b/src/libcore/ops.rs @@ -203,7 +203,9 @@ macro_rules! add_impl { )*) } -add_impl! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 f32 f64 } +add_impl! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 } +#[cfg(not(disable_float))] +add_impl! { f32 f64 } /// The `Sub` trait is used to specify the functionality of `-`. /// @@ -257,7 +259,9 @@ macro_rules! sub_impl { )*) } -sub_impl! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 f32 f64 } +sub_impl! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 } +#[cfg(not(disable_float))] +sub_impl! { f32 f64 } /// The `Mul` trait is used to specify the functionality of `*`. /// @@ -311,7 +315,9 @@ macro_rules! mul_impl { )*) } -mul_impl! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 f32 f64 } +mul_impl! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 } +#[cfg(not(disable_float))] +mul_impl! { f32 f64 } /// The `Div` trait is used to specify the functionality of `/`. /// @@ -365,7 +371,9 @@ macro_rules! div_impl { )*) } -div_impl! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 f32 f64 } +div_impl! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 } +#[cfg(not(disable_float))] +div_impl! { f32 f64 } /// The `Rem` trait is used to specify the functionality of `%`. /// @@ -421,6 +429,7 @@ macro_rules! rem_impl { rem_impl! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 } +#[cfg(not(disable_float))] #[stable(feature = "rust1", since = "1.0.0")] impl Rem for f32 { type Output = f32; @@ -440,6 +449,7 @@ impl Rem for f32 { } } +#[cfg(not(disable_float))] #[stable(feature = "rust1", since = "1.0.0")] impl Rem for f64 { type Output = f64; @@ -451,7 +461,9 @@ impl Rem for f64 { } } +#[cfg(not(disable_float))] forward_ref_binop! { impl Rem, rem for f64, f64 } +#[cfg(not(disable_float))] forward_ref_binop! { impl Rem, rem for f32, f32 } /// The `Neg` trait is used to specify the functionality of unary `-`. @@ -523,7 +535,9 @@ macro_rules! neg_impl_unsigned { } // neg_impl_unsigned! { usize u8 u16 u32 u64 } -neg_impl_numeric! { isize i8 i16 i32 i64 f32 f64 } +neg_impl_numeric! { isize i8 i16 i32 i64 } +#[cfg(not(disable_float))] +neg_impl_numeric! { f32 f64 } /// The `Not` trait is used to specify the functionality of unary `!`. /// From 669b9663f2a87552193b69a9769c7d75078858f5 Mon Sep 17 00:00:00 2001 From: Gerd Zellweger Date: Thu, 2 Jul 2015 21:42:10 -0700 Subject: [PATCH 2/3] Added test for #26449. --- src/test/run-make/issue-26449/Makefile | 6 ++++++ 1 file changed, 6 insertions(+) create mode 100644 src/test/run-make/issue-26449/Makefile diff --git a/src/test/run-make/issue-26449/Makefile b/src/test/run-make/issue-26449/Makefile new file mode 100644 index 0000000000000..08f868789546d --- /dev/null +++ b/src/test/run-make/issue-26449/Makefile @@ -0,0 +1,6 @@ +-include ../tools.mk + +all: + $(RUSTC) -C target-feature=-mmx,-sse,-sse2 ../../../libcore/lib.rs 2>&1 | \ + grep "LLVM ERROR: SSE register return with SSE disabled" + $(RUSTC) --cfg disable_float -C target-feature=-mmx,-sse,-sse2 ../../../libcore/lib.rs From 939a76e5b16e768bfbd84846d6a7c7e602ebd9bf Mon Sep 17 00:00:00 2001 From: Gerd Zellweger Date: Thu, 2 Jul 2015 21:47:54 -0700 Subject: [PATCH 3/3] No warnings for compiling disable_float config #26449. --- src/libcore/fmt/mod.rs | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/src/libcore/fmt/mod.rs b/src/libcore/fmt/mod.rs index c854b2761f612..9156f29665ee9 100644 --- a/src/libcore/fmt/mod.rs +++ b/src/libcore/fmt/mod.rs @@ -17,6 +17,7 @@ use prelude::*; use cell::{Cell, RefCell, Ref, RefMut, BorrowState}; use marker::PhantomData; use mem; +#[cfg(not(disable_float))] use num::flt2dec; use ops::Deref; use result; @@ -653,6 +654,7 @@ impl<'a> Formatter<'a> { /// Takes the formatted parts and applies the padding. /// Assumes that the caller already has rendered the parts with required precision, /// so that `self.precision` can be ignored. + #[cfg(not(disable_float))] fn pad_formatted_parts(&mut self, formatted: &flt2dec::Formatted) -> Result { if let Some(mut width) = self.width { // for the sign-aware zero padding, we render the sign first and @@ -689,6 +691,7 @@ impl<'a> Formatter<'a> { } } + #[cfg(not(disable_float))] fn write_formatted_parts(&mut self, formatted: &flt2dec::Formatted) -> Result { fn write_bytes(buf: &mut Write, s: &[u8]) -> Result { buf.write_str(unsafe { str::from_utf8_unchecked(s) }) @@ -1054,6 +1057,7 @@ impl<'a, T> Pointer for &'a mut T { } } +#[cfg(not(disable_float))] // Common code of floating point Debug and Display. fn float_to_decimal_common(fmt: &mut Formatter, num: &T, negative_zero: bool) -> Result where T: flt2dec::DecodableFloat @@ -1078,6 +1082,7 @@ fn float_to_decimal_common(fmt: &mut Formatter, num: &T, negative_zero: bool) fmt.pad_formatted_parts(&formatted) } +#[cfg(not(disable_float))] // Common code of floating point LowerExp and UpperExp. fn float_to_exponential_common(fmt: &mut Formatter, num: &T, upper: bool) -> Result where T: flt2dec::DecodableFloat