[rtems-libbsd commit] librpc: Initial addition

Joel Sherrill joel at rtems.org
Fri Aug 3 19:17:39 UTC 2012


Module:    rtems-libbsd
Branch:    master
Commit:    20ec9e6659eaff417b57c62be9e1062fb3069c9c
Changeset: http://git.rtems.org/rtems-libbsd/commit/?id=20ec9e6659eaff417b57c62be9e1062fb3069c9c

Author:    Joel Sherrill <joel.sherrill at oarcorp.com>
Date:      Fri Aug  3 14:19:49 2012 -0500

librpc: Initial addition

This does not currently compile. There is an include file
issue and int32_t is not defined even though stdint.h is included
before its use.

---

 services/librpc/Makefile                        |   86 ++
 services/librpc/README_RTEMS                    |   64 +
 services/librpc/include/rpc/auth.h              |  262 ++++
 services/librpc/include/rpc/auth_unix.h         |   85 ++
 services/librpc/include/rpc/clnt.h              |  310 ++++
 services/librpc/include/rpc/clnt_soc.h          |  109 ++
 services/librpc/include/rpc/clnt_stat.h         |   84 ++
 services/librpc/include/rpc/pmap_clnt.h         |   89 ++
 services/librpc/include/rpc/pmap_prot.h         |  105 ++
 services/librpc/include/rpc/pmap_rmt.h          |   64 +
 services/librpc/include/rpc/rpc.h               |  116 ++
 services/librpc/include/rpc/rpc_com.h           |   65 +
 services/librpc/include/rpc/rpc_msg.h           |  205 +++
 services/librpc/include/rpc/rpcent.h            |   71 +
 services/librpc/include/rpc/svc.h               |  296 ++++
 services/librpc/include/rpc/svc_auth.h          |   58 +
 services/librpc/include/rpc/svc_soc.h           |  125 ++
 services/librpc/include/rpc/types.h             |   68 +
 services/librpc/include/rpc/xdr.h               |  312 ++++
 services/librpc/include/rpcsvc/bootparam_prot.x |  103 ++
 services/librpc/include/rpcsvc/crypt.x          |   91 ++
 services/librpc/include/rpcsvc/key_prot.x       |  282 ++++
 services/librpc/include/rpcsvc/klm_prot.x       |  139 ++
 services/librpc/include/rpcsvc/mount.x          |  257 ++++
 services/librpc/include/rpcsvc/nfs_prot.x       | 1265 ++++++++++++++++
 services/librpc/include/rpcsvc/nis.x            |  466 ++++++
 services/librpc/include/rpcsvc/nis_cache.x      |   87 ++
 services/librpc/include/rpcsvc/nis_callback.x   |   76 +
 services/librpc/include/rpcsvc/nis_db.h         |  164 +++
 services/librpc/include/rpcsvc/nis_object.x     |  317 ++++
 services/librpc/include/rpcsvc/nis_tags.h       |  137 ++
 services/librpc/include/rpcsvc/nislib.h         |  317 ++++
 services/librpc/include/rpcsvc/nlm_prot.x       |  183 +++
 services/librpc/include/rpcsvc/pmap_prot.x      |  284 ++++
 services/librpc/include/rpcsvc/rex.x            |  235 +++
 services/librpc/include/rpcsvc/rnusers.x        |  122 ++
 services/librpc/include/rpcsvc/rquota.x         |   67 +
 services/librpc/include/rpcsvc/rstat.x          |  151 ++
 services/librpc/include/rpcsvc/rwall.x          |   57 +
 services/librpc/include/rpcsvc/sm_inter.x       |  122 ++
 services/librpc/include/rpcsvc/spray.x          |   90 ++
 services/librpc/include/rpcsvc/yp.x             |  379 +++++
 services/librpc/include/rpcsvc/yp_prot.h        |  330 +++++
 services/librpc/include/rpcsvc/ypclnt.h         |   93 ++
 services/librpc/include/rpcsvc/yppasswd.x       |   75 +
 services/librpc/include/rpcsvc/ypupdate_prot.x  |   88 ++
 services/librpc/include/rpcsvc/ypxfrd.x         |  173 +++
 services/librpc/src/rpc/DISCLAIMER              |   28 +
 services/librpc/src/rpc/README                  |  233 +++
 services/librpc/src/rpc/auth_none.c             |  138 ++
 services/librpc/src/rpc/auth_unix.c             |  345 +++++
 services/librpc/src/rpc/authunix_prot.c         |   71 +
 services/librpc/src/rpc/bindresvport.3          |  106 ++
 services/librpc/src/rpc/bindresvport.c          |  160 ++
 services/librpc/src/rpc/clnt_generic.c          |  145 ++
 services/librpc/src/rpc/clnt_perror.c           |  259 ++++
 services/librpc/src/rpc/clnt_raw.c              |  248 ++++
 services/librpc/src/rpc/clnt_simple.c           |  127 ++
 services/librpc/src/rpc/clnt_tcp.c              |  605 ++++++++
 services/librpc/src/rpc/clnt_udp.c              |  579 ++++++++
 services/librpc/src/rpc/des_crypt.3             |  130 ++
 services/librpc/src/rpc/get_myaddress.c         |  117 ++
 services/librpc/src/rpc/getrpcent.3             |   98 ++
 services/librpc/src/rpc/getrpcent.c             |  301 ++++
 services/librpc/src/rpc/getrpcport.3            |   31 +
 services/librpc/src/rpc/getrpcport.c            |   69 +
 services/librpc/src/rpc/netname.c               |  139 ++
 services/librpc/src/rpc/netnamer.c              |  331 +++++
 services/librpc/src/rpc/pmap_clnt.c             |  151 ++
 services/librpc/src/rpc/pmap_getmaps.c          |   92 ++
 services/librpc/src/rpc/pmap_getport.c          |   98 ++
 services/librpc/src/rpc/pmap_prot.c             |   63 +
 services/librpc/src/rpc/pmap_prot2.c            |  122 ++
 services/librpc/src/rpc/pmap_rmt.c              |  441 ++++++
 services/librpc/src/rpc/publickey.3             |   47 +
 services/librpc/src/rpc/publickey.5             |   38 +
 services/librpc/src/rpc/rpc.3                   | 1767 +++++++++++++++++++++++
 services/librpc/src/rpc/rpc.5                   |   35 +
 services/librpc/src/rpc/rpc_callmsg.c           |  196 +++
 services/librpc/src/rpc/rpc_commondata.c        |   45 +
 services/librpc/src/rpc/rpc_dtablesize.c        |   65 +
 services/librpc/src/rpc/rpc_prot.c              |  336 +++++
 services/librpc/src/rpc/rpc_secure.3            |  254 ++++
 services/librpc/src/rpc/rpcdname.c              |   84 ++
 services/librpc/src/rpc/rstat.1                 |   58 +
 services/librpc/src/rpc/rstat_svc.8             |   22 +
 services/librpc/src/rpc/rtems_portmapper.c      |  500 +++++++
 services/librpc/src/rpc/rtems_rpc.c             |   95 ++
 services/librpc/src/rpc/rtime.3                 |   47 +
 services/librpc/src/rpc/rtime.c                 |  163 +++
 services/librpc/src/rpc/svc.c                   |  499 +++++++
 services/librpc/src/rpc/svc_auth.c              |  220 +++
 services/librpc/src/rpc/svc_auth_unix.c         |  152 ++
 services/librpc/src/rpc/svc_raw.c               |  173 +++
 services/librpc/src/rpc/svc_run.c               |   89 ++
 services/librpc/src/rpc/svc_simple.c            |  161 ++
 services/librpc/src/rpc/svc_tcp.c               |  489 +++++++
 services/librpc/src/rpc/svc_udp.c               |  484 +++++++
 services/librpc/src/xdr/xdr.3                   |  837 +++++++++++
 services/librpc/src/xdr/xdr.c                   |  858 +++++++++++
 services/librpc/src/xdr/xdr_array.c             |  160 ++
 services/librpc/src/xdr/xdr_float.c             |  343 +++++
 services/librpc/src/xdr/xdr_mem.c               |  245 ++++
 services/librpc/src/xdr/xdr_rec.c               |  608 ++++++++
 services/librpc/src/xdr/xdr_reference.c         |  142 ++
 services/librpc/src/xdr/xdr_sizeof.c            |  167 +++
 services/librpc/src/xdr/xdr_stdio.c             |  194 +++
 107 files changed, 23524 insertions(+), 0 deletions(-)

diff --git a/services/librpc/Makefile b/services/librpc/Makefile
new file mode 100644
index 0000000..5311260
--- /dev/null
+++ b/services/librpc/Makefile
@@ -0,0 +1,86 @@
+include ../../config.inc
+
+include $(RTEMS_MAKEFILE_PATH)/Makefile.inc
+include $(RTEMS_CUSTOM)
+include $(PROJECT_ROOT)/make/leaf.cfg
+
+CFLAGS += -I $(INSTALL_BASE)/include
+
+CFLAGS += -w 
+CFLAGS += -I include 
+CFLAGS += -std=gnu99
+CFLAGS += -MT $@ -MD -MP -MF $(basename $@).d
+
+C_FILES =
+# RPC Files
+C_FILES += src/rpc/auth_none.c
+C_FILES += src/rpc/auth_unix.c
+C_FILES += src/rpc/authunix_prot.c
+C_FILES += src/rpc/bindresvport.c
+C_FILES += src/rpc/clnt_generic.c
+C_FILES += src/rpc/clnt_perror.c
+C_FILES += src/rpc/clnt_raw.c
+C_FILES += src/rpc/clnt_simple.c
+C_FILES += src/rpc/clnt_tcp.c
+C_FILES += src/rpc/clnt_udp.c
+C_FILES += src/rpc/get_myaddress.c
+C_FILES += src/rpc/getrpcent.c
+C_FILES += src/rpc/getrpcport.c
+C_FILES += src/rpc/netname.c
+C_FILES += src/rpc/netnamer.c
+C_FILES += src/rpc/pmap_clnt.c
+C_FILES += src/rpc/pmap_getmaps.c
+C_FILES += src/rpc/pmap_getport.c
+C_FILES += src/rpc/pmap_prot2.c
+C_FILES += src/rpc/pmap_prot.c
+C_FILES += src/rpc/pmap_rmt.c
+C_FILES += src/rpc/rpc_callmsg.c
+C_FILES += src/rpc/rpc_commondata.c
+C_FILES += src/rpc/rpcdname.c
+C_FILES += src/rpc/rpc_dtablesize.c
+C_FILES += src/rpc/rpc_prot.c
+C_FILES += src/rpc/rtems_portmapper.c
+C_FILES += src/rpc/rtems_rpc.c
+C_FILES += src/rpc/rtime.c
+C_FILES += src/rpc/svc_auth.c
+C_FILES += src/rpc/svc_auth_unix.c
+C_FILES += src/rpc/svc.c
+C_FILES += src/rpc/svc_raw.c
+C_FILES += src/rpc/svc_run.c
+C_FILES += src/rpc/svc_simple.c
+C_FILES += src/rpc/svc_tcp.c
+C_FILES += src/rpc/svc_udp.c
+# XDR Files
+C_FILES += src/xdr/xdr_array.c
+C_FILES += src/xdr/xdr.c
+C_FILES += src/xdr/xdr_float.c
+C_FILES += src/xdr/xdr_mem.c
+C_FILES += src/xdr/xdr_rec.c
+C_FILES += src/xdr/xdr_reference.c
+C_FILES += src/xdr/xdr_sizeof.c
+C_FILES += src/xdr/xdr_stdio.c
+
+C_O_FILES = $(C_FILES:%.c=%.o)
+C_D_FILES = $(C_FILES:%.c=%.d)
+
+LIB = libxdr.a
+
+all: $(LIB)
+
+$(LIB): $(C_O_FILES)
+	$(AR) rcu $@ $^
+
+install: $(LIB)
+	install -d $(INSTALL_BASE)/include/rpc
+	install -d $(INSTALL_BASE)/include/xdr
+	cd include; for i in `find . -name '*.h'` ; do \
+	  install -c -m 644 -D "$$i" "$(INSTALL_BASE)/include/$$i" ; done
+	install -c -m 644 $(LIB) $(INSTALL_BASE)
+
+clean:
+	rm -f $(LIB) $(C_O_FILES) $(C_D_FILES) $(GEN_FILES)
+
+-include $(C_D_FILES)
+
+doc: 
+
diff --git a/services/librpc/README_RTEMS b/services/librpc/README_RTEMS
new file mode 100644
index 0000000..e60f879
--- /dev/null
+++ b/services/librpc/README_RTEMS
@@ -0,0 +1,64 @@
+USING RPC/XDR ON RTEMS
+======================
+For the most part, programmers using RPC/XDR routines on RTEMS
+can proceed as if they were to be using a POSIX/UNIX system.
+The only significant changes are those to start the portmapper
+and to allow use of RPC/XDR by multiple threads.
+
+Starting the portmapper
+=======================
+The SUN portmapper program has been modified to run as an RTEMS
+task.  Applications which need the portmapper can start this
+task by calling:
+	int rtems_rpc_start_portmapper (int priority);
+The return value is an RTEMS status code.
+
+Multi-threaded operation
+========================
+The RPC/XDR package has been modified to allow for multiple RTEMS
+tasks to use RPC/XDR routines.  If more than one task is to call
+an RPC/XDR routine, the additional tasks must call:
+	int rtems_rpc_task_init(void);
+before calling any RPC/XDR routines.  For example, the portmapper
+calls this routine since the portmapper uses RPC/XDR routines in
+a separate thread.
+The return value is an RTEMS status code.
+
+
+Porting Notes
+=============
+Most of the FreeBSD rpc library ports to RTEMS with little
+or no modification beyond that required to provide for operation
+in a multitasking environment.  Multitasking operation was
+provided by moving all `static persistence' variables into
+a single structure and using an RTEMS task variable to point
+to that structure.  
+
+Some of the library, however, has not made it into the RTEMS
+implementation.  FreeBSD source files which have been left out include:
+- Files which provide RPC to the AF_UNIX address family:
+	clnt_unix.c
+	svc_unix.c
+  An `ifndef __rtems__' was added to clnt_generic.c because clnt_unix.c
+  was omitted.
+- Files which need NIS:
+	auth_time.c
+- Files which provide DES authentication:
+	auth_des.c
+	authdes_prot.c
+	crypt_client.c
+	des_crypt.c
+	des_soft.c
+	getpublickey.c
+	key_call.c
+	key_prot_xdr.c
+	svc_auth_des.c
+
+The FreeBSD xdr source compiles and runs on RTEMS without modification.
+
+The original source was obtained from:
+	ftp://ftp.FreeBSD.org/pub/FreeBSD/
+		        branches/4.0-stable/src/lib/libc/rpc
+			branches/4.0-stable/src/lib/libc/xdr
+			branches/4.0-stable/src/include/rpc
+			branches/4.0-stable/src/include/rpcsvc
diff --git a/services/librpc/include/rpc/auth.h b/services/librpc/include/rpc/auth.h
new file mode 100644
index 0000000..13432bd
--- /dev/null
+++ b/services/librpc/include/rpc/auth.h
@@ -0,0 +1,262 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ *
+ *	from: @(#)auth.h 1.17 88/02/08 SMI
+ *	from: @(#)auth.h	2.3 88/08/07 4.0 RPCSRC
+ * $FreeBSD: src/include/rpc/auth.h,v 1.15 1999/08/27 23:45:02 peter Exp $
+ */
+
+/*
+ * auth.h, Authentication interface.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ *
+ * The data structures are completely opaque to the client.  The client
+ * is required to pass a AUTH * to routines that create rpc
+ * "sessions".
+ */
+
+#ifndef _RPC_AUTH_H
+#define _RPC_AUTH_H
+#include <sys/cdefs.h>
+#include <sys/socket.h>
+#include <rpc/xdr.h>
+
+#define MAX_AUTH_BYTES	400
+#define MAXNETNAMELEN	255	/* maximum length of network user's name */
+
+/*
+ * Status returned from authentication check
+ */
+enum auth_stat {
+	AUTH_OK=0,
+	/*
+	 * failed at remote end
+	 */
+	AUTH_BADCRED=1,			/* bogus credentials (seal broken) */
+	AUTH_REJECTEDCRED=2,		/* client should begin new session */
+	AUTH_BADVERF=3,			/* bogus verifier (seal broken) */
+	AUTH_REJECTEDVERF=4,		/* verifier expired or was replayed */
+	AUTH_TOOWEAK=5,			/* rejected due to security reasons */
+	/*
+	 * failed locally
+	*/
+	AUTH_INVALIDRESP=6,		/* bogus response verifier */
+	AUTH_FAILED=7,			/* some unknown reason */
+	_AUTH_STAT = 0xffffffff
+};
+
+union des_block {
+	struct {
+		u_int32_t high;
+		u_int32_t low;
+	} key;
+	char c[8];
+};
+typedef union des_block des_block;
+__BEGIN_DECLS
+extern bool_t xdr_des_block (XDR *, des_block *);
+__END_DECLS
+
+/*
+ * Authentication info.  Opaque to client.
+ */
+struct opaque_auth {
+	enum_t	oa_flavor;		/* flavor of auth */
+	caddr_t	oa_base;		/* address of more auth stuff */
+	u_int	oa_length;		/* not to exceed MAX_AUTH_BYTES */
+};
+__BEGIN_DECLS
+bool_t xdr_opaque_auth (XDR *xdrs, struct opaque_auth *ap);
+__END_DECLS
+
+
+/*
+ * Auth handle, interface to client side authenticators.
+ */
+typedef struct __rpc_auth {
+	struct	opaque_auth	ah_cred;
+	struct	opaque_auth	ah_verf;
+	union	des_block	ah_key;
+	struct auth_ops {
+		void	(*ah_nextverf) (struct __rpc_auth *);
+		/* nextverf & serialize */
+		int	(*ah_marshal) (struct __rpc_auth *, XDR *);
+		/* validate verifier */
+		int	(*ah_validate) (struct __rpc_auth *,
+				struct opaque_auth *);
+		/* refresh credentials */
+		int	(*ah_refresh) (struct __rpc_auth *);
+		/* destroy this structure */
+		void	(*ah_destroy) (struct __rpc_auth *);
+	} *ah_ops;
+	caddr_t ah_private;
+} AUTH;
+
+
+/*
+ * Authentication ops.
+ * The ops and the auth handle provide the interface to the authenticators.
+ *
+ * AUTH	*auth;
+ * XDR	*xdrs;
+ * struct opaque_auth verf;
+ */
+#define AUTH_NEXTVERF(auth)		\
+		((*((auth)->ah_ops->ah_nextverf))(auth))
+#define auth_nextverf(auth)		\
+		((*((auth)->ah_ops->ah_nextverf))(auth))
+
+#define AUTH_MARSHALL(auth, xdrs)	\
+		((*((auth)->ah_ops->ah_marshal))(auth, xdrs))
+#define auth_marshall(auth, xdrs)	\
+		((*((auth)->ah_ops->ah_marshal))(auth, xdrs))
+
+#define AUTH_VALIDATE(auth, verfp)	\
+		((*((auth)->ah_ops->ah_validate))((auth), verfp))
+#define auth_validate(auth, verfp)	\
+		((*((auth)->ah_ops->ah_validate))((auth), verfp))
+
+#define AUTH_REFRESH(auth)		\
+		((*((auth)->ah_ops->ah_refresh))(auth))
+#define auth_refresh(auth)		\
+		((*((auth)->ah_ops->ah_refresh))(auth))
+
+#define AUTH_DESTROY(auth)		\
+		((*((auth)->ah_ops->ah_destroy))(auth))
+#define auth_destroy(auth)		\
+		((*((auth)->ah_ops->ah_destroy))(auth))
+
+
+extern struct opaque_auth _null_auth;
+
+/*
+ * These are the various implementations of client side authenticators.
+ */
+
+/*
+ * Unix style authentication
+ * AUTH *authunix_create(machname, uid, gid, len, aup_gids)
+ *	char *machname;
+ *	int uid;
+ *	int gid;
+ *	int len;
+ *	int *aup_gids;
+ */
+__BEGIN_DECLS
+struct sockaddr_in;
+extern AUTH *authunix_create		(char *, int, int, int, int *);
+extern AUTH *authunix_create_default	(void);
+extern AUTH *authnone_create		(void);
+__END_DECLS
+
+/* Forward compatibility with TI-RPC */
+#define authsys_create authunix_create
+#define authsys_create_default authunix_create_default
+
+/*
+ * DES style authentication
+ * AUTH *authdes_create(servername, window, timehost, ckey)
+ * 	char *servername;		- network name of server
+ *	u_int window;			- time to live
+ * 	struct sockaddr *timehost;	- optional hostname to sync with
+ * 	des_block *ckey;		- optional conversation key to use
+ */
+__BEGIN_DECLS
+extern AUTH *authdes_create ( char *, u_int, struct sockaddr *, des_block * );
+#ifdef NOTYET
+/*
+ * TI-RPC supports this call, but it requires the inclusion of
+ * NIS+-specific headers which would require the inclusion of other
+ * headers which would result in a tangled mess. For now, the NIS+
+ * code prototypes this routine internally.
+ */
+extern AUTH *authdes_pk_create ( char *, netobj *, u_int,
+				     struct sockaddr *, des_block *,
+				     nis_server * );
+#endif
+__END_DECLS
+
+/*
+ * Netname manipulation routines.
+ */
+__BEGIN_DECLS
+extern int netname2user ( char *, uid_t *, gid_t *, int *, gid_t *);
+extern int netname2host ( char *, char *, int );
+extern int getnetname ( char * );
+extern int user2netname ( char *, uid_t, char * );
+extern int host2netname ( char *, char *, char * );
+extern void passwd2des ( char *, char * );
+__END_DECLS
+
+/*
+ * Keyserv interface routines.
+ * XXX Should not be here.
+ */
+#ifndef HEXKEYBYTES
+#define HEXKEYBYTES 48
+#endif
+typedef char kbuf[HEXKEYBYTES];
+typedef char *namestr;
+
+struct netstarg {
+	kbuf st_priv_key;
+	kbuf st_pub_key;
+	namestr st_netname;
+};
+
+__BEGIN_DECLS
+extern int key_decryptsession ( const char *, des_block * );
+extern int key_decryptsession_pk ( char *, netobj *, des_block * );
+extern int key_encryptsession ( const char *, des_block * );
+extern int key_encryptsession_pk ( char *, netobj *, des_block * );
+extern int key_gendes ( des_block * );
+extern int key_setsecret ( const char * );
+extern int key_secretkey_is_set ( void );
+extern int key_setnet ( struct netstarg * );
+extern int key_get_conv ( char *, des_block * );
+__END_DECLS
+
+/*
+ * Publickey routines.
+ */
+__BEGIN_DECLS
+extern int getpublickey ( char *, char * );
+extern int getpublicandprivatekey ( char *, char * );
+extern int getsecretkey ( char *, char *, char * );
+__END_DECLS
+
+
+#define AUTH_NONE	0		/* no authentication */
+#define	AUTH_NULL	0		/* backward compatibility */
+#define	AUTH_UNIX	1		/* unix style (uid, gids) */
+#define	AUTH_SYS	1		/* forward compatibility */
+#define	AUTH_SHORT	2		/* short hand unix style */
+#define AUTH_DES	3		/* des style (encrypted timestamps) */
+
+#endif /* !_RPC_AUTH_H */
diff --git a/services/librpc/include/rpc/auth_unix.h b/services/librpc/include/rpc/auth_unix.h
new file mode 100644
index 0000000..f822f3d
--- /dev/null
+++ b/services/librpc/include/rpc/auth_unix.h
@@ -0,0 +1,85 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ *
+ *	from: @(#)auth_unix.h 1.8 88/02/08 SMI
+ *	from: @(#)auth_unix.h	2.2 88/07/29 4.0 RPCSRC
+ * $FreeBSD: src/include/rpc/auth_unix.h,v 1.10 1999/08/27 23:45:03 peter Exp $
+ */
+
+/*
+ * auth_unix.h, Protocol for UNIX style authentication parameters for RPC
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+/*
+ * The system is very weak.  The client uses no encryption for  it
+ * credentials and only sends null verifiers.  The server sends backs
+ * null verifiers or optionally a verifier that suggests a new short hand
+ * for the credentials.
+ */
+
+#ifndef _RPC_AUTH_UNIX_H
+#define _RPC_AUTH_UNIX_H
+#include <sys/cdefs.h>
+#include <rpc/auth.h> /* opaque_auth */
+
+/* The machine name is part of a credential; it may not exceed 255 bytes */
+#define MAX_MACHINE_NAME 255
+
+/* gids compose part of a credential; there may not be more than 16 of them */
+#define NGRPS 16
+
+/*
+ * Unix style credentials.
+ */
+struct authunix_parms {
+	u_long	 aup_time;
+	char	*aup_machname;
+	int	 aup_uid;
+	int	 aup_gid;
+	u_int	 aup_len;
+	int	*aup_gids;
+};
+
+#define authsys_parms authunix_parms
+
+__BEGIN_DECLS
+extern bool_t xdr_authunix_parms(XDR *, struct authunix_parms *);
+__END_DECLS
+
+/*
+ * If a response verifier has flavor AUTH_SHORT,
+ * then the body of the response verifier encapsulates the following structure;
+ * again it is serialized in the obvious fashion.
+ */
+struct short_hand_verf {
+	struct opaque_auth new_cred;
+};
+
+#endif /* !_RPC_AUTH_UNIX_H */
diff --git a/services/librpc/include/rpc/clnt.h b/services/librpc/include/rpc/clnt.h
new file mode 100644
index 0000000..3042abe
--- /dev/null
+++ b/services/librpc/include/rpc/clnt.h
@@ -0,0 +1,310 @@
+/*	$NetBSD: clnt.h,v 1.14 2000/06/02 22:57:55 fvdl Exp $	*/
+
+/*
+ * The contents of this file are subject to the Sun Standards
+ * License Version 1.0 the (the "License";) You may not use
+ * this file except in compliance with the License.  You may
+ * obtain a copy of the License at lib/libc/rpc/LICENSE
+ *
+ * Software distributed under the License is distributed on
+ * an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, either
+ * express or implied.  See the License for the specific
+ * language governing rights and limitations under the License.
+ *
+ * The Original Code is Copyright 1998 by Sun Microsystems, Inc
+ *
+ * The Initial Developer of the Original Code is:  Sun
+ * Microsystems, Inc.
+ *
+ * All Rights Reserved.
+ *
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ *
+ *	from: @(#)clnt.h 1.31 94/04/29 SMI
+ *	from: @(#)clnt.h	2.1 88/07/29 4.0 RPCSRC
+ * $FreeBSD: src/include/rpc/clnt.h,v 1.21 2003/01/24 01:47:55 fjoe Exp $
+ */
+
+/*
+ * clnt.h - Client side remote procedure call interface.
+ *
+ * Copyright (c) 1986-1991,1994-1999 by Sun Microsystems, Inc.
+ * All rights reserved.
+ */
+
+
+#ifndef _RPC_CLNT_H_
+#define _RPC_CLNT_H_
+#include <rpc/clnt_stat.h>
+#include <sys/cdefs.h>
+#include <sys/un.h>
+#include <rpc/auth.h> /* auth_stat */
+
+/*
+ * Error info.
+ */
+struct rpc_err {
+	enum clnt_stat re_status;
+	union {
+		int RE_errno;		/* related system error */
+		enum auth_stat RE_why;	/* why the auth error occurred */
+		struct {
+			rpcvers_t low;	/* lowest version supported */
+			rpcvers_t high;	/* highest version supported */
+		} RE_vers;
+		struct {		/* maybe meaningful if RPC_FAILED */
+			int32_t s1;
+			int32_t s2;
+		} RE_lb;		/* life boot & debugging only */
+	} ru;
+#define	re_errno	ru.RE_errno
+#define	re_why		ru.RE_why
+#define	re_vers		ru.RE_vers
+#define	re_lb		ru.RE_lb
+};
+
+
+/*
+ * Client rpc handle.
+ * Created by individual implementations
+ * Client is responsible for initializing auth, see e.g. auth_none.c.
+ */
+typedef struct __rpc_client {
+	AUTH	*cl_auth;			/* authenticator */
+	struct clnt_ops {
+		/* call remote procedure */
+		enum clnt_stat	(*cl_call)(struct __rpc_client *,
+				    rpcproc_t, xdrproc_t, void *, xdrproc_t,
+				        void *, struct timeval);
+		/* abort a call */
+		void		(*cl_abort)(void);
+		/* get specific error code */
+		void		(*cl_geterr)(struct __rpc_client *,
+					struct rpc_err *);
+		/* frees results */
+		bool_t		(*cl_freeres)(struct __rpc_client *,
+					xdrproc_t, void *);
+		/* destroy this structure */
+		void		(*cl_destroy)(struct __rpc_client *);
+		/* the ioctl() of rpc */
+		bool_t          (*cl_control)(struct __rpc_client *, int,
+					char *);
+	} *cl_ops;
+	void			*cl_private;	/* private stuff */
+} CLIENT;
+
+#define RPCSMALLMSGSIZE	400	/* a more reasonable packet size */
+
+/*
+ * client side rpc interface ops
+ *
+ * Parameter types are:
+ *
+ */
+
+/*
+ * enum clnt_stat
+ * CLNT_CALL(rh, proc, xargs, argsp, xres, resp, timeout)
+ * 	CLIENT *rh;
+ *	rpcproc_t proc;
+ *	xdrproc_t xargs;
+ *	void *argsp;
+ *	xdrproc_t xres;
+ *	void *resp;
+ *	struct timeval timeout;
+ */
+#define	CLNT_CALL(rh, proc, xargs, argsp, xres, resp, secs)	\
+	((*(rh)->cl_ops->cl_call)(rh, proc, xargs, \
+		argsp, xres, resp, secs))
+#define	clnt_call(rh, proc, xargs, argsp, xres, resp, secs)	\
+	((*(rh)->cl_ops->cl_call)(rh, proc, xargs, \
+		argsp, xres, resp, secs))
+
+/*
+ * void
+ * CLNT_ABORT(rh);
+ * 	CLIENT *rh;
+ */
+#define	CLNT_ABORT(rh)	((*(rh)->cl_ops->cl_abort)(rh))
+#define	clnt_abort(rh)	((*(rh)->cl_ops->cl_abort)(rh))
+
+/*
+ * struct rpc_err
+ * CLNT_GETERR(rh);
+ * 	CLIENT *rh;
+ */
+#define	CLNT_GETERR(rh,errp)	((*(rh)->cl_ops->cl_geterr)(rh, errp))
+#define	clnt_geterr(rh,errp)	((*(rh)->cl_ops->cl_geterr)(rh, errp))
+
+
+/*
+ * bool_t
+ * CLNT_FREERES(rh, xres, resp);
+ * 	CLIENT *rh;
+ *	xdrproc_t xres;
+ *	void *resp;
+ */
+#define	CLNT_FREERES(rh,xres,resp) ((*(rh)->cl_ops->cl_freeres)(rh,xres,resp))
+#define	clnt_freeres(rh,xres,resp) ((*(rh)->cl_ops->cl_freeres)(rh,xres,resp))
+
+/*
+ * bool_t
+ * CLNT_CONTROL(cl, request, info)
+ *      CLIENT *cl;
+ *      u_int request;
+ *      char *info;
+ */
+#define	CLNT_CONTROL(cl,rq,in) ((*(cl)->cl_ops->cl_control)(cl,rq,in))
+#define	clnt_control(cl,rq,in) ((*(cl)->cl_ops->cl_control)(cl,rq,in))
+
+/*
+ * control operations that apply to udp, tcp and unix transports
+ *
+ * Note: options marked XXX are no-ops in this implementation of RPC.
+ * The are present in TI-RPC but can't be implemented here since they
+ * depend on the presence of STREAMS/TLI, which we don't have.
+ *
+ */
+#define CLSET_TIMEOUT       1   /* set timeout (timeval) */
+#define CLGET_TIMEOUT       2   /* get timeout (timeval) */
+#define CLGET_SERVER_ADDR   3   /* get server's address (sockaddr) */
+#define CLGET_FD            6	/* get connections file descriptor */
+#define CLGET_SVC_ADDR      7   /* get server's address (netbuf) */
+#define CLSET_FD_CLOSE      8   /* close fd while clnt_destroy */
+#define CLSET_FD_NCLOSE     9   /* Do not close fd while clnt_destroy */
+#define CLGET_XID           10	/* Get xid */
+#define CLSET_XID           11	/* Set xid */
+#define CLGET_VERS          12	/* Get version number */
+#define CLSET_VERS          13	/* Set version number */
+#define CLGET_PROG	    14	/* Get program number */
+#define CLSET_PROG          15	/* Set program number */
+#define CLSET_SVC_ADDR      16	/* get server's address (netbuf)         XXX */
+#define CLSET_PUSH_TIMOD    17	/* push timod if not already present     XXX */
+#define CLSET_POP_TIMOD     18	/* pop timod                             XXX */
+
+/*
+ * Connectionless only control operations
+ */
+#define CLSET_RETRY_TIMEOUT 4   /* set retry timeout (timeval) */
+#define CLGET_RETRY_TIMEOUT 5   /* get retry timeout (timeval) */
+
+/*
+ * Operations which GSSAPI needs. (Bletch.)
+ */
+#define CLGET_LOCAL_ADDR    19	/* get local addr (sockaddr) */
+
+
+/*
+ * void
+ * CLNT_DESTROY(rh);
+ * 	CLIENT *rh;
+ */
+#define	CLNT_DESTROY(rh)	((*(rh)->cl_ops->cl_destroy)(rh))
+#define	clnt_destroy(rh)	((*(rh)->cl_ops->cl_destroy)(rh))
+
+
+/*
+ * RPCTEST is a test program which is accessible on every rpc
+ * transport/port.  It is used for testing, performance evaluation,
+ * and network administration.
+ */
+
+#define RPCTEST_PROGRAM		((rpcprog_t)1)
+#define RPCTEST_VERSION		((rpcvers_t)1)
+#define RPCTEST_NULL_PROC	((rpcproc_t)2)
+#define RPCTEST_NULL_BATCH_PROC	((rpcproc_t)3)
+
+/*
+ * By convention, procedure 0 takes null arguments and returns them
+ */
+
+#define NULLPROC ((rpcproc_t)0)
+
+/*
+ * Below are the client handle creation routines for the various
+ * implementations of client side rpc.  They can return NULL if a
+ * creation failure occurs.
+ */
+
+/*
+ * Generic client creation routine. Supported protocols are "udp", "tcp"
+ * and "unix".
+ */
+__BEGIN_DECLS
+extern CLIENT *clnt_create(const char *, const rpcprog_t, const rpcvers_t,
+	const char *);
+__END_DECLS
+
+/*
+ * Added for compatibility to old rpc 4.0. Obsoleted by clnt_vc_create().
+ */
+__BEGIN_DECLS
+extern CLIENT *clntunix_create(struct sockaddr_un *,
+			       u_long, u_long, int *, u_int, u_int);
+__END_DECLS
+
+
+/*
+ * Print why creation failed
+ */
+__BEGIN_DECLS
+extern void clnt_pcreateerror(const char *);			/* stderr */
+extern char *clnt_spcreateerror(const char *);		/* string */
+__END_DECLS
+
+/*
+ * Like clnt_perror(), but is more verbose in its output
+ */
+__BEGIN_DECLS
+extern void clnt_perrno(enum clnt_stat);		/* stderr */
+extern char *clnt_sperrno(enum clnt_stat);		/* string */
+__END_DECLS
+
+/*
+ * Print an English error message, given the client error code
+ */
+__BEGIN_DECLS
+extern void clnt_perror(CLIENT *, const char *); 		/* stderr */
+extern char *clnt_sperror(CLIENT *, const char *);		/* string */
+__END_DECLS
+
+
+/*
+ * If a creation fails, the following allows the user to figure out why.
+ */
+struct rpc_createerr {
+	enum clnt_stat cf_stat;
+	struct rpc_err cf_error; /* useful when cf_stat == RPC_PMAPFAILURE */
+};
+
+extern struct rpc_createerr rpc_createerr;
+
+/* For backward compatibility */
+#include <rpc/clnt_soc.h>
+
+#endif /* !_RPC_CLNT_H_ */
diff --git a/services/librpc/include/rpc/clnt_soc.h b/services/librpc/include/rpc/clnt_soc.h
new file mode 100644
index 0000000..9aa99b8
--- /dev/null
+++ b/services/librpc/include/rpc/clnt_soc.h
@@ -0,0 +1,109 @@
+/*	$NetBSD: clnt_soc.h,v 1.1 2000/06/02 22:57:55 fvdl Exp $	*/
+/*	$FreeBSD: src/include/rpc/clnt_soc.h,v 1.2 2002/03/23 17:24:55 imp Exp $ */
+
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+/*
+ * Copyright (c) 1984 - 1991 by Sun Microsystems, Inc.
+ */
+
+/*
+ * clnt.h - Client side remote procedure call interface.
+ */
+
+#ifndef _RPC_CLNT_SOC_H
+#define _RPC_CLNT_SOC_H
+
+#include <time.h>
+
+/* derived from clnt_soc.h 1.3 88/12/17 SMI     */
+
+/*
+ * All the following declarations are only for backward compatibility
+ * with TS-RPC.
+ */
+
+#include <sys/cdefs.h>
+#include <rpc/clnt.h>
+
+#define UDPMSGSIZE      8800    /* rpc imposed limit on udp msg size */  
+
+/*
+ * TCP based rpc
+ * CLIENT *
+ * clnttcp_create(raddr, prog, vers, sockp, sendsz, recvsz)
+ *	struct sockaddr_in *raddr;
+ *	u_long prog;
+ *	u_long version;
+ *	register int *sockp;
+ *	u_int sendsz;
+ *	u_int recvsz;
+ */
+__BEGIN_DECLS
+extern CLIENT *clnttcp_create(struct sockaddr_in *, u_long, u_long, int *,
+				u_int, u_int);
+__END_DECLS
+
+/*
+ * Raw (memory) rpc.
+ */
+__BEGIN_DECLS
+extern CLIENT *clntraw_create(u_long, u_long);
+__END_DECLS
+
+
+/*
+ * UDP based rpc.
+ * CLIENT *
+ * clntudp_create(raddr, program, version, wait, sockp)
+ *	struct sockaddr_in *raddr;
+ *	u_long program;
+ *	u_long version;
+ *	struct timeval wait;
+ *	int *sockp;
+ *
+ * Same as above, but you specify max packet sizes.
+ * CLIENT *
+ * clntudp_bufcreate(raddr, program, version, wait, sockp, sendsz, recvsz)
+ *	struct sockaddr_in *raddr;
+ *	u_long program;
+ *	u_long version;
+ *	struct timeval wait;
+ *	int *sockp;
+ *	u_int sendsz;
+ *	u_int recvsz;
+ */
+__BEGIN_DECLS
+extern CLIENT *clntudp_create(struct sockaddr_in *, u_long, u_long,
+				     struct timeval, int *);
+extern CLIENT *clntudp_bufcreate(struct sockaddr_in *, u_long, u_long,
+				     struct timeval, int *, u_int, u_int);
+__END_DECLS
+
+#endif /* _RPC_CLNT_SOC_H */
diff --git a/services/librpc/include/rpc/clnt_stat.h b/services/librpc/include/rpc/clnt_stat.h
new file mode 100644
index 0000000..2c68745
--- /dev/null
+++ b/services/librpc/include/rpc/clnt_stat.h
@@ -0,0 +1,84 @@
+/*	$FreeBSD: src/include/rpc/clnt_stat.h,v 1.2 2001/03/20 08:20:50 alfred Exp $ */
+/*
+ * Copyright (c) 1986 - 1991, 1994, 1996, 1997 by Sun Microsystems, Inc.
+ * All rights reserved.
+ */
+
+/*
+ * clnt_stat.h - Client side remote procedure call enum
+ *
+ */
+
+#ifndef	_RPC_CLNT_STAT_H
+#define	_RPC_CLNT_STAT_H
+
+/* #pragma ident	"@(#)clnt_stat.h	1.2	97/04/28 SMI" */
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+enum clnt_stat {
+	RPC_SUCCESS = 0,			/* call succeeded */
+	/*
+	 * local errors
+	 */
+	RPC_CANTENCODEARGS = 1,		/* can't encode arguments */
+	RPC_CANTDECODERES = 2,		/* can't decode results */
+	RPC_CANTSEND = 3,			/* failure in sending call */
+	RPC_CANTRECV = 4,
+	/* failure in receiving result */
+	RPC_TIMEDOUT = 5,			/* call timed out */
+	RPC_INTR = 18,			/* call interrupted */
+	RPC_UDERROR = 23,			/* recv got uderr indication */
+	/*
+	 * remote errors
+	 */
+	RPC_VERSMISMATCH = 6,		/* rpc versions not compatible */
+	RPC_AUTHERROR = 7,		/* authentication error */
+	RPC_PROGUNAVAIL = 8,		/* program not available */
+	RPC_PROGVERSMISMATCH = 9,	/* program version mismatched */
+	RPC_PROCUNAVAIL = 10,		/* procedure unavailable */
+	RPC_CANTDECODEARGS = 11,		/* decode arguments error */
+	RPC_SYSTEMERROR = 12,		/* generic "other problem" */
+
+	/*
+	 * rpc_call & clnt_create errors
+	 */
+	RPC_UNKNOWNHOST = 13,		/* unknown host name */
+	RPC_UNKNOWNPROTO = 17,		/* unknown protocol */
+	RPC_UNKNOWNADDR = 19,		/* Remote address unknown */
+	RPC_NOBROADCAST = 21,		/* Broadcasting not supported */
+
+	/*
+	 * rpcbind errors
+	 */
+	RPC_RPCBFAILURE = 14,		/* the pmapper failed in its call */
+#define	RPC_PMAPFAILURE RPC_RPCBFAILURE
+	RPC_PROGNOTREGISTERED = 15,	/* remote program is not registered */
+	RPC_N2AXLATEFAILURE = 22,
+	/* Name to address translation failed */
+	/*
+	 * Misc error in the TLI library
+	 */
+	RPC_TLIERROR = 20,
+	/*
+	 * unspecified error
+	 */
+	RPC_FAILED = 16,
+	/*
+	 * asynchronous errors
+	 */
+	RPC_INPROGRESS = 24,
+	RPC_STALERACHANDLE = 25,
+	RPC_CANTCONNECT = 26,		/* couldn't make connection (cots) */
+	RPC_XPRTFAILED = 27,		/* received discon from remote (cots) */
+	RPC_CANTCREATESTREAM = 28,	/* can't push rpc module (cots) */
+	_CLNT_STAT = 0xffffffff
+};
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif	/* !_RPC_CLNT_STAT_H */
diff --git a/services/librpc/include/rpc/pmap_clnt.h b/services/librpc/include/rpc/pmap_clnt.h
new file mode 100644
index 0000000..86fff6b
--- /dev/null
+++ b/services/librpc/include/rpc/pmap_clnt.h
@@ -0,0 +1,89 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ *
+ *	from: @(#)pmap_clnt.h 1.11 88/02/08 SMI
+ *	from: @(#)pmap_clnt.h	2.1 88/07/29 4.0 RPCSRC
+ * $FreeBSD: src/include/rpc/pmap_clnt.h,v 1.11 1999/08/27 23:45:04 peter Exp $
+ */
+
+/*
+ * pmap_clnt.h
+ * Supplies C routines to get to portmap services.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+/*
+ * Usage:
+ *	success = pmap_set(program, version, protocol, port);
+ *	success = pmap_unset(program, version);
+ *	port = pmap_getport(address, program, version, protocol);
+ *	head = pmap_getmaps(address);
+ *	clnt_stat = pmap_rmtcall(address, program, version, procedure,
+ *		xdrargs, argsp, xdrres, resp, tout, port_ptr)
+ *		(works for udp only.)
+ * 	clnt_stat = clnt_broadcast(program, version, procedure,
+ *		xdrargs, argsp,	xdrres, resp, eachresult)
+ *		(like pmap_rmtcall, except the call is broadcasted to all
+ *		locally connected nets.  For each valid response received,
+ *		the procedure eachresult is called.  Its form is:
+ *	done = eachresult(resp, raddr)
+ *		bool_t done;
+ *		caddr_t resp;
+ *		struct sockaddr_in raddr;
+ *		where resp points to the results of the call and raddr is the
+ *		address if the responder to the broadcast.
+ */
+
+#ifndef _RPC_PMAPCLNT_H
+#define _RPC_PMAPCLNT_H
+
+#include <sys/cdefs.h>
+#include <netinet/in.h> /* struct sockaddr_in */
+#include <rpc/types.h>
+#include <rpc/xdr.h> /* xdrproc_t */
+
+__BEGIN_DECLS
+extern bool_t		pmap_set	(u_long, u_long, int, int);
+extern bool_t		pmap_unset	(u_long, u_long);
+extern struct pmaplist	*pmap_getmaps	(struct sockaddr_in *);
+extern enum clnt_stat	pmap_rmtcall	(struct sockaddr_in *,
+					     u_long, u_long, u_long,
+					     xdrproc_t, caddr_t,
+					     xdrproc_t, caddr_t,
+					     struct timeval, u_long *);
+extern enum clnt_stat	clnt_broadcast	(u_long, u_long, u_long,
+					     xdrproc_t, char *,
+					     xdrproc_t, char *,
+					     bool_t (*) (caddr_t,
+						 struct sockaddr_in *));
+extern u_short		pmap_getport	(struct sockaddr_in *,
+					     u_long, u_long, u_int);
+__END_DECLS
+
+#endif /* !_RPC_PMAPCLNT_H */
diff --git a/services/librpc/include/rpc/pmap_prot.h b/services/librpc/include/rpc/pmap_prot.h
new file mode 100644
index 0000000..14720e8
--- /dev/null
+++ b/services/librpc/include/rpc/pmap_prot.h
@@ -0,0 +1,105 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ *
+ *	from: @(#)pmap_prot.h 1.14 88/02/08 SMI
+ *	from: @(#)pmap_prot.h	2.1 88/07/29 4.0 RPCSRC
+ * $FreeBSD: src/include/rpc/pmap_prot.h,v 1.10 1999/08/27 23:45:04 peter Exp $
+ */
+
+/*
+ * pmap_prot.h
+ * Protocol for the local binder service, or pmap.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ *
+ * The following procedures are supported by the protocol:
+ *
+ * PMAPPROC_NULL() returns ()
+ * 	takes nothing, returns nothing
+ *
+ * PMAPPROC_SET(struct pmap) returns (bool_t)
+ * 	TRUE is success, FALSE is failure.  Registers the tuple
+ *	[prog, vers, prot, port].
+ *
+ * PMAPPROC_UNSET(struct pmap) returns (bool_t)
+ *	TRUE is success, FALSE is failure.  Un-registers pair
+ *	[prog, vers].  prot and port are ignored.
+ *
+ * PMAPPROC_GETPORT(struct pmap) returns (long unsigned).
+ *	0 is failure.  Otherwise returns the port number where the pair
+ *	[prog, vers] is registered.  It may lie!
+ *
+ * PMAPPROC_DUMP() RETURNS (struct pmaplist *)
+ *
+ * PMAPPROC_CALLIT(unsigned, unsigned, unsigned, string<>)
+ * 	RETURNS (port, string<>);
+ * usage: encapsulatedresults = PMAPPROC_CALLIT(prog, vers, proc, encapsulatedargs);
+ * 	Calls the procedure on the local machine.  If it is not registered,
+ *	this procedure is quite; ie it does not return error information!!!
+ *	This procedure only is supported on rpc/udp and calls via
+ *	rpc/udp.  This routine only passes null authentication parameters.
+ *	This file has no interface to xdr routines for PMAPPROC_CALLIT.
+ *
+ * The service supports remote procedure calls on udp/ip or tcp/ip socket 111.
+ */
+
+#ifndef _RPC_PMAPPROT_H
+#define _RPC_PMAPPROT_H
+#include <sys/cdefs.h>
+#include <rpc/xdr.h>
+
+#define PMAPPORT		((u_short)111)
+#define PMAPPROG		((u_long)100000)
+#define PMAPVERS		((u_long)2)
+#define PMAPVERS_PROTO		((u_long)2)
+#define PMAPVERS_ORIG		((u_long)1)
+#define PMAPPROC_NULL		((u_long)0)
+#define PMAPPROC_SET		((u_long)1)
+#define PMAPPROC_UNSET		((u_long)2)
+#define PMAPPROC_GETPORT	((u_long)3)
+#define PMAPPROC_DUMP		((u_long)4)
+#define PMAPPROC_CALLIT		((u_long)5)
+
+struct pmap {
+	long unsigned pm_prog;
+	long unsigned pm_vers;
+	long unsigned pm_prot;
+	long unsigned pm_port;
+};
+
+struct pmaplist {
+	struct pmap	pml_map;
+	struct pmaplist *pml_next;
+};
+
+__BEGIN_DECLS
+extern bool_t xdr_pmap		(XDR *, struct pmap *);
+extern bool_t xdr_pmaplist	(XDR *, struct pmaplist **);
+__END_DECLS
+
+#endif /* !_RPC_PMAPPROT_H */
diff --git a/services/librpc/include/rpc/pmap_rmt.h b/services/librpc/include/rpc/pmap_rmt.h
new file mode 100644
index 0000000..a5ea404
--- /dev/null
+++ b/services/librpc/include/rpc/pmap_rmt.h
@@ -0,0 +1,64 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ *
+ *	from: @(#)pmap_rmt.h 1.2 88/02/08 SMI
+ *	from: @(#)pmap_rmt.h	2.1 88/07/29 4.0 RPCSRC
+ * $FreeBSD: src/include/rpc/pmap_rmt.h,v 1.10 1999/08/27 23:45:05 peter Exp $
+ */
+
+/*
+ * Structures and XDR routines for parameters to and replies from
+ * the portmapper remote-call-service.
+ *
+ * Copyright (C) 1986, Sun Microsystems, Inc.
+ */
+
+#ifndef _RPC_PMAPRMT_H
+#define _RPC_PMAPRMT_H
+#include <sys/cdefs.h>
+#include <rpc/xdr.h>
+
+struct rmtcallargs {
+	u_long prog, vers, proc, arglen;
+	caddr_t args_ptr;
+	xdrproc_t xdr_args;
+};
+
+struct rmtcallres {
+	u_long *port_ptr;
+	u_long resultslen;
+	caddr_t results_ptr;
+	xdrproc_t xdr_results;
+};
+
+__BEGIN_DECLS
+extern bool_t xdr_rmtcall_args	(XDR *, struct rmtcallargs *);
+extern bool_t xdr_rmtcallres	(XDR *, struct rmtcallres *);
+__END_DECLS
+
+#endif /* !_RPC_PMAPRMT_H */
diff --git a/services/librpc/include/rpc/rpc.h b/services/librpc/include/rpc/rpc.h
new file mode 100644
index 0000000..95df085
--- /dev/null
+++ b/services/librpc/include/rpc/rpc.h
@@ -0,0 +1,116 @@
+/*	$NetBSD: rpc.h,v 1.13 2000/06/02 22:57:56 fvdl Exp $	*/
+
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ *
+ *	from: @(#)rpc.h 1.9 88/02/08 SMI
+ *	from: @(#)rpc.h	2.4 89/07/11 4.0 RPCSRC
+ * $FreeBSD: src/include/rpc/rpc.h,v 1.17 2002/03/23 17:24:55 imp Exp $
+ */
+
+/*
+ * rpc.h, Just includes the billions of rpc header files necessary to
+ * do remote procedure calling.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+#ifndef _RPC_RPC_H
+#define _RPC_RPC_H
+
+#include <rpc/types.h>		/* some typedefs */
+#include <netinet/in.h>
+
+/* external data representation interfaces */
+#include <rpc/xdr.h>		/* generic (de)serializer */
+
+/* Client side only authentication */
+#include <rpc/auth.h>		/* generic authenticator (client side) */
+
+/* Client side (mostly) remote procedure call */
+#include <rpc/clnt.h>		/* generic rpc stuff */
+
+/* semi-private protocol headers */
+#include <rpc/rpc_msg.h>	/* protocol for rpc messages */
+#include <rpc/auth_unix.h>	/* protocol for unix style cred */
+
+/* Server side only remote procedure callee */
+#include <rpc/svc.h>		/* service manager and multiplexer */
+#include <rpc/svc_auth.h>	/* service side authenticator */
+
+#include <rpc/rpcent.h>
+
+__BEGIN_DECLS
+extern int get_myaddress(struct sockaddr_in *);
+extern int bindresvport(int, struct sockaddr_in *);
+extern int bindresvport_sa(int, struct sockaddr *);
+__END_DECLS
+
+int rtems_rpc_task_init (void);
+int rtems_rpc_start_portmapper (int priority);
+
+#ifdef _RTEMS_RPC_INTERNAL_
+/*
+ * Multi-threaded support
+ * Group all global and static variables into a single spot.
+ * This area will be allocated on a per-task basis
+ */
+struct _rtems_rpc_task_variables {
+	int		svc_svc_maxfd;
+	fd_set		svc_svc_fdset;
+	SVCXPRT **	svc_xports;
+	int		svc_xportssize;
+	int		svc__svc_fdsetsize;
+	fd_set		*svc__svc_fdset;
+	struct svc_callout	*svc_svc_head;
+
+	char		*clnt_perror_buf;
+
+	struct clnt_raw_private *clnt_raw_private;
+
+	void		*call_rpc_private;
+
+	struct call_rpc_private *svc_raw_private;
+
+	struct prog_lst *svc_simple_proglst;
+	struct prog_lst *svc_simple_pl;
+	SVCXPRT		*svc_simple_transp;
+
+	char		*rpcdname_default_domain;
+
+	struct authsvc *svc_auths_Auths;
+};
+extern struct _rtems_rpc_task_variables *rtems_rpc_task_variables;
+
+#define svc_maxfd (rtems_rpc_task_variables->svc_svc_maxfd)
+#define svc_fdset (rtems_rpc_task_variables->svc_svc_fdset)
+#define __svc_fdsetsize (rtems_rpc_task_variables->svc__svc_fdsetsize)
+#define __svc_fdset (rtems_rpc_task_variables->svc__svc_fdset)
+
+#endif /* _RTEMS_RPC_INTERNAL_ */
+
+#endif /* !_RPC_RPC_H */
diff --git a/services/librpc/include/rpc/rpc_com.h b/services/librpc/include/rpc/rpc_com.h
new file mode 100644
index 0000000..9a1ce45
--- /dev/null
+++ b/services/librpc/include/rpc/rpc_com.h
@@ -0,0 +1,65 @@
+/*	$NetBSD: rpc_com.h,v 1.3 2000/12/10 04:10:08 christos Exp $	*/
+/*	$FreeBSD: src/include/rpc/rpc_com.h,v 1.6 2003/01/16 07:13:51 mbr Exp $ */
+
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+/*
+ * Copyright (c) 1986 - 1991 by Sun Microsystems, Inc.
+ */
+ 
+/*
+ * rpc_com.h, Common definitions for both the server and client side.
+ * All for the topmost layer of rpc
+ *
+ */
+
+#ifndef _RPC_RPCCOM_H
+#define	_RPC_RPCCOM_H
+
+#include <sys/cdefs.h>
+
+/* #pragma ident	"@(#)rpc_com.h	1.11	93/07/05 SMI" */
+
+/*
+ * The max size of the transport, if the size cannot be determined
+ * by other means.
+ */
+#define	RPC_MAXDATASIZE 9000
+#define	RPC_MAXADDRSIZE 1024
+
+__BEGIN_DECLS
+extern u_int __rpc_get_a_size(int);
+extern u_int __rpc_get_t_size(int, long);
+extern int __rpc_dtbsize(void);
+extern int _rpc_dtablesize(void);
+extern  int  _rpc_get_default_domain(char **);
+__END_DECLS
+
+#endif /* _RPC_RPCCOM_H */
diff --git a/services/librpc/include/rpc/rpc_msg.h b/services/librpc/include/rpc/rpc_msg.h
new file mode 100644
index 0000000..63a1f36
--- /dev/null
+++ b/services/librpc/include/rpc/rpc_msg.h
@@ -0,0 +1,205 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ *
+ *	from: @(#)rpc_msg.h 1.7 86/07/16 SMI
+ *	from: @(#)rpc_msg.h	2.1 88/07/29 4.0 RPCSRC
+ * $FreeBSD: src/include/rpc/rpc_msg.h,v 1.15 2003/01/01 18:48:42 schweikh Exp $
+ */
+
+/*
+ * rpc_msg.h
+ * rpc message definition
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifndef _RPC_RPC_MSG_H
+#define _RPC_RPC_MSG_H
+
+#include <rpc/types.h>
+#include <rpc/xdr.h> /* xdrproc_t */
+#include <rpc/auth.h> /* opaque_auth */
+
+struct rpc_err; /* forward */
+
+#define RPC_MSG_VERSION		((u_int32_t) 2)
+#define RPC_SERVICE_PORT	((u_short) 2048)
+
+/*
+ * Bottom up definition of an rpc message.
+ * NOTE: call and reply use the same overall stuct but
+ * different parts of unions within it.
+ */
+
+enum msg_type {
+	CALL=0,
+	REPLY=1,
+	_MSG_TYPE = 0xffffffff
+};
+
+enum reply_stat {
+	MSG_ACCEPTED=0,
+	MSG_DENIED=1,
+	_REPLY_STAT = 0xffffffff
+};
+
+enum accept_stat {
+	SUCCESS=0,
+	PROG_UNAVAIL=1,
+	PROG_MISMATCH=2,
+	PROC_UNAVAIL=3,
+	GARBAGE_ARGS=4,
+	SYSTEM_ERR=5,
+	_ACCEPT_STAT = 0xffffffff
+};
+
+enum reject_stat {
+	RPC_MISMATCH=0,
+	AUTH_ERROR=1,
+	_REJECT_STAT = 0xffffffff
+};
+
+/*
+ * Reply part of an rpc exchange
+ */
+
+/*
+ * Reply to an rpc request that was accepted by the server.
+ * Note: there could be an error even though the request was
+ * accepted.
+ */
+struct accepted_reply {
+	struct opaque_auth	ar_verf;
+	enum accept_stat	ar_stat;
+	union {
+		struct {
+			rpcvers_t low;
+			rpcvers_t high;
+		} AR_versions;
+		struct {
+			caddr_t	where;
+			xdrproc_t proc;
+		} AR_results;
+		/* and many other null cases */
+	} ru;
+#define	ar_results	ru.AR_results
+#define	ar_vers		ru.AR_versions
+};
+
+/*
+ * Reply to an rpc request that was rejected by the server.
+ */
+struct rejected_reply {
+	enum reject_stat rj_stat;
+	union {
+		struct {
+			rpcvers_t low;
+			rpcvers_t high;
+		} RJ_versions;
+		enum auth_stat RJ_why;  /* why authentication did not work */
+	} ru;
+#define	rj_vers	ru.RJ_versions
+#define	rj_why	ru.RJ_why
+};
+
+/*
+ * Body of a reply to an rpc request.
+ */
+struct reply_body {
+	enum reply_stat rp_stat;
+	union {
+		struct accepted_reply RP_ar;
+		struct rejected_reply RP_dr;
+	} ru;
+#define	rp_acpt	ru.RP_ar
+#define	rp_rjct	ru.RP_dr
+};
+
+/*
+ * Body of an rpc request call.
+ */
+struct call_body {
+	rpcvers_t cb_rpcvers;	/* must be equal to two */
+	rpcprog_t cb_prog;
+	rpcvers_t cb_vers;
+	rpcproc_t cb_proc;
+	struct opaque_auth cb_cred;
+	struct opaque_auth cb_verf; /* protocol specific - provided by client */
+};
+
+/*
+ * The rpc message
+ */
+struct rpc_msg {
+	u_int32_t		rm_xid;
+	enum msg_type		rm_direction;
+	union {
+		struct call_body RM_cmb;
+		struct reply_body RM_rmb;
+	} ru;
+#define	rm_call		ru.RM_cmb
+#define	rm_reply	ru.RM_rmb
+};
+#define	acpted_rply	ru.RM_rmb.ru.RP_ar
+#define	rjcted_rply	ru.RM_rmb.ru.RP_dr
+
+__BEGIN_DECLS
+/*
+ * XDR routine to handle a rpc message.
+ * xdr_callmsg(xdrs, cmsg)
+ * 	XDR *xdrs;
+ * 	struct rpc_msg *cmsg;
+ */
+extern bool_t	xdr_callmsg(XDR *, struct rpc_msg *);
+
+/*
+ * XDR routine to pre-serialize the static part of a rpc message.
+ * xdr_callhdr(xdrs, cmsg)
+ * 	XDR *xdrs;
+ * 	struct rpc_msg *cmsg;
+ */
+extern bool_t	xdr_callhdr(XDR *, struct rpc_msg *);
+
+/*
+ * XDR routine to handle a rpc reply.
+ * xdr_replymsg(xdrs, rmsg)
+ * 	XDR *xdrs;
+ * 	struct rpc_msg *rmsg;
+ */
+extern bool_t	xdr_replymsg(XDR *, struct rpc_msg *);
+
+/*
+ * Fills in the error part of a reply message.
+ * _seterr_reply(msg, error)
+ * 	struct rpc_msg *msg;
+ * 	struct rpc_err *error;
+ */
+extern void	_seterr_reply(struct rpc_msg *, struct rpc_err *);
+__END_DECLS
+
+#endif /* !_RPC_RPC_MSG_H */
diff --git a/services/librpc/include/rpc/rpcent.h b/services/librpc/include/rpc/rpcent.h
new file mode 100644
index 0000000..1cf4161
--- /dev/null
+++ b/services/librpc/include/rpc/rpcent.h
@@ -0,0 +1,71 @@
+/*	$NetBSD: rpcent.h,v 1.1 2000/06/02 22:57:56 fvdl Exp $	*/
+/*	$FreeBSD: src/include/rpc/rpcent.h,v 1.2 2002/03/23 17:24:55 imp Exp $ */
+
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+/*
+ * Copyright (c) 1986 - 1991 by Sun Microsystems, Inc.
+ */
+
+/*
+ * rpcent.h,
+ * For converting rpc program numbers to names etc.
+ *
+ */
+
+#ifndef _RPC_RPCENT_H
+#define _RPC_RPCENT_H
+
+#include <sys/cdefs.h>
+
+/*	#pragma ident "@(#)rpcent.h   1.13    94/04/25 SMI"	*/
+/*      @(#)rpcent.h 1.1 88/12/06 SMI   */
+
+
+struct rpcent {
+      char    *r_name;        /* name of server for this rpc program */
+      char    **r_aliases;    /* alias list */
+      int     r_number;       /* rpc program number */
+};
+
+__BEGIN_DECLS
+extern struct rpcent *getrpcbyname_r(const char *, struct rpcent *,
+				     char *, int);
+extern struct rpcent *getrpcbynumber_r(int, struct rpcent *, char *, int);
+extern struct rpcent *getrpcent_r(struct rpcent *, char *, int);
+
+/* Old interfaces that return a pointer to a static area;  MT-unsafe */
+extern struct rpcent *getrpcbyname(char *);
+extern struct rpcent *getrpcbynumber(int);
+extern struct rpcent *getrpcent(void);
+extern void setrpcent(int);
+extern void endrpcent(void);
+__END_DECLS
+
+#endif /* !_RPC_CENT_H */
diff --git a/services/librpc/include/rpc/svc.h b/services/librpc/include/rpc/svc.h
new file mode 100644
index 0000000..0ef3b8c
--- /dev/null
+++ b/services/librpc/include/rpc/svc.h
@@ -0,0 +1,296 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ *
+ *	from: @(#)svc.h 1.35 88/12/17 SMI
+ *	from: @(#)svc.h      1.27    94/04/25 SMI
+ * $FreeBSD: src/include/rpc/svc.h,v 1.24 2003/06/15 10:32:01 mbr Exp $
+ */
+
+/*
+ * svc.h, Server-side remote procedure call interface.
+ *
+ * Copyright (C) 1986-1993 by Sun Microsystems, Inc.
+ */
+
+#ifndef _RPC_SVC_H
+#define _RPC_SVC_H
+
+#include <sys/cdefs.h>
+#include <rpc/types.h>
+#include <rpc/xdr.h> /* xdrproc_t */
+#include <sys/socket.h> /* socklen_t */
+#include <netinet/in.h> /* struct sockaddr_in */
+#include <rpc/auth.h> /* auth_stat */
+
+/*
+ * This interface must manage two items concerning remote procedure calling:
+ *
+ * 1) An arbitrary number of transport connections upon which rpc requests
+ * are received.  The two most notable transports are TCP and UDP;  they are
+ * created and registered by routines in svc_tcp.c and svc_udp.c, respectively;
+ * they in turn call xprt_register and xprt_unregister.
+ *
+ * 2) An arbitrary number of locally registered services.  Services are
+ * described by the following four data: program number, version number,
+ * "service dispatch" function, a transport handle, and a boolean that
+ * indicates whether or not the exported program should be registered with a
+ * local binder service;  if true the program's number and version and the
+ * port number from the transport handle are registered with the binder.
+ * These data are registered with the rpc svc system via svc_register.
+ *
+ * A service's dispatch function is called whenever an rpc request comes in
+ * on a transport.  The request's program and version numbers must match
+ * those of the registered service.  The dispatch function is passed two
+ * parameters, struct svc_req * and SVCXPRT *, defined below.
+ */
+
+enum xprt_stat {
+	XPRT_DIED,
+	XPRT_MOREREQS,
+	XPRT_IDLE,
+	_XPRT_STAT = 0xffffffff
+};
+
+struct rpc_msg;
+
+/*
+ * Server side transport handle
+ */
+typedef struct __rpc_svcxprt {
+	int		xp_sock;
+	u_short		xp_port;	 /* associated port number */
+	struct xp_ops {
+	    /* receive incoming requests */
+	    bool_t	(*xp_recv)(struct __rpc_svcxprt *, struct rpc_msg *);
+	    /* get transport status */
+	    enum xprt_stat (*xp_stat)(struct __rpc_svcxprt *);
+	    /* get arguments */
+	    bool_t	(*xp_getargs)(struct __rpc_svcxprt *, xdrproc_t,
+				caddr_t args_ptr);
+	    /* send reply */
+	    bool_t	(*xp_reply)(struct __rpc_svcxprt *, struct rpc_msg *);
+	    /* free mem allocated for args */
+	    bool_t	(*xp_freeargs)(struct __rpc_svcxprt *, xdrproc_t,
+				caddr_t args_ptr);
+	    /* destroy this struct */
+	    void	(*xp_destroy)(struct __rpc_svcxprt *);
+	} *xp_ops;
+	socklen_t	xp_addrlen;	 /* length of remote address */
+	struct sockaddr_in xp_raddr;	 /* remote addr. (backward ABI compat) */
+	struct opaque_auth xp_verf;	 /* raw response verifier */
+	void		*xp_p1;		 /* private: for use by svc ops */
+	void		*xp_p2;		 /* private: for use by svc ops */
+} SVCXPRT;
+
+/*
+ * Service request
+ */
+struct svc_req {
+	u_int32_t	rq_prog;	/* service program number */
+	u_int32_t	rq_vers;	/* service protocol version */
+	u_int32_t	rq_proc;	/* the desired procedure */
+	struct opaque_auth rq_cred;	/* raw creds from the wire */
+	caddr_t		rq_clntcred;	/* read only cooked cred */
+	SVCXPRT		*rq_xprt;	/* associated transport */
+};
+
+
+/*
+ * Operations defined on an SVCXPRT handle
+ *
+ * SVCXPRT		*xprt;
+ * struct rpc_msg	*msg;
+ * xdrproc_t		 xargs;
+ * caddr_t		 argsp;
+ */
+#define SVC_RECV(xprt, msg)				\
+	(*(xprt)->xp_ops->xp_recv)((xprt), (msg))
+#define svc_recv(xprt, msg)				\
+	(*(xprt)->xp_ops->xp_recv)((xprt), (msg))
+
+#define SVC_STAT(xprt)					\
+	(*(xprt)->xp_ops->xp_stat)(xprt)
+#define svc_stat(xprt)					\
+	(*(xprt)->xp_ops->xp_stat)(xprt)
+
+#define SVC_GETARGS(xprt, xargs, argsp)			\
+	(*(xprt)->xp_ops->xp_getargs)((xprt), (xargs), (argsp))
+#define svc_getargs(xprt, xargs, argsp)			\
+	(*(xprt)->xp_ops->xp_getargs)((xprt), (xargs), (argsp))
+
+#define SVC_REPLY(xprt, msg)				\
+	(*(xprt)->xp_ops->xp_reply) ((xprt), (msg))
+#define svc_reply(xprt, msg)				\
+	(*(xprt)->xp_ops->xp_reply) ((xprt), (msg))
+
+#define SVC_FREEARGS(xprt, xargs, argsp)		\
+	(*(xprt)->xp_ops->xp_freeargs)((xprt), (xargs), (argsp))
+#define svc_freeargs(xprt, xargs, argsp)		\
+	(*(xprt)->xp_ops->xp_freeargs)((xprt), (xargs), (argsp))
+
+#define SVC_DESTROY(xprt)				\
+	(*(xprt)->xp_ops->xp_destroy)(xprt)
+#define svc_destroy(xprt)				\
+	(*(xprt)->xp_ops->xp_destroy)(xprt)
+
+/*
+ * Transport registration.
+ *
+ * xprt_register(xprt)
+ *	SVCXPRT *xprt;
+ */
+__BEGIN_DECLS
+extern void	xprt_register(SVCXPRT *);
+__END_DECLS
+
+/*
+ * Transport un-register
+ *
+ * xprt_unregister(xprt)
+ *	SVCXPRT *xprt;
+ */
+__BEGIN_DECLS
+extern void	xprt_unregister(SVCXPRT *);
+__END_DECLS
+
+
+/*
+ * When the service routine is called, it must first check to see if it
+ * knows about the procedure;  if not, it should call svcerr_noproc
+ * and return.  If so, it should deserialize its arguments via
+ * SVC_GETARGS (defined above).  If the deserialization does not work,
+ * svcerr_decode should be called followed by a return.  Successful
+ * decoding of the arguments should be followed the execution of the
+ * procedure's code and a call to svc_sendreply.
+ *
+ * Also, if the service refuses to execute the procedure due to too-
+ * weak authentication parameters, svcerr_weakauth should be called.
+ * Note: do not confuse access-control failure with weak authentication!
+ *
+ * NB: In pure implementations of rpc, the caller always waits for a reply
+ * msg.  This message is sent when svc_sendreply is called.
+ * Therefore pure service implementations should always call
+ * svc_sendreply even if the function logically returns void;  use
+ * xdr.h - xdr_void for the xdr routine.  HOWEVER, tcp based rpc allows
+ * for the abuse of pure rpc via batched calling or pipelining.  In the
+ * case of a batched call, svc_sendreply should NOT be called since
+ * this would send a return message, which is what batching tries to avoid.
+ * It is the service/protocol writer's responsibility to know which calls are
+ * batched and which are not.  Warning: responding to batch calls may
+ * deadlock the caller and server processes!
+ */
+
+__BEGIN_DECLS
+extern bool_t	svc_sendreply(SVCXPRT *, xdrproc_t, void *);
+extern void	svcerr_decode(SVCXPRT *);
+extern void	svcerr_weakauth(SVCXPRT *);
+extern void	svcerr_noproc(SVCXPRT *);
+extern void	svcerr_progvers(SVCXPRT *, rpcvers_t, rpcvers_t);
+extern void	svcerr_auth(SVCXPRT *, enum auth_stat);
+extern void	svcerr_noprog(SVCXPRT *);
+extern void	svcerr_systemerr(SVCXPRT *);
+__END_DECLS
+
+/*
+ * Lowest level dispatching -OR- who owns this process anyway.
+ * Somebody has to wait for incoming requests and then call the correct
+ * service routine.  The routine svc_run does infinite waiting; i.e.,
+ * svc_run never returns.
+ * Since another (co-existant) package may wish to selectively wait for
+ * incoming calls or other events outside of the rpc architecture, the
+ * routine svc_getreq is provided.  It must be passed readfds, the
+ * "in-place" results of a select system call (see select, section 2).
+ */
+
+/*
+ * Global keeper of rpc service descriptors in use
+ * dynamic; must be inspected before each call to select
+ */
+extern int svc_maxfd;
+extern fd_set svc_fdset;
+#define svc_fds svc_fdset.fds_bits[0]	/* compatibility */
+
+#ifndef _KERNEL
+/*
+ * a small program implemented by the svc_rpc implementation itself;
+ * also see clnt.h for protocol numbers.
+ */
+__BEGIN_DECLS
+extern void rpctest_service(void);
+__END_DECLS
+#endif
+
+__BEGIN_DECLS
+extern void	svc_getreq(int);
+extern void	svc_getreqset(fd_set *);
+extern void	svc_getreqset2(fd_set *, int); /* XXX: nonstd, undoc */
+extern void	svc_run(void);
+__END_DECLS
+
+/*
+ * Socket to use on svcxxx_create call to get default socket
+ */
+#define	RPC_ANYSOCK	-1
+#define RPC_ANYFD	RPC_ANYSOCK
+
+/*
+ * These are the existing service side transport implementations
+ */
+
+__BEGIN_DECLS
+/*
+ * Transport independent svc_create routine.
+ */
+
+/*
+ * Connectionless and connectionful create routines
+ */
+
+extern SVCXPRT *svc_vc_create(const int, const u_int, const u_int);
+/*
+ *      const int fd;                           -- open connection end point
+ *      const u_int sendsize;                   -- max send size
+ *      const u_int recvsize;                   -- max recv size
+ */
+
+/*
+ * Added for compatibility to old rpc 4.0. Obsoleted by svc_vc_create().
+ */
+extern SVCXPRT *svcunix_create(int, u_int, u_int, char *);
+
+/*
+ * Added for compatibility to old rpc 4.0. Obsoleted by svc_fd_create().
+ */
+extern SVCXPRT *svcunixfd_create(int, u_int, u_int);
+__END_DECLS
+
+
+/* for backward compatibility */
+#include <rpc/svc_soc.h>
+
+#endif /* !_RPC_SVC_H */
diff --git a/services/librpc/include/rpc/svc_auth.h b/services/librpc/include/rpc/svc_auth.h
new file mode 100644
index 0000000..846752c
--- /dev/null
+++ b/services/librpc/include/rpc/svc_auth.h
@@ -0,0 +1,58 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ *
+ *	from: @(#)svc_auth.h 1.6 86/07/16 SMI
+ *	from: @(#)svc_auth.h	2.1 88/07/29 4.0 RPCSRC
+ * $FreeBSD: src/include/rpc/svc_auth.h,v 1.12 1999/08/27 23:45:05 peter Exp $
+ */
+
+/*
+ * svc_auth.h, Service side of rpc authentication.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifndef _RPC_SVCAUTH_H
+#define _RPC_SVCAUTH_H
+
+#include <sys/cdefs.h>
+
+struct rpc_msg;
+struct svc_req;
+
+/*
+ * Server side authenticator
+ */
+__BEGIN_DECLS
+extern enum auth_stat _authenticate (struct svc_req *, struct rpc_msg *);
+extern int svc_auth_reg (int, enum auth_stat (*)(struct svc_req *,
+						     struct rpc_msg *));
+extern enum auth_stat _svcauth_des (struct svc_req *, struct rpc_msg *);
+__END_DECLS
+
+#endif /* !_RPC_SVCAUTH_H */
diff --git a/services/librpc/include/rpc/svc_soc.h b/services/librpc/include/rpc/svc_soc.h
new file mode 100644
index 0000000..5b36fb4
--- /dev/null
+++ b/services/librpc/include/rpc/svc_soc.h
@@ -0,0 +1,125 @@
+/*	$NetBSD: svc_soc.h,v 1.1 2000/06/02 22:57:57 fvdl Exp $	*/
+/*	$FreeBSD: src/include/rpc/svc_soc.h,v 1.2 2002/03/23 17:24:55 imp Exp $ */
+
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+/*
+ * Copyright (c) 1986 - 1991 by Sun Microsystems, Inc.
+ */
+
+/*
+ * svc.h, Server-side remote procedure call interface.
+ */
+
+#ifndef _RPC_SVC_SOC_H
+#define _RPC_SVC_SOC_H
+#include <sys/cdefs.h>
+#include <rpc/types.h>
+#include <rpc/svc.h> /* SVCXPRT */
+
+/* #pragma ident   "@(#)svc_soc.h  1.11    94/04/25 SMI" */
+/*      svc_soc.h 1.8 89/05/01 SMI      */
+
+/*
+ * All the following declarations are only for backward compatibility
+ * with TS-RPC
+ */
+
+/*
+ *  Approved way of getting address of caller
+ */
+#define svc_getcaller(x) (&(x)->xp_raddr)
+
+/*
+ * Service registration
+ *
+ * svc_register(xprt, prog, vers, dispatch, protocol)
+ *	SVCXPRT *xprt;
+ *	u_long prog;
+ *	u_long vers;
+ *	void (*dispatch)();
+ *	int protocol;    like TCP or UDP, zero means do not register 
+ */
+__BEGIN_DECLS
+extern bool_t	svc_register(SVCXPRT *, u_long, u_long,
+		    void (*)(struct svc_req *, SVCXPRT *), int);
+__END_DECLS
+
+/*
+ * Service un-registration
+ *
+ * svc_unregister(prog, vers)
+ *	u_long prog;
+ *	u_long vers;
+ */
+__BEGIN_DECLS
+extern void	svc_unregister(u_long, u_long);
+__END_DECLS
+
+
+/*
+ * Memory based rpc for testing and timing.
+ */
+__BEGIN_DECLS
+extern SVCXPRT *svcraw_create(void);
+__END_DECLS
+
+
+/*
+ * Udp based rpc.
+ */
+__BEGIN_DECLS
+extern SVCXPRT *svcudp_create(int);
+extern SVCXPRT *svcudp_bufcreate(int, u_int, u_int);
+__END_DECLS
+
+
+/*
+ * Tcp based rpc.
+ */
+__BEGIN_DECLS
+extern SVCXPRT *svctcp_create(int, u_int, u_int);
+__END_DECLS
+
+/*
+ * Fd based rpc.
+ */
+__BEGIN_DECLS
+extern SVCXPRT *svcfd_create(int, u_int, u_int);
+__END_DECLS
+
+/*
+ * AF_UNIX socket based rpc.
+ */
+__BEGIN_DECLS
+extern SVCXPRT *svcunix_create (int, u_int, u_int, char *);
+extern SVCXPRT *svcunixfd_create (int, u_int, u_int);
+__END_DECLS
+
+#endif /* !_RPC_SVC_SOC_H */
diff --git a/services/librpc/include/rpc/types.h b/services/librpc/include/rpc/types.h
new file mode 100644
index 0000000..05375d3
--- /dev/null
+++ b/services/librpc/include/rpc/types.h
@@ -0,0 +1,68 @@
+/*	$NetBSD: types.h,v 1.13 2000/06/13 01:02:44 thorpej Exp $	*/
+
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ *
+ *	from: @(#)types.h 1.18 87/07/24 SMI
+ *	from: @(#)types.h	2.3 88/08/15 4.0 RPCSRC
+ * $FreeBSD: src/include/rpc/types.h,v 1.11 2003/12/07 21:10:06 marcel Exp $
+ */
+
+/*
+ * Rpc additions to <sys/types.h>
+ */
+#ifndef _RPC_TYPES_H
+#define _RPC_TYPES_H
+
+#include <stdint.h>
+
+typedef int32_t bool_t;
+typedef int32_t enum_t;
+
+typedef uint32_t rpcprog_t;
+typedef uint32_t rpcvers_t;
+typedef uint32_t rpcproc_t;
+typedef uint32_t rpcprot_t;
+typedef uint32_t rpcport_t;
+typedef  int32_t rpc_inline_t;
+ 
+#define __dontcare__	-1
+
+#ifndef FALSE
+#	define FALSE	(0)
+#endif
+#ifndef TRUE
+#	define TRUE	(1)
+#endif
+
+#define mem_alloc(bsize)	malloc(bsize)
+#define mem_free(ptr, bsize)	free(ptr)
+
+#include <sys/time.h>
+
+#endif /* !_RPC_TYPES_H */
diff --git a/services/librpc/include/rpc/xdr.h b/services/librpc/include/rpc/xdr.h
new file mode 100644
index 0000000..30f2bcc
--- /dev/null
+++ b/services/librpc/include/rpc/xdr.h
@@ -0,0 +1,312 @@
+/*	$NetBSD: xdr.h,v 1.19 2000/07/17 05:00:45 matt Exp $	*/
+
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ *
+ *	from: @(#)xdr.h 1.19 87/04/22 SMI
+ *	from: @(#)xdr.h	2.2 88/07/29 4.0 RPCSRC
+ * $FreeBSD: src/include/rpc/xdr.h,v 1.23 2003/03/07 13:19:40 nectar Exp $
+ */
+
+/*
+ * xdr.h, External Data Representation Serialization Routines.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifndef _RPC_XDR_H
+#define _RPC_XDR_H
+
+#include <sys/cdefs.h>
+
+#include <rpc/types.h>
+
+/*
+ * XDR provides a conventional way for converting between C data
+ * types and an external bit-string representation.  Library supplied
+ * routines provide for the conversion on built-in C data types.  These
+ * routines and utility routines defined here are used to help implement
+ * a type encode/decode routine for each user-defined type.
+ *
+ * Each data type provides a single procedure which takes two arguments:
+ *
+ *	bool_t
+ *	xdrproc(xdrs, argresp)
+ *		XDR *xdrs;
+ *		<type> *argresp;
+ *
+ * xdrs is an instance of a XDR handle, to which or from which the data
+ * type is to be converted.  argresp is a pointer to the structure to be
+ * converted.  The XDR handle contains an operation field which indicates
+ * which of the operations (ENCODE, DECODE * or FREE) is to be performed.
+ *
+ * XDR_DECODE may allocate space if the pointer argresp is null.  This
+ * data can be freed with the XDR_FREE operation.
+ *
+ * We write only one procedure per data type to make it easy
+ * to keep the encode and decode procedures for a data type consistent.
+ * In many cases the same code performs all operations on a user defined type,
+ * because all the hard work is done in the component type routines.
+ * decode as a series of calls on the nested data types.
+ */
+
+/*
+ * Xdr operations.  XDR_ENCODE causes the type to be encoded into the
+ * stream.  XDR_DECODE causes the type to be extracted from the stream.
+ * XDR_FREE can be used to release the space allocated by an XDR_DECODE
+ * request.
+ */
+enum xdr_op {
+	XDR_ENCODE=0,
+	XDR_DECODE=1,
+	XDR_FREE=2
+};
+
+/*
+ * This is the number of bytes per unit of external data.
+ */
+#define BYTES_PER_XDR_UNIT	(4)
+#define RNDUP(x)  ((((x) + BYTES_PER_XDR_UNIT - 1) / BYTES_PER_XDR_UNIT) \
+		    * BYTES_PER_XDR_UNIT)
+
+/*
+ * The XDR handle.
+ * Contains operation which is being applied to the stream,
+ * an operations vector for the particular implementation (e.g. see xdr_mem.c),
+ * and two private fields for the use of the particular implementation.
+ */
+typedef struct __rpc_xdr {
+	enum xdr_op	x_op;		/* operation; fast additional param */
+	const struct xdr_ops {
+		/* get a long from underlying stream */
+		bool_t	(*x_getlong)(struct __rpc_xdr *, long *);
+		/* put a long to " */
+		bool_t	(*x_putlong)(struct __rpc_xdr *, const long *);
+		/* get some bytes from " */
+		bool_t	(*x_getbytes)(struct __rpc_xdr *, char *, u_int);
+		/* put some bytes to " */
+		bool_t	(*x_putbytes)(struct __rpc_xdr *, const char *, u_int);
+		/* returns bytes off from beginning */
+		u_int	(*x_getpostn)(struct __rpc_xdr *);
+		/* lets you reposition the stream */
+		bool_t  (*x_setpostn)(struct __rpc_xdr *, u_int);
+		/* buf quick ptr to buffered data */
+		int32_t *(*x_inline)(struct __rpc_xdr *, u_int);
+		/* free privates of this xdr_stream */
+		void	(*x_destroy)(struct __rpc_xdr *);
+	} *x_ops;
+	char *	 	x_public;	/* users' data */
+	void *		x_private;	/* pointer to private data */
+	char *	 	x_base;		/* private used for position info */
+	u_int		x_handy;	/* extra private word */
+} XDR;
+
+/*
+ * A xdrproc_t exists for each data type which is to be encoded or decoded.
+ *
+ * The second argument to the xdrproc_t is a pointer to an opaque pointer.
+ * The opaque pointer generally points to a structure of the data type
+ * to be decoded.  If this pointer is 0, then the type routines should
+ * allocate dynamic storage of the appropriate size and return it.
+ */
+typedef	bool_t (*xdrproc_t) (XDR *, void *, ...);
+
+/*
+ * Operations defined on a XDR handle
+ *
+ * XDR		*xdrs;
+ * long		*longp;
+ * caddr_t	 addr;
+ * u_int	 len;
+ * u_int	 pos;
+ */
+#define XDR_GETLONG(xdrs, longp)			\
+	(*(xdrs)->x_ops->x_getlong)(xdrs, longp)
+#define xdr_getlong(xdrs, longp)			\
+	(*(xdrs)->x_ops->x_getlong)(xdrs, longp)
+
+#define XDR_PUTLONG(xdrs, longp)			\
+	(*(xdrs)->x_ops->x_putlong)(xdrs, longp)
+#define xdr_putlong(xdrs, longp)			\
+	(*(xdrs)->x_ops->x_putlong)(xdrs, longp)
+
+#define XDR_GETBYTES(xdrs, addr, len)			\
+	(*(xdrs)->x_ops->x_getbytes)(xdrs, addr, len)
+#define xdr_getbytes(xdrs, addr, len)			\
+	(*(xdrs)->x_ops->x_getbytes)(xdrs, addr, len)
+
+#define XDR_PUTBYTES(xdrs, addr, len)			\
+	(*(xdrs)->x_ops->x_putbytes)(xdrs, addr, len)
+#define xdr_putbytes(xdrs, addr, len)			\
+	(*(xdrs)->x_ops->x_putbytes)(xdrs, addr, len)
+
+#define XDR_GETPOS(xdrs)				\
+	(*(xdrs)->x_ops->x_getpostn)(xdrs)
+#define xdr_getpos(xdrs)				\
+	(*(xdrs)->x_ops->x_getpostn)(xdrs)
+
+#define XDR_SETPOS(xdrs, pos)				\
+	(*(xdrs)->x_ops->x_setpostn)(xdrs, pos)
+#define xdr_setpos(xdrs, pos)				\
+	(*(xdrs)->x_ops->x_setpostn)(xdrs, pos)
+
+#define	XDR_INLINE(xdrs, len)				\
+	(*(xdrs)->x_ops->x_inline)(xdrs, len)
+#define	xdr_inline(xdrs, len)				\
+	(*(xdrs)->x_ops->x_inline)(xdrs, len)
+
+#define	XDR_DESTROY(xdrs)				\
+	if ((xdrs)->x_ops->x_destroy) 			\
+		(*(xdrs)->x_ops->x_destroy)(xdrs)
+#define	xdr_destroy(xdrs)				\
+	if ((xdrs)->x_ops->x_destroy) 			\
+		(*(xdrs)->x_ops->x_destroy)(xdrs)
+
+/*
+ * Support struct for discriminated unions.
+ * You create an array of xdrdiscrim structures, terminated with
+ * an entry with a null procedure pointer.  The xdr_union routine gets
+ * the discriminant value and then searches the array of structures
+ * for a matching value.  If a match is found the associated xdr routine
+ * is called to handle that part of the union.  If there is
+ * no match, then a default routine may be called.
+ * If there is no match and no default routine it is an error.
+ */
+#define NULL_xdrproc_t ((xdrproc_t)0)
+struct xdr_discrim {
+	int	value;
+	xdrproc_t proc;
+};
+
+/*
+ * In-line routines for fast encode/decode of primitive data types.
+ * Caveat emptor: these use single memory cycles to get the
+ * data from the underlying buffer, and will fail to operate
+ * properly if the data is not aligned.  The standard way to use these
+ * is to say:
+ *	if ((buf = XDR_INLINE(xdrs, count)) == NULL)
+ *		return (FALSE);
+ *	<<< macro calls >>>
+ * where ``count'' is the number of bytes of data occupied
+ * by the primitive data types.
+ *
+ * N.B. and frozen for all time: each data type here uses 4 bytes
+ * of external representation.
+ */
+#define IXDR_GET_LONG(buf)		((long)ntohl((u_long)*(buf)++))
+#define IXDR_PUT_LONG(buf, v)		(*(buf)++ = (long)htonl((u_long)v))
+
+#define IXDR_GET_BOOL(buf)		((bool_t)IXDR_GET_LONG(buf))
+#define IXDR_GET_ENUM(buf, t)		((t)IXDR_GET_LONG(buf))
+#define IXDR_GET_U_LONG(buf)		((u_long)IXDR_GET_LONG(buf))
+#define IXDR_GET_SHORT(buf)		((short)IXDR_GET_LONG(buf))
+#define IXDR_GET_U_SHORT(buf)		((u_short)IXDR_GET_LONG(buf))
+
+#define IXDR_PUT_BOOL(buf, v)		IXDR_PUT_LONG((buf), ((long)(v)))
+#define IXDR_PUT_ENUM(buf, v)		IXDR_PUT_LONG((buf), ((long)(v)))
+#define IXDR_PUT_U_LONG(buf, v)		IXDR_PUT_LONG((buf), ((long)(v)))
+#define IXDR_PUT_SHORT(buf, v)		IXDR_PUT_LONG((buf), ((long)(v)))
+#define IXDR_PUT_U_SHORT(buf, v)	IXDR_PUT_LONG((buf), ((long)(v)))
+
+/*
+ * These are the "generic" xdr routines.
+ */
+__BEGIN_DECLS
+extern bool_t	xdr_void(void);
+extern bool_t	xdr_int(XDR *, int *);
+extern bool_t	xdr_u_int(XDR *, u_int *);
+extern bool_t	xdr_long(XDR *, long *);
+extern bool_t	xdr_u_long(XDR *, u_long *);
+extern bool_t	xdr_short(XDR *, short *);
+extern bool_t	xdr_u_short(XDR *, u_short *);
+extern bool_t	xdr_int16_t(XDR *, int16_t *);
+extern bool_t	xdr_u_int16_t(XDR *, u_int16_t *);
+extern bool_t	xdr_int32_t(XDR *, int32_t *);
+extern bool_t	xdr_u_int32_t(XDR *, u_int32_t *);
+extern bool_t	xdr_int64_t(XDR *, int64_t *);
+extern bool_t	xdr_u_int64_t(XDR *, u_int64_t *);
+extern bool_t	xdr_bool(XDR *, bool_t *);
+extern bool_t	xdr_enum(XDR *, enum_t *);
+extern bool_t	xdr_array(XDR *, char **, u_int *, u_int, u_int, xdrproc_t);
+extern bool_t	xdr_bytes(XDR *, char **, u_int *, u_int);
+extern bool_t	xdr_opaque(XDR *, caddr_t, u_int);
+extern bool_t	xdr_string(XDR *, char **, u_int);
+extern bool_t	xdr_union(XDR *, enum_t *, char *, const struct xdr_discrim *, xdrproc_t);
+extern unsigned long	xdr_sizeof (xdrproc_t, void *);
+extern bool_t	xdr_char(XDR *, char *);
+extern bool_t	xdr_u_char(XDR *, u_char *);
+extern bool_t	xdr_vector(XDR *, char *, u_int, u_int, xdrproc_t);
+extern bool_t	xdr_float(XDR *, float *);
+extern bool_t	xdr_double(XDR *, double *);
+extern bool_t	xdr_reference(XDR *, caddr_t *, u_int, xdrproc_t);
+extern bool_t	xdr_pointer(XDR *, caddr_t *, u_int, xdrproc_t);
+extern bool_t	xdr_wrapstring(XDR *, char **);
+extern void	xdr_free(xdrproc_t, char *);
+__END_DECLS
+
+/*
+ * Common opaque bytes objects used by many rpc protocols;
+ * declared here due to commonality.
+ */
+#define MAX_NETOBJ_SZ 1024
+struct netobj {
+	u_int	n_len;
+	char	*n_bytes;
+};
+typedef struct netobj netobj;
+extern bool_t   xdr_netobj(XDR *, struct netobj *);
+
+/*
+ * These are the public routines for the various implementations of
+ * xdr streams.
+ */
+__BEGIN_DECLS
+/* XDR using memory buffers */
+extern void   xdrmem_create(XDR *, char *, u_int, enum xdr_op);
+
+/* XDR using stdio library */
+#ifdef _STDIO_H_
+extern void   xdrstdio_create(XDR *, FILE *, enum xdr_op);
+#endif
+
+/* XDR pseudo records for tcp */
+extern void   xdrrec_create(XDR *, u_int, u_int, char *,
+				int (*) (caddr_t, caddr_t, int),
+				int (*) (caddr_t, caddr_t, int));
+
+/* make end of xdr record */
+extern bool_t xdrrec_endofrecord(XDR *, bool_t);
+
+/* move to beginning of next record */
+extern bool_t xdrrec_skiprecord(XDR *);
+
+/* true if no more input */
+extern bool_t xdrrec_eof(XDR *);
+__END_DECLS
+
+#endif /* !_RPC_XDR_H */
diff --git a/services/librpc/include/rpcsvc/bootparam_prot.x b/services/librpc/include/rpcsvc/bootparam_prot.x
new file mode 100644
index 0000000..0f74c8f
--- /dev/null
+++ b/services/librpc/include/rpcsvc/bootparam_prot.x
@@ -0,0 +1,103 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+/*
+ * RPC for bootparms service.
+ * There are two procedures:
+ *   WHOAMI takes a net address and returns a client name and also a
+ *	likely net address for routing
+ *   GETFILE takes a client name and file identifier and returns the
+ *	server name, server net address and pathname for the file.
+ *   file identifiers typically include root, swap, pub and dump
+ */
+
+#ifdef RPC_HDR
+%#include <rpc/types.h>
+%#include <sys/time.h>
+%#include <sys/errno.h>
+%#include <sys/param.h>
+%#include <sys/syslimits.h>
+%#include <sys/ucred.h>
+#else
+%#ifndef lint
+%/*static char sccsid[] = "from: @(#)bootparam_prot.x 1.2 87/06/24 Copyr 1987 Sun Micro";*/
+%/*static char sccsid[] = "from: @(#)bootparam_prot.x	2.1 88/08/01 4.0 RPCSRC";*/
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/bootparam_prot.x,v 1.5 1999/08/27 23:45:07 peter Exp $";
+%#endif /* not lint */
+#endif
+
+const MAX_MACHINE_NAME  = 255;
+const MAX_PATH_LEN	= 1024;
+const MAX_FILEID	= 32;
+const IP_ADDR_TYPE	= 1;
+
+typedef	string	bp_machine_name_t<MAX_MACHINE_NAME>;
+typedef	string	bp_path_t<MAX_PATH_LEN>;
+typedef	string	bp_fileid_t<MAX_FILEID>;
+
+struct	ip_addr_t {
+	char	net;
+	char	host;
+	char	lh;
+	char	impno;
+};
+
+union bp_address switch (int address_type) {
+	case IP_ADDR_TYPE:
+		ip_addr_t	ip_addr;
+};
+
+struct bp_whoami_arg {
+	bp_address		client_address;
+};
+
+struct bp_whoami_res {
+	bp_machine_name_t	client_name;
+	bp_machine_name_t	domain_name;
+	bp_address		router_address;
+};
+
+struct bp_getfile_arg {
+	bp_machine_name_t	client_name;
+	bp_fileid_t		file_id;
+};
+	
+struct bp_getfile_res {
+	bp_machine_name_t	server_name;
+	bp_address		server_address;
+	bp_path_t		server_path;
+};
+
+program BOOTPARAMPROG {
+	version BOOTPARAMVERS {
+		bp_whoami_res	BOOTPARAMPROC_WHOAMI(bp_whoami_arg) = 1;
+		bp_getfile_res	BOOTPARAMPROC_GETFILE(bp_getfile_arg) = 2;
+	} = 1;
+} = 100026;
diff --git a/services/librpc/include/rpcsvc/crypt.x b/services/librpc/include/rpcsvc/crypt.x
new file mode 100644
index 0000000..8df1654
--- /dev/null
+++ b/services/librpc/include/rpcsvc/crypt.x
@@ -0,0 +1,91 @@
+/*
+ * Copyright (c) 1996
+ *	Bill Paul <wpaul at ctr.columbia.edu>.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *	This product includes software developed by Bill Paul.
+ * 4. Neither the name of the author nor the names of any co-contributors
+ *    may be used to endorse or promote products derived from this software
+ *    without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY Bill Paul AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL Bill Paul OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * $FreeBSD: src/include/rpcsvc/crypt.x,v 1.3 1999/08/27 23:45:08 peter Exp $
+ */
+
+#ifndef RPC_HDR
+%#ifndef lint
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/crypt.x,v 1.3 1999/08/27 23:45:08 peter Exp $";
+%#endif
+#endif
+
+/*
+ * This protocol definition exists because of the U.S. government and
+ * its stupid export laws. We can't export DES code from the United
+ * States to other countries (even though the code already exists
+ * outside the U.S. -- go figure that one out) but we need to make
+ * Secure RPC work. The normal way around this is to break the DES
+ * code out into a shared library; we can then provide a dummy lib
+ * in the base OS and provide the real lib in the secure dist, which
+ * the user can install later. But we need Secure RPC for NIS+, and
+ * there are several system programs that use NIS+ which are statically
+ * linked. We would have to provide replacements for these programs
+ * in the secure dist, but there are a lot, and this is a pain. The
+ * shared lib trick won't work for these programs, and we can't change
+ * them once they're compiled.
+ *
+ * One solution for this problem is to do the DES encryption as a system
+ * call; no programs need to be changed and we can even supply the DES
+ * support as an LKM. But this bloats the kernel. Maybe if we have
+ * Secure NFS one day this will be worth it, but for now we should keep
+ * this mess in user space.
+ *
+ * So we have this second solution: we provide a server that does the
+ * DES encryption for us. In this case, the server is keyserv (we need
+ * it to make Secure RPC work anyway) and we use this protocol to ship
+ * the data back and forth between keyserv and the application.
+ */
+
+enum des_dir { ENCRYPT_DES, DECRYPT_DES };
+enum des_mode { CBC_DES, ECB_DES };
+
+struct desargs {
+	u_char des_key[8];	/* key (with low bit parity) */
+	des_dir des_dir;	/* direction */
+	des_mode des_mode;	/* mode */
+	u_char des_ivec[8];	/* input vector */
+	opaque desbuf<>;
+};
+
+struct desresp {
+	opaque desbuf<>;
+	u_char des_ivec[8];
+	int stat;
+};
+
+program CRYPT_PROG {
+	version CRYPT_VERS {
+		desresp
+		DES_CRYPT(desargs) = 1;
+	} = 1;
+} = 600100029;
diff --git a/services/librpc/include/rpcsvc/key_prot.x b/services/librpc/include/rpcsvc/key_prot.x
new file mode 100644
index 0000000..f545569
--- /dev/null
+++ b/services/librpc/include/rpcsvc/key_prot.x
@@ -0,0 +1,282 @@
+%/*
+% * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+% * unrestricted use provided that this legend is included on all tape
+% * media and as a part of the software program in whole or part.  Users
+% * may copy or modify Sun RPC without charge, but are not authorized
+% * to license or distribute it to anyone else except as part of a product or
+% * program developed by the user.
+% *
+% * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+% * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+% * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+% *
+% * Sun RPC is provided with no support and without any obligation on the
+% * part of Sun Microsystems, Inc. to assist in its use, correction,
+% * modification or enhancement.
+% *
+% * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+% * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+% * OR ANY PART THEREOF.
+% *
+% * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+% * or profits or other special, indirect and consequential damages, even if
+% * Sun has been advised of the possibility of such damages.
+% *
+% * Sun Microsystems, Inc.
+% * 2550 Garcia Avenue
+% * Mountain View, California  94043
+% */
+/*
+ * Key server protocol definition
+ * Copyright (C) 1990, 1991 Sun Microsystems, Inc.
+ *
+ * The keyserver is a public key storage/encryption/decryption service
+ * The encryption method used is based on the Diffie-Hellman exponential
+ * key exchange technology.
+ *
+ * The key server is local to each machine, akin to the portmapper.
+ * Under TI-RPC, communication with the keyserver is through the
+ * loopback transport.
+ *
+ * NOTE: This .x file generates the USER level headers for the keyserver.
+ * the KERNEL level headers are created by hand as they kernel has special
+ * requirements.
+ */
+
+%/* From: #pragma ident	"@(#)key_prot.x	1.7	94/04/29 SMI" */
+%
+%/* Copyright (c)  1990, 1991 Sun Microsystems, Inc. */
+%
+%/* 
+% * Compiled from key_prot.x using rpcgen.
+% * DO NOT EDIT THIS FILE!
+% * This is NOT source code!
+% */
+
+/*
+ * PROOT and MODULUS define the way the Diffie-Hellman key is generated.
+ *
+ * MODULUS should be chosen as a prime of the form: MODULUS == 2*p + 1,
+ * where p is also prime.
+ *
+ * PROOT satisfies the following two conditions:
+ * (1) (PROOT ** 2) % MODULUS != 1
+ * (2) (PROOT ** p) % MODULUS != 1
+ *
+ */
+
+const PROOT = 3;
+const HEXMODULUS = "d4a0ba0250b6fd2ec626e7efd637df76c716e22d0944b88b";
+
+const HEXKEYBYTES = 48;		/* HEXKEYBYTES == strlen(HEXMODULUS) */
+const KEYSIZE = 192;		/* KEYSIZE == bit length of key */
+const KEYBYTES = 24;		/* byte length of key */
+
+/*
+ * The first 16 hex digits of the encrypted secret key are used as
+ * a checksum in the database.
+ */
+const KEYCHECKSUMSIZE = 16;
+
+/*
+ * status of operation
+ */
+enum keystatus {
+	KEY_SUCCESS,	/* no problems */
+	KEY_NOSECRET,	/* no secret key stored */
+	KEY_UNKNOWN,	/* unknown netname */
+	KEY_SYSTEMERR 	/* system error (out of memory, encryption failure) */
+};
+
+typedef opaque keybuf[HEXKEYBYTES];	/* store key in hex */
+
+typedef string netnamestr<MAXNETNAMELEN>;
+
+/*
+ * Argument to ENCRYPT or DECRYPT 
+ */
+struct cryptkeyarg {
+	netnamestr remotename;
+	des_block deskey;
+};
+
+/*
+ * Argument to ENCRYPT_PK or DECRYPT_PK
+ */
+struct cryptkeyarg2 {
+	netnamestr remotename;
+	netobj	remotekey;	/* Contains a length up to 1024 bytes */
+	des_block deskey;
+};
+
+
+/*
+ * Result of ENCRYPT, DECRYPT, ENCRYPT_PK, and DECRYPT_PK
+ */
+union cryptkeyres switch (keystatus status) {
+case KEY_SUCCESS:
+	des_block deskey;
+default:
+	void;
+};
+
+const MAXGIDS  = 16;	/* max number of gids in gid list */
+
+/*
+ * Unix credential 
+ */	
+struct unixcred {
+	u_int uid;
+	u_int gid;
+	u_int gids<MAXGIDS>;	
+};
+
+/*
+ * Result returned from GETCRED
+ */
+union getcredres switch (keystatus status) {
+case KEY_SUCCESS:
+	unixcred cred;
+default:
+	void;
+};
+/*
+ * key_netstarg;
+ */
+
+struct key_netstarg {
+	keybuf st_priv_key;
+	keybuf st_pub_key;
+	netnamestr st_netname;
+};
+
+union key_netstres switch (keystatus status){
+case KEY_SUCCESS:
+	key_netstarg knet;
+default:
+	void;
+};	
+
+#ifdef RPC_HDR
+%
+%#ifndef opaque
+%#define opaque char
+%#endif
+%
+#endif
+program KEY_PROG {
+	version KEY_VERS {
+
+		/*
+		 * This is my secret key.
+	 	 * Store it for me.
+		 */
+		keystatus 
+		KEY_SET(keybuf) = 1;	
+	
+		/*
+		 * I want to talk to X.
+		 * Encrypt a conversation key for me.
+	 	 */
+		cryptkeyres
+		KEY_ENCRYPT(cryptkeyarg) = 2;	
+
+		/*
+		 * X just sent me a message.
+		 * Decrypt the conversation key for me.
+		 */
+		cryptkeyres
+		KEY_DECRYPT(cryptkeyarg) = 3;
+
+		/*
+		 * Generate a secure conversation key for me
+		 */
+		des_block 
+		KEY_GEN(void) = 4;
+
+		/*
+		 * Get me the uid, gid and group-access-list associated
+		 * with this netname (for kernel which cannot use NIS)
+		 */
+		getcredres
+		KEY_GETCRED(netnamestr) = 5;
+	} = 1;
+	version KEY_VERS2 {
+
+		/*
+		 * #######
+		 * Procedures 1-5 are identical to version 1
+		 * #######
+		 */
+
+		/*
+		 * This is my secret key.
+	 	 * Store it for me.
+		 */
+		keystatus 
+		KEY_SET(keybuf) = 1;	
+	
+		/*
+		 * I want to talk to X.
+		 * Encrypt a conversation key for me.
+	 	 */
+		cryptkeyres
+		KEY_ENCRYPT(cryptkeyarg) = 2;	
+
+		/*
+		 * X just sent me a message.
+		 * Decrypt the conversation key for me.
+		 */
+		cryptkeyres
+		KEY_DECRYPT(cryptkeyarg) = 3;
+
+		/*
+		 * Generate a secure conversation key for me
+		 */
+		des_block 
+		KEY_GEN(void) = 4;
+
+		/*
+		 * Get me the uid, gid and group-access-list associated
+		 * with this netname (for kernel which cannot use NIS)
+		 */
+		getcredres
+		KEY_GETCRED(netnamestr) = 5;
+		
+		/*
+		 * I want to talk to X. and I know X's public key
+		 * Encrypt a conversation key for me.
+	 	 */
+		cryptkeyres
+		KEY_ENCRYPT_PK(cryptkeyarg2) = 6;	
+
+		/*
+		 * X just sent me a message. and I know X's public key
+		 * Decrypt the conversation key for me.
+		 */
+		cryptkeyres
+		KEY_DECRYPT_PK(cryptkeyarg2) = 7;
+		
+		/* 
+		 * Store my public key, netname and private key. 
+		 */
+		keystatus
+		KEY_NET_PUT(key_netstarg) = 8;
+		
+		/*
+		 * Retrieve my public key, netname and private key. 
+		 */
+ 		key_netstres
+		KEY_NET_GET(void) = 9;
+		
+		/*
+		 * Return me the conversation key that is constructed 
+		 * from my secret key and this publickey. 
+		 */
+
+		cryptkeyres 
+		KEY_GET_CONV(keybuf) = 10; 
+
+		
+	} = 2;
+} = 100029;
diff --git a/services/librpc/include/rpcsvc/klm_prot.x b/services/librpc/include/rpcsvc/klm_prot.x
new file mode 100644
index 0000000..c4cfe36
--- /dev/null
+++ b/services/librpc/include/rpcsvc/klm_prot.x
@@ -0,0 +1,139 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+/*
+ * Kernel/lock manager protocol definition
+ * Copyright (C) 1986 Sun Microsystems, Inc.
+ *
+ * protocol used between the UNIX kernel (the "client") and the
+ * local lock manager.  The local lock manager is a deamon running
+ * above the kernel.
+ */
+
+#ifndef RPC_HDR
+%#ifndef lint
+%/*static char sccsid[] = "from: @(#)klm_prot.x 1.7 87/07/08 Copyr 1987 Sun Micro";*/
+%/*static char sccsid[] = "from: @(#)klm_prot.x	2.1 88/08/01 4.0 RPCSRC";*/
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/klm_prot.x,v 1.6 1999/08/27 23:45:08 peter Exp $";
+%#endif /* not lint */
+#endif
+
+const	LM_MAXSTRLEN = 1024;
+
+/*
+ * lock manager status returns
+ */
+enum klm_stats {
+	klm_granted = 0,	/* lock is granted */
+	klm_denied = 1,		/* lock is denied */
+	klm_denied_nolocks = 2, /* no lock entry available */
+	klm_working = 3 	/* lock is being processed */
+};
+
+/*
+ * lock manager lock identifier
+ */
+struct klm_lock {
+	string server_name<LM_MAXSTRLEN>;
+	netobj fh;		/* a counted file handle */
+	int pid;		/* holder of the lock */
+	unsigned l_offset;	/* beginning offset of the lock */
+	unsigned l_len;		/* byte length of the lock;
+				 * zero means through end of file */
+};
+
+/*
+ * lock holder identifier
+ */
+struct klm_holder {
+	bool exclusive;		/* FALSE if shared lock */
+	int svid;		/* holder of the lock (pid) */
+	unsigned l_offset;	/* beginning offset of the lock */
+	unsigned l_len;		/* byte length of the lock;
+				 * zero means through end of file */
+};
+
+/*
+ * reply to KLM_LOCK / KLM_UNLOCK / KLM_CANCEL
+ */
+struct klm_stat {
+	klm_stats stat;
+};
+
+/*
+ * reply to a KLM_TEST call
+ */
+union klm_testrply switch (klm_stats stat) {
+	case klm_denied:
+		struct klm_holder holder;
+	default: /* All other cases return no arguments */
+		void;
+};
+
+
+/*
+ * arguments to KLM_LOCK
+ */
+struct klm_lockargs {
+	bool block;
+	bool exclusive;
+	struct klm_lock alock;
+};
+
+/*
+ * arguments to KLM_TEST
+ */
+struct klm_testargs {
+	bool exclusive;
+	struct klm_lock alock;
+};
+
+/*
+ * arguments to KLM_UNLOCK
+ */
+struct klm_unlockargs {
+	struct klm_lock alock;
+};
+
+program KLM_PROG {
+	version KLM_VERS {
+
+		klm_testrply	KLM_TEST (struct klm_testargs) =	1;
+
+		klm_stat	KLM_LOCK (struct klm_lockargs) =	2;
+
+		klm_stat	KLM_CANCEL (struct klm_lockargs) =	3;
+		/* klm_granted=> the cancel request fails due to lock is already granted */
+		/* klm_denied=> the cancel request successfully aborts
+lock request  */
+
+		klm_stat	KLM_UNLOCK (struct klm_unlockargs) =	4;
+	} = 1;
+} = 100020;
diff --git a/services/librpc/include/rpcsvc/mount.x b/services/librpc/include/rpcsvc/mount.x
new file mode 100644
index 0000000..f68a06f
--- /dev/null
+++ b/services/librpc/include/rpcsvc/mount.x
@@ -0,0 +1,257 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+/*
+ * Protocol description for the mount program
+ */
+
+#ifndef RPC_HDR
+%#ifndef lint
+%/*static char sccsid[] = "from: @(#)mount.x 1.2 87/09/18 Copyr 1987 Sun Micro";*/
+%/*static char sccsid[] = "from: @(#)mount.x	2.1 88/08/01 4.0 RPCSRC";*/
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/mount.x,v 1.6 1999/08/27 23:45:08 peter Exp $";
+%#endif /* not lint */
+#endif
+
+const MNTPATHLEN = 1024;	/* maximum bytes in a pathname argument */
+const MNTNAMLEN = 255;		/* maximum bytes in a name argument */
+const FHSIZE = 32;		/* size in bytes of a file handle */
+#ifdef WANT_NFS3
+const FHSIZE3 = 64;		/* size in bytes of a file handle (v3) */
+#endif
+
+/*
+ * The fhandle is the file handle that the server passes to the client.
+ * All file operations are done using the file handles to refer to a file
+ * or a directory. The file handle can contain whatever information the
+ * server needs to distinguish an individual file.
+ */
+typedef opaque fhandle[FHSIZE];	
+#ifdef WANT_NFS3
+typedef opaque fhandle3<FHSIZE3>;
+#endif
+
+/*
+ * If a status of zero is returned, the call completed successfully, and 
+ * a file handle for the directory follows. A non-zero status indicates
+ * some sort of error. The status corresponds with UNIX error numbers.
+ */
+union fhstatus switch (unsigned fhs_status) {
+case 0:
+	fhandle fhs_fhandle;
+default:
+	void;
+};
+
+#ifdef WANT_NFS3
+/*
+ * Status codes returned by the version 3 mount call.
+ */
+enum mountstat3 {
+	MNT3_OK = 0,                 /* no error */
+	MNT3ERR_PERM = 1,            /* Not owner */
+	MNT3ERR_NOENT = 2,           /* No such file or directory */
+	MNT3ERR_IO = 5,              /* I/O error */
+	MNT3ERR_ACCES = 13,          /* Permission denied */
+	MNT3ERR_NOTDIR = 20,         /* Not a directory */
+	MNT3ERR_INVAL = 22,          /* Invalid argument */
+	MNT3ERR_NAMETOOLONG = 63,    /* Filename too long */
+	MNT3ERR_NOTSUPP = 10004,     /* Operation not supported */
+	MNT3ERR_SERVERFAULT = 10006  /* A failure on the server */
+};
+
+struct mountres3_ok {
+	fhandle3	fhandle;
+	int		auth_flavors<>;
+};
+
+union mountres3 switch (mountstat3 fhs_status) {
+case 0:
+	mountres3_ok	mountinfo;
+default:
+	void;
+};
+#endif
+
+/*
+ * The type dirpath is the pathname of a directory
+ */
+typedef string dirpath<MNTPATHLEN>;
+
+/*
+ * The type name is used for arbitrary names (hostnames, groupnames)
+ */
+typedef string name<MNTNAMLEN>;
+
+/*
+ * A list of who has what mounted
+ */
+typedef struct mountbody *mountlist;
+struct mountbody {
+	name ml_hostname;
+	dirpath ml_directory;
+	mountlist ml_next;
+};
+
+/*
+ * A list of netgroups
+ */
+typedef struct groupnode *groups;
+struct groupnode {
+	name gr_name;
+	groups gr_next;
+};
+
+/*
+ * A list of what is exported and to whom
+ */
+typedef struct exportnode *exports;
+struct exportnode {
+	dirpath ex_dir;
+	groups ex_groups;
+	exports ex_next;
+};
+
+program MOUNTPROG {
+	/*
+	 * Version one of the mount protocol communicates with version two
+	 * of the NFS protocol. Version three communicates with
+	 * version three of the NFS protocol. The only connecting
+	 * point is the fhandle structure, which is the same for both
+	 * protocols.
+	 */
+	version MOUNTVERS {
+		/*
+		 * Does no work. It is made available in all RPC services
+		 * to allow server reponse testing and timing
+		 */
+		void
+		MOUNTPROC_NULL(void) = 0;
+
+		/*	
+		 * If fhs_status is 0, then fhs_fhandle contains the
+	 	 * file handle for the directory. This file handle may
+		 * be used in the NFS protocol. This procedure also adds
+		 * a new entry to the mount list for this client mounting
+		 * the directory.
+		 * Unix authentication required.
+		 */
+		fhstatus 
+		MOUNTPROC_MNT(dirpath) = 1;
+
+		/*
+		 * Returns the list of remotely mounted filesystems. The 
+		 * mountlist contains one entry for each hostname and 
+		 * directory pair.
+		 */
+		mountlist
+		MOUNTPROC_DUMP(void) = 2;
+
+		/*
+		 * Removes the mount list entry for the directory
+		 * Unix authentication required.
+		 */
+		void
+		MOUNTPROC_UMNT(dirpath) = 3;
+
+		/*
+		 * Removes all of the mount list entries for this client
+		 * Unix authentication required.
+		 */
+		void
+		MOUNTPROC_UMNTALL(void) = 4;
+
+		/*
+		 * Returns a list of all the exported filesystems, and which
+		 * machines are allowed to import it.
+		 */
+		exports
+		MOUNTPROC_EXPORT(void)  = 5;
+
+		/*
+		 * Identical to MOUNTPROC_EXPORT above
+		 */
+		exports
+		MOUNTPROC_EXPORTALL(void) = 6;
+	} = 1;
+#ifdef WANT_NFS3
+	version MOUNTVERS3 {
+		/*
+		 * Does no work. It is made available in all RPC services
+		 * to allow server reponse testing and timing
+		 */
+		void
+		MOUNTPROC_NULL(void) = 0;
+
+		/*
+		 * If mountres3.fhs_status is MNT3_OK, then
+		 * mountres3.mountinfo contains the file handle for
+		 * the directory and a list of acceptable
+		 * authentication flavors.  This file handle may only
+		 * be used in the NFS version 3 protocol.  This
+		 * procedure also results in the server adding a new
+		 * entry to its mount list recording that this client
+		 * has mounted the directory. AUTH_UNIX authentication
+		 * or better is required.
+		 */
+		mountres3
+		MOUNTPROC_MNT(dirpath) = 1;
+
+		/*
+		 * Returns the list of remotely mounted filesystems. The 
+		 * mountlist contains one entry for each hostname and 
+		 * directory pair.
+		 */
+		mountlist
+		MOUNTPROC_DUMP(void) = 2;
+
+		/*
+		 * Removes the mount list entry for the directory
+		 * Unix authentication required.
+		 */
+		void
+		MOUNTPROC_UMNT(dirpath) = 3;
+
+		/*
+		 * Removes all of the mount list entries for this client
+		 * Unix authentication required.
+		 */
+		void
+		MOUNTPROC_UMNTALL(void) = 4;
+
+		/*
+		 * Returns a list of all the exported filesystems, and which
+		 * machines are allowed to import it.
+		 */
+		exports
+		MOUNTPROC_EXPORT(void)  = 5;
+	} = 3;
+#endif
+} = 100005;
diff --git a/services/librpc/include/rpcsvc/nfs_prot.x b/services/librpc/include/rpcsvc/nfs_prot.x
new file mode 100644
index 0000000..c1e592c
--- /dev/null
+++ b/services/librpc/include/rpcsvc/nfs_prot.x
@@ -0,0 +1,1265 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#ifndef RPC_HDR
+%#ifndef lint
+%/*static char sccsid[] = "from: @(#)nfs_prot.x 1.2 87/10/12 Copyr 1987 Sun Micro";*/
+%/*static char sccsid[] = "from: @(#)nfs_prot.x	2.1 88/08/01 4.0 RPCSRC";*/
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/nfs_prot.x,v 1.7 1999/08/27 23:45:08 peter Exp $";
+%#endif /* not lint */
+#endif
+
+const NFS_PORT          = 2049;
+const NFS_MAXDATA       = 8192;
+const NFS_MAXPATHLEN    = 1024;
+const NFS_MAXNAMLEN	= 255;
+const NFS_FHSIZE	= 32;
+const NFS_COOKIESIZE	= 4;
+const NFS_FIFO_DEV	= -1;	/* size kludge for named pipes */
+
+/*
+ * File types
+ */
+const NFSMODE_FMT  = 0170000;	/* type of file */
+const NFSMODE_DIR  = 0040000;	/* directory */
+const NFSMODE_CHR  = 0020000;	/* character special */
+const NFSMODE_BLK  = 0060000;	/* block special */
+const NFSMODE_REG  = 0100000;	/* regular */
+const NFSMODE_LNK  = 0120000;	/* symbolic link */
+const NFSMODE_SOCK = 0140000;	/* socket */
+const NFSMODE_FIFO = 0010000;	/* fifo */
+
+/*
+ * Error status
+ */
+enum nfsstat {
+	NFS_OK= 0,		/* no error */
+	NFSERR_PERM=1,		/* Not owner */
+	NFSERR_NOENT=2,		/* No such file or directory */
+	NFSERR_IO=5,		/* I/O error */
+	NFSERR_NXIO=6,		/* No such device or address */
+	NFSERR_ACCES=13,	/* Permission denied */
+	NFSERR_EXIST=17,	/* File exists */
+	NFSERR_NODEV=19,	/* No such device */
+	NFSERR_NOTDIR=20,	/* Not a directory*/
+	NFSERR_ISDIR=21,	/* Is a directory */
+	NFSERR_FBIG=27,		/* File too large */
+	NFSERR_NOSPC=28,	/* No space left on device */
+	NFSERR_ROFS=30,		/* Read-only file system */
+	NFSERR_NAMETOOLONG=63,	/* File name too long */
+	NFSERR_NOTEMPTY=66,	/* Directory not empty */
+	NFSERR_DQUOT=69,	/* Disc quota exceeded */
+	NFSERR_STALE=70,	/* Stale NFS file handle */
+	NFSERR_WFLUSH=99	/* write cache flushed */
+};
+
+/*
+ * File types
+ */
+enum ftype {
+	NFNON = 0,	/* non-file */
+	NFREG = 1,	/* regular file */
+	NFDIR = 2,	/* directory */
+	NFBLK = 3,	/* block special */
+	NFCHR = 4,	/* character special */
+	NFLNK = 5,	/* symbolic link */
+	NFSOCK = 6,	/* unix domain sockets */
+	NFBAD = 7,	/* unused */
+	NFFIFO = 8 	/* named pipe */
+};
+
+/*
+ * File access handle
+ */
+struct nfs_fh {
+	opaque data[NFS_FHSIZE];
+};
+
+/* 
+ * Timeval
+ */
+struct nfstime {
+	unsigned seconds;
+	unsigned useconds;
+};
+
+
+/*
+ * File attributes
+ */
+struct fattr {
+	ftype type;		/* file type */
+	unsigned mode;		/* protection mode bits */
+	unsigned nlink;		/* # hard links */
+	unsigned uid;		/* owner user id */
+	unsigned gid;		/* owner group id */
+	unsigned size;		/* file size in bytes */
+	unsigned blocksize;	/* prefered block size */
+	unsigned rdev;		/* special device # */
+	unsigned blocks;	/* Kb of disk used by file */
+	unsigned fsid;		/* device # */
+	unsigned fileid;	/* inode # */
+	nfstime	atime;		/* time of last access */
+	nfstime	mtime;		/* time of last modification */
+	nfstime	ctime;		/* time of last change */
+};
+
+/*
+ * File attributes which can be set
+ */
+struct sattr {
+	unsigned mode;	/* protection mode bits */
+	unsigned uid;	/* owner user id */
+	unsigned gid;	/* owner group id */
+	unsigned size;	/* file size in bytes */
+	nfstime	atime;	/* time of last access */
+	nfstime	mtime;	/* time of last modification */
+};
+
+
+typedef string filename<NFS_MAXNAMLEN>; 
+typedef string nfspath<NFS_MAXPATHLEN>;
+
+/*
+ * Reply status with file attributes
+ */
+union attrstat switch (nfsstat status) {
+case NFS_OK:
+	fattr attributes;
+default:
+	void;
+};
+
+struct sattrargs {
+	nfs_fh file;
+	sattr attributes;
+};
+
+/*
+ * Arguments for directory operations
+ */
+struct diropargs {
+	nfs_fh	dir;	/* directory file handle */
+	filename name;		/* name (up to NFS_MAXNAMLEN bytes) */
+};
+
+struct diropokres {
+	nfs_fh file;
+	fattr attributes;
+};
+
+/*
+ * Results from directory operation
+ */
+union diropres switch (nfsstat status) {
+case NFS_OK:
+	diropokres diropres;
+default:
+	void;
+};
+
+union readlinkres switch (nfsstat status) {
+case NFS_OK:
+	nfspath data;
+default:
+	void;
+};
+
+/*
+ * Arguments to remote read
+ */
+struct readargs {
+	nfs_fh file;		/* handle for file */
+	unsigned offset;	/* byte offset in file */
+	unsigned count;		/* immediate read count */
+	unsigned totalcount;	/* total read count (from this offset)*/
+};
+
+/*
+ * Status OK portion of remote read reply
+ */
+struct readokres {
+	fattr	attributes;	/* attributes, need for pagin*/
+	opaque data<NFS_MAXDATA>;
+};
+
+union readres switch (nfsstat status) {
+case NFS_OK:
+	readokres reply;
+default:
+	void;
+};
+
+/*
+ * Arguments to remote write 
+ */
+struct writeargs {
+	nfs_fh	file;		/* handle for file */
+	unsigned beginoffset;	/* beginning byte offset in file */
+	unsigned offset;	/* current byte offset in file */
+	unsigned totalcount;	/* total write count (to this offset)*/
+	opaque data<NFS_MAXDATA>;
+};
+
+struct createargs {
+	diropargs where;
+	sattr attributes;
+};
+
+struct renameargs {
+	diropargs from;
+	diropargs to;
+};
+
+struct linkargs {
+	nfs_fh from;
+	diropargs to;
+};
+
+struct symlinkargs {
+	diropargs from;
+	nfspath to;
+	sattr attributes;
+};
+
+
+typedef opaque nfscookie[NFS_COOKIESIZE];
+
+/*
+ * Arguments to readdir
+ */
+struct readdirargs {
+	nfs_fh dir;		/* directory handle */
+	nfscookie cookie;
+	unsigned count;		/* number of directory bytes to read */
+};
+
+struct entry {
+	unsigned fileid;
+	filename name;
+	nfscookie cookie;
+	entry *nextentry;
+};
+
+struct dirlist {
+	entry *entries;
+	bool eof;
+};
+
+union readdirres switch (nfsstat status) {
+case NFS_OK:
+	dirlist reply;
+default:
+	void;
+};
+
+struct statfsokres {
+	unsigned tsize;	/* preferred transfer size in bytes */
+	unsigned bsize;	/* fundamental file system block size */
+	unsigned blocks;	/* total blocks in file system */
+	unsigned bfree;	/* free blocks in fs */
+	unsigned bavail;	/* free blocks avail to non-superuser */
+};
+
+union statfsres switch (nfsstat status) {
+case NFS_OK:
+	statfsokres reply;
+default:
+	void;
+};
+
+#ifdef WANT_NFS3
+
+/*
+ * NFSv3 constants and types
+ */
+const NFS3_FHSIZE	= 64;	/* maximum size in bytes of a file handle */
+const NFS3_COOKIEVERFSIZE = 8;	/* size of a cookie verifier for READDIR */
+const NFS3_CREATEVERFSIZE = 8;	/* size of the verifier used for CREATE */
+const NFS3_WRITEVERFSIZE = 8;	/* size of the verifier used for WRITE */
+
+typedef unsigned hyper uint64;
+typedef hyper int64;
+typedef unsigned long uint32;
+typedef long int32;
+typedef string filename3<>;
+typedef string nfspath3<>;
+typedef uint64 fileid3;
+typedef uint64 cookie3;
+typedef opaque cookieverf3[NFS3_COOKIEVERFSIZE];
+typedef opaque createverf3[NFS3_CREATEVERFSIZE];
+typedef opaque writeverf3[NFS3_WRITEVERFSIZE];
+typedef uint32 uid3;
+typedef uint32 gid3;
+typedef uint64 size3;
+typedef uint64 offset3;
+typedef uint32 mode3;
+typedef uint32 count3;
+
+/*
+ * Error status (v3)
+ */
+enum nfsstat3 {
+	NFS3_OK	= 0,
+	NFS3ERR_PERM		= 1,
+	NFS3ERR_NOENT		= 2,
+	NFS3ERR_IO		= 5,
+	NFS3ERR_NXIO		= 6,
+	NFS3ERR_ACCES		= 13,
+	NFS3ERR_EXIST		= 17,
+	NFS3ERR_XDEV		= 18,
+	NFS3ERR_NODEV		= 19,
+	NFS3ERR_NOTDIR		= 20,
+	NFS3ERR_ISDIR		= 21,
+	NFS3ERR_INVAL		= 22,
+	NFS3ERR_FBIG		= 27,
+	NFS3ERR_NOSPC		= 28,
+	NFS3ERR_ROFS		= 30,
+	NFS3ERR_MLINK		= 31,
+	NFS3ERR_NAMETOOLONG	= 63,
+	NFS3ERR_NOTEMPTY	= 66,
+	NFS3ERR_DQUOT		= 69,
+	NFS3ERR_STALE		= 70,
+	NFS3ERR_REMOTE		= 71,
+	NFS3ERR_BADHANDLE	= 10001,
+	NFS3ERR_NOT_SYNC	= 10002,
+	NFS3ERR_BAD_COOKIE	= 10003,
+	NFS3ERR_NOTSUPP		= 10004,
+	NFS3ERR_TOOSMALL	= 10005,
+	NFS3ERR_SERVERFAULT	= 10006,
+	NFS3ERR_BADTYPE		= 10007,
+	NFS3ERR_JUKEBOX		= 10008
+};
+
+/*
+ * File types (v3)
+ */
+enum ftype3 {
+	NF3REG	= 1,		/* regular file */
+	NF3DIR	= 2,		/* directory */
+	NF3BLK	= 3,		/* block special */
+	NF3CHR	= 4,		/* character special */
+	NF3LNK	= 5,		/* symbolic link */
+	NF3SOCK	= 6,		/* unix domain sockets */
+	NF3FIFO	= 7		/* named pipe */
+};
+
+struct specdata3 {
+	uint32	specdata1;
+	uint32	specdata2;
+};
+
+/*
+ * File access handle (v3)
+ */
+struct nfs_fh3 {
+	opaque data<NFS3_FHSIZE>;
+};
+
+/* 
+ * Timeval (v3)
+ */
+struct nfstime3 {
+	uint32	seconds;
+	uint32	nseconds;
+};
+
+
+/*
+ * File attributes (v3)
+ */
+struct fattr3 {
+	ftype3	type;		/* file type */
+	mode3	mode;		/* protection mode bits */
+	uint32	nlink;		/* # hard links */
+	uid3	uid;		/* owner user id */
+	gid3	gid;		/* owner group id */
+	size3	size;		/* file size in bytes */
+	size3	used;		/* prefered block size */
+	specdata3 rdev;		/* special device # */
+	uint64 fsid;		/* device # */
+	fileid3	fileid;		/* inode # */
+	nfstime3 atime;		/* time of last access */
+	nfstime3 mtime;		/* time of last modification */
+	nfstime3 ctime;		/* time of last change */
+};
+
+union post_op_attr switch (bool attributes_follow) {
+case TRUE:
+	fattr3	attributes;
+case FALSE:
+	void;
+};
+
+struct wcc_attr {
+	size3	size;
+	nfstime3 mtime;
+	nfstime3 ctime;
+};
+
+union pre_op_attr switch (bool attributes_follow) {
+case TRUE:
+	wcc_attr attributes;
+case FALSE:
+	void;
+};
+
+struct wcc_data {
+	pre_op_attr before;
+	post_op_attr after;
+};
+
+union post_op_fh3 switch (bool handle_follows) {
+case TRUE:
+	nfs_fh3	handle;
+case FALSE:
+	void;
+};
+
+/*
+ * File attributes which can be set (v3)
+ */
+enum time_how {
+	DONT_CHANGE		= 0,
+	SET_TO_SERVER_TIME	= 1,
+	SET_TO_CLIENT_TIME	= 2
+};
+
+union set_mode3 switch (bool set_it) {
+case TRUE:
+	mode3	mode;
+default:
+	void;
+};
+
+union set_uid3 switch (bool set_it) {
+case TRUE:
+	uid3	uid;
+default:
+	void;
+};
+
+union set_gid3 switch (bool set_it) {
+case TRUE:
+	gid3	gid;
+default:
+	void;
+};
+
+union set_size3 switch (bool set_it) {
+case TRUE:
+	size3	size;
+default:
+	void;
+};
+
+union set_atime switch (time_how set_it) {
+case SET_TO_CLIENT_TIME:
+	nfstime3	atime;
+default:
+	void;
+};
+
+union set_mtime switch (time_how set_it) {
+case SET_TO_CLIENT_TIME:
+	nfstime3	mtime;
+default:
+	void;
+};
+
+struct sattr3 {
+	set_mode3	mode;
+	set_uid3	uid;
+	set_gid3	gid;
+	set_size3	size;
+	set_atime	atime;
+	set_mtime	mtime;
+};
+
+/*
+ * Arguments for directory operations (v3)
+ */
+struct diropargs3 {
+	nfs_fh3	dir;		/* directory file handle */
+	filename3 name;		/* name (up to NFS_MAXNAMLEN bytes) */
+};
+
+/*
+ * Arguments to getattr (v3).
+ */
+struct GETATTR3args {
+	nfs_fh3		object;
+};
+
+struct GETATTR3resok {
+	fattr3		obj_attributes;
+};
+
+union GETATTR3res switch (nfsstat3 status) {
+case NFS3_OK:
+	GETATTR3resok	resok;
+default:
+	void;
+};
+
+/*
+ * Arguments to setattr (v3).
+ */
+union sattrguard3 switch (bool check) {
+case TRUE:
+	nfstime3	obj_ctime;
+case FALSE:
+	void;
+};
+
+struct SETATTR3args {
+	nfs_fh3		object;
+	sattr3		new_attributes;
+	sattrguard3	guard;
+};
+
+struct SETATTR3resok {
+	wcc_data	obj_wcc;
+};
+
+struct SETATTR3resfail {
+	wcc_data	obj_wcc;
+};
+
+union SETATTR3res switch (nfsstat3 status) {
+case NFS3_OK:
+	SETATTR3resok	resok;
+default:
+	SETATTR3resfail	resfail;
+};
+
+/*
+ * Arguments to lookup (v3).
+ */
+struct LOOKUP3args {
+	diropargs3	what;
+};
+
+struct LOOKUP3resok {
+	nfs_fh3		object;
+	post_op_attr	obj_attributes;
+	post_op_attr	dir_attributes;
+};
+
+struct LOOKUP3resfail {
+	post_op_attr	dir_attributes;
+};
+
+union LOOKUP3res switch (nfsstat3 status) {
+case NFS3_OK:
+	LOOKUP3resok	resok;
+default:
+	LOOKUP3resfail	resfail;
+};
+
+/*
+ * Arguments to access (v3).
+ */
+const ACCESS3_READ	= 0x0001;
+const ACCESS3_LOOKUP	= 0x0002;
+const ACCESS3_MODIFY	= 0x0004;
+const ACCESS3_EXTEND	= 0x0008;
+const ACCESS3_DELETE	= 0x0010;
+const ACCESS3_EXECUTE	= 0x0020;
+
+struct ACCESS3args {
+	nfs_fh3		object;
+	uint32		access;
+};
+
+struct ACCESS3resok {
+	post_op_attr	obj_attributes;
+	uint32		access;
+};
+
+struct ACCESS3resfail {
+	post_op_attr	obj_attributes;
+};
+
+union ACCESS3res switch (nfsstat3 status) {
+case NFS3_OK:
+	ACCESS3resok	resok;
+default:
+	ACCESS3resfail	resfail;
+};
+
+/*
+ * Arguments to readlink (v3).
+ */
+struct READLINK3args {
+	nfs_fh3		symlink;
+};
+
+struct READLINK3resok {
+	post_op_attr	symlink_attributes;
+	nfspath3	data;
+};
+
+struct READLINK3resfail {
+	post_op_attr	symlink_attributes;
+};
+
+union READLINK3res switch (nfsstat3 status) {
+case NFS3_OK:
+	READLINK3resok	resok;
+default:
+	READLINK3resfail resfail;
+};
+
+/*
+ * Arguments to read (v3).
+ */
+struct READ3args {
+	nfs_fh3		file;
+	offset3		offset;
+	count3		count;
+};
+
+struct READ3resok {
+	post_op_attr	file_attributes;
+	count3		count;
+	bool		eof;
+	opaque		data<>;
+};
+
+struct READ3resfail {
+	post_op_attr	file_attributes;
+};
+
+/* XXX: solaris 2.6 uses ``nfsstat'' here */
+union READ3res switch (nfsstat3 status) {
+case NFS3_OK:
+	READ3resok	resok;
+default:
+	READ3resfail	resfail;
+};
+
+/*
+ * Arguments to write (v3).
+ */
+enum stable_how {
+	UNSTABLE	= 0,
+	DATA_SYNC	= 1,
+	FILE_SYNC	= 2
+};
+
+struct WRITE3args {
+	nfs_fh3		file;
+	offset3		offset;
+	count3		count;
+	stable_how	stable;
+	opaque		data<>;
+};
+
+struct WRITE3resok {
+	wcc_data	file_wcc;
+	count3		count;
+	stable_how	committed;
+	writeverf3	verf;
+};
+
+struct WRITE3resfail {
+	wcc_data	file_wcc;
+};
+
+union WRITE3res switch (nfsstat3 status) {
+case NFS3_OK:
+	WRITE3resok	resok;
+default:
+	WRITE3resfail	resfail;
+};
+
+/*
+ * Arguments to create (v3).
+ */
+enum createmode3 {
+	UNCHECKED	= 0,
+	GUARDED		= 1,
+	EXCLUSIVE	= 2
+};
+
+union createhow3 switch (createmode3 mode) {
+case UNCHECKED:
+case GUARDED:
+	sattr3		obj_attributes;
+case EXCLUSIVE:
+	createverf3	verf;
+};
+
+struct CREATE3args {
+	diropargs3	where;
+	createhow3	how;
+};
+
+struct CREATE3resok {
+	post_op_fh3	obj;
+	post_op_attr	obj_attributes;
+	wcc_data	dir_wcc;
+};
+
+struct CREATE3resfail {
+	wcc_data	dir_wcc;
+};
+
+union CREATE3res switch (nfsstat3 status) {
+case NFS3_OK:
+	CREATE3resok	resok;
+default:
+	CREATE3resfail	resfail;
+};
+
+/*
+ * Arguments to mkdir (v3).
+ */
+struct MKDIR3args {
+	diropargs3	where;
+	sattr3		attributes;
+};
+
+struct MKDIR3resok {
+	post_op_fh3	obj;
+	post_op_attr	obj_attributes;
+	wcc_data	dir_wcc;
+};
+
+struct MKDIR3resfail {
+	wcc_data	dir_wcc;
+};
+
+union MKDIR3res switch (nfsstat3 status) {
+case NFS3_OK:
+	MKDIR3resok	resok;
+default:
+	MKDIR3resfail	resfail;
+};
+
+/*
+ * Arguments to symlink (v3).
+ */
+struct symlinkdata3 {
+	sattr3		symlink_attributes;
+	nfspath3	symlink_data;
+};
+
+struct SYMLINK3args {
+	diropargs3	where;
+	symlinkdata3	symlink;
+};
+
+struct SYMLINK3resok {
+	post_op_fh3	obj;
+	post_op_attr	obj_attributes;
+	wcc_data	dir_wcc;
+};
+
+struct SYMLINK3resfail {
+	wcc_data	dir_wcc;
+};
+
+union SYMLINK3res switch (nfsstat3 status) {
+case NFS3_OK:
+	SYMLINK3resok	resok;
+default:
+	SYMLINK3resfail	resfail;
+};
+
+/*
+ * Arguments to mknod (v3).
+ */
+struct devicedata3 {
+	sattr3		dev_attributes;
+	specdata3	spec;
+};
+
+union mknoddata3 switch (ftype3 type) {
+case NF3CHR:
+case NF3BLK:
+	devicedata3	device;
+case NF3SOCK:
+case NF3FIFO:
+	sattr3		pipe_attributes;
+default:
+	void;
+};
+
+struct MKNOD3args {
+	diropargs3	where;
+	mknoddata3	what;
+};
+
+struct MKNOD3resok {
+	post_op_fh3	obj;
+	post_op_attr	obj_attributes;
+	wcc_data	dir_wcc;
+};
+
+struct MKNOD3resfail {
+	wcc_data	dir_wcc;
+};
+
+union MKNOD3res switch (nfsstat3 status) {
+case NFS3_OK:
+	MKNOD3resok	resok;
+default:
+	MKNOD3resfail	resfail;
+};
+
+/*
+ * Arguments to remove (v3).
+ */
+struct REMOVE3args {
+	diropargs3	object;
+};
+
+struct REMOVE3resok {
+	wcc_data	dir_wcc;
+};
+
+struct REMOVE3resfail {
+	wcc_data	dir_wcc;
+};
+
+union REMOVE3res switch (nfsstat3 status) {
+case NFS3_OK:
+	REMOVE3resok	resok;
+default:
+	REMOVE3resfail	resfail;
+};
+
+/*
+ * Arguments to rmdir (v3).
+ */
+struct RMDIR3args {
+	diropargs3	object;
+};
+
+struct RMDIR3resok {
+	wcc_data	dir_wcc;
+};
+
+struct RMDIR3resfail {
+	wcc_data	dir_wcc;
+};
+
+union RMDIR3res switch (nfsstat3 status) {
+case NFS3_OK:
+	RMDIR3resok	resok;
+default:
+	RMDIR3resfail	resfail;
+};
+
+/*
+ * Arguments to rename (v3).
+ */
+struct RENAME3args {
+	diropargs3	from;
+	diropargs3	to;
+};
+
+struct RENAME3resok {
+	wcc_data	fromdir_wcc;
+	wcc_data	todir_wcc;
+};
+
+struct RENAME3resfail {
+	wcc_data	fromdir_wcc;
+	wcc_data	todir_wcc;
+};
+
+union RENAME3res switch (nfsstat3 status) {
+case NFS3_OK:
+	RENAME3resok	resok;
+default:
+	RENAME3resfail	resfail;
+};
+
+/*
+ * Arguments to link (v3).
+ */
+struct LINK3args {
+	nfs_fh3		file;
+	diropargs3	link;
+};
+
+struct LINK3resok {
+	post_op_attr	file_attributes;
+	wcc_data	linkdir_wcc;
+};
+
+struct LINK3resfail {
+	post_op_attr	file_attributes;
+	wcc_data	linkdir_wcc;
+};
+
+union LINK3res switch (nfsstat3 status) {
+case NFS3_OK:
+	LINK3resok	resok;
+default:
+	LINK3resfail	resfail;
+};
+
+/*
+ * Arguments to readdir (v3).
+ */
+struct READDIR3args {
+	nfs_fh3		dir;
+	cookie3		cookie;
+	cookieverf3	cookieverf;
+	count3		count;
+};
+
+struct entry3 {
+	fileid3		fileid;
+	filename3	name;
+	cookie3		cookie;
+	entry3		*nextentry;
+};
+
+struct dirlist3 {
+	entry3		*entries;
+	bool		eof;
+};
+
+struct READDIR3resok {
+	post_op_attr	dir_attributes;
+	cookieverf3	cookieverf;
+	dirlist3	reply;
+};
+
+struct READDIR3resfail {
+	post_op_attr	dir_attributes;
+};
+
+union READDIR3res switch (nfsstat3 status) {
+case NFS3_OK:
+	READDIR3resok	resok;
+default:
+	READDIR3resfail	resfail;
+};
+
+/*
+ * Arguments to readdirplus (v3).
+ */
+struct READDIRPLUS3args {
+	nfs_fh3		dir;
+	cookie3		cookie;
+	cookieverf3	cookieverf;
+	count3		dircount;
+	count3		maxcount;
+};
+
+struct entryplus3 {
+	fileid3		fileid;
+	filename3	name;
+	cookie3		cookie;
+	post_op_attr	name_attributes;
+	post_op_fh3	name_handle;
+	entryplus3	*nextentry;
+};
+
+struct dirlistplus3 {
+	entryplus3	*entries;
+	bool		eof;
+};
+
+struct READDIRPLUS3resok {
+	post_op_attr	dir_attributes;
+	cookieverf3	cookieverf;
+	dirlistplus3	reply;
+};
+
+struct READDIRPLUS3resfail {
+	post_op_attr	dir_attributes;
+};
+
+union READDIRPLUS3res switch (nfsstat3 status) {
+case NFS3_OK:
+	READDIRPLUS3resok	resok;
+default:
+	READDIRPLUS3resfail	resfail;
+};
+
+/*
+ * Arguments to fsstat (v3).
+ */
+struct FSSTAT3args {
+	nfs_fh3		fsroot;
+};
+
+struct FSSTAT3resok {
+	post_op_attr	obj_attributes;
+	size3		tbytes;
+	size3		fbytes;
+	size3		abytes;
+	size3		tfiles;
+	size3		ffiles;
+	size3		afiles;
+	uint32		invarsec;
+};
+
+struct FSSTAT3resfail {
+	post_op_attr	obj_attributes;
+};
+
+union FSSTAT3res switch (nfsstat3 status) {
+case NFS3_OK:
+	FSSTAT3resok	resok;
+default:
+	FSSTAT3resfail	resfail;
+};
+
+/*
+ * Arguments to fsinfo (v3).
+ */
+const FSF3_LINK		= 0x0001;
+const FSF3_SYMLINK	= 0x0002;
+const FSF3_HOMOGENEOUS	= 0x0008;
+const FSF3_CANSETTIME	= 0x0010;
+
+struct FSINFO3args {
+	nfs_fh3		fsroot;
+};
+
+struct FSINFO3resok {
+	post_op_attr	obj_attributes;
+	uint32		rtmax;
+	uint32		rtpref;
+	uint32		rtmult;
+	uint32		wtmax;
+	uint32		wtpref;
+	uint32		wtmult;
+	uint32		dtpref;
+	size3		maxfilesize;
+	nfstime3	time_delta;
+	uint32		properties;
+};
+
+struct FSINFO3resfail {
+	post_op_attr	obj_attributes;
+};
+
+union FSINFO3res switch (nfsstat3 status) {
+case NFS3_OK:
+	FSINFO3resok	resok;
+default:
+	FSINFO3resfail	resfail;
+};
+
+/*
+ * Arguments to pathconf (v3).
+ */
+struct PATHCONF3args {
+	nfs_fh3		object;
+};
+
+struct PATHCONF3resok {
+	post_op_attr	obj_attributes;
+	uint32		linkmax;
+	uint32		name_max;
+	bool		no_trunc;
+	bool		chown_restricted;
+	bool		case_insensitive;
+	bool		case_preserving;
+};
+
+struct PATHCONF3resfail {
+	post_op_attr	obj_attributes;
+};
+
+union PATHCONF3res switch (nfsstat3 status) {
+case NFS3_OK:
+	PATHCONF3resok	resok;
+default:
+	PATHCONF3resfail	resfail;
+};
+
+/*
+ * Arguments to commit (v3).
+ */
+struct COMMIT3args {
+	nfs_fh3		file;
+	offset3		offset;
+	count3		count;
+};
+
+struct COMMIT3resok {
+	wcc_data	file_wcc;
+	writeverf3	verf;
+};
+
+struct COMMIT3resfail {
+	wcc_data	file_wcc;
+};
+
+union COMMIT3res switch (nfsstat3 status) {
+case NFS3_OK:
+	COMMIT3resok	resok;
+default:
+	COMMIT3resfail	resfail;
+};
+
+#endif /* WANT_NFS3 */
+
+/*
+ * Remote file service routines
+ */
+program NFS_PROGRAM {
+	version NFS_VERSION {
+		void 
+		NFSPROC_NULL(void) = 0;
+
+		attrstat 
+		NFSPROC_GETATTR(nfs_fh) =	1;
+
+		attrstat 
+		NFSPROC_SETATTR(sattrargs) = 2;
+
+		void 
+		NFSPROC_ROOT(void) = 3;
+
+		diropres 
+		NFSPROC_LOOKUP(diropargs) = 4;
+
+		readlinkres 
+		NFSPROC_READLINK(nfs_fh) = 5;
+
+		readres 
+		NFSPROC_READ(readargs) = 6;
+
+		void 
+		NFSPROC_WRITECACHE(void) = 7;
+
+		attrstat
+		NFSPROC_WRITE(writeargs) = 8;
+
+		diropres
+		NFSPROC_CREATE(createargs) = 9;
+
+		nfsstat
+		NFSPROC_REMOVE(diropargs) = 10;
+
+		nfsstat
+		NFSPROC_RENAME(renameargs) = 11;
+
+		nfsstat
+		NFSPROC_LINK(linkargs) = 12;
+
+		nfsstat
+		NFSPROC_SYMLINK(symlinkargs) = 13;
+
+		diropres
+		NFSPROC_MKDIR(createargs) = 14;
+
+		nfsstat
+		NFSPROC_RMDIR(diropargs) = 15;
+
+		readdirres
+		NFSPROC_READDIR(readdirargs) = 16;
+
+		statfsres
+		NFSPROC_STATFS(nfs_fh) = 17;
+	} = 2;
+} = 100003;
+#ifdef WANT_NFS3
+program NFS3_PROGRAM {
+	version NFS_V3 {
+		void
+		NFSPROC3_NULL(void)			= 0;
+
+		GETATTR3res
+		NFSPROC3_GETATTR(GETATTR3args)		= 1;
+
+		SETATTR3res
+		NFSPROC3_SETATTR(SETATTR3args)		= 2;
+
+		LOOKUP3res
+		NFSPROC3_LOOKUP(LOOKUP3args)		= 3;
+
+		ACCESS3res
+		NFSPROC3_ACCESS(ACCESS3args)		= 4;
+
+		READLINK3res
+		NFSPROC3_READLINK(READLINK3args)	= 5;
+
+		READ3res
+		NFSPROC3_READ(READ3args)		= 6;
+
+		WRITE3res
+		NFSPROC3_WRITE(WRITE3args)		= 7;
+
+		CREATE3res
+		NFSPROC3_CREATE(CREATE3args)		= 8;
+
+		MKDIR3res
+		NFSPROC3_MKDIR(MKDIR3args)		= 9;
+
+		SYMLINK3res
+		NFSPROC3_SYMLINK(SYMLINK3args)		= 10;
+
+		MKNOD3res
+		NFSPROC3_MKNOD(MKNOD3args)		= 11;
+
+		REMOVE3res
+		NFSPROC3_REMOVE(REMOVE3args)		= 12;
+
+		RMDIR3res
+		NFSPROC3_RMDIR(RMDIR3args)		= 13;
+
+		RENAME3res
+		NFSPROC3_RENAME(RENAME3args)		= 14;
+
+		LINK3res
+		NFSPROC3_LINK(LINK3args)		= 15;
+
+		READDIR3res
+		NFSPROC3_READDIR(READDIR3args)		= 16;
+
+		READDIRPLUS3res
+		NFSPROC3_READDIRPLUS(READDIRPLUS3args)	= 17;
+
+		FSSTAT3res
+		NFSPROC3_FSSTAT(FSSTAT3args)		= 18;
+
+		FSINFO3res
+		NFSPROC3_FSINFO(FSINFO3args)		= 19;
+
+		PATHCONF3res
+		NFSPROC3_PATHCONF(PATHCONF3args)	= 20;
+
+		COMMIT3res
+		NFSPROC3_COMMIT(COMMIT3args)		= 21;
+	} = 3;
+} = 100003;
+#endif
diff --git a/services/librpc/include/rpcsvc/nis.x b/services/librpc/include/rpcsvc/nis.x
new file mode 100644
index 0000000..ba6c6d1
--- /dev/null
+++ b/services/librpc/include/rpcsvc/nis.x
@@ -0,0 +1,466 @@
+%/*
+% * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+% * unrestricted use provided that this legend is included on all tape
+% * media and as a part of the software program in whole or part.  Users
+% * may copy or modify Sun RPC without charge, but are not authorized
+% * to license or distribute it to anyone else except as part of a product or
+% * program developed by the user or with the express written consent of
+% * Sun Microsystems, Inc.
+% *
+% * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+% * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+% * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+% *
+% * Sun RPC is provided with no support and without any obligation on the
+% * part of Sun Microsystems, Inc. to assist in its use, correction,
+% * modification or enhancement.
+% *
+% * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+% * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+% * OR ANY PART THEREOF.
+% *
+% * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+% * or profits or other special, indirect and consequential damages, even if
+% * Sun has been advised of the possibility of such damages.
+% *
+% * Sun Microsystems, Inc.
+% * 2550 Garcia Avenue
+% * Mountain View, California  94043
+% */
+
+#ifndef RPC_HDR
+%#ifndef lint
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/nis.x,v 1.3 1999/08/27 23:45:09 peter Exp $";
+%#endif /* not lint */
+#endif
+
+/* 
+ * From 4.1 : @(#)nis.x	1.61 Copyright 1989 Sun Microsystems
+ *
+ * RPC Language Protocol description file for NIS Plus
+ * This version : 1.61
+ * Last Modified : 3/19/91
+ */
+#ifdef RPC_HDR
+%/*
+% *	nis.h
+% *
+% *	This file is the main include file for NIS clients. It contains
+% *	both the client library function defines and the various data
+% * 	structures used by the NIS service. It includes the file nis_tags.h
+% *	which defines the tag values. This allows the tags to change without
+% *	having to change the nis.x file.
+% * 	
+% *	NOTE : DO NOT EDIT THIS FILE! It is automatically generated when
+% *	       rpcgen is run on the nis.x file. Note that there is a 
+% *	       simple sed script to remove some unneeded lines. (See the
+% *	       Makefile target nis.h)
+% *
+% */
+%#include <rpcsvc/nis_tags.h>
+#endif
+
+/* This gets stuffed into the source files. */
+#if RPC_HDR
+%#include <rpc/xdr.h>
+#endif
+/*
+ * This is just pointless.
+ */
+#ifdef SUN_STUPIDITY
+#if RPC_SVC
+%#include "nis_svc.h"
+#endif
+#endif
+
+/* Include the RPC Language description of NIS objects */
+#include "nis_object.x"
+
+/* Errors  that can be returned by the service */
+enum nis_error {
+	NIS_SUCCESS = 0,	/* A-ok, let's rock n roll 	*/
+	NIS_S_SUCCESS = 1,	/* Name found (maybe)	   	*/
+	NIS_NOTFOUND = 2,	/* Name definitely not found 	*/
+	NIS_S_NOTFOUND = 3,	/* Name maybe not found 	*/
+	NIS_CACHEEXPIRED = 4,	/* Name exists but cache out of date */
+	NIS_NAMEUNREACHABLE = 5, /* Can't get there from here */
+	NIS_UNKNOWNOBJ = 6,	/* Object type is bogus */
+	NIS_TRYAGAIN = 7,	/* I'm busy, call back */
+	NIS_SYSTEMERROR = 8,	/* Out of band failure */
+	NIS_CHAINBROKEN = 9,	/* First/Next warning */
+	NIS_PERMISSION = 10,	/* Not enough permission to access */
+	NIS_NOTOWNER = 11,	/* You don't own it, sorry */
+	NIS_NOT_ME = 12,	/* I don't serve this name */
+	NIS_NOMEMORY = 13,	/* Outta VM! Help! */
+	NIS_NAMEEXISTS = 14,	/* Can't create over another name */
+	NIS_NOTMASTER = 15,	/* I'm justa secondaray, don't ask me */
+	NIS_INVALIDOBJ = 16,	/* Object is broken somehow */
+	NIS_BADNAME = 17,	/* Unparsable name */
+	NIS_NOCALLBACK = 18,	/* Couldn't talk to call back proc */
+	NIS_CBRESULTS = 19,	/* Results being called back to you */
+	NIS_NOSUCHNAME = 20,	/* Name unknown */
+	NIS_NOTUNIQUE = 21,	/* Value is not uniques (entry) */
+	NIS_IBMODERROR = 22,	/* Inf. Base. Modify error. */
+	NIS_NOSUCHTABLE = 23,	/* Name for table was wrong */
+	NIS_TYPEMISMATCH = 24, 	/* Entry and table type mismatch */
+	NIS_LINKNAMEERROR = 25,	/* Link points to bogus name */
+	NIS_PARTIAL = 26,	/* Partial success, found table */
+	NIS_TOOMANYATTRS = 27,	/* Too many attributes */
+	NIS_RPCERROR = 28,	/* RPC error encountered */
+	NIS_BADATTRIBUTE = 29,	/* Bad or invalid attribute */
+	NIS_NOTSEARCHABLE = 30,	/* Non-searchable object searched */
+	NIS_CBERROR = 31,	/* Error during callback (svc crash) */
+	NIS_FOREIGNNS = 32,	/* Foreign Namespace */
+	NIS_BADOBJECT = 33,	/* Malformed object structure */
+	NIS_NOTSAMEOBJ = 34,	/* Object swapped during deletion */
+	NIS_MODFAIL = 35,	/* Failure during a Modify. */
+	NIS_BADREQUEST = 36,	/* Illegal query for table */
+	NIS_NOTEMPTY = 37,	/* Attempt to remove a non-empty tbl */
+	NIS_COLDSTART_ERR = 38, /* Error accesing the cold start file */
+	NIS_RESYNC = 39,	/* Transaction log too far out of date */
+	NIS_FAIL = 40,		/* NIS operation failed. */
+	NIS_UNAVAIL = 41,	/* NIS+ service is unavailable (client) */
+	NIS_RES2BIG = 42,	/* NIS+ result too big for datagram */
+	NIS_SRVAUTH = 43,	/* NIS+ server wasn't authenticated. */
+	NIS_CLNTAUTH = 44,	/* NIS+ Client wasn't authenticated. */
+	NIS_NOFILESPACE = 45,	/* NIS+ server ran out of disk space */
+	NIS_NOPROC = 46,	/* NIS+ server couldn't create new proc */
+	NIS_DUMPLATER = 47	/* NIS+ server already has dump child */
+};
+
+
+/* 
+ * Structure definitions for the parameters and results of the actual
+ * NIS RPC calls.
+ *
+ * This is the standard result (in the protocol) of most of the nis 
+ * requests.
+ */
+
+struct nis_result {
+	nis_error	status;		/* Status of the response */
+	nis_object	objects<>;	/* objects found 	  */
+	netobj		cookie;		/* Cookie Data 		  */
+	u_long		zticks;		/* server ticks	 	  */
+	u_long		dticks;		/* DBM ticks.		  */
+	u_long		aticks;		/* Cache (accel) ticks	  */
+	u_long		cticks;		/* Client ticks		  */
+};
+
+/* 
+ * A Name Service request 
+ * This request is used to access the name space, ns_name is the name 
+ * of the object within the namespace and the object is it's value, for
+ * add/modify, a copy of the original for remove. 
+ */
+
+struct ns_request {
+	nis_name	ns_name;	/* Name in the NIS name space	*/
+	nis_object	ns_object<1>;	/* Optional Object (add/remove)	*/
+};
+
+/* 
+ * An information base request
+ * This request includes the NIS name of the table we wish to search, the
+ * search criteria in the form of attribute/value pairs and an optional
+ * callback program number. If the callback program number is provided
+ * the server will send back objects one at a time, otherwise it will
+ * return them all in the response.
+ */
+
+struct ib_request {
+	nis_name  	ibr_name;	/* The name of the Table 	*/
+	nis_attr  	ibr_srch<>; 	/* The search critereia 	*/
+	u_long		ibr_flags;	/* Optional flags 		*/
+	nis_object	ibr_obj<1>;	/* optional object (add/modify) */
+	nis_server	ibr_cbhost<1>;	/* Optional callback info	*/
+	u_long		ibr_bufsize;	/* Optional first/next bufsize	*/
+	netobj		ibr_cookie;	/* The first/next cookie	*/
+};
+
+/*
+ * This argument to the PING call notifies the replicas that something in 
+ * a directory has changed and this is it's timestamp. The replica will use
+ * the timestamp to determine if its resync operation was successful.
+ */
+struct ping_args {
+	nis_name	dir;	/* Directory that had the change */
+	u_long		stamp;	/* timestamp of the transaction  */
+};
+
+/* 
+ * These are the type of entries that are stored in the transaction log, 
+ * note that modifications will appear as two entries, for names, they have
+ * a "OLD" entry followed by a "NEW" entry. For entries in tables, there
+ * is a remove followed by an add. It is done this way so that we can read
+ * the log backwards to back out transactions and forwards to propogate
+ * updated.
+ */
+enum log_entry_t {
+	LOG_NOP = 0,
+	ADD_NAME = 1,		/* Name Added to name space 		  */
+	REM_NAME = 2,		/* Name removed from name space 	  */
+	MOD_NAME_OLD = 3,	/* Name was modified in the name space 	  */
+	MOD_NAME_NEW = 4,	/* Name was modified in the name space 	  */
+	ADD_IBASE = 5,		/* Entry added to information base 	  */
+	REM_IBASE = 6,		/* Entry removed from information base    */
+	MOD_IBASE = 7,		/* Entry was modified in information base */
+	UPD_STAMP = 8		/* Update timestamp (used as fenceposts)  */
+};
+	
+/*
+ * This result is returned from the name service when it is requested to 
+ * dump logged entries from its transaction log. Information base updates
+ * will have the name of the information base in the le_name field and
+ * a canonical set of attribute/value pairs to fully specify the entry's
+ * 'name'. 
+ */
+struct log_entry {
+	u_long		le_time;	/* Time in seconds 		*/
+	log_entry_t	le_type;	/* Type of log entry 		*/
+	nis_name	le_princp;	/* Principal making the change	*/
+	nis_name	le_name;	/* Name of table/dir involved 	*/
+	nis_attr	le_attrs<>;	/* List of AV pairs.		*/
+	nis_object	le_object;	/* Actual object value 		*/
+};
+
+struct log_result {
+	nis_error 	lr_status;	/* The status itself 	 	*/
+	netobj		lr_cookie;	/* Used by the dump callback	*/
+	log_entry	lr_entries<>;	/* zero or more entries 	*/
+};
+	
+struct cp_result {
+	nis_error	cp_status;	/* Status of the checkpoint 	*/
+	u_long		cp_zticks;	/* Service 'ticks' 	    	*/
+	u_long		cp_dticks;	/* Database 'ticks'	    	*/
+};
+
+/*
+ * This structure defines a generic NIS tag list. The taglist contains
+ * zero or tags, each of which is a type and a value. (u_long). 
+ * These are used to report statistics (see tag definitions below)
+ * and to set or reset state variables.
+ */
+struct nis_tag {
+	u_long	tag_type;	/* Statistic tag (may vary) 	 */
+	string	tag_val<1024>;	/* Statistic value may also vary */
+};
+
+struct nis_taglist {
+	nis_tag tags<>;		/* List of tags */
+};
+
+struct dump_args {
+	nis_name	da_dir;		/* Directory to dump 	*/
+	u_long		da_time;	/* From this timestamp	*/
+	nis_server	da_cbhost<1>;	/* Callback to use.	*/
+};
+
+struct fd_args {
+	nis_name	dir_name;  /* The directory we're looking for */
+	nis_name	requester; /* Host principal name for signature */
+};
+
+struct fd_result {
+	nis_error	status;		/* Status returned by function	*/
+	nis_name	source;		/* Source of this answer   	*/
+	opaque		dir_data<>;	/* Directory Data (XDR'ed) 	*/ 
+	opaque		signature<>;	/* Signature of the source 	*/
+};
+
+
+/* 
+ * What's going on here? Well, it's like this. When the service
+ * is being compiled it wants to have the service definition specific
+ * info included, and when the client is being compiled it wants that
+ * info. This includes the appropriate file which was generated by
+ * make in the protocols directory (probably /usr/include/rpcsvc).
+ *
+ * Uhm... guys? With RPC, you aren't supposed to have seperate
+ * server-specific and client-specific header files. You have one header
+ * file that's suitable for both. If your code doesn't work using just
+ * the one header file, I submit to you that it's broken.
+ *							-Bill
+ */
+#ifdef SUN_STUPIDITY
+#ifdef RPC_SVC
+%#include "nis_svc.h"
+#endif
+#ifdef RPC_CLNT
+%#include "nis_clnt.h"
+#endif
+#endif
+
+program  NIS_PROG {
+
+	/* RPC Language description of the NIS+ protocol */
+	version NIS_VERSION {
+		/* The name service functions */
+		nis_result  NIS_LOOKUP(ns_request) = 1;
+		nis_result  NIS_ADD(ns_request) = 2;
+		nis_result  NIS_MODIFY(ns_request) = 3;
+		nis_result  NIS_REMOVE(ns_request) = 4;
+
+		/* The information base functions */
+		nis_result  NIS_IBLIST(ib_request) = 5;
+		nis_result  NIS_IBADD(ib_request) = 6;
+		nis_result  NIS_IBMODIFY(ib_request) = 7;
+		nis_result  NIS_IBREMOVE(ib_request) = 8;
+		nis_result  NIS_IBFIRST(ib_request) = 9;
+		nis_result  NIS_IBNEXT(ib_request) = 10;
+
+		/* NIS Administrative functions */
+		fd_result   NIS_FINDDIRECTORY(fd_args) = 12;
+
+		/* If fetch and optionally reset statistics */
+		nis_taglist  NIS_STATUS(nis_taglist) = 14;
+		
+		/* Dump changes to directory since time in da_time */
+		log_result  NIS_DUMPLOG(dump_args) = 15;
+		
+		/* Dump contents of directory named */
+		log_result  NIS_DUMP(dump_args) = 16;
+
+		/* Check status of callback thread */
+		bool	    NIS_CALLBACK(netobj) = 17;
+
+		/* Return last update time for named dir */
+		u_long      NIS_CPTIME(nis_name) = 18;
+
+		/* Checkpoint directory or table named */
+		cp_result   NIS_CHECKPOINT(nis_name) = 19;
+
+		/* Send 'status changed' ping to replicates */
+		void	    NIS_PING(ping_args) = 20;
+	
+		/* Modify server behaviour (such as debugging) */
+		nis_taglist NIS_SERVSTATE(nis_taglist) = 21;
+	
+		/* Create a Directory */
+		nis_error   NIS_MKDIR(nis_name) = 22;
+	
+		/* Remove a Directory */
+		nis_error   NIS_RMDIR(nis_name) = 23;
+		
+		/* Update public keys of a directory object */
+		nis_error   NIS_UPDKEYS(nis_name) = 24;
+	} = 3;
+} = 100300;
+
+/*
+ * Included below are the defines that become part of nis.h,
+ * they are technically not part of the protocol, but do define
+ * key aspects of the implementation and are therefore useful
+ * in building a conforming server or client.
+ */
+#if RPC_HDR
+%/*
+% * Generic "hash" datastructures, used by all types of hashed data.
+% */
+%struct nis_hash_data {
+%	nis_name		name;	   /* NIS name of hashed item      */
+%	int			keychain;  /* It's hash key (for pop)      */
+%	struct nis_hash_data	*next;	   /* Hash collision pointer       */
+%	struct nis_hash_data	*prv_item; /* A serial, doubly linked list */
+%	struct nis_hash_data	*nxt_item; /* of items in the hash table   */
+%};
+%typedef struct nis_hash_data NIS_HASH_ITEM;
+%
+%struct nis_hash_table {
+%	NIS_HASH_ITEM	*keys[64];	/* A hash table of items           */
+%	NIS_HASH_ITEM	*first;		/* The first "item" in serial list */
+%};
+%typedef struct nis_hash_table NIS_HASH_TABLE;
+%
+%/* Structure for storing dynamically allocated static data */
+%struct nis_sdata {
+%	void	*buf;	/* Memory allocation pointer 	*/
+%	u_long	size;	/* Buffer size			*/
+%};
+%
+%/* Generic client creating flags */
+%#define ZMH_VC		1
+%#define ZMH_DG		2
+%#define ZMH_AUTH	4
+%
+%/* Testing Access rights for objects */
+%
+%#define NIS_READ_ACC		1
+%#define NIS_MODIFY_ACC		2
+%#define NIS_CREATE_ACC		4
+%#define NIS_DESTROY_ACC	8
+%/* Test macros. a == access rights, m == desired rights. */
+%#define WORLD(a, m)	(((a) & (m)) != 0)
+%#define GROUP(a, m)	(((a) & ((m) << 8)) != 0)
+%#define OWNER(a, m)	(((a) & ((m) << 16)) != 0)
+%#define NOBODY(a, m)	(((a) & ((m) << 24)) != 0)
+%
+%#define OATYPE(d, n) (((d)->do_armask.do_armask_val+n)->oa_otype)
+%#define OARIGHTS(d, n) (((d)->do_armask.do_armask_val+n)->oa_rights)
+%#define WORLD_DEFAULT (NIS_READ_ACC)
+%#define GROUP_DEFAULT (NIS_READ_ACC << 8)
+%#define OWNER_DEFAULT ((NIS_READ_ACC +\
+			 NIS_MODIFY_ACC +\
+			 NIS_CREATE_ACC +\
+			 NIS_DESTROY_ACC) << 16)
+%#define DEFAULT_RIGHTS (WORLD_DEFAULT | GROUP_DEFAULT | OWNER_DEFAULT)
+%
+%/* Result manipulation defines ... */
+%#define NIS_RES_NUMOBJ(x)	((x)->objects.objects_len)
+%#define NIS_RES_OBJECT(x)	((x)->objects.objects_val)
+%#define NIS_RES_COOKIE(x)	((x)->cookie)
+%#define NIS_RES_STATUS(x)	((x)->status)
+%
+%/* These defines make getting at the variant part of the object easier. */
+%#define TA_data zo_data.objdata_u.ta_data
+%#define EN_data zo_data.objdata_u.en_data
+%#define DI_data zo_data.objdata_u.di_data
+%#define LI_data zo_data.objdata_u.li_data
+%#define GR_data zo_data.objdata_u.gr_data
+%
+%#define __type_of(o) ((o)->zo_data.zo_type)
+%
+%/* Declarations for the internal subroutines in nislib.c */
+%enum name_pos {SAME_NAME, HIGHER_NAME, LOWER_NAME, NOT_SEQUENTIAL, BAD_NAME};
+%typedef enum name_pos name_pos;
+%
+%/*
+% * Defines for getting at column data in entry objects. Because RPCGEN
+% * generates some rather wordy structures, we create some defines that
+% * collapse the needed keystrokes to access a particular value using
+% * these definitions they take an nis_object *, and an int and return
+% * a u_char * for Value, and an int for length.
+% */
+%#define ENTRY_VAL(obj, col) \
+	(obj)->EN_data.en_cols.en_cols_val[col].ec_value.ec_value_val
+%#define ENTRY_LEN(obj, col) \
+	(obj)->EN_data.en_cols.en_cols_val[col].ec_value.ec_value_len
+%
+%#ifdef __cplusplus
+%}
+%#endif
+%
+%/* Prototypes, and extern declarations for the NIS library functions. */
+%#include <rpcsvc/nislib.h>
+%#endif /* __NIS_RPCGEN_H */
+%/* EDIT_START */
+%
+%/*
+% * nis_3.h
+% * 
+% * This file contains definitions that are only of interest to the actual
+% * service daemon and client stubs. Normal users of NIS will not include
+% * this file.
+% *
+% * NOTE : This include file is automatically created by a combination 
+% * of rpcgen and sed. DO NOT EDIT IT, change the nis.x file instead
+% * and then remake this file.
+% */
+%#ifndef __nis_3_h
+%#define __nis_3_h
+%#ifdef __cplusplus
+%extern "C" {
+%#endif
+#endif
diff --git a/services/librpc/include/rpcsvc/nis_cache.x b/services/librpc/include/rpcsvc/nis_cache.x
new file mode 100644
index 0000000..8343cfd
--- /dev/null
+++ b/services/librpc/include/rpcsvc/nis_cache.x
@@ -0,0 +1,87 @@
+%/*
+% * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+% * unrestricted use provided that this legend is included on all tape
+% * media and as a part of the software program in whole or part.  Users
+% * may copy or modify Sun RPC without charge, but are not authorized
+% * to license or distribute it to anyone else except as part of a product or
+% * program developed by the user or with the express written consent of
+% * Sun Microsystems, Inc.
+% *
+% * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+% * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+% * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+% *
+% * Sun RPC is provided with no support and without any obligation on the
+% * part of Sun Microsystems, Inc. to assist in its use, correction,
+% * modification or enhancement.
+% *
+% * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+% * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+% * OR ANY PART THEREOF.
+% *
+% * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+% * or profits or other special, indirect and consequential damages, even if
+% * Sun has been advised of the possibility of such damages.
+% *
+% * Sun Microsystems, Inc.
+% * 2550 Garcia Avenue
+% * Mountain View, California  94043
+% */
+
+/*
+ *	nis_cache.x
+ *
+ *	Copyright (c) 1988-1992 Sun Microsystems Inc
+ *	All Rights Reserved.
+ */
+
+/* From: %#pragma ident	"@(#)nis_cache.x	1.11	94/05/03 SMI" */
+
+#ifndef RPC_HDR
+%#ifndef lint
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/nis_cache.x,v 1.3 1999/08/27 23:45:09 peter Exp $";
+%#endif /* not lint */
+#endif
+
+#ifdef RPC_HDR
+%#include <rpc/types.h>
+%#include <rpcsvc/nis.h>
+%
+%/* default cache file */
+%#define CACHEFILE "/var/nis/NIS_SHARED_DIRCACHE" 
+%
+%/* clients have to read-lock the cache file, and SVR4 locking requires that */
+%/*   the file be writable, but we don't want a world-writable cache file.   */
+%/*   So... everyone agrees to use a different, world-writable file for the  */
+%/*   locking operations, but the data is in CACHEFILE.                      */
+%#define CACHELOCK "/usr/tmp/.NIS_DIR_CACHELOCK"
+%
+%/* the file containing one trusted XDR'ed directory object.
+% * This has to be present for the system to work.
+% */
+%#define COLD_START_FILE "/var/nis/NIS_COLD_START"
+%
+%enum pc_status {HIT, MISS, NEAR_MISS};
+%
+%extern int __nis_debuglevel;
+%
+%
+#endif
+
+#ifdef RPC_CLNT
+#ifdef SOLARIS
+%#include "../gen/nis_clnt.h"
+#else
+%#include "nis.h"
+#endif
+#endif
+
+program CACHEPROG {
+	version CACHE_VER_1 {
+		void NIS_CACHE_ADD_ENTRY(fd_result) = 1;
+		void NIS_CACHE_REMOVE_ENTRY(directory_obj) = 2;
+		void NIS_CACHE_READ_COLDSTART(void) = 3;
+		void NIS_CACHE_REFRESH_ENTRY(string<>) = 4;
+	} = 1;
+} = 100301;
diff --git a/services/librpc/include/rpcsvc/nis_callback.x b/services/librpc/include/rpcsvc/nis_callback.x
new file mode 100644
index 0000000..4e74aa0
--- /dev/null
+++ b/services/librpc/include/rpcsvc/nis_callback.x
@@ -0,0 +1,76 @@
+%/*
+% * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+% * unrestricted use provided that this legend is included on all tape
+% * media and as a part of the software program in whole or part.  Users
+% * may copy or modify Sun RPC without charge, but are not authorized
+% * to license or distribute it to anyone else except as part of a product or
+% * program developed by the user or with the express written consent of
+% * Sun Microsystems, Inc.
+% *
+% * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+% * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+% * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+% *
+% * Sun RPC is provided with no support and without any obligation on the
+% * part of Sun Microsystems, Inc. to assist in its use, correction,
+% * modification or enhancement.
+% *
+% * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+% * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+% * OR ANY PART THEREOF.
+% *
+% * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+% * or profits or other special, indirect and consequential damages, even if
+% * Sun has been advised of the possibility of such damages.
+% *
+% * Sun Microsystems, Inc.
+% * 2550 Garcia Avenue
+% * Mountain View, California  94043
+% */
+
+/*
+ *	nis_callback.x
+ *
+ *	Copyright (c) 1988-1992 Sun Microsystems Inc
+ *	All Rights Reserved.
+ */
+
+/* From: %#pragma ident	"@(#)nis_callback.x	1.7	94/05/03 SMI" */
+
+#ifndef RPC_HDR
+%#ifndef lint
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/nis_callback.x,v 1.3 1999/08/27 23:45:09 peter Exp $";
+%#endif /* not lint */
+#endif
+
+/*
+ * "@(#)zns_cback.x 1.2 90/09/10 Copyr 1990 Sun Micro" 
+ *
+ * RPCL description of the Callback Service.
+ */
+
+#ifdef RPC_HDR
+%#include <rpcsvc/nis.h>
+#endif
+#ifdef RPC_XDR
+#ifdef SOLARIS
+%#include "nis_clnt.h"
+#else
+%#include "nis.h"
+#endif
+#endif
+
+typedef nis_object	*obj_p;
+
+struct cback_data {
+	obj_p		entries<>;	/* List of objects */
+};
+
+program CB_PROG {
+	version CB_VERS {
+		bool	CBPROC_RECEIVE(cback_data) = 1;
+		void	CBPROC_FINISH(void) = 2;
+		void	CBPROC_ERROR(nis_error) = 3;
+	} = 1;
+} = 100302;
diff --git a/services/librpc/include/rpcsvc/nis_db.h b/services/librpc/include/rpcsvc/nis_db.h
new file mode 100644
index 0000000..71785b0
--- /dev/null
+++ b/services/librpc/include/rpcsvc/nis_db.h
@@ -0,0 +1,164 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ *
+ * $FreeBSD: src/include/rpcsvc/nis_db.h,v 1.5 1999/08/27 23:45:09 peter Exp $
+ */
+
+/*
+ * Copyright (c) 1991, by Sun Microsystems Inc.
+ */
+
+/*
+ * This header file defines the interface to the NIS database. All
+ * implementations of the database must export at least these routines.
+ * They must also follow the conventions set herein. See the implementors
+ * guide for specific semantics that are required.
+ */
+
+#ifndef	_RPCSVC_NIS_DB_H
+#define	_RPCSVC_NIS_DB_H
+
+
+/* From: #pragma ident	"@(#)nis_db.h	1.8	94/05/03 SMI" */
+
+/*
+ * Note: although the version of <rpcsvc/nis_db.h> shipped with Solaris
+ * 2.5/2.5.x is actually older than this one (according to the ident
+ * string), it contains changes and a few added functions. Those changes
+ * have been hand merged into this file to bring it up to date.
+ */
+
+#include <rpc/rpc.h>
+#include <rpcsvc/nis.h>
+
+#ifdef	__cplusplus
+extern "C" {
+#endif
+
+enum db_status {
+	DB_SUCCESS = 0,
+	DB_NOTFOUND = 1,
+	DB_NOTUNIQUE = 2,
+	DB_BADTABLE = 3,
+	DB_BADQUERY = 4,
+	DB_BADOBJECT = 5,
+	DB_MEMORY_LIMIT = 6,
+	DB_STORAGE_LIMIT = 7,
+	DB_INTERNAL_ERROR = 8,
+	_DB_STATUS = 0xffffffff
+};
+typedef enum db_status db_status;
+
+enum db_action {
+	DB_LOOKUP = 0,
+	DB_REMOVE = 1,
+	DB_ADD = 2,
+	DB_FIRST = 3,
+	DB_NEXT = 4,
+	DB_ALL = 5,
+	DB_RESET_NEXT = 6,
+	_DB_ACTION = 0xffffffff
+};
+typedef enum db_action db_action;
+
+typedef entry_obj *entry_object_p;
+
+typedef struct {
+	u_int db_next_desc_len;
+	char *db_next_desc_val;
+} db_next_desc;
+
+struct db_result {
+	db_status status;
+	db_next_desc nextinfo;
+	struct {
+		u_int objects_len;
+		entry_object_p *objects_val;
+	} objects;
+	long ticks;
+};
+typedef struct db_result db_result;
+
+/*
+ * Prototypes for the database functions.
+ */
+
+#if (__STDC__)
+
+extern bool_t db_initialize(char *);
+#ifdef ORIGINAL_DECLS
+extern bool_t db_create_table(char *, table_obj *);
+extern bool_t db_destroy_table(char *);
+#else
+extern db_status db_create_table(char *, table_obj *);
+extern db_status db_destroy_table(char *);
+#endif
+extern db_result *db_first_entry(char *, int, nis_attr *);
+extern db_result *db_next_entry(char *, db_next_desc *);
+extern db_result *db_reset_next_entry(char *, db_next_desc *);
+extern db_result *db_list_entries(char *, int, nis_attr *);
+extern db_result *db_add_entry(char *, int,  nis_attr *, entry_obj *);
+extern db_result *db_remove_entry(char *, int, nis_attr *);
+extern db_status db_checkpoint(char *);
+extern db_status db_standby(char *);
+#ifndef ORIGINAL_DECLS
+extern db_status db_table_exists(char *);
+extern db_status db_unload_table(char *);
+extern void db_free_result(db_result *);
+#endif
+
+#else /* Non-prototype definitions */
+
+extern bool_t db_initialize();
+#ifdef ORIGINAL_DECLS
+extern bool_t db_create_table();
+extern bool_t db_destroy_table();
+#else
+extern db_status db_create_table();
+extern db_status db_destroy_table();
+#endif
+extern db_result *db_first_entry();
+extern db_result *db_next_entry();
+extern db_result *db_reset_next_entry();
+extern db_result *db_list_entries();
+extern db_result *db_add_entry();
+extern db_result *db_remove_entry();
+extern db_status db_checkpoint();
+extern db_status db_standby();
+#ifndef ORIGINAL_DECLS
+extern db_status db_table_exists();
+extern db_status db_unload_table();
+extern void db_free_result();
+#endif
+#endif  /* __STDC__ */
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif	/* _RPCSVC_NIS_DB_H */
diff --git a/services/librpc/include/rpcsvc/nis_object.x b/services/librpc/include/rpcsvc/nis_object.x
new file mode 100644
index 0000000..3156724
--- /dev/null
+++ b/services/librpc/include/rpcsvc/nis_object.x
@@ -0,0 +1,317 @@
+%/*
+% * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+% * unrestricted use provided that this legend is included on all tape
+% * media and as a part of the software program in whole or part.  Users
+% * may copy or modify Sun RPC without charge, but are not authorized
+% * to license or distribute it to anyone else except as part of a product or
+% * program developed by the user or with the express written consent of
+% * Sun Microsystems, Inc.
+% *
+% * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+% * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+% * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+% *
+% * Sun RPC is provided with no support and without any obligation on the
+% * part of Sun Microsystems, Inc. to assist in its use, correction,
+% * modification or enhancement.
+% *
+% * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+% * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+% * OR ANY PART THEREOF.
+% *
+% * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+% * or profits or other special, indirect and consequential damages, even if
+% * Sun has been advised of the possibility of such damages.
+% *
+% * Sun Microsystems, Inc.
+% * 2550 Garcia Avenue
+% * Mountain View, California  94043
+% */
+
+/*
+ *	nis_object.x
+ *
+ *	Copyright (c) 1988-1992 Sun Microsystems Inc
+ *	All Rights Reserved.
+ */
+
+/* From: %#pragma ident	"@(#)nis_object.x	1.10	94/05/03 SMI" */
+
+#if RPC_HDR
+%
+%#ifndef __nis_object_h
+%#define __nis_object_h
+%
+#endif
+/* 
+ * 	This file defines the format for a NIS object in RPC language.
+ * It is included by the main .x file and the database access protocol
+ * file. It is common because both of them need to deal with the same
+ * type of object. Generating the actual code though is a bit messy because
+ * the nis.x file and the nis_dba.x file will generate xdr routines to 
+ * encode/decode objects when only one set is needed. Such is life when
+ * one is using rpcgen.
+ *
+ * Note, the protocol doesn't specify any limits on such things as
+ * maximum name length, number of attributes, etc. These are enforced
+ * by the database backend. When you hit them you will no. Also see
+ * the db_getlimits() function for fetching the limit values.
+ *
+ */
+
+/* Some manifest constants, chosen to maximize flexibility without
+ * plugging the wire full of data.
+ */
+const NIS_MAXSTRINGLEN = 255;
+const NIS_MAXNAMELEN   = 1024;
+const NIS_MAXATTRNAME  = 32;
+const NIS_MAXATTRVAL   = 2048;
+const NIS_MAXCOLUMNS   = 64;
+const NIS_MAXATTR      = 16;
+const NIS_MAXPATH      = 1024;
+const NIS_MAXREPLICAS  = 128;
+const NIS_MAXLINKS     = 16;
+
+const NIS_PK_NONE      = 0;	/* no public key (unix/sys auth) */
+const NIS_PK_DH	       = 1;	/* Public key is Diffie-Hellman type */
+const NIS_PK_RSA       = 2;	/* Public key if RSA type */
+const NIS_PK_KERB      = 3;	/* Use kerberos style authentication */
+
+/*
+ * The fundamental name type of NIS. The name may consist of two parts,
+ * the first being the fully qualified name, and the second being an 
+ * optional set of attribute/value pairs.
+ */
+struct nis_attr {
+	string	zattr_ndx<>;	/* name of the index 		*/
+	opaque	zattr_val<>;	/* Value for the attribute. 	*/
+};
+
+typedef string nis_name<>;	/* The NIS name itself. */
+
+/* NIS object types are defined by the following enumeration. The numbers
+ * they use are based on the following scheme :
+ *		     0 - 1023 are reserved for Sun,
+ * 		1024 - 2047 are defined to be private to a particular tree.
+ *		2048 - 4095 are defined to be user defined.
+ *		4096 - ...  are reserved for future use.
+ */
+
+enum zotypes {
+	BOGUS_OBJ  	= 0,	/* Uninitialized object structure 	*/
+	NO_OBJ   	= 1,	/* NULL object (no data)	 	*/
+	DIRECTORY_OBJ 	= 2,	/* Directory object describing domain 	*/
+	GROUP_OBJ  	= 3,	/* Group object (a list of names) 	*/
+	TABLE_OBJ  	= 4,	/* Table object (a database schema) 	*/
+	ENTRY_OBJ  	= 5,	/* Entry object (a database record) 	*/
+	LINK_OBJ   	= 6, 	/* A name link.				*/
+	PRIVATE_OBJ   	= 7 	/* Private object (all opaque data) 	*/
+};
+
+/*
+ * The types of Name services NIS knows about. They are enumerated
+ * here. The Binder code will use this type to determine if it has
+ * a set of library routines that will access the indicated name service.
+ */
+enum nstype {
+	UNKNOWN = 0,
+	NIS = 1,	/* Nis Plus Service		*/
+	SUNYP = 2,	/* Old NIS Service		*/
+	IVY = 3,	/* Nis Plus Plus Service	*/
+	DNS = 4,	/* Domain Name Service		*/
+	X500 = 5,	/* ISO/CCCIT X.500 Service	*/
+	DNANS = 6,	/* Digital DECNet Name Service	*/
+	XCHS = 7,	/* Xerox ClearingHouse Service	*/
+	CDS= 8
+};
+
+/*
+ * DIRECTORY - The name service object. These objects identify other name
+ * servers that are serving some portion of the name space. Each has a
+ * type associated with it. The resolver library will note whether or not
+ * is has the needed routines to access that type of service. 
+ * The oarmask structure defines an access rights mask on a per object 
+ * type basis for the name spaces. The only bits currently used are 
+ * create and destroy. By enabling or disabling these access rights for
+ * a specific object type for a one of the accessor entities (owner,
+ * group, world) the administrator can control what types of objects 
+ * may be freely added to the name space and which require the 
+ * administrator's approval.
+ */
+struct oar_mask {
+	u_long	oa_rights;	/* Access rights mask 	*/
+	zotypes	oa_otype;	/* Object type 		*/
+};
+
+struct endpoint {
+	string		uaddr<>;
+	string		family<>;   /* Transport family (INET, OSI, etc) */
+	string		proto<>;    /* Protocol (TCP, UDP, CLNP,  etc)   */
+};
+
+/*
+ * Note: pkey is a netobj which is limited to 1024 bytes which limits the
+ * keysize to 8192 bits. This is consider to be a reasonable limit for
+ * the expected lifetime of this service.
+ */
+struct nis_server {
+	nis_name	name; 	 	/* Principal name of the server  */
+	endpoint	ep<>;  		/* Universal addr(s) for server  */
+	u_long		key_type;	/* Public key type		 */
+	netobj		pkey;		/* server's public key  	 */
+};
+
+struct directory_obj {
+	nis_name   do_name;	 /* Name of the directory being served   */
+	nstype	   do_type;	 /* one of NIS, DNS, IVY, YP, or X.500 	 */
+	nis_server do_servers<>; /* <0> == Primary name server     	 */
+	u_long	   do_ttl;	 /* Time To Live (for caches) 		 */
+	oar_mask   do_armask<>;  /* Create/Destroy rights by object type */
+};
+
+/* 
+ * ENTRY - This is one row of data from an information base. 
+ * The type value is used by the client library to convert the entry to 
+ * it's internal structure representation. The Table name is a back pointer
+ * to the table where the entry is stored. This allows the client library 
+ * to determine where to send a request if the client wishes to change this
+ * entry but got to it through a LINK rather than directly.
+ * If the entry is a "standalone" entry then this field is void.
+ */
+const EN_BINARY   = 1;	/* Indicates value is binary data 	*/
+const EN_CRYPT    = 2;	/* Indicates the value is encrypted	*/
+const EN_XDR      = 4;	/* Indicates the value is XDR encoded	*/
+const EN_MODIFIED = 8;	/* Indicates entry is modified. 	*/
+const EN_ASN1     = 64;	/* Means contents use ASN.1 encoding    */
+
+struct entry_col {
+	u_long	ec_flags;	/* Flags for this value */
+	opaque	ec_value<>;	/* It's textual value	*/
+};
+
+struct entry_obj {
+	string 	en_type<>;	/* Type of entry such as "passwd" */
+	entry_col en_cols<>;	/* Value for the entry		  */
+};
+
+/*
+ * GROUP - The group object contains a list of NIS principal names. Groups
+ * are used to authorize principals. Each object has a set of access rights
+ * for members of its group. Principal names in groups are in the form 
+ * name.directory and recursive groups are expressed as @groupname.directory
+ */
+struct group_obj {
+	u_long		gr_flags;	/* Flags controlling group	*/
+	nis_name	gr_members<>;  	/* List of names in group 	*/
+};
+
+/*
+ * LINK - This is the LINK object. It is quite similar to a symbolic link
+ * in the UNIX filesystem. The attributes in the main object structure are
+ * relative to the LINK data and not what it points to (like the file system)
+ * "modify" privleges here indicate the right to modify what the link points
+ * at and not to modify that actual object pointed to by the link.
+ */
+struct link_obj {
+	zotypes	 li_rtype;	/* Real type of the object	*/
+	nis_attr li_attrs<>;	/* Attribute/Values for tables	*/
+	nis_name li_name; 	/* The object's real NIS name	*/
+};
+
+/*
+ * TABLE - This is the table object. It implements a simple 
+ * data base that applications and use for configuration or 
+ * administration purposes. The role of the table is to group together
+ * a set of related entries. Tables are the simple database component
+ * of NIS. Like many databases, tables are logically divided into columns
+ * and rows. The columns are labeled with indexes and each ENTRY makes
+ * up a row. Rows may be addressed within the table by selecting one
+ * or more indexes, and values for those indexes. Each row which has
+ * a value for the given index that matches the desired value is returned.
+ * Within the definition of each column there is a flags variable, this
+ * variable contains flags which determine whether or not the column is
+ * searchable, contains binary data, and access rights for the entry objects
+ * column value. 
+ */
+
+const TA_BINARY     = 1;	/* Means table data is binary 		*/
+const TA_CRYPT      = 2;	/* Means value should be encrypted 	*/
+const TA_XDR        = 4;	/* Means value is XDR encoded		*/
+const TA_SEARCHABLE = 8;	/* Means this column is searchable	*/
+const TA_CASE       = 16;	/* Means this column is Case Sensitive	*/
+const TA_MODIFIED   = 32;	/* Means this columns attrs are modified*/
+const TA_ASN1       = 64;	/* Means contents use ASN.1 encoding     */
+
+struct table_col {
+	string	tc_name<64>;	/* Column Name 	 	   */
+	u_long	tc_flags;	/* control flags	   */
+	u_long	tc_rights;	/* Access rights mask	   */
+};
+
+struct table_obj {
+	string 	  ta_type<64>;	 /* Table type such as "passwd"	*/
+	int	  ta_maxcol;	 /* Total number of columns	*/
+	u_char	  ta_sep;	 /* Separator character 	*/
+	table_col ta_cols<>; 	 /* The number of table indexes */
+	string	  ta_path<>;	 /* A search path for this table */
+};
+
+/*
+ * This union joins together all of the currently known objects. 
+ */
+union objdata switch (zotypes zo_type) {
+        case DIRECTORY_OBJ :
+                struct directory_obj di_data;
+        case GROUP_OBJ :
+                struct group_obj gr_data;
+        case TABLE_OBJ :
+                struct table_obj ta_data;
+        case ENTRY_OBJ:
+                struct entry_obj en_data;
+        case LINK_OBJ :
+                struct link_obj li_data;
+        case PRIVATE_OBJ :
+                opaque	po_data<>;
+	case NO_OBJ :
+		void;
+        case BOGUS_OBJ :
+		void;
+        default :
+                void;
+};
+
+/*
+ * This is the basic NIS object data type. It consists of a generic part
+ * which all objects contain, and a specialized part which varies depending
+ * on the type of the object. All of the specialized sections have been
+ * described above. You might have wondered why they all start with an 
+ * integer size, followed by the useful data. The answer is, when the 
+ * server doesn't recognize the type returned it treats it as opaque data. 
+ * And the definition for opaque data is {int size; char *data;}. In this
+ * way, servers and utility routines that do not understand a given type
+ * may still pass it around. One has to be careful in setting
+ * this variable accurately, it must take into account such things as
+ * XDR padding of structures etc. The best way to set it is to note one's
+ * position in the XDR encoding stream, encode the structure, look at the
+ * new position and calculate the size. 
+ */
+struct nis_oid {
+	u_long	ctime;		/* Time of objects creation 	*/
+	u_long	mtime;		/* Time of objects modification */
+};
+
+struct nis_object {
+	nis_oid	 zo_oid;	/* object identity verifier.		*/ 
+	nis_name zo_name;	/* The NIS name for this object		*/
+	nis_name zo_owner;	/* NIS name of object owner.		*/
+	nis_name zo_group;	/* NIS name of access group.		*/
+	nis_name zo_domain;	/* The administrator for the object	*/
+	u_long	 zo_access;	/* Access rights (owner, group, world)	*/
+	u_long	 zo_ttl;	/* Object's time to live in seconds.	*/
+	objdata	 zo_data;	/* Data structure for this type 	*/
+};
+#if RPC_HDR
+%
+%#endif /* if __nis_object_h */
+%
+#endif
diff --git a/services/librpc/include/rpcsvc/nis_tags.h b/services/librpc/include/rpcsvc/nis_tags.h
new file mode 100644
index 0000000..0eaee6d
--- /dev/null
+++ b/services/librpc/include/rpcsvc/nis_tags.h
@@ -0,0 +1,137 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+/*
+ * Copyright (c) 1991, Sun Microsystems Inc.
+ */
+
+/*
+ *	nis_tags.h
+ *
+ *	This file contains the tags and statistics definitions. It is
+ *	automatically included by nis.h
+ */
+
+#ifndef	_RPCSVC_NIS_TAGS_H
+#define	_RPCSVC_NIS_TAGS_H
+
+/* From: #pragma ident	"@(#)nis_tags.h	1.10	94/05/03 SMI" */
+/* from file: zns_tags.h	1.7 Copyright (c) 1990 Sun Microsystems */
+
+#ifdef	__cplusplus
+extern "C" {
+#endif
+
+#ifndef ORIGINAL_DECLS
+#define		NIS_DIR "data"
+#endif
+
+/* Lookup and List function flags */
+#define	FOLLOW_LINKS	(1<<0)	/* Follow link objects 			*/
+#define	FOLLOW_PATH	(1<<1)	/* Follow the path in a table 		*/
+#define	HARD_LOOKUP	(1<<2)	/* Block until successful 		*/
+#define	ALL_RESULTS	(1<<3)	/* Retrieve all results 		*/
+#define	NO_CACHE	(1<<4)	/* Do not return 'cached' results 	*/
+#define	MASTER_ONLY	(1<<5)	/* Get value only from master server	*/
+#define	EXPAND_NAME	(1<<6)	/* Expand partitially qualified names	*/
+
+/* Semantic modification for table operations flags */
+#define	RETURN_RESULT	(1<<7)	/* Return resulting object to client    */
+#define	ADD_OVERWRITE	(1<<8)	/* Allow overwrites on ADD		*/
+#define	REM_MULTIPLE	(1<<9)	/* Allow wildcard deletes		*/
+#define	MOD_SAMEOBJ	(1<<10)	/* Check modified object before write	*/
+#define	ADD_RESERVED	(1<<11)	/* Spare ADD semantic			*/
+#define	REM_RESERVED	(1<<12)	/* Spare REM semantic			*/
+#ifdef ORIGINAL_DECLS
+#define	MOD_RESERVED	(1<<13)	/* Spare MOD semantic			*/
+#else
+#define	MOD_EXCLUSIVE	(1<<13)	/* Modify no overwrite on modified keys	*/
+#endif
+
+/* Transport specific modifications to the operation */
+#define	USE_DGRAM	(1<<16) /* Use a datagram transport 		*/
+#define	NO_AUTHINFO	(1<<17) /* Don't bother attaching auth info	*/
+
+/*
+ * Declarations for "standard" NIS+ tags
+ * State variable tags have values	0 - 2047
+ * Statistic tags have values		2048 - 65535
+ * User Tags have values		>2^16
+ */
+#define	TAG_DEBUG	1	/* set debug level 		*/
+#define	TAG_STATS	2	/* Enable/disable statistics 	*/
+#define	TAG_GCACHE	3	/* Flush the Group Cache	*/
+#ifndef ORIGINAL_DECLS
+#define	TAG_GCACHE_ALL	TAG_GCACHE
+#endif
+#define	TAG_DCACHE	4	/* Flush the directory cache	*/
+#ifndef ORIGINAL_DECLS
+#define	TAG_DCACHE_ONE	TAG_DCACHE
+#endif
+#define	TAG_OCACHE	5	/* Flush the Object Cache	*/
+#define	TAG_SECURE	6	/* Set the security level 	*/
+#ifndef ORIGINAL_DECLS
+#define	TAG_TCACHE_ONE	7	/* Flush the table cache	*/
+#define	TAG_DCACHE_ALL	8	/* Flush entire directory cache */
+#define TAG_TCACHE_ALL	9	/* Flush entire table cache	*/
+#define	TAG_GCACHE_ONE	10	/* Flush one group object	*/
+#define	TAG_DCACHE_ONE_REFRESH 11 /* Flush and refresh one DO	*/
+#endif
+
+#define	TAG_OPSTATS	2048	/* NIS+ operations statistics   */
+#define	TAG_THREADS	2049	/* Child process/thread status  */
+#define	TAG_HEAP	2050	/* Heap usage statistics	*/
+#define	TAG_UPDATES	2051	/* Updates to this service	*/
+#define	TAG_VISIBLE	2052	/* First update that isn't replicated */
+#define	TAG_S_DCACHE	2053	/* Directory cache statistics	*/
+#define	TAG_S_OCACHE	2054	/* Object cache statistics	*/
+#define	TAG_S_GCACHE	2055	/* Group cache statistics	*/
+#define	TAG_S_STORAGE	2056	/* Group cache statistics	*/
+#define	TAG_UPTIME	2057	/* Time that server has been up */
+#ifndef ORIGINAL_DECLS
+#define	TAG_DIRLIST	2058    /* Dir served by this server	*/
+#define	TAG_NISCOMPAT	2059    /* Whether supports NIS compat mode */
+#define	TAG_DNSFORWARDING 2060	/* Whether DNS forwarding supported*/
+#define	TAG_SECURITY_LEVEL 2061 /* Security level of the server */
+#define	TAG_ROOTSERVER	2062	/* Whether root server		*/
+#endif
+
+/*
+ * Declarations for the Group object flags. Currently
+ * there are only 3.
+ */
+#define	IMPMEM_GROUPS  1	/* Implicit Membership allowed 	*/
+#define	RECURS_GROUPS  2	/* Recursive Groups allowed 	*/
+#define	NEGMEM_GROUPS  4	/* Negative Groups allowed	*/
+
+#ifdef	__cplusplus
+}
+#endif
+
+#endif	/* _RPCSVC_NIS_TAGS_H */
diff --git a/services/librpc/include/rpcsvc/nislib.h b/services/librpc/include/rpcsvc/nislib.h
new file mode 100644
index 0000000..9f874d2
--- /dev/null
+++ b/services/librpc/include/rpcsvc/nislib.h
@@ -0,0 +1,317 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+/*
+ * Copyright (c) 1991, Sun Microsystems Inc.
+ */
+
+/*
+ * This file contains the interfaces that are visible in the SunOS 5.x
+ * implementation of NIS Plus. When using C++ the defined __cplusplus and
+ * __STDC__ should both be true.
+ */
+
+#ifndef	_RPCSVC_NISLIB_H
+#define	_RPCSVC_NISLIB_H
+
+/* From: #pragma ident	"@(#)nislib.h	1.16	94/05/03 SMI" */
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+struct signature {
+	int signature_len;
+	char *signature_val;
+};
+
+#ifdef __STDC__
+extern void nis_freeresult(nis_result *);
+extern nis_result * nis_lookup(nis_name, u_long);
+extern nis_result * nis_list(nis_name, u_long,
+	int (*)(nis_name, nis_object *, void *), void *);
+extern nis_result * nis_add(nis_name, nis_object *);
+extern nis_result * nis_remove(nis_name, nis_object *);
+extern nis_result * nis_modify(nis_name, nis_object *);
+
+extern nis_result * nis_add_entry(nis_name, nis_object *, u_long);
+extern nis_result * nis_remove_entry(nis_name, nis_object *, u_long);
+extern nis_result * nis_modify_entry(nis_name, nis_object *, u_long);
+extern nis_result * nis_first_entry(nis_name);
+extern nis_result * nis_next_entry(nis_name, netobj *);
+
+extern nis_error nis_mkdir(nis_name, nis_server *);
+extern nis_error nis_rmdir(nis_name, nis_server *);
+extern name_pos nis_dir_cmp(nis_name, nis_name);
+
+extern nis_name * nis_getnames(nis_name);
+extern void nis_freenames(nis_name *);
+extern nis_name nis_domain_of(nis_name);
+extern nis_name nis_leaf_of(nis_name);
+extern nis_name nis_leaf_of_r(const nis_name, char *, size_t);
+extern nis_name nis_name_of(nis_name);
+extern nis_name nis_local_group(void);
+extern nis_name nis_local_directory(void);
+extern nis_name nis_local_principal(void);
+extern nis_name nis_local_host(void);
+
+extern void nis_destroy_object(nis_object *);
+extern nis_object * nis_clone_object(nis_object *, nis_object *);
+extern void nis_print_object(nis_object *);
+
+extern char * nis_sperrno(nis_error);
+extern void nis_perror(nis_error, char *);
+extern char * nis_sperror(nis_error, char *);
+extern void nis_lerror(nis_error, char *);
+
+extern void nis_print_group_entry(nis_name);
+extern bool_t nis_ismember(nis_name, nis_name);
+extern nis_error nis_creategroup(nis_name, u_long);
+extern nis_error nis_destroygroup(nis_name);
+extern nis_error nis_addmember(nis_name, nis_name);
+extern nis_error nis_removemember(nis_name, nis_name);
+extern nis_error nis_verifygroup(nis_name);
+
+extern void nis_freeservlist(nis_server **);
+extern nis_server ** nis_getservlist(nis_name);
+extern nis_error nis_stats(nis_server *, nis_tag *, int, nis_tag **);
+extern nis_error nis_servstate(nis_server *, nis_tag *, int, nis_tag **);
+extern void nis_freetags(nis_tag *, int);
+
+extern nis_result * nis_checkpoint(nis_name);
+extern void nis_ping(nis_name, u_long, nis_object *);
+
+/*
+ * XXX: PLEASE NOTE THAT THE FOLLOWING FUNCTIONS ARE INTERNAL
+ * TO NIS+ AND SHOULD NOT BE USED BY ANY APPLICATION PROGRAM.
+ * THEIR SEMANTICS AND/OR SIGNATURE CAN CHANGE WITHOUT NOTICE.
+ * SO, PLEASE DO NOT USE THEM.  YOU ARE WARNED!!!!
+ */
+
+extern char ** __break_name(nis_name, int *);
+extern int __name_distance(char **, char **);
+extern nis_result * nis_make_error(nis_error, u_long, u_long, u_long, u_long);
+extern nis_attr * __cvt2attr(int *, char **);
+extern void nis_free_request(ib_request *);
+extern nis_error nis_get_request(nis_name, nis_object *, netobj*, ib_request*);
+extern nis_object * nis_read_obj(char *);
+extern int nis_write_obj(char *, nis_object *);
+extern int nis_in_table(nis_name, NIS_HASH_TABLE *, int *);
+extern int nis_insert_item(NIS_HASH_ITEM *, NIS_HASH_TABLE *);
+extern NIS_HASH_ITEM * nis_find_item(nis_name, NIS_HASH_TABLE *);
+extern NIS_HASH_ITEM * nis_remove_item(nis_name, NIS_HASH_TABLE *);
+extern void nis_insert_name(nis_name, NIS_HASH_TABLE *);
+extern void nis_remove_name(nis_name, NIS_HASH_TABLE *);
+extern CLIENT * nis_make_rpchandle(nis_server *, int, u_long, u_long, u_long,
+								int, int);
+extern void * nis_get_static_storage(struct nis_sdata *, u_long, u_long);
+extern char * nis_data(char *);
+extern void nis_print_rights(u_long);
+extern void nis_print_directory(directory_obj *);
+extern void nis_print_group(group_obj *);
+extern void nis_print_table(table_obj *);
+extern void nis_print_link(link_obj *);
+extern void nis_print_entry(entry_obj *);
+extern nis_object * nis_get_object(char *, char *, char *, u_long, u_long,
+								    zotypes);
+extern nis_server * __nis_init_callback(CLIENT *,
+    int (*)(nis_name, nis_object *, void *), void *);
+extern int nis_getdtblsize(void);
+extern int __nis_run_callback(netobj *, u_long, struct timeval *, CLIENT *);
+
+extern log_result *nis_dumplog(nis_server *, nis_name, u_long);
+extern log_result *nis_dump(nis_server *, nis_name,
+    int (*)(nis_name, nis_object *, void *));
+
+extern bool_t __do_ismember(nis_name, nis_name,
+    nis_result *(*)(nis_name, u_long));
+extern nis_name __nis_map_group(nis_name);
+extern nis_name __nis_map_group_r(nis_name, char*, size_t);
+
+extern nis_error __nis_CacheBind(char *, directory_obj *);
+extern nis_error __nis_CacheSearch(char *, directory_obj *);
+extern bool_t __nis_CacheRemoveEntry(directory_obj *);
+extern void __nis_CacheRestart(void);
+extern void __nis_CachePrint(void);
+extern void __nis_CacheDumpStatistics(void);
+extern bool_t writeColdStartFile(directory_obj *);
+
+extern CLIENT * __get_ti_clnt(char *, CLIENT *, char **, pid_t *);
+extern int __strcmp_case_insens(char *, char *);
+extern int __strncmp_case_insens(char *, char *);
+
+extern fd_result * nis_finddirectory(directory_obj *, nis_name);
+extern int __start_clock(int);
+extern u_long __stop_clock(int);
+
+/*
+ * This particular function is part of the FreeBSD NIS+ implementation
+ * only. Ideally it should be somewhere else, but it is used by both
+ * rpc.nisd and nis_cachemgr, and there aren't that many headers common
+ * to both programs.
+ */
+
+extern struct signature *__nis_calculate_encrypted_cksum(unsigned char *, unsigned int, char *, int);
+
+#else
+
+/* Non-prototype definitions (old fashioned C) */
+
+extern void nis_freeresult();
+extern nis_result * nis_lookup();
+extern nis_result * nis_list();
+extern nis_result * nis_add();
+extern nis_result * nis_remove();
+extern nis_result * nis_modify();
+
+extern nis_result * nis_add_entry();
+extern nis_result * nis_remove_entry();
+extern nis_result * nis_modify_entry();
+extern nis_result * nis_first_entry();
+extern nis_result * nis_next_entry();
+
+extern nis_error nis_mkdir();
+extern nis_error nis_rmdir();
+extern name_pos nis_dir_cmp();
+
+extern nis_name *nis_getnames();
+extern void nis_freenames();
+extern nis_name nis_domain_of();
+extern nis_name nis_leaf_of();
+extern nis_name nis_leaf_of_r();
+extern nis_name nis_name_of();
+extern nis_name nis_local_group();
+extern nis_name nis_local_directory();
+extern nis_name nis_local_principal();
+extern nis_name nis_local_host();
+
+extern void nis_destroy_object();
+extern nis_object * nis_clone_object();
+extern void nis_print_object();
+
+extern char * nis_sperrno();
+extern void nis_perror();
+extern char * nis_sperror();
+extern void nis_lerror();
+
+extern void nis_print_group_entry();
+extern bool_t nis_ismember();
+extern nis_error nis_creategroup();
+extern nis_error nis_destroygroup();
+extern nis_error nis_addmember();
+extern nis_error nis_removemember();
+extern nis_error nis_verifygroup();
+
+extern void nis_freeservlist();
+extern nis_server ** nis_getservlist();
+extern nis_error nis_stats();
+extern nis_error nis_servstate();
+extern void nis_freetags();
+
+extern nis_result * nis_checkpoint();
+extern void nis_ping();
+
+/*
+ * XXX: PLEASE NOTE THAT THE FOLLOWING FUNCTIONS ARE INTERNAL
+ * TO NIS+ AND SHOULD NOT BE USED BY ANY APPLICATION PROGRAM.
+ * THEIR SEMANTICS AND/OR SIGNATURE CAN CHANGE WITHOUT NOTICE.
+ * SO, PLEASE DO NOT USE THEM.  YOU ARE WARNED!!!!
+ */
+extern char ** __break_name();
+extern int __name_distance();
+extern nis_result * nis_make_error();
+extern nis_attr * __cvt2attr();
+extern void nis_free_request();
+extern nis_error nis_get_request();
+extern nis_object * nis_read_obj();
+extern int nis_write_obj();
+extern int nis_in_table();
+extern int nis_insert_item();
+extern NIS_HASH_ITEM * nis_find_item();
+extern NIS_HASH_ITEM * nis_remove_item();
+extern void nis_insert_name();
+extern void nis_remove_name();
+extern CLIENT * nis_make_rpchandle();
+extern void * nis_get_static_storage();
+extern char * nis_data();
+
+extern void nis_print_rights();
+extern void nis_print_directory();
+extern void nis_print_group();
+extern void nis_print_table();
+extern void nis_print_link();
+extern void nis_print_entry();
+extern nis_object * nis_get_object();
+
+extern nis_server * __nis_init_callback();
+extern int nis_getdtblsize();
+extern int __nis_run_callback();
+
+extern log_result * nis_dump();
+extern log_result * nis_dumplog();
+
+extern bool_t __do_ismember();
+extern nis_name __nis_map_group();
+extern nis_name __nis_map_group_r();
+
+
+extern nis_error __nis_CacheBind();
+extern directory_obj * __nis_CacheSearch();
+extern bool_t __nis_CacheRemoveEntry();
+extern void __nis_CacheRestart();
+extern void __nis_CachePrint();
+extern void __nis_CacheDumpStatistics();
+extern bool_t writeColdStartFile();
+
+extern CLIENT * __get_ti_clnt();
+extern int __strcmp_case_insens();
+extern int __strncmp_case_insens();
+
+extern fd_result * nis_finddirectory();
+extern int __start_clock();
+extern u_long __stop_clock();
+
+/*
+ * This particular function is part of the FreeBSD NIS+ implementation
+ * only. Ideally it should be somewhere else, but it is used by both
+ * rpc.nisd and nis_cachemgr, and there aren't that many headers common
+ * to both programs.
+ */
+
+extern struct signature *__nis_calculate_encrypted_cksum();
+
+#endif
+
+#define	NUL '\0'
+
+#ifdef	__cplusplus
+}
+#endif
+
+#endif	/* _RPCSVC_NISLIB_H */
diff --git a/services/librpc/include/rpcsvc/nlm_prot.x b/services/librpc/include/rpcsvc/nlm_prot.x
new file mode 100644
index 0000000..fdc6d6e
--- /dev/null
+++ b/services/librpc/include/rpcsvc/nlm_prot.x
@@ -0,0 +1,183 @@
+/* @(#)nlm_prot.x	2.1 88/08/01 4.0 RPCSRC */
+/* @(#)nlm_prot.x 1.8 87/09/21 Copyr 1987 Sun Micro */
+
+/*
+ * Network lock manager protocol definition
+ * Copyright (C) 1986 Sun Microsystems, Inc.
+ *
+ * protocol used between local lock manager and remote lock manager
+ */
+
+#ifdef RPC_HDR
+%#define LM_MAXSTRLEN	1024
+%#define MAXNAMELEN	LM_MAXSTRLEN+1
+#else
+%#ifndef lint
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/nlm_prot.x,v 1.8 1999/08/27 23:45:10 peter Exp $";
+%#endif /* not lint */
+#endif
+
+/*
+ * status of a call to the lock manager
+ */
+enum nlm_stats {
+	nlm_granted = 0,
+	nlm_denied = 1,
+	nlm_denied_nolocks = 2,
+	nlm_blocked = 3,
+	nlm_denied_grace_period = 4
+};
+
+struct nlm_holder {
+	bool exclusive;
+	int svid;
+	netobj oh;
+	unsigned l_offset;
+	unsigned l_len;
+};
+
+union nlm_testrply switch (nlm_stats stat) {
+	case nlm_denied:
+		struct nlm_holder holder;
+	default:
+		void;
+};
+
+struct nlm_stat {
+	nlm_stats stat;
+};
+
+struct nlm_res {
+	netobj cookie;
+	nlm_stat stat;
+};
+
+struct nlm_testres {
+	netobj cookie;
+	nlm_testrply stat;
+};
+
+struct nlm_lock {
+	string caller_name<LM_MAXSTRLEN>;
+	netobj fh;		/* identify a file */
+	netobj oh;		/* identify owner of a lock */
+	int svid;		/* generated from pid for svid */
+	unsigned l_offset;
+	unsigned l_len;
+};
+
+struct nlm_lockargs {
+	netobj cookie;
+	bool block;
+	bool exclusive;
+	struct nlm_lock alock;
+	bool reclaim;		/* used for recovering locks */
+	int state;		/* specify local status monitor state */
+};
+
+struct nlm_cancargs {
+	netobj cookie;		
+	bool block;
+	bool exclusive;
+	struct nlm_lock alock;
+};
+
+struct nlm_testargs {
+	netobj cookie;		
+	bool exclusive;
+	struct nlm_lock alock;
+};
+
+struct nlm_unlockargs {
+	netobj cookie;		
+	struct nlm_lock alock;
+};
+
+
+#ifdef RPC_HDR
+%/*
+% * The following enums are actually bit encoded for efficient
+% * boolean algebra.... DON'T change them.....
+% */
+#endif
+enum	fsh_mode {
+	fsm_DN  = 0,	/* deny none */
+	fsm_DR  = 1,	/* deny read */
+	fsm_DW  = 2,	/* deny write */
+	fsm_DRW = 3	/* deny read/write */
+};
+
+enum	fsh_access {
+	fsa_NONE = 0,	/* for completeness */
+	fsa_R    = 1,	/* read only */
+	fsa_W    = 2,	/* write only */
+	fsa_RW   = 3	/* read/write */
+};
+
+struct	nlm_share {
+	string caller_name<LM_MAXSTRLEN>;
+	netobj	fh;
+	netobj	oh;
+	fsh_mode	mode;
+	fsh_access	access;
+};
+
+struct	nlm_shareargs {
+	netobj	cookie;
+	nlm_share	share;
+	bool	reclaim;
+};
+
+struct	nlm_shareres {
+	netobj	cookie;
+	nlm_stats	stat;
+	int	sequence;
+};
+
+struct	nlm_notify {
+	string name<MAXNAMELEN>;
+	long state;
+};
+
+/*
+ * Over-the-wire protocol used between the network lock managers
+ */
+
+program NLM_PROG {
+	version NLM_VERS {
+
+		nlm_testres	NLM_TEST(struct nlm_testargs) =	1;
+
+		nlm_res		NLM_LOCK(struct nlm_lockargs) =	2;
+
+		nlm_res		NLM_CANCEL(struct nlm_cancargs) = 3;
+		nlm_res		NLM_UNLOCK(struct nlm_unlockargs) =	4;
+
+		/*
+		 * remote lock manager call-back to grant lock
+		 */
+		nlm_res		NLM_GRANTED(struct nlm_testargs)= 5;
+		/*
+		 * message passing style of requesting lock
+		 */
+		void		NLM_TEST_MSG(struct nlm_testargs) = 6;
+		void		NLM_LOCK_MSG(struct nlm_lockargs) = 7;
+		void		NLM_CANCEL_MSG(struct nlm_cancargs) =8;
+		void		NLM_UNLOCK_MSG(struct nlm_unlockargs) = 9;
+		void		NLM_GRANTED_MSG(struct nlm_testargs) = 10;
+		void		NLM_TEST_RES(nlm_testres) = 11;
+		void		NLM_LOCK_RES(nlm_res) = 12;
+		void		NLM_CANCEL_RES(nlm_res) = 13;
+		void		NLM_UNLOCK_RES(nlm_res) = 14;
+		void		NLM_GRANTED_RES(nlm_res) = 15;
+	} = 1;
+
+	version NLM_VERSX {
+		nlm_shareres	NLM_SHARE(nlm_shareargs) = 20;
+		nlm_shareres	NLM_UNSHARE(nlm_shareargs) = 21;
+		nlm_res		NLM_NM_LOCK(nlm_lockargs) = 22;
+		void		NLM_FREE_ALL(nlm_notify) = 23;
+	} = 3;
+
+} = 100021;
diff --git a/services/librpc/include/rpcsvc/pmap_prot.x b/services/librpc/include/rpcsvc/pmap_prot.x
new file mode 100644
index 0000000..2e9c089
--- /dev/null
+++ b/services/librpc/include/rpcsvc/pmap_prot.x
@@ -0,0 +1,284 @@
+%/*
+% * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+% * unrestricted use provided that this legend is included on all tape
+% * media and as a part of the software program in whole or part.  Users
+% * may copy or modify Sun RPC without charge, but are not authorized
+% * to license or distribute it to anyone else except as part of a product or
+% * program developed by the user.
+% *
+% * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+% * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+% * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+% *
+% * Sun RPC is provided with no support and without any obligation on the
+% * part of Sun Microsystems, Inc. to assist in its use, correction,
+% * modification or enhancement.
+% *
+% * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+% * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+% * OR ANY PART THEREOF.
+% *
+% * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+% * or profits or other special, indirect and consequential damages, even if
+% * Sun has been advised of the possibility of such damages.
+% *
+% * Sun Microsystems, Inc.
+% * 2550 Garcia Avenue
+% * Mountain View, California  94043
+% */
+%/*
+% * Copyright (c) 1984,1989 by Sun Microsystems, Inc.
+% */
+
+%/* from pmap_prot.x */
+
+#ifdef RPC_HDR
+%
+%#pragma ident	"@(#)pmap_prot.x	1.6	94/04/29 SMI"
+%
+%#ifndef _KERNEL
+%
+#endif
+
+/*
+ * Port Mapper Protocol Specification (in RPC Language)
+ * derived from RFC 1057
+ */
+
+%/*
+% * Protocol for the local binder service, or pmap.
+% *
+% * Copyright (C) 1984, Sun Microsystems, Inc.
+% *
+% * The following procedures are supported by the protocol:
+% *
+% * PMAPPROC_NULL() returns ()
+% * 	takes nothing, returns nothing
+% *
+% * PMAPPROC_SET(struct pmap) returns (bool_t)
+% * 	TRUE is success, FALSE is failure.  Registers the tuple
+% *	[prog, vers, prot, port].
+% *
+% * PMAPPROC_UNSET(struct pmap) returns (bool_t)
+% *	TRUE is success, FALSE is failure.  Un-registers pair
+% *	[prog, vers].  prot and port are ignored.
+% *
+% * PMAPPROC_GETPORT(struct pmap) returns (long unsigned).
+% *	0 is failure.  Otherwise returns the port number where the pair
+% *	[prog, vers] is registered.  It may lie!
+% *
+% * PMAPPROC_DUMP() RETURNS (struct pmaplist_ptr)
+% *
+% * PMAPPROC_CALLIT(unsigned, unsigned, unsigned, string<>)
+% * 	RETURNS (port, string<>);
+% * usage: encapsulatedresults = PMAPPROC_CALLIT(prog, vers, proc,
+% *						encapsulatedargs);
+% * 	Calls the procedure on the local machine.  If it is not registered,
+% *	this procedure is quite; ie it does not return error information!!!
+% *	This procedure only is supported on rpc/udp and calls via
+% *	rpc/udp.  This routine only passes null authentication parameters.
+% *	This file has no interface to xdr routines for PMAPPROC_CALLIT.
+% *
+% * The service supports remote procedure calls on udp/ip or tcp/ip socket 111.
+% */
+%
+const PMAPPORT = 111;	/* portmapper port number */
+%
+%
+%/*
+% * A mapping of (program, version, protocol) to port number
+% */
+
+struct pmap {
+	unsigned long pm_prog;
+	unsigned long pm_vers;
+	unsigned long pm_prot;
+	unsigned long pm_port;
+};
+#ifdef RPC_HDR
+%
+%typedef pmap PMAP;
+%
+#endif
+%
+%/*
+% * Supported values for the "prot" field
+% */
+%
+const PMAP_IPPROTO_TCP = 6;	/* protocol number for TCP/IP */
+const PMAP_IPPROTO_UDP = 17;	/* protocol number for UDP/IP */
+%
+%
+%/*
+% * A list of mappings
+% *
+% * Below are two definitions for the pmaplist structure.  This is done because
+% * xdr_pmaplist() is specified to take a struct pmaplist **, rather than a
+% * struct pmaplist * that rpcgen would produce.  One version of the pmaplist
+% * structure (actually called pm__list) is used with rpcgen, and the other is
+% * defined only in the header file for compatibility with the specified
+% * interface.
+% */
+
+struct pm__list {
+	pmap pml_map;
+	struct pm__list *pml_next;
+};
+
+typedef pm__list *pmaplist_ptr;		/* results of PMAPPROC_DUMP */
+
+#ifdef RPC_HDR
+%
+%typedef struct pm__list pmaplist;
+%typedef struct pm__list PMAPLIST;
+%
+%#ifndef __cplusplus
+%struct pmaplist {
+%	PMAP pml_map;
+%	struct pmaplist *pml_next;
+%};
+%#endif
+%
+%#ifdef __cplusplus
+%extern "C" {
+%#endif
+%#ifdef __STDC__
+%extern  bool_t xdr_pmaplist(XDR *, pmaplist**);
+%#else /* K&R C */
+%bool_t xdr_pmaplist();
+%#endif
+%#ifdef	__cplusplus
+%}
+%#endif
+%
+#endif
+
+%
+%/*
+% * Arguments to callit
+% */
+
+struct rmtcallargs {
+	unsigned long prog;
+	unsigned long vers;
+	unsigned long proc;
+	opaque args<>;
+};
+#ifdef RPC_HDR
+%
+%/*
+% * Client-side only representation of rmtcallargs structure.
+% *
+% * The routine that XDRs the rmtcallargs structure must deal with the
+% * opaque arguments in the "args" structure.  xdr_rmtcall_args() needs to be
+% * passed the XDR routine that knows the args' structure.  This routine
+% * doesn't need to go over-the-wire (and it wouldn't make sense anyway) since
+% * the application being called knows the args structure already.  So we use a
+% * different "XDR" structure on the client side, p_rmtcallargs, which includes
+% * the args' XDR routine.
+% */
+%struct p_rmtcallargs {
+%	u_long prog;
+%	u_long vers;
+%	u_long proc;
+%	struct {
+%		u_int args_len;
+%		char *args_val;
+%	} args;
+%	xdrproc_t	xdr_args;	/* encodes args */
+%};
+%
+#endif	/* def RPC_HDR */
+%
+%
+%/*
+% * Results of callit
+% */
+
+struct rmtcallres {
+	unsigned long port;
+	opaque res<>;
+};
+#ifdef RPC_HDR
+%
+%/*
+% * Client-side only representation of rmtcallres structure.
+% */
+%struct p_rmtcallres {
+%	u_long port;
+%	struct {
+%		u_int res_len;
+%		char *res_val;
+%	} res;
+%	xdrproc_t	xdr_res;	/* decodes res */
+%};
+%
+#endif	/* def RPC_HDR */
+
+/*
+ * Port mapper procedures
+ */
+
+program PMAPPROG {
+   version PMAPVERS {
+	void
+	PMAPPROC_NULL(void)	= 0;
+
+	bool
+	PMAPPROC_SET(pmap)	= 1;
+
+	bool
+	PMAPPROC_UNSET(pmap)	= 2;
+
+	unsigned long
+	PMAPPROC_GETPORT(pmap)	= 3;
+
+	pmaplist_ptr
+	PMAPPROC_DUMP(void)	= 4;
+
+	rmtcallres
+	PMAPPROC_CALLIT(rmtcallargs)  = 5;
+   } = 2;
+} = 100000;
+%
+#ifdef RPC_HDR
+%#define PMAPVERS_PROTO		((u_long)2)
+%#define PMAPVERS_ORIG		((u_long)1)
+%
+%#else		/* ndef _KERNEL */
+%
+%#include <rpc/pmap_rmt.h>
+%
+%#ifdef __cplusplus
+%extern "C" {
+%#endif
+%
+%#define	PMAPPORT 111
+%
+%struct pmap {
+%	long unsigned pm_prog;
+%	long unsigned pm_vers;
+%	long unsigned pm_prot;
+%	long unsigned pm_port;
+%};
+%typedef struct pmap PMAP;
+%#ifdef __STDC__
+%extern bool_t xdr_pmap (XDR *, struct pmap *);
+%#else
+%extern bool_t xdr_pmap ();
+%#endif
+%
+%struct pmaplist {
+%	struct pmap pml_map;
+%	struct pmaplist *pml_next;
+%};
+%typedef struct pmaplist PMAPLIST;
+%typedef struct pmaplist *pmaplist_ptr;
+%
+%
+%#ifdef __cplusplus
+%}
+%#endif
+%
+%#endif		/* ndef _KERNEL */
+#endif
diff --git a/services/librpc/include/rpcsvc/rex.x b/services/librpc/include/rpcsvc/rex.x
new file mode 100644
index 0000000..928efa2
--- /dev/null
+++ b/services/librpc/include/rpcsvc/rex.x
@@ -0,0 +1,235 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+/*
+ * Remote execution (rex) protocol specification
+ */
+
+#ifndef RPC_HDR
+%#ifndef lint
+%/*static char sccsid[] = "from: @(#)rex.x 1.3 87/09/18 Copyr 1987 Sun Micro";*/
+%/*static char sccsid[] = "from: @(#)rex.x	2.1 88/08/01 4.0 RPCSRC";*/
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/rex.x,v 1.6 1999/08/27 23:45:10 peter Exp $";
+%#endif /* not lint */
+#endif
+
+const STRINGSIZE = 1024;
+typedef string rexstring<1024>;
+
+/*
+ * values to pass to REXPROC_SIGNAL
+ */
+const SIGINT = 2;	/* interrupt */
+
+/*
+ * Values for rst_flags, below 
+ */
+const REX_INTERACTIVE = 1;	/* interactive mode */
+
+struct rex_start {
+	rexstring rst_cmd<>;	/* list of command and args */
+	rexstring rst_host;	/* working directory host name */
+	rexstring rst_fsname;	/* working directory file system name */
+	rexstring rst_dirwithin;/* working directory within file system */
+	rexstring rst_env<>;	/* list of environment */
+	unsigned int rst_port0;	/* port for stdin */
+	unsigned int rst_port1;	/* port for stdout */
+	unsigned int rst_port2;	/* port for stderr */
+	unsigned int rst_flags;	/* options - see const above */
+};
+
+struct rex_result {
+   	int rlt_stat;		/* integer status code */
+	rexstring rlt_message;	/* string message for human consumption */
+};
+
+
+struct sgttyb {
+	unsigned four;	/* always equals 4 */
+	opaque chars[4];
+	/* chars[0] == input speed */
+	/* chars[1] == output speed */
+	/* chars[2] == kill character */
+	/* chars[3] == erase character */
+	unsigned flags;
+};
+/* values for speeds above (baud rates)  */
+const B0  = 0;
+const B50 = 1;
+const B75 = 2;
+const B110 = 3;
+const B134 = 4;
+const B150 = 5;
+const B200 = 6;
+const B300 = 7;
+const B600 = 8;
+const B1200 = 9;
+const B1800 = 10;
+const B2400 = 11;
+const B4800 = 12;
+const B9600 = 13;
+const B19200 = 14;
+const B38400 = 15;
+
+/* values for flags above */
+const TANDEM = 0x00000001; /* send stopc on out q full */
+const CBREAK = 0x00000002; /* half-cooked mode */
+const LCASE = 0x00000004; /* simulate lower case */
+const ECHO = 0x00000008; /* echo input */
+const CRMOD = 0x00000010; /* map \r to \r\n on output */
+const RAW = 0x00000020; /* no i/o processing */
+const ODDP = 0x00000040; /* get/send odd parity */
+const EVENP = 0x00000080; /* get/send even parity */
+const ANYP = 0x000000c0; /* get any parity/send none */
+const NLDELAY = 0x00000300; /* \n delay */
+const  NL0 = 0x00000000;
+const  NL1 = 0x00000100; /* tty 37 */
+const  NL2 = 0x00000200; /* vt05 */
+const  NL3 = 0x00000300;
+const TBDELAY = 0x00000c00; /* horizontal tab delay */
+const  TAB0 = 0x00000000;
+const  TAB1 = 0x00000400; /* tty 37 */
+const  TAB2 = 0x00000800;
+const XTABS = 0x00000c00; /* expand tabs on output */
+const CRDELAY = 0x00003000; /* \r delay */
+const  CR0 = 0x00000000;
+const  CR1 = 0x00001000; /* tn 300 */
+const  CR2 = 0x00002000; /* tty 37 */
+const  CR3 = 0x00003000; /* concept 100 */
+const VTDELAY = 0x00004000; /* vertical tab delay */
+const  FF0 = 0x00000000;
+const  FF1 = 0x00004000; /* tty 37 */
+const BSDELAY = 0x00008000; /* \b delay */
+const  BS0 = 0x00000000;
+const  BS1 = 0x00008000;
+const CRTBS = 0x00010000; /* do backspacing for crt */
+const PRTERA = 0x00020000; /* \ ... / erase */
+const CRTERA = 0x00040000; /* " \b " to wipe out char */
+const TILDE = 0x00080000; /* hazeltine tilde kludge */
+const MDMBUF = 0x00100000; /* start/stop output on carrier intr */
+const LITOUT = 0x00200000; /* literal output */
+const TOSTOP = 0x00400000; /* SIGTTOU on background output */
+const FLUSHO = 0x00800000; /* flush output to terminal */
+const NOHANG = 0x01000000; /* no SIGHUP on carrier drop */
+const L001000 = 0x02000000;
+const CRTKIL = 0x04000000; /* kill line with " \b " */
+const PASS8 = 0x08000000;
+const CTLECH = 0x10000000; /* echo control chars as ^X */
+const PENDIN = 0x20000000; /* tp->t_rawq needs reread */
+const DECCTQ = 0x40000000; /* only ^Q starts after ^S */
+const NOFLSH = 0x80000000; /* no output flush on signal */
+
+struct tchars {
+	unsigned six;	/* always equals 6 */
+	opaque chars[6];
+	/* chars[0] == interrupt char */
+	/* chars[1] == quit char */
+	/* chars[2] == start output char */
+	/* chars[3] == stop output char */
+	/* chars[4] == end-of-file char */
+	/* chars[5] == input delimeter (like nl) */
+};
+
+struct ltchars {
+	unsigned six;	/* always equals 6 */
+	opaque chars[6];
+	/* chars[0] == stop process signal */
+	/* chars[1] == delayed stop process signal */
+	/* chars[2] == reprint line */
+	/* chars[3] == flush output */
+	/* chars[4] == word erase */
+	/* chars[5] == literal next character */
+	unsigned mode;
+};
+
+struct rex_ttysize {
+	int ts_lines;
+	int ts_cols;
+};
+
+struct rex_ttymode {
+    sgttyb basic;    /* standard unix tty flags */
+    tchars more; /* interrupt, kill characters, etc. */
+    ltchars yetmore; /* special Berkeley characters */
+    unsigned andmore;     /* and Berkeley modes */
+};
+
+/* values for andmore above */
+const LCRTBS = 0x0001;	/* do backspacing for crt */
+const LPRTERA = 0x0002;	/* \ ... / erase */
+const LCRTERA = 0x0004;	/* " \b " to wipe out char */
+const LTILDE = 0x0008;	/* hazeltine tilde kludge */
+const LMDMBUF = 0x0010;	/* start/stop output on carrier intr */
+const LLITOUT = 0x0020;	/* literal output */
+const LTOSTOP = 0x0040;	/* SIGTTOU on background output */
+const LFLUSHO = 0x0080;	/* flush output to terminal */
+const LNOHANG = 0x0100;	/* no SIGHUP on carrier drop */
+const LL001000 = 0x0200;
+const LCRTKIL = 0x0400;	/* kill line with " \b " */
+const LPASS8 = 0x0800;
+const LCTLECH = 0x1000;	/* echo control chars as ^X */
+const LPENDIN = 0x2000;	/* needs reread */
+const LDECCTQ = 0x4000;	/* only ^Q starts after ^S */
+const LNOFLSH = 0x8000;	/* no output flush on signal */
+
+program REXPROG {
+	version REXVERS {
+
+		/*
+		 * Start remote execution
+		 */
+		rex_result 
+		REXPROC_START(rex_start) = 1;
+
+		/*
+		 * Wait for remote execution to terminate
+		 */
+		rex_result
+		REXPROC_WAIT(void) = 2;
+
+		/*
+		 * Send tty modes
+		 */
+		void
+		REXPROC_MODES(rex_ttymode) = 3;
+
+		/*
+		 * Send window size change
+		 */
+		void
+		REXPROC_WINCH(rex_ttysize) = 4;
+
+		/*
+		 * Send other signal
+		 */
+		void
+		REXPROC_SIGNAL(int) = 5;
+	} = 1;
+} = 100017;
diff --git a/services/librpc/include/rpcsvc/rnusers.x b/services/librpc/include/rpcsvc/rnusers.x
new file mode 100644
index 0000000..393eaf4
--- /dev/null
+++ b/services/librpc/include/rpcsvc/rnusers.x
@@ -0,0 +1,122 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+/*
+ * Find out about remote users
+ */
+
+#ifndef RPC_HDR
+%#ifndef lint
+%/*static char sccsid[] = "from: @(#)rnusers.x 1.2 87/09/20 Copyr 1987 Sun Micro";*/
+%/*static char sccsid[] = "from: @(#)rnusers.x	2.1 88/08/01 4.0 RPCSRC";*/
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/rnusers.x,v 1.6 1999/08/27 23:45:10 peter Exp $";
+%#endif /* not lint */
+#endif
+
+const MAXUSERS = 100;
+const MAXUTLEN = 256;
+
+struct utmp {
+	string ut_line<MAXUTLEN>;
+	string ut_name<MAXUTLEN>;
+	string ut_host<MAXUTLEN>;
+	int ut_time;
+};
+
+
+struct utmpidle {
+	utmp ui_utmp;
+	unsigned int ui_idle;
+};
+
+typedef utmp utmparr<MAXUSERS>;
+
+typedef utmpidle utmpidlearr<MAXUSERS>;
+
+const RUSERS_MAXUSERLEN = 32;
+const RUSERS_MAXLINELEN = 32;
+const RUSERS_MAXHOSTLEN = 257;
+
+struct rusers_utmp {
+	string ut_user<RUSERS_MAXUSERLEN>;	/* aka ut_name */
+	string ut_line<RUSERS_MAXLINELEN>;	/* device */
+	string ut_host<RUSERS_MAXHOSTLEN>;	/* host user logged on from */
+	int ut_type;				/* type of entry */
+	int ut_time;				/* time entry was made */
+	unsigned int ut_idle;			/* minutes idle */
+};
+
+typedef rusers_utmp utmp_array<>;
+
+program RUSERSPROG {
+	/*
+	 * Old version does not include idle information
+	 */
+	version RUSERSVERS_ORIG {
+		int
+		RUSERSPROC_NUM(void) = 1;
+
+		utmparr
+		RUSERSPROC_NAMES(void) = 2;
+
+		utmparr
+		RUSERSPROC_ALLNAMES(void) = 3;
+	} = 1;
+
+	/*
+	 * Includes idle information
+	 */
+	version RUSERSVERS_IDLE {
+		int
+		RUSERSPROC_NUM(void) = 1;
+
+		utmpidlearr
+		RUSERSPROC_NAMES(void) = 2;
+
+		utmpidlearr
+		RUSERSPROC_ALLNAMES(void) = 3;
+	} = 2;
+
+	/*
+	 * Version 3 rusers procedures (from Solaris).
+	 * (Thanks a lot Sun.)
+	 */
+	version RUSERSVERS_3 {
+		int
+		RUSERSPROC_NUM(void) = 1;
+
+		utmp_array
+		RUSERSPROC_NAMES(void) = 2;
+
+		utmp_array
+		RUSERSPROC_ALLNAMES(void) = 3;
+	} = 3;
+
+} = 100002;
diff --git a/services/librpc/include/rpcsvc/rquota.x b/services/librpc/include/rpcsvc/rquota.x
new file mode 100644
index 0000000..72864d1
--- /dev/null
+++ b/services/librpc/include/rpcsvc/rquota.x
@@ -0,0 +1,67 @@
+/*
+ * Remote quota protocol
+ * Requires unix authentication
+ */
+
+#ifndef RPC_HDR
+%#ifndef lint
+%/*static char sccsid[] = "from: @(#)rquota.x 1.2 87/09/20 Copyr 1987 Sun Micro";*/
+%/*static char sccsid[] = "from: @(#)rquota.x	2.1 88/08/01 4.0 RPCSRC";*/
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/rquota.x,v 1.6 1999/08/27 23:45:10 peter Exp $";
+%#endif /* not lint */
+#endif
+
+const RQ_PATHLEN = 1024;
+
+struct getquota_args {
+	string gqa_pathp<RQ_PATHLEN>;  	/* path to filesystem of interest */
+	int gqa_uid;	        	/* inquire about quota for uid */
+};
+
+/*
+ * remote quota structure
+ */
+struct rquota {
+	int rq_bsize;			/* block size for block counts */
+	bool rq_active;  		/* indicates whether quota is active */
+	unsigned int rq_bhardlimit;	/* absolute limit on disk blks alloc */
+	unsigned int rq_bsoftlimit;	/* preferred limit on disk blks */
+	unsigned int rq_curblocks;	/* current block count */
+	unsigned int rq_fhardlimit;	/* absolute limit on allocated files */
+	unsigned int rq_fsoftlimit;	/* preferred file limit */
+	unsigned int rq_curfiles;	/* current # allocated files */
+	unsigned int rq_btimeleft;	/* time left for excessive disk use */
+	unsigned int rq_ftimeleft;	/* time left for excessive files */
+};	
+
+enum gqr_status {
+	Q_OK = 1,		/* quota returned */
+	Q_NOQUOTA = 2,  	/* noquota for uid */
+	Q_EPERM = 3		/* no permission to access quota */
+};
+
+union getquota_rslt switch (gqr_status status) {
+case Q_OK:
+	rquota gqr_rquota;	/* valid if status == Q_OK */
+case Q_NOQUOTA:
+	void;
+case Q_EPERM:
+	void;
+};
+
+program RQUOTAPROG {
+	version RQUOTAVERS {
+		/*
+		 * Get all quotas
+		 */
+		getquota_rslt
+		RQUOTAPROC_GETQUOTA(getquota_args) = 1;
+
+		/*
+	 	 * Get active quotas only
+		 */
+		getquota_rslt
+		RQUOTAPROC_GETACTIVEQUOTA(getquota_args) = 2;
+	} = 1;
+} = 100011;
diff --git a/services/librpc/include/rpcsvc/rstat.x b/services/librpc/include/rpcsvc/rstat.x
new file mode 100644
index 0000000..fee9d52
--- /dev/null
+++ b/services/librpc/include/rpcsvc/rstat.x
@@ -0,0 +1,151 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+/*
+ * Gather statistics on remote machines
+ */
+
+#ifdef RPC_HDR
+
+%#ifndef FSCALE
+%/*
+% * Scale factor for scaled integers used to count load averages.
+% */
+%#define FSHIFT  8               /* bits to right of fixed binary point */
+%#define FSCALE  (1<<FSHIFT)
+%
+%#endif /* ndef FSCALE */
+
+#else
+
+%#ifndef lint
+%/*static char sccsid[] = "from: @(#)rstat.x 1.2 87/09/18 Copyr 1987 Sun Micro";*/
+%/*static char sccsid[] = "from: @(#)rstat.x	2.2 88/08/01 4.0 RPCSRC";*/
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/rstat.x,v 1.6 1999/08/27 23:45:11 peter Exp $";
+%#endif /* not lint */
+
+#endif /* def RPC_HDR */
+
+const RSTAT_CPUSTATES = 4;
+const RSTAT_DK_NDRIVE = 4;
+
+/*
+ * GMT since 0:00, January 1, 1970
+ */
+struct rstat_timeval {
+	unsigned int tv_sec;	/* seconds */
+	unsigned int tv_usec;	/* and microseconds */
+};
+
+struct statstime {				/* RSTATVERS_TIME */
+	int cp_time[RSTAT_CPUSTATES];
+	int dk_xfer[RSTAT_DK_NDRIVE];
+	unsigned int v_pgpgin;	/* these are cumulative sum */
+	unsigned int v_pgpgout;
+	unsigned int v_pswpin;
+	unsigned int v_pswpout;
+	unsigned int v_intr;
+	int if_ipackets;
+	int if_ierrors;
+	int if_oerrors;
+	int if_collisions;
+	unsigned int v_swtch;
+	int avenrun[3];         /* scaled by FSCALE */
+	rstat_timeval boottime;
+	rstat_timeval curtime;
+	int if_opackets;
+};
+
+struct statsswtch {			/* RSTATVERS_SWTCH */
+	int cp_time[RSTAT_CPUSTATES];
+	int dk_xfer[RSTAT_DK_NDRIVE];
+	unsigned int v_pgpgin;	/* these are cumulative sum */
+	unsigned int v_pgpgout;
+	unsigned int v_pswpin;
+	unsigned int v_pswpout;
+	unsigned int v_intr;
+	int if_ipackets;
+	int if_ierrors;
+	int if_oerrors;
+	int if_collisions;
+	unsigned int v_swtch;
+	unsigned int avenrun[3];/* scaled by FSCALE */
+	rstat_timeval boottime;
+	int if_opackets;
+};
+
+struct stats {				/* RSTATVERS_ORIG */
+	int cp_time[RSTAT_CPUSTATES];
+	int dk_xfer[RSTAT_DK_NDRIVE];
+	unsigned int v_pgpgin;	/* these are cumulative sum */
+	unsigned int v_pgpgout;
+	unsigned int v_pswpin;
+	unsigned int v_pswpout;
+	unsigned int v_intr;
+	int if_ipackets;
+	int if_ierrors;
+	int if_oerrors;
+	int if_collisions;
+	int if_opackets;
+};
+
+
+program RSTATPROG {
+	/*
+	 * Newest version includes current time and context switching info
+	 */
+	version RSTATVERS_TIME {
+		statstime
+		RSTATPROC_STATS(void) = 1;
+
+		unsigned int
+		RSTATPROC_HAVEDISK(void) = 2;
+	} = 3;
+	/*
+	 * Does not have current time
+	 */
+	version RSTATVERS_SWTCH {
+		statsswtch
+		RSTATPROC_STATS(void) = 1;
+
+		unsigned int
+		RSTATPROC_HAVEDISK(void) = 2;
+	} = 2;
+	/*
+	 * Old version has no info about current time or context switching
+	 */
+	version RSTATVERS_ORIG {
+		stats
+		RSTATPROC_STATS(void) = 1;
+
+		unsigned int
+		RSTATPROC_HAVEDISK(void) = 2;
+	} = 1;
+} = 100001;
diff --git a/services/librpc/include/rpcsvc/rwall.x b/services/librpc/include/rpcsvc/rwall.x
new file mode 100644
index 0000000..6c26c1f
--- /dev/null
+++ b/services/librpc/include/rpcsvc/rwall.x
@@ -0,0 +1,57 @@
+%/*
+% * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+% * unrestricted use provided that this legend is included on all tape
+% * media and as a part of the software program in whole or part.  Users
+% * may copy or modify Sun RPC without charge, but are not authorized
+% * to license or distribute it to anyone else except as part of a product or
+% * program developed by the user or with the express written consent of
+% * Sun Microsystems, Inc.
+% *
+% * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+% * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+% * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+% *
+% * Sun RPC is provided with no support and without any obligation on the
+% * part of Sun Microsystems, Inc. to assist in its use, correction,
+% * modification or enhancement.
+% *
+% * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+% * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+% * OR ANY PART THEREOF.
+% *
+% * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+% * or profits or other special, indirect and consequential damages, even if
+% * Sun has been advised of the possibility of such damages.
+% *
+% * Sun Microsystems, Inc.
+% * 2550 Garcia Avenue
+% * Mountain View, California  94043
+% */
+
+%/*
+% * Copyright (c) 1984, 1990 by Sun Microsystems, Inc.
+% */
+%
+%/* from @(#)rwall.x	1.6 91/03/11 TIRPC 1.0 */
+
+#ifdef RPC_HDR
+%
+%#ifndef _rpcsvc_rwall_h
+%#define _rpcsvc_rwall_h
+%
+%typedef char *wrapstring;
+%
+#endif
+
+program WALLPROG {
+	version WALLVERS {
+		void	
+		WALLPROC_WALL(wrapstring) = 2;
+
+	} = 1;
+} = 100008;
+
+#ifdef RPC_HDR
+%
+%#endif /* ! _rpcsvc_rwall_h */
+#endif
diff --git a/services/librpc/include/rpcsvc/sm_inter.x b/services/librpc/include/rpcsvc/sm_inter.x
new file mode 100644
index 0000000..2071516
--- /dev/null
+++ b/services/librpc/include/rpcsvc/sm_inter.x
@@ -0,0 +1,122 @@
+/* @(#)sm_inter.x	2.2 88/08/01 4.0 RPCSRC */
+/* @(#)sm_inter.x 1.7 87/06/24 Copyr 1987 Sun Micro */
+
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+/*
+ * Status monitor protocol specification
+ * Copyright (C) 1986 Sun Microsystems, Inc.
+ *
+ */
+
+#ifndef RPC_HDR
+%#ifndef lint
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/sm_inter.x,v 1.8 1999/08/27 23:45:11 peter Exp $";
+%#endif /* not lint */
+#endif
+
+program SM_PROG { 
+	version SM_VERS  {
+		/* res_stat = stat_succ if status monitor agrees to monitor */
+		/* res_stat = stat_fail if status monitor cannot monitor */
+		/* if res_stat == stat_succ, state = state number of site sm_name */
+		struct sm_stat_res			 SM_STAT(struct sm_name) = 1;
+
+		/* res_stat = stat_succ if status monitor agrees to monitor */
+		/* res_stat = stat_fail if status monitor cannot monitor */
+		/* stat consists of state number of local site */
+		struct sm_stat_res			 SM_MON(struct mon) = 2;
+
+		/* stat consists of state number of local site */
+		struct sm_stat				 SM_UNMON(struct mon_id) = 3;
+
+		/* stat consists of state number of local site */
+		struct sm_stat				 SM_UNMON_ALL(struct my_id) = 4;
+
+		void					 SM_SIMU_CRASH(void) = 5;
+
+	} = 1;
+} = 100024;
+
+const	SM_MAXSTRLEN = 1024;
+
+struct sm_name {
+	string mon_name<SM_MAXSTRLEN>;
+};
+
+struct my_id {
+	string	 my_name<SM_MAXSTRLEN>;		/* name of the site iniates the monitoring request*/
+	int	my_prog;			/* rpc program # of the requesting process */
+	int	my_vers;			/* rpc version # of the requesting process */
+	int	my_proc;			/* rpc procedure # of the requesting process */
+};
+
+struct mon_id {
+	string	mon_name<SM_MAXSTRLEN>;		/* name of the site to be monitored */
+	struct my_id my_id;
+};
+
+
+struct mon{
+	struct mon_id mon_id;
+	opaque priv[16]; 		/* private information to store at monitor for requesting process */
+};
+
+
+/*
+ * state # of status monitor monitonically increases each time
+ * status of the site changes:
+ * an even number (>= 0) indicates the site is down and
+ * an odd number (> 0) indicates the site is up;
+ */
+struct sm_stat {
+	int state;		/* state # of status monitor */
+};
+
+enum res {
+	stat_succ = 0,		/* status monitor agrees to monitor */
+	stat_fail = 1		/* status monitor cannot monitor */
+};
+
+struct sm_stat_res {
+	res res_stat;
+	int state;
+};
+
+/* 
+ * structure of the status message sent back by the status monitor
+ * when monitor site status changes
+ */
+struct status {
+	string mon_name<SM_MAXSTRLEN>;
+	int state;
+	opaque priv[16];		/* stored private information */
+};
diff --git a/services/librpc/include/rpcsvc/spray.x b/services/librpc/include/rpcsvc/spray.x
new file mode 100644
index 0000000..a4d086a
--- /dev/null
+++ b/services/librpc/include/rpcsvc/spray.x
@@ -0,0 +1,90 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+/*
+ * Spray a server with packets
+ * Useful for testing flakiness of network interfaces
+ */
+
+#ifndef RPC_HDR
+%#ifndef lint
+%/*static char sccsid[] = "from: @(#)spray.x 1.2 87/09/18 Copyr 1987 Sun Micro";*/
+%/*static char sccsid[] = "from: @(#)spray.x	2.1 88/08/01 4.0 RPCSRC";*/
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/spray.x,v 1.6 1999/08/27 23:45:11 peter Exp $";
+%#endif /* not lint */
+#endif
+
+const SPRAYMAX = 8845;	/* max amount can spray */
+
+/*
+ * GMT since 0:00, 1 January 1970
+ */
+struct spraytimeval {
+	unsigned int sec;
+	unsigned int usec;
+};
+
+/*
+ * spray statistics
+ */
+struct spraycumul {
+	unsigned int counter;
+	spraytimeval clock;
+};
+
+/*
+ * spray data
+ */
+typedef opaque sprayarr<SPRAYMAX>;
+
+program SPRAYPROG {
+	version SPRAYVERS {
+		/*
+		 * Just throw away the data and increment the counter
+		 * This call never returns, so the client should always 
+		 * time it out.
+		 */
+		void
+		SPRAYPROC_SPRAY(sprayarr) = 1;
+
+		/*
+		 * Get the value of the counter and elapsed time  since
+		 * last CLEAR.
+		 */
+		spraycumul	
+		SPRAYPROC_GET(void) = 2;
+
+		/*
+		 * Clear the counter and reset the elapsed time
+		 */
+		void
+		SPRAYPROC_CLEAR(void) = 3;
+	} = 1;
+} = 100012;
diff --git a/services/librpc/include/rpcsvc/yp.x b/services/librpc/include/rpcsvc/yp.x
new file mode 100644
index 0000000..aa87265
--- /dev/null
+++ b/services/librpc/include/rpcsvc/yp.x
@@ -0,0 +1,379 @@
+/* @(#)yp.x	2.1 88/08/01 4.0 RPCSRC */
+
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+/*
+ * Protocol description file for the Yellow Pages Service
+ */
+
+#ifndef RPC_HDR
+%#ifndef lint
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/yp.x,v 1.12 1999/08/27 23:45:12 peter Exp $";
+%#endif /* not lint */
+#endif
+
+const YPMAXRECORD = 1024;
+const YPMAXDOMAIN = 64;
+const YPMAXMAP = 64;
+const YPMAXPEER = 64;
+
+
+enum ypstat {
+	YP_TRUE		=  1,
+	YP_NOMORE	=  2,
+	YP_FALSE	=  0,
+	YP_NOMAP	= -1,
+	YP_NODOM	= -2,
+	YP_NOKEY	= -3,
+	YP_BADOP	= -4,
+	YP_BADDB	= -5,
+	YP_YPERR	= -6,
+	YP_BADARGS	= -7,
+	YP_VERS		= -8
+};
+
+
+enum ypxfrstat {
+	YPXFR_SUCC	=  1,
+	YPXFR_AGE	=  2,
+	YPXFR_NOMAP	= -1,
+	YPXFR_NODOM	= -2,
+	YPXFR_RSRC	= -3,
+	YPXFR_RPC	= -4,
+	YPXFR_MADDR	= -5,
+	YPXFR_YPERR	= -6,
+	YPXFR_BADARGS	= -7,
+	YPXFR_DBM	= -8,
+	YPXFR_FILE	= -9,
+	YPXFR_SKEW	= -10,
+	YPXFR_CLEAR	= -11,
+	YPXFR_FORCE	= -12,
+	YPXFR_XFRERR	= -13,
+	YPXFR_REFUSED	= -14
+};
+
+
+typedef string domainname<YPMAXDOMAIN>;
+typedef string mapname<YPMAXMAP>;
+typedef string peername<YPMAXPEER>;
+typedef opaque keydat<YPMAXRECORD>;
+typedef opaque valdat<YPMAXRECORD>;
+
+
+struct ypmap_parms {
+	domainname domain;	
+	mapname map;
+	unsigned int ordernum;
+	peername peer;
+};
+
+struct ypreq_key {
+	domainname domain;
+	mapname map;
+	keydat key;
+};
+
+struct ypreq_nokey {
+	domainname domain;	
+	mapname map;
+};
+	
+struct ypreq_xfr {
+	ypmap_parms map_parms;
+	unsigned int transid;
+	unsigned int prog;
+	unsigned int port;
+};
+
+
+struct ypresp_val {
+	ypstat stat;
+	valdat val;
+};
+
+struct ypresp_key_val {
+	ypstat stat;
+#ifdef STUPID_SUN_BUG /* These are backwards */
+	keydat key;
+	valdat val;
+#else
+	valdat val;
+	keydat key;
+#endif
+};
+
+
+struct ypresp_master {
+	ypstat stat;	
+	peername peer;
+};
+
+struct ypresp_order {
+	ypstat stat;
+	unsigned int ordernum;
+};
+
+union ypresp_all switch (bool more) {
+case TRUE:
+	ypresp_key_val val;
+case FALSE:
+	void;
+};
+
+struct ypresp_xfr {
+	unsigned int transid;
+	ypxfrstat xfrstat;
+};
+
+struct ypmaplist {
+	mapname map;
+	ypmaplist *next;
+};
+
+struct ypresp_maplist {
+	ypstat stat;
+	ypmaplist *maps;
+};
+
+enum yppush_status {
+	YPPUSH_SUCC	=  1,	/* Success */
+	YPPUSH_AGE 	=  2,	/* Master's version not newer */
+	YPPUSH_NOMAP	= -1,	/* Can't find server for map */
+	YPPUSH_NODOM	= -2,	/* Domain not supported */
+	YPPUSH_RSRC	= -3,	/* Local resource alloc failure */
+	YPPUSH_RPC	= -4,	/* RPC failure talking to server */
+	YPPUSH_MADDR 	= -5,	/* Can't get master address */
+	YPPUSH_YPERR	= -6,	/* YP server/map db error */
+	YPPUSH_BADARGS	= -7,	/* Request arguments bad */
+	YPPUSH_DBM	= -8,	/* Local dbm operation failed */
+	YPPUSH_FILE	= -9,	/* Local file I/O operation failed */
+	YPPUSH_SKEW	= -10,	/* Map version skew during transfer */
+	YPPUSH_CLEAR	= -11,	/* Can't send "Clear" req to local ypserv */
+	YPPUSH_FORCE	= -12,	/* No local order number in map  use -f flag. */
+	YPPUSH_XFRERR 	= -13,	/* ypxfr error */
+	YPPUSH_REFUSED	= -14 	/* Transfer request refused by ypserv */
+};
+
+struct yppushresp_xfr {
+	unsigned transid;
+	yppush_status status;
+};
+
+/*
+ * Response structure and overall result status codes.  Success and failure
+ * represent two separate response message types.
+ */
+ 
+enum ypbind_resptype {
+	YPBIND_SUCC_VAL = 1, 
+	YPBIND_FAIL_VAL = 2
+};
+ 
+struct ypbind_binding {
+    opaque ypbind_binding_addr[4]; /* In network order */
+    opaque ypbind_binding_port[2]; /* In network order */
+};   
+
+union ypbind_resp switch (ypbind_resptype ypbind_status) {
+case YPBIND_FAIL_VAL:
+        unsigned ypbind_error;
+case YPBIND_SUCC_VAL:
+        ypbind_binding ypbind_bindinfo;
+};     
+
+/* Detailed failure reason codes for response field ypbind_error*/
+ 
+const YPBIND_ERR_ERR    = 1;	/* Internal error */
+const YPBIND_ERR_NOSERV = 2;	/* No bound server for passed domain */
+const YPBIND_ERR_RESC   = 3;	/* System resource allocation failure */
+ 
+ 
+/*
+ * Request data structure for ypbind "Set domain" procedure.
+ */
+struct ypbind_setdom {
+	domainname ypsetdom_domain;
+	ypbind_binding ypsetdom_binding;
+	unsigned ypsetdom_vers;
+};
+
+
+/*
+ * NIS v1 support for backwards compatibility
+ */
+enum ypreqtype {
+	YPREQ_KEY = 1,
+	YPREQ_NOKEY = 2,
+	YPREQ_MAP_PARMS = 3
+};
+
+enum ypresptype {
+	YPRESP_VAL = 1,
+	YPRESP_KEY_VAL = 2,
+	YPRESP_MAP_PARMS = 3
+};
+
+union yprequest switch (ypreqtype yp_reqtype) {
+case YPREQ_KEY:
+	ypreq_key yp_req_keytype;
+case YPREQ_NOKEY:
+	ypreq_nokey yp_req_nokeytype;
+case YPREQ_MAP_PARMS:
+	ypmap_parms yp_req_map_parmstype;
+};
+
+union ypresponse switch (ypresptype yp_resptype) {
+case YPRESP_VAL:
+	ypresp_val yp_resp_valtype;
+case YPRESP_KEY_VAL:
+	ypresp_key_val yp_resp_key_valtype;
+case YPRESP_MAP_PARMS:
+	ypmap_parms yp_resp_map_parmstype;
+};
+
+#if !defined(YPBIND_ONLY) && !defined(YPPUSH_ONLY)
+/*
+ * YP access protocol
+ */
+program YPPROG {
+/*
+ * NIS v1 support for backwards compatibility
+ */
+	version YPOLDVERS {
+		void
+		YPOLDPROC_NULL(void) = 0;
+
+		bool
+		YPOLDPROC_DOMAIN(domainname) = 1;
+
+		bool
+		YPOLDPROC_DOMAIN_NONACK(domainname) = 2;
+
+		ypresponse
+		YPOLDPROC_MATCH(yprequest) = 3;
+
+		ypresponse
+		YPOLDPROC_FIRST(yprequest) = 4;
+
+		ypresponse
+		YPOLDPROC_NEXT(yprequest) = 5;
+
+		ypresponse
+		YPOLDPROC_POLL(yprequest) = 6;
+
+		ypresponse
+		YPOLDPROC_PUSH(yprequest) = 7;
+
+		ypresponse
+		YPOLDPROC_PULL(yprequest) = 8;
+
+		ypresponse
+		YPOLDPROC_GET(yprequest) = 9;
+	} = 1;
+
+	version YPVERS {
+		void 
+		YPPROC_NULL(void) = 0;
+
+		bool 
+		YPPROC_DOMAIN(domainname) = 1;	
+
+		bool
+		YPPROC_DOMAIN_NONACK(domainname) = 2;
+
+		ypresp_val
+		YPPROC_MATCH(ypreq_key) = 3;
+
+		ypresp_key_val 
+#ifdef STUPID_SUN_BUG /* should be ypreq_nokey */
+		YPPROC_FIRST(ypreq_key) = 4;
+#else
+		YPPROC_FIRST(ypreq_nokey) = 4;
+#endif
+		ypresp_key_val 
+		YPPROC_NEXT(ypreq_key) = 5;
+
+		ypresp_xfr
+		YPPROC_XFR(ypreq_xfr) = 6;
+
+		void
+		YPPROC_CLEAR(void) = 7;
+
+		ypresp_all
+		YPPROC_ALL(ypreq_nokey) = 8;
+
+		ypresp_master
+		YPPROC_MASTER(ypreq_nokey) = 9;
+
+		ypresp_order
+		YPPROC_ORDER(ypreq_nokey) = 10;
+
+		ypresp_maplist 
+		YPPROC_MAPLIST(domainname) = 11;
+	} = 2;
+} = 100004;
+#endif
+#if !defined(YPSERV_ONLY) && !defined(YPBIND_ONLY)
+/*
+ * YPPUSHPROC_XFRRESP is the callback routine for result of YPPROC_XFR
+ */
+program YPPUSH_XFRRESPPROG {
+	version YPPUSH_XFRRESPVERS {
+		void
+		YPPUSHPROC_NULL(void) = 0;
+#ifdef STUPID_SUN_BUG /* argument and return value are backwards */
+		yppushresp_xfr	
+		YPPUSHPROC_XFRRESP(void) = 1;
+#else
+		void
+		YPPUSHPROC_XFRRESP(yppushresp_xfr) = 1;
+#endif
+	} = 1;
+} = 0x40000000;	/* transient: could be anything up to 0x5fffffff */
+#endif
+#if !defined(YPSERV_ONLY) && !defined(YPPUSH_ONLY)
+/*
+ * YP binding protocol
+ */
+program YPBINDPROG {
+	version YPBINDVERS {
+		void
+		YPBINDPROC_NULL(void) = 0;
+	
+		ypbind_resp
+		YPBINDPROC_DOMAIN(domainname) = 1;
+
+		void
+		YPBINDPROC_SETDOM(ypbind_setdom) = 2;
+	} = 2;
+} = 100007;
+
+#endif
diff --git a/services/librpc/include/rpcsvc/yp_prot.h b/services/librpc/include/rpcsvc/yp_prot.h
new file mode 100644
index 0000000..f29f3ce
--- /dev/null
+++ b/services/librpc/include/rpcsvc/yp_prot.h
@@ -0,0 +1,330 @@
+/*
+ * Copyright (c) 1992/3 Theo de Raadt <deraadt at fsa.ca>
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. The name of the author may not be used to endorse or promote
+ *    products derived from this software without specific prior written
+ *    permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * $FreeBSD: src/include/rpcsvc/yp_prot.h,v 1.10 1999/08/27 23:45:12 peter Exp $
+ */
+
+#ifndef _RPCSVC_YP_PROT_H_
+#define _RPCSVC_YP_PROT_H_
+
+/*
+ * YPSERV PROTOCOL:
+ *
+ * ypserv supports the following procedures:
+ *
+ * YPPROC_NULL		takes (void), returns (void).
+ * 			called to check if server is alive.
+ * YPPROC_DOMAIN	takes (char *), returns (bool_t).
+ * 			true if ypserv serves the named domain.
+ * YPPROC_DOMAIN_NOACK	takes (char *), returns (bool_t).
+ * 			true if ypserv serves the named domain.
+ *			used for broadcasts, does not ack if ypserv
+ *			doesn't handle named domain.
+ * YPPROC_MATCH		takes (struct ypreq_key), returns (struct ypresp_val)
+ * 			does a lookup.
+ * YPPROC_FIRST		takes (struct ypreq_nokey) returns (ypresp_key_val).
+ * 			gets the first key/datum from the map.
+ * YPPROC_NEXT		takes (struct ypreq_key) returns (ypresp_key_val).
+ * 			gets the next key/datum from the map.
+ * YPPROC_XFR		takes (struct ypreq_xfr), returns (void).
+ * 			tells ypserv to check if there is a new version of
+ *			the map.
+ * YPPROC_CLEAR		takes (void), returns (void).
+ * 			tells ypserv to flush it's file cache, so that
+ *			newly transferred files will get read.
+ * YPPROC_ALL		takes (struct ypreq_nokey), returns (bool_t and
+ *			struct ypresp_key_val).
+ * 			returns an array of data, with the bool_t being
+ * 			false on the last datum. read the source, it's
+ *			convoluted.
+ * YPPROC_MASTER	takes (struct ypreq_nokey), returns (ypresp_master).
+ * YPPROC_ORDER		takes (struct ypreq_nokey), returns (ypresp_order).
+ * YPPROC_MAPLIST	takes (char *), returns (struct ypmaplist *).
+ */
+
+#ifndef BOOL_DEFINED
+typedef u_int bool;
+#define BOOL_DEFINED
+#endif
+
+/* Program and version symbols, magic numbers */
+
+#define YPPROG		((u_long)100004)
+#define YPVERS		((u_long)2)
+#define YPVERS_ORIG	((u_long)1)
+#define YPMAXRECORD	((u_long)1024)
+#define YPMAXDOMAIN	((u_long)64)
+#define YPMAXMAP	((u_long)64)
+#define YPMAXPEER	((u_long)256)
+
+/*
+ * I don't know if anything of sun's depends on this, or if they
+ * simply defined it so that their own code wouldn't try to send
+ * packets over the ethernet MTU. This YP code doesn't use it.
+ */
+#define YPMSGSZ		1600
+
+#ifndef DATUM
+typedef struct {
+	char	*dptr;
+	int	dsize;
+} datum;
+#define DATUM
+#endif
+
+struct ypmap_parms {
+	char *domain;
+	char *map;
+	u_long ordernum;
+	char *owner;
+};
+
+struct ypreq_key {
+	char *domain;
+	char *map;
+	datum keydat;
+};
+
+struct ypreq_nokey {
+	char *domain;
+	char *map;
+};
+
+struct ypreq_xfr {
+	struct ypmap_parms map_parms;
+	u_long transid;
+	u_long proto;
+	u_short port;
+};
+#define ypxfr_domain	map_parms.domain
+#define ypxfr_map	map_parms.map
+#define ypxfr_ordernum	map_parms.ordernum
+#define ypxfr_owner	map_parms.owner
+
+struct ypresp_val {
+	u_long status;
+	datum valdat;
+};
+
+struct ypresp_key_val {
+	u_long status;
+	datum keydat;
+	datum valdat;
+};
+
+struct ypresp_master {
+	u_long status;
+	char *master;
+};
+
+struct ypresp_order {
+	u_long status;
+	u_long ordernum;
+};
+
+struct ypmaplist {
+	char ypml_name[YPMAXMAP + 1];
+	struct ypmaplist *ypml_next;
+};
+
+struct ypresp_maplist {
+	u_long status;
+	struct ypmaplist *list;
+};
+
+/* ypserv procedure numbers */
+#define YPPROC_NULL		((u_long)0)
+#define YPPROC_DOMAIN		((u_long)1)
+#define YPPROC_DOMAIN_NONACK	((u_long)2)
+#define YPPROC_MATCH		((u_long)3)
+#define YPPROC_FIRST		((u_long)4)
+#define YPPROC_NEXT		((u_long)5)
+#define YPPROC_XFR		((u_long)6)
+#define YPPROC_CLEAR		((u_long)7)
+#define YPPROC_ALL		((u_long)8)
+#define YPPROC_MASTER		((u_long)9)
+#define YPPROC_ORDER		((u_long)10)
+#define YPPROC_MAPLIST		((u_long)11)
+
+/* ypserv procedure return status values */
+#define YP_TRUE	 	((long)1)	/* general purpose success code */
+#define YP_NOMORE 	((long)2)	/* no more entries in map */
+#define YP_FALSE 	((long)0)	/* general purpose failure code */
+#define YP_NOMAP 	((long)-1)	/* no such map in domain */
+#define YP_NODOM 	((long)-2)	/* domain not supported */
+#define YP_NOKEY 	((long)-3)	/* no such key in map */
+#define YP_BADOP 	((long)-4)	/* invalid operation */
+#define YP_BADDB 	((long)-5)	/* server data base is bad */
+#define YP_YPERR 	((long)-6)	/* YP server error */
+#define YP_BADARGS 	((long)-7)	/* request arguments bad */
+#define YP_VERS		((long)-8)	/* YP server version mismatch */
+
+/*
+ * Sun's header file says:
+ * "Domain binding data structure, used by ypclnt package and ypserv modules.
+ * Users of the ypclnt package (or of this protocol) don't HAVE to know about
+ * it, but it must be available to users because _yp_dobind is a public
+ * interface."
+ *
+ * This is totally bogus! Nowhere else does Sun state that _yp_dobind() is
+ * a public interface, and I don't know any reason anyone would want to call
+ * it. But, just in case anyone does actually expect it to be available..
+ * we provide this.. exactly as Sun wants it.
+ */
+struct dom_binding {
+	struct dom_binding *dom_pnext;
+	char dom_domain[YPMAXDOMAIN + 1];
+	struct sockaddr_in dom_server_addr;
+	u_short dom_server_port;
+	int dom_socket;
+	CLIENT *dom_client;
+	u_short dom_local_port;
+	long dom_vers;
+};
+
+/*
+ * YPBIND PROTOCOL:
+ *
+ * ypbind supports the following procedures:
+ *
+ * YPBINDPROC_NULL	takes (void), returns (void).
+ *			to check if ypbind is running.
+ * YPBINDPROC_DOMAIN	takes (char *), returns (struct ypbind_resp).
+ *			requests that ypbind start to serve the
+ *			named domain (if it doesn't already)
+ * YPBINDPROC_SETDOM	takes (struct ypbind_setdom), returns (void).
+ *			used by ypset.
+ */
+
+#define YPBINDPROG		((u_long)100007)
+#define YPBINDVERS		((u_long)2)
+#define YPBINDVERS_ORIG		((u_long)1)
+
+/* ypbind procedure numbers */
+#define YPBINDPROC_NULL		((u_long)0)
+#define YPBINDPROC_DOMAIN	((u_long)1)
+#define YPBINDPROC_SETDOM	((u_long)2)
+
+/* error code in ypbind_resp.ypbind_status */
+enum ypbind_resptype {
+	YPBIND_SUCC_VAL = 1,
+	YPBIND_FAIL_VAL = 2,
+	_YPBIND_RESPTYPE = 0xffffffff
+};
+
+/* network order, of course */
+struct ypbind_binding {
+	struct in_addr	ypbind_binding_addr;
+	u_short		ypbind_binding_port;
+};
+
+struct ypbind_resp {
+	enum ypbind_resptype	ypbind_status;
+	union {
+		u_long			ypbind_error;
+		struct ypbind_binding	ypbind_bindinfo;
+	} ypbind_respbody;
+};
+
+/* error code in ypbind_resp.ypbind_respbody.ypbind_error */
+#define YPBIND_ERR_ERR		1	/* internal error */
+#define YPBIND_ERR_NOSERV	2	/* no bound server for passed domain */
+#define YPBIND_ERR_RESC		3	/* system resource allocation failure */
+
+/*
+ * Request data structure for ypbind "Set domain" procedure.
+ */
+struct ypbind_setdom {
+	char ypsetdom_domain[YPMAXDOMAIN + 1];
+	struct ypbind_binding ypsetdom_binding;
+	u_short ypsetdom_vers;
+};
+#define ypsetdom_addr ypsetdom_binding.ypbind_binding_addr
+#define ypsetdom_port ypsetdom_binding.ypbind_binding_port
+
+/*
+ * YPPUSH PROTOCOL:
+ *
+ * Sun says:
+ * "Protocol between clients (ypxfr, only) and yppush
+ *  yppush speaks a protocol in the transient range, which
+ *  is supplied to ypxfr as a command-line parameter when it
+ *  is activated by ypserv."
+ *
+ * This protocol is not implemented, naturally, because this YP
+ * implementation only does the client side.
+ */
+#define YPPUSHVERS		((u_long)1)
+#define YPPUSHVERS_ORIG		((u_long)1)
+
+/* yppush procedure numbers */
+#define YPPUSHPROC_NULL		((u_long)0)
+#define YPPUSHPROC_XFRRESP	((u_long)1)
+
+struct yppushresp_xfr {
+	u_long	transid;
+	u_long	status;
+};
+
+/* yppush status value in yppushresp_xfr.status */
+#define YPPUSH_SUCC	((long)1)	/* Success */
+#define YPPUSH_AGE	((long)2)	/* Master's version not newer */
+#define YPPUSH_NOMAP 	((long)-1)	/* Can't find server for map */
+#define YPPUSH_NODOM 	((long)-2)	/* Domain not supported */
+#define YPPUSH_RSRC 	((long)-3)	/* Local resource alloc failure */
+#define YPPUSH_RPC 	((long)-4)	/* RPC failure talking to server */
+#define YPPUSH_MADDR	((long)-5)	/* Can't get master address */
+#define YPPUSH_YPERR 	((long)-6)	/* YP server/map db error */
+#define YPPUSH_BADARGS 	((long)-7)	/* Request arguments bad */
+#define YPPUSH_DBM	((long)-8)	/* Local dbm operation failed */
+#define YPPUSH_FILE	((long)-9)	/* Local file I/O operation failed */
+#define YPPUSH_SKEW	((long)-10)	/* Map version skew during transfer */
+#define YPPUSH_CLEAR	((long)-11)	/* Can't send "Clear" req to local ypserv */
+#define YPPUSH_FORCE	((long)-12)	/* No local order number in map - use -f */
+#define YPPUSH_XFRERR	((long)-13)	/* ypxfr error */
+#define YPPUSH_REFUSED	((long)-14)	/* Transfer request refused by ypserv */
+
+struct inaddr;
+__BEGIN_DECLS
+bool_t	xdr_datum (XDR *, datum *);
+bool_t	xdr_ypreq_key (XDR *, struct ypreq_key *);
+bool_t	xdr_ypreq_nokey (XDR *, struct ypreq_nokey *);
+bool_t	xdr_ypreq_xfr (XDR *, struct ypreq_xfr *);
+bool_t	xdr_ypresp_val (XDR *, struct ypresp_val *);
+bool_t	xdr_ypresp_key_val (XDR *, struct ypresp_key_val *);
+bool_t	xdr_ypbind_resp (XDR *, struct ypbind_resp *);
+bool_t	xdr_ypbind_setdom (XDR *, struct ypbind_setdom *);
+bool_t	xdr_yp_inaddr (XDR *, struct inaddr *);
+bool_t	xdr_ypmap_parms (XDR *, struct ypmap_parms *);
+bool_t	xdr_yppushresp_xfr (XDR *, struct yppushresp_xfr *);
+bool_t	xdr_ypresp_order (XDR *, struct ypresp_order *);
+bool_t	xdr_ypresp_master (XDR *, struct ypresp_master *);
+bool_t	xdr_ypresp_maplist (XDR *, struct ypresp_maplist *);
+__END_DECLS
+
+#endif /* _RPCSVC_YP_PROT_H_ */
diff --git a/services/librpc/include/rpcsvc/ypclnt.h b/services/librpc/include/rpcsvc/ypclnt.h
new file mode 100644
index 0000000..6b8edfe
--- /dev/null
+++ b/services/librpc/include/rpcsvc/ypclnt.h
@@ -0,0 +1,93 @@
+/*
+ * Copyright (c) 1992/3 Theo de Raadt <deraadt at fsa.ca>
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. The name of the author may not be used to endorse or promote
+ *    products derived from this software without specific prior written
+ *    permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * $FreeBSD: src/include/rpcsvc/ypclnt.h,v 1.11 1999/08/27 23:45:12 peter Exp $
+ */
+
+#ifndef _RPCSVC_YPCLNT_H_
+#define _RPCSVC_YPCLNT_H_
+
+#include <sys/cdefs.h>
+
+#define YPERR_BADARGS	1		/* args to function are bad */
+#define YPERR_RPC	2		/* RPC failure */
+#define YPERR_DOMAIN	3		/* can't bind to a server for domain */
+#define YPERR_MAP	4		/* no such map in server's domain */
+#define YPERR_KEY	5		/* no such key in map */
+#define YPERR_YPERR	6		/* some internal YP server or client error */
+#define YPERR_RESRC	7		/* local resource allocation failure */
+#define YPERR_NOMORE	8		/* no more records in map database */
+#define YPERR_PMAP	9		/* can't communicate with portmapper */
+#define YPERR_YPBIND	10		/* can't communicate with ypbind */
+#define YPERR_YPSERV	11		/* can't communicate with ypserv */
+#define YPERR_NODOM	12		/* local domain name not set */
+#define YPERR_BADDB	13		/* YP data base is bad */
+#define YPERR_VERS	14		/* YP version mismatch */
+#define YPERR_ACCESS	15		/* access violation */
+#define YPERR_BUSY	16		/* database is busy */
+
+/*
+ * Types of update operations
+ */
+#define YPOP_CHANGE	1		/* change, do not add */
+#define YPOP_INSERT	2		/* add, do not change */
+#define YPOP_DELETE	3		/* delete this entry */
+#define YPOP_STORE 	4		/* add, or change */
+
+struct ypall_callback {
+	/* return non-0 to stop getting called */
+	int (*foreach) (unsigned long, char *, int, char *, int, void *);
+	char *data;		/* opaque pointer for use of callback fn */
+};
+
+struct dom_binding;
+
+__BEGIN_DECLS
+int	yp_bind		(char *dom);
+int	_yp_dobind	(char *dom, struct dom_binding **ypdb);
+void	yp_unbind	(char *dom);
+int	yp_get_default_domain (char **domp);
+int	yp_match 	(char *indomain, char *inmap,
+			    const char *inkey, int inkeylen, char **outval,
+			    int *outvallen);
+int	yp_first 	(char *indomain, char *inmap,
+			    char **outkey, int *outkeylen, char **outval,
+			    int *outvallen);
+int	yp_next		(char *indomain, char *inmap,
+			    char *inkey, int inkeylen, char **outkey,
+			    int *outkeylen, char **outval, int *outvallen);
+int	yp_master	(char *indomain, char *inmap, char **outname);
+int	yp_order	(char *indomain, char *inmap, int *outorder);
+int	yp_all		(char *indomain, char *inmap,
+			    struct ypall_callback *incallback);
+char *	yperr_string	(int incode);
+char *	ypbinderr_string (int incode);
+int	ypprot_err	(unsigned int incode);
+__END_DECLS
+
+#endif /* _RPCSVC_YPCLNT_H_ */
diff --git a/services/librpc/include/rpcsvc/yppasswd.x b/services/librpc/include/rpcsvc/yppasswd.x
new file mode 100644
index 0000000..73dca8e
--- /dev/null
+++ b/services/librpc/include/rpcsvc/yppasswd.x
@@ -0,0 +1,75 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+/*
+ * YP password update protocol
+ * Requires unix authentication
+ */
+
+#ifndef RPC_HDR
+%#ifndef lint
+%/*static char sccsid[] = "from: @(#)yppasswd.x 1.1 87/04/13 Copyr 1987 Sun Micro";*/
+%/*static char sccsid[] = "from: @(#)yppasswd.x	2.1 88/08/01 4.0 RPCSRC";*/
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/yppasswd.x,v 1.6 1999/08/27 23:45:12 peter Exp $";
+%#endif /* not lint */
+#endif
+
+program YPPASSWDPROG {
+	version YPPASSWDVERS {
+		/*
+		 * Update my passwd entry 
+		 */
+		int
+		YPPASSWDPROC_UPDATE(yppasswd) = 1;
+	} = 1;
+} = 100009;
+
+
+struct x_passwd {
+	string pw_name<>;	/* username */
+	string pw_passwd<>;	/* encrypted password */
+	int pw_uid;		/* user id */
+	int pw_gid;		/* group id */
+	string pw_gecos<>;	/* in real life name */
+	string pw_dir<>;	/* home directory */
+	string pw_shell<>;	/* default shell */
+};
+
+struct yppasswd {
+	string oldpass<>;	/* unencrypted old password */
+	x_passwd newpw;		/* new passwd entry */
+};
+
+
+#ifdef RPC_HDR
+%#include <sys/cdefs.h>
+%extern int _yppasswd ( char * , struct x_passwd * );
+%#define yppasswd(x,y) _yppasswd(x,y)
+#endif
diff --git a/services/librpc/include/rpcsvc/ypupdate_prot.x b/services/librpc/include/rpcsvc/ypupdate_prot.x
new file mode 100644
index 0000000..f16d5ee
--- /dev/null
+++ b/services/librpc/include/rpcsvc/ypupdate_prot.x
@@ -0,0 +1,88 @@
+%/*
+% * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+% * unrestricted use provided that this legend is included on all tape
+% * media and as a part of the software program in whole or part.  Users
+% * may copy or modify Sun RPC without charge, but are not authorized
+% * to license or distribute it to anyone else except as part of a product or
+% * program developed by the user or with the express written consent of
+% * Sun Microsystems, Inc.
+% *
+% * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+% * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+% * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+% *
+% * Sun RPC is provided with no support and without any obligation on the
+% * part of Sun Microsystems, Inc. to assist in its use, correction,
+% * modification or enhancement.
+% *
+% * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+% * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+% * OR ANY PART THEREOF.
+% *
+% * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+% * or profits or other special, indirect and consequential damages, even if
+% * Sun has been advised of the possibility of such damages.
+% *
+% * Sun Microsystems, Inc.
+% * 2550 Garcia Avenue
+% * Mountain View, California  94043
+% */
+
+%/*
+% * Copyright (c) 1986, 1990 by Sun Microsystems, Inc.
+% */
+%
+%/* from @(#)ypupdate_prot.x	1.3 91/03/11 TIRPC 1.0 */
+#ifndef RPC_HDR
+%#ifndef lint
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/ypupdate_prot.x,v 1.3 1999/08/27 23:45:13 peter Exp $";
+%#endif
+#endif
+%
+%/*
+% * Compiled from ypupdate_prot.x using rpcgen
+% * This is NOT source code!
+% * DO NOT EDIT THIS FILE!
+% */
+
+/*
+ * YP update service protocol
+ */
+#ifdef RPC_HDR
+%
+%#ifndef _rpcsvc_ypupdate_prot_h
+%#define _rpcsvc_ypupdate_prot_h
+%
+#endif
+
+const MAXMAPNAMELEN = 255;
+const MAXYPDATALEN  = 1023;
+const MAXERRMSGLEN  = 255;
+
+program YPU_PROG {
+	version YPU_VERS {
+		u_int YPU_CHANGE(ypupdate_args) = 1;
+		u_int YPU_INSERT(ypupdate_args) = 2;
+		u_int YPU_DELETE(ypdelete_args) = 3;
+		u_int YPU_STORE(ypupdate_args)  = 4;
+	} = 1;
+} = 100028;
+
+typedef opaque yp_buf<MAXYPDATALEN>;
+
+struct ypupdate_args {
+	string mapname<MAXMAPNAMELEN>;
+	yp_buf key;
+	yp_buf datum;
+};
+
+struct ypdelete_args {
+	string mapname<MAXMAPNAMELEN>;
+	yp_buf key;
+};
+
+#ifdef RPC_HDR
+%
+%#endif /* !_rpcsvc_ypupdate_prot_h */
+#endif
diff --git a/services/librpc/include/rpcsvc/ypxfrd.x b/services/librpc/include/rpcsvc/ypxfrd.x
new file mode 100644
index 0000000..1845a4f
--- /dev/null
+++ b/services/librpc/include/rpcsvc/ypxfrd.x
@@ -0,0 +1,173 @@
+/*
+ * Copyright (c) 1995, 1996
+ *	Bill Paul <wpaul at ctr.columbia.edu>.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *	This product includes software developed by Bill Paul.
+ * 4. Neither the name of the author nor the names of any co-contributors
+ *    may be used to endorse or promote products derived from this software
+ *    without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY Bill Paul AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL Bill Paul OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * $FreeBSD: src/include/rpcsvc/ypxfrd.x,v 1.7 1999/08/27 23:45:13 peter Exp $
+ */
+
+/*
+ * This protocol definition file describes a file transfer
+ * system used to very quickly move NIS maps from one host to
+ * another. This is similar to what Sun does with their ypxfrd
+ * protocol, but it must be stressed that this protocol is _NOT_
+ * compatible with Sun's. There are a couple of reasons for this:
+ *
+ * 1) Sun's protocol is proprietary. The protocol definition is
+ *    not freely available in any of the SunRPC source distributions,
+ *    even though the NIS v2 protocol is.
+ *
+ * 2) The idea here is to transfer entire raw files rather than
+ *    sending just the records. Sun uses ndbm for its NIS map files,
+ *    while FreeBSD uses Berkeley DB. Both are hash databases, but the
+ *    formats are incompatible, making it impossible for them to
+ *    use each others' files. Even if FreeBSD adopted ndbm for its
+ *    database format, FreeBSD/i386 is a little-endian OS and
+ *    SunOS/SPARC is big-endian; ndbm is byte-order sensitive and
+ *    not very smart about it, which means an attempt to read a
+ *    database on a little-endian box that was created on a big-endian
+ *    box (or vice-versa) can cause the ndbm code to eat itself.
+ *    Luckily, Berkeley DB is able to deal with this situation in
+ *    a more graceful manner.
+ *
+ * While the protocol is incompatible, the idea is the same: we just open
+ * up a TCP pipe to the client and transfer the raw map database 
+ * from the master server to the slave. This is many times faster than
+ * the standard yppush/ypxfr transfer method since it saves us from
+ * having to recreate the map databases via the DB library each time.
+ * For example: creating a passwd database with 30,000 entries with yp_mkdb
+ * can take a couple of minutes, but to just copy the file takes only a few
+ * seconds.
+ */
+
+#ifndef RPC_HDR
+%#ifndef lint
+%static const char rcsid[] =
+%  "$FreeBSD: src/include/rpcsvc/ypxfrd.x,v 1.7 1999/08/27 23:45:13 peter Exp $";
+%#endif /* not lint */
+#endif
+
+/* XXX cribbed from yp.x */
+const _YPMAXRECORD = 1024;
+const _YPMAXDOMAIN = 64;
+const _YPMAXMAP = 64;
+const _YPMAXPEER = 64;
+
+/* Suggested default -- not necesarrily the one used. */
+const YPXFRBLOCK = 32767;
+
+/*
+ * Possible return codes from the remote server.
+ */
+enum xfrstat {
+	XFR_REQUEST_OK	= 1,	/* Transfer request granted */
+	XFR_DENIED	= 2,	/* Transfer request denied */
+	XFR_NOFILE	= 3,	/* Requested map file doesn't exist */
+	XFR_ACCESS	= 4,	/* File exists, but I couldn't access it */
+	XFR_BADDB	= 5,	/* File is not a hash database */
+	XFR_READ_OK	= 6,	/* Block read successfully */
+	XFR_READ_ERR	= 7,	/* Read error during transfer */
+	XFR_DONE	= 8,	/* Transfer completed */
+	XFR_DB_ENDIAN_MISMATCH	= 9,	/* Database byte order mismatch */
+	XFR_DB_TYPE_MISMATCH	= 10	/* Database type mismatch */
+};
+
+/*
+ * Database type specifications. The client can use this to ask
+ * the server for a particular type of database or just take whatever
+ * the server has to offer.
+ */
+enum xfr_db_type {
+	XFR_DB_ASCII		= 1,	/* Flat ASCII text */
+	XFR_DB_BSD_HASH		= 2,	/* Berkeley DB, hash method */
+	XFR_DB_BSD_BTREE	= 3,	/* Berkeley DB, btree method */
+	XFR_DB_BSD_RECNO	= 4,	/* Berkeley DB, recno method */
+	XFR_DB_BSD_MPOOL	= 5,	/* Berkeley DB, mpool method */
+	XFR_DB_BSD_NDBM		= 6,	/* Berkeley DB, hash, ndbm compat */
+	XFR_DB_GNU_GDBM		= 7,	/* GNU GDBM */
+	XFR_DB_DBM		= 8,	/* Old, deprecated dbm format */
+	XFR_DB_NDBM		= 9,	/* ndbm format (used by Sun's NISv2) */
+	XFR_DB_OPAQUE		= 10,	/* Mystery format -- just pass along */
+	XFR_DB_ANY		= 11,	/* I'll take any format you've got */
+	XFR_DB_UNKNOWN		= 12	/* Unknown format */
+};
+
+/*
+ * Machine byte order specification. This allows the client to check
+ * that it's copying a map database from a machine of similar byte sex.
+ * This is necessary for handling database libraries that are fatally
+ * byte order sensitive.
+ *
+ * The XFR_ENDIAN_ANY type is for use with the Berkeley DB database
+ * formats; Berkeley DB is smart enough to make up for byte order
+ * differences, so byte sex isn't important.
+ */
+enum xfr_byte_order {
+	XFR_ENDIAN_BIG		= 1,	/* We want big endian */
+	XFR_ENDIAN_LITTLE	= 2,	/* We want little endian */
+	XFR_ENDIAN_ANY		= 3	/* We'll take whatever you got */
+};
+
+typedef string xfrdomain<_YPMAXDOMAIN>;
+typedef string xfrmap<_YPMAXMAP>;
+typedef string xfrmap_filename<_YPMAXMAP>;	/* actual name of map file */
+
+/*
+ * Ask the remote ypxfrd for a map using this structure.
+ * Note: we supply both a map name and a map file name. These are not
+ * the same thing. In the case of ndbm, maps are stored in two files:
+ * map.bykey.pag and may.bykey.dir. We may also have to deal with
+ * file extensions (on the off chance that the remote server is supporting
+ * multiple DB formats). To handle this, we tell the remote server both
+ * what map we want and, in the case of ndbm, whether we want the .dir
+ * or the .pag part. This name should not be a fully qualified path:
+ * it's up to the remote server to decide which directories to look in.
+ */
+struct ypxfr_mapname {
+	xfrmap xfrmap;
+	xfrdomain xfrdomain;
+	xfrmap_filename xfrmap_filename;
+	xfr_db_type xfr_db_type;
+	xfr_byte_order xfr_byte_order;
+};
+
+/* Read response using this structure. */
+union xfr switch (bool ok) {
+case TRUE:
+	opaque xfrblock_buf<>;
+case FALSE:
+	xfrstat xfrstat;
+};
+
+program YPXFRD_FREEBSD_PROG {
+	version YPXFRD_FREEBSD_VERS {
+		union xfr
+		YPXFRD_GETMAP(ypxfr_mapname) = 1;
+	} = 1;
+} = 600100069;	/* 100069 + 60000000 -- 100069 is the Sun ypxfrd prog number */
diff --git a/services/librpc/src/rpc/DISCLAIMER b/services/librpc/src/rpc/DISCLAIMER
new file mode 100644
index 0000000..1a66d5f
--- /dev/null
+++ b/services/librpc/src/rpc/DISCLAIMER
@@ -0,0 +1,28 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
diff --git a/services/librpc/src/rpc/README b/services/librpc/src/rpc/README
new file mode 100644
index 0000000..ad9d70f
--- /dev/null
+++ b/services/librpc/src/rpc/README
@@ -0,0 +1,233 @@
+RPCSRC 4.0 7/11/89
+
+This distribution contains Sun Microsystem's implementation of the
+RPC and XDR protocols and is compatible with 4.2BSD and 4.3BSD.  Also
+included is complete documentation, utilities, RPC service
+specification files, and demonstration services in the format used by
+the RPC protocol compiler (rpcgen).  See WHAT'S NEW below for
+details.
+
+NOTE ABOUT SECURE RPC:
+
+This release of RPCSRC contains most of the code needed to implement
+Secure RPC (see "DES Authentication" in the RPC Protocol Specification,
+doc/rpc.rfc.ms).  Due to legal considerations, we are unable to
+distribute an implementation of DES, the Data Encryption Standard, which
+Secure RPC requires.  For this reason, all of the files, documentation, and
+programs associated with Secure RPC have been placed into a separate
+directory, secure_rpc.  The RPC library contained in the main body of this
+release *DOES NOT* support Secure RPC.  See secure_rpc/README for more
+details.  (A DES library was posted in Volume 18 of comp.sources.unix.)
+
+If you wish to report bugs found in this release, send mail to:
+
+Portable ONC/NFS
+Sun Microsystems, Inc
+MS 12-33
+2550 Garcia Avenue
+Mountain View, CA  94043
+
+or send Email to nfsnet at sun.com (the Internet) or sun!nfsnet (Usenet).
+
+ROADMAP
+
+The directory hierarchy is as follows:
+
+    demo/       Various demonstration services
+    demo/dir        Remote directory lister
+    demo/msg        Remote console message delivery service
+    demo/sort       Remote sort service
+
+    doc/        Documentation for RPC, XDR and NFS in "-ms" format.
+
+    etc/        Utilities (rpcinfo and portmap).  portmap must be
+                started by root before any other RPC network services are
+                used.  SEE BELOW FOR BUGFIX TO 4.3BSD COMPILER.
+
+    man/        Manual pages for RPC library, rpcgen, and utilities.
+
+    rpc/        The RPC and XDR library.  SEE BELOW
+                FOR BUGFIX TO 4.2BSD COMPILER.
+
+    rpcgen/     The RPC Language compiler (for .x files)
+
+    rpcsvc/     Service definition files for various services and the
+                server and client code for the Remote Status service.
+
+    secure_rpc/ The files in this directory are used to build a version of
+                the RPC library with DES Authentication.  See the README
+                file in that directory for more details.
+
+BUILD INSTRUCTIONS
+
+Makefiles can be found in all directories except for man.  The
+Makefile in the top directory will cause these others to be invoked
+(except for in the doc, man and demo directories), in turn building the
+entire release.
+
+WARNING!  THE DEFAULT INSTALLATION PROCEDURES WILL INSTALL FILES
+IN /usr/include, /usr/lib, /usr/bin and /etc.
+
+The master RPC include file, rpc/rpc.h, is used by all programs and
+routines that use RPC.  It includes other RPC and system include files
+needed by the RPC system.  PLEASE NOTE: If your system has NFS, it
+may have been based on Sun's NFS Source.  The include files installed
+by this package may duplicate include files you will find on your NFS
+system.  The RPCSRC 4.0 include files are upwardly compatible to all
+NFS Source include files as of the date of this distribution (not
+including any new definitions or declarations added by your system
+vendor).  HOWEVER: Please read the comments towards the end of
+rpc/rpc.h regarding rpc/netdb.h.  You may need to uncomment the
+inclusion of that file if the structures it defines are already
+defined by your system's include files.
+
+After making any compiler fixes that are needed (see below), at
+the top directory, type:
+
+    make install
+
+For all installations, the Makefile macro DESTDIR is prepended to the
+installation path.  It is defined to be null in the Makefiles, so
+installations are relative to root.  (You will probably need root
+privileges for installing the files under the default path.)  To
+install the files under some other tree (e.g., /usr/local), use the
+command:
+
+    make install DESTDIR=/usr/local
+
+This will place the include files in /usr/local/usr/include, the RPC
+library in /usr/local/usr/lib, rpcgen in /usr/local/usr/bin, and the
+utilities in /usr/local/etc.  You'll have to edit the Makefiles or
+install the files by hand if you want to do anything other than this
+kind of relocation of the installation tree.
+
+The RPC library will be built and installed first.  By default it is
+installed in /usr/lib as "librpclib.a".  The directory
+/usr/include/rpc will also be created, and several header files will
+be installed there.  ALL RPC SERVICES INCLUDE THESE HEADER FILES.
+
+The programs in etc/ link in routines from librpclib.a.  If you change
+where it is installed, be sure to edit etc/'s Makefile to reflect this.
+These programs are installed in /etc.  PORTMAP MUST BE RUNNING ON
+YOUR SYSTEM BEFORE YOU START ANY OTHER RPC SERVICE.
+
+rpcgen is installed in /usr/bin.  This program is required to build
+the demonstration services in demo and the rstat client and server in
+rpcsvc/.
+
+The rpcsvc/ directory will install its files in the directory
+/usr/include/rpcsvc.  The Remote Status service (rstat_svc) will be
+compiled and installed in /etc.  If you wish to make this service
+available, you should either start this service when needed or have
+it started at boot time by invoking it in your /etc/rc.local script.
+(Be sure that portmap is started first!)  Sun has modified its
+version of inetd to automatically start RPC services.  (Use "make
+LIB=" when building rstat on a Sun Workstation.)  The Remote Status
+client (rstat) will be installed in /usr/bin.  This program queries
+the rstat_svc on a remote host and prints a system status summary
+similar to the one printed by "uptime".
+
+The documentation is not built during the "make install" command.
+Typing "make" in the doc directory will cause all of the manuals to
+be formatted using nroff into a single file.  We have had a report
+that certain "troff" equivalents have trouble processing the full
+manual.  If you have trouble, try building the manuals individually
+(see the Makefile).
+
+The demonstration services in the demo directory are not built by the
+top-level "make install" command.  To build these, cd to the demo
+directory and enter "make".  The three services will be built.
+RPCGEN MUST BE INSTALLED in a path that make can find.  To run the
+services, start the portmap program as root and invoke the service
+(you probably will want to put it in the background).  rpcinfo can be
+used to check that the service succeeded in getting registered with
+portmap, and to ping the service (see rpcinfo's man page).  You can
+then use the corresponding client program to exercise the service.
+To build these services on a Sun workstation, you must prevent the
+Makefile from trying to link the RPC library (as these routines are
+already a part of Sun's libc).  Use: "make LIB=".
+
+BUGFIX FOR 4.3BSD COMPILER
+
+The use of a 'void *' declaration for one of the arguments in
+the reply_proc() procedure in etc/rpcinfo.c will trigger a bug
+in the 4.3BSD compiler.  The bug is fixed by the following change to
+the compiler file mip/manifest.h:
+
+*** manifest.h.r1.1	Thu Apr 30 13:52:25 1987
+--- manifest.h.r1.2	Mon Nov 23 18:58:17 1987
+***************
+*** 21,27 ****
+  /*
+   * Bogus type values
+   */
+! #define TNULL	PTR		/* pointer to UNDEF */
+  #define TVOID	FTN		/* function returning UNDEF (for void) */
+  
+  /*
+--- 21,27 ----
+  /*
+   * Bogus type values
+   */
+! #define TNULL	INCREF(MOETY)	/* pointer to MOETY -- impossible type */
+  #define TVOID	FTN		/* function returning UNDEF (for void) */
+  
+  /*
+
+If you cannot fix your compiler, change the declaration in reply_proc()
+from 'void *' to 'char *'.
+
+BUGFIX FOR 4.2BSD COMPILER
+
+Unpatched 4.2BSD compilers complain about valid C.  You can make old
+compilers happy by changing some voids to ints.  However, the fix to
+the 4.2 VAX compiler is as follows (to mip/trees.c):
+
+*** trees.c.r1.1	Mon May 11 13:47:58 1987
+--- trees.c.r1.2	Wed Jul  2 18:28:52 1986
+***************
+*** 1247,1253 ****
+  		if(o==CAST && mt1==0)return(TYPL+TYMATCH);
+  		if( mt12 & MDBI ) return( TYPL+LVAL+TYMATCH );
+  		else if( (mt1&MENU)||(mt2&MENU) ) return( LVAL+NCVT+TYPL+PTMATCH+PUN );
+! 		else if( mt12 == 0 ) break;
+  		else if( mt1 & MPTR ) return( LVAL+PTMATCH+PUN );
+  		else if( mt12 & MPTI ) return( TYPL+LVAL+TYMATCH+PUN );
+  		break;
+--- 1261,1269 ----
+  		if(o==CAST && mt1==0)return(TYPL+TYMATCH);
+  		if( mt12 & MDBI ) return( TYPL+LVAL+TYMATCH );
+  		else if( (mt1&MENU)||(mt2&MENU) ) return( LVAL+NCVT+TYPL+PTMATCH+PUN );
+! 		/* if right is TVOID and looks like a CALL, is not ok */
+! 		else if (mt2 == 0 && (p->in.right->in.op == CALL || p->in.right->in.op == UNARY CALL))
+! 			break;
+  		else if( mt1 & MPTR ) return( LVAL+PTMATCH+PUN );
+  		else if( mt12 & MPTI ) return( TYPL+LVAL+TYMATCH+PUN );
+  		break;
+
+WHAT'S NEW IN THIS RELEASE: RPCSRC 4.0
+
+The previous release was RPCSRC 3.9.  As with all previous releases,
+this release is based directly on files from Sun Microsystem's
+implementation.
+
+Upgrade from RPCSRC 3.9
+
+1)  RPCSRC 4.0 upgrades RPCSRC 3.9.  Improvements from SunOS 4.0 have
+    been integrated into this release.
+
+Secure RPC (in the secure_rpc/ directory)
+
+2)  DES Authentication routines and programs are provided.
+3)  A new manual, "Secure NFS" is provided, which describes Secure RPC
+    and Secure NFS.
+4)  Skeleton routines and manual pages are provided which describe the
+    DES encryption procedures required by Secure RPC.  HOWEVER, NO DES
+    ROUTINE IS PROVIDED.
+
+New Functionality
+
+5)  rpcinfo can now be used to de-register services from the portmapper
+    which may have terminated abnormally.
+6)  A new client, rstat, is provided which queries the rstat_svc and
+    prints a status line similar to the one displayed by "uptime".
diff --git a/services/librpc/src/rpc/auth_none.c b/services/librpc/src/rpc/auth_none.c
new file mode 100644
index 0000000..48b3741
--- /dev/null
+++ b/services/librpc/src/rpc/auth_none.c
@@ -0,0 +1,138 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)auth_none.c 1.19 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)auth_none.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/auth_none.c,v 1.9 1999/08/28 00:00:32 peter Exp $";
+#endif
+
+/*
+ * auth_none.c
+ * Creates a client authentication handle for passing "null"
+ * credentials and verifiers to remote systems.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdlib.h>
+#include <rpc/types.h>
+#include <rpc/xdr.h>
+#include <rpc/auth.h>
+#define MAX_MARSHAL_SIZE 20
+
+/*
+ * Authenticator operations routines
+ */
+static void	authnone_verf(AUTH*);
+static void	authnone_destroy(AUTH*);
+static int	authnone_marshal(AUTH*, XDR*);
+static int	authnone_validate(AUTH*, struct opaque_auth *);
+static int	authnone_refresh(AUTH*);
+
+static struct auth_ops ops = {
+	authnone_verf,
+	authnone_marshal,
+	authnone_validate,
+	authnone_refresh,
+	authnone_destroy
+};
+
+static struct authnone_private {
+	AUTH	no_client;
+	char	marshalled_client[MAX_MARSHAL_SIZE];
+	u_int	mcnt;
+} *authnone_private;
+
+AUTH *
+authnone_create(void)
+{
+	struct authnone_private *ap = authnone_private;
+	XDR xdr_stream;
+	XDR *xdrs;
+
+	if (ap == 0) {
+		ap = (struct authnone_private *)calloc(1, sizeof (*ap));
+		if (ap == 0)
+			return (0);
+		authnone_private = ap;
+	}
+	if (!ap->mcnt) {
+		ap->no_client.ah_cred = ap->no_client.ah_verf = _null_auth;
+		ap->no_client.ah_ops = &ops;
+		xdrs = &xdr_stream;
+		xdrmem_create(xdrs, ap->marshalled_client, (u_int)MAX_MARSHAL_SIZE,
+		    XDR_ENCODE);
+		(void)xdr_opaque_auth(xdrs, &ap->no_client.ah_cred);
+		(void)xdr_opaque_auth(xdrs, &ap->no_client.ah_verf);
+		ap->mcnt = XDR_GETPOS(xdrs);
+		XDR_DESTROY(xdrs);
+	}
+	return (&ap->no_client);
+}
+
+/*ARGSUSED*/
+static int
+authnone_marshal(AUTH *client, XDR *xdrs)
+{
+	struct authnone_private *ap = authnone_private;
+
+	if (ap == 0)
+		return (0);
+	return ((*xdrs->x_ops->x_putbytes)(xdrs,
+	    ap->marshalled_client, ap->mcnt));
+}
+
+static void
+authnone_verf(AUTH *client)
+{
+}
+
+static int
+authnone_validate(AUTH *client, struct opaque_auth *opaque)
+{
+
+	return (TRUE);
+}
+
+static int
+authnone_refresh(AUTH *client)
+{
+
+	return (FALSE);
+}
+
+static void
+authnone_destroy(AUTH *client)
+{
+}
diff --git a/services/librpc/src/rpc/auth_unix.c b/services/librpc/src/rpc/auth_unix.c
new file mode 100644
index 0000000..67d3962
--- /dev/null
+++ b/services/librpc/src/rpc/auth_unix.c
@@ -0,0 +1,345 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)auth_unix.c 1.19 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)auth_unix.c	2.2 88/08/01 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/auth_unix.c,v 1.12 1999/12/29 05:04:16 peter Exp $";
+#endif
+
+/*
+ * auth_unix.c, Implements UNIX style authentication parameters.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ *
+ * The system is very weak.  The client uses no encryption for it's
+ * credentials and only sends null verifiers.  The server sends backs
+ * null verifiers or optionally a verifier that suggests a new short hand
+ * for the credentials.
+ *
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <string.h>
+
+#include <sys/param.h>
+#include <rpc/types.h>
+#include <rpc/xdr.h>
+#include <rpc/auth.h>
+#include <rpc/auth_unix.h>
+
+/*
+ * Unix authenticator operations vector
+ */
+static void	authunix_nextverf(AUTH*);
+static int	authunix_marshal(AUTH*, XDR*);
+static int	authunix_validate(AUTH*, struct opaque_auth *);
+static int	authunix_refresh(AUTH*);
+static void	authunix_destroy(AUTH*);
+
+static struct auth_ops auth_unix_ops = {
+	authunix_nextverf,
+	authunix_marshal,
+	authunix_validate,
+	authunix_refresh,
+	authunix_destroy
+};
+
+/*
+ * This struct is pointed to by the ah_private field of an auth_handle.
+ */
+struct audata {
+	struct opaque_auth	au_origcred;	/* original credentials */
+	struct opaque_auth	au_shcred;	/* short hand cred */
+	u_long			au_shfaults;	/* short hand cache faults */
+	char			au_marshed[MAX_AUTH_BYTES];
+	u_int			au_mpos;	/* xdr pos at end of marshed */
+};
+#define	AUTH_PRIVATE(auth)	((struct audata *)auth->ah_private)
+
+static void marshal_new_auth(AUTH *);
+
+/*
+ * This goop is here because some servers refuse to accept a
+ * credential with more than some number (usually 8) supplementary
+ * groups.  Blargh!
+ */
+static int authunix_maxgrouplist = 0;
+
+void
+set_rpc_maxgrouplist(int num)
+{
+	authunix_maxgrouplist = num;
+}
+
+/*
+ * Create a unix style authenticator.
+ * Returns an auth handle with the given stuff in it.
+ */
+AUTH *
+authunix_create(
+	char *machname,
+	int uid,
+	int gid,
+	int len,
+	int *aup_gids)
+{
+	struct authunix_parms aup;
+	char mymem[MAX_AUTH_BYTES];
+	struct timeval now;
+	XDR xdrs;
+	register AUTH *auth;
+	register struct audata *au;
+
+	/*
+	 * Allocate and set up auth handle
+	 */
+	auth = (AUTH *)mem_alloc(sizeof(*auth));
+#ifndef _KERNEL
+	if (auth == NULL) {
+		(void)fprintf(stderr, "authunix_create: out of memory\n");
+		return (NULL);
+	}
+#endif
+	au = (struct audata *)mem_alloc(sizeof(*au));
+#ifndef _KERNEL
+	if (au == NULL) {
+		(void)fprintf(stderr, "authunix_create: out of memory\n");
+		return (NULL);
+	}
+#endif
+	auth->ah_ops = &auth_unix_ops;
+	auth->ah_private = (caddr_t)au;
+	auth->ah_verf = au->au_shcred = _null_auth;
+	au->au_shfaults = 0;
+
+	/*
+	 * fill in param struct from the given params
+	 */
+	(void)gettimeofday(&now,  (struct timezone *)0);
+	aup.aup_time = now.tv_sec;
+	aup.aup_machname = machname;
+	aup.aup_uid = uid;
+	aup.aup_gid = gid;
+	/* GW: continuation of max group list hack */
+	if(authunix_maxgrouplist != 0) {
+		aup.aup_len = ((len < authunix_maxgrouplist) ? len
+			       : authunix_maxgrouplist);
+	} else {
+		aup.aup_len = (u_int)len;
+	}
+	aup.aup_gids = aup_gids;
+
+	/*
+	 * Serialize the parameters into origcred
+	 */
+	xdrmem_create(&xdrs, mymem, MAX_AUTH_BYTES, XDR_ENCODE);
+	if (! xdr_authunix_parms(&xdrs, &aup))
+		abort();
+	au->au_origcred.oa_length = len = XDR_GETPOS(&xdrs);
+	au->au_origcred.oa_flavor = AUTH_UNIX;
+#ifdef _KERNEL
+	au->au_origcred.oa_base = mem_alloc((u_int) len);
+#else
+	if ((au->au_origcred.oa_base = mem_alloc((u_int) len)) == NULL) {
+		(void)fprintf(stderr, "authunix_create: out of memory\n");
+		return (NULL);
+	}
+#endif
+	memcpy(au->au_origcred.oa_base, mymem, (u_int)len);
+
+	/*
+	 * set auth handle to reflect new cred.
+	 */
+	auth->ah_cred = au->au_origcred;
+	marshal_new_auth(auth);
+	return (auth);
+}
+
+/*
+ * Returns an auth handle with parameters determined by doing lots of
+ * syscalls.
+ */
+AUTH *
+authunix_create_default(void)
+{
+	register int len;
+	char machname[MAX_MACHINE_NAME + 1];
+	register int uid;
+	register int gid;
+	int gids[NGRPS];
+	int i;
+	gid_t real_gids[NGROUPS];
+
+	if (gethostname(machname, MAX_MACHINE_NAME) == -1)
+		abort();
+	machname[MAX_MACHINE_NAME] = 0;
+	uid = (int)geteuid();
+	gid = (int)getegid();
+	if ((len = getgroups(NGROUPS, real_gids)) < 0)
+		abort();
+	if(len > NGRPS) len = NGRPS; /* GW: turn `gid_t's into `int's */
+	for(i = 0; i < len; i++) {
+		gids[i] = (int)real_gids[i];
+	}
+	return (authunix_create(machname, uid, gid, len, gids));
+}
+
+/*
+ * authunix operations
+ */
+
+static void
+authunix_nextverf(AUTH *auth)
+{
+	/* no action necessary */
+}
+
+static int
+authunix_marshal(AUTH *auth, XDR *xdrs)
+{
+	struct audata *au = AUTH_PRIVATE(auth);
+
+	return (XDR_PUTBYTES(xdrs, au->au_marshed, au->au_mpos));
+}
+
+static int
+authunix_validate( AUTH *auth, struct opaque_auth *verf )
+{
+	register struct audata *au;
+	XDR xdrs;
+
+	if (verf->oa_flavor == AUTH_SHORT) {
+		au = AUTH_PRIVATE(auth);
+		xdrmem_create(&xdrs, verf->oa_base, verf->oa_length, XDR_DECODE);
+
+		if (au->au_shcred.oa_base != NULL) {
+			mem_free(au->au_shcred.oa_base,
+			    au->au_shcred.oa_length);
+			au->au_shcred.oa_base = NULL;
+		}
+		if (xdr_opaque_auth(&xdrs, &au->au_shcred)) {
+			auth->ah_cred = au->au_shcred;
+		} else {
+			xdrs.x_op = XDR_FREE;
+			(void)xdr_opaque_auth(&xdrs, &au->au_shcred);
+			au->au_shcred.oa_base = NULL;
+			auth->ah_cred = au->au_origcred;
+		}
+		marshal_new_auth(auth);
+	}
+	return (TRUE);
+}
+
+static int
+authunix_refresh(AUTH *auth)
+{
+	struct audata *au = AUTH_PRIVATE(auth);
+	struct authunix_parms aup;
+	struct timeval now;
+	XDR xdrs;
+	int stat;
+
+	if (auth->ah_cred.oa_base == au->au_origcred.oa_base) {
+		/* there is no hope.  Punt */
+		return (FALSE);
+	}
+	au->au_shfaults ++;
+
+	/* first deserialize the creds back into a struct authunix_parms */
+	aup.aup_machname = NULL;
+	aup.aup_gids = (int *)NULL;
+	xdrmem_create(&xdrs, au->au_origcred.oa_base,
+	    au->au_origcred.oa_length, XDR_DECODE);
+	stat = xdr_authunix_parms(&xdrs, &aup);
+	if (! stat)
+		goto done;
+
+	/* update the time and serialize in place */
+	(void)gettimeofday(&now, (struct timezone *)0);
+	aup.aup_time = now.tv_sec;
+	xdrs.x_op = XDR_ENCODE;
+	XDR_SETPOS(&xdrs, 0);
+	stat = xdr_authunix_parms(&xdrs, &aup);
+	if (! stat)
+		goto done;
+	auth->ah_cred = au->au_origcred;
+	marshal_new_auth(auth);
+done:
+	/* free the struct authunix_parms created by deserializing */
+	xdrs.x_op = XDR_FREE;
+	(void)xdr_authunix_parms(&xdrs, &aup);
+	XDR_DESTROY(&xdrs);
+	return (stat);
+}
+
+static void
+authunix_destroy(AUTH *auth)
+{
+	struct audata *au = AUTH_PRIVATE(auth);
+
+	mem_free(au->au_origcred.oa_base, au->au_origcred.oa_length);
+
+	if (au->au_shcred.oa_base != NULL)
+		mem_free(au->au_shcred.oa_base, au->au_shcred.oa_length);
+
+	mem_free(auth->ah_private, sizeof(struct audata));
+
+	if (auth->ah_verf.oa_base != NULL)
+		mem_free(auth->ah_verf.oa_base, auth->ah_verf.oa_length);
+
+	mem_free((caddr_t)auth, sizeof(*auth));
+}
+
+/*
+ * Marshals (pre-serializes) an auth struct.
+ * sets private data, au_marshed and au_mpos
+ */
+static void
+marshal_new_auth(AUTH *auth)
+{
+	XDR		xdr_stream;
+	XDR	*xdrs = &xdr_stream;
+	struct audata *au = AUTH_PRIVATE(auth);
+
+	xdrmem_create(xdrs, au->au_marshed, MAX_AUTH_BYTES, XDR_ENCODE);
+	if ((! xdr_opaque_auth(xdrs, &(auth->ah_cred))) ||
+	    (! xdr_opaque_auth(xdrs, &(auth->ah_verf)))) {
+		perror("auth_none.c - Fatal marshalling problem");
+	} else {
+		au->au_mpos = XDR_GETPOS(xdrs);
+	}
+	XDR_DESTROY(xdrs);
+}
diff --git a/services/librpc/src/rpc/authunix_prot.c b/services/librpc/src/rpc/authunix_prot.c
new file mode 100644
index 0000000..84acf46
--- /dev/null
+++ b/services/librpc/src/rpc/authunix_prot.c
@@ -0,0 +1,71 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)authunix_prot.c 1.15 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)authunix_prot.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/authunix_prot.c,v 1.6 1999/08/28 00:00:33 peter Exp $";
+#endif
+
+/*
+ * authunix_prot.c
+ * XDR for UNIX style authentication parameters for RPC
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <rpc/types.h>
+#include <rpc/xdr.h>
+#include <rpc/auth.h>
+#include <rpc/auth_unix.h>
+
+/*
+ * XDR for unix authentication parameters.
+ */
+bool_t
+xdr_authunix_parms(
+	XDR *xdrs,
+	struct authunix_parms *p)
+{
+
+	if (xdr_u_long(xdrs, &(p->aup_time))
+	    && xdr_string(xdrs, &(p->aup_machname), MAX_MACHINE_NAME)
+	    && xdr_int(xdrs, &(p->aup_uid))
+	    && xdr_int(xdrs, &(p->aup_gid))
+	    && xdr_array(xdrs, (caddr_t *)(void *)&(p->aup_gids),
+		    &(p->aup_len), NGRPS, sizeof(int), (xdrproc_t) xdr_int) ) {
+		return (TRUE);
+	}
+	return (FALSE);
+}
diff --git a/services/librpc/src/rpc/bindresvport.3 b/services/librpc/src/rpc/bindresvport.3
new file mode 100644
index 0000000..02a079d
--- /dev/null
+++ b/services/librpc/src/rpc/bindresvport.3
@@ -0,0 +1,106 @@
+.\" @(#)bindresvport.3n	2.2 88/08/02 4.0 RPCSRC; from 1.7 88/03/14 SMI
+.\" $FreeBSD: src/lib/libc/rpc/bindresvport.3,v 1.10 2000/01/27 02:55:01 bde Exp $
+.\"
+.Dd January 27, 2000
+.Dt BINDRESVPORT 3
+.Os
+.Sh NAME
+.Nm bindresvport ,
+.Nm bindresvport_sa
+.Ndbind a socket to a privileged IP port
+.Sh SYNOPSIS
+.Fd #include <rpc/rpc.h>
+.Ft int
+.Fn bindresvport "int sd" "struct sockaddr_in *sin"
+.Ft int
+.Fn bindresvport_sa "int sd" "struct sockaddr *sa"
+.Sh DESCRIPTION
+.Fn bindresvport
+and
+.Fn bindresvport_sa
+are used to bind a socket descriptor to a privileged
+.Tn IP
+port, that is, a
+port number in the range 0-1023.
+.Pp
+Only root can bind to a privileged port; this call will fail for any
+other users.
+.Pp
+When
+.Va sin
+is not null,
+.Va sin->sin_family
+must be initialized to the address family of the socket, passed by
+.Va sd .
+If the value of sin->sin_port is non-zero
+.Fn bindresvport
+will attempt to use that specific port.  If it fails, it chooses another
+privileged port automatically.
+.Pp
+It is legal to pass null pointer to
+.Va sin .
+In this case, the caller cannot get the port number
+.Fn bindresvport
+has picked.
+.Pp
+Function prototype of
+.Fn bindresvport
+is biased to
+.Dv AF_INET
+socket.
+.Fn bindresvport_sa
+acts exactly the same, with more neutral function prototype.
+Note that both functions behave exactly the same, and
+both support
+.Dv AF_INET6
+sockets as well as
+.Dv AF_INET
+sockets.
+.Sh RETURN VALUES
+.Fn bindresvport
+and
+.Fn bindresvport_sa
+return 0 if they are successful, otherwise \-1 is returned and
+.Va errno
+set to reflect the cause of the error.
+.Sh ERRORS
+The
+.Fn bindresvport
+and
+.Fn bindresvport_sa
+functions fail if:
+.Bl -tag -width Er
+.It Bq Er EBADF
+.Fa sd
+is not a valid descriptor.
+.It Bq Er ENOTSOCK
+.Fa sd
+is not a socket.
+.It Bq Er EADDRNOTAVAIL
+The specified address is not available from the local machine.
+.It Bq Er EADDRINUSE
+The specified address is already in use.
+.It Bq Er EINVAL
+The socket is already bound to an address,
+or the socket family and the family of specified address mismatch.
+.It Bq Er EACCES
+The requested address is protected, and the current user
+has inadequate permission to access it.
+.It Bq Er EFAULT
+The
+.Fa name
+parameter is not in a valid part of the user
+address space.
+.It Bq Er ENOBUFS
+Insufficient resources were available in the system
+to perform the operation.
+.It Bq Er EPFNOSUPPORT
+The protocol family has not been configured into the
+system, no implementation for it exists,
+or address family did not match between arguments.
+.El
+.Sh "SEE ALSO"
+.Xr bind 2 ,
+.Xr socket 2 ,
+.Xr rresvport 3 ,
+.Xr rresvport_af 3
diff --git a/services/librpc/src/rpc/bindresvport.c b/services/librpc/src/rpc/bindresvport.c
new file mode 100644
index 0000000..849d664
--- /dev/null
+++ b/services/librpc/src/rpc/bindresvport.c
@@ -0,0 +1,160 @@
+/*	$NetBSD: bindresvport.c,v 1.19 2000/07/06 03:03:59 christos Exp $	*/
+
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)bindresvport.c 1.8 88/02/08 SMI";*/
+/*static char *sccsid = "from: @(#)bindresvport.c	2.2 88/07/29 4.0 RPCSRC";*/
+/*from: OpenBSD: bindresvport.c,v 1.7 1996/07/30 16:25:47 downsj Exp */
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/bindresvport.c,v 1.12 2000/01/26 09:02:42 shin Exp $";
+#endif
+
+/*
+ * Copyright (c) 1987 by Sun Microsystems, Inc.
+ *
+ * Portions Copyright(C) 1996, Jason Downs.  All rights reserved.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <sys/types.h>
+#include <sys/socket.h>
+
+#include <netinet/in.h>
+
+#include <errno.h>
+#include <string.h>
+#include <unistd.h>
+
+#include <rpc/rpc.h>
+
+/*
+ * Bind a socket to a privileged IP port
+ */
+int
+bindresvport(
+	int sd,
+	struct sockaddr_in *sin)
+{
+	return bindresvport_sa(sd, (struct sockaddr *)sin);
+}
+
+/*
+ * Bind a socket to a privileged IP port
+ */
+int
+bindresvport_sa(
+	int sd,
+	struct sockaddr *sa)
+{
+	int old, error, af;
+	struct sockaddr myaddr;
+	struct sockaddr_in *sin;
+#ifdef INET6
+	struct sockaddr_in6 *sin6;
+#endif
+	int proto, portrange, portlow;
+	u_int16_t port;
+	socklen_t salen;
+
+	if (sa == NULL) {
+		salen = sizeof(myaddr);
+		sa = (struct sockaddr *)&myaddr;
+
+		if (getsockname(sd, sa, &salen) == -1)
+			return -1;	/* errno is correctly set */
+
+		af = sa->sa_family;
+		memset(&myaddr, 0, salen);
+	} else
+		af = sa->sa_family;
+
+	switch (af) {
+	case AF_INET:
+		proto = IPPROTO_IP;
+		portrange = IP_PORTRANGE;
+		portlow = IP_PORTRANGE_LOW;
+		sin = (struct sockaddr_in *)sa;
+		salen = sizeof(struct sockaddr_in);
+		port = sin->sin_port;
+		break;
+#ifdef INET6
+	case AF_INET6:
+		proto = IPPROTO_IPV6;
+		portrange = IPV6_PORTRANGE;
+		portlow = IPV6_PORTRANGE_LOW;
+		sin6 = (struct sockaddr_in6 *)sa;
+		salen = sizeof(struct sockaddr_in6);
+		port = sin6->sin6_port;
+		break;
+#endif
+	default:
+		errno = EPFNOSUPPORT;
+		return (-1);
+	}
+	sa->sa_family = af;
+	sa->sa_len = salen;
+
+	if (port == 0) {
+		socklen_t oldlen = sizeof(old);
+
+		error = getsockopt(sd, proto, portrange, &old, &oldlen);
+		if (error < 0)
+			return (error);
+
+		error = setsockopt(sd, proto, portrange, &portlow,
+		    sizeof(portlow));
+		if (error < 0)
+			return (error);
+	}
+
+	error = bind(sd, sa, salen);
+
+	if (port == 0) {
+		int saved_errno = errno;
+
+		if (error) {
+			if (setsockopt(sd, proto, portrange, &old,
+			    sizeof(old)) < 0)
+				errno = saved_errno;
+			return (error);
+		}
+
+		if (sa != (struct sockaddr *)&myaddr) {
+			/* Hmm, what did the kernel assign? */
+			if (getsockname(sd, sa, &salen) < 0)
+				errno = saved_errno;
+			return (error);
+		}
+	}
+	return (error);
+}
diff --git a/services/librpc/src/rpc/clnt_generic.c b/services/librpc/src/rpc/clnt_generic.c
new file mode 100644
index 0000000..232af02
--- /dev/null
+++ b/services/librpc/src/rpc/clnt_generic.c
@@ -0,0 +1,145 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)clnt_generic.c 1.4 87/08/11 (C) 1987 SMI";*/
+/*static char *sccsid = "from: @(#)clnt_generic.c	2.2 88/08/01 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/clnt_generic.c,v 1.9 1999/08/28 00:00:35 peter Exp $";
+#endif
+
+/*
+ * Copyright (C) 1987, Sun Microsystems, Inc.
+ */
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <rpc/rpc.h>
+#include <sys/socket.h>
+#include <sys/errno.h>
+#include <netdb.h>
+#include <string.h>
+
+/*
+ * Generic client creation: takes (hostname, program-number, protocol) and
+ * returns client handle. Default options are set, which the user can
+ * change using the rpc equivalent of ioctl()'s.
+ */
+CLIENT *
+clnt_create(
+	const char *hostname,
+	rpcprog_t prog,
+	rpcvers_t vers,
+	const char *proto)
+{
+	struct hostent *h;
+	struct protoent *p;
+	struct sockaddr_in sin;
+#ifndef __rtems__
+	struct sockaddr_un sun;
+#endif
+	int sock;
+	struct timeval tv;
+	CLIENT *client;
+
+#ifndef __rtems__
+	if (!strcmp(proto, "unix")) {
+		bzero((char *)&sun, sizeof(sun));
+		sun.sun_family = AF_UNIX;
+		strcpy(sun.sun_path, hostname);
+		sun.sun_len = sizeof(sun.sun_len) + sizeof(sun.sun_family) +
+				strlen(sun.sun_path) + 1;
+		sock = RPC_ANYSOCK;
+		client = clntunix_create(&sun, prog, vers, &sock, 0, 0);
+		if (client == NULL)
+			return(NULL);
+		tv.tv_sec = 25;
+		tv.tv_usec = 0;
+		clnt_control(client, CLSET_TIMEOUT, &tv);
+		return(client);
+	}
+#endif
+
+	h = gethostbyname(hostname);
+	if (h == NULL) {
+		rpc_createerr.cf_stat = RPC_UNKNOWNHOST;
+		return (NULL);
+	}
+	if (h->h_addrtype != AF_INET) {
+		/*
+		 * Only support INET for now
+		 */
+		rpc_createerr.cf_stat = RPC_SYSTEMERROR;
+		rpc_createerr.cf_error.re_errno = EAFNOSUPPORT;
+		return (NULL);
+	}
+	memset(&sin, 0, sizeof(sin));
+	sin.sin_len = sizeof(struct sockaddr_in);
+	sin.sin_family = h->h_addrtype;
+	sin.sin_port = 0;
+	memcpy((char*)&sin.sin_addr, h->h_addr, h->h_length);
+	p = getprotobyname(proto);
+	if (p == NULL) {
+		rpc_createerr.cf_stat = RPC_UNKNOWNPROTO;
+		rpc_createerr.cf_error.re_errno = EPFNOSUPPORT;
+		return (NULL);
+	}
+	sock = RPC_ANYSOCK;
+	switch (p->p_proto) {
+	case IPPROTO_UDP:
+		tv.tv_sec = 5;
+		tv.tv_usec = 0;
+		client = clntudp_create(&sin, prog, vers, tv, &sock);
+		if (client == NULL) {
+			return (NULL);
+		}
+#if 0	/* XXX do we need this? */
+		tv.tv_sec = 25;
+		tv.tv_usec = 0;
+		clnt_control(client, CLSET_TIMEOUT, &tv);
+#endif
+		break;
+	case IPPROTO_TCP:
+		client = clnttcp_create(&sin, prog, vers, &sock, 0, 0);
+		if (client == NULL) {
+			return (NULL);
+		}
+#if 0	/* XXX do we need this? */
+		tv.tv_sec = 25;
+		tv.tv_usec = 0;
+		clnt_control(client, CLSET_TIMEOUT, &tv);
+#endif
+		break;
+	default:
+		rpc_createerr.cf_stat = RPC_SYSTEMERROR;
+		rpc_createerr.cf_error.re_errno = EPFNOSUPPORT;
+		return (NULL);
+	}
+	return (client);
+}
diff --git a/services/librpc/src/rpc/clnt_perror.c b/services/librpc/src/rpc/clnt_perror.c
new file mode 100644
index 0000000..1d2cfc0
--- /dev/null
+++ b/services/librpc/src/rpc/clnt_perror.c
@@ -0,0 +1,259 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)clnt_perror.c 1.15 87/10/07 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)clnt_perror.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/clnt_perror.c,v 1.11 1999/08/28 00:00:35 peter Exp $";
+#endif
+
+/*
+ * clnt_perror.c
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ *
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <rpc/rpc.h>
+#include <rpc/types.h>
+#include <rpc/auth.h>
+#include <rpc/clnt.h>
+
+static char *auth_errmsg(enum auth_stat stat);
+#define CLNT_PERROR_BUFLEN 256
+
+#define buf (rtems_rpc_task_variables->clnt_perror_buf)
+
+static char *
+_buf(void)
+{
+
+	if (buf == 0)
+		buf = (char *)malloc(CLNT_PERROR_BUFLEN);
+	return (buf);
+}
+
+/*
+ * Print reply error info
+ */
+char *
+clnt_sperror(
+	CLIENT *rpch,
+	const char *s)
+{
+	struct rpc_err e;
+	char *err;
+	char *str = _buf();
+	char *strstart = str;
+
+	if (str == 0)
+		return (0);
+	CLNT_GETERR(rpch, &e);
+
+	(void) sprintf(str, "%s: %s", s, clnt_sperrno(e.re_status));
+	str += strlen(str);
+
+	switch (e.re_status) {
+	case RPC_SUCCESS:
+	case RPC_CANTENCODEARGS:
+	case RPC_CANTDECODERES:
+	case RPC_TIMEDOUT:
+	case RPC_PROGUNAVAIL:
+	case RPC_PROCUNAVAIL:
+	case RPC_CANTDECODEARGS:
+	case RPC_SYSTEMERROR:
+	case RPC_UNKNOWNHOST:
+	case RPC_UNKNOWNPROTO:
+	case RPC_PMAPFAILURE:
+	case RPC_PROGNOTREGISTERED:
+	case RPC_FAILED:
+		break;
+
+	case RPC_CANTSEND:
+	case RPC_CANTRECV:
+		(void) snprintf(str, CLNT_PERROR_BUFLEN - (str - strstart),
+			"; errno = %s\n", strerror(e.re_errno));
+		break;
+
+	case RPC_VERSMISMATCH:
+		(void) sprintf(str,
+			"; low version = %lu, high version = %lu\n",
+			(u_long)e.re_vers.low, (u_long)e.re_vers.high);
+		break;
+
+	case RPC_AUTHERROR:
+		err = auth_errmsg(e.re_why);
+		(void) sprintf(str,"; why = ");
+		str += strlen(str);
+		if (err != NULL) {
+			(void) sprintf(str, "%s\n",err);
+		} else {
+			(void) sprintf(str,
+				"(unknown authentication error - %d)\n",
+				(int) e.re_why);
+		}
+		break;
+
+	case RPC_PROGVERSMISMATCH:
+		(void) sprintf(str,
+			"; low version = %lu, high version = %lu\n",
+			(u_long)e.re_vers.low, (u_long)e.re_vers.high);
+		break;
+
+	default:	/* unknown */
+		(void) sprintf(str,
+			"; s1 = %lu, s2 = %lu\n",
+			(long)e.re_lb.s1, (long)e.re_lb.s2);
+		break;
+	}
+	strstart[CLNT_PERROR_BUFLEN-2] = '\n';
+	strstart[CLNT_PERROR_BUFLEN-1] = '\0';
+	return(strstart) ;
+}
+
+void
+clnt_perror(
+	CLIENT *rpch,
+	const char *s)
+{
+	(void) fprintf(stderr,"%s\n",clnt_sperror(rpch,s));
+}
+
+
+static const char *const rpc_errlist[] = {
+	"RPC: Success",				/*  0 - RPC_SUCCESS */
+	"RPC: Can't encode arguments",		/*  1 - RPC_CANTENCODEARGS */
+	"RPC: Can't decode result",		/*  2 - RPC_CANTDECODERES */
+	"RPC: Unable to send",			/*  3 - RPC_CANTSEND */
+	"RPC: Unable to receive",		/*  4 - RPC_CANTRECV */
+	"RPC: Timed out",			/*  5 - RPC_TIMEDOUT */
+	"RPC: Incompatible versions of RPC",	/*  6 - RPC_VERSMISMATCH */
+	"RPC: Authentication error",		/*  7 - RPC_AUTHERROR */
+	"RPC: Program unavailable",		/*  8 - RPC_PROGUNAVAIL */
+	"RPC: Program/version mismatch",	/*  9 - RPC_PROGVERSMISMATCH */
+	"RPC: Procedure unavailable",		/* 10 - RPC_PROCUNAVAIL */
+	"RPC: Server can't decode arguments",	/* 11 - RPC_CANTDECODEARGS */
+	"RPC: Remote system error",		/* 12 - RPC_SYSTEMERROR */
+	"RPC: Unknown host",			/* 13 - RPC_UNKNOWNHOST */
+	"RPC: Port mapper failure",		/* 14 - RPC_PMAPFAILURE */
+	"RPC: Program not registered",		/* 15 - RPC_PROGNOTREGISTERED */
+	"RPC: Failed (unspecified error)",	/* 16 - RPC_FAILED */
+	"RPC: Unknown protocol"			/* 17 - RPC_UNKNOWNPROTO */
+};
+
+
+/*
+ * This interface for use by clntrpc
+ */
+char *
+clnt_sperrno(
+	enum clnt_stat stat)
+{
+	unsigned int errnum = stat;
+
+	if (errnum < (sizeof(rpc_errlist)/sizeof(rpc_errlist[0])))
+		return (char *)rpc_errlist[errnum];
+
+	return ("RPC: (unknown error code)");
+}
+
+void
+clnt_perrno(
+	enum clnt_stat num)
+{
+	(void) fprintf(stderr,"%s\n",clnt_sperrno(num));
+}
+
+
+char *
+clnt_spcreateerror(
+	const char *s)
+{
+	char *str = _buf();
+
+	if (str == 0)
+		return(0);
+	switch (rpc_createerr.cf_stat) {
+	case RPC_PMAPFAILURE:
+		(void) snprintf(str, CLNT_PERROR_BUFLEN, "%s: %s - %s\n", s,
+		    clnt_sperrno(rpc_createerr.cf_stat),
+		    clnt_sperrno(rpc_createerr.cf_error.re_status));
+		break;
+
+	case RPC_SYSTEMERROR:
+		(void) snprintf(str, CLNT_PERROR_BUFLEN, "%s: %s - %s\n", s,
+		    clnt_sperrno(rpc_createerr.cf_stat),
+		    strerror(rpc_createerr.cf_error.re_errno));
+		break;
+	default:
+		(void) snprintf(str, CLNT_PERROR_BUFLEN, "%s: %s\n", s,
+		clnt_sperrno(rpc_createerr.cf_stat));
+		break;
+	}
+	str[CLNT_PERROR_BUFLEN-2] = '\n';
+	str[CLNT_PERROR_BUFLEN-1] = '\0';
+	return (str);
+}
+
+void
+clnt_pcreateerror(
+	const char *s)
+{
+	(void) fprintf(stderr,"%s\n",clnt_spcreateerror(s));
+}
+
+static const char *const auth_errlist[] = {
+	"Authentication OK",			/* 0 - AUTH_OK */
+	"Invalid client credential",		/* 1 - AUTH_BADCRED */
+	"Server rejected credential",		/* 2 - AUTH_REJECTEDCRED */
+	"Invalid client verifier",		/* 3 - AUTH_BADVERF */
+	"Server rejected verifier",		/* 4 - AUTH_REJECTEDVERF */
+	"Client credential too weak",		/* 5 - AUTH_TOOWEAK */
+	"Invalid server verifier",		/* 6 - AUTH_INVALIDRESP */
+	"Failed (unspecified error)"		/* 7 - AUTH_FAILED */
+};
+
+static char *
+auth_errmsg(
+	enum auth_stat stat)
+{
+	unsigned int errnum = stat;
+
+	if (errnum < (sizeof(auth_errlist)/sizeof(auth_errlist[0])))
+		return (char *)auth_errlist[errnum];
+
+	return(NULL);
+}
diff --git a/services/librpc/src/rpc/clnt_raw.c b/services/librpc/src/rpc/clnt_raw.c
new file mode 100644
index 0000000..c522cec
--- /dev/null
+++ b/services/librpc/src/rpc/clnt_raw.c
@@ -0,0 +1,248 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)clnt_raw.c 1.22 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)clnt_raw.c	2.2 88/08/01 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/clnt_raw.c,v 1.10 1999/08/28 00:00:36 peter Exp $";
+#endif
+
+/*
+ * clnt_raw.c
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ *
+ * Memory based rpc for simple testing and timing.
+ * Interface to create an rpc client and server in the same process.
+ * This lets us similate rpc and get round trip overhead, without
+ * any interference from the kernel.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <rpc/rpc.h>
+#include <stdlib.h>
+#include <stdio.h>
+
+#define MCALL_MSG_SIZE 24
+
+/*
+ * This is the "network" we will be moving stuff over.
+ */
+struct clnt_raw_private {
+	CLIENT	client_object;
+	XDR	xdr_stream;
+	char	_raw_buf[UDPMSGSIZE];
+	union {
+	    struct rpc_msg	mashl_rpcmsg;
+	    char 		mashl_callmsg[MCALL_MSG_SIZE];
+	} u;
+	u_int	mcnt;
+};
+#define clntraw_private (rtems_rpc_task_variables->clnt_raw_private)
+
+static enum clnt_stat	clntraw_call(CLIENT *h, rpcproc_t proc, xdrproc_t xargs, void *argsp, xdrproc_t xresults, void *resultsp, struct timeval timeout);
+static void		clntraw_abort(void);
+static void		clntraw_geterr(CLIENT *h, struct rpc_err*);
+static bool_t		clntraw_freeres(CLIENT *, xdrproc_t, void*);
+static bool_t		clntraw_control(CLIENT *, int, char *);
+static void		clntraw_destroy(CLIENT *);
+
+static struct clnt_ops client_ops = {
+	clntraw_call,
+	clntraw_abort,
+	clntraw_geterr,
+	clntraw_freeres,
+	clntraw_destroy,
+	clntraw_control
+};
+
+/*
+ * Create a client handle for memory based rpc.
+ */
+CLIENT *
+clntraw_create(
+	u_long prog,
+	u_long vers )
+{
+	struct clnt_raw_private *clp = clntraw_private;
+	struct rpc_msg call_msg;
+	XDR *xdrs = &clp->xdr_stream;
+	CLIENT	*client = &clp->client_object;
+
+	if (clp == 0) {
+		clp = (struct clnt_raw_private *)calloc(1, sizeof (*clp));
+		if (clp == 0)
+			return (0);
+		clntraw_private = clp;
+	}
+	/*
+	 * pre-serialize the static part of the call msg and stash it away
+	 */
+	call_msg.rm_direction = CALL;
+	call_msg.rm_call.cb_rpcvers = RPC_MSG_VERSION;
+	call_msg.rm_call.cb_prog = prog;
+	call_msg.rm_call.cb_vers = vers;
+	xdrmem_create(xdrs, clp->u.mashl_callmsg, MCALL_MSG_SIZE, XDR_ENCODE);
+	if (! xdr_callhdr(xdrs, &call_msg)) {
+		perror("clnt_raw.c - Fatal header serialization error.");
+	}
+	clp->mcnt = XDR_GETPOS(xdrs);
+	XDR_DESTROY(xdrs);
+
+	/*
+	 * Set xdrmem for client/server shared buffer
+	 */
+	xdrmem_create(xdrs, clp->_raw_buf, UDPMSGSIZE, XDR_FREE);
+
+	/*
+	 * create client handle
+	 */
+	client->cl_ops = &client_ops;
+	client->cl_auth = authnone_create();
+	return (client);
+}
+
+static enum clnt_stat
+clntraw_call(
+	CLIENT *h,
+	rpcproc_t proc,
+	xdrproc_t xargs,
+	void *argsp,
+	xdrproc_t xresults,
+	void *resultsp,
+	struct timeval timeout )
+{
+	struct clnt_raw_private *clp = clntraw_private;
+	XDR *xdrs = &clp->xdr_stream;
+	struct rpc_msg msg;
+	enum clnt_stat status;
+	struct rpc_err error;
+
+	if (clp == 0)
+		return (RPC_FAILED);
+call_again:
+	/*
+	 * send request
+	 */
+	xdrs->x_op = XDR_ENCODE;
+	XDR_SETPOS(xdrs, 0);
+	clp->u.mashl_rpcmsg.rm_xid ++ ;
+	if ((! XDR_PUTBYTES(xdrs, clp->u.mashl_callmsg, clp->mcnt)) ||
+	    (! XDR_PUTLONG(xdrs, (long *)&proc)) ||
+	    (! AUTH_MARSHALL(h->cl_auth, xdrs)) ||
+	    (! (*xargs)(xdrs, argsp))) {
+		return (RPC_CANTENCODEARGS);
+	}
+	(void)XDR_GETPOS(xdrs);  /* called just to cause overhead */
+
+	/*
+	 * We have to call server input routine here because this is
+	 * all going on in one process. Yuk.
+	 */
+	svc_getreq(1);
+
+	/*
+	 * get results
+	 */
+	xdrs->x_op = XDR_DECODE;
+	XDR_SETPOS(xdrs, 0);
+	msg.acpted_rply.ar_verf = _null_auth;
+	msg.acpted_rply.ar_results.where = resultsp;
+	msg.acpted_rply.ar_results.proc = xresults;
+	if (! xdr_replymsg(xdrs, &msg))
+		return (RPC_CANTDECODERES);
+	_seterr_reply(&msg, &error);
+	status = error.re_status;
+
+	if (status == RPC_SUCCESS) {
+		if (! AUTH_VALIDATE(h->cl_auth, &msg.acpted_rply.ar_verf)) {
+			status = RPC_AUTHERROR;
+		}
+	}  /* end successful completion */
+	else {
+		if (AUTH_REFRESH(h->cl_auth))
+			goto call_again;
+	}  /* end of unsuccessful completion */
+
+	if (status == RPC_SUCCESS) {
+		if (! AUTH_VALIDATE(h->cl_auth, &msg.acpted_rply.ar_verf)) {
+			status = RPC_AUTHERROR;
+		}
+		if (msg.acpted_rply.ar_verf.oa_base != NULL) {
+			xdrs->x_op = XDR_FREE;
+			(void)xdr_opaque_auth(xdrs, &(msg.acpted_rply.ar_verf));
+		}
+	}
+
+	return (status);
+}
+
+static void
+clntraw_geterr(CLIENT *cl, struct rpc_err *err)
+{
+}
+
+
+static bool_t
+clntraw_freeres(
+	CLIENT *cl,
+	xdrproc_t xdr_res,
+	void *res_ptr )
+{
+	struct clnt_raw_private *clp = clntraw_private;
+	XDR *xdrs = &clp->xdr_stream;
+	bool_t rval;
+
+	if (clp == 0)
+	{
+		rval = (bool_t) RPC_FAILED;
+		return (rval);
+	}
+	xdrs->x_op = XDR_FREE;
+	return ((*xdr_res)(xdrs, res_ptr));
+}
+
+static void
+clntraw_abort(void)
+{
+}
+
+static bool_t
+clntraw_control(CLIENT *cl, int request, char *info)
+{
+	return (FALSE);
+}
+
+static void
+clntraw_destroy(CLIENT *cl)
+{
+}
diff --git a/services/librpc/src/rpc/clnt_simple.c b/services/librpc/src/rpc/clnt_simple.c
new file mode 100644
index 0000000..3cf17b4
--- /dev/null
+++ b/services/librpc/src/rpc/clnt_simple.c
@@ -0,0 +1,127 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)clnt_simple.c 1.35 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)clnt_simple.c	2.2 88/08/01 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/clnt_simple.c,v 1.12 2000/01/27 23:06:35 jasone Exp $";
+#endif
+
+/*
+ * clnt_simple.c
+ * Simplified front end to rpc.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <sys/param.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <string.h>
+#include <rpc/rpc.h>
+#include <sys/socket.h>
+#include <netdb.h>
+
+struct call_rpc_private {
+	CLIENT	*client;
+	int	socket;
+	int	oldprognum, oldversnum, valid;
+	char	*oldhost;
+};
+#define callrpc_private (rtems_rpc_task_variables->call_rpc_private)
+
+int
+callrpc(
+	char *host,
+	int prognum, int versnum, int procnum,
+	xdrproc_t inproc, char *in,
+	xdrproc_t outproc, char *out )
+{
+	register struct call_rpc_private *crp = callrpc_private;
+	struct sockaddr_in server_addr;
+	enum clnt_stat clnt_stat;
+	struct hostent *hp;
+	struct timeval timeout, tottimeout;
+
+	if (crp == 0) {
+		crp = (struct call_rpc_private *)calloc(1, sizeof (*crp));
+		if (crp == 0)
+			return (0);
+		callrpc_private = crp;
+	}
+	if (crp->oldhost == NULL) {
+		crp->oldhost = malloc(MAXHOSTNAMELEN);
+		crp->oldhost[0] = 0;
+		crp->socket = RPC_ANYSOCK;
+	}
+	if (crp->valid && crp->oldprognum == prognum && crp->oldversnum == versnum
+		&& strcmp(crp->oldhost, host) == 0) {
+		/* reuse old client */
+	} else {
+		crp->valid = 0;
+		if (crp->socket != -1)
+			(void)_RPC_close(crp->socket);
+		crp->socket = RPC_ANYSOCK;
+		if (crp->client) {
+			clnt_destroy(crp->client);
+			crp->client = NULL;
+		}
+		if ((hp = gethostbyname(host)) == NULL)
+			return ((int) RPC_UNKNOWNHOST);
+		timeout.tv_usec = 0;
+		timeout.tv_sec = 5;
+		memset(&server_addr, 0, sizeof(server_addr));
+		memcpy((char *)&server_addr.sin_addr, hp->h_addr, hp->h_length);
+		server_addr.sin_len = sizeof(struct sockaddr_in);
+		server_addr.sin_family = AF_INET;
+		server_addr.sin_port =  0;
+		if ((crp->client = clntudp_create(&server_addr, (u_long)prognum,
+		    (u_long)versnum, timeout, &crp->socket)) == NULL)
+			return ((int) rpc_createerr.cf_stat);
+		crp->valid = 1;
+		crp->oldprognum = prognum;
+		crp->oldversnum = versnum;
+		(void) strcpy(crp->oldhost, host);
+	}
+	tottimeout.tv_sec = 25;
+	tottimeout.tv_usec = 0;
+	clnt_stat = clnt_call(crp->client, procnum, inproc, in,
+	    outproc, out, tottimeout);
+	/*
+	 * if call failed, empty cache
+	 */
+	if (clnt_stat != RPC_SUCCESS)
+		crp->valid = 0;
+	return ((int) clnt_stat);
+}
diff --git a/services/librpc/src/rpc/clnt_tcp.c b/services/librpc/src/rpc/clnt_tcp.c
new file mode 100644
index 0000000..f53edae
--- /dev/null
+++ b/services/librpc/src/rpc/clnt_tcp.c
@@ -0,0 +1,605 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)clnt_tcp.c 1.37 87/10/05 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)clnt_tcp.c	2.2 88/08/01 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/clnt_tcp.c,v 1.14 2000/01/27 23:06:36 jasone Exp $";
+#endif
+
+/*
+ * clnt_tcp.c, Implements a TCP/IP based, client side RPC.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ *
+ * TCP based RPC supports 'batched calls'.
+ * A sequence of calls may be batched-up in a send buffer.  The rpc call
+ * return immediately to the client even though the call was not necessarily
+ * sent.  The batching occurs if the results' xdr routine is NULL (0) AND
+ * the rpc timeout value is zero (see clnt.h, rpc).
+ *
+ * Clients should NOT casually batch calls that in fact return results; that is,
+ * the server side should be aware that a call is batched and not produce any
+ * return message.  Batched calls that produce many result messages can
+ * deadlock (netlock) the client and the server....
+ *
+ * Now go hang yourself.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <string.h>
+#include <rpc/rpc.h>
+#include <sys/socket.h>
+#include <netdb.h>
+#include <errno.h>
+#include <rpc/pmap_clnt.h>
+#include <sys/select.h>
+
+#define MCALL_MSG_SIZE 24
+
+static int	readtcp(char *, char*, int);
+static int	writetcp(char *, char*, int);
+
+static enum clnt_stat	clnttcp_call(CLIENT *, rpcproc_t, xdrproc_t, void*, xdrproc_t, void*, struct timeval);
+static void		clnttcp_abort(void);
+static void		clnttcp_geterr(CLIENT *, struct rpc_err*);
+static bool_t		clnttcp_freeres(CLIENT *, xdrproc_t, void*);
+static bool_t           clnttcp_control(CLIENT *, int, char *);
+static void		clnttcp_destroy(CLIENT *);
+
+static struct clnt_ops tcp_ops = {
+	clnttcp_call,
+	clnttcp_abort,
+	clnttcp_geterr,
+	clnttcp_freeres,
+	clnttcp_destroy,
+	clnttcp_control
+};
+
+struct ct_data {
+	int		ct_sock;
+	bool_t		ct_closeit;	/* close it on destroy */
+	struct timeval	ct_wait;	/* wait interval in milliseconds */
+	bool_t          ct_waitset;       /* wait set by clnt_control? */
+	struct sockaddr_in ct_addr;
+	struct rpc_err	ct_error;
+	union {
+		char	ct_mcallc[MCALL_MSG_SIZE];	/* marshalled callmsg */
+		u_int32_t ct_mcalli;
+	} ct_u;
+	u_int		ct_mpos;			/* pos after marshal */
+	XDR		ct_xdrs;	/* XDR stream */
+};
+
+/*
+ * Create a client handle for a tcp/ip connection.
+ * If *sockp<0, *sockp is set to a newly created TCP socket and it is
+ * connected to raddr.  If *sockp non-negative then
+ * raddr is ignored.  The rpc/tcp package does buffering
+ * similar to stdio, so the client must pick send and receive buffer sizes,];
+ * 0 => use the default.
+ * If raddr->sin_port is 0, then a binder on the remote machine is
+ * consulted for the right port number.
+ * NB: *sockp is copied into a private area.
+ * NB: It is the clients responsibility to close *sockp.
+ * NB: The rpch->cl_auth is set null authentication.  Caller may wish to set this
+ * something more useful.
+ */
+CLIENT *
+clnttcp_create(
+	struct sockaddr_in *raddr,
+	u_long prog,		/* program number */
+	u_long vers,		/* version number */
+	int *sockp,
+	u_int sendsz,
+	u_int recvsz)
+{
+	CLIENT *h;
+	struct ct_data *ct = NULL;	/* client handle */
+	struct timeval now;
+	struct rpc_msg call_msg;
+	static uintptr_t disrupt;
+
+	if (disrupt == 0)
+		disrupt = (uintptr_t)raddr;
+
+	h  = (CLIENT *)mem_alloc(sizeof(*h));
+	if (h == NULL) {
+		(void)fprintf(stderr, "clnttcp_create: out of memory\n");
+		rpc_createerr.cf_stat = RPC_SYSTEMERROR;
+		rpc_createerr.cf_error.re_errno = errno;
+		goto fooy;
+	}
+	ct = (struct ct_data *)mem_alloc(sizeof (*ct));
+	if (ct == NULL) {
+		(void)fprintf(stderr, "clnttcp_create: out of memory\n");
+		rpc_createerr.cf_stat = RPC_SYSTEMERROR;
+		rpc_createerr.cf_error.re_errno = errno;
+		goto fooy;
+	}
+
+	/*
+	 * If no port number given ask the pmap for one
+	 */
+	if (raddr->sin_port == 0) {
+		u_short port;
+		if ((port = pmap_getport(raddr, prog, vers, IPPROTO_TCP)) == 0) {
+			mem_free((caddr_t)ct, sizeof(struct ct_data));
+			mem_free((caddr_t)h, sizeof(CLIENT));
+			return ((CLIENT *)NULL);
+		}
+		raddr->sin_port = htons(port);
+	}
+
+	/*
+	 * If no socket given, open one
+	 */
+	if (*sockp < 0) {
+		*sockp = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
+		(void)bindresvport(*sockp, (struct sockaddr_in *)0);
+		if ((*sockp < 0)
+		    || (connect(*sockp, (struct sockaddr *)raddr,
+		    sizeof(*raddr)) < 0)) {
+			rpc_createerr.cf_stat = RPC_SYSTEMERROR;
+			rpc_createerr.cf_error.re_errno = errno;
+			if (*sockp != -1)
+				(void)_RPC_close(*sockp);
+			goto fooy;
+		}
+		ct->ct_closeit = TRUE;
+	} else {
+		ct->ct_closeit = FALSE;
+	}
+
+	/*
+	 * Set up private data struct
+	 */
+	ct->ct_sock = *sockp;
+	ct->ct_wait.tv_usec = 0;
+	ct->ct_waitset = FALSE;
+	ct->ct_addr = *raddr;
+
+	/*
+	 * Initialize call message
+	 */
+	(void)gettimeofday(&now, (struct timezone *)0);
+	call_msg.rm_xid = (++disrupt) ^ getpid() ^ now.tv_sec ^ now.tv_usec;
+	call_msg.rm_direction = CALL;
+	call_msg.rm_call.cb_rpcvers = RPC_MSG_VERSION;
+	call_msg.rm_call.cb_prog = prog;
+	call_msg.rm_call.cb_vers = vers;
+
+	/*
+	 * pre-serialize the static part of the call msg and stash it away
+	 */
+	xdrmem_create(&(ct->ct_xdrs), ct->ct_u.ct_mcallc, MCALL_MSG_SIZE,
+	    XDR_ENCODE);
+	if (! xdr_callhdr(&(ct->ct_xdrs), &call_msg)) {
+		if (ct->ct_closeit) {
+			(void)_RPC_close(*sockp);
+		}
+		goto fooy;
+	}
+	ct->ct_mpos = XDR_GETPOS(&(ct->ct_xdrs));
+	XDR_DESTROY(&(ct->ct_xdrs));
+
+	/*
+	 * Create a client handle which uses xdrrec for serialization
+	 * and authnone for authentication.
+	 */
+	xdrrec_create(&(ct->ct_xdrs), sendsz, recvsz,
+	    (caddr_t)ct, readtcp, writetcp);
+	h->cl_ops = &tcp_ops;
+	h->cl_private = (caddr_t) ct;
+	h->cl_auth = authnone_create();
+	return (h);
+
+fooy:
+	/*
+	 * Something goofed, free stuff and barf
+	 */
+	if (ct)
+		mem_free((caddr_t)ct, sizeof(struct ct_data));
+	if (h)
+		mem_free((caddr_t)h, sizeof(CLIENT));
+	return ((CLIENT *)NULL);
+}
+
+static enum clnt_stat
+clnttcp_call(
+	CLIENT *h,
+	rpcproc_t proc,
+	xdrproc_t xdr_args,
+	void *args_ptr,
+	xdrproc_t xdr_results,
+	void *results_ptr,
+	struct timeval timeout)
+{
+	struct ct_data *ct = (struct ct_data *) h->cl_private;
+	XDR *xdrs = &(ct->ct_xdrs);
+	struct rpc_msg reply_msg;
+	u_int32_t x_id;
+	u_int32_t *msg_x_id = &ct->ct_u.ct_mcalli;	/* yuk */
+	bool_t shipnow;
+	int refreshes = 2;
+
+	if (!ct->ct_waitset) {
+		ct->ct_wait = timeout;
+	}
+
+	shipnow =
+	    (xdr_results == (xdrproc_t)0 && timeout.tv_sec == 0
+	    && timeout.tv_usec == 0) ? FALSE : TRUE;
+
+call_again:
+	xdrs->x_op = XDR_ENCODE;
+	ct->ct_error.re_status = RPC_SUCCESS;
+	x_id = ntohl(--(*msg_x_id));
+	if ((! XDR_PUTBYTES(xdrs, ct->ct_u.ct_mcallc, ct->ct_mpos)) ||
+	    (! XDR_PUTLONG(xdrs, (long *)&proc)) ||
+	    (! AUTH_MARSHALL(h->cl_auth, xdrs)) ||
+	    (! (*xdr_args)(xdrs, args_ptr))) {
+		if (ct->ct_error.re_status == RPC_SUCCESS)
+			ct->ct_error.re_status = RPC_CANTENCODEARGS;
+		(void)xdrrec_endofrecord(xdrs, TRUE);
+		return (ct->ct_error.re_status);
+	}
+	if (! xdrrec_endofrecord(xdrs, shipnow)) {
+		return (ct->ct_error.re_status = RPC_CANTSEND);
+	}
+	if (! shipnow) {
+		return (RPC_SUCCESS);
+	}
+	/*
+	 * Hack to provide rpc-based message passing
+	 */
+	if (timeout.tv_sec == 0 && timeout.tv_usec == 0) {
+		return(ct->ct_error.re_status = RPC_TIMEDOUT);
+	}
+
+
+	/*
+	 * Keep receiving until we get a valid transaction id
+	 */
+	xdrs->x_op = XDR_DECODE;
+	while (TRUE) {
+		reply_msg.acpted_rply.ar_verf = _null_auth;
+		reply_msg.acpted_rply.ar_results.where = NULL;
+		reply_msg.acpted_rply.ar_results.proc = (xdrproc_t)xdr_void;
+		if (! xdrrec_skiprecord(xdrs))
+			return (ct->ct_error.re_status);
+		/* now decode and validate the response header */
+		if (! xdr_replymsg(xdrs, &reply_msg)) {
+			if (ct->ct_error.re_status == RPC_SUCCESS)
+				continue;
+			return (ct->ct_error.re_status);
+		}
+		if (reply_msg.rm_xid == x_id)
+			break;
+	}
+
+	/*
+	 * process header
+	 */
+	_seterr_reply(&reply_msg, &(ct->ct_error));
+	if (ct->ct_error.re_status == RPC_SUCCESS) {
+		if (! AUTH_VALIDATE(h->cl_auth, &reply_msg.acpted_rply.ar_verf)) {
+			ct->ct_error.re_status = RPC_AUTHERROR;
+			ct->ct_error.re_why = AUTH_INVALIDRESP;
+		} else if (! (*xdr_results)(xdrs, results_ptr)) {
+			if (ct->ct_error.re_status == RPC_SUCCESS)
+				ct->ct_error.re_status = RPC_CANTDECODERES;
+		}
+		/* free verifier ... */
+		if (reply_msg.acpted_rply.ar_verf.oa_base != NULL) {
+			xdrs->x_op = XDR_FREE;
+			(void)xdr_opaque_auth(xdrs, &(reply_msg.acpted_rply.ar_verf));
+		}
+	}  /* end successful completion */
+	else {
+		/* maybe our credentials need to be refreshed ... */
+		if (refreshes-- && AUTH_REFRESH(h->cl_auth))
+			goto call_again;
+	}  /* end of unsuccessful completion */
+	return (ct->ct_error.re_status);
+}
+
+static void
+clnttcp_geterr(
+	CLIENT *h,
+	struct rpc_err *errp)
+{
+	struct ct_data *ct;
+
+	ct = (struct ct_data *) h->cl_private;
+	*errp = ct->ct_error;
+}
+
+static bool_t
+clnttcp_freeres(
+	CLIENT *cl,
+	xdrproc_t xdr_res,
+	void *res_ptr)
+{
+	struct ct_data *ct;
+	XDR *xdrs;
+
+	ct = (struct ct_data *)cl->cl_private;
+	xdrs = &(ct->ct_xdrs);
+	
+	xdrs->x_op = XDR_FREE;
+	return ((*xdr_res)(xdrs, res_ptr));
+}
+
+static void
+clnttcp_abort(void)
+{
+}
+
+
+static bool_t
+clnttcp_control(
+	CLIENT *cl,
+	int request,
+	char *info)
+{
+	struct ct_data *ct;
+	struct timeval *tv;
+	socklen_t len;
+	
+	ct = (struct ct_data *)cl->cl_private;
+
+	switch (request) {
+	case CLSET_FD_CLOSE:
+		ct->ct_closeit = TRUE;
+		break;
+	case CLSET_FD_NCLOSE:
+		ct->ct_closeit = FALSE;
+		break;
+	case CLSET_TIMEOUT:
+		if (info == NULL)
+			return(FALSE);
+		tv = (struct timeval *)info;
+		ct->ct_wait.tv_sec = tv->tv_sec;
+		ct->ct_wait.tv_usec = tv->tv_usec;
+		ct->ct_waitset = TRUE;
+		break;
+	case CLGET_TIMEOUT:
+		if (info == NULL)
+			return(FALSE);
+		*(struct timeval *)info = ct->ct_wait;
+		break;
+	case CLGET_SERVER_ADDR:
+		if (info == NULL)
+			return(FALSE);
+		*(struct sockaddr_in *)info = ct->ct_addr;
+		break;
+	case CLGET_FD:
+		if (info == NULL)
+			return(FALSE);
+		*(int *)info = ct->ct_sock;
+		break;
+	case CLGET_XID:
+		/*
+		 * use the knowledge that xid is the
+		 * first element in the call structure
+		 * This will get the xid of the PREVIOUS call
+		 */
+		if (info == NULL)
+			return(FALSE);
+		*(u_int32_t *)info =
+			ntohl(*(u_int32_t *)&ct->ct_u.ct_mcalli);
+		break;
+	case CLSET_XID:
+		/* This will set the xid of the NEXT call */
+		if (info == NULL)
+			return(FALSE);
+		*(u_int32_t *)&ct->ct_u.ct_mcalli =
+			htonl(*((u_int32_t *)info) + 1);
+		/* decrement by 1 as clnttcp_call() increments once */
+	case CLGET_VERS:
+		/*
+		 * This RELIES on the information that, in the call body,
+		 * the version number field is the fifth field from the
+		 * begining of the RPC header. MUST be changed if the
+		 * call_struct is changed
+		 */
+		if (info == NULL)
+			return(FALSE);
+		*(u_int32_t *)info =
+			ntohl(*(u_int32_t *)(ct->ct_u.ct_mcallc +
+						4 * BYTES_PER_XDR_UNIT));
+		break;
+	case CLSET_VERS:
+		if (info == NULL)
+			return(FALSE);
+		*(u_int32_t *)(ct->ct_u.ct_mcallc +
+			4 * BYTES_PER_XDR_UNIT) =
+			htonl(*(u_int32_t *)info);
+		break;
+
+	case CLGET_PROG:
+		/*
+		 * This RELIES on the information that, in the call body,
+		 * the program number field is the fourth field from the
+		 * begining of the RPC header. MUST be changed if the
+		 * call_struct is changed
+		 */
+		if (info == NULL)
+			return(FALSE);
+		*(u_int32_t *)info = ntohl(*(u_int32_t *)(ct->ct_u.ct_mcallc +
+						3 * BYTES_PER_XDR_UNIT));
+		break;
+
+	case CLSET_PROG:
+		if (info == NULL)
+			return(FALSE);
+		*(u_int32_t *)(ct->ct_u.ct_mcallc + 3 * BYTES_PER_XDR_UNIT)
+				= htonl(*(u_int32_t *)info);
+		break;
+
+	case CLGET_LOCAL_ADDR:
+		len = sizeof(struct sockaddr);
+		if (getsockname(ct->ct_sock, (struct sockaddr *)info, &len) <0)
+			return(FALSE);
+		break;
+
+	case CLGET_RETRY_TIMEOUT:
+	case CLSET_RETRY_TIMEOUT:
+	case CLGET_SVC_ADDR:
+	case CLSET_SVC_ADDR:
+	case CLSET_PUSH_TIMOD:
+	case CLSET_POP_TIMOD:
+	default:
+		return (FALSE);
+	}
+	return (TRUE);
+}
+
+
+static void
+clnttcp_destroy(
+	CLIENT *h)
+{
+	struct ct_data *ct =
+	    (struct ct_data *) h->cl_private;
+
+	if (ct->ct_closeit) {
+		(void)_RPC_close(ct->ct_sock);
+	}
+	XDR_DESTROY(&(ct->ct_xdrs));
+	mem_free(ct, sizeof(struct ct_data));
+	mem_free(h, sizeof(CLIENT));
+}
+
+/*
+ * Interface between xdr serializer and tcp connection.
+ * Behaves like the system calls, read & write, but keeps some error state
+ * around for the rpc level.
+ */
+static int
+readtcp(
+	char *_ct,
+	char *buf,
+	int len)
+{
+	struct ct_data *ct = (struct ct_data*) _ct;
+	fd_set *fds, readfds;
+	struct timeval start, after, duration, delta, tmp, tv;
+	int r, save_errno;
+
+	if (len == 0)
+		return (0);
+
+	if (ct->ct_sock + 1 > FD_SETSIZE) {
+		int bytes = howmany(ct->ct_sock + 1, NFDBITS) * sizeof(fd_mask);
+		fds = (fd_set *)malloc(bytes);
+		if (fds == NULL)
+			return (-1);
+		memset(fds, 0, bytes);
+	} else {
+		fds = &readfds;
+		FD_ZERO(fds);
+	}
+
+	gettimeofday(&start, NULL);
+	delta = ct->ct_wait;
+	while (TRUE) {
+		/* XXX we know the other bits are still clear */
+		FD_SET(ct->ct_sock, fds);
+		tv = delta;	/* in case select writes back */
+		r = select(ct->ct_sock+1, fds, NULL, NULL, &tv);
+		save_errno = errno;
+
+		gettimeofday(&after, NULL);
+		timersub(&start, &after, &duration);
+		timersub(&ct->ct_wait, &duration, &tmp);
+		delta = tmp;
+		if (delta.tv_sec < 0 || !timerisset(&delta))
+			r = 0;
+
+		switch (r) {
+		case 0:
+			if (fds != &readfds)
+				free(fds);
+			ct->ct_error.re_status = RPC_TIMEDOUT;
+			return (-1);
+
+		case -1:
+			if (errno == EINTR)
+				continue;
+			if (fds != &readfds)
+				free(fds);
+			ct->ct_error.re_status = RPC_CANTRECV;
+			ct->ct_error.re_errno = save_errno;
+			return (-1);
+		}
+		break;
+	}
+	switch (len = _RPC_read(ct->ct_sock, buf, len)) {
+
+	case 0:
+		/* premature eof */
+		ct->ct_error.re_errno = ECONNRESET;
+		ct->ct_error.re_status = RPC_CANTRECV;
+		len = -1;  /* it's really an error */
+		break;
+
+	case -1:
+		ct->ct_error.re_errno = errno;
+		ct->ct_error.re_status = RPC_CANTRECV;
+		break;
+	}
+	return (len);
+}
+
+static int
+writetcp(
+	char *_ct,
+	char *buf,
+	int len)
+{
+	struct ct_data *ct = (struct ct_data *) _ct;
+	int i, cnt;
+
+	for (cnt = len; cnt > 0; cnt -= i, buf += i) {
+		if ((i = _RPC_write(ct->ct_sock, buf, cnt)) == -1) {
+			ct->ct_error.re_errno = errno;
+			ct->ct_error.re_status = RPC_CANTSEND;
+			return (-1);
+		}
+	}
+	return (len);
+}
diff --git a/services/librpc/src/rpc/clnt_udp.c b/services/librpc/src/rpc/clnt_udp.c
new file mode 100644
index 0000000..369da95
--- /dev/null
+++ b/services/librpc/src/rpc/clnt_udp.c
@@ -0,0 +1,579 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)clnt_udp.c 1.39 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)clnt_udp.c	2.2 88/08/01 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/clnt_udp.c,v 1.15 2000/01/27 23:06:36 jasone Exp $";
+#endif
+
+/*
+ * clnt_udp.c, Implements a UDP/IP based, client side RPC.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <string.h>
+#include <rpc/rpc.h>
+#include <sys/socket.h>
+#include <sys/ioctl.h>
+#include <netdb.h>
+#include <errno.h>
+#include <rpc/pmap_clnt.h>
+#include <sys/select.h>
+
+/*
+ * UDP bases client side rpc operations
+ */
+static enum clnt_stat	clntudp_call(CLIENT *, rpcproc_t, xdrproc_t, void*, xdrproc_t, void*, struct timeval);
+static void		clntudp_abort(void);
+static void		clntudp_geterr(CLIENT *, struct rpc_err*);
+static bool_t		clntudp_freeres(CLIENT *, xdrproc_t, void*);
+static bool_t           clntudp_control(CLIENT *, int, char *);
+static void		clntudp_destroy(CLIENT *);
+
+static struct clnt_ops udp_ops = {
+	clntudp_call,
+	clntudp_abort,
+	clntudp_geterr,
+	clntudp_freeres,
+	clntudp_destroy,
+	clntudp_control
+};
+
+/*
+ * Private data kept per client handle
+ */
+struct cu_data {
+	int		   cu_sock;
+	bool_t			cu_closeit;	/* opened by library */
+	struct sockaddr_in cu_raddr;
+	int		   cu_rlen;
+	struct timeval		cu_wait;	/* retransmit interval */
+	struct timeval		cu_total;	/* total time for the call */
+	struct rpc_err	   cu_error;
+	XDR		   cu_outxdrs;
+	u_int		   cu_xdrpos;
+	u_int			cu_sendsz;	/* send size */
+	union {
+	  u_int32_t	   *i32;
+	  char		   *c;
+	} _cu_outbuf;
+#define cu_outbuf _cu_outbuf.c
+	u_int			cu_recvsz;	/* recv size */
+	union {
+	  u_int32_t	*i32;
+	  char		c[1];
+	} _cu_inbuf;
+#define cu_inbuf _cu_inbuf.c
+};
+
+/*
+ * Create a UDP based client handle.
+ * If *sockp<0, *sockp is set to a newly created UPD socket.
+ * If raddr->sin_port is 0 a binder on the remote machine
+ * is consulted for the correct port number.
+ * NB: It is the clients responsibility to close *sockp.
+ * NB: The rpch->cl_auth is initialized to null authentication.
+ *     Caller may wish to set this something more useful.
+ *
+ * wait is the amount of time used between retransmitting a call if
+ * no response has been heard;  retransmition occurs until the actual
+ * rpc call times out.
+ *
+ * sendsz and recvsz are the maximum allowable packet sizes that can be
+ * sent and received.
+ */
+CLIENT *
+clntudp_bufcreate(
+	struct sockaddr_in *raddr,
+	u_long program,		/* program number */
+	u_long version,		/* version number */
+	struct timeval wait,
+	int *sockp,
+	u_int sendsz,
+	u_int recvsz)
+{
+	CLIENT *cl = NULL;		/* client handle */
+	struct cu_data *cu = NULL;	/* private data */
+	struct timeval now;
+	struct rpc_msg call_msg;
+	static uintptr_t disrupt;
+
+	if (disrupt == 0)
+		disrupt = (uintptr_t)raddr;
+
+	cl = (CLIENT *)mem_alloc(sizeof(CLIENT));
+	if (cl == NULL) {
+		(void) fprintf(stderr, "clntudp_create: out of memory\n");
+		rpc_createerr.cf_stat = RPC_SYSTEMERROR;
+		rpc_createerr.cf_error.re_errno = errno;
+		goto fooy;
+	}
+	sendsz = ((sendsz + 3) / 4) * 4;
+	recvsz = ((recvsz + 3) / 4) * 4;
+	cu = mem_alloc(sizeof (*cu) + sendsz + recvsz);
+	if (cu == NULL) {
+		(void) fprintf(stderr, "clntudp_create: out of memory\n");
+		rpc_createerr.cf_stat = RPC_SYSTEMERROR;
+		rpc_createerr.cf_error.re_errno = errno;
+		goto fooy;
+	}
+	cu->cu_outbuf = &cu->cu_inbuf[recvsz];
+
+	(void)gettimeofday(&now, (struct timezone *)0);
+	if (raddr->sin_port == 0) {
+		u_short port;
+		if ((port =
+		    pmap_getport(raddr, program, version, IPPROTO_UDP)) == 0) {
+			goto fooy;
+		}
+		raddr->sin_port = htons(port);
+	}
+	cl->cl_ops = &udp_ops;
+	cl->cl_private = (caddr_t)cu;
+	cu->cu_raddr = *raddr;
+	cu->cu_rlen = sizeof (cu->cu_raddr);
+	cu->cu_wait = wait;
+	cu->cu_total.tv_sec = -1;
+	cu->cu_total.tv_usec = -1;
+	cu->cu_sendsz = sendsz;
+	cu->cu_recvsz = recvsz;
+	call_msg.rm_xid = (++disrupt) ^ getpid() ^ now.tv_sec ^ now.tv_usec;
+	call_msg.rm_direction = CALL;
+	call_msg.rm_call.cb_rpcvers = RPC_MSG_VERSION;
+	call_msg.rm_call.cb_prog = program;
+	call_msg.rm_call.cb_vers = version;
+	xdrmem_create(&(cu->cu_outxdrs), cu->cu_outbuf,
+	    sendsz, XDR_ENCODE);
+	if (! xdr_callhdr(&(cu->cu_outxdrs), &call_msg)) {
+		goto fooy;
+	}
+	cu->cu_xdrpos = XDR_GETPOS(&(cu->cu_outxdrs));
+	if (*sockp < 0) {
+		int dontblock = 1;
+
+		*sockp = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
+		if (*sockp < 0) {
+			rpc_createerr.cf_stat = RPC_SYSTEMERROR;
+			rpc_createerr.cf_error.re_errno = errno;
+			goto fooy;
+		}
+		/* attempt to bind to priv port */
+		(void)bindresvport(*sockp, (struct sockaddr_in *)0);
+		/* the sockets rpc controls are non-blocking */
+		(void)ioctl(*sockp, FIONBIO, (char *) &dontblock);
+		cu->cu_closeit = TRUE;
+	} else {
+		cu->cu_closeit = FALSE;
+	}
+	cu->cu_sock = *sockp;
+	cl->cl_auth = authnone_create();
+	return (cl);
+fooy:
+	if (cu)
+		mem_free((caddr_t)cu, sizeof(*cu) + sendsz + recvsz);
+	if (cl)
+		mem_free((caddr_t)cl, sizeof(CLIENT));
+	return ((CLIENT *)NULL);
+}
+
+CLIENT *
+clntudp_create(
+	struct sockaddr_in *raddr,
+	u_long program,		/* program number */
+	u_long version,		/* version number */
+	struct timeval wait,
+	int *sockp)
+{
+
+	return(clntudp_bufcreate(raddr, program, version, wait, sockp,
+	    UDPMSGSIZE, UDPMSGSIZE));
+}
+
+static enum clnt_stat
+clntudp_call(
+	CLIENT	*cl,			/* client handle */
+	rpcproc_t	proc,		/* procedure number */
+	xdrproc_t	xargs,		/* xdr routine for args */
+	void		*argsp,		/* pointer to args */
+	xdrproc_t	xresults,	/* xdr routine for results */
+	void		*resultsp,	/* pointer to results */
+	struct timeval	utimeout )	/* seconds to wait before giving up */
+{
+	struct cu_data *cu = (struct cu_data *)cl->cl_private;
+	XDR *xdrs;
+	size_t outlen = 0;
+	int inlen;
+	socklen_t fromlen;
+	fd_set *fds, readfds;
+	struct sockaddr_in from;
+	struct rpc_msg reply_msg;
+	XDR reply_xdrs;
+	struct timeval time_waited, start, after, tmp1, tmp2, tv;
+	bool_t ok;
+	int nrefreshes = 2;	/* number of times to refresh cred */
+	struct timeval timeout;
+
+	if (cu->cu_total.tv_usec == -1)
+		timeout = utimeout;     /* use supplied timeout */
+	else
+		timeout = cu->cu_total; /* use default timeout */
+
+	if (cu->cu_sock + 1 > FD_SETSIZE) {
+		int bytes = howmany(cu->cu_sock + 1, NFDBITS) * sizeof(fd_mask);
+		fds = (fd_set *)malloc(bytes);
+		if (fds == NULL)
+			return (cu->cu_error.re_status = RPC_CANTSEND);
+		memset(fds, 0, bytes);
+	} else {
+		fds = &readfds;
+		FD_ZERO(fds);
+	}
+
+	timerclear(&time_waited);
+
+call_again:
+	xdrs = &(cu->cu_outxdrs);
+	xdrs->x_op = XDR_ENCODE;
+	XDR_SETPOS(xdrs, cu->cu_xdrpos);
+	/*
+	 * the transaction is the first thing in the out buffer
+	 */
+	(*(u_short *)(cu->cu_outbuf))++;
+	if ((! XDR_PUTLONG(xdrs, (long *)&proc)) ||
+	    (! AUTH_MARSHALL(cl->cl_auth, xdrs)) ||
+	    (! (*xargs)(xdrs, argsp))) {
+		if (fds != &readfds)
+			free(fds);
+		return (cu->cu_error.re_status = RPC_CANTENCODEARGS);
+	}
+	outlen = (size_t)XDR_GETPOS(xdrs);
+
+send_again:
+	if (sendto(cu->cu_sock, cu->cu_outbuf, outlen, 0,
+	    (struct sockaddr *)&(cu->cu_raddr), cu->cu_rlen) != outlen) {
+		cu->cu_error.re_errno = errno;
+		if (fds != &readfds)
+			free(fds);
+		return (cu->cu_error.re_status = RPC_CANTSEND);
+	}
+
+	/*
+	 * Hack to provide rpc-based message passing
+	 */
+	if (!timerisset(&timeout)) {
+		if (fds != &readfds)
+			free(fds);
+		return (cu->cu_error.re_status = RPC_TIMEDOUT);
+	}
+	/*
+	 * sub-optimal code appears here because we have
+	 * some clock time to spare while the packets are in flight.
+	 * (We assume that this is actually only executed once.)
+	 */
+	reply_msg.acpted_rply.ar_verf = _null_auth;
+	reply_msg.acpted_rply.ar_results.where = resultsp;
+	reply_msg.acpted_rply.ar_results.proc = xresults;
+
+	gettimeofday(&start, NULL);
+	for (;;) {
+		/* XXX we know the other bits are still clear */
+		FD_SET(cu->cu_sock, fds);
+		tv = cu->cu_wait;
+		switch (select(cu->cu_sock+1, fds, NULL, NULL, &tv)) {
+
+		case 0:
+			timeradd(&time_waited, &cu->cu_wait, &tmp1);
+			time_waited = tmp1;
+			if (timercmp(&time_waited, &timeout, <))
+				goto send_again;
+			if (fds != &readfds)
+				free(fds);
+			return (cu->cu_error.re_status = RPC_TIMEDOUT);
+
+		case -1:
+			if (errno == EINTR) {
+				gettimeofday(&after, NULL);
+				timersub(&after, &start, &tmp1);
+				timeradd(&time_waited, &tmp1, &tmp2);
+				time_waited = tmp2;
+				if (timercmp(&time_waited, &timeout, <))
+					continue;
+				if (fds != &readfds)
+					free(fds);
+				return (cu->cu_error.re_status = RPC_TIMEDOUT);
+			}
+			cu->cu_error.re_errno = errno;
+			if (fds != &readfds)
+				free(fds);
+			return (cu->cu_error.re_status = RPC_CANTRECV);
+		}
+
+		do {
+			fromlen = sizeof(struct sockaddr);
+			inlen = recvfrom(cu->cu_sock, cu->cu_inbuf,
+				(int) cu->cu_recvsz, 0,
+				(struct sockaddr *)&from, &fromlen);
+		} while (inlen < 0 && errno == EINTR);
+		if (inlen < 0) {
+			if (errno == EWOULDBLOCK)
+				continue;
+			cu->cu_error.re_errno = errno;
+			if (fds != &readfds)
+				free(fds);
+			return (cu->cu_error.re_status = RPC_CANTRECV);
+		}
+		if (inlen < sizeof(u_int32_t))
+			continue;
+		/* see if reply transaction id matches sent id */
+		if (*(cu->_cu_inbuf.i32) != *(cu->_cu_outbuf.i32))
+			continue;
+		/* we now assume we have the proper reply */
+		break;
+	}
+
+	/*
+	 * now decode and validate the response
+	 */
+	xdrmem_create(&reply_xdrs, cu->cu_inbuf, (u_int)inlen, XDR_DECODE);
+	ok = xdr_replymsg(&reply_xdrs, &reply_msg);
+	/* XDR_DESTROY(&reply_xdrs);  save a few cycles on noop destroy */
+	if (ok) {
+		_seterr_reply(&reply_msg, &(cu->cu_error));
+		if (cu->cu_error.re_status == RPC_SUCCESS) {
+			if (! AUTH_VALIDATE(cl->cl_auth,
+				&reply_msg.acpted_rply.ar_verf)) {
+				cu->cu_error.re_status = RPC_AUTHERROR;
+				cu->cu_error.re_why = AUTH_INVALIDRESP;
+			}
+			if (reply_msg.acpted_rply.ar_verf.oa_base != NULL) {
+				xdrs->x_op = XDR_FREE;
+				(void)xdr_opaque_auth(xdrs,
+				    &(reply_msg.acpted_rply.ar_verf));
+			}
+		}  /* end successful completion */
+		else {
+			/* maybe our credentials need to be refreshed ... */
+			if (nrefreshes > 0 && AUTH_REFRESH(cl->cl_auth)) {
+				nrefreshes--;
+				goto call_again;
+			}
+		}  /* end of unsuccessful completion */
+	}  /* end of valid reply message */
+	else {
+		/*
+		 * It's possible for xdr_replymsg() to fail partway
+		 * through its attempt to decode the result from the
+		 * server. If this happens, it will leave the reply
+		 * structure partially populated with dynamically
+		 * allocated memory. (This can happen if someone uses
+		 * clntudp_bufcreate() to create a CLIENT handle and
+		 * specifies a receive buffer size that is too small.)
+		 * This memory must be free()ed to avoid a leak.
+		 */
+		int op = reply_xdrs.x_op;
+		reply_xdrs.x_op = XDR_FREE;
+		xdr_replymsg(&reply_xdrs, &reply_msg);
+		reply_xdrs.x_op = op;
+		cu->cu_error.re_status = RPC_CANTDECODERES;
+	}
+	if (fds != &readfds)
+		free(fds);
+	return (cu->cu_error.re_status);
+}
+
+static void
+clntudp_geterr(
+	CLIENT *cl,
+	struct rpc_err *errp)
+{
+	struct cu_data *cu = (struct cu_data *)cl->cl_private;
+
+	*errp = cu->cu_error;
+}
+
+
+static bool_t
+clntudp_freeres(
+	CLIENT *cl,
+	xdrproc_t xdr_res,
+	void *res_ptr)
+{
+	struct cu_data *cu = (struct cu_data *)cl->cl_private;
+	XDR *xdrs = &(cu->cu_outxdrs);
+
+	xdrs->x_op = XDR_FREE;
+	return ((*xdr_res)(xdrs, res_ptr));
+}
+
+static void
+clntudp_abort(void)
+{
+}
+
+
+static bool_t
+clntudp_control(
+	CLIENT *cl,
+	int request,
+	char *info)
+{
+	struct cu_data *cu = (struct cu_data *)cl->cl_private;
+	struct timeval *tv;
+	socklen_t len;
+
+	switch (request) {
+	case CLSET_FD_CLOSE:
+		cu->cu_closeit = TRUE;
+		break;
+	case CLSET_FD_NCLOSE:
+		cu->cu_closeit = FALSE;
+		break;
+	case CLSET_TIMEOUT:
+		if (info == NULL)
+			return(FALSE);
+		tv = (struct timeval *)info;
+		cu->cu_total.tv_sec = tv->tv_sec;
+		cu->cu_total.tv_usec = tv->tv_usec;
+		break;
+	case CLGET_TIMEOUT:
+		if (info == NULL)
+			return(FALSE);
+		*(struct timeval *)info = cu->cu_total;
+		break;
+	case CLSET_RETRY_TIMEOUT:
+		if (info == NULL)
+			return(FALSE);
+		tv = (struct timeval *)info;
+		cu->cu_wait.tv_sec = tv->tv_sec;
+		cu->cu_wait.tv_usec = tv->tv_usec;
+		break;
+	case CLGET_RETRY_TIMEOUT:
+		if (info == NULL)
+			return(FALSE);
+		*(struct timeval *)info = cu->cu_wait;
+		break;
+	case CLGET_SERVER_ADDR:
+		if (info == NULL)
+			return(FALSE);
+		*(struct sockaddr_in *)info = cu->cu_raddr;
+		break;
+	case CLGET_FD:
+		if (info == NULL)
+			return(FALSE);
+		*(int *)info = cu->cu_sock;
+		break;
+	case CLGET_XID:
+		/*
+		 * use the knowledge that xid is the
+		 * first element in the call structure *.
+		 * This will get the xid of the PREVIOUS call
+		 */
+		if (info == NULL)
+			return(FALSE);
+		*(u_long *)info = ntohl(*(u_long *)cu->cu_outbuf);
+		break;
+	case CLSET_XID:
+		/* This will set the xid of the NEXT call */
+		if (info == NULL)
+			return(FALSE);
+		*(u_long *)cu->cu_outbuf =  htonl(*(u_long *)info - 1);
+		/* decrement by 1 as clntudp_call() increments once */
+	case CLGET_VERS:
+		/*
+		 * This RELIES on the information that, in the call body,
+		 * the version number field is the fifth field from the
+		 * begining of the RPC header. MUST be changed if the
+		 * call_struct is changed
+		 */
+		if (info == NULL)
+			return(FALSE);
+		*(u_long *)info = ntohl(*(u_long *)(cu->cu_outbuf +
+						4 * BYTES_PER_XDR_UNIT));
+		break;
+	case CLSET_VERS:
+		if (info == NULL)
+			return(FALSE);
+		*(u_long *)(cu->cu_outbuf + 4 * BYTES_PER_XDR_UNIT)
+				= htonl(*(u_long *)info);
+		break;
+	case CLGET_PROG:
+		/*
+		 * This RELIES on the information that, in the call body,
+		 * the program number field is the fourth field from the
+		 * begining of the RPC header. MUST be changed if the
+		 * call_struct is changed
+		 */
+		if (info == NULL)
+			return(FALSE);
+		*(u_long *)info = ntohl(*(u_long *)(cu->cu_outbuf +
+						3 * BYTES_PER_XDR_UNIT));
+		break;
+	case CLSET_PROG:
+		if (info == NULL)
+			return(FALSE);
+		*(u_long *)(cu->cu_outbuf + 3 * BYTES_PER_XDR_UNIT)
+				= htonl(*(u_long *)info);
+		break;
+	case CLGET_LOCAL_ADDR:
+		len = sizeof(struct sockaddr);
+		if (getsockname(cu->cu_sock, (struct sockaddr *)info, &len) <0)
+			return(FALSE);
+		break;
+	case CLGET_SVC_ADDR:
+	case CLSET_SVC_ADDR:
+	case CLSET_PUSH_TIMOD:
+	case CLSET_POP_TIMOD:
+	default:
+		return (FALSE);
+	}
+	return (TRUE);
+}
+
+static void
+clntudp_destroy(
+	CLIENT *cl)
+{
+	struct cu_data *cu = (struct cu_data *)cl->cl_private;
+
+	if (cu->cu_closeit) {
+		(void)_RPC_close(cu->cu_sock);
+	}
+	XDR_DESTROY(&(cu->cu_outxdrs));
+	mem_free(cu, (sizeof (*cu) + cu->cu_sendsz + cu->cu_recvsz));
+	mem_free(cl, sizeof (CLIENT));
+}
diff --git a/services/librpc/src/rpc/des_crypt.3 b/services/librpc/src/rpc/des_crypt.3
new file mode 100644
index 0000000..a92f577
--- /dev/null
+++ b/services/librpc/src/rpc/des_crypt.3
@@ -0,0 +1,130 @@
+.\" @(#)des_crypt.3	2.1 88/08/11 4.0 RPCSRC; from 1.16 88/03/02 SMI;
+.\" $FreeBSD: src/lib/libc/rpc/des_crypt.3,v 1.4 2000/03/02 09:13:45 sheldonh Exp $
+.\"
+.TH DES_CRYPT 3  "6 October 1987"
+.SH NAME
+des_crypt, ecb_crypt, cbc_crypt, des_setparity \- fast DES encryption
+.SH SYNOPSIS
+.nf
+.B #include <des_crypt.h>
+.LP
+.B int ecb_crypt(key, data, datalen, mode)
+.B char *key;
+.B char *data;
+.B unsigned datalen;
+.B unsigned mode;
+.LP
+.B int cbc_crypt(key, data, datalen, mode, ivec)
+.B char *key;
+.B char *data;
+.B unsigned datalen;
+.B unsigned mode;
+.B char *ivec;
+.LP
+.B void des_setparity(key)
+.B char *key;
+.fi
+.SH DESCRIPTION
+.IX encryption cbc_crypt "" \fLcbc_crypt\fP
+.IX "des encryption" cbc_crypt "DES encryption" \fLcbc_crypt\fP
+.IX encryption des_setparity "" \fLdes_setparity\fP
+.IX "des encryption" des_setparity "DES encryption" \fLdes_setparity\fP
+.B ecb_crypt(\|)
+and
+.B cbc_crypt(\|)
+implement the
+.SM NBS
+.SM DES
+(Data Encryption Standard).
+These routines are faster and more general purpose than
+.BR crypt (3).
+They also are able to utilize
+.SM DES
+hardware if it is available.
+.B ecb_crypt(\|)
+encrypts in
+.SM ECB
+(Electronic Code Book)
+mode, which encrypts blocks of data independently.
+.B cbc_crypt(\|)
+encrypts in
+.SM CBC
+(Cipher Block Chaining)
+mode, which chains together
+successive blocks.
+.SM CBC
+mode protects against insertions, deletions and
+substitutions of blocks.
+Also, regularities in the clear text will
+not appear in the cipher text.
+.LP
+Here is how to use these routines.  The first parameter,
+.IR key ,
+is the 8-byte encryption key with parity.
+To set the key's parity, which for
+.SM DES
+is in the low bit of each byte, use
+.IR des_setparity .
+The second parameter,
+.IR data ,
+contains the data to be encrypted or decrypted.
+The
+third parameter,
+.IR datalen ,
+is the length in bytes of
+.IR data ,
+which must be a multiple of 8. The fourth parameter,
+.IR mode ,
+is formed by
+.SM OR\s0'ing
+together some things.  For the encryption direction 'or' in either
+.SM DES_ENCRYPT
+or
+.SM DES_DECRYPT\s0.
+For software versus hardware
+encryption, 'or' in either
+.SM DES_HW
+or
+.SM DES_SW\s0.
+If
+.SM DES_HW
+is specified, and there is no hardware, then the encryption is performed
+in software and the routine returns
+.SM DESERR_NOHWDEVICE\s0.
+For
+.IR cbc_crypt ,
+the parameter
+.I ivec
+is the the 8-byte initialization
+vector for the chaining.  It is updated to the next initialization
+vector upon return.
+.LP
+.SH "SEE ALSO"
+.BR des (1),
+.BR crypt (3)
+.SH DIAGNOSTICS
+.PD 0
+.TP 20
+.SM DESERR_NONE
+No error.
+.TP
+.SM DESERR_NOHWDEVICE
+Encryption succeeded, but done in software instead of the requested hardware.
+.TP
+.SM DESERR_HWERR
+An error occurred in the hardware or driver.
+.TP
+.SM DESERR_BADPARAM
+Bad parameter to routine.
+.PD
+.LP
+Given a result status
+.IR stat ,
+the macro
+.SM DES_FAILED\c
+.BR ( stat )
+is false only for the first two statuses.
+.SH RESTRICTIONS
+These routines are not available in RPCSRC 4.0.
+This information is provided to describe the DES interface expected by
+Secure RPC.
diff --git a/services/librpc/src/rpc/get_myaddress.c b/services/librpc/src/rpc/get_myaddress.c
new file mode 100644
index 0000000..0804c85
--- /dev/null
+++ b/services/librpc/src/rpc/get_myaddress.c
@@ -0,0 +1,117 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)get_myaddress.c 1.4 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)get_myaddress.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/get_myaddress.c,v 1.17 2000/01/27 23:06:37 jasone Exp $";
+#endif
+
+/*
+ * get_myaddress.c
+ *
+ * Get client's IP address via ioctl.  This avoids using the yellowpages.
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <rpc/types.h>
+#include <rpc/xdr.h>
+#include <rpc/pmap_prot.h>
+#include <sys/socket.h>
+#include <stdio.h>
+#include <unistd.h>
+#include <sys/mbuf.h>
+#include <net/if.h>
+#include <sys/ioctl.h>
+#include <netinet/in.h>
+#include <arpa/inet.h>
+
+/*
+ * don't use gethostbyname, which would invoke yellow pages
+ *
+ * Avoid loopback interfaces.  We return information from a loopback
+ * interface only if there are no other possible interfaces.
+ */
+int
+get_myaddress(
+	struct sockaddr_in *addr)
+{
+	int s;
+	char buf[BUFSIZ];
+	struct ifconf ifc;
+	struct ifreq ifreq, *ifr, *end;
+	int loopback = 0, gotit = 0;
+
+	if ((s = socket(AF_INET, SOCK_DGRAM, 0)) < 0) {
+		return(-1);
+	}
+	ifc.ifc_len = sizeof (buf);
+	ifc.ifc_buf = buf;
+	if (ioctl(s, SIOCGIFCONF, (char *)&ifc) < 0) {
+		_RPC_close(s);
+		return(-1);
+	}
+again:
+	ifr = ifc.ifc_req;
+	end = (struct ifreq *) (ifc.ifc_buf + ifc.ifc_len);
+
+	while (ifr < end) {
+		ifreq = *ifr;
+		if (ioctl(s, SIOCGIFFLAGS, (char *)&ifreq) < 0) {
+			_RPC_close(s);
+			return(-1);
+		}
+		if (((ifreq.ifr_flags & IFF_UP) &&
+		    ifr->ifr_addr.sa_family == AF_INET &&
+			!(ifreq.ifr_flags & IFF_LOOPBACK)) ||
+		    (loopback == 1 && (ifreq.ifr_flags & IFF_LOOPBACK)
+			&& (ifr->ifr_addr.sa_family == AF_INET)
+			&& (ifreq.ifr_flags &  IFF_UP))) {
+			*addr = *((struct sockaddr_in *)&ifr->ifr_addr);
+			addr->sin_port = htons(PMAPPORT);
+			gotit = 1;
+			break;
+		}
+		if (ifr->ifr_addr.sa_len)
+			ifr = (struct ifreq *) ((caddr_t) ifr +
+			      ifr->ifr_addr.sa_len -
+			      sizeof(struct sockaddr));
+		ifr++;
+	}
+	if (gotit == 0 && loopback == 0) {
+		loopback = 1;
+		goto again;
+	}
+	(void)_RPC_close(s);
+	return (gotit ? 0 : -1);
+}
diff --git a/services/librpc/src/rpc/getrpcent.3 b/services/librpc/src/rpc/getrpcent.3
new file mode 100644
index 0000000..1e92e9d
--- /dev/null
+++ b/services/librpc/src/rpc/getrpcent.3
@@ -0,0 +1,98 @@
+.\" @(#)getrpcent.3n	2.2 88/08/02 4.0 RPCSRC; from 1.11 88/03/14 SMI
+.\" $FreeBSD: src/lib/libc/rpc/getrpcent.3,v 1.11 1999/08/28 00:00:39 peter Exp $
+.\"
+.Dd December 14, 1987
+.Dt GETRPCENT 3
+.Os
+.Sh NAME
+.Nm getrpcent ,
+.Nm getrpcbyname ,
+.Nm getrpcbynumber ,
+.Nm endrpcent ,
+.Nm setrpcent
+.Nd get RPC entry
+.Sh SYNOPSIS
+.Fd #include <rpc/rpc.h>
+.Ft struct rpcent *
+.Fn getrpcent void
+.Ft struct rpcent *
+.Fn getrpcbyname "char *name"
+.Ft struct rpcent *
+.Fn getrpcbynumber "int number"
+.Ft void
+.Fn setrpcent "int stayopen"
+.Ft void
+.Fn endrpcent void
+.Sh DESCRIPTION
+The
+.Fn getrpcent ,
+.Fn getrpcbyname ,
+and
+.Fn getrpcbynumber
+functions each return a pointer to an object with the
+following structure
+containing the broken-out
+fields of a line in the rpc program number data base,
+.Pa /etc/rpc .
+.Bd -literal
+
+struct	rpcent {
+	char	*r_name;	/* name of server for this rpc program */
+	char	**r_aliases;	/* alias list */
+	long	r_number;	/* rpc program number */
+};
+.Ed
+.Pp
+The members of this structure are:
+.Bl -tag -width r_aliasesxxx
+.It Fa r_name
+The name of the server for this rpc program.
+.It Fa r_aliases
+A zero terminated list of alternate names for the rpc program.
+.It Fa r_number
+The rpc program number for this service.
+.El
+.Pp
+The
+.Fn getrpcent
+function reads the next line of the file, opening the file if necessary.
+The
+.Nm getrpcent
+function opens and rewinds the file.  If the
+.Fa stayopen
+flag is non-zero,
+the net data base will not be closed after each call to
+.Fn getrpcent
+(either directly, or indirectly through one of
+the other 
+.Fn getrpcent
+function family.
+.Pp
+.Fn endrpcent
+closes the file.
+.Pp
+.Fn getrpcbyname
+and
+.Fn getrpcbynumber
+sequentially search from the beginning
+of the file until a matching rpc program name or
+program number is found, or until end-of-file is encountered.
+.Sh FILES
+.Bl -tag -width /etc/rpc -compact
+.It Pa /etc/rpc
+.El
+.Sh "SEE ALSO"
+.Xr rpc 5 ,
+.Xr rpcinfo 8 ,
+.Xr ypserv 8
+.Sh DIAGNOSTICS
+A
+.Dv NULL
+pointer is returned on 
+.Dv EOF
+or error.
+.Sh BUGS
+All information
+is contained in a static area
+so it must be copied if it is
+to be saved.
diff --git a/services/librpc/src/rpc/getrpcent.c b/services/librpc/src/rpc/getrpcent.c
new file mode 100644
index 0000000..fdd0f88
--- /dev/null
+++ b/services/librpc/src/rpc/getrpcent.c
@@ -0,0 +1,301 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user or with the express written consent of
+ * Sun Microsystems, Inc.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)getrpcent.c 1.14 91/03/11 Copyr 1984 Sun Micro";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/getrpcent.c,v 1.10 1999/08/28 00:00:39 peter Exp $";
+#endif
+
+/*
+ * Copyright (c) 1984 by Sun Microsystems, Inc.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <sys/types.h>
+#include <string.h>
+#include <rpc/rpc.h>
+#ifdef YP
+#include <rpcsvc/yp_prot.h>
+#include <rpcsvc/ypclnt.h>
+#endif
+
+/*
+ * Internet version.
+ */
+struct rpcdata {
+	FILE	*rpcf;
+	int	stayopen;
+#define	MAXALIASES	35
+	char	*rpc_aliases[MAXALIASES];
+	struct	rpcent rpc;
+	char	line[BUFSIZ+1];
+#ifdef	YP
+	char	*domain;
+	char	*current;
+	int	currentlen;
+#endif
+} *rpcdata;
+
+#ifdef	YP
+static int	__yp_nomap = 0;
+extern int _yp_check(char **);
+#endif	/* YP */
+
+static	struct rpcent *interpret(char *val, int len);
+
+static char RPCDB[] = "/etc/rpc";
+
+static struct rpcdata *
+_rpcdata(void)
+{
+	register struct rpcdata *d = rpcdata;
+
+	if (d == 0) {
+		d = (struct rpcdata *)calloc(1, sizeof (struct rpcdata));
+		rpcdata = d;
+	}
+	return (d);
+}
+
+struct rpcent *
+getrpcbynumber(int number)
+{
+	register struct rpcdata *d = _rpcdata();
+	register struct rpcent *p;
+#ifdef	YP
+	int reason;
+	char adrstr[16];
+#endif
+
+	if (d == 0)
+		return (0);
+#ifdef	YP
+        if (!__yp_nomap && _yp_check(&d->domain)) {
+                sprintf(adrstr, "%d", number);
+                reason = yp_match(d->domain, "rpc.bynumber", adrstr, strlen(adrstr),
+                                  &d->current, &d->currentlen);
+                switch(reason) {
+                case 0:
+                        break;
+                case YPERR_MAP:
+                        __yp_nomap = 1;
+                        goto no_yp;
+                        break;
+                default:
+                        return(0);
+                        break;
+                }
+                d->current[d->currentlen] = '\0';
+                p = interpret(d->current, d->currentlen);
+                (void) free(d->current);
+                return p;
+        }
+no_yp:
+#endif	/* YP */
+	setrpcent(0);
+	while ((p = getrpcent())) {
+		if (p->r_number == number)
+			break;
+	}
+	endrpcent();
+	return (p);
+}
+
+struct rpcent *
+getrpcbyname(char *name)
+{
+	struct rpcent *rpc = NULL;
+	char **rp;
+
+	setrpcent(0);
+	while ((rpc = getrpcent())) {
+		if (strcmp(rpc->r_name, name) == 0)
+			goto done;
+		for (rp = rpc->r_aliases; *rp != NULL; rp++) {
+			if (strcmp(*rp, name) == 0)
+				goto done;
+		}
+	}
+done:
+	endrpcent();
+	return (rpc);
+}
+
+void
+setrpcent(int f)
+{
+	register struct rpcdata *d = _rpcdata();
+
+	if (d == 0)
+		return;
+#ifdef	YP
+        if (!__yp_nomap && _yp_check(NULL)) {
+                if (d->current)
+                        free(d->current);
+                d->current = NULL;
+                d->currentlen = 0;
+                return;
+        }
+        __yp_nomap = 0;
+#endif	/* YP */
+	if (d->rpcf == NULL)
+		d->rpcf = fopen(RPCDB, "r");
+	else
+		rewind(d->rpcf);
+	d->stayopen |= f;
+}
+
+void
+endrpcent(void)
+{
+	register struct rpcdata *d = _rpcdata();
+
+	if (d == 0)
+		return;
+#ifdef	YP
+        if (!__yp_nomap && _yp_check(NULL)) {
+        	if (d->current && !d->stayopen)
+                        free(d->current);
+                d->current = NULL;
+                d->currentlen = 0;
+                return;
+        }
+        __yp_nomap = 0;
+#endif	/* YP */
+	if (d->rpcf && !d->stayopen) {
+		fclose(d->rpcf);
+		d->rpcf = NULL;
+	}
+}
+
+struct rpcent *
+getrpcent(void)
+{
+	register struct rpcdata *d = _rpcdata();
+#ifdef	YP
+	struct rpcent *hp;
+	int reason;
+	char *val = NULL;
+	int vallen;
+#endif
+
+	if (d == 0)
+		return(NULL);
+#ifdef	YP
+        if (!__yp_nomap && _yp_check(&d->domain)) {
+                if (d->current == NULL && d->currentlen == 0) {
+                        reason = yp_first(d->domain, "rpc.bynumber",
+                                          &d->current, &d->currentlen,
+                                          &val, &vallen);
+                } else {
+                        reason = yp_next(d->domain, "rpc.bynumber",
+                                         d->current, d->currentlen,
+                                         &d->current, &d->currentlen,
+                                         &val, &vallen);
+                }
+                switch(reason) {
+                case 0:
+                        break;
+                case YPERR_MAP:
+                        __yp_nomap = 1;
+                        goto no_yp;
+                        break;
+                default:
+                        return(0);
+                        break;
+                }
+                val[vallen] = '\0';
+                hp = interpret(val, vallen);
+                (void) free(val);
+                return hp;
+        }
+no_yp:
+#endif	/* YP */
+	if (d->rpcf == NULL && (d->rpcf = fopen(RPCDB, "r")) == NULL)
+		return (NULL);
+	/* -1 so there is room to append a \n below */
+        if (fgets(d->line, BUFSIZ - 1, d->rpcf) == NULL)
+		return (NULL);
+	return (interpret(d->line, strlen(d->line)));
+}
+
+static struct rpcent *
+interpret(
+	char *val,
+	int len)
+{
+	register struct rpcdata *d = _rpcdata();
+	char *p;
+	register char *cp, **q;
+
+	if (d == 0)
+		return (0);
+	(void) strncpy(d->line, val, BUFSIZ);
+	d->line[BUFSIZ] = '\0';
+	p = d->line;
+	p[len] = '\n';
+	if (*p == '#')
+		return (getrpcent());
+	cp = strpbrk(p, "#\n");
+	if (cp == NULL)
+		return (getrpcent());
+	*cp = '\0';
+	cp = strpbrk(p, " \t");
+	if (cp == NULL)
+		return (getrpcent());
+	*cp++ = '\0';
+	/* THIS STUFF IS INTERNET SPECIFIC */
+	d->rpc.r_name = d->line;
+	while (*cp == ' ' || *cp == '\t')
+		cp++;
+	d->rpc.r_number = atoi(cp);
+	q = d->rpc.r_aliases = d->rpc_aliases;
+	cp = strpbrk(cp, " \t");
+	if (cp != NULL)
+		*cp++ = '\0';
+	while (cp && *cp) {
+		if (*cp == ' ' || *cp == '\t') {
+			cp++;
+			continue;
+		}
+		if (q < &(d->rpc_aliases[MAXALIASES - 1]))
+			*q++ = cp;
+		cp = strpbrk(cp, " \t");
+		if (cp != NULL)
+			*cp++ = '\0';
+	}
+	*q = NULL;
+	return (&d->rpc);
+}
diff --git a/services/librpc/src/rpc/getrpcport.3 b/services/librpc/src/rpc/getrpcport.3
new file mode 100644
index 0000000..0e9175e
--- /dev/null
+++ b/services/librpc/src/rpc/getrpcport.3
@@ -0,0 +1,31 @@
+.\" @(#)getrpcport.3r	2.2 88/08/02 4.0 RPCSRC; from 1.12 88/02/26 SMI
+.\" $FreeBSD: src/lib/libc/rpc/getrpcport.3,v 1.6 1999/08/28 00:00:40 peter Exp $
+.\"
+.Dd October 6, 1987
+.Dt GETRPCPORT 3
+.Os
+.Sh NAME
+.Nm getrpcport
+.Nd get RPC port number
+.Sh SYNOPSIS
+.Ft int
+.Fn getrpcport "char *host" "int prognum" "int versnum" "int proto"
+.Sh DESCRIPTION
+.Fn getrpcport
+returns the port number for version
+.Fa versnum
+of the RPC program
+.Fa prognum
+running on
+.Fa host
+and using protocol
+.Fa proto .
+It returns 0 if it cannot contact the portmapper, or if
+.Fa prognum
+is not registered.  If
+.Fa prognum
+is registered but not with version
+.Fa versnum ,
+it will still return a port number (for some version of the program)
+indicating that the program is indeed registered.
+The version mismatch will be detected upon the first call to the service.
diff --git a/services/librpc/src/rpc/getrpcport.c b/services/librpc/src/rpc/getrpcport.c
new file mode 100644
index 0000000..f783bac
--- /dev/null
+++ b/services/librpc/src/rpc/getrpcport.c
@@ -0,0 +1,69 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)getrpcport.c 1.3 87/08/11 SMI";*/
+/*static char *sccsid = "from: @(#)getrpcport.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/getrpcport.c,v 1.10 1999/08/28 00:00:40 peter Exp $";
+#endif
+
+/*
+ * Copyright (c) 1985 by Sun Microsystems, Inc.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdio.h>
+#include <string.h>
+#include <rpc/rpc.h>
+#include <rpc/pmap_clnt.h>
+#include <netdb.h>
+#include <sys/socket.h>
+
+int
+getrpcport(
+	char *host,
+	int prognum, 
+	int versnum, 
+	int proto )
+{
+	struct sockaddr_in addr;
+	struct hostent *hp;
+
+	if ((hp = gethostbyname(host)) == NULL)
+		return (0);
+	memset(&addr, 0, sizeof(addr));
+	addr.sin_len = sizeof(struct sockaddr_in);
+	addr.sin_family = AF_INET;
+	addr.sin_port =  0;
+	memcpy((char *)&addr.sin_addr, hp->h_addr, hp->h_length);
+	return (pmap_getport(&addr, prognum, versnum, proto));
+}
diff --git a/services/librpc/src/rpc/netname.c b/services/librpc/src/rpc/netname.c
new file mode 100644
index 0000000..e75ef73
--- /dev/null
+++ b/services/librpc/src/rpc/netname.c
@@ -0,0 +1,139 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user or with the express written consent of
+ * Sun Microsystems, Inc.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+#if !defined(lint) && defined(SCCSIDS)
+static char sccsid[] = "@(#)netname.c 1.8 91/03/11 Copyr 1986 Sun Micro";
+#endif
+
+/*
+ * netname utility routines
+ * convert from unix names to network names and vice-versa
+ * This module is operating system dependent!
+ * What we define here will work with any unix system that has adopted
+ * the sun NIS domain architecture.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <sys/param.h>
+#include <rpc/rpc.h>
+#include <rpc/rpc_com.h>
+#ifdef YP
+#include <rpcsvc/yp_prot.h>
+#include <rpcsvc/ypclnt.h>
+#endif
+#include <ctype.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <string.h>
+#include <stdio.h>
+
+#ifndef MAXHOSTNAMELEN
+#define MAXHOSTNAMELEN 256
+#endif
+#ifndef NGROUPS
+#define NGROUPS 16
+#endif
+
+static char *OPSYS = "unix";
+
+/*
+ * Figure out my fully qualified network name
+ */
+int
+getnetname(char name[MAXNETNAMELEN+1])
+{
+	uid_t uid;
+
+	uid = geteuid();
+	if (uid == 0) {
+		return (host2netname(name, (char *) NULL, (char *) NULL));
+	} else {
+		return (user2netname(name, uid, (char *) NULL));
+	}
+}
+
+
+/*
+ * Convert unix cred to network-name
+ */
+int
+user2netname(
+	char netname[MAXNETNAMELEN + 1],
+	uid_t uid,
+	char *domain)
+{
+	char *dfltdom;
+
+#define MAXIPRINT	(11)	/* max length of printed integer */
+
+	if (domain == NULL) {
+		if (_rpc_get_default_domain(&dfltdom) != 0) {
+			return (0);
+		}
+		domain = dfltdom;
+	}
+	if (strlen(domain) + 1 + MAXIPRINT > MAXNETNAMELEN) {
+		return (0);
+	}
+	(void) sprintf(netname, "%s.%ld@%s", OPSYS, (u_long)uid, domain);	
+	return (1);
+}
+
+
+/*
+ * Convert host to network-name
+ */
+int
+host2netname(
+	char netname[MAXNETNAMELEN + 1],
+	char *host,
+	char *domain)
+{
+	char *dfltdom;
+	char hostname[MAXHOSTNAMELEN+1];
+
+	if (domain == NULL) {
+		if (_rpc_get_default_domain(&dfltdom) != 0) {
+			return (0);
+		}
+		domain = dfltdom;
+	}
+	if (host == NULL) {
+		(void) gethostname(hostname, sizeof(hostname));
+		host = hostname;
+	}
+	if (strlen(domain) + 1 + strlen(host) > MAXNETNAMELEN) {
+		return (0);
+	} 
+	(void) sprintf(netname, "%s.%s@%s", OPSYS, host, domain);
+	return (1);
+}
diff --git a/services/librpc/src/rpc/netnamer.c b/services/librpc/src/rpc/netnamer.c
new file mode 100644
index 0000000..aa9397e
--- /dev/null
+++ b/services/librpc/src/rpc/netnamer.c
@@ -0,0 +1,331 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user or with the express written consent of
+ * Sun Microsystems, Inc.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+#if !defined(lint) && defined(SCCSIDS)
+static char sccsid[] = "@(#)netnamer.c 1.13 91/03/11 Copyr 1986 Sun Micro";
+#endif
+/*
+ * netname utility routines convert from unix names to network names and
+ * vice-versa This module is operating system dependent! What we define here
+ * will work with any unix system that has adopted the sun NIS domain
+ * architecture.
+ */
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <sys/param.h>
+#include <rpc/rpc.h>
+#include <rpc/rpc_com.h>
+#ifdef YP
+#include <rpcsvc/yp_prot.h>
+#include <rpcsvc/ypclnt.h>
+#endif
+#include <ctype.h>
+#include <stdio.h>
+#include <grp.h>
+#include <pwd.h>
+#include <string.h>
+#include <stdlib.h>
+#include <unistd.h>
+
+static char    *OPSYS = "unix";
+#ifdef YP
+static char    *NETID = "netid.byname";
+#endif
+static char    *NETIDFILE = "/etc/netid";
+
+static int getnetid ( char *, char * );
+static int _getgroups ( char *, gid_t * );
+
+#ifndef NGROUPS
+#define NGROUPS 16
+#endif
+
+/*
+ * Convert network-name into unix credential
+ */
+int
+netname2user(
+	char            netname[MAXNETNAMELEN + 1],
+	uid_t            *uidp,
+	gid_t            *gidp,
+	int            *gidlenp,
+	gid_t	       *gidlist)
+{
+	char           *p;
+	int             gidlen;
+	uid_t           uid;
+	long		luid;
+	struct passwd  *pwd;
+	char            val[1024];
+	char           *val1, *val2;
+	char           *domain;
+	int             vallen;
+	int             err;
+
+	if (getnetid(netname, val)) {
+		p = strtok(val, ":");
+		if (p == NULL)
+			return (0);
+		*uidp = (uid_t) atol(val);
+		p = strtok(NULL, "\n,");
+		*gidp = (gid_t) atol(p);
+		if (p == NULL) {
+			return (0);
+		}
+		gidlen = 0;
+		for (gidlen = 0; gidlen < NGROUPS; gidlen++) {
+			p = strtok(NULL, "\n,");
+			if (p == NULL)
+				break;
+			gidlist[gidlen] = (gid_t) atol(p);
+		}
+		*gidlenp = gidlen;
+
+		return (1);
+	}
+	val1 = strchr(netname, '.');
+	if (val1 == NULL)
+		return (0);
+	if (strncmp(netname, OPSYS, (val1-netname)))
+		return (0);
+	val1++;
+	val2 = strchr(val1, '@');
+	if (val2 == NULL)
+		return (0);
+	vallen = val2 - val1;
+	if (vallen > (1024 - 1))
+		vallen = 1024 - 1;
+	(void) strncpy(val, val1, 1024);
+	val[vallen] = 0;
+
+	err = _rpc_get_default_domain(&domain);	/* change to rpc */
+	if (err)
+		return (0);
+
+	if (strcmp(val2 + 1, domain))
+		return (0);	/* wrong domain */
+
+	if (sscanf(val, "%ld", &luid) != 1)
+		return (0);
+	uid = luid;
+
+	/* use initgroups method */
+	pwd = getpwuid(uid);
+	if (pwd == NULL)
+		return (0);
+	*uidp = pwd->pw_uid;
+	*gidp = pwd->pw_gid;
+	*gidlenp = _getgroups(pwd->pw_name, gidlist);
+	return (1);
+}
+
+/*
+ * initgroups
+ */
+
+static int
+_getgroups(
+	char           *uname,
+	gid_t          groups[NGROUPS])
+{
+	gid_t           ngroups = 0;
+	register struct group *grp;
+	register int    i;
+	register int    j;
+	int             filter;
+
+	setgrent();
+	while ((grp = getgrent())) {
+		for (i = 0; grp->gr_mem[i]; i++)
+			if (!strcmp(grp->gr_mem[i], uname)) {
+				if (ngroups == NGROUPS) {
+#ifdef DEBUG
+					fprintf(stderr,
+				"initgroups: %s is in too many groups\n", uname);
+#endif
+					goto toomany;
+				}
+				/* filter out duplicate group entries */
+				filter = 0;
+				for (j = 0; j < ngroups; j++)
+					if (groups[j] == grp->gr_gid) {
+						filter++;
+						break;
+					}
+				if (!filter)
+					groups[ngroups++] = grp->gr_gid;
+			}
+	}
+toomany:
+	endgrent();
+	return (ngroups);
+}
+
+/*
+ * Convert network-name to hostname
+ */
+int
+netname2host(
+	char            netname[MAXNETNAMELEN + 1],
+	char           *hostname,
+	int             hostlen)
+{
+	int             err;
+	char            valbuf[1024];
+	char           *val;
+	char           *val2;
+	int             vallen;
+	char           *domain;
+
+	if (getnetid(netname, valbuf)) {
+		val = valbuf;
+		if ((*val == '0') && (val[1] == ':')) {
+			(void) strncpy(hostname, val + 2, hostlen);
+			return (1);
+		}
+	}
+	val = strchr(netname, '.');
+	if (val == NULL)
+		return (0);
+	if (strncmp(netname, OPSYS, (val - netname)))
+		return (0);
+	val++;
+	val2 = strchr(val, '@');
+	if (val2 == NULL)
+		return (0);
+	vallen = val2 - val;
+	if (vallen > (hostlen - 1))
+		vallen = hostlen - 1;
+	(void) strncpy(hostname, val, vallen);
+	hostname[vallen] = 0;
+
+	err = _rpc_get_default_domain(&domain);	/* change to rpc */
+	if (err)
+		return (0);
+
+	if (strcmp(val2 + 1, domain))
+		return (0);	/* wrong domain */
+	else
+		return (1);
+}
+
+/*
+ * reads the file /etc/netid looking for a + to optionally go to the
+ * network information service.
+ */
+int
+getnetid(
+	char *key, 
+	char *ret)
+{
+	char            buf[1024];	/* big enough */
+	char           *res;
+	char           *mkey;
+	char           *mval;
+	FILE           *fd;
+#ifdef YP
+	char           *domain;
+	int             err;
+	char           *lookup;
+	int             len;
+#endif
+
+	fd = fopen(NETIDFILE, "r");
+	if (fd == (FILE *) 0) {
+#ifdef YP
+		res = "+";
+		goto getnetidyp;
+#else
+		return (0);
+#endif
+	}
+	for (;;) {
+		if (fd == (FILE *) 0)
+			return (0);	/* getnetidyp brings us here */
+		res = fgets(buf, 1024, fd);
+		if (res == 0) {
+			fclose(fd);
+			return (0);
+		}
+		if (res[0] == '#')
+			continue;
+		else if (res[0] == '+') {
+#ifdef YP
+	getnetidyp:
+			err = yp_get_default_domain(&domain);
+			if (err) {
+				continue;
+			}
+			lookup = NULL;
+			err = yp_match(domain, NETID, key,
+				strlen(key), &lookup, &len);
+			if (err) {
+#ifdef DEBUG
+				fprintf(stderr, "match failed error %d\n", err);
+#endif
+				continue;
+			}
+			lookup[len] = 0;
+			strcpy(ret, lookup);
+			free(lookup);
+			if (fd != NULL)
+				fclose(fd);
+			return (2);
+#else	/* YP */
+#ifdef DEBUG
+			fprintf(stderr,
+"Bad record in %s '+' -- NIS not supported in this library copy\n",
+				NETIDFILE);
+#endif
+			continue;
+#endif	/* YP */
+		} else {
+			mkey = strtok(buf, "\t ");
+			if (mkey == NULL) {
+				fprintf(stderr,
+		"Bad record in %s -- %s", NETIDFILE, buf);
+				continue;
+			}
+			mval = strtok(NULL, " \t#\n");
+			if (mval == NULL) {
+				fprintf(stderr,
+		"Bad record in %s val problem - %s", NETIDFILE, buf);
+				continue;
+			}
+			if (strcmp(mkey, key) == 0) {
+				strcpy(ret, mval);
+				fclose(fd);
+				return (1);
+
+			}
+		}
+	}
+}
diff --git a/services/librpc/src/rpc/pmap_clnt.c b/services/librpc/src/rpc/pmap_clnt.c
new file mode 100644
index 0000000..7c02867
--- /dev/null
+++ b/services/librpc/src/rpc/pmap_clnt.c
@@ -0,0 +1,151 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)pmap_clnt.c 1.37 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)pmap_clnt.c	2.2 88/08/01 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/pmap_clnt.c,v 1.11 2000/01/27 23:06:39 jasone Exp $";
+#endif
+
+/*
+ * pmap_clnt.c
+ * Client interface to pmap rpc service.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <unistd.h>
+#include <rpc/rpc.h>
+#include <rpc/pmap_prot.h>
+#include <rpc/pmap_clnt.h>
+#include <netinet/in.h>
+
+static struct timeval timeout = { 5, 0 };
+static struct timeval tottimeout = { 60, 0 };
+
+#ifndef PORTMAPSOCK
+#define PORTMAPSOCK "/var/run/portmapsock"
+#endif
+
+/*
+ * Set a mapping between program,version and port.
+ * Calls the pmap service remotely to do the mapping.
+ */
+bool_t
+pmap_set(
+	u_long program,
+	u_long version,
+	int protocol,
+	int port)    /* was u_short but changed to match prototype */
+{
+	struct sockaddr_in myaddress;
+	int socket = -1;
+	CLIENT *client;
+	struct pmap parms;
+	bool_t rslt;
+	struct stat st;
+
+	/*
+	 * Temporary hack for backwards compatibility. Eventually
+	 * this test will go away and we'll use only the "unix" transport.
+	 */
+	if (stat(PORTMAPSOCK, &st) == 0 && st.st_mode & S_IFSOCK)
+		client = clnt_create(PORTMAPSOCK, PMAPPROG, PMAPVERS, "unix");
+	else  {
+		if (get_myaddress(&myaddress) != 0)
+			return (FALSE);
+		myaddress.sin_addr.s_addr = htonl(INADDR_LOOPBACK);
+		client = clntudp_bufcreate(&myaddress, PMAPPROG, PMAPVERS,
+	    		timeout, &socket, RPCSMALLMSGSIZE, RPCSMALLMSGSIZE);
+	}
+
+	if (client == (CLIENT *)NULL)
+		return (FALSE);
+	parms.pm_prog = program;
+	parms.pm_vers = version;
+	parms.pm_prot = protocol;
+	parms.pm_port = port;
+	if (CLNT_CALL(client, PMAPPROC_SET, (xdrproc_t)xdr_pmap, &parms, (xdrproc_t)xdr_bool, &rslt,
+	    tottimeout) != RPC_SUCCESS) {
+		clnt_perror(client, "Cannot register service");
+		return (FALSE);
+	}
+	CLNT_DESTROY(client);
+	if (socket != -1)
+		(void)_RPC_close(socket);
+	return (rslt);
+}
+
+/*
+ * Remove the mapping between program, version and port.
+ * Calls the pmap service remotely to do the un-mapping.
+ */
+bool_t
+pmap_unset(
+	u_long program,
+	u_long version)
+{
+	struct sockaddr_in myaddress;
+	int socket = -1;
+	register CLIENT *client;
+	struct pmap parms;
+	bool_t rslt;
+	struct stat st;
+
+	/*
+	 * Temporary hack for backwards compatibility. Eventually
+	 * this test will go away and we'll use only the "unix" transport.
+	 */
+	if (stat(PORTMAPSOCK, &st) == 0 && st.st_mode & S_IFSOCK)
+		client = clnt_create(PORTMAPSOCK, PMAPPROG, PMAPVERS, "unix");
+	else {
+		if (get_myaddress(&myaddress) != 0)
+			return (FALSE);
+		myaddress.sin_addr.s_addr = htonl(INADDR_LOOPBACK);
+		client = clntudp_bufcreate(&myaddress, PMAPPROG, PMAPVERS,
+	    		timeout, &socket, RPCSMALLMSGSIZE, RPCSMALLMSGSIZE);
+	}
+	if (client == (CLIENT *)NULL)
+		return (FALSE);
+	parms.pm_prog = program;
+	parms.pm_vers = version;
+	parms.pm_port = parms.pm_prot = 0;
+	CLNT_CALL(client, PMAPPROC_UNSET, (xdrproc_t)xdr_pmap, &parms, (xdrproc_t)xdr_bool, &rslt,
+	    tottimeout);
+	CLNT_DESTROY(client);
+	if (socket != -1)
+		(void)_RPC_close(socket);
+	return (rslt);
+}
diff --git a/services/librpc/src/rpc/pmap_getmaps.c b/services/librpc/src/rpc/pmap_getmaps.c
new file mode 100644
index 0000000..b284b57
--- /dev/null
+++ b/services/librpc/src/rpc/pmap_getmaps.c
@@ -0,0 +1,92 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)pmap_getmaps.c 1.10 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)pmap_getmaps.c	2.2 88/08/01 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/pmap_getmaps.c,v 1.11 2000/01/27 23:06:39 jasone Exp $";
+#endif
+
+/*
+ * pmap_getmap.c
+ * Client interface to pmap rpc service.
+ * contains pmap_getmaps, which is only tcp service involved
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <rpc/rpc.h>
+#include <rpc/pmap_prot.h>
+#include <rpc/pmap_clnt.h>
+#include <sys/socket.h>
+#include <netdb.h>
+#include <stdio.h>
+#include <unistd.h>
+#include <errno.h>
+#include <sys/mbuf.h>
+#include <net/if.h>
+#include <sys/ioctl.h>
+#define NAMELEN 255
+#define MAX_BROADCAST_SIZE 1400
+
+/*
+ * Get a copy of the current port maps.
+ * Calls the pmap service remotely to do get the maps.
+ */
+struct pmaplist *
+pmap_getmaps(struct sockaddr_in *address)
+{
+	struct pmaplist *head = NULL;
+	int socket = -1;
+	struct timeval minutetimeout;
+	CLIENT *client;
+
+	minutetimeout.tv_sec = 60;
+	minutetimeout.tv_usec = 0;
+	address->sin_port = htons(PMAPPORT);
+	client = clnttcp_create(address, PMAPPROG,
+	    PMAPVERS, &socket, 50, 500);
+	if (client != NULL) {
+		if (CLNT_CALL(client, (rpcproc_t)PMAPPROC_DUMP, 
+		    (xdrproc_t)xdr_void, NULL,
+		    (xdrproc_t)xdr_pmaplist, &head, minutetimeout) !=
+		    RPC_SUCCESS) {
+			clnt_perror(client, "pmap_getmaps rpc problem");
+		}
+		CLNT_DESTROY(client);
+	}
+	if (socket != -1)
+		(void)_RPC_close(socket);
+	address->sin_port = 0;
+	return (head);
+}
diff --git a/services/librpc/src/rpc/pmap_getport.c b/services/librpc/src/rpc/pmap_getport.c
new file mode 100644
index 0000000..c75b4d5
--- /dev/null
+++ b/services/librpc/src/rpc/pmap_getport.c
@@ -0,0 +1,98 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)pmap_getport.c 1.9 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)pmap_getport.c	2.2 88/08/01 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/pmap_getport.c,v 1.10 2000/01/27 23:06:40 jasone Exp $";
+#endif
+
+/*
+ * pmap_getport.c
+ * Client interface to pmap rpc service.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <rpc/rpc.h>
+#include <rpc/pmap_prot.h>
+#include <rpc/pmap_clnt.h>
+#include <sys/socket.h>
+#include <sys/mbuf.h>
+#include <net/if.h>
+#include <unistd.h>
+
+static const struct timeval timeout = { 5, 0 };
+static const struct timeval tottimeout = { 60, 0 };
+
+/*
+ * Find the mapped port for program,version.
+ * Calls the pmap service remotely to do the lookup.
+ * Returns 0 if no map exists.
+ */
+u_short
+pmap_getport(
+	struct sockaddr_in *address,
+	u_long program,
+	u_long version,
+	u_int protocol )
+{
+	u_short port = 0;
+	int socket = -1;
+	CLIENT *client;
+	struct pmap parms;
+
+	address->sin_port = htons(PMAPPORT);
+	client = clntudp_bufcreate(address, PMAPPROG,
+	    PMAPVERS, timeout, &socket, RPCSMALLMSGSIZE, RPCSMALLMSGSIZE);
+	if (client != NULL) {
+		parms.pm_prog = program;
+		parms.pm_vers = version;
+		parms.pm_prot = protocol;
+		parms.pm_port = 0;  /* not needed or used */
+		if (CLNT_CALL(client, (rpcproc_t)PMAPPROC_GETPORT,
+		    (xdrproc_t)xdr_pmap,
+		    &parms, (xdrproc_t)xdr_u_short, &port, tottimeout) !=
+		    RPC_SUCCESS){
+			rpc_createerr.cf_stat = RPC_PMAPFAILURE;
+			clnt_geterr(client, &rpc_createerr.cf_error);
+		} else if (port == 0) {
+			rpc_createerr.cf_stat = RPC_PROGNOTREGISTERED;
+		}
+		CLNT_DESTROY(client);
+	}
+	if (socket != -1)
+		(void)_RPC_close(socket);
+	address->sin_port = 0;
+	return (port);
+}
diff --git a/services/librpc/src/rpc/pmap_prot.c b/services/librpc/src/rpc/pmap_prot.c
new file mode 100644
index 0000000..30aedce
--- /dev/null
+++ b/services/librpc/src/rpc/pmap_prot.c
@@ -0,0 +1,63 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)pmap_prot.c 1.17 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)pmap_prot.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/pmap_prot.c,v 1.6 1999/08/28 00:00:42 peter Exp $";
+#endif
+
+/*
+ * pmap_prot.c
+ * Protocol for the local binder service, or pmap.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <rpc/types.h>
+#include <rpc/xdr.h>
+#include <rpc/pmap_prot.h>
+
+
+bool_t
+xdr_pmap(
+	XDR *xdrs,
+	struct pmap *regs)
+{
+
+	if (xdr_u_long(xdrs, &regs->pm_prog) &&
+		xdr_u_long(xdrs, &regs->pm_vers) &&
+		xdr_u_long(xdrs, &regs->pm_prot))
+		return (xdr_u_long(xdrs, &regs->pm_port));
+	return (FALSE);
+}
diff --git a/services/librpc/src/rpc/pmap_prot2.c b/services/librpc/src/rpc/pmap_prot2.c
new file mode 100644
index 0000000..208c8a4
--- /dev/null
+++ b/services/librpc/src/rpc/pmap_prot2.c
@@ -0,0 +1,122 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)pmap_prot2.c 1.3 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)pmap_prot2.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/pmap_prot2.c,v 1.7 1999/08/28 00:00:42 peter Exp $";
+#endif
+
+/*
+ * pmap_prot2.c
+ * Protocol for the local binder service, or pmap.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <rpc/types.h>
+#include <rpc/xdr.h>
+#include <rpc/pmap_prot.h>
+
+
+/*
+ * What is going on with linked lists? (!)
+ * First recall the link list declaration from pmap_prot.h:
+ *
+ * struct pmaplist {
+ *	struct pmap pml_map;
+ *	struct pmaplist *pml_map;
+ * };
+ *
+ * Compare that declaration with a corresponding xdr declaration that
+ * is (a) pointer-less, and (b) recursive:
+ *
+ * typedef union switch (bool_t) {
+ *
+ *	case TRUE: struct {
+ *		struct pmap;
+ * 		pmaplist_t foo;
+ *	};
+ *
+ *	case FALSE: struct {};
+ * } pmaplist_t;
+ *
+ * Notice that the xdr declaration has no nxt pointer while
+ * the C declaration has no bool_t variable.  The bool_t can be
+ * interpreted as ``more data follows me''; if FALSE then nothing
+ * follows this bool_t; if TRUE then the bool_t is followed by
+ * an actual struct pmap, and then (recursively) by the
+ * xdr union, pamplist_t.
+ *
+ * This could be implemented via the xdr_union primitive, though this
+ * would cause a one recursive call per element in the list.  Rather than do
+ * that we can ``unwind'' the recursion
+ * into a while loop and do the union arms in-place.
+ *
+ * The head of the list is what the C programmer wishes to past around
+ * the net, yet is the data that the pointer points to which is interesting;
+ * this sounds like a job for xdr_reference!
+ */
+bool_t
+xdr_pmaplist(
+	XDR *xdrs,
+	struct pmaplist **rp)
+{
+	/*
+	 * more_elements is pre-computed in case the direction is
+	 * XDR_ENCODE or XDR_FREE.  more_elements is overwritten by
+	 * xdr_bool when the direction is XDR_DECODE.
+	 */
+	bool_t more_elements;
+	register int freeing = (xdrs->x_op == XDR_FREE);
+	register struct pmaplist **next = NULL;
+
+	while (TRUE) {
+		more_elements = (bool_t)(*rp != NULL);
+		if (! xdr_bool(xdrs, &more_elements))
+			return (FALSE);
+		if (! more_elements)
+			return (TRUE);  /* we are done */
+		/*
+		 * the unfortunate side effect of non-recursion is that in
+		 * the case of freeing we must remember the next object
+		 * before we free the current object ...
+		 */
+		if (freeing)
+			next = &((*rp)->pml_next);
+		if (! xdr_reference(xdrs, (caddr_t *)rp,
+		    (u_int)sizeof(struct pmaplist), (xdrproc_t) xdr_pmap))
+			return (FALSE);
+		rp = (freeing) ? next : &((*rp)->pml_next);
+	}
+}
diff --git a/services/librpc/src/rpc/pmap_rmt.c b/services/librpc/src/rpc/pmap_rmt.c
new file mode 100644
index 0000000..1ab72b2
--- /dev/null
+++ b/services/librpc/src/rpc/pmap_rmt.c
@@ -0,0 +1,441 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)pmap_rmt.c 1.21 87/08/27 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)pmap_rmt.c	2.2 88/08/01 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/pmap_rmt.c,v 1.15 2000/01/27 23:06:40 jasone Exp $";
+#endif
+
+/*
+ * pmap_rmt.c
+ * Client interface to pmap rpc service.
+ * remote call and broadcast service
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <sys/ioctl.h>
+#include <sys/socket.h>
+
+#include <net/if.h>
+#include <netinet/in.h>
+#include <arpa/inet.h>
+
+#include <assert.h>
+#include <errno.h>
+#include <stdio.h>
+#include <string.h>
+#include <unistd.h>
+
+#include <rpc/rpc.h>
+#include <rpc/pmap_prot.h>
+#include <rpc/pmap_clnt.h>
+#include <rpc/pmap_rmt.h>
+
+#include <stdlib.h>
+#include <sys/select.h>
+
+#define MAX_BROADCAST_SIZE 1400
+
+static const struct timeval timeout = { 3, 0 };
+
+/*
+ * pmapper remote-call-service interface.
+ * This routine is used to call the pmapper remote call service
+ * which will look up a service program in the port maps, and then
+ * remotely call that routine with the given parameters.  This allows
+ * programs to do a lookup and call in one step.
+*/
+enum clnt_stat
+pmap_rmtcall(
+	struct sockaddr_in *addr,
+	u_long prog,
+	u_long vers,
+	u_long proc,
+	xdrproc_t xdrargs,
+	caddr_t argsp,
+	xdrproc_t xdrres,
+	caddr_t resp,
+	struct timeval tout,
+	u_long *port_ptr)
+{
+	int sock = -1;
+	CLIENT *client;
+	struct rmtcallargs a;
+	struct rmtcallres r;
+	enum clnt_stat stat;
+
+	assert(addr != NULL);
+	assert(port_ptr != NULL);
+
+	addr->sin_port = htons(PMAPPORT);
+	client = clntudp_create(addr, PMAPPROG, PMAPVERS, timeout, &sock);
+	if (client != NULL) {
+		a.prog = prog;
+		a.vers = vers;
+		a.proc = proc;
+		a.args_ptr = argsp;
+		a.xdr_args = xdrargs;
+		r.port_ptr = port_ptr;
+		r.results_ptr = resp;
+		r.xdr_results = xdrres;
+		stat = CLNT_CALL(client, (rpcproc_t)PMAPPROC_CALLIT,
+		    (xdrproc_t)xdr_rmtcall_args, &a, (xdrproc_t)xdr_rmtcallres, 
+		    &r, tout);
+		CLNT_DESTROY(client);
+	} else {
+		stat = RPC_FAILED;
+	}
+	if (sock != -1)
+		(void)_RPC_close(sock);
+	addr->sin_port = 0;
+	return (stat);
+}
+
+
+/*
+ * XDR remote call arguments
+ * written for XDR_ENCODE direction only
+ */
+bool_t
+xdr_rmtcall_args(
+	XDR *xdrs,
+	struct rmtcallargs *cap)
+{
+	u_int lenposition, argposition, position;
+
+	assert(xdrs != NULL);
+	assert(cap != NULL);
+
+	if (xdr_u_long(xdrs, &(cap->prog)) &&
+	    xdr_u_long(xdrs, &(cap->vers)) &&
+	    xdr_u_long(xdrs, &(cap->proc))) {
+		lenposition = XDR_GETPOS(xdrs);
+		if (! xdr_u_long(xdrs, &(cap->arglen)))
+		    return (FALSE);
+		argposition = XDR_GETPOS(xdrs);
+		if (! (*(cap->xdr_args))(xdrs, cap->args_ptr))
+		    return (FALSE);
+		position = XDR_GETPOS(xdrs);
+		cap->arglen = (u_long)position - (u_long)argposition;
+		XDR_SETPOS(xdrs, lenposition);
+		if (! xdr_u_long(xdrs, &(cap->arglen)))
+		    return (FALSE);
+		XDR_SETPOS(xdrs, position);
+		return (TRUE);
+	}
+	return (FALSE);
+}
+
+/*
+ * XDR remote call results
+ * written for XDR_DECODE direction only
+ */
+bool_t
+xdr_rmtcallres(
+	XDR *xdrs,
+	struct rmtcallres *crp)
+{
+	caddr_t port_ptr;
+
+	assert(xdrs != NULL);
+	assert(crp != NULL);
+
+	port_ptr = (caddr_t)(void *)crp->port_ptr;
+	if (xdr_reference(xdrs, &port_ptr, sizeof (u_long),
+	    (xdrproc_t)xdr_u_long) && xdr_u_long(xdrs, &crp->resultslen)) {
+		crp->port_ptr = (u_long *)(void *)port_ptr;
+		return ((*(crp->xdr_results))(xdrs, crp->results_ptr));
+	}
+	return (FALSE);
+}
+
+
+/*
+ * The following is kludged-up support for simple rpc broadcasts.
+ * Someday a large, complicated system will replace these trivial
+ * routines which only support udp/ip .
+ */
+
+static int
+getbroadcastnets(
+	struct in_addr *addrs,
+	int sock,  /* any valid socket will do */
+	char *buf  /* why allocxate more when we can use existing... */  )
+{
+	struct ifconf ifc;
+	struct ifreq ifreq, *ifr;
+	struct sockaddr_in *sin;
+	struct	in_addr addr;
+	char *cp, *cplim;
+	int n, i = 0;
+
+        ifc.ifc_len = UDPMSGSIZE;
+        ifc.ifc_buf = buf;
+        if (ioctl(sock, SIOCGIFCONF, (char *)&ifc) < 0) {
+                perror("broadcast: ioctl (get interface configuration)");
+                return (0);
+        }
+#define max(a, b) (a > b ? a : b)
+#define size(p)	max((p).sa_len, sizeof(p))
+	cplim = buf + ifc.ifc_len; /*skip over if's with big ifr_addr's */
+	for (cp = buf; cp < cplim;
+			cp += sizeof (ifr->ifr_name) + size(ifr->ifr_addr)) {
+		ifr = (struct ifreq *)cp;
+		if (ifr->ifr_addr.sa_family != AF_INET)
+			continue;
+		ifreq = *ifr;
+                if (ioctl(sock, SIOCGIFFLAGS, (char *)&ifreq) < 0) {
+                        perror("broadcast: ioctl (get interface flags)");
+                        continue;
+                }
+                if ((ifreq.ifr_flags & IFF_BROADCAST) &&
+		    (ifreq.ifr_flags & IFF_UP)) {
+			sin = (struct sockaddr_in *)&ifr->ifr_addr;
+#ifdef SIOCGIFBRDADDR   /* 4.3BSD */
+			if (ioctl(sock, SIOCGIFBRDADDR, (char *)&ifreq) < 0) {
+				addr =
+				    inet_makeaddr(inet_netof(sin->sin_addr),
+				    INADDR_ANY);
+			} else {
+				addr = ((struct sockaddr_in*)
+				  &ifreq.ifr_addr)->sin_addr;
+			}
+#else /* 4.2 BSD */
+			addr = inet_makeaddr(inet_netof(sin->sin_addr),
+			    INADDR_ANY);
+#endif
+			for (n=i-1; n>=0; n--) {
+				if (addr.s_addr == addrs[n].s_addr)
+					break;
+			}
+			if (n<0) {
+				addrs[i++] = addr;
+			}
+		}
+	}
+	return (i);
+}
+
+typedef bool_t (*resultproc_t)(caddr_t, struct sockaddr_in *);
+
+enum clnt_stat
+clnt_broadcast(
+	u_long		prog,		/* program number */
+	u_long		vers,		/* version number */
+	u_long		proc,		/* procedure number */
+	xdrproc_t	xargs,		/* xdr routine for args */
+	caddr_t		argsp,		/* pointer to args */
+	xdrproc_t	xresults,	/* xdr routine for results */
+	caddr_t		resultsp,	/* pointer to results */
+	resultproc_t	eachresult	/* call with each result obtained */ )
+{
+	enum clnt_stat stat = RPC_SUCCESS; /* to avoid warning */
+	AUTH *unix_auth = authunix_create_default();
+	XDR xdr_stream;
+	register XDR *xdrs = &xdr_stream;
+	int outlen, inlen, nets;
+	socklen_t fromlen;
+	register int sock;
+	int on = 1;
+	fd_set *fds = 0, readfds; /* initialized to avoid warning */
+	register int i;
+	bool_t done = FALSE;
+	register u_long xid;
+	u_long port;
+	struct in_addr addrs[20];
+	struct sockaddr_in baddr, raddr; /* broadcast and response addresses */
+	struct rmtcallargs a;
+	struct rmtcallres r;
+	struct rpc_msg msg;
+	struct timeval t, tv;
+	char outbuf[MAX_BROADCAST_SIZE], inbuf[UDPMSGSIZE];
+	static uintptr_t disrupt;
+
+	if (disrupt == 0)
+		disrupt = (uintptr_t) resultsp;
+
+	/*
+	 * initialization: create a socket, a broadcast address, and
+	 * preserialize the arguments into a send buffer.
+	 */
+	if ((sock = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP)) < 0) {
+		perror("Cannot create socket for broadcast rpc");
+		stat = RPC_CANTSEND;
+		goto done_broad;
+	}
+#ifdef SO_BROADCAST
+	if (setsockopt(sock, SOL_SOCKET, SO_BROADCAST, &on, sizeof (on)) < 0) {
+		perror("Cannot set socket option SO_BROADCAST");
+		stat = RPC_CANTSEND;
+		goto done_broad;
+	}
+#endif /* def SO_BROADCAST */
+	if (sock + 1 > FD_SETSIZE) {
+		int bytes = howmany(sock + 1, NFDBITS) * sizeof(fd_mask);
+		fds = (fd_set *)malloc(bytes);
+		if (fds == NULL) {
+			stat = RPC_CANTSEND;
+			goto done_broad;
+		}
+		memset(fds, 0, bytes);
+	} else {
+		fds = &readfds;
+		FD_ZERO(fds);
+	}
+
+	nets = getbroadcastnets(addrs, sock, inbuf);
+	memset(&baddr, 0, sizeof (baddr));
+	baddr.sin_len = sizeof(struct sockaddr_in);
+	baddr.sin_family = AF_INET;
+	baddr.sin_port = htons(PMAPPORT);
+	baddr.sin_addr.s_addr = htonl(INADDR_ANY);
+	(void)gettimeofday(&t, (struct timezone *)0);
+	msg.rm_xid = xid = (++disrupt) ^ getpid() ^ t.tv_sec ^ t.tv_usec;
+	t.tv_usec = 0;
+	msg.rm_direction = CALL;
+	msg.rm_call.cb_rpcvers = RPC_MSG_VERSION;
+	msg.rm_call.cb_prog = PMAPPROG;
+	msg.rm_call.cb_vers = PMAPVERS;
+	msg.rm_call.cb_proc = PMAPPROC_CALLIT;
+	msg.rm_call.cb_cred = unix_auth->ah_cred;
+	msg.rm_call.cb_verf = unix_auth->ah_verf;
+	a.prog = prog;
+	a.vers = vers;
+	a.proc = proc;
+	a.xdr_args = xargs;
+	a.args_ptr = argsp;
+	r.port_ptr = &port;
+	r.xdr_results = xresults;
+	r.results_ptr = resultsp;
+	xdrmem_create(xdrs, outbuf, MAX_BROADCAST_SIZE, XDR_ENCODE);
+	if ((! xdr_callmsg(xdrs, &msg)) || (! xdr_rmtcall_args(xdrs, &a))) {
+		stat = RPC_CANTENCODEARGS;
+		goto done_broad;
+	}
+	outlen = (int)xdr_getpos(xdrs);
+	xdr_destroy(xdrs);
+	/*
+	 * Basic loop: broadcast a packet and wait a while for response(s).
+	 * The response timeout grows larger per iteration.
+	 *
+	 * XXX This will loop about 5 times the stop. If there are
+	 * lots of signals being received by the process it will quit
+	 * send them all in one quick burst, not paying attention to
+	 * the intended function of sending them slowly over half a
+	 * minute or so
+	 */
+	for (t.tv_sec = 4; t.tv_sec <= 14; t.tv_sec += 2) {
+		for (i = 0; i < nets; i++) {
+			baddr.sin_addr = addrs[i];
+			if (sendto(sock, outbuf, outlen, 0,
+				(struct sockaddr *)&baddr,
+				sizeof (struct sockaddr)) != outlen) {
+				perror("Cannot send broadcast packet");
+				stat = RPC_CANTSEND;
+				goto done_broad;
+			}
+		}
+		if (eachresult == NULL) {
+			stat = RPC_SUCCESS;
+			goto done_broad;
+		}
+	recv_again:
+		msg.acpted_rply.ar_verf = _null_auth;
+		msg.acpted_rply.ar_results.where = (caddr_t)&r;
+		msg.acpted_rply.ar_results.proc = (xdrproc_t) xdr_rmtcallres;
+		/* XXX we know the other bits are still clear */
+		FD_SET(sock, fds);
+		tv = t;		/* for select() that copies back */
+		switch (select(sock + 1, fds, NULL, NULL, &tv)) {
+
+		case 0:  /* timed out */
+			stat = RPC_TIMEDOUT;
+			continue;
+
+		case -1:  /* some kind of error */
+			if (errno == EINTR)
+				goto recv_again;
+			perror("Broadcast select problem");
+			stat = RPC_CANTRECV;
+			goto done_broad;
+
+		}  /* end of select results switch */
+	try_again:
+		fromlen = sizeof(struct sockaddr);
+		inlen = recvfrom(sock, inbuf, UDPMSGSIZE, 0,
+			(struct sockaddr *)&raddr, &fromlen);
+		if (inlen < 0) {
+			if (errno == EINTR)
+				goto try_again;
+			perror("Cannot receive reply to broadcast");
+			stat = RPC_CANTRECV;
+			goto done_broad;
+		}
+		if (inlen < sizeof(u_int32_t))
+			goto recv_again;
+		/*
+		 * see if reply transaction id matches sent id.
+		 * If so, decode the results.
+		 */
+		xdrmem_create(xdrs, inbuf, (u_int)inlen, XDR_DECODE);
+		if (xdr_replymsg(xdrs, &msg)) {
+			if ((msg.rm_xid == xid) &&
+				(msg.rm_reply.rp_stat == MSG_ACCEPTED) &&
+				(msg.acpted_rply.ar_stat == SUCCESS)) {
+				raddr.sin_port = htons((u_short)port);
+				done = (*eachresult)(resultsp, &raddr);
+			}
+			/* otherwise, we just ignore the errors ... */
+		}
+		xdrs->x_op = XDR_FREE;
+		msg.acpted_rply.ar_results.proc = (xdrproc_t) xdr_void;
+		(void)xdr_replymsg(xdrs, &msg);
+		(void)(*xresults)(xdrs, resultsp);
+		xdr_destroy(xdrs);
+		if (done) {
+			stat = RPC_SUCCESS;
+			goto done_broad;
+		} else {
+			goto recv_again;
+		}
+	}
+done_broad:
+	if (fds != &readfds)
+		free(fds);
+	if (sock >= 0)
+		(void)_RPC_close(sock);
+	AUTH_DESTROY(unix_auth);
+	return (stat);
+}
diff --git a/services/librpc/src/rpc/publickey.3 b/services/librpc/src/rpc/publickey.3
new file mode 100644
index 0000000..29094f9
--- /dev/null
+++ b/services/librpc/src/rpc/publickey.3
@@ -0,0 +1,47 @@
+.\" @(#)publickey.3r	2.1 88/08/07 4.0 RPCSRC
+.\" $FreeBSD: src/lib/libc/rpc/publickey.3,v 1.4 2000/03/02 09:13:46 sheldonh Exp $
+.\"
+.TH PUBLICKEY 3R  "6 October 1987"
+.SH NAME
+publickey, getpublickey, getsecretkey \- get public or secret key
+.SH SYNOPSIS
+.nf
+.B #include <rpc/rpc.h>
+.B #include <rpc/key_prot.h>
+.LP
+.B getpublickey(netname, publickey)
+.B	char netname[\s-1MAXNETNAMELEN\s0+1];
+.B	char publickey[\s-1HEXKEYBYTES\s0+1];
+.LP
+.B getsecretkey(netname, secretkey, passwd)
+.B	char netname[\s-1MAXNETNAMELEN\s0+1];
+.B	char secretkey[\s-1HEXKEYBYTES\s0+1];
+.B	char *passwd;
+.fi
+.SH DESCRIPTION
+.IX "getpublickey function" "" "\fLgetpublickey()\fP function"
+.IX "getsecretkey function" "" "\fLgetsecretkey()\fP function"
+These routines are used to get public and secret keys from the
+.SM YP
+database.
+.B getsecretkey(\|)
+has an extra argument,
+.IR passwd ,
+which is used to decrypt the encrypted secret key stored in the database.
+Both routines return 1 if they are successful in finding the key, 0 otherwise.
+The keys are returned as
+.SM NULL\s0-terminated,
+hexadecimal strings.
+If the password supplied to
+.B getsecretkey(\|)
+fails to decrypt the secret key, the routine will return 1 but the
+.I secretkey
+argument will be a
+.SM NULL
+string (``'').
+.SH "SEE ALSO"
+.BR publickey (5)
+.LP
+.I \s-1RPC\s0 Programmer's Manual
+in
+.TX NETP
diff --git a/services/librpc/src/rpc/publickey.5 b/services/librpc/src/rpc/publickey.5
new file mode 100644
index 0000000..9f7a325
--- /dev/null
+++ b/services/librpc/src/rpc/publickey.5
@@ -0,0 +1,38 @@
+.\" $FreeBSD: src/lib/libc/rpc/publickey.5,v 1.5 2000/03/02 09:13:46 sheldonh Exp $
+.\" @(#)publickey.5	2.1 88/08/07 4.0 RPCSRC; from 1.6 88/02/29 SMI;
+.TH PUBLICKEY 5 "19 October 1987"
+.SH NAME
+publickey \- public key database
+.SH SYNOPSIS
+.B /etc/publickey
+.SH DESCRIPTION
+.LP
+.B /etc/publickey
+is the public key database used for secure
+networking.
+Each entry in
+the database consists of a network user
+name (which may either refer to
+a user or a hostname), followed by the user's
+public key (in hex
+notation), a colon, and then the user's
+secret key encrypted with
+its login password (also in hex notation).
+.LP
+This file is altered either by the user through the
+.BR chkey (1)
+command or by the system administrator through the
+.BR newkey (8)
+command.
+The file
+.B /etc/publickey
+should only contain data on the NIS master machine, where it
+is converted into the
+.SM NIS
+database
+.BR publickey.byname .
+.SH SEE ALSO
+.BR chkey (1),
+.BR publickey (3R),
+.BR newkey (8),
+.BR ypupdated (8C)
diff --git a/services/librpc/src/rpc/rpc.3 b/services/librpc/src/rpc/rpc.3
new file mode 100644
index 0000000..f40b643
--- /dev/null
+++ b/services/librpc/src/rpc/rpc.3
@@ -0,0 +1,1767 @@
+.\" @(#)rpc.3n	2.4 88/08/08 4.0 RPCSRC; from 1.19 88/06/24 SMI
+.\" $FreeBSD: src/lib/libc/rpc/rpc.3,v 1.11 2000/03/02 09:13:47 sheldonh Exp $
+.\"
+.TH RPC 3 "16 February 1988"
+.SH NAME
+rpc \- library routines for remote procedure calls
+.SH SYNOPSIS AND DESCRIPTION
+These routines allow C programs to make procedure
+calls on other machines across the network.
+First, the client calls a procedure to send a
+data packet to the server.
+Upon receipt of the packet, the server calls a dispatch routine
+to perform the requested service, and then sends back a
+reply.
+Finally, the procedure call returns to the client.
+.LP
+Routines that are used for Secure RPC (DES authentication) are described in
+.BR rpc_secure (3).
+Secure RPC can be used only if DES encryption is available.
+.LP
+.ft B
+.nf
+.sp .5
+#include <rpc/rpc.h>
+.fi
+.ft R
+.br
+.if t .ne 8
+.LP
+.ft B
+.nf
+.sp .5
+void
+auth_destroy(auth)
+\s-1AUTH\s0 *auth;
+.fi
+.ft R
+.IP
+A macro that destroys the authentication information associated with
+.IR auth .
+Destruction usually involves deallocation of private data
+structures.
+The use of
+.I auth
+is undefined after calling
+.BR auth_destroy(\|) .
+.br
+.if t .ne 6
+.LP
+.ft B
+.nf
+.sp .5
+\s-1AUTH\s0 *
+authnone_create(\|)
+.fi
+.ft R
+.IP
+Create and returns an
+.SM RPC
+authentication handle that passes nonusable authentication
+information with each remote procedure call.
+This is the
+default authentication used by
+.SM RPC.
+.if t .ne 10
+.LP
+.ft B
+.nf
+.sp .5
+\s-1AUTH\s0 *
+authunix_create(host, uid, gid, len, aup_gids)
+char *host;
+int uid, gid, len, *aup.gids;
+.fi
+.ft R
+.IP
+Create and return an
+.SM RPC
+authentication handle that contains
+.UX
+authentication information.
+The parameter
+.I host
+is the name of the machine on which the information was
+created;
+.I uid
+is the user's user
+.SM ID ;
+.I gid
+is the user's current group
+.SM ID ;
+.I len
+and
+.I aup_gids
+refer to a counted array of groups to which the user belongs.
+It is easy to impersonate a user.
+.br
+.if t .ne 5
+.LP
+.ft B
+.nf
+.sp .5
+\s-1AUTH\s0 *
+authunix_create_default(\|)
+.fi
+.ft R
+.IP
+Calls
+.B authunix_create(\|)
+with the appropriate parameters.
+.br
+.if t .ne 13
+.LP
+.ft B
+.nf
+.sp .5
+callrpc(host, prognum, versnum, procnum, inproc, in, outproc, out)
+char *host;
+u_long prognum, versnum, procnum;
+char *in, *out;
+xdrproc_t inproc, outproc;
+.fi
+.ft R
+.IP
+Call the remote procedure associated with
+.IR prognum ,
+.IR versnum ,
+and
+.I procnum
+on the machine,
+.IR host .
+The parameter
+.I in
+is the address of the procedure's argument(s), and
+.I out
+is the address of where to place the result(s);
+.I inproc
+is used to encode the procedure's parameters, and
+.I outproc
+is used to decode the procedure's results.
+This routine returns zero if it succeeds, or the value of
+.B "enum clnt_stat"
+cast to an integer if it fails.
+The routine
+.B clnt_perrno(\|)
+is handy for translating failure statuses into messages.
+.IP
+Warning: calling remote procedures with this routine
+uses
+.SM UDP/IP
+as a transport; see
+.B clntudp_create(\|)
+for restrictions.
+You do not have control of timeouts or authentication using
+this routine.
+.br
+.if t .ne 16
+.LP
+.ft B
+.nf
+.sp .5
+enum clnt_stat
+clnt_broadcast(prognum, versnum, procnum, inproc, in, outproc, out, eachresult)
+u_long prognum, versnum, procnum;
+char *in, *out;
+xdrproc_t inproc, outproc;
+resultproc_t eachresult;
+.fi
+.ft R
+.IP
+Like
+.BR callrpc(\|) ,
+except the call message is broadcast to all locally
+connected broadcast nets.
+Each time it receives a
+response, this routine calls
+.BR eachresult(\|) ,
+whose form is:
+.IP
+.RS 1i
+.ft B
+.nf
+eachresult(out, addr)
+char *out;
+struct sockaddr_in *addr;
+.ft R
+.fi
+.RE
+.IP
+where
+.I out
+is the same as
+.I out
+passed to
+.BR clnt_broadcast(\|) ,
+except that the remote procedure's output is decoded there;
+.I addr
+points to the address of the machine that sent the results.
+If
+.B eachresult(\|)
+returns zero,
+.B clnt_broadcast(\|)
+waits for more replies; otherwise it returns with appropriate
+status.
+.IP
+Warning: broadcast sockets are limited in size to the
+maximum transfer unit of the data link.
+For ethernet,
+this value is 1500 bytes.
+.br
+.if t .ne 13
+.LP
+.ft B
+.nf
+.sp .5
+enum clnt_stat
+clnt_call(clnt, procnum, inproc, in, outproc, out, tout)
+\s-1CLIENT\s0 *clnt;
+u_long
+procnum;
+xdrproc_t inproc, outproc;
+char *in, *out;
+struct timeval tout;
+.fi
+.ft R
+.IP
+A macro that calls the remote procedure
+.I procnum
+associated with the client handle,
+.IR clnt ,
+which is obtained with an
+.SM RPC
+client creation routine such as
+.BR clnt_create(\|) .
+The parameter
+.I in
+is the address of the procedure's argument(s), and
+.I out
+is the address of where to place the result(s);
+.I inproc
+is used to encode the procedure's parameters, and
+.I outproc
+is used to decode the procedure's results;
+.I tout
+is the time allowed for results to come back.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+clnt_destroy(clnt)
+\s-1CLIENT\s0 *clnt;
+.fi
+.ft R
+.IP
+A macro that destroys the client's
+.SM RPC
+handle.
+Destruction usually involves deallocation
+of private data structures, including
+.I clnt
+itself.  Use of
+.I clnt
+is undefined after calling
+.BR clnt_destroy(\|) .
+If the
+.SM RPC
+library opened the associated socket, it will close it also.
+Otherwise, the socket remains open.
+.br
+.if t .ne 10
+.LP
+.ft B
+.nf
+.sp .5
+\s-1CLIENT\s0 *
+clnt_create(host, prog, vers, proto)
+char *host;
+u_long prog, vers;
+char *proto;
+.fi
+.ft R
+.IP
+Generic client creation routine.
+.I host
+identifies the name of the remote host where the server
+is located.
+.I proto
+indicates which kind of transport protocol to use.
+The
+currently supported values for this field are \(lqudp\(rq
+and \(lqtcp\(rq.
+Default timeouts are set, but can be modified using
+.BR clnt_control(\|) .
+.IP
+Warning: Using
+.SM UDP
+has its shortcomings.  Since
+.SM UDP\s0-based
+.SM RPC
+messages can only hold up to 8 Kbytes of encoded data,
+this transport cannot be used for procedures that take
+large arguments or return huge results.
+.br
+.if t .ne 10
+.LP
+.ft B
+.nf
+.sp .5
+bool_t
+clnt_control(cl, req, info)
+\s-1CLIENT\s0 *cl;
+u_int req;
+char *info;
+.fi
+.ft R
+.IP
+A macro used to change or retrieve various information
+about a client object.
+.I req
+indicates the type of operation, and
+.I info
+is a pointer to the information.
+For both
+.SM UDP
+and
+.SM TCP\s0,
+the supported values of
+.I req
+and their argument types and what they do are:
+.IP
+.nf
+.ta +2.0i +2.0i +2.0i
+.SM CLSET_TIMEOUT\s0	struct timeval	set total timeout
+.SM CLGET_TIMEOUT\s0	struct timeval	get total timeout
+.fi
+.IP
+Note: if you set the timeout using
+.BR clnt_control(\|) ,
+the timeout parameter passed to
+.B clnt_call(\|)
+will be ignored in all future calls.
+.IP
+.nf
+.SM CLGET_SERVER_ADDR\s0	struct sockaddr_in 	get server's address
+.fi
+.br
+.IP
+The following operations are valid for
+.SM UDP
+only:
+.IP
+.nf
+.ta +2.0i ; +2.0i ; +2.0i
+.SM CLSET_RETRY_TIMEOUT\s0		struct timeval	set the retry timeout
+.SM CLGET_RETRY_TIMEOUT\s0		struct timeval	get the retry timeout
+.fi
+.br
+.IP
+The retry timeout is the time that
+.SM "UDP RPC"
+waits for the server to reply before
+retransmitting the request.
+.br
+.if t .ne 10
+.LP
+.ft B
+.nf
+.sp .5
+clnt_freeres(clnt, outproc, out)
+\s-1CLIENT\s0 *clnt;
+xdrproc_t outproc;
+char *out;
+.fi
+.ft R
+.IP
+A macro that frees any data allocated by the
+.SM RPC/XDR
+system when it decoded the results of an
+.SM RPC
+call.  The
+parameter
+.I out
+is the address of the results, and
+.I outproc
+is the
+.SM XDR
+routine describing the results.
+This routine returns one if the results were successfully
+freed,
+and zero otherwise.
+.br
+.if t .ne 6
+.LP
+.ft B
+.nf
+.sp .5
+void
+clnt_geterr(clnt, errp)
+\s-1CLIENT\s0 *clnt;
+struct rpc_err *errp;
+.fi
+.ft R
+.IP
+A macro that copies the error structure out of the client
+handle
+to the structure at address
+.IR errp .
+.br
+.if t .ne 8
+.LP
+.ft B
+.nf
+.sp .5
+void
+clnt_pcreateerror(s)
+char *s;
+.fi
+.ft R
+.IP
+Print a message to standard error indicating
+why a client
+.SM RPC
+handle could not be created.
+The message is prepended with string
+.I s
+and a colon.
+Used when a
+.BR clnt_create(\|) ,
+.BR clntraw_create(\|) ,
+.BR clnttcp_create(\|) ,
+or
+.B clntudp_create(\|)
+call fails.
+.br
+.if t .ne 8
+.LP
+.ft B
+.nf
+.sp .5
+void
+clnt_perrno(stat)
+enum clnt_stat stat;
+.fi
+.ft R
+.IP
+Print a message to standard error corresponding
+to the condition indicated by
+.IR stat .
+Used after
+.BR callrpc(\|) .
+.br
+.if t .ne 8
+.LP
+.ft B
+.nf
+.sp .5
+clnt_perror(clnt, s)
+\s-1CLIENT\s0 *clnt;
+char *s;
+.fi
+.ft R
+.IP
+Print a message to standard error indicating why an
+.SM RPC
+call failed;
+.I clnt
+is the handle used to do the call.
+The message is prepended with string
+.I s
+and a colon.
+Used after
+.BR clnt_call(\|) .
+.br
+.if t .ne 9
+.LP
+.ft B
+.nf
+.sp .5
+char *
+clnt_spcreateerror
+char *s;
+.fi
+.ft R
+.IP
+Like
+.BR clnt_pcreateerror(\|) ,
+except that it returns a string
+instead of printing to the standard error.
+.IP
+Bugs: returns pointer to static data that is overwritten
+on each call.
+.br
+.if t .ne 9
+.LP
+.ft B
+.nf
+.sp .5
+char *
+clnt_sperrno(stat)
+enum clnt_stat stat;
+.fi
+.ft R
+.IP
+Take the same arguments as
+.BR clnt_perrno(\|) ,
+but instead of sending a message to the standard error
+indicating why an
+.SM RPC
+call failed, return a pointer to a string which contains
+the message.  The string ends with a
+.SM NEWLINE\s0.
+.IP
+.B clnt_sperrno(\|)
+is used instead of
+.B clnt_perrno(\|)
+if the program does not have a standard error (as a program
+running as a server quite likely does not), or if the
+programmer
+does not want the message to be output with
+.BR printf ,
+or if a message format different from that supported by
+.B clnt_perrno(\|)
+is to be used.
+Note: unlike
+.B clnt_sperror(\|)
+and
+.BR clnt_spcreaterror(\|) ,
+.B clnt_sperrno(\|)
+returns pointer to static data, but the
+result will not get overwritten on each call.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+char *
+clnt_sperror(rpch, s)
+\s-1CLIENT\s0 *rpch;
+char *s;
+.fi
+.ft R
+.IP
+Like
+.BR clnt_perror(\|) ,
+except that (like
+.BR clnt_sperrno(\|) )
+it returns a string instead of printing to standard error.
+.IP
+Bugs: returns pointer to static data that is overwritten
+on each call.
+.br
+.if t .ne 10
+.LP
+.ft B
+.nf
+.sp .5
+\s-1CLIENT\s0 *
+clntraw_create(prognum, versnum)
+u_long prognum, versnum;
+.fi
+.ft R
+.IP
+This routine creates a toy
+.SM RPC
+client for the remote program
+.IR prognum ,
+version
+.IR versnum .
+The transport used to pass messages to the service is
+actually a buffer within the process's address space, so the
+corresponding
+.SM RPC
+server should live in the same address space; see
+.BR svcraw_create(\|) .
+This allows simulation of
+.SM RPC
+and acquisition of
+.SM RPC
+overheads, such as round trip times, without any
+kernel interference.
+This routine returns
+.SM NULL
+if it fails.
+.br
+.if t .ne 15
+.LP
+.ft B
+.nf
+.sp .5
+\s-1CLIENT\s0 *
+clnttcp_create(addr, prognum, versnum, sockp, sendsz, recvsz)
+struct sockaddr_in *addr;
+u_long prognum, versnum;
+int *sockp;
+u_int sendsz, recvsz;
+.fi
+.ft R
+.IP
+This routine creates an
+.SM RPC
+client for the remote program
+.IR prognum ,
+version
+.IR versnum ;
+the client uses
+.SM TCP/IP
+as a transport.
+The remote program is located at Internet
+address
+.IR *addr .
+If
+.\"The following in-line font conversion is necessary for the hyphen indicator
+\fB\%addr\->sin_port\fR
+is zero, then it is set to the actual port that the remote
+program is listening on (the remote
+.B portmap
+service is consulted for this information). The parameter
+.I sockp
+is a socket; if it is
+.BR \s-1RPC_ANYSOCK\s0 ,
+then this routine opens a new one and sets
+.IR sockp .
+Since
+.SM TCP\s0-based
+.SM RPC
+uses buffered
+.SM I/O ,
+the user may specify the size of the send and receive buffers
+with the parameters
+.I sendsz
+and
+.IR recvsz ;
+values of zero choose suitable defaults.
+This routine returns
+.SM NULL
+if it fails.
+.br
+.if t .ne 15
+.LP
+.ft B
+.nf
+.sp .5
+\s-1CLIENT\s0 *
+clntudp_create(addr, prognum, versnum, wait, sockp)
+struct sockaddr_in *addr;
+u_long prognum, versnum;
+struct timeval wait;
+int *sockp;
+.fi
+.ft R
+.IP
+This routine creates an
+.SM RPC
+client for the remote program
+.IR prognum ,
+version
+.IR versnum ;
+the client uses
+.SM UDP/IP
+as a transport.
+The remote program is located at Internet
+address
+.IR addr .
+If
+\fB\%addr\->sin_port\fR
+is zero, then it is set to actual port that the remote
+program is listening on (the remote
+.B portmap
+service is consulted for this information). The parameter
+.I sockp
+is a socket; if it is
+.BR \s-1RPC_ANYSOCK\s0 ,
+then this routine opens a new one and sets
+.IR sockp .
+The
+.SM UDP
+transport resends the call message in intervals of
+.B wait
+time until a response is received or until the call times
+out.
+The total time for the call to time out is specified by
+.BR clnt_call(\|) .
+.IP
+Warning: since
+.SM UDP\s0-based
+.SM RPC
+messages can only hold up to 8 Kbytes
+of encoded data, this transport cannot be used for procedures
+that take large arguments or return huge results.
+.br
+.if t .ne 8
+.LP
+.ft B
+.nf
+.sp .5
+\s-1CLIENT\s0 *
+clntudp_bufcreate(addr, prognum, versnum, wait, sockp, sendsize, recosize)
+struct sockaddr_in *addr;
+u_long prognum, versnum;
+struct timeval wait;
+int *sockp;
+unsigned int sendsize;
+unsigned int recosize;
+.fi
+.ft R
+.IP
+This routine creates an
+.SM RPC
+client for the remote program
+.IR prognum ,
+on
+.IR versnum ;
+the client uses
+.SM UDP/IP
+as a transport.
+The remote program is located at Internet
+address
+.IR addr .
+If
+\fB\%addr\->sin_port\fR
+is zero, then it is set to actual port that the remote
+program is listening on (the remote
+.B portmap
+service is consulted for this information). The parameter
+.I sockp
+is a socket; if it is
+.BR \s-1RPC_ANYSOCK\s0 ,
+then this routine opens a new one and sets
+.BR sockp .
+The
+.SM UDP
+transport resends the call message in intervals of
+.B wait
+time until a response is received or until the call times
+out.
+The total time for the call to time out is specified by
+.BR clnt_call(\|) .
+.IP
+This allows the user to specify the maximum packet size for sending and receiving 
+.SM UDP\s0-based
+.SM RPC
+messages.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+int
+get_myaddress(addr)
+struct sockaddr_in *addr;
+.fi
+.ft R
+.IP
+Stuff the machine's
+.SM IP
+address into
+.IR *addr ,
+without consulting the library routines that deal with
+.BR /etc/hosts .
+The port number is always set to
+.BR htons(\s-1PMAPPORT\s0) .
+Returns zero on success, non-zero on failure.
+.br
+.if t .ne 10
+.LP
+.ft B
+.nf
+.sp .5
+struct pmaplist *
+pmap_getmaps(addr)
+struct sockaddr_in *addr;
+.fi
+.ft R
+.IP
+A user interface to the
+.B portmap
+service, which returns a list of the current
+.SM RPC
+program-to-port mappings
+on the host located at
+.SM IP
+address
+.IR *addr .
+This routine can return
+.SM NULL .
+The command
+.RB ` "rpcinfo \-p" '
+uses this routine.
+.br
+.if t .ne 12
+.LP
+.ft B
+.nf
+.sp .5
+u_short
+pmap_getport(addr, prognum, versnum, protocol)
+struct sockaddr_in *addr;
+u_long prognum, versnum, protocol;
+.fi
+.ft R
+.IP
+A user interface to the
+.B portmap
+service, which returns the port number
+on which waits a service that supports program number
+.IR prognum ,
+version
+.IR versnum ,
+and speaks the transport protocol associated with
+.IR protocol .
+The value of
+.I protocol
+is most likely
+.B
+.SM IPPROTO_UDP
+or 
+.BR \s-1IPPROTO_TCP\s0 .
+A return value of zero means that the mapping does not exist
+or that
+the
+.SM RPC
+system failed to contact the remote
+.B portmap
+service.  In the latter case, the global variable
+.B rpc_createerr(\|)
+contains the
+.SM RPC
+status.
+.br
+.if t .ne 15
+.LP
+.ft B
+.nf
+.sp .5
+enum clnt_stat
+pmap_rmtcall(addr, prognum, versnum, procnum, inproc, in, outproc, out, tout, portp)
+struct sockaddr_in *addr;
+u_long prognum, versnum, procnum;
+char *in, *out;
+xdrproc_t inproc, outproc;
+struct timeval tout;
+u_long *portp;
+.fi
+.ft R
+.IP
+A user interface to the
+.B portmap
+service, which instructs
+.B portmap
+on the host at
+.SM IP
+address
+.I *addr
+to make an
+.SM RPC
+call on your behalf to a procedure on that host.
+The parameter
+.I *portp
+will be modified to the program's port number if the
+procedure
+succeeds.
+The definitions of other parameters are discussed
+in
+.B callrpc(\|)
+and
+.BR clnt_call(\|) .
+This procedure should be used for a \(lqping\(rq and nothing
+else.
+See also
+.BR clnt_broadcast(\|) .
+.br
+.if t .ne 9
+.LP
+.ft B
+.nf
+.sp .5
+pmap_set(prognum, versnum, protocol, port)
+u_long prognum, versnum, protocol;
+u_short port;
+.fi
+.ft R
+.IP
+A user interface to the
+.B portmap
+service, which establishes a mapping between the triple
+.RI [ prognum , versnum , protocol\fR]
+and
+.I port
+on the machine's
+.B portmap
+service.
+The value of
+.I protocol
+is most likely
+.B
+.SM IPPROTO_UDP
+or 
+.BR \s-1IPPROTO_TCP\s0 .
+This routine returns one if it succeeds, zero otherwise.
+Automatically done by
+.BR svc_register(\|) .
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+pmap_unset(prognum, versnum)
+u_long prognum, versnum;
+.fi
+.ft R
+.IP
+A user interface to the
+.B portmap
+service, which destroys all mapping between the triple
+.RI [ prognum , versnum , *\fR]
+and
+.B ports
+on the machine's
+.B portmap
+service.
+This routine returns one if it succeeds, zero
+otherwise.
+.br
+.if t .ne 15
+.LP
+.ft B
+.nf
+.sp .5
+registerrpc(prognum, versnum, procnum, procname, inproc, outproc)
+u_long prognum, versnum, procnum;
+char *(*procname) (\|) ;
+xdrproc_t inproc, outproc;
+.fi
+.ft R
+.IP
+Register procedure
+.I procname
+with the
+.SM RPC
+service package.  If a request arrives for program
+.IR prognum ,
+version
+.IR versnum ,
+and procedure
+.IR procnum ,
+.I procname
+is called with a pointer to its parameter(s);
+.I progname
+should return a pointer to its static result(s);
+.I inproc
+is used to decode the parameters while
+.I outproc
+is used to encode the results.
+This routine returns zero if the registration succeeded, \-1
+otherwise.
+.IP
+Warning: remote procedures registered in this form
+are accessed using the
+.SM UDP/IP
+transport; see
+.B svcudp_create(\|)
+for restrictions.
+.br
+.if t .ne 5
+.LP
+.ft B
+.nf
+.sp .5
+struct rpc_createerr     rpc_createerr;
+.fi
+.ft R
+.IP
+A global variable whose value is set by any
+.SM RPC
+client creation routine
+that does not succeed.  Use the routine
+.B clnt_pcreateerror(\|)
+to print the reason why.
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+svc_destroy(xprt)
+\s-1SVCXPRT\s0 *
+xprt;
+.fi
+.ft R
+.IP
+A macro that destroys the
+.SM RPC
+service transport handle,
+.IR xprt .
+Destruction usually involves deallocation
+of private data structures, including
+.I xprt
+itself.  Use of
+.I xprt
+is undefined after calling this routine.
+.br
+.if t .ne 8
+.LP
+.ft B
+.nf
+.sp .5
+fd_set svc_fdset;
+.fi
+.ft R
+.IP
+A global variable reflecting the
+.SM RPC
+service side's
+read file descriptor bit mask; it is suitable as a template parameter
+to the
+.B select
+system call.
+This is only of interest
+if a service implementor does not call
+.BR svc_run(\|) ,
+but rather does his own asynchronous event processing.
+This variable is read-only (do not pass its address to
+.BR select !),
+yet it may change after calls to
+.B svc_getreqset(\|)
+or any creation routines.
+.br
+As well, note that if the process has descriptor limits
+which are extended beyond
+.BR FD_SETSIZE ,
+this variable will only be usable for the first
+.BR FD_SETSIZE
+descriptors.
+.br
+.if t .ne 6
+.LP
+.ft B
+.nf
+.sp .5
+int svc_fds;
+.fi
+.ft R
+.IP
+Similar to
+.BR svc_fedset(\|) ,
+but limited to 32 descriptors.
+This
+interface is obsoleted by
+.BR svc_fdset(\|) .
+.br
+.if t .ne 9
+.LP
+.ft B
+.nf
+.sp .5
+svc_freeargs(xprt, inproc, in)
+\s-1SVCXPRT\s0 *xprt;
+xdrproc_t inproc;
+char *in;
+.fi
+.ft R
+.IP
+A macro that frees any data allocated by the
+.SM RPC/XDR
+system when it decoded the arguments to a service procedure
+using
+.BR svc_getargs(\|) .
+This routine returns 1 if the results were successfully
+freed,
+and zero otherwise.
+.br
+.if t .ne 10
+.LP
+.ft B
+.nf
+.sp .5
+svc_getargs(xprt, inproc, in)
+\s-1SVCXPRT\s0 *xprt;
+xdrproc_t inproc;
+char *in;
+.fi
+.ft R
+.IP
+A macro that decodes the arguments of an
+.SM RPC
+request
+associated with the
+.SM RPC
+service transport handle,
+.IR xprt .
+The parameter
+.I in
+is the address where the arguments will be placed;
+.I inproc
+is the
+.SM XDR
+routine used to decode the arguments.
+This routine returns one if decoding succeeds, and zero
+otherwise.
+.br
+.if t .ne 9
+.LP
+.ft B
+.nf
+.sp .5
+struct sockaddr_in *
+svc_getcaller(xprt)
+\s-1SVCXPRT\s0 *xprt;
+.fi
+.ft R
+.IP
+The approved way of getting the network address of the caller
+of a procedure associated with the
+.SM RPC
+service transport handle,
+.IR xprt .
+.br
+.if t .ne 9
+.LP
+.ft B
+.nf
+.sp .5
+svc_getreqset(rdfds)
+fd_set *rdfds;
+.fi
+.ft R
+.IP
+This routine is only of interest if a service implementor
+does not call
+.BR svc_run(\|) ,
+but instead implements custom asynchronous event processing.
+It is called when the
+.B select
+system call has determined that an
+.SM RPC
+request has arrived on some
+.SM RPC
+.B socket(s) ;
+.I rdfds
+is the resultant read file descriptor bit mask.
+The routine returns when all sockets associated with the
+value of
+.I rdfds
+have been serviced.
+.br
+.if t .ne 6
+.LP
+.ft B
+.nf
+.sp .5
+svc_getreq(rdfds)
+int rdfds;
+.fi
+.ft R
+.IP
+Similar to
+.BR svc_getreqset(\|) ,
+but limited to 32 descriptors.
+This interface is obsoleted by
+.BR svc_getreqset(\|) .
+.br
+.if t .ne 17
+.LP
+.ft B
+.nf
+.sp .5
+svc_register(xprt, prognum, versnum, dispatch, protocol)
+\s-1SVCXPRT\s0 *xprt;
+u_long prognum, versnum;
+void (*dispatch) (\|);
+u_long protocol;
+.fi
+.ft R
+.IP
+Associates
+.I prognum
+and
+.I versnum
+with the service dispatch procedure,
+.IR dispatch .
+If
+.I protocol
+is zero, the service is not registered with the
+.B portmap
+service.  If
+.I protocol
+is non-zero, then a mapping of the triple
+.RI [ prognum , versnum , protocol\fR]
+to
+\fB\%xprt\->xp_port\fR
+is established with the local
+.B portmap
+service (generally
+.I protocol
+is zero,
+.B
+.SM IPPROTO_UDP
+or 
+.B
+.SM IPPROTO_TCP
+).
+The procedure
+.I dispatch
+has the following form:
+.RS 1i
+.ft B
+.nf
+dispatch(request, xprt)
+struct svc_req *request;
+\s-1SVCXPRT\s0 *xprt;
+.ft R
+.fi
+.RE
+.IP
+The
+.B svc_register(\|)
+routine returns one if it succeeds, and zero otherwise.
+.br
+.if t .ne 6
+.LP
+.ft B
+.nf
+.sp .5
+svc_run(\|)
+.fi
+.ft R
+.IP
+This routine never returns.
+It waits for
+.SM RPC
+requests to arrive, and calls the appropriate service
+procedure using
+.B svc_getreq(\|)
+when one arrives.
+This procedure is usually waiting for a
+.B select(\|)
+system call to return.
+.br
+.if t .ne 9
+.LP
+.ft B
+.nf
+.sp .5
+svc_sendreply(xprt, outproc, out)
+\s-1SVCXPRT\s0 *xprt;
+xdrproc_t outproc;
+char *out;
+.fi
+.ft R
+.IP
+Called by an
+.SM RPC
+service's dispatch routine to send the results of a
+remote procedure call.  The parameter
+.I xprt
+is the request's associated transport handle;
+.I outproc
+is the
+.SM XDR
+routine which is used to encode the results; and
+.I out
+is the address of the results.
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+void
+svc_unregister(prognum, versnum)
+u_long prognum, versnum;
+.fi
+.ft R
+.IP
+Remove all mapping of the double
+.RI [ prognum , versnum ]
+to dispatch routines, and of the triple
+.RI [ prognum , versnum , *\fR]
+to port number.
+.br
+.if t .ne 9
+.LP
+.ft B
+.nf
+.sp .5
+void
+svcerr_auth(xprt, why)
+\s-1SVCXPRT\s0 *xprt;
+enum auth_stat why;
+.fi
+.ft R
+.IP
+Called by a service dispatch routine that refuses to perform
+a remote procedure call due to an authentication error.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+void
+svcerr_decode(xprt)
+\s-1SVCXPRT\s0 *xprt;
+.fi
+.ft R
+.IP
+Called by a service dispatch routine that cannot successfully
+decode its parameters.
+See also
+.BR svc_getargs(\|) .
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+void
+svcerr_noproc(xprt)
+\s-1SVCXPRT\s0 *xprt;
+.fi
+.ft R
+.IP
+Called by a service dispatch routine that does not implement
+the procedure number that the caller requests.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+void
+svcerr_noprog(xprt)
+\s-1SVCXPRT\s0 *xprt;
+.fi
+.ft R
+.IP
+Called when the desired program is not registered with the
+.SM RPC
+package.
+Service implementors usually do not need this routine.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+void
+svcerr_progvers(xprt)
+\s-1SVCXPRT\s0 *xprt;
+.fi
+.ft R
+.IP
+Called when the desired version of a program is not registered
+with the
+.SM RPC
+package.
+Service implementors usually do not need this routine.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+void
+svcerr_systemerr(xprt)
+\s-1SVCXPRT\s0 *xprt;
+.fi
+.ft R
+.IP
+Called by a service dispatch routine when it detects a system
+error
+not covered by any particular protocol.
+For example, if a service can no longer allocate storage,
+it may call this routine.
+.br
+.if t .ne 8
+.LP
+.ft B
+.nf
+.sp .5
+void
+svcerr_weakauth(xprt)
+\s-1SVCXPRT\s0 *xprt;
+.fi
+.ft R
+.IP
+Called by a service dispatch routine that refuses to perform
+a remote procedure call due to insufficient
+authentication parameters.  The routine calls
+.BR "svcerr_auth(xprt, \s-1AUTH_TOOWEAK\s0)" .
+.br
+.if t .ne 11
+.LP
+.ft B
+.nf
+.sp .5
+\s-1SVCXPRT\s0 *
+svcraw_create(\|)
+.fi
+.ft R
+.IP
+This routine creates a toy
+.SM RPC
+service transport, to which it returns a pointer.  The
+transport
+is really a buffer within the process's address space,
+so the corresponding
+.SM RPC
+client should live in the same
+address space;
+see
+.BR clntraw_create(\|) .
+This routine allows simulation of
+.SM RPC
+and acquisition of
+.SM RPC
+overheads (such as round trip times), without any kernel
+interference.
+This routine returns
+.SM NULL
+if it fails.
+.br
+.if t .ne 11
+.LP
+.ft B
+.nf
+.sp .5
+\s-1SVCXPRT\s0 *
+svctcp_create(sock, send_buf_size, recv_buf_size)
+int sock;
+u_int send_buf_size, recv_buf_size;
+.fi
+.ft R
+.IP
+This routine creates a
+.SM TCP/IP\s0-based
+.SM RPC
+service transport, to which it returns a pointer.
+The transport is associated with the socket
+.IR sock ,
+which may be
+.BR \s-1RPC_ANYSOCK\s0 ,
+in which case a new socket is created.
+If the socket is not bound to a local
+.SM TCP
+port, then this routine binds it to an arbitrary port.  Upon
+completion,
+\fB\%xprt\->xp_sock\fR
+is the transport's socket descriptor, and
+\fB\%xprt\->xp_port\fR
+is the transport's port number.
+This routine returns
+.SM NULL
+if it fails.
+Since
+.SM TCP\s0-based
+.SM RPC
+uses buffered
+.SM I/O ,
+users may specify the size of buffers; values of zero
+choose suitable defaults.
+.br
+.if t .ne 11
+.LP
+.ft B
+.nf
+.sp .5
+\s-1SVCXPRT\s0 *
+svcfd_create(fd, sendsize, recvsize)
+int fd;
+u_int sendsize;
+u_int recvsize;
+.fi
+.ft R
+.IP
+Create a service on top of any open descriptor.
+Typically,
+this
+descriptor is a connected socket for a stream protocol such
+as
+.SM TCP\s0.
+.I sendsize
+and
+.I recvsize
+indicate sizes for the send and receive buffers.  If they are
+zero, a reasonable default is chosen.
+.br
+.if t .ne 10
+.LP
+.ft B
+.nf
+.sp .5
+\s-1SVCXPRT\s0 *
+svcudp_bufcreate(sock, sendsize, recosize)
+int sock;
+.fi
+.ft R
+.IP
+This routine creates a
+.SM UDP/IP\s0-based
+.SM RPC
+service transport, to which it returns a pointer.
+The transport is associated with the socket
+.IR sock ,
+which may be
+.B \s-1RPC_ANYSOCK\s0 ,
+in which case a new socket is created.
+If the socket is not bound to a local
+.SM UDP
+port, then this routine binds it to an arbitrary port.
+Upon
+completion,
+\fB\%xprt\->xp_sock\fR
+is the transport's socket descriptor, and
+\fB\%xprt\->xp_port\fR
+is the transport's port number.
+This routine returns
+.SM NULL
+if it fails.
+.IP
+This allows the user to specify the maximum packet size for sending and 
+receiving
+.SM UDP\s0-based
+.SM RPC messages.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+xdr_accepted_reply(xdrs, ar)
+\s-1XDR\s0 *xdrs;
+struct accepted_reply *ar;
+.fi
+.ft R
+.IP
+Used for encoding
+.SM RPC
+reply messages.
+This routine is useful for users who
+wish to generate
+\s-1RPC\s0-style
+messages without using the
+.SM RPC
+package.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+xdr_authunix_parms(xdrs, aupp)
+\s-1XDR\s0 *xdrs;
+struct authunix_parms *aupp;
+.fi
+.ft R
+.IP
+Used for describing
+.SM UNIX
+credentials.
+This routine is useful for users
+who wish to generate these credentials without using the
+.SM RPC
+authentication package.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+void
+xdr_callhdr(xdrs, chdr)
+\s-1XDR\s0 *xdrs;
+struct rpc_msg *chdr;
+.fi
+.ft R
+.IP
+Used for describing
+.SM RPC
+call header messages.
+This routine is useful for users who wish to generate
+.SM RPC\s0-style
+messages without using the
+.SM RPC
+package.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+xdr_callmsg(xdrs, cmsg)
+\s-1XDR\s0 *xdrs;
+struct rpc_msg *cmsg;
+.fi
+.ft R
+.IP
+Used for describing
+.SM RPC
+call messages.
+This routine is useful for users who wish to generate
+.SM RPC\s0-style
+messages without using the
+.SM RPC
+package.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+xdr_opaque_auth(xdrs, ap)
+\s-1XDR\s0 *xdrs;
+struct opaque_auth *ap;
+.fi
+.ft R
+.IP
+Used for describing
+.SM RPC
+authentication information messages.
+This routine is useful for users who wish to generate
+.SM RPC\s0-style
+messages without using the
+.SM RPC
+package.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+xdr_pmap(xdrs, regs)
+\s-1XDR\s0 *xdrs;
+struct pmap *regs;
+.fi
+.ft R
+.IP
+Used for describing parameters to various
+.B portmap
+procedures, externally.
+This routine is useful for users who wish to generate
+these parameters without using the
+.B pmap
+interface.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+xdr_pmaplist(xdrs, rp)
+\s-1XDR\s0 *xdrs;
+struct pmaplist **rp;
+.fi
+.ft R
+.IP
+Used for describing a list of port mappings, externally.
+This routine is useful for users who wish to generate
+these parameters without using the
+.B pmap
+interface.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+xdr_rejected_reply(xdrs, rr)
+\s-1XDR\s0 *xdrs;
+struct rejected_reply *rr;
+.fi
+.ft R
+.IP
+Used for describing
+.SM RPC
+reply messages.
+This routine is useful for users who wish to generate
+.SM RPC\s0-style
+messages without using the
+.SM RPC
+package.
+.br
+.if t .ne 8
+.LP
+.ft B
+.nf
+.sp .5
+xdr_replymsg(xdrs, rmsg)
+\s-1XDR\s0 *xdrs;
+struct rpc_msg *rmsg;
+.fi
+.ft R
+.IP
+Used for describing
+.SM RPC
+reply messages.
+This routine is useful for users who wish to generate
+.SM RPC
+style messages without using the
+.SM RPC
+package.
+.br
+.if t .ne 8
+.LP
+.ft B
+.nf
+.sp .5
+void
+xprt_register(xprt)
+\s-1SVCXPRT\s0 *xprt;
+.fi
+.ft R
+.IP
+After
+.SM RPC
+service transport handles are created,
+they should register themselves with the
+.SM RPC
+service package.
+This routine modifies the global variable
+.BR svc_fds(\|) .
+Service implementors usually do not need this routine.
+.br
+.if t .ne 8
+.LP
+.ft B
+.nf
+.sp .5
+void
+xprt_unregister(xprt)
+\s-1SVCXPRT\s0 *xprt;
+.fi
+.ft R
+.IP
+Before an
+.SM RPC
+service transport handle is destroyed,
+it should unregister itself with the
+.SM RPC
+service package.
+This routine modifies the global variable
+.BR svc_fds(\|) .
+Service implementors usually do not need this routine.
+.SH SEE ALSO
+.BR rpc_secure (3),
+.BR xdr (3)
+.br
+The following manuals:
+.RS
+.ft I
+Remote Procedure Calls: Protocol Specification
+.br
+Remote Procedure Call Programming Guide
+.br
+rpcgen Programming Guide
+.br
+.ft R
+.RE
+.IR "\s-1RPC\s0: Remote Procedure Call Protocol Specification" ,
+.SM RFC1050, Sun Microsystems, Inc.,
+.SM USC-ISI\s0.
+
diff --git a/services/librpc/src/rpc/rpc.5 b/services/librpc/src/rpc/rpc.5
new file mode 100644
index 0000000..36f895d
--- /dev/null
+++ b/services/librpc/src/rpc/rpc.5
@@ -0,0 +1,35 @@
+.\" $FreeBSD: src/lib/libc/rpc/rpc.5,v 1.6 1999/08/28 00:00:44 peter Exp $
+.\" @(#)rpc.5	2.2 88/08/03 4.0 RPCSRC; from 1.4 87/11/27 SMI;
+.Dd September 26, 1985
+.Dt RPC 5
+.Sh NAME
+.Nm rpc
+.Nd rpc program number data base
+.Sh SYNOPSIS
+/etc/rpc
+.Sh DESCRIPTION
+The
+.Pa /etc/rpc
+file contains user readable names that
+can be used in place of rpc program numbers.
+Each line has the following information:
+.Pp
+.Bl -bullet -compact
+.It
+name of server for the rpc program
+.It
+rpc program number
+.It
+aliases
+.El
+.Pp
+Items are separated by any number of blanks and/or
+tab characters.
+A ``#'' indicates the beginning of a comment; characters up to the end of
+the line are not interpreted by routines which search the file.
+.Sh FILES
+.Bl -tag -compact -width /etc/rpc
+.Pa /etc/rpc
+.El
+.Sh "SEE ALSO"
+.Xr getrpcent 3
diff --git a/services/librpc/src/rpc/rpc_callmsg.c b/services/librpc/src/rpc/rpc_callmsg.c
new file mode 100644
index 0000000..b44ebb4
--- /dev/null
+++ b/services/librpc/src/rpc/rpc_callmsg.c
@@ -0,0 +1,196 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)rpc_callmsg.c 1.4 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)rpc_callmsg.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/rpc_callmsg.c,v 1.9 1999/08/28 00:00:45 peter Exp $";
+#endif
+
+/*
+ * rpc_callmsg.c
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ *
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <sys/param.h>
+#include <stdlib.h>
+#include <string.h>
+#include <rpc/rpc.h>
+
+/*
+ * XDR a call message
+ */
+bool_t
+xdr_callmsg(
+	XDR *xdrs,
+	struct rpc_msg *cmsg)
+{
+	register int32_t *buf;
+	register struct opaque_auth *oa;
+
+	if (xdrs->x_op == XDR_ENCODE) {
+		if (cmsg->rm_call.cb_cred.oa_length > MAX_AUTH_BYTES) {
+			return (FALSE);
+		}
+		if (cmsg->rm_call.cb_verf.oa_length > MAX_AUTH_BYTES) {
+			return (FALSE);
+		}
+		buf = XDR_INLINE(xdrs, 8 * BYTES_PER_XDR_UNIT
+			+ RNDUP(cmsg->rm_call.cb_cred.oa_length)
+			+ 2 * BYTES_PER_XDR_UNIT
+			+ RNDUP(cmsg->rm_call.cb_verf.oa_length));
+		if (buf != NULL) {
+			IXDR_PUT_LONG(buf, cmsg->rm_xid);
+			IXDR_PUT_ENUM(buf, cmsg->rm_direction);
+			if (cmsg->rm_direction != CALL) {
+				return (FALSE);
+			}
+			IXDR_PUT_LONG(buf, cmsg->rm_call.cb_rpcvers);
+			if (cmsg->rm_call.cb_rpcvers != RPC_MSG_VERSION) {
+				return (FALSE);
+			}
+			IXDR_PUT_LONG(buf, cmsg->rm_call.cb_prog);
+			IXDR_PUT_LONG(buf, cmsg->rm_call.cb_vers);
+			IXDR_PUT_LONG(buf, cmsg->rm_call.cb_proc);
+			oa = &cmsg->rm_call.cb_cred;
+			IXDR_PUT_ENUM(buf, oa->oa_flavor);
+			IXDR_PUT_LONG(buf, oa->oa_length);
+			if (oa->oa_length) {
+				memcpy((caddr_t)buf, oa->oa_base, oa->oa_length);
+				buf += RNDUP(oa->oa_length) / sizeof (int32_t);
+			}
+			oa = &cmsg->rm_call.cb_verf;
+			IXDR_PUT_ENUM(buf, oa->oa_flavor);
+			IXDR_PUT_LONG(buf, oa->oa_length);
+			if (oa->oa_length) {
+				memcpy((caddr_t)buf, oa->oa_base, oa->oa_length);
+				/* no real need....
+				buf += RNDUP(oa->oa_length) / sizeof (int32_t);
+				*/
+			}
+			return (TRUE);
+		}
+	}
+	if (xdrs->x_op == XDR_DECODE) {
+		buf = XDR_INLINE(xdrs, 8 * BYTES_PER_XDR_UNIT);
+		if (buf != NULL) {
+			cmsg->rm_xid = IXDR_GET_LONG(buf);
+			cmsg->rm_direction = IXDR_GET_ENUM(buf, enum msg_type);
+			if (cmsg->rm_direction != CALL) {
+				return (FALSE);
+			}
+			cmsg->rm_call.cb_rpcvers = IXDR_GET_LONG(buf);
+			if (cmsg->rm_call.cb_rpcvers != RPC_MSG_VERSION) {
+				return (FALSE);
+			}
+			cmsg->rm_call.cb_prog = IXDR_GET_LONG(buf);
+			cmsg->rm_call.cb_vers = IXDR_GET_LONG(buf);
+			cmsg->rm_call.cb_proc = IXDR_GET_LONG(buf);
+			oa = &cmsg->rm_call.cb_cred;
+			oa->oa_flavor = IXDR_GET_ENUM(buf, enum_t);
+			oa->oa_length = IXDR_GET_LONG(buf);
+			if (oa->oa_length) {
+				if (oa->oa_length > MAX_AUTH_BYTES) {
+					return (FALSE);
+				}
+				if (oa->oa_base == NULL) {
+					oa->oa_base = (caddr_t)
+						mem_alloc(oa->oa_length);
+				}
+				buf = XDR_INLINE(xdrs, RNDUP(oa->oa_length));
+				if (buf == NULL) {
+					if (xdr_opaque(xdrs, oa->oa_base,
+					    oa->oa_length) == FALSE) {
+						return (FALSE);
+					}
+				} else {
+					memcpy(oa->oa_base, (caddr_t)buf,
+					    oa->oa_length);
+					/* no real need....
+					buf += RNDUP(oa->oa_length) /
+						sizeof (int32_t);
+					*/
+				}
+			}
+			oa = &cmsg->rm_call.cb_verf;
+			buf = XDR_INLINE(xdrs, 2 * BYTES_PER_XDR_UNIT);
+			if (buf == NULL) {
+				if (xdr_enum(xdrs, &oa->oa_flavor) == FALSE ||
+				    xdr_u_int(xdrs, &oa->oa_length) == FALSE) {
+					return (FALSE);
+				}
+			} else {
+				oa->oa_flavor = IXDR_GET_ENUM(buf, enum_t);
+				oa->oa_length = IXDR_GET_LONG(buf);
+			}
+			if (oa->oa_length) {
+				if (oa->oa_length > MAX_AUTH_BYTES) {
+					return (FALSE);
+				}
+				if (oa->oa_base == NULL) {
+					oa->oa_base = (caddr_t)
+						mem_alloc(oa->oa_length);
+				}
+				buf = XDR_INLINE(xdrs, RNDUP(oa->oa_length));
+				if (buf == NULL) {
+					if (xdr_opaque(xdrs, oa->oa_base,
+					    oa->oa_length) == FALSE) {
+						return (FALSE);
+					}
+				} else {
+					memcpy(oa->oa_base, (caddr_t)buf,
+					    oa->oa_length);
+					/* no real need...
+					buf += RNDUP(oa->oa_length) /
+						sizeof (int32_t);
+					*/
+				}
+			}
+			return (TRUE);
+		}
+	}
+	if (
+	    xdr_u_int32_t(xdrs, &(cmsg->rm_xid)) &&
+	    xdr_enum(xdrs, (enum_t *)(void *)&(cmsg->rm_direction)) &&
+	    (cmsg->rm_direction == CALL) &&
+	    xdr_u_int32_t(xdrs, &(cmsg->rm_call.cb_rpcvers)) &&
+	    (cmsg->rm_call.cb_rpcvers == RPC_MSG_VERSION) &&
+	    xdr_u_int32_t(xdrs, &(cmsg->rm_call.cb_prog)) &&
+	    xdr_u_int32_t(xdrs, &(cmsg->rm_call.cb_vers)) &&
+	    xdr_u_int32_t(xdrs, &(cmsg->rm_call.cb_proc)) &&
+	    xdr_opaque_auth(xdrs, &(cmsg->rm_call.cb_cred)) )
+	    return (xdr_opaque_auth(xdrs, &(cmsg->rm_call.cb_verf)));
+	return (FALSE);
+}
diff --git a/services/librpc/src/rpc/rpc_commondata.c b/services/librpc/src/rpc/rpc_commondata.c
new file mode 100644
index 0000000..ad22568
--- /dev/null
+++ b/services/librpc/src/rpc/rpc_commondata.c
@@ -0,0 +1,45 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)rpc_commondata.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/rpc_commondata.c,v 1.7 1999/08/28 00:00:45 peter Exp $";
+#endif
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <rpc/rpc.h>
+/*
+ * This file should only contain common data (global data) that is exported
+ * by public interfaces
+ */
+struct opaque_auth _null_auth;
+struct rpc_createerr rpc_createerr;
diff --git a/services/librpc/src/rpc/rpc_dtablesize.c b/services/librpc/src/rpc/rpc_dtablesize.c
new file mode 100644
index 0000000..65f2953
--- /dev/null
+++ b/services/librpc/src/rpc/rpc_dtablesize.c
@@ -0,0 +1,65 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)rpc_dtablesize.c 1.2 87/08/11 Copyr 1987 Sun Micro";*/
+/*static char *sccsid = "from: @(#)rpc_dtablesize.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/rpc_dtablesize.c,v 1.10 1999/08/28 00:00:45 peter Exp $";
+#endif
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <sys/types.h>
+#include <unistd.h>
+
+/*
+ * Cache the result of getdtablesize(), so we don't have to do an
+ * expensive system call every time.
+ */
+/*
+ * XXX In FreeBSD 2.x, you can have the maximum number of open file
+ * descriptors be greater than FD_SETSIZE (which us 256 by default).
+ *
+ * Since old programs tend to use this call to determine the first arg
+ * for select(), having this return > FD_SETSIZE is a Bad Idea(TM)!
+ */
+int
+_rpc_dtablesize(void)
+{
+	static int size;
+
+	if (size == 0) {
+		size = getdtablesize();
+		if (size > FD_SETSIZE)
+			size = FD_SETSIZE;
+	}
+	return (size);
+}
diff --git a/services/librpc/src/rpc/rpc_prot.c b/services/librpc/src/rpc/rpc_prot.c
new file mode 100644
index 0000000..0718c9a
--- /dev/null
+++ b/services/librpc/src/rpc/rpc_prot.c
@@ -0,0 +1,336 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)rpc_prot.c 1.36 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)rpc_prot.c	2.3 88/08/07 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/rpc_prot.c,v 1.8 1999/08/28 00:00:46 peter Exp $";
+#endif
+
+/*
+ * rpc_prot.c
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ *
+ * This set of routines implements the rpc message definition,
+ * its serializer and some common rpc utility routines.
+ * The routines are meant for various implementations of rpc -
+ * they are NOT for the rpc client or rpc service implementations!
+ * Because authentication stuff is easy and is part of rpc, the opaque
+ * routines are also in this program.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <assert.h>
+#include <sys/param.h>
+
+#include <rpc/rpc.h>
+
+static void accepted(enum accept_stat, struct rpc_err *);
+static void rejected(enum reject_stat, struct rpc_err *);
+
+/* * * * * * * * * * * * * * XDR Authentication * * * * * * * * * * * */
+
+extern struct opaque_auth _null_auth;
+
+/*
+ * XDR an opaque authentication struct
+ * (see auth.h)
+ */
+bool_t
+xdr_opaque_auth(
+	XDR *xdrs,
+	struct opaque_auth *ap)
+{
+
+	assert(xdrs != NULL);
+	assert(ap != NULL);
+
+	if (xdr_enum(xdrs, &(ap->oa_flavor)))
+		return (xdr_bytes(xdrs, &ap->oa_base,
+			&ap->oa_length, MAX_AUTH_BYTES));
+	return (FALSE);
+}
+
+/*
+ * XDR a DES block
+ */
+bool_t
+xdr_des_block(
+	XDR *xdrs,
+	des_block *blkp)
+{
+
+	assert(xdrs != NULL);
+	assert(blkp != NULL);
+
+	return (xdr_opaque(xdrs, (caddr_t)blkp, sizeof(des_block)));
+}
+
+/* * * * * * * * * * * * * * XDR RPC MESSAGE * * * * * * * * * * * * * * * */
+
+/*
+ * XDR the MSG_ACCEPTED part of a reply message union
+ */
+bool_t
+xdr_accepted_reply(
+	XDR *xdrs,
+	struct accepted_reply *ar)
+{
+
+	/* personalized union, rather than calling xdr_union */
+	if (! xdr_opaque_auth(xdrs, &(ar->ar_verf)))
+		return (FALSE);
+	if (! xdr_enum(xdrs, (enum_t *)(void *)&(ar->ar_stat)))
+		return (FALSE);
+	switch (ar->ar_stat) {
+
+	case SUCCESS:
+		return ((*(ar->ar_results.proc))(xdrs, ar->ar_results.where));
+
+	case PROG_MISMATCH:
+		if (! xdr_u_int32_t(xdrs, &(ar->ar_vers.low)))
+			return (FALSE);
+		return (xdr_u_int32_t(xdrs, &(ar->ar_vers.high)));
+
+	case GARBAGE_ARGS:
+	case SYSTEM_ERR:
+	case PROC_UNAVAIL:
+	case PROG_UNAVAIL:
+		break;
+	}
+	return (TRUE);  /* TRUE => open ended set of problems */
+}
+
+/*
+ * XDR the MSG_DENIED part of a reply message union
+ */
+bool_t
+xdr_rejected_reply(
+	XDR *xdrs,
+	struct rejected_reply *rr )
+{
+
+	/* personalized union, rather than calling xdr_union */
+	if (! xdr_enum(xdrs, (enum_t *)(void *)&(rr->rj_stat)))
+		return (FALSE);
+	switch (rr->rj_stat) {
+
+	case RPC_MISMATCH:
+		if (! xdr_u_int32_t(xdrs, &(rr->rj_vers.low)))
+			return (FALSE);
+		return (xdr_u_int32_t(xdrs, &(rr->rj_vers.high)));
+
+	case AUTH_ERROR:
+		return (xdr_enum(xdrs, (enum_t *)(void *)&(rr->rj_why)));
+	}
+	return (FALSE);
+}
+
+static const struct xdr_discrim reply_dscrm[3] = {
+	{ (int)MSG_ACCEPTED, (xdrproc_t)xdr_accepted_reply },
+	{ (int)MSG_DENIED, (xdrproc_t)xdr_rejected_reply },
+	{ __dontcare__, NULL_xdrproc_t } };
+
+/*
+ * XDR a reply message
+ */
+bool_t
+xdr_replymsg(
+	XDR *xdrs,
+	struct rpc_msg *rmsg)
+{
+	if (
+	    xdr_u_int32_t(xdrs, &(rmsg->rm_xid)) &&
+	    xdr_enum(xdrs, (enum_t *)(void *)&(rmsg->rm_direction)) &&
+	    (rmsg->rm_direction == REPLY) )
+		return (xdr_union(xdrs, (enum_t *)(void *)&(rmsg->rm_reply.rp_stat),
+		   (caddr_t)&(rmsg->rm_reply.ru), reply_dscrm, NULL_xdrproc_t));
+	return (FALSE);
+}
+
+
+/*
+ * Serializes the "static part" of a call message header.
+ * The fields include: rm_xid, rm_direction, rpcvers, prog, and vers.
+ * The rm_xid is not really static, but the user can easily munge on the fly.
+ */
+bool_t
+xdr_callhdr(
+	XDR *xdrs,
+	struct rpc_msg *cmsg)
+{
+
+	cmsg->rm_direction = CALL;
+	cmsg->rm_call.cb_rpcvers = RPC_MSG_VERSION;
+	if (
+	    (xdrs->x_op == XDR_ENCODE) &&
+	    xdr_u_int32_t(xdrs, &(cmsg->rm_xid)) &&
+	    xdr_enum(xdrs, (enum_t *)(void *)&(cmsg->rm_direction)) &&
+	    xdr_u_int32_t(xdrs, &(cmsg->rm_call.cb_rpcvers)) &&
+	    xdr_u_int32_t(xdrs, &(cmsg->rm_call.cb_prog)) )
+	    return (xdr_u_int32_t(xdrs, &(cmsg->rm_call.cb_vers)));
+	return (FALSE);
+}
+
+/* ************************** Client utility routine ************* */
+
+static void
+accepted(
+	enum accept_stat acpt_stat,
+	struct rpc_err *error)
+{
+
+	assert(error != NULL);
+
+	switch (acpt_stat) {
+
+	case PROG_UNAVAIL:
+		error->re_status = RPC_PROGUNAVAIL;
+		return;
+
+	case PROG_MISMATCH:
+		error->re_status = RPC_PROGVERSMISMATCH;
+		return;
+
+	case PROC_UNAVAIL:
+		error->re_status = RPC_PROCUNAVAIL;
+		return;
+
+	case GARBAGE_ARGS:
+		error->re_status = RPC_CANTDECODEARGS;
+		return;
+
+	case SYSTEM_ERR:
+		error->re_status = RPC_SYSTEMERROR;
+		return;
+
+	case SUCCESS:
+		error->re_status = RPC_SUCCESS;
+		return;
+	}
+	/* something's wrong, but we don't know what ... */
+	error->re_status = RPC_FAILED;
+	error->re_lb.s1 = (int32_t)MSG_ACCEPTED;
+	error->re_lb.s2 = (int32_t)acpt_stat;
+}
+
+static void
+rejected(
+	enum reject_stat rjct_stat,
+	struct rpc_err *error)
+{
+
+	assert(error != NULL);
+
+	switch (rjct_stat) {
+	case RPC_MISMATCH:
+		error->re_status = RPC_VERSMISMATCH;
+		return;
+
+	case AUTH_ERROR:
+		error->re_status = RPC_AUTHERROR;
+		return;
+	}
+	/* something's wrong, but we don't know what ... */
+	error->re_status = RPC_FAILED;
+	error->re_lb.s1 = (int32_t)MSG_DENIED;
+	error->re_lb.s2 = (int32_t)rjct_stat;
+}
+
+/*
+ * given a reply message, fills in the error
+ */
+void
+_seterr_reply(
+	struct rpc_msg *msg,
+	struct rpc_err *error)
+{
+
+	assert(msg != NULL);
+	assert(error != NULL);
+
+	/* optimized for normal, SUCCESSful case */
+	switch (msg->rm_reply.rp_stat) {
+
+	case MSG_ACCEPTED:
+		if (msg->acpted_rply.ar_stat == SUCCESS) {
+			error->re_status = RPC_SUCCESS;
+			return;
+		}
+		accepted(msg->acpted_rply.ar_stat, error);
+		break;
+
+	case MSG_DENIED:
+		rejected(msg->rjcted_rply.rj_stat, error);
+		break;
+
+	default:
+		error->re_status = RPC_FAILED;
+		error->re_lb.s1 = (int32_t)(msg->rm_reply.rp_stat);
+		break;
+	}
+	switch (error->re_status) {
+
+	case RPC_VERSMISMATCH:
+		error->re_vers.low = msg->rjcted_rply.rj_vers.low;
+		error->re_vers.high = msg->rjcted_rply.rj_vers.high;
+		break;
+
+	case RPC_AUTHERROR:
+		error->re_why = msg->rjcted_rply.rj_why;
+		break;
+
+	case RPC_PROGVERSMISMATCH:
+		error->re_vers.low = msg->acpted_rply.ar_vers.low;
+		error->re_vers.high = msg->acpted_rply.ar_vers.high;
+		break;
+
+	case RPC_FAILED:
+	case RPC_SUCCESS:
+	case RPC_PROGNOTREGISTERED:
+	case RPC_PMAPFAILURE:
+	case RPC_UNKNOWNPROTO:
+	case RPC_UNKNOWNHOST:
+	case RPC_SYSTEMERROR:
+	case RPC_CANTDECODEARGS:
+	case RPC_PROCUNAVAIL:
+	case RPC_PROGUNAVAIL:
+	case RPC_TIMEDOUT:
+	case RPC_CANTRECV:
+	case RPC_CANTSEND:
+	case RPC_CANTDECODERES:
+	case RPC_CANTENCODEARGS:
+	default:
+		break;
+	}
+}
diff --git a/services/librpc/src/rpc/rpc_secure.3 b/services/librpc/src/rpc/rpc_secure.3
new file mode 100644
index 0000000..4efd9b8
--- /dev/null
+++ b/services/librpc/src/rpc/rpc_secure.3
@@ -0,0 +1,254 @@
+.\" @(#)rpc_secure.3n	2.1 88/08/08 4.0 RPCSRC; from 1.19 88/06/24 SMI
+.\" $FreeBSD: src/lib/libc/rpc/rpc_secure.3,v 1.6 2000/03/02 09:13:48 sheldonh Exp $
+.\"
+.Dd February 16, 1988
+.Dt RPC 3
+.Sh NAME
+.Nm rpc_secure
+.Nd library routines for secure remote procedure calls
+.Sh SYNOPSIS
+.Fd #include <rpc/rpc.h>
+.Ft AUTH *
+.Fo authdes_create
+.Fa "char *name"
+.Fa "unsigned window"
+.Fa "struct sockaddr *addr"
+.Fa "des_block *ckey"
+.Fc
+.Ft int
+.Fn authdes_getucred "struct authdes_cred *adc" "uid_t *uid" "gid_t *gid" "int *grouplen" "gid_t *groups"
+.Ft int
+.Fn getnetname "char *name"
+.Ft int
+.Fn host2netname "char *name" "char *host" "char *domain"
+.Ft int
+.Fn key_decryptsession "const char *remotename" "des_block *deskey"
+.Ft int
+.Fn key_encryptsession "const char *remotename" "des_block *deskey"
+.Ft int
+.Fn key_gendes "des_block *deskey"
+.Ft int
+.Fn key_setsecret "const char *key"
+.Ft int
+.Fn netname2host "char *name" "char *host" "int hostlen"
+.Ft int
+.Fn netname2user "char *name" "uid_t *uidp" "gid_t *gidp" "int *gidlenp" "gid_t *gidlist"
+.Ft int
+.Fn user2netname "char *name" "uid_t uid" "char *domain"
+.Sh DESCRIPTION
+These routines are part of the
+.Tn RPC
+library.  They implement
+.Tn DES
+Authentication.  See
+.Xr rpc 3
+for further details about
+.Tn RPC .
+.Pp
+The
+.Fn authdes_create
+is the first of two routines which interface to the
+.Tn RPC
+secure authentication system, known as
+.Tn DES
+authentication.
+The second is
+.Fn authdes_getucred ,
+below.
+.Pp
+Note: the keyserver daemon
+.Xr keyserv 8
+must be running for the
+.Tn DES
+authentication system to work.
+.Pp
+.Fn Authdes_create ,
+used on the client side, returns an authentication handle that
+will enable the use of the secure authentication system.
+The first parameter
+.Fa name
+is the network name, or
+.Fa netname ,
+of the owner of the server process.
+This field usually
+represents a
+.Fa hostname
+derived from the utility routine
+.Fn host2netname ,
+but could also represent a user name using
+.Fn user2netname .
+The second field is window on the validity of
+the client credential, given in seconds.  A small
+window is more secure than a large one, but choosing
+too small of a window will increase the frequency of
+resynchronizations because of clock drift.
+The third
+parameter
+.Fa addr
+is optional.  If it is
+.Dv NULL ,
+then the authentication system will assume
+that the local clock is always in sync with the server's
+clock, and will not attempt resynchronizations.
+If an address
+is supplied, however, then the system will use the address
+for consulting the remote time service whenever
+resynchronization
+is required.
+This parameter is usually the
+address of the
+.Tn RPC
+server itself.
+The final parameter
+.Fa ckey
+is also optional.  If it is
+.Dv NULL ,
+then the authentication system will
+generate a random
+.Tn DES
+key to be used for the encryption of credentials.
+If it is supplied, however, then it will be used instead.
+.Pp
+.Fn Authdes_getucred ,
+the second of the two
+.Tn DES
+authentication routines,
+is used on the server side for converting a
+.Tn DES
+credential, which is
+operating system independent, into a
+.Ux
+credential.
+This routine differs from utility routine
+.Fn netname2user
+in that
+.Fn authdes_getucred
+pulls its information from a cache, and does not have to do a
+Yellow Pages lookup every time it is called to get its information.
+.Pp
+.Fn Getnetname
+installs the unique, operating-system independent netname of
+the
+caller in the fixed-length array
+.Fa name .
+Returns
+.Dv TRUE
+if it succeeds and
+.Dv FALSE
+if it fails.
+.Pp
+.Fn Host2netname
+converts from a domain-specific hostname to an
+operating-system independent netname.
+Returns
+.Dv TRUE
+if it succeeds and
+.Dv FALSE
+if it fails.
+Inverse of
+.Fn netname2host .
+.Pp
+.Fn Key_decryptsession
+is an interface to the keyserver daemon, which is associated
+with
+.Tn RPC Ns 's
+secure authentication system (
+.Tn DES
+authentication).
+User programs rarely need to call it, or its associated routines
+.Fn key_encryptsession ,
+.Fn key_gendes
+and
+.Fn key_setsecret .
+System commands such as
+.Xr login 1
+and the
+.Tn RPC
+library are the main clients of these four routines.
+.Pp
+.Fn Key_decryptsession
+takes a server netname and a
+.Tn DES
+key, and decrypts the key by
+using the the public key of the the server and the secret key
+associated with the effective uid of the calling process.  It
+is the inverse of
+.Fn key_encryptsession .
+.Pp
+.Fn Key_encryptsession
+is a keyserver interface routine.
+It
+takes a server netname and a des key, and encrypts
+it using the public key of the the server and the secret key
+associated with the effective uid of the calling process.  It
+is the inverse of
+.Fn key_decryptsession .
+.Pp
+.Fn Key_gendes
+is a keyserver interface routine.
+It
+is used to ask the keyserver for a secure conversation key.
+Choosing one
+.Qq random
+is usually not good enough,
+because
+the common ways of choosing random numbers, such as using the
+current time, are very easy to guess.
+.Pp
+.Fn Key_setsecret
+is a keyserver interface routine.
+It is used to set the key for
+the effective
+.Fa uid
+of the calling process.
+.Pp
+.Fn Netname2host
+converts from an operating-system independent netname to a
+domain-specific hostname.
+Returns
+.Dv TRUE
+if it succeeds and
+.Dv FALSE
+if it fails.  Inverse of
+.Fn host2netname .
+.Pp
+.Fn Netname2user
+converts from an operating-system independent netname to a
+domain-specific user ID.
+Returns
+.Dv TRUE
+if it succeeds and
+.Dv FALSE
+if it fails.
+Inverse of
+.Fn user2netname .
+.Pp
+.Fn User2netname
+converts from a domain-specific username to an operating-system
+independent netname.
+Returns
+.Dv TRUE
+if it succeeds and
+.Dv FALSE
+if it fails.
+Inverse of
+.Fn netname2user .
+.Sh SEE ALSO
+.Xr rpc 3 ,
+.Xr xdr 3 ,
+.Xr keyserv 8
+.Pp
+The following manuals:
+.Rs
+.%B Remote Procedure Calls: Protocol Specification
+.Re
+.Rs
+.%B Remote Procedure Call Programming Guide
+.Re
+.Rs
+.%B Rpcgen Programming Guide
+.Re
+.Rs
+.%B RPC: Remote Procedure Call Protocol Specification
+.%O RFC1050, Sun Microsystems Inc., USC-ISI
+.Re
diff --git a/services/librpc/src/rpc/rpcdname.c b/services/librpc/src/rpc/rpcdname.c
new file mode 100644
index 0000000..6482a74
--- /dev/null
+++ b/services/librpc/src/rpc/rpcdname.c
@@ -0,0 +1,84 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user or with the express written consent of
+ * Sun Microsystems, Inc.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+#if !defined(lint) && defined(SCCSIDS)
+static char sccsid[] = "@(#)rpcdname.c 1.7 91/03/11 Copyr 1989 Sun Micro";
+#endif
+
+/*
+ * rpcdname.c
+ * Gets the default domain name
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdlib.h>
+#include <unistd.h>
+#include <string.h>
+#include <rpc/rpc.h>
+
+int getdomainname(char *, size_t);
+
+#define default_domain (rtems_rpc_task_variables->rpcdname_default_domain)
+
+static char *
+get_default_domain(void)
+{
+	char temp[256];
+
+	if (default_domain)
+		return (default_domain);
+	if (getdomainname(temp, sizeof(temp)) < 0)
+		return (0);
+	if (strlen(temp) > 0) {
+		default_domain = (char *)malloc((strlen(temp)+(size_t)1));
+		if (default_domain == 0)
+			return (0);
+		(void) strcpy(default_domain, temp);
+		return (default_domain);
+	}
+	return (0);
+}
+
+/*
+ * This is a wrapper for the system call getdomainname which returns a
+ * ypclnt.h error code in the failure case.  It also checks to see that
+ * the domain name is non-null, knowing that the null string is going to
+ * get rejected elsewhere in the NIS client package.
+ */
+int
+_rpc_get_default_domain(
+	char **domain )
+{
+	if ((*domain = get_default_domain()) != 0)
+		return (0);
+	return (-1);
+}
diff --git a/services/librpc/src/rpc/rstat.1 b/services/librpc/src/rpc/rstat.1
new file mode 100644
index 0000000..6cc47c2
--- /dev/null
+++ b/services/librpc/src/rpc/rstat.1
@@ -0,0 +1,58 @@
+.\" $FreeBSD: src/lib/libc/rpc/rstat.1,v 1.5 1999/08/28 00:00:46 peter Exp $
+.\" @(#)rstat.1	2.1 88/08/03 4.0 RPCSRC
+.TH RSTAT 1 "3 August 1988"
+.SH NAME
+rstat \- remote status display
+.SH SYNOPSIS
+.B rstat
+.B host
+.SH DESCRIPTION
+.LP
+.B rstat
+displays a summary of the current system status of a particular
+.BR host .
+The output shows the current time of day, how long the system has
+been up,
+and the load averages.
+The load average numbers give the number of jobs in the run queue
+averaged over 1, 5 and 15 minutes.
+.PP
+The
+.B rstat_svc(8)
+daemon must be running on the remote host for this command to
+work.
+.B rstat
+uses an RPC protocol defined in /usr/include/rpcsvc/rstat.x.
+.SH EXAMPLE
+.RS
+.ft B
+.nf
+example% rstat otherhost
+7:36am  up 6 days, 16:45,  load average: 0.20, 0.23, 0.18
+example%
+.ft R
+.fi
+.RE
+.SH DIAGNOSTICS
+.LP
+rstat: RPC: Program not registered
+.IP
+The
+.B rstat_svc
+daemon has not been started on the remote host.
+.LP
+rstat: RPC: Timed out
+.IP
+A communication error occurred.  Either the network is
+excessively congested, or the
+.B rstat_svc
+daemon has terminated on the remote host.
+.LP
+rstat: RPC: Port mapper failure - RPC: Timed out
+.IP
+The remote host is not running the portmapper (see
+.BR portmap(8) ),
+and cannot accommodate any RPC-based services.  The host may be down.
+.SH "SEE ALSO"
+.BR portmap (8),
+.BR rstat_svc (8)
diff --git a/services/librpc/src/rpc/rstat_svc.8 b/services/librpc/src/rpc/rstat_svc.8
new file mode 100644
index 0000000..e2eae8b
--- /dev/null
+++ b/services/librpc/src/rpc/rstat_svc.8
@@ -0,0 +1,22 @@
+.\" $FreeBSD: src/lib/libc/rpc/rstat_svc.8,v 1.5 1999/08/28 00:00:47 peter Exp $
+.\" @(#)rstat_svc.8c	2.2 88/08/03 4.0 RPCSRC; from 1.10 87/09/09 SMI
+.TH RSTAT_SVC 8 "24 November 1987"
+.SH NAME
+rstat_svc \- kernel statistics server
+.SH SYNOPSIS
+.B /etc/rstat_svc
+.SH DESCRIPTION
+.LP
+.B rstat_svc
+is a server which returns performance statistics
+obtained from the kernel.
+These statistics are graphically displayed by the Sun Microsystems program,
+.BR perfmeter (1).
+The
+.B rstat_svc
+daemon is normally invoked at boot time through /etc/rc.local.
+.PP
+.B rstat_svc
+uses an RPC protocol defined in /usr/include/rpcsvc/rstat.x.
+.\" .SH "SEE ALSO"
+.\" .BR rstat (1),
diff --git a/services/librpc/src/rpc/rtems_portmapper.c b/services/librpc/src/rpc/rtems_portmapper.c
new file mode 100644
index 0000000..9d327b5
--- /dev/null
+++ b/services/librpc/src/rpc/rtems_portmapper.c
@@ -0,0 +1,500 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <rpc/rpc.h>
+#include <rpc/pmap_prot.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <malloc.h>
+#include <netdb.h>
+#include <sys/socket.h>
+#include <sys/ioctl.h>
+#include <sys/wait.h>
+#include <sys/signal.h>
+
+static void reg_service(struct svc_req *rqstp, SVCXPRT *xprt);
+static void callit(struct svc_req *rqstp, SVCXPRT *xprt);
+static struct pmaplist *pmaplist;
+static int debugging = 0;
+
+#include <rtems.h>
+#define fork()	(-1)
+
+
+static rtems_task rtems_portmapper (rtems_task_argument unused)
+{
+	SVCXPRT *xprt;
+	int sock;
+	struct sockaddr_in addr;
+	int len = sizeof(struct sockaddr_in);
+	register struct pmaplist *pml;
+
+	rtems_rpc_task_init ();
+	if ((sock = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP)) < 0) {
+		perror("portmap cannot create socket");
+		rtems_task_delete (RTEMS_SELF);
+	}
+
+	addr.sin_addr.s_addr = 0;
+	addr.sin_family = AF_INET;
+	addr.sin_port = htons(PMAPPORT);
+	if (bind(sock, (struct sockaddr *)&addr, len) != 0) {
+		perror("portmap cannot bind");
+		close (sock);
+		rtems_task_delete (RTEMS_SELF);
+	}
+
+	if ((xprt = svcudp_create(sock)) == (SVCXPRT *)NULL) {
+		fprintf(stderr, "couldn't do udp_create\n");
+		close (sock);
+		rtems_task_delete (RTEMS_SELF);
+	}
+	/* make an entry for ourself */
+	pml = (struct pmaplist *)malloc(sizeof(struct pmaplist));
+	pml->pml_next = 0;
+	pml->pml_map.pm_prog = PMAPPROG;
+	pml->pml_map.pm_vers = PMAPVERS;
+	pml->pml_map.pm_prot = IPPROTO_UDP;
+	pml->pml_map.pm_port = PMAPPORT;
+	pmaplist = pml;
+
+	if ((sock = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) < 0) {
+		perror("portmap cannot create socket");
+		close (sock);
+		rtems_task_delete (RTEMS_SELF);
+	}
+	if (bind(sock, (struct sockaddr *)&addr, len) != 0) {
+		perror("portmap cannot bind");
+		close (sock);
+		rtems_task_delete (RTEMS_SELF);
+	}
+	if ((xprt = svctcp_create(sock, RPCSMALLMSGSIZE, RPCSMALLMSGSIZE))
+	    == (SVCXPRT *)NULL) {
+		fprintf(stderr, "couldn't do tcp_create\n");
+		close (sock);
+		rtems_task_delete (RTEMS_SELF);
+	}
+	/* make an entry for ourself */
+	pml = (struct pmaplist *)malloc(sizeof(struct pmaplist));
+	pml->pml_map.pm_prog = PMAPPROG;
+	pml->pml_map.pm_vers = PMAPVERS;
+	pml->pml_map.pm_prot = IPPROTO_TCP;
+	pml->pml_map.pm_port = PMAPPORT;
+	pml->pml_next = pmaplist;
+	pmaplist = pml;
+
+	(void)svc_register(xprt, PMAPPROG, PMAPVERS, reg_service, FALSE);
+
+	svc_run();
+	fprintf(stderr, "run_svc returned unexpectedly\n");
+	close (sock);
+	rtems_task_delete (RTEMS_SELF);
+}
+
+static struct pmaplist *
+find_service(
+  u_long prog,
+  u_long vers,
+  int prot )
+{
+  register struct pmaplist *hit = NULL;
+  register struct pmaplist *pml;
+
+  for (pml = pmaplist; pml != NULL; pml = pml->pml_next) {
+	if ((pml->pml_map.pm_prog != prog) ||
+		(pml->pml_map.pm_prot != prot))
+		continue;
+	hit = pml;
+	if (pml->pml_map.pm_vers == vers)
+	    break;
+  }
+  return (hit);
+}
+
+/* 
+ * 1 OK, 0 not
+ */
+static void reg_service(
+	struct svc_req *rqstp,
+	SVCXPRT *xprt )
+{
+	struct pmap reg;
+	struct pmaplist *pml, *prevpml, *fnd;
+	int ans, port;
+	caddr_t t;
+	
+#ifdef DEBUG
+	fprintf(stderr, "server: about do a switch\n");
+#endif
+	switch (rqstp->rq_proc) {
+
+	case PMAPPROC_NULL:
+		/*
+		 * Null proc call
+		 */
+		if ((!svc_sendreply(xprt, (xdrproc_t) xdr_void, NULL)) &&
+		     debugging) {
+			abort();
+		}
+		break;
+
+	case PMAPPROC_SET:
+		/*
+		 * Set a program,version to port mapping
+		 */
+		if (!svc_getargs(xprt, (xdrproc_t) xdr_pmap, (caddr_t)&reg))
+			svcerr_decode(xprt);
+		else {
+			/*
+			 * check to see if already used
+			 * find_service returns a hit even if
+			 * the versions don't match, so check for it
+			 */
+			fnd = find_service(reg.pm_prog, reg.pm_vers, reg.pm_prot);
+			if (fnd && fnd->pml_map.pm_vers == reg.pm_vers) {
+				if (fnd->pml_map.pm_port == reg.pm_port) {
+					ans = 1;
+					goto done;
+				}
+				else {
+					ans = 0;
+					goto done;
+				}
+			} else {
+				/* 
+				 * add to END of list
+				 */
+				pml = (struct pmaplist *)
+				    malloc(sizeof(struct pmaplist));
+				pml->pml_map = reg;
+				pml->pml_next = 0;
+				if (pmaplist == 0) {
+					pmaplist = pml;
+				} else {
+					for (fnd= pmaplist; fnd->pml_next != 0;
+					    fnd = fnd->pml_next);
+					fnd->pml_next = pml;
+				}
+				ans = 1;
+			}
+		done:
+			if ((!svc_sendreply(xprt, (xdrproc_t) xdr_long, (caddr_t)&ans)) &&
+			    debugging) {
+				fprintf(stderr, "svc_sendreply\n");
+				abort();
+			}
+		}
+		break;
+
+	case PMAPPROC_UNSET:
+		/*
+		 * Remove a program,version to port mapping.
+		 */
+		if (!svc_getargs(xprt, (xdrproc_t) xdr_pmap, (caddr_t)&reg))
+			svcerr_decode(xprt);
+		else {
+			ans = 0;
+			for (prevpml = NULL, pml = pmaplist; pml != NULL; ) {
+				if ((pml->pml_map.pm_prog != reg.pm_prog) ||
+					(pml->pml_map.pm_vers != reg.pm_vers)) {
+					/* both pml & prevpml move forwards */
+					prevpml = pml;
+					pml = pml->pml_next;
+					continue;
+				}
+				/* found it; pml moves forward, prevpml stays */
+				ans = 1;
+				t = (caddr_t)pml;
+				pml = pml->pml_next;
+				if (prevpml == NULL)
+					pmaplist = pml;
+				else
+					prevpml->pml_next = pml;
+				free(t);
+			}
+			if ((!svc_sendreply(xprt, (xdrproc_t) xdr_long, (caddr_t)&ans)) &&
+			    debugging) {
+				fprintf(stderr, "svc_sendreply\n");
+				abort();
+			}
+		}
+		break;
+
+	case PMAPPROC_GETPORT:
+		/*
+		 * Lookup the mapping for a program,version and return its port
+		 */
+		if (!svc_getargs(xprt, (xdrproc_t) xdr_pmap, (caddr_t)&reg))
+			svcerr_decode(xprt);
+		else {
+			fnd = find_service(reg.pm_prog, reg.pm_vers, reg.pm_prot);
+			if (fnd)
+				port = fnd->pml_map.pm_port;
+			else
+				port = 0;
+			if ((!svc_sendreply(xprt, (xdrproc_t) xdr_long, (caddr_t)&port)) &&
+			    debugging) {
+				fprintf(stderr, "svc_sendreply\n");
+				abort();
+			}
+		}
+		break;
+
+	case PMAPPROC_DUMP:
+		/*
+		 * Return the current set of mapped program,version
+		 */
+		if (!svc_getargs(xprt, (xdrproc_t) xdr_void, NULL))
+			svcerr_decode(xprt);
+		else {
+			if ((!svc_sendreply(xprt, (xdrproc_t) xdr_pmaplist,
+			    (caddr_t)&pmaplist)) && debugging) {
+				fprintf(stderr, "svc_sendreply\n");
+				abort();
+			}
+		}
+		break;
+
+	case PMAPPROC_CALLIT:
+		/*
+		 * Calls a procedure on the local machine.  If the requested
+		 * procedure is not registered this procedure does not return
+		 * error information!!
+		 * This procedure is only supported on rpc/udp and calls via 
+		 * rpc/udp.  It passes null authentication parameters.
+		 */
+		callit(rqstp, xprt);
+		break;
+
+	default:
+		svcerr_noproc(xprt);
+		break;
+	}
+}
+
+
+/*
+ * Stuff for the rmtcall service
+ */
+#define ARGSIZE 9000
+
+struct encap_parms {
+	u_long arglen;
+	char *args;
+};
+
+static bool_t
+xdr_encap_parms(
+	XDR *xdrs,
+	struct encap_parms *epp )
+{
+
+	u_int temp_epp_arglen = epp->arglen;
+	return (xdr_bytes(xdrs, &(epp->args), &temp_epp_arglen, ARGSIZE));
+}
+
+struct rmtcallargs {
+	u_long	rmt_prog;
+	u_long	rmt_vers;
+	u_long	rmt_port;
+	u_long	rmt_proc;
+	struct encap_parms rmt_args;
+};
+
+static bool_t
+xdr_rmtcall_args(
+	register XDR *xdrs,
+	register struct rmtcallargs *cap )
+{
+
+	/* does not get a port number */
+	if (xdr_u_long(xdrs, &(cap->rmt_prog)) &&
+	    xdr_u_long(xdrs, &(cap->rmt_vers)) &&
+	    xdr_u_long(xdrs, &(cap->rmt_proc))) {
+		return (xdr_encap_parms(xdrs, &(cap->rmt_args)));
+	}
+	return (FALSE);
+}
+
+static bool_t
+xdr_rmtcall_result(
+	register XDR *xdrs,
+	register struct rmtcallargs *cap )
+{
+	if (xdr_u_long(xdrs, &(cap->rmt_port)))
+		return (xdr_encap_parms(xdrs, &(cap->rmt_args)));
+	return (FALSE);
+}
+
+/*
+ * only worries about the struct encap_parms part of struct rmtcallargs.
+ * The arglen must already be set!!
+ */
+static bool_t
+xdr_opaque_parms(
+	XDR *xdrs,
+	void *args,
+	... )
+{
+        struct rmtcallargs *cap = (struct rmtcallargs *) args;
+
+	return (xdr_opaque(xdrs, cap->rmt_args.args, cap->rmt_args.arglen));
+}
+
+/*
+ * This routine finds and sets the length of incoming opaque paraters
+ * and then calls xdr_opaque_parms.
+ */
+static bool_t
+xdr_len_opaque_parms(
+	XDR *xdrs,
+	void *args, 
+	... )
+{
+        struct rmtcallargs *cap = (struct rmtcallargs *) args;
+	register u_int beginpos, lowpos, highpos, currpos, pos;
+
+	beginpos = lowpos = pos = xdr_getpos(xdrs);
+	highpos = lowpos + ARGSIZE;
+	while ((int)(highpos - lowpos) >= 0) {
+		currpos = (lowpos + highpos) / 2;
+		if (xdr_setpos(xdrs, currpos)) {
+			pos = currpos;
+			lowpos = currpos + 1;
+		} else {
+			highpos = currpos - 1;
+		}
+	}
+	xdr_setpos(xdrs, beginpos);
+	cap->rmt_args.arglen = pos - beginpos;
+	return (xdr_opaque_parms(xdrs, cap));
+}
+
+/*
+ * Call a remote procedure service
+ * This procedure is very quiet when things go wrong.
+ * The proc is written to support broadcast rpc.  In the broadcast case,
+ * a machine should shut-up instead of complain, less the requestor be
+ * overrun with complaints at the expense of not hearing a valid reply ...
+ *
+ * This now forks so that the program & process that it calls can call 
+ * back to the portmapper.
+ */
+static void
+callit(
+	struct svc_req *rqstp,
+	SVCXPRT *xprt )
+{
+	struct rmtcallargs a;
+	struct pmaplist *pml;
+	u_short port;
+	struct sockaddr_in me;
+	int pid, socket = -1;
+	CLIENT *client;
+	struct authunix_parms *au = (struct authunix_parms *)rqstp->rq_clntcred;
+	struct timeval timeout;
+	char buf[ARGSIZE];
+
+	timeout.tv_sec = 5;
+	timeout.tv_usec = 0;
+	a.rmt_args.args = buf;
+	if (!svc_getargs(xprt, (xdrproc_t) xdr_rmtcall_args, (caddr_t)&a))
+	    return;
+	if ((pml = find_service(a.rmt_prog, a.rmt_vers, IPPROTO_UDP)) == NULL)
+	    return;
+	/*
+	 * fork a child to do the work.  Parent immediately returns.
+	 * Child exits upon completion.
+	 */
+	if ((pid = fork()) != 0) {
+		if (debugging && (pid < 0)) {
+			fprintf(stderr, "portmap CALLIT: cannot fork.\n");
+		}
+		return;
+	}
+	port = pml->pml_map.pm_port;
+	get_myaddress(&me);
+	me.sin_port = htons(port);
+	client = clntudp_create(&me, a.rmt_prog, a.rmt_vers, timeout, &socket);
+	if (client != (CLIENT *)NULL) {
+		if (rqstp->rq_cred.oa_flavor == AUTH_UNIX) {
+			client->cl_auth = authunix_create(au->aup_machname,
+			   au->aup_uid, au->aup_gid, au->aup_len, au->aup_gids);
+		}
+		a.rmt_port = (u_long)port;
+		if (clnt_call(client, a.rmt_proc, xdr_opaque_parms, &a,
+		    xdr_len_opaque_parms, &a, timeout) == RPC_SUCCESS) {
+			svc_sendreply(xprt, (xdrproc_t) xdr_rmtcall_result, (caddr_t)&a);
+		}
+		AUTH_DESTROY(client->cl_auth);
+		clnt_destroy(client);
+	}
+	(void)close(socket);
+	exit(0);
+}
+
+/*
+ * Start the RPC portmapper
+ */
+int rtems_rpc_start_portmapper (int priority)
+{
+	rtems_mode mode;
+	rtems_status_code sc;
+	rtems_id tid;
+	static int started;
+
+	rtems_task_mode (RTEMS_NO_PREEMPT, RTEMS_PREEMPT_MASK, &mode);
+	if (started) {
+		rtems_task_mode (mode, RTEMS_PREEMPT_MASK, &mode);
+		return RTEMS_SUCCESSFUL;
+	}
+	sc = rtems_task_create (rtems_build_name('P', 'M', 'A', 'P'),
+		priority,
+		ARGSIZE + 8000,
+		RTEMS_PREEMPT|RTEMS_NO_TIMESLICE|RTEMS_NO_ASR|RTEMS_INTERRUPT_LEVEL(0),
+		RTEMS_NO_FLOATING_POINT|RTEMS_LOCAL,
+		&tid);
+	if (sc != RTEMS_SUCCESSFUL) {
+		rtems_task_mode (mode, RTEMS_PREEMPT_MASK, &mode);
+		return sc;
+	}
+	sc = rtems_task_start (tid, rtems_portmapper, 0);
+	if (sc != RTEMS_SUCCESSFUL) {
+		rtems_task_mode (mode, RTEMS_PREEMPT_MASK, &mode);
+		return sc;
+	}
+	started = 1;
+	rtems_task_mode (mode, RTEMS_PREEMPT_MASK, &mode);
+	return RTEMS_SUCCESSFUL;
+}
diff --git a/services/librpc/src/rpc/rtems_rpc.c b/services/librpc/src/rpc/rtems_rpc.c
new file mode 100644
index 0000000..5d31f12
--- /dev/null
+++ b/services/librpc/src/rpc/rtems_rpc.c
@@ -0,0 +1,95 @@
+/*
+ * RTEMS multi-tasking support
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <rpc/rpc.h>
+#include <rtems.h>
+#include <stdlib.h>
+
+/*
+ * RPC variables for single-thread
+ */
+static struct _rtems_rpc_task_variables rpc_default = {
+	-1,		/* svc_maxfd */
+	{{0}},		/* svc_svc_fdset */
+	NULL,		/* svc_xports */
+	0,		/* svc_xportssize */
+	0,		/* svc__svc_fdsetsize */		
+	0,		/* svc__svc_fdset */
+	NULL,		/* svc_svc_head */
+	0,		/* clnt_perror_buf */
+	0,		/* clnt_raw_private */
+	0,		/* call_rpc_private */
+	0,		/* svc_raw_private */
+
+	0,		/* svc_simple_proglst */
+	0,		/* svc_simple_pl */
+	0,		/* svc_simple_transp */
+
+	0,		/* rpcdname_default_domain */
+	0		/* svc_auths_Auths */
+};
+
+/*
+ * RPC values for initializing a new per-task set of variables
+ */
+static const struct _rtems_rpc_task_variables rpc_init = {
+	-1,		/* svc_maxfd */
+	{{0}},		/* svc_svc_fdset */
+	NULL,		/* svc_xports */
+	0,		/* svc_xportssize */
+	0,		/* svc__svc_fdsetsize */		
+	0,		/* svc__svc_fdset */
+	NULL,		/* svc_svc_head */
+	0,		/* clnt_perror_buf */
+	0,		/* clnt_raw_private */
+	0,		/* call_rpc_private */
+	0,		/* svc_raw_private */
+
+	0,		/* svc_simple_proglst */
+	0,		/* svc_simple_pl */
+	0,		/* svc_simple_transp */
+
+	0,		/* rpcdname_default_domain */
+	0		/* svc_auths_Auths */
+};
+
+/*
+ * Per-task pointer to RPC data
+ */
+struct _rtems_rpc_task_variables *rtems_rpc_task_variables = &rpc_default;
+
+/*
+ * Set up per-task RPC variables
+ */
+int rtems_rpc_task_init (void)
+{
+	rtems_status_code sc;
+	struct _rtems_rpc_task_variables *tvp;
+
+	if (rtems_rpc_task_variables == &rpc_default) {
+		tvp = malloc (sizeof *tvp);
+		if (tvp == NULL)
+			return RTEMS_NO_MEMORY;
+		/*
+		 * FIXME: Should have destructor which cleans up
+		 * all RPC stuff:
+		 *	- Close all files
+		 *	- Go through and free linked list elements
+		 *	- Free other allocated memory (e.g. clnt_perror_buf)
+		 */
+		sc = rtems_task_variable_add (
+			RTEMS_SELF, (void *)&rtems_rpc_task_variables, NULL);
+		if (sc != RTEMS_SUCCESSFUL) {
+			free (tvp);
+			return sc;
+		}
+		*tvp = rpc_init;
+		rtems_rpc_task_variables = tvp;
+	}
+	return RTEMS_SUCCESSFUL;
+}
diff --git a/services/librpc/src/rpc/rtime.3 b/services/librpc/src/rpc/rtime.3
new file mode 100644
index 0000000..ad3e538
--- /dev/null
+++ b/services/librpc/src/rpc/rtime.3
@@ -0,0 +1,47 @@
+.\" @(#)rtime.3n	2.1 88/08/08 4.0 RPCSRC; from 1.5 88/02/08 SMI
+.\" $FreeBSD: src/lib/libc/rpc/rtime.3,v 1.4 2000/03/02 09:13:48 sheldonh Exp $
+.\"
+.TH RTIME 3  "22 November 1987"
+.SH NAME
+rtime \- get remote time
+.SH SYNOPSIS
+.nf
+.B #include <sys/types.h>
+.B #include <sys/time.h>
+.B #include <netinet/in.h>
+.LP
+.B int rtime(addrp, timep, timeout)
+.B struct sockaddr_in \(**addrp;
+.B struct timeval \(**timep;
+.B struct timeval \(**timeout;
+.fi
+.SH DESCRIPTION
+.B rtime(\|)
+consults the Internet Time Server at the address pointed to by
+.I addrp
+and returns the remote time in the
+.B timeval
+struct pointed to by
+.IR timep .
+Normally, the
+.SM UDP
+protocol is used when consulting the Time Server.
+The
+.I timeout
+parameter specifies how long the
+routine should wait before giving
+up when waiting for a reply.  If
+.I timeout
+is specified as
+.SM NULL\s0,
+however, the routine will instead use
+.SM TCP
+and block until a reply is received from the time server.
+.LP
+The routine returns 0 if it is successful.
+Otherwise,
+it returns \-1 and
+.B errno
+is set to reflect the cause of the error.
+.SH "SEE ALSO"
+.BR timed (8c)
diff --git a/services/librpc/src/rpc/rtime.c b/services/librpc/src/rpc/rtime.c
new file mode 100644
index 0000000..af63d5b
--- /dev/null
+++ b/services/librpc/src/rpc/rtime.c
@@ -0,0 +1,163 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+/*
+ * Copyright (c) 1988 by Sun Microsystems, Inc.
+
+ */
+
+/*
+ * rtime - get time from remote machine
+ *
+ * gets time, obtaining value from host
+ * on the udp/time socket.  Since timeserver returns
+ * with time of day in seconds since Jan 1, 1900,  must
+ * subtract seconds before Jan 1, 1970 to get
+ * what unix uses.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdlib.h>
+#include <string.h>
+#include <unistd.h>
+#include <errno.h>
+#include <sys/types.h>
+#include <sys/socket.h>
+#include <sys/time.h>
+#include <netinet/in.h>
+#include <stdio.h>
+#include <netdb.h>
+#include <sys/select.h>
+#include <inttypes.h>
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/* from: static char sccsid[] = 	"@(#)rtime.c	2.2 88/08/10 4.0 RPCSRC; from 1.8 88/02/08 SMI"; */
+static const char rcsid[] = "$FreeBSD: src/lib/libc/rpc/rtime.c,v 1.5 2000/01/27 23:06:41 jasone Exp $";
+#endif
+
+extern int _rpc_dtablesize( void );
+
+#define NYEARS	(UINT32_C(1970) - UINT32_C(1900))
+#define TOFFSET (UINT32_C(60)*UINT32_C(60)*UINT32_C(24)*(UINT32_C(365)*NYEARS + (NYEARS/UINT32_C(4))))
+
+static void do_close( int );
+
+int
+rtime(
+	struct sockaddr_in *addrp,
+	struct timeval *timep,
+	struct timeval *timeout )
+{
+	int s;
+	fd_set readfds;
+	int res;
+	uint32_t thetime;
+	struct sockaddr_in from;
+	socklen_t fromlen;
+	int type;
+	struct servent *serv;
+
+	if (timeout == NULL) {
+		type = SOCK_STREAM;
+	} else {
+		type = SOCK_DGRAM;
+	}
+	s = socket(AF_INET, type, 0);
+	if (s < 0) {
+		return(-1);
+	}
+	addrp->sin_family = AF_INET;
+
+	/* TCP and UDP port are the same in this case */
+	if ((serv = getservbyname("time", "tcp")) == NULL) {
+		return(-1);
+	}
+
+	addrp->sin_port = serv->s_port;
+
+	if (type == SOCK_DGRAM) {
+		res = sendto(s, (char *)&thetime, sizeof(thetime), 0, 
+			     (struct sockaddr *)addrp, sizeof(*addrp));
+		if (res < 0) {
+			do_close(s);
+			return(-1);	
+		}
+		do {
+			FD_ZERO(&readfds);
+			FD_SET(s, &readfds);
+			res = select(_rpc_dtablesize(), &readfds,
+				     (fd_set *)NULL, (fd_set *)NULL, timeout);
+		} while (res < 0 && errno == EINTR);
+		if (res <= 0) {
+			if (res == 0) {
+				errno = ETIMEDOUT;
+			}
+			do_close(s);
+			return(-1);	
+		}
+		fromlen = sizeof(from);
+		res = recvfrom(s, (char *)&thetime, sizeof(thetime), 0, 
+			       (struct sockaddr *)&from, &fromlen);
+		do_close(s);
+		if (res < 0) {
+			return(-1);	
+		}
+	} else {
+		if (connect(s, (struct sockaddr *)addrp, sizeof(*addrp)) < 0) {
+			do_close(s);
+			return(-1);
+		}
+		res = _RPC_read(s, (char *)&thetime, sizeof(thetime));
+		do_close(s);
+		if (res < 0) {
+			return(-1);
+		}
+	}
+	if (res != sizeof(thetime)) {
+		errno = EIO;
+		return(-1);	
+	}
+	thetime = ntohl(thetime);
+	timep->tv_sec = thetime - TOFFSET;
+	timep->tv_usec = 0;
+	return(0);
+}
+
+static void
+do_close(int s)
+{
+	int save;
+
+	save = errno;
+	(void)_RPC_close(s);
+	errno = save;
+}
diff --git a/services/librpc/src/rpc/svc.c b/services/librpc/src/rpc/svc.c
new file mode 100644
index 0000000..9cc5cf3
--- /dev/null
+++ b/services/librpc/src/rpc/svc.c
@@ -0,0 +1,499 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)svc.c 1.44 88/02/08 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)svc.c	2.4 88/08/11 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/svc.c,v 1.14 1999/08/28 00:00:48 peter Exp $";
+#endif
+
+/*
+ * svc.c, Server-side remote procedure call interface.
+ *
+ * There are two sets of procedures here.  The xprt routines are
+ * for handling transport handles.  The svc routines handle the
+ * list of service routines.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <string.h>
+#ifdef HAVE_STRINGS_H
+#include <strings.h> /* for ffs */
+#endif
+#include <stdlib.h>
+#include <sys/errno.h>
+#include <rpc/rpc.h>
+#include <rpc/pmap_clnt.h>
+
+#define xports (rtems_rpc_task_variables->svc_xports)
+#define xportssize (rtems_rpc_task_variables->svc_xportssize)
+
+#define NULL_SVC ((struct svc_callout *)0)
+#define	RQCRED_SIZE	400		/* this size is excessive */
+
+#define max(a, b) (a > b ? a : b)
+
+/*
+ * The services list
+ * Each entry represents a set of procedures (an rpc program).
+ * The dispatch routine takes request structs and runs the
+ * apropriate procedure.
+ */
+struct svc_callout {
+	struct svc_callout *sc_next;
+	u_long		    sc_prog;
+	u_long		    sc_vers;
+	void		    (*sc_dispatch)(struct svc_req *r, SVCXPRT *xprt);
+};
+#define svc_head (rtems_rpc_task_variables->svc_svc_head)
+
+static struct svc_callout *svc_find(u_long prog, u_long vers, 
+  struct svc_callout **prev);
+
+/* ***************  SVCXPRT related stuff **************** */
+
+/*
+ * Activate a transport handle.
+ */
+void
+xprt_register(
+	SVCXPRT *xprt )
+{
+	register int sock = xprt->xp_sock;
+
+	if (sock + 1 > __svc_fdsetsize) {
+		int bytes = sizeof (fd_set);
+		fd_set *fds;
+
+		fds = (fd_set *)malloc(bytes);
+		memset(fds, 0, bytes);
+		if (__svc_fdset) {
+			memcpy(fds, __svc_fdset, bytes);
+			free(__svc_fdset);
+		}
+		__svc_fdset = fds;
+		__svc_fdsetsize = bytes * NBBY;
+	}
+
+	if (sock < FD_SETSIZE)
+		FD_SET(sock, &svc_fdset);
+	FD_SET(sock, __svc_fdset);
+
+	if (xports == NULL || sock + 1 > xportssize) {
+		SVCXPRT **xp;
+		int size = FD_SETSIZE;
+
+		if (sock + 1 > size)
+			size = sock + 1;
+		xp = (SVCXPRT **)mem_alloc(size * sizeof(SVCXPRT *));
+		memset(xp, 0, size * sizeof(SVCXPRT *));
+		if (xports) {
+			memcpy(xp, xports, xportssize * sizeof(SVCXPRT *));
+			free(xports);
+		}
+		xportssize = size;
+		xports = xp;
+	}
+	xports[sock] = xprt;
+	svc_maxfd = max(svc_maxfd, sock);
+}
+
+/*
+ * De-activate a transport handle.
+ */
+void
+xprt_unregister(
+	SVCXPRT *xprt )
+{
+	register int sock = xprt->xp_sock;
+
+	if (xports[sock] == xprt) {
+		xports[sock] = (SVCXPRT *)0;
+		if (sock < FD_SETSIZE)
+			FD_CLR(sock, &svc_fdset);
+		FD_CLR(sock, __svc_fdset);
+		if (sock == svc_maxfd) {
+			for (svc_maxfd--; svc_maxfd >= 0; svc_maxfd--)
+				if (xports[svc_maxfd])
+					break;
+		}
+		/*
+		 * XXX could use svc_maxfd as a hint to
+		 * decrease the size of __svc_fdset
+		 */
+	}
+}
+
+
+/* ********************** CALLOUT list related stuff ************* */
+
+/*
+ * Add a service program to the callout list.
+ * The dispatch routine will be called when a rpc request for this
+ * program number comes in.
+ */
+bool_t
+svc_register(
+	SVCXPRT *xprt,
+	u_long prog,
+	u_long vers,
+	void (*dispatch)(struct svc_req *r, SVCXPRT *xprt),
+	int protocol )
+{
+	struct svc_callout *prev;
+	register struct svc_callout *s;
+
+	if ((s = svc_find(prog, vers, &prev)) != NULL_SVC) {
+		if (s->sc_dispatch == dispatch)
+			goto pmap_it;  /* he is registering another xptr */
+		return (FALSE);
+	}
+	s = (struct svc_callout *)mem_alloc(sizeof(struct svc_callout));
+	if (s == (struct svc_callout *)0) {
+		return (FALSE);
+	}
+	s->sc_prog = prog;
+	s->sc_vers = vers;
+	s->sc_dispatch = dispatch;
+	s->sc_next = svc_head;
+	svc_head = s;
+pmap_it:
+	/* now register the information with the local binder service */
+	if (protocol) {
+		return (pmap_set(prog, vers, protocol, xprt->xp_port));
+	}
+	return (TRUE);
+}
+
+/*
+ * Remove a service program from the callout list.
+ */
+void
+svc_unregister(
+	u_long prog,
+	u_long vers )
+{
+	struct svc_callout *prev;
+	register struct svc_callout *s;
+
+	if ((s = svc_find(prog, vers, &prev)) == NULL_SVC)
+		return;
+	if (prev == NULL_SVC) {
+		svc_head = s->sc_next;
+	} else {
+		prev->sc_next = s->sc_next;
+	}
+	s->sc_next = NULL_SVC;
+	mem_free((char *) s, (u_int) sizeof(struct svc_callout));
+	/* now unregister the information with the local binder service */
+	(void)pmap_unset(prog, vers);
+}
+
+/*
+ * Search the callout list for a program number, return the callout
+ * struct.
+ */
+static struct svc_callout *
+svc_find(
+	u_long prog,
+	u_long vers,
+	struct svc_callout **prev )
+{
+	register struct svc_callout *s, *p;
+
+	p = NULL_SVC;
+	for (s = svc_head; s != NULL_SVC; s = s->sc_next) {
+		if ((s->sc_prog == prog) && (s->sc_vers == vers))
+			goto done;
+		p = s;
+	}
+done:
+	*prev = p;
+	return (s);
+}
+
+/* ******************* REPLY GENERATION ROUTINES  ************ */
+
+/*
+ * Send a reply to an rpc request
+ */
+bool_t
+svc_sendreply(
+	register SVCXPRT *xprt,
+	xdrproc_t xdr_results,
+	void *xdr_location )
+{
+	struct rpc_msg rply;
+
+	rply.rm_direction = REPLY;
+	rply.rm_reply.rp_stat = MSG_ACCEPTED;
+	rply.acpted_rply.ar_verf = xprt->xp_verf;
+	rply.acpted_rply.ar_stat = SUCCESS;
+	rply.acpted_rply.ar_results.where = xdr_location;
+	rply.acpted_rply.ar_results.proc = xdr_results;
+	return (SVC_REPLY(xprt, &rply));
+}
+
+/*
+ * No procedure error reply
+ */
+void
+svcerr_noproc(
+	register SVCXPRT *xprt )
+{
+	struct rpc_msg rply;
+
+	rply.rm_direction = REPLY;
+	rply.rm_reply.rp_stat = MSG_ACCEPTED;
+	rply.acpted_rply.ar_verf = xprt->xp_verf;
+	rply.acpted_rply.ar_stat = PROC_UNAVAIL;
+	SVC_REPLY(xprt, &rply);
+}
+
+/*
+ * Can't decode args error reply
+ */
+void
+svcerr_decode(
+	register SVCXPRT *xprt )
+{
+	struct rpc_msg rply;
+
+	rply.rm_direction = REPLY;
+	rply.rm_reply.rp_stat = MSG_ACCEPTED;
+	rply.acpted_rply.ar_verf = xprt->xp_verf;
+	rply.acpted_rply.ar_stat = GARBAGE_ARGS;
+	SVC_REPLY(xprt, &rply);
+}
+
+/*
+ * Some system error
+ */
+void
+svcerr_systemerr(
+	register SVCXPRT *xprt )
+{
+	struct rpc_msg rply;
+
+	rply.rm_direction = REPLY;
+	rply.rm_reply.rp_stat = MSG_ACCEPTED;
+	rply.acpted_rply.ar_verf = xprt->xp_verf;
+	rply.acpted_rply.ar_stat = SYSTEM_ERR;
+	SVC_REPLY(xprt, &rply);
+}
+
+/*
+ * Authentication error reply
+ */
+void
+svcerr_auth(
+	SVCXPRT *xprt,
+	enum auth_stat why )
+{
+	struct rpc_msg rply;
+
+	rply.rm_direction = REPLY;
+	rply.rm_reply.rp_stat = MSG_DENIED;
+	rply.rjcted_rply.rj_stat = AUTH_ERROR;
+	rply.rjcted_rply.rj_why = why;
+	SVC_REPLY(xprt, &rply);
+}
+
+/*
+ * Auth too weak error reply
+ */
+void
+svcerr_weakauth(
+	SVCXPRT *xprt )
+{
+
+	svcerr_auth(xprt, AUTH_TOOWEAK);
+}
+
+/*
+ * Program unavailable error reply
+ */
+void
+svcerr_noprog(
+	register SVCXPRT *xprt )
+{
+	struct rpc_msg rply;
+
+	rply.rm_direction = REPLY;
+	rply.rm_reply.rp_stat = MSG_ACCEPTED;
+	rply.acpted_rply.ar_verf = xprt->xp_verf;
+	rply.acpted_rply.ar_stat = PROG_UNAVAIL;
+	SVC_REPLY(xprt, &rply);
+}
+
+/*
+ * Program version mismatch error reply
+ */
+void
+svcerr_progvers(
+	register SVCXPRT *xprt,
+	rpcvers_t low_vers,
+	rpcvers_t high_vers )
+{
+	struct rpc_msg rply;
+
+	rply.rm_direction = REPLY;
+	rply.rm_reply.rp_stat = MSG_ACCEPTED;
+	rply.acpted_rply.ar_verf = xprt->xp_verf;
+	rply.acpted_rply.ar_stat = PROG_MISMATCH;
+	rply.acpted_rply.ar_vers.low = low_vers;
+	rply.acpted_rply.ar_vers.high = high_vers;
+	SVC_REPLY(xprt, &rply);
+}
+
+/* ******************* SERVER INPUT STUFF ******************* */
+
+/*
+ * Get server side input from some transport.
+ *
+ * Statement of authentication parameters management:
+ * This function owns and manages all authentication parameters, specifically
+ * the "raw" parameters (msg.rm_call.cb_cred and msg.rm_call.cb_verf) and
+ * the "cooked" credentials (rqst->rq_clntcred).
+ * However, this function does not know the structure of the cooked
+ * credentials, so it make the following assumptions:
+ *   a) the structure is contiguous (no pointers), and
+ *   b) the cred structure size does not exceed RQCRED_SIZE bytes.
+ * In all events, all three parameters are freed upon exit from this routine.
+ * The storage is trivially management on the call stack in user land, but
+ * is mallocated in kernel land.
+ */
+
+void
+svc_getreq(
+	int rdfds )
+{
+	fd_set readfds;
+
+	FD_ZERO(&readfds);
+	readfds.fds_bits[0] = rdfds;
+	svc_getreqset(&readfds);
+}
+
+void
+svc_getreqset(
+	fd_set *readfds )
+{
+	svc_getreqset2(readfds, FD_SETSIZE);
+}
+
+void
+svc_getreqset2(
+	fd_set *readfds,
+	int width )
+{
+	enum xprt_stat stat;
+	struct rpc_msg msg;
+	int prog_found;
+	u_long low_vers;
+	u_long high_vers;
+	struct svc_req r;
+	register SVCXPRT *xprt;
+	register int bit;
+	register int sock;
+	register fd_mask mask, *maskp;
+	char cred_area[2*MAX_AUTH_BYTES + RQCRED_SIZE];
+	msg.rm_call.cb_cred.oa_base = cred_area;
+	msg.rm_call.cb_verf.oa_base = &(cred_area[MAX_AUTH_BYTES]);
+	r.rq_clntcred = &(cred_area[2*MAX_AUTH_BYTES]);
+
+
+	maskp = readfds->fds_bits;
+	for (sock = 0; sock < width; sock += NFDBITS) {
+	    for (mask = *maskp++; (bit = ffs(mask)); mask ^= (1 << (bit - 1))) {
+		/* sock has input waiting */
+		xprt = xports[sock + bit - 1];
+		if (xprt == NULL)
+			/* But do we control sock? */
+			continue;
+		/* now receive msgs from xprtprt (support batch calls) */
+		do {
+			if (SVC_RECV(xprt, &msg)) {
+
+				/* now find the exported program and call it */
+				register struct svc_callout *s;
+				enum auth_stat why;
+
+				r.rq_xprt = xprt;
+				r.rq_prog = msg.rm_call.cb_prog;
+				r.rq_vers = msg.rm_call.cb_vers;
+				r.rq_proc = msg.rm_call.cb_proc;
+				r.rq_cred = msg.rm_call.cb_cred;
+				/* first authenticate the message */
+				if ((why= _authenticate(&r, &msg)) != AUTH_OK) {
+					svcerr_auth(xprt, why);
+					goto call_done;
+				}
+				/* now match message with a registered service*/
+				prog_found = FALSE;
+				low_vers = (u_long) - 1;
+				high_vers = 0;
+				for (s = svc_head; s != NULL_SVC; s = s->sc_next) {
+					if (s->sc_prog == r.rq_prog) {
+						if (s->sc_vers == r.rq_vers) {
+							(*s->sc_dispatch)(&r, xprt);
+							goto call_done;
+						}  /* found correct version */
+						prog_found = TRUE;
+						if (s->sc_vers < low_vers)
+							low_vers = s->sc_vers;
+						if (s->sc_vers > high_vers)
+							high_vers = s->sc_vers;
+					}   /* found correct program */
+				}
+				/*
+				 * if we got here, the program or version
+				 * is not served ...
+				 */
+				if (prog_found)
+					svcerr_progvers(xprt,
+					low_vers, high_vers);
+				else
+					 svcerr_noprog(xprt);
+				/* Fall through to ... */
+			}
+		call_done:
+			if ((stat = SVC_STAT(xprt)) == XPRT_DIED){
+				SVC_DESTROY(xprt);
+				break;
+			}
+		} while (stat == XPRT_MOREREQS);
+	    }
+	}
+}
diff --git a/services/librpc/src/rpc/svc_auth.c b/services/librpc/src/rpc/svc_auth.c
new file mode 100644
index 0000000..b498a9c
--- /dev/null
+++ b/services/librpc/src/rpc/svc_auth.c
@@ -0,0 +1,220 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+/*
+ * Copyright (c) 1986-1991 by Sun Microsystems Inc. 
+ */
+
+/* #ident	"@(#)svc_auth.c	1.16	94/04/24 SMI" */
+
+#if !defined(lint) && defined(SCCSIDS)
+#if 0
+static char sccsid[] = "@(#)svc_auth.c 1.26 89/02/07 Copyr 1984 Sun Micro";
+#else
+static const char rcsid[] =
+ "$FreeBSD: src/lib/libc/rpc/svc_auth.c,v 1.7 1999/12/29 05:04:16 peter Exp $";
+#endif
+#endif
+
+/*
+ * svc_auth.c, Server-side rpc authenticator interface.
+ *
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#ifdef _KERNEL
+#include <sys/param.h>
+#include <rpc/types.h>
+#include <rpc/xdr.h>
+#include <rpc/auth.h>
+#include <rpc/clnt.h>
+#include <rpc/rpc_msg.h>
+#include <rpc/svc.h>
+#include <rpc/svc_auth.h>
+#else
+#include <stdlib.h>
+#include <rpc/rpc.h>
+#endif
+#include <sys/types.h>
+
+/*
+ * svcauthsw is the bdevsw of server side authentication.
+ *
+ * Server side authenticators are called from authenticate by
+ * using the client auth struct flavor field to index into svcauthsw.
+ * The server auth flavors must implement a routine that looks
+ * like:
+ *
+ *	enum auth_stat
+ *	flavorx_auth(rqst, msg)
+ *		register struct svc_req *rqst;
+ *		register struct rpc_msg *msg;
+ *
+ */
+
+enum auth_stat _svcauth_null(struct svc_req *rqst, struct rpc_msg *msg);	/* no authentication */
+enum auth_stat _svcauth_unix(struct svc_req *rqst, struct rpc_msg *msg);		/* (system) unix style (uid, gids) */
+enum auth_stat _svcauth_short(struct svc_req *rqst, struct rpc_msg *msg);	/* short hand unix style */
+enum auth_stat _svcauth_des(struct svc_req *rqst, struct rpc_msg *msg);		/* des style */
+
+/* declarations to allow servers to specify new authentication flavors */
+struct authsvc {
+	int	flavor;
+	enum	auth_stat (*handler)(struct svc_req *rqst, struct rpc_msg *msg);
+	struct	authsvc	  *next;
+};
+#define Auths (rtems_rpc_task_variables->svc_auths_Auths)
+
+/*
+ * The call rpc message, msg has been obtained from the wire.  The msg contains
+ * the raw form of credentials and verifiers.  authenticate returns AUTH_OK
+ * if the msg is successfully authenticated.  If AUTH_OK then the routine also
+ * does the following things:
+ * set rqst->rq_xprt->verf to the appropriate response verifier;
+ * sets rqst->rq_client_cred to the "cooked" form of the credentials.
+ *
+ * NB: rqst->rq_cxprt->verf must be pre-alloctaed;
+ * its length is set appropriately.
+ *
+ * The caller still owns and is responsible for msg->u.cmb.cred and
+ * msg->u.cmb.verf.  The authentication system retains ownership of
+ * rqst->rq_client_cred, the cooked credentials.
+ *
+ * There is an assumption that any flavour less than AUTH_NULL is
+ * invalid.
+ */
+enum auth_stat
+_authenticate(
+	struct svc_req *rqst,
+	struct rpc_msg *msg )
+{
+	register int cred_flavor;
+	register struct authsvc *asp;
+
+	rqst->rq_cred = msg->rm_call.cb_cred;
+	rqst->rq_xprt->xp_verf.oa_flavor = _null_auth.oa_flavor;
+	rqst->rq_xprt->xp_verf.oa_length = 0;
+	cred_flavor = rqst->rq_cred.oa_flavor;
+	switch (cred_flavor) {
+	case AUTH_NULL:
+		return(_svcauth_null(rqst, msg));
+	case AUTH_UNIX:
+		return(_svcauth_unix(rqst, msg));
+	case AUTH_SHORT:
+		return(_svcauth_short(rqst, msg));
+	/*
+	 * We leave AUTH_DES turned off by default because svcauth_des()
+	 * needs getpublickey(), which is in librpcsvc, not libc. If we
+ 	 * included AUTH_DES as a built-in flavor, programs that don't
+	 * have -lrpcsvc in their Makefiles wouldn't link correctly, even
+	 * though they don't use AUTH_DES. And I'm too lazy to go through
+	 * the tree looking for all of them.
+	 */
+#ifdef DES_BUILTIN
+	case AUTH_DES:
+		return(_svcauth_des(rqst, msg));
+#endif
+	}
+
+	/* flavor doesn't match any of the builtin types, so try new ones */
+	for (asp = Auths; asp; asp = asp->next) {
+		if (asp->flavor == cred_flavor) {
+			enum auth_stat as;
+
+			as = (*asp->handler)(rqst, msg);
+			return (as);
+		}
+	}
+
+	return (AUTH_REJECTEDCRED);
+}
+
+/*ARGSUSED*/
+enum auth_stat
+_svcauth_null(
+	struct svc_req *rqst,
+	struct rpc_msg *msg)
+{
+	return (AUTH_OK);
+}
+
+/*
+ *  Allow the rpc service to register new authentication types that it is
+ *  prepared to handle.  When an authentication flavor is registered,
+ *  the flavor is checked against already registered values.  If not
+ *  registered, then a new Auths entry is added on the list.
+ *
+ *  There is no provision to delete a registration once registered.
+ *
+ *  This routine returns:
+ *	 0 if registration successful
+ *	 1 if flavor already registered
+ *	-1 if can't register (errno set)
+ */
+
+int
+svc_auth_reg(
+	int cred_flavor,
+	enum auth_stat (*handler)(struct svc_req *rqst, struct rpc_msg *msg))
+{
+	register struct authsvc *asp;
+
+	switch (cred_flavor) {
+	    case AUTH_NULL:
+	    case AUTH_UNIX:
+	    case AUTH_SHORT:
+#ifdef DES_BUILTIN
+	    case AUTH_DES:
+#endif
+		/* already registered */
+		return (1);
+
+	    default:
+		for (asp = Auths; asp; asp = asp->next) {
+			if (asp->flavor == cred_flavor) {
+				/* already registered */
+				return (1);
+			}
+		}
+
+		/* this is a new one, so go ahead and register it */
+		asp = (struct authsvc *)mem_alloc(sizeof (*asp));
+		if (asp == NULL) {
+			return (-1);
+		}
+		asp->flavor = cred_flavor;
+		asp->handler = handler;
+		asp->next = Auths;
+		Auths = asp;
+		break;
+	}
+	return (0);
+}
diff --git a/services/librpc/src/rpc/svc_auth_unix.c b/services/librpc/src/rpc/svc_auth_unix.c
new file mode 100644
index 0000000..ce39599
--- /dev/null
+++ b/services/librpc/src/rpc/svc_auth_unix.c
@@ -0,0 +1,152 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)svc_auth_unix.c 1.28 88/02/08 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)svc_auth_unix.c	2.3 88/08/01 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/svc_auth_unix.c,v 1.8 1999/08/28 00:00:49 peter Exp $";
+#endif
+
+/*
+ * svc_auth_unix.c
+ * Handles UNIX flavor authentication parameters on the service side of rpc.
+ * There are two svc auth implementations here: AUTH_UNIX and AUTH_SHORT.
+ * _svcauth_unix does full blown unix style uid,gid+gids auth,
+ * _svcauth_short uses a shorthand auth to index into a cache of longhand auths.
+ * Note: the shorthand has been gutted for efficiency.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdio.h>
+#include <string.h>
+#include <rpc/rpc.h>
+
+/*
+ * Unix longhand authenticator
+ */
+enum auth_stat
+_svcauth_unix(
+	struct svc_req *rqst,
+	struct rpc_msg *msg )
+{
+	register enum auth_stat stat;
+	XDR xdrs;
+	register struct authunix_parms *aup;
+	register int32_t *buf;
+	struct area {
+		struct authunix_parms area_aup;
+		char area_machname[MAX_MACHINE_NAME+1];
+		int area_gids[NGRPS];
+	} *area;
+	u_int auth_len;
+	int str_len, gid_len;
+	register int i;
+
+	area = (struct area *) rqst->rq_clntcred;
+	aup = &area->area_aup;
+	aup->aup_machname = area->area_machname;
+	aup->aup_gids = area->area_gids;
+	auth_len = (u_int)msg->rm_call.cb_cred.oa_length;
+	xdrmem_create(&xdrs, msg->rm_call.cb_cred.oa_base, auth_len,XDR_DECODE);
+	buf = XDR_INLINE(&xdrs, auth_len);
+	if (buf != NULL) {
+		aup->aup_time = IXDR_GET_LONG(buf);
+		str_len = IXDR_GET_U_LONG(buf);
+		if (str_len > MAX_MACHINE_NAME) {
+			stat = AUTH_BADCRED;
+			goto done;
+		}
+		memcpy(aup->aup_machname, (caddr_t)buf, (u_int)str_len);
+		aup->aup_machname[str_len] = 0;
+		str_len = RNDUP(str_len);
+		buf += str_len / sizeof (int32_t);
+		aup->aup_uid = IXDR_GET_LONG(buf);
+		aup->aup_gid = IXDR_GET_LONG(buf);
+		gid_len = IXDR_GET_U_LONG(buf);
+		if (gid_len > NGRPS) {
+			stat = AUTH_BADCRED;
+			goto done;
+		}
+		aup->aup_len = gid_len;
+		for (i = 0; i < gid_len; i++) {
+			aup->aup_gids[i] = IXDR_GET_LONG(buf);
+		}
+		/*
+		 * five is the smallest unix credentials structure -
+		 * timestamp, hostname len (0), uid, gid, and gids len (0).
+		 */
+		if ((5 + gid_len) * BYTES_PER_XDR_UNIT + str_len > auth_len) {
+			(void) printf("bad auth_len gid %d str %d auth %d\n",
+			    gid_len, str_len, auth_len);
+			stat = AUTH_BADCRED;
+			goto done;
+		}
+	} else if (! xdr_authunix_parms(&xdrs, aup)) {
+		xdrs.x_op = XDR_FREE;
+		(void)xdr_authunix_parms(&xdrs, aup);
+		stat = AUTH_BADCRED;
+		goto done;
+	}
+
+	/* get the verifier */
+	if ((u_int)msg->rm_call.cb_verf.oa_length) {
+		rqst->rq_xprt->xp_verf.oa_flavor = 
+			msg->rm_call.cb_verf.oa_flavor;
+		rqst->rq_xprt->xp_verf.oa_base = 
+			msg->rm_call.cb_verf.oa_base;
+		rqst->rq_xprt->xp_verf.oa_length = 
+			msg->rm_call.cb_verf.oa_length;
+	} else {
+		rqst->rq_xprt->xp_verf.oa_flavor = AUTH_NULL;
+		rqst->rq_xprt->xp_verf.oa_length = 0;
+	}
+	stat = AUTH_OK;
+done:
+	XDR_DESTROY(&xdrs);
+	return (stat);
+}
+
+
+/*
+ * Shorthand unix authenticator
+ * Looks up longhand in a cache.
+ */
+/*ARGSUSED*/
+enum auth_stat
+_svcauth_short(
+	struct svc_req *rqst,
+	struct rpc_msg *msg )
+{
+	return (AUTH_REJECTEDCRED);
+}
diff --git a/services/librpc/src/rpc/svc_raw.c b/services/librpc/src/rpc/svc_raw.c
new file mode 100644
index 0000000..4685370
--- /dev/null
+++ b/services/librpc/src/rpc/svc_raw.c
@@ -0,0 +1,173 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)svc_raw.c 1.15 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)svc_raw.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/svc_raw.c,v 1.7 1999/08/28 00:00:49 peter Exp $";
+#endif
+
+/*
+ * svc_raw.c,   This a toy for simple testing and timing.
+ * Interface to create an rpc client and server in the same UNIX process.
+ * This lets us similate rpc and get rpc (round trip) overhead, without
+ * any interference from the kernal.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <rpc/rpc.h>
+#include <stdlib.h>
+
+/*
+ * This is the "network" that we will be moving data over
+ */
+struct svc_raw_private {
+	char	_raw_buf[UDPMSGSIZE];
+	SVCXPRT	server;
+	XDR	xdr_stream;
+	char	verf_body[MAX_AUTH_BYTES];
+};
+#define svcraw_private ((struct svc_raw_private *)(rtems_rpc_task_variables)->svc_raw_private)
+
+static bool_t		svcraw_recv(SVCXPRT *xprt, struct rpc_msg *msg);
+static enum xprt_stat 	svcraw_stat(SVCXPRT *xprt);
+static bool_t		svcraw_getargs(SVCXPRT *xprt, xdrproc_t xdr_args, caddr_t args_ptr);
+static bool_t		svcraw_reply(SVCXPRT *xprt, struct rpc_msg *msg);
+static bool_t		svcraw_freeargs(SVCXPRT *xprt, xdrproc_t xdr_args, caddr_t args_ptr);
+static void		svcraw_destroy(SVCXPRT *xprt);
+
+static struct xp_ops server_ops = {
+	svcraw_recv,
+	svcraw_stat,
+	svcraw_getargs,
+	svcraw_reply,
+	svcraw_freeargs,
+	svcraw_destroy
+};
+
+SVCXPRT *
+svcraw_create(void)
+{
+	register struct svc_raw_private *srp = svcraw_private;
+
+	if (srp == 0) {
+		srp = (struct svc_raw_private *)calloc(1, sizeof (*srp));
+		if (srp == 0)
+			return (0);
+	}
+	srp->server.xp_sock = 0;
+	srp->server.xp_port = 0;
+	srp->server.xp_ops = &server_ops;
+	srp->server.xp_verf.oa_base = srp->verf_body;
+	xdrmem_create(&srp->xdr_stream, srp->_raw_buf, UDPMSGSIZE, XDR_FREE);
+	return (&srp->server);
+}
+
+static enum xprt_stat
+svcraw_stat(SVCXPRT *xprt)
+{
+
+	return (XPRT_IDLE);
+}
+
+static bool_t
+svcraw_recv(
+	SVCXPRT *xprt,
+	struct rpc_msg *msg)
+{
+	register struct svc_raw_private *srp = svcraw_private;
+	register XDR *xdrs;
+
+	if (srp == 0)
+		return (0);
+	xdrs = &srp->xdr_stream;
+	xdrs->x_op = XDR_DECODE;
+	XDR_SETPOS(xdrs, 0);
+	if (! xdr_callmsg(xdrs, msg))
+	       return (FALSE);
+	return (TRUE);
+}
+
+static bool_t
+svcraw_reply(
+	SVCXPRT *xprt,
+	struct rpc_msg *msg)
+{
+	register struct svc_raw_private *srp = svcraw_private;
+	register XDR *xdrs;
+
+	if (srp == 0)
+		return (FALSE);
+	xdrs = &srp->xdr_stream;
+	xdrs->x_op = XDR_ENCODE;
+	XDR_SETPOS(xdrs, 0);
+	if (! xdr_replymsg(xdrs, msg))
+	       return (FALSE);
+	(void)XDR_GETPOS(xdrs);  /* called just for overhead */
+	return (TRUE);
+}
+
+static bool_t
+svcraw_getargs(
+	SVCXPRT *xprt,
+	xdrproc_t xdr_args,
+	caddr_t args_ptr)
+{
+	register struct svc_raw_private *srp = svcraw_private;
+
+	if (srp == 0)
+		return (FALSE);
+	return ((*xdr_args)(&srp->xdr_stream, args_ptr));
+}
+
+static bool_t
+svcraw_freeargs(
+	SVCXPRT *xprt,
+	xdrproc_t xdr_args,
+	caddr_t args_ptr)
+{
+	register struct svc_raw_private *srp = svcraw_private;
+	register XDR *xdrs;
+
+	if (srp == 0)
+		return (FALSE);
+	xdrs = &srp->xdr_stream;
+	xdrs->x_op = XDR_FREE;
+	return ((*xdr_args)(xdrs, args_ptr));
+}
+
+static void
+svcraw_destroy(SVCXPRT *xprt)
+{
+}
diff --git a/services/librpc/src/rpc/svc_run.c b/services/librpc/src/rpc/svc_run.c
new file mode 100644
index 0000000..963aa0d
--- /dev/null
+++ b/services/librpc/src/rpc/svc_run.c
@@ -0,0 +1,89 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)svc_run.c 1.1 87/10/13 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)svc_run.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/svc_run.c,v 1.10 1999/08/28 00:00:49 peter Exp $";
+#endif
+
+/*
+ * This is the rpc server side idle loop
+ * Wait for input, call server program.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <rpc/rpc.h>
+#include <stdio.h>
+#include <sys/errno.h>
+#include <sys/types.h>
+#include <sys/time.h>
+#include <unistd.h>
+#include <stdlib.h>
+#include <string.h>
+#include <sys/select.h>
+
+void
+svc_run(void)
+{
+	fd_set *fds;
+
+	for (;;) {
+		if (__svc_fdset) {
+			int bytes = sizeof (fd_set);
+			fds = (fd_set *)malloc(bytes);
+			memcpy(fds, __svc_fdset, bytes);
+		} else
+			fds = NULL;
+		switch (select(svc_maxfd + 1, fds, NULL, NULL,
+				(struct timeval *)0)) {
+		case -1:
+			if (errno == EINTR) {
+				if (fds)
+					free(fds);
+				continue;
+			}
+			perror("svc_run: - select failed");
+			if (fds)
+				free(fds);
+			return;
+		case 0:
+			if (fds)
+				free(fds);
+			continue;
+		default:
+			/* if fds == NULL, select() can't return a result */
+			svc_getreqset2(fds, svc_maxfd + 1);
+			free(fds);
+		}
+	}
+}
diff --git a/services/librpc/src/rpc/svc_simple.c b/services/librpc/src/rpc/svc_simple.c
new file mode 100644
index 0000000..30f213d
--- /dev/null
+++ b/services/librpc/src/rpc/svc_simple.c
@@ -0,0 +1,161 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)svc_simple.c 1.18 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)svc_simple.c	2.2 88/08/01 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/svc_simple.c,v 1.9 1999/08/28 00:00:50 peter Exp $";
+#endif
+
+/*
+ * svc_simple.c
+ * Simplified front end to rpc.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <inttypes.h>
+#include <rpc/rpc.h>
+#include <rpc/pmap_clnt.h>
+#include <sys/socket.h>
+#include <netdb.h>
+
+#include <inttypes.h> /* for PRIxx printf formats */
+
+struct prog_lst {
+	char *(*p_progname)(char *);
+	rpcprog_t  p_prognum;
+	rpcproc_t  p_procnum;
+	xdrproc_t p_inproc, p_outproc;
+	struct prog_lst *p_nxt;
+};
+static void universal(struct svc_req *, SVCXPRT *);
+#define proglst (rtems_rpc_task_variables->svc_simple_proglst)
+#define pl (rtems_rpc_task_variables->svc_simple_pl)
+#define transp (rtems_rpc_task_variables->svc_simple_transp)
+
+int
+registerrpc(
+	int prognum,
+	int versnum,
+	int procnum,
+	char *(*progname)(char *),
+	xdrproc_t inproc,
+	xdrproc_t outproc )
+{
+
+	if (procnum == NULLPROC) {
+		(void) fprintf(stderr,
+		    "can't reassign procedure number %" PRIu32 "\n", NULLPROC);
+		return (-1);
+	}
+	if (transp == 0) {
+		transp = svcudp_create(RPC_ANYSOCK);
+		if (transp == NULL) {
+			(void) fprintf(stderr, "couldn't create an rpc server\n");
+			return (-1);
+		}
+	}
+	(void) pmap_unset((u_long)prognum, (u_long)versnum);
+	if (!svc_register(transp, (u_long)prognum, (u_long)versnum,
+	    universal, IPPROTO_UDP)) {
+	    	(void) fprintf(stderr, "couldn't register prog %d vers %d\n",
+		    prognum, versnum);
+		return (-1);
+	}
+	pl = (struct prog_lst *)malloc(sizeof(struct prog_lst));
+	if (pl == NULL) {
+		(void) fprintf(stderr, "registerrpc: out of memory\n");
+		return (-1);
+	}
+	pl->p_progname = progname;
+	pl->p_prognum = prognum;
+	pl->p_procnum = procnum;
+	pl->p_inproc = inproc;
+	pl->p_outproc = outproc;
+	pl->p_nxt = proglst;
+	proglst = pl;
+	return (0);
+}
+
+static void
+universal(
+	struct svc_req *rqstp,
+	SVCXPRT *atransp )
+{
+	int prog, proc;
+	char *outdata;
+	char xdrbuf[UDPMSGSIZE];
+	struct prog_lst *lpl;
+
+	/*
+	 * enforce "procnum 0 is echo" convention
+	 */
+	if (rqstp->rq_proc == NULLPROC) {
+		if (svc_sendreply(atransp, (xdrproc_t) xdr_void, NULL) == FALSE) {
+			(void) fprintf(stderr, "xxx\n");
+			exit(1);
+		}
+		return;
+	}
+	prog = rqstp->rq_prog;
+	proc = rqstp->rq_proc;
+	for (lpl = proglst; lpl != NULL; lpl = lpl->p_nxt)
+		if (lpl->p_prognum == prog && lpl->p_procnum == proc) {
+			/* decode arguments into a CLEAN buffer */
+			memset(xdrbuf, 0, sizeof(xdrbuf)); /* required ! */
+			if (!svc_getargs(atransp, lpl->p_inproc, xdrbuf)) {
+				svcerr_decode(atransp);
+				return;
+			}
+			outdata = (*(lpl->p_progname))(xdrbuf);
+			if (outdata == NULL &&
+			    lpl->p_outproc != (xdrproc_t) xdr_void)
+				/* there was an error */
+				return;
+			if (!svc_sendreply(atransp, lpl->p_outproc, outdata)) {
+				(void) fprintf(stderr,
+				    "trouble replying to prog %" PRIu32 "\n",
+				    lpl->p_prognum);
+				exit(1);
+			}
+			/* free the decoded arguments */
+			(void)svc_freeargs(atransp, lpl->p_inproc, xdrbuf);
+			return;
+		}
+	(void) fprintf(stderr, "never registered prog %d\n", prog);
+	exit(1);
+}
diff --git a/services/librpc/src/rpc/svc_tcp.c b/services/librpc/src/rpc/svc_tcp.c
new file mode 100644
index 0000000..0f87080
--- /dev/null
+++ b/services/librpc/src/rpc/svc_tcp.c
@@ -0,0 +1,489 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)svc_tcp.c 1.21 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)svc_tcp.c	2.2 88/08/01 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/svc_tcp.c,v 1.18 2000/01/27 23:06:41 jasone Exp $";
+#endif
+
+/*
+ * svc_tcp.c, Server side for TCP/IP based RPC.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ *
+ * Actually implements two flavors of transporter -
+ * a tcp rendezvouser (a listner and connection establisher)
+ * and a record/tcp stream.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <string.h>
+#include <rpc/rpc.h>
+#include <sys/socket.h>
+#include <sys/ioctl.h>
+#include <errno.h>
+#include <sys/select.h>
+
+/*
+ * Ops vector for TCP/IP based rpc service handle
+ */
+static bool_t		svctcp_recv(SVCXPRT *xprt, struct rpc_msg *msg);
+static enum xprt_stat	svctcp_stat(SVCXPRT *xprt);
+static bool_t		svctcp_getargs(SVCXPRT *xprt, xdrproc_t xdr_args, caddr_t args_ptr);
+static bool_t		svctcp_reply(SVCXPRT *xprt, struct rpc_msg *msg);
+static bool_t		svctcp_freeargs(SVCXPRT *xprt, xdrproc_t xdr_args, caddr_t args_ptr);
+static void		svctcp_destroy(SVCXPRT *xprt);
+
+static struct xp_ops svctcp_op = {
+	svctcp_recv,
+	svctcp_stat,
+	svctcp_getargs,
+	svctcp_reply,
+	svctcp_freeargs,
+	svctcp_destroy
+};
+
+/*
+ * Ops vector for TCP/IP rendezvous handler
+ */
+static bool_t		rendezvous_request(SVCXPRT *xprt, struct rpc_msg *msg);
+static enum xprt_stat	rendezvous_stat(SVCXPRT *xprt);
+
+static struct xp_ops svctcp_rendezvous_op = {
+	rendezvous_request,
+	rendezvous_stat,
+	(bool_t (*)(SVCXPRT *xprt, xdrproc_t xdr_args, caddr_t args_ptr))abort,
+	(bool_t (*)(SVCXPRT *xprt, struct rpc_msg *msg))abort,
+	(bool_t (*)(SVCXPRT *xprt, xdrproc_t xdr_args, caddr_t args_ptr))abort,
+	svctcp_destroy
+};
+
+static int readtcp(char *, char*, int), writetcp(char *, char*, int);
+static SVCXPRT *makefd_xprt( int fd, u_int sendsize, u_int recvsize);
+
+struct tcp_rendezvous { /* kept in xprt->xp_p1 */
+	u_int sendsize;
+	u_int recvsize;
+};
+
+struct tcp_conn {  /* kept in xprt->xp_p1 */
+	enum xprt_stat strm_stat;
+	u_long x_id;
+	XDR xdrs;
+	char verf_body[MAX_AUTH_BYTES];
+};
+
+/*
+ * Usage:
+ *	xprt = svctcp_create(sock, send_buf_size, recv_buf_size);
+ *
+ * Creates, registers, and returns a (rpc) tcp based transporter.
+ * Once *xprt is initialized, it is registered as a transporter
+ * see (svc.h, xprt_register).  This routine returns
+ * a NULL if a problem occurred.
+ *
+ * If sock<0 then a socket is created, else sock is used.
+ * If the socket, sock is not bound to a port then svctcp_create
+ * binds it to an arbitrary port.  The routine then starts a tcp
+ * listener on the socket's associated port.  In any (successful) case,
+ * xprt->xp_sock is the registered socket number and xprt->xp_port is the
+ * associated port number.
+ *
+ * Since tcp streams do buffered io similar to stdio, the caller can specify
+ * how big the send and receive buffers are via the second and third parms;
+ * 0 => use the system default.
+ */
+SVCXPRT *
+svctcp_create(
+	int sock,
+	u_int sendsize,
+	u_int recvsize)
+{
+	bool_t madesock = FALSE;
+	register SVCXPRT *xprt;
+	register struct tcp_rendezvous *r;
+	struct sockaddr_in addr;
+	socklen_t len = sizeof(struct sockaddr_in);
+	int on;
+
+	if (sock == RPC_ANYSOCK) {
+		if ((sock = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) < 0) {
+			perror("svctcp_.c - udp socket creation problem");
+			return ((SVCXPRT *)NULL);
+		}
+		madesock = TRUE;
+	}
+	on = 1;
+	if (ioctl(sock, FIONBIO, &on) < 0) {
+		perror("svc_tcp.c - cannot turn on non-blocking mode");
+		if (madesock)
+		       (void)_RPC_close(sock);
+		return ((SVCXPRT *)NULL);
+	}
+	memset(&addr, 0, sizeof (addr));
+	addr.sin_len = sizeof(struct sockaddr_in);
+	addr.sin_family = AF_INET;
+	if (bindresvport(sock, &addr)) {
+		addr.sin_port = 0;
+		(void)bind(sock, (struct sockaddr *)&addr, len);
+	}
+	if ((getsockname(sock, (struct sockaddr *)&addr, &len) != 0)  ||
+	    (listen(sock, 2) != 0)) {
+		perror("svctcp_.c - cannot getsockname or listen");
+		if (madesock)
+		       (void)_RPC_close(sock);
+		return ((SVCXPRT *)NULL);
+	}
+	r = (struct tcp_rendezvous *)mem_alloc(sizeof(*r));
+	if (r == NULL) {
+		(void) fprintf(stderr, "svctcp_create: out of memory\n");
+		return (NULL);
+	}
+	r->sendsize = sendsize;
+	r->recvsize = recvsize;
+	xprt = (SVCXPRT *)mem_alloc(sizeof(SVCXPRT));
+	if (xprt == NULL) {
+		(void) fprintf(stderr, "svctcp_create: out of memory\n");
+		return (NULL);
+	}
+	xprt->xp_p2 = NULL;
+	xprt->xp_p1 = (caddr_t)r;
+	xprt->xp_verf = _null_auth;
+	xprt->xp_ops = &svctcp_rendezvous_op;
+	xprt->xp_port = ntohs(addr.sin_port);
+	xprt->xp_sock = sock;
+	xprt_register(xprt);
+	return (xprt);
+}
+
+/*
+ * Like svtcp_create(), except the routine takes any *open* UNIX file
+ * descriptor as its first input.
+ */
+SVCXPRT *
+svcfd_create(
+	int fd,
+	u_int sendsize,
+	u_int recvsize)
+{
+
+	return (makefd_xprt(fd, sendsize, recvsize));
+}
+
+static SVCXPRT *
+makefd_xprt(
+	int fd,
+	u_int sendsize,
+	u_int recvsize)
+{
+	register SVCXPRT *xprt;
+	register struct tcp_conn *cd;
+
+	xprt = (SVCXPRT *)mem_alloc(sizeof(SVCXPRT));
+	if (xprt == (SVCXPRT *)NULL) {
+		(void) fprintf(stderr, "svc_tcp: makefd_xprt: out of memory\n");
+		goto done;
+	}
+	cd = (struct tcp_conn *)mem_alloc(sizeof(struct tcp_conn));
+	if (cd == (struct tcp_conn *)NULL) {
+		(void) fprintf(stderr, "svc_tcp: makefd_xprt: out of memory\n");
+		mem_free((char *) xprt, sizeof(SVCXPRT));
+		xprt = (SVCXPRT *)NULL;
+		goto done;
+	}
+	cd->strm_stat = XPRT_IDLE;
+	xdrrec_create(&(cd->xdrs), sendsize, recvsize,
+	    (caddr_t)xprt, readtcp, writetcp);
+	xprt->xp_p2 = NULL;
+	xprt->xp_p1 = (caddr_t)cd;
+	xprt->xp_verf.oa_base = cd->verf_body;
+	xprt->xp_addrlen = 0;
+	xprt->xp_ops = &svctcp_op;  /* truely deals with calls */
+	xprt->xp_port = 0;  /* this is a connection, not a rendezvouser */
+	xprt->xp_sock = fd;
+	xprt_register(xprt);
+    done:
+	return (xprt);
+}
+
+static bool_t
+rendezvous_request(
+	SVCXPRT *xprt,
+	struct rpc_msg *msg)
+{
+	int sock;
+	struct tcp_rendezvous *r;
+	struct sockaddr_in addr;
+	socklen_t len;
+	int off;
+
+	r = (struct tcp_rendezvous *)xprt->xp_p1;
+    again:
+	len = sizeof(struct sockaddr_in);
+	if ((sock = accept(xprt->xp_sock, (struct sockaddr *)&addr,
+	    &len)) < 0) {
+		if (errno == EINTR)
+			goto again;
+	       return (FALSE);
+	}
+	/*
+	 * Guard against FTP bounce attacks.
+	 */
+	if (addr.sin_port == htons(20)) {
+		_RPC_close(sock);
+		return (FALSE);
+	}
+	/*
+	 * The listening socket is in FIONBIO mode and we inherit it.
+	 */
+	off = 0;
+	if (ioctl(sock, FIONBIO, &off) < 0) {
+		_RPC_close(sock);
+		return (FALSE);
+	}
+	/*
+	 * make a new transporter (re-uses xprt)
+	 */
+	xprt = makefd_xprt(sock, r->sendsize, r->recvsize);
+	xprt->xp_raddr = addr;
+	xprt->xp_addrlen = len;
+	return (FALSE); /* there is never an rpc msg to be processed */
+}
+
+static enum xprt_stat
+rendezvous_stat(SVCXPRT *xprt)
+{
+
+	return (XPRT_IDLE);
+}
+
+static void
+svctcp_destroy(
+	SVCXPRT *xprt)
+{
+	register struct tcp_conn *cd = (struct tcp_conn *)xprt->xp_p1;
+
+	xprt_unregister(xprt);
+	(void)_RPC_close(xprt->xp_sock);
+	if (xprt->xp_port != 0) {
+		/* a rendezvouser socket */
+		xprt->xp_port = 0;
+	} else {
+		/* an actual connection socket */
+		XDR_DESTROY(&(cd->xdrs));
+	}
+	mem_free((caddr_t)cd, sizeof(struct tcp_conn));
+	mem_free((caddr_t)xprt, sizeof(SVCXPRT));
+}
+
+/*
+ * All read operations timeout after 35 seconds.
+ * A timeout is fatal for the connection.
+ */
+static struct timeval wait_per_try = { 35, 0 };
+
+/*
+ * reads data from the tcp conection.
+ * any error is fatal and the connection is closed.
+ * (And a read of zero bytes is a half closed stream => error.)
+ *
+ * Note: we have to be careful here not to allow ourselves to become
+ * blocked too long in this routine. While we're waiting for data from one
+ * client, another client may be trying to connect. To avoid this situation,
+ * some code from svc_run() is transplanted here: the select() loop checks
+ * all RPC descriptors including the one we want and calls svc_getreqset2()
+ * to handle new requests if any are detected.
+ */
+static int
+readtcp(
+	char *_xprt,
+	char *buf,
+	int len)
+{
+	SVCXPRT *xprt = (SVCXPRT*) _xprt;
+	register int sock = xprt->xp_sock;
+	struct timeval start, delta, tv;
+	struct timeval tmp1, tmp2;
+	fd_set *fds;
+
+	delta = wait_per_try;
+	fds = NULL;
+	gettimeofday(&start, NULL);
+	do {
+		int bytes = sizeof (fd_set);
+		if (fds != NULL)
+			free(fds);
+		fds = (fd_set *)malloc(bytes);
+		if (fds == NULL)
+			goto fatal_err;
+		memcpy(fds, __svc_fdset, bytes);
+
+		/* XXX we know the other bits are still clear */
+		FD_SET(sock, fds);
+		tv = delta;	/* in case select() implements writeback */
+		switch (select(svc_maxfd + 1, fds, NULL, NULL, &tv)) {
+		case -1:
+			if (errno != EINTR)
+				goto fatal_err;
+			gettimeofday(&tmp1, NULL);
+			timersub(&tmp1, &start, &tmp2);
+			timersub(&wait_per_try, &tmp2, &tmp1);
+			if (tmp1.tv_sec < 0 || !timerisset(&tmp1))
+				goto fatal_err;
+			delta = tmp1;
+			continue;
+		case 0:
+			goto fatal_err;
+		default:
+			if (!FD_ISSET(sock, fds)) {
+				svc_getreqset2(fds, svc_maxfd + 1);
+				gettimeofday(&tmp1, NULL);
+				timersub(&tmp1, &start, &tmp2);
+				timersub(&wait_per_try, &tmp2, &tmp1);
+				if (tmp1.tv_sec < 0 || !timerisset(&tmp1))
+					goto fatal_err;
+				delta = tmp1;
+				continue;
+			}
+		}
+	} while (!FD_ISSET(sock, fds));
+	if ((len = _RPC_read(sock, buf, len)) > 0) {
+		if (fds != NULL)
+			free(fds);
+		return (len);
+	}
+fatal_err:
+	((struct tcp_conn *)(xprt->xp_p1))->strm_stat = XPRT_DIED;
+	if (fds != NULL)
+		free(fds);
+	return (-1);
+}
+
+/*
+ * writes data to the tcp connection.
+ * Any error is fatal and the connection is closed.
+ */
+static int
+writetcp(
+	char *_xprt,
+	char *buf,
+	int len)
+{
+	SVCXPRT *xprt = (SVCXPRT *) _xprt;
+	register int i, cnt;
+
+	for (cnt = len; cnt > 0; cnt -= i, buf += i) {
+		if ((i = _RPC_write(xprt->xp_sock, buf, cnt)) < 0) {
+			((struct tcp_conn *)(xprt->xp_p1))->strm_stat =
+			    XPRT_DIED;
+			return (-1);
+		}
+	}
+	return (len);
+}
+
+static enum xprt_stat
+svctcp_stat(
+	SVCXPRT *xprt)
+{
+	register struct tcp_conn *cd =
+	    (struct tcp_conn *)(xprt->xp_p1);
+
+	if (cd->strm_stat == XPRT_DIED)
+		return (XPRT_DIED);
+	if (! xdrrec_eof(&(cd->xdrs)))
+		return (XPRT_MOREREQS);
+	return (XPRT_IDLE);
+}
+
+static bool_t
+svctcp_recv(
+	SVCXPRT *xprt,
+	struct rpc_msg *msg)
+{
+	register struct tcp_conn *cd =
+	    (struct tcp_conn *)(xprt->xp_p1);
+	register XDR *xdrs = &(cd->xdrs);
+
+	xdrs->x_op = XDR_DECODE;
+	(void)xdrrec_skiprecord(xdrs);
+	if (xdr_callmsg(xdrs, msg)) {
+		cd->x_id = msg->rm_xid;
+		return (TRUE);
+	}
+	cd->strm_stat = XPRT_DIED;	/* XXXX */
+	return (FALSE);
+}
+
+static bool_t
+svctcp_getargs(
+	SVCXPRT *xprt,
+	xdrproc_t xdr_args,
+	caddr_t args_ptr)
+{
+
+	return ((*xdr_args)(&(((struct tcp_conn *)(xprt->xp_p1))->xdrs), args_ptr));
+}
+
+static bool_t
+svctcp_freeargs(
+	SVCXPRT *xprt,
+	xdrproc_t xdr_args,
+	caddr_t args_ptr)
+{
+	register XDR *xdrs =
+	    &(((struct tcp_conn *)(xprt->xp_p1))->xdrs);
+
+	xdrs->x_op = XDR_FREE;
+	return ((*xdr_args)(xdrs, args_ptr));
+}
+
+static bool_t
+svctcp_reply(
+	SVCXPRT *xprt,
+	struct rpc_msg *msg)
+{
+	register struct tcp_conn *cd =
+	    (struct tcp_conn *)(xprt->xp_p1);
+	register XDR *xdrs = &(cd->xdrs);
+	register bool_t stat;
+
+	xdrs->x_op = XDR_ENCODE;
+	msg->rm_xid = cd->x_id;
+	stat = xdr_replymsg(xdrs, msg);
+	(void)xdrrec_endofrecord(xdrs, TRUE);
+	return (stat);
+}
diff --git a/services/librpc/src/rpc/svc_udp.c b/services/librpc/src/rpc/svc_udp.c
new file mode 100644
index 0000000..8b7e167
--- /dev/null
+++ b/services/librpc/src/rpc/svc_udp.c
@@ -0,0 +1,484 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)svc_udp.c 1.24 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)svc_udp.c	2.2 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/rpc/svc_udp.c,v 1.13 2000/01/27 23:06:41 jasone Exp $";
+#endif
+
+/*
+ * svc_udp.c,
+ * Server side for UDP/IP based RPC.  (Does some caching in the hopes of
+ * achieving execute-at-most-once semantics.)
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <string.h>
+#include <rpc/rpc.h>
+#include <sys/socket.h>
+#include <errno.h>
+
+#define rpc_buffer(xprt) ((xprt)->xp_p1)
+#define MAX(a, b)     ((a > b) ? a : b)
+
+static bool_t		svcudp_recv(SVCXPRT *xprt, struct rpc_msg *msg);
+static bool_t		svcudp_reply(SVCXPRT *xprt, struct rpc_msg *msg);
+static enum xprt_stat	svcudp_stat(SVCXPRT *xprt);
+static bool_t		svcudp_getargs(SVCXPRT *xprt, xdrproc_t xdr_args, caddr_t args_ptr);
+static bool_t		svcudp_freeargs(SVCXPRT *xprt, xdrproc_t xdr_args, caddr_t args_ptr);
+static void		svcudp_destroy(SVCXPRT *xprt);
+static void		cache_set (SVCXPRT *, u_long);
+static int		cache_get (SVCXPRT *, struct rpc_msg *, char **, u_long *);
+
+static struct xp_ops svcudp_op = {
+	svcudp_recv,
+	svcudp_stat,
+	svcudp_getargs,
+	svcudp_reply,
+	svcudp_freeargs,
+	svcudp_destroy
+};
+
+/*
+ * kept in xprt->xp_p2
+ */
+struct svcudp_data {
+	u_int   su_iosz;	/* byte size of send.recv buffer */
+	u_long	su_xid;		/* transaction id */
+	XDR	su_xdrs;	/* XDR handle */
+	char	su_verfbody[MAX_AUTH_BYTES];	/* verifier body */
+	char * 	su_cache;	/* cached data, NULL if no cache */
+};
+#define	su_data(xprt)	((struct svcudp_data *)(xprt->xp_p2))
+
+/*
+ * Usage:
+ *	xprt = svcudp_create(sock);
+ *
+ * If sock<0 then a socket is created, else sock is used.
+ * If the socket, sock is not bound to a port then svcudp_create
+ * binds it to an arbitrary port.  In any (successful) case,
+ * xprt->xp_sock is the registered socket number and xprt->xp_port is the
+ * associated port number.
+ * Once *xprt is initialized, it is registered as a transporter;
+ * see (svc.h, xprt_register).
+ * The routines returns NULL if a problem occurred.
+ */
+SVCXPRT *
+svcudp_bufcreate(
+	int sock,
+	u_int sendsz,
+	u_int recvsz )
+{
+	bool_t madesock = FALSE;
+	register SVCXPRT *xprt;
+	register struct svcudp_data *su;
+	struct sockaddr_in addr;
+	socklen_t len = sizeof(struct sockaddr_in);
+
+	if (sock == RPC_ANYSOCK) {
+		if ((sock = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP)) < 0) {
+			perror("svcudp_create: socket creation problem");
+			return ((SVCXPRT *)NULL);
+		}
+		madesock = TRUE;
+	}
+	memset((char *)&addr, 0, sizeof (addr));
+	addr.sin_len = sizeof(struct sockaddr_in);
+	addr.sin_family = AF_INET;
+	if (bindresvport(sock, &addr)) {
+		addr.sin_port = 0;
+		(void)bind(sock, (struct sockaddr *)&addr, len);
+	}
+	if (getsockname(sock, (struct sockaddr *)&addr, &len) != 0) {
+		perror("svcudp_create - cannot getsockname");
+		if (madesock)
+			(void)_RPC_close(sock);
+		return ((SVCXPRT *)NULL);
+	}
+	xprt = (SVCXPRT *)mem_alloc(sizeof(SVCXPRT));
+	if (xprt == NULL) {
+		(void)fprintf(stderr, "svcudp_create: out of memory\n");
+		return (NULL);
+	}
+	su = (struct svcudp_data *)mem_alloc(sizeof(*su));
+	if (su == NULL) {
+		(void)fprintf(stderr, "svcudp_create: out of memory\n");
+		return (NULL);
+	}
+	su->su_iosz = ((MAX(sendsz, recvsz) + 3) / 4) * 4;
+	if ((rpc_buffer(xprt) = mem_alloc(su->su_iosz)) == NULL) {
+		(void)fprintf(stderr, "svcudp_create: out of memory\n");
+		return (NULL);
+	}
+	xdrmem_create(
+	    &(su->su_xdrs), rpc_buffer(xprt), su->su_iosz, XDR_DECODE);
+	su->su_cache = NULL;
+	xprt->xp_p2 = (caddr_t)su;
+	xprt->xp_verf.oa_base = su->su_verfbody;
+	xprt->xp_ops = &svcudp_op;
+	xprt->xp_port = ntohs(addr.sin_port);
+	xprt->xp_sock = sock;
+	xprt_register(xprt);
+	return (xprt);
+}
+
+SVCXPRT *
+svcudp_create(
+	int sock)
+{
+
+	return(svcudp_bufcreate(sock, UDPMSGSIZE, UDPMSGSIZE));
+}
+
+static enum xprt_stat
+svcudp_stat(
+	SVCXPRT *xprt)
+{
+
+	return (XPRT_IDLE);
+}
+
+static bool_t
+svcudp_recv(
+	SVCXPRT *xprt,
+	struct rpc_msg *msg)
+{
+	register struct svcudp_data *su = su_data(xprt);
+	register XDR *xdrs = &(su->su_xdrs);
+	register int rlen;
+	char *reply;
+	u_long replylen;
+
+    again:
+	xprt->xp_addrlen = sizeof(struct sockaddr_in);
+	rlen = recvfrom(xprt->xp_sock, rpc_buffer(xprt), (int) su->su_iosz,
+	    0, (struct sockaddr *)&(xprt->xp_raddr), &(xprt->xp_addrlen));
+	if (rlen == -1 && errno == EINTR)
+		goto again;
+	if (rlen == -1 || rlen < 4*sizeof(u_int32_t))
+		return (FALSE);
+	xdrs->x_op = XDR_DECODE;
+	XDR_SETPOS(xdrs, 0);
+	if (! xdr_callmsg(xdrs, msg))
+		return (FALSE);
+	su->su_xid = msg->rm_xid;
+	if (su->su_cache != NULL) {
+		if (cache_get(xprt, msg, &reply, &replylen)) {
+			(void) sendto(xprt->xp_sock, reply, (int) replylen, 0,
+			  (struct sockaddr *) &xprt->xp_raddr, xprt->xp_addrlen);
+			return (TRUE);
+		}
+	}
+	return (TRUE);
+}
+
+static bool_t
+svcudp_reply(
+	SVCXPRT *xprt,
+	struct rpc_msg *msg)
+{
+	register struct svcudp_data *su = su_data(xprt);
+	register XDR *xdrs = &(su->su_xdrs);
+	register int slen;
+	register bool_t stat = FALSE;
+
+	xdrs->x_op = XDR_ENCODE;
+	XDR_SETPOS(xdrs, 0);
+	msg->rm_xid = su->su_xid;
+	if (xdr_replymsg(xdrs, msg)) {
+		slen = (int)XDR_GETPOS(xdrs);
+		if (sendto(xprt->xp_sock, rpc_buffer(xprt), slen, 0,
+		    (struct sockaddr *)&(xprt->xp_raddr), xprt->xp_addrlen)
+		    == slen) {
+			stat = TRUE;
+			if (su->su_cache && slen >= 0) {
+				cache_set(xprt, (u_long) slen);
+			}
+		}
+	}
+	return (stat);
+}
+
+static bool_t
+svcudp_getargs(
+	SVCXPRT *xprt,
+	xdrproc_t xdr_args,
+	caddr_t args_ptr)
+{
+
+	return ((*xdr_args)(&(su_data(xprt)->su_xdrs), args_ptr));
+}
+
+static bool_t
+svcudp_freeargs(
+	SVCXPRT *xprt,
+	xdrproc_t xdr_args,
+	caddr_t args_ptr)
+{
+	register XDR *xdrs = &(su_data(xprt)->su_xdrs);
+
+	xdrs->x_op = XDR_FREE;
+	return ((*xdr_args)(xdrs, args_ptr));
+}
+
+static void
+svcudp_destroy(
+	SVCXPRT *xprt)
+{
+	register struct svcudp_data *su = su_data(xprt);
+
+	xprt_unregister(xprt);
+	(void)_RPC_close(xprt->xp_sock);
+	XDR_DESTROY(&(su->su_xdrs));
+	mem_free(rpc_buffer(xprt), su->su_iosz);
+	mem_free((caddr_t)su, sizeof(struct svcudp_data));
+	mem_free((caddr_t)xprt, sizeof(SVCXPRT));
+}
+
+
+/***********this could be a separate file*********************/
+
+/*
+ * Fifo cache for udp server
+ * Copies pointers to reply buffers into fifo cache
+ * Buffers are sent again if retransmissions are detected.
+ */
+
+#define SPARSENESS 4	/* 75% sparse */
+
+#define CACHE_PERROR(msg)	\
+	(void) fprintf(stderr,"%s\n", msg)
+
+#define ALLOC(type, size)	\
+	(type *) mem_alloc((unsigned) (sizeof(type) * (size)))
+
+#define BZERO(addr, type, size)	 \
+	memset((char *) addr, 0, sizeof(type) * (int) (size))
+
+/*
+ * An entry in the cache
+ */
+typedef struct cache_node *cache_ptr;
+struct cache_node {
+	/*
+	 * Index into cache is xid, proc, vers, prog and address
+	 */
+	u_long cache_xid;
+	u_long cache_proc;
+	u_long cache_vers;
+	u_long cache_prog;
+	struct sockaddr_in cache_addr;
+	/*
+	 * The cached reply and length
+	 */
+	char * cache_reply;
+	u_long cache_replylen;
+	/*
+ 	 * Next node on the list, if there is a collision
+	 */
+	cache_ptr cache_next;
+};
+
+
+
+/*
+ * The entire cache
+ */
+struct udp_cache {
+	u_long uc_size;		/* size of cache */
+	cache_ptr *uc_entries;	/* hash table of entries in cache */
+	cache_ptr *uc_fifo;	/* fifo list of entries in cache */
+	u_long uc_nextvictim;	/* points to next victim in fifo list */
+	u_long uc_prog;		/* saved program number */
+	u_long uc_vers;		/* saved version number */
+	u_long uc_proc;		/* saved procedure number */
+	struct sockaddr_in uc_addr; /* saved caller's address */
+};
+
+
+/*
+ * the hashing function
+ */
+#define CACHE_LOC(transp, xid)	\
+ (xid % (SPARSENESS*((struct udp_cache *) su_data(transp)->su_cache)->uc_size))
+
+
+/*
+ * Enable use of the cache.
+ * Note: there is no disable.
+ */
+int svcudp_enablecache(
+	SVCXPRT *transp,
+	u_long size)
+{
+	struct svcudp_data *su = su_data(transp);
+	struct udp_cache *uc;
+
+	if (su->su_cache != NULL) {
+		CACHE_PERROR("enablecache: cache already enabled");
+		return(0);
+	}
+	uc = ALLOC(struct udp_cache, 1);
+	if (uc == NULL) {
+		CACHE_PERROR("enablecache: could not allocate cache");
+		return(0);
+	}
+	uc->uc_size = size;
+	uc->uc_nextvictim = 0;
+	uc->uc_entries = ALLOC(cache_ptr, size * SPARSENESS);
+	if (uc->uc_entries == NULL) {
+		CACHE_PERROR("enablecache: could not allocate cache data");
+		return(0);
+	}
+	BZERO(uc->uc_entries, cache_ptr, size * SPARSENESS);
+	uc->uc_fifo = ALLOC(cache_ptr, size);
+	if (uc->uc_fifo == NULL) {
+		CACHE_PERROR("enablecache: could not allocate cache fifo");
+		return(0);
+	}
+	BZERO(uc->uc_fifo, cache_ptr, size);
+	su->su_cache = (char *) uc;
+	return(1);
+}
+
+
+/*
+ * Set an entry in the cache
+ */
+static void
+cache_set(
+	SVCXPRT *xprt,
+	u_long replylen)
+{
+	register cache_ptr victim;
+	register cache_ptr *vicp;
+	register struct svcudp_data *su = su_data(xprt);
+	struct udp_cache *uc = (struct udp_cache *) su->su_cache;
+	u_int loc;
+	char *newbuf;
+
+	/*
+ 	 * Find space for the new entry, either by
+	 * reusing an old entry, or by mallocing a new one
+	 */
+	victim = uc->uc_fifo[uc->uc_nextvictim];
+	if (victim != NULL) {
+		loc = CACHE_LOC(xprt, victim->cache_xid);
+		for (vicp = &uc->uc_entries[loc];
+		  *vicp != NULL && *vicp != victim;
+		  vicp = &(*vicp)->cache_next)
+				;
+		if (*vicp == NULL) {
+			CACHE_PERROR("cache_set: victim not found");
+			return;
+		}
+		*vicp = victim->cache_next;	/* remote from cache */
+		newbuf = victim->cache_reply;
+	} else {
+		victim = ALLOC(struct cache_node, 1);
+		if (victim == NULL) {
+			CACHE_PERROR("cache_set: victim alloc failed");
+			return;
+		}
+		newbuf = mem_alloc(su->su_iosz);
+		if (newbuf == NULL) {
+			CACHE_PERROR("cache_set: could not allocate new rpc_buffer");
+			return;
+		}
+	}
+
+	/*
+	 * Store it away
+	 */
+	victim->cache_replylen = replylen;
+	victim->cache_reply = rpc_buffer(xprt);
+	rpc_buffer(xprt) = newbuf;
+	xdrmem_create(&(su->su_xdrs), rpc_buffer(xprt), su->su_iosz, XDR_ENCODE);
+	victim->cache_xid = su->su_xid;
+	victim->cache_proc = uc->uc_proc;
+	victim->cache_vers = uc->uc_vers;
+	victim->cache_prog = uc->uc_prog;
+	victim->cache_addr = uc->uc_addr;
+	loc = CACHE_LOC(xprt, victim->cache_xid);
+	victim->cache_next = uc->uc_entries[loc];
+	uc->uc_entries[loc] = victim;
+	uc->uc_fifo[uc->uc_nextvictim++] = victim;
+	uc->uc_nextvictim %= uc->uc_size;
+}
+
+/*
+ * Try to get an entry from the cache
+ * return 1 if found, 0 if not found
+ */
+static int
+cache_get(
+	SVCXPRT *xprt,
+	struct rpc_msg *msg,
+	char **replyp,
+	u_long *replylenp)
+{
+	u_int loc;
+	register cache_ptr ent;
+	register struct svcudp_data *su = su_data(xprt);
+	register struct udp_cache *uc = (struct udp_cache *) su->su_cache;
+
+#	define EQADDR(a1, a2)	(memcmp(&a1, &a2, sizeof(a1)) == 0)
+
+	loc = CACHE_LOC(xprt, su->su_xid);
+	for (ent = uc->uc_entries[loc]; ent != NULL; ent = ent->cache_next) {
+		if (ent->cache_xid == su->su_xid &&
+		  ent->cache_proc == uc->uc_proc &&
+		  ent->cache_vers == uc->uc_vers &&
+		  ent->cache_prog == uc->uc_prog &&
+		  EQADDR(ent->cache_addr, uc->uc_addr)) {
+			*replyp = ent->cache_reply;
+			*replylenp = ent->cache_replylen;
+			return(1);
+		}
+	}
+	/*
+	 * Failed to find entry
+	 * Remember a few things so we can do a set later
+	 */
+	uc->uc_proc = msg->rm_call.cb_proc;
+	uc->uc_vers = msg->rm_call.cb_vers;
+	uc->uc_prog = msg->rm_call.cb_prog;
+	uc->uc_addr = xprt->xp_raddr;
+	return(0);
+}
diff --git a/services/librpc/src/xdr/xdr.3 b/services/librpc/src/xdr/xdr.3
new file mode 100644
index 0000000..c1cdb11
--- /dev/null
+++ b/services/librpc/src/xdr/xdr.3
@@ -0,0 +1,837 @@
+.\" @(#)xdr.3n	2.2 88/08/03 4.0 RPCSRC; from 1.16 88/03/14 SMI
+.\" $FreeBSD: src/lib/libc/xdr/xdr.3,v 1.8 2000/03/02 09:14:05 sheldonh Exp $
+.\"
+.TH XDR 3 "16 February 1988"
+.SH NAME
+xdr \- library routines for external data representation
+.SH SYNOPSIS AND DESCRIPTION
+.LP
+These routines allow C programmers to describe
+arbitrary data structures in a machine-independent fashion.
+Data for remote procedure calls are transmitted using these
+routines.
+.LP
+.ft B
+.nf
+.sp .5
+xdr_array(xdrs, arrp, sizep, maxsize, elsize, elproc)
+\s-1XDR\s0 *xdrs;
+char **arrp;
+u_int *sizep, maxsize, elsize;
+xdrproc_t elproc;
+.fi
+.ft R
+.IP
+A filter primitive that translates between variable-length
+arrays
+and their corresponding external representations.
+The
+parameter
+.I arrp
+is the address of the pointer to the array, while
+.I sizep
+is the address of the element count of the array;
+this element count cannot exceed
+.IR maxsize .
+The parameter
+.I elsize
+is the
+.I sizeof
+each of the array's elements, and
+.I elproc
+is an
+.SM XDR
+filter that translates between
+the array elements' C form, and their external
+representation.
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 8
+.LP
+.ft B
+.nf
+.sp .5
+xdr_bool(xdrs, bp)
+\s-1XDR\s0 *xdrs;
+bool_t *bp;
+.fi
+.ft R
+.IP
+A filter primitive that translates between booleans (C
+integers)
+and their external representations.
+When encoding data, this
+filter produces values of either one or zero.
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 10
+.LP
+.ft B
+.nf
+.sp .5
+xdr_bytes(xdrs, sp, sizep, maxsize)
+\s-1XDR\s0 *xdrs;
+char **sp;
+u_int *sizep, maxsize;
+.fi
+.ft R
+.IP
+A filter primitive that translates between counted byte
+strings and their external representations.
+The parameter
+.I sp
+is the address of the string pointer.
+The length of the
+string is located at address
+.IR sizep ;
+strings cannot be longer than
+.IR maxsize .
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+xdr_char(xdrs, cp)
+\s-1XDR\s0 *xdrs;
+char *cp;
+.fi
+.ft R
+.IP
+A filter primitive that translates between C characters
+and their external representations.
+This routine returns one if it succeeds, zero otherwise.
+Note: encoded characters are not packed, and occupy 4 bytes
+each.
+For arrays of characters, it is worthwhile to
+consider
+.BR xdr_bytes(\|) ,
+.B xdr_opaque(\|)
+or
+.BR xdr_string(\|) .
+.br
+.if t .ne 8
+.LP
+.ft B
+.nf
+.sp .5
+void
+xdr_destroy(xdrs)
+\s-1XDR\s0 *xdrs;
+.fi
+.ft R
+.IP
+A macro that invokes the destroy routine associated with the
+.SM XDR
+stream,
+.IR xdrs .
+Destruction usually involves freeing private data structures
+associated with the stream.  Using
+.I xdrs
+after invoking
+.B xdr_destroy(\|)
+is undefined.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+xdr_double(xdrs, dp)
+\s-1XDR\s0 *xdrs;
+double *dp;
+.fi
+.ft R
+.IP
+A filter primitive that translates between C
+.B double
+precision numbers and their external representations.
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+xdr_enum(xdrs, ep)
+\s-1XDR\s0 *xdrs;
+enum_t *ep;
+.fi
+.ft R
+.IP
+A filter primitive that translates between C
+.BR enum s
+(actually integers) and their external representations.
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 8
+.LP
+.ft B
+.nf
+.sp .5
+xdr_float(xdrs, fp)
+\s-1XDR\s0 *xdrs;
+float *fp;
+.fi
+.ft R
+.IP
+A filter primitive that translates between C
+.BR float s
+and their external representations.
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 9
+.LP
+.ft B
+.nf
+.sp .5
+void
+xdr_free(proc, objp)
+xdrproc_t proc;
+char *objp;
+.fi
+.ft R
+.IP
+Generic freeing routine.
+The first argument is the
+.SM XDR
+routine for the object being freed.
+The second argument
+is a pointer to the object itself.
+Note: the pointer passed
+to this routine is
+.I not
+freed, but what it points to
+.I is
+freed (recursively).
+.br
+.if t .ne 8
+.LP
+.ft B
+.nf
+.sp .5
+u_int
+xdr_getpos(xdrs)
+\s-1XDR\s0 *xdrs;
+.fi
+.ft R
+.IP
+A macro that invokes the get-position routine
+associated with the
+.SM XDR
+stream,
+.IR xdrs .
+The routine returns an unsigned integer,
+which indicates the position of the
+.SM XDR
+byte stream.
+A desirable feature of
+.SM XDR
+streams is that simple arithmetic works with this number,
+although the
+.SM XDR
+stream instances need not guarantee this.
+.br
+.if t .ne 4
+.LP
+.ft B
+.nf
+.sp .5
+.br
+long *
+xdr_inline(xdrs, len)
+\s-1XDR\s0 *xdrs;
+int len;
+.fi
+.ft R
+.IP
+A macro that invokes the in-line routine associated with the
+.SM XDR
+stream,
+.IR xdrs .
+The routine returns a pointer
+to a contiguous piece of the stream's buffer;
+.I len
+is the byte length of the desired buffer.
+Note: pointer is cast to
+.BR "long *" .
+.IP
+Warning:
+.B xdr_inline(\|)
+may return
+.SM NULL
+(0)
+if it cannot allocate a contiguous piece of a buffer.
+Therefore the behavior may vary among stream instances;
+it exists for the sake of efficiency.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+xdr_int(xdrs, ip)
+\s-1XDR\s0 *xdrs;
+int *ip;
+.fi
+.ft R
+.IP
+A filter primitive that translates between C integers
+and their external representations.
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+xdr_long(xdrs, lp)
+\s-1XDR\s0 *xdrs;
+long *lp;
+.fi
+.ft R
+.IP
+A filter primitive that translates between C
+.B long
+integers and their external representations.
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 12
+.LP
+.ft B
+.nf
+.sp .5
+void
+xdrmem_create(xdrs, addr, size, op)
+\s-1XDR\s0 *xdrs;
+char *addr;
+u_int size;
+enum xdr_op op;
+.fi
+.ft R
+.IP
+This routine initializes the
+.SM XDR
+stream object pointed to by
+.IR xdrs .
+The stream's data is written to, or read from,
+a chunk of memory at location
+.I addr
+whose length is no more than
+.I size
+bytes long.  The
+.I op
+determines the direction of the
+.SM XDR
+stream
+(either
+.BR \s-1XDR_ENCODE\s0 ,
+.BR \s-1XDR_DECODE\s0 ,
+or
+.BR \s-1XDR_FREE\s0 ).
+.br
+.if t .ne 10
+.LP
+.ft B
+.nf
+.sp .5
+xdr_opaque(xdrs, cp, cnt)
+\s-1XDR\s0 *xdrs;
+char *cp;
+u_int cnt;
+.fi
+.ft R
+.IP
+A filter primitive that translates between fixed size opaque
+data
+and its external representation.
+The parameter
+.I cp
+is the address of the opaque object, and
+.I cnt
+is its size in bytes.
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 10
+.LP
+.ft B
+.nf
+.sp .5
+xdr_pointer(xdrs, objpp, objsize, xdrobj)
+\s-1XDR\s0 *xdrs;
+char **objpp;
+u_int objsize;
+xdrproc_t xdrobj;
+.fi
+.ft R
+.IP
+Like
+.B xdr_reference(\|)
+execpt that it serializes
+.SM NULL
+pointers, whereas
+.B xdr_reference(\|)
+does not.  Thus,
+.B xdr_pointer(\|)
+can represent
+recursive data structures, such as binary trees or
+linked lists.
+.br
+.if t .ne 15
+.LP
+.ft B
+.nf
+.sp .5
+void
+xdrrec_create(xdrs, sendsize, recvsize, handle, readit, writeit)
+\s-1XDR\s0 *xdrs;
+u_int sendsize, recvsize;
+char *handle;
+int (*readit) (\|), (*writeit) (\|);
+.fi
+.ft R
+.IP
+This routine initializes the
+.SM XDR
+stream object pointed to by
+.IR xdrs .
+The stream's data is written to a buffer of size
+.IR sendsize ;
+a value of zero indicates the system should use a suitable
+default.
+The stream's data is read from a buffer of size
+.IR recvsize ;
+it too can be set to a suitable default by passing a zero
+value.
+When a stream's output buffer is full,
+.I writeit
+is called.  Similarly, when a stream's input buffer is empty,
+.I readit
+is called.  The behavior of these two routines is similar to
+the
+system calls
+.B read
+and
+.BR write ,
+except that
+.I handle
+is passed to the former routines as the first parameter.
+Note: the
+.SM XDR
+stream's
+.I op
+field must be set by the caller.
+.IP
+Warning: this
+.SM XDR
+stream implements an intermediate record stream.
+Therefore there are additional bytes in the stream
+to provide record boundary information.
+.br
+.if t .ne 9
+.LP
+.ft B
+.nf
+.sp .5
+xdrrec_endofrecord(xdrs, sendnow)
+\s-1XDR\s0 *xdrs;
+int sendnow;
+.fi
+.ft R
+.IP
+This routine can be invoked only on
+streams created by
+.BR xdrrec_create(\|) .
+The data in the output buffer is marked as a completed
+record,
+and the output buffer is optionally written out if
+.I sendnow
+is non-zero.
+This routine returns one if it succeeds, zero
+otherwise.
+.br
+.if t .ne 8
+.LP
+.ft B
+.nf
+.sp .5
+xdrrec_eof(xdrs)
+\s-1XDR\s0 *xdrs;
+int empty;
+.fi
+.ft R
+.IP
+This routine can be invoked only on
+streams created by
+.BR xdrrec_create(\|) .
+After consuming the rest of the current record in the stream,
+this routine returns one if the stream has no more input,
+zero otherwise.
+.br
+.if t .ne 3
+.LP
+.ft B
+.nf
+.sp .5
+xdrrec_skiprecord(xdrs)
+\s-1XDR\s0 *xdrs;
+.fi
+.ft R
+.IP
+This routine can be invoked only on
+streams created by
+.BR xdrrec_create(\|) .
+It tells the
+.SM XDR
+implementation that the rest of the current record
+in the stream's input buffer should be discarded.
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 11
+.LP
+.ft B
+.nf
+.sp .5
+xdr_reference(xdrs, pp, size, proc)
+\s-1XDR\s0 *xdrs;
+char **pp;
+u_int size;
+xdrproc_t proc;
+.fi
+.ft R
+.IP
+A primitive that provides pointer chasing within structures.
+The parameter
+.I pp
+is the address of the pointer;
+.I size
+is the
+.I sizeof
+the structure that
+.I *pp
+points to; and
+.I proc
+is an
+.SM XDR
+procedure that filters the structure
+between its C form and its external representation.
+This routine returns one if it succeeds, zero otherwise.
+.IP
+Warning: this routine does not understand
+.SM NULL
+pointers.
+Use
+.B xdr_pointer(\|)
+instead.
+.br
+.if t .ne 10
+.LP
+.ft B
+.nf
+.sp .5
+xdr_setpos(xdrs, pos)
+\s-1XDR\s0 *xdrs;
+u_int pos;
+.fi
+.ft R
+.IP
+A macro that invokes the set position routine associated with
+the
+.SM XDR
+stream
+.IR xdrs .
+The parameter
+.I pos
+is a position value obtained from
+.BR xdr_getpos(\|) .
+This routine returns one if the
+.SM XDR
+stream could be repositioned,
+and zero otherwise.
+.IP
+Warning: it is difficult to reposition some types of
+.SM XDR
+streams, so this routine may fail with one
+type of stream and succeed with another.
+.br
+.if t .ne 8
+.LP
+.ft B
+.nf
+.sp .5
+xdr_short(xdrs, sp)
+\s-1XDR\s0 *xdrs;
+short *sp;
+.fi
+.ft R
+.IP
+A filter primitive that translates between C
+.B short
+integers and their external representations.
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 10
+.LP
+.ft B
+.nf
+.sp .5
+void
+xdrstdio_create(xdrs, file, op)
+\s-1XDR\s0 *xdrs;
+\s-1FILE\s0 *file;
+enum xdr_op op;
+.fi
+.ft R
+.IP
+This routine initializes the
+.SM XDR
+stream object pointed to by
+.IR xdrs .
+The
+.SM XDR
+stream data is written to, or read from, the Standard
+.B I/O
+stream
+.IR file .
+The parameter
+.I op
+determines the direction of the
+.SM XDR
+stream (either
+.BR \s-1XDR_ENCODE\s0 ,
+.BR \s-1XDR_DECODE\s0 ,
+or
+.BR \s-1XDR_FREE\s0 ).
+.IP
+Warning: the destroy routine associated with such
+.SM XDR
+streams calls
+.B fflush(\|)
+on the
+.I file
+stream, but never
+.BR fclose(\|) .
+.br
+.if t .ne 9
+.LP
+.ft B
+.nf
+.sp .5
+xdr_string(xdrs, sp, maxsize)
+\s-1XDR\s0
+*xdrs;
+char **sp;
+u_int maxsize;
+.fi
+.ft R
+.IP
+A filter primitive that translates between C strings and
+their
+corresponding external representations.
+Strings cannot be longer than
+.IR maxsize .
+Note: 
+.I sp
+is the address of the string's pointer.
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 8
+.LP
+.ft B
+.nf
+.sp .5
+xdr_u_char(xdrs, ucp)
+\s-1XDR\s0 *xdrs;
+unsigned char *ucp;
+.fi
+.ft R
+.IP
+A filter primitive that translates between
+.B unsigned
+C characters and their external representations.
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 9
+.LP
+.ft B
+.nf
+.sp .5
+xdr_u_int(xdrs, up)
+\s-1XDR\s0 *xdrs;
+unsigned *up;
+.fi
+.ft R
+.IP
+A filter primitive that translates between C
+.B unsigned
+integers and their external representations.
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+xdr_u_long(xdrs, ulp)
+\s-1XDR\s0 *xdrs;
+unsigned long *ulp;
+.fi
+.ft R
+.IP
+A filter primitive that translates between C
+.B "unsigned long"
+integers and their external representations.
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 7
+.LP
+.ft B
+.nf
+.sp .5
+xdr_u_short(xdrs, usp)
+\s-1XDR\s0 *xdrs;
+unsigned short *usp;
+.fi
+.ft R
+.IP
+A filter primitive that translates between C
+.B "unsigned short"
+integers and their external representations.
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 16
+.LP
+.ft B
+.nf
+.sp .5
+xdr_union(xdrs, dscmp, unp, choices, dfault)
+\s-1XDR\s0 *xdrs;
+int *dscmp;
+char *unp;
+struct xdr_discrim *choices;
+bool_t (*defaultarm) (\|);  /* may equal \s-1NULL\s0 */
+.fi
+.ft R
+.IP
+A filter primitive that translates between a discriminated C
+.B union
+and its corresponding external representation.
+It first
+translates the discriminant of the union located at
+.IR dscmp .
+This discriminant is always an
+.BR enum_t .
+Next the union located at
+.I unp
+is translated.  The parameter
+.I choices
+is a pointer to an array of
+.B xdr_discrim(\|)
+structures.
+Each structure contains an ordered pair of
+.RI [ value , proc ].
+If the union's discriminant is equal to the associated
+.IR value ,
+then the
+.I proc
+is called to translate the union.  The end of the
+.B xdr_discrim(\|)
+structure array is denoted by a routine of value
+.SM NULL\s0.
+If the discriminant is not found in the
+.I choices
+array, then the
+.I defaultarm
+procedure is called (if it is not
+.SM NULL\s0).
+Returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 6
+.LP
+.ft B
+.nf
+.sp .5
+xdr_vector(xdrs, arrp, size, elsize, elproc)
+\s-1XDR\s0 *xdrs;
+char *arrp;
+u_int size, elsize;
+xdrproc_t elproc;
+.fi
+.ft R
+.IP
+A filter primitive that translates between fixed-length
+arrays
+and their corresponding external representations.  The
+parameter
+.I arrp
+is the address of the pointer to the array, while
+.I size
+is the element count of the array.  The parameter
+.I elsize
+is the
+.I sizeof
+each of the array's elements, and
+.I elproc
+is an
+.SM XDR
+filter that translates between
+the array elements' C form, and their external
+representation.
+This routine returns one if it succeeds, zero otherwise.
+.br
+.if t .ne 5
+.LP
+.ft B
+.nf
+.sp .5
+xdr_void(\|)
+.fi
+.ft R
+.IP
+This routine always returns one.
+It may be passed to
+.SM RPC
+routines that require a function parameter,
+where nothing is to be done.
+.br
+.if t .ne 10
+.LP
+.ft B
+.nf
+.sp .5
+xdr_wrapstring(xdrs, sp)
+\s-1XDR\s0 *xdrs;
+char **sp;
+.fi
+.ft R
+.IP
+A primitive that calls
+.B "xdr_string(xdrs, sp,\s-1MAXUN.UNSIGNED\s0 );"
+where
+.B
+.SM MAXUN.UNSIGNED
+is the maximum value of an unsigned integer.
+.B xdr_wrapstring(\|)
+is handy because the
+.SM RPC
+package passes a maximum of two
+.SM XDR
+routines as parameters, and
+.BR xdr_string(\|) ,
+one of the most frequently used primitives, requires three.
+Returns one if it succeeds, zero otherwise.
+.SH SEE ALSO
+.BR rpc (3)
+.LP
+The following manuals:
+.RS
+.ft I
+eXternal Data Representation Standard: Protocol Specification
+.br
+eXternal Data Representation: Sun Technical Notes
+.ft R
+.br
+.IR "\s-1XDR\s0: External Data Representation Standard" ,
+.SM RFC1014, Sun Microsystems, Inc.,
+.SM USC-ISI\s0.
diff --git a/services/librpc/src/xdr/xdr.c b/services/librpc/src/xdr/xdr.c
new file mode 100644
index 0000000..80c29bb
--- /dev/null
+++ b/services/librpc/src/xdr/xdr.c
@@ -0,0 +1,858 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)xdr.c 1.35 87/08/12";*/
+/*static char *sccsid = "from: @(#)xdr.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/xdr/xdr.c,v 1.9 1999/08/28 00:02:55 peter Exp $";
+#endif
+
+/*
+ * xdr.c, Generic XDR routines implementation.
+ *
+ * Copyright (C) 1986, Sun Microsystems, Inc.
+ *
+ * These are the "generic" xdr routines used to serialize and de-serialize
+ * most common data items.  See xdr.h for more info on the interface to
+ * xdr.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <rpc/types.h>
+#include <rpc/xdr.h>
+
+#if defined(__rtems__)
+#define warnx(msg) fprintf(stderr, msg "\n");
+#endif
+
+/*
+ * constants specific to the xdr "protocol"
+ */
+#define XDR_FALSE	((long) 0)
+#define XDR_TRUE	((long) 1)
+#define LASTUNSIGNED	((u_int) 0-1)
+
+/*
+ * for unit alignment
+ */
+static const char xdr_zero[BYTES_PER_XDR_UNIT] = { 0, 0, 0, 0 };
+
+/*
+ * Free a data structure using XDR
+ * Not a filter, but a convenient utility nonetheless
+ */
+void
+xdr_free(
+	xdrproc_t proc,
+	char *objp)
+{
+	XDR x;
+
+	x.x_op = XDR_FREE;
+	(*proc)(&x, objp);
+}
+
+/*
+ * XDR nothing
+ */
+bool_t
+xdr_void(void)
+{
+
+	return (TRUE);
+}
+
+
+/*
+ * XDR integers
+ */
+bool_t
+xdr_int(
+	XDR *xdrs,
+	int *ip)
+{
+	long l;
+
+	switch (xdrs->x_op) {
+
+	case XDR_ENCODE:
+		l = (long) *ip;
+		return (XDR_PUTLONG(xdrs, &l));
+
+	case XDR_DECODE:
+		if (!XDR_GETLONG(xdrs, &l)) {
+			return (FALSE);
+		}
+		*ip = (int) l;
+		return (TRUE);
+
+	case XDR_FREE:
+		return (TRUE);
+	}
+	/* NOTREACHED */
+	return (FALSE);
+}
+
+/*
+ * XDR unsigned integers
+ */
+bool_t
+xdr_u_int(
+	XDR *xdrs,
+	u_int *up)
+{
+	u_long l;
+
+	switch (xdrs->x_op) {
+
+	case XDR_ENCODE:
+		l = (u_long) *up;
+		return (XDR_PUTLONG(xdrs, (long *)&l));
+
+	case XDR_DECODE:
+		if (!XDR_GETLONG(xdrs, (long *)&l)) {
+			return (FALSE);
+		}
+		*up = (u_int) l;
+		return (TRUE);
+
+	case XDR_FREE:
+		return (TRUE);
+	}
+	/* NOTREACHED */
+	return (FALSE);
+}
+
+
+/*
+ * XDR long integers
+ * same as xdr_u_long - open coded to save a proc call!
+ */
+bool_t
+xdr_long(
+	XDR *xdrs,
+	long *lp)
+{
+	switch (xdrs->x_op) {
+	case XDR_ENCODE:
+		return (XDR_PUTLONG(xdrs, lp));
+	case XDR_DECODE:
+		return (XDR_GETLONG(xdrs, lp));
+	case XDR_FREE:
+		return (TRUE);
+	}
+	/* NOTREACHED */
+	return (FALSE);
+}
+
+/*
+ * XDR unsigned long integers
+ * same as xdr_long - open coded to save a proc call!
+ */
+bool_t
+xdr_u_long(
+	XDR *xdrs,
+	u_long *ulp)
+{
+	switch (xdrs->x_op) {
+	case XDR_ENCODE:
+		return (XDR_PUTLONG(xdrs, (long *)ulp));
+	case XDR_DECODE:
+		return (XDR_GETLONG(xdrs, (long *)ulp));
+	case XDR_FREE:
+		return (TRUE);
+	}
+	/* NOTREACHED */
+	return (FALSE);
+}
+
+
+/*
+ * XDR 32-bit integers
+ * same as xdr_u_int32_t - open coded to save a proc call!
+ */
+bool_t
+xdr_int32_t(
+	XDR *xdrs,
+	int32_t *int32_p)
+{
+	long l;
+
+	switch (xdrs->x_op) {
+
+	case XDR_ENCODE:
+		l = (long) *int32_p;
+		return (XDR_PUTLONG(xdrs, &l));
+
+	case XDR_DECODE:
+		if (!XDR_GETLONG(xdrs, &l)) {
+			return (FALSE);
+		}
+		*int32_p = (int32_t) l;
+		return (TRUE);
+
+	case XDR_FREE:
+		return (TRUE);
+	}
+	/* NOTREACHED */
+	return (FALSE);
+}
+
+/*
+ * XDR unsigned 32-bit integers
+ * same as xdr_int32_t - open coded to save a proc call!
+ */
+bool_t
+xdr_u_int32_t(
+	XDR *xdrs,
+	u_int32_t *u_int32_p)
+{
+	u_long l;
+
+	switch (xdrs->x_op) {
+
+	case XDR_ENCODE:
+		l = (u_long) *u_int32_p;
+		return (XDR_PUTLONG(xdrs, (long *)&l));
+
+	case XDR_DECODE:
+		if (!XDR_GETLONG(xdrs, (long *)&l)) {
+			return (FALSE);
+		}
+		*u_int32_p = (u_int32_t) l;
+		return (TRUE);
+
+	case XDR_FREE:
+		return (TRUE);
+	}
+	return (FALSE);
+}
+
+/*
+ * XDR short integers
+ */
+bool_t
+xdr_short(
+	XDR *xdrs,
+	short *sp)
+{
+	long l;
+
+	switch (xdrs->x_op) {
+
+	case XDR_ENCODE:
+		l = (long) *sp;
+		return (XDR_PUTLONG(xdrs, &l));
+
+	case XDR_DECODE:
+		if (!XDR_GETLONG(xdrs, &l)) {
+			return (FALSE);
+		}
+		*sp = (short) l;
+		return (TRUE);
+
+	case XDR_FREE:
+		return (TRUE);
+	}
+	/* NOTREACHED */
+	return (FALSE);
+}
+
+/*
+ * XDR unsigned short integers
+ */
+bool_t
+xdr_u_short(
+	XDR *xdrs,
+	u_short *usp)
+{
+	u_long l;
+
+	switch (xdrs->x_op) {
+
+	case XDR_ENCODE:
+		l = (u_long) *usp;
+		return (XDR_PUTLONG(xdrs, (long *)&l));
+
+	case XDR_DECODE:
+		if (!XDR_GETLONG(xdrs, (long *)&l)) {
+			return (FALSE);
+		}
+		*usp = (u_short) l;
+		return (TRUE);
+
+	case XDR_FREE:
+		return (TRUE);
+	}
+	/* NOTREACHED */
+	return (FALSE);
+}
+
+
+/*
+ * XDR 16-bit integers
+ */
+bool_t
+xdr_int16_t(
+	XDR *xdrs,
+	int16_t *int16_p)
+{
+	long l;
+
+	switch (xdrs->x_op) {
+
+	case XDR_ENCODE:
+		l = (long) *int16_p;
+		return (XDR_PUTLONG(xdrs, &l));
+
+	case XDR_DECODE:
+		if (!XDR_GETLONG(xdrs, &l)) {
+			return (FALSE);
+		}
+		*int16_p = (int16_t) l;
+		return (TRUE);
+
+	case XDR_FREE:
+		return (TRUE);
+	}
+	/* NOTREACHED */
+	return (FALSE);
+}
+
+/*
+ * XDR unsigned 16-bit integers
+ */
+bool_t
+xdr_u_int16_t(
+	XDR *xdrs,
+	u_int16_t *u_int16_p)
+{
+	u_long l;
+
+	switch (xdrs->x_op) {
+
+	case XDR_ENCODE:
+		l = (u_long) *u_int16_p;
+		return (XDR_PUTLONG(xdrs, (long *)&l));
+
+	case XDR_DECODE:
+		if (!XDR_GETLONG(xdrs, (long *)&l)) {
+			return (FALSE);
+		}
+		*u_int16_p = (u_int16_t) l;
+		return (TRUE);
+
+	case XDR_FREE:
+		return (TRUE);
+	}
+	/* NOTREACHED */
+	return (FALSE);
+}
+
+
+/*
+ * XDR a char
+ */
+bool_t
+xdr_char(
+	XDR *xdrs,
+	char *cp)
+{
+	int i;
+
+	i = (*cp);
+	if (!xdr_int(xdrs, &i)) {
+		return (FALSE);
+	}
+	*cp = i;
+	return (TRUE);
+}
+
+/*
+ * XDR an unsigned char
+ */
+bool_t
+xdr_u_char(
+	XDR *xdrs,
+	u_char *cp)
+{
+	u_int u;
+
+	u = (*cp);
+	if (!xdr_u_int(xdrs, &u)) {
+		return (FALSE);
+	}
+	*cp = u;
+	return (TRUE);
+}
+
+/*
+ * XDR booleans
+ */
+bool_t
+xdr_bool(
+	XDR *xdrs,
+	bool_t *bp)
+{
+	long lb;
+
+	switch (xdrs->x_op) {
+
+	case XDR_ENCODE:
+		lb = *bp ? XDR_TRUE : XDR_FALSE;
+		return (XDR_PUTLONG(xdrs, &lb));
+
+	case XDR_DECODE:
+		if (!XDR_GETLONG(xdrs, &lb)) {
+			return (FALSE);
+		}
+		*bp = (lb == XDR_FALSE) ? FALSE : TRUE;
+		return (TRUE);
+
+	case XDR_FREE:
+		return (TRUE);
+	}
+	/* NOTREACHED */
+	return (FALSE);
+}
+
+/*
+ * XDR enumerations
+ */
+bool_t
+xdr_enum(
+	XDR *xdrs,
+	enum_t *ep)
+{
+#ifndef lint
+	/*
+	 * enums are treated as ints
+	 */
+	if (sizeof (enum_t) == sizeof (long)) {
+		return (xdr_long(xdrs, (long *)ep));
+	} else if (sizeof (enum_t) == sizeof (int)) {
+		return (xdr_int(xdrs, (int *)ep));
+	} else if (sizeof (enum_t) == sizeof (short)) {
+		return (xdr_short(xdrs, (short *)ep));
+	} else {
+		return (FALSE);
+	}
+#else
+	(void) (xdr_short(xdrs, (short *)ep));
+	(void) (xdr_int(xdrs, (int *)ep));
+	return (xdr_long(xdrs, (long *)ep));
+#endif
+}
+
+/*
+ * XDR opaque data
+ * Allows the specification of a fixed size sequence of opaque bytes.
+ * cp points to the opaque object and cnt gives the byte length.
+ */
+bool_t
+xdr_opaque(
+	XDR *xdrs,
+	caddr_t cp,
+	u_int cnt)
+{
+	u_int rndup;
+	static int crud[BYTES_PER_XDR_UNIT];
+
+	/*
+	 * if no data we are done
+	 */
+	if (cnt == 0)
+		return (TRUE);
+
+	/*
+	 * round byte count to full xdr units
+	 */
+	rndup = cnt % BYTES_PER_XDR_UNIT;
+	if (rndup > 0)
+		rndup = BYTES_PER_XDR_UNIT - rndup;
+
+	if (xdrs->x_op == XDR_DECODE) {
+		if (!XDR_GETBYTES(xdrs, cp, cnt)) {
+			return (FALSE);
+		}
+		if (rndup == 0)
+			return (TRUE);
+		return (XDR_GETBYTES(xdrs, (caddr_t)crud, rndup));
+	}
+
+	if (xdrs->x_op == XDR_ENCODE) {
+		if (!XDR_PUTBYTES(xdrs, cp, cnt)) {
+			return (FALSE);
+		}
+		if (rndup == 0)
+			return (TRUE);
+		return (XDR_PUTBYTES(xdrs, xdr_zero, rndup));
+	}
+
+	if (xdrs->x_op == XDR_FREE) {
+		return (TRUE);
+	}
+
+	return (FALSE);
+}
+
+/*
+ * XDR counted bytes
+ * *cpp is a pointer to the bytes, *sizep is the count.
+ * If *cpp is NULL maxsize bytes are allocated
+ */
+bool_t
+xdr_bytes(
+	XDR *xdrs,
+	char **cpp,
+	u_int *sizep,
+	u_int maxsize)
+{
+	char *sp = *cpp;  /* sp is the actual string pointer */
+	u_int nodesize;
+
+	/*
+	 * first deal with the length since xdr bytes are counted
+	 */
+	if (! xdr_u_int(xdrs, sizep)) {
+		return (FALSE);
+	}
+	nodesize = *sizep;
+	if ((nodesize > maxsize) && (xdrs->x_op != XDR_FREE)) {
+		return (FALSE);
+	}
+
+	/*
+	 * now deal with the actual bytes
+	 */
+	switch (xdrs->x_op) {
+
+	case XDR_DECODE:
+		if (nodesize == 0) {
+			return (TRUE);
+		}
+		if (sp == NULL) {
+			*cpp = sp = mem_alloc(nodesize);
+		}
+		if (sp == NULL) {
+			warnx("xdr_bytes: out of memory");
+			return (FALSE);
+		}
+		/* FALLTHROUGH */
+
+	case XDR_ENCODE:
+		return (xdr_opaque(xdrs, sp, nodesize));
+
+	case XDR_FREE:
+		if (sp != NULL) {
+			mem_free(sp, nodesize);
+			*cpp = NULL;
+		}
+		return (TRUE);
+	}
+	/* NOTREACHED */
+	return (FALSE);
+}
+
+/*
+ * Implemented here due to commonality of the object.
+ */
+bool_t
+xdr_netobj(
+	XDR *xdrs,
+	struct netobj *np)
+{
+
+	return (xdr_bytes(xdrs, &np->n_bytes, &np->n_len, MAX_NETOBJ_SZ));
+}
+
+/*
+ * XDR a descriminated union
+ * Support routine for discriminated unions.
+ * You create an array of xdrdiscrim structures, terminated with
+ * an entry with a null procedure pointer.  The routine gets
+ * the discriminant value and then searches the array of xdrdiscrims
+ * looking for that value.  It calls the procedure given in the xdrdiscrim
+ * to handle the discriminant.  If there is no specific routine a default
+ * routine may be called.
+ * If there is no specific or default routine an error is returned.
+ */
+bool_t
+xdr_union(
+	XDR *xdrs,
+	enum_t *dscmp,		/* enum to decide which arm to work on */
+	char *unp,		/* the union itself */
+	const struct xdr_discrim *choices,	/* [value, xdr proc] for each arm */
+	xdrproc_t dfault)	/* default xdr routine */
+{
+	enum_t dscm;
+
+	/*
+	 * we deal with the discriminator;  it's an enum
+	 */
+	if (! xdr_enum(xdrs, dscmp)) {
+		return (FALSE);
+	}
+	dscm = *dscmp;
+
+	/*
+	 * search choices for a value that matches the discriminator.
+	 * if we find one, execute the xdr routine for that value.
+	 */
+	for (; choices->proc != NULL_xdrproc_t; choices++) {
+		if (choices->value == dscm)
+			return ((*(choices->proc))(xdrs, unp, LASTUNSIGNED));
+	}
+
+	/*
+	 * no match - execute the default xdr routine if there is one
+	 */
+	return ((dfault == NULL_xdrproc_t) ? FALSE :
+	    (*dfault)(xdrs, unp, LASTUNSIGNED));
+}
+
+
+/*
+ * Non-portable xdr primitives.
+ * Care should be taken when moving these routines to new architectures.
+ */
+
+
+/*
+ * XDR null terminated ASCII strings
+ * xdr_string deals with "C strings" - arrays of bytes that are
+ * terminated by a NULL character.  The parameter cpp references a
+ * pointer to storage; If the pointer is null, then the necessary
+ * storage is allocated.  The last parameter is the max allowed length
+ * of the string as specified by a protocol.
+ */
+bool_t
+xdr_string(
+	XDR *xdrs,
+	char **cpp,
+	u_int maxsize)
+{
+	char *sp = *cpp;  /* sp is the actual string pointer */
+	u_int size = 0;
+	u_int nodesize;
+
+	/*
+	 * first deal with the length since xdr strings are counted-strings
+	 */
+	switch (xdrs->x_op) {
+	case XDR_FREE:
+		if (sp == NULL) {
+			return(TRUE);	/* already free */
+		}
+		/* FALLTHROUGH */
+	case XDR_ENCODE:
+		size = strlen(sp);
+		break;
+	case XDR_DECODE:
+		break;
+	}
+	if (! xdr_u_int(xdrs, &size)) {
+		return (FALSE);
+	}
+	if (size > maxsize) {
+		return (FALSE);
+	}
+	nodesize = size + 1;
+
+	/*
+	 * now deal with the actual bytes
+	 */
+	switch (xdrs->x_op) {
+
+	case XDR_DECODE:
+		if (nodesize == 0) {
+			return (TRUE);
+		}
+		if (sp == NULL)
+			*cpp = sp = mem_alloc(nodesize);
+		if (sp == NULL) {
+			warnx("xdr_string: out of memory");
+			return (FALSE);
+		}
+		sp[size] = 0;
+		/* FALLTHROUGH */
+
+	case XDR_ENCODE:
+		return (xdr_opaque(xdrs, sp, size));
+
+	case XDR_FREE:
+		mem_free(sp, nodesize);
+		*cpp = NULL;
+		return (TRUE);
+	}
+	/* NOTREACHED */
+	return (FALSE);
+}
+
+/*
+ * Wrapper for xdr_string that can be called directly from
+ * routines like clnt_call
+ */
+bool_t
+xdr_wrapstring(
+	XDR *xdrs,
+	char **cpp)
+{
+	return xdr_string(xdrs, cpp, LASTUNSIGNED);
+}
+
+/*
+ * XDR 64-bit integers
+ */
+bool_t
+xdr_int64_t(
+	XDR *xdrs,
+	int64_t *int64_p)
+{
+	int64_t x;
+
+	switch (xdrs->x_op) {
+	case XDR_ENCODE:
+		return (xdr_opaque(xdrs, (caddr_t)int64_p, sizeof(int64_t)));
+	case XDR_DECODE:
+		if (!xdr_opaque(xdrs, (caddr_t)&x, sizeof x)) {
+			return (FALSE);
+		}
+		*int64_p = x;
+		return (TRUE);
+	case XDR_FREE:
+		return (TRUE);
+	}
+	/* NOTREACHED */
+	return (FALSE);
+}
+
+
+/*
+ * XDR unsigned 64-bit integers
+ */
+bool_t
+xdr_u_int64_t(
+	XDR *xdrs,
+	u_int64_t *uint64_p)
+{
+	u_int64_t x;
+
+	switch (xdrs->x_op) {
+	case XDR_ENCODE:
+		return (xdr_opaque(xdrs, (caddr_t)uint64_p, sizeof(u_int64_t)));
+	case XDR_DECODE:
+		if (!xdr_opaque(xdrs, (caddr_t)&x, sizeof x)) {
+			return (FALSE);
+		}
+		*uint64_p = x;
+		return (TRUE);
+	case XDR_FREE:
+		return (TRUE);
+	}
+	/* NOTREACHED */
+	return (FALSE);
+}
+
+/* FIXME: RTEMS does not support u_longlong_t and longlong_t, yet */
+#if !defined(__rtems__)
+/*
+ * XDR hypers
+ */
+bool_t
+xdr_hyper(xdrs, llp)
+	XDR *xdrs;
+	longlong_t *llp;
+{
+
+	/*
+	 * Don't bother open-coding this; it's a fair amount of code.  Just
+	 * call xdr_int64_t().
+	 */
+	return (xdr_int64_t(xdrs, (int64_t *)llp));
+}
+
+
+/*
+ * XDR unsigned hypers
+ */
+bool_t
+xdr_u_hyper(xdrs, ullp)
+	XDR *xdrs;
+	u_longlong_t *ullp;
+{
+
+	/*
+	 * Don't bother open-coding this; it's a fair amount of code.  Just
+	 * call xdr_u_int64_t().
+	 */
+	return (xdr_u_int64_t(xdrs, (u_int64_t *)ullp));
+}
+
+
+/*
+ * XDR longlong_t's
+ */
+bool_t
+xdr_longlong_t(xdrs, llp)
+	XDR *xdrs;
+	longlong_t *llp;
+{
+
+	/*
+	 * Don't bother open-coding this; it's a fair amount of code.  Just
+	 * call xdr_int64_t().
+	 */
+	return (xdr_int64_t(xdrs, (int64_t *)llp));
+}
+
+
+/*
+ * XDR u_longlong_t's
+ */
+bool_t
+xdr_u_longlong_t(xdrs, ullp)
+	XDR *xdrs;
+	u_longlong_t *ullp;
+{
+
+	/*
+	 * Don't bother open-coding this; it's a fair amount of code.  Just
+	 * call xdr_u_int64_t().
+	 */
+	return (xdr_u_int64_t(xdrs, (u_int64_t *)ullp));
+}
+#endif
diff --git a/services/librpc/src/xdr/xdr_array.c b/services/librpc/src/xdr/xdr_array.c
new file mode 100644
index 0000000..190dc3c
--- /dev/null
+++ b/services/librpc/src/xdr/xdr_array.c
@@ -0,0 +1,160 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)xdr_array.c 1.10 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)xdr_array.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/xdr/xdr_array.c,v 1.8 1999/08/28 00:02:55 peter Exp $";
+#endif
+
+/*
+ * xdr_array.c, Generic XDR routines impelmentation.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ *
+ * These are the "non-trivial" xdr primitives used to serialize and de-serialize
+ * arrays.  See xdr.h for more info on the interface to xdr.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <rpc/types.h>
+#include <rpc/xdr.h>
+
+#define LASTUNSIGNED ((u_int) 0-1)
+
+/*
+ * XDR an array of arbitrary elements
+ * *addrp is a pointer to the array, *sizep is the number of elements.
+ * If addrp is NULL (*sizep * elsize) bytes are allocated.
+ * elsize is the size (in bytes) of each element, and elproc is the
+ * xdr procedure to call to handle each element of the array.
+ */
+bool_t
+xdr_array(
+	register XDR *xdrs,
+	caddr_t *addrp,		/* array pointer */
+	u_int *sizep,		/* number of elements */
+	u_int maxsize,		/* max numberof elements */
+	u_int elsize,		/* size in bytes of each element */
+	xdrproc_t elproc)	/* xdr routine to handle each element */
+{
+	register u_int i;
+	register caddr_t target = *addrp;
+	register u_int c;  /* the actual element count */
+	register bool_t stat = TRUE;
+	register u_int nodesize;
+
+	/* like strings, arrays are really counted arrays */
+	if (! xdr_u_int(xdrs, sizep)) {
+		return (FALSE);
+	}
+	c = *sizep;
+	if ((c > maxsize) && (xdrs->x_op != XDR_FREE)) {
+		return (FALSE);
+	}
+	nodesize = c * elsize;
+
+	/*
+	 * if we are deserializing, we may need to allocate an array.
+	 * We also save time by checking for a null array if we are freeing.
+	 */
+	if (target == NULL)
+		switch (xdrs->x_op) {
+		case XDR_DECODE:
+			if (c == 0)
+				return (TRUE);
+			*addrp = target = mem_alloc(nodesize);
+			if (target == NULL) {
+				(void) fprintf(stderr,
+					"xdr_array: out of memory\n");
+				return (FALSE);
+			}
+			memset(target, 0, nodesize);
+			break;
+
+		case XDR_FREE:
+			return (TRUE);
+		case XDR_ENCODE:  /* to avoid warning */
+			break;
+	}
+
+	/*
+	 * now we xdr each element of array
+	 */
+	for (i = 0; (i < c) && stat; i++) {
+		stat = (*elproc)(xdrs, target, LASTUNSIGNED);
+		target += elsize;
+	}
+
+	/*
+	 * the array may need freeing
+	 */
+	if (xdrs->x_op == XDR_FREE) {
+		mem_free(*addrp, nodesize);
+		*addrp = NULL;
+	}
+	return (stat);
+}
+
+/*
+ * xdr_vector():
+ *
+ * XDR a fixed length array. Unlike variable-length arrays,
+ * the storage of fixed length arrays is static and unfreeable.
+ * > basep: base of the array
+ * > size: size of the array
+ * > elemsize: size of each element
+ * > xdr_elem: routine to XDR each element
+ */
+bool_t
+xdr_vector(
+	register XDR *xdrs,
+	register char *basep,
+	register u_int nelem,
+	register u_int elemsize,
+	register xdrproc_t xdr_elem)
+{
+	register u_int i;
+	register char *elptr;
+
+	elptr = basep;
+	for (i = 0; i < nelem; i++) {
+		if (! (*xdr_elem)(xdrs, elptr, LASTUNSIGNED)) {
+			return(FALSE);
+		}
+		elptr += elemsize;
+	}
+	return(TRUE);
+}
diff --git a/services/librpc/src/xdr/xdr_float.c b/services/librpc/src/xdr/xdr_float.c
new file mode 100644
index 0000000..2517072
--- /dev/null
+++ b/services/librpc/src/xdr/xdr_float.c
@@ -0,0 +1,343 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)xdr_float.c 1.12 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)xdr_float.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/xdr/xdr_float.c,v 1.7 1999/08/28 00:02:55 peter Exp $";
+#endif
+
+/*
+ * xdr_float.c, Generic XDR routines impelmentation.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ *
+ * These are the "floating point" xdr routines used to (de)serialize
+ * most common data items.  See xdr.h for more info on the interface to
+ * xdr.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdio.h>
+#include <sys/types.h>
+#include <sys/param.h>
+#include <rpc/types.h>
+#include <rpc/xdr.h>
+
+/*
+ * NB: Not portable.
+ * This routine works on machines with IEEE754 FP and Vaxen.
+ */
+
+#if defined(__alpha__) || \
+    defined(_AM29K) || \
+    defined(__arm__) || \
+    defined(__H8300__) || defined(__h8300__) || \
+    defined(__hppa__) || \
+    defined(__i386__) || \
+    defined(__lm32__) || \
+    defined(__m68k__) || defined(__mc68000__) || \
+    defined(__mips__) || \
+    defined(__nios2__) || \
+    defined(__ns32k__) || \
+    defined(__sparc__) || \
+    defined(__ppc__) || defined(__PPC__) || \
+    defined(__sh__) || \
+    defined(__AVR__) || \
+    defined(__BFIN__) || \
+    defined(__m32c__) || \
+    defined(__M32R__) || \
+    defined(__v850)
+
+#include <rtems/endian.h>
+#if !defined(IEEEFP)
+#define IEEEFP
+#endif
+
+#elif defined(_TMS320C3x) || defined(_TMS320C4x)
+#error "Texas Instruments C3x/C4x Not supported."
+
+#elif defined(vax)
+
+/* What IEEE single precision floating point looks like on a Vax */
+struct	ieee_single {
+	unsigned int	mantissa: 23;
+	unsigned int	exp     : 8;
+	unsigned int	sign    : 1;
+};
+
+/* Vax single precision floating point */
+struct	vax_single {
+	unsigned int	mantissa1 : 7;
+	unsigned int	exp       : 8;
+	unsigned int	sign      : 1;
+	unsigned int	mantissa2 : 16;
+};
+
+#define VAX_SNG_BIAS	0x81
+#define IEEE_SNG_BIAS	0x7f
+
+static struct sgl_limits {
+	struct vax_single s;
+	struct ieee_single ieee;
+} sgl_limits[2] = {
+	{{ 0x7f, 0xff, 0x0, 0xffff },	/* Max Vax */
+	{ 0x0, 0xff, 0x0 }},		/* Max IEEE */
+	{{ 0x0, 0x0, 0x0, 0x0 },	/* Min Vax */
+	{ 0x0, 0x0, 0x0 }}		/* Min IEEE */
+};
+/* end of vax */
+#else
+#error "xdr_float.c: unknown CPU"
+#endif
+
+
+bool_t
+xdr_float(
+	register XDR *xdrs,
+	register float *fp)
+{
+#ifdef IEEEFP
+	bool_t rv;
+	long tmpl;
+#else
+	struct ieee_single is;
+	struct vax_single vs, *vsp;
+	struct sgl_limits *lim;
+	int i;
+#endif
+	switch (xdrs->x_op) {
+
+	case XDR_ENCODE:
+#ifdef IEEEFP
+		tmpl = *(int32_t *)fp;
+		return (XDR_PUTLONG(xdrs, &tmpl));
+#else
+		vs = *((struct vax_single *)fp);
+		for (i = 0, lim = sgl_limits;
+			i < sizeof(sgl_limits)/sizeof(struct sgl_limits);
+			i++, lim++) {
+			if ((vs.mantissa2 == lim->s.mantissa2) &&
+				(vs.exp == lim->s.exp) &&
+				(vs.mantissa1 == lim->s.mantissa1)) {
+				is = lim->ieee;
+				goto shipit;
+			}
+		}
+		is.exp = vs.exp - VAX_SNG_BIAS + IEEE_SNG_BIAS;
+		is.mantissa = (vs.mantissa1 << 16) | vs.mantissa2;
+	shipit:
+		is.sign = vs.sign;
+		return (XDR_PUTLONG(xdrs, (long *)&is));
+#endif
+
+	case XDR_DECODE:
+#ifdef IEEEFP
+		rv = XDR_GETLONG(xdrs, &tmpl);
+		*(int32_t *)fp = tmpl;
+		return (rv);
+#else
+		vsp = (struct vax_single *)fp;
+		if (!XDR_GETLONG(xdrs, (long *)&is))
+			return (FALSE);
+		for (i = 0, lim = sgl_limits;
+			i < sizeof(sgl_limits)/sizeof(struct sgl_limits);
+			i++, lim++) {
+			if ((is.exp == lim->ieee.exp) &&
+				(is.mantissa == lim->ieee.mantissa)) {
+				*vsp = lim->s;
+				goto doneit;
+			}
+		}
+		vsp->exp = is.exp - IEEE_SNG_BIAS + VAX_SNG_BIAS;
+		vsp->mantissa2 = is.mantissa;
+		vsp->mantissa1 = (is.mantissa >> 16);
+	doneit:
+		vsp->sign = is.sign;
+		return (TRUE);
+#endif
+
+	case XDR_FREE:
+		return (TRUE);
+	}
+	return (FALSE);
+}
+
+#ifdef vax
+/* What IEEE double precision floating point looks like on a Vax */
+struct	ieee_double {
+	unsigned int	mantissa1 : 20;
+	unsigned int	exp       : 11;
+	unsigned int	sign      : 1;
+	unsigned int	mantissa2 : 32;
+};
+
+/* Vax double precision floating point */
+struct  vax_double {
+	unsigned int	mantissa1 : 7;
+	unsigned int	exp       : 8;
+	unsigned int	sign      : 1;
+	unsigned int	mantissa2 : 16;
+	unsigned int	mantissa3 : 16;
+	unsigned int	mantissa4 : 16;
+};
+
+#define VAX_DBL_BIAS	0x81
+#define IEEE_DBL_BIAS	0x3ff
+#define MASK(nbits)	((1 << nbits) - 1)
+
+static struct dbl_limits {
+	struct	vax_double d;
+	struct	ieee_double ieee;
+} dbl_limits[2] = {
+	{{ 0x7f, 0xff, 0x0, 0xffff, 0xffff, 0xffff },	/* Max Vax */
+	{ 0x0, 0x7ff, 0x0, 0x0 }},			/* Max IEEE */
+	{{ 0x0, 0x0, 0x0, 0x0, 0x0, 0x0},		/* Min Vax */
+	{ 0x0, 0x0, 0x0, 0x0 }}				/* Min IEEE */
+};
+
+#endif /* vax */
+
+
+bool_t
+xdr_double(
+	register XDR *xdrs,
+	double *dp)
+{
+#ifdef IEEEFP
+	register int32_t *i32p;
+	bool_t rv;
+	long tmpl;
+#else
+	register long *lp;
+	struct	ieee_double id;
+	struct	vax_double vd;
+	register struct dbl_limits *lim;
+	int i;
+#endif
+
+	switch (xdrs->x_op) {
+
+	case XDR_ENCODE:
+#ifdef IEEEFP
+		i32p = (int32_t *)dp;
+#if BYTE_ORDER == BIG_ENDIAN
+		tmpl = *i32p++;
+		rv = XDR_PUTLONG(xdrs, &tmpl);
+		if (!rv)
+			return (rv);
+		tmpl = *i32p;
+		rv = XDR_PUTLONG(xdrs, &tmpl);
+#else
+		tmpl = *(i32p+1);
+		rv = XDR_PUTLONG(xdrs, &tmpl);
+		if (!rv)
+			return (rv);
+		tmpl = *i32p;
+		rv = XDR_PUTLONG(xdrs, &tmpl);
+#endif
+		return (rv);
+#else
+		vd = *((struct vax_double *)dp);
+		for (i = 0, lim = dbl_limits;
+			i < sizeof(dbl_limits)/sizeof(struct dbl_limits);
+			i++, lim++) {
+			if ((vd.mantissa4 == lim->d.mantissa4) &&
+				(vd.mantissa3 == lim->d.mantissa3) &&
+				(vd.mantissa2 == lim->d.mantissa2) &&
+				(vd.mantissa1 == lim->d.mantissa1) &&
+				(vd.exp == lim->d.exp)) {
+				id = lim->ieee;
+				goto shipit;
+			}
+		}
+		id.exp = vd.exp - VAX_DBL_BIAS + IEEE_DBL_BIAS;
+		id.mantissa1 = (vd.mantissa1 << 13) | (vd.mantissa2 >> 3);
+		id.mantissa2 = ((vd.mantissa2 & MASK(3)) << 29) |
+				(vd.mantissa3 << 13) |
+				((vd.mantissa4 >> 3) & MASK(13));
+	shipit:
+		id.sign = vd.sign;
+		lp = (long *)&id;
+		return (XDR_PUTLONG(xdrs, lp++) && XDR_PUTLONG(xdrs, lp));
+#endif
+
+	case XDR_DECODE:
+#ifdef IEEEFP
+		i32p = (int32_t *)dp;
+#if BYTE_ORDER == BIG_ENDIAN
+		rv = XDR_GETLONG(xdrs, &tmpl);
+		*i32p++ = tmpl;
+		if (!rv)
+			return (rv);
+		rv = XDR_GETLONG(xdrs, &tmpl);
+		*i32p = tmpl;
+#else
+		rv = XDR_GETLONG(xdrs, &tmpl);
+		*(i32p+1) = tmpl;
+		if (!rv)
+			return (rv);
+		rv = XDR_GETLONG(xdrs, &tmpl);
+		*i32p = tmpl;
+#endif
+		return (rv);
+#else
+		lp = (long *)&id;
+		if (!XDR_GETLONG(xdrs, lp++) || !XDR_GETLONG(xdrs, lp))
+			return (FALSE);
+		for (i = 0, lim = dbl_limits;
+			i < sizeof(dbl_limits)/sizeof(struct dbl_limits);
+			i++, lim++) {
+			if ((id.mantissa2 == lim->ieee.mantissa2) &&
+				(id.mantissa1 == lim->ieee.mantissa1) &&
+				(id.exp == lim->ieee.exp)) {
+				vd = lim->d;
+				goto doneit;
+			}
+		}
+		vd.exp = id.exp - IEEE_DBL_BIAS + VAX_DBL_BIAS;
+		vd.mantissa1 = (id.mantissa1 >> 13);
+		vd.mantissa2 = ((id.mantissa1 & MASK(13)) << 3) |
+				(id.mantissa2 >> 29);
+		vd.mantissa3 = (id.mantissa2 >> 13);
+		vd.mantissa4 = (id.mantissa2 << 3);
+	doneit:
+		vd.sign = id.sign;
+		*dp = *((double *)&vd);
+		return (TRUE);
+#endif
+
+	case XDR_FREE:
+		return (TRUE);
+	}
+	return (FALSE);
+}
diff --git a/services/librpc/src/xdr/xdr_mem.c b/services/librpc/src/xdr/xdr_mem.c
new file mode 100644
index 0000000..5b30419
--- /dev/null
+++ b/services/librpc/src/xdr/xdr_mem.c
@@ -0,0 +1,245 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)xdr_mem.c 1.19 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)xdr_mem.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/xdr/xdr_mem.c,v 1.8 1999/08/28 00:02:56 peter Exp $";
+#endif
+
+/*
+ * xdr_mem.h, XDR implementation using memory buffers.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ *
+ * If you have some data to be interpreted as external data representation
+ * or to be converted to external data representation in a memory buffer,
+ * then this is the package for you.
+ *
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <string.h>
+#include <rpc/types.h>
+#include <rpc/xdr.h>
+#include <netinet/in.h>
+
+static bool_t	xdrmem_getlong_aligned(XDR *xdrs, long *lp);
+static bool_t	xdrmem_putlong_aligned(XDR *xdrs, const long *lp);
+static bool_t	xdrmem_getlong_unaligned(XDR *xdrs, long *lp);
+static bool_t	xdrmem_putlong_unaligned(XDR *xdrs, const long *lp);
+static bool_t	xdrmem_getbytes(XDR *xdrs, caddr_t addr, u_int len);
+static bool_t	xdrmem_putbytes(XDR *xdrs, const char *addr, u_int len);
+static u_int	xdrmem_getpos(XDR *xdrs); /* XXX w/64-bit pointers, u_int not enough! */
+static bool_t	xdrmem_setpos(XDR *xdrs, u_int pos);
+static int32_t *xdrmem_inline_aligned(XDR *xdrs, u_int len);
+static int32_t *xdrmem_inline_unaligned(XDR *xdrs, u_int len);
+static void	xdrmem_destroy(XDR *);
+
+static struct	xdr_ops xdrmem_ops_aligned = {
+	xdrmem_getlong_aligned,
+	xdrmem_putlong_aligned,
+	xdrmem_getbytes,
+	xdrmem_putbytes,
+	xdrmem_getpos,
+	xdrmem_setpos,
+	xdrmem_inline_aligned,
+	xdrmem_destroy
+};
+
+static struct	xdr_ops xdrmem_ops_unaligned = {
+	xdrmem_getlong_unaligned,
+	xdrmem_putlong_unaligned,
+	xdrmem_getbytes,
+	xdrmem_putbytes,
+	xdrmem_getpos,
+	xdrmem_setpos,
+	xdrmem_inline_unaligned,
+	xdrmem_destroy
+};
+
+/*
+ * The procedure xdrmem_create initializes a stream descriptor for a
+ * memory buffer.
+ */
+void
+xdrmem_create(
+	XDR *xdrs,
+	char * addr,
+	u_int size,
+	enum xdr_op op)
+{
+
+	xdrs->x_op = op;
+	xdrs->x_ops = ((uintptr_t)addr & (sizeof(int32_t) - 1))
+		? &xdrmem_ops_unaligned : &xdrmem_ops_aligned;
+	xdrs->x_private = xdrs->x_base = addr;
+	xdrs->x_handy = size;
+}
+
+static void
+xdrmem_destroy(XDR *xdrs)
+{
+
+}
+
+static bool_t
+xdrmem_getlong_aligned(
+	XDR *xdrs,
+	long *lp)
+{
+
+	if ((xdrs->x_handy -= sizeof(int32_t)) < 0)
+		return (FALSE);
+	*lp = ntohl(*(int32_t *)(xdrs->x_private));
+	xdrs->x_private += sizeof(int32_t);
+	return (TRUE);
+}
+
+static bool_t
+xdrmem_putlong_aligned(
+	XDR *xdrs,
+	const long *lp)
+{
+
+	if ((xdrs->x_handy -= sizeof(int32_t)) < 0)
+		return (FALSE);
+	*(int32_t *)xdrs->x_private = htonl(*lp);
+	xdrs->x_private += sizeof(int32_t);
+	return (TRUE);
+}
+
+static bool_t
+xdrmem_getlong_unaligned(
+	XDR *xdrs,
+	long *lp)
+{
+	int32_t l;
+
+	if ((xdrs->x_handy -= sizeof(int32_t)) < 0)
+		return (FALSE);
+	memcpy(&l, xdrs->x_private, sizeof(int32_t));
+	*lp = ntohl(l);
+	xdrs->x_private += sizeof(int32_t);
+	return (TRUE);
+}
+
+static bool_t
+xdrmem_putlong_unaligned(
+	XDR *xdrs,
+	const long *lp)
+{
+	int32_t l;
+
+	if ((xdrs->x_handy -= sizeof(int32_t)) < 0)
+		return (FALSE);
+	l = htonl(*lp);
+	memcpy(xdrs->x_private, &l, sizeof(int32_t));
+	xdrs->x_private += sizeof(int32_t);
+	return (TRUE);
+}
+
+static bool_t
+xdrmem_getbytes(
+	XDR *xdrs,
+	caddr_t addr,
+	u_int len)
+{
+
+	if ((xdrs->x_handy -= len) < 0)
+		return (FALSE);
+	memcpy(addr, xdrs->x_private, len);
+	xdrs->x_private += len;
+	return (TRUE);
+}
+
+static bool_t
+xdrmem_putbytes(
+	XDR *xdrs,
+	const char *addr,
+	u_int len)
+{
+
+	if ((xdrs->x_handy -= len) < 0)
+		return (FALSE);
+	memcpy(xdrs->x_private, addr, len);
+	xdrs->x_private += len;
+	return (TRUE);
+}
+
+static u_int
+xdrmem_getpos(
+	XDR *xdrs)
+{
+
+	/* XXX w/64-bit pointers, u_int not enough! */
+	return ((uintptr_t)xdrs->x_private - (uintptr_t)xdrs->x_base);
+}
+
+static bool_t
+xdrmem_setpos(
+	XDR *xdrs,
+	u_int pos)
+{
+	void *newaddr = xdrs->x_base + pos;
+	void *lastaddr = xdrs->x_private + xdrs->x_handy;
+
+	if (newaddr > lastaddr)
+		return (FALSE);
+	xdrs->x_private = newaddr;
+	xdrs->x_handy = (intptr_t)lastaddr - (intptr_t)newaddr;
+	return (TRUE);
+}
+
+static int32_t *
+xdrmem_inline_aligned(
+	XDR *xdrs,
+	u_int len)
+{
+	int32_t *buf = 0;
+
+	if (xdrs->x_handy >= len) {
+		xdrs->x_handy -= len;
+		buf = (int32_t *)xdrs->x_private;
+		xdrs->x_private += len;
+	}
+	return (buf);
+}
+
+static int32_t *
+xdrmem_inline_unaligned(
+	XDR *xdrs,
+	u_int len)
+{
+	
+	return (0);
+}
diff --git a/services/librpc/src/xdr/xdr_rec.c b/services/librpc/src/xdr/xdr_rec.c
new file mode 100644
index 0000000..7e47527
--- /dev/null
+++ b/services/librpc/src/xdr/xdr_rec.c
@@ -0,0 +1,608 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)xdr_rec.c 1.21 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)xdr_rec.c	2.2 88/08/01 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/xdr/xdr_rec.c,v 1.12 2000/01/19 06:12:32 wpaul Exp $";
+#endif
+
+/*
+ * xdr_rec.c, Implements TCP/IP based XDR streams with a "record marking"
+ * layer above tcp (for rpc's use).
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ *
+ * These routines interface XDRSTREAMS to a tcp/ip connection.
+ * There is a record marking layer between the xdr stream
+ * and the tcp transport level.  A record is composed on one or more
+ * record fragments.  A record fragment is a thirty-two bit header followed
+ * by n bytes of data, where n is contained in the header.  The header
+ * is represented as a htonl(u_long).  Thegh order bit encodes
+ * whether or not the fragment is the last fragment of the record
+ * (1 => fragment is last, 0 => more fragments to follow.
+ * The other 31 bits encode the byte length of the fragment.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <rpc/types.h>
+#include <rpc/xdr.h>
+#include <netinet/in.h>
+#include <unistd.h>   /* for lseek() */
+
+typedef struct rec_strm RECSTREAM;
+
+static u_int	fix_buf_size(u_int);
+static bool_t	flush_out(RECSTREAM *rstrm, bool_t eor);
+static bool_t	get_input_bytes(RECSTREAM *rstrm, caddr_t addr, int len);
+static bool_t	set_input_fragment(RECSTREAM *rstrm);
+static bool_t	skip_input_bytes(RECSTREAM *rstrm, long cnt);
+
+static bool_t	xdrrec_getlong(XDR *xdrs, long *lp);
+static bool_t	xdrrec_putlong(XDR *xdrs, const long *lp);
+static bool_t	xdrrec_getbytes(XDR *xdrs, caddr_t addr, u_int len);
+static bool_t	xdrrec_putbytes(XDR *xdrs, const char *addr, u_int len);
+static u_int	xdrrec_getpos(XDR *xdrs);
+static bool_t	xdrrec_setpos(XDR *xdrs, u_int pos);
+static int32_t *xdrrec_inline(XDR *xdrs, u_int len);
+static void	xdrrec_destroy(XDR *xdrs);
+
+static struct  xdr_ops xdrrec_ops = {
+	xdrrec_getlong,
+	xdrrec_putlong,
+	xdrrec_getbytes,
+	xdrrec_putbytes,
+	xdrrec_getpos,
+	xdrrec_setpos,
+	xdrrec_inline,
+	xdrrec_destroy
+};
+
+/*
+ * A record is composed of one or more record fragments.
+ * A record fragment is a two-byte header followed by zero to
+ * 2**32-1 bytes.  The header is treated as a long unsigned and is
+ * encode/decoded to the network via htonl/ntohl.  The low order 31 bits
+ * are a byte count of the fragment.  The highest order bit is a boolean:
+ * 1 => this fragment is the last fragment of the record,
+ * 0 => this fragment is followed by more fragment(s).
+ *
+ * The fragment/record machinery is not general;  it is constructed to
+ * meet the needs of xdr and rpc based on tcp.
+ */
+
+#define LAST_FRAG ((u_int32_t)(1L << 31))
+
+struct rec_strm {
+	caddr_t tcp_handle;
+	caddr_t the_buffer;
+	/*
+	 * out-goung bits
+	 */
+	int (*writeit) (caddr_t, caddr_t, int);
+	caddr_t out_base;	/* output buffer (points to frag header) */
+	caddr_t out_finger;	/* next output position */
+	caddr_t out_boundry;	/* data cannot up to this address */
+	u_int32_t *frag_header;	/* beginning of current fragment */
+	bool_t frag_sent;	/* true if buffer sent in middle of record */
+	/*
+	 * in-coming bits
+	 */
+	int (*readit) (caddr_t, caddr_t, int);
+	u_long in_size;	/* fixed size of the input buffer */
+	caddr_t in_base;
+	caddr_t in_finger;	/* location of next byte to be had */
+	caddr_t in_boundry;	/* can read up to this location */
+	long fbtbc;		/* fragment bytes to be consumed */
+	bool_t last_frag;
+	u_int sendsize;
+	u_int recvsize;
+};
+
+
+/*
+ * Create an xdr handle for xdrrec
+ * xdrrec_create fills in xdrs.  Sendsize and recvsize are
+ * send and recv buffer sizes (0 => use default).
+ * tcp_handle is an opaque handle that is passed as the first parameter to
+ * the procedures readit and writeit.  Readit and writeit are read and
+ * write respectively.   They are like the system
+ * calls expect that they take an opaque handle rather than an fd.
+ */
+void
+xdrrec_create(
+	XDR *xdrs,
+	u_int sendsize,
+	u_int recvsize,
+	caddr_t tcp_handle,
+	int (*readit)(char*, char*, int),  /* like read, but pass it a tcp_handle, not sock */
+	int (*writeit)(char*, char*, int)  /* like write, but pass it a tcp_handle, not sock */
+)
+{
+	RECSTREAM *rstrm =
+		(RECSTREAM *)mem_alloc(sizeof(RECSTREAM));
+
+	if (rstrm == NULL) {
+		(void)fprintf(stderr, "xdrrec_create: out of memory\n");
+		/*
+		 *  This is bad.  Should rework xdrrec_create to
+		 *  return a handle, and in this case return NULL
+		 */
+		return;
+	}
+	/*
+	 * adjust sizes and allocate buffer quad byte aligned
+	 */
+	rstrm->sendsize = sendsize = fix_buf_size(sendsize);
+	rstrm->recvsize = recvsize = fix_buf_size(recvsize);
+	rstrm->the_buffer = mem_alloc(sendsize + recvsize + BYTES_PER_XDR_UNIT);
+	if (rstrm->the_buffer == NULL) {
+		(void)fprintf(stderr, "xdrrec_create: out of memory\n");
+		return;
+	}
+	for (rstrm->out_base = rstrm->the_buffer;
+		(uintptr_t)rstrm->out_base % BYTES_PER_XDR_UNIT != 0;
+		rstrm->out_base++);
+	rstrm->in_base = rstrm->out_base + sendsize;
+	/*
+	 * now the rest ...
+	 */
+	xdrs->x_ops = &xdrrec_ops;
+	xdrs->x_private = (caddr_t)rstrm;
+	rstrm->tcp_handle = tcp_handle;
+	rstrm->readit = readit;
+	rstrm->writeit = writeit;
+	rstrm->out_finger = rstrm->out_boundry = rstrm->out_base;
+	rstrm->frag_header = (u_int32_t *)rstrm->out_base;
+	rstrm->out_finger += sizeof(u_int32_t);
+	rstrm->out_boundry += sendsize;
+	rstrm->frag_sent = FALSE;
+	rstrm->in_size = recvsize;
+	rstrm->in_boundry = rstrm->in_base;
+	rstrm->in_finger = (rstrm->in_boundry += recvsize);
+	rstrm->fbtbc = 0;
+	rstrm->last_frag = TRUE;
+}
+
+
+/*
+ * The reoutines defined below are the xdr ops which will go into the
+ * xdr handle filled in by xdrrec_create.
+ */
+
+static bool_t
+xdrrec_getlong(
+	XDR *xdrs,
+	long *lp)
+{
+	RECSTREAM *rstrm = (RECSTREAM *)(xdrs->x_private);
+	int32_t *buflp = (int32_t *)(rstrm->in_finger);
+	int32_t mylong;
+
+	/* first try the inline, fast case */
+	if ((rstrm->fbtbc >= sizeof(int32_t)) &&
+		(((intptr_t)rstrm->in_boundry - (intptr_t)buflp) >= sizeof(int32_t))) {
+		*lp = (long)ntohl((u_int32_t)(*buflp));
+		rstrm->fbtbc -= sizeof(int32_t);
+		rstrm->in_finger += sizeof(int32_t);
+	} else {
+		if (! xdrrec_getbytes(xdrs, (caddr_t)&mylong, sizeof(int32_t)))
+			return (FALSE);
+		*lp = (long)ntohl((u_int32_t)mylong);
+	}
+	return (TRUE);
+}
+
+static bool_t
+xdrrec_putlong(
+	XDR *xdrs,
+	const long *lp)
+{
+	RECSTREAM *rstrm = (RECSTREAM *)(xdrs->x_private);
+	int32_t *dest_lp = ((int32_t *)(rstrm->out_finger));
+
+	if ((rstrm->out_finger += sizeof(int32_t)) > rstrm->out_boundry) {
+		/*
+		 * this case should almost never happen so the code is
+		 * inefficient
+		 */
+		rstrm->out_finger -= sizeof(int32_t);
+		rstrm->frag_sent = TRUE;
+		if (! flush_out(rstrm, FALSE))
+			return (FALSE);
+		dest_lp = ((int32_t *)(rstrm->out_finger));
+		rstrm->out_finger += sizeof(int32_t);
+	}
+	*dest_lp = (int32_t)htonl((u_int32_t)(*lp));
+	return (TRUE);
+}
+
+static bool_t  /* must manage buffers, fragments, and records */
+xdrrec_getbytes(
+	XDR *xdrs,
+	caddr_t addr,
+	u_int len)
+{
+	RECSTREAM *rstrm = (RECSTREAM *)(xdrs->x_private);
+	int current;
+
+	while (len > 0) {
+		current = rstrm->fbtbc;
+		if (current == 0) {
+			if (rstrm->last_frag)
+				return (FALSE);
+			if (! set_input_fragment(rstrm))
+				return (FALSE);
+			continue;
+		}
+		current = (len < current) ? len : current;
+		if (! get_input_bytes(rstrm, addr, current))
+			return (FALSE);
+		addr += current;
+		rstrm->fbtbc -= current;
+		len -= current;
+	}
+	return (TRUE);
+}
+
+static bool_t
+xdrrec_putbytes(
+	XDR *xdrs,
+	const char *addr,
+	u_int len)
+{
+	RECSTREAM *rstrm = (RECSTREAM *)(xdrs->x_private);
+	long current;
+
+	while (len > 0) {
+		current = (intptr_t)rstrm->out_boundry -
+			(intptr_t)rstrm->out_finger;
+		current = (len < current) ? len : current;
+		memcpy(rstrm->out_finger, addr, current);
+		rstrm->out_finger += current;
+		addr += current;
+		len -= current;
+		if (rstrm->out_finger == rstrm->out_boundry) {
+			rstrm->frag_sent = TRUE;
+			if (! flush_out(rstrm, FALSE))
+				return (FALSE);
+		}
+	}
+	return (TRUE);
+}
+
+static u_int
+xdrrec_getpos(
+	XDR *xdrs)
+{
+	RECSTREAM *rstrm = (RECSTREAM *)xdrs->x_private;
+	long pos;
+
+	pos = lseek((intptr_t)rstrm->tcp_handle, (off_t) 0, 1);
+	if (pos != -1)
+		switch (xdrs->x_op) {
+
+		case XDR_ENCODE:
+			pos += rstrm->out_finger - rstrm->out_base;
+			break;
+
+		case XDR_DECODE:
+			pos -= rstrm->in_boundry - rstrm->in_finger;
+			break;
+
+		default:
+			pos = -1;
+			break;
+		}
+	return ((u_int) pos);
+}
+
+static bool_t
+xdrrec_setpos(
+	XDR *xdrs,
+	u_int pos)
+{
+	RECSTREAM *rstrm = (RECSTREAM *)xdrs->x_private;
+	u_int currpos = xdrrec_getpos(xdrs);
+	int delta = currpos - pos;
+	caddr_t newpos;
+
+	if ((int)currpos != -1)
+		switch (xdrs->x_op) {
+
+		case XDR_ENCODE:
+			newpos = rstrm->out_finger - delta;
+			if ((newpos > (caddr_t)(rstrm->frag_header)) &&
+				(newpos < rstrm->out_boundry)) {
+				rstrm->out_finger = newpos;
+				return (TRUE);
+			}
+			break;
+
+		case XDR_DECODE:
+			newpos = rstrm->in_finger - delta;
+			if ((delta < (int)(rstrm->fbtbc)) &&
+				(newpos <= rstrm->in_boundry) &&
+				(newpos >= rstrm->in_base)) {
+				rstrm->in_finger = newpos;
+				rstrm->fbtbc -= delta;
+				return (TRUE);
+			}
+			break;
+		case XDR_FREE:  /* to avoid warning */
+			break;
+		}
+	return (FALSE);
+}
+
+static int32_t *
+xdrrec_inline(
+	XDR *xdrs,
+	u_int len)
+{
+	RECSTREAM *rstrm = (RECSTREAM *)xdrs->x_private;
+	int32_t * buf = NULL;
+
+	switch (xdrs->x_op) {
+
+	case XDR_ENCODE:
+		if ((rstrm->out_finger + len) <= rstrm->out_boundry) {
+			buf = (int32_t *) rstrm->out_finger;
+			rstrm->out_finger += len;
+		}
+		break;
+
+	case XDR_DECODE:
+		if ((len <= rstrm->fbtbc) &&
+			((rstrm->in_finger + len) <= rstrm->in_boundry)) {
+			buf = (int32_t *) rstrm->in_finger;
+			rstrm->fbtbc -= len;
+			rstrm->in_finger += len;
+		}
+		break;
+	case XDR_FREE:  /* to avoid warning */
+		break;
+	}
+	return (buf);
+}
+
+static void
+xdrrec_destroy(
+	XDR *xdrs)
+{
+	RECSTREAM *rstrm = (RECSTREAM *)xdrs->x_private;
+
+	mem_free(rstrm->the_buffer,
+		rstrm->sendsize + rstrm->recvsize + BYTES_PER_XDR_UNIT);
+	mem_free((caddr_t)rstrm, sizeof(RECSTREAM));
+}
+
+
+/*
+ * Exported routines to manage xdr records
+ */
+
+/*
+ * Before reading (deserializing from the stream, one should always call
+ * this procedure to guarantee proper record alignment.
+ */
+bool_t
+xdrrec_skiprecord(
+	XDR *xdrs)
+{
+	RECSTREAM *rstrm = (RECSTREAM *)(xdrs->x_private);
+
+	while (rstrm->fbtbc > 0 || (! rstrm->last_frag)) {
+		if (! skip_input_bytes(rstrm, rstrm->fbtbc))
+			return (FALSE);
+		rstrm->fbtbc = 0;
+		if ((! rstrm->last_frag) && (! set_input_fragment(rstrm)))
+			return (FALSE);
+	}
+	rstrm->last_frag = FALSE;
+	return (TRUE);
+}
+
+/*
+ * Look ahead fuction.
+ * Returns TRUE iff there is no more input in the buffer
+ * after consuming the rest of the current record.
+ */
+bool_t
+xdrrec_eof(
+	XDR *xdrs)
+{
+	RECSTREAM *rstrm = (RECSTREAM *)(xdrs->x_private);
+
+	while (rstrm->fbtbc > 0 || (! rstrm->last_frag)) {
+		if (! skip_input_bytes(rstrm, rstrm->fbtbc))
+			return (TRUE);
+		rstrm->fbtbc = 0;
+		if ((! rstrm->last_frag) && (! set_input_fragment(rstrm)))
+			return (TRUE);
+	}
+	if (rstrm->in_finger == rstrm->in_boundry)
+		return (TRUE);
+	return (FALSE);
+}
+
+/*
+ * The client must tell the package when an end-of-record has occurred.
+ * The second paraemters tells whether the record should be flushed to the
+ * (output) tcp stream.  (This let's the package support batched or
+ * pipelined procedure calls.)  TRUE => immmediate flush to tcp connection.
+ */
+bool_t
+xdrrec_endofrecord(
+	XDR *xdrs,
+	bool_t sendnow)
+{
+	RECSTREAM *rstrm = (RECSTREAM *)(xdrs->x_private);
+	u_long len;  /* fragment length */
+
+	if (sendnow || rstrm->frag_sent ||
+		((uintptr_t)rstrm->out_finger + sizeof(u_int32_t) >=
+		(uintptr_t)rstrm->out_boundry)) {
+		rstrm->frag_sent = FALSE;
+		return (flush_out(rstrm, TRUE));
+	}
+	len = (uintptr_t)(rstrm->out_finger) - (uintptr_t)(rstrm->frag_header) -
+	   sizeof(u_int32_t);
+	*(rstrm->frag_header) = htonl((u_int32_t)len | LAST_FRAG);
+	rstrm->frag_header = (u_int32_t *)rstrm->out_finger;
+	rstrm->out_finger += sizeof(u_int32_t);
+	return (TRUE);
+}
+
+
+/*
+ * Internal useful routines
+ */
+static bool_t
+flush_out(
+	RECSTREAM *rstrm,
+	bool_t eor)
+{
+	u_int32_t eormask = (eor == TRUE) ? LAST_FRAG : 0;
+	u_int32_t len = (uintptr_t)(rstrm->out_finger) -
+		(uintptr_t)(rstrm->frag_header) - sizeof(u_int32_t);
+
+	*(rstrm->frag_header) = htonl(len | eormask);
+	len = (uintptr_t)(rstrm->out_finger) - (uintptr_t)(rstrm->out_base);
+	if ((*(rstrm->writeit))(rstrm->tcp_handle, rstrm->out_base, (int)len)
+		!= (int)len)
+		return (FALSE);
+	rstrm->frag_header = (u_int32_t *)rstrm->out_base;
+	rstrm->out_finger = (caddr_t)rstrm->out_base + sizeof(u_int32_t);
+	return (TRUE);
+}
+
+static bool_t  /* knows nothing about records!  Only about input buffers */
+fill_input_buf(
+	RECSTREAM *rstrm)
+{
+	caddr_t where;
+	u_long i;
+	long len;
+
+	where = rstrm->in_base;
+	i = (uintptr_t)rstrm->in_boundry % BYTES_PER_XDR_UNIT;
+	where += i;
+	len = rstrm->in_size - i;
+	if ((len = (*(rstrm->readit))(rstrm->tcp_handle, where, len)) == -1)
+		return (FALSE);
+	rstrm->in_finger = where;
+	where += len;
+	rstrm->in_boundry = where;
+	return (TRUE);
+}
+
+static bool_t  /* knows nothing about records!  Only about input buffers */
+get_input_bytes(
+	RECSTREAM *rstrm,
+	caddr_t addr,
+	int len)
+{
+	long current;
+
+	while (len > 0) {
+		current = (intptr_t)rstrm->in_boundry - (intptr_t)rstrm->in_finger;
+		if (current == 0) {
+			if (! fill_input_buf(rstrm))
+				return (FALSE);
+			continue;
+		}
+		current = (len < current) ? len : current;
+		memcpy(addr, rstrm->in_finger, current);
+		rstrm->in_finger += current;
+		addr += current;
+		len -= current;
+	}
+	return (TRUE);
+}
+
+static bool_t  /* next two bytes of the input stream are treated as a header */
+set_input_fragment(
+	RECSTREAM *rstrm)
+{
+	u_int32_t header;
+
+	if (! get_input_bytes(rstrm, (caddr_t)&header, sizeof(header)))
+		return (FALSE);
+	header = (long)ntohl(header);
+	rstrm->last_frag = ((header & LAST_FRAG) == 0) ? FALSE : TRUE;
+	/*
+	 * Sanity check. Try not to accept wildly incorrect
+	 * record sizes. Unfortunately, the only record size
+	 * we can positively identify as being 'wildly incorrect'
+	 * is zero. Ridiculously large record sizes may look wrong,
+	 * but we don't have any way to be certain that they aren't
+	 * what the client actually intended to send us.
+	 */
+	if (header == 0)
+		return(FALSE);
+	rstrm->fbtbc = header & (~LAST_FRAG);
+	return (TRUE);
+}
+
+static bool_t  /* consumes input bytes; knows nothing about records! */
+skip_input_bytes(
+	RECSTREAM *rstrm,
+	long cnt)
+{
+	long current;
+
+	while (cnt > 0) {
+		current = (intptr_t)rstrm->in_boundry - (intptr_t)rstrm->in_finger;
+		if (current == 0) {
+			if (! fill_input_buf(rstrm))
+				return (FALSE);
+			continue;
+		}
+		current = (cnt < current) ? cnt : current;
+		rstrm->in_finger += current;
+		cnt -= current;
+	}
+	return (TRUE);
+}
+
+static u_int
+fix_buf_size(
+	u_int s)
+{
+
+	if (s < 100)
+		s = 4000;
+	return (RNDUP(s));
+}
diff --git a/services/librpc/src/xdr/xdr_reference.c b/services/librpc/src/xdr/xdr_reference.c
new file mode 100644
index 0000000..a2a6ee5
--- /dev/null
+++ b/services/librpc/src/xdr/xdr_reference.c
@@ -0,0 +1,142 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)xdr_reference.c 1.11 87/08/11 SMI";*/
+/*static char *sccsid = "from: @(#)xdr_reference.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/xdr/xdr_reference.c,v 1.8 1999/08/28 00:02:56 peter Exp $";
+#endif
+
+/*
+ * xdr_reference.c, Generic XDR routines impelmentation.
+ *
+ * Copyright (C) 1987, Sun Microsystems, Inc.
+ *
+ * These are the "non-trivial" xdr primitives used to serialize and de-serialize
+ * "pointers".  See xdr.h for more info on the interface to xdr.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <rpc/types.h>
+#include <rpc/xdr.h>
+
+#define LASTUNSIGNED ((u_int) 0-1)
+
+/*
+ * XDR an indirect pointer
+ * xdr_reference is for recursively translating a structure that is
+ * referenced by a pointer inside the structure that is currently being
+ * translated.  pp references a pointer to storage. If *pp is null
+ * the  necessary storage is allocated.
+ * size is the sizeof the referneced structure.
+ * proc is the routine to handle the referenced structure.
+ */
+bool_t
+xdr_reference(
+	register XDR *xdrs,
+	caddr_t *pp,		/* the pointer to work on */
+	u_int size,		/* size of the object pointed to */
+	xdrproc_t proc)		/* xdr routine to handle the object */
+{
+	register caddr_t loc = *pp;
+	register bool_t stat;
+
+	if (loc == NULL)
+		switch (xdrs->x_op) {
+		case XDR_FREE:
+			return (TRUE);
+
+		case XDR_DECODE:
+			*pp = loc = (caddr_t) mem_alloc(size);
+			if (loc == NULL) {
+				(void) fprintf(stderr,
+				    "xdr_reference: out of memory\n");
+				return (FALSE);
+			}
+			memset(loc, 0, (int)size);
+			break;
+		case XDR_ENCODE:  /* to avoid warning */
+			break;
+	}
+
+	stat = (*proc)(xdrs, loc, LASTUNSIGNED);
+
+	if (xdrs->x_op == XDR_FREE) {
+		mem_free(loc, size);
+		*pp = NULL;
+	}
+	return (stat);
+}
+
+
+/*
+ * xdr_pointer():
+ *
+ * XDR a pointer to a possibly recursive data structure. This
+ * differs with xdr_reference in that it can serialize/deserialiaze
+ * trees correctly.
+ *
+ *  What's sent is actually a union:
+ *
+ *  union object_pointer switch (boolean b) {
+ *  case TRUE: object_data data;
+ *  case FALSE: void nothing;
+ *  }
+ *
+ * > objpp: Pointer to the pointer to the object.
+ * > obj_size: size of the object.
+ * > xdr_obj: routine to XDR an object.
+ *
+ */
+bool_t
+xdr_pointer(
+	register XDR *xdrs,
+	char **objpp,
+	u_int obj_size,
+	xdrproc_t xdr_obj)
+{
+
+	bool_t more_data;
+
+	more_data = (*objpp != NULL);
+	if (! xdr_bool(xdrs,&more_data)) {
+		return (FALSE);
+	}
+	if (! more_data) {
+		*objpp = NULL;
+		return (TRUE);
+	}
+	return (xdr_reference(xdrs,objpp,obj_size,xdr_obj));
+}
diff --git a/services/librpc/src/xdr/xdr_sizeof.c b/services/librpc/src/xdr/xdr_sizeof.c
new file mode 100644
index 0000000..72a7ff9
--- /dev/null
+++ b/services/librpc/src/xdr/xdr_sizeof.c
@@ -0,0 +1,167 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ * 
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ * 
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ * 
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ * 
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ * 
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+/*
+ * xdr_sizeof.c
+ *
+ * Copyright 1990 Sun Microsystems, Inc.
+ *
+ * General purpose routine to see how much space something will use
+ * when serialized using XDR.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <rpc/types.h>
+#include <rpc/xdr.h>
+#include <sys/types.h>
+#include <stdlib.h>
+
+/* ARGSUSED */
+static bool_t
+x_putlong(
+	XDR *xdrs,
+	const long *longp)
+{
+	xdrs->x_handy += BYTES_PER_XDR_UNIT;
+	return (TRUE);
+}
+
+/* ARGSUSED */
+static bool_t
+x_putbytes(
+	XDR *xdrs,
+	const char  *bp,
+	u_int len)
+{
+	xdrs->x_handy += len;
+	return (TRUE);
+}
+
+static u_int
+x_getpostn(
+	XDR *xdrs)
+{
+	return (xdrs->x_handy);
+}
+
+/* ARGSUSED */
+static bool_t
+x_setpostn(
+	XDR *xdrs,
+	u_int pos)
+{
+	/* This is not allowed */
+	return (FALSE);
+}
+
+static int32_t *
+x_inline(
+	XDR *xdrs,
+	u_int len)
+{
+	if (len == 0) {
+		return (NULL);
+	}
+	if (xdrs->x_op != XDR_ENCODE) {
+		return (NULL);
+	}
+	if (len < (intptr_t) xdrs->x_base) {
+		/* x_private was already allocated */
+		xdrs->x_handy += len;
+		return ((int32_t *) xdrs->x_private);
+	} else {
+		/* Free the earlier space and allocate new area */
+		if (xdrs->x_private)
+			free(xdrs->x_private);
+		if ((xdrs->x_private = (caddr_t) malloc(len)) == NULL) {
+			xdrs->x_base = 0;
+			return (NULL);
+		}
+		xdrs->x_base = (caddr_t)((intptr_t) len);
+		xdrs->x_handy += len;
+		return ((int32_t *) xdrs->x_private);
+	}
+}
+
+static int
+harmless(void)
+{
+	/* Always return FALSE/NULL, as the case may be */
+	return (0);
+}
+
+static void
+x_destroy(
+	XDR *xdrs)
+{
+	xdrs->x_handy = 0;
+	xdrs->x_base = 0;
+	if (xdrs->x_private) {
+		free(xdrs->x_private);
+		xdrs->x_private = NULL;
+	}
+	return;
+}
+
+unsigned long
+xdr_sizeof(
+	xdrproc_t func,
+	void *data)
+{
+	XDR x;
+	struct xdr_ops ops;
+	bool_t stat;
+	/* to stop ANSI-C compiler from complaining */
+	typedef  bool_t (* dummyfunc1)(XDR *, long *);
+	typedef  bool_t (* dummyfunc2)(XDR *, caddr_t, u_int);
+
+	ops.x_putlong = x_putlong;
+	ops.x_putbytes = x_putbytes;
+	ops.x_inline = x_inline;
+	ops.x_getpostn = x_getpostn;
+	ops.x_setpostn = x_setpostn;
+	ops.x_destroy = x_destroy;
+
+	/* the other harmless ones */
+	ops.x_getlong =  (dummyfunc1) harmless;
+	ops.x_getbytes = (dummyfunc2) harmless;
+
+	x.x_op = XDR_ENCODE;
+	x.x_ops = &ops;
+	x.x_handy = 0;
+	x.x_private = (caddr_t) NULL;
+	x.x_base = (caddr_t) 0;
+
+	stat = func(&x, data);
+	if (x.x_private)
+		free(x.x_private);
+	return (stat == TRUE ? (unsigned) x.x_handy: 0);
+}
diff --git a/services/librpc/src/xdr/xdr_stdio.c b/services/librpc/src/xdr/xdr_stdio.c
new file mode 100644
index 0000000..ca67941
--- /dev/null
+++ b/services/librpc/src/xdr/xdr_stdio.c
@@ -0,0 +1,194 @@
+/*
+ * Sun RPC is a product of Sun Microsystems, Inc. and is provided for
+ * unrestricted use provided that this legend is included on all tape
+ * media and as a part of the software program in whole or part.  Users
+ * may copy or modify Sun RPC without charge, but are not authorized
+ * to license or distribute it to anyone else except as part of a product or
+ * program developed by the user.
+ *
+ * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
+ * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
+ *
+ * Sun RPC is provided with no support and without any obligation on the
+ * part of Sun Microsystems, Inc. to assist in its use, correction,
+ * modification or enhancement.
+ *
+ * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
+ * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC
+ * OR ANY PART THEREOF.
+ *
+ * In no event will Sun Microsystems, Inc. be liable for any lost revenue
+ * or profits or other special, indirect and consequential damages, even if
+ * Sun has been advised of the possibility of such damages.
+ *
+ * Sun Microsystems, Inc.
+ * 2550 Garcia Avenue
+ * Mountain View, California  94043
+ */
+
+#if defined(LIBC_SCCS) && !defined(lint)
+/*static char *sccsid = "from: @(#)xdr_stdio.c 1.16 87/08/11 Copyr 1984 Sun Micro";*/
+/*static char *sccsid = "from: @(#)xdr_stdio.c	2.1 88/07/29 4.0 RPCSRC";*/
+static char *rcsid = "$FreeBSD: src/lib/libc/xdr/xdr_stdio.c,v 1.7 1999/08/28 00:02:56 peter Exp $";
+#endif
+
+/*
+ * xdr_stdio.c, XDR implementation on standard i/o file.
+ *
+ * Copyright (C) 1984, Sun Microsystems, Inc.
+ *
+ * This set of routines implements a XDR on a stdio stream.
+ * XDR_ENCODE serializes onto the stream, XDR_DECODE de-serializes
+ * from the stream.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <rpc/types.h>
+#include <stdio.h>
+#include <rpc/xdr.h>
+#include <netinet/in.h>
+
+static bool_t	xdrstdio_getlong(XDR *xdrs, long *lp);
+static bool_t	xdrstdio_putlong(XDR *xdrs, const long *lp);
+static bool_t	xdrstdio_getbytes(XDR *xdrs, caddr_t addr, u_int len);
+static bool_t	xdrstdio_putbytes(XDR *xdrs, const char *addr, u_int len);
+static u_int	xdrstdio_getpos(XDR *xdrs);
+static bool_t	xdrstdio_setpos(XDR *xdrs, u_int pos);
+static int32_t *xdrstdio_inline(XDR *xdrs, u_int len);
+static void	xdrstdio_destroy(XDR *);
+
+/*
+ * Ops vector for stdio type XDR
+ */
+static struct xdr_ops	xdrstdio_ops = {
+	xdrstdio_getlong,	/* deseraialize a long int */
+	xdrstdio_putlong,	/* seraialize a long int */
+	xdrstdio_getbytes,	/* deserialize counted bytes */
+	xdrstdio_putbytes,	/* serialize counted bytes */
+	xdrstdio_getpos,	/* get offset in the stream */
+	xdrstdio_setpos,	/* set offset in the stream */
+	xdrstdio_inline,	/* prime stream for inline macros */
+	xdrstdio_destroy	/* destroy stream */
+};
+
+/*
+ * Initialize a stdio xdr stream.
+ * Sets the xdr stream handle xdrs for use on the stream file.
+ * Operation flag is set to op.
+ */
+void
+xdrstdio_create(
+	XDR *xdrs,
+	FILE *file,
+	enum xdr_op op)
+{
+
+	xdrs->x_op = op;
+	xdrs->x_ops = &xdrstdio_ops;
+	xdrs->x_private = (caddr_t)file;
+	xdrs->x_handy = 0;
+	xdrs->x_base = 0;
+}
+
+/*
+ * Destroy a stdio xdr stream.
+ * Cleans up the xdr stream handle xdrs previously set up by xdrstdio_create.
+ */
+static void
+xdrstdio_destroy(
+	XDR *xdrs)
+{
+	(void)fflush((FILE *)xdrs->x_private);
+	/* xx should we close the file ?? */
+}
+
+static bool_t
+xdrstdio_getlong(
+	XDR *xdrs,
+	long *lp)
+{
+
+	if (fread((caddr_t)lp, sizeof(int32_t), 1,
+		(FILE *)xdrs->x_private) != 1)
+		return (FALSE);
+	*lp = (long)ntohl((int32_t)*lp);
+	return (TRUE);
+}
+
+static bool_t
+xdrstdio_putlong(
+	XDR *xdrs,
+	const long *lp)
+{
+
+	long mycopy = (long)htonl((int32_t)*lp);
+
+	if (fwrite((caddr_t)&mycopy, sizeof(int32_t), 1,
+		(FILE *)xdrs->x_private) != 1)
+		return (FALSE);
+	return (TRUE);
+}
+
+static bool_t
+xdrstdio_getbytes(
+	XDR *xdrs,
+	caddr_t addr,
+	u_int len )
+{
+
+	if ((len != 0) && (fread(addr, (int)len, 1, (FILE *)xdrs->x_private) != 1))
+		return (FALSE);
+	return (TRUE);
+}
+
+static bool_t
+xdrstdio_putbytes(
+	XDR *xdrs,
+	const char *addr,
+	u_int len)
+{
+
+	if ((len != 0) && (fwrite(addr, (int)len, 1, (FILE *)xdrs->x_private) != 1))
+		return (FALSE);
+	return (TRUE);
+}
+
+static u_int
+xdrstdio_getpos(
+	XDR *xdrs)
+{
+
+	return ((u_int) ftell((FILE *)xdrs->x_private));
+}
+
+static bool_t
+xdrstdio_setpos(
+	XDR *xdrs,
+	u_int pos)
+{
+
+	return ((fseek((FILE *)xdrs->x_private, (long)pos, 0) < 0) ?
+		FALSE : TRUE);
+}
+
+static int32_t *
+xdrstdio_inline(
+	XDR *xdrs,
+	u_int len)
+{
+
+	/*
+	 * Must do some work to implement this: must insure
+	 * enough data in the underlying stdio buffer,
+	 * that the buffer is aligned so that we can indirect through a
+	 * long *, and stuff this pointer in xdrs->x_buf.  Doing
+	 * a fread or fwrite to a scratch buffer would defeat
+	 * most of the gains to be had here and require storage
+	 * management on this buffer, so we don't do this.
+	 */
+	return (NULL);
+}




More information about the vc mailing list