passbian

  C++博客 :: 首页 :: 联系 :: 聚合  :: 管理
  2 Posts :: 0 Stories :: 0 Comments :: 0 Trackbacks

常用链接

留言簿(1)

我参与的团队

搜索

  •  

最新评论

阅读排行榜

评论排行榜

2010年2月3日 #

 在MFC,ATL的源代码中充斥着__declspec(selectany)   的声明。selectany可以让我们在.h文件中初始化一个全局变量而不是只能放在.cpp中。比如有一个类,其中有一个静态变量,那么我们可以在.h 中通过类似"   __declspec(selectany)   type   class::variable   =   value;   "这样的代码来初始化这个全局变量。既是该.h被多次include,链接器也会为我们剔除多重定义的错误。这个有什么好处呢,我觉得对于 teamplate的编程会有很多便利。

posted @ 2010-02-03 13:56 卞冬华 阅读(261) | 评论 (0)编辑 收藏

2009年9月21日 #

在对基于COM的应用程序进行调试时,线程的套间类型,往往是我们必须知道的信息。如果应用程序是基于.Net的,那么问题很容易解决。我们可以加载SOS扩展库,然后调用!comstate命令,即可列出所有线程的套间类型。但是如果应用程序不是基于.Net的,SOS扩展库将无法使用。这时如何获取线程的套间类型呢?

 

要想获取套间类型信息,必须知道这个信息存在什么地方。答案是线程的TEB里。查看TEB结构,可以看到在其偏移0xf80处,有一个字段ReservedForOle。如下所示:

 

0:000> dt ntdll!_TEB

   ……

   +0xf7c ReservedForPerf  : Ptr32 Void

   +0xf80 ReservedForOle   : Ptr32 Void

   +0xf84 WaitingOnLoaderLock : Uint4B

   ……

 

当一个线程与一个套间关联上后,这个字段会保存一个指针,指向一个与套间相关的线程局部存储的数据结构。在这个数据结构的0xc偏移处,存放的正是套间的类型信息。

 

根据以上知识,我们可以如下获取套间类型:

 

0:000> r $teb

$teb=7ffdd000

0:000> dd 7ffdd000+f80 l1

7ffddf80  0016f178

0:000> dd 16f178+c l1

0016f184  0000008b

0:000> ? 8b & 80

Evaluate expression: 128 = 00000080

 

以上四步,第一步是得到线程TEB地址,第二步获取ReservedForOle  指针值,第三步获取套间类型字段。第四步把该字段值和0x80相与,如果不为0,则是STA,否则为MTA。上例结果为128,所以当前线程为STA。然后可以切换到其他线程,重复同样的操作,得到套间类型。

 

有一点值得注意的是,如果线程没有与套间关联,则第二步获取的ReservedForOle  指针值为空,也就无法获取套间类型。

 

上述步骤可以归结为一条命令,应用于当前进程的所有线程,并打印结果,如下:

 

~*e .if ( poi(@$teb+f80) == 0) { .echo Unknown } .else { .if ( poi(poi(@$teb+f80)+c) & 80 ) { .echo STA } .else { .echo MTA } }

posted @ 2009-09-21 10:23 卞冬华 阅读(118) | 评论 (0)编辑 收藏