📄 555.htm
字号:
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=gb2312">
<title>CTerm非常精华下载</title>
</head>
<body bgcolor="#FFFFFF">
<table border="0" width="100%" cellspacing="0" cellpadding="0" height="577">
<tr><td width="32%" rowspan="3" height="123"><img src="DDl_back.jpg" width="300" height="129" alt="DDl_back.jpg"></td><td width="30%" background="DDl_back2.jpg" height="35"><p align="center"><a href="http://apue.dhs.org"><font face="黑体"><big><big>apue</big></big></font></a></td></tr>
<tr>
<td width="68%" background="DDl_back2.jpg" height="44"><big><big><font face="黑体"><p align="center"> ● UNIX网络编程 (BM: clown) </font></big></big></td></tr>
<tr>
<td width="68%" height="44" bgcolor="#000000"><font face="黑体"><big><big><p align="center"></big></big><a href="http://cterm.163.net"><img src="banner.gif" width="400" height="60" alt="banner.gif"border="0"></a></font></td>
</tr>
<tr><td width="100%" colspan="2" height="100" align="center" valign="top"><br><p align="center">[<a href="index.htm">回到开始</a>][<a href="15.htm">上一层</a>][<a href="556.htm">下一篇</a>]
<hr><p align="left"><small>★ 将该常规程序划分成两部分 <br>
<br>
<br>
<br>
下图是常规程序的函数关系图。 <br>
<br>
<br>
<br>
main ---- nextin <br>
<br>
| <br>
<br>
| <br>
<br>
---- insertw <br>
<br>
| <br>
<br>
| <br>
<br>
---- initw <br>
<br>
| <br>
| <br>
<br>
| <br>
<br>
---- deletew <br>
<br>
| <br>
<br>
| <br>
<br>
---- lookupw <br>
<br>
<br>
<br>
nextin用于读取下一个输入行,需要访问标准输入stdin,应该和main函数放在一 <br>
<br>
起。 <br>
<br>
<br>
<br>
原则:执行I/O或者访问了文件句柄的过程不能轻易转移到远程主机上。 <br>
<br>
<br>
<br>
<br>
lookupw需要访问全部单词数据库,如果执行lookupw的主机和字典所在主机不是同 <br>
<br>
一主机, <br>
<br>
则对lookupw的RPC调用就必须将整个字典作为参数传递,这是不可取的。 <br>
<br>
<br>
<br>
原则:执行过程的主机应该和过程执行中需访问数据所在主机一致。 <br>
<br>
<br>
<br>
于是可以按照如下图示划分远程过程: <br>
<br>
<br>
<br>
client端 server端 <br>
<br>
发起RPC远程过程调用端 响应RPC远程过程调用端 <br>
<br>
<br>
<br>
<br>
------------ ------------------------------------- <br>
<br>
| | RPC调用 | | <br>
<br>
| main -|----------------| initw lookupw | <br>
<br>
| | | 字典数据结构 | <br>
<br>
| nextin | | insertw deletew | <br>
<br>
| | | | <br>
<br>
------------ ------------------------------------- <br>
<br>
<br>
<br>
/* dict1.c -- main, nextin */ <br>
<br>
<br>
<br>
#include <stdio.h> <br>
<br>
#include <ctype.h> <br>
<br>
<br>
<br>
#define MAXWORD 50 /* maximum length of a command or word */ <br>
<br>
<br>
<br>
/* ------------------------------------------------------------------ <br>
<br>
* main -- insert, delete, or lookup words in a dictionary as <br>
<br>
specified <br>
<br>
* ------------------------------------------------------------------ <br>
<br>
*/ <br>
<br>
<br>
<br>
int main ( int argc, char * argv[] ) <br>
<br>
{ <br>
<br>
char word[ MAXWORD + 1 ]; /* space to hold word from input line <br>
<br>
*/ <br>
<br>
char cmd; <br>
<br>
int wordlen; /* length of input word */ <br>
<br>
printf( "Please input:\n" ); <br>
<br>
while ( 1 ) <br>
<br>
{ <br>
<br>
wordlen = nextin( &cmd, word ); <br>
<br>
if ( wordlen < 0 ) <br>
<br>
{ <br>
{ <br>
<br>
exit( 0 ); <br>
<br>
} <br>
<br>
switch ( cmd ) <br>
<br>
{ <br>
<br>
case 'I': /* 初始化 */ <br>
<br>
initw(); <br>
<br>
printf( "Dictionary initialized to empty.\n" ); <br>
<br>
break; <br>
<br>
case 'i': /* 插入 */ <br>
<br>
insertw( word ); <br>
<br>
<br>
<br>
<br>
printf( "%s inserted.\n", word ); <br>
<br>
break; <br>
<br>
case 'd': /* 删除 */ <br>
<br>
if ( deletew( word ) ) <br>
<br>
{ <br>
<br>
printf( "%s deleted.\n", word ); <br>
<br>
} <br>
<br>
else <br>
<br>
{ <br>
<br>
printf( "%s not found.\n", word ); <br>
<br>
} <br>
} <br>
<br>
break; <br>
<br>
case 'l': /* 查询 */ <br>
<br>
if ( lookupw( word ) ) <br>
<br>
{ <br>
<br>
printf( "%s was found.\n", word ); <br>
<br>
} <br>
<br>
else <br>
<br>
{ <br>
<br>
printf( "%s was not found.\n", word ); <br>
<br>
} <br>
<br>
break; <br>
<br>
case 'q': /* 退出 */ <br>
<br>
printf( "Program quits.\n" ); <br>
<br>
ch = getc( stdin ); <br>
<br>
} /* end of while */ <br>
<br>
if ( ch == EOF ) <br>
<br>
{ <br>
<br>
return( -1 ); <br>
<br>
} <br>
<br>
*cmd = ( char )ch; <br>
<br>
ch = getc( stdin ); <br>
<br>
while ( isspace( ch ) ) <br>
<br>
{ <br>
<br>
ch = getc( stdin ); <br>
<br>
} /* end of while */ <br>
<br>
if ( ch == EOF ) <br>
<br>
{ <br>
<br>
return( -1 ); <br>
<br>
} <br>
<br>
if ( ch == '\n' ) <br>
<br>
{ <br>
<br>
return( 0 ); <br>
<br>
} <br>
} <br>
<br>
i = 0; <br>
<br>
while ( !isspace( ch ) ) <br>
<br>
{ <br>
<br>
if ( ++i > MAXWORD ) <br>
<br>
{ <br>
<br>
printf( "error: word too long.\n" ); <br>
<br>
exit( 1 ); <br>
<br>
} <br>
<br>
*word++ = ch; <br>
<br>
ch = getc( stdin ); <br>
<br>
} /* end of while */ <br>
<br>
*word = '\0'; <br>
<br>
return i; <br>
<br>
} /* end of nextin */ <br>
<br>
<br>
<br>
************************************************************************ <br>
<br>
******* <br>
<br>
<br>
<br>
/* dict2.c -- initw, insertw, deletew, lookupw */ <br>
<br>
<br>
<br>
#define MAXWORD 50 /* maximum length of a command or word */ <br>
<br>
#define DICTSIZ 100 /* maximum number of entries in dictionary. */ <br>
<br>
<br>
<br>
char dict[ DICTSIZ ][ MAXWORD + 1 ]; /* storage for a dictionary of <br>
<br>
words */ <br>
<br>
int nwords = 0; /* number of words in the <br>
<br>
dictionary */ <br>
<br>
<br>
<br>
/* ------------------------------------------------------------------ <br>
<br>
* initw -- initialize the dictionary to contain no words at all <br>
<br>
* ------------------------------------------------------------------ <br>
<br>
*/ <br>
<br>
<br>
<br>
<br>
int initw ( void ) <br>
<br>
{ <br>
<br>
nwords = 0; <br>
<br>
return 1; <br>
<br>
} /* end of initw */ <br>
<br>
<br>
<br>
/* ------------------------------------------------------------------ <br>
<br>
* insertw -- insert a word in the dictionary <br>
<br>
* ------------------------------------------------------------------ <br>
<br>
*/ <br>
<br>
<br>
<br>
<br>
int insertw ( const char * word ) <br>
<br>
{ <br>
<br>
strcpy( dict[nwords], word ); <br>
<br>
nwords++; <br>
<br>
return( nwords ); <br>
<br>
} /* end of insertw */ <br>
<br>
<br>
<br>
/* ------------------------------------------------------------------ <br>
<br>
* deletew -- delete a word from the dictionary <br>
<br>
* ------------------------------------------------------------------ <br>
<br>
*/ <br>
*/ <br>
<br>
<br>
<br>
int deletew ( const char * word ) <br>
<br>
{ <br>
<br>
int i; <br>
<br>
for ( i = 0; i < nwords; i++ ) <br>
<br>
{ <br>
<br>
if ( strcmp( word, dict[i] ) == 0 ) <br>
<br>
{ <br>
<br>
nwords--; <br>
<br>
strcpy( dict[i], dict[nwords] ); <br>
<br>
return( 1 ); <br>
<br>
} <br>
<br>
} /* end of for */ <br>
<br>
return( 0 ); <br>
<br>
} /* end of deletew */ <br>
<br>
<br>
<br>
/* ------------------------------------------------------------------ <br>
<br>
* lookupw -- look up a word in the dictionary <br>
<br>
* ------------------------------------------------------------------ <br>
<br>
*/ <br>
<br>
<br>
<br>
int lookupw ( const char * word ) <br>
<br>
{ <br>
<br>
int i; <br>
<br>
for ( i = 0; i < nwords; i++ ) <br>
<br>
{ <br>
<br>
if ( strcmp( word, dict[i] ) == 0 ) <br>
<br>
{ <br>
<br>
return( 1 ); <br>
<br>
} <br>
<br>
} /* end of for */ <br>
<br>
return( 0 ); <br>
<br>
} /* end of lookupw */ <br>
<br>
<br>
<br>
注意,对于符号常量MAXWORD的定义在两边都出现了。 <br>
<br>
<br>
<br>
[scz@ /home/scz/src]> cat > dict1.c <br>
<br>
[scz@ /home/scz/src]> cat > dict2.c <br>
<br>
[scz@ /home/scz/src]> gcc -O3 -o dict1.o -c dict1.c <br>
<br>
[scz@ /home/scz/src]> gcc -O3 -o dict2.o -c dict2.c <br>
<br>
<br>
<br>
此时进行部分编译(-c选项),可以提前修正很多语法错误,避免程序员的注意 <br>
<br>
力从RPC上移开。这里的两部分代码不构成完整的应用,剩下的代码以后增加。 <br>
<br>
<br>
<br>
<br>
★ 创建一个rpcgen规格说明 <br>
<br>
<br>
<br>
这个规格说明文件包括: <br>
<br>
<br>
<br>
. 声明在client或者(这更常见)server(远程程序)中所使用的常量 <br>
<br>
. 声明所使用的数据类型(特别是对远程过程的参数) <br>
<br>
. 声明远程程序、每个程序中所包含的过程、以及它们的参数类型 <br>
<br>
<br>
<br>
<br>
<br>
RPC使用一些数字来标识远程程序以及在这些程序中的远程过程。在规格说明 <br>
<br>
文件中的程序声明定义了诸如程序的RPC号、版本号、以及分配给程序中的过 <br>
<br>
程的编号等等。所有这些声明都必须用RPC编程语言给出,而不是用C。在RPC <br>
<br>
中string代表以null结束的字符串,而C用char *表示,必须注意这些细微的 <br>
<br>
差别。 <br>
<br>
<br>
<br>
文件rdict.x给出了一个rpcgen规格说明,包含了字典程序之RPC版的声明。 <br>
<br>
<br>
<br>
/* rdict.x */ <br>
<br>
<br>
<br>
/* RPC declarations for dictionary program */ <br>
<br>
<br>
<br>
const MAXWORD = 50; /* maximum length of a command or word */ <br>
<br>
const DICTSIZ = 100; /* number of entries in dictionary */ <br>
<br>
<br>
<br>
struct example /* unused structure declared here to */ <br>
<br>
{ <br>
<br>
int exfield1; /* illustrate how rpcgen builds XDR */ <br>
<br>
char exfield2; /* routines to convert structures */ <br>
<br>
}; <br>
<br>
<br>
<br>
/* ------------------------------------------------------------------ <br>
<br>
* RDICTPROG -- remote program that provides insert, delete, and <br>
<br>
lookup <br>
lookup <br>
<br>
* ------------------------------------------------------------------ <br>
<br>
*/ <br>
<br>
<br>
<br>
program RDICTPROG /* name of remote program ( not used ) */ <br>
<br>
<br>
<br>
{ <br>
<br>
version RDICTVERS /* declaration of version ( see below ) */ <br>
<br>
{ <br>
<br>
int INITW ( void ) = 1; /* first procedure in this <br>
<br>
program */ <br>
<br>
int INSERTW ( string ) = 2; /* second procedure in this program <br>
<br>
*/ <br>
<br>
int DELETEW ( string ) = 3; /* third procedure in this <br>
<br>
program */ <br>
<br>
int LOOKUPW ( string ) = 4; /* fourth procedure in this program <br>
<br>
*/ <br>
<br>
} = 1; /* definition of the program version */ <br>
<br>
} = 0x30090949; /* remote program number ( must be unique ) */ <br>
<br>
<br>
<br>
一个rpcgen规格说明文件并没有囊括在最初的程序中的所能找到的所有声明,仅仅 <br>
<br>
<br>
<br>
定义了那些在client和server之间要共享的常量和数据类型,或者是那些需要指明 <br>
<br>
<br>
<br>
的参数。 <br>
<br>
按照约定,规格说明文件使用大写名字定义过程和程序,并不绝对要求使用大写, <br>
<br>
但这样做有助于避免冲突。 <br>
<br>
-- <br>
;34m※ 来源: 武汉白云黄鹤站 bbs.whnet.edu.cn. [FROM: 202.106.243. <br>
213] m <br>
-- <br>
</small><hr>
<p align="center">[<a href="index.htm">回到开始</a>][<a href="15.htm">上一层</a>][<a href="556.htm">下一篇</a>]
<p align="center"><a href="http://cterm.163.net">欢迎访问Cterm主页</a></p>
</table>
</body>
</html>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -