Jasmine Jasmine - 1 month ago 9
C Question

XORing a 32 bit integer with itself

I'm stuck on XORing a 32-bit integer with it itself. I'm supposed to XOR the 4 8-bit portions of the integers. I understand how it works, but without storing the integer anywhere, I don't get how to do this.

I've thought it over and I'm thinking of using binary left shift and right shift operators to separate the 32 bit integer into 4 parts to XOR them. For example, if I were to use an 8-bit integer, I would do something like this:

int a = <some integer here>
(a << 4) ^ (a >> 4)


So far, it isn't working the way I thought it would work.

Here's a part of my code:

else if (choice == 2) {
int bits = 8;

printf("Enter an integer for checksum calculation: ");
scanf("%d", &in);
printf("Integer: %d, ", in);

int x = in, i;
int mask = 1 << sizeof(int) * bits - 1;

printf("Bit representation: ");

for (i = 1; i <= sizeof(int) * bits; i++) {
if (x & mask)
putchar('1');
else
putchar('0');

x <<= 1;
if (! (i % 8)) {
putchar(' ');
}
}
printf("\n");

}


Here's an example of an output:

What type of display do you want?
Enter 1 for character parity, 2 for integer checksum: 2
Enter an integer for checksum calculation: 1024
Integer: 1024, Bit representation: 00000000 00000000 00000100 00000000
Checksum of the number is: 4, Bit representation: 00000100

Answer

To accumulate the XOR of 8-bit values, you simply shift and XOR each part of the value. Since only the low-order byte matters, you can do it fast if you accumulate and don't bother to mask until the end. For example:

uint32_t simple_checksum( uint32_t *v, size_t count )
{
    uint32_t checksum = 0;
    uint32_t *end = v + count;
    for( ; v != end; v++ )
    {
        checksum ^= (*v >> 24) ^ (*v >> 16) ^ (*v >> 8) ^ *v;
    }
    return checksum & 0xff;  /* everything from bits 8 upward is rubbish */
}

If you're just after a single value's checksum, you could just do this:

uint8_t checksum = (uint8_t)( (a >> 24) ^ (a >> 16) ^ (a >> 8) ^ a );

Or if you wanted it in a larger datatype, just mask similar to the first example:

uint32_t checksum = ( (a >> 24) ^ (a >> 16) ^ (a >> 8) ^ a ) & 0xff;
Comments