Bit counter using basic logic gates
Given inputs A, B, C, D and outputs X, Y, Z, where XYZ is a 3 bit unsigned binary number representing the number of bits in ABCD that are 1.  Let X be the most siginfiant bit of the binary number and let Z be the least significant bit.

The truth table for the function looks like...

ABCD => XYZ
0000 => 000
0001 => 001
0010 => 001
0011 => 010
0100 => 001
0101 => 010
0110 => 010
0111 => 011
1000 => 001
1001 => 010
1010 => 010
1011 => 011
1100 => 010
1101 => 011
1110 => 011
1111 => 100

From the truth table we see plainly that the X output is only 1 when all bits in ABCD are 1.  Therefore...

X = A AND B AND C AND D

We see plainly that the Z output only 1 when an odd number of bits are 1.  An odd parity function is easily implemented using XOR gates.  Therefore...

Z =  A XOR B XOR C XOR D

The function for the Y output is a little less obvious.  1 when at least two of ABCD are on but not when all four are on.  The Y term may be written as all combinations of two inputs being on except when all four are on.

Y = ((A AND B) OR (A AND C) OR (A AND D) OR (B AND C) OR (B AND D) OR (C AND D)) AND NOT X

As an alternate to what is described above, this function could also be constructed by cascading a two bit adder and two three bit adders.  The first adder adds A and B.  The second adder adds the result of the first adder to C.  And the third adder adds the result of the second adder to D, and so on for any number of inputs.