Skip to content

Commit d792925

Browse files
committed
Shim some of the old std::simd functionality.
Overload the operators using the traits so that things mostly keep working during the deprecation period.
1 parent 62ba85b commit d792925

File tree

3 files changed

+56
-16
lines changed

3 files changed

+56
-16
lines changed

src/libcore/lib.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,7 @@
7979
#![feature(reflect)]
8080
#![feature(rustc_attrs)]
8181
#![cfg_attr(stage0, feature(simd))]
82-
#![cfg_attr(not(stage0), feature(repr_simd))]
82+
#![cfg_attr(not(stage0), feature(repr_simd, platform_intrinsics))]
8383
#![feature(staged_api)]
8484
#![feature(unboxed_closures)]
8585

src/libcore/simd.rs

+54-14
Original file line numberDiff line numberDiff line change
@@ -10,25 +10,12 @@
1010

1111
//! SIMD vectors.
1212
//!
13-
//! These types can be used for accessing basic SIMD operations. Each of them
14-
//! implements the standard arithmetic operator traits (Add, Sub, Mul, Div,
15-
//! Rem, Shl, Shr) through compiler magic, rather than explicitly. Currently
13+
//! These types can be used for accessing basic SIMD operations. Currently
1614
//! comparison operators are not implemented. To use SSE3+, you must enable
1715
//! the features, like `-C target-feature=sse3,sse4.1,sse4.2`, or a more
1816
//! specific `target-cpu`. No other SIMD intrinsics or high-level wrappers are
1917
//! provided beyond this module.
2018
//!
21-
//! ```rust
22-
//! #![feature(core_simd)]
23-
//!
24-
//! fn main() {
25-
//! use std::simd::f32x4;
26-
//! let a = f32x4(40.0, 41.0, 42.0, 43.0);
27-
//! let b = f32x4(1.0, 1.1, 3.4, 9.8);
28-
//! println!("{:?}", a + b);
29-
//! }
30-
//! ```
31-
//!
3219
//! # Stability Note
3320
//!
3421
//! These are all experimental. The interface may change entirely, without
@@ -44,6 +31,30 @@
4431
#![allow(missing_docs)]
4532
#![allow(deprecated)]
4633

34+
use ops::{Add, Sub, Mul, Div, Shl, Shr, BitAnd, BitOr, BitXor};
35+
36+
// FIXME(stage0): the contents of macro can be inlined.
37+
// ABIs are verified as valid as soon as they are parsed, i.e. before
38+
// `cfg` stripping. The `platform-intrinsic` ABI is new, so stage0
39+
// doesn't know about it, but it still errors out when it hits it
40+
// (despite this being in a `cfg(not(stage0))` module).
41+
macro_rules! argh {
42+
() => {
43+
extern "platform-intrinsic" {
44+
fn simd_add<T>(x: T, y: T) -> T;
45+
fn simd_sub<T>(x: T, y: T) -> T;
46+
fn simd_mul<T>(x: T, y: T) -> T;
47+
fn simd_div<T>(x: T, y: T) -> T;
48+
fn simd_shl<T>(x: T, y: T) -> T;
49+
fn simd_shr<T>(x: T, y: T) -> T;
50+
fn simd_and<T>(x: T, y: T) -> T;
51+
fn simd_or<T>(x: T, y: T) -> T;
52+
fn simd_xor<T>(x: T, y: T) -> T;
53+
}
54+
}
55+
}
56+
argh!();
57+
4758
#[repr(simd)]
4859
#[derive(Copy, Clone, Debug)]
4960
#[repr(C)]
@@ -101,3 +112,32 @@ pub struct f32x4(pub f32, pub f32, pub f32, pub f32);
101112
#[derive(Copy, Clone, Debug)]
102113
#[repr(C)]
103114
pub struct f64x2(pub f64, pub f64);
115+
116+
macro_rules! impl_traits {
117+
($($trayt: ident, $method: ident, $func: ident: $($ty: ty),*;)*) => {
118+
$($(
119+
impl $trayt<$ty> for $ty {
120+
type Output = Self;
121+
fn $method(self, other: Self) -> Self {
122+
unsafe {
123+
$func(self, other)
124+
}
125+
}
126+
}
127+
)*)*
128+
}
129+
}
130+
131+
impl_traits! {
132+
Add, add, simd_add: u8x16, u16x8, u32x4, u64x2, i8x16, i16x8, i32x4, i64x2, f32x4, f64x2;
133+
Sub, sub, simd_sub: u8x16, u16x8, u32x4, u64x2, i8x16, i16x8, i32x4, i64x2, f32x4, f64x2;
134+
Mul, mul, simd_mul: u8x16, u16x8, u32x4, u64x2, i8x16, i16x8, i32x4, i64x2, f32x4, f64x2;
135+
136+
Div, div, simd_div: f32x4, f64x2;
137+
138+
Shl, shl, simd_shl: u8x16, u16x8, u32x4, u64x2, i8x16, i16x8, i32x4, i64x2;
139+
Shr, shr, simd_shr: u8x16, u16x8, u32x4, u64x2, i8x16, i16x8, i32x4, i64x2;
140+
BitAnd, bitand, simd_and: u8x16, u16x8, u32x4, u64x2, i8x16, i16x8, i32x4, i64x2;
141+
BitOr, bitor, simd_or: u8x16, u16x8, u32x4, u64x2, i8x16, i16x8, i32x4, i64x2;
142+
BitXor, bitxor, simd_xor: u8x16, u16x8, u32x4, u64x2, i8x16, i16x8, i32x4, i64x2;
143+
}

src/test/bench/shootout-spectralnorm.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -91,7 +91,7 @@ fn mult<F>(v: &[f64], out: &mut [f64], start: usize, a: F)
9191
for (j, chunk) in v.chunks(2).enumerate().map(|(j, s)| (2 * j, s)) {
9292
let top = f64x2(chunk[0], chunk[1]);
9393
let bot = f64x2(a(i, j), a(i, j + 1));
94-
sum += top / bot;
94+
sum = sum + top / bot;
9595
}
9696
let f64x2(a, b) = sum;
9797
*slot = a + b;

0 commit comments

Comments
 (0)