AC9,由VS2005的ATL向导生成的默认COM对象代码分析ATL如何实现COM,第九部分。
ATL中的线程安全是由CXXXxxxCriticalSection提供的,使用的policy策略,使用者可以得到Lock、Unlock两个方法来处理同步问题,而且,ATL的诸多policy给使用者提供了恰好足够的线程安全。注意恰好足够的说法,也就是说首先它够用,更重要的是没有额外负担。
本来这点东西是不足以写成单独一部分的,但是考虑到一个包括大部分模板类的部分非一时半会能写完,就先发这点写完的东西吧。
//恰好足够的线程安全
//atlbase.h
CComSingleThreadModel
CComMultiThreadModel
CComMultiThreadModelNoCS
//这三个线程模型定义了不同级别的CriticalSection,分别是(这是一组typedef,每个线程模型里都定义了这四个类型):
AutoCriticalSection
AutoDeleteCriticalSection
CriticalSection
//各个基本的CriticalSection
//atlcore.h //在atlcore中一共定义了5个CriticalSection
class CXXXxxxCriticalSection //comcore这5个Section都定义了这四个方法,只不过根据不同需求有的方法不能被访问
{
public:
HRESULT Lock() throw() { return S_OK; }
HRESULT Unlock() throw() { return S_OK; }
HRESULT Init() throw() { return S_OK; }
HRESULT Term() throw() { return S_OK; }
};
CComFakeCriticalSection //4方法都是空方法,只是提供格式上的policy,不处理线程安全问题
CComCriticalSection //提供对CRITICAL_SECTION提供封装
CComAutoCriticalSection :public CComCriticalSection //Init、Term被屏蔽,构造、析够自动处理
CComSafeDeleteCriticalSection :public CComCriticalSection //提供初始化检测
CComAutoDeleteCriticalSection :public CComSafeDeleteCriticalSection //自动,你使用Lock、Unlock不用管其他的了
//由于历史原因,存在了这么多类,实际使用中应该优先使用 CComAutoCriticalSection
//atlbase.h
#if defined(_ATL_SINGLE_THREADED)
#if defined(_ATL_APARTMENT_THREADED) || defined(_ATL_FREE_THREADED)
#pragma message ("More than one global threading model defined.")
#endif
typedef CComSingleThreadModel CComObjectThreadModel;
typedef CComSingleThreadModel CComGlobalsThreadModel;
#elif defined(_ATL_APARTMENT_THREADED)
#if defined(_ATL_SINGLE_THREADED) || defined(_ATL_FREE_THREADED)
#pragma message ("More than one global threading model defined.")
#endif
typedef CComSingleThreadModel CComObjectThreadModel;
typedef CComMultiThreadModel CComGlobalsThreadModel;
#elif defined(_ATL_FREE_THREADED)
#if defined(_ATL_SINGLE_THREADED) || defined(_ATL_APARTMENT_THREADED)
#pragma message ("More than one global threading model defined.")
#endif
typedef CComMultiThreadModel CComObjectThreadModel;
typedef CComMultiThreadModel CComGlobalsThreadModel;
#else
#pragma message ("No global threading model defined")
#endif
//根据stdafx.h中的宏定义组件获得定义的线程模型。
CComObjectRootEx
//封装提供了恰好足够的线程安全的引用计数