diff options
author | Thiago Macieira <thiago.macieira@intel.com> | 2022-02-18 17:29:58 -0800 |
---|---|---|
committer | Thiago Macieira <thiago.macieira@intel.com> | 2022-02-19 13:40:15 -0800 |
commit | 5f7e02efb8b70adf00a4f393e7c2a1c93daef9b3 (patch) | |
tree | 9dd184fd4702fe7d97bd50b994238f4a2f25a3ad /src/corelib/global | |
parent | ff63a38bb82849eb3eb13f7aae99fa2fa5d71e2d (diff) |
qsimd_p.h: Restore compatibility with C code
The qCpuHasFeature() macro doesn't work in C mode in x86 because it
tries to use enums only available in C++ mode, but the qCpuFeatures()
function does. You can write:
if ((qCompilerCpuFeatures & cpu_feature_avx2) ||
(qCpuFeatures() & cpu_feature_avx2))
In C code and this will compile.
Change-Id: Ic15405335d804bdea761fffd16d50dc4f17f572e
Reviewed-by: Allan Sandfeld Jensen <allan.jensen@qt.io>
Diffstat (limited to 'src/corelib/global')
-rw-r--r-- | src/corelib/global/qsimd.cpp | 11 | ||||
-rw-r--r-- | src/corelib/global/qsimd_p.h | 71 |
2 files changed, 32 insertions, 50 deletions
diff --git a/src/corelib/global/qsimd.cpp b/src/corelib/global/qsimd.cpp index 72fcf63094..d2a0686097 100644 --- a/src/corelib/global/qsimd.cpp +++ b/src/corelib/global/qsimd.cpp @@ -584,10 +584,10 @@ static inline uint detectProcessorFeatures() static const quint64 minFeature = qCompilerCpuFeatures; static constexpr auto SimdInitialized = QCpuFeatureType(1) << (sizeof(QCpuFeatureType) * 8 - 1); -QBasicAtomicInteger<QCpuFeatureType> qt_cpu_features[1] = { 0 }; +Q_ATOMIC(QCpuFeatureType) QT_MANGLE_NAMESPACE(qt_cpu_features)[1] = { 0 }; QT_FUNCTION_TARGET_BASELINE -quint64 qDetectCpuFeatures() +uint64_t QT_MANGLE_NAMESPACE(qDetectCpuFeatures)() { auto minFeatureTest = minFeature; #if defined(Q_OS_LINUX) && defined(Q_PROCESSOR_ARM_64) @@ -595,7 +595,7 @@ quint64 qDetectCpuFeatures() // automatically by compilers, we can just add runtime check. minFeatureTest &= ~(CpuFeatureAES|CpuFeatureCRC32); #endif - quint64 f = detectProcessorFeatures(); + QCpuFeatureType f = detectProcessorFeatures(); // Intentionally NOT qgetenv (this code runs too early) if (char *disable = getenv("QT_NO_CPU_FEATURE"); disable && *disable) { @@ -632,7 +632,8 @@ quint64 qDetectCpuFeatures() } assert((f & SimdInitialized) == 0); - qt_cpu_features[0].storeRelease(f | SimdInitialized); + f |= SimdInitialized; + std::atomic_store_explicit(QT_MANGLE_NAMESPACE(qt_cpu_features), f, std::memory_order_relaxed); return f; } @@ -791,7 +792,7 @@ static bool checkRdrndWorks() noexcept { return false; } namespace { struct QSimdInitializer { - inline QSimdInitializer() { qDetectCpuFeatures(); } + inline QSimdInitializer() { QT_MANGLE_NAMESPACE(qDetectCpuFeatures)(); } }; } diff --git a/src/corelib/global/qsimd_p.h b/src/corelib/global/qsimd_p.h index ad769ee7a6..ccb995588b 100644 --- a/src/corelib/global/qsimd_p.h +++ b/src/corelib/global/qsimd_p.h @@ -1,7 +1,7 @@ /**************************************************************************** ** -** Copyright (C) 2016 The Qt Company Ltd. -** Copyright (C) 2018 Intel Corporation. +** Copyright (C) 2021 The Qt Company Ltd. +** Copyright (C) 2022 Intel Corporation. ** Contact: https://www.qt.io/licensing/ ** ** This file is part of the QtCore module of the Qt Toolkit. @@ -253,28 +253,6 @@ asm( defined(__FMA__) && defined(__LZCNT__) && defined(__RDRND__) # define __haswell__ 1 # endif - -QT_BEGIN_NAMESPACE -static const quint64 qCompilerCpuFeatures = _compilerCpuFeatures; - -// This constant does not include all CPU features found in a Haswell, only -// those that we'd have optimized code for. -// Note: must use Q_CONSTEXPR here, as this file may be compiled in C mode. -static const quint64 CpuFeatureArchHaswell = 0 - | CpuFeatureSSE2 - | CpuFeatureSSE3 - | CpuFeatureSSSE3 - | CpuFeatureSSE4_1 - | CpuFeatureSSE4_2 - | CpuFeatureFMA - | CpuFeaturePOPCNT - | CpuFeatureAVX - | CpuFeatureF16C - | CpuFeatureAVX2 - | CpuFeatureBMI - | CpuFeatureBMI2; -QT_END_NAMESPACE - #endif /* Q_PROCESSOR_X86 */ // NEON intrinsics @@ -329,12 +307,6 @@ inline uint8_t vaddv_u8(uint8x8_t v8) #endif #endif - -#ifdef __cplusplus -#include <qatomic.h> - -QT_BEGIN_NAMESPACE - #ifndef Q_PROCESSOR_X86 enum CPUFeatures { #if defined(Q_PROCESSOR_ARM) @@ -368,29 +340,35 @@ static const quint64 qCompilerCpuFeatures = 0 ; #endif -#ifdef Q_PROCESSOR_X86 -using QCpuFeatureType = quint64; +#ifdef __cplusplus +# include <atomic> +# define Q_ATOMIC(T) std::atomic<T> +QT_BEGIN_NAMESPACE +using std::atomic_load_explicit; +static constexpr auto memory_order_relaxed = std::memory_order_relaxed; +extern "C" { #else -using QCpuFeatureType = unsigned; +# include <stdatomic.h> +# include <stdbool.h> +# define Q_ATOMIC(T) _Atomic(T) #endif -extern Q_CORE_EXPORT QBasicAtomicInteger<QCpuFeatureType> qt_cpu_features[1]; -Q_CORE_EXPORT quint64 qDetectCpuFeatures(); -#if defined(Q_PROCESSOR_X86) && QT_COMPILER_SUPPORTS_HERE(RDRND) && !defined(QT_BOOTSTRAPPED) -Q_CORE_EXPORT qsizetype qRandomCpu(void *, qsizetype) noexcept; +#ifdef Q_PROCESSOR_X86 +typedef uint64_t QCpuFeatureType; +static const QCpuFeatureType qCompilerCpuFeatures = _compilerCpuFeatures; +static const QCpuFeatureType CpuFeatureArchHaswell = cpu_haswell; #else -static inline qsizetype qRandomCpu(void *, qsizetype) noexcept -{ - return 0; -} +typedef unsigned QCpuFeatureType; #endif +extern Q_CORE_EXPORT Q_ATOMIC(QCpuFeatureType) QT_MANGLE_NAMESPACE(qt_cpu_features)[1]; +Q_CORE_EXPORT uint64_t QT_MANGLE_NAMESPACE(qDetectCpuFeatures)(); -static inline quint64 qCpuFeatures() +static inline uint64_t qCpuFeatures() { - quint64 features = qt_cpu_features[0].loadRelaxed(); - if constexpr (!QT_SUPPORTS_INIT_PRIORITY) { + quint64 features = atomic_load_explicit(QT_MANGLE_NAMESPACE(qt_cpu_features), memory_order_relaxed); + if (!QT_SUPPORTS_INIT_PRIORITY) { if (Q_UNLIKELY(features == 0)) - features = qDetectCpuFeatures(); + features = QT_MANGLE_NAMESPACE(qDetectCpuFeatures)(); } return features; } @@ -398,6 +376,9 @@ static inline quint64 qCpuFeatures() #define qCpuHasFeature(feature) (((qCompilerCpuFeatures & CpuFeature ## feature) == CpuFeature ## feature) \ || ((qCpuFeatures() & CpuFeature ## feature) == CpuFeature ## feature)) +#ifdef __cplusplus +} // extern "C" + # if defined(Q_PROCESSOR_X86) && QT_COMPILER_SUPPORTS_HERE(RDRND) && !defined(QT_BOOTSTRAPPED) Q_CORE_EXPORT qsizetype qRandomCpu(void *, qsizetype) noexcept; |