From b967b1449e0f6a9cd274cfec6dd3109e9ed0f821 Mon Sep 17 00:00:00 2001 From: Simon Hosie Date: Fri, 6 Nov 2015 16:36:43 +0000 Subject: [PATCH] Add ARMv8 CRC32C support. --- README | 8 +++++++- src/city-test.cc | 4 ++-- src/city.cc | 15 +++++++++++---- 3 files changed, 20 insertions(+), 7 deletions(-) diff --git a/README b/README index 0ec1917..ee576b8 100644 --- a/README +++ b/README @@ -99,12 +99,18 @@ On systems with gcc, we generally recommend: make all check CXXFLAGS="-g -O3" sudo make install -Or, if your system has the CRC32 instruction, and you want to build everything: +If your system has the SSE CRC32 instruction, and you want to build everything: ./configure --enable-sse4.2 make all check CXXFLAGS="-g -O3 -msse4.2" sudo make install +Or, for the ARMv8 CRC32C instruction: + +./configure --enable-sse4.2 +make all check CXXFLAGS="-g -O3 -march=armv8-a+crc" +sudo make install + Note that our build system doesn't try to determine the appropriate compiler flag for enabling SSE4.2. For gcc it is "-msse4.2". The --enable-sse4.2 flag to the configure script controls whether citycrc.h is installed when diff --git a/src/city-test.cc b/src/city-test.cc index 06c9828..b94ab25 100644 --- a/src/city-test.cc +++ b/src/city-test.cc @@ -22,7 +22,7 @@ #include #include #include "city.h" -#ifdef __SSE4_2__ +#if defined __SSE4_2__ || defined __ARM_FEATURE_CRC32 #include "citycrc.h" #endif @@ -1279,7 +1279,7 @@ void Test(const uint64* expected, int offset, int len) { Check(expected[4], Uint128High64(u)); Check(expected[5], Uint128Low64(v)); Check(expected[6], Uint128High64(v)); -#ifdef __SSE4_2__ +#if defined __SSE4_2__ || defined __ARM_FEATURE_CRC32 const uint128 y = CityHashCrc128(data + offset, len); const uint128 z = CityHashCrc128WithSeed(data + offset, len, kSeed128); uint64 crc256_results[4]; diff --git a/src/city.cc b/src/city.cc index 41cd5ee..65d882f 100644 --- a/src/city.cc +++ b/src/city.cc @@ -512,9 +512,16 @@ uint128 CityHash128(const char *s, size_t len) { CityHash128WithSeed(s, len, uint128(k0, k1)); } -#ifdef __SSE4_2__ +#if defined __SSE4_2__ || defined __ARM_FEATURE_CRC32 #include +#ifdef __SSE4_2__ #include +#define crc32_u64 _mm_crc32_u64 +#endif +#ifdef __ARM_FEATURE_CRC32 +#include +#define crc32_u64 __crc32cd +#endif // Requires len >= 240. static void CityHashCrc256Long(const char *s, size_t len, @@ -550,9 +557,9 @@ static void CityHashCrc256Long(const char *s, size_t len, g += e; \ e += z; \ g += x; \ - z = _mm_crc32_u64(z, b + g); \ - y = _mm_crc32_u64(y, e + h); \ - x = _mm_crc32_u64(x, f + a); \ + z = crc32_u64(z, b + g); \ + y = crc32_u64(y, e + h); \ + x = crc32_u64(x, f + a); \ e = Rotate(e, r); \ c += e; \ s += 40