源码网商城,靠谱的源码在线交易网站 我的订单 购物车 帮助

源码网商城

分享Visual Studio原生开发的10个调试技巧

  • 时间:2020-09-21 00:49 编辑: 来源: 阅读:
  • 扫一扫,手机访问
摘要:分享Visual Studio原生开发的10个调试技巧
最近碰巧读了Ivan Shcherbakov写的一篇文章,《[url=http://www.1sucai.cn/softjc/74166.html]11个强大的Visual Studio调试小技巧[/url]》。这篇文章只介绍了一些有关Visual Studio的基本调试技巧,但是还有其他一些同样有用的技巧。我整理了一些Visual Studio(至少在VS 2008下)原生开发的调试技巧。(如果你是工作在托管代码下,调试器会有更多的特性,在CodeProject中有介绍它们的文章),下面是我的整理的一些技巧: 异常中断 | Break on Exception Watch窗口中的伪变量 | Pseudo-variables in Watch Windows 符号越界后查看堆对象 | 查看数组的值 避免进入不必要的函数 从代码启动调试器 | Launch the debugger from code 在Output窗口打印 隔离内存泄漏 调试发行版 | Debug the Release Build 远程调试 [b]技巧1: 异常中断 [/b] 在处理被调用之前,异常发生时可以 启动调试器进行中断,可以让你在异常发生后立即调试程序。操作调用栈便于你去查找异常发生的根本原因。 Vistual Studio允许你去指定想要中断的异常类型或者特殊异常。选择菜单Debug>Exceptions弹出对话框,你可以指定原生的(或者托管的)异常,除了调试器自带的一些默认异常,你还可以添加自己的自定义异常。 [img]http://files.jb51.net/file_images/article/201308/2013081312173918.png[/img] 下面是一个std::exception 异常抛出时调试器中断的例子。 [img]http://files.jb51.net/file_images/article/201308/2013081312173919.png[/img] 更多阅读: [list] [*]1.  [url=http://msdn.microsoft.com/en-us/library/d14azbfh.aspx]异常抛出时如何中断[/url] [/*][*]2.  [url=http://msdn.microsoft.com/en-us/library/tw4t258c.aspx]如何添加新的异常[/url] [/*][/list][b]技巧2:Watch窗口中的伪变量[/b] Watch窗口或QuickWatch对话框提供一些特定的(调试器可识别的)变量,被称为伪变量。文档包含以下: $tid—–当前线程的线程ID $pid——进程ID $cmdline———-启动程序的命令行字符串 $user———-正在运行程序的账户信息 $registername—–显示寄存器registername 的内容 不管怎么样,关于最后一个错误的伪变量是非常有用的: $err——–显示最后一个错误的错误码 $err,hr—显示最后一个错误的错误信息 [img]http://files.jb51.net/file_images/article/201308/2013081312173920.png[/img] 更多阅读:[url=http://msdn.microsoft.com/en-us/library/ms164891.aspx]伪变量[/url] [b]技巧3:符合越界后查看堆对象 [/b]有时候,在调试符号越界后,你还想查看对象的值,这个时候,watch窗口中的变量是被禁用的,不能再查看(也不能更新),尽管对象仍然存在。你如果知道对象的地址,可以继续充分地观察它。你可以将地址转换为该对象类型的指针,放在watch窗中。 下面的例子中,当单步跳出do_foo()之后,_foo不能再被访问。但是,将它的地址转换为foo*后,就可以继续观察这个对象。 [img]http://files.jb51.net/file_images/article/201308/2013081312173921.png[/img] [b]技巧4:查看数组的值 [/b]如果你在操作一个很大的数组(我们假设至少有几百个元素吧,但是可能更少),在Watch窗口中展开数组,查找一些特定范围内的元素很麻烦,因为你要不停地滚动.如果数组是分配在堆上的话,你甚至不能在watch窗口中展开数组元素.对此,有一个解决办法。你可以使用(array+ <offset>),<count> 去查看从<offset>位置开始的特定范围的<count>元素(当然,这儿的数组是你的实际对象)。如果想查看整个数组,可以简单使用array,<count>. [img]http://files.jb51.net/file_images/article/201308/2013081312173922.png[/img] 如果你的数组是在堆上,你可以在watch窗口中将它展开,但是要查看某个特定范围的值,用法稍有不同:((T*) array + <offset>),<count>(注意这种用法对于堆上的多维数组也有效)。但是这种情况下,T是指数组元素的类型。 [img]http://files.jb51.net/file_images/article/201308/2013081312173923.png[/img] 如果你在用MFC,并使用其中的'array'容器,像 CArray, CDWordArray,CStringArray等等。你当然可以使用同样的过滤方法。除此之外,你必须查看array的m_pData成员,它是保存数据的真实缓存。 [img]http://files.jb51.net/file_images/article/201308/2013081312173924.png[/img] [b]技巧5:避免进入不必要的函数[/b] 很多时候,你在调试代码时可能会进入到你想跳过的函数,像构造函数,赋值操作或者其他的。其中最困扰我的是CString构造函数。下面是一个例子,当你准备单步执行take_a_string()函数时,首先进入到CString的构造函数。 void take_a_string(CString const &text){}void test_string(){ take_a_string(_T("sample"));}
[img]http://files.jb51.net/file_images/article/201308/2013081312173925.png[/img]

幸运的是可以告诉调试器去跳过哪些方法,类或者整个命名空间。实现它的方法也已经改变了,回到使用VS6的日子,通常是通过autoexp.dat文件来指定的。Vistual Studio 2002改成了使用注册表设置。想要跳过一些函数,你需要在注册表里添加一些值(详情如下):
[list=1]实际位置取决于你使用的Vistual Studio版本和操作系统平台(x86或x64,因为注册表只能在64位的Windows下浏览)值的名字是数字,代表规则的优先级;数字越大,优先级越高。值数据是一个正则表达式的REG_SZ值,用于指定怎样过滤和执行。[/list]为了避免进入任何CString方法,我添加了下面的规则:
[img]http://files.jb51.net/file_images/article/201308/2013081312173926.png[/img]

有了这个,即使你强制进入上例中的take_a_string(),调试器也会跳过CString的构造函数。
更多阅读:
[list]
[*] [url=http://blogs.msdn.com/b/andypennell/archive/2004/02/06/69004.aspx]使用Visual C++调试器怎样避免进入函数[/url] 
[/*][*][url=http://www.codeguru.com/cpp/v-s/debug/article.php/c1281/Tune-the-debugger-using-AutoExpdat.htm]使用AutoExp.dat调整调试器[/url] [/*][/list][b]技巧6:从代码启动调试器 Launch the debugger from code[/b]
你可能很少需要将调试器附加到程序中,但你不能在Attach窗口这样做(可能因为中断发生太快而没有捕获到),你也不能一开始就在调试器中启动程序。你可以在程序中产生中断给调试器一个机会通过调用内部的_degbugbreak()来附加。

[url=http://msdn.microsoft.com/en-us/library/f408b4et.aspx] 内部方法_debugbreak[/url] [*][url=http://www.codeproject.com/Articles/10022/DebugBreak-and-ASSERTs-that-work-always-anywhere]任何时候都离不开设置断点和断言[/url] [/*][*][url=http://www.cprogramming.com/tutorial/visual_studio_debugging_code_setup.html]Visual Studio 20005/2008的调试,第四部分:为调试器设置代码[/url] [/*][/list][b]技巧7:在output窗口打印 [/b]通过调用DebugOutputString可以在调试器的output窗口显示一段特定的文本。如果没有附加的调试器,该函数什么也不做。 [img]http://files.jb51.net/file_images/article/201308/2013081312173930.png[/img] 更多阅读: [list] [*][url=http://msdn.microsoft.com/en-us/library/windows/desktop/aa363362.aspx]函数OutputDebugString[/url] [/*][*][url=http://www.codeproject.com/Articles/23776/Mechanism-of-OutputDebugString]函数OutputDebugString的调用机制[/url] [/*][/list][b]技巧8:隔离内存泄漏 [/b] 内存泄漏是在原生开发中的一个很重要的问题,要检测内存泄漏是一个很严峻的挑战,尤其是在大型项目中。Vistual Studio可以提供检测内存泄漏的报告,还有其他的一些应用程序(免费的或商业的)也可以帮助你检测内存泄漏.有些情况下,在一些内存分配最终会导致泄漏时,可以使用调试器去中断。但是你必须找到可再现的分配编号(尽管没那么容易)。如果能做到这一点,执行程序时调试器才会中断。 我们来看下面的代码,分配了8个字节,却一直没释放分配的内存。Visual Studio提供了造成内存泄漏的对象的报告,多运行几次,会发现一直是同一个分配编号(341)。
[url=http://msdn.microsoft.com/en-us/library/fsk896zz.aspx]怎样调试发行版[/url] [b]技巧10:远程调试 [/b]另一个重要的调试就是远程调试,这是一个更大的话题,多次被提到,这里我只做一下简单的概括: 你需要在远程机器上安装远程调试监控 远程调试监控必须以管理员身份运行,并且用户必须属于管理员组 在你运行监控时,会开启一个新的服务,该服务的名字必须用Visual Studio的Attach to Progress窗口的Qualifier组合框的值。 [img]http://files.jb51.net/file_images/article/201308/2013081312173934.png[/img] [img]http://files.jb51.net/file_images/article/201308/2013081312173935.png[/img] [list=1] [*]远程和本地机器上的防火墙必须允许Visual Studio和远程调试监控之间能够通信 [/*][*]想要调试,PDB文件是关键;为了能够让VisualStudio自动加载它们,必须满足以下条件: [/*][/list] 1)本地的PDB文件必须可用(在远程机器的相同路径下放置一个对应的模块)。  2) 远程机器上的托管PDB文化必须可用。 远程调试监控下载: [list] [*] [url=http://www.microsoft.com/en-us/download/details.aspx?id=10647]Visual Studio 2008 Service Pack 1 Remote Debugger[/url] [/*][*][url=http://www.microsoft.com/en-us/download/details.aspx?id=475]Microsoft Visual Studio 2010 Remote Debugger[/url] [/*][/list] 更多阅读: [list] [*][url=http://msdn.microsoft.com/en-us/library/bt727f1t.aspx]设置远程调试[/url] [/*][*][url=http://msdn.microsoft.com/en-us/library/xf8k2h6a.aspx]怎么运行远程调试监控[/url] [/*][*][url=http://blogs.technet.com/b/monicaboris/archive/2004/02/16/74520.aspx]远程调试时加载调试符号:本地对托管[/url] [/*][*][url=http://www.wintellect.com/blogs/jrobbins/pdb-files-what-every-developer-must-know]PDB文件:开发者须知[/url] [/*][*][url=http://www.wintellect.com/blogs/jrobbins/visual-studio-remote-debugging-and-pdb-files]Visual Studio远程调试和PDB文件[/url] [/*][*][url=http://msdn.microsoft.com/en-us/library/x54fht41.aspx]怎样指定符号位置和加载行为[/url] [/*][/list][b]结束语 [/b] Ivan Shcherbakov那篇文章和我这篇文章提到的调试技巧,在大多数的调试问题中都是必不可少的。想要知道更多的关于调试技巧的知识,建议阅读文章中提供的额外阅读。 原文链接: [url=http://www.codeproject.com/Articles/469416/10-More-Visual-Studio-Debugging-Tips-for-Native-De]Marius Bancila[/url]   翻译: [url=http://blog.jobbole.com/]伯乐在线 [/url]- [url=http://blog.jobbole.com/author/jobbole/]伯乐在线读者[/url] 译文链接: [url=http://blog.jobbole.com/45249/]http://blog.jobbole.com/45249/[/url]
  • 全部评论(0)
联系客服
客服电话:
400-000-3129
微信版

扫一扫进微信版
返回顶部