伪代码:如何从位和字节解码PNG文件?

ANo*_*tly 11 algorithm png image bitmap pseudocode

我一直试图通过逆向工程我在GIMP中创建的.png文件来解决这个问题.它是4x4像素.我的目标是将原始像素解码出文件,目的是将其反转以进行编码.

这是文件的完整十六进制转储:

89504E47 0D0A1A0A 0000000D 49484452 00000004 00000004  
08020000 00269309 29000000 3F494441 54081D01 3400CBFF  
01CC96B1 134FE120 C0CECDF1 5101FFA5 60000000 000000E0  
403201DF E59286DF 6D000000 00000004 EDB11F00 2E007A21  
93EDB11F 3063136F 4733525A 00000000 49454E44 AE426082  
Run Code Online (Sandbox Code Playgroud)

根据规范,我们从PNG签名开始,这是前8个字节.

89504E47 0D0A1A0A

然后我们重复"块"结构,这个文件有3个"块",标题(IHDR),图像数据(IDAT),然后是结束"块"(IEND).

每个块被安排成:块数据长度的前4个字节,数据类型的接下来的4个字节,然后是实际数据的n个字节,然后是4个字节用于循环冗余校验(CRC)数据类型和实际数据部分.

通过......

0000000D

是块的数据长度(13个字节).

49484452

是块的类型(IHDR).

00000004 00000004 08020000 00

是块的数据(4字节宽度,高度; 1字节位深度,颜色类型,压缩方法,滤波方法,隔行扫描方法).

269309 29

是数据和类型的CRC(设法让代码从这里开始工作.

000000 3F

是下一个块的数据长度(63个字节).

494441 54

是块的类型(IDAT).

081D01 3400CBFF 01CC96B1 134FE120 C0CECDF1 5101FFA5 60000000 000000E0 403201DF E59286DF 6D000000 00000004 EDB11F00 2E007A21 93EDB11F 3063136F

是块的实际数据(压缩和过滤的图像数据).

所以我的实际问题是如何将最后一部分解码为原始像素?

根据规范,我必须首先解压缩数据(INFLATE?)然后不过滤它(??)以留下像素的扫描线(我的目标).

如果这可以用伪代码解释那将是惊人的!否则我对Swift很熟悉,对C语言则不太熟悉......

Mar*_*ell 2

我认为pngcheck会对你有很大帮助:

pngcheck -vv result.png
Run Code Online (Sandbox Code Playgroud)

样本输出

File: result.png (334985 bytes)
  chunk IHDR at offset 0x0000c, length 13
    600 x 450 image, 24-bit RGB, non-interlaced
  chunk IDAT at offset 0x00025, length 65536
    zlib: deflated, 32K window, default compression
    row filters (0 none, 1 sub, 2 up, 3 avg, 4 paeth):
      1 4 4 4 4 4 4 4 1 4 4 4 4 4 4 4 1 4 4 4 4 4 4 4 4
      1 4 4 1 4 1 4 1 4 4 4 4 4 4 1 1 1 1 1 1 1 1 1 1 1
      1 1 1 1 1 1 1 1 1 4 4 1 1 1 1 1 1 1 4 4 1 4 1 1 4
      4 4 4 4 4 1 4 4 4 4 4 4 4 1 4 4 4 4 4 4 4 (96 out of 450)
  chunk IDAT at offset 0x10031, length 65536
    row filters (0 none, 1 sub, 2 up, 3 avg, 4 paeth):
      1 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 1
      4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4
      4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 1 4 4
      4 4 4 4 4 4 4 4 4 4 4 4 4 1 4 4 4 (188 out of 450)
  chunk IDAT at offset 0x2003d, length 65536
    row filters (0 none, 1 sub, 2 up, 3 avg, 4 paeth):
      4 4 4 4 4 4 4 4 4 4 4 4 1 4 4 4 4 4 4 4 4 4 4 4 4
      4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4
      4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4
      4 1 4 4 4 4 4 4 4 4 (273 out of 450)
  chunk IDAT at offset 0x30049, length 65536
    row filters (0 none, 1 sub, 2 up, 3 avg, 4 paeth):
      4 4 4 4 4 4 4 4 4 2 4 4 4 4 4 1 4 4 4 4 4 4 4 4 4
      4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4
      4 4 4 4 4 4 4 4 4 4 4 4 4 1 4 4 4 4 4 4 4 1 4 4 4
      4 4 4 4 1 4 4 4 (356 out of 450)
  chunk IDAT at offset 0x40055, length 65536
    row filters (0 none, 1 sub, 2 up, 3 avg, 4 paeth):
      4 4 4 4 1 4 4 4 4 4 4 4 1 4 4 4 4 4 4 4 4 4 4 4 4
      4 4 4 1 4 4 4 4 4 4 4 1 1 1 4 4 1 4 4 1 1 1 4 4 4
      4 4 1 1 1 4 1 4 4 4 1 4 1 4 4 4 1 4 1 4 4 4 4 4 4
      4 1 1 4 1 4 4 1 4 1 (441 out of 450)
  chunk IDAT at offset 0x50061, length 7188
    row filters (0 none, 1 sub, 2 up, 3 avg, 4 paeth):
      4 1 1 4 4 4 4 1 4 (450 out of 450)
  chunk IEND at offset 0x51c81, length 0
No errors detected in result.png (8 chunks, 58.6% compression).
Run Code Online (Sandbox Code Playgroud)