pwnable.kr-uaf

题目描述: Mommy, what is Use After Free bug? ssh [email protected] -p2222 (pw:guest) 根据题目描述我们知道该题考察UAF(use after free)漏洞,关于UAF,简单说下就是内存地址在free后并没有被销毁,下次为相同的结构类型分配大小类似的空间时,之前的内存空间会被重新使用,如果第二次的指针能够被用户所控制,就造成了UAF漏洞。然后有些基础知识(转自:http://blog.csdn.net/qq_20307987/article/details/51511230):   1 UAF:引用一段被释放的内存可导致程序崩溃,或处理非预期数值,或执行无干指令。使用被释放的内存可带来诸多不利后果,根据具体实例和缺陷发生时机,轻则导致程序合法数据被破坏,重则可执行任意指令。 2 UAF错误的原因: (1)导致程序出错和发生异常的各种条件 (2)程序负责释放内存的指令发生混乱 其实简单来说就是因为分配的内存释放后,指针没有因为内存释放而变为NULL,而是继续指向已经释放的内存。攻击者可以利用这个指针对内存进行读写。(这个指针可以称为恶性迷途指针) 3 UAF漏洞的利用: (1)先搞出来一个迷途指针 (2)精心构造数据填充被释放的内存区域 (3)再次使用该指针,让填充的数据使eip发生跳转。 4 在填充的阶段要考虑系统的内存分配机制,这里介绍一下SLUB SLUB 对对象类型没有限制,两个对象只要大小差不多就可以重用同一块内存,而不在乎类型是否相同。样的话,同一个笼子既可以放鸡,又可以放鸭。也就是说我们释放掉sock对象A以后马上再创建对象B,只要A和B大小相同(不在乎B的类型),那么B就极有可能重用A的内存。SLAB差不多,只不过要求类型也要相同。 既然B可以为任意对象类型,那我们当然希望选择一个用起来顺手的对象类型。至少要符合以下2个条件: 用户可以控制该对象的大小 用户空间可以对该对象写入数据 如果碰巧这块问题内存新分配的数据是比如C++中的类,那这块内存堆对上可能散落着各种函数指针,只要用shellcode的地址覆盖其中一个函数指针,就能够达成执行任意指令。   5 malloc函数做了那些事情。 大于512字节的请求,是纯粹的最佳分配,通常取决于FIFO,就是最近使用过的。 小于64字节的请求,这是一个缓存分配器,保持一个快速的再生池块。 在这个两者之间的,对于大的和小的请求的组合,做的最好的是通过尝试,找到满足两个目标的最好的。 对于特别大的字节,大于128KB,如果支持的话,依赖于系统内存映射设备。   6 虚函数,一旦一个类有虚函数,编译器会为这个类建立一张vtable。子类继承父类vtable中所有项,当子类有同名函数时,修改vtable同名函数地址,改为指向子类的函数地址,子类有新的虚函数时,在vtable中添加。记住,私有函数无法继承,但如果私有函数是虚函数,vtable中会有相应的函数地址,所有子类可以通过手段得到父类的虚私有函数。   7 vptr每个对象都会有一个,而vptable是每个类有一个 vptr指向vtable 一个类中就算有多个虚函数,也只有一个vptr 做多重继承的时候,继承了多个父类,就会有多个vptr   8 虚函数表的结构:它是一个函数指针表,每一个表项都指向一个函数。任何一个包含至少一个虚函数的类都会有这样一张表。需要注意的是vtable只包含虚函数的指针,没有函数体。实现上是一个函数指针的数组。虚函数表既有继承性又有多态性。每个派生类的vtable继承了它各个基类的vtable,如果基类vtable中包含某一项,则其派生类的vtable中也将包含同样的一项,但是两项的值可能不同。如果派生类覆写(override)了该项对应的虚函数,则派生类vtable的该项指向覆写后的虚函数,没有覆写的话,则沿用基类的值。 […]