1//===-- InstructionUtils.h --------------------------------------*- C++ -*-===// 2// 3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4// See https://llvm.org/LICENSE.txt for license information. 5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6// 7//===----------------------------------------------------------------------===// 8 9#ifndef LLDB_SOURCE_PLUGINS_PROCESS_UTILITY_INSTRUCTIONUTILS_H 10#define LLDB_SOURCE_PLUGINS_PROCESS_UTILITY_INSTRUCTIONUTILS_H 11 12#include <cassert> 13#include <cstdint> 14 15// Common utilities for manipulating instruction bit fields. 16 17namespace lldb_private { 18 19// Return the bit field(s) from the most significant bit (msbit) to the 20// least significant bit (lsbit) of a 64-bit unsigned value. 21static inline uint64_t Bits64(const uint64_t bits, const uint32_t msbit, 22 const uint32_t lsbit) { 23 assert(msbit < 64 && lsbit <= msbit); 24 return (bits >> lsbit) & ((1ull << (msbit - lsbit + 1)) - 1); 25} 26 27// Return the bit field(s) from the most significant bit (msbit) to the 28// least significant bit (lsbit) of a 32-bit unsigned value. 29static inline uint32_t Bits32(const uint32_t bits, const uint32_t msbit, 30 const uint32_t lsbit) { 31 assert(msbit < 32 && lsbit <= msbit); 32 return (bits >> lsbit) & ((1u << (msbit - lsbit + 1)) - 1); 33} 34 35// Return the bit value from the 'bit' position of a 32-bit unsigned value. 36static inline uint32_t Bit32(const uint32_t bits, const uint32_t bit) { 37 return (bits >> bit) & 1u; 38} 39 40static inline uint64_t Bit64(const uint64_t bits, const uint32_t bit) { 41 return (bits >> bit) & 1ull; 42} 43 44// Set the bit field(s) from the most significant bit (msbit) to the 45// least significant bit (lsbit) of a 32-bit unsigned value to 'val'. 46static inline void SetBits32(uint32_t &bits, const uint32_t msbit, 47 const uint32_t lsbit, const uint32_t val) { 48 assert(msbit < 32 && lsbit < 32 && msbit >= lsbit); 49 uint32_t mask = ((1u << (msbit - lsbit + 1)) - 1); 50 bits &= ~(mask << lsbit); 51 bits |= (val & mask) << lsbit; 52} 53 54// Set the 'bit' position of a 32-bit unsigned value to 'val'. 55static inline void SetBit32(uint32_t &bits, const uint32_t bit, 56 const uint32_t val) { 57 SetBits32(bits, bit, bit, val); 58} 59 60// Rotate a 32-bit unsigned value right by the specified amount. 61static inline uint32_t Rotr32(uint32_t bits, uint32_t amt) { 62 assert(amt < 32 && "Invalid rotate amount"); 63 return (bits >> amt) | (bits << ((32 - amt) & 31)); 64} 65 66// Rotate a 32-bit unsigned value left by the specified amount. 67static inline uint32_t Rotl32(uint32_t bits, uint32_t amt) { 68 assert(amt < 32 && "Invalid rotate amount"); 69 return (bits << amt) | (bits >> ((32 - amt) & 31)); 70} 71 72// Create a mask that starts at bit zero and includes "bit" 73static inline uint64_t MaskUpToBit(const uint64_t bit) { 74 if (bit >= 63) 75 return -1ll; 76 return (1ull << (bit + 1ull)) - 1ull; 77} 78 79// Return an integer result equal to the number of bits of x that are ones. 80static inline uint32_t BitCount(uint64_t x) { 81 // c accumulates the total bits set in x 82 uint32_t c; 83 for (c = 0; x; ++c) { 84 x &= x - 1; // clear the least significant bit set 85 } 86 return c; 87} 88 89static inline bool BitIsSet(const uint64_t value, const uint64_t bit) { 90 return (value & (1ull << bit)) != 0; 91} 92 93static inline bool BitIsClear(const uint64_t value, const uint64_t bit) { 94 return (value & (1ull << bit)) == 0; 95} 96 97static inline uint64_t UnsignedBits(const uint64_t value, const uint64_t msbit, 98 const uint64_t lsbit) { 99 uint64_t result = value >> lsbit; 100 result &= MaskUpToBit(msbit - lsbit); 101 return result; 102} 103 104static inline int64_t SignedBits(const uint64_t value, const uint64_t msbit, 105 const uint64_t lsbit) { 106 uint64_t result = UnsignedBits(value, msbit, lsbit); 107 if (BitIsSet(value, msbit)) { 108 // Sign extend 109 result |= ~MaskUpToBit(msbit - lsbit); 110 } 111 return result; 112} 113 114} // namespace lldb_private 115 116#endif // LLDB_SOURCE_PLUGINS_PROCESS_UTILITY_INSTRUCTIONUTILS_H 117