Looking at the PNG specification, it appears that the PNG pixel data chunk starts with IDAT and ends with IEND (slightly clearer explanation here). In the middle are values that don't make sense to make sense to me.
How can I get usable RGB values from this, without using any libraries (ie from the raw binary file)?
As an example, I made a 2x2px image with 4 black rgb(0,0,0) pixels in Photoshop:

Here's the resulting data (in the raw binary input, the hex values, and the human-readable ASCII):
BINARY      HEX ASCII
01001001    49  'I'
01000100    44  'D'
01000001    41  'A'
01010100    54  'T'
01111000    78  'x'
11011010    DA  '\xda'
01100010    62  'b'
01100000    60  '`'
01000000    40  '@'
00000110    06  '\x06'
00000000    00  '\x00'
00000000    00  '\x00'
00000000    00  '\x00'
00000000    00  '\x00'
11111111    FF  '\xff'
11111111    FF  '\xff'
00000011    03  '\x03'
00000000    00  '\x00'
00000000    00  '\x00'
00001110    0E  '\x0e'
00000000    00  '\x00'
00000001    01  '\x01'
10000011    83  '\x83'
11010100    D4  '\xd4'
11101100    EC  '\xec'
10001110    8E  '\x8e'
00000000    00  '\x00'
00000000    00  '\x00'
00000000    00  '\x00'
00000000    00  '\x00'
01001001    49  'I'
01000101    45  'E'
01001110    4E  'N'
01000100    44  'D'