Skip Navigation Links | |
Exit Print View | |
ONC+ Developer's Guide Oracle Solaris 11.1 Information Library |
1. Introduction to ONC+ Technologies
4. Programmer's Interface to RPC
Client Side of Simplified Interface
Server Side of the Simplified Interface
Hand-Coded Registration Routine
Client Side of the Top-Level Interface
Client Side of the Intermediate-Level Interface
Server Side of the Intermediate-Level Interface
Client Side of the Expert-Level Interface
Server Side of the Expert-Level Interface
Client Side of the Bottom-Level Interface
Server Side of the Bottom-Level Interface
Connection-Oriented Transports
5. Advanced RPC Programming Techniques
6. Porting From TS-RPC to TI-RPC
7. Multithreaded RPC Programming
8. Extensions to the Oracle Solaris RPC Library
Two pseudo-RPC interface routines bypass all the network software. The routines shown in clnt_raw_create() and svc_raw_create() do not use any real transport.
Note - Do not use raw mode on production systems. Raw mode is intended as a debugging aid only. Raw mode is not MT safe.
The following code example is compiled and linked using the following makefile:
all: raw CFLAGS += -g raw: raw.o cc -g -o raw raw.o -lnsl
Example 4-19 Simple Program Using Raw RPC
/* * A simple program to increment a number by 1 */ #include <stdio.h> #include <rpc/rpc.h> #include <rpc/raw.h> #define prognum 0x40000001 #define versnum 1 #define INCR 1 struct timeval TIMEOUT = {0, 0}; static void server(); main (argc, argv) int argc; char **argv; { CLIENT *cl; SVCXPRT *svc; int num = 0, ans; int flag; if (argc == 2) num = atoi(argv[1]); svc = svc_raw_create(); if (svc == (SVCXPRT *) NULL) { fprintf(stderr, "Could not create server handle\n"); exit(1); } flag = svc_reg( svc, prognum, versnum, server, (struct netconfig *) NULL ); if (flag == 0) { fprintf(stderr, "Error: svc_reg failed.\n"); exit(1); } cl = clnt_raw_create( prognum, versnum ); if (cl == (CLIENT *) NULL) { clnt_pcreateerror("Error: clnt_raw_create"); exit(1); } if (clnt_call(cl, INCR, xdr_int, (caddr_t) &num, xdr_int, (caddr_t) &ans, TIMEOUT) != RPC_SUCCESS) { clnt_perror(cl, "Error: client_call with raw"); exit(1); } printf("Client: number returned %d\n", ans); exit(0); } static void server(rqstp, transp) struct svc_req *rqstp; SVCXPRT *transp; { int num; fprintf(stderr, "Entering server procedure.\n"); switch(rqstp->rq_proc) { case NULLPROC: if (svc_sendreply( transp, xdr_void, (caddr_t) NULL) == FALSE) { fprintf(stderr, "error in null proc\n"); exit(1); } return; case INCR: break; default: svcerr_noproc(transp); return; } if (!svc_getargs( transp, xdr_int, &num)) { svcerr_decode(transp); return; } fprintf(stderr, "Server procedure: about to increment.\n"); num++; if (svc_sendreply(transp, xdr_int, &num) == FALSE) { fprintf(stderr, "error in sending answer\n"); exit (1); } fprintf(stderr, "Leaving server procedure.\n"); }
Note the following points about the example:
The server must be created before the client.
svc_raw_create() has no parameters.
The server is not registered with rpcbind. The last parameter to svc_reg() is (struct netconfig *) NULL.
svc_run() is not called.
All the RPC calls occur within the same thread of control.