FCBarcelone 2020-10-08 19:05 采纳率: 0%
浏览 31

分析PE文件头导入表,IID和Name得到的地址不对,name=0,跪求大佬指点一下

void ImPortD() {
DWORD dwDataStartRVA;//输入表的RVA
PIMAGE_IMPORT_DESCRIPTOR pImportDesc;//指向输入表的指针
//IMAGE_DIRECTORY_ENTRY_IMPORT=1
dwDataStartRVA = ycOptionalHeader->DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress;
if (!dwDataStartRVA)

return;
//RVA转VA,注意VA是打开的PE文件在本进程空间中映射的VA
pImportDesc = (PIMAGE_IMPORT_DESCRIPTOR)ImageRvaToVa(ycNTHeader, ImageBase, dwDataStartRVA, NULL);
//分析IID数组成员,直到成员为0

while (pImportDesc->FirstThunk){ // while(pImportDesc-> OriginalFirstThunk
    //当前IID数组成员的取值:
    pImportDesc->OriginalFirstThunk;  //INT RVA
    pImportDesc->TimeDateStamp;
    pImportDesc->ForwarderChain;
    pImportDesc->Name;  //Name RVA
    pImportDesc->FirstThunk;    //IAT RVA
    pImportDesc++;  //指针++,下1个数组成员
}//end while
//分析某个.dll对应的INT或IAT数组成员    
char    cOrd[30], cMemAddr[30], * FuncName; //函数序号,地址,函数名
DWORD dwThunk; //OriginalFirstThunk或FirstThunk值 
DWORD* pdwRVA = NULL; //OriginalFirstThunk或FirstThunk RVA指针   
DWORD* pdwThunk = NULL; //IMAGE_THUNK_DATA的指针 
PIMAGE_IMPORT_BY_NAME pByName = NULL; // BY_NAME的指针   
//获取第一个IID
pImportDesc = (PIMAGE_IMPORT_DESCRIPTOR)ImageRvaToVa(ycNTHeader, ImageBase, dwDataStartRVA, NULL);
while (pImportDesc->FirstThunk) {   //pImportDesc->OriginalFirstThun
    //取OriginalFirstThunk或FirstThunk  32位取值
    dwThunk = pImportDesc->OriginalFirstThunk;
    //取OriginalFirstThunk或FirstThunk  RVA值        
    pdwRVA = (DWORD*)dwThunk;
    //IMAGE_THUNK_DATA的VA
    pdwThunk = (DWORD*)ImageRvaToVa(ycNTHeader, ImageBase, dwThunk, NULL);  

    if (!pdwThunk)  
        return;

    while (*pdwThunk)//指向INT或IAT数组
    {
        if (HIWORD(*pdwThunk) == 0x8000) {//判断ThunkValue最高位的取值0?1
            //printf("序号");
        }//是序号
        else {  //是函数名
                //循环处理下一个函数
            ++pdwRVA;       //OriginalFirstThunk或FirstThunk  RVA值++
            ++pdwThunk; //IMAGE_THUNK_DATA的指针
        }//end while
        }
        pImportDesc++;//循环,下1个.dll的导入函数
        }//end while    

printf("IID=%X\n", (int)pImportDesc-(int)ImageBase);
printf("name=%X\n", (char*)ImageRvaToVa(ycNTHeader, ImageBase, pImportDesc->Name, NULL));
  • 写回答

1条回答 默认 最新

  • 你知我知皆知 2024-07-25 09:10
    关注

    以下回答参考 皆我百晓生券券喵儿 等免费微信小程序相关内容作答,并由本人整理回复。

    首先,你需要确保你的C语言程序已经正确地编译并链接。如果你使用的是GCC,你可以运行以下命令来编译你的程序:

    gcc -o my_program my_program.c
    

    然后,你可以在命令行中运行它:

    ./my_program
    

    这将输出两个字符串:一个显示了导入表中的IID,另一个显示了导入表中的名称。

    现在让我们一步一步解释你的代码是如何工作的:

    void ImPortD()
    {
        DWORD dwDataStartRVA;//输入表的RVA
    
        PIMAGE_IMPORT_DESCRIPTOR pImportDesc;//指向输入表的指针
    
        //IMAGE_DIRECTORY_ENTRY_IMPORT=1
        dwDataStartRVA = ycOptionalHeader->DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress;
    
        if (!dwDataStartRVA)
            return;
    
        //RVA转VA,注意VA是打开的PE文件在本进程空间中映射的VA
        pImportDesc = (PIMAGE_IMPORT_DESCRIPTOR)ImageRvaToVa(ycNTHeader, ImageBase, dwDataStartRVA, NULL);
    
        //分析IID数组成员,直到成员为0
        while (pImportDesc->FirstThunk){
            //当前IID数组成员的取值:
            pImportDesc->OriginalFirstThunk;  //INT RVA
            pImportDesc->TimeDateStamp;
            pImportDesc->ForwarderChain;
            pImportDesc->Name;  //Name RVA
            pImportDesc->FirstThunk;    //IAT RVA
            pImportDesc++;  //指针++,下1个数组成员
        }
    
        //分析某个.dll对应的INT或IAT数组成员
        char    cOrd[30], cMemAddr[30], * FuncName; //函数序号,地址,函数名
        DWORD dwThunk; //OriginalFirstThunk或FirstThunk值
        DWORD* pdwRVA = NULL; //OriginalFirstThunk或FirstThunk RVA指针
        DWORD* pdwThunk = NULL; //IMAGE_THUNK_DATA的指针
        PIMAGE_IMPORT_BY_NAME pByName = NULL; // BY_NAME的指针
    
        //获取第一个IID
        pImportDesc = (PIMAGE_IMPORT_DESCRIPTOR)ImageRvaToVa(ycNTHeader, ImageBase, dwDataStartRVA, NULL);
        while (pImportDesc->FirstThunk) {
            //取OriginalFirstThunk或FirstThunk  32位取值
            dwThunk = pImportDesc->OriginalFirstThunk;
            //取OriginalFirstThunk或FirstThunk  RVA值        
            pdwRVA = (DWORD*)dwThunk;
            //IMAGE_THUNK_DATA的VA
            pdwThunk = (DWORD*)ImageRvaToVa(ycNTHeader, ImageBase, dwThunk, NULL);  
    
            if (!pdwThunk)
                return;
    
            while (*pdwThunk)//指向INT或IAT数组
            {
                if (HIWORD(*pdwThunk) == 0x8000) {//判断ThunkValue最高位的取值0?1
                    //printf("序号");
                } else {  //是函数名
                        //循环处理下一个函数
                    ++pdwRVA;       //OriginalFirstThunk或FirstThunk  RVA值++
                    ++pdwThunk; //IMAGE_THUNK_DATA的指针
                }//end while
            }
            pImportDesc++;//循环,下1个.dll的导入函数
        }//end while
    
        printf("IID=%X\n", (int)pImportDesc-(int)ImageBase);
        printf("name=%X\n", (char*)ImageRvaToVa(ycNTHeader, ImageBase, pImportDesc->Name, NULL));
    }
    

    这段代码首先计算了输入表的RVA,并初始化了一个PIMAGE_IMPORT_DESCRIPTOR结构体变量pImportDesc。接下来,它遍历了这个结构体,直到找到一个名为“0”的成员(即第0个成员)。对于每个成员,它会检查它的OriginalFirstThunkFirstThunk成员是否等于0,如果是,则表示这是一个函数的入口点;如果不是,则表示这是函数的名称。对于每一个函数,它都会打印出函数的入口点和名称。最后,它会打印出导入表中的IID和名称。

    评论

报告相同问题?

悬赏问题

  • ¥15 系统 24h2 专业工作站版,浏览文件夹的图库,视频,图片之类的怎样删除?
  • ¥15 怎么把512还原为520格式
  • ¥15 MATLAB的动态模态分解出现错误,以CFX非定常模拟结果为快照
  • ¥15 求高通平台Softsim调试经验
  • ¥15 canal如何实现将mysql多张表(月表)采集入库到目标表中(一张表)?
  • ¥15 wpf ScrollViewer实现冻结左侧宽度w范围内的视图
  • ¥15 栅极驱动低侧烧毁MOSFET
  • ¥30 写segy数据时出错3
  • ¥100 linux下qt运行QCefView demo报错
  • ¥50 F1C100S下的红外解码IR_RX驱动问题