from pngparser import PngParser, chunktypes
import zlib

def calc_crc(chunk):
    return zlib.crc32(chunk.type + chunk.data).to_bytes(chunktypes.CHUNK_CRC_SIZE, 'big')

parser = PngParser("./intro-forensics-3")
header = parser.get_header()
header.crc = calc_crc(header)

data_chunks = [chunk  for chunk in parser.get_all() if chunk.type not in  [b"IHDR", b"IEND"]]

for chunk in data_chunks:
    chunk.crc = calc_crc(chunk)

end_chunk = parser.get_by_type(chunktypes.TYPE_IEND)
end_chunk[0].crc = calc_crc(end_chunk[0])

correct_chunk = [data_chunks[21], data_chunks[16], data_chunks[18], data_chunks[24], data_chunks[4], data_chunks[13], data_chunks[23], data_chunks[5], data_chunks[19], data_chunks[10], data_chunks[8], data_chunks[6], data_chunks[14], data_chunks[15], data_chunks[2], data_chunks[9], data_chunks[22], data_chunks[3], data_chunks[1], data_chunks[17], data_chunks[12], data_chunks[0], data_chunks[7]]

possible_chunks = [(id,x) for id,x in enumerate(data_chunks) if x not in correct_chunk]

for (id, chunk) in possible_chunks:
    chunks = [header] + correct_chunk + [chunk] + end_chunk

    png_file = bytes.fromhex("89 50 4E 47 0D 0A 1A 0A".replace(" ", ""))

    for chunk in chunks:
        png_file += chunk.to_bytes()

    with open(f"reconstructed_{id}.png", "wb") as f:
        f.write(png_file)
