美文网首页
hxp CTF 2018复现

hxp CTF 2018复现

作者: 黑羽re | 来源:发表于2019-12-01 13:15 被阅读0次

听说hxp 2019要和C3CTF合办了,就看看2018hxp的题目

资源

https://ctf.link/

We try to archive our CTFs as well as possible.
For all our past CTFs we offer you virtual machines which allow you to play the CTFs whenever you want!
See this post for more information.

下载 https://ctf.link/hxp_ctf_2018.ova,然后virtualbox运行,访问http://127.0.0.1:82 就看到题目平台了

平台

Troll

这个类型可以翻译成:菜鸟

cat flag

nc 127.0.0.1 13370

cat flag

我一开始认为这是一道bash jail的题目,因为提供了shell环境嘛,都忽略了flag文件的权限是可读。思维陷入定式了。最后用cat -A flag把前面ansi编码的部分显示出来了。

Web

题目数量较少

time for h4x0rpsch0rr?

源代码有一段可疑的部分:

<a href="admin.php">Admin Access</a>
<script src="mqtt.min.js"></script>
<script>
  var client = mqtt.connect('ws://' + location.hostname + ':60805')
  client.subscribe('hxp.io/temperature/Munich')

  client.on('message', function (topic, payload) {
    var temp = parseFloat(payload)
    var result = 'NO'

/* secret formular, please no steal*/
if (-273.15 <= temp && temp < Infinity) {
  result = 'YES'
}
document.getElementById('beer').innerText = result

  })
</script>

网络层有101状态码的请求,是个MQTT服务

MQTT

访问http://127.0.0.1:8001/admin.php

下载MQTT-SPY工具https://github.com/eclipse/paho.mqtt-spy

操作方法是https://blog.csdn.net/sinat_28771747/article/details/99057034

注意配置Server URI要选择websockets

在这篇关于MQTT的博客中讲到,可以利用#通配

利用通配符获取订阅所有Topic
MQTT 主题(Topic) 支持’+’, ‘#’的通配符,’+’通配一个层级,’#’通配多个层级(必须在末尾)。
也就是说 如果我们有两个Topic分别为 CMD/123/456 CMD/789/666 那么我们可以订阅CMD来获取其CMD下的全部消息

MQTT

然而返回的只有一堆13.37。。。

翻了下官方文档https://github.com/mqtt/mqtt.github.io/wiki/SYS-Topics

这篇文章https://www.jianshu.com/p/0b0788c799fc (原文地址为https://morphuslabs.com/hacking-the-iot-with-mqtt-8edaf0d07b9b)提到通过SYS Topics订阅所有主题可能会泄露信息,并给出了调试方法:使用$SYS/#

SYS

出现了一个webcam(网络摄像头),订阅该话题,发现一张图片,导出之

export

获得账号

webcam

尝试登录吧!(OTP[one time password]具有时效性,手速要快)

User Password OTP
iot_fag I<3SecurID 图上6位数字的信息

即可获得flag。

wor,这就是道IoT的题目,为啥放在web里了

参考:

https://ctftime.org/writeup/12533

Crypto

daring

考点:RSA padding+小公钥

源码对flag部分右侧进行了"\0"的padding,这里扩展一下
左边的 padding 不用管

>>>a="a\x00\x00\x00"
>>>b'\x00\x00a\x00\x00\x00'
>>>bytes_to_long(a)
1627389952L
>>>bytes_to_long(b)
>>>1627389952L

右边的padding想象成bit-shift,每一位都是*256(末尾添加16进制的00),因为

(msg^e \ mod \ n) * (x^e \ mod \ n) \Longleftrightarrow (mgs*x)^e \ mod \ n

我们有了 (mgs*x)^e \ mod \ n 通过逆元把 x 除下去,再配合 e=3的低加密指数攻击,即可

exp:

#!/usr/bin/env python3
from Crypto.Cipher import AES
from Crypto.Hash import SHA256
from Crypto.Util import Counter
from Crypto.PublicKey import RSA
from Crypto.Util.number import *
import gmpy2
n = RSA.importKey(open("pubkey.txt",'r').read()).n
c=int.from_bytes(open("rsa.enc","rb").read(), 'big')
n = 131439155143175043265322066353951646221438306790938190998522265782952062884373948320963990364387806423377384374007937468177671276323489634193305141101111897782540226757793029784559400156340831524038843044706502635279773784856499312207447550053071060656400930280068219967242645499076062394053507154455753332851
e = 3
c = 101289393626607127554187202298707999567698627700625294597228051901600521870872558312539860683380184719944341606093685609696440268292221391526643817365119976661650070266220933422021322751640444938685602977931512982716940247950481943615907166261417571982743004278833526863190964577524016799705809805830751851372
flag_size = len(open("aes.enc", 'rb').read())
new_ct = c * pow(inverse(256, n) ** (128-flag_size), e, n)
new_ct %= n
for i in range(10000):
    potential_pt, is_cube = gmpy2.iroot(new_ct + (n * i), e)
    if is_cube:
        print(i, long_to_bytes(potential_pt))
        break
# (23, 'hxp{DARINGPADS_1s_4n_4n4gr4m_0f_RSAPADDING}')

给AES的目的是把flag的长度算出来。但其实可以通过循环遍历flag_size(128)最终肯定能找到对应的那组

对应的exp:

#!/usr/bin/env python3
from Crypto.Cipher import AES
from Crypto.Hash import SHA256
from Crypto.Util import Counter
from Crypto.PublicKey import RSA
from Crypto.Util.number import *
import gmpy2
n = RSA.importKey(open("pubkey.txt",'r').read()).n
c=int.from_bytes(open("rsa.enc","rb").read(), 'big')
n = 131439155143175043265322066353951646221438306790938190998522265782952062884373948320963990364387806423377384374007937468177671276323489634193305141101111897782540226757793029784559400156340831524038843044706502635279773784856499312207447550053071060656400930280068219967242645499076062394053507154455753332851
e = 3
c = 101289393626607127554187202298707999567698627700625294597228051901600521870872558312539860683380184719944341606093685609696440268292221391526643817365119976661650070266220933422021322751640444938685602977931512982716940247950481943615907166261417571982743004278833526863190964577524016799705809805830751851372
for k in  range(128):
    new_ct = c * pow(inverse(256, n) ** (128-k), e, n)
    new_ct %= n
    for i in range(10000):
        potential_pt, is_cube = gmpy2.iroot(new_ct + (n * i), e)
        if is_cube:
            print(i, long_to_bytes(potential_pt))
            break

待续

相关文章

网友评论

      本文标题:hxp CTF 2018复现

      本文链接:https://www.haomeiwen.com/subject/ebyzwctx.html