COM组件开发(三)——类厂对象

COM类厂对象的实现

        COM客户程序要使用COM对象是通过COM库创建而来的,而实际上COM库是调用COM对象的类厂来创建的。COM类厂对象也是一个COM对象,所以它也从IUnknow继承而来,而它又支持IClassFactory接口:

class IClassFactory:public IUnknow
{
    public:
        virtual HRESULT CreateInstance(IUnkonwn* pUnkOuter, REFIID iid, void** ppObject)=0;
        virtual HRESULT LockServer(BOOL fLock)=0;
};
        所以,一个普通的类厂应该是这样的:

class CSampleFactory: public IClassFactory
{
    public:       
       CSampleFactory();
       HRESULT __stdcall QueryInterface(REFIID riid, void** ppObject);
       ULONG __stdcall AddRef();
       ULONG __stdcall Release();
       HRESULT __stdcall CreateInstance(IUnknown* pUnkOuter, REFIID riid, void** ppObject);
       HRESULT __stdcall LockServer(BOOL fLock);
    private:
       ULONG m_dwRefCount;
}; 

CreateInstance是构造COM对象的函数,通过传入接口的IID,从ppObject输出COM接口指针,而pUnkOuter一般设为NULL,该参数在聚合时起作用。

LockServer是用来控制COM类厂的生命周期的函数,将fLock设为TRUE后,即使组件程序中所有COM对象已释放了,该类厂指针也会一直保存并且有效,当不再需要的时候设为FALSE即可。

         若要使用类厂对象去创建COM对象,首先得创建类厂对象,可以使用库函数CoGetClassObject来创建COM类的类厂,若找到的COM对象是进程内组件,则使用DLL导出函数DllGetClassObject函数创建类厂,然后将对象指针传出。

STDAPI DLLGetClassObject(REFCLSID rclsid, REFIID riid, void** ppObject)
{
  if(rclsid == CLSID_SAMPLE)
  {
    CSampleFactory* csf = new CSampleFactory();
    if(FAILED(csf->QueryInterface(riid, ppObject)))
    {
       delete pFactory;
       *ppObject = NULL;
       return E_INVALIDARG;
    }
   }
   return NO_ERROR;
}
        若创建的是进程外组件,则要分别调用CoRegisterClassObject和CoRevokeClassObject去注册和反注册类厂对象才能正常地创建、销毁COM对象。


COM自动注册

        在cmd窗体下,使用命令

                regsvr32 d:\sample.dll

        对sample.dll进行注册,这时会调用该dll导出的DllRegisterServer。

        另外,使用

                regsvr32 /u d:\sample.dll

        对其进行反注册,同样会调用导出函数DllUnregisterServer。

        以上的命令是对进程内组件有效,而对进程外组件不必使用以上命令,由于自身是可执行程序,所以在运行时一般会自动调用DllRegisterServer和DllUnregisterServer。


COM自动卸载

         客户端程序调用CoFreeUnusedLibraries来释放组件,但是释放组件需要满足:组件中的对象数目为0和类厂的锁计数为0,要知道是否满足以上条件,需要导出函数DllCanUnloadNow,该函数通过判断组件对象的引用计数来判断是否可以释放组件。

  • 0
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值