0%

看malloc源码学到的一些细节

前话

我说真的…这个缩进看的怀疑人生 mmp。

里面内容肯定也有理解错误的地方…我相信以后还会多次看malloc的源码。

源码前前后后差不多看了一个多月,配合起华庭的Glibc内存管理效果更佳!


1.进行fastbin attack的时候 大小范围要在两个size_t(也就是)内

2.如果使用smallbin默认的分配(不使用unlink) 只检查bk -> fd ?= victim(感觉没啥用)

3.largebin 从大到小排序,

nextsize也是从大到小排序。

由于从前向后遍历时本身就代表了一个最大的chunk 所以可以直接作为这个大小的代表,

假如有这个大小的chunk存在的话 则放在最后,不去改变nextsize这个链表。

4.只有当要申请的大小为large_chunk的时候调用malloc_consolidate(遍历fastbin合并,放入bins中)(一直理解错了)。

5.一直在想为啥默认都将prev_inuse位设为1…一阵头脑风暴后,在free的时候会将相邻的chunk直接合并…所以再次分配的时候就不会管了…真是想了个蠢问题。

6.在搜寻比当前所需size大的chunk时候,搜寻的方式非常有趣。binmap这个数组每一个成员为一个map,一个dword的长度,32位每一位都为一个bins的idx所对应的bin,1则为这个bin中有成员,最后用&操作就可以很快的将整个Bins遍历过去,确定一个block(也就是一个map),最后遍历这个map。

7.当topchunk没有分配成功的时候,就会调用malloc_consolidate,再尝试在这里重新分配一次。如果都没有成功,就调用sysmalloc。

8.在分配的时候会从unsorttedbin的最后一个开始尝试分配,一旦没分配成功就会将其放入bins中。

9.这边对malloc做一个小总结:

​ (1).当申请一个smallbin时:

​ [1].当申请的大小属于fastbin时,首先会从fastbin中寻找有没有适合的chunk,没有的话进入下一步。

​ [2].有两种情况,一种是fastbin中没有合适的chunk,抑或是需要的大小大于fastbin的范围(大于max_fast),那么就去smallbin中找适合chunk。在这种情况下,对要分配的chunk做一次检查,bck -> fd == victim,比unlink()少检查了一个。若没有找到合适chunk,便从unsortedbin中进行遍历检查,在找到合适的chunk之前,每一个被检查的chunk假如大小不符合,都会被放入相应的bin中。(这里可以产生unsortedbin attack,将unsortedbin的地址写入任意地址)若找到了且剩余chunk大小大于minsize(4 * size_t),那么剩下的这部分将会继续留在unsortedbin中,否则一并给用户。但若想分配smallbin的话条件要更多一些。首先,这个unsortedbin中只能有这个要被分配的chunk。其次,这个chunk还要是last_remainder(切割之后的chunk|但我记得最后free的chunk也可以?明天试一下)(最后一步只是表面可以,实际上要从unsortedbin中直接分配出去只有这一条路径,而上面这一步只是将这个bin先放入smallbin中,再进行搜寻,最后搜寻到的结果放入(间接分配)),这样才能将这个chunk分配出去。到这里不满足,就会去将整个bins遍历一次,遍历方法上述又讲。假如到这一步也没解决问题,那只能动用top_chunk了。大小满足切就是了。但这里又有一个情况,加入top_chunk大小不满足,就会执行一次malloc_consolidate(),在代码注释中指的是多线程的情况,这里就不多做赘述。那么之后再入之前那样作便是。假如还是不满足,就调用sysmalloc。这里还没看,后面补充。

​ (2).当申请一个largebin时:流程和上面区别不大,值得注意的就是会在开始调用malloc_consolidate()。其他一些点上面都有提及。

10.感觉sysmalloc没啥好讲的…sbrk和mmap看的一脸雾水mmp。

11.malloc_consolidate()细节。将fastbin中所有的chunk附近的空闲chunk合并,各个放入unsortedbin中。如果隔壁是top_chunk,即与top_chunk合并。

12.fastbin这个指针数组实时更新的是最后free的chunk的地址…一直理解错了。那么double_free的检查就很好理解了。

13.TRIM_FASTBINS这个鸟东西。我说我看了半天_int_free怎么也不知道为啥fastbin在free的时候为啥不会被合并,原来是这个位被置了。

14.在free函数中,除了fastbin,其他被free的chunk都会放入unsortedbin中,而从unsortedbin 到各种bins中则是在malloc的时候进行一次while循环将所有的chunk放入相对应的bins中。

15.最后一个之前抱有疑问的东西是为啥当释放一个不属于fastbin的chunk的时候会将相邻的fastbin合并,本身源码中是没有看见这样的一个循环的。我一开始想是不是修改这个chunk的prev_size达到要求,后来发现也不是。所以在这里我只能猜测是通过最后的那个heap_trim。再点进去脑子有点疼。

16.先总结到这吧…直接放上去了。


写在最后

初步看完源码,下一个准备看密码学了Orz。

自己pwn还是菜的一比。A爷爷比我不知道高到哪里去了Orz。

不管是Re还是Pwn还是密码学还是以后的安全路,真的都很有趣。

路程才刚开始,期待即将到来的大二生活!

高数补考怎么办…