最近,接到一个活,要写一个程序,用来批量分析一堆dll和对应的PDB,

其实工作很简单,就是根据一堆偏移,通过PDB文件,找到对应dll里面对应位置的明文符号,

简单的需求,实现起来,通常都很麻烦,

微软的demo中,有一个demo叫做dia,这个demo可以提供类似的功能,

我很高兴地编译了这个项目,但是失败了,加载符号失败,

通过单步调试,越过了若干个小问题(比如msdia120没注册这种),发现出现问题的位置位于 loadDataForExe 这个函数上,

这个函数原型是

virtual HRESULT STDMETHODCALLTYPE loadDataForExe( LPCOLESTR executable, LPCOLESTR searchPath, IUnknown *pCallback) = 0

可以看出,参数1是要解析的可执行文件,参数2是目标dll活着exe,参数3是一个接口,可以为NULL,或者按照微软demo中不用修改。

但是执行之后发现,它给我报错,说路径错误,无法找到目标pdb。

具体错误细节不说了,浪费时间。

说说怎么解决这个问题吧。

解决方式比较简单,

首先确定思路,这个函数不能用,说明它不能自己下载符号了,那么怎么办,

解决办法就是我们下载符号,然后让它直接加载就好了,另一个函数是可以用的 loadDataFromPdb。

确定了思路,那么就要铺平道路,我怎么怎么自己下载符号,

最简单的办法,其实就是使用Windows自己的下载功能,为了尽量少开发,所以可以使用WinDBG内部的功能来自动下载符号。

这样,符号文件有了,加载方式有了,就差如何把符号文件和可执行文件对应起来了,如何对应。

通过分析,我们发现,实际上符号文件落地之后是有个特殊的目录名字的,这个名字很像一个MD5,或者很像一个GUID,

通过分析程序,最终发现,这个目录名字实际上是可执行文件内部记录的一个GUID,再在最后补上一个字符 1。

具体一点,就是这样。

 PCHAR pBuffer = (PCHAR)h;
PCHAR pTemp = pBuffer + 0x3C;
pTemp = pBuffer + *(DWORD *)pTemp;
if (!(pTemp[] == 'P' && pTemp[] == 'E' && pTemp[] == '\0' && pTemp[] == '\0'))
{
return NULL;
}
PVOID *pv;
pv = (PVOID*)(pTemp + 0xA8); // 找到调试节
pTemp = pBuffer + (DWORD)*pv; // 计算调试节指定的内存地址
pv = (PVOID *)(pTemp + * ); // 找到偏移
pTemp = pBuffer + (DWORD)*pv; // 找到 UUID 基址
if (!(pTemp[] == 'R' && pTemp[] == 'S' && pTemp[] == 'D' && pTemp[] == 'S'))
{
return NULL;
}
GUID tGuid = { };
memcpy_s(&tGuid, sizeof(tGuid), pTemp + , sizeof(tGuid));

先根据可执行文件,找到PE头,从PE头里面找到调试节,

调试节里面找到GUID的偏移地址,

GUID偏移地址的前四个字符固定是RSDS,判断了之后,如果没有问题,

那么之后就是一个GUID的长度,

最后把这个GUID格式化出来变成字符串,最后再在后面补一个字符 '1' 即拼装成了当前文件对应的PDB目录名字,

然后通过这个目录名字可以拼接出一个完整的目录,很像Windows dbghelp.dll 拼接出来的目录,

然后去里面就能找到自己对应的pdb。

整个过程叙述结束。

最后总结一下。

解决pdb无法加载的方法:自己下载,独立加载。

方法:

1:使用WinDBG命令行下载可执行文件对应的PDB文件。

2:根据可执行文件计算PDB路径,寻找目标PDB。

3:找到目标PDB之后,loadDataFromPdb 直接加载PDB就好了。

Windows开发,关于通过写代码加载PDB的那些事的更多相关文章

  1. 支付宝小程序室内地图导航开发-支付宝小程序JS加载esmap地图

    如果是微信小程序开发,请参考微信小程序室内地图导航开发-微信小程序JS加载esmap地图文章 一.在支付宝小程序里显示室内三维地图 需要满足的两个条件 调用ESMap室内地图需要用到小程序web-vi ...

  2. WPF中,怎样将XAML代码加载为相应的对象?

    原文:WPF中,怎样将XAML代码加载为相应的对象? 在前面"在WPF中,如何得到任何Object对象的XAML代码?"一文中,我介绍了使用System.Windows.Marku ...

  3. 解决代码加载慢,以至于乱码—————VUE

    vue.js解决开始代码加载,以至于乱码 vue.js通过几行代码可以解决这个问题 css: [v-cloak] { display: none; } html: <div id="a ...

  4. 背水一战 Windows 10 (11) - 资源: CustomResource, ResourceDictionary, 加载外部的 ResourceDictionary 文件

    [源码下载] 背水一战 Windows 10 (11) - 资源: CustomResource, ResourceDictionary, 加载外部的 ResourceDictionary 文件 作者 ...

  5. 打开地图文件和shape文件代码加载Mxd文档

    代码加载Mxd文档 用代码添加Mxd文档,用到AxMapControl.LoadMxFile(sFilePath),我们只要将Mxd文档的路径传给这个方法即可 /// <summary>  ...

  6. 【转载】一行代码加载网络图片到ImageView——Android Picasso

    原文链接:一句代码加载网络图片到ImageView——Android Picasso  注意:此处使用下面代码需要先配置一下gradle,下载所需包. 具体操作如下图: compile 'com.sq ...

  7. AngularJS进阶(三十)AngularJS项目开发技巧之图片预加载

    AngularJS项目开发技巧之图片预加载 绪 项目(移动端采用Ionic 框架)开发完毕,测试阶段发现移动APP首页的广告图片(图片由服务器端返回相应url地址)很难加载,主要原因还是网速.如下图左 ...

  8. 模块 DLL C:\WINDOWS\system32\inetsrv\aspnetcore.dll 未能加载。返回的数据为错误信息。

    更新了win10的版本后,就启动原来的iis发布的程序 程序池就自动关闭.后来 启动网站 iis程序池自动关闭. 在为应用程序池“.NET v4.5”提供服务的工作进程“21908”中,协议“http ...

  9. Unity开发实战探讨-资源的加载释放最佳策略简要心得

    Unity开发实战探讨-资源的加载释放最佳策略简要心得 看过我另外一篇关于Unity资源释放随笔<Unity开发实战探讨-资源的加载释放最佳策略>如果觉得略微复杂,那么下面是一些比较简要的 ...

随机推荐

  1. python车牌精确定位

    #coding=utf-8 import cv2 # 使用的是HyperLPR已经训练好了的分类器 watch_cascade = cv2.CascadeClassifier('model/casca ...

  2. 2018-5-20-C#-BBcode-转-Markdown

    title author date CreateTime categories C# BBcode 转 Markdown lindexi 2018-05-20 14:58:57 +0800 2018- ...

  3. 2018-8-10-win10-UWP-序列化

    title author date CreateTime categories win10 UWP 序列化 lindexi 2018-08-10 19:16:50 +0800 2018-2-13 17 ...

  4. Cent OS 7 VNC 安装

    关闭防火墙 关闭selinux 挂载光盘到本地 #yum install tigervnc-server -y #cp /lib/systemd/system/vncserver@.service / ...

  5. weblogic启动脚本

    DATE=`date +%Y%m%d%H%M%S` user=`whoami` logDir=/app/logs/sguap_admin #启动日志存放路径sguap是例子系统简称# logDestd ...

  6. java 两个对象共使一个方法

  7. mongodb 自增序列实现

    MongoDB没有像SQL数据库外开箱即用自动递增功能.默认情况下,它采用了12字节的ObjectId为_id字段作为主键来唯一地标识文档.然而,可能存在的情况,我们可能希望_id字段有一些其它的自动 ...

  8. CONNECT_BY_ROOT

    1.select * from  EMP t  where t.deptno = 10;   EMPNO     ENAME     JOB     MGR     HIREDATE     SAL  ...

  9. vue项目中引入mui.poppicker.js文件时报错“Uncaught ReferenceError: mui is not defined”

    解决:在mui.js的源文件后最后加上 window.mui = mui;

  10. 报错——selinux配置文件修改错误导致无法启动虚拟机

    selinux配置文件修改错误导致无法启动虚拟机 问题 错误修改配置文件 [root@centos73 ~]# cat /etc/selinux/config # This file controls ...