C++ Bitset << operator not working. Pointer to bitset variable - c++

I have a set of bitsets pointers in an unordered_map
static unordered_map< size_t, bitset<BITSIZE>* > systemBits;
And my function
template<typename system>
static bitset<BITSIZE> & getBitFor() {
size_t hash = typeid(system).hash_code();
bitset<BITSIZE> * bit = systemBits[hash];
if(bit == NULL) {
bit = new bitset<BITSIZE>(0);
(*bit) << POS++; // tried *bit << POS++ as well;
systemBits[hash] = bit;
}
return *bit;
}
Whereas POS is an int set to 1 at first.
All that I'm trying to do is shift the bitset with the amounts of position per new bitset.
(*bit) << POS++;
However this doesn't seem to work. When I cout the returned bitset all its bits are set to 0.
If I do to the following:
bit->flip();
or
(*bit).flip();
The bitset returned does flip all the 0 to 1.
What gives? Why does the shift operator have no effect at all?

Because you're not assigning the result to anything . You'd have the same problem if you were trying to shift an int.
Also, you've initialized your bitset to zero, and zero shifted by any amount is always zero.

Related

How to extract one specific bit from a uint16_t variable properly

Long story short, I am currently coding a wrapper in C++ for a C - library which extracts the value of registers on an embedded system. To monitor what happens, I need to read the value of a bit for some registers and make a getter for each of them.
Basically, I would like my method to return one bool from a bit stored into a uint16_t variable. On a 'naive' and uncaffeinated approach I was doing something like that :
bool getBusyDevice(int fd) // fd stands for file descriptor, for each instance of the class
{
uint16_t statusRegVal = 0;
get_commandReg(fd, &statusRegVal); // C-library function to get the value of status register
uint16_t shift = 0; // depends on the bit to access - for reusability
bool Busy = (bool) (statusRegVal >> shift);
return busy;
}
I am not quite happy with the result and I would like to know if there was a 'proper' way to do that...
Thanks a lot for your advice !
The normal way to get just a single bit is to use the bitwise and operator &. Like e.g. statusRegVal & bitValue. If the bit is set then the result will be equal to bitValue, meaning to get a boolean result you could do a simple comparison: statusRegVal & bitValue == bitValue.
So if you want to check if bit zero (which has the value 0x0001) is set, then you could simply do
return statusRegVal & 0x0001 == 0x0001;
For better understanding of what you want, take a look at the following link
Masking: https://en.wikipedia.org/wiki/Mask_(computing)
and
Bit Manipulation: https://en.wikipedia.org/wiki/Bit_manipulation
Conclusion:
If you want to read specific number of bits in variable(register), you should make a MASK with this variable with bits positions.
say you've 2Byte variable (u16Reg) and you want to read bits [5,7] so,
value = ((u16Reg & 0x00A0) >> 5).
In you case, you want to read one bit and return with its status TRUE or FALSE.
value = ((u16Reg & (0x0001 << n)) >> n)
where n is the bit number you want to read.
Lets understand it.
say u16Reg = 0x529D = 0b0101001010011101; bit[0] = 1 and bit[15] = 0; and you want to get bit number 9.
So, First make sure that all bits are zeros except yours (9).
(0b0101001010011101 & (0x0001 << 9)) =
(0b0101001010011101 & 0x0200) =
(0b0101001010011101 & 0b0000001000000000) =
(0b0000001000000000) = 0x0200
this means TRUE in case you mean nonZero is TRUE. But if TRUE means 0x01, you should move this bit to bit[0] as following:
(0x0200 >> 9) = 0x0001 is TRUE
If you can understand this, you can make it simpler like:
value = ((u16Reg >> n) & 0x0001)
Why not to use templates:
template<int SHIFT>
bool boolRegVal(uint16_t val) {
return val & (1 << SHIFT);
}
And then usage:
boolRegVal<4>(statusRegVal);
The casting to bool won't be helpful because it doesn't 1 bit type.
you must clean the rest of the bits, and then check if you've got 0.
You can do something like this:
bool Busy = ((statusRegVal >> shift) & 1) ? true : false;
The standard library provides std::bitset for manipulating bits. Here's an example but am sure you can guess what it does.
#include <bitset>
#include <iostream>
using namespace std;
int main(int, char**){
typedef bitset<sizeof(int)*8> BitsType; //or uint16_t or whatever
BitsType bits(0xDEADBEEF);
for(int i = 0; i < 5; ++i) //access the bits
cout << "bits[" << i << "] = " << bits[i] << '\n';
cout << "bit[3] = " << bits[3] << '\n'; //original
bits.flip(3);
cout << "bit[3] = " << bits[3] << '\n'; //b[3] = !b[3]
return 0;
}
The operator [](size_t) is overloaded to return a reference so you can assign to it too. bits[4] = false for example. And finally, when done playing with your bits :) you can convert back to long (or ulong) or in your case uint16_t value = static_cast<uint16_t>(bits.to_ulong()). Kudos to stdlib.

Bits aren't being reset?

I am using Bit Scan Forward to detect set bits within a unit64_t, use each set bit index within my program, clear the set bit and then proceed to find the next set bit. However, when the initial uint64_t value is:
0000000000001000000000000000000000000000000000000000000000000000
The below code isn't resetting the 52nd bit, therefore it gets stuck in the while loop:
uint64_t bits64 = data;
//Detects index being 52
int32_t index = __builtin_ffsll(bits64);
while(0 != index){
//My logic
//Set bit isn't being cleared here
clearNthBitOf64(bits64, index);
//Still picks-up bit 52 as being set
index = __builtin_ffsll(bits64);
}
void clearNthBitOf64(uint64_t& input, const uint32_t n) {
input &= ~(1 << n);
}
From the docs:
— Built-in Function: int __builtin_ffs (int x)
Returns one plus the index of the least significant 1-bit of x, or if x is zero, returns zero.
You're simply off by one on your clear function, it should be:
clearNthBitOf64(bits64, index-1);
Also your clear function is overflowing. You need to ensure that what you're left shifting is of sufficient size:
void clearNthBitOf64(uint64_t& input, const uint32_t n) {
input &= ~(1ULL << n);
// ^^^
}
__builtin_ffsll "returns one plus the index of the least significant 1-bit of x, or if x is zero, returns zero." You need to adjust the left shift to ~(1ULL << (n - 1)) or change the function call to clearNthBitOf64(bits64, index - 1);

How to check a particular bit of a "long long int" in C++

I'm trying to check a particular bit of a long long integer
long long int val=23355665641326;
int bit_no=32;
if( (val & (1<<bit_no)) == 0)
cout<<bit_no<<"'th bit is not set\n";
else
cout<<bit_no<<"'th bit is set\n";
the binary equivalent of 23355665641326 is -
101010011110111101010001001110110111101101110
^
we see, 32'th bit is set. But my code returns not set :(
how can i check the bit?
Your life would be easy if you use std::bitset instead:
constexpr auto N = CHAR_BIT * sizeof(long long int);
std::bitset<N> val(23355665641326LL);
Now you can test a particular bit as:
if ( val.test(i) ) {
//bit at index i is set!
}
Or you can use the faster — but unsafe — version, as:
if ( val[i] ) {
//bit at index i is set!
}
test() performs bound check and throws std::out_of_range if the index is invalid, whereas operator[] does not, in which case invalid index leads to undefined behavior.
You can use 1LL<<bit_no to check the bit status of a long long int.
As you are dealing with long long int you need to use long long type 1
Because if you use normal 1(int), you can check upto 31 bit
So just change the checking portion like this -
if( (val & (1LL<<bit_no) ) == 0)
^^^
To overcome with the need of adding the suffix to the check simply do something like this:
if(!!((val >> bit_no) & 1))
std::cout << "not set";
else
std::cout << "is set";

platform difference?

I was trying out the bitset class in C++ and I tried this with the number 137 as an example:
So, I converted it to binary number which gave me 10001001. Now, I wanted to cut off the MSB and store the rest bits 0001001 in another bit instance called bitarray and I was expecting to see that in the bitarray but it wasn't giving the right value. what could have been the problem? I was just trying to split the MSB from the rest of the bits in the 137 binary representation...here is the code:
bitset<8> bitarray;
bitset<8> bitsetObject(num);
int val = bitsetObject.size();
for (int i = 0; i <= (val - 1); i++)
{
if (i == 6)
break;
else
bitarray[i] = bitsetObject[i + 1];
}
If anyone knows how I could easily slice from the second element to the last element in the bitsetObject array, let me know. Thanks..
If you're just trying to make a new bitset object with the most significant set bit reset, then consider the following:
template<std::size_t N>
std::bitset<N> strip_mssb(std::bitset<N> bitarray)
{
for (std::size_t i = bitarray.size(); i--;)
if (bitarray[i])
{
bitarray.reset(i);
break;
}
return bitarray;
}
Online demo.
You set bitarray[0] equal to bitsetObject[1], which is 0 (assuming num is really 137).
You seem to expect the least bit of bitarray to be equal to 1.

add 1 to c++ bitset

I have a c++ bitset of given length. I want to generate all possible combinations of this bitset for which I thought of adding 1 2^bitset.length times. How to do this? Boost library solution is also acceptable
Try this:
/*
* This function adds 1 to the bitset.
*
* Since the bitset does not natively support addition we do it manually.
* If XOR a bit with 1 leaves it as one then we did not overflow so we can break out
* otherwise the bit is zero meaning it was previously one which means we have a bit
* overflow which must be added 1 to the next bit etc.
*/
void increment(boost::dynamic_bitset<>& bitset)
{
for(int loop = 0;loop < bitset.count(); ++loop)
{
if ((bitset[loop] ^= 0x1) == 0x1)
{ break;
}
}
}
All possible combinations? Just use 64-bit unsigned integer and make your life easier.
Not best, but brute force way, but you can add 1 by converting using to_ulong()
bitset<32> b (13);
b = b.to_ulong() + 1;
Using boost library, you can try the following:
For example, a bitset of length 4
boost::dynamic_bitset<> bitset;
for (int i = 0; i < pow(2.0, 4); i++) {
bitset = boost::dynamic_bitset<>(4, i);
std::cout << bitset << std::endl;
}