Specifications

Page 14 Remote Procedure Call Programming Guide
3.3. The Calling Side
When you use callrpc() you have no control over the RPC delivery mechanism or the socket used to trans-
port the data. To illustrate the layer of RPC that lets you adjust these parameters, consider the following
code to call the nusers service:
#include <stdio.h>
#include <rpc/rpc.h>
#include <utmp.h>
#include <rpcsvc/rusers.h>
#include <sys/socket.h>
#include <sys/time.h>
#include <netdb.h>
main(argc, argv)
int argc;
char **argv;
{
struct hostent *hp;
struct timeval pertry_timeout, total_timeout;
struct sockaddr_in server_addr;
int sock = RPC_ANYSOCK;
register CLIENT *client;
enum clnt_stat clnt_stat;
unsigned long nusers;
if (argc != 2) {
fprintf(stderr, "usage: nusers hostname\n");
exit(-1);
}
if ((hp = gethostbyname(argv[1])) == NULL) {
fprintf(stderr, "can’t get addr for %s\n",argv[1]);
exit(-1);
}
pertry_timeout.tv_sec = 3;
pertry_timeout.tv_usec = 0;
bcopy(hp->h_addr, (caddr_t)&server_addr.sin_addr,
hp->h_length);
server_addr.sin_family = AF_INET;
server_addr.sin_port = 0;
if ((client = clntudp_create(&server_addr, RUSERSPROG,
RUSERSVERS, pertry_timeout, &sock)) == NULL) {
clnt_pcreateerror("clntudp_create");
exit(-1);
}
total_timeout.tv_sec = 20;
total_timeout.tv_usec = 0;
clnt_stat = clnt_call(client, RUSERSPROC_NUM, xdr_void,
0, xdr_u_long, &nusers, total_timeout);
if (clnt_stat != RPC_SUCCESS) {
clnt_perror(client, "rpc");
exit(-1);
}
clnt_destroy(client);
close(sock);
exit(0);
}
The low-level version of callrpc() is clnt_call() which takes a CLIENT pointer rather than a host name. The
parameters to clnt_call() are a CLIENT pointer, the procedure number, the XDR routine for serializing the