Copy bits from one integer to another

© Parineeth M R

Question 35. Copy the bits between the specified start bit and end bit positions of one integer into another integer. For instance if source integer is 0xBBB and destination integer is 0xAEC and we copy the bits from 4 to 7 from source to destination, the result is 0xABC


Let the source integer be 0xBBB, destination integer be 0xAEC and we have to copy bits from position 4 to 7. The strategy we use is as follows:

1. Construct a mask (let’s call it ones mask) in which all the bits are initially set to 1. If we need to copy n bits and the total number of bits in the integer is m, then right shift the ones mask by (m-n). So if we need to copy 4 bits between bit 4 and bit 7, and total number of bits in integer is 32, we perform ones_mask >> (32 – 4). So ones_mask will have a value 0xF.

2. Left shift the ones mask to the starting position from where we have to copy the bits. The ones mask will now have 1’s from the start bit position to the end bit position. In this example, starting bit position is 4, so we perform (ones_mask << 4) = (0xF << 4) = 0xF0.

3. Construct a zeroes mask which is the complement of the ones mask. The zeroes mask will have 0’s from the start bit to the end bit. So if ones mask is 0xF0, then zeroes mask will be 0xFFFFFF0F.

4. AND the destination integer with the zeroes mask to clear out the bits in the destination from start bit to end bit. So if destination is 0xAEC, then 0xAEC & 0xFFFFFF0F will give 0xA0C

5. AND the source integer with the ones mask so that only the bits from start and end bit positions remain and the rest of the bits are cleared. If the source integer is 0xBBB, then 0xBBB & 0xF0 will give 0xB0

6. OR the source and destination. So 0xA0C | 0xB0 will give 0xABC

C/C++


/*
dest: destination integer into which the bits have to be copied
src: source integer from which the bits have to be copied 
end_pos: Most Significant bit position upto where the bits should be copied
start_pos: Least Significant bit position from where the bits should be copied
	end_pos should be >= start_pos
Return value: result integer after copying bits from source to destination
*/
unsigned int copy_bits(unsigned int dest, unsigned int src, 
			unsigned int end_pos, unsigned int start_pos)
{
	unsigned int num_bits_to_copy = end_pos - start_pos + 1;
	unsigned int num_bits_in_int = sizeof(unsigned int) * 8;
	unsigned int zeroes_mask;
	unsigned int ones_mask = ~((unsigned int) 0); /*all ones*/

	/*Use the bit-wise right shift operator to remove the excess 1's 
	in the mask*/
	ones_mask = ones_mask >> (num_bits_in_int - num_bits_to_copy);

	/*Left shift the 1's to the starting position. ones_mask will contain 1's
	from start_pos to end_pos*/
	ones_mask = ones_mask << start_pos;

	/*zeroes_mask will contain 0's from start_pos to end_pos*/
	zeroes_mask = ~ones_mask;

	/*clear the bits in destination from start_pos to end_pos*/
	dest = dest & zeroes_mask;

	/*retain the bits in source from start_pos to end_pos and clear the 
	remaining bits*/
	src = src & ones_mask;
	
	/*copy the source bits into the destination*/
	dest = dest | src;
	
	return dest;
}




Java


/*
dest: destination integer into which the bits have to be copied
src: source integer from which the bits have to be copied 
endPos: Most Significant bit position upto where the bits should be copied
startPos: Least Significant bit position from where the bits should be copied
	endPos should be >= startPos
Return value: result integer after copying bits from source to destination
*/
public static int copyBits(int dest, int src,  int endPos,  int startPos) {
	 int numBitsToCopy = endPos - startPos + 1;
	 int numBitsInInt = 32;
	 int onesMask = ~(0); /*Initialize the mask to all 1's*/

	/*Use the bit-wise right shift operator to remove the excess 1's 
	in the mask*/
	onesMask = onesMask >>> (numBitsInInt - numBitsToCopy);

	/*Left shift the 1's to the starting position. onesMask will contain 
	1's from startPos to endPos*/
	onesMask = onesMask << startPos;

	/*zeroesMask will contain 0's from startPos to endPos*/
	int zeroesMask = ~onesMask;

	/*clear the bits in destination from startPos to endPos*/
	dest = dest & zeroesMask;

	/*retain the bits in source from startPos to endPos and clear 
	the remaining bits*/
	src = src & onesMask;

	/*copy the source bits into the destination*/
	dest = dest | src;

	return dest;
}



Python


#dest: destination integer into which the bits have to be copied
#src: source integer from which the bits have to be copied 
#end_pos: Most Significant bit position upto where the bits should be copied
#start_pos: Least Significant bit position from where the bits should be copied
#	end_pos should be >= start_pos
#Return value: result integer after copying bits from source to destination
def copy_bits(dest,  src,  end_pos,  start_pos) :
	num_bits_to_copy = end_pos - start_pos + 1
	num_bits_in_int = 32
	ones_mask = (1 << 32) - 1

	#Use the bit-wise right shift operator to remove the excess 1's 
	#in the mask
	ones_mask = ones_mask >> (num_bits_in_int - num_bits_to_copy)

	#Left shift the 1's to the starting position. ones_mask will contain 1's
	#from start_pos to end_pos
	ones_mask = ones_mask << start_pos

	#zeroes_mask will contain 0's from start_pos to end_pos
	zeroes_mask = ~ones_mask

	#clear the bits in destination from start_pos to end_pos
	dest = dest & zeroes_mask

	#retain the bits in source from start_pos to end_pos and 
	#clear the remaining bits
	src = src & ones_mask

	#copy the source bits into the destination
	dest = dest | src

	return dest