views:

145

answers:

4
+3  Q: 

C++ shifting bits

I am new to shifting bits, but I am trying to debug the following snippet:

if (!(strcmp(arr[i].GetValType(), "f64")))
 {
        dem_content_buff[BytFldPos] = tmp_data;
     dem_content_buff[BytFldPos + 1] =  tmp_data >> 8;
     dem_content_buff[BytFldPos + 2] = tmp_data >> 16;
     dem_content_buff[BytFldPos + 3] = tmp_data >> 24;
     dem_content_buff[BytFldPos + 4] = tmp_data >> 32;
     dem_content_buff[BytFldPos + 5] = tmp_data >> 40;
     dem_content_buff[BytFldPos + 6] = tmp_data >> 48;
     dem_content_buff[BytFldPos + 7] = tmp_data >> 56;
        }    

I am getting a warning saying the lines with "32" to "56" have a shift count that is too large. The "f64" in the predicate just means that the data should be 64bit data.

How should this be done?

edit:

I should have put more of the code in.

tmp_data = simulated_data[index_data];

if (!(strcmp(dems[i].GetValType(), "s32")))

{ dem_content_buff[BytFldPos] = tmp_data; dem_content_buff[BytFldPos + 1] = tmp_data >> 8; dem_content_buff[BytFldPos + 2] = tmp_data >> 16; dem_content_buff[BytFldPos + 3] = tmp_data >> 24;
}

if (!(strcmp(dems[i].GetValType(), "f64"))) { dem_content_buff[BytFldPos] = tmp_data; dem_content_buff[BytFldPos + 1] = tmp_data >> 8; dem_content_buff[BytFldPos + 2] = tmp_data >> 16; dem_content_buff[BytFldPos + 3] = tmp_data >> 24; dem_content_buff[BytFldPos + 4] = tmp_data >> 32; dem_content_buff[BytFldPos + 5] = tmp_data >> 40; dem_content_buff[BytFldPos + 6] = tmp_data >> 48; dem_content_buff[BytFldPos + 7] = tmp_data >> 56; }

So, dem_content_buff right now only holds ints. Can I not use this array for the 64 bit data either?

+2  A: 

What is the type of tmp_data?

My guess is that tmp_data is only 32-bits, hence the error. It will need to be a 64-bit unsigned int, which is can be achieved using the non-standard (but well-supported) unsigned long long data type.

Peter Alexander
This code doesn't put any restrictions on the type of `dem_content_buff`. In fact, it looks like it's supposed to be an 8-bit type.
Carl Norum
tmp_data is an int.
Bobby
@Carl, Well spotted, I misread the code.
Peter Alexander
+1  A: 

Make sure to use 64bit long type for the tmp_data as was suggested before the unsinged long long should work, but check your compiler and architecture documentation.

The code should look like this. Also, make sure that your demp_content_buff is declared as unsigned char * or unsigned char [].

Then change your code to:

if (!(strcmp(arr[i].GetValType(), "f64")))
    {
        dem_content_buff[BytFldPos] =  ( tmp_data & 0xff );
        dem_content_buff[BytFldPos + 1] =  (tmp_data >> 8 ) & 0xff ;
        dem_content_buff[BytFldPos + 2] =  (tmp_data >> 16) & 0xff ;
        dem_content_buff[BytFldPos + 3] =  (tmp_data >> 24) & 0xff;
        dem_content_buff[BytFldPos + 4] =  (tmp_data >> 32) & 0xff;
        dem_content_buff[BytFldPos + 5] =  (tmp_data >> 40) & 0xff;
        dem_content_buff[BytFldPos + 6] =  (tmp_data >> 48) & 0xff;
        dem_content_buff[BytFldPos + 7] =  (tmp_data >> 56) & 0xff;
        }   
Vlad
+1  A: 

For the shift operator to work shifting more than 32 bits, tmp_data will need to be a 64-bit type - as several other answers indicated.

However, you would also want simulated_data to be an array of some 64-bit type otherwise tmp_data will always be zero (or a sign-extended set of 1 bits) in the most significant bits when you assign its original value:

tmp_data = simulated_data[index_data];
Michael Burr
+1  A: 

If you're using Visual Studio, make sure that you define tmp_data as:

__int64 tmp_data;              // Visual studio version

instead of

unsigned long long tmp_data;   // GCC version
Cthutu