PWN January 03, 2020

House of Lor

Words count 6.6k Reading time 6 mins. Read count 0

一、原理:

先来看下small bin中的源码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
if (in_smallbin_range(nb)) {
// 获取 small bin 的索引
idx = smallbin_index(nb);
// 获取对应 small bin 中的 chunk 指针
bin = bin_at(av, idx);
// 先执行 victim= last(bin),获取 small bin 的最后一个 chunk
// 如果 victim = bin ,那说明该 bin 为空。
// 如果不相等,那么会有两种情况
if ((victim = last(bin)) != bin) {
// 第一种情况,small bin 还没有初始化。
if (victim == 0) /* initialization check */
// 执行初始化,将 fast bins 中的 chunk 进行合并
malloc_consolidate(av);
// 第二种情况,small bin 中存在空闲的 chunk
else {
// 获取 small bin 中倒数第二个 chunk 。
bck = victim->bk;
// 检查 bck->fd 是不是 victim,防止伪造
if (__glibc_unlikely(bck->fd != victim)) {
errstr = "malloc(): smallbin double linked list corrupted";
goto errout;
}
// 设置 victim 对应的 inuse 位
set_inuse_bit_at_offset(victim, nb);
// 修改 small bin 链表,将 small bin 的最后一个 chunk 取出来
bin->bk = bck;
bck->fd = bin;
// 如果不是 main_arena,设置对应的标志
if (av != &main_arena) set_non_main_arena(victim);
// 细致的检查
check_malloced_chunk(av, victim, nb);
// 将申请到的 chunk 转化为对应的 mem 状态
void *p = chunk2mem(victim);
// 如果设置了 perturb_type , 则将获取到的chunk初始化为 perturb_type ^ 0xff
alloc_perturb(p, bytes);
return p;
}
}
}

这个攻击方式是针对small bin的攻击,首先要先放一个fastbin大小的堆块,然后通过申请0x1000,触发malloc consolidate的处理,把堆块放到small bin中,才能开始我们的攻击,需要的条件:

有3个堆块,small bin中的free_chunk(能控制bk),fake_chunk(能控制fd和bk)、fake_chunk的bk指向的fake_chunk2(能控制fd),实现的链子如下:

57232173165

free_chunk:0x25f20a0 、fake_chunk:0x25f2000 、fake_chunk2:0x25f2140,同时把指针构造好了:

57232186551

下面申请0x68的大小,得到free_chunk,结果如下:

57232206103

再申请就得到了fake_chunk,结果如下:

57232208581

对fake_chunk修改:

1
edit(8,'oooooooo')

57232215562

对原始0号块修改:

1
edit(0,'pppppppp')

57232224856

这样就有2个指针可以操作这个堆块,0和8,有了fake_chunk,就可以改内存了,演示就结束了,通过这种攻击,就可以实现,申请出任意地址的堆块,我想到的利用是:申请出bss上的内存块!

small bin中的free_chunk

bss中的fake_chunk(被申请的victim)

bss中的fake_chunk2

(需要满足的条件是UAF改bk指针、bss地址知道且可写、heap地址知道,随意的是bss中的chunk都不检查size很爽,满足指针即可,和large bin的分配有点相似的地方,也是可以申请出fake_chunk,但是比largebin简单。

0%