How to check whether only 2 bits in a number at a specific position are on (edge‑case‑safe) with C

1 Answer

0 votes
#include <stdio.h>
#include <stdint.h>

/* Print a 64-bit number as bits (no leading zeros trimmed) */
void print_bits(uint64_t v, int width) {
    for (int i = width - 1; i >= 0; i--) {
        putchar((v & (1ULL << i)) ? '1' : '0');
    }
}

/*
    exact_bit_set:
    ----------------
    Returns 1 only if:

      • pos1 and pos2 are valid (>= 0, < 64, and not equal)
      • value has EXACTLY those two bits set
      • all other bits are OFF

    Bit positions are ZERO‑BASED from the RIGHT (LSB = position 0).
*/
int exact_bit_set(int pos1, int pos2, uint64_t value) {
    if (pos1 < 0 || pos2 < 0 || pos1 >= 64 || pos2 >= 64)
        return 0;

    if (pos1 == pos2)
        return 0;

    uint64_t mask = (1ULL << pos1) | (1ULL << pos2);
    
    return value == mask;
}

int main(void) {
    struct Test {
        uint64_t value;
        int x, y;
        int width;
    };

    struct Test tests[] = {
        {0b1000010000ULL, 4, 9, 10},
        {0b0010000010ULL, 1, 7, 10},
        {0b0000100100ULL, 2, 5, 10},
        {0b1000010000ULL, 3, 9, 10},
        {0b1001010000ULL, 4, 9, 10},
        {0b1111111111ULL, 4, 9, 10},
        {0b0000000000ULL, 4, 9, 10},
        {0b1000010000ULL, 4, 8, 10},
        {1ULL,            0, 0, 1},
        {1ULL,            0, 1, 1},
        {0ULL,            1, 1, 1}
    };

    int count = sizeof(tests) / sizeof(tests[0]);

    for (int i = 0; i < count; i++) {
        uint64_t v = tests[i].value;
        int x = tests[i].x;
        int y = tests[i].y;

        print_bits(v, tests[i].width);
        printf("  bits(%d, %d)  ->  %s\n",
               x, y,
               exact_bit_set(x, y, v) ? "true" : "false");
    }

    return 0;
}


/*
OUTPUT:

1000010000  bits(4, 9)  ->  true
0010000010  bits(1, 7)  ->  true
0000100100  bits(2, 5)  ->  true
1000010000  bits(3, 9)  ->  false
1001010000  bits(4, 9)  ->  false
1111111111  bits(4, 9)  ->  false
0000000000  bits(4, 9)  ->  false
1000010000  bits(4, 8)  ->  false
1  bits(0, 0)  ->  false
1  bits(0, 1)  ->  false
0  bits(1, 1)  ->  false

*/

 



answered Apr 3 by avibootz

Related questions

...