rpcb_prot.c revision 90271
174462Salfred/* $NetBSD: rpcb_prot.c,v 1.3 2000/07/14 08:40:42 fvdl Exp $ */ 274462Salfred/* $FreeBSD: head/lib/libc/rpc/rpcb_prot.c 90271 2002-02-05 23:43:43Z alfred $ */ 374462Salfred 474462Salfred/* 574462Salfred * Sun RPC is a product of Sun Microsystems, Inc. and is provided for 674462Salfred * unrestricted use provided that this legend is included on all tape 774462Salfred * media and as a part of the software program in whole or part. Users 874462Salfred * may copy or modify Sun RPC without charge, but are not authorized 974462Salfred * to license or distribute it to anyone else except as part of a product or 1074462Salfred * program developed by the user. 1174462Salfred * 1274462Salfred * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE 1374462Salfred * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR 1474462Salfred * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE. 1574462Salfred * 1674462Salfred * Sun RPC is provided with no support and without any obligation on the 1774462Salfred * part of Sun Microsystems, Inc. to assist in its use, correction, 1874462Salfred * modification or enhancement. 1974462Salfred * 2074462Salfred * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE 2174462Salfred * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC 2274462Salfred * OR ANY PART THEREOF. 2374462Salfred * 2474462Salfred * In no event will Sun Microsystems, Inc. be liable for any lost revenue 2574462Salfred * or profits or other special, indirect and consequential damages, even if 2674462Salfred * Sun has been advised of the possibility of such damages. 2774462Salfred * 2874462Salfred * Sun Microsystems, Inc. 2974462Salfred * 2550 Garcia Avenue 3074462Salfred * Mountain View, California 94043 3174462Salfred */ 3274462Salfred/* 3374462Salfred * Copyright (c) 1986-1991 by Sun Microsystems Inc. 3474462Salfred */ 3574462Salfred 3674462Salfred/* #ident "@(#)rpcb_prot.c 1.13 94/04/24 SMI" */ 3774462Salfred 3874462Salfred#if 0 3974462Salfred#if !defined(lint) && defined(SCCSIDS) 4074462Salfredstatic char sccsid[] = "@(#)rpcb_prot.c 1.9 89/04/21 Copyr 1984 Sun Micro"; 4174462Salfred#endif 4274462Salfred#endif 4374462Salfred 4474462Salfred/* 4574462Salfred * rpcb_prot.c 4674462Salfred * XDR routines for the rpcbinder version 3. 4774462Salfred * 4874462Salfred * Copyright (C) 1984, 1988, Sun Microsystems, Inc. 4974462Salfred */ 5074462Salfred 5174462Salfred#include "namespace.h" 5274462Salfred#include <rpc/rpc.h> 5374462Salfred#include <rpc/types.h> 5474462Salfred#include <rpc/xdr.h> 5574462Salfred#include <rpc/rpcb_prot.h> 5674462Salfred#include "un-namespace.h" 5774462Salfred 5874462Salfredbool_t 5974462Salfredxdr_rpcb(xdrs, objp) 6074462Salfred XDR *xdrs; 6174462Salfred RPCB *objp; 6274462Salfred{ 6374462Salfred if (!xdr_u_int32_t(xdrs, &objp->r_prog)) { 6474462Salfred return (FALSE); 6574462Salfred } 6674462Salfred if (!xdr_u_int32_t(xdrs, &objp->r_vers)) { 6774462Salfred return (FALSE); 6874462Salfred } 6974462Salfred if (!xdr_string(xdrs, &objp->r_netid, (u_int)~0)) { 7074462Salfred return (FALSE); 7174462Salfred } 7274462Salfred if (!xdr_string(xdrs, &objp->r_addr, (u_int)~0)) { 7374462Salfred return (FALSE); 7474462Salfred } 7574462Salfred if (!xdr_string(xdrs, &objp->r_owner, (u_int)~0)) { 7674462Salfred return (FALSE); 7774462Salfred } 7874462Salfred return (TRUE); 7974462Salfred} 8074462Salfred 8174462Salfred/* 8274462Salfred * rpcblist_ptr implements a linked list. The RPCL definition from 8374462Salfred * rpcb_prot.x is: 8474462Salfred * 8574462Salfred * struct rpcblist { 8674462Salfred * rpcb rpcb_map; 8774462Salfred * struct rpcblist *rpcb_next; 8874462Salfred * }; 8974462Salfred * typedef rpcblist *rpcblist_ptr; 9074462Salfred * 9174462Salfred * Recall that "pointers" in XDR are encoded as a boolean, indicating whether 9274462Salfred * there's any data behind the pointer, followed by the data (if any exists). 9374462Salfred * The boolean can be interpreted as ``more data follows me''; if FALSE then 9474462Salfred * nothing follows the boolean; if TRUE then the boolean is followed by an 9574462Salfred * actual struct rpcb, and another rpcblist_ptr (declared in RPCL as "struct 9674462Salfred * rpcblist *"). 9774462Salfred * 9874462Salfred * This could be implemented via the xdr_pointer type, though this would 9974462Salfred * result in one recursive call per element in the list. Rather than do that 10074462Salfred * we can ``unwind'' the recursion into a while loop and use xdr_reference to 10174462Salfred * serialize the rpcb elements. 10274462Salfred */ 10374462Salfred 10474462Salfredbool_t 10574462Salfredxdr_rpcblist_ptr(xdrs, rp) 10674462Salfred XDR *xdrs; 10774462Salfred rpcblist_ptr *rp; 10874462Salfred{ 10974462Salfred /* 11074462Salfred * more_elements is pre-computed in case the direction is 11174462Salfred * XDR_ENCODE or XDR_FREE. more_elements is overwritten by 11274462Salfred * xdr_bool when the direction is XDR_DECODE. 11374462Salfred */ 11474462Salfred bool_t more_elements; 11574462Salfred int freeing = (xdrs->x_op == XDR_FREE); 11674462Salfred rpcblist_ptr next; 11774462Salfred rpcblist_ptr next_copy; 11874462Salfred 11990271Salfred next = NULL; 12074462Salfred for (;;) { 12174462Salfred more_elements = (bool_t)(*rp != NULL); 12274462Salfred if (! xdr_bool(xdrs, &more_elements)) { 12374462Salfred return (FALSE); 12474462Salfred } 12574462Salfred if (! more_elements) { 12674462Salfred return (TRUE); /* we are done */ 12774462Salfred } 12874462Salfred /* 12974462Salfred * the unfortunate side effect of non-recursion is that in 13074462Salfred * the case of freeing we must remember the next object 13174462Salfred * before we free the current object ... 13274462Salfred */ 13374462Salfred if (freeing) 13474462Salfred next = (*rp)->rpcb_next; 13574462Salfred if (! xdr_reference(xdrs, (caddr_t *)rp, 13674462Salfred (u_int)sizeof (rpcblist), (xdrproc_t)xdr_rpcb)) { 13774462Salfred return (FALSE); 13874462Salfred } 13974462Salfred if (freeing) { 14074462Salfred next_copy = next; 14174462Salfred rp = &next_copy; 14274462Salfred /* 14374462Salfred * Note that in the subsequent iteration, next_copy 14474462Salfred * gets nulled out by the xdr_reference 14574462Salfred * but next itself survives. 14674462Salfred */ 14774462Salfred } else { 14874462Salfred rp = &((*rp)->rpcb_next); 14974462Salfred } 15074462Salfred } 15174462Salfred /*NOTREACHED*/ 15274462Salfred} 15374462Salfred 15474462Salfred/* 15574462Salfred * xdr_rpcblist() is specified to take a RPCBLIST **, but is identical in 15674462Salfred * functionality to xdr_rpcblist_ptr(). 15774462Salfred */ 15874462Salfredbool_t 15974462Salfredxdr_rpcblist(xdrs, rp) 16074462Salfred XDR *xdrs; 16174462Salfred RPCBLIST **rp; 16274462Salfred{ 16374462Salfred bool_t dummy; 16474462Salfred 16574462Salfred dummy = xdr_rpcblist_ptr(xdrs, (rpcblist_ptr *)rp); 16674462Salfred return (dummy); 16774462Salfred} 16874462Salfred 16974462Salfred 17074462Salfredbool_t 17174462Salfredxdr_rpcb_entry(xdrs, objp) 17274462Salfred XDR *xdrs; 17374462Salfred rpcb_entry *objp; 17474462Salfred{ 17574462Salfred if (!xdr_string(xdrs, &objp->r_maddr, (u_int)~0)) { 17674462Salfred return (FALSE); 17774462Salfred } 17874462Salfred if (!xdr_string(xdrs, &objp->r_nc_netid, (u_int)~0)) { 17974462Salfred return (FALSE); 18074462Salfred } 18174462Salfred if (!xdr_u_int32_t(xdrs, &objp->r_nc_semantics)) { 18274462Salfred return (FALSE); 18374462Salfred } 18474462Salfred if (!xdr_string(xdrs, &objp->r_nc_protofmly, (u_int)~0)) { 18574462Salfred return (FALSE); 18674462Salfred } 18774462Salfred if (!xdr_string(xdrs, &objp->r_nc_proto, (u_int)~0)) { 18874462Salfred return (FALSE); 18974462Salfred } 19074462Salfred return (TRUE); 19174462Salfred} 19274462Salfred 19374462Salfredbool_t 19474462Salfredxdr_rpcb_entry_list_ptr(xdrs, rp) 19574462Salfred XDR *xdrs; 19674462Salfred rpcb_entry_list_ptr *rp; 19774462Salfred{ 19874462Salfred /* 19974462Salfred * more_elements is pre-computed in case the direction is 20074462Salfred * XDR_ENCODE or XDR_FREE. more_elements is overwritten by 20174462Salfred * xdr_bool when the direction is XDR_DECODE. 20274462Salfred */ 20374462Salfred bool_t more_elements; 20474462Salfred int freeing = (xdrs->x_op == XDR_FREE); 20574462Salfred rpcb_entry_list_ptr next; 20674462Salfred rpcb_entry_list_ptr next_copy; 20774462Salfred 20890271Salfred next = NULL; 20974462Salfred for (;;) { 21074462Salfred more_elements = (bool_t)(*rp != NULL); 21174462Salfred if (! xdr_bool(xdrs, &more_elements)) { 21274462Salfred return (FALSE); 21374462Salfred } 21474462Salfred if (! more_elements) { 21574462Salfred return (TRUE); /* we are done */ 21674462Salfred } 21774462Salfred /* 21874462Salfred * the unfortunate side effect of non-recursion is that in 21974462Salfred * the case of freeing we must remember the next object 22074462Salfred * before we free the current object ... 22174462Salfred */ 22274462Salfred if (freeing) 22374462Salfred next = (*rp)->rpcb_entry_next; 22474462Salfred if (! xdr_reference(xdrs, (caddr_t *)rp, 22574462Salfred (u_int)sizeof (rpcb_entry_list), 22674462Salfred (xdrproc_t)xdr_rpcb_entry)) { 22774462Salfred return (FALSE); 22874462Salfred } 22974462Salfred if (freeing) { 23074462Salfred next_copy = next; 23174462Salfred rp = &next_copy; 23274462Salfred /* 23374462Salfred * Note that in the subsequent iteration, next_copy 23474462Salfred * gets nulled out by the xdr_reference 23574462Salfred * but next itself survives. 23674462Salfred */ 23774462Salfred } else { 23874462Salfred rp = &((*rp)->rpcb_entry_next); 23974462Salfred } 24074462Salfred } 24174462Salfred /*NOTREACHED*/ 24274462Salfred} 24374462Salfred 24474462Salfred/* 24574462Salfred * XDR remote call arguments 24674462Salfred * written for XDR_ENCODE direction only 24774462Salfred */ 24874462Salfredbool_t 24974462Salfredxdr_rpcb_rmtcallargs(xdrs, p) 25074462Salfred XDR *xdrs; 25174462Salfred struct rpcb_rmtcallargs *p; 25274462Salfred{ 25374462Salfred struct r_rpcb_rmtcallargs *objp = 25474462Salfred (struct r_rpcb_rmtcallargs *)(void *)p; 25574462Salfred u_int lenposition, argposition, position; 25674462Salfred int32_t *buf; 25774462Salfred 25874462Salfred buf = XDR_INLINE(xdrs, 3 * BYTES_PER_XDR_UNIT); 25974462Salfred if (buf == NULL) { 26074462Salfred if (!xdr_u_int32_t(xdrs, &objp->prog)) { 26174462Salfred return (FALSE); 26274462Salfred } 26374462Salfred if (!xdr_u_int32_t(xdrs, &objp->vers)) { 26474462Salfred return (FALSE); 26574462Salfred } 26674462Salfred if (!xdr_u_int32_t(xdrs, &objp->proc)) { 26774462Salfred return (FALSE); 26874462Salfred } 26974462Salfred } else { 27074462Salfred IXDR_PUT_U_INT32(buf, objp->prog); 27174462Salfred IXDR_PUT_U_INT32(buf, objp->vers); 27274462Salfred IXDR_PUT_U_INT32(buf, objp->proc); 27374462Salfred } 27474462Salfred 27574462Salfred /* 27674462Salfred * All the jugglery for just getting the size of the arguments 27774462Salfred */ 27874462Salfred lenposition = XDR_GETPOS(xdrs); 27974462Salfred if (! xdr_u_int(xdrs, &(objp->args.args_len))) { 28074462Salfred return (FALSE); 28174462Salfred } 28274462Salfred argposition = XDR_GETPOS(xdrs); 28374462Salfred if (! (*objp->xdr_args)(xdrs, objp->args.args_val)) { 28474462Salfred return (FALSE); 28574462Salfred } 28674462Salfred position = XDR_GETPOS(xdrs); 28774462Salfred objp->args.args_len = (u_int)((u_long)position - (u_long)argposition); 28874462Salfred XDR_SETPOS(xdrs, lenposition); 28974462Salfred if (! xdr_u_int(xdrs, &(objp->args.args_len))) { 29074462Salfred return (FALSE); 29174462Salfred } 29274462Salfred XDR_SETPOS(xdrs, position); 29374462Salfred return (TRUE); 29474462Salfred} 29574462Salfred 29674462Salfred/* 29774462Salfred * XDR remote call results 29874462Salfred * written for XDR_DECODE direction only 29974462Salfred */ 30074462Salfredbool_t 30174462Salfredxdr_rpcb_rmtcallres(xdrs, p) 30274462Salfred XDR *xdrs; 30374462Salfred struct rpcb_rmtcallres *p; 30474462Salfred{ 30574462Salfred bool_t dummy; 30674462Salfred struct r_rpcb_rmtcallres *objp = (struct r_rpcb_rmtcallres *)(void *)p; 30774462Salfred 30874462Salfred if (!xdr_string(xdrs, &objp->addr, (u_int)~0)) { 30974462Salfred return (FALSE); 31074462Salfred } 31174462Salfred if (!xdr_u_int(xdrs, &objp->results.results_len)) { 31274462Salfred return (FALSE); 31374462Salfred } 31474462Salfred dummy = (*(objp->xdr_res))(xdrs, objp->results.results_val); 31574462Salfred return (dummy); 31674462Salfred} 31774462Salfred 31874462Salfredbool_t 31974462Salfredxdr_netbuf(xdrs, objp) 32074462Salfred XDR *xdrs; 32174462Salfred struct netbuf *objp; 32274462Salfred{ 32374462Salfred bool_t dummy; 32474462Salfred 32574462Salfred if (!xdr_u_int32_t(xdrs, (u_int32_t *) &objp->maxlen)) { 32674462Salfred return (FALSE); 32774462Salfred } 32874462Salfred dummy = xdr_bytes(xdrs, (char **)&(objp->buf), 32974462Salfred (u_int *)&(objp->len), objp->maxlen); 33074462Salfred return (dummy); 33174462Salfred} 332