Search code examples
cbinaryhexbit-manipulationbit

How do I extract bits from 32 bit number


I have do not have much knowledge of C and I'm stuck with a problem since one of my colleague is on leave.

I have a 32 bit number and i have to extract bits from it. I did go through a few threads but I'm still not clear how to do so. I would be highly obliged if someone can help me.

Here is an example of what I need to do:

Assume hex number = 0xD7448EAB.
In binary = 1101 0111 0100 0100 1000 1110 1010 1011.
I need to extract the 16 bits, and output that value. I want bits 10 through 25.

The lower 10 bits (Decimal) are ignored. i.e., 10 1010 1011 are ignored.
And the upper 6 bits (Overflow) are ignored. i.e. 1101 01 are ignored.

The remaining 16 bits of data needs to be the output which is 11 0100 0100 1000 11 (numbers in italics are needed as the output).

This was an example but I will keep getting different hex numbers all the time and I need to extract the same bits as I explained.

How do I solve this?
Thank you.

For this example you would output 1101 0001 0010 0011, which is 0xD123, or 53,539 decimal.


Solution

  • You need masks to get the bits you want. Masks are numbers that you can use to sift through bits in the manner you want (keep bits, delete/clear bits, modify numbers etc). What you need to know are the AND, OR, XOR, NOT, and shifting operations. For what you need, you'll only need a couple.

    You know shifting: x << y moves bits from x *y positions to the left*.

    How to get x bits set to 1 in order: (1 << x) - 1

    How to get x bits set to 1, in order, starting from y to y + x: ((1 << x) -1) << y

    The above is your mask for the bits you need. So for example if you want 16 bits of 0xD7448EAB, from 10 to 25, you'll need the above, for x = 16 and y = 10.

    And now to get the bits you want, just AND your number 0xD7448EAB with the mask above and you'll get the masked 0xD7448EAB with only the bits you want. Later, if you want to go through each one, you'll need to shift your result by 10 to the right and process each bit at a time (at position 0).

    The answer may be a bit longer, but it's better design than just hard coding with 0xff or whatever.