利用windbg调试class type,value type以及MethodTable等强化C#的基本概念

本文通过windbg调试一个简单的程序,来清除说明.Net framework中class type,value type的内存分配方式的不同,以及object内部的重要组成MethodTable的作用

用于说明问题的source code如下:

 1  using  System;
 2  using  System.Collections.Generic;
 3  using  System.Linq;
 4  using  System.Text;
 5  using  System.Collections;
 6 
 7  namespace  VSDebug
 8  {
 9       class  StringHolder
10      {
11           public   string  StringData;
12           public  StringHolder( string  stringData)
13          {
14              StringData  =  stringData;
15          }
16      } 
17 
18       class   TestClass
19      {
20           public  ArrayList Holders;
21          [STAThread]
22           static   void  Main( string [] args)
23          {
24              TestClass testClass  =   new  TestClass();
25              TestClass testClass1  =   new  TestClass();
26              testClass.Holders  =   new  ArrayList();
27               for  ( int  i  =   0 ; i  <   10 ++ i)
28              {
29                  testClass.Holders.Add( new  StringHolder( " Hello " ));
30              }
31              Console.ReadLine();
32          } 
33 
34      }
35  }
36 

 

设置project 的debug属性为enabled unmanaged code debugging,在31行设置breakpoint,然后press F5开始调试,并打开intermediate window开始windbg sos 调试

.load sos

extension C:\Windows\Microsoft.NET\Framework\v2.0.50727\sos.dll loaded

!dumpheap -stat

PDB symbol for mscorwks.dll not loaded

total 2086 objects

Statistics:

MT Count TotalSize Class Name

79100f58 1 12 System.Security.Permissions.SecurityPermission

790fdc5c 1 20 System.Text.StringBuilder

79104368 1 24 System.Collections.ArrayList

790fcc48 1 24 System.Reflection.Assembly

0023304c 2 24 VSDebug.TestClass

790feba4 1 28 System.SharedStatics

790fd0f0 3 36 System.Object

790ff734 2 40 System.RuntimeType

79100e38 1 44 System.Security.FrameSecurityDescriptor

790ff120 1 44 System.AppDomainSetup

7912dd40 1 64 System.Char[]

79100a18 2 72 System.Security.PermissionSet

790fe17c 1 72 System.ExecutionEngineException

790fe0e0 1 72 System.StackOverflowException

790fe044 1 72 System.OutOfMemoryException

790fed00 1 100 System.AppDomain

003c7508 7 100 Free

002330cc 10 120 VSDebug.StringHolder

790fe284 2 144 System.Threading.ThreadAbortException

7912d8f8 9 8992 System.Object[]

790fd8c4 2037 129576 System.String

Total 2086 objects

下面对each column作简要说明:

MT-〉MethodTable. 首先说明MethodTable的作用。我们知道每种type可以有多个instance。在C++中,每个instance,其每个field可以享有独立的space,而对于type的method提供一个公共的method入口地址。也就是说不管多少个相同类型的instance,其都指向了同一个同一的函数入口地址。在这个函数入口地址描述表中记录了各个函数的入口地址。而MethodTable就有点类似的作用。自不过所有Assembly都是自描述的,因此我们可以从MethodTable中,可以知道相应的instance。因此通过相应的debug命令!dumpheap -mt MTAddress可以知道在MethodTable中相关联的所有instance了

Count ->某个特定MethodTable地址下相关联的objects的数目

TotalSize->所占空间

Class Name->object descriptive information

请看下面:

!dumpheap -mt 0023304c

Address MT Size

0286168c 0023304c 12

02861698 0023304c 12

total 2 objects

Statistics:

MT Count TotalSize Class Name

0023304c 2 24 VSDebug.TestClass

Total 2 objects

可以看出,在该MethodTable中关联的有2个objects,一个object address是:0286168c,而另外一个object address 是:02861698

在.net中,我们知道,对于class type的object,其object ref是占用stack上的空间,而 object ref则指向了GC heap上的空间。刚才我们已经知道在heap上有2个VsDebug.TestClass的object,并且其Heap Address也已给出。

下面看看在stack是否有相应的VsDebug.TestClass ref指向其object.

!dso

OS Thread Id: 0xed8 (3800)

ESP/REG Object Name

ecx 02861788 System.Object[]

0014eef0 028616a4 System.Collections.ArrayList

0014eef8 028617d8 VSDebug.StringHolder

0014f064 028616a4 System.Collections.ArrayList

0014f068 028617d8 VSDebug.StringHolder

0014f06c 0286168c VSDebug.TestClass

0014f074 02861788 System.Object[] (System.Object[])

0014f29c 02861698 VSDebug.TestClass

0014f2a4 02861660 System.Object[] (System.String[])

0014f2bc 02861660 System.Object[] (System.String[])

0014f394 02861660 System.Object[] (System.String[])

0014f53c 02861660 System.Object[] (System.String[])

0014f564 02861660 System.Object[] (System.String[])

果然,可以看到在stack上看到2个指向heap上的VsDebug.TestClass 类型的object :) 

转载于:https://www.cnblogs.com/Winston/archive/2008/11/25/1340748.html

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值