Windows RPC远程过程调用(1): 最基本的

Windows本身支持成为一个RPC服务器。WindowsXP上面默认的RPC/tcpip功能没有打开,必须运行gpedit.msc,计算机配置->管理模版->系统->远程过程调用->用于未验证的RPC...->选择"已启动",限定项选择"无"。

第1步:编写 IDL(Interface Description Language,接口描述语言)文件

test.idl

[
     uuid("9B26A55E-6DCD-4988-B83C-C6171F1DF5AC"), 
     version(1.0)
]

interface HelloWorld  
{
     // 我们定义的方法
     int intAdd(int x, int y);
}

一个可选的文件是应用程序配置文件(.acf),它的作用是对 RPC 接口进行配置:

test.acf

[
implicit_handle(handle_t test_Binding)
]
interface HelloWorld  
{
}

编译 IDL 文件,在VC或VS命令行运行以下命令:
midl test.idl


然后,会产生test.h、test_c.c、test_s.c几个文件,分别是头文件、客户端文件、服务器端文件。


第2步:编写服务器端程序

新建win32控制端程序,添加文件server.c:

#include<windows.h>  
#include <stdlib.h>
#include <stdio.h>

#include "test.h"
int intAdd( int x, int y)
{
	printf("%d + %d = %d\n", x, y, x+y);
	return x+y;
}

int main(int argc,char * argv[])
{	// 采用tcp协议,13521端口
	RpcServerUseProtseqEp((unsigned char *)"ncacn_ip_tcp", RPC_C_PROTSEQ_MAX_REQS_DEFAULT, 
		(unsigned char *)"13521", NULL);    
	// 注册,HelloWorld_v1_0_s_ifspec定义域头文件test.h
	RpcServerRegisterIf(HelloWorld_v1_0_s_ifspec, NULL, NULL);
	// 开始监听,本函数将一直阻塞
	RpcServerListen(1,20,FALSE);
	return 0;
}

// 下面的函数是为了满足链接需要而写的,没有的话会出现链接错误
void __RPC_FAR* __RPC_USER midl_user_allocate(size_t len)
{
	return(malloc(len));
}
void __RPC_USER midl_user_free(void __RPC_FAR *ptr)
{
	free(ptr);
}

在菜单“工程”——“设置”——“链接”——“对象模块”中,添加rpcrt4.lib。

test.h、test_s.c这2个文件也添加到server工程中。


然后,编译,即可运行。


第3步:编写客户端程序

同样地,建立一个工程client。

在菜单“工程”——“设置”——“链接”——“对象模块”中,添加rpcrt4.lib。

test.h、test_c.c这2个文件也添加到client工程中。

添加源文件client.c:

#include <windows.h>
#include <stdlib.h>
#include <stdio.h>

#include "test.h"

int main()
{
	unsigned char * pszStringBinding = NULL;
	int x, y, rval;

	RpcStringBindingCompose(
		NULL,
		(unsigned char*)"ncacn_ip_tcp",
		(unsigned char*)"localhost" /*NULL*/,
		(unsigned char*)"13521",
		NULL,
		&pszStringBinding
		);

	// 绑定接口,这里要和 test.acf 的配置一致,那么就是test_Binding
	RpcBindingFromStringBinding(pszStringBinding, & test_Binding );

	// 下面是调用服务端的函数了
	RpcTryExcept
	{
		while(1)
		{
			printf("Input two integer: ");
			scanf("%d %d", &x, &y);
			rval = intAdd(x, y); 
			printf("%d\n", rval);
		}
		
	}
	RpcExcept(1)
	{
		printf( "RPC Exception %d\n", RpcExceptionCode() );
	}
	RpcEndExcept
		
		
	// 释放资源
	RpcStringFree(&pszStringBinding);
    RpcBindingFree(&test_Binding);

	return 0;
}

// 下面的函数是为了满足链接需要而写的,没有的话会出现链接错误
void __RPC_FAR* __RPC_USER midl_user_allocate(size_t len)
{
	return(malloc(len));
}
void __RPC_USER midl_user_free(void __RPC_FAR *ptr)
{
	free(ptr);
}

编译运行,即可。


程序功能:

在client中,输入2个整数,那么server会计算其和,并返回。

你可能感兴趣的:(windows,user,服务器,null,interface,binding)