Add runtime aes/crypto check for ARM

Yocto apparantly enables it hard at compile time.

Change-Id: I1d4c7402eacc714859c61f469ebed85682d48b51
Reviewed-by: Thiago Macieira <thiago.macieira@intel.com>
This commit is contained in:
Allan Sandfeld Jensen 2021-04-19 16:43:00 +02:00
parent 5d0085049e
commit 8179d7edf6
3 changed files with 28 additions and 4 deletions

View File

@ -68,9 +68,11 @@
#define HWCAP_VFPv3D16 16384 #define HWCAP_VFPv3D16 16384
// copied from <asm/hwcap.h> (ARM): // copied from <asm/hwcap.h> (ARM):
#define HWCAP2_AES (1 << 0)
#define HWCAP2_CRC32 (1 << 4) #define HWCAP2_CRC32 (1 << 4)
// copied from <asm/hwcap.h> (Aarch64) // copied from <asm/hwcap.h> (Aarch64)
#define HWCAP_AES (1 << 3)
#define HWCAP_CRC32 (1 << 7) #define HWCAP_CRC32 (1 << 7)
// copied from <linux/auxvec.h> // copied from <linux/auxvec.h>
@ -93,12 +95,14 @@ QT_BEGIN_NAMESPACE
/* Data: /* Data:
neon neon
crc32 crc32
aes
*/ */
static const char features_string[] = static const char features_string[] =
" neon\0" " neon\0"
" crc32\0" " crc32\0"
" aes\0"
"\0"; "\0";
static const int features_indices[] = { 0, 6 }; static const int features_indices[] = { 0, 6, 13 };
#elif defined(Q_PROCESSOR_MIPS) #elif defined(Q_PROCESSOR_MIPS)
/* Data: /* Data:
dsp dsp
@ -152,6 +156,8 @@ static inline quint64 detectProcessorFeatures()
// For Aarch64: // For Aarch64:
if (vector[i+1] & HWCAP_CRC32) if (vector[i+1] & HWCAP_CRC32)
features |= CpuFeatureCRC32; features |= CpuFeatureCRC32;
if (vector[i+1] & HWCAP_AES)
features |= CpuFeatureAES;
# endif # endif
// Aarch32, or ARMv7 or before: // Aarch32, or ARMv7 or before:
if (vector[i+1] & HWCAP_NEON) if (vector[i+1] & HWCAP_NEON)
@ -162,6 +168,8 @@ static inline quint64 detectProcessorFeatures()
if (vector[i] == AT_HWCAP2) { if (vector[i] == AT_HWCAP2) {
if (vector[i+1] & HWCAP2_CRC32) if (vector[i+1] & HWCAP2_CRC32)
features |= CpuFeatureCRC32; features |= CpuFeatureCRC32;
if (vector[i+1] & HWCAP2_AES)
features |= CpuFeatureAES;
} }
# endif # endif
} }
@ -179,6 +187,9 @@ static inline quint64 detectProcessorFeatures()
#if defined(__ARM_FEATURE_CRC32) #if defined(__ARM_FEATURE_CRC32)
features |= CpuFeatureCRC32; features |= CpuFeatureCRC32;
#endif #endif
#if defined(__ARM_FEATURE_CRYPTO)
features |= CpuFeatureAES;
#endif
return features; return features;
} }
@ -586,6 +597,12 @@ Q_CORE_EXPORT QBasicAtomicInteger<unsigned> qt_cpu_features[2] = { Q_BASIC_ATOMI
quint64 qDetectCpuFeatures() quint64 qDetectCpuFeatures()
{ {
auto minFeatureTest = minFeature;
#if defined(Q_OS_LINUX) && defined(Q_PROCESSOR_ARM_64)
// Yocto hard-codes CRC32+AES on. Since they are unlikely to be used
// automatically by compilers, we can just add runtime check.
minFeatureTest &= ~(CpuFeatureAES|CpuFeatureCRC32);
#endif
quint64 f = detectProcessorFeatures(); quint64 f = detectProcessorFeatures();
QByteArray disable = qgetenv("QT_NO_CPU_FEATURE"); QByteArray disable = qgetenv("QT_NO_CPU_FEATURE");
if (!disable.isEmpty()) { if (!disable.isEmpty()) {
@ -601,8 +618,8 @@ quint64 qDetectCpuFeatures()
#else #else
bool runningOnValgrind = false; bool runningOnValgrind = false;
#endif #endif
if (Q_UNLIKELY(!runningOnValgrind && minFeature != 0 && (f & minFeature) != minFeature)) { if (Q_UNLIKELY(!runningOnValgrind && minFeatureTest != 0 && (f & minFeatureTest) != minFeatureTest)) {
quint64 missing = minFeature & ~f; quint64 missing = minFeatureTest & ~f;
fprintf(stderr, "Incompatible processor. This Qt build requires the following features:\n "); fprintf(stderr, "Incompatible processor. This Qt build requires the following features:\n ");
for (int i = 0; i < features_count; ++i) { for (int i = 0; i < features_count; ++i) {
if (missing & (Q_UINT64_C(1) << i)) if (missing & (Q_UINT64_C(1) << i))

View File

@ -311,6 +311,8 @@ enum CPUFeatures {
CpuFeatureNEON = 2, CpuFeatureNEON = 2,
CpuFeatureARM_NEON = CpuFeatureNEON, CpuFeatureARM_NEON = CpuFeatureNEON,
CpuFeatureCRC32 = 4, CpuFeatureCRC32 = 4,
CpuFeatureAES = 8,
CpuFeatureARM_CRYPTO = CpuFeatureAES,
#elif defined(Q_PROCESSOR_MIPS) #elif defined(Q_PROCESSOR_MIPS)
CpuFeatureDSP = 2, CpuFeatureDSP = 2,
CpuFeatureDSPR2 = 4, CpuFeatureDSPR2 = 4,
@ -327,6 +329,9 @@ static const quint64 qCompilerCpuFeatures = 0
#if defined __ARM_FEATURE_CRC32 #if defined __ARM_FEATURE_CRC32
| CpuFeatureCRC32 | CpuFeatureCRC32
#endif #endif
#if defined __ARM_FEATURE_CRYPTO
| CpuFeatureAES
#endif
#if defined __mips_dsp #if defined __mips_dsp
| CpuFeatureDSP | CpuFeatureDSP
#endif #endif

View File

@ -670,7 +670,9 @@ size_t qHashBits(const void *p, size_t size, size_t seed) noexcept
if (seed && qCpuHasFeature(AES) && qCpuHasFeature(SSE4_2)) if (seed && qCpuHasFeature(AES) && qCpuHasFeature(SSE4_2))
return aeshash(reinterpret_cast<const uchar *>(p), size, seed); return aeshash(reinterpret_cast<const uchar *>(p), size, seed);
#elif defined(__ARM_FEATURE_CRYPTO) #elif defined(__ARM_FEATURE_CRYPTO)
if (seed) // Do additional runtime check as Yocto hard enables Crypto extension for
// all armv8 configs
if (seed && (qCpuFeatures() & CpuFeatureAES))
return aeshash(reinterpret_cast<const uchar *>(p), size, seed); return aeshash(reinterpret_cast<const uchar *>(p), size, seed);
#endif #endif
if (size <= QT_POINTER_SIZE) if (size <= QT_POINTER_SIZE)