\documentstyle[makeidx,size,12pt]{trreport}
%---------------------------------------------------------------------------
% xstat-ispec.tex
%
% Interface specification document for the AFS xstat data collection tool.
%
% Edward R. Zayas
% Transarc Corporation
% Pittsburgh, PA 15219
%
% Copyright (C) 1991 Edward R. Zayas and Transarc Corporation
% All rights reserved
%===========================================================================

\setcounter{tocdepth}{5}     % Table of Contents Depth
\setcounter{secnumdepth}{5}  % Section Numbering Depth
\makeindex
\footchapdate

\begin{document}

%------------------------------------------------------------------------
% Define title page

\title{Interface Specification \\ 
	for the \\ 
	AFS-3 {\it xstat} Data Collection Facility}
\documentname{AFS-3 {\it xstat} Interface Spec}
\author{Edward R. Zayas \\ \ \\ Transarc Corporation}
\date{Version 1.0 of 18 September 1991 16:08 \\ 
\copyright Copyright 1991 Transarc Corporation \\
All Rights Reserved \\
FS-00-D187}

\maketitle
\tableofcontents 

%========================================================================
\chapter{Introduction}
\label{xstat-Intro}

%-----------------------------------------------------------------------
\section{Overview}
\label{xstat-Overview}

The AFS 3.1 product release has been instrumented to allow clients to
collect extended statistics concerning the operation of the {\it
FileServer} and {\it CacheManager} agents.  This change consists of
two new RPC calls added to each of the {\it FileServer} and {\it
CacheManager} callback interfaces, as described in the interface
specification document entitled {\it AFS-3 FileServer/CacheManager
Interface Specification}.

Collecting information using these interface extensions requires some
care.  First, any program calling the {\it FileServer} interface
directly must also export the {\it CacheManager}'s callback interface.
AFS {\it FileServers} were designed to consider any party calling its
RPC routines a full-fledged {\it CacheManager}, and thus uses the
callback interface to make sure that the ``{\it CacheManager}'' asking
for this service is fully synchronized regarding the callback state on
its cached files.  A {\it FileServer} will also periodically generate
keep-alive probes of its stable of {\it CacheManager}s that have
interacted with it.  Thus, the calling program must also answer these
probes.  In addition to the callback complication, it is expected that
any serious data-collection facility will gather data at fixed
intervals.  It is unreasonable to ask {\it FileServer}s and {\it
CacheManager}s to keep track of the set of clients collecting this
information.  Rather, the onus must be on the user-level collector
process to gather the desired data on a regular basis.

This document describes the {\it xstat} facility, which may be used to
simplify the creation of applications wishing to use the new server
RPC calls to regularly collect statistical information.  The {\it
xstat} service consists of two libraries which user-level applications
can import, namely {\it libxstat_fs.a} and {\it libxstat_cm.a} (for
the {\it FileServer} and {\it CacheManager} respectively).  The main
routine provided by these libraries allows the caller to register a
set of servers to be examined, the frequency of the probes, and a
routine written by the user which will be called each time data is
collected.  Thus, all the lightweight processes, callback
interactions, and timing issues have been handled by these two
libraries, with the user free to simply process the data as it
arrives.

%-----------------------------------------------------------------------
\section{Data Collections}
\label{xstat-Overview-DC}

The {\it FileServer} and {\it CacheManager} each define one or more
{\it data collections} which clients may fetch.  A data collection is
simply a related set of numbers which may be collected as a unit.  The
RPC interface calls refer to these data collections by a numerical
identifier, with the lowest defined to be zero.  For example, each of
the {\it FileServer} and {\it CacheManager} define {\it profiling} and
{\it performance} data collections.  The profiling collections keep
longword counts for each of the internal functions called within the
servers, allowing bottleneck analysis to be performed.  The
performance collections include many interesting measurements of
internal quantities, including disk I/O figures for the {\it
FileServer} and cache hit/miss information for {\it CacheManager}s.

%-----------------------------------------------------------------------
\section{Document Layout}
\label{xstat-Overview-Layout}

This document will first present the definitions used by this
facility, including bookkeeping information and the data collection
structures currently exported by the {\it FileServer} and {\it
CacheManager}.  After that, the programming interfaces for the two
servers are specified.  Finally, the body of a handler routine which
processes the arrival of a {\it CacheManager} {\tt
AFSCB_XSTATSCOLL_PERF_INFO} data collection (see Sections
\ref{xstat-DC-CM-CMPerfStats} and \ref{xstat-PI-CM-Init}) is provided
as an example of how these types of routines should be written.

%========================================================================
\chapter{Bookkeeping Information}
\label{xstat-Bookkeeping}

In order to communicate information concerning data that has just been
collected, the {\it xstat} libraries define certain structures and
exports a set of variables.  The routine specified by the programmer
as responsible for handling the arrival of a data collection (See
Sections \ref{xstat-PI-FS-Init} and \ref{xstat-PI-CM-Init}) will look
at these variables to determine such things as the type of collection
just received, the time of its arrival, whether it was successfully
fetched, and the number of probes performed so far.  The definition
from the two separate libraries are very similar, as they convey
basically the identical type of information.  In each case, structures
are defined to record the connection information regarding the AFS
agents being observed, probe structures which contain the full results
of an attempt to pull one of the desired data collections from the
server, and variables which instantiate this information.

%-----------------------------------------------------------------------
\section{{\it FileServer}}
\label{xstat-Bookkeeping-FS}

%-----------------------------------------------------------------------
\subsection{Connection Structure}
\label{xstat-Bookkeeping-FS-Connection}

The {\tt xstat_fs_ConnectionInfo} structure is defined to allow the
user to have all the information for a particular {\it FileServer} at
their fingertips.  Included is the original socket information they
fed in for the given server, the {\it Rx} connection structure built
in turn by the library, and the human-readable version of the host
name.

\begin{programexample}
struct xstat_fs_ConnectionInfo {
    struct sockaddr_in skt;		/*Socket info*/
    struct rx_connection *rxconn;	/*Rx connection*/
    char hostName[256];			/*Computed hostname*/
};
\end{programexample}

%-----------------------------------------------------------------------
\subsection{Probe Result Structure}
\label{xstat-Bookkeeping-FS-Probe}

The {\tt xstat_fs_ProbeResults} structure encapsulates all the
information concerning a particular instance of a data collection
fetched from a {\it FileServer}.  The handler routine must examine
this information to properly process the newly-arrived data.  This
structure reports the probe number to which this information
corresponds, the time on the server at which the measurement was
taken, information on the connection from which this data was fetched,
whether the probe was successful, and the specific collection number
contained in the data buffer.

\begin{programexample}
struct xstat_fs_ProbeResults {
    int probeNum;			   /*Probe number*/
    long probeTime;			   /*Time probe initiated*/
    struct xstat_fs_ConnectionInfo *connP; /*Connection polled*/
    long collectionNumber;		   /*Collection received*/
    AFS_CollData data;			   /*Ptr to data collected*/
    int probeOK;			   /*Latest probe successful?*/
};
\end{programexample}

%-----------------------------------------------------------------------
\subsection{Associated Variables}
\label{xstat-Bookkeeping-FS-Vars}

The status of the data collection task is exported to callers via the
following four variables maintained by the {\it libxstat_fs.a}
library.  Since the data collection handler routine specified by the
user executes in the library's context, all of these variables are
visible to it.

\begin{programexample}
extern int xstat_fs_numServers;		/*# connected servers*/
extern struct xstat_fs_ConnectionInfo
    *xstat_fs_ConnInfo;			/*Ptr to connections*/
extern int numCollections;		/*Num data collections*/
extern struct xstat_fs_ProbeResults
    xstat_fs_Results;			/*Latest probe results*/
\end{programexample}

%-----------------------------------------------------------------------
\section{{\it CacheManager}}
\label{xstat-Bookkeeping-CM}

The bookkeeping definitions and variables exported by the {\it
libxstat_cm.a} library are exact analogues of those found within the
library supporting {\it FileServer} data collection.

%-----------------------------------------------------------------------
\subsection{Connection Structure}
\label{xstat-Bookkeeping-CM-Connection}

The {\tt xstat_cm_ConnectionInfo} structure is defined to allow the
user to have all the information for a particular {\it CacheManager}
at their fingertips.  Included is the original socket information they
fed in for the given server, the {\it Rx} connection structure built
in turn by the library, and the human-readable version of the host
name.

\begin{programexample}
struct xstat_cm_ConnectionInfo {
    struct sockaddr_in skt;		/*Socket info*/
    struct rx_connection *rxconn;	/*Rx connection*/
    char hostName[256];			/*Computed hostname*/
};
\end{programexample}

%-----------------------------------------------------------------------
\subsection{Probe Result Structure}
\label{xstat-Bookkeeping-CM-Probe}

The {\tt xstat_fs_ProbeResults} structure encapsulates all the
information concerning a particular instance of a data collection
fetched from a {\it CacheManager}.  For more details, refer to the
{\it FileServer} analogue in Section \ref{xstat-Bookkeeping-FS-Probe}

\begin{programexample}
struct xstat_cm_ProbeResults {
    int probeNum;			   /*Probe number*/
    long probeTime;			   /*Time probe initiated*/
    struct xstat_cm_ConnectionInfo *connP; /*Connection polled*/
    long collectionNumber;		   /*Collection received*/
    AFSCB_CollData data;		   /*Ptr to data collected*/
    int probeOK;			   /*Latest probe successful?*/
};
\end{programexample}

%-----------------------------------------------------------------------
\subsection{Associated Variables}
\label{xstat-Bookkeeping-CM-Vars}

The status of the data collection task is exported to callers via the
following four variables maintained by the {\it libxstat_cm.a}
library.  Since the data collection handler routine specified by the
user executes in the library's context, all of these variables are
visible to it.

\begin{programexample}
extern int xstat_cm_numServers;		/*# connected servers*/
extern struct xstat_cm_ConnectionInfo
    *xstat_cm_ConnInfo;			/*Ptr to connections*/
extern int numCollections;		/*Num data collections*/
extern struct xstat_cm_ProbeResults
    xstat_cm_Results;			/*Latest probe results*/
\end{programexample}

%========================================================================
\chapter{Defined Data Collections}
\label{xstat-DC}

%-----------------------------------------------------------------------
\section{{\it FileServer} Collections}
\label{xstat-DC-FS}

%-----------------------------------------------------------------------
\subsection{{\tt struct afs_FSCallStats}}
\label{xstat-DC-FS-FSCallStats}

This is the data collection specified by the {\tt
AFS_XSTATSCOLL_CALL_INFO} identifier, whose value is 0.  It consists
of an array of longword fields, each one logging the number of calls
to the internal {\it FileServer} routine implied by the name of the
field.  Thus, field {\tt C_SRXAFS_FetchData} counts the number of
times the {\it SRXAFS_FetchData()} function was called.

{\bf Note:} This structure and hence the corresponding data collection
are {\bf not} available in the AFS 3.1 product.  A request for the
{\it FileServer}'s {\tt AFS_XSTATSCOLL_CALL_INFO} collection will
succeed, but return a zero-length array.  This collection will be
fully supported in future releases.

%\begin{programexample}
%
%\end{programexample}

%-----------------------------------------------------------------------
\subsection{{\tt struct afs_PerfStats}}
\label{xstat-DC-FS-FSPerfStats}

This is the data collection specified by the {\tt
AFS_XSTATSCOLL_PERF_INFO} identifier, whose value is 1.  It reports on
several internal performance statistics relating to vnode cache
entries, directory package operations, {\it Rx} activity, and host
entries.

\begin{programexample}
struct afs_PerfStats {
    long numPerfCalls;		/*# of performance calls rcvd*/

    /*
     * Vnode cache section.
     */
    long vcache_L_Entries;	/*Num entries in LARGE vnode cache*/
    long vcache_L_Allocs;	/*# allocs, large*/
    long vcache_L_Gets;		/*# gets, large*/
    long vcache_L_Reads;	/*# reads, large*/
    long vcache_L_Writes;	/*# writes, large*/

    long vcache_S_Entries;	/*Num entries in SMALL vnode cache*/
    long vcache_S_Allocs;	/*# allocs, small*/
    long vcache_S_Gets;		/*# gets, small*/
    long vcache_S_Reads;	/*# reads, small*/
    long vcache_S_Writes;	/*# writes, small*/

    long vcache_H_Entries;	/*Num entries in HEADER vnode cache */
    long vcache_H_Gets;		/*# gets*/
    long vcache_H_Replacements;	/*# replacements*/

    /*
     * Directory package section.
     */
    long dir_Buffers;		/*Num buffers in use*/
    long dir_Calls;		/*Num read calls made*/
    long dir_IOs;		/*I/O ops performed*/

    /*
     * Rx section.  These numbers represent the contents of the
     * rx_stats structure maintained by Rx.  All other Rx info,
     * including struct rx_debug and connection stuff is available
     * via the rxdebug interface.
     */
    long rx_packetRequests;		/*Packet alloc requests*/
    long rx_noPackets_RcvClass;		/*Failed pkt requests, receives*/
    long rx_noPackets_SendClass;	/*Ditto, sends*/
    long rx_noPackets_SpecialClass;	/*Ditto, specials*/
    long rx_socketGreedy;		/*Did SO_GREEDY succeed?*/
    long rx_bogusPacketOnRead;		/*Short pkts rcvd*/
    long rx_bogusHost;			/*Host addr from bogus pkts*/
    long rx_noPacketOnRead;		/*Read pkts w/no packet there*/
    long rx_noPacketBuffersOnRead;	/*Pkts dropped from buff shortage*/
    long rx_selects;			/*Selects waiting on pkt or timeout*/
    long rx_sendSelects;		/*Selects forced upon sends*/
    long rx_packetsRead_RcvClass;	/*Packets read, rcv class*/
    long rx_packetsRead_SendClass;	/*Packets read, send class*/
    long rx_packetsRead_SpecialClass;	/*Packets read, special class*/
    long rx_dataPacketsRead;		/*Uniq data packets read off wire*/
    long rx_ackPacketsRead;		/*Ack packets read*/
    long rx_dupPacketsRead;		/*Duplicate data packets read*/
    long rx_spuriousPacketsRead;	/*Inappropriate packets read*/
    long rx_packetsSent_RcvClass;	/*Packets sent, rcv class*/
    long rx_packetsSent_SendClass;	/*Packets sent, send class*/
    long rx_packetsSent_SpecialClass;	/*Packets sent, special class*/
    long rx_ackPacketsSent;		/*Ack packets sent*/
    long rx_pingPacketsSent;		/*Ping packets sent*/
    long rx_abortPacketsSent;		/*Abort packets sent*/
    long rx_busyPacketsSent;		/*Busy packets sent*/
    long rx_dataPacketsSent;		/*Unique data packets sent*/
    long rx_dataPacketsReSent;		/*Retransmissions sent*/
    long rx_dataPacketsPushed;		/*Retransmissions pushed by NACK*/
    long rx_ignoreAckedPacket;		/*Packets w/acked flag on rxi_Start*/
    long rx_totalRtt_Sec;		/*Ttl round trip time, secs*/
    long rx_totalRtt_Usec;		/*Ttl round trip time, usecs*/
    long rx_minRtt_Sec;			/*Min round trip time, secs*/
    long rx_minRtt_Usec;		/*Min round trip time, usecs*/
    long rx_maxRtt_Sec;			/*Max round trip time, secs*/
    long rx_maxRtt_Usec;		/*Max round trip time, usecs*/
    long rx_nRttSamples;		/*Round trip samples*/
    long rx_nServerConns;		/*Ttl server connections*/
    long rx_nClientConns;		/*Ttl client connections*/
    long rx_nPeerStructs;		/*Ttl peer structures*/
    long rx_nCallStructs;		/*Ttl call structures*/
    long rx_nFreeCallStructs;		/*Ttl free call structures*/

    /*
     * Host module fields.
     */
    long host_NumHostEntries;		/*Number of host entries*/
    long host_HostBlocks;		/*Blocks in use for hosts*/
    long host_NonDeletedHosts;		/*Non-deleted hosts*/
    long host_HostsInSameNetOrSubnet;	/*" in same [sub]net as server*/
    long host_HostsInDiffSubnet;	/*" in different subnet as server*/
    long host_HostsInDiffNetwork;	/*" in different network as server*/
    long host_NumClients;		/*Number of client entries*/
    long host_ClientBlocks;		/*Blocks in use for clients*/

    /*
     * Spares
     */
    long spare[32];
};
\end{programexample}

%-----------------------------------------------------------------------
\section{{\it CacheManager} Collections}
\label{xstat-DC-CM}

%-----------------------------------------------------------------------
\subsection{{\tt struct afs_CMCallStats}}
\label{xstat-DC-CM-CMCallStats}

This is the data collection specified by the {\tt
AFSCB_XSTATSCOLL_CALL_INFO} identifier, whose value is 0.  It consists
of an array of longword fields, each one logging the number of calls to
the internal {\it CacheManager} routine implied by the name of the
field.  Thus, field {\tt C_afs_init} counts the number of
times the {\it afs_init()} function was called.

\begin{programexample}
struct afs_CMCallStats {
    long C_afs_init;			/* afs_aix_subr.c*/
    long C_gop_rdwr;			/* afs_aix_subr.c*/
    long C_aix_gnode_rele;		/* afs_aix_subr.c*/
    long C_gettimeofday;		/* afs_aix_subr.c*/
    long C_m_cpytoc;			/* afs_aix_subr.c*/
    long C_aix_vattr_null;		/* afs_aix_subr.c*/
    long C_afs_gn_ftrunc;		/* afs_aixops.c*/
    long C_afs_gn_rdwr;			/* afs_aixops.c*/
    long C_afs_gn_ioctl;		/* afs_aixops.c*/
    long C_afs_gn_lockctl;		/* afs_aixops.c*/
    long C_afs_gn_readlink;		/* afs_aixops.c*/
    long C_afs_gn_readdir;		/* afs_aixops.c*/
    long C_afs_gn_select;		/* afs_aixops.c*/
    long C_afs_gn_strategy;		/* afs_aixops.c*/
    long C_afs_gn_symlink;		/* afs_aixops.c*/
    long C_afs_gn_revoke;		/* afs_aixops.c*/
    long C_afs_gn_link;			/* afs_aixops.c*/
    long C_afs_gn_mkdir;		/* afs_aixops.c*/
    long C_afs_gn_mknod;		/* afs_aixops.c*/
    long C_afs_gn_remove;		/* afs_aixops.c*/
    long C_afs_gn_rename;		/* afs_aixops.c*/
    long C_afs_gn_rmdir;		/* afs_aixops.c*/
    long C_afs_gn_fid;			/* afs_aixops.c*/
    long C_afs_gn_lookup;		/* afs_aixops.c*/
    long C_afs_gn_open;			/* afs_aixops.c*/
    long C_afs_gn_create;		/* afs_aixops.c*/
    long C_afs_gn_hold;			/* afs_aixops.c*/
    long C_afs_gn_close;		/* afs_aixops.c*/
    long C_afs_gn_map;			/* afs_aixops.c*/
    long C_afs_gn_rele;			/* afs_aixops.c*/
    long C_afs_gn_unmap;		/* afs_aixops.c*/
    long C_afs_gn_access;		/* afs_aixops.c*/
    long C_afs_gn_getattr;		/* afs_aixops.c*/
    long C_afs_gn_setattr;		/* afs_aixops.c*/
    long C_afs_gn_fclear;		/* afs_aixops.c*/
    long C_afs_gn_fsync;		/* afs_aixops.c*/
    long C_pHash;			/* afs_buffer.c*/
    long C_DInit;			/* afs_buffer.c*/
    long C_DRead;			/* afs_buffer.c*/
    long C_FixupBucket;			/* afs_buffer.c*/
    long C_afs_newslot;			/* afs_buffer.c*/
    long C_DRelease;			/* afs_buffer.c*/
    long C_DFlush;			/* afs_buffer.c*/
    long C_DFlushEntry;			/* afs_buffer.c*/
    long C_DVOffset;			/* afs_buffer.c*/
    long C_DZap;			/* afs_buffer.c*/
    long C_DNew;			/* afs_buffer.c*/
    long C_shutdown_bufferpackage;	/* afs_buffer.c*/
    long C_afs_CheckKnownBad;		/* afs_cache.c*/
    long C_afs_RemoveVCB;		/* afs_cache.c*/
    long C_afs_NewVCache;		/* afs_cache.c*/
    long C_afs_FlushActiveVcaches;	/* afs_cache.c*/
    long C_afs_VerifyVCache;		/* afs_cache.c*/
    long C_afs_WriteVCache;		/* afs_cache.c*/
    long C_afs_GetVCache;		/* afs_cache.c*/
    long C_afs_StuffVcache;		/* afs_cache.c*/
    long C_afs_FindVCache;		/* afs_cache.c*/
    long C_afs_PutDCache;		/* afs_cache.c*/
    long C_afs_PutVCache;		/* afs_cache.c*/
    long C_CacheStoreProc;		/* afs_cache.c*/
    long C_afs_FindDCache;		/* afs_cache.c*/
    long C_afs_TryToSmush;		/* afs_cache.c*/
    long C_afs_AdjustSize;		/* afs_cache.c*/
    long C_afs_CheckSize;		/* afs_cache.c*/
    long C_afs_StoreWarn;		/* afs_cache.c*/
    long C_CacheFetchProc;		/* afs_cache.c*/
    long C_UFS_CacheStoreProc;		/* afs_cache.c*/
    long C_UFS_CacheFetchProc;		/* afs_cache.c*/
    long C_afs_GetDCache;		/* afs_cache.c*/
    long C_afs_SimpleVStat;		/* afs_cache.c*/
    long C_afs_ProcessFS;		/* afs_cache.c*/
    long C_afs_InitCacheInfo;		/* afs_cache.c*/
    long C_afs_InitVolumeInfo;		/* afs_cache.c*/
    long C_afs_InitCacheFile;		/* afs_cache.c*/
    long C_afs_CacheInit;		/* afs_cache.c*/
    long C_afs_GetDSlot;		/* afs_cache.c*/
    long C_afs_WriteThroughDSlots;	/* afs_cache.c*/
    long C_afs_MemGetDSlot;		/* afs_cache.c*/
    long C_afs_UFSGetDSlot;		/* afs_cache.c*/
    long C_afs_StoreDCache;		/* afs_cache.c*/
    long C_afs_StoreMini;		/* afs_cache.c*/
    long C_shutdown_cache;		/* afs_cache.c*/
    long C_afs_StoreAllSegments;	/* afs_cache.c*/
    long C_afs_InvalidateAllSegments;	/* afs_cache.c*/
    long C_afs_TruncateAllSegments;	/* afs_cache.c*/
    long C_afs_CheckVolSync;		/* afs_cache.c*/
    long C_afs_wakeup;			/* afs_cache.c*/
    long C_afs_CFileOpen;		/* afs_cache.c*/
    long C_afs_CFileTruncate;		/* afs_cache.c*/
    long C_afs_GetDownD;		/* afs_cache.c*/
    long C_afs_WriteDCache;		/* afs_cache.c*/
    long C_afs_FlushDCache;		/* afs_cache.c*/
    long C_afs_GetDownDSlot;		/* afs_cache.c*/
    long C_afs_FlushVCache;		/* afs_cache.c*/
    long C_afs_GetDownV;		/* afs_cache.c*/
    long C_afs_QueueVCB;		/* afs_cache.c*/
    long C_afs_call;      		/* afs_call.c */
    long C_afs_syscall_call;		/* afs_call.c*/
    long C_syscall;			/* afs_call.c*/
    long C_lpioctl;			/* afs_call.c*/
    long C_lsetpag;			/* afs_call.c*/
    long C_afs_syscall;			/* afs_call.c*/
    long C_afs_CheckInit;		/* afs_call.c*/
    long C_afs_shutdown;		/* afs_call.c*/
    long C_shutdown_BKG;		/* afs_call.c*/
    long C_shutdown_afstest;		/* afs_call.c*/
    long C_SRXAFSCB_GetCE;		/* afs_callback.c*/
    long C_ClearCallBack;		/* afs_callback.c*/
    long C_SRXAFSCB_GetLock;		/* afs_callback.c*/
    long C_SRXAFSCB_CallBack;		/* afs_callback.c*/
    long C_SRXAFSCB_InitCallBackState;	/* afs_callback.c*/
    long C_SRXAFSCB_Probe;		/* afs_callback.c*/
    long C_afs_RXCallBackServer;	/* afs_callback.c*/
    long C_shutdown_CB;			/* afs_callback.c*/
    long C_afs_Chunk;			/* afs_chunk.c*/
    long C_afs_ChunkBase;		/* afs_chunk.c*/
    long C_afs_ChunkOffset;		/* afs_chunk.c*/
    long C_afs_ChunkSize;		/* afs_chunk.c*/
    long C_afs_ChunkToBase;		/* afs_chunk.c*/
    long C_afs_ChunkToSize;		/* afs_chunk.c*/
    long C_afs_SetChunkSize;		/* afs_chunk.c*/
    long C_afs_config;			/* afs_config.c*/
    long C_mem_freebytes;		/* afs_config.c*/
    long C_mem_getbytes;		/* afs_config.c*/
    long C_fpalloc;			/* afs_config.c*/
    long C_kluge_init;			/* afs_config.c*/
    long C_ufdalloc;			/* afs_config.c*/
    long C_ufdfree;			/* afs_config.c*/
    long C_commit;			/* afs_config.c*/
    long C_dev_ialloc;			/* afs_config.c*/
    long C_ffree;			/* afs_config.c*/
    long C_iget;	       	 	/* afs_config.c*/
    long C_iptovp;			/* afs_config.c*/
    long C_ilock;			/* afs_config.c*/
    long C_irele;			/* afs_config.c*/
    long C_iput;			/* afs_config.c*/
    long C_afs_Daemon;			/* afs_daemons.c*/
    long C_afs_CheckRootVolume;		/* afs_daemons.c*/
    long C_BPath;			/* afs_daemons.c*/
    long C_BPrefetch;			/* afs_daemons.c*/
    long C_BStore;			/* afs_daemons.c*/
    long C_afs_BBusy;			/* afs_daemons.c*/
    long C_afs_BQueue;			/* afs_daemons.c*/
    long C_afs_BRelease;		/* afs_daemons.c*/
    long C_afs_BackgroundDaemon;	/* afs_daemons.c*/
    long C_shutdown_daemons;		/* afs_daemons.c*/
    long C_exporter_add;		/* afs_exporter.c*/
    long C_exporter_find;		/* afs_exporter.c*/
    long C_afs_gfs_kalloc;		/* afs_gfs_subr.c*/
    long C_IsAfsVnode;			/* afs_gfs_subr.c*/
    long C_SetAfsVnode;			/* afs_gfs_subr.c*/
    long C_afs_gfs_kfree;		/* afs_gfs_subr.c*/
    long C_gop_lookupname;		/* afs_gfs_subr.c*/
    long C_gfsvop_getattr;		/* afs_gfs_subr.c*/
    long C_gfsvop_rdwr;			/* afs_gfs_subr.c*/
    long C_afs_uniqtime;		/* afs_gfs_subr.c*/
    long C_gfs_vattr_null;		/* afs_gfs_subr.c*/
    long C_afs_lock;			/* afs_gfsops.c*/
    long C_afs_unlock;			/* afs_gfsops.c*/
    long C_afs_update;			/* afs_gfsops.c*/
    long C_afs_gclose;			/* afs_gfsops.c*/
    long C_afs_gopen;			/* afs_gfsops.c*/
    long C_afs_greadlink;		/* afs_gfsops.c*/
    long C_afs_select;			/* afs_gfsops.c*/
    long C_afs_gbmap;			/* afs_gfsops.c*/
    long C_afs_getfsdata;		/* afs_gfsops.c*/
    long C_afs_gsymlink;		/* afs_gfsops.c*/
    long C_afs_namei;			/* afs_gfsops.c*/
    long C_printgnode;			/* afs_gfsops.c*/
    long C_HaveGFSLock;			/* afs_gfsops.c*/
    long C_afs_gmount;			/* afs_gfsops.c*/
    long C_AddGFSLock;			/* afs_gfsops.c*/
    long C_RemoveGFSLock;		/* afs_gfsops.c*/
    long C_afs_grlock;			/* afs_gfsops.c*/
    long C_afs_gumount;			/* afs_gfsops.c*/
    long C_afs_gget;			/* afs_gfsops.c*/
    long C_afs_glink;			/* afs_gfsops.c*/
    long C_afs_gmkdir;			/* afs_gfsops.c*/
    long C_afs_sbupdate;		/* afs_gfsops.c*/
    long C_afs_unlink;			/* afs_gfsops.c*/
    long C_afs_grmdir;			/* afs_gfsops.c*/
    long C_afs_makenode;		/* afs_gfsops.c*/
    long C_afs_grename;			/* afs_gfsops.c*/
    long C_afs_rele;			/* afs_gfsops.c*/
    long C_afs_syncgp;			/* afs_gfsops.c*/
    long C_afs_getval;			/* afs_gfsops.c*/
    long C_afs_gfshack;			/* afs_gfsops.c*/
    long C_afs_trunc;			/* afs_gfsops.c*/
    long C_afs_rwgp;			/* afs_gfsops.c*/
    long C_afs_stat;			/* afs_gfsops.c*/
    long C_afsc_link;			/* afs_hp_subr.c*/
    long C_hpsobind;			/* afs_hp_subr.c*/
    long C_hpsoclose;			/* afs_hp_subr.c*/
    long C_hpsocreate;			/* afs_hp_subr.c*/
    long C_hpsoreserve;			/* afs_hp_subr.c*/
    long C_afs_vfs_mount;		/* afs_hp_subr.c*/
    long C_devtovfs;			/* afs_istuff.c*/
    long C_igetinode;			/* afs_istuff.c*/
    long C_afs_syscall_iopen;		/* afs_istuff.c*/
    long C_iopen;			/* afs_istuff.c*/
    long C_afs_syscall_iincdec;		/* afs_istuff.c*/
    long C_afs_syscall_ireadwrite;	/* afs_istuff.c*/
    long C_iincdec;			/* afs_istuff.c*/
    long C_ireadwrite;			/* afs_istuff.c*/
    long C_oiread;			/* afs_istuff.c*/
    long C_AHash;			/* afs_istuff.c*/
    long C_QTOA;			/* afs_istuff.c*/
    long C_afs_FindPartByDev;		/* afs_istuff.c*/
    long C_aux_init;			/* afs_istuff.c*/
    long C_afs_GetNewPart;		/* afs_istuff.c*/
    long C_afs_InitAuxVolFile;		/* afs_istuff.c*/
    long C_afs_CreateAuxEntry;		/* afs_istuff.c*/
    long C_afs_GetAuxSlot;		/* afs_istuff.c*/
    long C_afs_GetDownAux;		/* afs_istuff.c*/
    long C_afs_FlushAuxCache;		/* afs_istuff.c*/
    long C_afs_GetAuxInode;		/* afs_istuff.c*/
    long C_afs_PutAuxInode;		/* afs_istuff.c*/
    long C_afs_ReadAuxInode;		/* afs_istuff.c*/
    long C_afs_WriteAuxInode;		/* afs_istuff.c*/
    long C_afs_auxcall;			/* afs_istuff.c*/
    long C_tmpdbg_auxtbl;		/* afs_istuff.c*/
    long C_tmpdbg_parttbl;		/* afs_istuff.c*/
    long C_idec;			/* afs_istuff.c*/
    long C_iinc;			/* afs_istuff.c*/
    long C_iread;			/* afs_istuff.c*/
    long C_iwrite;			/* afs_istuff.c*/
    long C_getinode;			/* afs_istuff.c*/
    long C_trygetfs;			/* afs_istuff.c*/
    long C_iforget;			/* afs_istuff.c*/
    long C_afs_syscall_icreate;		/* afs_istuff.c*/
    long C_icreate;			/* afs_istuff.c*/
    long C_Lock_Init;			/* afs_lock.c*/
    long C_Lock_Obtain;			/* afs_lock.c*/
    long C_Lock_ReleaseR;		/* afs_lock.c*/
    long C_Lock_ReleaseW;		/* afs_lock.c*/
    long C_afs_BozonLock;		/* afs_lock.c*/
    long C_afs_BozonUnlock;		/* afs_lock.c*/
    long C_osi_SleepR;			/* afs_lock.c*/
    long C_osi_SleepS;			/* afs_lock.c*/
    long C_osi_SleepW;			/* afs_lock.c*/
    long C_osi_Sleep;			/* afs_lock */
    long C_afs_BozonInit;		/* afs_lock.c*/
    long C_afs_CheckBozonLock;		/* afs_lock.c*/
    long C_xxxinit;			/* afs_main.c*/
    long C_KernelEntry;			/* afs_main.c*/
    long C_afs_InitMemCache;		/* afs_memcache.c*/
    long C_afs_LookupMCE;		/* afs_memcache.c*/
    long C_afs_MemReadBlk;		/* afs_memcache.c*/
    long C_afs_MemReadUIO;		/* afs_memcache.c*/
    long C_afs_MemWriteBlk;		/* afs_memcache.c*/
    long C_afs_MemCacheStoreProc;	/* afs_memcache.c*/
    long C_afs_MemCacheTruncate;	/* afs_memcache.c*/
    long C_afs_MemWriteUIO;		/* afs_memcache.c*/
    long C_afs_MemCacheFetchProc;	/* afs_memcache.c*/
    long C_afs_vnode_pager_create;	/* afs_next_aux.c*/
    long C_next_KernelEntry;		/* afs_next_subr.c*/
    long C_afs_GetNfsClientPag;		/* afs_nfsclnt.c*/
    long C_afs_FindNfsClientPag;	/* afs_nfsclnt.c*/
    long C_afs_PutNfsClientPag;		/* afs_nfsclnt.c*/
    long C_afs_nfsclient_reqhandler;	/* afs_nfsclnt.c*/
    long C_afs_nfsclient_GC;		/* afs_nfsclnt.c*/
    long C_afs_nfsclient_hold;		/* afs_nfsclnt.c*/
    long C_afs_nfsclient_stats;		/* afs_nfsclnt.c*/
    long C_afs_nfsclient_sysname;	/* afs_nfsclnt.c*/
    long C_afs_nfsclient_shutdown;	/* afs_nfsclnt.c*/
    long C_afs_rfs_readdir_fixup;	/* afs_nfssrv.c */
    long C_afs_rfs_dispatch;		/* afs_nfssrv.c*/
    long C_afs_xnfs_svc;		/* afs_nfssrv.c*/
    long C_afs_xdr_putrddirres;		/* afs_nfssrv.c*/
    long C_afs_rfs_readdir;		/* afs_nfssrv.c*/
    long C_afs_rfs_rddirfree;		/* afs_nfssrv.c*/
    long C_rfs_dupcreate;		/* afs_nfssrv.c*/
    long C_rfs_dupsetattr;		/* afs_nfssrv.c*/
    long C_Nfs2AfsCall;			/* afs_nfssrv.c*/
    long C_afs_sun_xuntext;		/* afs_osi.c*/
    long C_osi_Active;			/* afs_osi.c*/
    long C_osi_FlushPages;		/* afs_osi.c*/
    long C_osi_FlushText;		/* afs_osi.c*/
    long C_osi_CallProc;		/* afs_osi.c*/
    long C_osi_CancelProc;		/* afs_osi.c*/
    long C_osi_Invisible;		/* afs_osi.c*/
    long C_osi_Time;			/* afs_osi.c*/
    long C_osi_Alloc;			/* afs_osi.c*/
    long C_osi_SetTime;			/* afs_osi.c*/
    long C_osi_Dump;			/* afs_osi.c*/
    long C_osi_Free;			/* afs_osi.c*/
    long C_shutdown_osi;		/* afs_osi.c*/
    long C_osi_UFSOpen;			/* afs_osifile.c*/
    long C_osi_Close;			/* afs_osifile.c*/
    long C_osi_Stat;			/* afs_osifile.c*/
    long C_osi_Truncate;		/* afs_osifile.c*/
    long C_osi_Read;			/* afs_osifile.c*/
    long C_osi_Write;			/* afs_osifile.c*/
    long C_osi_MapStrategy;		/* afs_osifile.c*/
    long C_shutdown_osifile;		/* afs_osifile.c*/
    long C_osi_FreeSendSpace;		/* afs_osinet.c*/
    long C_osi_FreeSmallSpace;		/* afs_osinet.c*/
    long C_pkt_iodone;			/* afs_osinet.c*/
    long C_shutdown_osinet;		/* afs_osinet.c*/
    long C_afs_cs;			/* afs_osinet.c*/
    long C_osi_AllocSendSpace;		/* afs_osinet.c*/
    long C_osi_AllocSmallSpace;		/* afs_osinet.c*/
    long C_osi_CloseToTheEdge;		/* afs_osinet.c*/
    long C_osi_xgreedy;			/* afs_osinet.c*/
    long C_osi_FreeSocket;		/* afs_osinet.c*/
    long C_osi_NewSocket;		/* afs_osinet.c*/
    long C_trysblock;			/* afs_osinet.c*/
    long C_osi_NetSend;			/* afs_osinet.c*/
    long C_WaitHack;			/* afs_osinet.c*/
    long C_osi_CancelWait;		/* afs_osinet.c*/
    long C_osi_InitWaitHandle;		/* afs_osinet.c*/
    long C_osi_Wakeup;			/* afs_osinet.c*/
    long C_osi_Wait;			/* afs_osinet.c*/
    long C_dirp_Read;			/* afs_physio.c*/
    long C_dirp_SetCacheDev;		/* afs_physio.c*/
    long C_Die;				/* afs_physio.c*/
    long C_dirp_Cpy;			/* afs_physio.c*/
    long C_dirp_Eq;			/* afs_physio.c*/
    long C_dirp_Write;			/* afs_physio.c*/
    long C_dirp_Zap;			/* afs_physio.c*/
    long C_PSetVolumeStatus;		/* afs_pioctl.c*/
    long C_PFlush;			/* afs_pioctl.c*/
    long C_PNewStatMount;		/* afs_pioctl.c*/
    long C_PGetTokens;			/* afs_pioctl.c*/
    long C_PUnlog;			/* afs_pioctl.c*/
    long C_PCheckServers;		/* afs_pioctl.c*/
    long C_PMariner;			/* afs_pioctl.c*/
    long C_PCheckAuth;			/* afs_pioctl.c*/
    long C_PCheckVolNames;		/* afs_pioctl.c*/
    long C_PFindVolume;			/* afs_pioctl.c*/
    long C_Prefetch;			/* afs_pioctl.c*/
    long C_PGetCacheSize;		/* afs_pioctl.c*/
    long C_PRemoveCallBack;		/* afs_pioctl.c*/
    long C_PSetCacheSize;		/* afs_pioctl.c*/
    long C_PViceAccess;			/* afs_pioctl.c*/
    long C_PListCells;			/* afs_pioctl.c*/
    long C_PNewCell;			/* afs_pioctl.c*/
    long C_PRemoveMount;		/* afs_pioctl.c*/
    long C_HandleIoctl;			/* afs_pioctl.c*/
    long C__AFSIOCTL;			/* afs_pioctl.c*/
    long C__VALIDAFSIOCTL;		/* afs_pioctl.c*/
    long C_PGetCellStatus;		/* afs_pioctl.c*/
    long C_PSetCellStatus;		/* afs_pioctl.c*/
    long C_PVenusLogging;		/* afs_pioctl.c*/
    long C_PFlushVolumeData;		/* afs_pioctl.c*/
    long C_PSetSysName;			/* afs_pioctl.c*/
    long C_PExportAfs;			/* afs_pioctl.c*/
    long C_HandleClientContext;		/* afs_pioctl.c*/
    long C_afs_ioctl;			/* afs_pioctl.c*/
    long C_afs_xioctl;			/* afs_pioctl.c*/
    long C_afs_pioctl;			/* afs_pioctl.c*/
    long C_afs_syscall_pioctl;		/* afs_pioctl.c*/
    long C_HandlePioctl;		/* afs_pioctl.c*/
    long C_PGetAcl;			/* afs_pioctl.c*/
    long C_PGetFID;			/* afs_pioctl.c*/
    long C_PSetAcl;			/* afs_pioctl.c*/
    long C_PBogus;			/* afs_pioctl.c*/
    long C_PGetFileCell;		/* afs_pioctl.c*/
    long C_PGetWSCell;			/* afs_pioctl.c*/
    long C_PNoop;			/* afs_pioctl.c*/
    long C_PGetUserCell;		/* afs_pioctl.c*/
    long C_PSetTokens;			/* afs_pioctl.c*/
    long C_PGetVolumeStatus;		/* afs_pioctl.c*/
    long C_afs_ResetAccessCache;	/* afs_resource.c*/
    long C_afs_FindUser;		/* afs_resource.c*/
    long C_afs_ResetUserConns;		/* afs_resource.c*/
    long C_afs_ResourceInit;		/* afs_resource.c*/
    long C_afs_GetCell;			/* afs_resource.c*/
    long C_afs_GetCellByIndex;		/* afs_resource.c*/
    long C_afs_GetCellByName;		/* afs_resource.c*/
    long C_afs_NewCell;			/* afs_resource.c*/
    long C_afs_GetUser;			/* afs_resource.c*/
    long C_afs_PutUser;			/* afs_resource.c*/
    long C_afs_SetPrimary;		/* afs_resource.c*/
    long C_CheckVLDB;			/* afs_resource.c*/
    long C_afs_GetVolume;		/* afs_resource.c*/
    long C_afs_GetVolumeByName;		/* afs_resource.c*/
    long C_InstallVolumeEntry;		/* afs_resource.c*/
    long C_InstallVolumeInfo;		/* afs_resource.c*/
    long C_afs_FindServer;		/* afs_resource.c*/
    long C_afs_PutVolume;		/* afs_resource.c*/
    long C_afs_random;			/* afs_resource.c*/
    long C_ranstage;			/* afs_resource.c*/
    long C_RemoveUserConns;		/* afs_resource.c*/
    long C_afs_MarinerLog;		/* afs_resource.c*/
    long C_afs_vtoi;			/* afs_resource.c*/
    long C_afs_GetServer;		/* afs_resource.c*/
    long C_afs_SortServers;		/* afs_resource.c*/
    long C_afs_Conn;			/* afs_resource.c*/
    long C_afs_ConnByHost;		/* afs_resource.c*/
    long C_afs_ConnByMHosts;		/* afs_resource.c*/
    long C_afs_Analyze;			/* afs_resource.c*/
    long C_afs_PutConn;			/* afs_resource.c*/
    long C_afs_ResetVolumeInfo;		/* afs_resource.c*/
    long C_StartLogFile;		/* afs_resource.c*/
    long C_afs_SetLogFile;		/* afs_resource.c*/
    long C_EndLogFile;			/* afs_resource.c*/
    long C_afs_dp;			/* afs_resource.c*/
    long C_fprf;			/* afs_resource.c*/
    long C_fprint;			/* afs_resource.c*/
    long C_fprintn;			/* afs_resource.c*/
    long C_afs_CheckLocks;		/* afs_resource.c*/
    long C_puttofile;			/* afs_resource.c*/
    long C_shutdown_AFS;		/* afs_resource.c*/
    long C_afs_CheckCacheResets;	/* afs_resource.c*/
    long C_afs_GCUserData;		/* afs_resource.c*/
    long C_VSleep;			/* afs_resource.c*/
    long C_afs_CheckCode;		/* afs_resource.c*/
    long C_afs_CopyError;		/* afs_resource.c*/
    long C_afs_FinalizeReq;		/* afs_resource.c*/
    long C_afs_cv2string;		/* afs_resource.c*/
    long C_afs_FindVolCache;		/* afs_resource.c*/
    long C_afs_GetVolCache;		/* afs_resource.c*/
    long C_afs_GetVolSlot;		/* afs_resource.c*/
    long C_afs_WriteVolCache;		/* afs_resource.c*/
    long C_afs_UFSGetVolSlot;		/* afs_resource.c*/
    long C_afs_CheckVolumeNames;	/* afs_resource.c*/
    long C_afs_MemGetVolSlot;		/* afs_resource.c*/
    long C_print_internet_address;	/* afs_resource.c*/
    long C_CheckVLServer;		/* afs_resource.c*/
    long C_HaveCallBacksFrom;		/* afs_resource.c*/
    long C_ServerDown;			/* afs_resource.c*/
    long C_afs_CheckServers;		/* afs_resource.c*/
    long C_afs_AddToMean;		/* afs_stat.c*/
    long C_afs_GetCMStat;		/* afs_stat.c*/
    long C_afs_getpage;			/* afs_sun_subr.c*/
    long C_afs_putpage;			/* afs_sun_subr.c*/
    long C_afs_nfsrdwr;			/* afs_sun_subr.c*/
    long C_afs_map;			/* afs_sun_subr.c*/
    long C_afs_cmp;			/* afs_sun_subr.c*/
    long C_afs_cntl;			/* afs_sun_subr.c*/
    long C_afs_dump;			/* afs_sun_subr.c*/
    long C_afs_realvp;			/* afs_sun_subr.c*/
    long C_afs_PageLeft;		/* afs_sun_subr.c*/
    long C_afsinit;			/* afs_vfsops.c*/
    long C_afs_mount;			/* afs_vfsops.c*/
    long C_afs_unmount;			/* afs_vfsops.c*/
    long C_afs_root;			/* afs_vfsops.c*/
    long C_afs_statfs;			/* afs_vfsops.c*/
    long C_afs_sync;			/* afs_vfsops.c*/
    long C_afs_vget;			/* afs_vfsops.c*/
    long C_afs_mountroot;		/* afs_vfsops.c*/
    long C_afs_swapvp;			/* afs_vfsops.c*/
    long C_afs_AddMarinerName;		/* afs_vnodeops.c*/
    long C_afs_setpag;			/* afs_vnodeops.c*/
    long C_genpag;			/* afs_vnodeops.c*/
    long C_getpag;			/* afs_vnodeops.c*/
    long C_afs_GetMariner;		/* afs_vnodeops.c*/
    long C_afs_badop;			/* afs_vnodeops.c*/
    long C_afs_index;			/* afs_vnodeops.c*/
    long C_afs_noop;			/* afs_vnodeops.c*/
    long C_afs_open;			/* afs_vnodeops.c*/
    long C_afs_closex;			/* afs_vnodeops.c*/
    long C_afs_close;			/* afs_vnodeops.c*/
    long C_afs_MemWrite;		/* afs_vnodeops.c*/
    long C_afs_write;			/* afs_vnodeops.c*/
    long C_afs_UFSWrite;		/* afs_vnodeops.c*/
    long C_afs_rdwr;			/* afs_vnodeops.c*/
    long C_afs_MemRead;			/* afs_vnodeops.c*/
    long C_afs_read;			/* afs_vnodeops.c*/
    long C_FIXUPSTUPIDINODE;		/* afs_vnodeops.c*/
    long C_afs_UFSRead;			/* afs_vnodeops.c*/
    long C_afs_CopyOutAttrs;		/* afs_vnodeops.c*/
    long C_afs_getattr;			/* afs_vnodeops.c*/
    long C_afs_VAttrToAS;		/* afs_vnodeops.c*/
    long C_afs_setattr;			/* afs_vnodeops.c*/
    long C_EvalMountPoint;		/* afs_vnodeops.c*/
    long C_afs_access;			/* afs_vnodeops.c*/
    long C_ENameOK;			/* afs_vnodeops.c*/
    long C_HandleAtName;		/* afs_vnodeops.c*/
    long C_getsysname;			/* afs_vnodeops.c*/
    long C_strcat;			/* afs_vnodeops.c*/
    long C_afs_lookup;			/* afs_vnodeops.c*/
    long C_afs_create;			/* afs_vnodeops.c*/
    long C_afs_LocalHero;		/* afs_vnodeops.c*/
    long C_FetchWholeEnchilada;		/* afs_vnodeops.c*/
    long C_afs_remove;			/* afs_vnodeops.c*/
    long C_afs_link;			/* afs_vnodeops.c*/
    long C_afs_rename;			/* afs_vnodeops.c*/
    long C_afs_InitReq;			/* afs_vnodeops.c*/
    long C_afs_mkdir;			/* afs_vnodeops.c*/
    long C_BlobScan;			/* afs_vnodeops.c*/
    long C_afs_rmdir;			/* afs_vnodeops.c*/
    long C_RecLen;			/* afs_vnodeops.c*/
    long C_RoundToInt;			/* afs_vnodeops.c*/
    long C_afs_readdir_with_offlist;	/* afs_vnodeops.c*/
    long C_DIRSIZ_LEN;			/* afs_vnodeops.c*/
    long C_afs_readdir_move;		/* afs_vnodeops.c*/
    long C_afs_readdir_iter;		/* afs_vnodeops.c*/
    long C_HandleFlock;			/* afs_vnodeops.c*/
    long C_afs_readdir;			/* afs_vnodeops.c*/
    long C_afs_symlink;			/* afs_vnodeops.c*/
    long C_afs_HandleLink;		/* afs_vnodeops.c*/
    long C_afs_MemHandleLink;		/* afs_vnodeops.c*/
    long C_afs_UFSHandleLink;		/* afs_vnodeops.c*/
    long C_afs_readlink;		/* afs_vnodeops.c*/
    long C_afs_fsync;			/* afs_vnodeops.c*/
    long C_afs_inactive;		/* afs_vnodeops.c*/
    long C_afs_ustrategy;		/* afs_vnodeops.c*/
    long C_afs_bread;			/* afs_vnodeops.c*/
    long C_afs_brelse;			/* afs_vnodeops.c*/
    long C_afs_bmap;			/* afs_vnodeops.c*/
    long C_afs_fid;			/* afs_vnodeops.c*/
    long C_afs_strategy;		/* afs_vnodeops.c*/
    long C_afs_FakeClose;		/* afs_vnodeops.c*/
    long C_afs_FakeOpen;		/* afs_vnodeops.c*/
    long C_afs_StoreOnLastReference;	/* afs_vnodeops.c*/
    long C_afs_GetAccessBits;		/* afs_vnodeops.c*/
    long C_afs_AccessOK;		/* afs_vnodeops.c*/
    long C_shutdown_vnodeops;		/* afs_vnodeops.c*/
    long C_afsio_copy;			/* afs_vnodeops.c*/
    long C_afsio_trim;			/* afs_vnodeops.c*/
    long C_afs_page_read;		/* afs_vnodeops.c*/
    long C_afs_page_write;		/* afs_vnodeops.c*/
    long C_afsio_skip;			/* afs_vnodeops.c*/
    long C_afs_read1dir;		/* afs_vnodeops.c*/
    long C_afs_get_groups_from_pag;	/* afs_vnodeops.c*/
    long C_afs_get_pag_from_groups;	/* afs_vnodeops.c*/
    long C_PagInCred;			/* afs_vnodeops.c*/
    long C_afs_getgroups;		/* afs_vnodeops.c*/
    long C_setpag;			/* afs_vnodeops.c*/
    long C_afs_setgroups;		/* afs_vnodeops.c*/
    long C_afs_page_in;			/* afs_vnodeops.c*/
    long C_afs_page_out;		/* afs_vnodeops.c*/
    long C_AddPag;			/* afs_vnodeops.c*/
    long C_afs_AdvanceFD;		/* afs_vnodeops.c*/
    long C_afs_lockf;			/* afs_vnodeops.c*/
    long C_afs_xsetgroups;		/* afs_vnodeops.c*/
    long C_afs_nlinks;			/* afs_vnodeops.c*/
    long C_DoLockWarning;		/* afs_vnodeops.c*/
    long C_afs_lockctl;			/* afs_vnodeops.c*/
    long C_afs_xflock;			/* afs_vnodeops.c*/
};
\end{programexample}

%-----------------------------------------------------------------------
\subsection{{\tt struct afs_CMPerfStats}}
\label{xstat-DC-CM-CMPerfStats}

This is the data collection specified by the {\tt
AFSCB_XSTATSCOLL_PERF_INFO} identifier, whose value is 1.  It reports
on several internal performance statistics relating to cache usage,
the number of different cells contacted, and local disk utilization.

\begin{programexample}
struct afs_CMPerfStats {
    long numPerfCalls;		/*# of performance calls rcvd*/
    long epoch;			/*Cache Manager epoch time*/
    long numCellsContacted;	/*# cells corresponded with*/
    long dlocalAccesses;	/*# data accesses to files within cell*/
    long vlocalAccesses;	/*# stat accesses to files within cell*/
    long dremoteAccesses;	/*# data accesses to files outside of cell*/
    long vremoteAccesses;	/*# stat accesses to files outside of cell*/
    long cacheNumEntries;	/*# cache entries*/
    long cacheBlocksTotal;	/*# (1K) blocks configured for cache*/
    long cacheBlocksInUse;	/*# cache blocks actively in use*/
    long cacheBlocksOrig;	/*# cache blocks at bootup*/
    long cacheMaxDirtyChunks;	/*Max # dirty cache chunks tolerated*/
    long cacheCurrDirtyChunks;	/*Current # dirty cache chunks*/
    long dcacheHits;		/*# data files found in local cache*/
    long vcacheHits;		/*# stat entries found in local cache*/
    long dcacheMisses;		/*# data files NOT found in local cache*/
    long vcacheMisses;		/*# stat entries NOT found in local cache*/
    long cacheFlushes;		/*# files flushed from cache*/
    long cacheFilesReused;	/*# cache files reused*/
    long numServerRecords;	/*# of servers currently on record*/
    long ProtServerAddr;	/*Addr of Protection Server used*/
    long spare[32];		/*Spares*/
};
\end{programexample}

%========================================================================
\chapter{Programming Interface}
\label{xstat-PI}

%-----------------------------------------------------------------------
\section{{\it FileServer} Calls}
\label{xstat-PI-FS}

%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

\functionsubsection{xstat_fs_Init}
	{Init the {\it xstat_fs} module}
\index{xstat_fs_Init}
\label{xstat-PI-FS-Init}

\begin{functionexample}
int {\fn xstat_fs_Init}(\=\+IN int a_numServers,
IN struct sockaddr_in *a_socketArray,
IN a_ProbeFreqInSecs,
IN (*a_ProbeHandler),
IN int a_debug)
\end{functionexample}

\noparam

Fully initialize the {\it xstat_fs} module.  First, the set of {\it
Rx} connections to the {\it a_numServers} {\it FileServer}s whose
socket addresses are specified in {\it a_socketArray} is created.  One
LWP is started up to handle incoming callback interface calls,
generated by the specified {\it FileServer}.  This satisfies the
requirement that the caller emulate a fully-operational {\it
CacheManager}.  In addition, a probe LWP is started up which will get
the two defined data collections every {\it a_ProbeFreqInSecs}
seconds.  Upon arrival of each data collection, the probe LWP will call
the {\it a_ProbeHandler} routine, which is expected to store and/or
process the body of the collection as the user sees fit.  If the {\it
a_debug} parameter is set to a non-zero value, then debugging output
will be generated and directed to {\tt stderr}.

\begin{returncodes}
\returncode{---} Error codes from underlying systems percolate
through; no error codes specific to the function are generated by {\it
xstat_fs_Init()}.
\end{returncodes}

%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

\functionsubsubsection{xstat_fs_ForceProbeNow}
	{Force an immediate probe to the connected {\it FileServer}s.}
\index{xstat_fs_ForceProbeNow}
\label{xstat-PI-FS-ForceProbeNow}

\begin{functionexample}
int {\fn xstat_fs_ForceProbeNow}()
\end{functionexample}

\noparam

Wake up the probe LWP, thus prompting it to immediately begin a new
round of probes.  Prodding the probe LWP in this fashion does not
affect its data collection interval; after this ``command
performance'', it will resume its normal polling schedule.

\begin{returncodes}
\returncode{-1} The module was never initialized.
\end{returncodes}

%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

\functionsubsection{xstat_fs_Cleanup}
	{Clean up memory and {\it Rx} connection state}
\index{xstat_fs_Cleanup}
\label{xstat-PI-FS-Cleanup}

\begin{functionexample}
int {\fn xstat_fs_Cleanup}(\=\+IN int a_releaseMem)
\end{functionexample}

\noparam

Explicitly destroy all {\it Rx} connections generated to the set of
probed {\it FileServers}.  If {\it a_releaseMem} has been given a
non-zero value, free the connection array created by the associated
{\it xstat_fs_Init()} call.

\begin{returncodes}
\returncode{-1} The module was never initialized, or there was a
problem with the underlying connection array.
\end{returncodes}




%-----------------------------------------------------------------------
\section{{\it CacheManager} Calls}
\label{xstat-PI-CM}

%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
\functionsubsection{xstat_cm_Init}
	{Init the {\it xstat_cm} module}
\index{xstat_cm_Init}
\label{xstat-PI-CM-Init}

\begin{functionexample}
int {\fn xstat_cm_Init}(\=\+IN int a_numServers,
IN struct sockaddr_in *a_socketArray,
IN a_ProbeFreqInSecs,
IN (*a_ProbeHandler),
IN int a_debug)
\end{functionexample}

\noparam

Fully initialize the {\it xstat_cm} module.  First, the set of {\it
Rx} connections to the {\it a_numServers} {\it CacheManagers}s whose
socket addresses are specified in {\it a_socketArray} is created.  A
probe LWP is started up which will get the two defined data
collections every {\it a_ProbeFreqInSecs} seconds.  Upon arrival of
each data collection, the probe LWP will call the {\it a_ProbeHandler}
routine, which is expected to store and/or process the body of the
collection as the user sees fit.  If the {\it a_debug} parameter is
set to a non-zero value, then debugging output will be generated and
directed to {\tt stderr}.

\begin{returncodes}
\returncode{---} Error codes from underlying systems percolate
through; no error codes specific to the function are generated by {\it
xstat_cm_Init()}.
\end{returncodes}

%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

\functionsubsubsection{xstat_cm_ForceProbeNow}
	{Force an immediate probe to the connected {\it CacheManagers}s.}
\index{xstat_cm_ForceProbeNow}
\label{xstat-PI-CM-ForceProbeNow}

\begin{functionexample}
int {\fn xstat_cm_ForceProbeNow}()
\end{functionexample}

\noparam

Wake up the probe LWP, thus prompting it to immediately begin a new
round of probes.  Prodding the probe LWP in this fashion does not
affect its data collection interval; after this ``command
performance'', it will resume its normal polling schedule.

\begin{returncodes}
\returncode{-1} The module was never initialized.
\end{returncodes}

%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

\functionsubsection{xstat_cm_Cleanup}
	{Clean up memory and {\it Rx} connection state}
\index{xstat_cm_Cleanup}
\label{xstat-PI-CM-Cleanup}

\begin{functionexample}
int {\fn xstat_cm_Cleanup}(\=\+IN int a_releaseMem)
\end{functionexample}

\noparam

Explicitly destroy all {\it Rx} connections generated to the set of
probed {\it FileServers}.  If {\it a_releaseMem} has been given a
non-zero value, free the connection array created by the associated
{\it xstat_cm_Init()} call.

\begin{returncodes}
\returncode{-1} The module was never initialized, or there was a
problem with the underlying connection array.
\end{returncodes}

%========================================================================
\chapter{Example Handler Routine}
\label{xstat-Handler}

This chapter contains the body of the {\it CM_Handler()} routine,
whose job it is to process the arrival of a {\it CacheManager} {\tt
AFSCB_XSTATSCOLL_PERF_INFO} data collection, as described in Section
\ref{xstat-DC-CM-CMPerfStats} and \ref{xstat-PI-CM-Init}.  Also
contained is the text of the {\it PrintPerfInfo()} function which it
in turn calls to echo the contents of the {\it CacheManager}
performance numbers just collected.

This code will demonstrate the use and interrelation of the
definitions and variables described in Chapter
\ref{xstat-Bookkeeping}.

%-----------------------------------------------------------------------
\section{{\tt CM_Handler} Function}
\label{xstat-Handler-CM}

\begin{programexample}
/*------------------------------------------------------------------------
 * CM_Handler
 *
 * Description:
 *	Handler routine passed to the xstat_cm module.  This handler is
 *	called immediately after a poll of one of the Cache Managers has
 *	taken place.  All it needs to know is exported by the xstat_cm
 *	module, namely the data structure where the probe results are
 *	stored.
 *
 * Arguments:
 *	None.
 *
 * Returns:
 *	0 on success,
 *	-1 otherwise.
 *
 * Environment:
 *	See above.  All we do now is print out what we got.
 *
 * Side Effects:
 *	As advertised.
 *------------------------------------------------------------------------*/

int CM_Handler()

{ /*CM_Handler*/

    static char rn[] = "CM_Handler";	/*Routine name*/

    printf("\n--------------------------------------------------\n");

    /*
     * If the probe failed, there isn't much we can do except gripe.
     */
    if (xstat_cm_Results.probeOK) {
	printf("%s: Probe %d, collection %d to CM on '%s' failed, code=%d\n",
	       rn, xstat_cm_Results.probeNum,
	       xstat_cm_Results.collectionNumber,
	       xstat_cm_Results.connP->hostName,
	       xstat_cm_Results.probeOK);
	return(0);
    }

    switch(xstat_cm_Results.collectionNumber) {
      case AFSCB_XSTATSCOLL_CALL_INFO:
	PrintCallInfo();
	break;

      case AFSCB_XSTATSCOLL_PERF_INFO:
	PrintPerfInfo();
	break;

      default:
	printf("** Unknown collection: %d\n",
	       xstat_cm_Results.collectionNumber);
    }

    /*
     * Return the happy news.
     */
    return(0);

} /*CM_Handler*/
\end{programexample}

%-----------------------------------------------------------------------
\section{{\tt PrintPerfInfo} Function}
\label{xstat-PrintPerfInfo}

\begin{programexample}
/*------------------------------------------------------------------------
 * PrintPerfInfo
 *
 * Description:
 *	Print out the AFSCB_XSTATSCOLL_CALL_INFO collection we just
 *	received.
 *
 * Arguments:
 *	None.
 *
 * Returns:
 *	Nothing.
 *
 * Environment:
 *	All the info we need is nestled into xstat_cm_Results.
 *
 * Side Effects:
 *	As advertised.
 *------------------------------------------------------------------------*/

void PrintPerfInfo()

{ /*PrintPerfInfo*/

    static char rn[] = "PrintPerfInfo";	/*Routine name*/
    static long perfLongs =
	(sizeof(struct afs_CMPerfStats) >> 2); /*Correct # longs to rcv*/
    long numLongs;			/*# longwords received*/
    struct afs_CMPerfStats *perfP;	/*Ptr to performance stats*/
    char *printableTime;		/*Ptr to printable time string*/

    numLongs = xstat_cm_Results.data.AFSCB_CollData_len;
    if (numLongs != perfLongs) {
	printf("** Data size mismatch in performance collection!");
	printf("** Expecting %d, got %d\n",
	       perfLongs, numLongs);
    }

    printableTime = ctime(&(xstat_cm_Results.probeTime));
    perfP = (struct afs_CMPerfStats *)
	(xstat_cm_Results.data.AFSCB_CollData_val);
    printf("[%s] Results of poll %d, AFSCB_XSTATSCOLL_PERF_INFO (collection %d, %d longs), CM on '%s', %s:\n",
	   rn, xstat_cm_Results.probeNum,
	   xstat_cm_Results.collectionNumber,
	   numLongs,
	   xstat_cm_Results.connP->hostName,
	   printableTime);

    printf("numPerfCalls         : %d\n", perfP->numPerfCalls);
    printf("numCellsContacted    : %d\n", perfP->numCellsContacted);
    printf("dlocalAccesses       : %d\n", perfP->dlocalAccesses);
    printf("vlocalAccesses       : %d\n", perfP->vlocalAccesses);
    printf("dremoteAccesses      : %d\n", perfP->dremoteAccesses);
    printf("vremoteAccesses      : %d\n", perfP->vremoteAccesses);
    printf("cacheNumEntries      : %d\n", perfP->cacheNumEntries);
    printf("cacheBlocksTotal     : %d\n", perfP->cacheBlocksTotal);
    printf("cacheBlocksInUse     : %d\n", perfP->cacheBlocksInUse);
    printf("cacheBlocksOrig      : %d\n", perfP->cacheBlocksOrig);
    printf("cacheMaxDirtyChunks  : %d\n", perfP->cacheMaxDirtyChunks);
    printf("cacheCurrDirtyChunks : %d\n", perfP->cacheCurrDirtyChunks);
    printf("dcacheHits           : %d\n", perfP->dcacheHits);
    printf("vcacheHits           : %d\n", perfP->vcacheHits);
    printf("dcacheMisses         : %d\n", perfP->dcacheMisses);
    printf("vcacheMisses         : %d\n", perfP->vcacheMisses);
    printf("cacheFilesReused     : %d\n", perfP->cacheFilesReused);
    printf("numServerRecords     : %d\n", perfP->numServerRecords);

} /*PrintPerfInfo*/
\end{programexample}

\printindex
\end{document}

%
% Subdivisions of this kind of document:
%
%	\section, \subsection, \subsubsection, \paragraph, \subparagraph.
%
