Search code examples
cbit

Sign extending to 32 bits, starting with n bits - C


I am new to C and getting some practice with bit manipulation.

Suppose I have an n bit two's complement number such that n > 0 and n < 31. If I know the size of n in advance, how can I sign extend it to 32 bits?

If n was 16 bits,

int32_t extendMe(int16_t n) {
    return (int32_t) n;
}

assuming I have the data definitions.

Suppose I have an n bit value that I want to sign extend to 32, how can I accomplish this?

Thank you.


Solution

  • If this really is about interpreting arbitrary bit patterns as numbers represented in n bits using two's complement, here's some sloppy example code doing that:

    #include <stdio.h>
    #include <inttypes.h>
    
    // this assumes the number is in the least significant `bits`, with
    // the most significat of these being the sign bit.
    int32_t fromTwosComplement(uint32_t pattern, unsigned int bits)
    {
        // read sign bit
        int negative = !!(pattern & (1U << (bits-1)));
    
        // bit mask for all bits *except* the sign bit
        uint32_t mask = (1U << (bits-1)) - 1;
    
        // extract value without sign
        uint32_t val = pattern & mask;
    
        if (negative)
        {
            // if negative, apply two's complement
            val ^= mask;
            ++val;
            return -val;
        }
        else
        {
            return val;
        }
    }
    
    int main(void)
    {
        printf("%" PRId32 "\n", fromTwosComplement(0x1f, 5)); // output -1
        printf("%" PRId32 "\n", fromTwosComplement(0x01, 5)); // output 1
    }