看雪论坛
发新帖

[求助]谁能告诉我ida怎么用脚本取函数代码啊?

shijiaoan 2006-3-28 03:57 15554
晕,求大家帮帮忙了 小第要取一个函数的代码 子函数有100多个 手动取太麻烦了啊 有谁帮忙写一个脚本 或者教教我怎么写脚本啊 有谁有脚本函数的说明的?看了ida的帮助 都是英文的看不大懂
本主题帖已收到 0 次赞赏,累计¥0.00
最新回复 (18)
10
dreaman 2006-4-3 18:22
2
将下面内容保存到一个文本文件,然后用idapro的装入idc文件执行它,执行前先将光标定位在要生成代码的过程上.

#include "idc.idc"

static ElementExist(arrayid,size,val)
{
        auto i,v;
        for(i=0;i<size;i++)
        {
                v=GetArrayElement(AR_LONG,arrayid,i);
                if(v==val)
                        return 1;
        }
        return 0;
}
static GenFuncIns(st,arrayid,size)
{
        auto start,end,i,ins,x,xt;
        start=st;
        end=FindFuncEnd(start);
        for(i=start;i<end;)
        {
                ins=GetDisasm(i);
                for(x=Rfirst(i);x!=BADADDR;x=Rnext(i,x))
                {
            xt=XrefType();
                        if(xt == fl_CN && !ElementExist(arrayid,size,x))
                        {
                                SetArrayLong(arrayid,size,x);
                                size++;
                        }
                }
                i=ItemEnd(i);/*FindCode(i,1);*/
                Message(form("%s\r\n",ins));
        }
        return size;
}
static main()
{
        auto arrayid,size,pos,st;
        st=ScreenEA();
        if(st==BADADDR)
        {
                Warning("您需要选中一个函数起始地址!");
                return;
        }
        arrayid=CreateArray("gen_func_ins");
        if(arrayid<0)
        {               
                arrayid=GetArrayId("gen_func_ins");
        }
        pos=0;
        SetArrayLong(arrayid,pos,st);
        size=1;
        for(pos=0;pos<size;pos++)
        {
                st=GetArrayElement(AR_LONG,arrayid,pos);       
                Message(form("proc:%8.8x\r\n",st));       
                size=GenFuncIns(st,arrayid,size);
                Message("\r\n");
        }
        DeleteArray(arrayid);
}
30
softworm 2006-4-3 19:45
3
用OD的binary copy不是很方便吗
10
dreaman 2006-4-4 11:04
4
OD的binary copy是拷贝连续的代码吧,楼主说的好象是需要提取一个指定函数及其调用的子函数的代码,可能还是得用脚本比较合适.
11
gzgzlxg 2006-4-5 10:45
5
dreaman这段代码写的不错,我给改了几句,让生成的代码有跳转地址,对于改写可以减少工作。但那个":"号还是有点问题,到处乱加,哈哈,我对IDC的脚本实在是玩不转。
#include "idc.idc"

static ElementExist(arrayid,size,val)
{
  auto i,v;
  for(i=0;i<size;i++)
  {
    v=GetArrayElement(AR_LONG,arrayid,i);
    if(v==val)
      return 1;
  }
  return 0;
}
static GenFuncIns(st,arrayid,size)
{
  auto start,end,i,ins,x,xt,name;
  start=st;
  end=FindFuncEnd(start);
  for(i=start;i<end;)
  {
    ins=GetDisasm(i);
    for(x=Rfirst(i);x!=BADADDR;x=Rnext(i,x))
    {
      xt=XrefType();
      if(xt == fl_CN && !ElementExist(arrayid,size,x))
      {
        SetArrayLong(arrayid,size,x);
        size++;
      }
    }
    if ((name=GetTrueNameEx(i,i)) != 0)
            if (LocByName(name) == start)
                    Message("%s\r\n",name);
            else
                    Message("%s:\r\n",name);
    i=ItemEnd(i);/*FindCode(i,1);*/
    Message(form("    %s\r\n",ins));
  }
  return size;
}
static main()
{
  auto arrayid,size,pos,st,name;
  st=ScreenEA();
  if(st==BADADDR)
  {
    Warning("您需要选中一个函数起始地址!");
    return;
  }
  arrayid=CreateArray("gen_func_ins");
  if(arrayid<0)
  {   
    arrayid=GetArrayId("gen_func_ins");
  }
  pos=0;
  SetArrayLong(arrayid,pos,st);
  size=1;
  for(pos=0;pos<size;pos++)
  {
    st=GetArrayElement(AR_LONG,arrayid,pos);  
    Message(form("proc:%8.8x\r\n",st));
    if ((name=GetType(st)) != 0)
            Message("%s\r\n",GetType(st));
    size=GenFuncIns(st,arrayid,size);
    Message("\r\n");
  }
  DeleteArray(arrayid);
}
1
ViperDodge 2006-4-5 12:40
6
  问一下,脚本执行完毕后,结果放在哪里?
11
gzgzlxg 2006-4-5 13:08
7
直接拷贝出去,如果代码太大,就会溢出,这是有两个办法,要么改这个IDC让他直接写成文件,要么加大IDA的缓冲区。
2
bshjp 2006-4-5 15:32
8
gzgzlxg 能不能把代码写出的文件的脚本加进来~
shijiaoan 2006-4-5 17:05
9
非常感谢上面两位高手!
shijiaoan 2006-4-5 17:28
10
哈哈 我也修改了一下 这样可以写到文件里了 而且对于错误的call也能辨认
#include "idc.idc"

static ElementExist(arrayid,size,val)
{
  auto i,v;
  for(i=0;i<size;i++)
  {
    v=GetArrayElement(AR_LONG,arrayid,i);
    if(v==val)
      return 1;
  }
  return 0;
}
static GenFuncIns(st,arrayid,size)
{
  auto start,end,i,ins,x,xt,funcend;
  start=st;
  end=FindFuncEnd(start);
  for(i=start;i<end;)
  {
    ins=GetDisasm(i);
    for(x=Rfirst(i);x!=BADADDR;x=Rnext(i,x))
    {
      xt=XrefType();
      if(xt == fl_CN && !ElementExist(arrayid,size,x))
      {
        SetArrayLong(arrayid,size,x);
        size++;
      }
    }
    i=ItemEnd(i);/*FindCode(i,1);*/
    //Message(form("%s\r\n",ins));
  }
  return size;
}
static main()
{
  auto arrayid,size,pos,st,file,funcend;
  st=ScreenEA();
  file=fopen("c:\Get.asm","a+");
  if(st==BADADDR)
  {
    Warning("您需要选中一个函数起始地址!");
    return;
  }
  arrayid=CreateArray("gen_func_ins");
  if(arrayid<0)
  {   
    arrayid=GetArrayId("gen_func_ins");
  }
  pos=0;
  SetArrayLong(arrayid,pos,st);
  size=1;
  for(pos=0;pos<size;pos++)
  {
    st=GetArrayElement(AR_LONG,arrayid,pos);  
    Message(form("proc:%8.8x\r\n",st));  
    funcend=FindFuncEnd(st);
    if (funcend!=BADADDR)
    {
      Message("正在将这个函数代码写入c:\Get.asm中...\r\n");  
      GenerateFile(OFILE_ASM,file, st,funcend, 0);
    }
    else
    {
      Message(form("proc:%8.8x Write false\r\n",st));
    }
    size=GenFuncIns(st,arrayid,size);
  }
  DeleteArray(arrayid);
Message("All done, exiting...\n");
}
10
dreaman 2006-4-5 19:07
11
改过的比我写的好多了.
11
gzgzlxg 2006-4-6 00:21
12
再改写一下,见笑了。
生成的文件放在c盘的根目录不好,所以改到当前打开的 idb 文件目录下,文件名由 idb 的文件名加上 Part 组成。
#include "idc.idc"

static ElementExist(arrayid,size,val)
{
  auto i,v;
  for(i=0;i<size;i++)
  {
    v=GetArrayElement(AR_LONG,arrayid,i);
    if(v==val)
      return 1;
  }
  return 0;
}
static GenFuncIns(st,arrayid,size)
{
  auto start,end,i,ins,x,xt,funcend;
  start=st;
  end=FindFuncEnd(start);
  for(i=start;i<end;)
  {
    ins=GetDisasm(i);
    for(x=Rfirst(i);x!=BADADDR;x=Rnext(i,x))
    {
      xt=XrefType();
      if(xt == fl_CN && !ElementExist(arrayid,size,x))
      {
        SetArrayLong(arrayid,size,x);
        size++;
      }
    }
    i=ItemEnd(i);/*FindCode(i,1);*/
    //Message(form("%s\r\n",ins));
  }
  return size;
}
static main()
{
  auto arrayid,size,pos,st,file,funcend,path;
  st=ScreenEA();
  path = GetIdbPath();
  path = substr(path, 0, strlen(path) - 4) + "Part.asm";
  file=fopen(path,"w+");
  if(st==BADADDR)
  {
    Warning("您需要选中一个函数起始地址!");
    return;
  }
  arrayid=CreateArray("gen_func_ins");
  if(arrayid<0)
  {    
    arrayid=GetArrayId("gen_func_ins");
  }
  pos=0;
  SetArrayLong(arrayid,pos,st);
  size=1;
  for(pos=0;pos<size;pos++)
  {
    st=GetArrayElement(AR_LONG,arrayid,pos);  
    Message(form("proc:%8.8x\r\n",st));  
    funcend=FindFuncEnd(st);
    if (funcend!=BADADDR)
    {
      Message("正在将这个函数代码写入 %s \n",path);  
      GenerateFile(OFILE_ASM,file, st,funcend, 0);
    }
    else
    {
      Message(form("proc:%8.8x Write false\r\n",st)); 
    }
    size=GenFuncIns(st,arrayid,size);
  }
  DeleteArray(arrayid);
  fclose(file);
Message("All done, exiting...\n");
}
11
FishSeeWater 2006-4-6 08:41
13
牛老大们多写点IDA教程呀:)
我等菜鸟很需要的:)
jules 2006-4-6 09:56
14
顶牛牛们
ida反编译出来的代码可读性比od高挺多的,希望牛牛们多贴一些ida的使用技巧
4
快雪时晴 2006-4-6 11:56
15
顺便问问牛人们有么有OD下的同类脚本
shijiaoan 2006-4-7 15:18
16
代码取出来了 但是又有一个问题出现了 就是代码中的数据太多
mov        dword_B9BBA8, eax像这样的很多,200多个,都是全局变量 太多了一个个取出来好麻烦 有没有高手知道怎么解决的?
luogeng 2006-7-18 11:46
17
高手啊,谢谢了
shijiaoan 2006-8-18 18:25
18
原来全局变量就只能手动取
deepwater 2006-8-19 09:23
19
甚好
返回



©2000-2017 看雪学院 | Based on Xiuno BBS | 知道创宇带宽支持 | 微信公众号:ikanxue
Time: 0.013, SQL: 10 / 京ICP备10040895号-17