• [CTF隐写]png中CRC检验错误的分析


    [CTF隐写]png中CRC检验错误的分析

    最近接连碰到了3道关于png中CRC检验错误的隐写题,查阅了相关资料后学到了不少姿势,在这里做一个总结


    题目来源:

    • bugku-MISC-隐写2
    • bugku-MISC-再来一道隐写
    • JarvisOJ-MISC-炫酷的战队logo

    基础知识:

    ​ 先分析png的文件格式,用16进制编辑器010editor打开一张正常的png图片,逐字节分析如下:

    前八个字节89 50 4E 47 0D 0A 1A 0A为png的文件头,该段格式是固定的

    上图中高亮部分称为为chunk[0]段,可以分为以下几块:

    • 前四个字节00 00 00 0D(即为十进制的13)代表数据块的长度为13,数据块包含了png图片的宽高等信息,该段格式是固定的

    • 之后的四个字节49 48 44 52(即为ASCII码的IHDR)是文件头数据块的标示,该段格式也是固定的

    • 之后进入13位数据块,前8个字节00 00 05 56 00 00 03 00中:

      • 前四个字节00 00 05 56(即为十进制的1366),代表该图片的宽,该段数据是由图片的实际宽决定的

      • 后四个字节00 00 03 00(即为十进制的768),代表该图片的高,该段数据是由图片的实际高度决定的

        这8个字节都属于13位数据块的内容,因此数据块应再向后数5个字节,即为00 00 05 56 00 00 03 00 08 02 00 00 00

    • 剩余的4位40 5C AB 95为该png的CRC检验码,也就是本篇文章要重点讨论的地方,该段数据是由IDCH以及十三位数据块(即上文中的49 48 44 52 00 00 05 56 00 00 03 00 08 02 00 00 00)计算得到的

    有了之上的基础知识,再来看大部分png中CRC检验错误的出题思路:

    对一张正常的图片,通过修改其宽度或者高度隐藏信息,使计算出的CRC校验码与原图的CRC校验码不一致;windows的图片查看器会忽略错误的CRC校验码,因此会显示图片,但此时的图片已经是修改过的,所以会有显示不全或扭曲等情况,借此可以隐藏信息。

    而Linux下的图片查看器不会忽略错误的CRC校验码,因此用Linux打开修改过宽或高的png图片时,会出现打不开的情况

    以隐写2题目举例

    在windows和Linux下分别打开图片,如下图,windows中可以打开,deepin系统显示为空白,因此猜测是该png的宽或高被修改导致CRC校验码错误

    于是用010editor打开该png分析其字节信息,如下图

    红框圈住的部分即为该png的宽和高,红圈圈住的部分为该png的CRC校验码,箭头部分为010editor的templete检测出了png的CRC错误

    于是我们可以通过爆破图片修改前的宽和高来匹配CRC校验码,并用正确的宽和高来修复图片

    为了做题的方便,先尝试爆破高度,脚本如下:

    
    # -*- coding: utf-8 -*-
    import binascii
    import struct
    
    #x49x48x44x52x00x00x01xF4x00x00x01xA4x08x06x00x00x00
    
    crc32key = 0xCBD6DF8A
    for i in range(0, 65535):
      height = struct.pack('>i', i)
      #CRC: CBD6DF8A
      data = 'x49x48x44x52x00x00x01xF4' + height + 'x08x06x00x00x00'
    
      crc32result = binascii.crc32(data) & 0xffffffff
    
      if crc32result == crc32key:
        print ''.join(map(lambda c: "%02X" % ord(c), height))
    

    运行脚本,输出000001F4,即原图片高度为00 00 01 F4爆破成功

    因此我们用010editor修改png的高度为原高度,如下,并保存为新图片

    此时我们发现deepin的图片查看器已经可以正常的打开图片了,说明我们修复成功

    第二题与第一题类似,不再复述;第三题较前两题有所改变,留给大家动手实践


    几点补充:

    • 判断是否为crc校验码错误的方法:

      • windows下图片可以打开,其他系统下图片不能打开
      • 使用010editor的template检测,这也是我16进制编辑器力推010editor的原因之一
      • 使用诸如tweakpng,pngcheck等工具
    • 修复png的crc检验码方法:

      • 本文中所列的爆破出正确的宽或高,并用16进制编辑器修复
      • 利用windows忽略crc检验码的特性,我们可以用tweakpng任意修改图片的宽和高,直至得到有用的信息,事实上,这是最快的方法

    虽说在windows下使用tweakpng是最简单的方法,但还是建议大家在练习过程中通过编程来实现,毕竟对于程序员而言,最大的成就莫过于用自己写的代码来解决问题。

  • 相关阅读:
    函数指针作为函数參数,实现冒泡排序的升序排序和降序排序
    为什么通过空指针(NULL)能够正确调用类的部分成员函数
    vc6.0 点编译时提示Cannot complile the file 'D:souce-codevc-workspace对话框MainFrm.h'; no compile tool is
    struts2中Action訪问servlet的两种方式
    删除LINUX更新后多余的内核
    cocos2d-x 3.0rc2版公布了
    The user specified as a definer ('root'@'%') does not exist
    HDU 4287 Intelligent IME(map运用)
    HDU 4925 Apple Tree(推理)
    Linux下使用Fastboot给手机刷ROM
  • 原文地址:https://www.cnblogs.com/WangAoBo/p/7108278.html
Copyright © 2020-2023  润新知