注册 登录
自由的生活_软路由 返回首页

心想事成的个人空间 https://bbs.routerclub.com/?681 [收藏] [复制] [分享] [RSS]

日志

再说mips函数劫持二

热度 1已有 1982 次阅读2013-8-14 22:59

才搜索到一个博客,原来国外的牛人已经有人在做这个了。
地址是:
http://jan.stancek.eu/mips_function_runtime_detour
还是转过来
/*
 * detour for malloc on mips
 * (c) Jan Stancek, May 2010
 *
 * At runtime, malloc beginning is overwritten to jump to my_malloc,
 * libc_malloc will jump to trampoline and then back to malloc+XX
 * to provide standard malloc functionality
 *
 *
 *                               +---------------------------------------------+
 *                               |                                             |
 *  0x2ab68964 - malloc          |    0x30000000 - trampoline (libc_malloc)    |   0x400010 - my_malloc
 * +-------------------------+   |   +-----------------------------+           |  +---------------------------+
 * | jump to my_malloc       | --+   | repair $t9 code             |<----+     +->| some code                 |
 * |                         |       | first X malloc instructions |     +--------| jump to libc_malloc       |
 * | the rest of malloc code |<------| jump to malloc+X            |              | some code                 |
 * | (unchanged)             |       |                             |              +---------------------------+
 * | ...                     |       +-----------------------------+
 * |                         |
 * +-------------------------+
 */
 
/*
original malloc code:
Dump of assembler code for function malloc:
   0x2acd6964 <+0>:     lui     gp,0x6
   0x2acd6968 <+4>:     addiu   gp,gp,-25780
   0x2acd696c <+8>:     addu    gp,gp,t9
   0x2acd6970 <+12>:    addiu   sp,sp,-88
   0x2acd6974 <+16>:    sw      ra,84(sp)
   0x2acd6978 <+20>:    sw      s8,80(sp)
   0x2acd697c <+24>:    sw      s7,76(sp)
   0x2acd6980 <+28>:    sw      s6,72(sp)
   0x2acd6984 <+32>:    sw      s5,68(sp)
   0x2acd6988 <+36>:    sw      s4,64(sp)
   0x2acd698c <+40>:    sw      s3,60(sp)
   0x2acd6990 <+44>:    sw      s2,56(sp)
   0x2acd6994 <+48>:    sw      s1,52(sp)
   0x2acd6998 <+52>:    sw      s0,48(sp)
   0x2acd699c <+56>:    sw      gp,24(sp)
 
Dump of assembler code from 0x2ab68964 to 0x2ab68984:
   0x2ab68964:  lui     t9,0x40
   0x2ab68968:  li      at,0xa10
   0x2ab6896c:  addu    t9,t9,at
   0x2ab68970:  jr      t9
   0x2ab68974:  nop
   0x2ab68978:  sw      s8,80(sp)
   0x2ab6897c:  sw      s7,76(sp)
   0x2ab68980:  sw      s6,72(sp)
End of assembler dump.
(gdb) info symbol 0x400a10
my_malloc in section .text of /tmp/JSt1/a.out
 
Dump of assembler code from 0x30000000 to 0x30000038:
   0x30000000:  lui     t9,0x2ab6
   0x30000004:  li      at,0x8964
   0x30000008:  addu    t9,t9,at
   0x3000000c:  lui     gp,0x6
   0x30000010:  addiu   gp,gp,-25780
   0x30000014:  addu    gp,gp,t9
   0x30000018:  addiu   sp,sp,-88
   0x3000001c:  sw      ra,84(sp)
   0x30000020:  lui     t9,0x2ab6
   0x30000024:  li      at,0x8978
   0x30000028:  addu    t9,t9,at
   0x3000002c:  jr      t9
   0x30000030:  nop
   0x30000034:  nop
*/
 
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <sys/mman.h>
#include <asm/cachectl.h>
#include <asm/unistd.h>
 
#define PAGESIZE 4096
#define TRAMPSIZE 20
 
int tramp_base = 0x30000000;
void *(*libc_malloc)(size_t) = NULL;
 
/*
  40096c:       3c19ffff        lui     t9,0xffff
  400970:       3401eeee        li      at,0xeeee
  400974:       0321c821        addu    t9,t9,at
  400978:       03200008        jr      t9
  40097c:       00000000        nop
*/
unsigned char tramp_code[TRAMPSIZE]={ 0x3c, 0x19, 0xff, 0xff,
                             0x34, 0x01, 0xee, 0xee,
                             0x03, 0x21, 0xc8, 0x21,
                             0x03, 0x20, 0x00, 0x08,
                             0x00, 0x00, 0x00, 0x00 };
 
void trampoline_tests()
{
    asm (
            "lui $t9, 0xffff\n"
            "addu $t9, $t9, 0xeeee\n"
            "jr $t9\n"
            ::
        );
}
 
void prepare_tramp_code(void *jump_addr)
{
    int addr = (int) jump_addr;
    tramp_code[2] = (addr >> 24) & 0xff;
    tramp_code[3] = (addr >> 16) & 0xff;
    tramp_code[6] = (addr >> 8) & 0xff;
    tramp_code[7] = addr & 0xff;
}
 
void *my_malloc(size_t size)
{
    void *ret = NULL;
 
    printf("my maloooooooooc\n");
    ret = libc_malloc(size);
    printf("my maloooooooooc ret %p\n", ret);
 
    return ret;
}
 
void dump_mem(void *addr, int len)
{
    int i;
    unsigned char *c;
 
    printf("dump from %p\n", addr);
    for (i=0;i<len;i++)
    {
        c = ((unsigned char *)addr)+i;
        printf("%x ", *c);
        if (i % TRAMPSIZE == TRAMPSIZE -1)
        {
            printf("\n");
        }
    }
    printf("\n");
}
 
void test()
{
    void *v;
    int i;
 
    for (i=0;i<1024;i++)
    {
        v = malloc(200);
        if (v==(int *)0x12345678)
        {
            break;
        }
    }
    printf("after %d\n", i);
}
 
int main()
{
    void *malloc_ptr = (void *) &malloc;
    void *malloc_trampoline = NULL;
    void *malloc_page_ptr = NULL;
    void *malloc_tramp_to_orig = NULL;
    int i = 0;
 
    printf("malloc: %p\n", malloc_ptr);
    printf("my_malloc: %p\n", (void *) &my_malloc);
 
    malloc_trampoline  = mmap((void *)(tramp_base & ~(PAGESIZE-1)), PAGESIZE,
            PROT_READ | PROT_WRITE | PROT_EXEC, MAP_PRIVATE | MAP_ANONYMOUS | MAP_FIXED, 0, 0);
 
    malloc_page_ptr = (void *)(((size_t)malloc_ptr) & ~(PAGESIZE-1));
    if (mprotect(malloc_page_ptr, PAGESIZE*(2), PROT_READ | PROT_WRITE | PROT_EXEC) == -1)
    {
        printf("mprotect failed\n");
        return 2;
    }
 
    if (malloc_trampoline == MAP_FAILED)
    {
        printf("mmap failed\n");
        return 3;
    }
 
    malloc_tramp_to_orig = malloc_trampoline;
 
    // 0x00 - 0x0c malloc repair code for $t9
    prepare_tramp_code(malloc_ptr);
    memcpy(malloc_tramp_to_orig, tramp_code, 0x0c);
 
    // store instruction at malloc beginning to trampoline 0xc - 0x20
    for (i=0;i<TRAMPSIZE;i++)
    {
        unsigned char *dst = ((unsigned char *)malloc_tramp_to_orig)+i+0x0c;
        unsigned char *src = ((unsigned char *)malloc_ptr)+i;
        *dst = *src;
    }
 
    // jump from trampoline to original malloc+TRAMPSIZE, 0x20 - 0x34
    prepare_tramp_code((unsigned char *) malloc_ptr+TRAMPSIZE);
    memcpy((unsigned char *) malloc_tramp_to_orig+0x0c+TRAMPSIZE, tramp_code, TRAMPSIZE);
 
    libc_malloc = (void *(*)(size_t)) malloc_tramp_to_orig;
 
    // jump from original malloc to my_malloc
    prepare_tramp_code((unsigned char *) &my_malloc);
    memcpy((unsigned char *) malloc_ptr, tramp_code, TRAMPSIZE);
 
    dump_mem(malloc_ptr, TRAMPSIZE);
    dump_mem(malloc_tramp_to_orig, TRAMPSIZE*3);
 
    // flush the icache
    asm(
            "lw $a0, %0\n"
            "nop\n"
            "li $a1, %1\n"
            "li $a2, %2\n"
            "li $v0, %3\n"
            "syscall\n"
            :: "m" (malloc_ptr), "i" (TRAMPSIZE), "i" (ICACHE), "i" (__NR_cacheflush) );
 
    // and we are ready to test it
    test();
 
    printf("this is the end....\n");
    return 0;
}

makefile:

all:
        /opt/uclibc-toolchain/ifx-lxdb-1-2/gcc-3.4.4/toolchain-mips-sf/bin-ccache/mips-linux-gcc -g3 -O0 -Wall patch.c

路过

雷人

握手

鲜花

鸡蛋

发表评论 评论 (1 个评论)

回复 htqt 2014-4-15 00:51
太牛,看不懂

facelist doodle 涂鸦板

您需要登录后才可以评论 登录 | 注册

QQ|Archiver|手机版|小黑屋|软路由 ( 渝ICP备15001194号-1|渝公网安备 50011602500124号 )

GMT+8, 2024-4-28 15:20 , Processed in 0.044343 second(s), 6 queries , Gzip On, Redis On.

Powered by Discuz! X3.5 Licensed

© 2001-2023 Discuz! Team.

返回顶部