138cd7de5STim Shen //===----------------------------------------------------------------------===// 238cd7de5STim Shen // 357b08b09SChandler Carruth // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 457b08b09SChandler Carruth // See https://llvm.org/LICENSE.txt for license information. 557b08b09SChandler Carruth // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 638cd7de5STim Shen // 738cd7de5STim Shen //===----------------------------------------------------------------------===// 838cd7de5STim Shen 938cd7de5STim Shen // UNSUPPORTED: c++98, c++03, c++11, c++14 1038cd7de5STim Shen 1138cd7de5STim Shen // <experimental/simd> 1238cd7de5STim Shen // 1338cd7de5STim Shen // loads [simd.load] 1438cd7de5STim Shen // template <class U, class Flags> void copy_from(const U* mem, Flags f); 1538cd7de5STim Shen 1638cd7de5STim Shen #include <experimental/simd> 1738cd7de5STim Shen #include <cstdint> 18*a0686015SDavid Zarzycki #include <cassert> 1938cd7de5STim Shen 2038cd7de5STim Shen #include "test_macros.h" 2138cd7de5STim Shen 2238cd7de5STim Shen namespace ex = std::experimental::parallelism_v2; 2338cd7de5STim Shen 2438cd7de5STim Shen template <class T, class... Args> 2538cd7de5STim Shen auto not_supported_load(Args&&... args) -> decltype( 2638cd7de5STim Shen std::declval<ex::native_simd<T>>().copy_from(std::forward<Args>(args)...), 2738cd7de5STim Shen void()) = delete; 2838cd7de5STim Shen 2938cd7de5STim Shen template <class T> 3038cd7de5STim Shen void not_supported_load(...) {} 3138cd7de5STim Shen 3238cd7de5STim Shen template <class T, class... Args> 3338cd7de5STim Shen auto supported_load(Args&&... args) -> decltype( 3438cd7de5STim Shen std::declval<ex::native_simd<T>>().copy_from(std::forward<Args>(args)...), 3538cd7de5STim Shen void()) {} 3638cd7de5STim Shen 3738cd7de5STim Shen template <class T> 3838cd7de5STim Shen void supported_load(...) = delete; 3938cd7de5STim Shen 4038cd7de5STim Shen void compile_load() { 4138cd7de5STim Shen supported_load<int>((int*)nullptr, ex::element_aligned_tag()); 4238cd7de5STim Shen supported_load<uint32_t>((int*)nullptr, ex::element_aligned_tag()); 4338cd7de5STim Shen supported_load<double>((float*)nullptr, ex::element_aligned_tag()); 4438cd7de5STim Shen supported_load<uint16_t>((unsigned int*)nullptr, ex::element_aligned_tag()); 4538cd7de5STim Shen supported_load<uint32_t>((float*)nullptr, ex::element_aligned_tag()); 4638cd7de5STim Shen 4738cd7de5STim Shen not_supported_load<int>((int*)nullptr, int()); 4838cd7de5STim Shen } 4938cd7de5STim Shen 5038cd7de5STim Shen template <typename SimdType> 5138cd7de5STim Shen void test_load() { 5238cd7de5STim Shen alignas(32) int32_t buffer[] = {4, 3, 2, 1}; 5338cd7de5STim Shen { 5438cd7de5STim Shen SimdType a; 5538cd7de5STim Shen a.copy_from(buffer, ex::element_aligned_tag()); 5638cd7de5STim Shen assert(a[0] == 4); 5738cd7de5STim Shen assert(a[1] == 3); 5838cd7de5STim Shen assert(a[2] == 2); 5938cd7de5STim Shen assert(a[3] == 1); 6038cd7de5STim Shen } 6138cd7de5STim Shen { 6238cd7de5STim Shen SimdType a; 6338cd7de5STim Shen a.copy_from(buffer, ex::vector_aligned_tag()); 6438cd7de5STim Shen assert(a[0] == 4); 6538cd7de5STim Shen assert(a[1] == 3); 6638cd7de5STim Shen assert(a[2] == 2); 6738cd7de5STim Shen assert(a[3] == 1); 6838cd7de5STim Shen } 6938cd7de5STim Shen { 7038cd7de5STim Shen SimdType a; 7138cd7de5STim Shen a.copy_from(buffer, ex::overaligned_tag<32>()); 7238cd7de5STim Shen assert(a[0] == 4); 7338cd7de5STim Shen assert(a[1] == 3); 7438cd7de5STim Shen assert(a[2] == 2); 7538cd7de5STim Shen assert(a[3] == 1); 7638cd7de5STim Shen } 7738cd7de5STim Shen 7838cd7de5STim Shen { 7938cd7de5STim Shen SimdType a; 8038cd7de5STim Shen a.copy_from(buffer, ex::element_aligned); 8138cd7de5STim Shen assert(a[0] == 4); 8238cd7de5STim Shen assert(a[1] == 3); 8338cd7de5STim Shen assert(a[2] == 2); 8438cd7de5STim Shen assert(a[3] == 1); 8538cd7de5STim Shen } 8638cd7de5STim Shen { 8738cd7de5STim Shen SimdType a; 8838cd7de5STim Shen a.copy_from(buffer, ex::vector_aligned); 8938cd7de5STim Shen assert(a[0] == 4); 9038cd7de5STim Shen assert(a[1] == 3); 9138cd7de5STim Shen assert(a[2] == 2); 9238cd7de5STim Shen assert(a[3] == 1); 9338cd7de5STim Shen } 9438cd7de5STim Shen { 9538cd7de5STim Shen SimdType a; 9638cd7de5STim Shen a.copy_from(buffer, ex::overaligned<32>); 9738cd7de5STim Shen assert(a[0] == 4); 9838cd7de5STim Shen assert(a[1] == 3); 9938cd7de5STim Shen assert(a[2] == 2); 10038cd7de5STim Shen assert(a[3] == 1); 10138cd7de5STim Shen } 10238cd7de5STim Shen } 10338cd7de5STim Shen 10438cd7de5STim Shen template <typename SimdType> 10538cd7de5STim Shen void test_converting_load() { 10638cd7de5STim Shen float buffer[] = {1., 2., 4., 8.}; 10738cd7de5STim Shen SimdType a; 10838cd7de5STim Shen a.copy_from(buffer, ex::element_aligned_tag()); 10938cd7de5STim Shen assert(a[0] == 1); 11038cd7de5STim Shen assert(a[1] == 2); 11138cd7de5STim Shen assert(a[2] == 4); 11238cd7de5STim Shen assert(a[3] == 8); 11338cd7de5STim Shen } 11438cd7de5STim Shen 1152df59c50SJF Bastien int main(int, char**) { 11638cd7de5STim Shen // TODO: adjust the tests when this assertion fails. 11738cd7de5STim Shen assert(ex::native_simd<int32_t>::size() >= 4); 11838cd7de5STim Shen test_load<ex::native_simd<int32_t>>(); 11938cd7de5STim Shen test_load<ex::fixed_size_simd<int32_t, 4>>(); 12038cd7de5STim Shen test_converting_load<ex::native_simd<int32_t>>(); 12138cd7de5STim Shen test_converting_load<ex::fixed_size_simd<int32_t, 4>>(); 1222df59c50SJF Bastien 1232df59c50SJF Bastien return 0; 12438cd7de5STim Shen } 125