views:

392

answers:

5

I've been going through the K&R C Programming Language book and I'm stuck on Exercise 2-6 which reads:

Write a function setbits(x,p,n,y) that returns x with the n bits that begin at position p set to the rightmost n bits of y, leaving the other bits unchanged.

I'm having trouble understanding the exact thing they're looking for me to do. I looked at a possible answer here, but I still don't really understand. I think it's the wording that's throwing me off. Can anyone maybe explain what they're looking for me to do in a different way? I'm hoping that different wording will help me understand what I need to do code wise.

+2  A: 

For example:

int i = setbits(0xAB = b10101011, 5, 3, 0xAA = b10101010);
i equals 0x93 = b10010011

We take the 3 bits beginning at position 5 in x (101), and replace them with the rightmost three bits from y (010).

Avi
+1  A: 

The operation is "bitfield insert"

The idea is that y would usually be fewer than n bits, but in case it's not, only use n. In english, the task is to insert y into x beginning at p, using a field width of n.

DigitalRoss
A: 

Replace n bits of x, starting at p position, with the rightmost n bits of y.

And probably you should take advantage of the getbits() routine in chapter 2.9

Nick D
+1  A: 

That "possible answer" is just code without comments. No wonder it didn't help you.

The question (and probably the answerers) assume that you are familiar with bit fields. This sort of thing is very common in embedded programming where you control hardware registers.

Say there's a register that sets the audio volume level, among other things. It might, at the same time, let you select speakers or microphones and things like that. The bits might look like this:

ssAAAmxx -- Each letter represents a bitfield within that number. To change the volume, you have to alter the value of "AAA". Now, lets say you have something in your program that lets you adjust the volume. It's a simple control, and it always returns a number between 0 and 7. The format for that looks like this:

xxxxxAAA -- You job then, is to take the AAA bits from this (call it "y"), and set them into that number above (call it "x"), without altering the bits that aren't the A's. Thus, the problem would read, "Take the rightmost 3 bits of y, and set them into x, starting with bit 5 (remember, they count bits from zero). Then, 3 and 5 in our example become n and p in the original problem.

gbarry
+3  A: 

Expounding on Avi's answer:

int i = setbits(0xAB = b10101011, 5, 3, 0xAA = b10101010);
i equals 0x93 = b10010011

Say your i = 0xAB. In binary, this is: 10101011

Let's number each of the bit positions.

Position #: 7   6   5   4   3   2   1   0
Bit:        1   0   1   0   1   0   1   1

The right-most bit (the least-significant) is position "0". The left-most (most-significant) is position "7".

So the next two values, p and n, are saying "You want to modify n bits starting at bit p." So if p=5 and n=3, you want to start at bit number 5, and in total you're modifying 3 bits. Which means bits 5, 4, 3. "101" in this example.

Position #: 7   6   5   4   3   2   1   0
Bit:        1   0   1   0   1   0   1   1
                   |         |
                    ---------
               (Modifying these three bits)

How are we modifying them? We are replacing them. With another set of 3 bits. The three least-significant bits from y.

So here's y:

Position #: 7   6   5   4   3   2   1   0
Bit:        1   0   1   0   1   0   1   0 

And the right-most bits would be bits 2, 1, 0. or the value "010". Of course, if the value of n=6, then you'd want to replace those six bits from i with "101010" - the rightmost 6 bits.

So your task is to take the specified bits from i - in this case, "101" - and replace them with the specified bits in y - "010".

If you do this, then your return value is

1 0 1 0 1 0 1 0

rascher
This is a very nice, thorough explanation. Thank you very much.
Koby