Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Can bit shifting ever add a 1 instead of a zero in C ? And how to avoid it? [closed]

Tags:

c

bit-shift

I have a program that uses 0th bit for something and then bits 7-1 for something else. In order to check bits 7-1 I do a

int number = number >> 1;

which gives me the bits 7-1.

so for example 1111 1110 becomes 0111 1111

I am curious if there is an edge case where that left bit will become a 1 instead of a 0? Because that would screw up my program.

If there is such case, how can I avoid it and make sure it never happens?

like image 694
Duxa Avatar asked Oct 25 '25 09:10

Duxa


2 Answers

There are lots of thing to consider.

First of all if it is int - and it is unsigned you can be sure that all the left shifted bits are 0-'s. The 8th bit should always be 0 to make sure that the 8th bit is 0 because that is what becomes the 7th bit after left shifting.

For signed number the story is quite different. Suppose this is int8_t and right shifting this is implementation defined. But on most implementations it would give 1110 0000 after right shifting 1010 0000. That's the thing.

Now you said it can be char. Three types of char - signed , unsigned and plain.

With unsigned the story is same as before. With signed it is also same as before. With plain you don't know how char is by default interpreted on your implementation. How to check what it is?

Check the CHAR_MIN to determine if it is signed or unsigned and then if it is signed then the result of right shift is implementation defined as mentioned by standard. So in this case it holds too what is being told about signed type.

C11 §6.5.7 Shift operators ¶5 says: If E1 has a signed type and a negative value, the resulting value is implementation-defined. (Jonathan Leffler pointed this out)

like image 56
user2736738 Avatar answered Oct 27 '25 00:10

user2736738


After right shifting, the empty spaces are filled by leading 0s.

For example, 11111000 >> 1 = 01111100

It will always be led by 0(s) provided it is an unsigned data type unless explicitly made to 1 using shift operators.

A tip - you can ensure that your program uses unsigned data type to always get leading zeros. You declare your variable as any of unsigned types. Example - unsigned int, unsigned char, unsigned long, etc

like image 26
Thomas Avatar answered Oct 27 '25 00:10

Thomas