snoop_nisplus.c revision 7c478bd95313f5f23a4c958a745db2134aa03244
/*
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
* Common Development and Distribution License, Version 1.0 only
* (the "License"). You may not use this file except in compliance
* with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* See the License for the specific language governing permissions
* and limitations under the License.
*
* When distributing Covered Code, include this CDDL HEADER in each
* file and include the License file at usr/src/OPENSOLARIS.LICENSE.
* If applicable, add the following below this CDDL HEADER, with the
* fields enclosed by brackets "[]" replaced with your own identifying
* information: Portions Copyright [yyyy] [name of copyright owner]
*
* CDDL HEADER END
*/
/*
* Copyright (c) 1991, 1999, 2001 by Sun Microsystems, Inc.
* All rights reserved.
*/
#pragma ident "%Z%%M% %I% %E% SMI"
#include <ctype.h>
#include <setjmp.h>
#include <string.h>
#include <rpcsvc/nis_callback.h>
#include "snoop.h"
#include "nis_clnt.h"
extern char *dlc_header;
/*
* Number of spaces for each level of indentation. Since this value is
* assumed in most of the strings below, defining it is pretty quixotic.
*/
#define INDENT_SPACES 4
/*
* ==== Old (pre Sep '91) format for public keys in NIS+ directories, now
* removed from the header files. Should be removed from snoop once
* we're sure we won't see old-style packets
*/
#ifndef SZ_PKEY
#define SZ_PKEY 64
#endif /* SZ_PKEY */
/*
* ==== New (Aug '91) NIS+ remote procedure, which hasn't made into our
* header files yet. When it does, nuke this stuff.
*/
#ifndef NIS_UPDKEYS
#define NIS_UPDKEYS 24
#endif /* NIS_UPDKEYS */
/*
* ==== Constants for public keys. We should use NIS_MAXKEYLEN and the
* key-type constants from the NIS+ header files, but at present (Aug '91)
* we're ahead of the header files.
*/
#define KEYLEN_FIRST 0
#define KEYLEN_LIMIT 1024
#define KEYTYPE_FIRST 0
#define KEYTYPE_LIMIT 3
static char *procnames_short[] = {
"Null", /* 0 */
"Lookup", /* 1 */
"Add", /* 2 */
"Modify", /* 3 */
"Remove", /* 4 */
"IBlist", /* 5 */
"IBadd", /* 6 */
"IBmodify", /* 7 */
"IBremove", /* 8 */
"IBfirst", /* 9 */
"IBnext", /* 10 */
"** Unused 11", /* 11 */
"FindDir", /* 12 */
"** Unused 13", /* 13 */
"Status", /* 14 */
"DumpLog", /* 15 */
"Dump", /* 16 */
"Callback", /* 17 */
"CheckpointTime", /* 18 */
"Checkpoint", /* 19 */
"Ping", /* 20 */
"ServerState", /* 21 */
"MakeDir", /* 22 */
"RemoveDir", /* 23 */
"UpdateKeys", /* 24 */
};
static char *procnames_long[] = {
"Null procedure", /* 0 */
"Lookup", /* 1 */
"Add", /* 2 */
"Modify", /* 3 */
"Remove", /* 4 */
"List IBase", /* 5 */
"Add to IBase", /* 6 */
"Modify IBase", /* 7 */
"Remove from IBase", /* 8 */
"IBase First Entry", /* 9 */
"IBase Next Entry", /* 10 */
"** 11 (Unused) **", /* 11 */
"Find Directory", /* 12 */
"** 13 (Unused) **", /* 13 */
"Dump Directory Log", /* 15 */
"Dump Directory Contents", /* 16 */
"Check Callback Thread", /* 17 */
"Get Checkpoint Time", /* 18 */
"Establish Checkpoint", /* 19 */
"Ping Replicas", /* 20 */
"Change Server State", /* 21 */
"Make Directory", /* 22 */
"Remove Directory", /* 23 */
"Update Public Keys", /* 24 */
};
#define MAXPROC 24
static void detail_bool(void);
static void detail_callback(void);
static void detail_cback_data(void);
static void detail_cookie(void);
static void detail_cp_result(void);
static void detail_cptime(void);
static void detail_dump_args(void);
static void detail_ib_request(void);
static void detail_fd_args(void);
static void detail_fd_result(void);
static void detail_log_entry(void);
static void detail_log_result(void);
static void detail_nis_attrs(int);
static void detail_nis_error(void);
static void detail_nis_name(void);
static void detail_nis_result(void);
static void detail_nis_taglist(void);
static void detail_ns_request(void);
static void detail_ping_args(void);
static int is_printable(char *, unsigned int);
static void sum_bool(char *);
static void sum_callback(char *);
static void sum_cback_data(char *);
static void sum_cp_result(char *);
static void sum_cptime(char *);
static void sum_dump_args(char *);
static void sum_ib_request(char *);
static void sum_fd_args(char *);
static void sum_fd_result(char *);
static void sum_log_result(char *);
static void sum_nis_error(char *);
static void sum_nis_name(char *);
static void sum_nis_result(char *);
static void sum_nis_taglist(char *);
static void sum_ns_request(char *);
static void sum_ping_args(char *);
void
char *data;
int len;
{
char *line;
return;
return;
}
line = get_sum_line();
"NIS+ C %s",
switch (proc) {
case NIS_LOOKUP:
case NIS_ADD:
case NIS_MODIFY:
case NIS_REMOVE:
break;
case NIS_IBLIST:
case NIS_IBADD:
case NIS_IBMODIFY:
case NIS_IBREMOVE:
case NIS_IBFIRST:
case NIS_IBNEXT:
break;
case NIS_FINDDIRECTORY:
break;
case NIS_STATUS:
case NIS_SERVSTATE:
break;
case NIS_DUMPLOG:
case NIS_DUMP:
break;
case NIS_CALLBACK:
break;
case NIS_PING:
break;
case NIS_CPTIME:
case NIS_CHECKPOINT:
case NIS_MKDIR:
case NIS_RMDIR:
case NIS_UPDKEYS:
break;
default:
/* === mutter about bogus procnums? */
break;
}
} else {
switch (proc) {
case NIS_LOOKUP:
case NIS_ADD:
case NIS_MODIFY:
case NIS_REMOVE:
case NIS_IBLIST:
case NIS_IBADD:
case NIS_IBMODIFY:
case NIS_IBREMOVE:
case NIS_IBFIRST:
case NIS_IBNEXT:
break;
case NIS_FINDDIRECTORY:
break;
case NIS_STATUS:
case NIS_SERVSTATE:
break;
case NIS_DUMPLOG:
case NIS_DUMP:
break;
case NIS_CALLBACK:
break;
case NIS_CPTIME:
break;
case NIS_CHECKPOINT:
break;
case NIS_PING:
break;
case NIS_MKDIR:
case NIS_RMDIR:
case NIS_UPDKEYS:
break;
default:
/* === mutter about bogus procnums? */
break;
}
}
}
show_space();
return;
}
"Proc = %d (%s)",
switch (proc) {
case NIS_LOOKUP:
case NIS_ADD:
case NIS_MODIFY:
case NIS_REMOVE:
break;
case NIS_IBLIST:
case NIS_IBADD:
case NIS_IBMODIFY:
case NIS_IBREMOVE:
case NIS_IBFIRST:
case NIS_IBNEXT:
break;
case NIS_FINDDIRECTORY:
break;
case NIS_STATUS:
case NIS_SERVSTATE:
break;
case NIS_DUMPLOG:
case NIS_DUMP:
break;
case NIS_CALLBACK:
break;
case NIS_PING:
break;
case NIS_CPTIME:
case NIS_CHECKPOINT:
case NIS_MKDIR:
case NIS_RMDIR:
case NIS_UPDKEYS:
break;
default:
/* === mutter about bogus procnums? */
break;
}
} else {
switch (proc) {
case NIS_LOOKUP:
case NIS_ADD:
case NIS_MODIFY:
case NIS_REMOVE:
case NIS_IBLIST:
case NIS_IBADD:
case NIS_IBMODIFY:
case NIS_IBREMOVE:
case NIS_IBFIRST:
case NIS_IBNEXT:
break;
case NIS_FINDDIRECTORY:
break;
case NIS_STATUS:
case NIS_SERVSTATE:
break;
case NIS_DUMPLOG:
case NIS_DUMP:
break;
case NIS_CALLBACK:
detail_bool();
break;
case NIS_CPTIME:
break;
case NIS_CHECKPOINT:
break;
case NIS_PING:
break;
case NIS_MKDIR:
case NIS_RMDIR:
case NIS_UPDKEYS:
break;
default:
/* === mutter about bogus procnums? */
break;
}
}
show_trailer();
}
}
static char *cbnames_short[] = {
"Null", /* 0 */
"Receive", /* 1 */
"Finish", /* 2 */
"Error", /* 3 */
};
static char *cbnames_long[] = {
"Null procedure", /* 0 */
"Receive Callback Data", /* 1 */
"Finish Callback", /* 2 */
"Callback Error", /* 3 */
};
void
char *data;
int len;
{
char *line;
return;
}
line = get_sum_line();
"NIS+ Callback C %s",
switch (proc) {
case CBPROC_RECEIVE:
break;
case CBPROC_FINISH:
/* void: nothing to do */
break;
case CBPROC_ERROR:
break;
default:
/* === mutter about bogus procnums? */
break;
}
} else {
switch (proc) {
case CBPROC_RECEIVE:
break;
case CBPROC_FINISH:
case CBPROC_ERROR:
/* void: nothing to do */
break;
default:
/* === mutter about bogus procnums? */
break;
}
}
}
show_space();
return;
}
"Proc = %d (%s)",
switch (proc) {
case CBPROC_RECEIVE:
break;
case CBPROC_FINISH:
/* void: nothing to do */
break;
case CBPROC_ERROR:
break;
default:
/* === mutter about bogus procnums? */
break;
}
} else {
switch (proc) {
case CBPROC_RECEIVE:
detail_bool();
break;
case CBPROC_FINISH:
case CBPROC_ERROR:
/* void: nothing to do */
break;
default:
/* === mutter about bogus procnums? */
break;
}
}
show_trailer();
}
}
/*
* stringof_XXX() routines -- return printable representations of various
* numeric values. Would be nice if we could get this from the NIS+
* library instead of reinventing them.
* N.B. Mucho use of pointer-to-static result types (ugh); don't expect the
* return value to stay good for long.
*/
#ifndef RIGHTS_FORMAT
#define RIGHTS_FORMAT 1
#endif /* RIGHTS_FORMAT */
static struct {
int shift;
char *name;
} rightsclasses[] = {
#if RIGHTS_FORMAT == 1
24, "",
16, "",
8, "",
0, "",
16, "o:",
8, "g:",
0, "w:",
24, "u:",
#else /* RIGHTS_FORMAT == 3 */
16, "owner:",
8, "group:",
0, "world:",
24, "unauth:",
#endif /* RIGHTS_FORMAT */
};
char *
unsigned rights;
{
static char rightsbuf[100];
char *p;
int i;
for (i = 0; i < 4; i++) {
p += strlen(p);
*p++ = ' ';
}
if (rights == 0) {
p[-1] = ')'; /* Nuke that last space */
p[ 0] = 0;
} else {
}
return (rightsbuf);
}
char *
unsigned flags;
{
static char flagsbuf[120];
if (flags == 0) {
return (flagsbuf);
}
"%08x (%s%s%s%s",
if (flags != 0) {
"** Unknown bits %08x **, ", flags);
}
/* Replace the trailing ", " with ")" */
return (flagsbuf);
}
char *
unsigned flags;
{
static char flagsbuf[120];
if (flags == 0) {
return (flagsbuf);
}
"%08x (%s%s%s%s%s",
if (flags != 0) {
"** Unknown bits %08x **, ", flags);
}
/* Replace the trailing ", " with ")" */
return (flagsbuf);
}
char *
unsigned flags;
{
static char flagsbuf[100];
if (flags == 0) {
return (flagsbuf);
}
"%08x (%s%s%s%s",
if (flags != 0) {
"** Unknown bits %08x **, ", flags);
}
/* Replace the trailing ", " with ")" */
return (flagsbuf);
}
char *
unsigned flags;
{
static char flagsbuf[80];
if (flags == 0) {
return (flagsbuf);
}
"%08x (%s%s%s",
if (flags != 0) {
"** Unknown bits %08x **, ", flags);
}
/* Replace the trailing ", " with ")" */
return (flagsbuf);
}
char *
int ttype;
{
switch (ttype) {
case TAG_DEBUG: return ("DEBUG");
case TAG_STATS: return ("STATS");
case TAG_GCACHE: return ("GCACHE");
case TAG_DCACHE: return ("DCACHE");
case TAG_OCACHE: return ("OCACHE");
case TAG_SECURE: return ("SECURE");
#ifdef undef
/*
* Old tags, removed September '91 (some of the tag-numbers have been
* reassigned, just to make things completely confusing).
*/
case TAG_LOOKUPS: return ("LOOKUPS";
case TAG_S_LOOKUPS: return ("S_LOOKUPS";
case TAG_U_LOOKUPS: return ("U_LOOKUPS";
#endif /* undef */
case TAG_OPSTATS: return ("OPSTATS");
case TAG_THREADS: return ("THREADS");
case TAG_UPDATES: return ("UPDATES");
case TAG_VISIBLE: return ("VISIBLE");
case TAG_S_DCACHE: return ("S_DCACHE");
case TAG_S_OCACHE: return ("S_OCACHE");
case TAG_S_GCACHE: return ("S_GCACHE");
case TAG_S_STORAGE: return ("S_STORAGE");
default: return ("*Unknown*");
}
}
char *
int otype;
{
static char buf[30];
switch (otype) {
case NIS_BOGUS_OBJ: return ("BOGUS (uninitialized?)");
case NIS_NO_OBJ: return ("NULL");
case NIS_DIRECTORY_OBJ: return ("DIRECTORY");
case NIS_GROUP_OBJ: return ("GROUP");
case NIS_TABLE_OBJ: return ("TABLE");
case NIS_ENTRY_OBJ: return ("ENTRY");
case NIS_LINK_OBJ: return ("LINK");
case NIS_PRIVATE_OBJ: return ("PRIVATE");
return (buf);
}
}
char *
int et;
{
static char buf[30];
switch (et) {
case ADD_NAME: return ("ADD_NAME");
case REM_NAME: return ("REM_NAME");
case MOD_NAME_OLD: return ("MOD_NAME_OLD");
case MOD_NAME_NEW: return ("MOD_NAME_NEW");
case ADD_IBASE: return ("ADD_IBASE");
case REM_IBASE: return ("REM_IBASE");
case MOD_IBASE: return ("MOD_IBASE");
case UPD_STAMP: return ("UPD_STAMP");
return (buf);
}
}
char *
unsigned ktype;
{
static char buf[40];
char *p;
switch (ktype) {
case 0: strcpy(p, "(None)"); break;
default: strcpy(p, "(** Unknown **)"); break;
}
return (buf);
}
static void
char *line;
{
}
static unsigned
char *line;
{
unsigned err = getxdr_u_long();
return (err);
}
static void
char *line;
{
/* Leave the optional object for detailed listings */
}
int nchars_attrval = 32;
static void
char *line;
{
unsigned long nattrs;
unsigned long len;
int pos;
char *val;
nattrs = getxdr_u_long();
switch (nattrs) {
case 0:
/* === Could print "No attrs " */
break;
case 1:
pos = getxdr_pos();
} else {
}
} else {
} else {
/*
* Too lazy to print hex ourselves; instead,
* back up and use snoop's hex-printer
*/
}
}
*line++ = ']';
*line = 0;
break;
default:
/* === Note that we haven't skipped the attrs */
break;
}
/* === Don't bother with flags, obj, cbhost, bufsize, cookie */
}
static void
char *line;
{
#ifdef LESS_TERSE
#endif /* LESS_TERSE */
}
static void
char *line;
{
unsigned ntags;
unsigned ttype;
ntags = getxdr_u_long();
if (ntags == 0) {
return;
}
ttype = getxdr_u_long();
if (ntags > 1) {
}
}
static void
char *line;
{
}
/*ARGSUSED*/
static void
char *line;
{
/* netobjs are pretty opaque, so don't try to summarize */
}
static void
char *line;
{
}
static void
char *line;
{
}
static void
char *line;
{
}
static void
char *line;
{
unsigned nobjs;
(void) sumxdr_nis_error(line);
nobjs = getxdr_u_long();
if (nobjs != 0) {
}
}
static void
char *line;
{
(void) sumxdr_nis_error(line);
#ifdef LESS_TERSE
#endif /* LESS_TERSE */
}
static void
char *line;
{
unsigned nents;
(void) sumxdr_nis_error(line);
nents = getxdr_u_long();
}
static void
char *line;
{
}
static void
char *line;
{
}
static void
char *line;
{
(void) sumxdr_nis_error(line);
}
static void
char *line;
{
(void) sumxdr_nis_error(line);
}
/*
* showxdr_longhex() -- ersatz wrapper around showxdr_hex() to ensure we
* don't display too much on one line. Multi-line results will
* === probably look pretty awful, but we may at least prevent core-dumps
*/
int nwords_longhex = 8;
static void
int len;
char *fmt;
{
while (len > nbytes_longhex) {
len -= nbytes_longhex;
}
}
static void
{
int pos;
pos = getxdr_pos();
}
void
{
showxdr_time(" Object created at %s");
showxdr_time(" last modified at %s");
}
static void
int outdent; /* Crock to get indentation right. Normally zero; */
/* set to four instead to remove leading spaces */
{
unsigned nep;
unsigned ktype;
int pos1;
nep = getxdr_u_long();
while (nep-- > 0) { /* list of endpoints */
(void) showxdr_string(1024,
outdent + " Uaddr = %s");
(void) showxdr_string(1024,
outdent + " Family = %s");
(void) showxdr_string(1024,
outdent + " Protocol = %s");
}
/*
* The format of the public-key information has changed (Aug '91).
* Ye olde style was a u_char[64] (which XDR's pretty inefficiently,
* but that's another matter). The new format has a key-type
* enumeration followed by an opaque<NIS_MAXKEYLEN>. For now
* (hence probably for all time) we'll hard-code the values of the
* enumeration and of NIS_MAXKEYLEN here rather than getting them
* from a header file. Tsk. Also for now, we'll try to guess
* whether we're looking at the new format or the old.
*/
pos1 = getxdr_pos();
ktype = getxdr_u_long();
int pos2;
unsigned klen;
pos2 = getxdr_pos();
klen = getxdr_u_long();
if (klen < KEYLEN_LIMIT) {
/*
* Smells like new-style key; let's hope so. If we're
* wrong, it may cause XDR underflow. Ugh. ====
*/
outdent + " Key type = %s",
if (klen != 0) {
if (ktype == NIS_PK_DHEXT) {
int marker;
int key_count;
marker = getxdr_pos();
key_count = 1;
a_u_long = getxdr_u_long();
((ushort_t)0xffff);
* 4;
" Key %d length = %hu bits",
" Algorithm type = %hu",
algtype);
if (keylen != 0)
" Key value = %s");
key_count++;
}
} else {
" Key value = %s");
}
}
return;
}
}
/*
* It didn't smell new, so assume it's the old u_char[64], which
* XDR's as 64 32-bit words (ouch).
*/
outdent + " [Public Key not displayed]");
}
void
{
unsigned nstyp;
int pos;
char *line;
SHOW_NIS_NAME(" Name = %s");
pos = getxdr_pos();
nstyp = getxdr_u_long();
switch (nstyp) {
case NIS:
break;
case SUNYP:
break;
case DNS:
break;
default:
break;
}
while (nserv-- > 0) { /* array of servers */
}
(void) showxdr_u_long(" Time to live = %lu (seconds)");
/* === show time in more useful form too? */
while (nar-- > 0) { /* list of ar masks */
pos = getxdr_pos();
ar = getxdr_u_long();
otype = getxdr_u_long();
}
}
void
{
unsigned val;
int pos;
pos = getxdr_pos();
val = getxdr_u_long();
while (val-- > 0) {
SHOW_NIS_NAME(" %s");
}
}
void
{
unsigned ncols;
unsigned col;
(void) showxdr_long (" Max Columns = %d");
unsigned val;
char format[23];
/* === Print all three on one line? */
pos1 = getxdr_pos();
val = getxdr_u_long();
pos2 = getxdr_pos();
val = getxdr_u_long();
}
}
void
{
char *entyp;
int is_nis_object = 0;
/* Don't rely on entyp[] remaining valid */
unsigned flags;
/* === Print both on one line? */
pos1 = getxdr_pos();
flags = getxdr_u_long();
pos2 = getxdr_pos();
if (ncols == 1) {
" Flags = %s",
} else {
"%6d: Flags = %s",
}
len = getxdr_u_long();
if (is_nis_object &&
len == sizeof (unsigned long) &&
/* Special case for type = "NIS object" */
unsigned otype = getxdr_u_long();
" Value = %08x (ObjType = %s)",
} else {
" Value = Binary %s");
}
} else {
" Value = ASCII \"%s\"");
}
}
}
void
{
int pos;
int val;
pos = getxdr_pos();
val = getxdr_long();
detail_nis_attrs(0);
SHOW_NIS_NAME(" Real Name= %s");
}
void
{
/* ==== Need something fancier than this to be really useful */
}
void
{
int pos;
SHOW_NIS_NAME(" Name = %s");
SHOW_NIS_NAME(" Owner = %s");
SHOW_NIS_NAME(" Group = %s");
SHOW_NIS_NAME(" Domain = %s");
pos = getxdr_pos();
rights = getxdr_u_long();
(void) showxdr_u_long(" Lifetime = %8lu (seconds)");
/* ?? show_space(); */
pos = getxdr_pos();
otype = getxdr_u_long();
" ObjType = %08x (%s)",
switch (otype) {
case NIS_DIRECTORY_OBJ:
break;
case NIS_GROUP_OBJ:
break;
case NIS_TABLE_OBJ:
break;
case NIS_ENTRY_OBJ:
break;
case NIS_LINK_OBJ:
break;
case NIS_PRIVATE_OBJ:
break;
default:
/* ==== Can't do anything clever, right? */
break;
}
}
static void
{
unsigned nobjs;
SHOW_NAME();
nobjs = getxdr_u_long();
/* nobjs should be 0 or 1 only; === should check it ? */
if (nobjs != 0) {
}
while (nobjs-- > 0) {
}
}
static void
{
unsigned len;
unsigned flags;
int pos;
SHOW_NAME();
pos = getxdr_pos();
flags = getxdr_u_long();
pos = getxdr_pos();
len = getxdr_u_long();
if (len == 0) {
} else {
/* len should be 0 or 1 only; === should check it ? */
while (len-- > 0) {
}
}
pos = getxdr_pos();
len = getxdr_u_long();
if (len == 0) {
} else {
/* len should be 0 or 1 only; === should check it ? */
while (len-- > 0) {
}
}
(void) showxdr_u_long("Bufsize = %lu");
}
static void
{
SHOW_NAME();
SHOW_NIS_NAME("Requester = %s");
}
static void
{
unsigned ntags;
unsigned tagn;
unsigned ttype;
int pos;
if (ntags != 1) {
}
pos = getxdr_pos();
ttype = getxdr_u_long();
" Tag name = %08x (%s)",
/* ^ ==== nis.x says it's a string rather than an opaque, */
/* but is it really? */
}
}
static void
{
unsigned nserv;
int pos;
SHOW_NAME();
showxdr_time("Time = %s");
pos = getxdr_pos();
nserv = getxdr_u_long();
if (nserv == 1) {
} else if (nserv > 1) {
"Num callbacks = %lu (!?):", nserv);
}
while (nserv-- > 0) {
}
}
static void
detail_callback() /* i.e. the netobj argument to NIS_CALLBACK */
{
}
static void
{
unsigned len;
int pos;
pos = getxdr_pos();
len = getxdr_u_long();
if (len == 0) {
} else {
}
}
static void
{
SHOW_NAME();
showxdr_time("Time = %s");
}
static void
{
SHOW_NAME();
}
static void
{
if (getxdr_long() == 0) {
} else {
if (nobjs != 1) {
}
}
}
}
static void
{
int pos;
pos = getxdr_pos();
nobjs = getxdr_u_long();
if (nobjs != 1) {
}
}
showxdr_u_long("Server ticks = %8lu");
showxdr_u_long("Database ticks = %8lu");
}
static void
{
int pos;
unsigned len;
int dir_pos;
unsigned dir_len;
int dir_end;
SHOW_NAME();
/* nis.x doesn't say so, but the opaque contains a directory_obj */
if (dir_len == 0) {
} else {
dir_pos = getxdr_pos();
/* ^^^^^^^^^^ Did XDR do this already? */
pos = getxdr_pos();
"(Skipping %d unused bytes at end of directory object)",
}
}
len = getxdr_u_long();
if (len == 0) {
"Signature = NULL");
} else {
if (len > 8) {
"Signature length is %lu, expected <= 8 bytes",
len);
}
}
}
/*
* is_printable() -- looks for a string of (len-1) printable characters
* followed by a NUL. Characters are deemed printable iff ctype's
* isprint() macro says so, thus tab (^I) is regarded as unprintable.
* === Is this test more stringent than we want, esp wrt placement of NUL?
*/
static int
char *str;
unsigned len;
{
while (len > 1) {
return (0);
}
}
}
static void
int outdent; /* Crock to get indentation right. Normally zero; */
/* set to four instead to remove leading spaces */
{
unsigned nattrs;
while (nattrs-- > 0) {
char *str;
unsigned len;
int pos;
outdent + " AttrName = %s");
pos = getxdr_pos();
" AttrVal = ASCII \"%s\"");
} else {
" AttrVal = Binary %s");
}
}
}
static void
{
int pos;
long val;
showxdr_time(" Log Time = %s");
pos = getxdr_pos();
val = getxdr_long();
SHOW_NIS_NAME(" Principal = %s");
SHOW_NIS_NAME(" Table/dir = %s");
detail_nis_attrs(0);
}
static void
{
int pos;
pos = getxdr_pos();
len = getxdr_u_long();
if (nents != 1) {
}
}
}
static void
{
int pos;
unsigned val;
pos = getxdr_pos();
val = getxdr_u_long();
}
static void
{
showxdr_time("Time = %s");
}
static void
{
showxdr_u_long("Ticks (Server) = %lu");
showxdr_u_long(" (Database) = %lu");
}