      1
      2
      3
      4
      5
      6
      7
      8
      9
     10
     11
     12
     13
     14
     15
     16
     17
     18
     19
     20
     21
     22
     23
     24
     25
     26
     27
     28
     29
     30
     31
     32
     33
     34
     35
     36
     37
     38
     39
     40
     41
     42
     43
     44
     45
     46
     47
     48
     49
     50
     51
     52
     53
     54
     55
     56
     57
     58
     59
     60
     61
     62
     63
     64
     65
     66
     67
     68
     69
     70
     71
     72
     73
     74
     75
     76
     77
     78
     79
     80
     81
     82
     83
     84
     85
     86
     87
     88
     89
     90
     91
     92
     93
     94
     95
     96
     97
     98
     99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
    110
    111
    112
    113
    114
    115
    116
    117
    118
    119
    120

    //! Implements integer shifts.
    #![allow(unused)]

    macro_rules! impl_shifts {
        ($id:ident, $elem_ty:ident, $($by:ident),+) => {
            $(
                impl ::ops::Shl<$by> for $id {
                    type Output = Self;
                    #[inline]
                    fn shl(self, other: $by) -> Self {
                        use coresimd::simd_llvm::simd_shl;
                        unsafe { simd_shl(self, $id::splat(other as $elem_ty)) }
                    }
                }
                impl ::ops::Shr<$by> for $id {
                    type Output = Self;
                    #[inline]
                    fn shr(self, other: $by) -> Self {
                        use coresimd::simd_llvm::simd_shr;
                        unsafe { simd_shr(self, $id::splat(other as $elem_ty)) }
                    }
                }

                impl ::ops::ShlAssign<$by> for $id {
                    #[inline]
                    fn shl_assign(&mut self, other: $by) {
                        *self = *self << other;
                    }
                }
                impl ::ops::ShrAssign<$by> for $id {
                    #[inline]
                    fn shr_assign(&mut self, other: $by) {
                        *self = *self >> other;
                    }
                }

            )+
        }
    }

    macro_rules! impl_all_scalar_shifts {
        ($id:ident, $elem_ty:ident) => {
            impl_shifts!(
                $id, $elem_ty, u8, u16, u32, u64, usize, i8, i16, i32, i64, isize
            );
        };
    }

    #[cfg(test)]
    macro_rules! test_shift_ops {
        ($id:ident, $elem_ty:ident, $($index_ty:ident),+) => {
            #[test]
            fn scalar_shift_ops() {
                use ::coresimd::simd::$id;
                use ::std::mem;
                let z = $id::splat(0 as $elem_ty);
                let o = $id::splat(1 as $elem_ty);
                let t = $id::splat(2 as $elem_ty);
                let f = $id::splat(4 as $elem_ty);

                $(
                    {
                        let zi = 0 as $index_ty;
                        let oi = 1 as $index_ty;
                        let ti = 2 as $index_ty;
                        let maxi = (mem::size_of::<$elem_ty>() * 8 - 1) as $index_ty;

                        // shr
                        assert_eq!(z >> zi, z);
                        assert_eq!(z >> oi, z);
                        assert_eq!(z >> ti, z);
                        assert_eq!(z >> ti, z);

                        assert_eq!(o >> zi, o);
                        assert_eq!(t >> zi, t);
                        assert_eq!(f >> zi, f);
                        assert_eq!(f >> maxi, z);

                        assert_eq!(o >> oi, z);
                        assert_eq!(t >> oi, o);
                        assert_eq!(t >> ti, z);
                        assert_eq!(f >> oi, t);
                        assert_eq!(f >> ti, o);
                        assert_eq!(f >> maxi, z);

                        // shl
                        assert_eq!(z << zi, z);
                        assert_eq!(o << zi, o);
                        assert_eq!(t << zi, t);
                        assert_eq!(f << zi, f);
                        assert_eq!(f << maxi, z);

                        assert_eq!(o << oi, t);
                        assert_eq!(o << ti, f);
                        assert_eq!(t << oi, f);

                        {  // shr_assign
                            let mut v = o;
                            v >>= oi;
                            assert_eq!(v, z);
                        }
                        {  // shl_assign
                            let mut v = o;
                            v <<= oi;
                            assert_eq!(v, t);
                        }
                    }
                )+
            }
        };
    }

    #[cfg(test)]
    macro_rules! test_all_scalar_shift_ops {
        ($id:ident, $elem_ty:ident) => {
            test_shift_ops!(
                $id, $elem_ty, u8, u16, u32, u64, usize, i8, i16, i32, i64, isize
            );
        };
    }

# Help

## Keyboard Shortcuts

`?`
  Show this help dialog
`S`
  Focus the search field
`↑`
  Move up in search results
`↓`
  Move down in search results
`↹`
  Switch tab
`⏎`
  Go to active search result
`+`
  Expand all sections
`-`
  Collapse all sections

## Search Tricks

Prefix searches with a type followed by a colon (e.g. `fn:`) to restrict the search to a given type.

Accepted types are: `fn`, `mod`, `struct`, `enum`, `trait`, `type`, `macro`, and `const`.

Search functions by type signature (e.g. `vec -> usize` or `* -> vec`)

Search multiple things at once by splitting your query with comma (e.g. `str,u8` or `String,struct:Vec,test`)