windowsclient崩溃分析和调试
本文介绍windows上崩溃分析的一些手段,顺便提多进程调试、死锁等。
1.崩溃分析过程
1.1 确认错误码
不管是用windbg还是用vs。首先应该注意的是错误码,而90%以上的崩溃都是非法訪问。
在非法訪问时。能够看一下訪问的目标地址。
地址是0,或者离0非常近(0x00000008或0xfffffffc)。
一般和空指针相关。假设是一个貌似正常的地址,通常是对象已析构后訪问其数据,或者堆破坏。
1.2确认崩溃相应的C++操作
什么是确认崩溃相应的C++操作:
比方非法訪问,通常得有个mov指令才会触发内存訪问,然后导致崩溃。而mov指针相应于C++的哪一步呢?
比方a->b->c->foo();
在看到源代码时,会定位于这一行,可是,并不清楚是哪一步訪问失败。
所以这个时候要查看相应汇编代码。
大概会有好几个mov,简单的分析就知道是哪一步时訪问失败。
对编码的影响:
这就要求,不要在单个语句中写太复杂的东西比方
x ? b[i] : y > 0 ? c->member[8] : *ptr;
这种代码崩溃。要还原到错误的地方非常难。
虚函数调用:
通常
mov edx, dword ptr [ecx]
mov edx, dword ptr [edx+0x??
]
call edx
意味着虚函数调用。每一行都可能是崩溃位置(在call内崩溃时,vs会标注出下一条语句的位置)。
在第一行崩溃意味着拿到一个非法指针,可能是空,也能够指向非法地址。
在第二行崩溃意味着对象已经析构,ecx指向能够訪问,可是值不正确。所以拿到的虚函数表不正确。
在最后一行崩溃一般另一个崩溃栈,可是看不到栈帧,在vs中相应的栈桢显示一个地址。没其他内容。
也一般意味着对象析构。
对象及析构函数:
析构函数是常常发生崩溃的地方,假设没实用户提供的析构函数,会定位到几行汇编。所以没事,就写个
析构函数吧,至少能定位到是析构函数。
在析构函数外部还会有一大堆汇编代码,里面是对象成员析构的代码。崩溃在里面的时候,难以确认
是哪个对象析构。
假设用指针,在析构函数中主动调用Release或delete,这样能够显示调用,不用去猜是谁在析构,当然
用指针或值对象。在逻辑上各有其优点。在此不表。
假设崩溃位置是call或jmp到某个A::~A()的位置。能够推測到析构的对象的类型是A。
对象析构顺序是从后往前,从子类到基类,依据这点,结合崩溃位置。能够推測谁析构。
利用对象布局,比方成员在对象中的偏移,可能有得于推測谁析构出问题。
能够人为地在对象布局中引入一些填充的字节,使得能看到this对象(线上崩溃没有堆上的数据,由于
截取fulldump并上报有操作上的难度。所以this指向堆上时可能看不到,而在栈上则有可能),有利于分析。
还原上下文:
线上拿到的dump的信息少,不能调试。所以能够依据崩溃所在模块。崩溃在模块中的偏移量,在本地
调试相应的bin,找到相应的模块。偏移量。打上断点,能够在本地还原出崩溃时的运行环境。
当然,
在本地运行到相应位置时不一定崩溃,可是,有了很多其它上下文信息。能够比較easy确定相应的C++操作。
使用IDA:
能够使用IDA让汇编代码更好看,较easy分析流程。
关闭alsr。指定建议模块载入地址:
这样可能使得更easy分析。
可是会使得安全性减少,能够用于小流量版本号。
ln指令:
windbg中ln指令能够依据地址。还原出相应的信息,比方该地址是在某个类的某个方法中。
有时可能会
还原出几个信息:A::foo() + 0x?
?, B::foo1() + 0x??。这就须要自己依据上下文推断了。
代码优化:
代码优化使得分析更难,能够尝试改变一些编译选项,减少优化级别,保留栈桢,关闭应用程序全局优化,
使得在release下的分析easy些。
所见并不是真实:
windbg和vs看到的栈帧可能是假的:可能在中间某一些可能已经乱了,可能栈桢省略使得vs分析的结果不正确。
(通常是vs分析得不正确。另外也有windbg杯具的时候)
对于在中间已经乱掉的栈。能够依据返回地址。栈參数,栈桢省略数据等,又一次还原出栈。只是在90%的情况
下,即使还原出来,也不知道下一步怎么办。
对象还原:
线上崩溃没有堆,能够将感兴趣的对象拷贝复制到栈上(自己得控制深拷贝)。然后崩溃上报中就能够看到
对象的状态了。
(注意代码优化可能使得拷贝无效)
1.3C++上的逻辑
在确定崩溃和C++操作的关系后,就是自己逻辑上的问题了,基本上能遇到的问题都是对象生命周期管理
不当,进而造成非法訪问。
指针的判空能规避一处的非法訪问,可是能够把错误进一步扩散。指针判空。且用且珍惜。
在设计或编码时,应当考虑代码的可调试性。比方chromium中的线程池中,加入任务时,会生成当前调用
信息。和task绑定,以使于定位错误。
1.4堆破坏
基本无解,崩溃现场和引入错误的点相差太远。
仅仅能尽人事,听天命了。
比方,开一下页堆。存在一定概率使得崩溃出现,看人品。
比方。换一个CRT堆。或者自己写个,增强错误检測。
比方。CRT本身。尤其是调试的堆,堆上有些填充信息。使得在看到的时候或多或少叹口气:大概认识这些
填充信息,想要很多其它的信息,难啊。。
。
比方。能够自己写个调试器,自己插入页堆,或者使用系统的页堆。使得检測自己主动化,然后通过大规模数据
使之重现。
2.其他
多进程调试:
能够通过在
HKEY_LOCAL_MACHINE\Software\Microsoft\Windows NT\CurrentVersion\Image File Execution Options
建立关心的进程名的项。填上debugger键值,值为调试器路径,使得进程创建时就attach。(gflags也是
改这里)。
可是问题是,有的模块是按需载入的,在这个时候还不能在相应模块中下断点。
另外能够自己在关心的位置加上MessageBox或ATLASSERT之类的代码,等弹出对话框时再attach到相应进程。
activex:
attach方法同理。
可是,IE的多进程模型会使得attach不方便。
在IE9及以上,其进程模型是一个主进程,控制多个tab进程,按一定规则创建tab进程,将任务分派到
tab上。同一个网页打开两次,可能分配到不同的进程上,也可能是同样的进程。在同一个进程中,同一
个activex可能有多个实例,并且每一个实例相应的主线程还不一定是同一个线程。
通常会控制仅仅开一个tab,使得调试更加easy。另外能够开多tab。然后关闭,然后再开,来測试同一个进程
有多外activex实例的情况。更进一步,能够自己调用IWebBrowser2,来模拟很多其它的情况。
np插件:
chrome中这个简单些。一个插件一个进程,多个实例。共享主线程。
还有些开源工具将activex适配为np插件,使得能够在chrome中调用ax。调试。
多机调试:
前面说过,windbg,vs都支持。
死锁:
死锁现场不会是线上问题(能够通过一定手段,使得在线上发生死锁时报告。可是基本上没用过,相应的
手段在线下有玩过)。线下问题通常会有现场,或者能拿到full dump。
一般使用windbg来看,用~*kb或者
这系列的命令看看线程都在干什么。而重点关注的则是WaitForSingleObjectEx之类的调用。
通过分析调用
相应的參数。进一步能还原出,拿到 分发器 对象后不归还的线程是谁。
或者也能够!runaway找到占用CPU
高的线程,然后看看该线程在干什么。线程循环等待,则死锁了。线程一直在那里跑,可能是死循环了。
线下的死锁检測,一般能够向主线程发一个消息来实现。
warning:有可能某个线程拿到分发器对象,可是该线程已经挂掉了。
windowsclient崩溃分析和调试的更多相关文章
- iOS 崩溃分析
崩溃统计分析,在APP中是非常常见一种优化APP,发现APP的BUG的方式. 1.异常处理 可通过try catch 方式处理,如果发生异常,会走catch ,最终走fianlly.对一些我们不想他崩 ...
- TCPflow:在Linux中分析和调试网络流量的利器(转)
TCPflow是一款功能强大的.基于命令行的免费开源工具,用于在Unix之类的系统(如Linux)上分析网络流量.它可捕获通过TCP连接接收或传输的数据,并存储在文件中供以后分析,采用的格式便于协议分 ...
- core dump文件分析和调试
core介绍 当程序运行的过程中异常终止或崩溃,操作系统会将程序当时的内存状态记录下来,保存在一个文件中,这种行为就叫做Core Dump(中文有的翻译成"核心转储").我们可以认 ...
- iOS崩溃分析
崩溃的分析 最近修复了一些iOS项目的崩溃,想分析总结一下这些崩溃的原因,以及预防.崩溃的原因一般有下面几种: 内存访问错误(这个出现的比较多,原因多种多样) 非法指令的执行(超出权限范围内的指令) ...
- Android内存泄漏分析及调试
尊重原创作者,转载请注明出处: http://blog.csdn.net/gemmem/article/details/13017999 此文承接我的另一篇文章:Android进程的内存管理分析 首先 ...
- 4、QT分析之调试跟踪系统
原文地址:http://blog.163.com/net_worm/blog/static/127702419201002004518944/ 在我们前面的分析中,经常看到qWarning()和qDe ...
- jvm间歇性崩溃分析
http://www.cnblogs.com/LBSer/p/4417148.html 1 问题描述 某服务有两台机器,每隔几天会报警load高,一开始看监控发现gc时间抖动很大,以为是发生了full ...
- Windows内核分析——内核调试机制的实现(NtCreateDebugObject、DbgkpPostFakeProcessCreateMessages、DbgkpPostFakeThreadMessages分析)
本文主要分析内核中与调试相关的几个内核函数. 首先是NtCreateDebugObject函数,用于创建一个内核调试对象,分析程序可知,其实只是一层对ObCreateObject的封装,并初始化一些结 ...
- (转)Android内存泄漏分析及调试
http://blog.csdn.net/gemmem/article/details/13017999 此文承接我的另一篇文章:Android进程的内存管理分析 首先了解一下dalvik的Ga ...
随机推荐
- 菜鸟nginx源代码剖析数据结构篇(九) 内存池ngx_pool_t
菜鸟nginx源代码剖析数据结构篇(九) 内存池ngx_pool_t Author:Echo Chen(陈斌) Email:chenb19870707@gmail.com Blog:Blog.csdn ...
- android 给url添加cookie
前些天因为项目需要写了一个通过网络连接去服务端拿数据的方法,但是需要让程序添加上cookie,因为之前对cookie 没有怎么研究过(包括做web 那会也没有用过或者说很少用),所以 一时用起来不太会 ...
- caioj1497&&bzoj3125: CITY
震惊!bzoj居然又被苏大佬D飞了... 这题煞笔模板题好吧. 然而bzojAC caiojWA%40??? 好强啊 今天早上发现是m打成n了囧 #include<cstdio> #inc ...
- Fine-tuning CaffeNet for Style Recognition on “Flickr Style” Data 数据下载遇到的问题
(下载的时候没有提示 不知道是正在下 还是出现错误 卡着了)..一直没有反应 下载前要以管理员身份运行 sudo su 再 python examples/finetune_flickr_style/ ...
- ffmpeg x264编译与使用介绍
问题1:我用的是最新版本的ffmpeg和x264,刚刚编译出来,编译没有问题,但是在linux 环境使用ffmpeg的库时发现报错error C3861: 'UINT64_C': identifier ...
- HD-ACM算法专攻系列(23)——Crixalis's Equipment
题目描述: AC源码:此次考察贪心算法,解题思路:贪心的原则是使留下的空间最大,优先选择Bi与Ai差值最大的,至于为什么?这里用只有2个设备为例,(A1,B1)与(A2,B2),假设先搬运A1,搬运的 ...
- mybatis通用的crud的接口
http://git.oschina.net/jrl/mybatis-mapper https://www.oschina.net/p/mybatis-plus
- 数组常用API
内容待添加... //根据分数排名字 //方法1 var students = ['小明','小红','小花'] var scores = {小明:,小红:,小花:} //1 添加分数到student ...
- s2sh的MVC执行流程和执行原理
=======================执行流程 1. 从页面开始,提交表单或者点击链接会触发一个action 2. action交给struts2处理,读取src目录struts.xml文件, ...
- 使用 Object.create实现js 继承
二.Object.create实现继承 本文将来学习第七种继承方式Object.create()方法来实现继承,关于此方法的详细描述,请戳这里.下面来通过几个实例来学习该方法的使用: var Pare ...