堆漏洞挖掘——fastbin attack漏洞

一、核心思想

  • 通过fastbins链的管理,达到目标地址(target)读写。

二、原理图解

fastbin存储freechunk的单链表结构:

  • 第一步:我们知道被free的chunk会被放入到arena所管理的fastbins链中。如果此时我们malloc一个堆块p,并将其free到fastbin链中,但是我们的p指针没有置空,所以仍然指向于这个freechunk的fd成员处。
char *p=malloc(size);

free(p);

  • 第二步:释放之后,arena管理的fastbin中bin头的fd指针指向于我们申请的这个chunk,p指针就是chunk的fd,如上图所示。
  • 第三步:这个chunk的fd指针本来指向于数值0,此时我们通过p指针将fd指针指向于我们的target地址。
*p=target

  • 第四步:此时我们再去malloc与我们释放的chunk相等大小的chunk,那么被上面被free掉的chunk就会从fastbin单链表中移除,根据fastbin链表的单链表结构,此时arena的fastbin的bin头的fd指针指向于我们的target地址了。
char *q=malloc(size);

  • 第五步:由于此arena的fastbin的bin头的fd指针指向于我们的target地址了。此时我们再去malloc的时候,就是把target这块地址malloc出来给应用层使用了,此时我们就可以使用返回的target的指定地址,对target进行读写了。
char *r=malloc(size);

三、目标地址的构造

  • 如果从fastbins中malloc一个freechunk时,glibc会做以下两个检测:
    • 检测1:检测你要malloc的freechunk的大小是否在该chunk所在的fastbin链的大小尺寸范围内(例如:一个fastbin链所存储的chunk大小必须在0x30-0x40之间,但是你要申请的这个chunk却是0x50,那么就会程序就报错退出)。
    • 检测2:检测你这个freechunk的size成员的PREV_INUSE为是否为1,为1才可以通过检测。
  • 检测详情见文章:https://blog.csdn.net/qq_41453285/article/details/97753705
  • 因此,如果我们想要从fastbin中malloc出这个target地址来使用,需要做以下的构造:

构造①

  • 构造什么:我们需要让target目标地址指定偏移位置处(size成员地址处)的数值与当前fastbin所管理的freechunk的大小范围一致
  • 存在的问题:我们所攻击的target地址的指定偏移位置处(size成员地址处)的数值不一定能够满足当前的fastbin所管理的大小范围
  • 如何解决:虽然我们的target地址处的数值不能满足fastbin的要求,那么可以通过内存地址的偏移,取target地址附近的其它地址,查看其它地址的指定偏移处是否满足fastbin的大小要求,如果有满足的,那么就将这块地址作为攻击目标
  • 如下图所示,我们不是直接将target地址作为攻击目标放入fastbin中,因为其指定偏移地址处的伪造size成员数值不能够满足系统要求,因此我们选择了target地址附近的一块其他地址来作为攻击的目标,其指定偏移地址处的数值符合fastbin所管理的要求。

构造②

  • 构造什么:如果构造①通过了,那么系统还会检测目标地址偏移的size成员数值的PREV_INUSE为是否为1,以及NON_MAIN_ARENA、IS_MAPPED位的规则。这一系列就是要通过do_check_malloced_chunk函数的检测。
  • do_check_malloced_chunk函数检测见文章:https://blog.csdn.net/qq_41453285/article/details/97753705
  • 存在的问题:如果我们的攻击目标地址的指定偏移的size成员数值的IS_MAPPED位不为1,那么glibc就会认为该地址不是由mmap系统调用所申请的,于是就执行if,但是assert中的断言会是程序终止(因为不满足)。

  • 如何解决:所以我们选取的攻击目标地址的偏移size成员数值的NON_MAIN_ARENA、IS_MAPPED、PREV_INUSE位都要为1,比如当前fastbin所能管理的freechunk大小为0x70~0x80,而伪造的size成员处的数值为0x71、0x72这样的数值不能够符合要求的,但0x7f这样的地址就可以满足需要,因此构造完①之后,攻击目标地址的伪造size成员成员数值的NON_MAIN_ARENA、IS_MAPPED、PREV_INUSE位都要为1,0x7f就可以满足。

四、漏洞的技巧点

  • 技巧①:我们malloc的时候,尽量malloc一个大小在0x70~0x80之间的堆块(因此malloc的参数要为0x60~0x70之间),因为这样我们的目标地址就会被放入0x70~0x80大小范围的fastbin链中,此时我们去构造堆块的时候,由于系统中0x7f这样的数值比较好找,所以能够构造0x7f这样的数值来跳过glibc的检测一。
  • 技巧②:接着技巧①,如果此时我们没有数值为0x7f这样的地址来让我们构造,那么我们就需要使用借助unsortedbin attack了,利用unsortedbin attack向我们的目标地址处写入一个0x7f的数值(见文章:https://blog.csdn.net/qq_41453285/article/details/99329694)。

五、__malloc_hook攻击

六、演示案例

  • 待续。

  • 我是小董,V公众点击"笔记白嫖"解锁更多【堆漏洞挖掘】资料内容。

相关推荐
©️2020 CSDN 皮肤主题: 护眼 设计师:闪电赇 返回首页