diff --git a/.github/workflows/cross-ppc.yml b/.github/workflows/cross-ppc.yml index 82785efee..ca9cb5cbd 100644 --- a/.github/workflows/cross-ppc.yml +++ b/.github/workflows/cross-ppc.yml @@ -35,7 +35,7 @@ jobs: uses: actions/checkout@v6 - name: Setup run: | - cmake -B _build \ + cmake -B build/ \ -DBUILD_TESTS=ON -DDOWNLOAD_DOCTEST=ON \ -DBUILD_BENCHMARK=${{ matrix.target.full }} -DBUILD_EXAMPLES=${{ matrix.target.full }} \ -DCMAKE_BUILD_TYPE=Release \ @@ -43,7 +43,15 @@ jobs: -DCMAKE_CXX_FLAGS="${{ matrix.target.flags }}" \ -DCMAKE_TOOLCHAIN_FILE=${{ github.workspace }}/.github/toolchains/${{ matrix.sys.compiler }}-${{ matrix.target.dir }}.cmake - name: Build - run: cmake --build _build --verbose -j1 + run: cmake --build build/ --verbose -j1 + - name: Set CPU feature test expectations + run: | - name: Testing xsimd - run: qemu-${{ matrix.target.platform }} -cpu power10 -L /usr/${{ matrix.target.dir}}/ ./test/test_xsimd - working-directory: ${{ github.workspace }}/_build + run: | + # Set CPU feature test expectations, 0 is explicit absence of the feature + export XSIMD_TEST_CPU_ASSUME_SSE4_2="0" + export XSIMD_TEST_CPU_ASSUME_NEON64="0" + export XSIMD_TEST_CPU_ASSUME_RVV="0" + export XSIMD_TEST_CPU_ASSUME_VSX="1" + + qemu-${{ matrix.target.platform }} -cpu power10 -L /usr/${{ matrix.target.dir}}/ ./build/test/test_xsimd diff --git a/.github/workflows/linux.yml b/.github/workflows/linux.yml index 4585ae3b9..26c63e23a 100644 --- a/.github/workflows/linux.yml +++ b/.github/workflows/linux.yml @@ -123,6 +123,7 @@ jobs: # Set CPU feature test expectations, 0 is explicit absence of the feature export XSIMD_TEST_CPU_ASSUME_NEON64="0" export XSIMD_TEST_CPU_ASSUME_RVV="0" + export XSIMD_TEST_CPU_ASSUME_VSX="0" cd _build/test if echo '${{ matrix.sys.flags }}' | grep -q 'avx512' ; then # Running with emulation, must have AVX512, lower tier are checked by implications in tests diff --git a/include/xsimd/config/xsimd_config.hpp b/include/xsimd/config/xsimd_config.hpp index 662e550ff..9dd0c3347 100644 --- a/include/xsimd/config/xsimd_config.hpp +++ b/include/xsimd/config/xsimd_config.hpp @@ -499,6 +499,17 @@ #define XSIMD_WITH_WASM 0 #endif +/** + * @ingroup xsimd_config_macro + * + * Set to 1 if the target is in the PowerPC architecture family, to 0 otherwise + */ +#if defined(__powerpc__) || defined(__powerpc64__) || defined(_ARCH_PPC) || defined(_ARCH_PPC64) +#define XSIMD_TARGET_PPC 1 +#else +#define XSIMD_TARGET_PPC 0 +#endif + /** * @ingroup xsimd_config_macro * diff --git a/include/xsimd/config/xsimd_cpu_features_ppc.hpp b/include/xsimd/config/xsimd_cpu_features_ppc.hpp new file mode 100644 index 000000000..510124617 --- /dev/null +++ b/include/xsimd/config/xsimd_cpu_features_ppc.hpp @@ -0,0 +1,54 @@ +/*************************************************************************** + * Copyright (c) Johan Mabille, Sylvain Corlay, Wolf Vollprecht and * + * Martin Renou * + * Copyright (c) QuantStack * + * Copyright (c) Serge Guelton * + * * + * Distributed under the terms of the BSD 3-Clause License. * + * * + * The full license is in the file LICENSE, distributed with this software. * + ***************************************************************************/ + +#ifndef XSIMD_CPU_FEATURES_PPC_HPP +#define XSIMD_CPU_FEATURES_PPC_HPP + +#include "./xsimd_config.hpp" +#include "./xsimd_getauxval.hpp" + +namespace xsimd +{ + /** + * An opinionated CPU feature detection utility for PowerPC. + * + * On Linux, runtime detection uses getauxval to query the auxiliary vector. + * On other platforms, only compile-time information is used. + * + * This is well defined on all architectures. + * It will always return false on non-PowerPC architectures. + */ + class ppc_cpu_features : private linux_hwcap_backend_default + { + public: + inline bool vsx() const noexcept; + }; + + /******************** + * Implementation * + ********************/ + + inline bool ppc_cpu_features::vsx() const noexcept + { +#if XSIMD_TARGET_PPC && XSIMD_HAVE_LINUX_GETAUXVAL +#ifdef PPC_FEATURE_HAS_VSX + return hwcap().has_feature(PPC_FEATURE_HAS_VSX); +#else + // Possibly missing on older Linux distributions + return hwcap().has_feature(0x00000080); +#endif +#else + return XSIMD_WITH_VSX; +#endif + } +} + +#endif diff --git a/include/xsimd/config/xsimd_cpuid.hpp b/include/xsimd/config/xsimd_cpuid.hpp index d58897f66..38b84c79f 100644 --- a/include/xsimd/config/xsimd_cpuid.hpp +++ b/include/xsimd/config/xsimd_cpuid.hpp @@ -14,6 +14,7 @@ #include "../types/xsimd_all_registers.hpp" #include "./xsimd_cpu_features_arm.hpp" +#include "./xsimd_cpu_features_ppc.hpp" #include "./xsimd_cpu_features_riscv.hpp" #include "./xsimd_cpu_features_x86.hpp" #include "./xsimd_inline.hpp" @@ -80,9 +81,10 @@ namespace xsimd wasm = 1; #endif -#if XSIMD_WITH_VSX - vsx = 1; -#endif + // Safe on all platforms, it will be false if non PowerPC. + const auto ppc_cpu = xsimd::ppc_cpu_features(); + + vsx = ppc_cpu.vsx(); // Safe on all platforms, it will be all false if non risc-v. const auto riscv_cpu = xsimd::riscv_cpu_features(); diff --git a/test/test_cpu_features.cpp b/test/test_cpu_features.cpp index fdc15d745..0e127e855 100644 --- a/test/test_cpu_features.cpp +++ b/test/test_cpu_features.cpp @@ -169,3 +169,10 @@ TEST_CASE("[cpu_features] risc-v features from environment") CHECK_ENV_FEATURE("XSIMD_TEST_CPU_ASSUME_RVV", cpu.rvv()); } + +TEST_CASE("[cpu_features] ppc features from environment") +{ + xsimd::ppc_cpu_features cpu; + + CHECK_ENV_FEATURE("XSIMD_TEST_CPU_ASSUME_VSX", cpu.vsx()); +}