Home | History | Annotate | Download | only in src
      1 // Copyright 2006-2008 the V8 project authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #ifndef V8_COMPILER_INTRINSICS_H_
      6 #define V8_COMPILER_INTRINSICS_H_
      7 
      8 namespace v8 {
      9 namespace internal {
     10 
     11 class CompilerIntrinsics {
     12  public:
     13   // Returns number of zero bits preceding least significant 1 bit.
     14   // Undefined for zero value.
     15   INLINE(static int CountTrailingZeros(uint32_t value));
     16 
     17   // Returns number of zero bits following most significant 1 bit.
     18   // Undefined for zero value.
     19   INLINE(static int CountLeadingZeros(uint32_t value));
     20 
     21   // Returns the number of bits set.
     22   INLINE(static int CountSetBits(uint32_t value));
     23 };
     24 
     25 #ifdef __GNUC__
     26 int CompilerIntrinsics::CountTrailingZeros(uint32_t value) {
     27   return __builtin_ctz(value);
     28 }
     29 
     30 int CompilerIntrinsics::CountLeadingZeros(uint32_t value) {
     31   return __builtin_clz(value);
     32 }
     33 
     34 int CompilerIntrinsics::CountSetBits(uint32_t value) {
     35   return __builtin_popcount(value);
     36 }
     37 
     38 #elif defined(_MSC_VER)
     39 
     40 #pragma intrinsic(_BitScanForward)
     41 #pragma intrinsic(_BitScanReverse)
     42 
     43 int CompilerIntrinsics::CountTrailingZeros(uint32_t value) {
     44   unsigned long result;  //NOLINT
     45   _BitScanForward(&result, static_cast<long>(value));  //NOLINT
     46   return static_cast<int>(result);
     47 }
     48 
     49 int CompilerIntrinsics::CountLeadingZeros(uint32_t value) {
     50   unsigned long result;  //NOLINT
     51   _BitScanReverse(&result, static_cast<long>(value));  //NOLINT
     52   return 31 - static_cast<int>(result);
     53 }
     54 
     55 int CompilerIntrinsics::CountSetBits(uint32_t value) {
     56   // Manually count set bits.
     57   value = ((value >>  1) & 0x55555555) + (value & 0x55555555);
     58   value = ((value >>  2) & 0x33333333) + (value & 0x33333333);
     59   value = ((value >>  4) & 0x0f0f0f0f) + (value & 0x0f0f0f0f);
     60   value = ((value >>  8) & 0x00ff00ff) + (value & 0x00ff00ff);
     61   value = ((value >> 16) & 0x0000ffff) + (value & 0x0000ffff);
     62   return value;
     63 }
     64 
     65 #else
     66 #error Unsupported compiler
     67 #endif
     68 
     69 } }  // namespace v8::internal
     70 
     71 #endif  // V8_COMPILER_INTRINSICS_H_
     72