You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@impala.apache.org by mi...@apache.org on 2026/09/23 03:08:23 UTC

(impala) 01/02: IMPALA-15369: Check for the CRC32 extension at startup on ARM64

This is an automated email from the ASF dual-hosted git repository.

asf-gitbox-commits pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/impala.git

commit 74159a83430aa0b9ea0ac4dcb9a4c965ebf3a681
Author: Zoltan Borok-Nagy <bo...@cloudera.com>
AuthorDate: Thu Sep 17 16:05:24 2026 +0200

    IMPALA-15369: Check for the CRC32 extension at startup on ARM64
    
    On aarch64, Impala is built with -march=armv8-a+crc, and native code
    and codegen use CRC32 instructions for hashing (HashUtil::Hash(),
    LlvmCodeGen::GetHashFunction()) without checking for them at runtime.
    The CRC32 extension is optional in ARMv8.0, so on such CPUs the daemons
    crash with SIGILL once a CRC32 code path runs, instead of failing at
    startup with a clear message.
    
    This change adds a CpuInfo::CRC32 hardware flag. CpuInfo::Init() now
    also parses the 'Features' line of /proc/cpuinfo, which is where the
    kernel lists the CPU features on aarch64 (x86_64 uses 'flags').
    CpuInfo::EnforceCpuRequirements() fails on aarch64 if CRC32 is not
    supported. All daemons already call it from InitCommonRuntime() and
    exit with an error message if it fails, like for the AVX/AVX2
    requirement on x86_64.
    
    Testing:
     - Core tests show no new errors on ARM machine
    
    Change-Id: Ic01f8f8009e6e2d8dbfd324d83353b0d4dbf1d4c
    Assisted-by: Claude Opus 5.5 (Claude Code)
    Reviewed-on: http://gerrit.cloudera.org:8080/24888
    Reviewed-by: Impala Public Jenkins <im...@cloudera.com>
    Tested-by: Impala Public Jenkins <im...@cloudera.com>
---
 be/src/util/cpu-info.cc | 19 +++++++++++++++----
 be/src/util/cpu-info.h  |  2 ++
 2 files changed, 17 insertions(+), 4 deletions(-)

diff --git a/be/src/util/cpu-info.cc b/be/src/util/cpu-info.cc
index 8c3b33627..660d00bc5 100644
--- a/be/src/util/cpu-info.cc
+++ b/be/src/util/cpu-info.cc
@@ -75,6 +75,7 @@ const int64_t CpuInfo::POPCNT;
 const int64_t CpuInfo::AVX;
 const int64_t CpuInfo::AVX2;
 const int64_t CpuInfo::PCLMULQDQ;
+const int64_t CpuInfo::CRC32;
 
 bool CpuInfo::initialized_ = false;
 int64_t CpuInfo::hardware_flags_ = 0;
@@ -99,7 +100,8 @@ static struct {
   { "popcnt",    CpuInfo::POPCNT },
   { "avx",       CpuInfo::AVX },
   { "avx2",      CpuInfo::AVX2 },
-  { "pclmulqdq", CpuInfo::PCLMULQDQ }
+  { "pclmulqdq", CpuInfo::PCLMULQDQ },
+  { "crc32",     CpuInfo::CRC32 }
 };
 static const long num_flags = sizeof(flag_mappings) / sizeof(flag_mappings[0]);
 
@@ -135,7 +137,9 @@ void CpuInfo::Init() {
       value = line.substr(colon + 1, string::npos);
       trim(name);
       trim(value);
-      if (name.compare("flags") == 0) {
+      // The CPU flags are listed under 'flags' on x86_64 and under 'Features' on
+      // aarch64.
+      if (name.compare("flags") == 0 || name.compare("Features") == 0) {
         hardware_flags_ |= ParseCPUFlags(value);
       } else if (name.compare("cpu MHz") == 0) {
         // Every core will report a different speed.  We'll take the max, assuming
@@ -253,8 +257,7 @@ void CpuInfo::InitNumaNodeToCores() {
 }
 
 Status CpuInfo::EnforceCpuRequirements() {
-  // This imposes a CPU requirement for x86_64. This function may later be modified
-  // to impose a similar requirement for other platforms.
+  // This imposes a CPU requirement for x86_64 and aarch64.
 #ifdef __x86_64__
   if (!CpuInfo::IsSupported(CpuInfo::AVX)) {
     return Status("This machine does not meet the minimum requirements for Impala "
@@ -269,6 +272,14 @@ Status CpuInfo::EnforceCpuRequirements() {
                   "Extensions 2). To run in legacy mode with only AVX support, "
                   "set enable_legacy_avx_support=true.");
   }
+#elif defined(__aarch64__)
+  // Impala is built with -march=armv8-a+crc and uses CRC32 instructions for hashing
+  // without checking for them at runtime. The CRC32 extension is optional in ARMv8.0
+  // (and mandatory from ARMv8.1), so verify that the CPU supports it.
+  if (!CpuInfo::IsSupported(CpuInfo::CRC32)) {
+    return Status("This machine does not meet the minimum requirements for Impala "
+                  "functionality. The CPU does not support the ARMv8 CRC32 extension.");
+  }
 #endif
   return Status::OK();
 }
diff --git a/be/src/util/cpu-info.h b/be/src/util/cpu-info.h
index f3154b110..58bbefb74 100644
--- a/be/src/util/cpu-info.h
+++ b/be/src/util/cpu-info.h
@@ -46,6 +46,8 @@ class CpuInfo {
   static const int64_t AVX       = (1 << 5);
   static const int64_t AVX2      = (1 << 6);
   static const int64_t PCLMULQDQ = (1 << 7);
+  /// ARMv8 CRC32 extension (aarch64 only).
+  static const int64_t CRC32     = (1 << 8);
 
   /// Cache enums for L1 (data), L2 and L3
   enum CacheLevel {