2 * support/nfs/rcpdispatch.c
4 * Generic RPC dispatcher.
6 * Copyright (C) 1995, 1996, Olaf Kirch <okir@monad.swb.de>
15 #include <rpc/pmap_clnt.h>
17 #include <arpa/inet.h>
24 rpc_dispatch(struct svc_req *rqstp, SVCXPRT *transp,
25 struct rpc_dtable *dtable, int nvers,
26 void *argp, void *resp)
28 struct rpc_dentry *dent;
30 if (rqstp->rq_vers > nvers) {
31 svcerr_progvers(transp, 1, nvers);
34 dtable += (rqstp->rq_vers - 1);
35 if (rqstp->rq_proc > dtable->nproc) {
36 svcerr_noproc(transp);
40 dent = dtable->entries + rqstp->rq_proc;
42 if (dent->func == NULL) {
43 svcerr_noproc(transp);
47 memset(argp, 0, dent->xdr_arg_size);
48 memset(resp, 0, dent->xdr_res_size);
50 if (!svc_getargs(transp, dent->xdr_arg_fn, argp)) {
51 svcerr_decode(transp);
55 if ((dent->func)(rqstp, argp, resp) && resp != 0) {
56 if (!svc_sendreply(transp, dent->xdr_res_fn, (caddr_t)resp))
57 svcerr_systemerr(transp);
59 if (!svc_freeargs(transp, dent->xdr_arg_fn, argp)) {
60 xlog(L_ERROR, "failed to free RPC arguments");
67 * This is our replacement for svc_run. It turns off some signals while
68 * executing the server procedures to avoid nasty race conditions.
71 rpc_svcrun(fd_set *morefds, void (*func)(int fd))
73 sigset_t block, current;
82 for (i = 0; i < FD_SETSIZE; i++)
83 if (FD_ISSET(i, morefds))
86 switch (select(FD_SETSIZE, &readfds, NULL, NULL, NULL)) {
90 xlog(L_ERROR, "svc_run: - select failed");
99 for (i = 0; i < FD_SETSIZE; i++)
100 if (FD_ISSET(i, morefds) &&
101 FD_ISSET(i, &readfds))
105 sigaddset(&block, SIGALRM);
106 sigaddset(&block, SIGVTALRM);
107 sigaddset(&block, SIGIO);
108 sigprocmask(SIG_BLOCK, &block, ¤t);
109 svc_getreqset(&readfds);
110 sigprocmask(SIG_SETMASK, ¤t, NULL);