Search code examples
cenumscoap

Buffer Parsing in C


i am looking at the CoAP implementation in ContikiOS, particularly at the header parsing and i am having some trouble understanding two operations. The code is bellow.

coap_pkt->version = (COAP_HEADER_VERSION_MASK & coap_pkt->buffer[0]) >> COAP_HEADER_VERSION_POSITION;
coap_pkt->type = (COAP_HEADER_TYPE_MASK & coap_pkt->buffer[0]) >> COAP_HEADER_TYPE_POSITION;

The coap_pkt the structure that houses the packet and the parsed values.

  • the version is an uint8_t (unsigned char) type
  • The buffer houses the packet
  • The COAP_HEADER_VERSION_MASK value is 0xC0
  • COAP_HEADER_VERSION_POSITION is 6
  • the type value is an enum structure with 4 values
  • COAP_HEADER_TYPE_MASK value is 0x30
  • COAP_HEADER_TYPE_POSITION value is 4

Now according to CoAP RFC 7252 the both the version and the type occupy two bits and so the mask operations and used values make sense to me.

My question is why are the shifting values different in the two operations ?,does it have something to do with one using an unsigned char and another the enum structure?


Solution

  • Basically this shifts both of the values down to the least significant bits.

    The version bits are at the most significant bits, let's call them bits 7 and 6. So, the four possible values with the mask applied are 0xC0, 0x80, 0x40 and 0x00. For later use, e.g. for version comparisons, changing the range to 3, 2, 1 and 0 might be more useful, so shifting by six bits moves the value to bits 1 and 0. (In fact the mask is unnecessary in this case because the shifting eliminates all but the most significant two bits.)

    It's the same story with the type bits, but those are bits 5 and 4, giving you 0x30, 0x20, 0x10 and 0x00 after applying the mask. Shifting by four bits moves those bits to 1 and 0.