pwn-kernel_Heap总结
一、SLUB和SLAB:内核的堆比用户的堆会简单很多,需要了解一些机制。
1.分配的大小:也是类似对齐的,但也有点不同
linux下查看命令:cat /proc/slabinfo
可以看到kmalloc分为很多的大小,从大到小分别为8k->8字节,每个都相当于是一个桶,里面存储所有的空闲块或者非空闲块。所以当我们分配17字节时,得到的空间其实是32字节,5K字节得到的是8K字节的空间。这个在用堆溢出的时候需要用到。
2.管理机制:单链表结构
(1)申请原则:
以一定大小的空闲chunk作为一个单链表,以fd串联,并且chunk的结构只有一个fd,不像用户态中有有头结构:
如果申请期间改变了空闲链表第一个chunk的fd,那么再申请一次得到该chunk,然后再申请就得到修改后的fd。如上图,如果0xffff8880029f8000是对应slub桶大小的chunk空闲链表第一个,那么申请该大小chunk后得到的是0xffff8880029f8000,再申请一次就会得到0x6bc360。
▲这个具体的管理结构不知道在哪,但是如果再申请该大小的chunk:
①0x6bc360在被申请出来之前,其fd为一个有效的可用地址,比如
0x6bc360 –> 0x6bc460,那么就会得到连续得到0x6bc360和0x6bc460。
②0x6bc360在被申请出来之前,其fd为0,比如
0x6bc360 –> 0x0,那么先得到0x6bc360,然后会从另一个桶中申请chunk,该大小的空闲链表桶就会废弃不再使用,相当于系统默认该桶用完。之后再申请该大小的chunk会从新桶中继续申请。
③0x6bc360在被申请出来之前,其fd为无效地址,比如
0x6bc360 –> 0x40,那么先得到0x6bc360,然后再申请,系统就会崩溃。
(2)释放原则:
同样是以一定大小的空闲chunk作为一个单链表,以fd串联,也类似fastbin结构,先进后出:
这里可以看到,释放完三个chunk之后,再申请,会先得到chunk0,再得到chunk2,chunk1。所以这里也同样可以看出,在释放之后,该chunk的fd会被改写,指向下一个空闲chunk。只不过不用看size和其他七七八八的检查,只用fd即可打类似fastbin的攻击了,方便了很多。