What is the": "(colon) for in the statement of a member of a structure?

I saw this:

typedef struct {
    unsigned char a : 1;
    unsigned char b : 7;
} Tipo;

What does this statement mean? What is this 1 and 7?

Author: Maniero, 2017-01-20

1 answers

Let's run this code to better understand:

#include <stdio.h>

typedef struct {
    unsigned char a : 1;
    unsigned char b : 7;
} Tipo;

int main(void) {
    Tipo x = { .a = 1, .b = 64 };
    printf("%d e %d\n", x.a, x.b);
    printf("%zd\n", sizeof(Tipo));
}

See working on ideone. E no repl.it. also I put on GitHub for future reference .

Try to put a value greater than 1 on the member a. It doesn't work, it can only be 0 or 1. Have you picked up why?

In the second impression we see that the size of this structure is 1 byte. And now, did you kill?

The colon is used when the structure is used to assemble a string of bits and each member is called the bit field. So what comes after : is the amount of bits that that member contains. So a can only have 0 or 1. It only has 1 bit. The same goes if you try to put more than 127 in b that only has 7 bits.

Ideally these structures should have a total size multiple of 8 to fit with a byte, but if it does not, a alignment will occur according to the rules of the compiler.

Possible member types are specified as _Bool, signed int, unsigned int and others specified by the compiler, which is what was used. It is usually better to use types with universally defined size. So it's better a int32_t than a int.

It is very common for this type of structure to be within a larger structure with other members.

It is also very common to use with union. So you can access a union member as a data single and the other member of the Union as a bit structure.

#include <stdio.h>

typedef union {
    char valor;
    struct {
        unsigned char a : 1;
        unsigned char b : 1;
        unsigned char c : 1;
        unsigned char d : 1;
        unsigned char e : 1;
        unsigned char f : 1;
        unsigned char g : 1;
        unsigned char : 1;
    } bits;
} Tipo;

int main(void) {
    Tipo x = { .valor = 87 };
    printf("%d %d %d %d %d %d %d", x.bits.a, x.bits.b, x.bits.c, x.bits.d, x.bits.e, x.bits.f, x.bits.g);
}

See working on ideone. E no repl.it. also I put on GitHub for future reference .

Note that I showed another point. You are not required to identify all the bits. Of course, not putting a name on some bit, or set of bits, you will not be able to access its value in a direct and named way.

 16
Author: Maniero, 2020-11-20 15:38:47