乔延臣 发表于 2014-12-23 10:09

IDA 批量 导出 Function Window的信息

本帖最后由 乔延臣 于 2014-12-23 10:12 编辑

引用:http://grapeel.com/?p=251问题描述:如何批量获取PE文件的汇编代码.asm以及.asm文件中的函数标志位?如下图所示,最右边的R、F、L等就是函数的标志位,其中L表示Library Function,这些函数都是从系统库中调用的,在分析时一般情况下是不需要分析的,只要根据函数名字了解了这个函数的功能就够了,所以需要根据标志位把这些函数区分出来。http://grapeel.com/wp-content/uploads/2014/12/image_thumb2.png解决方案:借鉴自:批量模式:http://bbs.pediy.com/showthread.php?t=147777函数信息:http://blog.csdn.net/whatday/article/details/8630354由于没有深入研究IDA,所以只能借鉴别人的工作,在别人工作基础上修改运用。在IDA的根目录下有个idc目录,是存储以idc语言编写插件的一个目录,目录下的ida.idc是IDA启动时调用的一个插件,当批量模式idaw.exe执行时也会调用。首先在该目录下新建一个idc文件,可以以export_func_flag.idc命名,具体代码如下:#include <idc.idc>
static export_func_flag()
{
    auto addr,path,file,imagebase;
    file = fopen(GetInputFilePath(),"rb");
    if (0 == file)
    {
      Warning("open INPUTFILE failed!");
      return;
    }
    if (0 != fseek(file,0x3c,0))
    {
      Warning("seek e_lfanew failed!");
      fclose(file);
      return;
    }
    imagebase = readlong(file,0);
    if (0 != fseek(file,imagebase + 0x34,0))
    {
      Warning("seek imagebase failed!");
      fclose(file);
      return;      
    }
    imagebase = readlong(file,0);
    fclose(file);
    path = GetInputFilePath()+".lu";
    if (BADADDR == path)
    {
      Warning("AskFile failed!");
      return;
    }
    file = fopen(path,"w");
    if (0 == file)
    {
      Warning("fopen failed!");
      return;
    }
    addr = MinEA();
    auto x, y;
    if ("" != GetFunctionName(addr))
    {
                  fprintf(file,"%s",GetFunctionName(addr));
                  x = GetFunctionFlags(addr);
                  if (x & FUNC_LIB)
                            fprintf(file, "\t0");
                  else
                            fprintf(file, "\t1");
      fprintf(file, "\n");
    }
    for(addr = NextFunction(addr);BADADDR != addr;addr = NextFunction(addr))
    {
         fprintf(file,"%s",GetFunctionName(addr));
                  x = GetFunctionFlags(addr);
                  if (x & FUNC_LIB)
                            fprintf(file, "\t0");
                  else
                            fprintf(file, "\t1");
      fprintf(file, "\n");
    }
    fclose(file);
    Message("output functions' names finished!");
}之后,在ida.idc的#include <idc.idc>下添加上#include <export_func_flag.idc>,并在main函数中加入两行代码,如下所示:static main(void)
{
//
//      This function is executed when IDA is started.
//
//      Add statements to fine-tune your IDA here.
//

// Instantiate the breakpoints singleton object
Breakpoints = BreakpointManager();
//AddHotkey("Alt-9","CamelLu");
Wait();
export_func_flag();

// uncomment this line to remove full paths in the debugger process options:
// SetCharPrm(INF_LFLAGS, LFLG_DBG_NOPATH|GetCharPrm(INF_LFLAGS));
}记住,一定要加上Wait();这行代码,否则在未逆向完全时就输出,得到的信息不完整。之后,需要再在这个目录中新建一个批量模式脚本,命名为myanalysis.idc,代码如下:#include <idc.idc>
static main()
{

// turn on coagulation of data in the final pass of analysis
SetShortPrm(INF_AF2, GetShortPrm(INF_AF2) | AF2_DODATA);

Message("Waiting for the end of the auto analysis...\n");
Wait();

Message("\n\n------ Creating the output file.... --------\n");
auto file = GetInputFilePath() + ".asm";
WriteTxt(file, 0, BADADDR);         // create the assembler file
Message("All done, exiting...\n");
Exit(0);                              // exit to OS, error code 0 - success

}批量模式的命令行为:idaw-A -c -Smyanalysis.idc pe.exe这样就会得到idb文件、asm文件以及lu文件,其中lu文件为函数信息文件。http://grapeel.com/wp-content/uploads/2014/12/image3.png0表示是Library Function,1表示是正常文件。当然这是IDA根据sig目录下的指纹识别的,若是没有相关的库,那也就识别不出是否是Library Function了。

Mrsin 发表于 2014-12-23 10:21

{:301_1000:}楼主学习了 !沙发也拿走了!

yyz219 发表于 2014-12-23 10:32

懒惰的上帝 发表于 2014-12-23 10:57

太深奥小白看不懂{:1_919:}

菜鸟也想飞 发表于 2016-10-28 14:45

感谢分享!!!

菜鸟也想飞 发表于 2016-10-28 21:09

学习了,对我帮助很大,谢谢

乔延臣 发表于 2016-11-8 11:02

菜鸟也想飞 发表于 2016-10-28 21:09
学习了,对我帮助很大,谢谢

助人为乐:lol
页: [1]
查看完整版本: IDA 批量 导出 Function Window的信息