Avoid undefined behavior from memcpy for the portable build.

This commit is contained in:
Zoltan Szabadka 2015-09-28 12:38:29 +02:00
parent 10aaa83ffe
commit 5919712922
2 changed files with 14 additions and 3 deletions

View File

@ -94,7 +94,16 @@ static uint32_t DecodeWindowBits(BrotliBitReader* br) {
static BROTLI_INLINE BROTLI_NO_ASAN void memmove16( static BROTLI_INLINE BROTLI_NO_ASAN void memmove16(
uint8_t* dst, uint8_t* src) { uint8_t* dst, uint8_t* src) {
#ifdef __ARM_NEON__ #if BROTLI_SAFE_MEMMOVE
/* For x86 this compiles to the same binary as signle memcpy.
On ARM memcpy is not inlined, so it works slower.
This implementation makes decompression 1% slower than regular one,
and 2% slower than NEON implementation.
*/
uint32_t buffer[4];
memcpy(buffer, src, 16);
memcpy(dst, buffer, 16);
#elif defined(__ARM_NEON__)
vst1q_u8(dst, vld1q_u8(src)); vst1q_u8(dst, vld1q_u8(src));
#else #else
/* memcpy is unsafe for overlapping regions and ASAN detects this. /* memcpy is unsafe for overlapping regions and ASAN detects this.

View File

@ -17,7 +17,7 @@
Build options are: Build options are:
* BROTLI_BUILD_PORTABLE disables dangerous optimizations, like unaligned * BROTLI_BUILD_PORTABLE disables dangerous optimizations, like unaligned
read and overlapping memcpy read and overlapping memcpy; this reduces decompression speed by 5%
* BROTLI_DEBUG dumps file name and line number when decoder detects stream * BROTLI_DEBUG dumps file name and line number when decoder detects stream
or memory error or memory error
* BROTLI_DECODE_DEBUG enables asserts and dumps various state information * BROTLI_DECODE_DEBUG enables asserts and dumps various state information
@ -43,8 +43,10 @@
#ifdef BROTLI_BUILD_PORTABLE #ifdef BROTLI_BUILD_PORTABLE
#define BROTLI_ALIGNED_READ 1 #define BROTLI_ALIGNED_READ 1
#define BROTLI_SAFE_MEMMOVE 1
#else #else
#define BROTLI_ALIGNED_READ 0 #define BROTLI_ALIGNED_READ 0
#define BROTLI_SAFE_MEMMOVE 0
#endif #endif
#define BROTLI_ASAN_BUILD __has_feature(address_sanitizer) #define BROTLI_ASAN_BUILD __has_feature(address_sanitizer)
@ -136,7 +138,7 @@ OR:
#define BROTLI_NOINLINE #define BROTLI_NOINLINE
#endif #endif
#if BROTLI_ASAN_BUILD #if BROTLI_ASAN_BUILD && !defined(BROTLI_BUILD_PORTABLE)
#define BROTLI_NO_ASAN __attribute__((no_sanitize("address"))) BROTLI_NOINLINE #define BROTLI_NO_ASAN __attribute__((no_sanitize("address"))) BROTLI_NOINLINE
#else #else
#define BROTLI_NO_ASAN #define BROTLI_NO_ASAN