Is there a more optimal way to approach some of these bitwise functions?
The comment \\ basically sizeof(int) using bit manipulation
is wrong. sizeof(int) gives the number of bytes (technically, "storage units"), but your function gives the number of bits.

If you change the name of the function to something descriptive like bits_in_int(), you might not need the comment.

The C language says that a char must always be a storage unit.  If you know how many bits are in a char, you can just multiply by sizeof(int) to get the number of bits in an int.  And there's a constant, CHAR_BIT, in header &lt;limits.h&gt; which is the number of bits in a character.  So your whole int_size() function could be reduced to the compile-time expression sizeof(int) * CHAR_BIT;

If you really want to figure it out yourself, instead of using language-defined tools, your function could still use better style.  First, a for loop shouldn't try to put everything in the loop header.  The header should concern itself with the iteration.  Everything else should either go before the loop, or in the loop body.  I would replace your loop with:

for (unsigned int i = ~0u; i &gt; 0; i &gt;&gt;= 1)
{
    size++;
}


size has nothing to do with controlling the loop, so I moved it to the body. I changed ~00u to ~0u.  I see no reason to use an octal zero (00) instead of a decimal zero (0).

(Incidentally, I suggest never writing a single-statement loop or if statement without the braces.  The typing you save doesn't make up for the increased risk of introducing an error in the future.)

This loop:

for(int i = 0; i &lt; int_size(); i++)
     printf("%X",bit_get(data,i));


is inefficient.  You're computing int_size() each time through the loop.  This is better:

const unsigned int size = int_size();
for(int i = 0; i &lt; size; i++)
{
    printf("%X",bit_get(data,i));
}


(You're calling int_size() more than once in other functions; I won't keep mentioning it.)

Get in the habit of declaring things const whenever possible.  It makes the code clearer to the reader.  It sometimes helps the compiler do a better job optimizing. And it makes you more aware of stuff that you can move out of loop bodies.

If a function returns an unsigned int, it probably doesn't make sense to return -1 to mean "invalid input" (function bitpat_get) or "not found" (function bitpat_search).  -1 converts to an unsigned int filled with 1 bits (at least on a two's complement machine).  This is probably a valid result for some input, so the calling code can't reliably extract the meaning from the return value.

Does bitpat_search() behave reasonably if the caller lies?  What if the value passed in n is wrong for the given pattern?  If the caller is supposed to do n = bit_width(source), why not do the calculation inside bitpat_search() instead of making the caller pass n?