zoukankan      html  css  js  c++  java
  • .NET 调试入门(二) dump 出程序数据

    前言

             有时候我们需要看程序中运行情况怎么,如:某对象字段的具体值是多少等问题,我们就可以用调试工具找到答案。我们还是沿用前面的程序。原代码在文章低部。

    dump栈上的值

    在线程4中输入!ClrStack -a结果说该线程不是托管线程,于是我们用~0s 转到主线程,在输入该命令,他的调用栈相关信息就已经出来了,如下面所示:

    image

    在Main方法中有2个变量

    此时我们用得!do得到它的值,结果显示说他不是一个类字段,那说明他是一个值类型,我们用dd命令发现在栈上果然有3个值分别是0x64,转成10进制那就是100。

    image 

    dump堆上的对象

    如果值类型包含在类中那么他会保存在堆上。要看堆中有那些对象,可以用!dumpheap 命令。然而堆上的对象非常多,我们一般可以在!dumpheap增加一个-type  来查找堆中的指定类型。如下图所示:

    image

    通过该命令我们就得到了,ObjTypes的对象的地址:00000000027eab68

    当然!dumpheap 还有其它参考具体如下:

    !dumpheap:dump堆中的所有对象
    !dumpheap -type <类型,包括命名空间> :dump堆中的指定对象
    !dumpheap -mt <方法表地址> :dump堆中的指定对象
    !dumpheap -min <最小内存大小> :dump堆中大于指定内存的对象
    !dumpheap -startAtLowerBound <开始地址> 显示该地址块中有那些对象。
    !dumpheap -thinlock:查看堆上所有瘦锁对象
    !dumpheap -stat 统计堆中各对象的个数,类型于sql中的group by

    然后在调用!do命令,就会得到该实体的具体数据有那些,具体效果如下图所示:

    image

    我们可以看到改对象有3个字段,一个是Coordinate的值类型,注:VT=1说明是值类型。另外有二个数组类型分别是int和object数组类型。

    dump值类型数据

    查看值类型数据一般用!dumpvc <方法表地址> <值类型地址>; 导出值类型数据,结果如下:

    image

    我们发现ObjTypes中的Coordinate有定义了3个int类型分别是xCord、yCord、zCord 他们各自的值为100

    dump数组中的数据

    dump 数组中的数据,我们用 !da -details <数组地址>,结果如下:

    image

    同理,dump 字符串数组也是一样:

    image

    !da 也有一些相关参数可以设置,具体如下:

    !da(!DumpArray)[-start <数组那个索引开始>] [-length<显示数组多少个元素>] [-details] [-nofields] 数据地址
      [-details] 显示数组的详细信息,包括具体值。
      [-nofields] 只显示内容不会显字符串类型中的各个域

    示例代码

    代码如下:

    using System;
    using System.Text;
    
    namespace Advanced.NET.Debugging.Chapter3
    {
        public class ObjTypes
        {
            public struct Coordinate
            {
                public int xCord;
                public int yCord;
                public int zCord;
    
                public Coordinate(int x, int y, int z)
                {
                    xCord = x;
                    yCord = y;
                    zCord = z;
                }
            }
    
            private Coordinate coordinate;
    
            int[] intArray = new int[] { 1, 2, 3, 4, 5 };
            string[] strArray = new string[] {"Welcome", 
                                              "to",
                                              "Advanced",
                                              ".NET",
                                              "Debugging"};
    
            static void Main(string[] args)
            {
                Coordinate point= new Coordinate(100, 100, 100);
                Console.WriteLine("Press any key to continue (AddCoordinate)");
                Console.ReadKey();
                ObjTypes ob = new ObjTypes();
                ob.AddCoordinate(point);
    
                Console.WriteLine("Press any key to continue (Arrays)");
                Console.ReadKey();
                ob.PrintArrays();
                
                Console.WriteLine("Press any key to continue (Generics)");
                Console.ReadKey();
                Comparer c = new Comparer();
                Console.WriteLine("Greater {0}", c.GreaterThan(5, 10));
    
                Console.WriteLine("Press any key to continue (Exception)");
                Console.ReadKey();
                ob.ThrowException(null);
            }
    
            public void AddCoordinate(Coordinate coord)
            {
                coordinate.xCord += coord.xCord;
                coordinate.yCord += coord.yCord;
                coordinate.zCord += coord.zCord;
    
                Console.WriteLine("x:{0}, y:{1}, z:{2}",
                                  coordinate.xCord,
                                  coordinate.yCord,
                                  coordinate.xCord);
            }
    
            public void PrintArrays()
            {
                foreach (int i in intArray)
                {
                    Console.WriteLine("Int: {0}", i);
                }
                foreach (string s in strArray)
                {
                    Console.WriteLine("Str: {0}", s);
                }
            }
    
            public void ThrowException(ObjTypes obj)
            {
                if (obj == null)
                {
                    throw new System.ArgumentException("Obj cannot be null");
                }
            }
        }
    
        public class Comparer where T: IComparable
        {
            public T GreaterThan(T d, T d2)
            {
                int ret = d.CompareTo(d2);
                if (ret > 0)
                    return d;
                else
                    return d2;
            }
    
            public T LessThan(T d, T d2)
            {
                int ret = d.CompareTo(d2);
                if (ret < 0)
                    return d;
                else
                    return d2;
            }
        }
    }
    作者: 吉桂昕
    出处: http://www.cnblogs.com/jiguixin
    我的新浪微博: http://weibo.com/jiguixin
    本文版权归【吉桂昕】和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。如果觉得还有帮助的话,可以点一下右下角的【推荐】,希望能够持续的为大家带来好的技术文章!想跟我一起进步么?那就【关注】我吧。
  • 相关阅读:
    汉语-谚语:条条大路通罗马
    汉语-词语:缱绻
    几何-对称图形:中心对称图形
    java解析获取Excel中的数据--同时兼容2003及2007
    如何使gcc输出搜索到的头文件路径?
    如何使tmux可以像vi一样操作(如快速跳转到某一行)?
    如何使tmux能够使用鼠标上下滚动?
    ID3v2: 为aac格式的音频文件添加ID3v2 Header
    FFmpeg: 利用FFmpeg提取音频文件中的metadata
    C语言:变长结构体
  • 原文地址:https://www.cnblogs.com/jiguixin/p/3147683.html
Copyright © 2011-2022 走看看