ATL转载做笔记

来源:互联网 发布:知美术馆哪个投资的 编辑:程序博客网 时间:2024/05/16 12:49
转载地址:http://www.cnblogs.com/tekkaman/
ATL线程模型解析

ATL的三种线程模型

1、_ATL_SINGLE_THREADED

2、_ATL_APARTMENT_THREADED

3、_ATL_FREE_THREADED

线程模型的支持

  线程模型的支持,以类为单位,每个类提供2种功能,一个是互斥的加减,另一个是CS。

1、CComSingleThreadModel

2、CComMultiThreadModel

3、CComMultiThreadModelNoCS

深入解析线程模型

默认线程模型

 默认线程定义代码在atldef.h头文件中,除此之的外,以上代码在atlbase.h中,另外,CS相关部分前文已经解析。

ATL之如何聚合一个组件

如何聚合一个组件

1、Add an IUnknown pointer to your class object and initialize it to NULL in the constructor.

2、Override FinalConstruct to create the aggregate. 

3、Use the IUnknown pointer you defined as the parameter to the COM_INTERFACE_ENTRY_AGGREGATE macro.

4、Override FinalRelease to release the IUnknown pointer.

Warning :If you wanna use interface in FinalConstruct,please use DECLARE_PROTECT_FINAL_CONSTRUCT macro to protect your object from deleting.

Examples:

 
ATL之眼花缭乱的CComObject

眼花缭乱的CComObject

1、CComObject :为独立激活的COM组件提供服务,功能包涵:

  (1)锁服务器。

  (2)正常的引用计数。

  (3)正常的QueryInterface。

2、CComAggObject :为被聚合激活的COM组件提供服务,功能包涵:

  (1)锁服务器。

  (2)包容接口实际类。

  (3)正常的引用计数。

  (4)将调用转发给内部包容对象的QueryInterface。(除了IUnknown请求外)

3、CComContainedObject :为被聚合海派的COM组件提供服务,功能包涵:

  (1)将调用转发给外部组件的引用计数。

  (2)将调用转发给外部组件的QueryInterface。

4、CComPolyObject :为既会被聚合激活也会被独立激活的COM组件提供服务,功能包涵:

  (1)在有外部指针传入的时候,表现行为同CComAggObject。

  (2)在没外部指针传入的时候,表现行为同CComObject。

5、CComObjectCached :当组件引用计数为1时,不影响服务器的生命周期,功能包涵:

  (1)修改的引用计数,在引用大于1时,才锁住服务器。

  (2)正常的QueryInterface。

6、CComObjectNoLock :不锁服务器的组件,功能包涵:

  (1)正常的引用计数。(不锁服务器)

  (2)正常的QueryInterface。

7、CComObjectGlobal :为全局变量提供服务,功能包涵:

  (1)在构造函数中完成通常在CComCreator::CreateInstance中的组件调用。

  (2)引用计数变形为锁服务器。

  (3)正常的QueryInterface。

8、CComObjectStack :为局部COM组件提供服务,功能包涵:

  (1)禁止引用计数。

  (2)禁止QueryInterface。

9、CComObjectStackEx :为局部COM组件提供更好的服务,功能包涵:

  (1)正常的引用计数。

  (2)正常的QueryInterface。

  (3)在析构函数中断言(dwRef == 0)。(以此保证当组件释放时不存在对其的引用)

ATL中的各种CriticalSection

ATL中的各种CriticalSection

1、CComCriticalSection,最基本CriticalSection,只是简单地包装了一下Windows CirticalSection。

2、CComAutoCriticalSection,在构造和析构函数中初始化CriticalSection,不允许自由Init和Tern。

3、CComSafeDeleteCriticalSection,用来保证cs不会被反复的初始化和删除,另外保证自动释放资源。亦即,你随便用吧,你忘了释放cs时,我来帮你擦屁股,你擦了的时候,我就不帮你擦了。

4、CComAutoDeleteCriticalSection,在(3)的基础上,禁止手动释放cs。目的是统一释放。

5、CComFakeCriticalSection,假的,一切都是假的,一个空壳,只是为了方便实现代码级的统一。

以上五个类在头文件“atlcore.h”中,分析完毕。

巧妙的Section — — 剖析ATL OBJECT_MAP的自动建立

基本知识

1、#pragma section,建立一个section。下例中,ATL是section名,_a是section中的的段名,段默认大小为104H,另外默认段内数据初始化为0。意即一个section可以包含多个名字不同的段。不懂section的请查阅PE文件结构。

2、合并两个Section

3、allocate将指定的变量放在指定的section中的指定的段中。

4、VC编译器属性,假设定义了同一section的三个段,ATL$_a、ATL$_b、ATL$_c,则这三个段在section内会按名称顺序依次排列。

ATL OBJ_MAP 的建立

根据【基本知识】,很容易分析出,上文定义了一个ATL section,然后在其中定义了三个段,__a、__z、__m。

为什么要这么做呢?

ATL将一个指针放在__a段,那么取其地址&__pobjMapEntryFirst表示的就是__a段的起始地址。

ATL将一人指针放在__z段,那么取其地址&__pobjMapEntryLast表示的就是__z段的起始地址。

最后,ATL将所有OBJ_MAP_ITEM的数据放在__m段中。

那么,做了以上这么多事之后呢?我们怎样获取和遍历对象数组?

其实答案已经出来了,上面分析了,我们有了起始指针__pobjMapEntryFirst,我们有了结尾指针__pobjMapEntryLast,而根据【基本知识】,__m段夹在这两个指针之间,所以我们只要从起始指针遍历到结尾指针就能获取到所有的对象了。

ok,剖析OVER,最后感叹一下,牛B轰轰的ATL!

原创粉丝点击