Path: blob/master/thirdparty/embree/common/simd/vboold4_avx.h
9912 views
// Copyright 2009-2021 Intel Corporation1// SPDX-License-Identifier: Apache-2.023#pragma once45#define vboolf vboolf_impl6#define vboold vboold_impl7#define vint vint_impl8#define vuint vuint_impl9#define vllong vllong_impl10#define vfloat vfloat_impl11#define vdouble vdouble_impl1213namespace embree14{15/* 4-wide AVX bool type for 64bit data types*/16template<>17struct vboold<4>18{19ALIGNED_STRUCT_(32);2021typedef vboold4 Bool;2223enum { size = 4 }; // number of SIMD elements24union { // data25__m256d v;26struct { __m128d vl,vh; };27long long i[4];28};2930////////////////////////////////////////////////////////////////////////////////31/// Constructors, Assignment & Cast Operators32////////////////////////////////////////////////////////////////////////////////3334__forceinline vboold() {}35__forceinline vboold(const vboold4& a) { v = a.v; }36__forceinline vboold4& operator =(const vboold4& a) { v = a.v; return *this; }3738__forceinline vboold(__m256d a) : v(a) {}39__forceinline vboold(__m256i a) : v(_mm256_castsi256_pd(a)) {}4041__forceinline operator const __m256() const { return _mm256_castpd_ps(v); }42__forceinline operator const __m256i() const { return _mm256_castpd_si256(v); }43__forceinline operator const __m256d() const { return v; }4445__forceinline vboold(int a)46{47assert(a >= 0 && a <= 255);48#if defined (__AVX2__)49const __m256i mask = _mm256_set_epi64x(0x8, 0x4, 0x2, 0x1);50const __m256i b = _mm256_set1_epi64x(a);51const __m256i c = _mm256_and_si256(b,mask);52v = _mm256_castsi256_pd(_mm256_cmpeq_epi64(c,mask));53#else54vl = mm_lookupmask_pd[a & 0x3];55vh = mm_lookupmask_pd[a >> 2];56#endif57}5859////////////////////////////////////////////////////////////////////////////////60/// Constants61////////////////////////////////////////////////////////////////////////////////6263__forceinline vboold(FalseTy) : v(_mm256_setzero_pd()) {}64#if !defined(__aarch64__)65__forceinline vboold(TrueTy) : v(_mm256_cmp_pd(_mm256_setzero_pd(), _mm256_setzero_pd(), _CMP_EQ_OQ)) {}66#else67__forceinline vboold(TrueTy) : v(_mm256_cmpeq_pd(_mm256_setzero_pd(), _mm256_setzero_pd())) {}68#endif6970////////////////////////////////////////////////////////////////////////////////71/// Array Access72////////////////////////////////////////////////////////////////////////////////7374__forceinline bool operator [](size_t index) const { assert(index < 4); return (_mm256_movemask_pd(v) >> index) & 1; }75__forceinline long long& operator [](size_t index) { assert(index < 4); return i[index]; }76};7778////////////////////////////////////////////////////////////////////////////////79/// Unary Operators80////////////////////////////////////////////////////////////////////////////////8182__forceinline vboold4 operator !(const vboold4& a) { return _mm256_xor_pd(a, vboold4(embree::True)); }8384////////////////////////////////////////////////////////////////////////////////85/// Binary Operators86////////////////////////////////////////////////////////////////////////////////8788__forceinline vboold4 operator &(const vboold4& a, const vboold4& b) { return _mm256_and_pd(a, b); }89__forceinline vboold4 operator |(const vboold4& a, const vboold4& b) { return _mm256_or_pd (a, b); }90__forceinline vboold4 operator ^(const vboold4& a, const vboold4& b) { return _mm256_xor_pd(a, b); }9192__forceinline vboold4 andn(const vboold4& a, const vboold4& b) { return _mm256_andnot_pd(b, a); }9394__forceinline vboold4& operator &=(vboold4& a, const vboold4& b) { return a = a & b; }95__forceinline vboold4& operator |=(vboold4& a, const vboold4& b) { return a = a | b; }96__forceinline vboold4& operator ^=(vboold4& a, const vboold4& b) { return a = a ^ b; }9798////////////////////////////////////////////////////////////////////////////////99/// Comparison Operators + Select100////////////////////////////////////////////////////////////////////////////////101102__forceinline vboold4 operator !=(const vboold4& a, const vboold4& b) { return _mm256_xor_pd(a, b); }103__forceinline vboold4 operator ==(const vboold4& a, const vboold4& b) { return _mm256_xor_pd(_mm256_xor_pd(a,b),vboold4(embree::True)); }104105__forceinline vboold4 select(const vboold4& mask, const vboold4& t, const vboold4& f) {106return _mm256_blendv_pd(f, t, mask);107}108109////////////////////////////////////////////////////////////////////////////////110/// Movement/Shifting/Shuffling Functions111////////////////////////////////////////////////////////////////////////////////112113#if !defined(__aarch64__)114__forceinline vboold4 unpacklo(const vboold4& a, const vboold4& b) { return _mm256_unpacklo_pd(a, b); }115__forceinline vboold4 unpackhi(const vboold4& a, const vboold4& b) { return _mm256_unpackhi_pd(a, b); }116#endif117118#if defined(__AVX2__)119template<int i0, int i1, int i2, int i3>120__forceinline vboold4 shuffle(const vboold4& v) {121return _mm256_permute4x64_pd(v, _MM_SHUFFLE(i3, i2, i1, i0));122}123124template<int i>125__forceinline vboold4 shuffle(const vboold4& v) {126return _mm256_permute4x64_pd(v, _MM_SHUFFLE(i, i, i, i));127}128#endif129130131////////////////////////////////////////////////////////////////////////////////132/// Reduction Operations133////////////////////////////////////////////////////////////////////////////////134135__forceinline bool reduce_and(const vboold4& a) { return _mm256_movemask_pd(a) == (unsigned int)0xf; }136__forceinline bool reduce_or (const vboold4& a) { return !_mm256_testz_pd(a,a); }137138__forceinline bool all (const vboold4& a) { return _mm256_movemask_pd(a) == (unsigned int)0xf; }139__forceinline bool any (const vboold4& a) { return !_mm256_testz_pd(a,a); }140__forceinline bool none(const vboold4& a) { return _mm256_testz_pd(a,a) != 0; }141142__forceinline bool all (const vboold4& valid, const vboold4& b) { return all((!valid) | b); }143__forceinline bool any (const vboold4& valid, const vboold4& b) { return any(valid & b); }144__forceinline bool none(const vboold4& valid, const vboold4& b) { return none(valid & b); }145146__forceinline unsigned int movemask(const vboold4& a) { return _mm256_movemask_pd(a); }147__forceinline size_t popcnt (const vboold4& a) { return popcnt((size_t)_mm256_movemask_pd(a)); }148149////////////////////////////////////////////////////////////////////////////////150/// Get/Set Functions151////////////////////////////////////////////////////////////////////////////////152153__forceinline bool get(const vboold4& a, size_t index) { return a[index]; }154__forceinline void set (vboold4& a, size_t index) { a[index] = -1; }155__forceinline void clear(vboold4& a, size_t index) { a[index] = 0; }156157////////////////////////////////////////////////////////////////////////////////158/// Output Operators159////////////////////////////////////////////////////////////////////////////////160161__forceinline embree_ostream operator <<(embree_ostream cout, const vboold4& a) {162return cout << "<" << a[0] << ", " << a[1] << ", " << a[2] << ", " << a[3] << ", "163<< a[4] << ", " << a[5] << ", " << a[6] << ", " << a[7] << ">";164}165}166167#undef vboolf168#undef vboold169#undef vint170#undef vuint171#undef vllong172#undef vfloat173#undef vdouble174175176