I am writing a C program. I want a variable that I can access as a char but I can also access the specific bits of. I was thinking I could use a union like this...
typedef union
{
unsigned char status;
bit bits[8];
}DeviceStatus;
but the compiler doesn't like this. Apparently you can't use bits in a structure. So what can I do instead?
The smallest unit that is addressable in C is always a byte (called
char
in C). You cannot access a bit directly. The closest way to get to accessing bits would be to define a data type calledbitpointer
and define some functions or macros for it:I recommend against unions because it is implementation-defined whether they are filled msb-to-lsb or lsb-to-msb (see ISO C99, 6.7.2.1p10).
Sure, but you actually want to use a struct to define the bits like this
Then you can access for
DeviceStatus ds;
you can accessds.u.bit1
. Also, some compilers will actually allow you to have anonymous structures within a union, such that you can just accessds.bit1
if you ommit the u from the typedef.You can do it by putting the bits in a struct inside the union, but it may or may not work, depending on your implementation. The language definition does not specify in what order the separate bits will be matched with the bits of the
unsigned char
; worse, it doesn't even guarantee that the bits will overlap with theunsigned char
(the compiler might decide to place the separate bits towards the most significant side of a word and theunsigned char
towards the least significant side or vice versa).The usual technique in your situation is to use bitwise operations. Define constants named after the meaning of the bits, e.g.,
Then to read and write individual bits:
As has already been stated, you can't address memory smaller than a byte in C. I would write a macro:
and use it to access the bits. That way, your access is the same, regardless of the size of the structure you're accessing. You would write your code as:
This gets you access close to your proposed system, which would use [] instead of ().
You have a couple of possibilities. One would be to just use Boolean math to get at the bits:
Another is to use bitfields:
The first is (at least arguably) more portable, but when you're dealing with status bits, chances are that the code isn't even slightly portable anyway, so you may not care much about that...