diff options
author | Kostya Kortchinsky <kostyak@google.com> | 2017-01-10 16:39:36 +0000 |
---|---|---|
committer | Kostya Kortchinsky <kostyak@google.com> | 2017-01-10 16:39:36 +0000 |
commit | c4d8f3f75433e6eb6ef37a23255fa8e9becfb70f (patch) | |
tree | 0a2599ed57e758980c895fd79fe396e76c3aa6bf /lib/scudo/scudo_crc32.cpp | |
parent | 60d67c3850c0d7768976410a996368ab56a0f4bf (diff) |
[scudo] Separate hardware CRC32 routines
Summary:
As raised in D28304, enabling SSE 4.2 for the whole Scudo tree leads to the
emission of SSE 4.2 instructions everywhere, while the runtime checks only
applied to the CRC32 computing function.
This patch separates the CRC32 function taking advantage of the hardware into
its own file, and only enabled -msse4.2 for that file, if detected to be
supported by the compiler.
Another consequence of removing SSE4.2 globally is realizing that memcpy were
not being optimized, which turned out to be due to the -fno-builtin in
SANITIZER_COMMON_CFLAGS. So we now explicitely enable builtins for Scudo.
The resulting assembly looks good, with some CALLs are introduced instead of
the CRC32 code being inlined.
Reviewers: kcc, mgorny, alekseyshl
Subscribers: llvm-commits
Differential Revision: https://reviews.llvm.org/D28417
git-svn-id: https://llvm.org/svn/llvm-project/compiler-rt/trunk@291570 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/scudo/scudo_crc32.cpp')
-rw-r--r-- | lib/scudo/scudo_crc32.cpp | 53 |
1 files changed, 53 insertions, 0 deletions
diff --git a/lib/scudo/scudo_crc32.cpp b/lib/scudo/scudo_crc32.cpp new file mode 100644 index 000000000..94c8c2424 --- /dev/null +++ b/lib/scudo/scudo_crc32.cpp @@ -0,0 +1,53 @@ +//===-- scudo_crc32.cpp -----------------------------------------*- C++ -*-===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// +/// +/// CRC32 function leveraging hardware specific instructions. This has to be +/// kept separated to restrict the use of compiler specific flags to this file. +/// +//===----------------------------------------------------------------------===// + +// Hardware CRC32 is supported at compilation via the following: +// - for i386 & x86_64: -msse4.2 +// - for ARM & AArch64: -march=armv8-a+crc or -mcrc +// An additional check must be performed at runtime as well to make sure the +// emitted instructions are valid on the target host. +#include "scudo_crc32.h" +#include "scudo_utils.h" + +#if defined(__SSE4_2__) || defined(__ARM_FEATURE_CRC32) +# ifdef __SSE4_2__ +# include <smmintrin.h> +# define CRC32_INTRINSIC FIRST_32_SECOND_64(_mm_crc32_u32, _mm_crc32_u64) +# endif +# ifdef __ARM_FEATURE_CRC32 +# include <arm_acle.h> +# define CRC32_INTRINSIC FIRST_32_SECOND_64(__crc32cw, __crc32cd) +# endif +#endif // defined(__SSE4_2__) || defined(__ARM_FEATURE_CRC32) + +namespace __scudo { + +#if defined(__SSE4_2__) || defined(__ARM_FEATURE_CRC32) +INLINE u32 computeHardwareCRC32(u32 Crc, uptr Data) { + return CRC32_INTRINSIC(Crc, Data); +} + +u32 computeCRC32(u32 Crc, uptr Data, u8 HashType) { + if (HashType == CRC32Hardware) { + return computeHardwareCRC32(Crc, Data); + } + return computeSoftwareCRC32(Crc, Data); +} +#else +u32 computeCRC32(u32 Crc, uptr Data, u8 HashType) { + return computeSoftwareCRC32(Crc, Data); +} +#endif // defined(__SSE4_2__) || defined(__ARM_FEATURE_CRC32) + +} // namespace __scudo |