@ -313,12 +313,14 @@ static inline void Slow_CRC32(uint64_t* l, uint8_t const **p) {
table0_ [ c > > 24 ] ;
table0_ [ c > > 24 ] ;
}
}
# ifdef __SSE4_2__
static inline void Fast_CRC32 ( uint64_t * l , uint8_t const * * p ) {
static inline void Fast_CRC32 ( uint64_t * l , uint8_t const * * p ) {
# ifdef __SSE4_2__
* l = _mm_crc32_u64 ( * l , LE_LOAD64 ( * p ) ) ;
* l = _mm_crc32_u64 ( * l , LE_LOAD64 ( * p ) ) ;
* p + = 8 ;
* p + = 8 ;
}
# else
Slow_CRC32 ( l , p ) ;
# endif
# endif
}
template < void ( * CRC32 ) ( uint64_t * , uint8_t const * * ) >
template < void ( * CRC32 ) ( uint64_t * , uint8_t const * * ) >
uint32_t ExtendImpl ( uint32_t crc , const char * buf , size_t size ) {
uint32_t ExtendImpl ( uint32_t crc , const char * buf , size_t size ) {
@ -363,14 +365,22 @@ uint32_t ExtendImpl(uint32_t crc, const char* buf, size_t size) {
return l ^ 0xffffffffu ;
return l ^ 0xffffffffu ;
}
}
// Detect if SS42 or not.
static bool isSSE42 ( ) {
# if defined(__GNUC__) && defined(__x86_64__) && !defined(IOS_CROSS_COMPILE)
uint32_t c_ ;
uint32_t d_ ;
__asm__ ( " cpuid " : " =c " ( c_ ) , " =d " ( d_ ) : " a " ( 1 ) : " ebx " ) ;
return c_ & ( 1U < < 20 ) ; // copied from CpuId.h in Folly.
# else
return false ;
# endif
}
typedef uint32_t ( * Function ) ( uint32_t , const char * , size_t ) ;
typedef uint32_t ( * Function ) ( uint32_t , const char * , size_t ) ;
static inline Function Choose_Extend ( ) {
static inline Function Choose_Extend ( ) {
# ifdef __SSE4_2__
return isSSE42 ( ) ? ExtendImpl < Fast_CRC32 > : ExtendImpl < Slow_CRC32 > ;
return ExtendImpl < Fast_CRC32 > ;
# else
return ExtendImpl < Slow_CRC32 > ;
# endif
}
}
Function ChosenExtend = Choose_Extend ( ) ;
Function ChosenExtend = Choose_Extend ( ) ;