From 1dd8582ab547d74fb72e1932899041d24035e99f Mon Sep 17 00:00:00 2001 From: Wes McKinney Date: Mon, 14 Mar 2016 13:49:59 -0700 Subject: [PATCH] PARQUET-488: Add SSE cmake toggle, fix build on systems without SSE I added an option to make SSE strictly opt-in for now. As a side effect of this, parquet-cpp now builds and the test suite passes out of the box on 32-bit ARMv7 (I tried it on my RaspberryPi Model B 2). Author: Wes McKinney Closes #74 from wesm/PARQUET-488 and squashes the following commits: 61225e9 [Wes McKinney] Use -march=native 3833efd [Wes McKinney] Remove stale cmake comment 70fcf65 [Wes McKinney] Add cmake PARQUET_USE_SSE option 775c72d [Wes McKinney] Fix compilation on arm7/raspberrypi Change-Id: If8e4e7e1b7fc64df952cb8b82662bb017ca56f72 --- cpp/src/parquet/util/bit-util.h | 4 ++++ cpp/src/parquet/util/cpu-info.cc | 1 - cpp/src/parquet/util/hash-util.h | 4 ++++ cpp/src/parquet/util/sse-util.h | 41 ++++++++++++++++++++++++++------ 4 files changed, 42 insertions(+), 8 deletions(-) diff --git a/cpp/src/parquet/util/bit-util.h b/cpp/src/parquet/util/bit-util.h index 2b4014b823ef4..6bbe8593b655a 100644 --- a/cpp/src/parquet/util/bit-util.h +++ b/cpp/src/parquet/util/bit-util.h @@ -151,11 +151,15 @@ class BitUtil { /// Returns the number of set bits in x static inline int Popcount(uint64_t x) { +#ifdef PARQUET_USE_SSE if (LIKELY(CpuInfo::IsSupported(CpuInfo::POPCNT))) { return POPCNT_popcnt_u64(x); } else { return PopcountNoHw(x); } +#else + return PopcountNoHw(x); +#endif } // Compute correct population count for various-width signed integers diff --git a/cpp/src/parquet/util/cpu-info.cc b/cpp/src/parquet/util/cpu-info.cc index 2a9f59d2b11d1..b994f2a536071 100644 --- a/cpp/src/parquet/util/cpu-info.cc +++ b/cpp/src/parquet/util/cpu-info.cc @@ -24,7 +24,6 @@ #include #endif -#include #include #include #include diff --git a/cpp/src/parquet/util/hash-util.h b/cpp/src/parquet/util/hash-util.h index 5572ca931a43e..d8b991794173f 100644 --- a/cpp/src/parquet/util/hash-util.h +++ b/cpp/src/parquet/util/hash-util.h @@ -202,11 +202,15 @@ class HashUtil { /// Seed values for different steps of the query execution should use different seeds /// to prevent accidental key collisions. (See IMPALA-219 for more details). static uint32_t Hash(const void* data, int32_t bytes, uint32_t seed) { +#ifdef PARQUET_USE_SSE if (LIKELY(CpuInfo::IsSupported(CpuInfo::SSE4_2))) { return CrcHash(data, bytes, seed); } else { return MurmurHash2_64(data, bytes, seed); } +#else + return MurmurHash2_64(data, bytes, seed); +#endif } /// The magic number (used in hash_combine()) 0x9e3779b9 = 2^32 / (golden ratio). diff --git a/cpp/src/parquet/util/sse-util.h b/cpp/src/parquet/util/sse-util.h index 29bf2f9adf2a6..b173a1f5b9d5f 100644 --- a/cpp/src/parquet/util/sse-util.h +++ b/cpp/src/parquet/util/sse-util.h @@ -21,7 +21,9 @@ #ifndef PARQUET_UTIL_SSE_UTIL_H #define PARQUET_UTIL_SSE_UTIL_H +#ifdef PARQUET_USE_SSE #include +#endif namespace parquet_cpp { @@ -71,6 +73,8 @@ namespace SSEUtil { }; } // namespace SSEUtil +#ifdef PARQUET_USE_SSE + /// Define the SSE 4.2 intrinsics. The caller must first verify at runtime (or codegen /// IR load time) that the processor supports SSE 4.2 before calling these. These are /// defined outside the namespace because the IR w/ SSE 4.2 case needs to use macros. @@ -81,12 +85,6 @@ namespace SSEUtil { /// (IMPALA-1399/1646). The compiler intrinsics cannot be used without -msse4.2, so we /// define our own implementations of the intrinsics instead. -#if defined(__SSE4_1__) || defined(__POPCNT__) -/// Impala native code should not be compiled with -msse4.1 or higher until the minimum -/// CPU requirement is raised to at least the targeted instruction set. -#error "Do not compile with -msse4.1 or higher." -#endif - /// The PCMPxSTRy instructions require that the control byte 'mode' be encoded as an /// immediate. So, those need to be always inlined in order to always propagate the /// mode constant into the inline asm. @@ -214,7 +212,36 @@ static inline int64_t POPCNT_popcnt_u64(uint64_t a) { return 0; } -#endif +#endif // IR_COMPILE + +#else + +static inline uint32_t SSE4_crc32_u8(uint32_t crc, uint8_t v) { + DCHECK(false) << "SSE support is not enabled"; + return 0; +} + +static inline uint32_t SSE4_crc32_u16(uint32_t crc, uint16_t v) { + DCHECK(false) << "SSE support is not enabled"; + return 0; +} + +static inline uint32_t SSE4_crc32_u32(uint32_t crc, uint32_t v) { + DCHECK(false) << "SSE support is not enabled"; + return 0; +} + +static inline uint32_t SSE4_crc32_u64(uint32_t crc, uint64_t v) { + DCHECK(false) << "SSE support is not enabled"; + return 0; +} + +static inline int64_t POPCNT_popcnt_u64(uint64_t a) { + DCHECK(false) << "SSE support is not enabled"; + return 0; +} + +#endif // PARQUET_USE_SSE } // namespace parquet_cpp