1. 概念

1.1. 代理和存根

代理和存根在COM,RPC等方面使用。

1.1.1. 列集marshaling

列集,对函数参数进行打包处理得过程,因为指针等数据,必须通过一定得转换,才能被另一组件所理解,列集完成后,RPC调用就会产生。可以说列集是一种数据格式的转换方法。

//列集有3种方式:
1. 类型库列集
  它可以列集与OLEAUTOMATION兼容的任何接口,意思是你的接口的返回值必须是HRESULT,所使用的参数的类型也应该是与C++的VARIANT结构兼容。
2. 通过创建Stub / proxy DLL
  这个DLL的源代由MIDL产生。你必须在服务器和客户机上都注册这个DLL(这是标准的marshal 方式)使用吃方法时,最好把stub / proxy代码编译作为一个独立的组件。
3. 自定义marshaling
  自定义marshal要求在你的组件中必须实现IMarshal接口。当COM需要marchal时,他首先通过QueryInterface看你是否支持IMarshal接口,如果你实现了该接口,也就是说,由你控制了你的COM的所有参数和返回值的打包、解包的方法模式。

1.1.2. 代理和存根dll的建立

使用工具MIDL,对一个IDL文件,MIDL会分析自动产生相应的代理/存根DLL的相关文件。

1.1.3. 怎么使用代理和存根?

对于你来说代理和存根的使用是透明的,你根本不用去关心如何使用他们,com库会知道怎么做。

1.2. COM

COM是一种跨应用和语言 共享二进制代码的方法。

更多参考:COM编程

1.3.RPC

RPC(Remote Procedure Call,远程过程调用)一般用来实现部署在不同机器上的系统之间的方法调用,使得程序能够像访问本地资源一样,通过网络传输去访问远端系统资源。

两台服务器A,B,一个应用部署在A服务器上,想要调用B服务器上应用提供的函数/方法,由于不在一个内存空间,不能直接调用,需要通过网络来表达调用的语义和传达调用的数据

通俗的语言解释一下什么是 RPC 框架

第一,
第二,要解决寻址的问题,也就是说,A服务器上的应用怎么告诉底层的RPC框架,如何连接到B服务器(如主机或IP地址)以及特定的端口,方法的名称名称是什么,这样才能完成调用。
比如基于Web服务协议栈的RPC,就要提供一个endpoint+URI,或者是从UDDI服务上查找。如果是RMI调用的话,还需要一个RMI+Registry来注册服务的地址。
参考: https://www.zhihu.com/question/25536695

什么是Web服务协议栈?

https://max.book118.com/html/2017/0501/103569652.shtm
http://www.webxml.com.cn/h/2B6C3575796C50772B41303D.aspx

1.4. 类厂(类工厂)

c++下,创建对象必须知道对象的类别,然后才能比如new一个出来。
而com下,你不知道组件的实际的类别,你只知道abstract class,也就是com接口,所以你不能创建。
但是客户并不关心实际的类别,只关心接口,
所以有必要引入一个间接的创建机制,让它来创建,这就是类厂,这是通用的设计模式。

2. 问题:COM的RPC为什么一定要使用Proxy和Stub?不能像Socket一样直连客户端和服务器吗?

在COM架构中调用者和被调用者如果在不同的套间,就不可以直接调用,而必须通过代理(Proxy)和占位(Stub)程序调用,通过Proxy和Stub之间的通讯来完成调用者和被调用者之间的调用,
即:`Server -- Stub -- Network --- Proxy --- Client`,
我的疑问是直接通过`Server -- Network --- Client`能实现吗?为什么一定要使用Proxy和Stub?
客户为什么要用代理和存根,而不直接同对象连接呢? 

2.1. 回答1【采用】

原因1:二进制层面不兼容二进制的内容依赖dll厂商所使用的编译器(指针失效)
对客户来说,他与所有com对象的连接都是通过指针来调用的, 而对服务来说,调用对象的接口函数也是通过指针来完成的,然而,指针只有在同一进程内才会有效。这样,代理和存根为了完成这个使命也就产生了。

代理和存根的作用不只这些,他还要打包所有的参数(包括接口指针),产生RPC(远程进程调用),通向另一个进程,或者对象运行所在的另一台机器。

原因2:COM要实现位置透明性
RPC是指远程过程调用,COM之所以要用Proxy/Stub,而不用WinSocket等通信手段直接通信是因为COM要实现位置透明性,即客户不需要知道服务器在哪。

原因3:封装需要
另一个重要原因是因为封装需要,客户如果和服务器直接通信,那么他们之间就得建立一个协议,指明参数的传递格式,用什么加密手段加密,公钥是什么等,这有违服务器的封装性,而且也留有严重的安全隐患(因为会话是由客户和服务器共同建立的,而客户和服务器并不是同一组织编写,客户方可以留下漏洞),而使用Proxy/Stub,Proxy和Stub都是编写服务器的组织编写的,留下漏洞的原因就只能是那个组织水平有限。

2.2. 回答2

楼主的意思可能是用COM来通讯为什么不是和Socket通讯一样直接连接而要通过代(Proxy)和(Stub)

COM在这里应该认为是DCOM最后也是要走Socket的,只是这些DCOM都帮你做好了,所以你不用自己写一个Socket来RPC一下,他让你感觉服务器就在本机上一样。

不是说COM不能做Socket,用COM和做Socket没有什么关系。

2.3. 回答3

我说得很清楚了,数据当然是靠RPC来传的
但是只有代理/存根dll知道把传来的数据包unmarshal成什么东西

如果没有proxy/stub
那么server怎么知道client传来的是什么东西,同样client也不知道server传来的是什么东西

参考:
https://www.jianshu.com/p/d93d0a11f556
https://bbs.csdn.net/topics/30442941
https://blog.csdn.net/malei8197/article/details/7881761

3.COM、COM+、DCOM和RPC?

1.COM、COM+、DCOM和RPC之间是什么关系
com 是底层基础构架,建立在C++的虚函数基础上,核心就是IUnknown。
dcom在com基础上实现了分布式,
实现分布式就要网络通讯,通讯就需要协议,那么dcom就通过rpc实现。
com+在dcom基础上又提供了服务,例如objec pooling,分布式事务等,类似J2ee server。

COM可以用于网络,用微软提供的WSDL Generator做成一个WebService就可以了.WebService是跨平台的,而DCOM不是
COM是默认使用ORPC(object rpc)通讯的,就是说com的实现使用了RPC,它也可以使用其他任何的协议

1 com 就是component object modal,也就是组件对象模型. com+其实就相当于com的升级,对原来com中存在的问题或者不足进行了补充和修改. dcom中的d 是distributed,分布式的意思,一般用于网络. rpc是remote procedure call,远程过程调用.要说2者之间的关系,其实2者之间应该说没什么关系,rpc是一种协议(TCP/IP协议族的子协议),com是一种方法(主要解决代码重用),不过据我所知,com里可以内嵌rpc的东西.
2,com应该可以实现rpc的功能,不过很显然,用com需要有服务器端和客户端.
3,回调函数的使用好像没有什么限制吧,这个我不清楚了.

2.能否用COM实现类似RPC的功能
dcom一出,位置就透明了,client可以无需关心server具体的位置。

3.RPC中能否设置回调函数或给客户端发送事件
可以。

参考:
https://bbs.csdn.net/topics/60504662

4. 涉及的XML技术

以上RPC等概念中,涉及了xml相关技术有:Web Services(三元素SOAP、WSDL、UDDI)

参考:XML技术

posted on 2022-03-01 18:21  西伯尔  阅读(233)  评论(0编辑  收藏  举报