why endianess matters among bits inside a byte?

2020-07-18 04:44发布

问题:

the following is the IP structure from library on a linux machine

   struct ip
      {
    #if __BYTE_ORDER == __LITTLE_ENDIAN
        unsigned int ip_hl:4;               /* header length */
        unsigned int ip_v:4;                /* version */
    #endif
    #if __BYTE_ORDER == __BIG_ENDIAN
        unsigned int ip_v:4;                /* version */
        unsigned int ip_hl:4;               /* header length */
    #endif
        u_int8_t ip_tos;                    /* type of service */
        u_short ip_len;                     /* total length */
        u_short ip_id;                      /* identification */
        u_short ip_off;                     /* fragment offset field */
    #define IP_RF 0x8000                    /* reserved fragment flag */
    #define IP_DF 0x4000                    /* dont fragment flag */
    #define IP_MF 0x2000                    /* more fragments flag */
    #define IP_OFFMASK 0x1fff               /* mask for fragmenting bits */
        u_int8_t ip_ttl;                    /* time to live */
        u_int8_t ip_p;                      /* protocol */
        u_short ip_sum;                     /* checksum */
        struct in_addr ip_src, ip_dst;      /* source and dest address */
      };

for these lines:

    #if __BYTE_ORDER == __LITTLE_ENDIAN
        unsigned int ip_hl:4;               /* header length */
        unsigned int ip_v:4;                /* version */
    #endif
    #if __BYTE_ORDER == __BIG_ENDIAN
        unsigned int ip_v:4;                /* version */
        unsigned int ip_hl:4;               /* header length */
    #endif

why endianess matters inside a byte? I think endianess only affect multi-byte integers, but here it seems to me that endianess also affect bits arrangement inside a byte?

besides, it is only a byte, why it is unsigned int, which is 4 bytes.

I notice in wireshark, ip_v and ip_hl is shown as 0x45 If I capture an IP packet. The first byte is composed of ip_v and ip_hl I put it into a character variable x

then what is the result of x & 0b11110000 ? is it always 4 no matther what endianess, or it may be 5?

回答1:

The endianess defines the place of the Most Significant Bit (MSB), it is related to the way the number inside a variable is interpreted in memory. Considering unsigned integers:

00000001 (Binary) = 1 (2 to the power of 0) -> If the most significant bit is to the left

00000001 (Binary) = 128 (2 to the power of 7) -> If the most significant bit is to the right

As you can see the position of the most significant bit is very important when it comes to the number representation in memory, even in 8 bit numbers.

For your last question you are right, it makes no difference if it is 1 byte or 4 because it is taking only 4 bits. But but remember that an unsigned int not always is a 4 bytes number.

Hope it helps!



回答2:

There is byte ordering which is relevant in case of multiple byte data. But in your case what matters is bit field ordering, which deals with the order of bits in case of a single byte data. There are no rules put forward by the C standard regarding bit field ordering. It is implementation dependent and decided by the compiler.

The size of the variable is not 4 bytes. It is just 4 bits. They are not independent variables. They are bit fields inside a structure.



标签: c bit endianness