- misc24
- misc25
- misc26
- misc27
- misc28
- misc29
- misc30
- misc31
- misc32
- misc33
提示:flag在图片上面。 解答:根据提示,应该是图片被裁减了,调整一下高度就可以。 修改高度为EE000000。 获取到flag。
ctfshow{dd7d8bc9e5e873eb7da3fa51d92ca4b7}
进一步学习:bmp图片格式 bmp的数值在存储上是按“高位放高位、低位放低位”的原则 。
BMP文件头:占14个字节。 1)0x00-0x01:2个字节。 BM(windows),BA(os/2 bitmap array),CI(os/2 color icon),CP(os/2 color pointer),IC(os/2 icon),PT (os/2 pointer) 本题是:424D(BM) 2)0x02-0x05:4个字节。表示位图文件的大小,即整个图片文件的大小(包括信息头)。 以本题为例,F0 4C 0A 00 =>00 0A 4C F0=>675056b =>659.234375 kb,与实际大小660kb一致。 3)0x06-0x09:2个保留位,各占2个字节,共4个字节,设置为0。 3)0x0A-0x0D:4个字节。文件头开始到实际图像数据之间的偏移量。 以本题为例,36 00 00 00 即54个字节。
注:一般遇到的图像以24位图像为主,即R、G、B三种颜色各用8个bt来表示,即位图数据。这类真彩图的位图数据,紧跟在信息头后面,所以对于24或32位图,从文件头开始偏移54个字节是位图数据。
位图信息头:40个字节。 1)0x0e-0x11:4个字节,位图信息头需要的字节数。 如:28 00 00 00 =>40个字节。 2)0x12-0x15:4个字节,图像宽度,以像素为单位。 例如本题:84 03 00 00 => 0384 =>900 3)0x16-0x19:4个字节,图像高度,以像素为单位。 本题就是修改了高度。 同时,正数表示倒向位数,负数表示正向位数。大多数bmp图片是倒向位数。 倒向位数:图像数据是从图像左下角到右上角排列的。 正向位数的图像,将不能被压缩。 4)0x1a-0x1b:2个字节,为目标说明颜色平面数,值总是被设为1。 5)0x1c-0x1d:2个字节,说明比特数/像素,其值为1、4、8、16、24、32。 6)0x1e-0x21:4个字节,说明图像数据压缩类型。 –> 0:不压缩(常用) –> 1:每个象素8比特的RLE压缩编码,BI_RLE8 –> 2:每个象素4比特的RLE压缩编码,BI_RLE4 –> 3:比特域,用于16/32位位图 –> 4:位图含JPEG图像(仅用于打印机) –> 5:位图含PNG图像(仅用于打印机) 7)0x22-0x25:4个字节,说明图像大小,以字节为单位。 8)0x26-0x29:4个字节,说明水平分辨率,有符号整数。可不设置,不设置为0。 9)0x2a-0x2d:4个字节,说明垂直分辨率,有符号整数。可不设置,不设置为0。 10)0x2e-0x31:4个字节,说明位图时间使用的颜色表中的颜色索引数(设置为0的话,则说明使用所有的调色板项) 决定调色板的带下。 11)0x32-0x35:4个字节,说明对图像显示有重要影响的颜色索引数码(设置为0,表示都重要)
位图数据: 1)如果位图信息头中的位图高度是正的,则位图数据在文件中的排列顺序是从左下角到右上角,以行为主序排列的。也就是第一个数据(此处24位,指前3个bytes)是图像最后一行第一列像素色彩数据,第二个数据是图像最后一行第二列像素色彩数据。 2)如果RGB24位位图,则使用3个bytes存储一个像素,按照BGR顺序存储。如果是32位ARGB数据,则按照BGRA的顺序存储。 3)如果存在调色板,则这些数据代表的是调色板的索引序号。
misc25提示:flag在图片下面。 解答:png图片,依旧修改高度。 获取flag。
进一步学习:png图片 (开始放的链接,现在要vip才能完整查看了,而且也并不全面,所以就更换了一个链接,这个链接是英文的png图片的规范要求,读不懂可以找翻译软件,我也还在学习~)
提示:flag还是在图片下面,但到底有多下面?。 解答:还是png图片,提示下面,还很靠下,那就高度调大一些。 获取flag,其中一部分flag需要真实高度。这需要用到脚本了。
脚本文件:
import os
import binascii
import struct
crcbp = open("misc26.png", "rb").read() #打开图片
for i in range(1024):
for j in range(1024):
data = crcbp[12:16] + struct.pack('>i', i)+struct.pack('>i', j)+crcbp[24:29]#从IHDR开始17个字节,其中宽和高用i和j代替,并以4个字节存放i和j。
crc32 = binascii.crc32(data) & 0xffffffff
if(crc32 == 0xec9ccbc6): #010Editor第二行倒数3字节,加第三行第一字节。按顺序写就行,不用改。
print(i, j)
print('hex:', hex(i), hex(j))
#900 606
#hex: 0x384 0x25e
获取到真实高度是0x25e。
ctfshow{94aef125e087a7ccf2e28e742efd704c}
misc27提示:flag在图片下面 解答:找FFC0,然后后面第4个字节位置就是高(2字节)和宽(2字节),用010Editor的话,鼠标放在高度的位置会给一个标识提示,告知是Y_image,然后修改高度即可。 获取flag。
ctfshow{5cc4f19eb01705b99bf41492430a1a14}
提示:flag在图片下面。 解答:gif动图,还是用010Editor,这个实在是好用,像这次不太清楚gif的图片格式,也可以通过其标注的颜色区分,再根据鼠标移动位置提供的提示,找到高度调整的位置。 或者在视图里选择模板结果,就可以提供一个窗口标识各个段,可以找到data区域的image部分,直接在下面修改高度。
模板结果如果是空白的话,可以在上方的“运行模板”选择对应的模板。(下面这个图是我随便找的一个png图,不是本题的)
调整高度后,显示出flag,但是由于gif动图,删的太快,没有看到,用lsp看即可。
ctfshow{59c8bc525426166b1c893fe12a387fd7}
提示:flag在图片下面。 解答:gif图片,修改高度,方式推荐查看模板结果修改,因为动图太多,这样修改更方便一些,每个图都要修改高度。 然后用gif分离器分离一下gif动图,在第8帧找到了flag。
ctfshow{03ce5be6d60a4b3c7465ab9410801440}
提示:正确的宽度是950。 解答:bmp修改宽度为950,即可获取flag。
提示:高度是正确的,但正确的宽度是多少呢。 解答:bmp图片。高度是150,需要计算,宽度,整个图片文件的大小是0x76f58字节(可以通过010查看结尾位置在0x76f47,然后加上1。因为初始位置是0),转成十进制是487256字节大小。 文件头的大小合计是54字节。 RGB每个像素由3个字节表示。
宽度就是:(487256-54)÷3÷150,约等于1082。修改宽度可以得到flag。
提示:高度是正确的,但正确的宽度是多少呢 解答:png图片,用上面的那个png的爆破脚本即可。但是crc32要修改为这个图片的0xe14a4c0b,同时循环条件的range()范围需要调大一些,可以直接改成2000。 最后的结果是宽度为1044。 ctfshow{685082227bcf70d17d1b39a5c1195aa9}
提示:出题人丧心病狂,把高度也改了 解答:png,方法同上。修改crc32为0x5255a798。 宽度:978,高度:142 ctfshow{03070a10ec3a3282ba1e352f4e07b0a9}