COM原理及应用----COM特性
理/存根程序并正确地进行了注册,则代理管理器和存根管理器会在需要的时候自动加载接口代理和接口存根。因此,从实现的角度来讲,我们的任务就是针对接口实现代理/存根程序。
代理/存根组件是一个DLL程序,除了实现接口代理和接口存根之外,还应该实现相应的类厂,代理/存根组件要求类厂支持IPSFactoryBuffer 接口,通过IPSFactoryBuffer::CreateProcy和IPSFactoryBuffer::CreateStub成员函数创建接口代理和接口存根对象。接口代理对象支持两个接口:它本身提供列集特性的接口和IRpcProxyBuffer接口,其中IRpcProxyBuffer接口只有Connect和Disconnect成员函数,被代理管理器用于创建或取消它与RPC通道的连接;它本身提供列集特性的接口的成员函数接受客户程序的调用,并把客户的调用参数放到RPC通道中,然后调用RPC通道的SendReceive成员函数,函数返回后,把返回值和输出参数解译出来。这些操作是接口代理对象应该完成的。与此相对应,接口存根只要实现IRpcStubBuffer接口,除了存根管理器所调用的几个与RPC通道连接的函数外,最主要的成员函数为IRpcStubBuffer::Invoke,RPC通道调用此函数以响应客户进程的SendReceive调用,Invoke函数把客户进程传递过来的参数解译出来,然后调用组件对象的接口成员函数,并把返回结果或者输出参数经过RPC通道传回到客户进程的RPC通道中。 接口代理对象和接口存根对象必须非常小心地处理接口成员函数的参数,尤其是一些指针或者结构参数,如果成员函数中包含接口指针类型,则还需要调用 CoMarshalInterface或者CoUnmarshalInterface函数,以便创建相应的存根或者代理对象。在代理和存根中对参数的处理必须严格一致,否则会发生不可预料的后果。如果客户进程和组件进程在同一台机器上运行,则COM会根据注册表中的接口信息,在两个进程中使用相同的代理/存根程序,所以我们只要保证接口的代理/存根程序中对参数的列集和散集格式一致,参数传递就不会有问题;但如果客户与组件程序在两台机器上,则不能严格保证两个进程会使用相同的代理/存根程序,那么对参数的列集和散集最好使用统一的数据格式表示,以保证参数传递的正确性。 如果一个进程外组件实现了多个COM接口,那么是否需要为每一个接口实现其代理/存根组件程序呢?在这些接口中,如果它是COM提供的标准接口,或者是 OLE标准接口,则COM或者OLE已经提供了其代理/存根程序,我们可以不管这些接口,直接使用即可;如果自定义的接口,则必须自己实现代理/存根程序,并注册到系统中,然后才能真正使用这些接口。 13、自定义接口的代理/存根程序的实现 Microsoft提供了MIDL实用工具帮助我们建立自定义接口的代理/存根程序。首先我们使用IDL(接口描述语言)语言建立接口描述文件,然后运行 MIDL工具,它会根据接口描述文件生成一些C语言源代码文件,用这些源代码文件可以创建代理/存根组件程序。它为我们提供了接口代理/存根组件的一种标准实现方法。 用IDL描述接口与C++描述接口有一些相似之处,但IDL是一种平台无关的标准化描述语言。Win32 SDK提供了所有COM或者OLE标准接口的IDL描述,包括unknown.idl(定义了IUnknown接口),可以在Visual C++的include目录下找到这些IDL文件。Microsoft的RPC开发包中包括运行程序MIDL.EXE和接口列集使用的 RpcProxy.h、Unknown.idl和wtypes.idl,以及RPC调用所需要的静态连接库和动态连接库。 一般地,用MIDL程序可以产生实现代理/存根组件程序所需要的所有C语言源代码文件:***.h为接口说明头文件;***_p.c为接口代理和存根的实现文件;***_i.c为定义所有GUID描述符的文件;dlldata.c包含代理/存根程序的入口函数及类厂所需的数据结构。 运行NMAKE程序可以生成代理/存根组件程序,在 |
凌众科技专业提供服务器租用、服务器托管、企业邮局、虚拟主机等服务,公司网站:http://www.lingzhong.cn 为了给广大客户了解更多的技术信息,本技术文章收集来源于网络,凌众科技尊重文章作者的版权,如果有涉及你的版权有必要删除你的文章,请和我们联系。以上信息与文章正文是不可分割的一部分,如果您要转载本文章,请保留以上信息,谢谢! |