第四届西南交通大学CTF新秀杯
cet6
以前没碰到过的usb流量分析,这题是鼠标流量。先记录一下完整的解题过程。
-
用tshark命令将HID Data提取至usb.txt,并去掉所有空行。
1
tshark -r cet6.pcap -T fields -e usbhid.data | sed '/^\s*$/d' > usb.txt
提取出的每条流量格式为:
01000200fdff0000
。即8个字节。 -
将流量中有效的x、y位移信息提取至result.txt。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18keys = open('usb.txt','r')
result=open('result.txt','w')
posx = 0
posy = 0
for line in keys:
x = int(line[4:6],16)
y = int(line[8:10],16)
if x > 127 :
x -= 256
if y > 127 :
y -= 256
posx += x
posy += y
btn_flag = int(line[0:2],16) # 1 for left , 2 for right , 0 for nothing
if btn_flag == 1 :
result.write(f"{posx} {-posy}\n")
keys.close()
result.close() -
使用gnuplot,输入
plot "result.txt"
即可输出图像,即本题Flag:flag{Mr_Song_needs_a_girlfriend}
。 -
亦可以将2、3两步合并为一步,以下贴出阴间出题人林博康的脚本
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26import matplotlib.pyplot as plt
with open('usb.txt', 'r') as f:
lines = f.readlines()
x = 0
y = 0
x_s = []
y_s = []
for line in lines:
delta_x = int(line[4:6], 16)
if delta_x > 0x7f:
delta_x -= 0x100
delta_y = int(line[8:10], 16)
if delta_y > 0x7f:
delta_y -= 0x100
x += delta_x
y -= delta_y
if line[1] == '1':
x_s.append(x)
y_s.append(y)
plt.scatter(x_s, y_s)
plt.show()可得到同样的输出结果,甚至效果可能更好一些。
接下来是吐槽time
由于我也是第一次做usb流量题,从网上找资料的时候也踩了不少坑。首先是提取流量,网上基本都是usb.capdata
,然而这题需要提取的是usbhid.data
。其次是流量长度,网上少有8字节的鼠标流量资料,基本都是4字节,甚至《从0到1:CTFer成长之路》中对鼠标流量的分析是3个字节,因此这题要找到正确的x、y位移信息也是一个坑。另外,键盘的流量信息倒是8字节的,我一开始也当作键盘流量去做,只能说是疯狂误导人。最后是画图,在网上疯狂找资料的时候也有不少博客附上了脚本,上文中第二步我所贴出的脚本实则从某博客中copy下来修改的,其中对于x、y两个变量的处理也给我整坑里去了,不过最终基本上慢慢修正好了。
最后的最后,贴一个此次没用上的,据说很好用的工具的链接:GitHub - WangYihang/UsbMiceDataHacker: USB鼠标流量包取证工具 , 主要用于绘制鼠标移动以及拖动轨迹 对于此题而言,修改一下提取流量包的命令和提取位移信息的命令应该就能用了。
后面想起来的补充:既然有提到键盘流量,就贴一个键盘流量转换的脚本吧,网上扒的,没试过,就当记录一下
1 | normalKeys = {"04":"a", "05":"b", "06":"c", "07":"d", "08":"e", "09":"f", "0a":"g", "0b":"h", "0c":"i", "0d":"j", "0e":"k", "0f":"l", "10":"m", "11":"n", "12":"o", "13":"p", "14":"q", "15":"r", "16":"s", "17":"t", "18":"u", "19":"v", "1a":"w", "1b":"x", "1c":"y", "1d":"z","1e":"1", "1f":"2", "20":"3", "21":"4", "22":"5", "23":"6","24":"7","25":"8","26":"9","27":"0","28":"<RET>","29":"<ESC>","2a":"<DEL>", "2b":"\t","2c":"<SPACE>","2d":"-","2e":"=","2f":"[","30":"]","31":"\\","32":"<NON>","33":";","34":"'","35":"<GA>","36":",","37":".","38":"/","39":"<CAP>","3a":"<F1>","3b":"<F2>", "3c":"<F3>","3d":"<F4>","3e":"<F5>","3f":"<F6>","40":"<F7>","41":"<F8>","42":"<F9>","43":"<F10>","44":"<F11>","45":"<F12>"} |
R.G!B?
老样子,先放解题过程
-
使用任意十六进制编辑器打开图片,因为此题是png图片,可搜索IEND(即搜索一下文件尾,我习惯于这么搜),能搜到两个结果,即这其实是两张图片,第二张图需手动补文件头。
-
提取出的两张图片放入StegSolve,在Analyse->Image Combiner中,切换到SUB(R,G,B separate),可发现猫腻,保存进行下一步。(可能有人会问:SUB不也有个二维码吗?但是这题的题目是RGB,SUB得出的图片并没有同时存在RGB三种颜色的色块,很明显SUB(R,G,B separate)猫腻更大)
-
通过以下脚本可提取出ook编码信息
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16from PIL import Image
img = Image.open("solved0.bmp")
ook = open("ook.txt", "r")
for y in range(0, 33):
for x in range(0, 33):
r, g, b = img.getpixel((x, y))
if r:
ook.write("Ook. ")
elif g:
ook.write("Ook? ")
elif b:
ook.write("Ook! ")
ook.close() -
将ook.txt的内容扔到ook在线解码即可获得Flag:
flag{w0w_st3g0_m4st3r}
继续吐槽time
这一题是在这学期开学前一周就拿到的题目,原题名字叫做RGB.?!,想来我大抵是被博博拿来做小白鼠了,本题所有的hint都是我踩坑问了博博的,最后知道有个rgb转ook我就没继续做了。因此本来其实并不想动这题,但不知道阴间人博博什么想法,总之是疯狂怂恿我做,才在这个周末终于解决了。对于第一个hint,我那时其实有想过有塞其他图片,但是我那时随手搜了个文件头却只得到一个结果,便去寻找其他思路了,碰壁无果因此询问博博。第二个hint,很明显那个二维码很显眼啊,谁第一个想法不是扫一扫呢,于是天真的我本想写个脚本提取出黑白的二维码图片,条件是当某像素rgb=(0,0,0)时为黑,某值不为0时为白,结果遇到了问题。天真的我选择输出黑块的rgb值,发现所有黑块都不是(0,0,0),修改脚本提取出二维码,然后被骗了。很可惜我没有意识到这并非纯黑的黑块究竟隐藏了什么信息。最后是第三个hint,至此我走投无路,才从博博口中得知ook编码,以及隐藏在题目中的提示,rgb三个值实则分别对应ook编码的.?!。所以其实原题目的暗示更加隐晦,以及hint3几近于明示,因为short ook只需要.?!即可解码。