我有一个现有的 C# 应用程序,我想将其用作 RPC 服务器,以便远程 RPC 客户端可以调用其 C# 函数。我在其 Windows SDK 中搜索并阅读了 Microsoft RPC 架构。它仅使用 C/C++ 来创建需要生成 IDL、ACF 文件和使用 MIDL 编译器的 RPC 服务器应用程序。
Microsoft RPC 服务器教程:http : //msdn.microsoft.com/en-us/library/windows/desktop/aa378869(v=vs.85).aspx
有没有一种方法可以将我现有的 C# 应用程序用作 RPC 服务器来在这样的 RPC 架构中工作?也许 RPC 服务器 C 包装器代码调用我的 C# 代码?我只是在大声思考。
感谢您的帮助,一些示例代码说明会非常有用。
凯文,这是可能的,但我也同意基里尔的看法,这非常困难。
主要问题是 .idl 语言是 C/C++ 特定的,因为是从 midl 编译器生成的代码。我以前通过将 .idl 编译为适当的 C/C++ 客户端/服务器存根,然后将代码转换为 C# PInvoke 来完成它。这个翻译是痛苦的(带有大写的“P”)。所涉及的结构具有循环引用,这使得在 C# 中变得相当困难,但并非不可能。
我们选择了更简单的方法,即单个入口点,而不是与大量接口方法作斗争。为此,我们的 IDL 如下所示:
[ uuid (546B0CE0-C70B-1067-B317-00DD010662DA),
version(1.0),
pointer_default(unique)
]
interface IRpcExec
{
error_status_t Exec(
[in] handle_t Binding,
[in] long lDataSize,
[size_is(lDataSize)] byte arData[*],
[out] long *plReturnSize,
[out, size_is(,*plReturnSize)] byte **arReturn
);
}
Run Code Online (Sandbox Code Playgroud)
然后 ACF 简单地声明它以返回错误:
interface IRpcExec
{
[comm_status, fault_status]
Exec();
}
Run Code Online (Sandbox Code Playgroud)
实际上,这允许我们接收一个 byte[],并返回一个 byte[],从而将 RPC 变成一个简单的传输层,而不是一个成熟的协议。完整的项目和来源可从:
http://csharptest.net/browse/src/RpcLibrary/
在这个简单的传输层之上是一个库,用于通过 Google 协议缓冲区(使用 Skeet 的protobuf-csharp-port)添加对全功能 RPC 机制的支持:
https://code.google.com/p/protobuf-csharp-rpc/