1997-03-27 02:28  Ulrich Drepper  <drepper@cygnus.com>

	* gmon/gmon.c (monstartup): Mark all messages.
	(write_call_graph): Rewrite to use larger I/O vector for writev
	call to reduce syscall overhead.
	(write_bb_counts): Simplify writev handling.

	* inet/rexec.c: Make string parameters `const'.
	* resolv/netdb.h: Add prototypes for rcmd, rexec, ruserok, and
	rresvport.

	* math/Makefile: Don't define CFLAGS-* macros to prevent inlining
	in libm-test.
	* math/libm-test.c (this_does_nothing): Remove functions.  It's
	notuseful on any platform but ix86.
	(inverse_func_pair_test): Don't use this_does_nothing.  Use
	memory reference.
	(identities1_test): Likewise.
	(identities2_test): Likewise.
	(identities3_test): Likewise.
	(basic_test): Likewise.
	Patch by Andreas Schwab.
	(BUILD_COMPLEX): New macro.  Create complex number from real and
	imaginary parts.  This works around bugs/inefficiencies in current
	gcc.
	(cexp_test): Use BUILD_COMPLEX.  Add more tests.

	* nss/nsswitch.c: Fix typo.

	* posix/glob.h: Add declaration for glob_pattern_p.
	* posix/glob.c: Rename glob_pattern_p to __glob_pattern_p and
	make glob_pattern_p a weak alias.  This function is used in other
	packages (e.g. bash).

	* signal/Makefile (routines): Add sigisempty, sigandset, and
	sigorset.
	* signal/signal.h: Add prototypes for sigisempty, sigandset, and
	sigorset.
	* signal/sigisempty.c: New file.
	* signal/sigandset.c: New file.
	* signal/sigorset.c: New file.
	* sysdeps/generic/sigset.h: Define __sigisemptyset, __sigandset,
	and __sigorset.
	* sysdeps/unix/sysv/linux/sigset.h: Likewise.

	* stdlib/strtod.c: Handle `n-char-sequence' in NaN parsing.  It
	determines the bits in the mantissa part of the NaN.
	* stdlib/strtof.c: Define SET_MANTISSA for float type.
	* wcsmbs/wcstof.c: Define SET_MANTISSA for float type.
	* stdlib/strtold.c: Define SET_MANTISSA for long double type.
	* wcsmbs/wcstold.c: Define SET_MANTISSA for long double type.

	* sysdeps/libm-ieee754/s_cexp.c: Use explicit assignment to
	complex number components.  Some more corrects for special cases.
	* sysdeps/libm-ieee754/s_cexpf.c: Likewise.
	* sysdeps/libm-ieee754/s_cexpl.c: Likewise.

	* sysdeps/sparc/elf/start.S: Remove as per request of Miguel de Icaza.

	* sysdeps/unix/sysv/linux/netinet/icmp.h: Remove since we have
	ip_icmp.h.  Reported by HJ Lu.

1997-03-25 03:50  Andreas Schwab  <schwab@issan.informatik.uni-dortmund.de>

	* sysdeps/m68k/Makefile (CFLAGS-rtld.c): Add -Wno-unused.

	* sysdeps/m68k/dl-machine.h (elf_machine_rela): Rewritten as for
	i386.
	(elf_machine_lookup_noexec_p, elf_machine_lookup_noplt_p,
	ELF_MACHINE_RELOC_NOPLT): Define.

1997-03-25 03:48  Andreas Schwab  <schwab@issan.informatik.uni-dortmund.de>

	* grp/grp.h: Include <stddef.h> only once.

1997-03-25 09:38  Andreas Schwab  <schwab@issan.informatik.uni-dortmund.de>

	* sysdeps/unix/sysv/linux/termbits.h (OXTABS): Don't define.
	* sysdeps/unix/sysv/linux/alpha/termbits.h (OXTABS): Likewise.

	* termios/sys/ttydefaults.h (TTYDEF_OFLAG): Use either OXTABS or
	TAB3, if one of them is defined.

1997-03-26 04:53  Ulrich Drepper  <drepper@cygnus.com>

	* posix/glob.c (next_brace_sub): Decrement depth counter when '}'
	is found.
	Patch by Dennis Henriksen <opus@flamingo.osrl.dk>.

1997-03-25  16:25  Thorsten Kukuk  <kukuk@vt.uni-paderborn.de>

	* sunrpc/Makefile: Comment gccwarn out.
	* sunrpc/auth_none.c: Fix prototypes and parameters for compiling
	with enabled warnings.
	* sunrpc/auth_unix.c: Likewise.
	* sunrpc/authuxprot.c: Likewise.
	* sunrpc/bindrsvprt.c: Likewise.
	* sunrpc/clnt_gen.c: Likewise.
	* sunrpc/clnt_perr.c: Likewise.
	* sunrpc/clnt_raw.c: Likewise.
	* sunrpc/clnt_simp.c: Likewise.
	* sunrpc/clnt_tcp.c: Likewise.
	* sunrpc/clnt_udp.c: Likewise.
	* sunrpc/get_myaddr.c: Likewise.
	* sunrpc/getrpcport.c: Likewise.
	* sunrpc/pm_getmaps.c: Likewise.
	* sunrpc/pm_getport.c: Likewise.
	* sunrpc/pmap_clnt.c: Likewise.
	* sunrpc/pmap_prot.c: Likewise.
	* sunrpc/pmap_prot2.c: Likewise.
	* sunrpc/pmap_rmt.c: Likewise.
	* sunrpc/rpc/auth.h: Likewise.
	* sunrpc/rpc/clnt.h: Likewise.
	* sunrpc/rpc/pmap_clnt.h: Likewise.
	* sunrpc/rpc/svc.h: Likewise.
	* sunrpc/rpc/svc_auth.h: Likewise.
	* sunrpc/rpc/types.h: Likewise.
	* sunrpc/rpc/xdr.h: Likewise.
	* sunrpc/rpc_clntout.c: Likewise.
	* sunrpc/rpc_cmsg.c: Likewise.
	* sunrpc/rpc_dtable.c: Likewise.
	* sunrpc/rpc_prot.c: Likewise.
	* sunrpc/svc.c: Likewise.
	* sunrpc/svc_auth.c: Likewise.
	* sunrpc/svc_authux.c: Likewise.
	* sunrpc/svc_raw.c: Likewise.
	* sunrpc/svc_run.c: Likewise.
	* sunrpc/svc_simple.c: Likewise.
	* sunrpc/svc_tcp.c: Likewise.
	* sunrpc/svc_udp.c: Likewise.
	* sunrpc/xdr.c: Likewise.
	* sunrpc/xdr_array.c: Likewise.
	* sunrpc/xdr_mem.c: Likewise.
	* sunrpc/xdr_rec.c: Likewise.
	* sunrpc/xdr_ref.c: Likewise.
	* sunrpc/xdr_stdio.c: Likewise.

1997-03-25 13:39  Ulrich Drepper  <drepper@cygnus.com>

	* math/libm-test.c (log2_test): Compile this function and call it.
	(exp2_test): Likewise, but check whether function really exists
	before testing.

	* math/Makefile (libm-calls): Add s_log2 and s_exp2.

1997-03-25 04:50  Ulrich Drepper  <drepper@cygnus.com>

	Implement exp2 function.
	* sysdeps/libm-i387/s_exp2.S: New file.
	* sysdeps/libm-i387/s_exp2f.S: New file.
	* sysdeps/libm-i387/s_exp2l.S: New file.

	Implement log2 function.
	* sysdeps/libm-i387/s_log2.S: New file.
	* sysdeps/libm-i387/s_log2f.S: New file.
	* sysdeps/libm-i387/s_log2l.S: New file.
	* sysdeps/libm-ieee754/s_log2.c: New file.
	* sysdeps/libm-ieee754/s_log2f.c: New file.
	* sysdeps/stub/s_log2.c: New file.  Stub version.
This commit is contained in:
Ulrich Drepper 1997-03-27 01:59:53 +00:00
parent 34b402e5a9
commit e7fd8a39ab
90 changed files with 8600 additions and 7072 deletions

160
ChangeLog
View File

@ -1,3 +1,163 @@
1997-03-27 02:28 Ulrich Drepper <drepper@cygnus.com>
* gmon/gmon.c (monstartup): Mark all messages.
(write_call_graph): Rewrite to use larger I/O vector for writev
call to reduce syscall overhead.
(write_bb_counts): Simplify writev handling.
* inet/rexec.c: Make string parameters `const'.
* resolv/netdb.h: Add prototypes for rcmd, rexec, ruserok, and
rresvport.
* math/Makefile: Don't define CFLAGS-* macros to prevent inlining
in libm-test.
* math/libm-test.c (this_does_nothing): Remove functions. It's
notuseful on any platform but ix86.
(inverse_func_pair_test): Don't use this_does_nothing. Use
memory reference.
(identities1_test): Likewise.
(identities2_test): Likewise.
(identities3_test): Likewise.
(basic_test): Likewise.
Patch by Andreas Schwab.
(BUILD_COMPLEX): New macro. Create complex number from real and
imaginary parts. This works around bugs/inefficiencies in current
gcc.
(cexp_test): Use BUILD_COMPLEX. Add more tests.
* nss/nsswitch.c: Fix typo.
* posix/glob.h: Add declaration for glob_pattern_p.
* posix/glob.c: Rename glob_pattern_p to __glob_pattern_p and
make glob_pattern_p a weak alias. This function is used in other
packages (e.g. bash).
* signal/Makefile (routines): Add sigisempty, sigandset, and
sigorset.
* signal/signal.h: Add prototypes for sigisempty, sigandset, and
sigorset.
* signal/sigisempty.c: New file.
* signal/sigandset.c: New file.
* signal/sigorset.c: New file.
* sysdeps/generic/sigset.h: Define __sigisemptyset, __sigandset,
and __sigorset.
* sysdeps/unix/sysv/linux/sigset.h: Likewise.
* stdlib/strtod.c: Handle `n-char-sequence' in NaN parsing. It
determines the bits in the mantissa part of the NaN.
* stdlib/strtof.c: Define SET_MANTISSA for float type.
* wcsmbs/wcstof.c: Define SET_MANTISSA for float type.
* stdlib/strtold.c: Define SET_MANTISSA for long double type.
* wcsmbs/wcstold.c: Define SET_MANTISSA for long double type.
* sysdeps/libm-ieee754/s_cexp.c: Use explicit assignment to
complex number components. Some more corrects for special cases.
* sysdeps/libm-ieee754/s_cexpf.c: Likewise.
* sysdeps/libm-ieee754/s_cexpl.c: Likewise.
* sysdeps/sparc/elf/start.S: Remove as per request of Miguel de Icaza.
* sysdeps/unix/sysv/linux/netinet/icmp.h: Remove since we have
ip_icmp.h. Reported by HJ Lu.
1997-03-25 03:50 Andreas Schwab <schwab@issan.informatik.uni-dortmund.de>
* sysdeps/m68k/Makefile (CFLAGS-rtld.c): Add -Wno-unused.
* sysdeps/m68k/dl-machine.h (elf_machine_rela): Rewritten as for
i386.
(elf_machine_lookup_noexec_p, elf_machine_lookup_noplt_p,
ELF_MACHINE_RELOC_NOPLT): Define.
1997-03-25 03:48 Andreas Schwab <schwab@issan.informatik.uni-dortmund.de>
* grp/grp.h: Include <stddef.h> only once.
1997-03-25 09:38 Andreas Schwab <schwab@issan.informatik.uni-dortmund.de>
* sysdeps/unix/sysv/linux/termbits.h (OXTABS): Don't define.
* sysdeps/unix/sysv/linux/alpha/termbits.h (OXTABS): Likewise.
* termios/sys/ttydefaults.h (TTYDEF_OFLAG): Use either OXTABS or
TAB3, if one of them is defined.
1997-03-26 04:53 Ulrich Drepper <drepper@cygnus.com>
* posix/glob.c (next_brace_sub): Decrement depth counter when '}'
is found.
Patch by Dennis Henriksen <opus@flamingo.osrl.dk>.
1997-03-25 16:25 Thorsten Kukuk <kukuk@vt.uni-paderborn.de>
* sunrpc/Makefile: Comment gccwarn out.
* sunrpc/auth_none.c: Fix prototypes and parameters for compiling
with enabled warnings.
* sunrpc/auth_unix.c: Likewise.
* sunrpc/authuxprot.c: Likewise.
* sunrpc/bindrsvprt.c: Likewise.
* sunrpc/clnt_gen.c: Likewise.
* sunrpc/clnt_perr.c: Likewise.
* sunrpc/clnt_raw.c: Likewise.
* sunrpc/clnt_simp.c: Likewise.
* sunrpc/clnt_tcp.c: Likewise.
* sunrpc/clnt_udp.c: Likewise.
* sunrpc/get_myaddr.c: Likewise.
* sunrpc/getrpcport.c: Likewise.
* sunrpc/pm_getmaps.c: Likewise.
* sunrpc/pm_getport.c: Likewise.
* sunrpc/pmap_clnt.c: Likewise.
* sunrpc/pmap_prot.c: Likewise.
* sunrpc/pmap_prot2.c: Likewise.
* sunrpc/pmap_rmt.c: Likewise.
* sunrpc/rpc/auth.h: Likewise.
* sunrpc/rpc/clnt.h: Likewise.
* sunrpc/rpc/pmap_clnt.h: Likewise.
* sunrpc/rpc/svc.h: Likewise.
* sunrpc/rpc/svc_auth.h: Likewise.
* sunrpc/rpc/types.h: Likewise.
* sunrpc/rpc/xdr.h: Likewise.
* sunrpc/rpc_clntout.c: Likewise.
* sunrpc/rpc_cmsg.c: Likewise.
* sunrpc/rpc_dtable.c: Likewise.
* sunrpc/rpc_prot.c: Likewise.
* sunrpc/svc.c: Likewise.
* sunrpc/svc_auth.c: Likewise.
* sunrpc/svc_authux.c: Likewise.
* sunrpc/svc_raw.c: Likewise.
* sunrpc/svc_run.c: Likewise.
* sunrpc/svc_simple.c: Likewise.
* sunrpc/svc_tcp.c: Likewise.
* sunrpc/svc_udp.c: Likewise.
* sunrpc/xdr.c: Likewise.
* sunrpc/xdr_array.c: Likewise.
* sunrpc/xdr_mem.c: Likewise.
* sunrpc/xdr_rec.c: Likewise.
* sunrpc/xdr_ref.c: Likewise.
* sunrpc/xdr_stdio.c: Likewise.
1997-03-25 13:39 Ulrich Drepper <drepper@cygnus.com>
* math/libm-test.c (log2_test): Compile this function and call it.
(exp2_test): Likewise, but check whether function really exists
before testing.
* math/Makefile (libm-calls): Add s_log2 and s_exp2.
1997-03-25 04:50 Ulrich Drepper <drepper@cygnus.com>
Implement exp2 function.
* sysdeps/libm-i387/s_exp2.S: New file.
* sysdeps/libm-i387/s_exp2f.S: New file.
* sysdeps/libm-i387/s_exp2l.S: New file.
Implement log2 function.
* sysdeps/libm-i387/s_log2.S: New file.
* sysdeps/libm-i387/s_log2f.S: New file.
* sysdeps/libm-i387/s_log2l.S: New file.
* sysdeps/libm-ieee754/s_log2.c: New file.
* sysdeps/libm-ieee754/s_log2f.c: New file.
* sysdeps/stub/s_log2.c: New file. Stub version.
1997-03-24 19:58 Richard Henderson <rth@tamu.edu>
* stdlib/tst-strtol.c (tests): Correct 64-bit entry.

View File

@ -1,6 +1,6 @@
Open jobs for finishing GNU libc:
---------------------------------
Status: January 1997
Status: March 1997
If you have time and talent to take over any of the jobs below please
contact <bug-glibc@prep.ai.mit.edu>

View File

@ -125,7 +125,7 @@ monstartup (lowpc, highpc)
cp = malloc (p->kcountsize + p->fromssize + p->tossize);
if (! cp)
{
ERR("monstartup: out of memory\n");
ERR(_("monstartup: out of memory\n"));
return;
}
bzero(cp, p->kcountsize + p->fromssize + p->tossize);
@ -194,25 +194,25 @@ static void
write_call_graph (fd)
int fd;
{
#define NARCS_PER_WRITEV 32
u_char tag = GMON_TAG_CG_ARC;
struct gmon_cg_arc_record raw_arc[4]
struct gmon_cg_arc_record raw_arc[NARCS_PER_WRITEV]
__attribute__ ((aligned (__alignof__ (char*))));
int from_index, to_index, from_len;
u_long frompc;
struct iovec iov[2 * NARCS_PER_WRITEV];
int nfilled;
struct iovec iov[8] =
for (nfilled = 0; nfilled < NARCS_PER_WRITEV; ++nfilled)
{
{ &tag, sizeof (tag) },
{ &raw_arc[0], sizeof (struct gmon_cg_arc_record) },
{ &tag, sizeof (tag) },
{ &raw_arc[1], sizeof (struct gmon_cg_arc_record) },
{ &tag, sizeof (tag) },
{ &raw_arc[2], sizeof (struct gmon_cg_arc_record) },
{ &tag, sizeof (tag) },
{ &raw_arc[3], sizeof (struct gmon_cg_arc_record) },
};
int nfilled = 0;
iov[2 * nfilled].iov_base = &tag;
iov[2 * nfilled].iov_len = sizeof (tag);
iov[2 * nfilled + 1].iov_base = &raw_arc[nfilled];
iov[2 * nfilled + 1].iov_len = sizeof (struct gmon_cg_arc_record);
}
nfilled = 0;
from_len = _gmonparam.fromssize / sizeof (*_gmonparam.froms);
for (from_index = 0; from_index < from_len; ++from_index)
{
@ -226,19 +226,20 @@ write_call_graph (fd)
to_index != 0;
to_index = _gmonparam.tos[to_index].link)
{
if (nfilled > 3)
*(char **) raw_arc[nfilled].from_pc = (char *) frompc;
*(char **) raw_arc[nfilled].self_pc =
(char *)_gmonparam.tos[to_index].selfpc;
*(int *) raw_arc[nfilled].count = _gmonparam.tos[to_index].count;
if (++nfilled == NARCS_PER_WRITEV)
{
__writev (fd, iov, 2 * nfilled);
nfilled = 0;
}
*(char **) raw_arc[nfilled].from_pc = (char *)frompc;
*(char **) raw_arc[nfilled].self_pc =
(char *)_gmonparam.tos[to_index].selfpc;
*(int *) raw_arc[nfilled].count = _gmonparam.tos[to_index].count;
++nfilled;
}
}
__writev (fd, iov, 2 * nfilled);
if (nfilled > 0)
__writev (fd, iov, 2 * nfilled);
}
@ -268,17 +269,11 @@ write_bb_counts (fd)
/* Write each group of basic-block info (all basic-blocks in a
compilation unit form a single group). */
nfilled = 0;
for (grp = __bb_head; grp; grp = grp->next)
{
ncounts = grp->ncounts;
if (nfilled > 0)
{
__writev (fd, bbbody, nfilled);
nfilled = 0;
}
__writev (fd, bbhead, 2);
for (i = 0; i < ncounts; ++i)
for (nfilled = i = 0; i < ncounts; ++i)
{
if (nfilled > (sizeof (bbbody) / sizeof (bbbody[0])) - 2)
{
@ -289,9 +284,9 @@ write_bb_counts (fd)
bbbody[nfilled++].iov_base = (char *) &grp->addresses[i];
bbbody[nfilled++].iov_base = &grp->counts[i];
}
if (nfilled > 0)
__writev (fd, bbbody, nfilled);
}
if (nfilled > 0)
__writev (fd, bbbody, nfilled);
}

View File

@ -32,9 +32,6 @@ __BEGIN_DECLS
#define __need_size_t
#include <stddef.h>
#define __need_size_t
#include <stddef.h>
/* The group structure. */
struct group

View File

@ -53,7 +53,7 @@ int
rexec(ahost, rport, name, pass, cmd, fd2p)
char **ahost;
int rport;
char *name, *pass, *cmd;
const char *name, *pass, *cmd;
int *fd2p;
{
struct sockaddr_in sin, sin2, from;

View File

@ -48,7 +48,7 @@ libm-calls = e_acos e_acosh e_asin e_atan2 e_atanh e_cosh e_exp e_fmod \
w_gamma_r w_hypot w_j0 w_j1 w_jn w_lgamma w_lgamma_r \
w_log w_log10 w_pow w_remainder w_scalb w_sinh w_sqrt \
s_signbit s_fpclassify s_fmax s_fmin s_fdim s_nan s_trunc \
s_remquo \
s_remquo s_log2 s_exp2 \
conj cimag creal cabs s_cexp
libm-routines = $(libm-support) $(libm-calls) \
$(patsubst %_rf,%f_r,$(libm-calls:=f)) \
@ -73,9 +73,6 @@ tests = test-float test-double $(test-longdouble-$(long-double-fcts))
# XXX This test is disabled for now since the functions are too buggy.
#test-longdouble-yes = test-longdouble
CFLAGS-test-float.c = -fno-inline
CFLAGS-test-double.c = -fno-inline
CFLAGS-test-longdouble.c = -fno-inline
LDLIBS-test-float = libm
LDLIBS-test-double = libm
LDLIBS-test-longdouble = libm

View File

@ -63,10 +63,6 @@
-s,--silent outputs only the error count (equals --verbose=0)
*/
/* Define if the following ISO C 9X functions are implemented: exp2,
log2. */
#undef ISO_9X_IMPLEMENTED
#ifndef _GNU_SOURCE
# define _GNU_SOURCE
#endif
@ -103,6 +99,12 @@ static MATHTYPE plus_infty, minus_infty, nan_value;
typedef MATHTYPE (*mathfunc) (MATHTYPE);
#define BUILD_COMPLEX(real, imag) \
({ __complex__ MATHTYPE __retval; \
__real__ __retval = (real); \
__imag__ __retval = (imag); \
__retval; })
#define ISINF(x) \
(sizeof (x) == sizeof (float) ? \
@ -135,18 +137,6 @@ asm ("fnstsw":"=a" (sw));
}
/*
Call to an external function so that floating point registers
get moved to memory
*/
static void
this_does_nothing (void)
{
clock_t dummy;
dummy = clock ();
}
/*
Get a random value x with min_value < x < max_value
and min_value, max_value finite,
@ -644,10 +634,15 @@ exp_test (void)
}
#ifdef ISO_9X_IMPLEMENTED
static void
exp2_test (void)
{
errno = 0;
exp2(0);
if (errno == ENOSYS)
/* Function not implemented. */
return;
check ("exp2 (+0) == 1", FUNC(exp2) (0), 1);
check ("exp2 (-0) == 1", FUNC(exp2) (minus_zero), 1);
@ -655,7 +650,6 @@ exp2_test (void)
check ("exp2 (-inf) == 0", FUNC(exp2) (minus_infty), 0);
check ("exp2 (10) == 1024", FUNC(exp2) (10), 1024);
}
#endif
static void
@ -892,7 +886,6 @@ log1p_test (void)
}
#ifdef ISO_9X_IMPLEMENTED
static void
log2_test (void)
{
@ -914,7 +907,6 @@ log2_test (void)
check ("log2 (256) == 8", FUNC(log2) (256.0), 8);
}
#endif
static void
@ -1540,32 +1532,92 @@ cexp_test (void)
{
__complex__ MATHTYPE result;
result = FUNC(cexp) (plus_zero + 1.0i * plus_zero);
result = FUNC(cexp) (BUILD_COMPLEX (plus_zero, plus_zero));
check ("real(cexp(0 + 0i)) = 1", __real__ result, 1);
check ("imag(cexp(0 + 0i)) = 0", __imag__ result, 0);
result = FUNC(cexp) (minus_zero + 1.0i * plus_zero);
result = FUNC(cexp) (BUILD_COMPLEX (minus_zero, plus_zero));
check ("real(cexp(-0 + 0i)) = 1", __real__ result, 1);
check ("imag(cexp(-0 + 0i)) = 0", __imag__ result, 0);
result = FUNC(cexp) (plus_zero + 1.0i * minus_zero);
result = FUNC(cexp) (BUILD_COMPLEX (plus_zero, minus_zero));
check ("real(cexp(0 - 0i)) = 1", __real__ result, 1);
check ("imag(cexp(0 - 0i)) = 0", __imag__ result, 0);
result = FUNC(cexp) (minus_zero + 1.0i * minus_zero);
check ("imag(cexp(0 - 0i)) = -0", __imag__ result, minus_zero);
result = FUNC(cexp) (BUILD_COMPLEX (minus_zero, minus_zero));
check ("real(cexp(-0 - 0i)) = 1", __real__ result, 1);
check ("imag(cexp(-0 - 0i)) = 0", __imag__ result, 0);
check ("imag(cexp(-0 - 0i)) = -0", __imag__ result, minus_zero);
result = FUNC(cexp) (plus_infty + 1.0i * plus_zero);
result = FUNC(cexp) (BUILD_COMPLEX (plus_infty, plus_zero));
check_isinfp ("real(cexp(+inf + 0i)) = +inf", __real__ result);
check ("imag(cexp(+inf + 0i)) = 0", __imag__ result, 0);
result = FUNC(cexp) (plus_infty + 1.0i * minus_zero);
result = FUNC(cexp) (BUILD_COMPLEX (plus_infty, minus_zero));
check_isinfp ("real(cexp(+inf - 0i)) = +inf", __real__ result);
check ("imag(cexp(+inf - 0i)) = 0", __imag__ result, 0);
result = FUNC(cexp) (minus_infty + 1.0i * plus_zero);
result = FUNC(cexp) (BUILD_COMPLEX (minus_infty, plus_zero));
check ("real(cexp(-inf + 0i)) = 0", __real__ result, 0);
check ("imag(cexp(-inf + 0i)) = 0", __imag__ result, 0);
result = FUNC(cexp) (minus_infty + 1.0i * minus_zero);
result = FUNC(cexp) (BUILD_COMPLEX (minus_infty, minus_zero));
check ("real(cexp(-inf - 0i)) = 0", __real__ result, 0);
check ("imag(cexp(-inf - 0i)) = 0", __imag__ result, 0);
check ("imag(cexp(-inf - 0i)) = -0", __imag__ result, minus_zero);
result = FUNC(cexp) (BUILD_COMPLEX (100.0, plus_infty));
check_isnan ("real(cexp(x + i inf)) = NaN", __real__ result);
check_isnan ("imag(cexp(x + i inf)) = NaN", __imag__ result);
result = FUNC(cexp) (BUILD_COMPLEX (100.0, minus_infty));
check_isnan ("real(cexp(x - i inf)) = NaN", __real__ result);
check_isnan ("imag(cexp(x - i inf)) = NaN", __imag__ result);
result = FUNC(cexp) (BUILD_COMPLEX (minus_infty, 2.0));
check ("real(cexp(-inf + 2.0i)) = -0", __real__ result, minus_zero);
check ("imag(cexp(-inf + 2.0i)) = 0", __imag__ result, 0);
result = FUNC(cexp) (BUILD_COMPLEX (minus_infty, 4.0));
check ("real(cexp(-inf + 4.0i)) = -0", __real__ result, minus_zero);
check ("imag(cexp(-inf + 4.0i)) = -0", __imag__ result, minus_zero);
result = FUNC(cexp) (BUILD_COMPLEX (plus_infty, 2.0));
check_isinfn ("real(cexp(+inf + 2.0i)) = -0", __real__ result);
check_isinfp ("imag(cexp(+inf + 2.0i)) = 0", __imag__ result);
result = FUNC(cexp) (BUILD_COMPLEX (plus_infty, 4.0));
check_isinfn ("real(cexp(+inf + 4.0i)) = -0", __real__ result);
check_isinfn ("imag(cexp(+inf + 4.0i)) = -0", __imag__ result);
result = FUNC(cexp) (BUILD_COMPLEX (plus_infty, plus_infty));
check_isinfp ("real(cexp(+inf + i inf)) = +inf", __real__ result);
check_isnan ("imag(cexp(+inf + i inf)) = NaN", __imag__ result);
result = FUNC(cexp) (BUILD_COMPLEX (plus_infty, minus_infty));
check_isinfp ("real(cexp(+inf - i inf)) = +inf", __real__ result);
check_isnan ("imag(cexp(+inf - i inf)) = NaN", __imag__ result);
result = FUNC(cexp) (BUILD_COMPLEX (minus_infty, plus_infty));
check ("real(cexp(-inf + i inf)) = 0", __real__ result, 0);
check ("imag(cexp(-inf + i inf)) = 0", __imag__ result, 0);
result = FUNC(cexp) (BUILD_COMPLEX (minus_infty, minus_infty));
check ("real(cexp(-inf - i inf)) = 0", __real__ result, 0);
check ("imag(cexp(-inf - i inf)) = 0", __imag__ result, 0);
result = FUNC(cexp) (BUILD_COMPLEX (minus_infty, nan_value));
check ("real(cexp(-inf + i NaN)) = 0", __real__ result, 0);
check ("imag(cexp(-inf + i NaN)) = 0", fabs (__imag__ result), 0);
result = FUNC(cexp) (BUILD_COMPLEX (plus_infty, nan_value));
check_isinfp ("real(cexp(+inf + i NaN)) = +inf", __real__ result);
check_isnan ("imag(cexp(+inf + i NaN)) = NaN", __imag__ result);
result = FUNC(cexp) (BUILD_COMPLEX (nan_value, 1.0));
check_isnan ("real(cexp(NaN + 1i)) = NaN", __real__ result);
check_isnan ("imag(cexp(NaN + 1i)) = NaN", __imag__ result);
result = FUNC(cexp) (BUILD_COMPLEX (nan_value, 1.0));
check_isnan ("real(cexp(NaN + i inf)) = NaN", __real__ result);
check_isnan ("imag(cexp(NaN + i inf)) = NaN", __imag__ result);
result = FUNC(cexp) (BUILD_COMPLEX (nan_value, 1.0));
check_isnan ("real(cexp(NaN + i NaN)) = NaN", __real__ result);
check_isnan ("imag(cexp(NaN + i NaN)) = NaN", __imag__ result);
result = FUNC(cexp) (BUILD_COMPLEX (0, nan_value));
check_isnan ("real(cexp(0 + i NaN)) = NaN", __real__ result);
check_isnan ("imag(cexp(0 + i NaN)) = NaN", __imag__ result);
result = FUNC(cexp) (BUILD_COMPLEX (1, nan_value));
check_isnan ("real(cexp(1 + i NaN)) = NaN", __real__ result);
check_isnan ("imag(cexp(1 + i NaN)) = NaN", __imag__ result);
}
@ -1578,9 +1630,9 @@ inverse_func_pair_test (const char *test_name,
int result;
a = f1 (x);
this_does_nothing ();
(void) &a;
b = inverse (a);
this_does_nothing ();
(void) &b;
result = check_equal (b, x, epsilon, &difference);
output_result (test_name, result,
@ -1630,11 +1682,11 @@ identities1_test (MATHTYPE x, MATHTYPE epsilon)
int result;
res1 = FUNC(sin) (x);
this_does_nothing ();
(void) &res1;
res2 = FUNC(cos) (x);
this_does_nothing ();
(void) &res2;
res3 = res1 * res1 + res2 * res2;
this_does_nothing ();
(void) &res3;
result = check_equal (res3, 1.0, epsilon, &diff);
output_result_ext ("sin^2 + cos^2 == 1", result,
@ -1650,13 +1702,13 @@ identities2_test (MATHTYPE x, MATHTYPE epsilon)
int result;
res1 = FUNC(sin) (x);
this_does_nothing ();
(void) &res1;
res2 = FUNC(cos) (x);
this_does_nothing ();
(void) &res2;
res3 = FUNC(tan) (x);
this_does_nothing ();
(void) &res3;
res4 = res1 / res2;
this_does_nothing ();
(void) &res4;
result = check_equal (res4, res3, epsilon, &diff);
output_result_ext ("sin/cos == tan", result,
@ -1672,11 +1724,11 @@ identities3_test (MATHTYPE x, MATHTYPE epsilon)
int result;
res1 = FUNC(sinh) (x);
this_does_nothing ();
(void) &res1;
res2 = FUNC(cosh) (x);
this_does_nothing ();
(void) &res2;
res3 = res2 * res2 - res1 * res1;
this_does_nothing ();
(void) &res3;
result = check_equal (res3, 1.0, epsilon, &diff);
output_result_ext ("cosh^2 - sinh^2 == 1", result,
@ -1721,7 +1773,10 @@ basic_tests (void)
NaN_var = nan_value;
Inf_var = one_var / zero_var;
this_does_nothing ();
(void) &zero_var;
(void) &one_var;
(void) &NaN_var;
(void) &Inf_var;
check_isinfp ("isinf (inf) == +1", Inf_var);
check_isinfn ("isinf (-inf) == -1", -Inf_var);
@ -1854,9 +1909,7 @@ main (int argc, char *argv[])
cos_test ();
cosh_test ();
exp_test ();
#ifdef ISO_9X_IMPLEMENTED
exp2_test ();
#endif
expm1_test ();
frexp_test ();
ilogb_test ();
@ -1864,9 +1917,7 @@ main (int argc, char *argv[])
log_test ();
log10_test ();
log1p_test ();
#ifdef ISO_9X_IMPLEMENTED
log2_test ();
#endif
logb_test ();
modf_test ();
scalb_test ();

View File

@ -106,8 +106,8 @@ __nss_database_lookup (const char *database, const char *alternate_name,
*ni = entry->service;
if (*ni == NULL && alternate_name != NULL)
/* We haven't found a an entry so far. Try to find it with
the alternative name. */
/* We haven't found an entry so far. Try to find it with the
alternative name. */
for (entry = service_table->entry; entry != NULL; entry = entry->next)
if (strcmp (alternate_name, entry->name) == 0)
*ni = entry->service;

View File

@ -250,7 +250,6 @@ extern char *alloca ();
#undef GLOB_PERIOD
#include <glob.h>
static int glob_pattern_p __P ((const char *pattern, int quote));
static int glob_in_dir __P ((const char *pattern, const char *directory,
int flags,
int (*errfunc) __P ((const char *, int)),
@ -288,7 +287,7 @@ next_brace_sub (const char *begin)
while (*cp != '\0' && (*cp != '}' || depth > 0))
{
if (*cp == '}')
++depth;
--depth;
++cp;
}
if (*cp == '\0')
@ -617,7 +616,7 @@ glob (pattern, flags, errfunc, pglob)
}
#endif /* Not VMS. */
if (glob_pattern_p (dirname, !(flags & GLOB_NOESCAPE)))
if (__glob_pattern_p (dirname, !(flags & GLOB_NOESCAPE)))
{
/* The directory name contains metacharacters, so we
have to glob for the directory, and then glob for
@ -844,8 +843,8 @@ prefix_array (dirname, array, n)
/* Return nonzero if PATTERN contains any metacharacters.
Metacharacters can be quoted with backslashes if QUOTE is nonzero. */
static int
glob_pattern_p (pattern, quote)
int
__glob_pattern_p (pattern, quote)
const char *pattern;
int quote;
{
@ -876,6 +875,9 @@ glob_pattern_p (pattern, quote)
return 0;
}
#ifdef _LIBC
weak_alias (__glob_pattern_p, glob_pattern_p)
#endif
/* Like `glob', but PATTERN is a final pathname component,
@ -900,7 +902,7 @@ glob_in_dir (pattern, directory, flags, errfunc, pglob)
struct globlink *names = NULL;
size_t nfound = 0;
if (!glob_pattern_p (pattern, !(flags & GLOB_NOESCAPE)))
if (!__glob_pattern_p (pattern, !(flags & GLOB_NOESCAPE)))
{
stream = NULL;
flags |= GLOB_NOCHECK;
@ -958,7 +960,7 @@ glob_in_dir (pattern, directory, flags, errfunc, pglob)
}
if (nfound == 0 && (flags & GLOB_NOMAGIC) &&
! glob_pattern_p (pattern, !(flags & GLOB_NOESCAPE)))
! __glob_pattern_p (pattern, !(flags & GLOB_NOESCAPE)))
flags |= GLOB_NOCHECK;
if (nfound == 0 && (flags & GLOB_NOCHECK))

View File

@ -1,4 +1,4 @@
/* Copyright (C) 1991, 1992, 1995, 1996 Free Software Foundation, Inc.
/* Copyright (C) 1991, 1992, 1995, 1996, 1997 Free Software Foundation, Inc.
This file is part of the GNU C Library. Its master source is NOT part of
the C library, however. The master source lives in /gd/gnu/lib.
@ -104,6 +104,16 @@ extern int glob __P ((const char *__pattern, int __flags,
extern void globfree __P ((glob_t *__pglob));
#ifdef _GNU_SOURCE
/* Return nonzero if PATTERN contains any metacharacters.
Metacharacters can be quoted with backslashes if QUOTE is nonzero.
This function is not part of the interface specified by POSIX.2
but several programs want to use it. */
extern int __glob_pattern_p __P ((__const char *__pattern, int __quote));
extern int glob_pattern_p __P ((__const char *__pattern, int __quote));
#endif
#ifdef __cplusplus
}
#endif

View File

@ -364,6 +364,39 @@ extern int getnetgrent_r __P ((char **__hostp, char **__userp,
#endif /* misc */
#ifdef __USE_BSD
/* Call `rshd' at port RPORT on remote machine *AHOST to execute CMD.
The local user is LOCUSER, on the remote machine the command is
executed as REMUSER. In *FD2P the descriptor to the socket for the
connection is returned. The caller must have the right to use a
reserved port. When the function returns *AHOST contains the
official host name. */
extern int rcmd __P ((char **__ahost, unsigned short int __rport,
__const char *__locuser, __const char *__remuser,
__const char *__cmd, int *__fd2p));
/* Call `rexecd' at port RPORT on remote machine *AHOST to execute
CMD. The process runs at the remote machine using the ID of user
NAME whose cleartext password is PASSWD. In *FD2P the descriptor
to the socket for the connection is returned. When the function
returns *AHOST contains the official host name. */
extern int rexec __P ((char **__ahost, int __rport, __const char *__name,
__const char *__pass, __const char *__cmd,
int *__fd2p));
/* Check whether user REMUSER on system RHOST is allowed to login as LOCUSER.
If SUSER is not zero the user tries to become superuser. Return 0 if
it is possible. */
extern int ruserok __P ((__const char *__rhost, int __suser,
__const char *__remuser, __const char *__locuser));
/* Try to allocate reserved port, returning a descriptor for a socket opened
at this port or -1 if unsuccessful. The search for an available port
will start at ALPORT and continues with lower numbers. */
extern int rresvport __P ((int *__alport));
#endif
/* Extension from POSIX.1g. */
#ifdef __USE_POSIX
/* Structure to contain information about address of a service provider. */

View File

@ -30,7 +30,8 @@ routines := signal raise killpg \
sigstack sigaltstack sigintr \
sigsetops sigempty sigfillset sigaddset sigdelset sigismem \
sigreturn \
siggetmask sysv_signal
siggetmask sysv_signal \
sigisempty sigandset sigorset
tests := tst-signal

36
signal/sigandset.c Normal file
View File

@ -0,0 +1,36 @@
/* Copyright (C) 1991, 1996, 1997 Free Software Foundation, Inc.
This file is part of the GNU C Library.
The GNU C Library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
The GNU C Library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with the GNU C Library; see the file COPYING.LIB. If not,
write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
Boston, MA 02111-1307, USA. */
#include <errno.h>
#include <signal.h>
/* Combine sets LEFT and RIGHT by logical AND and place result in DEST. */
int
sigandset (dest, left, right)
sigset_t *dest;
const sigset_t *left;
const sigset_t *right;
{
if (dest == NULL || left == NULL || right == NULL)
{
__set_errno (EINVAL);
return -1;
}
return __sigandset (dest, left, right);
}

View File

@ -1,4 +1,4 @@
/* Copyright (C) 1991, 92, 93, 95, 96, 97 Free Software Foundation, Inc.
/* Copyright (C) 1991, 1996, 1997 Free Software Foundation, Inc.
This file is part of the GNU C Library.
The GNU C Library is free software; you can redistribute it and/or
@ -16,10 +16,19 @@
write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
Boston, MA 02111-1307, USA. */
#ifndef _NETINET_ICMP_H
#define _NETINET_ICMP_H 1
#include <errno.h>
#include <signal.h>
#include <asm/types.h>
#include <linux/icmp.h>
/* Test whether SET is empty. */
int
sigisemptyset (set)
const sigset_t *set;
{
if (set == NULL)
{
__set_errno (EINVAL);
return -1;
}
#endif /* netinet/icmp.h */
return __sigisemptyset (set);
}

View File

@ -183,6 +183,19 @@ extern int sigdelset __P ((sigset_t *__set, int __signo));
/* Return 1 if SIGNO is in SET, 0 if not. */
extern int sigismember __P ((__const sigset_t *__set, int __signo));
#ifdef __USE_GNU
/* Return non-empty value is SET is not empty. */
extern int sigisemptyset __P ((__const sigset_t *__set));
/* Build new signal set by combining the two inputs set using logical AND. */
extern int sigandset __P ((sigset_t *__set, __const sigset_t *__left,
__const sigset_t *__right));
/* Build new signal set by combining the two inputs set using logical OR. */
extern int sigorset __P ((sigset_t *__set, __const sigset_t *__left,
__const sigset_t *__right));
#endif /* GNU */
/* Get the system-specific definitions of `struct sigaction'
and the `SA_*' and `SIG_*'. constants. */
#include <sigaction.h>

36
signal/sigorset.c Normal file
View File

@ -0,0 +1,36 @@
/* Copyright (C) 1991, 1996, 1997 Free Software Foundation, Inc.
This file is part of the GNU C Library.
The GNU C Library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
The GNU C Library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with the GNU C Library; see the file COPYING.LIB. If not,
write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
Boston, MA 02111-1307, USA. */
#include <errno.h>
#include <signal.h>
/* Combine sets LEFT and RIGHT by logical OR and place result in DEST. */
int
sigorset (dest, left, right)
sigset_t *dest;
const sigset_t *left;
const sigset_t *right;
{
if (dest == NULL || left == NULL || right == NULL)
{
__set_errno (EINVAL);
return -1;
}
return __sigorset (dest, left, right);
}

View File

@ -31,6 +31,12 @@
# endif
# define MPN2FLOAT __mpn_construct_double
# define FLOAT_HUGE_VAL HUGE_VAL
# define SET_MANTISSA(flt, mant) \
do { union ieee754_double u; \
u.d = (flt); \
u.ieee.mantissa0 = ((mant) >> 32) & 0xfffff; \
u.ieee.mantissa1 = (mant) & 0xffffffff; \
} while (0)
#endif
#ifdef USE_WIDE_CHAR
@ -44,6 +50,7 @@
# define ISXDIGIT(Ch) iswxdigit (Ch)
# define TOLOWER(Ch) towlower (Ch)
# define STRNCASECMP(S1, S2, N) __wcsncasecmp ((S1), (S2), (N))
# define STRTOULL(S, E, B) wcstoull ((S), (E), (B))
#else
# define STRING_TYPE char
# define CHAR_TYPE char
@ -53,6 +60,7 @@
# define ISXDIGIT(Ch) isxdigit (Ch)
# define TOLOWER(Ch) tolower (Ch)
# define STRNCASECMP(S1, S2, N) __strncasecmp ((S1), (S2), (N))
# define STRTOULL(S, E, B) strtoull ((S), (E), (B))
#endif
/* End of configuration part. */
@ -461,6 +469,8 @@ INTERNAL (STRTOF) (nptr, endptr, group)
if (TOLOWER (c) == L_('n') && STRNCASECMP (cp, L_("an"), 2) == 0)
{
FLOAT retval = NAN;
/* Return NaN. */
if (endptr != NULL)
{
@ -480,12 +490,25 @@ INTERNAL (STRTOF) (nptr, endptr, group)
/* The closing brace is missing. Only match the NAN
part. */
cp = startp;
else
{
/* This is a system-dependent way to specify the
bitmask used for the NaN. We expect it to be
a number which is put in the mantissa of the
number. */
STRING_TYPE *endp;
unsigned long long int mant;
mant = STRTOULL (startp, &endp, 0);
if (endp == cp)
SET_MANTISSA (retval, mant);
}
}
*endptr = (STRING_TYPE *) cp;
}
return NAN;
return retval;
}
/* It is really a text we do not recognize. */

View File

@ -6,5 +6,11 @@
#define STRTOF strtof
#define MPN2FLOAT __mpn_construct_float
#define FLOAT_HUGE_VAL HUGE_VALF
#define SET_MANTISSA(flt, mant) \
do { union ieee754_float u; \
u.f = (flt); \
u.ieee.mantissa = (mant) & 0x7fffff; \
(flt) = u.f; \
} while (0)
#include "strtod.c"

View File

@ -6,5 +6,12 @@
#define STRTOF strtold
#define MPN2FLOAT __mpn_construct_long_double
#define FLOAT_HUGE_VAL HUGE_VALL
#define SET_MANTISSA(flt, mant) \
do { union ieee854_long_double u; \
u.d = (flt); \
u.ieee.mantissa0 = ((mant) >> 32) & 0x7fffffff; \
u.ieee.mantissa1 = (mant) & 0xffffffff; \
(flt) = u.d; \
} while (0)
#include "strtod.c"

View File

@ -80,9 +80,6 @@ extra-objs = $(rpcgen-objs)
all: # Make this the default target; it will be defined in Rules.
# Sun's code is not too clean.
override +gccwarn := -w
include ../Makeconfig
ifeq (no,$(cross-compiling))
@ -96,6 +93,19 @@ librpcsvc-inhibit-o = .so # Build no shared rpcsvc library.
omit-deps = $(librpcsvc-routines)
endif
CFLAGS-xbootparam.c = -Wno-unused
CFLAGS-xnlm_prot.c = -Wno-unused
CFLAGS-xrstat.c = -Wno-unused
CFLAGS-xyppasswd.c = -Wno-unused
CFLAGS-xklm_prot.c = -Wno-unused
CFLAGS-xrex.c = -Wno-unused
CFLAGS-xsm_inter.c = -Wno-unused
CFLAGS-xmount.c = -Wno-unused
CFLAGS-xrusers.c = -Wno-unused
CFLAGS-xspray.c = -Wno-unused
CFLAGS-xnfs_prot.c = -Wno-unused
CFLAGS-xrquote.c = -Wno-unused
include ../Rules
$(objpfx)rpcgen: $(addprefix $(objpfx),$(rpcgen-objs)) $(common-objpfx)libc.a

View File

@ -6,23 +6,23 @@
* 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
@ -33,101 +33,104 @@ static char sccsid[] = "@(#)auth_none.c 1.19 87/08/11 Copyr 1984 Sun Micro";
/*
* auth_none.c
* Creates a client authentication handle for passing "null"
* credentials and verifiers to remote systems.
*
* Copyright (C) 1984, Sun Microsystems, Inc.
* Creates a client authentication handle for passing "null"
* credentials and verifiers to remote systems.
*
* Copyright (C) 1984, Sun Microsystems, Inc.
*/
#include <rpc/types.h>
#include <rpc/xdr.h>
#include <rpc/auth.h>
#define MAX_MARSHEL_SIZE 20
extern bool_t xdr_opaque_auth (XDR *, struct opaque_auth *);
/*
* Authenticator operations routines
*/
static void authnone_verf();
static void authnone_destroy();
static bool_t authnone_marshal();
static bool_t authnone_validate();
static bool_t authnone_refresh();
static void authnone_verf (AUTH *);
static void authnone_destroy (AUTH *);
static bool_t authnone_marshal (AUTH *, XDR *);
static bool_t authnone_validate (AUTH *, struct opaque_auth *);
static bool_t authnone_refresh (AUTH *);
static struct auth_ops ops = {
authnone_verf,
authnone_marshal,
authnone_validate,
authnone_refresh,
authnone_destroy
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_MARSHEL_SIZE];
u_int mcnt;
} *authnone_private;
static struct authnone_private
{
AUTH no_client;
char marshalled_client[MAX_MARSHEL_SIZE];
u_int mcnt;
}
*authnone_private;
AUTH *
authnone_create()
authnone_create (void)
{
register struct authnone_private *ap = authnone_private;
XDR xdr_stream;
register XDR *xdrs;
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_MARSHEL_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);
if (ap == 0)
{
ap = (struct authnone_private *) calloc (1, sizeof (*ap));
if (ap == 0)
return NULL;
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_MARSHEL_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*/
/*ARGSUSED */
static bool_t
authnone_marshal(client, xdrs)
AUTH *client;
XDR *xdrs;
authnone_marshal (AUTH *client, XDR *xdrs)
{
register struct authnone_private *ap = authnone_private;
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()
{
}
static bool_t
authnone_validate()
{
return (TRUE);
}
static bool_t
authnone_refresh()
{
return (FALSE);
if (ap == 0)
return (0);
return ((*xdrs->x_ops->x_putbytes) (xdrs,
ap->marshalled_client, ap->mcnt));
}
static void
authnone_destroy()
authnone_verf (AUTH *auth)
{
}
static bool_t
authnone_validate (AUTH *auth, struct opaque_auth *oa)
{
return TRUE;
}
static bool_t
authnone_refresh (AUTH *auth)
{
return FALSE;
}
static void
authnone_destroy (AUTH *auth)
{
}

View File

@ -45,6 +45,7 @@ static char sccsid[] = "@(#)auth_unix.c 1.19 87/08/11 Copyr 1984 Sun Micro";
#include <limits.h>
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <sys/param.h>
@ -53,36 +54,40 @@ static char sccsid[] = "@(#)auth_unix.c 1.19 87/08/11 Copyr 1984 Sun Micro";
#include <rpc/auth.h>
#include <rpc/auth_unix.h>
extern bool_t xdr_opaque_auth (XDR *, struct opaque_auth *);
/*
* Unix authenticator operations vector
*/
static void authunix_nextverf();
static bool_t authunix_marshal();
static bool_t authunix_validate();
static bool_t authunix_refresh();
static void authunix_destroy();
static void authunix_nextverf (AUTH *);
static bool_t authunix_marshal (AUTH *, XDR *);
static bool_t authunix_validate (AUTH *, struct opaque_auth *);
static bool_t 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
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 */
};
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 bool_t marshal_new_auth();
static bool_t marshal_new_auth (AUTH *);
/*
@ -90,77 +95,72 @@ static bool_t marshal_new_auth();
* Returns an auth handle with the given stuff in it.
*/
AUTH *
authunix_create(machname, uid, gid, len, aup_gids)
char *machname;
uid_t uid;
gid_t gid;
register int len;
gid_t *aup_gids;
authunix_create (machname, uid, gid, len, aup_gids)
char *machname;
uid_t uid;
gid_t gid;
int len;
gid_t *aup_gids;
{
struct authunix_parms aup;
char mymem[MAX_AUTH_BYTES];
struct timeval now;
XDR xdrs;
register AUTH *auth;
register struct audata *au;
struct authunix_parms aup;
char mymem[MAX_AUTH_BYTES];
struct timeval now;
XDR xdrs;
AUTH *auth;
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;
/*
* Allocate and set up auth handle
*/
auth = (AUTH *) mem_alloc (sizeof (*auth));
if (auth == NULL)
{
(void) fprintf (stderr, _("authunix_create: out of memory\n"));
return NULL;
}
au = (struct audata *) mem_alloc (sizeof (*au));
if (au == NULL)
{
(void) fprintf (stderr, _("authunix_create: out of memory\n"));
return NULL;
}
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;
aup.aup_len = (u_int)len;
aup.aup_gids = aup_gids;
/*
* 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;
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
bcopy(mymem, au->au_origcred.oa_base, (u_int)len);
/*
* 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;
if ((au->au_origcred.oa_base = mem_alloc ((u_int) len)) == NULL)
{
(void) fprintf (stderr, _("authunix_create: out of memory\n"));
return NULL;
}
bcopy (mymem, au->au_origcred.oa_base, (u_int) len);
/*
* set auth handle to reflect new cred.
*/
auth->ah_cred = au->au_origcred;
marshal_new_auth(auth);
return (auth);
/*
* set auth handle to reflect new cred.
*/
auth->ah_cred = au->au_origcred;
marshal_new_auth (auth);
return auth;
}
/*
@ -168,27 +168,27 @@ authunix_create(machname, uid, gid, len, aup_gids)
* syscalls.
*/
AUTH *
authunix_create_default()
authunix_create_default (void)
{
register int len;
char machname[MAX_MACHINE_NAME + 1];
register uid_t uid;
register gid_t gid;
int max_nr_groups = sysconf (_SC_NGROUPS_MAX);
gid_t gids[max_nr_groups];
int len;
char machname[MAX_MACHINE_NAME + 1];
uid_t uid;
gid_t gid;
int max_nr_groups = sysconf (_SC_NGROUPS_MAX);
gid_t gids[max_nr_groups];
if (gethostname(machname, MAX_MACHINE_NAME) == -1)
abort();
machname[MAX_MACHINE_NAME] = 0;
uid = geteuid();
gid = getegid();
if (gethostname (machname, MAX_MACHINE_NAME) == -1)
abort ();
machname[MAX_MACHINE_NAME] = 0;
uid = geteuid ();
gid = getegid ();
if ((len = getgroups(max_nr_groups, gids)) < 0)
abort();
/* This braindamaged Sun code forces us here to truncate the
list of groups to NGRPS members since the code in
authuxprot.c transforms a fixed array. Grrr. */
return (authunix_create(machname, uid, gid, MIN (NGRPS, len), gids));
if ((len = getgroups (max_nr_groups, gids)) < 0)
abort ();
/* This braindamaged Sun code forces us here to truncate the
list of groups to NGRPS members since the code in
authuxprot.c transforms a fixed array. Grrr. */
return authunix_create (machname, uid, gid, MIN (NGRPS, len), gids);
}
/*
@ -196,113 +196,112 @@ authunix_create_default()
*/
static void
authunix_nextverf(auth)
AUTH *auth;
authunix_nextverf (AUTH *auth)
{
/* no action necessary */
/* no action necessary */
}
static bool_t
authunix_marshal(auth, xdrs)
AUTH *auth;
XDR *xdrs;
authunix_marshal (AUTH *auth, XDR *xdrs)
{
register struct audata *au = AUTH_PRIVATE(auth);
struct audata *au = AUTH_PRIVATE (auth);
return (XDR_PUTBYTES(xdrs, au->au_marshed, au->au_mpos));
return XDR_PUTBYTES (xdrs, au->au_marshed, au->au_mpos);
}
static bool_t
authunix_validate(auth, verf)
register AUTH *auth;
struct opaque_auth *verf;
authunix_validate (AUTH *auth, struct opaque_auth *verf)
{
register struct audata *au;
XDR xdrs;
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 (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);
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;
}
return (TRUE);
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 bool_t
authunix_refresh(auth)
register AUTH *auth;
authunix_refresh (AUTH *auth)
{
register struct audata *au = AUTH_PRIVATE(auth);
struct authunix_parms aup;
struct timeval now;
XDR xdrs;
register int stat;
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 ++;
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 = (gid_t *)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;
/* first deserialize the creds back into a struct authunix_parms */
aup.aup_machname = NULL;
aup.aup_gids = (gid_t *) 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);
/* 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);
/* 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)
register AUTH *auth;
authunix_destroy (AUTH *auth)
{
register struct audata *au = AUTH_PRIVATE(auth);
struct audata *au = AUTH_PRIVATE (auth);
mem_free(au->au_origcred.oa_base, au->au_origcred.oa_length);
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);
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));
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);
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));
mem_free ((caddr_t) auth, sizeof (*auth));
}
/*
@ -310,19 +309,23 @@ authunix_destroy(auth)
* sets private data, au_marshed and au_mpos
*/
static bool_t
marshal_new_auth(auth)
register AUTH *auth;
marshal_new_auth (AUTH *auth)
{
XDR xdr_stream;
register XDR *xdrs = &xdr_stream;
register struct audata *au = AUTH_PRIVATE(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);
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);
return TRUE;
}

View File

@ -48,24 +48,22 @@ static char sccsid[] = "@(#)authunix_prot.c 1.15 87/08/11 Copyr 1984 Sun Micro";
* XDR for unix authentication parameters.
*/
bool_t
xdr_authunix_parms(xdrs, p)
register XDR *xdrs;
register struct authunix_parms *p;
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)
&& (sizeof (uid_t) == sizeof (short int)
? xdr_u_short(xdrs, (u_short *) &(p->aup_uid))
: xdr_u_int(xdrs, (u_int *) &(p->aup_uid)))
&& (sizeof (gid_t) == sizeof (short int)
? xdr_u_short(xdrs, (u_short *) &(p->aup_gid))
: xdr_u_int(xdrs, (u_int *) &(p->aup_gid)))
&& xdr_array(xdrs, (caddr_t *)&(p->aup_gids),
&(p->aup_len), NGRPS, sizeof(gid_t),
(sizeof (gid_t) == sizeof (short int)
? xdr_u_short : xdr_u_int)) ) {
return (TRUE);
}
return (FALSE);
if (xdr_u_long (xdrs, &(p->aup_time))
&& xdr_string (xdrs, &(p->aup_machname), MAX_MACHINE_NAME)
&& (sizeof (uid_t) == sizeof (short int)
? xdr_u_short (xdrs, (u_short *) & (p->aup_uid))
: xdr_u_int (xdrs, (u_int *) & (p->aup_uid)))
&& (sizeof (gid_t) == sizeof (short int)
? xdr_u_short (xdrs, (u_short *) & (p->aup_gid))
: xdr_u_int (xdrs, (u_int *) & (p->aup_gid)))
&& xdr_array (xdrs, (caddr_t *) & (p->aup_gids),
& (p->aup_len), NGRPS, sizeof (gid_t),
(sizeof (gid_t) == sizeof (short int)
? (xdrproc_t) xdr_u_short : (xdrproc_t) xdr_u_int)))
{
return TRUE;
}
return FALSE;
}

View File

@ -1,4 +1,3 @@
static char sccsid[] = "@(#)bindresvport.c 2.2 88/07/29 4.0 RPCSRC 1.8 88/02/08 SMI";
/*
* Sun RPC is a product of Sun Microsystems, Inc. and is provided for
* unrestricted use provided that this legend is included on all tape
@ -27,11 +26,15 @@ static char sccsid[] = "@(#)bindresvport.c 2.2 88/07/29 4.0 RPCSRC 1.8 88/02/08
* 2550 Garcia Avenue
* Mountain View, California 94043
*/
#if !defined(lint) && defined(SCCSIDS)
static char sccsid[] = "@(#)bindresvport.c 2.2 88/07/29 4.0 RPCSRC 1.8 88/02/08 SMI";
#endif
/*
* Copyright (c) 1987 by Sun Microsystems, Inc.
*/
#include <unistd.h>
#include <string.h>
#include <sys/types.h>
#include <sys/errno.h>
#include <sys/socket.h>
@ -40,41 +43,46 @@ static char sccsid[] = "@(#)bindresvport.c 2.2 88/07/29 4.0 RPCSRC 1.8 88/02/08
/*
* Bind a socket to a privileged IP port
*/
bindresvport(sd, sin)
int sd;
struct sockaddr_in *sin;
int
bindresvport (int sd, struct sockaddr_in *sin)
{
int res;
static short port;
struct sockaddr_in myaddr;
int res;
static short port;
struct sockaddr_in myaddr;
#ifndef errno
extern int errno;
extern int errno;
#endif
int i;
int i;
#define STARTPORT 600
#define ENDPORT (IPPORT_RESERVED - 1)
#define NPORTS (ENDPORT - STARTPORT + 1)
if (sin == (struct sockaddr_in *)0) {
sin = &myaddr;
bzero(sin, sizeof (*sin));
sin->sin_family = AF_INET;
} else if (sin->sin_family != AF_INET) {
__set_errno (EPFNOSUPPORT);
return (-1);
if (sin == (struct sockaddr_in *) 0)
{
sin = &myaddr;
bzero (sin, sizeof (*sin));
sin->sin_family = AF_INET;
}
else if (sin->sin_family != AF_INET)
{
__set_errno (EPFNOSUPPORT);
return -1;
}
if (port == 0)
{
port = (getpid () % NPORTS) + STARTPORT;
}
res = -1;
__set_errno (EADDRINUSE);
for (i = 0; i < NPORTS && res < 0 && errno == EADDRINUSE; i++)
{
sin->sin_port = htons (port++);
if (port > ENDPORT)
{
port = STARTPORT;
}
if (port == 0) {
port = (getpid() % NPORTS) + STARTPORT;
}
res = -1;
__set_errno (EADDRINUSE);
for (i = 0; i < NPORTS && res < 0 && errno == EADDRINUSE; i++) {
sin->sin_port = htons(port++);
if (port > ENDPORT) {
port = STARTPORT;
}
res = bind(sd, sin, sizeof(struct sockaddr_in));
}
return (res);
res = bind (sd, sin, sizeof (struct sockaddr_in));
}
return res;
}

View File

@ -35,6 +35,7 @@ static char sccsid[] = "@(#)clnt_generic.c 1.4 87/08/11 (C) 1987 SMI";
*/
#include <alloca.h>
#include <errno.h>
#include <string.h>
#include <rpc/rpc.h>
#include <sys/socket.h>
#include <sys/errno.h>
@ -46,95 +47,96 @@ static char sccsid[] = "@(#)clnt_generic.c 1.4 87/08/11 (C) 1987 SMI";
* change using the rpc equivalent of ioctl()'s.
*/
CLIENT *
clnt_create(hostname, prog, vers, proto)
char *hostname;
unsigned prog;
unsigned vers;
char *proto;
clnt_create (const char *hostname, u_long prog, u_long vers,
const char *proto)
{
struct hostent hostbuf, *h;
size_t hstbuflen;
char *hsttmpbuf;
struct protoent protobuf, *p;
size_t prtbuflen;
char *prttmpbuf;
struct sockaddr_in sin;
int sock;
struct timeval tv;
CLIENT *client;
int herr;
struct hostent hostbuf, *h;
size_t hstbuflen;
char *hsttmpbuf;
struct protoent protobuf, *p;
size_t prtbuflen;
char *prttmpbuf;
struct sockaddr_in sin;
int sock;
struct timeval tv;
CLIENT *client;
int herr;
hstbuflen = 1024;
hstbuflen = 1024;
hsttmpbuf = __alloca (hstbuflen);
while (__gethostbyname_r (hostname, &hostbuf, hsttmpbuf, hstbuflen,
&h, &herr) < 0)
if (herr != NETDB_INTERNAL || errno != ERANGE)
{
rpc_createerr.cf_stat = RPC_UNKNOWNHOST;
return NULL;
}
else
{
/* Enlarge the buffer. */
hstbuflen *= 2;
hsttmpbuf = __alloca (hstbuflen);
while (__gethostbyname_r (hostname, &hostbuf, hsttmpbuf, hstbuflen,
&h, &herr) < 0)
if (herr != NETDB_INTERNAL || errno != ERANGE)
{
rpc_createerr.cf_stat = RPC_UNKNOWNHOST;
return NULL;
}
else
{
/* Enlarge the buffer. */
hstbuflen *= 2;
hsttmpbuf = __alloca (hstbuflen);
}
}
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);
}
sin.sin_family = h->h_addrtype;
sin.sin_port = 0;
bzero(sin.sin_zero, sizeof(sin.sin_zero));
bcopy(h->h_addr, (char*)&sin.sin_addr, h->h_length);
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;
}
sin.sin_family = h->h_addrtype;
sin.sin_port = 0;
bzero (sin.sin_zero, sizeof (sin.sin_zero));
bcopy (h->h_addr, (char *) &sin.sin_addr, h->h_length);
prtbuflen = 1024;
prtbuflen = 1024;
prttmpbuf = __alloca (prtbuflen);
while (__getprotobyname_r (proto, &protobuf, prttmpbuf, prtbuflen, &p)
< 0)
if (errno != ERANGE)
{
rpc_createerr.cf_stat = RPC_UNKNOWNPROTO;
rpc_createerr.cf_error.re_errno = EPFNOSUPPORT;
return NULL;
}
else
{
/* Enlarge the buffer. */
prtbuflen *= 2;
prttmpbuf = __alloca (prtbuflen);
while (__getprotobyname_r (proto, &protobuf, prttmpbuf, prtbuflen, &p)
< 0)
if (errno != ERANGE)
{
rpc_createerr.cf_stat = RPC_UNKNOWNPROTO;
rpc_createerr.cf_error.re_errno = EPFNOSUPPORT;
return NULL;
}
else
{
/* Enlarge the buffer. */
prtbuflen *= 2;
prttmpbuf = __alloca (prtbuflen);
}
}
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);
}
tv.tv_sec = 25;
clnt_control(client, CLSET_TIMEOUT, &tv);
break;
case IPPROTO_TCP:
client = clnttcp_create(&sin, prog, vers, &sock, 0, 0);
if (client == NULL) {
return (NULL);
}
tv.tv_sec = 25;
tv.tv_usec = 0;
clnt_control(client, CLSET_TIMEOUT, &tv);
break;
default:
rpc_createerr.cf_stat = RPC_SYSTEMERROR;
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;
}
return (client);
tv.tv_sec = 25;
clnt_control (client, CLSET_TIMEOUT, (char *)&tv);
break;
case IPPROTO_TCP:
client = clnttcp_create (&sin, prog, vers, &sock, 0, 0);
if (client == NULL)
{
return NULL;
}
tv.tv_sec = 25;
tv.tv_usec = 0;
clnt_control (client, CLSET_TIMEOUT, (char *)&tv);
break;
default:
rpc_createerr.cf_stat = RPC_SYSTEMERROR;
rpc_createerr.cf_error.re_errno = EPFNOSUPPORT;
return (NULL);
}
return client;
}

View File

@ -38,165 +38,156 @@ static char sccsid[] = "@(#)clnt_perror.c 1.15 87/10/07 Copyr 1984 Sun Micro";
*
*/
#include <stdio.h>
#include <string.h>
#include <rpc/types.h>
#include <rpc/auth.h>
#include <rpc/clnt.h>
/* extern char *sys_errlist[]; --drepper@gnu */
/* extern char *sprintf(); --roland@gnu */
static char *auth_errmsg();
extern char *strcpy();
static char *auth_errmsg (enum auth_stat stat);
static char *buf;
static char *
_buf()
_buf (void)
{
if (buf == 0)
buf = (char *)malloc(256);
return (buf);
if (buf == NULL)
buf = (char *) malloc (256);
return buf;
}
/*
* Print reply error info
*/
char *
clnt_sperror(rpch, s)
CLIENT *rpch;
char *s;
clnt_sperror (CLIENT * rpch, const char *msg)
{
struct rpc_err e;
void clnt_perrno();
char *err;
char *str = _buf();
char *strstart = str;
char buf[1024];
struct rpc_err e;
char *err;
char *str = _buf ();
char *strstart = str;
int len;
if (str == 0)
return (0);
CLNT_GETERR(rpch, &e);
if (str == NULL)
return NULL;
CLNT_GETERR (rpch, &e);
(void) sprintf(str, "%s: ", s);
str += strlen(str);
len = sprintf (str, "%s: ", msg);
str += len;
(void) strcpy(str, clnt_sperrno(e.re_status));
str += strlen(str);
str = stpcpy (str, clnt_sperrno (e.re_status));
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;
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) sprintf(str, "; errno = %s",
sys_errlist[e.re_errno]);
str += strlen(str);
break;
case RPC_CANTSEND:
case RPC_CANTRECV:
len = sprintf (str, "; errno = %s", strerror_r (e.re_errno,
buf, sizeof buf));
str += len;
break;
case RPC_VERSMISMATCH:
(void) sprintf(str,
_("; low version = %lu, high version = %lu"),
e.re_vers.low, e.re_vers.high);
str += strlen(str);
break;
case RPC_VERSMISMATCH:
len= sprintf (str, _("; low version = %lu, high version = %lu"),
e.re_vers.low, e.re_vers.high);
str += len;
break;
case RPC_AUTHERROR:
err = auth_errmsg(e.re_why);
(void) sprintf(str,_("; why = "));
str += strlen(str);
if (err != NULL) {
(void) sprintf(str, "%s",err);
} else {
(void) sprintf(str,
_("(unknown authentication error - %d)"),
(int) e.re_why);
}
str += strlen(str);
break;
case RPC_PROGVERSMISMATCH:
(void) sprintf(str,
_("; low version = %lu, high version = %lu"),
e.re_vers.low, e.re_vers.high);
str += strlen(str);
break;
default: /* unknown */
(void) sprintf(str,
"; s1 = %lu, s2 = %lu",
e.re_lb.s1, e.re_lb.s2);
str += strlen(str);
break;
case RPC_AUTHERROR:
err = auth_errmsg (e.re_why);
str = stpcpy (str, _ ("; why = "));
if (err != NULL)
{
str = stpcpy (str, err);
}
(void) sprintf(str, "\n");
return(strstart) ;
else
{
len = sprintf (str, _("(unknown authentication error - %d)"),
(int) e.re_why);
str += len;
}
break;
case RPC_PROGVERSMISMATCH:
len = sprintf (str, _("; low version = %lu, high version = %lu"),
e.re_vers.low, e.re_vers.high);
str += len;
break;
default: /* unknown */
len = sprintf (str, "; s1 = %lu, s2 = %lu", e.re_lb.s1, e.re_lb.s2);
str += len;
break;
}
*str = '\n';
return (strstart);
}
void
clnt_perror(rpch, s)
CLIENT *rpch;
char *s;
clnt_perror (CLIENT * rpch, const char *msg)
{
(void) fprintf(stderr,"%s",clnt_sperror(rpch,s));
(void) fputs (clnt_sperror (rpch, msg), stderr);
}
struct rpc_errtab {
enum clnt_stat status;
char *message;
struct rpc_errtab
{
enum clnt_stat status;
const char *message;
};
static struct rpc_errtab rpc_errlist[] = {
{ RPC_SUCCESS,
N_("RPC: Success") },
{ RPC_CANTENCODEARGS,
N_("RPC: Can't encode arguments") },
{ RPC_CANTDECODERES,
N_("RPC: Can't decode result") },
{ RPC_CANTSEND,
N_("RPC: Unable to send") },
{ RPC_CANTRECV,
N_("RPC: Unable to receive") },
{ RPC_TIMEDOUT,
N_("RPC: Timed out") },
{ RPC_VERSMISMATCH,
N_("RPC: Incompatible versions of RPC") },
{ RPC_AUTHERROR,
N_("RPC: Authentication error") },
{ RPC_PROGUNAVAIL,
N_("RPC: Program unavailable") },
{ RPC_PROGVERSMISMATCH,
N_("RPC: Program/version mismatch") },
{ RPC_PROCUNAVAIL,
N_("RPC: Procedure unavailable") },
{ RPC_CANTDECODEARGS,
N_("RPC: Server can't decode arguments") },
{ RPC_SYSTEMERROR,
N_("RPC: Remote system error") },
{ RPC_UNKNOWNHOST,
N_("RPC: Unknown host") },
{ RPC_UNKNOWNPROTO,
N_("RPC: Unknown protocol") },
{ RPC_PMAPFAILURE,
N_("RPC: Port mapper failure") },
{ RPC_PROGNOTREGISTERED,
N_("RPC: Program not registered") },
{ RPC_FAILED,
N_("RPC: Failed (unspecified error)") }
static const struct rpc_errtab rpc_errlist[] =
{
{RPC_SUCCESS,
N_("RPC: Success")},
{RPC_CANTENCODEARGS,
N_("RPC: Can't encode arguments")},
{RPC_CANTDECODERES,
N_("RPC: Can't decode result")},
{RPC_CANTSEND,
N_("RPC: Unable to send")},
{RPC_CANTRECV,
N_("RPC: Unable to receive")},
{RPC_TIMEDOUT,
N_("RPC: Timed out")},
{RPC_VERSMISMATCH,
N_("RPC: Incompatible versions of RPC")},
{RPC_AUTHERROR,
N_("RPC: Authentication error")},
{RPC_PROGUNAVAIL,
N_("RPC: Program unavailable")},
{RPC_PROGVERSMISMATCH,
N_("RPC: Program/version mismatch")},
{RPC_PROCUNAVAIL,
N_("RPC: Procedure unavailable")},
{RPC_CANTDECODEARGS,
N_("RPC: Server can't decode arguments")},
{RPC_SYSTEMERROR,
N_("RPC: Remote system error")},
{RPC_UNKNOWNHOST,
N_("RPC: Unknown host")},
{RPC_UNKNOWNPROTO,
N_("RPC: Unknown protocol")},
{RPC_PMAPFAILURE,
N_("RPC: Port mapper failure")},
{RPC_PROGNOTREGISTERED,
N_("RPC: Program not registered")},
{RPC_FAILED,
N_("RPC: Failed (unspecified error)")}
};
@ -204,102 +195,109 @@ static struct rpc_errtab rpc_errlist[] = {
* This interface for use by clntrpc
*/
char *
clnt_sperrno(stat)
enum clnt_stat stat;
clnt_sperrno (enum clnt_stat stat)
{
int i;
int i;
for (i = 0; i < sizeof(rpc_errlist)/sizeof(struct rpc_errtab); i++) {
if (rpc_errlist[i].status == stat) {
return _(rpc_errlist[i].message);
}
for (i = 0; i < sizeof (rpc_errlist) / sizeof (struct rpc_errtab); i++)
{
if (rpc_errlist[i].status == stat)
{
return _(rpc_errlist[i].message);
}
return _("RPC: (unknown error code)");
}
return _("RPC: (unknown error code)");
}
void
clnt_perrno(num)
enum clnt_stat num;
clnt_perrno (enum clnt_stat num)
{
(void) fprintf(stderr,"%s",clnt_sperrno(num));
(void) fputs (clnt_sperrno (num), stderr);
}
char *
clnt_spcreateerror(s)
char *s;
clnt_spcreateerror (const char *msg)
{
extern int sys_nerr;
/* extern char *sys_errlist[]; --drepper@gnu */
char *str = _buf();
char buf[1024];
char *str = _buf ();
char *cp;
int len;
if (str == 0)
return(0);
(void) sprintf(str, "%s: ", s);
(void) strcat(str, clnt_sperrno(rpc_createerr.cf_stat));
switch (rpc_createerr.cf_stat) {
case RPC_PMAPFAILURE:
(void) strcat(str, " - ");
(void) strcat(str,
clnt_sperrno(rpc_createerr.cf_error.re_status));
break;
if (str == NULL)
return NULL;
len = sprintf (str, "%s: ", msg);
cp = str + len;
cp = stpcpy (cp, clnt_sperrno (rpc_createerr.cf_stat));
switch (rpc_createerr.cf_stat)
{
case RPC_PMAPFAILURE:
cp = stpcpy (cp, " - ");
cp = stpcpy (cp, clnt_sperrno (rpc_createerr.cf_error.re_status));
break;
case RPC_SYSTEMERROR:
(void) strcat(str, " - ");
if (rpc_createerr.cf_error.re_errno > 0
&& rpc_createerr.cf_error.re_errno < sys_nerr)
(void) strcat(str,
sys_errlist[rpc_createerr.cf_error.re_errno]);
else
(void) sprintf(&str[strlen(str)], _("Error %d"),
rpc_createerr.cf_error.re_errno);
break;
case RPC_SYSTEMERROR:
cp = stpcpy (str, " - ");
if (rpc_createerr.cf_error.re_errno > 0
&& rpc_createerr.cf_error.re_errno < sys_nerr)
cp = stpcpy (str, strerror_r (rpc_createerr.cf_error.re_errno,
buf, sizeof buf));
else
{
len = sprintf (cp, _("Error %d"), rpc_createerr.cf_error.re_errno);
cp += len;
}
(void) strcat(str, "\n");
return (str);
break;
default:
break;
}
*cp = '\n';
return str;
}
void
clnt_pcreateerror(s)
char *s;
clnt_pcreateerror (const char *msg)
{
(void) fprintf(stderr,"%s",clnt_spcreateerror(s));
(void) fputs (clnt_spcreateerror (msg), stderr);
}
struct auth_errtab {
enum auth_stat status;
char *message;
struct auth_errtab
{
enum auth_stat status;
const char *message;
};
static struct auth_errtab auth_errlist[] = {
{ AUTH_OK,
N_("Authentication OK") },
{ AUTH_BADCRED,
N_("Invalid client credential") },
{ AUTH_REJECTEDCRED,
N_("Server rejected credential") },
{ AUTH_BADVERF,
N_("Invalid client verifier") },
{ AUTH_REJECTEDVERF,
N_("Server rejected verifier") },
{ AUTH_TOOWEAK,
N_("Client credential too weak") },
{ AUTH_INVALIDRESP,
N_("Invalid server verifier") },
{ AUTH_FAILED,
N_("Failed (unspecified error)") },
static const struct auth_errtab auth_errlist[] =
{
{AUTH_OK,
N_("Authentication OK")},
{AUTH_BADCRED,
N_("Invalid client credential")},
{AUTH_REJECTEDCRED,
N_("Server rejected credential")},
{AUTH_BADVERF,
N_("Invalid client verifier")},
{AUTH_REJECTEDVERF,
N_("Server rejected verifier")},
{AUTH_TOOWEAK,
N_("Client credential too weak")},
{AUTH_INVALIDRESP,
N_("Invalid server verifier")},
{AUTH_FAILED,
N_("Failed (unspecified error)")},
};
static char *
auth_errmsg(stat)
enum auth_stat stat;
auth_errmsg (enum auth_stat stat)
{
int i;
size_t i;
for (i = 0; i < sizeof(auth_errlist)/sizeof(struct auth_errtab); i++) {
if (auth_errlist[i].status == stat) {
return _(auth_errlist[i].message);
}
for (i = 0; i < sizeof (auth_errlist) / sizeof (struct auth_errtab); i++)
{
if (auth_errlist[i].status == stat)
{
return _(auth_errlist[i].message);
}
return(NULL);
}
return NULL;
}

View File

@ -43,196 +43,209 @@ static char sccsid[] = "@(#)clnt_raw.c 1.22 87/08/11 Copyr 1984 Sun Micro";
*/
#include <rpc/rpc.h>
#include <rpc/svc.h>
#include <rpc/xdr.h>
extern bool_t xdr_opaque_auth (XDR *, struct opaque_auth *);
#define MCALL_MSG_SIZE 24
/*
* This is the "network" we will be moving stuff over.
*/
static struct clntraw_private {
CLIENT client_object;
XDR xdr_stream;
char _raw_buf[UDPMSGSIZE];
char mashl_callmsg[MCALL_MSG_SIZE];
u_int mcnt;
} *clntraw_private;
static struct clntraw_private
{
CLIENT client_object;
XDR xdr_stream;
char _raw_buf[UDPMSGSIZE];
char mashl_callmsg[MCALL_MSG_SIZE];
u_int mcnt;
}
*clntraw_private;
static enum clnt_stat clntraw_call();
static void clntraw_abort();
static void clntraw_geterr();
static bool_t clntraw_freeres();
static bool_t clntraw_control();
static void clntraw_destroy();
static enum clnt_stat clntraw_call (CLIENT *, u_long, xdrproc_t, caddr_t,
xdrproc_t, caddr_t, struct timeval);
static void clntraw_abort (void);
static void clntraw_geterr (CLIENT *, struct rpc_err *);
static bool_t clntraw_freeres (CLIENT *, xdrproc_t, caddr_t);
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
static struct clnt_ops client_ops =
{
clntraw_call,
clntraw_abort,
clntraw_geterr,
clntraw_freeres,
clntraw_destroy,
clntraw_control
};
void svc_getreq();
/*
* Create a client handle for memory based rpc.
*/
CLIENT *
clntraw_create(prog, vers)
u_long prog;
u_long vers;
clntraw_create (u_long prog, u_long vers)
{
register struct clntraw_private *clp = clntraw_private;
struct rpc_msg call_msg;
XDR *xdrs = &clp->xdr_stream;
CLIENT *client = &clp->client_object;
struct clntraw_private *clp = clntraw_private;
struct rpc_msg call_msg;
XDR *xdrs = &clp->xdr_stream;
CLIENT *client = &clp->client_object;
if (clp == 0) {
clp = (struct clntraw_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->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);
if (clp == 0)
{
clp = (struct clntraw_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->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);
/*
* 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);
/*
* create client handle
*/
client->cl_ops = &client_ops;
client->cl_auth = authnone_create ();
return client;
}
static enum clnt_stat
clntraw_call(h, proc, xargs, argsp, xresults, resultsp, timeout)
CLIENT *h;
u_long proc;
xdrproc_t xargs;
caddr_t argsp;
xdrproc_t xresults;
caddr_t resultsp;
struct timeval timeout;
clntraw_call (h, proc, xargs, argsp, xresults, resultsp, timeout)
CLIENT *h;
u_long proc;
xdrproc_t xargs;
caddr_t argsp;
xdrproc_t xresults;
caddr_t resultsp;
struct timeval timeout;
{
register struct clntraw_private *clp = clntraw_private;
register XDR *xdrs = &clp->xdr_stream;
struct rpc_msg msg;
enum clnt_stat status;
struct rpc_err error;
struct clntraw_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);
if (clp == NULL)
return RPC_FAILED;
call_again:
/*
* send request
*/
xdrs->x_op = XDR_ENCODE;
XDR_SETPOS(xdrs, 0);
((struct rpc_msg *)clp->mashl_callmsg)->rm_xid ++ ;
if ((! XDR_PUTBYTES(xdrs, clp->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 */
/*
* send request
*/
xdrs->x_op = XDR_ENCODE;
XDR_SETPOS (xdrs, 0);
((struct rpc_msg *) clp->mashl_callmsg)->rm_xid++;
if ((!XDR_PUTBYTES (xdrs, clp->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);
/*
* 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;
/*
* 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()
{
}
static bool_t
clntraw_freeres(cl, xdr_res, res_ptr)
CLIENT *cl;
xdrproc_t xdr_res;
caddr_t res_ptr;
{
register struct clntraw_private *clp = clntraw_private;
register XDR *xdrs = &clp->xdr_stream;
bool_t rval;
if (clp == 0)
if (status == RPC_SUCCESS)
{
if (!AUTH_VALIDATE (h->cl_auth, &msg.acpted_rply.ar_verf))
{
rval = (bool_t) RPC_FAILED;
return (rval);
status = RPC_AUTHERROR;
}
xdrs->x_op = XDR_FREE;
return ((*xdr_res)(xdrs, res_ptr));
} /* 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_abort()
clntraw_geterr (CLIENT *cl, struct rpc_err *err)
{
}
static bool_t
clntraw_freeres (cl, xdr_res, res_ptr)
CLIENT *cl;
xdrproc_t xdr_res;
caddr_t res_ptr;
{
struct clntraw_private *clp = clntraw_private;
XDR *xdrs = &clp->xdr_stream;
bool_t rval;
if (clp == NULL)
{
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()
clntraw_control (CLIENT *cl, int i, char *c)
{
return (FALSE);
return FALSE;
}
static void
clntraw_destroy()
clntraw_destroy (CLIENT *cl)
{
}

View File

@ -41,94 +41,102 @@ static char sccsid[] = "@(#)clnt_simple.c 1.35 87/08/11 Copyr 1984 Sun Micro";
#include <alloca.h>
#include <errno.h>
#include <stdio.h>
#include <unistd.h>
#include <rpc/rpc.h>
#include <sys/socket.h>
#include <netdb.h>
#include <strings.h>
static struct callrpc_private {
CLIENT *client;
int socket;
int oldprognum, oldversnum, valid;
char *oldhost;
} *callrpc_private;
static struct callrpc_private
{
CLIENT *client;
int socket;
u_long oldprognum, oldversnum, valid;
char *oldhost;
}
*callrpc_private;
callrpc(host, prognum, versnum, procnum, inproc, in, outproc, out)
char *host;
xdrproc_t inproc, outproc;
char *in, *out;
int
callrpc (const char *host, u_long prognum, u_long versnum, u_long procnum,
xdrproc_t inproc, const char *in, xdrproc_t outproc, char *out)
{
register struct callrpc_private *crp = callrpc_private;
struct sockaddr_in server_addr;
enum clnt_stat clnt_stat;
struct hostent hostbuf, *hp;
struct timeval timeout, tottimeout;
struct callrpc_private *crp = callrpc_private;
struct sockaddr_in server_addr;
enum clnt_stat clnt_stat;
struct hostent hostbuf, *hp;
struct timeval timeout, tottimeout;
if (crp == 0) {
crp = (struct callrpc_private *)calloc(1, sizeof (*crp));
if (crp == 0)
return (0);
callrpc_private = crp;
if (crp == 0)
{
crp = (struct callrpc_private *) calloc (1, sizeof (*crp));
if (crp == 0)
return 0;
callrpc_private = crp;
}
if (crp->oldhost == NULL)
{
crp->oldhost = malloc (256);
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
{
size_t buflen;
char *buffer;
int herr;
crp->valid = 0;
if (crp->socket != RPC_ANYSOCK)
{
(void) close (crp->socket);
crp->socket = RPC_ANYSOCK;
}
if (crp->oldhost == NULL) {
crp->oldhost = malloc(256);
crp->oldhost[0] = 0;
crp->socket = RPC_ANYSOCK;
if (crp->client)
{
clnt_destroy (crp->client);
crp->client = NULL;
}
if (crp->valid && crp->oldprognum == prognum && crp->oldversnum == versnum
&& strcmp(crp->oldhost, host) == 0) {
/* reuse old client */
} else {
size_t buflen;
char *buffer;
int herr;
crp->valid = 0;
if (crp->socket != RPC_ANYSOCK)
{
(void)close(crp->socket);
crp->socket = RPC_ANYSOCK;
}
if (crp->client) {
clnt_destroy(crp->client);
crp->client = NULL;
}
buflen = 1024;
buffer = __alloca (buflen);
while (__gethostbyname_r (host, &hostbuf, buffer, buflen,
&hp, &herr) < 0)
if (herr != NETDB_INTERNAL || errno != ERANGE)
return (int) RPC_UNKNOWNHOST;
else
{
/* Enlarge the buffer. */
buflen *= 2;
buffer = __alloca (buflen);
}
buflen = 1024;
buffer = __alloca (buflen);
while (__gethostbyname_r (host, &hostbuf, buffer, buflen,
&hp, &herr) < 0)
if (herr != NETDB_INTERNAL || errno != ERANGE)
return (int) RPC_UNKNOWNHOST;
else
{
/* Enlarge the buffer. */
buflen *= 2;
buffer = __alloca (buflen);
}
timeout.tv_usec = 0;
timeout.tv_sec = 5;
bcopy(hp->h_addr, (char *)&server_addr.sin_addr, hp->h_length);
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) strncpy(crp->oldhost, host, 255);
crp->oldhost[256] = '\0';
}
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);
timeout.tv_usec = 0;
timeout.tv_sec = 5;
bcopy (hp->h_addr, (char *) &server_addr.sin_addr, hp->h_length);
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) strncpy (crp->oldhost, host, 255);
crp->oldhost[256] = '\0';
}
tottimeout.tv_sec = 25;
tottimeout.tv_usec = 0;
clnt_stat = clnt_call (crp->client, procnum, inproc, (char *) in,
outproc, out, tottimeout);
/*
* if call failed, empty cache
*/
if (clnt_stat != RPC_SUCCESS)
crp->valid = 0;
return (int) clnt_stat;
}

View File

@ -50,48 +50,50 @@ static char sccsid[] = "@(#)clnt_tcp.c 1.37 87/10/05 Copyr 1984 Sun Micro";
* Now go hang yourself.
*/
#include <stdio.h>
#include <rpc/rpc.h>
#include <sys/socket.h>
#include <netdb.h>
#include <errno.h>
#include <stdio.h>
#include <unistd.h>
#include <rpc/rpc.h>
#include <sys/socket.h>
#include <rpc/pmap_clnt.h>
extern bool_t xdr_opaque_auth (XDR *, struct opaque_auth *);
#define MCALL_MSG_SIZE 24
#ifndef errno
extern int errno;
#endif
struct ct_data
{
int ct_sock;
bool_t ct_closeit;
struct timeval ct_wait;
bool_t ct_waitset; /* wait set by clnt_control? */
struct sockaddr_in ct_addr;
struct rpc_err ct_error;
char ct_mcall[MCALL_MSG_SIZE]; /* marshalled callmsg */
u_int ct_mpos; /* pos after marshal */
XDR ct_xdrs;
};
static int readtcp();
static int writetcp();
static int readtcp (char *, char *, int);
static int writetcp (char *, char *, int);
static enum clnt_stat clnttcp_call();
static void clnttcp_abort();
static void clnttcp_geterr();
static bool_t clnttcp_freeres();
static bool_t clnttcp_control();
static void clnttcp_destroy();
static enum clnt_stat clnttcp_call (CLIENT *, u_long, xdrproc_t, caddr_t,
xdrproc_t, caddr_t, struct timeval);
static void clnttcp_abort (void);
static void clnttcp_geterr (CLIENT *, struct rpc_err *);
static bool_t clnttcp_freeres (CLIENT *, xdrproc_t, caddr_t);
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;
struct timeval ct_wait;
bool_t ct_waitset; /* wait set by clnt_control? */
struct sockaddr_in ct_addr;
struct rpc_err ct_error;
char ct_mcall[MCALL_MSG_SIZE]; /* marshalled callmsg */
u_int ct_mpos; /* pos after marshal */
XDR ct_xdrs;
static struct clnt_ops tcp_ops =
{
clnttcp_call,
clnttcp_abort,
clnttcp_geterr,
clnttcp_freeres,
clnttcp_destroy,
clnttcp_control
};
/*
@ -109,284 +111,301 @@ struct ct_data {
* something more useful.
*/
CLIENT *
clnttcp_create(raddr, prog, vers, sockp, sendsz, recvsz)
struct sockaddr_in *raddr;
u_long prog;
u_long vers;
register int *sockp;
u_int sendsz;
u_int recvsz;
clnttcp_create (struct sockaddr_in *raddr, u_long prog, u_long vers,
int *sockp, u_int sendsz, u_int recvsz)
{
CLIENT *h;
register struct ct_data *ct;
struct timeval now;
struct rpc_msg call_msg;
CLIENT *h;
struct ct_data *ct = (struct ct_data *) mem_alloc (sizeof (*ct));
struct timeval now;
struct rpc_msg call_msg;
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;
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);
}
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;
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 >= 0)
(void) close (*sockp);
goto fooy;
}
ct->ct_closeit = TRUE;
}
else
{
ct->ct_closeit = FALSE;
}
/*
* 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);
/*
* 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 = 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_mcall, MCALL_MSG_SIZE,
XDR_ENCODE);
if (!xdr_callhdr (&(ct->ct_xdrs), &call_msg))
{
if (ct->ct_closeit)
{
(void) close (*sockp);
}
goto fooy;
}
ct->ct_mpos = XDR_GETPOS (&(ct->ct_xdrs));
XDR_DESTROY (&(ct->ct_xdrs));
/*
* 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 >= 0)
(void)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 = 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_mcall, MCALL_MSG_SIZE,
XDR_ENCODE);
if (! xdr_callhdr(&(ct->ct_xdrs), &call_msg)) {
if (ct->ct_closeit) {
(void)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);
/*
* 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
*/
mem_free((caddr_t)ct, sizeof(struct ct_data));
mem_free((caddr_t)h, sizeof(CLIENT));
return ((CLIENT *)NULL);
/*
* Something goofed, free stuff and barf
*/
mem_free ((caddr_t) ct, sizeof (struct ct_data));
mem_free ((caddr_t) h, sizeof (CLIENT));
return ((CLIENT *) NULL);
}
static enum clnt_stat
clnttcp_call(h, proc, xdr_args, args_ptr, xdr_results, results_ptr, timeout)
register CLIENT *h;
u_long proc;
xdrproc_t xdr_args;
caddr_t args_ptr;
xdrproc_t xdr_results;
caddr_t results_ptr;
struct timeval timeout;
clnttcp_call (h, proc, xdr_args, args_ptr, xdr_results, results_ptr, timeout)
CLIENT *h;
u_long proc;
xdrproc_t xdr_args;
caddr_t args_ptr;
xdrproc_t xdr_results;
caddr_t results_ptr;
struct timeval timeout;
{
register struct ct_data *ct = (struct ct_data *) h->cl_private;
register XDR *xdrs = &(ct->ct_xdrs);
struct rpc_msg reply_msg;
u_long x_id;
u_int32_t *msg_x_id = (u_int32_t *)(ct->ct_mcall); /* yuk */
register bool_t shipnow;
int refreshes = 2;
struct ct_data *ct = (struct ct_data *) h->cl_private;
XDR *xdrs = &(ct->ct_xdrs);
struct rpc_msg reply_msg;
u_long x_id;
u_int32_t *msg_x_id = (u_int32_t *) (ct->ct_mcall); /* yuk */
bool_t shipnow;
int refreshes = 2;
if (!ct->ct_waitset) {
ct->ct_wait = timeout;
}
if (!ct->ct_waitset)
{
ct->ct_wait = timeout;
}
shipnow =
(xdr_results == (xdrproc_t)0 && timeout.tv_sec == 0
&& timeout.tv_usec == 0) ? FALSE : TRUE;
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_mcall, 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);
}
xdrs->x_op = XDR_ENCODE;
ct->ct_error.re_status = RPC_SUCCESS;
x_id = ntohl (--(*msg_x_id));
if ((!XDR_PUTBYTES (xdrs, ct->ct_mcall, 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 = 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 */
/*
* 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(h, errp)
CLIENT *h;
struct rpc_err *errp;
clnttcp_geterr (h, errp)
CLIENT *h;
struct rpc_err *errp;
{
register struct ct_data *ct =
(struct ct_data *) h->cl_private;
struct ct_data *ct =
(struct ct_data *) h->cl_private;
*errp = ct->ct_error;
*errp = ct->ct_error;
}
static bool_t
clnttcp_freeres(cl, xdr_res, res_ptr)
CLIENT *cl;
xdrproc_t xdr_res;
caddr_t res_ptr;
clnttcp_freeres (cl, xdr_res, res_ptr)
CLIENT *cl;
xdrproc_t xdr_res;
caddr_t res_ptr;
{
register struct ct_data *ct = (struct ct_data *)cl->cl_private;
register XDR *xdrs = &(ct->ct_xdrs);
struct ct_data *ct = (struct ct_data *) cl->cl_private;
XDR *xdrs = &(ct->ct_xdrs);
xdrs->x_op = XDR_FREE;
return ((*xdr_res)(xdrs, res_ptr));
xdrs->x_op = XDR_FREE;
return (*xdr_res) (xdrs, res_ptr);
}
static void
clnttcp_abort()
clnttcp_abort ()
{
}
static bool_t
clnttcp_control(cl, request, info)
CLIENT *cl;
int request;
char *info;
clnttcp_control (cl, request, info)
CLIENT *cl;
int request;
char *info;
{
register struct ct_data *ct = (struct ct_data *)cl->cl_private;
struct ct_data *ct = (struct ct_data *) cl->cl_private;
switch (request) {
case CLSET_TIMEOUT:
ct->ct_wait = *(struct timeval *)info;
ct->ct_waitset = TRUE;
break;
case CLGET_TIMEOUT:
*(struct timeval *)info = ct->ct_wait;
break;
case CLGET_SERVER_ADDR:
*(struct sockaddr_in *)info = ct->ct_addr;
break;
default:
return (FALSE);
}
return (TRUE);
switch (request)
{
case CLSET_TIMEOUT:
ct->ct_wait = *(struct timeval *) info;
ct->ct_waitset = TRUE;
break;
case CLGET_TIMEOUT:
*(struct timeval *) info = ct->ct_wait;
break;
case CLGET_SERVER_ADDR:
*(struct sockaddr_in *) info = ct->ct_addr;
break;
default:
return FALSE;
}
return TRUE;
}
static void
clnttcp_destroy(h)
CLIENT *h;
clnttcp_destroy (CLIENT *h)
{
register struct ct_data *ct =
(struct ct_data *) h->cl_private;
struct ct_data *ct =
(struct ct_data *) h->cl_private;
if (ct->ct_closeit) {
(void)close(ct->ct_sock);
}
XDR_DESTROY(&(ct->ct_xdrs));
mem_free((caddr_t)ct, sizeof(struct ct_data));
mem_free((caddr_t)h, sizeof(CLIENT));
if (ct->ct_closeit)
{
(void) close (ct->ct_sock);
}
XDR_DESTROY (&(ct->ct_xdrs));
mem_free ((caddr_t) ct, sizeof (struct ct_data));
mem_free ((caddr_t) h, sizeof (CLIENT));
}
/*
@ -395,76 +414,77 @@ clnttcp_destroy(h)
* around for the rpc level.
*/
static int
readtcp(ct, buf, len)
register struct ct_data *ct;
caddr_t buf;
register int len;
readtcp (char *ctptr, char *buf, int len)
{
struct ct_data *ct = (struct ct_data *)ctptr;
#ifdef FD_SETSIZE
fd_set mask;
fd_set readfds;
fd_set mask;
fd_set readfds;
if (len == 0)
return (0);
FD_ZERO(&mask);
FD_SET(ct->ct_sock, &mask);
if (len == 0)
return 0;
FD_ZERO (&mask);
FD_SET (ct->ct_sock, &mask);
#else
register int mask = 1 << (ct->ct_sock);
int readfds;
int mask = 1 << (ct->ct_sock);
int readfds;
if (len == 0)
return (0);
if (len == 0)
return 0;
#endif /* def FD_SETSIZE */
while (TRUE) {
struct timeval timeout = ct->ct_wait;
readfds = mask;
switch (select(_rpc_dtablesize(), &readfds, (int*)NULL, (int*)NULL,
&timeout)) {
case 0:
ct->ct_error.re_status = RPC_TIMEDOUT;
return (-1);
case -1:
if (errno == EINTR)
continue;
ct->ct_error.re_status = RPC_CANTRECV;
ct->ct_error.re_errno = errno;
return (-1);
}
break;
}
switch (len = read(ct->ct_sock, buf, len)) {
while (TRUE)
{
struct timeval timeout = ct->ct_wait;
readfds = mask;
switch (select (_rpc_dtablesize (), &readfds, (fd_set*)NULL,
(fd_set*)NULL, &timeout))
{
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;
ct->ct_error.re_status = RPC_TIMEDOUT;
return -1;
case -1:
ct->ct_error.re_errno = errno;
ct->ct_error.re_status = RPC_CANTRECV;
break;
if (errno == EINTR)
continue;
ct->ct_error.re_status = RPC_CANTRECV;
ct->ct_error.re_errno = errno;
return -1;
}
return (len);
break;
}
switch (len = 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(ct, buf, len)
struct ct_data *ct;
caddr_t buf;
int len;
writetcp (char *ctptr, char *buf, int len)
{
register int i, cnt;
int i, cnt;
struct ct_data *ct = (struct ct_data*)ctptr;
for (cnt = len; cnt > 0; cnt -= i, buf += i) {
if ((i = write(ct->ct_sock, buf, cnt)) == -1) {
ct->ct_error.re_errno = errno;
ct->ct_error.re_status = RPC_CANTSEND;
return (-1);
}
for (cnt = len; cnt > 0; cnt -= i, buf += i)
{
if ((i = write (ct->ct_sock, buf, cnt)) == -1)
{
ct->ct_error.re_errno = errno;
ct->ct_error.re_status = RPC_CANTSEND;
return -1;
}
return (len);
}
return len;
}

View File

@ -38,54 +38,58 @@ static char sccsid[] = "@(#)clnt_udp.c 1.39 87/08/11 Copyr 1984 Sun Micro";
*/
#include <stdio.h>
#include <unistd.h>
#include <rpc/rpc.h>
#include <rpc/xdr.h>
#include <rpc/clnt.h>
#include <sys/socket.h>
#include <sys/ioctl.h>
#include <netdb.h>
#include <errno.h>
#include <rpc/pmap_clnt.h>
#ifndef errno
extern int errno;
#endif
extern bool_t xdr_opaque_auth (XDR *, struct opaque_auth *);
/*
* UDP bases client side rpc operations
*/
static enum clnt_stat clntudp_call();
static void clntudp_abort();
static void clntudp_geterr();
static bool_t clntudp_freeres();
static bool_t clntudp_control();
static void clntudp_destroy();
static enum clnt_stat clntudp_call (CLIENT *, u_long, xdrproc_t, caddr_t,
xdrproc_t, caddr_t, struct timeval);
static void clntudp_abort (void);
static void clntudp_geterr (CLIENT *, struct rpc_err *);
static bool_t clntudp_freeres (CLIENT *, xdrproc_t, caddr_t);
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
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;
struct sockaddr_in cu_raddr;
int cu_rlen;
struct timeval cu_wait;
struct timeval cu_total;
struct rpc_err cu_error;
XDR cu_outxdrs;
u_int cu_xdrpos;
u_int cu_sendsz;
char *cu_outbuf;
u_int cu_recvsz;
char cu_inbuf[1];
};
struct cu_data
{
int cu_sock;
bool_t cu_closeit;
struct sockaddr_in cu_raddr;
int cu_rlen;
struct timeval cu_wait;
struct timeval cu_total;
struct rpc_err cu_error;
XDR cu_outxdrs;
u_int cu_xdrpos;
u_int cu_sendsz;
char *cu_outbuf;
u_int cu_recvsz;
char cu_inbuf[1];
};
/*
* Create a UDP based client handle.
@ -104,342 +108,361 @@ struct cu_data {
* sent and received.
*/
CLIENT *
clntudp_bufcreate(raddr, program, version, wait, sockp, sendsz, recvsz)
struct sockaddr_in *raddr;
u_long program;
u_long version;
struct timeval wait;
register int *sockp;
u_int sendsz;
u_int recvsz;
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;
{
CLIENT *cl;
register struct cu_data *cu;
struct timeval now;
struct rpc_msg call_msg;
CLIENT *cl;
struct cu_data *cu = NULL;
struct timeval now;
struct rpc_msg call_msg;
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 = (struct cu_data *)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];
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 = (struct cu_data *) 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);
(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;
}
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 = 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;
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 = 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 prov 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;
*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;
}
cu->cu_sock = *sockp;
cl->cl_auth = authnone_create();
return (cl);
/* attempt to bind to prov 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);
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(raddr, program, version, wait, sockp)
struct sockaddr_in *raddr;
u_long program;
u_long version;
struct timeval wait;
register int *sockp;
clntudp_create (raddr, program, version, wait, sockp)
struct sockaddr_in *raddr;
u_long program;
u_long version;
struct timeval wait;
int *sockp;
{
return(clntudp_bufcreate(raddr, program, version, wait, sockp,
UDPMSGSIZE, UDPMSGSIZE));
return clntudp_bufcreate (raddr, program, version, wait, sockp,
UDPMSGSIZE, UDPMSGSIZE);
}
static enum clnt_stat
clntudp_call(cl, proc, xargs, argsp, xresults, resultsp, utimeout)
register CLIENT *cl; /* client handle */
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 */
struct timeval utimeout; /* seconds to wait before giving up */
clntudp_call (cl, proc, xargs, argsp, xresults, resultsp, utimeout)
CLIENT *cl; /* client handle */
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 */
struct timeval utimeout; /* seconds to wait before giving up */
{
register struct cu_data *cu = (struct cu_data *)cl->cl_private;
register XDR *xdrs;
register int outlen;
register int inlen;
int fromlen;
struct cu_data *cu = (struct cu_data *) cl->cl_private;
XDR *xdrs;
int outlen;
int inlen;
int fromlen;
#ifdef FD_SETSIZE
fd_set readfds;
fd_set mask;
fd_set readfds;
fd_set mask;
#else
int readfds;
register int mask;
int readfds;
int mask;
#endif /* def FD_SETSIZE */
struct sockaddr_in from;
struct rpc_msg reply_msg;
XDR reply_xdrs;
struct timeval time_waited;
bool_t ok;
int nrefreshes = 2; /* number of times to refresh cred */
struct timeval timeout;
struct sockaddr_in from;
struct rpc_msg reply_msg;
XDR reply_xdrs;
struct timeval time_waited;
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_total.tv_usec == -1)
{
timeout = utimeout; /* use supplied timeout */
}
else
{
timeout = cu->cu_total; /* use default timeout */
}
time_waited.tv_sec = 0;
time_waited.tv_usec = 0;
time_waited.tv_sec = 0;
time_waited.tv_usec = 0;
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)))
return (cu->cu_error.re_status = RPC_CANTENCODEARGS);
outlen = (int)XDR_GETPOS(xdrs);
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)))
return (cu->cu_error.re_status = RPC_CANTENCODEARGS);
outlen = (int) 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;
return (cu->cu_error.re_status = RPC_CANTSEND);
}
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;
return (cu->cu_error.re_status = RPC_CANTSEND);
}
/*
* Hack to provide rpc-based message passing
*/
if (timeout.tv_sec == 0 && timeout.tv_usec == 0) {
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;
/*
* Hack to provide rpc-based message passing
*/
if (timeout.tv_sec == 0 && timeout.tv_usec == 0)
{
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;
#ifdef FD_SETSIZE
FD_ZERO(&mask);
FD_SET(cu->cu_sock, &mask);
FD_ZERO (&mask);
FD_SET (cu->cu_sock, &mask);
#else
mask = 1 << cu->cu_sock;
mask = 1 << cu->cu_sock;
#endif /* def FD_SETSIZE */
for (;;) {
struct timeval timeout = cu->cu_wait;
readfds = mask;
switch (select(_rpc_dtablesize(), &readfds, (int *)NULL,
(int *)NULL, &timeout)) {
for (;;)
{
struct timeval timeout = cu->cu_wait;
readfds = mask;
switch (select (_rpc_dtablesize (), &readfds, (fd_set*) NULL,
(fd_set*) NULL, &timeout))
{
case 0:
time_waited.tv_sec += cu->cu_wait.tv_sec;
time_waited.tv_usec += cu->cu_wait.tv_usec;
while (time_waited.tv_usec >= 1000000) {
time_waited.tv_sec++;
time_waited.tv_usec -= 1000000;
}
if ((time_waited.tv_sec < timeout.tv_sec) ||
((time_waited.tv_sec == timeout.tv_sec) &&
(time_waited.tv_usec < timeout.tv_usec)))
goto send_again;
return (cu->cu_error.re_status = RPC_TIMEDOUT);
case 0:
time_waited.tv_sec += cu->cu_wait.tv_sec;
time_waited.tv_usec += cu->cu_wait.tv_usec;
while (time_waited.tv_usec >= 1000000)
{
time_waited.tv_sec++;
time_waited.tv_usec -= 1000000;
}
if ((time_waited.tv_sec < timeout.tv_sec) ||
((time_waited.tv_sec == timeout.tv_sec) &&
(time_waited.tv_usec < timeout.tv_usec)))
goto send_again;
return (cu->cu_error.re_status = RPC_TIMEDOUT);
/*
* buggy in other cases because time_waited is not being
* updated.
*/
case -1:
if (errno == EINTR)
continue;
cu->cu_error.re_errno = errno;
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;
return (cu->cu_error.re_status = RPC_CANTRECV);
}
if (inlen < 4)
continue;
/* see if reply transaction id matches sent id */
if (*((u_int32_t *)(cu->cu_inbuf)) != *((u_int32_t *)(cu->cu_outbuf)))
continue;
/* we now assume we have the proper reply */
break;
/*
* buggy in other cases because time_waited is not being
* updated.
*/
case -1:
if (errno == EINTR)
continue;
cu->cu_error.re_errno = errno;
return (cu->cu_error.re_status = RPC_CANTRECV);
}
/*
* 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 {
cu->cu_error.re_status = RPC_CANTDECODERES;
do
{
fromlen = sizeof (struct sockaddr);
inlen = recvfrom (cu->cu_sock, cu->cu_inbuf,
(int) cu->cu_recvsz, 0,
(struct sockaddr *) &from, &fromlen);
}
return (cu->cu_error.re_status);
while (inlen < 0 && errno == EINTR);
if (inlen < 0)
{
if (errno == EWOULDBLOCK)
continue;
cu->cu_error.re_errno = errno;
return (cu->cu_error.re_status = RPC_CANTRECV);
}
if (inlen < 4)
continue;
/* see if reply transaction id matches sent id */
if (*((u_int32_t *) (cu->cu_inbuf)) != *((u_int32_t *) (cu->cu_outbuf)))
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
{
cu->cu_error.re_status = RPC_CANTDECODERES;
}
return cu->cu_error.re_status;
}
static void
clntudp_geterr(cl, errp)
CLIENT *cl;
struct rpc_err *errp;
clntudp_geterr (CLIENT *cl, struct rpc_err *errp)
{
register struct cu_data *cu = (struct cu_data *)cl->cl_private;
struct cu_data *cu = (struct cu_data *) cl->cl_private;
*errp = cu->cu_error;
*errp = cu->cu_error;
}
static bool_t
clntudp_freeres(cl, xdr_res, res_ptr)
CLIENT *cl;
xdrproc_t xdr_res;
caddr_t res_ptr;
clntudp_freeres (CLIENT *cl, xdrproc_t xdr_res, caddr_t res_ptr)
{
register struct cu_data *cu = (struct cu_data *)cl->cl_private;
register XDR *xdrs = &(cu->cu_outxdrs);
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));
xdrs->x_op = XDR_FREE;
return (*xdr_res) (xdrs, res_ptr);
}
static void
clntudp_abort(/*h*/)
/*CLIENT *h;*/
clntudp_abort (void)
{
}
static bool_t
clntudp_control(cl, request, info)
CLIENT *cl;
int request;
char *info;
clntudp_control (CLIENT *cl, int request, char *info)
{
register struct cu_data *cu = (struct cu_data *)cl->cl_private;
struct cu_data *cu = (struct cu_data *) cl->cl_private;
switch (request) {
case CLSET_TIMEOUT:
cu->cu_total = *(struct timeval *)info;
break;
case CLGET_TIMEOUT:
*(struct timeval *)info = cu->cu_total;
break;
case CLSET_RETRY_TIMEOUT:
cu->cu_wait = *(struct timeval *)info;
break;
case CLGET_RETRY_TIMEOUT:
*(struct timeval *)info = cu->cu_wait;
break;
case CLGET_SERVER_ADDR:
*(struct sockaddr_in *)info = cu->cu_raddr;
break;
default:
return (FALSE);
}
return (TRUE);
switch (request)
{
case CLSET_TIMEOUT:
cu->cu_total = *(struct timeval *) info;
break;
case CLGET_TIMEOUT:
*(struct timeval *) info = cu->cu_total;
break;
case CLSET_RETRY_TIMEOUT:
cu->cu_wait = *(struct timeval *) info;
break;
case CLGET_RETRY_TIMEOUT:
*(struct timeval *) info = cu->cu_wait;
break;
case CLGET_SERVER_ADDR:
*(struct sockaddr_in *) info = cu->cu_raddr;
break;
default:
return FALSE;
}
return TRUE;
}
static void
clntudp_destroy(cl)
CLIENT *cl;
clntudp_destroy (CLIENT *cl)
{
register struct cu_data *cu = (struct cu_data *)cl->cl_private;
struct cu_data *cu = (struct cu_data *) cl->cl_private;
if (cu->cu_closeit) {
(void)close(cu->cu_sock);
}
XDR_DESTROY(&(cu->cu_outxdrs));
mem_free((caddr_t)cu, (sizeof(*cu) + cu->cu_sendsz + cu->cu_recvsz));
mem_free((caddr_t)cl, sizeof(CLIENT));
if (cu->cu_closeit)
{
(void) close (cu->cu_sock);
}
XDR_DESTROY (&(cu->cu_outxdrs));
mem_free ((caddr_t) cu, (sizeof (*cu) + cu->cu_sendsz + cu->cu_recvsz));
mem_free ((caddr_t) cl, sizeof (CLIENT));
}

View File

@ -38,6 +38,7 @@ static char sccsid[] = "@(#)get_myaddress.c 1.4 87/08/11 Copyr 1984 Sun Micro";
* Copyright (C) 1984, Sun Microsystems, Inc.
*/
#include <unistd.h>
#include <rpc/types.h>
#include <rpc/pmap_prot.h>
#include <sys/socket.h>
@ -53,40 +54,44 @@ static char sccsid[] = "@(#)get_myaddress.c 1.4 87/08/11 Copyr 1984 Sun Micro";
/*
* don't use gethostbyname, which would invoke yellow pages
*/
get_myaddress(addr)
struct sockaddr_in *addr;
void
get_myaddress (struct sockaddr_in *addr)
{
int s;
char buf[BUFSIZ];
struct ifconf ifc;
struct ifreq ifreq, *ifr;
int len;
int s;
char buf[BUFSIZ];
struct ifconf ifc;
struct ifreq ifreq, *ifr;
int len;
if ((s = socket(AF_INET, SOCK_DGRAM, 0)) < 0) {
perror("get_myaddress: socket");
exit(1);
if ((s = socket (AF_INET, SOCK_DGRAM, 0)) < 0)
{
perror ("get_myaddress: socket");
exit (1);
}
ifc.ifc_len = sizeof (buf);
ifc.ifc_buf = buf;
if (ioctl (s, SIOCGIFCONF, (char *) &ifc) < 0)
{
perror (_("get_myaddress: ioctl (get interface configuration)"));
exit (1);
}
ifr = ifc.ifc_req;
for (len = ifc.ifc_len; len; len -= sizeof ifreq)
{
ifreq = *ifr;
if (ioctl (s, SIOCGIFFLAGS, (char *) &ifreq) < 0)
{
perror ("get_myaddress: ioctl");
exit (1);
}
ifc.ifc_len = sizeof (buf);
ifc.ifc_buf = buf;
if (ioctl(s, SIOCGIFCONF, (char *)&ifc) < 0) {
perror(
_("get_myaddress: ioctl (get interface configuration)"));
exit(1);
if ((ifreq.ifr_flags & IFF_UP) &&
ifr->ifr_addr.sa_family == AF_INET)
{
*addr = *((struct sockaddr_in *) &ifr->ifr_addr);
addr->sin_port = htons (PMAPPORT);
break;
}
ifr = ifc.ifc_req;
for (len = ifc.ifc_len; len; len -= sizeof ifreq) {
ifreq = *ifr;
if (ioctl(s, SIOCGIFFLAGS, (char *)&ifreq) < 0) {
perror("get_myaddress: ioctl");
exit(1);
}
if ((ifreq.ifr_flags & IFF_UP) &&
ifr->ifr_addr.sa_family == AF_INET) {
*addr = *((struct sockaddr_in *)&ifr->ifr_addr);
addr->sin_port = htons(PMAPPORT);
break;
}
ifr++;
}
(void) close(s);
ifr++;
}
(void) close (s);
}

View File

@ -38,35 +38,37 @@ static char sccsid[] = "@(#)getrpcport.c 1.3 87/08/11 SMI";
#include <alloca.h>
#include <errno.h>
#include <stdio.h>
#include <rpc/rpc.h>
#include <netdb.h>
#include <string.h>
#include <rpc/rpc.h>
#include <rpc/clnt.h>
#include <rpc/pmap_clnt.h>
#include <sys/socket.h>
int
getrpcport(host, prognum, versnum, proto)
char *host;
getrpcport (const char *host, u_long prognum, u_long versnum, u_int proto)
{
struct sockaddr_in addr;
struct hostent hostbuf, *hp;
size_t buflen;
char *buffer;
int herr;
struct sockaddr_in addr;
struct hostent hostbuf, *hp;
size_t buflen;
char *buffer;
int herr;
buflen = 1024;
buflen = 1024;
buffer = __alloca (buflen);
while (__gethostbyname_r (host, &hostbuf, buffer, buflen, &hp, &herr)
< 0)
if (herr != NETDB_INTERNAL || errno != ERANGE)
return 0;
else
{
/* Enlarge the buffer. */
buflen *= 2;
buffer = __alloca (buflen);
while (__gethostbyname_r (host, &hostbuf, buffer, buflen, &hp, &herr)
< 0)
if (herr != NETDB_INTERNAL || errno != ERANGE)
return 0;
else
{
/* Enlarge the buffer. */
buflen *= 2;
buffer = __alloca (buflen);
}
}
bcopy(hp->h_addr, (char *) &addr.sin_addr, hp->h_length);
addr.sin_family = AF_INET;
addr.sin_port = 0;
return (pmap_getport(&addr, prognum, versnum, proto));
bcopy (hp->h_addr, (char *) &addr.sin_addr, hp->h_length);
addr.sin_family = AF_INET;
addr.sin_port = 0;
return pmap_getport (&addr, prognum, versnum, proto);
}

View File

@ -47,43 +47,34 @@ static char sccsid[] = "@(#)pmap_getmaps.c 1.10 87/08/11 Copyr 1984 Sun Micro";
#include <stdio.h>
#include <errno.h>
#if 0 /* these seem to be gratuitous --roland@gnu */
#include <net/if.h>
#include <sys/ioctl.h>
#define NAMELEN 255
#define MAX_BROADCAST_SIZE 1400
#endif
#ifndef errno
extern int errno;
#endif
/*
* Get a copy of the current port maps.
* Calls the pmap service remotely to do get the maps.
*/
struct pmaplist *
pmap_getmaps(address)
struct sockaddr_in *address;
pmap_getmaps (struct sockaddr_in *address)
{
struct pmaplist *head = (struct pmaplist *)NULL;
int socket = -1;
struct timeval minutetimeout;
register CLIENT *client;
struct pmaplist *head = (struct pmaplist *) 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 != (CLIENT *)NULL) {
if (CLNT_CALL(client, PMAPPROC_DUMP, xdr_void, NULL, xdr_pmaplist,
&head, minutetimeout) != RPC_SUCCESS) {
clnt_perror(client, "pmap_getmaps rpc problem");
}
CLNT_DESTROY(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 != (CLIENT *) NULL)
{
if (CLNT_CALL (client, PMAPPROC_DUMP, (xdrproc_t)xdr_void, NULL,
(xdrproc_t)xdr_pmaplist, (caddr_t)&head,
minutetimeout) != RPC_SUCCESS)
{
clnt_perror (client, _("pmap_getmaps rpc problem"));
}
/* (void)close(socket); CLNT_DESTROY already closed it */
address->sin_port = 0;
return (head);
CLNT_DESTROY (client);
}
/* (void)close(socket); CLNT_DESTROY already closed it */
address->sin_port = 0;
return head;
}

View File

@ -43,12 +43,10 @@ static char sccsid[] = "@(#)pmap_getport.c 1.9 87/08/11 Copyr 1984 Sun Micro";
#include <rpc/pmap_clnt.h>
#include <sys/socket.h>
#if 0 /* these seem to be gratuitous --roland@gnu */
#include <net/if.h>
#endif
static struct timeval timeout = { 5, 0 };
static struct timeval tottimeout = { 60, 0 };
static const struct timeval timeout =
{5, 0};
static const struct timeval tottimeout =
{60, 0};
/*
* Find the mapped port for program,version.
@ -56,35 +54,40 @@ static struct timeval tottimeout = { 60, 0 };
* Returns 0 if no map exists.
*/
u_short
pmap_getport(address, program, version, protocol)
struct sockaddr_in *address;
u_long program;
u_long version;
u_int protocol;
pmap_getport (address, program, version, protocol)
struct sockaddr_in *address;
u_long program;
u_long version;
u_int protocol;
{
u_short port = 0;
int socket = -1;
register CLIENT *client;
struct pmap parms;
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 != (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, PMAPPROC_GETPORT, xdr_pmap, &parms,
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);
address->sin_port = htons (PMAPPORT);
client = clntudp_bufcreate (address, PMAPPROG,
PMAPVERS, timeout, &socket, RPCSMALLMSGSIZE, RPCSMALLMSGSIZE);
if (client != (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, PMAPPROC_GETPORT, (xdrproc_t)xdr_pmap,
(caddr_t)&parms, (xdrproc_t)xdr_u_short,
(caddr_t)&port, tottimeout) != RPC_SUCCESS)
{
rpc_createerr.cf_stat = RPC_PMAPFAILURE;
clnt_geterr (client, &rpc_createerr.cf_error);
}
/* (void)close(socket); CLNT_DESTROY already closed it */
address->sin_port = 0;
return (port);
else if (port == 0)
{
rpc_createerr.cf_stat = RPC_PROGNOTREGISTERED;
}
CLNT_DESTROY (client);
}
/* (void)close(socket); CLNT_DESTROY already closed it */
address->sin_port = 0;
return port;
}

View File

@ -42,46 +42,43 @@ static char sccsid[] = "@(#)pmap_clnt.c 1.37 87/08/11 Copyr 1984 Sun Micro";
#include <rpc/pmap_prot.h>
#include <rpc/pmap_clnt.h>
static struct timeval timeout = { 5, 0 };
static struct timeval tottimeout = { 60, 0 };
void clnt_perror();
extern void get_myaddress (struct sockaddr_in *addr);
static const struct timeval timeout = {5, 0};
static const struct timeval tottimeout = {60, 0};
/*
* Set a mapping between program,version and port.
* Calls the pmap service remotely to do the mapping.
*/
bool_t
pmap_set(program, version, protocol, port)
u_long program;
u_long version;
int protocol;
u_short port;
pmap_set (u_long program, u_long version, int protocol, u_short port)
{
struct sockaddr_in myaddress;
int socket = -1;
register CLIENT *client;
struct pmap parms;
bool_t rslt;
struct sockaddr_in myaddress;
int socket = -1;
CLIENT *client;
struct pmap parms;
bool_t rslt;
get_myaddress(&myaddress);
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, xdr_pmap, &parms, xdr_bool, &rslt,
tottimeout) != RPC_SUCCESS) {
clnt_perror(client, _("Cannot register service"));
return (FALSE);
}
CLNT_DESTROY(client);
/* (void)close(socket); CLNT_DESTROY closes it */
return (rslt);
get_myaddress (&myaddress);
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, (caddr_t)&parms,
(xdrproc_t)xdr_bool, (caddr_t)&rslt,
tottimeout) != RPC_SUCCESS)
{
clnt_perror (client, _("Cannot register service"));
return FALSE;
}
CLNT_DESTROY (client);
/* (void)close(socket); CLNT_DESTROY closes it */
return rslt;
}
/*
@ -89,27 +86,25 @@ pmap_set(program, version, protocol, port)
* Calls the pmap service remotely to do the un-mapping.
*/
bool_t
pmap_unset(program, version)
u_long program;
u_long version;
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 sockaddr_in myaddress;
int socket = -1;
CLIENT *client;
struct pmap parms;
bool_t rslt;
get_myaddress(&myaddress);
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, xdr_pmap, &parms, xdr_bool, &rslt,
tottimeout);
CLNT_DESTROY(client);
/* (void)close(socket); CLNT_DESTROY already closed it */
return (rslt);
get_myaddress (&myaddress);
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, (caddr_t)&parms,
(xdrproc_t)xdr_bool, (caddr_t)&rslt, tottimeout);
CLNT_DESTROY (client);
/* (void)close(socket); CLNT_DESTROY already closed it */
return rslt;
}

View File

@ -6,23 +6,23 @@
* 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
@ -44,14 +44,14 @@ static char sccsid[] = "@(#)pmap_prot.c 1.17 87/08/11 Copyr 1984 Sun Micro";
bool_t
xdr_pmap(xdrs, regs)
XDR *xdrs;
struct pmap *regs;
xdr_pmap (xdrs, regs)
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);
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;
}

View File

@ -6,23 +6,23 @@
* 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
@ -43,34 +43,34 @@ static char sccsid[] = "@(#)pmap_prot2.c 1.3 87/08/11 Copyr 1984 Sun Micro";
#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;
* struct pmap pml_map;
* struct pmaplist *pml_map;
* };
*
* Compare that declaration with a corresponding xdr declaration that
* 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 {};
* 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.
* 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
@ -82,35 +82,37 @@ static char sccsid[] = "@(#)pmap_prot2.c 1.3 87/08/11 Copyr 1984 Sun Micro";
* this sounds like a job for xdr_reference!
*/
bool_t
xdr_pmaplist(xdrs, rp)
register XDR *xdrs;
register struct pmaplist **rp;
xdr_pmaplist (xdrs, rp)
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;
/*
* 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;
int freeing = (xdrs->x_op == XDR_FREE);
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), xdr_pmap))
return (FALSE);
rp = (freeing) ? next : &((*rp)->pml_next);
}
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);
}
}

View File

@ -39,6 +39,8 @@ static char sccsid[] = "@(#)pmap_rmt.c 1.21 87/08/27 Copyr 1984 Sun Micro";
* Copyright (C) 1984, Sun Microsystems, Inc.
*/
#include <unistd.h>
#include <string.h>
#include <rpc/rpc.h>
#include <rpc/pmap_prot.h>
#include <rpc/pmap_clnt.h>
@ -53,11 +55,7 @@ static char sccsid[] = "@(#)pmap_rmt.c 1.21 87/08/27 Copyr 1984 Sun Micro";
#include <arpa/inet.h>
#define MAX_BROADCAST_SIZE 1400
#ifndef errno
extern int errno;
#endif
static struct timeval timeout = { 3, 0 };
static struct timeval timeout = {3, 0};
/*
* pmapper remote-call-service interface.
@ -65,42 +63,46 @@ static struct timeval timeout = { 3, 0 };
* 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(addr, prog, vers, proc, xdrargs, argsp, xdrres, resp, tout, port_ptr)
struct sockaddr_in *addr;
u_long prog, vers, proc;
xdrproc_t xdrargs, xdrres;
caddr_t argsp, resp;
struct timeval tout;
u_long *port_ptr;
pmap_rmtcall (addr, prog, vers, proc, xdrargs, argsp, xdrres, resp, tout, port_ptr)
struct sockaddr_in *addr;
u_long prog, vers, proc;
xdrproc_t xdrargs, xdrres;
caddr_t argsp, resp;
struct timeval tout;
u_long *port_ptr;
{
int socket = -1;
register CLIENT *client;
struct rmtcallargs a;
struct rmtcallres r;
enum clnt_stat stat;
int socket = -1;
CLIENT *client;
struct rmtcallargs a;
struct rmtcallres r;
enum clnt_stat stat;
addr->sin_port = htons(PMAPPORT);
client = clntudp_create(addr, PMAPPROG, PMAPVERS, timeout, &socket);
if (client != (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, PMAPPROC_CALLIT, xdr_rmtcall_args, &a,
xdr_rmtcallres, &r, tout);
CLNT_DESTROY(client);
} else {
stat = RPC_FAILED;
}
/* (void)close(socket); CLNT_DESTROY already closed it */
addr->sin_port = 0;
return (stat);
addr->sin_port = htons (PMAPPORT);
client = clntudp_create (addr, PMAPPROG, PMAPVERS, timeout, &socket);
if (client != (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, PMAPPROC_CALLIT, (xdrproc_t)xdr_rmtcall_args,
(caddr_t)&a, (xdrproc_t)xdr_rmtcallres,
(caddr_t)&r, tout);
CLNT_DESTROY (client);
}
else
{
stat = RPC_FAILED;
}
/* (void)close(socket); CLNT_DESTROY already closed it */
addr->sin_port = 0;
return stat;
}
@ -109,30 +111,31 @@ pmap_rmtcall(addr, prog, vers, proc, xdrargs, argsp, xdrres, resp, tout, port_pt
* written for XDR_ENCODE direction only
*/
bool_t
xdr_rmtcall_args(xdrs, cap)
register XDR *xdrs;
register struct rmtcallargs *cap;
xdr_rmtcall_args (xdrs, cap)
XDR *xdrs;
struct rmtcallargs *cap;
{
u_int lenposition, argposition, position;
u_int lenposition, argposition, position;
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);
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;
}
/*
@ -140,19 +143,20 @@ xdr_rmtcall_args(xdrs, cap)
* written for XDR_DECODE direction only
*/
bool_t
xdr_rmtcallres(xdrs, crp)
register XDR *xdrs;
register struct rmtcallres *crp;
xdr_rmtcallres (xdrs, crp)
XDR *xdrs;
struct rmtcallres *crp;
{
caddr_t port_ptr;
caddr_t port_ptr;
port_ptr = (caddr_t)crp->port_ptr;
if (xdr_reference(xdrs, &port_ptr, sizeof (u_long),
xdr_u_long) && xdr_u_long(xdrs, &crp->resultslen)) {
crp->port_ptr = (u_long *)port_ptr;
return ((*(crp->xdr_results))(xdrs, crp->results_ptr));
}
return (FALSE);
port_ptr = (caddr_t) 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 *) port_ptr;
return (*(crp->xdr_results)) (xdrs, crp->results_ptr);
}
return FALSE;
}
@ -163,231 +167,253 @@ xdr_rmtcallres(xdrs, crp)
*/
static int
getbroadcastnets(addrs, sock, buf)
struct in_addr *addrs;
int sock; /* any valid socket will do */
char *buf; /* why allocate more when we can use existing... */
getbroadcastnets (struct in_addr *addrs, int sock, char *buf)
/* int sock: any valid socket will do */
/* char *buf: why allocate more when we can use existing... */
{
struct ifconf ifc;
struct ifreq ifreq, *ifr;
struct sockaddr_in *sin;
int n, i;
struct ifconf ifc;
struct ifreq ifreq, *ifr;
struct sockaddr_in *sin;
int n, i;
ifc.ifc_len = UDPMSGSIZE;
ifc.ifc_buf = buf;
if (ioctl(sock, SIOCGIFCONF, (char *)&ifc) < 0) {
perror(_("broadcast: ioctl (get interface configuration)"));
return (0);
}
ifr = ifc.ifc_req;
for (i = 0, n = ifc.ifc_len/sizeof (struct ifreq); n > 0; n--, ifr++) {
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) &&
ifr->ifr_addr.sa_family == AF_INET) {
sin = (struct sockaddr_in *)&ifr->ifr_addr;
#ifdef SIOCGIFBRDADDR /* 4.3BSD */
if (ioctl(sock, SIOCGIFBRDADDR, (char *)&ifreq) < 0) {
addrs[i++] = inet_makeaddr(inet_netof
/* Changed to pass struct instead of s_addr member
by roland@gnu. */
(sin->sin_addr), INADDR_ANY);
} else {
addrs[i++] = ((struct sockaddr_in*)
&ifreq.ifr_addr)->sin_addr;
}
#else /* 4.2 BSD */
addrs[i++] = inet_makeaddr(inet_netof
(sin->sin_addr.s_addr), INADDR_ANY);
#endif
}
ifc.ifc_len = UDPMSGSIZE;
ifc.ifc_buf = buf;
if (ioctl (sock, SIOCGIFCONF, (char *) &ifc) < 0)
{
perror (_("broadcast: ioctl (get interface configuration)"));
return (0);
}
ifr = ifc.ifc_req;
for (i = 0, n = ifc.ifc_len / sizeof (struct ifreq); n > 0; n--, ifr++)
{
ifreq = *ifr;
if (ioctl (sock, SIOCGIFFLAGS, (char *) &ifreq) < 0)
{
perror (_("broadcast: ioctl (get interface flags)"));
continue;
}
return (i);
if ((ifreq.ifr_flags & IFF_BROADCAST) &&
(ifreq.ifr_flags & IFF_UP) &&
ifr->ifr_addr.sa_family == AF_INET)
{
sin = (struct sockaddr_in *) &ifr->ifr_addr;
#ifdef SIOCGIFBRDADDR /* 4.3BSD */
if (ioctl (sock, SIOCGIFBRDADDR, (char *) &ifreq) < 0)
{
addrs[i++] = inet_makeaddr (inet_netof
/* Changed to pass struct instead of s_addr member
by roland@gnu. */
(sin->sin_addr), INADDR_ANY);
}
else
{
addrs[i++] = ((struct sockaddr_in *)
&ifreq.ifr_addr)->sin_addr;
}
#else /* 4.2 BSD */
addrs[i++] = inet_makeaddr (inet_netof
(sin->sin_addr.s_addr), INADDR_ANY);
#endif
}
}
return i;
}
enum clnt_stat
clnt_broadcast(prog, vers, proc, xargs, argsp, xresults, resultsp, eachresult)
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 */
clnt_broadcast (prog, vers, proc, xargs, argsp, xresults, resultsp, eachresult)
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;
AUTH *unix_auth = authunix_create_default();
XDR xdr_stream;
register XDR *xdrs = &xdr_stream;
int outlen, inlen, fromlen, nets;
register int sock;
int on = 1;
enum clnt_stat stat;
AUTH *unix_auth = authunix_create_default ();
XDR xdr_stream;
XDR *xdrs = &xdr_stream;
int outlen, inlen, fromlen, nets;
int sock;
int on = 1;
#ifdef FD_SETSIZE
fd_set mask;
fd_set readfds;
fd_set mask;
fd_set readfds;
#else
int readfds;
register int mask;
int readfds;
int mask;
#endif /* def FD_SETSIZE */
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, t1;
char outbuf[MAX_BROADCAST_SIZE], inbuf[UDPMSGSIZE];
int i;
bool_t done = FALSE;
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, t1;
char outbuf[MAX_BROADCAST_SIZE], inbuf[UDPMSGSIZE];
/*
* 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;
}
/*
* 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;
}
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 */
#ifdef FD_SETSIZE
FD_ZERO(&mask);
FD_SET(sock, &mask);
FD_ZERO (&mask);
FD_SET (sock, &mask);
#else
mask = (1 << sock);
mask = (1 << sock);
#endif /* def FD_SETSIZE */
nets = getbroadcastnets(addrs, sock, inbuf);
bzero((char *)&baddr, sizeof (baddr));
baddr.sin_family = AF_INET;
baddr.sin_port = htons(PMAPPORT);
baddr.sin_addr.s_addr = htonl(INADDR_ANY);
/* baddr.sin_addr.S_un.S_addr = htonl(INADDR_ANY); */
(void)gettimeofday(&t, (struct timezone *)0);
msg.rm_xid = xid = 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;
nets = getbroadcastnets (addrs, sock, inbuf);
bzero ((char *) &baddr, sizeof (baddr));
baddr.sin_family = AF_INET;
baddr.sin_port = htons (PMAPPORT);
baddr.sin_addr.s_addr = htonl (INADDR_ANY);
/* baddr.sin_addr.S_un.S_addr = htonl(INADDR_ANY); */
(void) gettimeofday (&t, (struct timezone *) 0);
msg.rm_xid = xid = 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.
*/
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;
}
}
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.
*/
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 = xdr_rmtcallres;
readfds = mask;
t1 = t;
switch (select(_rpc_dtablesize(), &readfds, (int *)NULL,
(int *)NULL, &t1)) {
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;
readfds = mask;
t1 = t;
switch (select (_rpc_dtablesize (), &readfds, (fd_set *) NULL,
(fd_set *) NULL, &t1))
{
case 0: /* timed out */
stat = RPC_TIMEDOUT;
continue;
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;
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_long))
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 ... */
} else {
} /* 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_long))
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 ... */
}
else
{
#ifdef notdef
/* some kind of deserialization problem ... */
if (msg.rm_xid == xid)
fprintf(stderr, "Broadcast deserialization problem");
/* otherwise, just random garbage */
/* some kind of deserialization problem ... */
if (msg.rm_xid == xid)
fprintf (stderr, "Broadcast deserialization problem");
/* otherwise, just random garbage */
#endif
}
xdrs->x_op = XDR_FREE;
msg.acpted_rply.ar_results.proc = 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;
}
}
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:
(void)close(sock);
AUTH_DESTROY(unix_auth);
return (stat);
(void) close (sock);
AUTH_DESTROY (unix_auth);
return stat;
}

View File

@ -42,6 +42,7 @@
#define _RPC_AUTH_H 1
#include <features.h>
#include <rpc/xdr.h>
__BEGIN_DECLS
@ -76,7 +77,7 @@ union des_block {
char c[8];
};
typedef union des_block des_block;
extern bool_t xdr_des_block();
extern bool_t xdr_des_block __P ((XDR *__xdrs, des_block *__blkp));
/*
* Authentication info. Opaque to client.
@ -90,19 +91,21 @@ struct opaque_auth {
/*
* Auth handle, interface to client side authenticators.
*/
typedef struct {
struct opaque_auth ah_cred;
struct opaque_auth ah_verf;
union des_block ah_key;
struct auth_ops {
void (*ah_nextverf)();
int (*ah_marshal)(); /* nextverf & serialize */
int (*ah_validate)(); /* validate verifier */
int (*ah_refresh)(); /* refresh credentials */
void (*ah_destroy)(); /* destroy this structure */
} *ah_ops;
caddr_t ah_private;
} AUTH;
typedef struct AUTH AUTH;
struct AUTH {
struct opaque_auth ah_cred;
struct opaque_auth ah_verf;
union des_block ah_key;
struct auth_ops {
void (*ah_nextverf) __P ((AUTH *));
int (*ah_marshal) __P ((AUTH *, XDR *)); /* nextverf & serialize */
int (*ah_validate) __P ((AUTH *, struct opaque_auth *));
/* validate verifier */
int (*ah_refresh) __P ((AUTH *)); /* refresh credentials */
void (*ah_destroy) __P ((AUTH *)); /* destroy this structure */
} *ah_ops;
caddr_t ah_private;
};
/*
@ -160,14 +163,17 @@ extern AUTH *authunix_create __P ((char *__machname, __uid_t __uid,
__gid_t *__aup_gids));
extern AUTH *authunix_create_default __P ((void));
extern AUTH *authnone_create __P ((void));
extern AUTH *authdes_create();
extern AUTH *authdes_create __P ((char *__servername, u_int __window,
struct sockaddr *__syncaddr,
des_block *__ckey));
#define AUTH_NONE 0 /* no authentication */
#define AUTH_NULL 0 /* backward compatibility */
#define AUTH_UNIX 1 /* unix style (uid, gids) */
#define AUTH_SYS 1 /* unix style (uid, gids) */
#define AUTH_UNIX AUTH_SYS
#define AUTH_SHORT 2 /* short hand unix style */
#define AUTH_DES 3 /* des style (encrypted timestamps) */
#define AUTH_KERB 4 /* kerberos style */
__END_DECLS

View File

@ -66,22 +66,33 @@ enum clnt_stat {
RPC_PROCUNAVAIL=10, /* procedure unavailable */
RPC_CANTDECODEARGS=11, /* decode arguments error */
RPC_SYSTEMERROR=12, /* generic "other problem" */
RPC_NOBROADCAST = 21, /* Broadcasting not supported */
/*
* callrpc & clnt_create errors
*/
RPC_UNKNOWNHOST=13, /* unknown host name */
RPC_UNKNOWNPROTO=17, /* unknown protocol */
RPC_UNKNOWNADDR = 19, /* Remote address unknown */
/*
* _ create errors
* rpcbind errors
*/
RPC_PMAPFAILURE=14, /* the pmapper failed in its call */
RPC_RPCBFAILURE=14, /* portmapper failed in its call */
#define RPC_PMAPFAILURE RPC_RPCBFAILURE
RPC_PROGNOTREGISTERED=15, /* remote program is not registered */
RPC_N2AXLATEFAILURE = 22, /* Name to addr translation failed */
/*
* unspecified error
*/
RPC_FAILED=16
RPC_FAILED=16,
RPC_INTR=18,
RPC_TLIERROR=20,
RPC_UDERROR=23,
/*
* asynchronous errors
*/
RPC_INPROGRESS = 24,
RPC_STALERACHANDLE = 25
};
@ -89,19 +100,19 @@ enum clnt_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 {
u_long low; /* lowest verion supported */
u_long high; /* highest verion supported */
} RE_vers;
struct { /* maybe meaningful if RPC_FAILED */
long s1;
long s2;
} RE_lb; /* life boot & debugging only */
} ru;
enum clnt_stat re_status;
union {
int RE_errno; /* related system error */
enum auth_stat RE_why; /* why the auth error occurred */
struct {
u_long low; /* lowest verion supported */
u_long high; /* highest verion supported */
} RE_vers;
struct { /* maybe meaningful if RPC_FAILED */
long s1;
long 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
@ -114,18 +125,25 @@ struct rpc_err {
* Created by individual implementations, see e.g. rpc_udp.c.
* Client is responsible for initializing auth, see e.g. auth_none.c.
*/
typedef struct {
AUTH *cl_auth; /* authenticator */
struct clnt_ops {
enum clnt_stat (*cl_call)(); /* call remote procedure */
void (*cl_abort)(); /* abort a call */
void (*cl_geterr)(); /* get specific error code */
bool_t (*cl_freeres)(); /* frees results */
void (*cl_destroy)();/* destroy this structure */
bool_t (*cl_control)();/* the ioctl() of rpc */
} *cl_ops;
caddr_t cl_private; /* private stuff */
} CLIENT;
typedef struct CLIENT CLIENT;
struct CLIENT {
AUTH *cl_auth; /* authenticator */
struct clnt_ops {
enum clnt_stat (*cl_call) __P ((CLIENT *, u_long, xdrproc_t,
caddr_t, xdrproc_t,
caddr_t, struct timeval));
/* call remote procedure */
void (*cl_abort) __P ((void)); /* abort a call */
void (*cl_geterr) __P ((CLIENT *, struct rpc_err *));
/* get specific error code */
bool_t (*cl_freeres) __P ((CLIENT *, xdrproc_t, caddr_t));
/* frees results */
void (*cl_destroy) __P ((CLIENT *)); /* destroy this structure */
bool_t (*cl_control) __P ((CLIENT *, int, char *));
/* the ioctl() of rpc */
} *cl_ops;
caddr_t cl_private; /* private stuff */
};
/*
@ -189,16 +207,29 @@ typedef struct {
#define clnt_control(cl,rq,in) ((*(cl)->cl_ops->cl_control)(cl,rq,in))
/*
* control operations that apply to both udp and tcp transports
* control operations that apply to all transports
*/
#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 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) */
#define CLSET_PUSH_TIMOD 17 /* push timod if not already present */
#define CLSET_POP_TIMOD 18 /* pop timod */
/*
* udp only control operations
* Connectionless only control operations
*/
#define CLSET_RETRY_TIMEOUT 4 /* set retry timeout (timeval) */
#define CLGET_RETRY_TIMEOUT 5 /* get retry timeout (timeval) */
#define CLSET_RETRY_TIMEOUT 4 /* set retry timeout (timeval) */
#define CLGET_RETRY_TIMEOUT 5 /* get retry timeout (timeval) */
/*
* void
@ -239,7 +270,8 @@ typedef struct {
* u_long prog;
* u_long vers;
*/
extern CLIENT *clntraw_create __P ((u_long __prog, u_long __vers));
extern CLIENT *clntraw_create __P ((__const u_long __prog,
__const u_long __vers));
/*
@ -247,12 +279,12 @@ extern CLIENT *clntraw_create __P ((u_long __prog, u_long __vers));
* CLIENT *
* clnt_create(host, prog, vers, prot)
* char *host; -- hostname
* u_int prog; -- program number
* u_int vers; -- version number
* u_long prog; -- program number
* u_ong vers; -- version number
* char *prot; -- protocol
*/
extern CLIENT *clnt_create __P ((char *__host, u_int __prog, u_int __vers,
char *__prot));
extern CLIENT *clnt_create __P ((__const char *__host, __const u_long __prog,
__const u_long __vers, __const char *__prot));
/*
@ -302,11 +334,17 @@ extern CLIENT *clntudp_bufcreate __P ((struct sockaddr_in *__raddr,
int *__sockp, u_int __sendsz,
u_int __recvsz));
extern int callrpc __P ((__const char *__host, __const u_long __prognum,
__const u_long __versnum, __const u_long __procnum,
__const xdrproc_t __inproc, __const char *__in,
__const xdrproc_t __outproc, char *__out));
extern int _rpc_dtablesize __P ((void));
/*
* Print why creation failed
*/
extern void clnt_pcreateerror __P ((char *__msg)); /* stderr */
extern char *clnt_spcreateerror __P ((char *__msg)); /* string */
extern void clnt_pcreateerror __P ((__const char *__msg)); /* stderr */
extern char *clnt_spcreateerror __P ((__const char *__msg)); /* string */
/*
* Like clnt_perror(), but is more verbose in its output
@ -316,8 +354,10 @@ extern void clnt_perrno __P ((enum clnt_stat __num)); /* stderr */
/*
* Print an English error message, given the client error code
*/
extern void clnt_perror __P ((CLIENT *__clnt, char *__msg)); /* stderr */
extern char *clnt_sperror __P ((CLIENT *__clnt, char *__msg)); /* string */
extern void clnt_perror __P ((CLIENT *__clnt, __const char *__msg));
/* stderr */
extern char *clnt_sperror __P ((CLIENT *__clnt, __const char *__msg));
/* string */
/*
* If a creation fails, the following allows the user to figure out why.
@ -336,7 +376,8 @@ extern struct rpc_createerr rpc_createerr;
*/
extern char *clnt_sperrno __P ((enum clnt_stat __num)); /* string */
extern int getrpcport __P ((__const char * __host, u_long __prognum,
u_long __versnum, u_int proto));
#define UDPMSGSIZE 8800 /* rpc imposed limit on udp msg size */
#define RPCSMALLMSGSIZE 400 /* a more reasonable packet size */

View File

@ -41,7 +41,7 @@
__BEGIN_DECLS
typedef bool_t (*resultproc_t)();
typedef bool_t (*resultproc_t) __P ((caddr_t resp, struct sockaddr_in *raddr));
/*
* Usage:
@ -65,29 +65,29 @@ typedef bool_t (*resultproc_t)();
* address if the responder to the broadcast.
*/
extern bool_t pmap_set __P ((u_long __program, u_long __version,
extern bool_t pmap_set __P ((__const u_long __program, __const u_long __vers,
int __protocol, u_short __port));
extern bool_t pmap_unset __P ((u_long __program, u_long __version));
extern bool_t pmap_unset __P ((__const u_long __program, __const u_long __vers));
extern struct pmaplist *pmap_getmaps __P ((struct sockaddr_in *__address));
extern enum clnt_stat pmap_rmtcall __P ((struct sockaddr_in *__addr,
u_long __prog, u_long __vers,
u_long __proc, xdrproc_t __xdrargs,
__const u_long __prog,
__const u_long __vers,
__const u_long __proc,
xdrproc_t __xdrargs,
caddr_t __argsp, xdrproc_t __xdrres,
caddr_t __resp, struct timeval __tout,
u_long *__port_ptr));
extern enum clnt_stat clnt_broadcast __P ((u_long __prog, u_long __vers,
u_long __proc, xdrproc_t __xargs,
extern enum clnt_stat clnt_broadcast __P ((__const u_long __prog,
__const u_long __vers,
__const u_long __proc,
xdrproc_t __xargs,
caddr_t __argsp,
xdrproc_t __xresults,
caddr_t __resultsp,
resultproc_t __eachresult));
extern u_short pmap_getport __P ((struct sockaddr_in *__address,
u_long __program, u_long __version,
__const u_long __program,
__const u_long __version,
u_int __protocol));
__END_DECLS

View File

@ -37,6 +37,9 @@
#ifndef __SVC_HEADER__
#define __SVC_HEADER__
#include <features.h>
#include <rpc/rpc_msg.h>
__BEGIN_DECLS
/*
@ -70,23 +73,31 @@ enum xprt_stat {
/*
* Server side transport handle
*/
typedef struct {
int xp_sock;
u_short xp_port; /* associated port number */
struct xp_ops {
bool_t (*xp_recv)(); /* receive incoming requests */
enum xprt_stat (*xp_stat)(); /* get transport status */
bool_t (*xp_getargs)(); /* get arguments */
bool_t (*xp_reply)(); /* send reply */
bool_t (*xp_freeargs)();/* free mem allocated for args */
void (*xp_destroy)(); /* destroy this struct */
} *xp_ops;
int xp_addrlen; /* length of remote address */
struct sockaddr_in xp_raddr; /* remote address */
struct opaque_auth xp_verf; /* raw response verifier */
caddr_t xp_p1; /* private */
caddr_t xp_p2; /* private */
} SVCXPRT;
typedef struct SVCXPRT SVCXPRT;
struct SVCXPRT {
int xp_sock;
u_short xp_port; /* associated port number */
const struct xp_ops {
bool_t (*xp_recv) __P ((SVCXPRT *__xprt, struct rpc_msg *__msg));
/* receive incoming requests */
enum xprt_stat (*xp_stat) __P ((SVCXPRT *__xprt));
/* get transport status */
bool_t (*xp_getargs) __P ((SVCXPRT *__xprt, xdrproc_t __xdr_args,
caddr_t args_ptr)); /* get arguments */
bool_t (*xp_reply) __P ((SVCXPRT *__xprt, struct rpc_msg *__msg));
/* send reply */
bool_t (*xp_freeargs) __P ((SVCXPRT *__xprt, xdrproc_t __xdr_args,
caddr_t args_ptr));
/* free mem allocated for args */
void (*xp_destroy) __P ((SVCXPRT *__xprt));
/* destroy this struct */
} *xp_ops;
int xp_addrlen; /* length of remote address */
struct sockaddr_in xp_raddr; /* remote address */
struct opaque_auth xp_verf; /* raw response verifier */
caddr_t xp_p1; /* private */
caddr_t xp_p2; /* private */
};
/*
* Approved way of getting address of caller
@ -153,11 +164,12 @@ struct svc_req {
* u_long prog;
* u_long vers;
* void (*dispatch)();
* int protocol; like TCP or UDP, zero means do not register
* u_long protocol; like TCP or UDP, zero means do not register
*/
extern bool_t svc_register __P ((SVCXPRT *__xprt, u_long __prog,
u_long __vers, void (*__dispatch) (),
int __protocol));
u_long __vers, void (*__dispatch)
__P ((struct svc_req *, SVCXPRT *)),
u_long __protocol));
/*
* Service un-registration
@ -257,11 +269,9 @@ extern int svc_fds;
* a small program implemented by the svc_rpc implementation itself;
* also see clnt.h for protocol numbers.
*/
extern void rpctest_service();
extern void svc_getreq __P ((int __rdfds));
extern void svc_getreqset __P ((fd_set *readfds));
extern void svc_run __P ((void)) __attribute__ ((noreturn));
extern void svc_run __P ((void)); /* __attribute__ ((noreturn)) */
/*
* Socket to use on svcxxx_create call to get default socket

View File

@ -39,6 +39,7 @@
#define _RPC_SVC_AUTH_H 1
#include <features.h>
#include <rpc/svc.h>
__BEGIN_DECLS

View File

@ -35,13 +35,21 @@
#ifndef __TYPES_RPC_HEADER__
#define __TYPES_RPC_HEADER__
#define bool_t int
#define enum_t int
#define FALSE (0)
#define TRUE (1)
#define __dontcare__ -1
typedef int bool_t;
typedef int enum_t;
#define __dontcare__ -1
#ifndef FALSE
# define FALSE (0)
#endif
#ifndef TRUE
# define TRUE (1)
#endif
#ifndef NULL
# define NULL 0
# define NULL 0
#endif
#include <stdlib.h> /* For malloc decl. */

View File

@ -54,10 +54,10 @@ __BEGIN_DECLS
*
* Each data type provides a single procedure which takes two arguments:
*
* bool_t
* xdrproc(xdrs, argresp)
* XDR *xdrs;
* <type> *argresp;
* 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
@ -80,11 +80,12 @@ __BEGIN_DECLS
* 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
};
enum xdr_op
{
XDR_ENCODE = 0,
XDR_DECODE = 1,
XDR_FREE = 2
};
/*
* This is the number of bytes per unit of external data.
@ -99,23 +100,36 @@ enum xdr_op {
* 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 {
enum xdr_op x_op; /* operation; fast additional param */
struct xdr_ops {
bool_t (*x_getlong)(); /* get a long from underlying stream */
bool_t (*x_putlong)(); /* put a long to " */
bool_t (*x_getbytes)();/* get some bytes from " */
bool_t (*x_putbytes)();/* put some bytes to " */
u_int (*x_getpostn)();/* returns bytes off from beginning */
bool_t (*x_setpostn)();/* lets you reposition the stream */
long * (*x_inline)(); /* buf quick ptr to buffered data */
void (*x_destroy)(); /* free privates of this xdr_stream */
} *x_ops;
caddr_t x_public; /* users' data */
caddr_t x_private; /* pointer to private data */
caddr_t x_base; /* private used for position info */
int x_handy; /* extra private word */
} XDR;
typedef struct XDR XDR;
struct XDR
{
enum xdr_op x_op; /* operation; fast additional param */
const struct xdr_ops
{
bool_t (*x_getlong) __P ((XDR * __xdrs, long *__lp));
/* get a long from underlying stream */
bool_t (*x_putlong) __P ((XDR * __xdrs, long *__lp));
/* put a long to " */
bool_t (*x_getbytes) __P ((XDR * __xdrs, caddr_t __addr, u_int __len));
/* get some bytes from " */
bool_t (*x_putbytes) __P ((XDR * __xdrs, __const caddr_t __addr,
u_int __len));
/* put some bytes to " */
u_int (*x_getpostn) __P ((XDR * __xdrs));
/* returns bytes off from beginning */
bool_t (*x_setpostn) __P ((XDR * __xdrs, u_int pos));
/* lets you reposition the stream */
long *(*x_inline) __P ((XDR * __xdrs, int len));
/* buf quick ptr to buffered data */
void (*x_destroy) __P ((XDR * __xdrs));
/* free privates of this xdr_stream */
}
*x_ops;
caddr_t x_public; /* users' data */
caddr_t x_private; /* pointer to private data */
caddr_t x_base; /* private used for position info */
int x_handy; /* extra private word */
};
/*
* A xdrproc_t exists for each data type which is to be encoded or decoded.
@ -124,18 +138,19 @@ typedef struct {
* 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.
* bool_t (*xdrproc_t)(XDR *, caddr_t *);
* bool_t (*xdrproc_t)(XDR *, caddr_t *);
*/
typedef bool_t (*xdrproc_t) __P ((XDR *, void *, ...));
typedef
bool_t (*xdrproc_t) __P ((XDR *, void *,...));
/*
* Operations defined on a XDR handle
*
* XDR *xdrs;
* long *longp;
* caddr_t addr;
* u_int len;
* u_int pos;
* 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)
@ -190,9 +205,10 @@ typedef bool_t (*xdrproc_t) __P ((XDR *, void *, ...));
* 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;
struct xdr_discrim
{
int value;
xdrproc_t proc;
};
/*
@ -201,9 +217,9 @@ struct xdr_discrim {
* 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 >>>
* 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.
*
@ -228,48 +244,49 @@ struct xdr_discrim {
/*
* These are the "generic" xdr routines.
*/
extern bool_t xdr_void ();
extern bool_t xdr_int __P ((XDR *__xdrs, int *__ip));
extern bool_t xdr_u_int __P ((XDR *__xdrs, u_int *__up));
extern bool_t xdr_long __P ((XDR *__xdrs, long *__lp));
extern bool_t xdr_u_long __P ((XDR *__xdrs, u_long *__ulp));
extern bool_t xdr_short __P ((XDR *__xdrs, short *__sp));
extern bool_t xdr_u_short __P ((XDR *__xdrs, u_short *__usp));
extern bool_t xdr_bool __P ((XDR *__xdrs, bool_t *__bp));
extern bool_t xdr_enum __P ((XDR *__xdrs, enum_t *__ep));
extern bool_t xdr_array __P ((XDR *_xdrs, caddr_t *__addrp, u_int *__sizep,
u_int __maxsize, u_int __elsize,
xdrproc_t __elproc));
extern bool_t xdr_bytes __P ((XDR *__xdrs, char **__cpp, u_int *__sizep,
u_int __maxsize));
extern bool_t xdr_opaque __P ((XDR *__xdrs, caddr_t __cp, u_int __cnt));
extern bool_t xdr_string __P ((XDR *__xdrs, char **__cpp, u_int __maxsize));
extern bool_t xdr_union __P ((XDR *__xdrs, enum_t *__dscmp, char *__unp,
struct xdr_discrim *__choices,
xdrproc_t dfault));
extern bool_t xdr_char __P ((XDR *__xdrs, char *__cp));
extern bool_t xdr_u_char __P ((XDR *__xdrs, u_char *__cp));
extern bool_t xdr_vector __P ((XDR *__xdrs, char *__basep, u_int __nelem,
u_int __elemsize, xdrproc_t __xdr_elem));
extern bool_t xdr_float __P ((XDR *__xdrs, float *__fp));
extern bool_t xdr_double __P ((XDR *__xdrs, double *__dp));
extern bool_t xdr_reference __P ((XDR *__xdrs, caddr_t *__pp, u_int __size,
xdrproc_t __proc));
extern bool_t xdr_pointer __P ((XDR *__xdrs, char **__objpp,
u_int __obj_size, xdrproc_t __xdr_obj));
extern bool_t xdr_wrapstring __P ((XDR *__xdrs, char **__cpp));
extern bool_t xdr_void __P ((void));
extern bool_t xdr_int __P ((XDR * __xdrs, int *__ip));
extern bool_t xdr_u_int __P ((XDR * __xdrs, u_int * __up));
extern bool_t xdr_long __P ((XDR * __xdrs, long *__lp));
extern bool_t xdr_u_long __P ((XDR * __xdrs, u_long * __ulp));
extern bool_t xdr_short __P ((XDR * __xdrs, short *__sp));
extern bool_t xdr_u_short __P ((XDR * __xdrs, u_short * __usp));
extern bool_t xdr_bool __P ((XDR * __xdrs, bool_t * __bp));
extern bool_t xdr_enum __P ((XDR * __xdrs, enum_t * __ep));
extern bool_t xdr_array __P ((XDR * _xdrs, caddr_t * __addrp, u_int * __sizep,
u_int __maxsize, u_int __elsize,
xdrproc_t __elproc));
extern bool_t xdr_bytes __P ((XDR * __xdrs, char **__cpp, u_int * __sizep,
u_int __maxsize));
extern bool_t xdr_opaque __P ((XDR * __xdrs, caddr_t __cp, u_int __cnt));
extern bool_t xdr_string __P ((XDR * __xdrs, char **__cpp, u_int __maxsize));
extern bool_t xdr_union __P ((XDR * __xdrs, enum_t * __dscmp, char *__unp,
__const struct xdr_discrim * __choices,
xdrproc_t dfault));
extern bool_t xdr_char __P ((XDR * __xdrs, char *__cp));
extern bool_t xdr_u_char __P ((XDR * __xdrs, u_char * __cp));
extern bool_t xdr_vector __P ((XDR * __xdrs, char *__basep, u_int __nelem,
u_int __elemsize, xdrproc_t __xdr_elem));
extern bool_t xdr_float __P ((XDR * __xdrs, float *__fp));
extern bool_t xdr_double __P ((XDR * __xdrs, double *__dp));
extern bool_t xdr_reference __P ((XDR * __xdrs, caddr_t * __pp, u_int __size,
xdrproc_t __proc));
extern bool_t xdr_pointer __P ((XDR * __xdrs, char **__objpp,
u_int __obj_size, xdrproc_t __xdr_obj));
extern bool_t xdr_wrapstring __P ((XDR * __xdrs, char **__cpp));
/*
* 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;
struct netobj
{
u_int n_len;
char *n_bytes;
};
typedef struct netobj netobj;
extern bool_t xdr_netobj __P ((XDR *__xdrs, struct netobj *__np));
extern bool_t xdr_netobj __P ((XDR * __xdrs, struct netobj * __np));
/*
* These are the public routines for the various implementations of
@ -277,26 +294,27 @@ extern bool_t xdr_netobj __P ((XDR *__xdrs, struct netobj *__np));
*/
/* XDR using memory buffers */
extern void xdrmem_create __P ((XDR *__xdrs, caddr_t __addr, u_int __size,
enum xdr_op __op));
extern void xdrmem_create __P ((XDR * __xdrs, caddr_t __addr, u_int __size,
enum xdr_op __op));
/* XDR using stdio library */
extern void xdrstdio_create __P ((XDR *__xdrs, FILE *__file,
enum xdr_op __op));
extern void xdrstdio_create __P ((XDR * __xdrs, FILE * __file,
enum xdr_op __op));
/* XDR pseudo records for tcp */
extern void xdrrec_create __P ((XDR *__xdrs, u_int __sendsize,
u_int __recvsize, caddr_t __tcp_handle,
int (*__readit) (), int (*__writeit) ()));
extern void xdrrec_create __P ((XDR * __xdrs, u_int __sendsize,
u_int __recvsize, caddr_t __tcp_handle,
int (*__readit) (char *, char *, int),
int (*__writeit) (char *, char *, int)));
/* make end of xdr record */
extern bool_t xdrrec_endofrecord __P ((XDR *__xdrs, bool_t __sendnow));
extern bool_t xdrrec_endofrecord __P ((XDR * __xdrs, bool_t __sendnow));
/* move to beginning of next record */
extern bool_t xdrrec_skiprecord __P ((XDR *__xdrs));
extern bool_t xdrrec_skiprecord __P ((XDR * __xdrs));
/* true if no more input */
extern bool_t xdrrec_eof __P ((XDR *__xdrs));
extern bool_t xdrrec_eof __P ((XDR * __xdrs));
/* free memory buffers for xdr */
extern void xdr_free __P ((xdrproc_t __proc, char *__objp));

View File

@ -31,7 +31,7 @@
/*
* From: @(#)rpc_clntout.c 1.11 89/02/22 (C) 1987 SMI
*/
char clntout_rcsid[] =
char clntout_rcsid[] =
"$Id$";
/*
@ -46,121 +46,141 @@ char clntout_rcsid[] =
#include "proto.h"
#define DEFAULT_TIMEOUT 25 /* in seconds */
static char RESULT[] = "clnt_res";
static const char RESULT[] = "clnt_res";
static void write_program(definition *def);
static void printbody(proc_list *proc);
static const char *ampr(const char *type);
static void printbody(proc_list *proc);
static void write_program (definition * def);
static void printbody (proc_list * proc);
static const char *ampr (const char *type);
static void printbody (proc_list * proc);
void
write_stubs(void)
write_stubs (void)
{
list *l;
definition *def;
list *l;
definition *def;
f_print(fout,
"\n/* Default timeout can be changed using clnt_control() */\n");
f_print(fout, "static struct timeval TIMEOUT = { %d, 0 };\n",
DEFAULT_TIMEOUT);
for (l = defined; l != NULL; l = l->next) {
def = (definition *) l->val;
if (def->def_kind == DEF_PROGRAM) {
write_program(def);
}
f_print (fout,
"\n/* Default timeout can be changed using clnt_control() */\n");
f_print (fout, "static struct timeval TIMEOUT = { %d, 0 };\n",
DEFAULT_TIMEOUT);
for (l = defined; l != NULL; l = l->next)
{
def = (definition *) l->val;
if (def->def_kind == DEF_PROGRAM)
{
write_program (def);
}
}
}
static void
write_program(definition *def)
write_program (definition * def)
{
version_list *vp;
proc_list *proc;
version_list *vp;
proc_list *proc;
for (vp = def->def.pr.versions; vp != NULL; vp = vp->next) {
for (proc = vp->procs; proc != NULL; proc = proc->next) {
f_print(fout, "\n");
ptype(proc->res_prefix, proc->res_type, 1);
f_print(fout, "*\n");
pvname(proc->proc_name, vp->vers_num);
printarglist( proc, "clnt", "CLIENT *" );
f_print(fout, "{\n");
printbody(proc);
f_print(fout, "}\n");
}
for (vp = def->def.pr.versions; vp != NULL; vp = vp->next)
{
for (proc = vp->procs; proc != NULL; proc = proc->next)
{
f_print (fout, "\n");
ptype (proc->res_prefix, proc->res_type, 1);
f_print (fout, "*\n");
pvname (proc->proc_name, vp->vers_num);
printarglist (proc, "clnt", "CLIENT *");
f_print (fout, "{\n");
printbody (proc);
f_print (fout, "}\n");
}
}
}
/* Writes out declarations of procedure's argument list.
In either ANSI C style, in one of old rpcgen style (pass by reference),
or new rpcgen style (multiple arguments, pass by value);
*/
*/
/* sample addargname = "clnt"; sample addargtype = "CLIENT * " */
void printarglist(proc_list *proc,
const char *addargname, const char *addargtype)
void
printarglist (proc_list * proc,
const char *addargname, const char *addargtype)
{
decl_list *l;
if (!newstyle) { /* old style: always pass argument by reference */
if (Cflag) { /* C++ style heading */
f_print(fout, "(");
ptype(proc->args.decls->decl.prefix, proc->args.decls->decl.type, 1);
f_print(fout, "*argp, %s%s)\n", addargtype, addargname );
if (!newstyle)
{ /* old style: always pass argument by reference */
if (Cflag)
{ /* C++ style heading */
f_print (fout, "(");
ptype (proc->args.decls->decl.prefix, proc->args.decls->decl.type, 1);
f_print (fout, "*argp, %s%s)\n", addargtype, addargname);
}
else
{
f_print (fout, "(argp, %s)\n", addargname);
f_print (fout, "\t");
ptype (proc->args.decls->decl.prefix, proc->args.decls->decl.type, 1);
f_print (fout, "*argp;\n");
}
}
else {
f_print(fout, "(argp, %s)\n", addargname);
f_print(fout, "\t");
ptype(proc->args.decls->decl.prefix, proc->args.decls->decl.type, 1);
f_print(fout, "*argp;\n");
else if (streq (proc->args.decls->decl.type, "void"))
{
/* newstyle, 0 argument */
if (Cflag)
f_print (fout, "(%s%s)\n", addargtype, addargname);
else
f_print (fout, "(%s)\n", addargname);
}
} else if (streq( proc->args.decls->decl.type, "void")) {
/* newstyle, 0 argument */
if( Cflag )
f_print(fout, "(%s%s)\n", addargtype, addargname );
else
f_print(fout, "(%s)\n", addargname);
} else {
/* new style, 1 or multiple arguments */
if( !Cflag ) {
f_print(fout, "(");
for (l = proc->args.decls; l != NULL; l = l->next)
f_print(fout, "%s, ", l->decl.name);
f_print(fout, "%s)\n", addargname );
for (l = proc->args.decls; l != NULL; l = l->next) {
pdeclaration(proc->args.argname, &l->decl, 1, ";\n" );
}
} else { /* C++ style header */
f_print(fout, "(");
for(l = proc->args.decls; l != NULL; l = l->next) {
pdeclaration(proc->args.argname, &l->decl, 0, ", " );
}
f_print(fout, " %s%s)\n", addargtype, addargname );
else
{
/* new style, 1 or multiple arguments */
if (!Cflag)
{
f_print (fout, "(");
for (l = proc->args.decls; l != NULL; l = l->next)
f_print (fout, "%s, ", l->decl.name);
f_print (fout, "%s)\n", addargname);
for (l = proc->args.decls; l != NULL; l = l->next)
{
pdeclaration (proc->args.argname, &l->decl, 1, ";\n");
}
}
else
{ /* C++ style header */
f_print (fout, "(");
for (l = proc->args.decls; l != NULL; l = l->next)
{
pdeclaration (proc->args.argname, &l->decl, 0, ", ");
}
f_print (fout, " %s%s)\n", addargtype, addargname);
}
}
}
if( !Cflag )
f_print(fout, "\t%s%s;\n", addargtype, addargname );
if (!Cflag)
f_print (fout, "\t%s%s;\n", addargtype, addargname);
}
static
const char *
ampr(const char *type)
ampr (const char *type)
{
if (isvectordef(type, REL_ALIAS)) {
return ("");
} else {
return ("&");
}
if (isvectordef (type, REL_ALIAS))
{
return "";
}
else
{
return "&";
}
}
static void
printbody(proc_list *proc)
printbody (proc_list * proc)
{
decl_list *l;
bool_t args2 = (proc->arg_num > 1);
@ -168,55 +188,68 @@ printbody(proc_list *proc)
/* For new style with multiple arguments, need a structure in which
to stuff the arguments. */
if ( newstyle && args2) {
f_print(fout, "\t%s", proc->args.argname);
f_print(fout, " arg;\n");
}
f_print(fout, "\tstatic ");
if (streq(proc->res_type, "void")) {
f_print(fout, "char ");
} else {
ptype(proc->res_prefix, proc->res_type, 0);
}
f_print(fout, "%s;\n",RESULT);
f_print(fout, "\n");
f_print(fout, "\tmemset((char *)%s%s, 0, sizeof(%s));\n",
ampr(proc->res_type ), RESULT, RESULT);
if (newstyle && !args2 && (streq( proc->args.decls->decl.type, "void"))) {
/* newstyle, 0 arguments */
f_print(fout,
"\tif (clnt_call(clnt, %s, xdr_void", proc->proc_name);
f_print(fout,
", NULL, xdr_%s, %s,%s, TIMEOUT) != RPC_SUCCESS) {\n",
stringfix(proc->res_type), ampr(proc->res_type), RESULT);
if (newstyle && args2)
{
f_print (fout, "\t%s", proc->args.argname);
f_print (fout, " arg;\n");
}
f_print (fout, "\tstatic ");
if (streq (proc->res_type, "void"))
{
f_print (fout, "char ");
}
else
{
ptype (proc->res_prefix, proc->res_type, 0);
}
f_print (fout, "%s;\n", RESULT);
f_print (fout, "\n");
f_print (fout, "\tmemset((char *)%s%s, 0, sizeof(%s));\n",
ampr (proc->res_type), RESULT, RESULT);
if (newstyle && !args2 && (streq (proc->args.decls->decl.type, "void")))
{
/* newstyle, 0 arguments */
f_print (fout,
"\tif (clnt_call(clnt, %s, xdr_void", proc->proc_name);
f_print (fout,
", NULL, xdr_%s, %s,%s, TIMEOUT) != RPC_SUCCESS) {\n",
stringfix (proc->res_type), ampr (proc->res_type), RESULT);
} else if ( newstyle && args2) {
/* newstyle, multiple arguments: stuff arguments into structure */
for (l = proc->args.decls; l != NULL; l = l->next) {
f_print(fout, "\targ.%s = %s;\n",
l->decl.name, l->decl.name);
}
f_print(fout,
"\tif (clnt_call(clnt, %s, xdr_%s", proc->proc_name,
proc->args.argname);
f_print(fout,
", &arg, xdr_%s, %s%s, TIMEOUT) != RPC_SUCCESS) {\n",
stringfix(proc->res_type), ampr(proc->res_type), RESULT);
} else { /* single argument, new or old style */
f_print(fout,
"\tif (clnt_call(clnt, %s, xdr_%s, %s%s, xdr_%s, %s%s, TIMEOUT) != RPC_SUCCESS) {\n",
proc->proc_name,
stringfix(proc->args.decls->decl.type),
(newstyle ? "&" : ""),
(newstyle ? proc->args.decls->decl.name : "argp"),
stringfix(proc->res_type), ampr(proc->res_type),RESULT);
}
f_print(fout, "\t\treturn (NULL);\n");
f_print(fout, "\t}\n");
if (streq(proc->res_type, "void")) {
f_print(fout, "\treturn ((void *)%s%s);\n",
ampr(proc->res_type),RESULT);
} else {
f_print(fout, "\treturn (%s%s);\n", ampr(proc->res_type),RESULT);
}
else if (newstyle && args2)
{
/* newstyle, multiple arguments: stuff arguments into structure */
for (l = proc->args.decls; l != NULL; l = l->next)
{
f_print (fout, "\targ.%s = %s;\n",
l->decl.name, l->decl.name);
}
f_print (fout,
"\tif (clnt_call(clnt, %s, xdr_%s", proc->proc_name,
proc->args.argname);
f_print (fout,
", &arg, xdr_%s, %s%s, TIMEOUT) != RPC_SUCCESS) {\n",
stringfix (proc->res_type), ampr (proc->res_type), RESULT);
}
else
{ /* single argument, new or old style */
f_print (fout,
"\tif (clnt_call(clnt, %s, xdr_%s, %s%s, xdr_%s, %s%s, TIMEOUT) != RPC_SUCCESS) {\n",
proc->proc_name,
stringfix (proc->args.decls->decl.type),
(newstyle ? "&" : ""),
(newstyle ? proc->args.decls->decl.name : "argp"),
stringfix (proc->res_type), ampr (proc->res_type), RESULT);
}
f_print (fout, "\t\treturn (NULL);\n");
f_print (fout, "\t}\n");
if (streq (proc->res_type, "void"))
{
f_print (fout, "\treturn ((void *)%s%s);\n",
ampr (proc->res_type), RESULT);
}
else
{
f_print (fout, "\treturn (%s%s);\n", ampr (proc->res_type), RESULT);
}
}

View File

@ -6,23 +6,23 @@
* 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
@ -38,153 +38,182 @@ static char sccsid[] = "@(#)rpc_callmsg.c 1.4 87/08/11 Copyr 1984 Sun Micro";
*
*/
#include <string.h>
#include <sys/param.h>
#include <rpc/rpc.h>
extern bool_t xdr_opaque_auth (XDR *, struct opaque_auth *);
/*
* XDR a call message
*/
bool_t
xdr_callmsg(xdrs, cmsg)
register XDR *xdrs;
register struct rpc_msg *cmsg;
xdr_callmsg (XDR *xdrs, struct rpc_msg *cmsg)
{
register long *buf;
register struct opaque_auth *oa;
long *buf;
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)
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) {
bcopy(oa->oa_base, (caddr_t)buf, oa->oa_length);
buf = (long *) ((char *) buf + RNDUP(oa->oa_length));
}
oa = &cmsg->rm_call.cb_verf;
IXDR_PUT_ENUM(buf, oa->oa_flavor);
IXDR_PUT_LONG(buf, oa->oa_length);
if (oa->oa_length) {
bcopy(oa->oa_base, (caddr_t)buf, oa->oa_length);
/* no real need....
buf = (long *) ((char *) buf + RNDUP(oa->oa_length));
*/
}
return (TRUE);
}
+ 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)
{
bcopy (oa->oa_base, (caddr_t) buf, oa->oa_length);
buf = (long *) ((char *) buf + RNDUP (oa->oa_length));
}
oa = &cmsg->rm_call.cb_verf;
IXDR_PUT_ENUM (buf, oa->oa_flavor);
IXDR_PUT_LONG (buf, oa->oa_length);
if (oa->oa_length)
{
bcopy (oa->oa_base, (caddr_t) buf, oa->oa_length);
/* no real need....
buf = (long *) ((char *) buf + RNDUP(oa->oa_length));
*/
}
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 {
bcopy((caddr_t)buf, oa->oa_base,
oa->oa_length);
/* no real need....
buf = (long *) ((char *) buf
+ RNDUP(oa->oa_length));
*/
}
}
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 {
bcopy((caddr_t)buf, oa->oa_base,
oa->oa_length);
/* no real need...
buf = (long *) ((char *) buf
+ RNDUP(oa->oa_length));
*/
}
}
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
{
bcopy ((caddr_t) buf, oa->oa_base,
oa->oa_length);
/* no real need....
buf = (long *) ((char *) buf
+ RNDUP(oa->oa_length));
*/
}
}
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
{
bcopy ((caddr_t) buf, oa->oa_base,
oa->oa_length);
/* no real need...
buf = (long *) ((char *) buf
+ RNDUP(oa->oa_length));
*/
}
}
return TRUE;
}
if (
xdr_u_long(xdrs, &(cmsg->rm_xid)) &&
xdr_enum(xdrs, (enum_t *)&(cmsg->rm_direction)) &&
(cmsg->rm_direction == CALL) &&
xdr_u_long(xdrs, &(cmsg->rm_call.cb_rpcvers)) &&
(cmsg->rm_call.cb_rpcvers == RPC_MSG_VERSION) &&
xdr_u_long(xdrs, &(cmsg->rm_call.cb_prog)) &&
xdr_u_long(xdrs, &(cmsg->rm_call.cb_vers)) &&
xdr_u_long(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);
}
if (
xdr_u_long (xdrs, &(cmsg->rm_xid)) &&
xdr_enum (xdrs, (enum_t *) & (cmsg->rm_direction)) &&
(cmsg->rm_direction == CALL) &&
xdr_u_long (xdrs, &(cmsg->rm_call.cb_rpcvers)) &&
(cmsg->rm_call.cb_rpcvers == RPC_MSG_VERSION) &&
xdr_u_long (xdrs, &(cmsg->rm_call.cb_prog)) &&
xdr_u_long (xdrs, &(cmsg->rm_call.cb_vers)) &&
xdr_u_long (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;
}

View File

@ -31,16 +31,19 @@
static char sccsid[] = "@(#)rpc_dtablesize.c 1.2 87/08/11 Copyr 1987 Sun Micro";
#endif
#include <unistd.h>
/*
* Cache the result of getdtablesize(), so we don't have to do an
* expensive system call every time.
*/
_rpc_dtablesize()
int
_rpc_dtablesize (void)
{
static int size;
if (size == 0) {
size = getdtablesize();
}
return (size);
static int size;
if (size == 0)
size = getdtablesize ();
return size;
}

View File

@ -55,26 +55,22 @@ static char sccsid[] = "@(#)rpc_prot.c 1.36 87/08/11 Copyr 1984 Sun Micro";
* (see auth.h)
*/
bool_t
xdr_opaque_auth(xdrs, ap)
register XDR *xdrs;
register struct opaque_auth *ap;
xdr_opaque_auth (XDR *xdrs, struct opaque_auth *ap)
{
if (xdr_enum(xdrs, &(ap->oa_flavor)))
return (xdr_bytes(xdrs, &ap->oa_base,
&ap->oa_length, MAX_AUTH_BYTES));
return (FALSE);
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(xdrs, blkp)
register XDR *xdrs;
register des_block *blkp;
xdr_des_block (XDR *xdrs, des_block *blkp)
{
return (xdr_opaque(xdrs, (caddr_t)blkp, sizeof(des_block)));
return xdr_opaque (xdrs, (caddr_t) blkp, sizeof (des_block));
}
/* * * * * * * * * * * * * * XDR RPC MESSAGE * * * * * * * * * * * * * * * */
@ -83,74 +79,70 @@ xdr_des_block(xdrs, blkp)
* XDR the MSG_ACCEPTED part of a reply message union
*/
bool_t
xdr_accepted_reply(xdrs, ar)
register XDR *xdrs;
register struct accepted_reply *ar;
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 *)&(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_long(xdrs, &(ar->ar_vers.low)))
return (FALSE);
return (xdr_u_long(xdrs, &(ar->ar_vers.high)));
}
return (TRUE); /* TRUE => open ended set of problems */
/* personalized union, rather than calling xdr_union */
if (!xdr_opaque_auth (xdrs, &(ar->ar_verf)))
return FALSE;
if (!xdr_enum (xdrs, (enum_t *) & (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_long (xdrs, &(ar->ar_vers.low)))
return FALSE;
return (xdr_u_long (xdrs, &(ar->ar_vers.high)));
default:
return TRUE;
}
return TRUE; /* TRUE => open ended set of problems */
}
/*
* XDR the MSG_DENIED part of a reply message union
*/
bool_t
xdr_rejected_reply(xdrs, rr)
register XDR *xdrs;
register struct rejected_reply *rr;
xdr_rejected_reply (XDR *xdrs, struct rejected_reply *rr)
{
/* personalized union, rather than calling xdr_union */
if (!xdr_enum (xdrs, (enum_t *) & (rr->rj_stat)))
return FALSE;
switch (rr->rj_stat)
{
case RPC_MISMATCH:
if (!xdr_u_long (xdrs, &(rr->rj_vers.low)))
return FALSE;
return xdr_u_long (xdrs, &(rr->rj_vers.high));
/* personalized union, rather than calling xdr_union */
if (! xdr_enum(xdrs, (enum_t *)&(rr->rj_stat)))
return (FALSE);
switch (rr->rj_stat) {
case RPC_MISMATCH:
if (! xdr_u_long(xdrs, &(rr->rj_vers.low)))
return (FALSE);
return (xdr_u_long(xdrs, &(rr->rj_vers.high)));
case AUTH_ERROR:
return (xdr_enum(xdrs, (enum_t *)&(rr->rj_why)));
}
return (FALSE);
case AUTH_ERROR:
return xdr_enum (xdrs, (enum_t *) & (rr->rj_why));
}
return FALSE;
}
static struct xdr_discrim reply_dscrm[3] = {
{ (int)MSG_ACCEPTED, xdr_accepted_reply },
{ (int)MSG_DENIED, xdr_rejected_reply },
{ __dontcare__, NULL_xdrproc_t } };
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(xdrs, rmsg)
register XDR *xdrs;
register struct rpc_msg *rmsg;
xdr_replymsg (xdrs, rmsg)
XDR *xdrs;
struct rpc_msg *rmsg;
{
if (
xdr_u_long(xdrs, &(rmsg->rm_xid)) &&
xdr_enum(xdrs, (enum_t *)&(rmsg->rm_direction)) &&
(rmsg->rm_direction == REPLY) )
return (xdr_union(xdrs, (enum_t *)&(rmsg->rm_reply.rp_stat),
(caddr_t)&(rmsg->rm_reply.ru), reply_dscrm, NULL_xdrproc_t));
return (FALSE);
if (xdr_u_long (xdrs, &(rmsg->rm_xid)) &&
xdr_enum (xdrs, (enum_t *) & (rmsg->rm_direction)) &&
(rmsg->rm_direction == REPLY))
return xdr_union (xdrs, (enum_t *) & (rmsg->rm_reply.rp_stat),
(caddr_t) & (rmsg->rm_reply.ru), reply_dscrm,
NULL_xdrproc_t);
return FALSE;
}
@ -160,128 +152,128 @@ xdr_replymsg(xdrs, rmsg)
* The rm_xid is not really static, but the user can easily munge on the fly.
*/
bool_t
xdr_callhdr(xdrs, cmsg)
register XDR *xdrs;
register struct rpc_msg *cmsg;
xdr_callhdr (xdrs, cmsg)
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_long(xdrs, &(cmsg->rm_xid)) &&
xdr_enum(xdrs, (enum_t *)&(cmsg->rm_direction)) &&
xdr_u_long(xdrs, &(cmsg->rm_call.cb_rpcvers)) &&
xdr_u_long(xdrs, &(cmsg->rm_call.cb_prog)) )
return (xdr_u_long(xdrs, &(cmsg->rm_call.cb_vers)));
return (FALSE);
cmsg->rm_direction = CALL;
cmsg->rm_call.cb_rpcvers = RPC_MSG_VERSION;
if (
(xdrs->x_op == XDR_ENCODE) &&
xdr_u_long (xdrs, &(cmsg->rm_xid)) &&
xdr_enum (xdrs, (enum_t *) & (cmsg->rm_direction)) &&
xdr_u_long (xdrs, &(cmsg->rm_call.cb_rpcvers)) &&
xdr_u_long (xdrs, &(cmsg->rm_call.cb_prog)))
return xdr_u_long (xdrs, &(cmsg->rm_call.cb_vers));
return FALSE;
}
/* ************************** Client utility routine ************* */
static void
accepted(acpt_stat, error)
register enum accept_stat acpt_stat;
register struct rpc_err *error;
accepted (enum accept_stat acpt_stat,
struct rpc_err *error)
{
switch (acpt_stat)
{
switch (acpt_stat) {
case PROG_UNAVAIL:
error->re_status = RPC_PROGUNAVAIL;
return;
case PROG_UNAVAIL:
error->re_status = RPC_PROGUNAVAIL;
return;
case PROG_MISMATCH:
error->re_status = RPC_PROGVERSMISMATCH;
return;
case PROG_MISMATCH:
error->re_status = RPC_PROGVERSMISMATCH;
return;
case PROC_UNAVAIL:
error->re_status = RPC_PROCUNAVAIL;
return;
case PROC_UNAVAIL:
error->re_status = RPC_PROCUNAVAIL;
return;
case GARBAGE_ARGS:
error->re_status = RPC_CANTDECODEARGS;
return;
case GARBAGE_ARGS:
error->re_status = RPC_CANTDECODEARGS;
return;
case SYSTEM_ERR:
error->re_status = RPC_SYSTEMERROR;
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 = (long)MSG_ACCEPTED;
error->re_lb.s2 = (long)acpt_stat;
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 = (long) MSG_ACCEPTED;
error->re_lb.s2 = (long) acpt_stat;
}
static void
rejected(rjct_stat, error)
register enum reject_stat rjct_stat;
register struct rpc_err *error;
rejected (enum reject_stat rjct_stat,
struct rpc_err *error)
{
switch (rjct_stat) {
case RPC_VERSMISMATCH:
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 = (long)MSG_DENIED;
error->re_lb.s2 = (long)rjct_stat;
switch (rjct_stat)
{
case RPC_VERSMISMATCH:
error->re_status = RPC_VERSMISMATCH;
return;
case AUTH_ERROR:
error->re_status = RPC_AUTHERROR;
return;
default:
/* something's wrong, but we don't know what ... */
error->re_status = RPC_FAILED;
error->re_lb.s1 = (long) MSG_DENIED;
error->re_lb.s2 = (long) rjct_stat;
return;
}
}
/*
* given a reply message, fills in the error
*/
void
_seterr_reply(msg, error)
register struct rpc_msg *msg;
register struct rpc_err *error;
_seterr_reply (struct rpc_msg *msg,
struct rpc_err *error)
{
/* 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;
/* optimized for normal, SUCCESSful case */
switch (msg->rm_reply.rp_stat) {
case MSG_DENIED:
rejected (msg->rjcted_rply.rj_stat, error);
break;
case MSG_ACCEPTED:
if (msg->acpted_rply.ar_stat == SUCCESS) {
error->re_status = RPC_SUCCESS;
return;
};
accepted(msg->acpted_rply.ar_stat, error);
break;
default:
error->re_status = RPC_FAILED;
error->re_lb.s1 = (long) (msg->rm_reply.rp_stat);
break;
}
switch (error->re_status)
{
case MSG_DENIED:
rejected(msg->rjcted_rply.rj_stat, error);
break;
case RPC_VERSMISMATCH:
error->re_vers.low = msg->rjcted_rply.rj_vers.low;
error->re_vers.high = msg->rjcted_rply.rj_vers.high;
break;
default:
error->re_status = RPC_FAILED;
error->re_lb.s1 = (long)(msg->rm_reply.rp_stat);
break;
}
switch (error->re_status) {
case RPC_AUTHERROR:
error->re_why = msg->rjcted_rply.rj_why;
break;
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_PROGVERSMISMATCH:
error->re_vers.low = msg->acpted_rply.ar_vers.low;
error->re_vers.high = msg->acpted_rply.ar_vers.high;
break;
default:
break;
}
}

View File

@ -28,10 +28,10 @@
* Mountain View, California 94043
*/
/*
/*
* From: @(#)rpc_sample.c 1.1 90/08/30 (C) 1987 SMI
*/
char sample_rcsid[] =
char sample_rcsid[] =
"$Id$";
/*
@ -45,209 +45,226 @@ char sample_rcsid[] =
#include "proto.h"
static char RQSTP[] = "rqstp";
static const char RQSTP[] = "rqstp";
static void write_sample_client(const char *program_name, version_list *vp);
static void write_sample_server(definition *def);
static void return_type(proc_list *plist);
static void write_sample_client (const char *program_name, version_list * vp);
static void write_sample_server (definition * def);
static void return_type (proc_list * plist);
void
write_sample_svc(definition *def)
write_sample_svc (definition * def)
{
if (def->def_kind != DEF_PROGRAM)
return;
write_sample_server(def);
if (def->def_kind != DEF_PROGRAM)
return;
write_sample_server (def);
}
int
write_sample_clnt(definition *def)
write_sample_clnt (definition * def)
{
version_list *vp;
int count = 0;
version_list *vp;
int count = 0;
if (def->def_kind != DEF_PROGRAM)
return( 0 );
/* generate sample code for each version */
for (vp = def->def.pr.versions; vp != NULL; vp = vp->next) {
write_sample_client(def->def_name, vp );
++count;
}
return( count );
if (def->def_kind != DEF_PROGRAM)
return (0);
/* generate sample code for each version */
for (vp = def->def.pr.versions; vp != NULL; vp = vp->next)
{
write_sample_client (def->def_name, vp);
++count;
}
return (count);
}
static void
write_sample_client(const char *program_name, version_list *vp)
write_sample_client (const char *program_name, version_list * vp)
{
proc_list *proc;
int i;
decl_list *l;
f_print(fout, "\n\nvoid\n" );
pvname( program_name, vp->vers_num );
if( Cflag )
f_print(fout,"( char* host )\n{\n" );
f_print (fout, "\n\nvoid\n");
pvname (program_name, vp->vers_num);
if (Cflag)
f_print (fout, "( char* host )\n{\n");
else
f_print(fout, "(host)\nchar *host;\n{\n" );
f_print(fout, "\tCLIENT *clnt;\n");
f_print (fout, "(host)\nchar *host;\n{\n");
f_print (fout, "\tCLIENT *clnt;\n");
i = 0;
for (proc = vp->procs; proc != NULL; proc = proc->next) {
f_print(fout, "\t");
ptype(proc->res_prefix, proc->res_type, 1);
f_print(fout, " *result_%d;\n",++i);
for (proc = vp->procs; proc != NULL; proc = proc->next)
{
f_print (fout, "\t");
ptype (proc->res_prefix, proc->res_type, 1);
f_print (fout, " *result_%d;\n", ++i);
/* print out declarations for arguments */
if( proc->arg_num < 2 && !newstyle) {
f_print( fout, "\t" );
if( !streq( proc->args.decls->decl.type, "void") )
ptype(proc->args.decls->decl.prefix, proc->args.decls->decl.type, 1);
else
f_print(fout, "char* "); /* cannot have "void" type */
f_print(fout, " ");
pvname( proc->proc_name, vp->vers_num );
f_print(fout, "_arg;\n");
} else if (!streq( proc->args.decls->decl.type, "void")) {
for (l = proc->args.decls; l != NULL; l = l->next) {
f_print( fout, "\t" );
ptype(l->decl.prefix, l->decl.type, 1);
f_print( fout, " ");
pvname( proc->proc_name, vp->vers_num );
f_print(fout, "_%s;\n", l->decl.name );
/* pdeclaration(proc->args.argname, &l->decl, 1, ";\n" );*/
if (proc->arg_num < 2 && !newstyle)
{
f_print (fout, "\t");
if (!streq (proc->args.decls->decl.type, "void"))
ptype (proc->args.decls->decl.prefix, proc->args.decls->decl.type, 1);
else
f_print (fout, "char* "); /* cannot have "void" type */
f_print (fout, " ");
pvname (proc->proc_name, vp->vers_num);
f_print (fout, "_arg;\n");
}
else if (!streq (proc->args.decls->decl.type, "void"))
{
for (l = proc->args.decls; l != NULL; l = l->next)
{
f_print (fout, "\t");
ptype (l->decl.prefix, l->decl.type, 1);
f_print (fout, " ");
pvname (proc->proc_name, vp->vers_num);
f_print (fout, "_%s;\n", l->decl.name);
/* pdeclaration(proc->args.argname, &l->decl, 1, ";\n" ); */
}
}
}
}
/* generate creation of client handle */
f_print(fout, "\tclnt = clnt_create(host, %s, %s, \"%s\");\n",
program_name, vp->vers_name, tirpcflag? "netpath" : "udp");
f_print(fout, "\tif (clnt == NULL) {\n");
f_print(fout, "\t\tclnt_pcreateerror(host);\n");
f_print(fout, "\t\texit(1);\n\t}\n");
f_print (fout, "\tclnt = clnt_create(host, %s, %s, \"%s\");\n",
program_name, vp->vers_name, tirpcflag ? "netpath" : "udp");
f_print (fout, "\tif (clnt == NULL) {\n");
f_print (fout, "\t\tclnt_pcreateerror(host);\n");
f_print (fout, "\t\texit(1);\n\t}\n");
/* generate calls to procedures */
i = 0;
for (proc = vp->procs; proc != NULL; proc = proc->next) {
f_print(fout, "\tresult_%d = ",++i);
pvname(proc->proc_name, vp->vers_num);
if (proc->arg_num < 2 && !newstyle) {
f_print(fout, "(" );
if( streq( proc->args.decls->decl.type, "void") ) /* cast to void* */
f_print(fout, "(void*)");
f_print(fout, "&" );
pvname(proc->proc_name, vp->vers_num );
f_print(fout, "_arg, clnt);\n");
} else if (streq( proc->args.decls->decl.type, "void")) {
f_print(fout, "(clnt);\n");
}
else {
f_print(fout, "(");
for (l = proc->args.decls; l != NULL; l = l->next) {
pvname( proc->proc_name, vp->vers_num );
f_print(fout, "_%s, ", l->decl.name);
for (proc = vp->procs; proc != NULL; proc = proc->next)
{
f_print (fout, "\tresult_%d = ", ++i);
pvname (proc->proc_name, vp->vers_num);
if (proc->arg_num < 2 && !newstyle)
{
f_print (fout, "(");
if (streq (proc->args.decls->decl.type, "void")) /* cast to void* */
f_print (fout, "(void*)");
f_print (fout, "&");
pvname (proc->proc_name, vp->vers_num);
f_print (fout, "_arg, clnt);\n");
}
f_print(fout, "clnt);\n");
}
f_print(fout, "\tif (result_%d == NULL) {\n", i);
f_print(fout, "\t\tclnt_perror(clnt, \"call failed:\");\n");
f_print(fout, "\t}\n");
else if (streq (proc->args.decls->decl.type, "void"))
{
f_print (fout, "(clnt);\n");
}
else
{
f_print (fout, "(");
for (l = proc->args.decls; l != NULL; l = l->next)
{
pvname (proc->proc_name, vp->vers_num);
f_print (fout, "_%s, ", l->decl.name);
}
f_print (fout, "clnt);\n");
}
f_print (fout, "\tif (result_%d == NULL) {\n", i);
f_print (fout, "\t\tclnt_perror(clnt, \"call failed:\");\n");
f_print (fout, "\t}\n");
}
f_print(fout, "\tclnt_destroy( clnt );\n" );
f_print(fout, "}\n");
f_print (fout, "\tclnt_destroy( clnt );\n");
f_print (fout, "}\n");
}
static void
write_sample_server(definition *def)
write_sample_server (definition * def)
{
version_list *vp;
proc_list *proc;
version_list *vp;
proc_list *proc;
for (vp = def->def.pr.versions; vp != NULL; vp = vp->next) {
for (proc = vp->procs; proc != NULL; proc = proc->next) {
f_print(fout, "\n");
/* if( Cflag )
f_print( fout, "extern \"C\"{\n");
*/
return_type(proc);
f_print(fout, "* \n");
if( Cflag )
pvname_svc(proc->proc_name, vp->vers_num);
else
pvname(proc->proc_name, vp->vers_num);
printarglist( proc, RQSTP, "struct svc_req *" );
for (vp = def->def.pr.versions; vp != NULL; vp = vp->next)
{
for (proc = vp->procs; proc != NULL; proc = proc->next)
{
f_print (fout, "\n");
/* if( Cflag )
f_print( fout, "extern \"C\"{\n");
*/
return_type (proc);
f_print (fout, "* \n");
if (Cflag)
pvname_svc (proc->proc_name, vp->vers_num);
else
pvname (proc->proc_name, vp->vers_num);
printarglist (proc, RQSTP, "struct svc_req *");
f_print(fout, "{\n");
f_print(fout, "\n\tstatic ");
if( !streq( proc->res_type, "void") )
return_type(proc);
else
f_print(fout, "char*" ); /* cannot have void type */
f_print(fout, " result;\n" /*, proc->res_type*/ /*?*/);
f_print(fout,
"\n\t/*\n\t * insert server code here\n\t */\n\n");
if( !streq( proc->res_type, "void") )
f_print(fout, "\treturn(&result);\n}\n");
else /* cast back to void * */
f_print(fout, "\treturn((void*) &result);\n}\n");
/* if( Cflag)
f_print( fout, "};\n");
*/
f_print (fout, "{\n");
f_print (fout, "\n\tstatic ");
if (!streq (proc->res_type, "void"))
return_type (proc);
else
f_print (fout, "char*"); /* cannot have void type */
f_print (fout, " result;\n" /*, proc->res_type *//*? */ );
f_print (fout,
"\n\t/*\n\t * insert server code here\n\t */\n\n");
if (!streq (proc->res_type, "void"))
f_print (fout, "\treturn(&result);\n}\n");
else /* cast back to void * */
f_print (fout, "\treturn((void*) &result);\n}\n");
/* if( Cflag)
f_print( fout, "};\n");
*/
}
}
}
}
static void
return_type(proc_list *plist)
return_type (proc_list * plist)
{
ptype( plist->res_prefix, plist->res_type, 1 );
ptype (plist->res_prefix, plist->res_type, 1);
}
void
add_sample_msg(void)
add_sample_msg (void)
{
f_print(fout, "/*\n");
f_print(fout, " * This is sample code generated by rpcgen.\n");
f_print(fout, " * These are only templates and you can use them\n");
f_print(fout, " * as a guideline for developing your own functions.\n");
f_print(fout, " */\n\n");
f_print (fout, "/*\n");
f_print (fout, " * This is sample code generated by rpcgen.\n");
f_print (fout, " * These are only templates and you can use them\n");
f_print (fout, " * as a guideline for developing your own functions.\n");
f_print (fout, " */\n\n");
}
void
write_sample_clnt_main(void)
write_sample_clnt_main (void)
{
list *l;
definition *def;
version_list *vp;
f_print(fout, "\n\n" );
if( Cflag )
f_print(fout,"main( int argc, char* argv[] )\n{\n" );
f_print (fout, "\n\n");
if (Cflag)
f_print (fout, "main( int argc, char* argv[] )\n{\n");
else
f_print(fout, "main(argc, argv)\nint argc;\nchar *argv[];\n{\n" );
f_print (fout, "main(argc, argv)\nint argc;\nchar *argv[];\n{\n");
f_print(fout, "\tchar *host;");
f_print(fout, "\n\n\tif(argc < 2) {");
f_print(fout, "\n\t\tprintf(\"usage: %%s server_host\\n\", argv[0]);\n" );
f_print(fout, "\t\texit(1);\n\t}");
f_print(fout, "\n\thost = argv[1];\n");
f_print (fout, "\tchar *host;");
f_print (fout, "\n\n\tif(argc < 2) {");
f_print (fout, "\n\t\tprintf(\"usage: %%s server_host\\n\", argv[0]);\n");
f_print (fout, "\t\texit(1);\n\t}");
f_print (fout, "\n\thost = argv[1];\n");
for (l = defined; l != NULL; l = l->next) {
def = l->val;
if (def->def_kind != DEF_PROGRAM) {
continue;
}
for (vp = def->def.pr.versions; vp != NULL; vp = vp->next) {
f_print( fout, "\t" );
pvname(def->def_name, vp->vers_num);
f_print( fout, "( host );\n" );
}
}
f_print(fout, "}\n");
for (l = defined; l != NULL; l = l->next)
{
def = l->val;
if (def->def_kind != DEF_PROGRAM)
{
continue;
}
for (vp = def->def.pr.versions; vp != NULL; vp = vp->next)
{
f_print (fout, "\t");
pvname (def->def_name, vp->vers_num);
f_print (fout, "( host );\n");
}
}
f_print (fout, "}\n");
}

View File

@ -31,12 +31,12 @@
/*
* From: @(#)rpc_scan.c 1.11 89/02/22 (C) 1987 SMI
*/
char scan_rcsid[] =
char scan_rcsid[] =
"$Id$";
/*
* rpc_scan.c, Scanner for the RPC protocol compiler
* Copyright (C) 1987, Sun Microsystems, Inc.
* rpc_scan.c, Scanner for the RPC protocol compiler
* Copyright (C) 1987, Sun Microsystems, Inc.
*/
#include <stdio.h>
#include <ctype.h>
@ -49,439 +49,499 @@ char scan_rcsid[] =
#define startcomment(where) (where[0] == '/' && where[1] == '*')
#define endcomment(where) (where[-1] == '*' && where[0] == '/')
static int pushed = 0; /* is a token pushed */
static token lasttok; /* last token, if pushed */
static int pushed = 0; /* is a token pushed */
static token lasttok; /* last token, if pushed */
static void unget_token(token *tokp);
static void findstrconst(const char **str, const char **val);
static void findchrconst(const char **str, const char **val);
static void findconst(const char **str, const char **val);
static void findkind(const char **mark, token *tokp);
static int cppline(const char *line);
static int directive(const char *line);
static void printdirective(const char *line);
static void docppline(const char *line, int *lineno, const char **fname);
static void unget_token (token * tokp);
static void findstrconst (const char **str, const char **val);
static void findchrconst (const char **str, const char **val);
static void findconst (const char **str, const char **val);
static void findkind (const char **mark, token * tokp);
static int cppline (const char *line);
static int directive (const char *line);
static void printdirective (const char *line);
static void docppline (const char *line, int *lineno, const char **fname);
/*
* scan expecting 1 given token
* scan expecting 1 given token
*/
void
scan(tok_kind expect, token *tokp)
scan (tok_kind expect, token * tokp)
{
get_token(tokp);
if (tokp->kind != expect) {
expected1(expect);
}
get_token (tokp);
if (tokp->kind != expect)
{
expected1 (expect);
}
}
/*
* scan expecting any of the 2 given tokens
* scan expecting any of the 2 given tokens
*/
void
scan2(tok_kind expect1, tok_kind expect2, token *tokp)
scan2 (tok_kind expect1, tok_kind expect2, token * tokp)
{
get_token(tokp);
if (tokp->kind != expect1 && tokp->kind != expect2) {
expected2(expect1, expect2);
}
get_token (tokp);
if (tokp->kind != expect1 && tokp->kind != expect2)
{
expected2 (expect1, expect2);
}
}
/*
* scan expecting any of the 3 given token
* scan expecting any of the 3 given token
*/
void
scan3(tok_kind expect1, tok_kind expect2, tok_kind expect3, token *tokp)
scan3 (tok_kind expect1, tok_kind expect2, tok_kind expect3, token * tokp)
{
get_token(tokp);
if (tokp->kind != expect1 && tokp->kind != expect2
&& tokp->kind != expect3) {
expected3(expect1, expect2, expect3);
}
get_token (tokp);
if (tokp->kind != expect1 && tokp->kind != expect2
&& tokp->kind != expect3)
{
expected3 (expect1, expect2, expect3);
}
}
/*
* scan expecting a constant, possibly symbolic
* scan expecting a constant, possibly symbolic
*/
void
scan_num(token *tokp)
scan_num (token * tokp)
{
get_token(tokp);
switch (tokp->kind) {
case TOK_IDENT:
break;
default:
error("constant or identifier expected");
}
get_token (tokp);
switch (tokp->kind)
{
case TOK_IDENT:
break;
default:
error ("constant or identifier expected");
}
}
/*
* Peek at the next token
* Peek at the next token
*/
void
peek(token *tokp)
peek (token * tokp)
{
get_token(tokp);
unget_token(tokp);
get_token (tokp);
unget_token (tokp);
}
/*
* Peek at the next token and scan it if it matches what you expect
* Peek at the next token and scan it if it matches what you expect
*/
int
peekscan(tok_kind expect, token *tokp)
peekscan (tok_kind expect, token * tokp)
{
peek(tokp);
if (tokp->kind == expect) {
get_token(tokp);
return (1);
}
return (0);
peek (tokp);
if (tokp->kind == expect)
{
get_token (tokp);
return (1);
}
return (0);
}
/*
* Get the next token, printing out any directive that are encountered.
* Get the next token, printing out any directive that are encountered.
*/
void
get_token(token *tokp)
get_token (token * tokp)
{
int commenting;
int commenting;
if (pushed) {
pushed = 0;
*tokp = lasttok;
return;
}
commenting = 0;
for (;;) {
if (*where == 0) {
for (;;) {
if (!fgets(curline, MAXLINESIZE, fin)) {
tokp->kind = TOK_EOF;
*curline = 0;
where = curline;
return;
}
linenum++;
if (commenting) {
break;
} else if (cppline(curline)) {
docppline(curline, &linenum,
&infilename);
} else if (directive(curline)) {
printdirective(curline);
} else {
break;
}
}
where = curline;
} else if (isspace(*where)) {
while (isspace(*where)) {
where++; /* eat */
}
} else if (commenting) {
for (where++; *where; where++) {
if (endcomment(where)) {
where++;
commenting--;
break;
}
}
} else if (startcomment(where)) {
where += 2;
commenting++;
} else {
break;
if (pushed)
{
pushed = 0;
*tokp = lasttok;
return;
}
commenting = 0;
for (;;)
{
if (*where == 0)
{
for (;;)
{
if (!fgets (curline, MAXLINESIZE, fin))
{
tokp->kind = TOK_EOF;
*curline = 0;
where = curline;
return;
}
}
/*
* 'where' is not whitespace, comment or directive Must be a token!
*/
switch (*where) {
case ':':
tokp->kind = TOK_COLON;
where++;
break;
case ';':
tokp->kind = TOK_SEMICOLON;
where++;
break;
case ',':
tokp->kind = TOK_COMMA;
where++;
break;
case '=':
tokp->kind = TOK_EQUAL;
where++;
break;
case '*':
tokp->kind = TOK_STAR;
where++;
break;
case '[':
tokp->kind = TOK_LBRACKET;
where++;
break;
case ']':
tokp->kind = TOK_RBRACKET;
where++;
break;
case '{':
tokp->kind = TOK_LBRACE;
where++;
break;
case '}':
tokp->kind = TOK_RBRACE;
where++;
break;
case '(':
tokp->kind = TOK_LPAREN;
where++;
break;
case ')':
tokp->kind = TOK_RPAREN;
where++;
break;
case '<':
tokp->kind = TOK_LANGLE;
where++;
break;
case '>':
tokp->kind = TOK_RANGLE;
where++;
break;
case '"':
tokp->kind = TOK_STRCONST;
findstrconst(&where, &tokp->str);
break;
case '\'':
tokp->kind = TOK_CHARCONST;
findchrconst(&where, &tokp->str);
break;
case '-':
case '0':
case '1':
case '2':
case '3':
case '4':
case '5':
case '6':
case '7':
case '8':
case '9':
tokp->kind = TOK_IDENT;
findconst(&where, &tokp->str);
break;
default:
if (!(isalpha(*where) || *where == '_')) {
char buf[100];
char *p;
s_print(buf, "illegal character in file: ");
p = buf + strlen(buf);
if (isprint(*where)) {
s_print(p, "%c", *where);
} else {
s_print(p, "%d", *where);
}
error(buf);
linenum++;
if (commenting)
{
break;
}
findkind(&where, tokp);
break;
else if (cppline (curline))
{
docppline (curline, &linenum,
&infilename);
}
else if (directive (curline))
{
printdirective (curline);
}
else
{
break;
}
}
where = curline;
}
else if (isspace (*where))
{
while (isspace (*where))
{
where++; /* eat */
}
}
else if (commenting)
{
for (where++; *where; where++)
{
if (endcomment (where))
{
where++;
commenting--;
break;
}
}
}
else if (startcomment (where))
{
where += 2;
commenting++;
}
else
{
break;
}
}
/*
* 'where' is not whitespace, comment or directive Must be a token!
*/
switch (*where)
{
case ':':
tokp->kind = TOK_COLON;
where++;
break;
case ';':
tokp->kind = TOK_SEMICOLON;
where++;
break;
case ',':
tokp->kind = TOK_COMMA;
where++;
break;
case '=':
tokp->kind = TOK_EQUAL;
where++;
break;
case '*':
tokp->kind = TOK_STAR;
where++;
break;
case '[':
tokp->kind = TOK_LBRACKET;
where++;
break;
case ']':
tokp->kind = TOK_RBRACKET;
where++;
break;
case '{':
tokp->kind = TOK_LBRACE;
where++;
break;
case '}':
tokp->kind = TOK_RBRACE;
where++;
break;
case '(':
tokp->kind = TOK_LPAREN;
where++;
break;
case ')':
tokp->kind = TOK_RPAREN;
where++;
break;
case '<':
tokp->kind = TOK_LANGLE;
where++;
break;
case '>':
tokp->kind = TOK_RANGLE;
where++;
break;
case '"':
tokp->kind = TOK_STRCONST;
findstrconst (&where, &tokp->str);
break;
case '\'':
tokp->kind = TOK_CHARCONST;
findchrconst (&where, &tokp->str);
break;
case '-':
case '0':
case '1':
case '2':
case '3':
case '4':
case '5':
case '6':
case '7':
case '8':
case '9':
tokp->kind = TOK_IDENT;
findconst (&where, &tokp->str);
break;
default:
if (!(isalpha (*where) || *where == '_'))
{
char buf[100];
char *p;
s_print (buf, _("illegal character in file: "));
p = buf + strlen (buf);
if (isprint (*where))
{
s_print (p, "%c", *where);
}
else
{
s_print (p, "%d", *where);
}
error (buf);
}
findkind (&where, tokp);
break;
}
}
static void
unget_token(token *tokp)
unget_token (token * tokp)
{
lasttok = *tokp;
pushed = 1;
lasttok = *tokp;
pushed = 1;
}
static void
findstrconst(const char **str, const char **val)
findstrconst (const char **str, const char **val)
{
const char *p;
char *tmp;
int size;
const char *p;
char *tmp;
int size;
p = *str;
do {
p++;
} while (*p && *p != '"');
if (*p == 0) {
error("unterminated string constant");
}
p++;
size = p - *str;
tmp = alloc(size + 1);
strncpy(tmp, *str, size);
tmp[size] = 0;
*val = tmp;
*str = p;
p = *str;
do
{
p++;
}
while (*p && *p != '"');
if (*p == 0)
{
error (_("unterminated string constant"));
}
p++;
size = p - *str;
tmp = alloc (size + 1);
strncpy (tmp, *str, size);
tmp[size] = 0;
*val = tmp;
*str = p;
}
static void
findchrconst(const char **str, const char **val)
findchrconst (const char **str, const char **val)
{
const char *p;
char *tmp;
int size;
const char *p;
char *tmp;
int size;
p = *str;
do {
p++;
} while (*p && *p != '\'');
if (*p == 0) {
error("unterminated string constant");
}
p++;
size = p - *str;
if (size != 3) {
error("empty char string");
}
tmp = alloc(size + 1);
strncpy(tmp, *str, size);
tmp[size] = 0;
*val = tmp;
*str = p;
p = *str;
do
{
p++;
}
while (*p && *p != '\'');
if (*p == 0)
{
error (_("unterminated string constant"));
}
p++;
size = p - *str;
if (size != 3)
{
error (_("empty char string"));
}
tmp = alloc (size + 1);
strncpy (tmp, *str, size);
tmp[size] = 0;
*val = tmp;
*str = p;
}
static void
findconst(const char **str, const char **val)
findconst (const char **str, const char **val)
{
const char *p;
char *tmp;
int size;
const char *p;
char *tmp;
int size;
p = *str;
if (*p == '0' && *(p + 1) == 'x') {
p++;
do {
p++;
} while (isxdigit(*p));
} else {
do {
p++;
} while (isdigit(*p));
p = *str;
if (*p == '0' && *(p + 1) == 'x')
{
p++;
do
{
p++;
}
size = p - *str;
tmp = alloc(size + 1);
strncpy(tmp, *str, size);
tmp[size] = 0;
*val = tmp;
*str = p;
while (isxdigit (*p));
}
else
{
do
{
p++;
}
while (isdigit (*p));
}
size = p - *str;
tmp = alloc (size + 1);
strncpy (tmp, *str, size);
tmp[size] = 0;
*val = tmp;
*str = p;
}
static token symbols[] = {
{TOK_CONST, "const"},
{TOK_UNION, "union"},
{TOK_SWITCH, "switch"},
{TOK_CASE, "case"},
{TOK_DEFAULT, "default"},
{TOK_STRUCT, "struct"},
{TOK_TYPEDEF, "typedef"},
{TOK_ENUM, "enum"},
{TOK_OPAQUE, "opaque"},
{TOK_BOOL, "bool"},
{TOK_VOID, "void"},
{TOK_CHAR, "char"},
{TOK_INT, "int"},
{TOK_UNSIGNED, "unsigned"},
{TOK_SHORT, "short"},
{TOK_LONG, "long"},
{TOK_FLOAT, "float"},
{TOK_DOUBLE, "double"},
{TOK_STRING, "string"},
{TOK_PROGRAM, "program"},
{TOK_VERSION, "version"},
{TOK_EOF, "??????"},
static const token symbols[] =
{
{TOK_CONST, "const"},
{TOK_UNION, "union"},
{TOK_SWITCH, "switch"},
{TOK_CASE, "case"},
{TOK_DEFAULT, "default"},
{TOK_STRUCT, "struct"},
{TOK_TYPEDEF, "typedef"},
{TOK_ENUM, "enum"},
{TOK_OPAQUE, "opaque"},
{TOK_BOOL, "bool"},
{TOK_VOID, "void"},
{TOK_CHAR, "char"},
{TOK_INT, "int"},
{TOK_UNSIGNED, "unsigned"},
{TOK_SHORT, "short"},
{TOK_LONG, "long"},
{TOK_FLOAT, "float"},
{TOK_DOUBLE, "double"},
{TOK_STRING, "string"},
{TOK_PROGRAM, "program"},
{TOK_VERSION, "version"},
{TOK_EOF, "??????"},
};
static void
findkind(const char **mark, token *tokp)
findkind (const char **mark, token * tokp)
{
int len;
token *s;
const char *str;
char *tmp;
int len;
token *s;
const char *str;
char *tmp;
str = *mark;
for (s = symbols; s->kind != TOK_EOF; s++) {
len = strlen(s->str);
if (strncmp(str, s->str, len) == 0) {
if (!isalnum(str[len]) && str[len] != '_') {
tokp->kind = s->kind;
tokp->str = s->str;
*mark = str + len;
return;
}
}
str = *mark;
for (s = symbols; s->kind != TOK_EOF; s++)
{
len = strlen (s->str);
if (strncmp (str, s->str, len) == 0)
{
if (!isalnum (str[len]) && str[len] != '_')
{
tokp->kind = s->kind;
tokp->str = s->str;
*mark = str + len;
return;
}
}
tokp->kind = TOK_IDENT;
for (len = 0; isalnum(str[len]) || str[len] == '_'; len++);
tmp = alloc(len + 1);
strncpy(tmp, str, len);
tmp[len] = 0;
tokp->str = tmp;
*mark = str + len;
}
tokp->kind = TOK_IDENT;
for (len = 0; isalnum (str[len]) || str[len] == '_'; len++);
tmp = alloc (len + 1);
strncpy (tmp, str, len);
tmp[len] = 0;
tokp->str = tmp;
*mark = str + len;
}
static int
cppline(const char *line)
cppline (const char *line)
{
return (line == curline && *line == '#');
return line == curline && *line == '#';
}
static int
directive(const char *line)
directive (const char *line)
{
return (line == curline && *line == '%');
return line == curline && *line == '%';
}
static void
printdirective(const char *line)
printdirective (const char *line)
{
f_print(fout, "%s", line + 1);
f_print (fout, "%s", line + 1);
}
static void
docppline(const char *line, int *lineno, const char **fname)
docppline (const char *line, int *lineno, const char **fname)
{
char *file;
int num;
char *p;
char *file;
int num;
char *p;
line++;
while (isspace(*line)) {
line++;
}
num = atoi(line);
while (isdigit(*line)) {
line++;
}
while (isspace(*line)) {
line++;
}
if (*line != '"') {
error("preprocessor error");
}
line++;
p = file = alloc(strlen(line) + 1);
while (*line && *line != '"') {
*p++ = *line++;
}
if (*line == 0) {
error("preprocessor error");
}
*p = 0;
if (*file == 0) {
*fname = NULL;
} else {
*fname = file;
}
*lineno = num - 1;
line++;
while (isspace (*line))
{
line++;
}
num = atoi (line);
while (isdigit (*line))
{
line++;
}
while (isspace (*line))
{
line++;
}
if (*line != '"')
{
error (_("preprocessor error"));
}
line++;
p = file = alloc (strlen (line) + 1);
while (*line && *line != '"')
{
*p++ = *line++;
}
if (*line == 0)
{
error (_("preprocessor error"));
}
*p = 0;
if (*file == 0)
{
*fname = NULL;
}
else
{
*fname = file;
}
*lineno = num - 1;
}

File diff suppressed because it is too large Load Diff

View File

@ -28,10 +28,10 @@
* Mountain View, California 94043
*/
/*
/*
* From: @(#)rpc_tblout.c 1.4 89/02/22 (C) 1988 SMI
*/
char tblout_rcsid[] =
char tblout_rcsid[] =
"$Id$";
/*
@ -47,124 +47,136 @@ char tblout_rcsid[] =
#define TABCOUNT 5
#define TABSTOP (TABSIZE*TABCOUNT)
static char tabstr[TABCOUNT+1] = "\t\t\t\t\t";
static const char tabstr[TABCOUNT + 1] = "\t\t\t\t\t";
static char tbl_hdr[] = "struct rpcgen_table %s_table[] = {\n";
static char tbl_end[] = "};\n";
static const char tbl_hdr[] = "struct rpcgen_table %s_table[] = {\n";
static const char tbl_end[] = "};\n";
static char null_entry[] = "\n\t(char *(*)())0,\n\
static const char null_entry[] = "\n\t(char *(*)())0,\n\
\t(xdrproc_t) xdr_void,\t\t\t0,\n\
\t(xdrproc_t) xdr_void,\t\t\t0,\n";
static char tbl_nproc[] = "int %s_nproc =\n\tsizeof(%s_table)/sizeof(%s_table[0]);\n\n";
static const char tbl_nproc[] = "int %s_nproc =\n\tsizeof(%s_table)/sizeof(%s_table[0]);\n\n";
static void write_table(const definition *def);
static void printit(const char *prefix, const char *type);
static void write_table (const definition * def);
static void printit (const char *prefix, const char *type);
void
write_tables(void)
write_tables (void)
{
list *l;
definition *def;
list *l;
definition *def;
f_print(fout, "\n");
for (l = defined; l != NULL; l = l->next) {
def = (definition *) l->val;
if (def->def_kind == DEF_PROGRAM) {
write_table(def);
}
f_print (fout, "\n");
for (l = defined; l != NULL; l = l->next)
{
def = (definition *) l->val;
if (def->def_kind == DEF_PROGRAM)
{
write_table (def);
}
}
}
static void
write_table(const definition *def)
write_table (const definition * def)
{
version_list *vp;
proc_list *proc;
int current;
int expected;
char progvers[100];
int warning;
version_list *vp;
proc_list *proc;
int current;
int expected;
char progvers[100];
int warning;
for (vp = def->def.pr.versions; vp != NULL; vp = vp->next) {
warning = 0;
s_print(progvers, "%s_%s",
locase(def->def_name), vp->vers_num);
/* print the table header */
f_print(fout, tbl_hdr, progvers);
for (vp = def->def.pr.versions; vp != NULL; vp = vp->next)
{
warning = 0;
s_print (progvers, "%s_%s",
locase (def->def_name), vp->vers_num);
/* print the table header */
f_print (fout, tbl_hdr, progvers);
if (nullproc(vp->procs)) {
expected = 0;
}
else {
expected = 1;
f_print(fout, null_entry);
}
for (proc = vp->procs; proc != NULL; proc = proc->next) {
current = atoi(proc->proc_num);
if (current != expected++) {
f_print(fout,
"\n/*\n * WARNING: table out of order\n */\n");
if (warning == 0) {
f_print(stderr,
"WARNING %s table is out of order\n",
progvers);
warning = 1;
nonfatalerrors = 1;
}
expected = current + 1;
}
f_print(fout, "\n\t(char *(*)())RPCGEN_ACTION(");
/* routine to invoke */
if( Cflag && !newstyle )
pvname_svc(proc->proc_name, vp->vers_num);
else {
if( newstyle )
f_print( fout, "_"); /* calls internal func */
pvname(proc->proc_name, vp->vers_num);
}
f_print(fout, "),\n");
/* argument info */
if( proc->arg_num > 1 )
printit((char*) NULL, proc->args.argname );
else
/* do we have to do something special for newstyle */
printit( proc->args.decls->decl.prefix,
proc->args.decls->decl.type );
/* result info */
printit(proc->res_prefix, proc->res_type);
}
/* print the table trailer */
f_print(fout, tbl_end);
f_print(fout, tbl_nproc, progvers, progvers, progvers);
if (nullproc (vp->procs))
{
expected = 0;
}
else
{
expected = 1;
f_print (fout, null_entry);
}
for (proc = vp->procs; proc != NULL; proc = proc->next)
{
current = atoi (proc->proc_num);
if (current != expected++)
{
f_print (fout,
"\n/*\n * WARNING: table out of order\n */\n");
if (warning == 0)
{
f_print (stderr,
"WARNING %s table is out of order\n",
progvers);
warning = 1;
nonfatalerrors = 1;
}
expected = current + 1;
}
f_print (fout, "\n\t(char *(*)())RPCGEN_ACTION(");
/* routine to invoke */
if (Cflag && !newstyle)
pvname_svc (proc->proc_name, vp->vers_num);
else
{
if (newstyle)
f_print (fout, "_"); /* calls internal func */
pvname (proc->proc_name, vp->vers_num);
}
f_print (fout, "),\n");
/* argument info */
if (proc->arg_num > 1)
printit ((char *) NULL, proc->args.argname);
else
/* do we have to do something special for newstyle */
printit (proc->args.decls->decl.prefix,
proc->args.decls->decl.type);
/* result info */
printit (proc->res_prefix, proc->res_type);
}
/* print the table trailer */
f_print (fout, tbl_end);
f_print (fout, tbl_nproc, progvers, progvers, progvers);
}
}
static void
printit(const char *prefix, const char *type)
printit (const char *prefix, const char *type)
{
int len;
int tabs;
int len;
int tabs;
len = fprintf(fout, "\txdr_%s,", stringfix(type));
/* account for leading tab expansion */
len += TABSIZE - 1;
/* round up to tabs required */
tabs = (TABSTOP - len + TABSIZE - 1)/TABSIZE;
f_print(fout, "%s", &tabstr[TABCOUNT-tabs]);
len = fprintf (fout, "\txdr_%s,", stringfix (type));
/* account for leading tab expansion */
len += TABSIZE - 1;
/* round up to tabs required */
tabs = (TABSTOP - len + TABSIZE - 1) / TABSIZE;
f_print (fout, "%s", &tabstr[TABCOUNT - tabs]);
if (streq(type, "void")) {
f_print(fout, "0");
} else {
f_print(fout, "sizeof ( ");
/* XXX: should "follow" be 1 ??? */
ptype(prefix, type, 0);
f_print(fout, ")");
}
f_print(fout, ",\n");
if (streq (type, "void"))
{
f_print (fout, "0");
}
else
{
f_print (fout, "sizeof ( ");
/* XXX: should "follow" be 1 ??? */
ptype (prefix, type, 0);
f_print (fout, ")");
}
f_print (fout, ",\n");
}

View File

@ -28,14 +28,14 @@
* Mountain View, California 94043
*/
/*
/*
* From: @(#)rpc_util.c 1.11 89/02/22 (C) 1987 SMI
*/
char util_rcsid[] =
"$Id$";
/*
* rpc_util.c, Utility routines for the RPC protocol compiler
* rpc_util.c, Utility routines for the RPC protocol compiler
*/
#include <stdio.h>
#include <ctype.h>
@ -63,425 +63,464 @@ FILE *fin; /* file pointer of current input */
list *defined; /* list of defined things */
static int findit(const definition *def, const char *type);
static const char *fixit(const char *type, const char *orig);
static int typedefed(const definition *def, const char *type);
static const char *toktostr(tok_kind kind);
static void printbuf(void);
static void printwhere(void);
static int findit (const definition * def, const char *type);
static const char *fixit (const char *type, const char *orig);
static int typedefed (const definition * def, const char *type);
static const char *toktostr (tok_kind kind);
static void printbuf (void);
static void printwhere (void);
/*
* Reinitialize the world
* Reinitialize the world
*/
void
reinitialize(void)
reinitialize (void)
{
memset(curline, 0, MAXLINESIZE);
where = curline;
linenum = 0;
defined = NULL;
memset (curline, 0, MAXLINESIZE);
where = curline;
linenum = 0;
defined = NULL;
}
/*
* string equality
* string equality
*/
int
streq(const char *a, const char *b)
streq (const char *a, const char *b)
{
return (strcmp(a, b) == 0);
return strcmp (a, b) == 0;
}
/*
* find a value in a list
* find a value in a list
*/
definition *
findval(list *lst, const char *val,
int (*cmp)(const definition *, const char *))
findval (list * lst, const char *val,
int (*cmp) (const definition *, const char *))
{
for (; lst != NULL; lst = lst->next) {
if (cmp(lst->val, val)) {
return (lst->val);
}
for (; lst != NULL; lst = lst->next)
{
if (cmp (lst->val, val))
{
return lst->val;
}
return NULL;
}
return NULL;
}
/*
* store a value in a list
* store a value in a list
*/
void
storeval(list **lstp, definition *val)
storeval (list ** lstp, definition * val)
{
list **l;
list *lst;
list **l;
list *lst;
for (l = lstp; *l != NULL; l = (list **) & (*l)->next);
lst = ALLOC(list);
lst->val = val;
lst->next = NULL;
*l = lst;
for (l = lstp; *l != NULL; l = (list **) & (*l)->next);
lst = ALLOC (list);
lst->val = val;
lst->next = NULL;
*l = lst;
}
static int
findit(const definition *def, const char *type)
findit (const definition * def, const char *type)
{
return (streq(def->def_name, type));
return streq (def->def_name, type);
}
static const char *
fixit(const char *type, const char *orig)
fixit (const char *type, const char *orig)
{
definition *def;
definition *def;
def = findval(defined, type, findit);
if (def == NULL || def->def_kind != DEF_TYPEDEF) {
return (orig);
}
switch (def->def.ty.rel) {
case REL_VECTOR:
return (def->def.ty.old_type);
case REL_ALIAS:
return (fixit(def->def.ty.old_type, orig));
default:
return (orig);
}
def = findval (defined, type, findit);
if (def == NULL || def->def_kind != DEF_TYPEDEF)
{
return orig;
}
switch (def->def.ty.rel)
{
case REL_VECTOR:
return (def->def.ty.old_type);
case REL_ALIAS:
return (fixit (def->def.ty.old_type, orig));
default:
return orig;
}
}
const char *
fixtype(const char *type)
fixtype (const char *type)
{
return (fixit(type, type));
return fixit (type, type);
}
const char *
stringfix(const char *type)
stringfix (const char *type)
{
if (streq(type, "string")) {
return "wrapstring";
}
else {
return type;
}
if (streq (type, "string"))
{
return "wrapstring";
}
else
{
return type;
}
}
void
ptype(const char *prefix, const char *type, int follow)
ptype (const char *prefix, const char *type, int follow)
{
if (prefix != NULL) {
if (streq(prefix, "enum")) {
f_print(fout, "enum ");
} else {
f_print(fout, "struct ");
}
if (prefix != NULL)
{
if (streq (prefix, "enum"))
{
f_print (fout, "enum ");
}
if (streq(type, "bool")) {
f_print(fout, "bool_t ");
} else if (streq(type, "string")) {
f_print(fout, "char *");
} else {
f_print(fout, "%s ", follow ? fixtype(type) : type);
else
{
f_print (fout, "struct ");
}
}
if (streq (type, "bool"))
{
f_print (fout, "bool_t ");
}
else if (streq (type, "string"))
{
f_print (fout, "char *");
}
else
{
f_print (fout, "%s ", follow ? fixtype (type) : type);
}
}
static int
typedefed(const definition *def, const char *type)
typedefed (const definition * def, const char *type)
{
if (def->def_kind != DEF_TYPEDEF || def->def.ty.old_prefix != NULL) {
return (0);
} else {
return (streq(def->def_name, type));
}
if (def->def_kind != DEF_TYPEDEF || def->def.ty.old_prefix != NULL)
{
return 0;
}
else
{
return streq (def->def_name, type);
}
}
int
isvectordef(const char *type, relation rel)
isvectordef (const char *type, relation rel)
{
definition *def;
definition *def;
for (;;) {
switch (rel) {
case REL_VECTOR:
return (!streq(type, "string"));
case REL_ARRAY:
return (0);
case REL_POINTER:
return (0);
case REL_ALIAS:
def = findval(defined, type, typedefed);
if (def == NULL) {
return (0);
}
type = def->def.ty.old_type;
rel = def->def.ty.rel;
}
for (;;)
{
switch (rel)
{
case REL_VECTOR:
return !streq (type, "string");
case REL_ARRAY:
return 0;
case REL_POINTER:
return (0);
case REL_ALIAS:
def = findval (defined, type, typedefed);
if (def == NULL)
{
return 0;
}
type = def->def.ty.old_type;
rel = def->def.ty.rel;
}
}
}
char *
locase(const char *str)
locase (const char *str)
{
char c;
static char buf[100];
char *p = buf;
char c;
static char buf[100];
char *p = buf;
while ((c = *str++)!=0) {
*p++ = (c >= 'A' && c <= 'Z') ? (c - 'A' + 'a') : c;
}
*p = 0;
return (buf);
while ((c = *str++) != 0)
{
*p++ = (c >= 'A' && c <= 'Z') ? (c - 'A' + 'a') : c;
}
*p = 0;
return buf;
}
void
pvname_svc(const char *pname, const char *vnum)
pvname_svc (const char *pname, const char *vnum)
{
f_print(fout, "%s_%s_svc", locase(pname), vnum);
f_print (fout, "%s_%s_svc", locase (pname), vnum);
}
void
pvname(const char *pname, const char *vnum)
pvname (const char *pname, const char *vnum)
{
f_print(fout, "%s_%s", locase(pname), vnum);
f_print (fout, "%s_%s", locase (pname), vnum);
}
/*
* print a useful (?) error message, and then die
* print a useful (?) error message, and then die
*/
void
error(const char *msg)
error (const char *msg)
{
printwhere();
f_print(stderr, "%s, line %d: ", infilename, linenum);
f_print(stderr, "%s\n", msg);
crash();
printwhere ();
f_print (stderr, "%s, line %d: ", infilename, linenum);
f_print (stderr, "%s\n", msg);
crash ();
}
/*
* Something went wrong, unlink any files that we may have created and then
* die.
* die.
*/
void
crash(void)
crash (void)
{
int i;
int i;
for (i = 0; i < nfiles; i++) {
(void) unlink(outfiles[i]);
}
exit(1);
for (i = 0; i < nfiles; i++)
{
(void) unlink (outfiles[i]);
}
exit (1);
}
void
record_open(const char *file)
record_open (const char *file)
{
if (nfiles < NFILES) {
outfiles[nfiles++] = file;
}
else {
f_print(stderr, "too many files!\n");
crash();
}
if (nfiles < NFILES)
{
outfiles[nfiles++] = file;
}
else
{
f_print (stderr, "too many files!\n");
crash ();
}
}
static char expectbuf[100];
/*
* error, token encountered was not the expected one
* error, token encountered was not the expected one
*/
void
expected1(tok_kind exp1)
expected1 (tok_kind exp1)
{
s_print(expectbuf, "expected '%s'",
toktostr(exp1));
error(expectbuf);
s_print (expectbuf, "expected '%s'",
toktostr (exp1));
error (expectbuf);
}
/*
* error, token encountered was not one of two expected ones
* error, token encountered was not one of two expected ones
*/
void
expected2(tok_kind exp1, tok_kind exp2)
expected2 (tok_kind exp1, tok_kind exp2)
{
s_print(expectbuf, "expected '%s' or '%s'",
toktostr(exp1),
toktostr(exp2));
error(expectbuf);
s_print (expectbuf, "expected '%s' or '%s'",
toktostr (exp1),
toktostr (exp2));
error (expectbuf);
}
/*
* error, token encountered was not one of 3 expected ones
* error, token encountered was not one of 3 expected ones
*/
void
expected3(tok_kind exp1, tok_kind exp2, tok_kind exp3)
expected3 (tok_kind exp1, tok_kind exp2, tok_kind exp3)
{
s_print(expectbuf, "expected '%s', '%s' or '%s'",
toktostr(exp1),
toktostr(exp2),
toktostr(exp3));
error(expectbuf);
s_print (expectbuf, "expected '%s', '%s' or '%s'",
toktostr (exp1),
toktostr (exp2),
toktostr (exp3));
error (expectbuf);
}
void
tabify(FILE *f, int tab)
tabify (FILE * f, int tab)
{
while (tab--) {
(void) fputc('\t', f);
}
while (tab--)
{
(void) fputc ('\t', f);
}
}
static token tokstrings[] = {
{TOK_IDENT, "identifier"},
{TOK_CONST, "const"},
{TOK_RPAREN, ")"},
{TOK_LPAREN, "("},
{TOK_RBRACE, "}"},
{TOK_LBRACE, "{"},
{TOK_LBRACKET, "["},
{TOK_RBRACKET, "]"},
{TOK_STAR, "*"},
{TOK_COMMA, ","},
{TOK_EQUAL, "="},
{TOK_COLON, ":"},
{TOK_SEMICOLON, ";"},
{TOK_UNION, "union"},
{TOK_STRUCT, "struct"},
{TOK_SWITCH, "switch"},
{TOK_CASE, "case"},
{TOK_DEFAULT, "default"},
{TOK_ENUM, "enum"},
{TOK_TYPEDEF, "typedef"},
{TOK_INT, "int"},
{TOK_SHORT, "short"},
{TOK_LONG, "long"},
{TOK_UNSIGNED, "unsigned"},
{TOK_DOUBLE, "double"},
{TOK_FLOAT, "float"},
{TOK_CHAR, "char"},
{TOK_STRING, "string"},
{TOK_OPAQUE, "opaque"},
{TOK_BOOL, "bool"},
{TOK_VOID, "void"},
{TOK_PROGRAM, "program"},
{TOK_VERSION, "version"},
{TOK_EOF, "??????"}
static const token tokstrings[] =
{
{TOK_IDENT, "identifier"},
{TOK_CONST, "const"},
{TOK_RPAREN, ")"},
{TOK_LPAREN, "("},
{TOK_RBRACE, "}"},
{TOK_LBRACE, "{"},
{TOK_LBRACKET, "["},
{TOK_RBRACKET, "]"},
{TOK_STAR, "*"},
{TOK_COMMA, ","},
{TOK_EQUAL, "="},
{TOK_COLON, ":"},
{TOK_SEMICOLON, ";"},
{TOK_UNION, "union"},
{TOK_STRUCT, "struct"},
{TOK_SWITCH, "switch"},
{TOK_CASE, "case"},
{TOK_DEFAULT, "default"},
{TOK_ENUM, "enum"},
{TOK_TYPEDEF, "typedef"},
{TOK_INT, "int"},
{TOK_SHORT, "short"},
{TOK_LONG, "long"},
{TOK_UNSIGNED, "unsigned"},
{TOK_DOUBLE, "double"},
{TOK_FLOAT, "float"},
{TOK_CHAR, "char"},
{TOK_STRING, "string"},
{TOK_OPAQUE, "opaque"},
{TOK_BOOL, "bool"},
{TOK_VOID, "void"},
{TOK_PROGRAM, "program"},
{TOK_VERSION, "version"},
{TOK_EOF, "??????"}
};
static const char *
toktostr(tok_kind kind)
toktostr (tok_kind kind)
{
token *sp;
token *sp;
for (sp = tokstrings; sp->kind != TOK_EOF && sp->kind != kind; sp++);
return (sp->str);
for (sp = tokstrings; sp->kind != TOK_EOF && sp->kind != kind; sp++);
return (sp->str);
}
static void
printbuf(void)
printbuf (void)
{
char c;
int i;
int cnt;
char c;
int i;
int cnt;
# define TABSIZE 4
#define TABSIZE 4
for (i = 0; (c = curline[i])!=0; i++) {
if (c == '\t') {
cnt = 8 - (i % TABSIZE);
c = ' ';
} else {
cnt = 1;
}
while (cnt--) {
(void) fputc(c, stderr);
}
for (i = 0; (c = curline[i]) != 0; i++)
{
if (c == '\t')
{
cnt = 8 - (i % TABSIZE);
c = ' ';
}
else
{
cnt = 1;
}
while (cnt--)
{
(void) fputc (c, stderr);
}
}
}
static void
printwhere(void)
printwhere (void)
{
int i;
char c;
int cnt;
int i;
char c;
int cnt;
printbuf();
for (i = 0; i < where - curline; i++) {
c = curline[i];
if (c == '\t') {
cnt = 8 - (i % TABSIZE);
} else {
cnt = 1;
}
while (cnt--) {
(void) fputc('^', stderr);
}
printbuf ();
for (i = 0; i < where - curline; i++)
{
c = curline[i];
if (c == '\t')
{
cnt = 8 - (i % TABSIZE);
}
(void) fputc('\n', stderr);
else
{
cnt = 1;
}
while (cnt--)
{
(void) fputc ('^', stderr);
}
}
(void) fputc ('\n', stderr);
}
char *
make_argname(const char *pname, const char *vname)
char *
make_argname (const char *pname, const char *vname)
{
char *name;
name = malloc(strlen(pname) + strlen(vname) + strlen(ARGEXT) + 3);
if (!name) {
fprintf(stderr, "failed in malloc");
exit(1);
}
sprintf(name, "%s_%s_%s", locase(pname), vname, ARGEXT);
return name;
char *name;
name = malloc (strlen (pname) + strlen (vname) + strlen (ARGEXT) + 3);
if (!name)
{
fprintf (stderr, "failed in malloc");
exit (1);
}
sprintf (name, "%s_%s_%s", locase (pname), vname, ARGEXT);
return name;
}
bas_type *typ_list_h;
bas_type *typ_list_t;
void
add_type(int len, const char *type)
add_type (int len, const char *type)
{
bas_type *ptr;
if ((ptr = malloc(sizeof(bas_type))) == NULL) {
fprintf(stderr, "failed in malloc");
exit(1);
}
if ((ptr = malloc (sizeof (bas_type))) == NULL)
{
fprintf (stderr, "failed in malloc");
exit (1);
}
ptr->name=type;
ptr->length=len;
ptr->next=NULL;
if(typ_list_t == NULL)
ptr->name = type;
ptr->length = len;
ptr->next = NULL;
if (typ_list_t == NULL)
{
typ_list_t=ptr;
typ_list_h=ptr;
typ_list_t = ptr;
typ_list_h = ptr;
}
else
{
typ_list_t->next=ptr;
typ_list_t=ptr;
typ_list_t->next = ptr;
typ_list_t = ptr;
}
}
bas_type *find_type(const char *type)
bas_type *
find_type (const char *type)
{
bas_type *ptr;
ptr=typ_list_h;
ptr = typ_list_h;
while(ptr != NULL)
while (ptr != NULL)
{
if(strcmp(ptr->name,type) == 0)
return(ptr);
else
ptr=ptr->next;
if (strcmp (ptr->name, type) == 0)
return ptr;
else
ptr = ptr->next;
};
return(NULL);
return NULL;
}

File diff suppressed because it is too large Load Diff

View File

@ -41,8 +41,9 @@ static char sccsid[] = "@(#)svc.c 1.41 87/10/13 Copyr 1984 Sun Micro";
* Copyright (C) 1984, Sun Microsystems, Inc.
*/
#include <sys/errno.h>
#include <errno.h>
#include <rpc/rpc.h>
#include <rpc/svc.h>
#include <rpc/pmap_clnt.h>
#ifndef errno
@ -58,7 +59,7 @@ static SVCXPRT *xports[NOFILE];
#endif /* def FD_SETSIZE */
#define NULL_SVC ((struct svc_callout *)0)
#define RQCRED_SIZE 400 /* this size is excessive */
#define RQCRED_SIZE 400 /* this size is excessive */
/*
* The services list
@ -66,14 +67,16 @@ static SVCXPRT *xports[NOFILE];
* The dispatch routine takes request structs and runs the
* appropriate procedure.
*/
static struct svc_callout {
struct svc_callout *sc_next;
u_long sc_prog;
u_long sc_vers;
void (*sc_dispatch)();
} *svc_head;
static struct svc_callout
{
struct svc_callout *sc_next;
u_long sc_prog;
u_long sc_vers;
void (*sc_dispatch) (struct svc_req *, SVCXPRT *);
}
*svc_head;
static struct svc_callout *svc_find();
static struct svc_callout *svc_find (u_long, u_long, struct svc_callout **);
/* *************** SVCXPRT related stuff **************** */
@ -81,25 +84,27 @@ static struct svc_callout *svc_find();
* Activate a transport handle.
*/
void
xprt_register(xprt)
SVCXPRT *xprt;
xprt_register (SVCXPRT *xprt)
{
register int sock = xprt->xp_sock;
register int sock = xprt->xp_sock;
#ifdef FD_SETSIZE
if (xports == NULL) {
xports = (SVCXPRT **)
mem_alloc(FD_SETSIZE * sizeof(SVCXPRT *));
}
if (sock < _rpc_dtablesize()) {
xports[sock] = xprt;
FD_SET(sock, &svc_fdset);
}
if (xports == NULL)
{
xports = (SVCXPRT **)
mem_alloc (FD_SETSIZE * sizeof (SVCXPRT *));
}
if (sock < _rpc_dtablesize ())
{
xports[sock] = xprt;
FD_SET (sock, &svc_fdset);
}
#else
if (sock < NOFILE) {
xports[sock] = xprt;
svc_fds |= (1 << sock);
}
if (sock < NOFILE)
{
xports[sock] = xprt;
svc_fds |= (1 << sock);
}
#endif /* def FD_SETSIZE */
}
@ -108,21 +113,23 @@ xprt_register(xprt)
* De-activate a transport handle.
*/
void
xprt_unregister(xprt)
SVCXPRT *xprt;
xprt_unregister (xprt)
SVCXPRT *xprt;
{
register int sock = xprt->xp_sock;
register int sock = xprt->xp_sock;
#ifdef FD_SETSIZE
if ((sock < _rpc_dtablesize()) && (xports[sock] == xprt)) {
xports[sock] = (SVCXPRT *)0;
FD_CLR(sock, &svc_fdset);
}
if ((sock < _rpc_dtablesize ()) && (xports[sock] == xprt))
{
xports[sock] = (SVCXPRT *) 0;
FD_CLR (sock, &svc_fdset);
}
#else
if ((sock < NOFILE) && (xports[sock] == xprt)) {
xports[sock] = (SVCXPRT *)0;
svc_fds &= ~(1 << sock);
}
if ((sock < NOFILE) && (xports[sock] == xprt))
{
xports[sock] = (SVCXPRT *) 0;
svc_fds &= ~(1 << sock);
}
#endif /* def FD_SETSIZE */
}
@ -135,60 +142,62 @@ xprt_unregister(xprt)
* program number comes in.
*/
bool_t
svc_register(xprt, prog, vers, dispatch, protocol)
SVCXPRT *xprt;
u_long prog;
u_long vers;
void (*dispatch)();
int protocol;
svc_register (SVCXPRT *xprt, u_long prog, u_long vers,
void (*dispatch) (struct svc_req *, SVCXPRT *), u_long protocol)
{
struct svc_callout *prev;
register struct svc_callout *s;
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;
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);
/* 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(prog, vers)
u_long prog;
u_long vers;
svc_unregister (prog, vers)
u_long prog;
u_long vers;
{
struct svc_callout *prev;
register struct svc_callout *s;
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);
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);
}
/*
@ -196,22 +205,20 @@ svc_unregister(prog, vers)
* struct.
*/
static struct svc_callout *
svc_find(prog, vers, prev)
u_long prog;
u_long vers;
struct svc_callout **prev;
svc_find (u_long prog, u_long vers, struct svc_callout **prev)
{
register struct svc_callout *s, *p;
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;
}
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);
*prev = p;
return s;
}
/* ******************* REPLY GENERATION ROUTINES ************ */
@ -220,132 +227,132 @@ done:
* Send a reply to an rpc request
*/
bool_t
svc_sendreply(xprt, xdr_results, xdr_location)
register SVCXPRT *xprt;
xdrproc_t xdr_results;
caddr_t xdr_location;
svc_sendreply (xprt, xdr_results, xdr_location)
register SVCXPRT *xprt;
xdrproc_t xdr_results;
caddr_t xdr_location;
{
struct rpc_msg rply;
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));
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(xprt)
register SVCXPRT *xprt;
svcerr_noproc (xprt)
register SVCXPRT *xprt;
{
struct rpc_msg rply;
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);
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(xprt)
register SVCXPRT *xprt;
svcerr_decode (xprt)
register SVCXPRT *xprt;
{
struct rpc_msg rply;
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);
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(xprt)
register SVCXPRT *xprt;
svcerr_systemerr (xprt)
register SVCXPRT *xprt;
{
struct rpc_msg rply;
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);
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(xprt, why)
SVCXPRT *xprt;
enum auth_stat why;
svcerr_auth (xprt, why)
SVCXPRT *xprt;
enum auth_stat why;
{
struct rpc_msg rply;
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);
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(xprt)
SVCXPRT *xprt;
svcerr_weakauth (xprt)
SVCXPRT *xprt;
{
svcerr_auth(xprt, AUTH_TOOWEAK);
svcerr_auth (xprt, AUTH_TOOWEAK);
}
/*
* Program unavailable error reply
*/
void
svcerr_noprog(xprt)
register SVCXPRT *xprt;
svcerr_noprog (xprt)
register SVCXPRT *xprt;
{
struct rpc_msg rply;
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);
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(xprt, low_vers, high_vers)
register SVCXPRT *xprt;
u_long low_vers;
u_long high_vers;
svcerr_progvers (xprt, low_vers, high_vers)
register SVCXPRT *xprt;
u_long low_vers;
u_long high_vers;
{
struct rpc_msg rply;
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);
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 ******************* */
@ -367,115 +374,127 @@ svcerr_progvers(xprt, low_vers, high_vers)
*/
void
svc_getreq(rdfds)
int rdfds;
svc_getreq (rdfds)
int rdfds;
{
#ifdef FD_SETSIZE
fd_set readfds;
fd_set readfds;
FD_ZERO(&readfds);
readfds.fds_bits[0] = rdfds;
svc_getreqset(&readfds);
FD_ZERO (&readfds);
readfds.fds_bits[0] = rdfds;
svc_getreqset (&readfds);
#else
int readfds = rdfds & svc_fds;
int readfds = rdfds & svc_fds;
svc_getreqset(&readfds);
svc_getreqset (&readfds);
#endif /* def FD_SETSIZE */
}
void
svc_getreqset(readfds)
svc_getreqset (readfds)
#ifdef FD_SETSIZE
fd_set *readfds;
fd_set *readfds;
{
#else
int *readfds;
int *readfds;
{
int readfds_local = *readfds;
int readfds_local = *readfds;
#endif /* def FD_SETSIZE */
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 u_long mask;
register int bit;
register u_int32_t *maskp;
register int setsize;
register int sock;
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]);
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 u_long mask;
register int bit;
register u_int32_t *maskp;
register int setsize;
register int sock;
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]);
#ifdef FD_SETSIZE
setsize = _rpc_dtablesize();
maskp = (u_int32_t *)readfds->fds_bits;
for (sock = 0; sock < setsize; sock += 32) {
for (mask = *maskp++; bit = ffs(mask); mask ^= (1 << (bit - 1))) {
/* sock has input waiting */
xprt = xports[sock + bit - 1];
setsize = _rpc_dtablesize ();
maskp = (u_int32_t *) readfds->fds_bits;
for (sock = 0; sock < setsize; sock += 32)
{
for (mask = *maskp++; bit = ffs (mask); mask ^= (1 << (bit - 1)))
{
/* sock has input waiting */
xprt = xports[sock + bit - 1];
#else
for (sock = 0; readfds_local != 0; sock++, readfds_local >>= 1) {
if ((readfds_local & 1) != 0) {
/* sock has input waiting */
xprt = xports[sock];
for (sock = 0; readfds_local != 0; sock++, readfds_local >>= 1)
{
if ((readfds_local & 1) != 0)
{
/* sock has input waiting */
xprt = xports[sock];
#endif /* def FD_SETSIZE */
/* now receive msgs from xprtprt (support batch calls) */
do {
if (SVC_RECV(xprt, &msg)) {
/* 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;
/* 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 = 0 - 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);
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 = 0 - 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);
}
}
}

View File

@ -1,6 +1,4 @@
#if !defined(lint) && defined(SCCSIDS)
static char sccsid[] = "@(#)svc_auth.c 2.1 88/08/07 4.0 RPCSRC; from 1.19 87/08/11 Copyr 1984 Sun Micro";
#endif
/* @(#)svc_auth.c 2.4 88/08/15 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
@ -29,15 +27,20 @@ static char sccsid[] = "@(#)svc_auth.c 2.1 88/08/07 4.0 RPCSRC; from 1.19 87/08/
* 2550 Garcia Avenue
* Mountain View, California 94043
*/
#if !defined(lint) && defined(SCCSIDS)
static char sccsid[] = "@(#)svc_auth.c 1.19 87/08/11 Copyr 1984 Sun Micro";
#endif
/*
* svc_auth_nodes.c, Server-side rpc authenticator interface,
* svc_auth.c, Server-side rpc authenticator interface.
* *WITHOUT* DES authentication.
*
* Copyright (C) 1984, Sun Microsystems, Inc.
*/
#include <rpc/rpc.h>
#include <rpc/svc.h>
#include <rpc/svc_auth.h>
/*
* svcauthsw is the bdevsw of server side authentication.
@ -47,25 +50,31 @@ static char sccsid[] = "@(#)svc_auth.c 2.1 88/08/07 4.0 RPCSRC; from 1.19 87/08/
* 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
* flavorx_auth(rqst, msg)
* register struct svc_req *rqst;
* register struct rpc_msg *msg;
*
*/
enum auth_stat _svcauth_null(); /* no authentication */
enum auth_stat _svcauth_unix(); /* unix style (uid, gids) */
enum auth_stat _svcauth_short(); /* short hand unix style */
static enum auth_stat _svcauth_null (struct svc_req *, struct rpc_msg *);
/* no authentication */
extern enum auth_stat _svcauth_unix (struct svc_req *, struct rpc_msg *);
/* unix style (uid, gids) */
extern enum auth_stat _svcauth_short (struct svc_req *, struct rpc_msg *);
/* short hand unix style */
static struct {
enum auth_stat (*authenticator)();
} svcauthsw[] = {
_svcauth_null, /* AUTH_NULL */
_svcauth_unix, /* AUTH_UNIX */
_svcauth_short, /* AUTH_SHORT */
static const struct
{
enum auth_stat (*authenticator) (struct svc_req *, struct rpc_msg *);
}
svcauthsw[] =
{
{ _svcauth_null }, /* AUTH_NULL */
{ _svcauth_unix }, /* AUTH_UNIX */
{ _svcauth_short } /* AUTH_SHORT */
};
#define AUTH_MAX 2 /* HIGHEST AUTH NUMBER */
#define AUTH_MAX 2 /* HIGHEST AUTH NUMBER */
/*
@ -87,28 +96,22 @@ static struct {
* invalid.
*/
enum auth_stat
_authenticate(rqst, msg)
register struct svc_req *rqst;
struct rpc_msg *msg;
_authenticate (register struct svc_req *rqst, struct rpc_msg *msg)
{
register int cred_flavor;
register int cred_flavor;
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;
if ((cred_flavor <= AUTH_MAX) && (cred_flavor >= AUTH_NULL)) {
return ((*(svcauthsw[cred_flavor].authenticator))(rqst, msg));
}
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;
if ((cred_flavor <= AUTH_MAX) && (cred_flavor >= AUTH_NULL))
return (*(svcauthsw[cred_flavor].authenticator)) (rqst, msg);
return (AUTH_REJECTEDCRED);
return AUTH_REJECTEDCRED;
}
enum auth_stat
_svcauth_null(/*rqst, msg*/)
/*struct svc_req *rqst;
struct rpc_msg *msg;*/
static enum auth_stat
_svcauth_null (struct svc_req *rqst, struct rpc_msg *msg)
{
return (AUTH_OK);
return AUTH_OK;
}

View File

@ -43,80 +43,89 @@ static char sccsid[] = "@(#)svc_auth_unix.c 1.28 88/02/08 Copyr 1984 Sun Micro";
*/
#include <stdio.h>
#include <string.h>
#include <rpc/rpc.h>
#include <rpc/svc.h>
/*
* Unix longhand authenticator
*/
enum auth_stat
_svcauth_unix(rqst, msg)
register struct svc_req *rqst;
register struct rpc_msg *msg;
_svcauth_unix (struct svc_req *rqst, struct rpc_msg *msg)
{
register enum auth_stat stat;
XDR xdrs;
register struct authunix_parms *aup;
register long *buf;
struct area {
struct authunix_parms area_aup;
char area_machname[MAX_MACHINE_NAME+1];
gid_t area_gids[NGRPS];
} *area;
u_int auth_len;
int str_len, gid_len;
register int i;
enum auth_stat stat;
XDR xdrs;
struct authunix_parms *aup;
long *buf;
struct area
{
struct authunix_parms area_aup;
char area_machname[MAX_MACHINE_NAME + 1];
gid_t area_gids[NGRPS];
}
*area;
u_int auth_len;
u_int str_len, gid_len;
u_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;
}
bcopy((caddr_t)buf, aup->aup_machname, (u_int)str_len);
aup->aup_machname[str_len] = 0;
str_len = RNDUP(str_len);
buf = (u_long *) ((char *) buf + str_len);
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;
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;
}
rqst->rq_xprt->xp_verf.oa_flavor = AUTH_NULL;
rqst->rq_xprt->xp_verf.oa_length = 0;
stat = AUTH_OK;
bcopy ((caddr_t) buf, aup->aup_machname, (u_int) str_len);
aup->aup_machname[str_len] = 0;
str_len = RNDUP (str_len);
buf = (u_long *) ((char *) buf + str_len);
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;
}
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);
XDR_DESTROY (&xdrs);
return stat;
}
@ -124,11 +133,9 @@ done:
* Shorthand unix authenticator
* Looks up longhand in a cache.
*/
/*ARGSUSED*/
/*ARGSUSED */
enum auth_stat
_svcauth_short(rqst, msg)
struct svc_req *rqst;
struct rpc_msg *msg;
_svcauth_short (struct svc_req *rqst, struct rpc_msg *msg)
{
return (AUTH_REJECTEDCRED);
return AUTH_REJECTEDCRED;
}

View File

@ -41,126 +41,121 @@ static char sccsid[] = "@(#)svc_raw.c 1.15 87/08/11 Copyr 1984 Sun Micro";
*/
#include <rpc/rpc.h>
#include <rpc/svc.h>
/*
* This is the "network" that we will be moving data over
*/
static struct svcraw_private {
char _raw_buf[UDPMSGSIZE];
SVCXPRT server;
XDR xdr_stream;
char verf_body[MAX_AUTH_BYTES];
} *svcraw_private;
static struct svcraw_private
{
char _raw_buf[UDPMSGSIZE];
SVCXPRT server;
XDR xdr_stream;
char verf_body[MAX_AUTH_BYTES];
}
*svcraw_private;
static bool_t svcraw_recv();
static enum xprt_stat svcraw_stat();
static bool_t svcraw_getargs();
static bool_t svcraw_reply();
static bool_t svcraw_freeargs();
static void svcraw_destroy();
static bool_t svcraw_recv (SVCXPRT *, struct rpc_msg *);
static enum xprt_stat svcraw_stat (SVCXPRT *);
static bool_t svcraw_getargs (SVCXPRT *, xdrproc_t, caddr_t);
static bool_t svcraw_reply (SVCXPRT *, struct rpc_msg *);
static bool_t svcraw_freeargs (SVCXPRT *, xdrproc_t, caddr_t);
static void svcraw_destroy (SVCXPRT *);
static struct xp_ops server_ops = {
svcraw_recv,
svcraw_stat,
svcraw_getargs,
svcraw_reply,
svcraw_freeargs,
svcraw_destroy
static struct xp_ops server_ops =
{
svcraw_recv,
svcraw_stat,
svcraw_getargs,
svcraw_reply,
svcraw_freeargs,
svcraw_destroy
};
SVCXPRT *
svcraw_create()
svcraw_create (void)
{
register struct svcraw_private *srp = svcraw_private;
struct svcraw_private *srp = svcraw_private;
if (srp == 0) {
srp = (struct svcraw_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);
if (srp == 0)
{
srp = (struct svcraw_private *) calloc (1, sizeof (*srp));
if (srp == 0)
return NULL;
}
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()
svcraw_stat (SVCXPRT *xprt)
{
return (XPRT_IDLE);
return XPRT_IDLE;
}
static bool_t
svcraw_recv(xprt, msg)
SVCXPRT *xprt;
struct rpc_msg *msg;
svcraw_recv (xprt, msg)
SVCXPRT *xprt;
struct rpc_msg *msg;
{
register struct svcraw_private *srp = svcraw_private;
register XDR *xdrs;
struct svcraw_private *srp = svcraw_private;
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);
if (srp == 0)
return FALSE;
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(xprt, msg)
SVCXPRT *xprt;
struct rpc_msg *msg;
svcraw_reply (SVCXPRT *xprt, struct rpc_msg *msg)
{
register struct svcraw_private *srp = svcraw_private;
register XDR *xdrs;
struct svcraw_private *srp = svcraw_private;
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);
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(xprt, xdr_args, args_ptr)
SVCXPRT *xprt;
xdrproc_t xdr_args;
caddr_t args_ptr;
svcraw_getargs (SVCXPRT *xprt, xdrproc_t xdr_args, caddr_t args_ptr)
{
register struct svcraw_private *srp = svcraw_private;
struct svcraw_private *srp = svcraw_private;
if (srp == 0)
return (FALSE);
return ((*xdr_args)(&srp->xdr_stream, args_ptr));
if (srp == 0)
return FALSE;
return (*xdr_args) (&srp->xdr_stream, args_ptr);
}
static bool_t
svcraw_freeargs(xprt, xdr_args, args_ptr)
SVCXPRT *xprt;
xdrproc_t xdr_args;
caddr_t args_ptr;
svcraw_freeargs (SVCXPRT *xprt, xdrproc_t xdr_args, caddr_t args_ptr)
{
register struct svcraw_private *srp = svcraw_private;
register XDR *xdrs;
struct svcraw_private *srp = svcraw_private;
XDR *xdrs;
if (srp == 0)
return (FALSE);
xdrs = &srp->xdr_stream;
xdrs->x_op = XDR_FREE;
return ((*xdr_args)(xdrs, args_ptr));
if (srp == 0)
return FALSE;
xdrs = &srp->xdr_stream;
xdrs->x_op = XDR_FREE;
return (*xdr_args) (xdrs, args_ptr);
}
static void
svcraw_destroy()
svcraw_destroy (SVCXPRT *xprt)
{
}

View File

@ -36,39 +36,39 @@ static char sccsid[] = "@(#)svc_run.c 1.1 87/10/13 Copyr 1984 Sun Micro";
* This is the rpc server side idle loop
* Wait for input, call server program.
*/
#include <errno.h>
#include <rpc/rpc.h>
#include <sys/errno.h>
void
svc_run()
svc_run (void)
{
#ifdef FD_SETSIZE
fd_set readfds;
fd_set readfds;
#else
int readfds;
int readfds;
#endif /* def FD_SETSIZE */
#ifndef errno
extern int errno;
#endif
for (;;) {
for (;;)
{
#ifdef FD_SETSIZE
readfds = svc_fdset;
readfds = svc_fdset;
#else
readfds = svc_fds;
readfds = svc_fds;
#endif /* def FD_SETSIZE */
switch (select(_rpc_dtablesize(), &readfds, (int *)0, (int *)0,
(struct timeval *)0)) {
case -1:
if (errno == EINTR) {
continue;
}
perror("svc_run: - select failed");
return;
case 0:
continue;
default:
svc_getreqset(&readfds);
}
switch (select (_rpc_dtablesize (), &readfds, (fd_set *)NULL,
(fd_set *)NULL, (struct timeval *) 0))
{
case -1:
if (errno == EINTR)
{
continue;
}
perror (_("svc_run: - select failed"));
return;
case 0:
continue;
default:
svc_getreqset (&readfds);
}
}
}

View File

@ -39,105 +39,117 @@ static char sccsid[] = "@(#)svc_simple.c 1.18 87/08/11 Copyr 1984 Sun Micro";
*/
#include <stdio.h>
#include <string.h>
#include <rpc/rpc.h>
#include <rpc/pmap_clnt.h>
#include <sys/socket.h>
#include <netdb.h>
static struct proglst {
char *(*p_progname)();
int p_prognum;
int p_procnum;
xdrproc_t p_inproc, p_outproc;
struct proglst *p_nxt;
} *proglst;
static void universal();
static struct proglst
{
char *(*p_progname) (char *);
int p_prognum;
int p_procnum;
xdrproc_t p_inproc, p_outproc;
struct proglst *p_nxt;
}
*proglst;
static void universal (struct svc_req *rqstp, SVCXPRT *transp);
static SVCXPRT *transp;
registerrpc(prognum, versnum, procnum, progname, inproc, outproc)
char *(*progname)();
xdrproc_t inproc, outproc;
int
registerrpc (u_long prognum, u_long versnum, u_long procnum,
char *(*progname) (char *), xdrproc_t inproc, xdrproc_t outproc)
{
struct proglst *pl;
struct proglst *pl;
if (procnum == NULLPROC) {
(void) fprintf(stderr,
_("can't reassign procedure number %d\n"), NULLPROC);
return (-1);
if (procnum == NULLPROC)
{
(void) fprintf (stderr,
_("can't reassign procedure number %d\n"), NULLPROC);
return -1;
}
if (transp == 0)
{
transp = svcudp_create (RPC_ANYSOCK);
if (transp == NULL)
{
(void) fputs (_("couldn't create an rpc server\n"), stderr);
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 proglst *)malloc(sizeof(struct proglst));
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);
}
(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 proglst *) malloc (sizeof (struct proglst));
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(rqstp, transp)
struct svc_req *rqstp;
SVCXPRT *transp;
universal (struct svc_req *rqstp, SVCXPRT *transp)
{
int prog, proc;
char *outdata;
char xdrbuf[UDPMSGSIZE];
struct proglst *pl;
int prog, proc;
char *outdata;
char xdrbuf[UDPMSGSIZE];
struct proglst *pl;
/*
* enforce "procnum 0 is echo" convention
*/
if (rqstp->rq_proc == NULLPROC) {
if (svc_sendreply(transp, xdr_void, (char *)NULL) == FALSE) {
(void) fprintf(stderr, "xxx\n");
exit(1);
}
return;
/*
* enforce "procnum 0 is echo" convention
*/
if (rqstp->rq_proc == NULLPROC)
{
if (svc_sendreply (transp, (xdrproc_t)xdr_void, (char *) NULL) == FALSE)
{
(void) fprintf (stderr, "xxx\n");
exit (1);
}
prog = rqstp->rq_prog;
proc = rqstp->rq_proc;
for (pl = proglst; pl != NULL; pl = pl->p_nxt)
if (pl->p_prognum == prog && pl->p_procnum == proc) {
/* decode arguments into a CLEAN buffer */
bzero(xdrbuf, sizeof(xdrbuf)); /* required ! */
if (!svc_getargs(transp, pl->p_inproc, xdrbuf)) {
svcerr_decode(transp);
return;
}
outdata = (*(pl->p_progname))(xdrbuf);
if (outdata == NULL && pl->p_outproc != xdr_void)
/* there was an error */
return;
if (!svc_sendreply(transp, pl->p_outproc, outdata)) {
(void) fprintf(stderr,
_("trouble replying to prog %d\n"),
pl->p_prognum);
exit(1);
}
/* free the decoded arguments */
(void)svc_freeargs(transp, pl->p_inproc, xdrbuf);
return;
}
(void) fprintf(stderr, _("never registered prog %d\n"), prog);
exit(1);
return;
}
prog = rqstp->rq_prog;
proc = rqstp->rq_proc;
for (pl = proglst; pl != NULL; pl = pl->p_nxt)
if (pl->p_prognum == prog && pl->p_procnum == proc)
{
/* decode arguments into a CLEAN buffer */
bzero (xdrbuf, sizeof (xdrbuf)); /* required ! */
if (!svc_getargs (transp, pl->p_inproc, xdrbuf))
{
svcerr_decode (transp);
return;
}
outdata = (*(pl->p_progname)) (xdrbuf);
if (outdata == NULL && pl->p_outproc != (xdrproc_t)xdr_void)
/* there was an error */
return;
if (!svc_sendreply (transp, pl->p_outproc, outdata))
{
(void) fprintf (stderr,
_ ("trouble replying to prog %d\n"),
pl->p_prognum);
exit (1);
}
/* free the decoded arguments */
(void) svc_freeargs (transp, pl->p_inproc, xdrbuf);
return;
}
(void) fprintf (stderr, _ ("never registered prog %d\n"), prog);
exit (1);
}

View File

@ -42,66 +42,70 @@ static char sccsid[] = "@(#)svc_tcp.c 1.21 87/08/11 Copyr 1984 Sun Micro";
*/
#include <stdio.h>
#include <unistd.h>
#include <string.h>
#include <rpc/rpc.h>
#include <sys/socket.h>
#include <errno.h>
#define abort ((bool_t (*) ()) abort)
#ifndef errno
extern errno;
#endif
#include <stdlib.h>
/*
* Ops vector for TCP/IP based rpc service handle
*/
static bool_t svctcp_recv();
static enum xprt_stat svctcp_stat();
static bool_t svctcp_getargs();
static bool_t svctcp_reply();
static bool_t svctcp_freeargs();
static void svctcp_destroy();
static bool_t svctcp_recv (SVCXPRT *, struct rpc_msg *);
static enum xprt_stat svctcp_stat (SVCXPRT *);
static bool_t svctcp_getargs (SVCXPRT *, xdrproc_t, caddr_t);
static bool_t svctcp_reply (SVCXPRT *, struct rpc_msg *);
static bool_t svctcp_freeargs (SVCXPRT *, xdrproc_t, caddr_t);
static void svctcp_destroy (SVCXPRT *);
static struct xp_ops svctcp_op = {
svctcp_recv,
svctcp_stat,
svctcp_getargs,
svctcp_reply,
svctcp_freeargs,
svctcp_destroy
static const 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();
static enum xprt_stat rendezvous_stat();
static bool_t rendezvous_request (SVCXPRT *, struct rpc_msg *);
static enum xprt_stat rendezvous_stat (SVCXPRT *);
static struct xp_ops svctcp_rendezvous_op = {
rendezvous_request,
rendezvous_stat,
abort,
abort,
abort,
svctcp_destroy
static const struct xp_ops svctcp_rendezvous_op =
{
rendezvous_request,
rendezvous_stat,
(bool_t (*) (SVCXPRT *, xdrproc_t, caddr_t)) abort,
(bool_t (*) (SVCXPRT *, struct rpc_msg *)) abort,
(bool_t (*) (SVCXPRT *, xdrproc_t, caddr_t)) abort,
svctcp_destroy
};
static int readtcp(), writetcp();
static SVCXPRT *makefd_xprt();
static int readtcp (char*, char *, int);
static int writetcp (char *, char *, int);
static SVCXPRT *makefd_xprt (int, u_int, u_int);
struct tcp_rendezvous { /* kept in xprt->xp_p1 */
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];
};
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);
* 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
@ -120,57 +124,60 @@ struct tcp_conn { /* kept in xprt->xp_p1 */
* 0 => use the system default.
*/
SVCXPRT *
svctcp_create(sock, sendsize, recvsize)
register int sock;
u_int sendsize;
u_int recvsize;
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;
int len = sizeof(struct sockaddr_in);
bool_t madesock = FALSE;
SVCXPRT *xprt;
struct tcp_rendezvous *r;
struct sockaddr_in addr;
int len = sizeof (struct sockaddr_in);
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;
if (sock == RPC_ANYSOCK)
{
if ((sock = socket (AF_INET, SOCK_STREAM, IPPROTO_TCP)) < 0)
{
perror (_("svctcp_.c - udp socket creation problem"));
return (SVCXPRT *) NULL;
}
bzero((char *)&addr, sizeof (addr));
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)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);
madesock = TRUE;
}
bzero ((char *) &addr, sizeof (addr));
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) close (sock);
return (SVCXPRT *) NULL;
}
r = (struct tcp_rendezvous *) mem_alloc (sizeof (*r));
if (r == NULL)
{
(void) fputs (_("svctcp_create: out of memory\n"), stderr);
return NULL;
}
r->sendsize = sendsize;
r->recvsize = recvsize;
xprt = (SVCXPRT *) mem_alloc (sizeof (SVCXPRT));
if (xprt == NULL)
{
(void) fputs (_("svctcp_create: out of memory\n"), stderr);
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;
}
/*
@ -178,109 +185,106 @@ svctcp_create(sock, sendsize, recvsize)
* descriptor as its first input.
*/
SVCXPRT *
svcfd_create(fd, sendsize, recvsize)
int fd;
u_int sendsize;
u_int recvsize;
svcfd_create (int fd, u_int sendsize, u_int recvsize)
{
return (makefd_xprt(fd, sendsize, recvsize));
return makefd_xprt (fd, sendsize, recvsize);
}
static SVCXPRT *
makefd_xprt(fd, sendsize, recvsize)
int fd;
u_int sendsize;
u_int recvsize;
makefd_xprt (int fd, u_int sendsize, u_int recvsize)
{
register SVCXPRT *xprt;
register struct tcp_conn *cd;
SVCXPRT *xprt;
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; /* truly deals with calls */
xprt->xp_port = 0; /* this is a connection, not a rendezvouser */
xprt->xp_sock = fd;
xprt_register(xprt);
done:
return (xprt);
xprt = (SVCXPRT *) mem_alloc (sizeof (SVCXPRT));
if (xprt == (SVCXPRT *) NULL)
{
(void) fputs (_("svc_tcp: makefd_xprt: out of memory\n"), stderr);
goto done;
}
cd = (struct tcp_conn *) mem_alloc (sizeof (struct tcp_conn));
if (cd == (struct tcp_conn *) NULL)
{
(void) fputs (_("svc_tcp: makefd_xprt: out of memory\n"), stderr);
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; /* truly 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(xprt)
register SVCXPRT *xprt;
rendezvous_request (SVCXPRT *xprt, struct rpc_msg *errmsg)
{
int sock;
struct tcp_rendezvous *r;
struct sockaddr_in addr;
int len;
int sock;
struct tcp_rendezvous *r;
struct sockaddr_in addr;
int len;
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);
}
/*
* 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 */
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;
}
/*
* 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()
rendezvous_stat (SVCXPRT *xprt)
{
return (XPRT_IDLE);
return XPRT_IDLE;
}
static void
svctcp_destroy(xprt)
register SVCXPRT *xprt;
svctcp_destroy (SVCXPRT *xprt)
{
register struct tcp_conn *cd = (struct tcp_conn *)xprt->xp_p1;
struct tcp_conn *cd = (struct tcp_conn *) xprt->xp_p1;
xprt_unregister(xprt);
(void)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));
xprt_unregister (xprt);
(void) 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 };
static struct timeval wait_per_try =
{35, 0};
/*
* reads data from the tcp connection.
@ -288,43 +292,47 @@ static struct timeval wait_per_try = { 35, 0 };
* (And a read of zero bytes is a half closed stream => error.)
*/
static int
readtcp(xprt, buf, len)
register SVCXPRT *xprt;
caddr_t buf;
register int len;
readtcp (char *xprtptr, char *buf, int len)
{
register int sock = xprt->xp_sock;
SVCXPRT *xprt = (SVCXPRT *)xprtptr;
int sock = xprt->xp_sock;
#ifdef FD_SETSIZE
fd_set mask;
fd_set readfds;
fd_set mask;
fd_set readfds;
FD_ZERO(&mask);
FD_SET(sock, &mask);
FD_ZERO (&mask);
FD_SET (sock, &mask);
#else
register int mask = 1 << sock;
int readfds;
int mask = 1 << sock;
int readfds;
#endif /* def FD_SETSIZE */
do {
struct timeval timeout = wait_per_try;
readfds = mask;
if (select(_rpc_dtablesize(), &readfds, (int*)NULL, (int*)NULL,
&timeout) <= 0) {
if (errno == EINTR) {
continue;
}
goto fatal_err;
}
#ifdef FD_SETSIZE
} while (!FD_ISSET(sock, &readfds));
#else
} while (readfds != mask);
#endif /* def FD_SETSIZE */
if ((len = read(sock, buf, len)) > 0) {
return (len);
do
{
struct timeval timeout = wait_per_try;
readfds = mask;
if (select (_rpc_dtablesize (), &readfds, (fd_set *) NULL,
(fd_set *) NULL, &timeout) <= 0)
{
if (errno == EINTR)
{
continue;
}
goto fatal_err;
}
#ifdef FD_SETSIZE
}
while (!FD_ISSET (sock, &readfds));
#else
}
while (readfds != mask);
#endif /* def FD_SETSIZE */
if ((len = read (sock, buf, len)) > 0)
{
return len;
}
fatal_err:
((struct tcp_conn *)(xprt->xp_p1))->strm_stat = XPRT_DIED;
return (-1);
((struct tcp_conn *) (xprt->xp_p1))->strm_stat = XPRT_DIED;
return -1;
}
/*
@ -332,91 +340,91 @@ fatal_err:
* Any error is fatal and the connection is closed.
*/
static int
writetcp(xprt, buf, len)
register SVCXPRT *xprt;
caddr_t buf;
int len;
writetcp (char *xprtptr, char * buf, int len)
{
register int i, cnt;
SVCXPRT *xprt = (SVCXPRT *)xprtptr;
int i, cnt;
for (cnt = len; cnt > 0; cnt -= i, buf += i) {
if ((i = write(xprt->xp_sock, buf, cnt)) < 0) {
((struct tcp_conn *)(xprt->xp_p1))->strm_stat =
XPRT_DIED;
return (-1);
}
for (cnt = len; cnt > 0; cnt -= i, buf += i)
{
if ((i = write (xprt->xp_sock, buf, cnt)) < 0)
{
((struct tcp_conn *) (xprt->xp_p1))->strm_stat =
XPRT_DIED;
return (-1);
}
return (len);
}
return (len);
}
static enum xprt_stat
svctcp_stat(xprt)
SVCXPRT *xprt;
svctcp_stat (SVCXPRT *xprt)
{
register struct tcp_conn *cd =
(struct tcp_conn *)(xprt->xp_p1);
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);
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(xprt, msg)
SVCXPRT *xprt;
register struct rpc_msg *msg;
svctcp_recv (xprt, msg)
SVCXPRT *xprt;
struct rpc_msg *msg;
{
register struct tcp_conn *cd =
(struct tcp_conn *)(xprt->xp_p1);
register XDR *xdrs = &(cd->xdrs);
struct tcp_conn *cd =
(struct tcp_conn *) (xprt->xp_p1);
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);
}
return (FALSE);
xdrs->x_op = XDR_DECODE;
(void) xdrrec_skiprecord (xdrs);
if (xdr_callmsg (xdrs, msg))
{
cd->x_id = msg->rm_xid;
return (TRUE);
}
return (FALSE);
}
static bool_t
svctcp_getargs(xprt, xdr_args, args_ptr)
SVCXPRT *xprt;
xdrproc_t xdr_args;
caddr_t args_ptr;
svctcp_getargs (xprt, xdr_args, args_ptr)
SVCXPRT *xprt;
xdrproc_t xdr_args;
caddr_t args_ptr;
{
return ((*xdr_args)(&(((struct tcp_conn *)(xprt->xp_p1))->xdrs), args_ptr));
return ((*xdr_args) (&(((struct tcp_conn *) (xprt->xp_p1))->xdrs), args_ptr));
}
static bool_t
svctcp_freeargs(xprt, xdr_args, args_ptr)
SVCXPRT *xprt;
xdrproc_t xdr_args;
caddr_t args_ptr;
svctcp_freeargs (xprt, xdr_args, args_ptr)
SVCXPRT *xprt;
xdrproc_t xdr_args;
caddr_t args_ptr;
{
register XDR *xdrs =
&(((struct tcp_conn *)(xprt->xp_p1))->xdrs);
XDR *xdrs =
&(((struct tcp_conn *) (xprt->xp_p1))->xdrs);
xdrs->x_op = XDR_FREE;
return ((*xdr_args)(xdrs, args_ptr));
xdrs->x_op = XDR_FREE;
return ((*xdr_args) (xdrs, args_ptr));
}
static bool_t
svctcp_reply(xprt, msg)
SVCXPRT *xprt;
register struct rpc_msg *msg;
svctcp_reply (xprt, msg)
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;
struct tcp_conn *cd =
(struct tcp_conn *) (xprt->xp_p1);
XDR *xdrs = &(cd->xdrs);
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);
xdrs->x_op = XDR_ENCODE;
msg->rm_xid = cd->x_id;
stat = xdr_replymsg (xdrs, msg);
(void) xdrrec_endofrecord (xdrs, TRUE);
return (stat);
}

View File

@ -40,6 +40,8 @@ static char sccsid[] = "@(#)svc_udp.c 1.24 87/08/11 Copyr 1984 Sun Micro";
*/
#include <stdio.h>
#include <unistd.h>
#include <string.h>
#include <rpc/rpc.h>
#include <sys/socket.h>
#include <errno.h>
@ -47,44 +49,46 @@ static char sccsid[] = "@(#)svc_udp.c 1.24 87/08/11 Copyr 1984 Sun Micro";
#define rpc_buffer(xprt) ((xprt)->xp_p1)
#ifndef MAX
# define MAX(a, b) ((a > b) ? a : b)
#define MAX(a, b) ((a > b) ? a : b)
#endif
static bool_t svcudp_recv();
static bool_t svcudp_reply();
static enum xprt_stat svcudp_stat();
static bool_t svcudp_getargs();
static bool_t svcudp_freeargs();
static void svcudp_destroy();
static bool_t svcudp_recv (SVCXPRT *, struct rpc_msg *);
static bool_t svcudp_reply (SVCXPRT *, struct rpc_msg *);
static enum xprt_stat svcudp_stat (SVCXPRT *);
static bool_t svcudp_getargs (SVCXPRT *, xdrproc_t, caddr_t);
static bool_t svcudp_freeargs (SVCXPRT *, xdrproc_t, caddr_t);
static void svcudp_destroy (SVCXPRT *);
static struct xp_ops svcudp_op = {
svcudp_recv,
svcudp_stat,
svcudp_getargs,
svcudp_reply,
svcudp_freeargs,
svcudp_destroy
static const struct xp_ops svcudp_op =
{
svcudp_recv,
svcudp_stat,
svcudp_getargs,
svcudp_reply,
svcudp_freeargs,
svcudp_destroy
};
#ifndef errno
extern int errno;
#endif
static int cache_get (SVCXPRT *, struct rpc_msg *, char **replyp,
u_long *replylenp);
static void cache_set (SVCXPRT *xprt, u_long replylen);
/*
* 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 */
};
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);
* 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
@ -96,173 +100,184 @@ struct svcudp_data {
* The routines returns NULL if a problem occurred.
*/
SVCXPRT *
svcudp_bufcreate(sock, sendsz, recvsz)
register int sock;
u_int sendsz, recvsz;
svcudp_bufcreate (sock, sendsz, recvsz)
int sock;
u_int sendsz, recvsz;
{
bool_t madesock = FALSE;
register SVCXPRT *xprt;
register struct svcudp_data *su;
struct sockaddr_in addr;
int len = sizeof(struct sockaddr_in);
bool_t madesock = FALSE;
SVCXPRT *xprt;
struct svcudp_data *su;
struct sockaddr_in addr;
int 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;
if (sock == RPC_ANYSOCK)
{
if ((sock = socket (AF_INET, SOCK_DGRAM, IPPROTO_UDP)) < 0)
{
perror (_("svcudp_create: socket creation problem"));
return (SVCXPRT *) NULL;
}
bzero((char *)&addr, sizeof (addr));
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)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);
madesock = TRUE;
}
bzero ((char *) &addr, sizeof (addr));
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) close (sock);
return (SVCXPRT *) NULL;
}
xprt = (SVCXPRT *) mem_alloc (sizeof (SVCXPRT));
if (xprt == NULL)
{
(void) fputs (_("svcudp_create: out of memory\n"), stderr);
return NULL;
}
su = (struct svcudp_data *) mem_alloc (sizeof (*su));
if (su == NULL)
{
(void) fputs (_("svcudp_create: out of memory\n"), stderr);
return NULL;
}
su->su_iosz = ((MAX (sendsz, recvsz) + 3) / 4) * 4;
if ((rpc_buffer (xprt) = mem_alloc (su->su_iosz)) == NULL)
{
(void) fputs (_("svcudp_create: out of memory\n"), stderr);
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(sock)
int sock;
svcudp_create (sock)
int sock;
{
return(svcudp_bufcreate(sock, UDPMSGSIZE, UDPMSGSIZE));
return svcudp_bufcreate (sock, UDPMSGSIZE, UDPMSGSIZE);
}
static enum xprt_stat
svcudp_stat(xprt)
SVCXPRT *xprt;
svcudp_stat (xprt)
SVCXPRT *xprt;
{
return (XPRT_IDLE);
return XPRT_IDLE;
}
static bool_t
svcudp_recv(xprt, msg)
register SVCXPRT *xprt;
struct rpc_msg *msg;
svcudp_recv (xprt, msg)
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;
struct svcudp_data *su = su_data (xprt);
XDR *xdrs = &(su->su_xdrs);
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 < 16) /* < 4 32-bit ints? */
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);
}
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 < 16) /* < 4 32-bit ints? */
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);
}
return TRUE;
}
static bool_t
svcudp_reply(xprt, msg)
register SVCXPRT *xprt;
struct rpc_msg *msg;
svcudp_reply (xprt, msg)
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;
struct svcudp_data *su = su_data (xprt);
XDR *xdrs = &(su->su_xdrs);
int slen;
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);
}
}
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);
}
return stat;
}
static bool_t
svcudp_getargs(xprt, xdr_args, args_ptr)
SVCXPRT *xprt;
xdrproc_t xdr_args;
caddr_t args_ptr;
svcudp_getargs (xprt, xdr_args, args_ptr)
SVCXPRT *xprt;
xdrproc_t xdr_args;
caddr_t args_ptr;
{
return ((*xdr_args)(&(su_data(xprt)->su_xdrs), args_ptr));
return (*xdr_args) (&(su_data (xprt)->su_xdrs), args_ptr);
}
static bool_t
svcudp_freeargs(xprt, xdr_args, args_ptr)
SVCXPRT *xprt;
xdrproc_t xdr_args;
caddr_t args_ptr;
svcudp_freeargs (xprt, xdr_args, args_ptr)
SVCXPRT *xprt;
xdrproc_t xdr_args;
caddr_t args_ptr;
{
register XDR *xdrs = &(su_data(xprt)->su_xdrs);
XDR *xdrs = &(su_data (xprt)->su_xdrs);
xdrs->x_op = XDR_FREE;
return ((*xdr_args)(xdrs, args_ptr));
xdrs->x_op = XDR_FREE;
return (*xdr_args) (xdrs, args_ptr);
}
static void
svcudp_destroy(xprt)
register SVCXPRT *xprt;
svcudp_destroy (xprt)
SVCXPRT *xprt;
{
register struct svcudp_data *su = su_data(xprt);
struct svcudp_data *su = su_data (xprt);
xprt_unregister(xprt);
(void)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));
xprt_unregister (xprt);
(void) 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));
}
@ -274,7 +289,7 @@ svcudp_destroy(xprt)
* Buffers are sent again if retransmissions are detected.
*/
#define SPARSENESS 4 /* 75% sparse */
#define SPARSENESS 4 /* 75% sparse */
#define CACHE_PERROR(msg) \
(void) fprintf(stderr,"%s\n", msg)
@ -289,41 +304,43 @@ svcudp_destroy(xprt)
* 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;
};
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 */
};
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 */
};
/*
@ -337,142 +354,151 @@ struct udp_cache {
* Enable use of the cache.
* Note: there is no disable.
*/
svcudp_enablecache(transp, size)
SVCXPRT *transp;
u_long size;
int
svcudp_enablecache (SVCXPRT *transp, u_long size)
{
struct svcudp_data *su = su_data(transp);
struct udp_cache *uc;
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);
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
cache_set(xprt, replylen)
SVCXPRT *xprt;
u_long replylen;
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;
cache_ptr victim;
cache_ptr *vicp;
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;
}
/*
* 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;
/*
* 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
cache_get(xprt, msg, replyp, replylenp)
SVCXPRT *xprt;
struct rpc_msg *msg;
char **replyp;
u_long *replylenp;
static int
cache_get (xprt, msg, replyp, replylenp)
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;
u_int loc;
cache_ptr ent;
struct svcudp_data *su = su_data (xprt);
struct udp_cache *uc = (struct udp_cache *) su->su_cache;
# define EQADDR(a1, a2) (bcmp((char*)&a1, (char*)&a2, sizeof(a1)) == 0)
#define EQADDR(a1, a2) (bcmp((char*)&a1, (char*)&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);
}
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);
}
/*
* 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;
}

View File

@ -57,72 +57,72 @@ static char sccsid[] = "@(#)xdr.c 1.35 87/08/12";
/*
* for unit alignment
*/
static char xdr_zero[BYTES_PER_XDR_UNIT] = { 0, 0, 0, 0 };
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(proc, objp)
xdrproc_t proc;
char *objp;
xdr_free (proc, objp)
xdrproc_t proc;
char *objp;
{
XDR x;
XDR x;
x.x_op = XDR_FREE;
(*proc)(&x, objp);
x.x_op = XDR_FREE;
(*proc) (&x, objp);
}
/*
* XDR nothing
*/
bool_t
xdr_void(/* xdrs, addr */)
/* XDR *xdrs; */
/* caddr_t addr; */
xdr_void (void)
{
return (TRUE);
return TRUE;
}
/*
* XDR integers
*/
bool_t
xdr_int(xdrs, ip)
XDR *xdrs;
int *ip;
xdr_int (xdrs, ip)
XDR *xdrs;
int *ip;
{
#ifdef lint
(void) (xdr_short(xdrs, (short *)ip));
return (xdr_long(xdrs, (long *)ip));
(void) (xdr_short (xdrs, (short *) ip));
return (xdr_long (xdrs, (long *) ip));
#else
# if INT_MAX < LONG_MAX
long l;
#if INT_MAX < LONG_MAX
long l;
switch (xdrs->x_op) {
case XDR_ENCODE:
l = (long) *ip;
return XDR_PUTLONG(xdrs, &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;
case XDR_FREE:
return TRUE;
case XDR_DECODE:
if (!XDR_GETLONG (xdrs, &l))
{
return FALSE;
}
return FALSE;
# elif INT_MAX == LONG_MAX
return xdr_long(xdrs, (long *)ip);
# elif INT_MAX == SHRT_MAX
return xdr_short(xdrs, (short *)ip);
# else
# error unexpected integer sizes in_xdr_int()
# endif
*ip = (int) l;
case XDR_FREE:
return TRUE;
}
return FALSE;
#elif INT_MAX == LONG_MAX
return xdr_long (xdrs, (long *) ip);
#elif INT_MAX == SHRT_MAX
return xdr_short (xdrs, (short *) ip);
#else
#error unexpected integer sizes in_xdr_int()
#endif
#endif
}
@ -130,38 +130,40 @@ xdr_int(xdrs, ip)
* XDR unsigned integers
*/
bool_t
xdr_u_int(xdrs, up)
XDR *xdrs;
u_int *up;
xdr_u_int (xdrs, up)
XDR *xdrs;
u_int *up;
{
#ifdef lint
(void) (xdr_short(xdrs, (short *)up));
return (xdr_u_long(xdrs, (u_long *)up));
(void) (xdr_short (xdrs, (short *) up));
return (xdr_u_long (xdrs, (u_long *) up));
#else
# if UINT_MAX < ULONG_MAX
u_long l;
#if UINT_MAX < ULONG_MAX
u_long l;
switch (xdrs->x_op) {
case XDR_ENCODE:
l = (u_long) *up;
return XDR_PUTLONG(xdrs, &l);
switch (xdrs->x_op)
{
case XDR_ENCODE:
l = (u_long) * up;
return XDR_PUTLONG (xdrs, &l);
case XDR_DECODE:
if (!XDR_GETLONG(xdrs, &l)) {
return FALSE;
}
*up = (u_int) l;
case XDR_FREE:
return TRUE;
case XDR_DECODE:
if (!XDR_GETLONG (xdrs, &l))
{
return FALSE;
}
return FALSE;
# elif UINT_MAX == ULONG_MAX
return xdr_u_long(xdrs, (u_long *)up);
# elif UINT_MAX == USHRT_MAX
return xdr_short(xdrs, (short *)up);
# else
# error unexpected integer sizes in_xdr_u_int()
# endif
*up = (u_int) l;
case XDR_FREE:
return TRUE;
}
return FALSE;
#elif UINT_MAX == ULONG_MAX
return xdr_u_long (xdrs, (u_long *) up);
#elif UINT_MAX == USHRT_MAX
return xdr_short (xdrs, (short *) up);
#else
#error unexpected integer sizes in_xdr_u_int()
#endif
#endif
}
@ -170,21 +172,21 @@ xdr_u_int(xdrs, up)
* same as xdr_u_long - open coded to save a proc call!
*/
bool_t
xdr_long(xdrs, lp)
register XDR *xdrs;
long *lp;
xdr_long (xdrs, lp)
XDR *xdrs;
long *lp;
{
if (xdrs->x_op == XDR_ENCODE)
return (XDR_PUTLONG(xdrs, lp));
if (xdrs->x_op == XDR_ENCODE)
return XDR_PUTLONG (xdrs, lp);
if (xdrs->x_op == XDR_DECODE)
return (XDR_GETLONG(xdrs, lp));
if (xdrs->x_op == XDR_DECODE)
return XDR_GETLONG (xdrs, lp);
if (xdrs->x_op == XDR_FREE)
return (TRUE);
if (xdrs->x_op == XDR_FREE)
return TRUE;
return (FALSE);
return FALSE;
}
/*
@ -192,77 +194,82 @@ xdr_long(xdrs, lp)
* same as xdr_long - open coded to save a proc call!
*/
bool_t
xdr_u_long(xdrs, ulp)
register XDR *xdrs;
u_long *ulp;
xdr_u_long (xdrs, ulp)
XDR *xdrs;
u_long *ulp;
{
switch (xdrs->x_op) {
case XDR_DECODE:
return XDR_GETLONG(xdrs, (long *)ulp);
switch (xdrs->x_op)
{
case XDR_DECODE:
return XDR_GETLONG (xdrs, (long *) ulp);
case XDR_ENCODE:
return XDR_PUTLONG(xdrs, (long *)ulp);
case XDR_ENCODE:
return XDR_PUTLONG (xdrs, (long *) ulp);
case XDR_FREE:
return TRUE;
}
return FALSE;
case XDR_FREE:
return TRUE;
}
return FALSE;
}
/*
* XDR short integers
*/
bool_t
xdr_short(xdrs, sp)
register XDR *xdrs;
short *sp;
xdr_short (xdrs, sp)
XDR *xdrs;
short *sp;
{
long l;
long l;
switch (xdrs->x_op) {
case XDR_ENCODE:
l = (long) *sp;
return XDR_PUTLONG(xdrs, &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;
case XDR_DECODE:
if (!XDR_GETLONG (xdrs, &l))
{
return FALSE;
}
return FALSE;
*sp = (short) l;
return TRUE;
case XDR_FREE:
return TRUE;
}
return FALSE;
}
/*
* XDR unsigned short integers
*/
bool_t
xdr_u_short(xdrs, usp)
register XDR *xdrs;
u_short *usp;
xdr_u_short (xdrs, usp)
XDR *xdrs;
u_short *usp;
{
u_long l;
u_long l;
switch (xdrs->x_op) {
case XDR_ENCODE:
l = (u_long) *usp;
return XDR_PUTLONG(xdrs, &l);
switch (xdrs->x_op)
{
case XDR_ENCODE:
l = (u_long) * usp;
return XDR_PUTLONG (xdrs, &l);
case XDR_DECODE:
if (!XDR_GETLONG(xdrs, &l)) {
return FALSE;
}
*usp = (u_short) l;
return TRUE;
case XDR_FREE:
return TRUE;
case XDR_DECODE:
if (!XDR_GETLONG (xdrs, &l))
{
return FALSE;
}
return FALSE;
*usp = (u_short) l;
return TRUE;
case XDR_FREE:
return TRUE;
}
return FALSE;
}
@ -270,110 +277,124 @@ xdr_u_short(xdrs, usp)
* XDR a char
*/
bool_t
xdr_char(xdrs, cp)
XDR *xdrs;
char *cp;
xdr_char (xdrs, cp)
XDR *xdrs;
char *cp;
{
int i;
int i;
i = (*cp);
if (!xdr_int(xdrs, &i)) {
return FALSE;
}
*cp = i;
return TRUE;
i = (*cp);
if (!xdr_int (xdrs, &i))
{
return FALSE;
}
*cp = i;
return TRUE;
}
/*
* XDR an unsigned char
*/
bool_t
xdr_u_char(xdrs, cp)
XDR *xdrs;
u_char *cp;
xdr_u_char (xdrs, cp)
XDR *xdrs;
u_char *cp;
{
u_int u;
u_int u;
u = (*cp);
if (!xdr_u_int(xdrs, &u)) {
return FALSE;
}
*cp = u;
return TRUE;
u = (*cp);
if (!xdr_u_int (xdrs, &u))
{
return FALSE;
}
*cp = u;
return TRUE;
}
/*
* XDR booleans
*/
bool_t
xdr_bool(xdrs, bp)
register XDR *xdrs;
bool_t *bp;
xdr_bool (xdrs, bp)
XDR *xdrs;
bool_t *bp;
{
long lb;
long lb;
switch (xdrs->x_op) {
case XDR_ENCODE:
lb = *bp ? XDR_TRUE : XDR_FALSE;
return XDR_PUTLONG(xdrs, &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;
case XDR_DECODE:
if (!XDR_GETLONG (xdrs, &lb))
{
return FALSE;
}
return FALSE;
*bp = (lb == XDR_FALSE) ? FALSE : TRUE;
return TRUE;
case XDR_FREE:
return TRUE;
}
return FALSE;
}
/*
* XDR enumerations
*/
bool_t
xdr_enum(xdrs, ep)
XDR *xdrs;
enum_t *ep;
xdr_enum (xdrs, ep)
XDR *xdrs;
enum_t *ep;
{
#ifndef lint
enum sizecheck { SIZEVAL }; /* used to find the size of an enum */
enum sizecheck
{
SIZEVAL
}; /* used to find the size of an enum */
/*
* enums are treated as ints
*/
if (sizeof (enum sizecheck) == 4) {
# if INT_MAX < LONG_MAX
long l;
/*
* enums are treated as ints
*/
if (sizeof (enum sizecheck) == 4)
{
#if INT_MAX < LONG_MAX
long l;
switch (xdrs->x_op) {
case XDR_ENCODE:
l = *ep;
return XDR_PUTLONG(xdrs, &l);
switch (xdrs->x_op)
{
case XDR_ENCODE:
l = *ep;
return XDR_PUTLONG (xdrs, &l);
case XDR_DECODE:
if (!XDR_GETLONG(xdrs, &l)) {
return FALSE;
}
*ep = l;
case XDR_FREE:
return TRUE;
case XDR_DECODE:
if (!XDR_GETLONG (xdrs, &l))
{
return FALSE;
}
*ep = l;
case XDR_FREE:
return TRUE;
}
return FALSE;
# else
return (xdr_long(xdrs, (long *)ep));
# endif
} else if (sizeof (enum sizecheck) == sizeof (short)) {
return xdr_short(xdrs, (short *)ep);
} else {
return FALSE;
}
return FALSE;
#else
return xdr_long (xdrs, (long *) ep);
#endif
}
else if (sizeof (enum sizecheck) == sizeof (short))
{
return xdr_short (xdrs, (short *) ep);
}
else
{
return FALSE;
}
#else /* lint */
(void) (xdr_short(xdrs, (short *)ep));
return (xdr_long(xdrs, (long *)ep));
(void) (xdr_short (xdrs, (short *) ep));
return xdr_long (xdrs, (long *) ep);
#endif /* lint */
}
@ -383,48 +404,51 @@ xdr_enum(xdrs, ep)
* cp points to the opaque object and cnt gives the byte length.
*/
bool_t
xdr_opaque(xdrs, cp, cnt)
register XDR *xdrs;
caddr_t cp;
register u_int cnt;
xdr_opaque (xdrs, cp, cnt)
XDR *xdrs;
caddr_t cp;
u_int cnt;
{
register u_int rndup;
static crud[BYTES_PER_XDR_UNIT];
u_int rndup;
static char crud[BYTES_PER_XDR_UNIT];
/*
* if no data we are done
*/
if (cnt == 0)
return TRUE;
/*
* 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;
/*
* round byte count to full xdr units
*/
rndup = cnt % BYTES_PER_XDR_UNIT;
if (rndup > 0)
rndup = BYTES_PER_XDR_UNIT - rndup;
switch (xdrs->x_op) {
case XDR_DECODE:
if (!XDR_GETBYTES(xdrs, cp, cnt)) {
return FALSE;
}
if (rndup == 0)
return TRUE;
return XDR_GETBYTES(xdrs, crud, rndup);
case XDR_ENCODE:
if (!XDR_PUTBYTES(xdrs, cp, cnt)) {
return FALSE;
}
if (rndup == 0)
return TRUE;
return XDR_PUTBYTES(xdrs, xdr_zero, rndup);
case XDR_FREE:
return TRUE;
switch (xdrs->x_op)
{
case XDR_DECODE:
if (!XDR_GETBYTES (xdrs, cp, cnt))
{
return FALSE;
}
return FALSE;
if (rndup == 0)
return TRUE;
return XDR_GETBYTES (xdrs, (caddr_t)crud, rndup);
case XDR_ENCODE:
if (!XDR_PUTBYTES (xdrs, cp, cnt))
{
return FALSE;
}
if (rndup == 0)
return TRUE;
return XDR_PUTBYTES (xdrs, xdr_zero, rndup);
case XDR_FREE:
return TRUE;
}
return FALSE;
}
/*
@ -433,66 +457,73 @@ xdr_opaque(xdrs, cp, cnt)
* If *cpp is NULL maxsize bytes are allocated
*/
bool_t
xdr_bytes(xdrs, cpp, sizep, maxsize)
register XDR *xdrs;
char **cpp;
register u_int *sizep;
u_int maxsize;
xdr_bytes (xdrs, cpp, sizep, maxsize)
XDR *xdrs;
char **cpp;
u_int *sizep;
u_int maxsize;
{
register char *sp = *cpp; /* sp is the actual string pointer */
register u_int nodesize;
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;
/*
* 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;
}
nodesize = *sizep;
if ((nodesize > maxsize) && (xdrs->x_op != XDR_FREE)) {
return FALSE;
if (sp == NULL)
{
*cpp = sp = (char *) mem_alloc (nodesize);
}
/*
* now deal with the actual bytes
*/
switch (xdrs->x_op) {
case XDR_DECODE:
if (nodesize == 0) {
return TRUE;
}
if (sp == NULL) {
*cpp = sp = (char *)mem_alloc(nodesize);
}
if (sp == NULL) {
(void) fprintf(stderr, "xdr_bytes: out of memory\n");
return FALSE;
}
/* fall into ... */
case XDR_ENCODE:
return xdr_opaque(xdrs, sp, nodesize);
case XDR_FREE:
if (sp != NULL) {
mem_free(sp, nodesize);
*cpp = NULL;
}
return TRUE;
if (sp == NULL)
{
(void) fprintf (stderr, "xdr_bytes: out of memory\n");
return FALSE;
}
return FALSE;
/* fall into ... */
case XDR_ENCODE:
return xdr_opaque (xdrs, sp, nodesize);
case XDR_FREE:
if (sp != NULL)
{
mem_free (sp, nodesize);
*cpp = NULL;
}
return TRUE;
}
return FALSE;
}
/*
* Implemented here due to commonality of the object.
*/
bool_t
xdr_netobj(xdrs, np)
XDR *xdrs;
struct netobj *np;
xdr_netobj (xdrs, np)
XDR *xdrs;
struct netobj *np;
{
return xdr_bytes(xdrs, &np->n_bytes, &np->n_len, MAX_NETOBJ_SZ);
return xdr_bytes (xdrs, &np->n_bytes, &np->n_len, MAX_NETOBJ_SZ);
}
/*
@ -507,37 +538,39 @@ xdr_netobj(xdrs, np)
* If there is no specific or default routine an error is returned.
*/
bool_t
xdr_union(xdrs, dscmp, unp, choices, dfault)
register XDR *xdrs;
enum_t *dscmp; /* enum to decide which arm to work on */
char *unp; /* the union itself */
struct xdr_discrim *choices; /* [value, xdr proc] for each arm */
xdrproc_t dfault; /* default xdr routine */
xdr_union (xdrs, dscmp, unp, choices, dfault)
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 */
{
register enum_t dscm;
enum_t dscm;
/*
* we deal with the discriminator; it's an enum
*/
if (! xdr_enum(xdrs, dscmp)) {
return FALSE;
}
dscm = *dscmp;
/*
* 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);
}
/*
* 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));
/*
* no match - execute the default xdr routine if there is one
*/
return ((dfault == NULL_xdrproc_t) ? FALSE :
(*dfault) (xdrs, unp, LASTUNSIGNED));
}
@ -556,64 +589,73 @@ xdr_union(xdrs, dscmp, unp, choices, dfault)
* of the string as specified by a protocol.
*/
bool_t
xdr_string(xdrs, cpp, maxsize)
register XDR *xdrs;
char **cpp;
u_int maxsize;
xdr_string (xdrs, cpp, maxsize)
XDR *xdrs;
char **cpp;
u_int maxsize;
{
register char *sp = *cpp; /* sp is the actual string pointer */
u_int size;
u_int nodesize;
char *sp = *cpp; /* sp is the actual string pointer */
u_int size;
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 */
}
/* fall through... */
case XDR_ENCODE:
if (sp == NULL)
return FALSE;
size = strlen(sp);
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 = (char *)mem_alloc(nodesize);
if (sp == NULL) {
(void) fprintf(stderr, "xdr_string: out of memory\n");
return FALSE;
}
sp[size] = 0;
/* fall into ... */
case XDR_ENCODE:
return xdr_opaque(xdrs, sp, size);
case XDR_FREE:
mem_free(sp, nodesize);
*cpp = NULL;
return TRUE;
/*
* 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 */
}
/* fall through... */
case XDR_ENCODE:
if (sp == NULL)
return FALSE;
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 = (char *) mem_alloc (nodesize);
if (sp == NULL)
{
(void) fprintf (stderr, "xdr_string: out of memory\n");
return FALSE;
}
sp[size] = 0;
/* fall into ... */
case XDR_ENCODE:
return xdr_opaque (xdrs, sp, size);
case XDR_FREE:
mem_free (sp, nodesize);
*cpp = NULL;
return TRUE;
}
return FALSE;
}
/*
@ -621,12 +663,13 @@ xdr_string(xdrs, cpp, maxsize)
* routines like clnt_call
*/
bool_t
xdr_wrapstring(xdrs, cpp)
XDR *xdrs;
char **cpp;
xdr_wrapstring (xdrs, cpp)
XDR *xdrs;
char **cpp;
{
if (xdr_string(xdrs, cpp, LASTUNSIGNED)) {
return TRUE;
}
return FALSE;
if (xdr_string (xdrs, cpp, LASTUNSIGNED))
{
return TRUE;
}
return FALSE;
}

View File

@ -41,7 +41,7 @@ static char sccsid[] = "@(#)xdr_array.c 1.10 87/08/11 Copyr 1984 Sun Micro";
*/
#include <stdio.h>
#include <string.h>
#include <rpc/types.h>
#include <rpc/xdr.h>
@ -56,68 +56,76 @@ static char sccsid[] = "@(#)xdr_array.c 1.10 87/08/11 Copyr 1984 Sun Micro";
* xdr procedure to call to handle each element of the array.
*/
bool_t
xdr_array(xdrs, addrp, sizep, maxsize, elsize, elproc)
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 */
xdr_array (xdrs, addrp, sizep, maxsize, elsize, elproc)
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;
u_int i;
caddr_t target = *addrp;
u_int c; /* the actual element count */
bool_t stat = TRUE;
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;
/* 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 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)
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);
}
bzero(target, nodesize);
break;
{
(void) fprintf (stderr,
"xdr_array: out of memory\n");
return FALSE;
}
bzero (target, nodesize);
break;
case XDR_FREE:
return (TRUE);
}
case XDR_FREE:
return TRUE;
default:
break;
}
/*
* now we xdr each element of array
*/
for (i = 0; (i < c) && stat; i++) {
stat = (*elproc)(xdrs, target, LASTUNSIGNED);
target += elsize;
}
/*
* 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);
/*
* the array may need freeing
*/
if (xdrs->x_op == XDR_FREE)
{
mem_free (*addrp, nodesize);
*addrp = NULL;
}
return stat;
}
/*
@ -131,22 +139,24 @@ xdr_array(xdrs, addrp, sizep, maxsize, elsize, elproc)
* > xdr_elem: routine to XDR each element
*/
bool_t
xdr_vector(xdrs, basep, nelem, elemsize, xdr_elem)
register XDR *xdrs;
register char *basep;
register u_int nelem;
register u_int elemsize;
register xdrproc_t xdr_elem;
xdr_vector (xdrs, basep, nelem, elemsize, xdr_elem)
XDR *xdrs;
char *basep;
u_int nelem;
u_int elemsize;
xdrproc_t xdr_elem;
{
register u_int i;
register char *elptr;
u_int i;
char *elptr;
elptr = basep;
for (i = 0; i < nelem; i++) {
if (! (*xdr_elem)(xdrs, elptr, LASTUNSIGNED)) {
return(FALSE);
}
elptr += elemsize;
elptr = basep;
for (i = 0; i < nelem; i++)
{
if (!(*xdr_elem) (xdrs, elptr, LASTUNSIGNED))
{
return FALSE;
}
return(TRUE);
elptr += elemsize;
}
return TRUE;
}

View File

@ -6,23 +6,23 @@
* 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
@ -43,142 +43,142 @@ static char sccsid[] = "@(#)xdr_mem.c 1.19 87/08/11 Copyr 1984 Sun Micro";
*/
#include <rpc/types.h>
#include <rpc/xdr.h>
#include <netinet/in.h>
#include <string.h>
#include <rpc/rpc.h>
static bool_t xdrmem_getlong();
static bool_t xdrmem_putlong();
static bool_t xdrmem_getbytes();
static bool_t xdrmem_putbytes();
static u_int xdrmem_getpos();
static bool_t xdrmem_setpos();
static long * xdrmem_inline();
static void xdrmem_destroy();
static bool_t xdrmem_getlong (XDR *, long *);
static bool_t xdrmem_putlong (XDR *, long *);
static bool_t xdrmem_getbytes (XDR *, caddr_t, u_int);
static bool_t xdrmem_putbytes (XDR *, caddr_t, u_int);
static u_int xdrmem_getpos (XDR *);
static bool_t xdrmem_setpos (XDR *, u_int);
static long *xdrmem_inline (XDR *, int);
static void xdrmem_destroy (XDR *);
static struct xdr_ops xdrmem_ops = {
xdrmem_getlong,
xdrmem_putlong,
xdrmem_getbytes,
xdrmem_putbytes,
xdrmem_getpos,
xdrmem_setpos,
xdrmem_inline,
xdrmem_destroy
static const struct xdr_ops xdrmem_ops =
{
xdrmem_getlong,
xdrmem_putlong,
xdrmem_getbytes,
xdrmem_putbytes,
xdrmem_getpos,
xdrmem_setpos,
xdrmem_inline,
xdrmem_destroy
};
/*
* The procedure xdrmem_create initializes a stream descriptor for a
* memory buffer.
* memory buffer.
*/
void
xdrmem_create(xdrs, addr, size, op)
register XDR *xdrs;
caddr_t addr;
u_int size;
enum xdr_op op;
xdrmem_create (xdrs, addr, size, op)
XDR *xdrs;
caddr_t addr;
u_int size;
enum xdr_op op;
{
xdrs->x_op = op;
xdrs->x_ops = &xdrmem_ops;
xdrs->x_private = xdrs->x_base = addr;
xdrs->x_handy = size;
xdrs->x_op = op;
xdrs->x_ops = &xdrmem_ops;
xdrs->x_private = xdrs->x_base = addr;
xdrs->x_handy = size;
}
static void
xdrmem_destroy(/*xdrs*/)
/*XDR *xdrs;*/
xdrmem_destroy (XDR *xdrs)
{
}
static bool_t
xdrmem_getlong(xdrs, lp)
register XDR *xdrs;
long *lp;
xdrmem_getlong (xdrs, lp)
XDR *xdrs;
long *lp;
{
if ((xdrs->x_handy -= 4) < 0)
return (FALSE);
*lp = (int32_t) ntohl((*((int32_t *)(xdrs->x_private))));
xdrs->x_private += 4;
return (TRUE);
if ((xdrs->x_handy -= 4) < 0)
return FALSE;
*lp = (int32_t) ntohl ((*((int32_t *) (xdrs->x_private))));
xdrs->x_private += 4;
return TRUE;
}
static bool_t
xdrmem_putlong(xdrs, lp)
register XDR *xdrs;
long *lp;
xdrmem_putlong (xdrs, lp)
XDR *xdrs;
long *lp;
{
if ((xdrs->x_handy -= 4) < 0)
return (FALSE);
*(int32_t *)xdrs->x_private = htonl(*lp);
xdrs->x_private += 4;
return (TRUE);
if ((xdrs->x_handy -= 4) < 0)
return FALSE;
*(int32_t *) xdrs->x_private = htonl (*lp);
xdrs->x_private += 4;
return TRUE;
}
static bool_t
xdrmem_getbytes(xdrs, addr, len)
register XDR *xdrs;
caddr_t addr;
register u_int len;
xdrmem_getbytes (xdrs, addr, len)
XDR *xdrs;
caddr_t addr;
u_int len;
{
if ((xdrs->x_handy -= len) < 0)
return (FALSE);
bcopy(xdrs->x_private, addr, len);
xdrs->x_private += len;
return (TRUE);
if ((xdrs->x_handy -= len) < 0)
return FALSE;
bcopy (xdrs->x_private, addr, len);
xdrs->x_private += len;
return TRUE;
}
static bool_t
xdrmem_putbytes(xdrs, addr, len)
register XDR *xdrs;
caddr_t addr;
register u_int len;
xdrmem_putbytes (xdrs, addr, len)
XDR *xdrs;
caddr_t addr;
u_int len;
{
if ((xdrs->x_handy -= len) < 0)
return (FALSE);
bcopy(addr, xdrs->x_private, len);
xdrs->x_private += len;
return (TRUE);
if ((xdrs->x_handy -= len) < 0)
return FALSE;
bcopy (addr, xdrs->x_private, len);
xdrs->x_private += len;
return TRUE;
}
static u_int
xdrmem_getpos(xdrs)
register XDR *xdrs;
xdrmem_getpos (xdrs)
XDR *xdrs;
{
return ((u_long)xdrs->x_private - (u_long)xdrs->x_base);
return (u_long) xdrs->x_private - (u_long) xdrs->x_base;
}
static bool_t
xdrmem_setpos(xdrs, pos)
register XDR *xdrs;
u_int pos;
xdrmem_setpos (xdrs, pos)
XDR *xdrs;
u_int pos;
{
register caddr_t newaddr = xdrs->x_base + pos;
register caddr_t lastaddr = xdrs->x_private + xdrs->x_handy;
caddr_t newaddr = xdrs->x_base + pos;
caddr_t lastaddr = xdrs->x_private + xdrs->x_handy;
if ((long)newaddr > (long)lastaddr)
return (FALSE);
xdrs->x_private = newaddr;
xdrs->x_handy = (long)lastaddr - (long)newaddr;
return (TRUE);
if ((long) newaddr > (long) lastaddr)
return FALSE;
xdrs->x_private = newaddr;
xdrs->x_handy = (long) lastaddr - (long) newaddr;
return TRUE;
}
static long *
xdrmem_inline(xdrs, len)
register XDR *xdrs;
int len;
xdrmem_inline (xdrs, len)
XDR *xdrs;
int len;
{
long *buf = 0;
long *buf = 0;
if (xdrs->x_handy >= len) {
xdrs->x_handy -= len;
buf = (long *) xdrs->x_private;
xdrs->x_private += len;
}
return (buf);
if (xdrs->x_handy >= len)
{
xdrs->x_handy -= len;
buf = (long *) xdrs->x_private;
xdrs->x_private += len;
}
return buf;
}

View File

@ -49,32 +49,29 @@ static char sccsid[] = "@(#)xdr_rec.c 1.21 87/08/11 Copyr 1984 Sun Micro";
*/
#include <stdio.h>
#include <rpc/types.h>
#include <rpc/xdr.h>
#include <netinet/in.h>
#include <string.h>
#include <unistd.h>
#include <rpc/rpc.h>
extern long lseek();
static bool_t xdrrec_getlong (XDR *, long *);
static bool_t xdrrec_putlong (XDR *, long *);
static bool_t xdrrec_getbytes (XDR *, caddr_t, u_int);
static bool_t xdrrec_putbytes (XDR *, caddr_t, u_int);
static u_int xdrrec_getpos (XDR *);
static bool_t xdrrec_setpos (XDR *, u_int);
static long *xdrrec_inline (XDR *, int);
static void xdrrec_destroy (XDR *);
static u_int fix_buf_size();
static bool_t xdrrec_getlong();
static bool_t xdrrec_putlong();
static bool_t xdrrec_getbytes();
static bool_t xdrrec_putbytes();
static u_int xdrrec_getpos();
static bool_t xdrrec_setpos();
static long * xdrrec_inline();
static void xdrrec_destroy();
static struct xdr_ops xdrrec_ops = {
xdrrec_getlong,
xdrrec_putlong,
xdrrec_getbytes,
xdrrec_putbytes,
xdrrec_getpos,
xdrrec_setpos,
xdrrec_inline,
xdrrec_destroy
static const struct xdr_ops xdrrec_ops =
{
xdrrec_getlong,
xdrrec_putlong,
xdrrec_getbytes,
xdrrec_putbytes,
xdrrec_getpos,
xdrrec_setpos,
xdrrec_inline,
xdrrec_destroy
};
/*
@ -92,32 +89,39 @@ static struct xdr_ops xdrrec_ops = {
#define LAST_FRAG (1UL << 31)
typedef struct rec_strm {
caddr_t tcp_handle;
caddr_t the_buffer;
/*
* out-going bits
*/
int (*writeit)();
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 curren fragment */
bool_t frag_sent; /* true if buffer sent in middle of record */
/*
* in-coming bits
*/
int (*readit)();
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;
} RECSTREAM;
typedef struct rec_strm
{
caddr_t tcp_handle;
caddr_t the_buffer;
/*
* out-going bits
*/
int (*writeit) (char *, char *, 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 curren fragment */
bool_t frag_sent; /* true if buffer sent in middle of record */
/*
* in-coming bits
*/
int (*readit) (char *, char *, 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;
}
RECSTREAM;
static u_int fix_buf_size (u_int);
static bool_t skip_input_bytes (RECSTREAM *, long);
static bool_t flush_out (RECSTREAM *, bool_t);
static bool_t set_input_fragment (RECSTREAM *);
static bool_t get_input_bytes (RECSTREAM *, caddr_t, int);
/*
* Create an xdr handle for xdrrec
@ -129,57 +133,56 @@ typedef struct rec_strm {
* calls expect that they take an opaque handle rather than an fd.
*/
void
xdrrec_create(xdrs, sendsize, recvsize, tcp_handle, readit, writeit)
register XDR *xdrs;
register u_int sendsize;
register u_int recvsize;
caddr_t tcp_handle;
int (*readit)(); /* like read, but pass it a tcp_handle, not sock */
int (*writeit)(); /* like write, but pass it a tcp_handle, not sock */
xdrrec_create (XDR *xdrs, u_int sendsize,
u_int recvsize, caddr_t tcp_handle,
int (*readit) (char *, char *, int),
int (*writeit) (char *, char *, int))
{
register RECSTREAM *rstrm =
(RECSTREAM *)mem_alloc(sizeof(RECSTREAM));
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;
(u_int)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 += 4;
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;
if (rstrm == NULL)
{
(void) fputs (_("xdrrec_create: out of memory\n"), stderr);
/*
* 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) fputs (_("xdrrec_create: out of memory\n"), stderr);
return;
}
for (rstrm->out_base = rstrm->the_buffer;
(u_int) 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 += 4;
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;
}
@ -189,208 +192,224 @@ xdrrec_create(xdrs, sendsize, recvsize, tcp_handle, readit, writeit)
*/
static bool_t
xdrrec_getlong(xdrs, lp)
XDR *xdrs;
long *lp;
xdrrec_getlong (xdrs, lp)
XDR *xdrs;
long *lp;
{
register RECSTREAM *rstrm = (RECSTREAM *) xdrs->x_private;
register int32_t *buflp = (int32_t *) rstrm->in_finger;
int32_t mylong;
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 >= BYTES_PER_XDR_UNIT &&
rstrm->in_boundry - (char *) buflp >= BYTES_PER_XDR_UNIT)
/* first try the inline, fast case */
if (rstrm->fbtbc >= BYTES_PER_XDR_UNIT &&
rstrm->in_boundry - (char *) buflp >= BYTES_PER_XDR_UNIT)
{
*lp = (int32_t) ntohl (*buflp);
rstrm->fbtbc -= BYTES_PER_XDR_UNIT;
rstrm->in_finger += BYTES_PER_XDR_UNIT;
}
else
{
if (!xdrrec_getbytes (xdrs, (caddr_t) & mylong,
BYTES_PER_XDR_UNIT))
return FALSE;
*lp = (int32_t) ntohl (mylong);
}
return TRUE;
}
static bool_t
xdrrec_putlong (xdrs, lp)
XDR *xdrs;
long *lp;
{
RECSTREAM *rstrm = (RECSTREAM *) xdrs->x_private;
int32_t *dest_lp = (int32_t *) rstrm->out_finger;
if ((rstrm->out_finger += BYTES_PER_XDR_UNIT) > rstrm->out_boundry)
{
/*
* this case should almost never happen so the code is
* inefficient
*/
rstrm->out_finger -= BYTES_PER_XDR_UNIT;
rstrm->frag_sent = TRUE;
if (!flush_out (rstrm, FALSE))
return FALSE;
dest_lp = (int32_t *) rstrm->out_finger;
rstrm->out_finger += BYTES_PER_XDR_UNIT;
}
*dest_lp = htonl (*lp);
return TRUE;
}
static bool_t /* must manage buffers, fragments, and records */
xdrrec_getbytes (xdrs, addr, len)
XDR *xdrs;
caddr_t addr;
u_int len;
{
RECSTREAM *rstrm = (RECSTREAM *) xdrs->x_private;
u_int current;
while (len > 0)
{
current = rstrm->fbtbc;
if (current == 0)
{
*lp = (int32_t) ntohl(*buflp);
rstrm->fbtbc -= BYTES_PER_XDR_UNIT;
rstrm->in_finger += BYTES_PER_XDR_UNIT;
} else {
if (! xdrrec_getbytes(xdrs, (caddr_t) &mylong,
BYTES_PER_XDR_UNIT))
return FALSE;
*lp = (int32_t) ntohl(mylong);
if (rstrm->last_frag)
return FALSE;
if (!set_input_fragment (rstrm))
return FALSE;
continue;
}
return TRUE;
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_putlong(xdrs, lp)
XDR *xdrs;
long *lp;
xdrrec_putbytes (xdrs, addr, len)
XDR *xdrs;
caddr_t addr;
u_int len;
{
register RECSTREAM *rstrm = (RECSTREAM *) xdrs->x_private;
register int32_t *dest_lp = (int32_t *) rstrm->out_finger;
RECSTREAM *rstrm = (RECSTREAM *) xdrs->x_private;
u_int current;
if ((rstrm->out_finger += BYTES_PER_XDR_UNIT) > rstrm->out_boundry) {
/*
* this case should almost never happen so the code is
* inefficient
*/
rstrm->out_finger -= BYTES_PER_XDR_UNIT;
rstrm->frag_sent = TRUE;
if (! flush_out(rstrm, FALSE))
return FALSE;
dest_lp = (int32_t *) rstrm->out_finger;
rstrm->out_finger += BYTES_PER_XDR_UNIT;
while (len > 0)
{
current = rstrm->out_boundry - rstrm->out_finger;
current = (len < current) ? len : current;
bcopy (addr, rstrm->out_finger, 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;
}
*dest_lp = htonl(*lp);
return TRUE;
}
static bool_t /* must manage buffers, fragments, and records */
xdrrec_getbytes(xdrs, addr, len)
XDR *xdrs;
register caddr_t addr;
register u_int len;
{
register RECSTREAM *rstrm = (RECSTREAM *) xdrs->x_private;
register 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(xdrs, addr, len)
XDR *xdrs;
register caddr_t addr;
register u_int len;
{
register RECSTREAM *rstrm = (RECSTREAM *) xdrs->x_private;
register int current;
while (len > 0) {
current = rstrm->out_boundry - rstrm->out_finger;
current = (len < current) ? len : current;
bcopy(addr, rstrm->out_finger, 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;
}
return TRUE;
}
static u_int
xdrrec_getpos(xdrs)
register XDR *xdrs;
xdrrec_getpos (XDR *xdrs)
{
register RECSTREAM *rstrm = (RECSTREAM *)xdrs->x_private;
register long pos;
RECSTREAM *rstrm = (RECSTREAM *) xdrs->x_private;
long pos;
pos = lseek((int)rstrm->tcp_handle, (long) 0, 1);
if (pos != -1)
switch (xdrs->x_op) {
pos = lseek ((int) rstrm->tcp_handle, (long) 0, 1);
if (pos != -1)
switch (xdrs->x_op)
{
case XDR_ENCODE:
pos += rstrm->out_finger - rstrm->out_base;
break;
case XDR_ENCODE:
pos += rstrm->out_finger - rstrm->out_base;
break;
case XDR_DECODE:
pos -= rstrm->in_boundry - rstrm->in_finger;
break;
case XDR_DECODE:
pos -= rstrm->in_boundry - rstrm->in_finger;
break;
default:
pos = (u_int) -1;
break;
}
return ((u_int) pos);
default:
pos = (u_int) - 1;
break;
}
return (u_int) pos;
}
static bool_t
xdrrec_setpos(xdrs, pos)
register XDR *xdrs;
u_int pos;
xdrrec_setpos (xdrs, pos)
XDR *xdrs;
u_int pos;
{
register RECSTREAM *rstrm = (RECSTREAM *) xdrs->x_private;
u_int currpos = xdrrec_getpos(xdrs);
int delta = currpos - pos;
caddr_t newpos;
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) {
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_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;
}
return FALSE;
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;
default:
break;
}
return FALSE;
}
static long *
xdrrec_inline(xdrs, len)
register XDR *xdrs;
int len;
xdrrec_inline (XDR *xdrs, int len)
{
register RECSTREAM *rstrm = (RECSTREAM *) xdrs->x_private;
long * buf = NULL;
RECSTREAM *rstrm = (RECSTREAM *) xdrs->x_private;
long *buf = NULL;
switch (xdrs->x_op) {
switch (xdrs->x_op)
{
case XDR_ENCODE:
if ((rstrm->out_finger + len) <= rstrm->out_boundry) {
buf = (long *) rstrm->out_finger;
rstrm->out_finger += len;
}
break;
case XDR_DECODE:
if ((len <= rstrm->fbtbc) &&
((rstrm->in_finger + len) <= rstrm->in_boundry)) {
buf = (long *) rstrm->in_finger;
rstrm->fbtbc -= len;
rstrm->in_finger += len;
}
break;
case XDR_ENCODE:
if ((rstrm->out_finger + len) <= rstrm->out_boundry)
{
buf = (long *) rstrm->out_finger;
rstrm->out_finger += len;
}
return buf;
break;
case XDR_DECODE:
if ((len <= rstrm->fbtbc) &&
((rstrm->in_finger + len) <= rstrm->in_boundry))
{
buf = (long *) rstrm->in_finger;
rstrm->fbtbc -= len;
rstrm->in_finger += len;
}
break;
default:
break;
}
return buf;
}
static void
xdrrec_destroy(xdrs)
register XDR *xdrs;
xdrrec_destroy (xdrs)
XDR *xdrs;
{
register RECSTREAM *rstrm = (RECSTREAM *)xdrs->x_private;
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));
mem_free (rstrm->the_buffer,
rstrm->sendsize + rstrm->recvsize + BYTES_PER_XDR_UNIT);
mem_free ((caddr_t) rstrm, sizeof (RECSTREAM));
}
@ -403,20 +422,21 @@ xdrrec_destroy(xdrs)
* this procedure to guarantee proper record alignment.
*/
bool_t
xdrrec_skiprecord(xdrs)
XDR *xdrs;
xdrrec_skiprecord (xdrs)
XDR *xdrs;
{
register RECSTREAM *rstrm = (RECSTREAM *) xdrs->x_private;
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;
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;
}
/*
@ -425,21 +445,22 @@ xdrrec_skiprecord(xdrs)
* after consuming the rest of the current record.
*/
bool_t
xdrrec_eof(xdrs)
XDR *xdrs;
xdrrec_eof (xdrs)
XDR *xdrs;
{
register RECSTREAM *rstrm = (RECSTREAM *) xdrs->x_private;
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;
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;
}
/*
@ -449,25 +470,25 @@ xdrrec_eof(xdrs)
* pipelined procedure calls.) TRUE => immediate flush to tcp connection.
*/
bool_t
xdrrec_endofrecord(xdrs, sendnow)
XDR *xdrs;
bool_t sendnow;
xdrrec_endofrecord (xdrs, sendnow)
XDR *xdrs;
bool_t sendnow;
{
register RECSTREAM *rstrm = (RECSTREAM *) xdrs->x_private;
register u_long len; /* fragment length */
RECSTREAM *rstrm = (RECSTREAM *) xdrs->x_private;
u_long len; /* fragment length */
if (sendnow || rstrm->frag_sent
|| rstrm->out_finger + BYTES_PER_XDR_UNIT >= rstrm->out_boundry)
{
rstrm->frag_sent = FALSE;
return flush_out(rstrm, TRUE);
}
len = (rstrm->out_finger - (char *) rstrm->frag_header
- BYTES_PER_XDR_UNIT);
*rstrm->frag_header = htonl((u_long)len | LAST_FRAG);
rstrm->frag_header = (u_int32_t *) rstrm->out_finger;
rstrm->out_finger += BYTES_PER_XDR_UNIT;
return TRUE;
if (sendnow || rstrm->frag_sent
|| rstrm->out_finger + BYTES_PER_XDR_UNIT >= rstrm->out_boundry)
{
rstrm->frag_sent = FALSE;
return flush_out (rstrm, TRUE);
}
len = (rstrm->out_finger - (char *) rstrm->frag_header
- BYTES_PER_XDR_UNIT);
*rstrm->frag_header = htonl ((u_long) len | LAST_FRAG);
rstrm->frag_header = (u_int32_t *) rstrm->out_finger;
rstrm->out_finger += BYTES_PER_XDR_UNIT;
return TRUE;
}
@ -475,110 +496,102 @@ xdrrec_endofrecord(xdrs, sendnow)
* Internal useful routines
*/
static bool_t
flush_out(rstrm, eor)
register RECSTREAM *rstrm;
bool_t eor;
flush_out (RECSTREAM *rstrm, bool_t eor)
{
register u_long eormask = (eor == TRUE) ? LAST_FRAG : 0;
register u_long len = (rstrm->out_finger
- (char *) rstrm->frag_header
- BYTES_PER_XDR_UNIT);
u_long eormask = (eor == TRUE) ? LAST_FRAG : 0;
u_long len = (rstrm->out_finger - (char *) rstrm->frag_header
- BYTES_PER_XDR_UNIT);
*rstrm->frag_header = htonl(len | eormask);
len = rstrm->out_finger - 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 + BYTES_PER_XDR_UNIT;
return TRUE;
*rstrm->frag_header = htonl (len | eormask);
len = rstrm->out_finger - 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 + BYTES_PER_XDR_UNIT;
return TRUE;
}
static bool_t /* knows nothing about records! Only about input buffers */
fill_input_buf(rstrm)
register RECSTREAM *rstrm;
static bool_t /* knows nothing about records! Only about input buffers */
fill_input_buf (RECSTREAM *rstrm)
{
register caddr_t where;
u_int i;
register int len;
caddr_t where;
u_int i;
int len;
where = rstrm->in_base;
i = (u_int)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;
where = rstrm->in_base;
i = (u_int) 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(rstrm, addr, len)
register RECSTREAM *rstrm;
register caddr_t addr;
register int len;
static bool_t /* knows nothing about records! Only about input buffers */
get_input_bytes (RECSTREAM *rstrm, caddr_t addr, int len)
{
register int current;
int current;
while (len > 0) {
current = rstrm->in_boundry - rstrm->in_finger;
if (current == 0) {
if (! fill_input_buf(rstrm))
return FALSE;
continue;
}
current = (len < current) ? len : current;
bcopy(rstrm->in_finger, addr, current);
rstrm->in_finger += current;
addr += current;
len -= current;
while (len > 0)
{
current = rstrm->in_boundry - rstrm->in_finger;
if (current == 0)
{
if (!fill_input_buf (rstrm))
return FALSE;
continue;
}
return TRUE;
current = (len < current) ? len : current;
bcopy (rstrm->in_finger, addr, 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(rstrm)
register RECSTREAM *rstrm;
static bool_t /* next two bytes of the input stream are treated as a header */
set_input_fragment (RECSTREAM *rstrm)
{
u_long header;
u_long header;
if (! get_input_bytes(rstrm, (caddr_t)&header, BYTES_PER_XDR_UNIT))
return FALSE;
header = ntohl(header);
rstrm->last_frag = ((header & LAST_FRAG) == 0) ? FALSE : TRUE;
rstrm->fbtbc = header & ~LAST_FRAG;
return TRUE;
if (!get_input_bytes (rstrm, (caddr_t) & header, BYTES_PER_XDR_UNIT))
return FALSE;
header = ntohl (header);
rstrm->last_frag = ((header & LAST_FRAG) == 0) ? FALSE : TRUE;
rstrm->fbtbc = header & ~LAST_FRAG;
return TRUE;
}
static bool_t /* consumes input bytes; knows nothing about records! */
skip_input_bytes(rstrm, cnt)
register RECSTREAM *rstrm;
long cnt;
static bool_t /* consumes input bytes; knows nothing about records! */
skip_input_bytes (RECSTREAM *rstrm, long cnt)
{
register int current;
int current;
while (cnt > 0) {
current = rstrm->in_boundry - 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;
while (cnt > 0)
{
current = rstrm->in_boundry - rstrm->in_finger;
if (current == 0)
{
if (!fill_input_buf (rstrm))
return FALSE;
continue;
}
return TRUE;
current = (cnt < current) ? cnt : current;
rstrm->in_finger += current;
cnt -= current;
}
return TRUE;
}
static u_int
fix_buf_size(s)
register u_int s;
fix_buf_size (u_int s)
{
if (s < 100)
s = 4000;
return RNDUP(s);
if (s < 100)
s = 4000;
return RNDUP (s);
}

View File

@ -41,6 +41,7 @@ static char sccsid[] = "@(#)xdr_reference.c 1.11 87/08/11 SMI";
*/
#include <stdio.h>
#include <string.h>
#include <rpc/types.h>
#include <rpc/xdr.h>
@ -56,38 +57,42 @@ static char sccsid[] = "@(#)xdr_reference.c 1.11 87/08/11 SMI";
* proc is the routine to handle the referenced structure.
*/
bool_t
xdr_reference(xdrs, pp, size, proc)
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 */
xdr_reference (xdrs, pp, size, proc)
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;
caddr_t loc = *pp;
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)
switch (xdrs->x_op) {
case XDR_FREE:
return (TRUE);
{
(void) fputs (_("xdr_reference: out of memory\n"), stderr);
return FALSE;
}
bzero (loc, (int) size);
break;
default:
break;
}
case XDR_DECODE:
*pp = loc = (caddr_t) mem_alloc(size);
if (loc == NULL) {
(void) fprintf(stderr,
"xdr_reference: out of memory\n");
return (FALSE);
}
bzero(loc, (int)size);
break;
}
stat = (*proc) (xdrs, loc, LASTUNSIGNED);
stat = (*proc)(xdrs, loc, LASTUNSIGNED);
if (xdrs->x_op == XDR_FREE) {
mem_free(loc, size);
*pp = NULL;
}
return (stat);
if (xdrs->x_op == XDR_FREE)
{
mem_free (loc, size);
*pp = NULL;
}
return stat;
}
@ -111,22 +116,24 @@ xdr_reference(xdrs, pp, size, proc)
*
*/
bool_t
xdr_pointer(xdrs,objpp,obj_size,xdr_obj)
register XDR *xdrs;
char **objpp;
u_int obj_size;
xdrproc_t xdr_obj;
xdr_pointer (xdrs, objpp, obj_size, xdr_obj)
XDR *xdrs;
char **objpp;
u_int obj_size;
xdrproc_t xdr_obj;
{
bool_t more_data;
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));
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);
}

View File

@ -45,27 +45,28 @@ static char sccsid[] = "@(#)xdr_stdio.c 1.16 87/08/11 Copyr 1984 Sun Micro";
#include <stdio.h>
#include <rpc/xdr.h>
static bool_t xdrstdio_getlong();
static bool_t xdrstdio_putlong();
static bool_t xdrstdio_getbytes();
static bool_t xdrstdio_putbytes();
static u_int xdrstdio_getpos();
static bool_t xdrstdio_setpos();
static long * xdrstdio_inline();
static void xdrstdio_destroy();
static bool_t xdrstdio_getlong (XDR *, long *);
static bool_t xdrstdio_putlong (XDR *, long *);
static bool_t xdrstdio_getbytes (XDR *, caddr_t, u_int);
static bool_t xdrstdio_putbytes (XDR *, caddr_t, u_int);
static u_int xdrstdio_getpos (XDR *);
static bool_t xdrstdio_setpos (XDR *, u_int);
static long *xdrstdio_inline (XDR *, int);
static void xdrstdio_destroy (XDR *);
/*
* Ops vector for stdio type XDR
*/
static struct xdr_ops xdrstdio_ops = {
xdrstdio_getlong, /* deserialize a long int */
xdrstdio_putlong, /* serialize 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 */
static const struct xdr_ops xdrstdio_ops =
{
xdrstdio_getlong, /* deserialize a long int */
xdrstdio_putlong, /* serialize 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 */
};
/*
@ -74,17 +75,17 @@ static struct xdr_ops xdrstdio_ops = {
* Operation flag is set to op.
*/
void
xdrstdio_create(xdrs, file, op)
register XDR *xdrs;
FILE *file;
enum xdr_op op;
xdrstdio_create (xdrs, file, op)
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;
xdrs->x_op = op;
xdrs->x_ops = &xdrstdio_ops;
xdrs->x_private = (caddr_t) file;
xdrs->x_handy = 0;
xdrs->x_base = 0;
}
/*
@ -92,95 +93,81 @@ xdrstdio_create(xdrs, file, op)
* Cleans up the xdr stream handle xdrs previously set up by xdrstdio_create.
*/
static void
xdrstdio_destroy(xdrs)
register XDR *xdrs;
xdrstdio_destroy (xdrs)
XDR *xdrs;
{
(void)fflush((FILE *)xdrs->x_private);
/* xx should we close the file ?? */
(void) fflush ((FILE *) xdrs->x_private);
/* xx should we close the file ?? */
};
static bool_t
xdrstdio_getlong(xdrs, lp)
XDR *xdrs;
register long *lp;
xdrstdio_getlong (xdrs, lp)
XDR *xdrs;
long *lp;
{
int32_t mycopy;
int32_t mycopy;
if (fread((caddr_t)&mycopy, 4, 1, (FILE *)xdrs->x_private) != 1)
return (FALSE);
*lp = (int32_t) ntohl(mycopy);
return (TRUE);
if (fread ((caddr_t) & mycopy, 4, 1, (FILE *) xdrs->x_private) != 1)
return FALSE;
*lp = (int32_t) ntohl (mycopy);
return TRUE;
}
static bool_t
xdrstdio_putlong(xdrs, lp)
XDR *xdrs;
long *lp;
xdrstdio_putlong (XDR *xdrs, long *lp)
{
int32_t mycopy = htonl(*lp);
lp = &mycopy;
if (fwrite((caddr_t)lp, 4, 1, (FILE *)xdrs->x_private) != 1)
return (FALSE);
return (TRUE);
long mycopy = htonl (*lp);
lp = &mycopy;
if (fwrite ((caddr_t) lp, 4, 1, (FILE *) xdrs->x_private) != 1)
return FALSE;
return TRUE;
}
static bool_t
xdrstdio_getbytes(xdrs, addr, len)
XDR *xdrs;
caddr_t addr;
u_int len;
xdrstdio_getbytes (xdrs, addr, len)
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);
if ((len != 0) && (fread (addr, (int) len, 1, (FILE *) xdrs->x_private) != 1))
return FALSE;
return TRUE;
}
static bool_t
xdrstdio_putbytes(xdrs, addr, len)
XDR *xdrs;
caddr_t addr;
u_int len;
xdrstdio_putbytes (XDR *xdrs, caddr_t addr, u_int len)
{
if ((len != 0) && (fwrite(addr, (int)len, 1, (FILE *)xdrs->x_private) != 1))
return (FALSE);
return (TRUE);
if ((len != 0) && (fwrite (addr, (int) len, 1, (FILE *) xdrs->x_private) != 1))
return FALSE;
return TRUE;
}
static u_int
xdrstdio_getpos(xdrs)
XDR *xdrs;
xdrstdio_getpos (XDR *xdrs)
{
return ((u_int) ftell((FILE *)xdrs->x_private));
return (u_int) ftell ((FILE *) xdrs->x_private);
}
static bool_t
xdrstdio_setpos(xdrs, pos)
XDR *xdrs;
u_int pos;
xdrstdio_setpos (XDR *xdrs, u_int pos)
{
return ((fseek((FILE *)xdrs->x_private, (long)pos, 0) < 0) ?
FALSE : TRUE);
return fseek ((FILE *) xdrs->x_private, (long) pos, 0) < 0 ? FALSE : TRUE;
}
static long *
xdrstdio_inline(xdrs, len)
XDR *xdrs;
u_int len;
xdrstdio_inline (XDR *xdrs, 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);
/*
* 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;
}

View File

@ -1,5 +1,5 @@
/* __sig_atomic_t, __sigset_t, and related definitions. Generic/BSD version.
Copyright (C) 1991, 1992, 1994, 1996 Free Software Foundation, Inc.
Copyright (C) 1991, 1992, 1994, 1996, 1997 Free Software Foundation, Inc.
This file is part of the GNU C Library.
The GNU C Library is free software; you can redistribute it and/or
@ -48,6 +48,14 @@ typedef unsigned long int __sigset_t;
#define __sigemptyset(set) ((*(set) = (__sigset_t) 0), 0)
#define __sigfillset(set) ((*(set) = ~(__sigset_t) 0), 0)
#ifdef _GNU_SOURCE
# define __sigisemptyset(set) (*(set) == (__sigset_t) 0)
# define __sigandset(dest, left, right) \
((*(set) = (*(left) & *(right))), 0)
# define __sigorset(dest, left, right) \
((*(set) = (*(left) | *(right))), 0)
#endif
/* These functions needn't check for a bogus signal number -- error
checking is done in the non __ versions. */

View File

@ -0,0 +1,38 @@
/*
* Written by J.T. Conklin <jtc@netbsd.org>.
* Adapted for exp2 by Ulrich Drepper <drepper@cygnus.com>.
* Public domain.
*/
#include <machine/asm.h>
ENTRY(__exp2)
fldl 4(%esp)
/* I added the following ugly construct because exp(+-Inf) resulted
in NaN. The ugliness results from the bright minds at Intel.
For the i686 the code can be written better.
-- drepper@cygnus.com. */
fxam /* Is NaN or +-Inf? */
fstsw %ax
movb $0x45, %dh
andb %ah, %dh
cmpb $0x05, %dh
je 1f /* Is +-Inf, jump. */
fld %st
frndint /* int(x) */
fsubr %st,%st(1) /* fract(x) */
fxch
f2xm1 /* 2^(fract(x)) - 1 */
fld1
faddp /* 2^(fract(x)) */
fscale /* e^x */
fstp %st(1)
ret
1: testl $0x200, %eax /* Test sign. */
jz 2f /* If positive, jump. */
fstp %st
fldz /* Set result to 0. */
2: ret
END (__exp2)
weak_alias (__exp2, exp2)

View File

@ -0,0 +1,38 @@
/*
* Written by J.T. Conklin <jtc@netbsd.org>.
* Adapted for exp2 by Ulrich Drepper <drepper@cygnus.com>.
* Public domain.
*/
#include <machine/asm.h>
ENTRY(__exp2f)
flds 4(%esp)
/* I added the following ugly construct because exp(+-Inf) resulted
in NaN. The ugliness results from the bright minds at Intel.
For the i686 the code can be written better.
-- drepper@cygnus.com. */
fxam /* Is NaN or +-Inf? */
fstsw %ax
movb $0x45, %dh
andb %ah, %dh
cmpb $0x05, %dh
je 1f /* Is +-Inf, jump. */
fld %st
frndint /* int(x) */
fsubr %st,%st(1) /* fract(x) */
fxch
f2xm1 /* 2^(fract(x)) - 1 */
fld1
faddp /* 2^(fract(x)) */
fscale /* e^x */
fstp %st(1)
ret
1: testl $0x200, %eax /* Test sign. */
jz 2f /* If positive, jump. */
fstp %st
fldz /* Set result to 0. */
2: ret
END (__exp2f)
weak_alias (__exp2f, exp2f)

View File

@ -0,0 +1,38 @@
/*
* Written by J.T. Conklin <jtc@netbsd.org>.
* Adapted for exp2 by Ulrich Drepper <drepper@cygnus.com>.
* Public domain.
*/
#include <machine/asm.h>
ENTRY(__exp2l)
fldt 4(%esp)
/* I added the following ugly construct because exp(+-Inf) resulted
in NaN. The ugliness results from the bright minds at Intel.
For the i686 the code can be written better.
-- drepper@cygnus.com. */
fxam /* Is NaN or +-Inf? */
fstsw %ax
movb $0x45, %dh
andb %ah, %dh
cmpb $0x05, %dh
je 1f /* Is +-Inf, jump. */
fld %st
frndint /* int(x) */
fsubr %st,%st(1) /* fract(x) */
fxch
f2xm1 /* 2^(fract(x)) - 1 */
fld1
faddp /* 2^(fract(x)) */
fscale /* e^x */
fstp %st(1)
ret
1: testl $0x200, %eax /* Test sign. */
jz 2f /* If positive, jump. */
fstp %st
fldz /* Set result to 0. */
2: ret
END (__exp2l)
weak_alias (__exp2l, exp2l)

View File

@ -0,0 +1,59 @@
/*
* Written by J.T. Conklin <jtc@netbsd.org>.
* Adapted for use as log2 by Ulrich Drepper <drepper@cygnus.com>.
* Public domain.
*
* Changed to use fyl2xp1 for values near 1, <drepper@cygnus.com>.
*/
#include <machine/asm.h>
#ifdef __ELF__
.section .rodata
#else
.text
#endif
.align ALIGNARG(4)
ASM_TYPE_DIRECTIVE(one,@object)
one: .double 1.0
ASM_SIZE_DIRECTIVE(one)
/* It is not important that this constant is precise. It is only
a value which is known to be on the safe side for using the
fyl2xp1 instruction. */
ASM_TYPE_DIRECTIVE(limit,@object)
limit: .double 0.29
ASM_SIZE_DIRECTIVE(limit)
#ifdef PIC
#define MO(op) op##@GOTOFF(%edx)
#else
#define MO(op) op
#endif
.text
ENTRY(__log2)
#ifdef PIC
call 1f
1: popl %edx
addl $_GLOBAL_OFFSET_TABLE_+[.-1b], %edx
#endif
fldl MO(one)
fldl 4(%esp) // x : 1
fld %st // x : x : 1
fsub %st(2), %st // x-1 : x : 1
fld %st // x-1 : x-1 : x : 1
fabs // |x-1| : x-1 : x : 1
fcompl MO(limit) // x-1 : x : 1
fnstsw // x-1 : x : 1
andb $0x45, %ah
jz 2f
fstp %st(1) // x-1 : 1
fyl2xp1 // log(x)
ret
2: fstp %st(0) // x : 1
fyl2x // log(x)
ret
END (__log2)
weak_alias (__log2, log2)

View File

@ -0,0 +1,59 @@
/*
* Written by J.T. Conklin <jtc@netbsd.org>.
* Adapted for use as log2 by Ulrich Drepper <drepper@cygnus.com>.
* Public domain.
*
* Changed to use fyl2xp1 for values near 1, <drepper@cygnus.com>.
*/
#include <machine/asm.h>
#ifdef __ELF__
.section .rodata
#else
.text
#endif
.align ALIGNARG(4)
ASM_TYPE_DIRECTIVE(one,@object)
one: .double 1.0
ASM_SIZE_DIRECTIVE(one)
/* It is not important that this constant is precise. It is only
a value which is known to be on the safe side for using the
fyl2xp1 instruction. */
ASM_TYPE_DIRECTIVE(limit,@object)
limit: .double 0.29
ASM_SIZE_DIRECTIVE(limit)
#ifdef PIC
#define MO(op) op##@GOTOFF(%edx)
#else
#define MO(op) op
#endif
.text
ENTRY(__log2f)
#ifdef PIC
call 1f
1: popl %edx
addl $_GLOBAL_OFFSET_TABLE_+[.-1b], %edx
#endif
fldl MO(one)
flds 4(%esp) // x : 1
fld %st // x : x : 1
fsub %st(2), %st // x-1 : x : 1
fld %st // x-1 : x-1 : x : 1
fabs // |x-1| : x-1 : x : 1
fcompl MO(limit) // x-1 : x : 1
fnstsw // x-1 : x : 1
andb $0x45, %ah
jz 2f
fstp %st(1) // x-1 : 1
fyl2xp1 // log(x)
ret
2: fstp %st(0) // x : 1
fyl2x // log(x)
ret
END (__log2f)
weak_alias (__log2f, log2f)

View File

@ -0,0 +1,59 @@
/*
* Written by J.T. Conklin <jtc@netbsd.org>.
* Adapted for use as log2 by Ulrich Drepper <drepper@cygnus.com>.
* Public domain.
*
* Changed to use fyl2xp1 for values near 1, <drepper@cygnus.com>.
*/
#include <machine/asm.h>
#ifdef __ELF__
.section .rodata
#else
.text
#endif
.align ALIGNARG(4)
ASM_TYPE_DIRECTIVE(one,@object)
one: .double 1.0
ASM_SIZE_DIRECTIVE(one)
/* It is not important that this constant is precise. It is only
a value which is known to be on the safe side for using the
fyl2xp1 instruction. */
ASM_TYPE_DIRECTIVE(limit,@object)
limit: .double 0.29
ASM_SIZE_DIRECTIVE(limit)
#ifdef PIC
#define MO(op) op##@GOTOFF(%edx)
#else
#define MO(op) op
#endif
.text
ENTRY(__log2l)
#ifdef PIC
call 1f
1: popl %edx
addl $_GLOBAL_OFFSET_TABLE_+[.-1b], %edx
#endif
fldl MO(one)
fldt 4(%esp) // x : 1
fld %st // x : x : 1
fsub %st(2), %st // x-1 : x : 1
fld %st // x-1 : x-1 : x : 1
fabs // |x-1| : x-1 : x : 1
fcompl MO(limit) // x-1 : x : 1
fnstsw // x-1 : x : 1
andb $0x45, %ah
jz 2f
fstp %st(1) // x-1 : 1
fyl2xp1 // log(x)
ret
2: fstp %st(0) // x : 1
fyl2x // log(x)
ret
END (__log2l)
weak_alias (__log2l, log2l)

View File

@ -31,13 +31,18 @@ __cexpf (__complex__ float x)
{
if (isfinite (__imag__ x))
{
retval = __expf (__real__ x) * (__cosf (__imag__ x)
+ 1i * __sinf (__imag__ x));
float exp_val = __expf (__real__ x);
__real__ retval = exp_val * __cosf (__imag__ x);
__imag__ retval = exp_val * __sinf (__imag__ x);
}
else
/* If the imaginary part is +-inf or NaN and the real part is
not +-inf the result is NaN + iNan. */
retval = __nanf ("") + 1.0i * __nanf ("");
{
/* If the imaginary part is +-inf or NaN and the real part
is not +-inf the result is NaN + iNaN. */
__real__ retval = __nanf ("");
__imag__ retval = __nanf ("");
}
}
else if (__isinff (__real__ x))
{
@ -46,17 +51,27 @@ __cexpf (__complex__ float x)
if (signbit (__real__ x) == 0 && __imag__ x == 0.0)
retval = HUGE_VALF;
else
retval = ((signbit (__real__ x) ? 0.0 : HUGE_VALF)
* (__cosf (__imag__ x) + 1i * __sinf (__imag__ x)));
{
float value = signbit (__real__ x) ? 0.0 : HUGE_VALF;
__real__ retval = value * __cosf (__imag__ x);
__imag__ retval = value * __sinf (__imag__ x);
}
}
else if (signbit (__real__ x) == 0)
{
__real__ retval = HUGE_VALF;
__imag__ retval = __nanf ("");
}
else if (signbit (__real__ x))
retval = HUGE_VALF + 1.0i * __nanf ("");
else
retval = 0.0;
}
else
/* If the real part is NaN the result is NaN + iNan. */
retval = __nanf ("") + 1.0i * __nanf ("");
{
/* If the real part is NaN the result is NaN + iNan. */
__real__ retval = __nanf ("");
__imag__ retval = __nanf ("");
}
return retval;
}

View File

@ -1,4 +1,4 @@
/* Return value of complex exponential function for long double complex value.
/* Return value of complex exponential function for float complex value.
Copyright (C) 1997 Free Software Foundation, Inc.
This file is part of the GNU C Library.
Contributed by Ulrich Drepper <drepper@cygnus.com>, 1997.
@ -31,33 +31,48 @@ __cexpl (__complex__ long double x)
{
if (isfinite (__imag__ x))
{
retval = __expl (__real__ x) * (__cosl (__imag__ x)
+ 1i * __sinl (__imag__ x));
long double exp_val = __expl (__real__ x);
__real__ retval = exp_val * __cosl (__imag__ x);
__imag__ retval = exp_val * __sinl (__imag__ x);
}
else
/* If the imaginary part is +-inf or NaN and the real part is
not +-inf the result is NaN + iNan. */
retval = __nanl ("") + 1.0i * __nanl ("");
{
/* If the imaginary part is +-inf or NaN and the real part
is not +-inf the result is NaN + iNaN. */
__real__ retval = __nanl ("");
__imag__ retval = __nanl ("");
}
}
else if (__isinfl (__real__ x))
{
if (isfinite (__imag x))
if (isfinite (__imag__ x))
{
if (signbit (__real__ x) == 0 && __imag__ x == 0.0)
retval = HUGE_VALL;
retval = HUGE_VAL;
else
retval = ((signbit (__real__ x) ? 0.0 : HUGE_VALL)
* (__cosl (__imag__ x) + 1i * __sinl (__imag__ x)));
{
long double value = signbit (__real__ x) ? 0.0 : HUGE_VALL;
__real__ retval = value * __cosl (__imag__ x);
__imag__ retval = value * __sinl (__imag__ x);
}
}
else if (signbit (__real__ x) == 0)
{
__real__ retval = HUGE_VALL;
__imag__ retval = __nanl ("");
}
else if (signbit (__real__ x))
retval = HUGE_VALL + 1.0i * __nanl ("");
else
retval = 0.0;
}
else
/* If the real part is NaN the result is NaN + iNan. */
retval = __nanl ("") + 1.0i * __nanl ("");
{
/* If the real part is NaN the result is NaN + iNaN. */
__real__ retval = __nanl ("");
__imag__ retval = __nanl ("");
}
return retval;
}
weak_alias (__cexpl, cexpl)
weak_alias (__cexp, cexp)

View File

@ -0,0 +1,129 @@
/* Adapted for log2 by Ulrich Drepper <drepper@cygnus.com>.
/*
* ====================================================
* Copyright (C) 1993 by Sun Microsystems, Inc. All rights reserved.
*
* Developed at SunPro, a Sun Microsystems, Inc. business.
* Permission to use, copy, modify, and distribute this
* software is freely granted, provided that this notice
* is preserved.
* ====================================================
*/
/* __log2(x)
* Return the logarithm to base 2 of x
*
* Method :
* 1. Argument Reduction: find k and f such that
* x = 2^k * (1+f),
* where sqrt(2)/2 < 1+f < sqrt(2) .
*
* 2. Approximation of log(1+f).
* Let s = f/(2+f) ; based on log(1+f) = log(1+s) - log(1-s)
* = 2s + 2/3 s**3 + 2/5 s**5 + .....,
* = 2s + s*R
* We use a special Reme algorithm on [0,0.1716] to generate
* a polynomial of degree 14 to approximate R The maximum error
* of this polynomial approximation is bounded by 2**-58.45. In
* other words,
* 2 4 6 8 10 12 14
* R(z) ~ Lg1*s +Lg2*s +Lg3*s +Lg4*s +Lg5*s +Lg6*s +Lg7*s
* (the values of Lg1 to Lg7 are listed in the program)
* and
* | 2 14 | -58.45
* | Lg1*s +...+Lg7*s - R(z) | <= 2
* | |
* Note that 2s = f - s*f = f - hfsq + s*hfsq, where hfsq = f*f/2.
* In order to guarantee error in log below 1ulp, we compute log
* by
* log(1+f) = f - s*(f - R) (if f is not too large)
* log(1+f) = f - (hfsq - s*(hfsq+R)). (better accuracy)
*
* 3. Finally, log(x) = k + log(1+f).
* = k+(f-(hfsq-(s*(hfsq+R))))
*
* Special cases:
* log2(x) is NaN with signal if x < 0 (including -INF) ;
* log2(+INF) is +INF; log(0) is -INF with signal;
* log2(NaN) is that NaN with no signal.
*
* Constants:
* The hexadecimal values are the intended ones for the following
* constants. The decimal values may be used, provided that the
* compiler will convert from decimal to binary accurately enough
* to produce the hexadecimal values shown.
*/
#include "math.h"
#include "math_private.h"
#ifdef __STDC__
static const double
#else
static double
#endif
two54 = 1.80143985094819840000e+16, /* 43500000 00000000 */
Lg1 = 6.666666666666735130e-01, /* 3FE55555 55555593 */
Lg2 = 3.999999999940941908e-01, /* 3FD99999 9997FA04 */
Lg3 = 2.857142874366239149e-01, /* 3FD24924 94229359 */
Lg4 = 2.222219843214978396e-01, /* 3FCC71C5 1D8E78AF */
Lg5 = 1.818357216161805012e-01, /* 3FC74664 96CB03DE */
Lg6 = 1.531383769920937332e-01, /* 3FC39A09 D078C69F */
Lg7 = 1.479819860511658591e-01; /* 3FC2F112 DF3E5244 */
#ifdef __STDC__
static const double zero = 0.0;
#else
static double zero = 0.0;
#endif
#ifdef __STDC__
double __log2(double x)
#else
double __log2(x)
double x;
#endif
{
double hfsq,f,s,z,R,w,t1,t2,dk;
int32_t k,hx,i,j;
u_int32_t lx;
EXTRACT_WORDS(hx,lx,x);
k=0;
if (hx < 0x00100000) { /* x < 2**-1022 */
if (((hx&0x7fffffff)|lx)==0)
return -two54/zero; /* log(+-0)=-inf */
if (hx<0) return (x-x)/zero; /* log(-#) = NaN */
k -= 54; x *= two54; /* subnormal number, scale up x */
GET_HIGH_WORD(hx,x);
}
if (hx >= 0x7ff00000) return x+x;
k += (hx>>20)-1023;
hx &= 0x000fffff;
i = (hx+0x95f64)&0x100000;
SET_HIGH_WORD(x,hx|(i^0x3ff00000)); /* normalize x or x/2 */
k += (i>>20);
dk = (double) k;
f = x-1.0;
if((0x000fffff&(2+hx))<3) { /* |f| < 2**-20 */
if(f==zero) return dk;
R = f*f*(0.5-0.33333333333333333*f);
return dk-(R-f);
}
s = f/(2.0+f);
z = s*s;
i = hx-0x6147a;
w = z*z;
j = 0x6b851-hx;
t1= w*(Lg2+w*(Lg4+w*Lg6));
t2= z*(Lg1+w*(Lg3+w*(Lg5+w*Lg7)));
i |= j;
R = t2+t1;
if(i>0) {
hfsq=0.5*f*f;
return dk-((hfsq-(s*(hfsq+R)))-f);
} else {
return dk-((s*(f-R))-f);
}
}

View File

@ -0,0 +1,90 @@
/* e_logf.c -- float version of e_log.c.
* Conversion to float by Ian Lance Taylor, Cygnus Support, ian@cygnus.com.
* adapted for log2 by Ulrich Drepper <drepper@cygnus.com>
*/
/*
* ====================================================
* Copyright (C) 1993 by Sun Microsystems, Inc. All rights reserved.
*
* Developed at SunPro, a Sun Microsystems, Inc. business.
* Permission to use, copy, modify, and distribute this
* software is freely granted, provided that this notice
* is preserved.
* ====================================================
*/
#include "math.h"
#include "math_private.h"
#ifdef __STDC__
static const float
#else
static float
#endif
two25 = 3.355443200e+07, /* 0x4c000000 */
Lg1 = 6.6666668653e-01, /* 3F2AAAAB */
Lg2 = 4.0000000596e-01, /* 3ECCCCCD */
Lg3 = 2.8571429849e-01, /* 3E924925 */
Lg4 = 2.2222198546e-01, /* 3E638E29 */
Lg5 = 1.8183572590e-01, /* 3E3A3325 */
Lg6 = 1.5313838422e-01, /* 3E1CD04F */
Lg7 = 1.4798198640e-01; /* 3E178897 */
#ifdef __STDC__
static const float zero = 0.0;
#else
static float zero = 0.0;
#endif
#ifdef __STDC__
float __log2f(float x)
#else
float __log2f(x)
float x;
#endif
{
float hfsq,f,s,z,R,w,t1,t2,dk;
int32_t k,ix,i,j;
GET_FLOAT_WORD(ix,x);
k=0;
if (ix < 0x00800000) { /* x < 2**-126 */
if ((ix&0x7fffffff)==0)
return -two25/zero; /* log(+-0)=-inf */
if (ix<0) return (x-x)/zero; /* log(-#) = NaN */
k -= 25; x *= two25; /* subnormal number, scale up x */
GET_FLOAT_WORD(ix,x);
}
if (ix >= 0x7f800000) return x+x;
k += (ix>>23)-127;
ix &= 0x007fffff;
i = (ix+(0x95f64<<3))&0x800000;
SET_FLOAT_WORD(x,ix|(i^0x3f800000)); /* normalize x or x/2 */
k += (i>>23);
dk = (float)k;
f = x-(float)1.0;
if((0x007fffff&(15+ix))<16) { /* |f| < 2**-20 */
if(f==zero) return dk;
R = f*f*((float)0.5-(float)0.33333333333333333*f);
return dk-(R-f);}
}
s = f/((float)2.0+f);
z = s*s;
i = ix-(0x6147a<<3);
w = z*z;
j = (0x6b851<<3)-ix;
t1= w*(Lg2+w*(Lg4+w*Lg6));
t2= z*(Lg1+w*(Lg3+w*(Lg5+w*Lg7)));
i |= j;
R = t2+t1;
if(i>0) {
hfsq=(float)0.5*f*f;
return dk-((hfsq-(s*(hfsq+R)))-f);
} else {
return dk-((s*(f-R))-f);
}
}
weak_alias (__log2f, log2f)

View File

@ -32,5 +32,5 @@ CFLAGS-setjmp.c := -fno-omit-frame-pointer
long-double-fcts = yes
ifeq ($(subdir),elf)
CFLAGS-rtld.c += -Wno-uninitialized
CFLAGS-rtld.c += -Wno-uninitialized -Wno-unused
endif

View File

@ -184,9 +184,16 @@ _dl_start_user:
| Jump to the user's entry point.
jmp (%a4)");
/* Nonzero iff TYPE describes a relocation that should
skip the executable when looking up the symbol value. */
#define elf_machine_lookup_noexec_p(type) ((type) == R_68K_COPY)
/* Nonzero iff TYPE describes relocation of a PLT entry, so
PLT entries should not be allowed to define the value. */
#define elf_machine_pltrel_p(type) ((type) == R_68K_JMP_SLOT)
#define elf_machine_lookup_noplt_p(type) ((type) == R_68K_JMP_SLOT)
/* A reloc type used for ld.so cmdline arg lookups to reject PLT entries. */
#define ELF_MACHINE_RELOC_NOPLT R_68K_JMP_SLOT
/* The m68k never uses Elf32_Rel relocations. */
#define ELF_MACHINE_NO_REL 1
@ -203,60 +210,50 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
const Elf32_Sym *sym, const struct r_found_version *version)
{
Elf32_Addr *const reloc_addr = (void *) (map->l_addr + reloc->r_offset);
Elf32_Addr loadbase;
switch (ELF32_R_TYPE (reloc->r_info))
if (ELF32_R_TYPE (reloc->r_info) == R_68K_RELATIVE)
*reloc_addr = map->l_addr + reloc->r_addend;
else
{
case R_68K_COPY:
loadbase = RESOLVE (&sym, version, DL_LOOKUP_NOEXEC);
memcpy (reloc_addr, (void *) (loadbase + sym->st_value), sym->st_size);
break;
case R_68K_GLOB_DAT:
loadbase = RESOLVE (&sym, version, 0);
*reloc_addr = sym ? (loadbase + sym->st_value) : 0;
break;
case R_68K_JMP_SLOT:
loadbase = RESOLVE (&sym, version, DL_LOOKUP_NOPLT);
*reloc_addr = sym ? (loadbase + sym->st_value) : 0;
break;
case R_68K_8:
loadbase = RESOLVE (&sym, version, 0);
*(char *) reloc_addr = ((sym ? (loadbase + sym->st_value) : 0)
+ reloc->r_addend);
break;
case R_68K_16:
loadbase = RESOLVE (&sym, version, 0);
*(short *) reloc_addr = ((sym ? (loadbase + sym->st_value) : 0)
+ reloc->r_addend);
break;
case R_68K_32:
loadbase = RESOLVE (&sym, version, 0);
*reloc_addr = ((sym ? (loadbase + sym->st_value) : 0)
+ reloc->r_addend);
break;
case R_68K_RELATIVE:
*reloc_addr = map->l_addr + reloc->r_addend;
break;
case R_68K_PC8:
loadbase = RESOLVE (&sym, version, 0);
*(char *) reloc_addr = ((sym ? (loadbase + sym->st_value) : 0)
+ reloc->r_addend - (Elf32_Addr) reloc_addr);
break;
case R_68K_PC16:
loadbase = RESOLVE (&sym, version, 0);
*(short *) reloc_addr = ((sym ? (loadbase + sym->st_value) : 0)
+ reloc->r_addend - (Elf32_Addr) reloc_addr);
break;
case R_68K_PC32:
loadbase = RESOLVE (&sym, version, 0);
*reloc_addr = ((sym ? (loadbase + sym->st_value) : 0)
+ reloc->r_addend - (Elf32_Addr) reloc_addr);
break;
case R_68K_NONE: /* Alright, Wilbur. */
break;
default:
assert (! "unexpected dynamic reloc type");
break;
Elf32_Addr value = RESOLVE (&sym, version, ELF32_R_TYPE (reloc->r_info));
if (sym)
value += sym->st_value;
switch (ELF32_R_TYPE (reloc->r_info))
{
case R_68K_COPY:
memcpy (reloc_addr, (void *) value, sym->st_size);
break;
case R_68K_GLOB_DAT:
case R_68K_JMP_SLOT:
*reloc_addr = value;
break;
case R_68K_8:
*(char *) reloc_addr = value + reloc->r_addend;
break;
case R_68K_16:
*(short *) reloc_addr = value + reloc->r_addend;
break;
case R_68K_32:
*reloc_addr = value + reloc->r_addend;
break;
case R_68K_PC8:
*(char *) reloc_addr
= value + reloc->r_addend - (Elf32_Addr) reloc_addr;
break;
case R_68K_PC16:
*(short *) reloc_addr
= value + reloc->r_addend - (Elf32_Addr) reloc_addr;
break;
case R_68K_PC32:
*reloc_addr = value + reloc->r_addend - (Elf32_Addr) reloc_addr;
break;
case R_68K_NONE: /* Alright, Wilbur. */
break;
default:
assert (! "unexpected dynamic reloc type");
break;
}
}
}

View File

@ -1,112 +0,0 @@
/* Startup code compliant to the ELF SPARC ABI.
Copyright (C) 1996, 1997 Free Software Foundation, Inc.
This file is part of the GNU C Library.
The GNU C Library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
The GNU C Library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with the GNU C Library; see the file COPYING.LIB. If not,
write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
Boston, MA 02111-1307, USA. */
/* This is the canonical entry point, usually the first thing in the text
segment. The SVR4/SPARC ABI (NOTE: I don't actually have it) says that
when the entry point runs, most registers' values are unspecified,
except for:
%g1 Contains a function pointer to be registered with `atexit'.
This is how the dynamic linker arranges to have DT_FINI
functions called for shared libraries that have been loaded
before this code runs.
%sp The stack contains the arguments and environment:
0(%sp) argc
4(%sp) argv[0]
...
(4*argc)(%sp) NULL
(4*(argc+1))(%sp) envp[0]
...
NULL
*/
.text
.align 16
.global _start
_start:
/* %g1 contains the address of the shared library termination
function, which we will register with `atexit' to be called by
`exit'. I suspect that on some systems, and when statically
linked, this will not be set by anything to any function
pointer; hopefully it will be zero so we don't try to call
random pointers. */
orcc %g1, %g0, %o0 /* Move %g1 to %o0 while testing it. */
be nofini
/* In delay slot: clear the frame pointer. The ABI suggests this
be done, to mark the outermost frame obviously. */
clr %fp
/* Call atexit, argument was set in %o0 above. */
call atexit
nop
nofini:
/* We will use some local variables in registers below. %g1 and
the %oN registers are call-clobbered, so we can't just use them. */
#define ARGC %l0
#define ARGV %l1
#define ENVP %l2
#define TMP %l3
/* Do essential libc initialization. In statically linked
programs under the GNU Hurd, this is what sets up the
arguments on the stack for the code below. */
call __libc_init_first
sethi %hi(_environ), TMP /* In delay slot: prepare to use &_environ. */
/* Extract the arguments and environment as encoded on the stack
and save them in local variables. */
ld [%sp + 64], ARGC /* After the register save area, ARGC. */
add %sp, 64+4, ARGV /* Next, the ARGV elements. */
/* After ARGC words that are the ARGV elements, and a zero word,
are the ENVP elements. Do ENVP = &ARGV[ARGC + 1]. */
add ARGC, 1, ENVP
sll ENVP, 2, ENVP
add ARGV, ENVP, ENVP
/* Store ENVP in the global variable `_environ'. */
ld [TMP + %lo(_environ)], ENVP
/* Call `_init', which is the entry point to our own `.init'
section; and register with `atexit' to have `exit' call
`_fini', which is the entry point to our own `.fini' section. */
call _init
sethi %hi(_fini), TMP /* In delay slot of call. */
or TMP, %lo(_fini), %o0 /* Argument to atexit is &_fini. */
call atexit
nop
/* Call the user's main function, and exit with its value. */
mov ARGC, %o0
mov ARGV, %o1
call main
mov ENVP, %o2
call exit /* This should never return. */
nop
unimp 0 /* Crash if somehow it does return. */
/* Define a symbol for the first piece of initialized data. */
.data
.global __data_start
__data_start:
.long 0
.weak data_start
data_start = __data_start

11
sysdeps/stub/s_log2l.c Normal file
View File

@ -0,0 +1,11 @@
#include <math.h>
#include <stdio.h>
long double
__log2l (long double x)
{
fputs ("__log2l not implemented\n", stderr);
return 0.0;
}
stub_warning (__log2l)

View File

@ -112,10 +112,6 @@ struct termios
#define VT1 00200000
#define XTABS 01000000 /* Hmm.. Linux/i386 considers this part of TABDLY.. */
/* On Linux there is no OXTABS bit defined. Take it as an alias for
XTABS. */
#define OXTABS XTABS
/* c_cflag bit meaning */
#define CBAUD 0000037
#define B0 0000000 /* hang up */

View File

@ -54,16 +54,47 @@ typedef struct
#define __sigword(sig) (((sig) - 1) / (8 * sizeof (unsigned long int)))
#if defined __GNUC__ && __GNUC__ >= 2
#define __sigemptyset(set) \
# define __sigemptyset(set) \
(__extension__ ({ int __cnt = _SIGSET_NWORDS; \
sigset_t *__set = (set); \
while (--__cnt >= 0) __set->__val[__cnt] = 0; \
0; }))
#define __sigfillset(set) \
# define __sigfillset(set) \
(__extension__ ({ int __cnt = _SIGSET_NWORDS; \
sigset_t *__set = (set); \
while (--__cnt >= 0) __set->__val[__cnt] = ~0UL; \
0; }))
# ifdef _GNU_SOURCE
/* The POSIX does not specify for handling the whole signal set in one
command. This is often wanted and so we define three more functions
here. */
# define __sigisemptyset(set) \
(__extension__ ({ int __cnt = _SIGSET_NWORDS; \
const sigset_t *__set = (set); \
int __ret = __set->__val[--__cnt]; \
while (!__ret && --__cnt >= 0) \
__ret = __set->__val[__cnt]; \
__ret; }))
# define __sigandset(dest, left, right) \
(__extension__ ({ int __cnt = _SIGSET_NWORDS; \
sigset_t *__dest = (dest); \
const sigset_t *__left = (left); \
const sigset_t *__right = (right); \
while (--__cnt >= 0) \
__dest->__val[__cnt] = (__left->__val[__cnt] \
& __right->__val[__cnt]); \
0; }))
# define __sigorset(dest, left, right) \
(__extension__ ({ int __cnt = _SIGSET_NWORDS; \
sigset_t *__dest = (dest); \
const sigset_t *__left = (left); \
const sigset_t *__right = (right); \
while (--__cnt >= 0) \
__dest->__val[__cnt] = (__left->__val[__cnt] \
| __right->__val[__cnt]); \
0; }))
# endif
#endif
/* These functions needn't check for a bogus signal number -- error

View File

@ -105,10 +105,6 @@ struct termios
#define FF0 0000000
#define FF1 0100000
/* On Linux there is no OXTABS bit defined. Take it as an alias for
XTABS. */
#define OXTABS XTABS
/* c_cflag bit meaning */
#define CBAUD 0010017
#define B0 0000000 /* hang up */

View File

@ -48,7 +48,15 @@
* Defaults on "first" open.
*/
#define TTYDEF_IFLAG (BRKINT | ISTRIP | ICRNL | IMAXBEL | IXON | IXANY)
#define TTYDEF_OFLAG (OPOST | ONLCR | OXTABS)
#ifdef OXTABS
# define TTYDEF_OFLAG (OPOST | ONLCR | OXTABS)
#else
# if defined TAB3
# define TTYDEF_OFLAG (OPOST | ONLCR | TAB3)
# else
# define TTYDEF_OFLAG (OPOST | ONLCR)
# endif
#endif
#define TTYDEF_LFLAG (ECHO | ICANON | ISIG | IEXTEN | ECHOE|ECHOKE|ECHOCTL)
#define TTYDEF_CFLAG (CREAD | CS7 | PARENB | HUPCL)
#define TTYDEF_SPEED (B9600)
@ -59,16 +67,16 @@
#define CTRL(x) (x&037)
#define CEOF CTRL('d')
#ifdef _POSIX_VDISABLE
#define CEOL _POSIX_VDISABLE
# define CEOL _POSIX_VDISABLE
#else
#define CEOL ((unsigned char)'\377') /* XXX avoid _POSIX_VDISABLE */
# define CEOL ((unsigned char)'\377') /* XXX avoid _POSIX_VDISABLE */
#endif
#define CERASE 0177
#define CINTR CTRL('c')
#ifdef _POSIX_VDISABLE
#define CSTATUS _POSIX_VDISABLE
# define CSTATUS _POSIX_VDISABLE
#else
#define CSTATUS ((unsigned char)'\377') /* XXX avoid _POSIX_VDISABLE */
# define CSTATUS ((unsigned char)'\377') /* XXX avoid _POSIX_VDISABLE */
#endif
#define CKILL CTRL('u')
#define CMIN 1

View File

@ -27,5 +27,11 @@
#define MPN2FLOAT __mpn_construct_float
#define FLOAT_HUGE_VAL HUGE_VALF
#define USE_WIDE_CHAR 1
#define SET_MANTISSA(flt, mant) \
do { union ieee754_float u; \
u.f = (flt); \
u.ieee.mantissa = (mant) & 0x7fffff; \
(flt) = u.f; \
} while (0)
#include "../stdlib/strtod.c"

View File

@ -27,5 +27,12 @@
#define MPN2FLOAT __mpn_construct_long_double
#define FLOAT_HUGE_VAL HUGE_VALL
#define USE_WIDE_CHAR 1
#define SET_MANTISSA(flt, mant) \
do { union ieee854_long_double u; \
u.d = (flt); \
u.ieee.mantissa0 = ((mant) >> 32) & 0x7fffffff; \
u.ieee.mantissa1 = (mant) & 0xffffffff; \
(flt) = u.d; \
} while (0)
#include "../stdlib/strtod.c"