Remove one more AFS_UCRED struct
[openafs.git] / src / afs / afs_pioctl.c
index d5a5df1..bd4a5f2 100644 (file)
@@ -10,8 +10,6 @@
 #include <afsconfig.h>
 #include "afs/param.h"
 
-RCSID
-    ("$Header$");
 
 #include "afs/sysincludes.h"   /* Standard vendor system headers */
 #ifdef AFS_OBSD_ENV
@@ -33,7 +31,6 @@ afs_int32 afs_showflags = GAGUSER | GAGCONSOLE;       /* show all messages */
 
 #ifdef AFS_DISCON_ENV
 afs_int32 afs_is_disconnected;
-afs_int32 afs_is_logging;
 afs_int32 afs_is_discon_rw;
 /* On reconnection, turn this knob on until it finishes,
  * then turn it off.
@@ -58,7 +55,7 @@ afs_int32 afs_in_sync = 0;
 
 #define DECL_PIOCTL(x) static int x(struct vcache *avc, int afun, struct vrequest *areq, \
        char *ain, char *aout, afs_int32 ainSize, afs_int32 *aoutSize, \
-       struct AFS_UCRED **acred)
+       AFS_UCRED **acred)
 
 /* Prototypes for pioctl routines */
 DECL_PIOCTL(PGetFID);
@@ -114,12 +111,13 @@ DECL_PIOCTL(PFlushMount);
 DECL_PIOCTL(PRxStatProc);
 DECL_PIOCTL(PRxStatPeer);
 DECL_PIOCTL(PPrefetchFromTape);
-DECL_PIOCTL(PResidencyCmd);
+DECL_PIOCTL(PFsCmd);
 DECL_PIOCTL(PCallBackAddr);
 DECL_PIOCTL(PDiscon);
 DECL_PIOCTL(PNFSNukeCreds);
 DECL_PIOCTL(PNewUuid);
 DECL_PIOCTL(PPrecache); 
+DECL_PIOCTL(PGetPAG);
 #if defined(AFS_CACHE_BYPASS)
 DECL_PIOCTL(PSetCachingThreshold);
 DECL_PIOCTL(PSetCachingBlkSize);
@@ -136,19 +134,22 @@ DECL_PIOCTL(PSetCachingBlkSize);
 /* Prototypes for private routines */
 #ifdef AFS_NEED_CLIENTCONTEXT
 static int HandleClientContext(struct afs_ioctl *ablob, int *com,
-                              struct AFS_UCRED **acred,
-                              struct AFS_UCRED *credp);
+                              AFS_UCRED **acred,
+                              AFS_UCRED *credp);
 #endif
 int HandleIoctl(register struct vcache *avc, register afs_int32 acom,
                struct afs_ioctl *adata);
 int afs_HandlePioctl(struct vnode *avp, afs_int32 acom,
                     register struct afs_ioctl *ablob, int afollow,
-                    struct AFS_UCRED **acred);
-static int Prefetch(char *apath, struct afs_ioctl *adata, int afollow,
-                   struct AFS_UCRED *acred);
+                    AFS_UCRED **acred);
+static int Prefetch(iparmtype apath, struct afs_ioctl *adata, int afollow,
+                   AFS_UCRED *acred);
 
+typedef int (*pioctlFunction) (struct vcache *, int, struct vrequest *,
+                              char *, char *, afs_int32, afs_int32 *,
+                              AFS_UCRED **);
 
-static int (*(VpioctlSw[])) () = {
+static pioctlFunction VpioctlSw[] = {
     PBogus,                    /* 0 */
        PSetAcl,                /* 1 */
        PGetAcl,                /* 2 */
@@ -216,12 +217,12 @@ static int (*(VpioctlSw[])) () = {
        PBogus,                 /* 64 -- arla: force cache check */
        PBogus,                 /* 65 -- arla: break callback */
        PPrefetchFromTape,      /* 66 -- MR-AFS: prefetch file from tape */
-       PResidencyCmd,          /* 67 -- MR-AFS: generic commnd interface */
+       PFsCmd,                 /* 67 -- RXOSD: generic commnd interface */
        PBogus,                 /* 68 -- arla: fetch stats */
        PGetVnodeXStatus2,      /* 69 - get caller access and some vcache status */
 };
 
-static int (*(CpioctlSw[])) () = {
+static pioctlFunction CpioctlSw[] = {
     PBogus,                    /* 0 */
        PNewAlias,              /* 1 -- create new cell alias */
        PListAliases,           /* 2 -- list cell aliases */
@@ -235,9 +236,10 @@ static int (*(CpioctlSw[])) () = {
     PBogus,                     /* 0 */
     PBogus,                     /* 0 */
     PPrecache,                  /* 12 */
+    PGetPAG,                    /* 13 */
 };
 
-static int (*(OpioctlSw[])) () = {
+static pioctlFunction OpioctlSw[]  = {
     PBogus,                    /* 0 */
     PNFSNukeCreds,             /* 1 -- nuke all creds for NFS client */
 #if defined(AFS_CACHE_BYPASS)
@@ -261,8 +263,9 @@ HandleIoctl(register struct vcache *avc, register afs_int32 acom,
 
     switch (acom & 0xff) {
     case 1:
-       avc->states |= CSafeStore;
+       avc->f.states |= CSafeStore;
        avc->asynchrony = 0;
+       /* SXW - Should we force a MetaData flush for this flag setting */
        break;
 
        /* case 2 used to be abort store, but this is no longer provided,
@@ -274,7 +277,7 @@ HandleIoctl(register struct vcache *avc, register afs_int32 acom,
            register struct cell *tcell;
            register afs_int32 i;
 
-           tcell = afs_GetCell(avc->fid.Cell, READ_LOCK);
+           tcell = afs_GetCell(avc->f.fid.Cell, READ_LOCK);
            if (tcell) {
                i = strlen(tcell->cellName) + 1;        /* bytes to copy out */
 
@@ -312,7 +315,6 @@ HandleIoctl(register struct vcache *avc, register afs_int32 acom,
     return code;               /* so far, none implemented */
 }
 
-
 #ifdef AFS_AIX_ENV
 /* For aix we don't temporarily bypass ioctl(2) but rather do our
  * thing directly in the vnode layer call, VNOP_IOCTL; thus afs_ioctl
@@ -383,16 +385,18 @@ afs_ioctl(OSI_VN_DECL(tvc), int cmd, void *arg, int flag, cred_t * cr,
 #ifdef AFS_AIX32_ENV
 #ifdef AFS_AIX51_ENV
 #ifdef __64BIT__
-kioctl(fdes, com, arg, ext, arg2, arg3)
+int
+kioctl(int fdes, int com, caddr_t arg, caddr_t ext, caddr_t arg2, 
+          caddr_t arg3)
 #else /* __64BIT__ */
-kioctl32(fdes, com, arg, ext, arg2, arg3)
+int
+kioctl32(int fdes, int com, caddr_t arg, caddr_t ext, caddr_t arg2, 
+            caddr_t arg3)
 #endif /* __64BIT__ */
-     caddr_t arg2, arg3;
 #else
-kioctl(fdes, com, arg, ext)
+int
+kioctl(int fdes, int com, caddr_t arg, caddr_t ext)
 #endif
-     int fdes, com;
-     caddr_t arg, ext;
 {
     struct a {
        int fd, com;
@@ -410,15 +414,12 @@ struct afs_ioctl_sys {
     int arg;
 };
 
-afs_xioctl(uap, rvp)
-     struct afs_ioctl_sys *uap;
-     rval_t *rvp;
+int 
+afs_xioctl(struct afs_ioctl_sys *uap, rval_t *rvp)
 {
 #elif defined(AFS_OSF_ENV)
-afs_xioctl(p, args, retval)
-     struct proc *p;
-     void *args;
-     long *retval;
+int 
+afs_xioctl(struct proc *p, void *args, long *retval)
 {
     struct a {
        long fd;
@@ -428,10 +429,8 @@ afs_xioctl(p, args, retval)
 #elif defined(AFS_FBSD50_ENV)
 #define arg data
 int
-afs_xioctl(td, uap, retval)
-     struct thread *td;
-     register struct ioctl_args *uap;
-     register_t *retval;
+afs_xioctl(struct thread *td, register struct ioctl_args *uap, 
+          register_t *retval)
 {
     struct proc *p = td->td_proc;
 #elif defined(AFS_DARWIN_ENV) || defined(AFS_XBSD_ENV)
@@ -442,10 +441,7 @@ struct ioctl_args {
 };
 
 int
-afs_xioctl(p, uap, retval)
-     struct proc *p;
-     register struct ioctl_args *uap;
-     register_t *retval;
+afs_xioctl(struct proc *p, register struct ioctl_args *uap, register_t *retval)
 {
 #elif defined(AFS_LINUX22_ENV)
 struct afs_ioctl_sys {
@@ -584,8 +580,7 @@ afs_xioctl(void)
 #ifdef AFS_LINUX22_ENV
                    return -code;
 #else
-                   setuerror(code);
-                   return;
+                   return (setuerror(code), code);
 #endif
 #endif
 #endif
@@ -684,6 +679,8 @@ afs_xioctl(void)
 #endif /* AFS_SUN5_ENV */
 #if defined(AFS_OSF_ENV) || defined(AFS_DARWIN_ENV) || defined(AFS_XBSD_ENV)
     return (code);
+#else
+    return 0;
 #endif
 }
 #endif /* AFS_SGI_ENV */
@@ -715,10 +712,7 @@ afs_pioctl(struct pioctlargs *uap, rval_t * rvp)
 }
 
 #elif defined(AFS_OSF_ENV)
-afs_pioctl(p, args, retval)
-     struct proc *p;
-     void *args;
-     int *retval;
+afs_pioctl(struct proc *p, void *args, int *retval)
 {
     struct a {
        char *path;
@@ -733,10 +727,7 @@ afs_pioctl(p, args, retval)
 
 #elif defined(AFS_FBSD50_ENV)
 int
-afs_pioctl(td, args, retval)
-     struct thread *td;
-     void *args;
-     int *retval;
+afs_pioctl(struct thread *td, void *args, int *retval)
 {
     struct a {
        char *path;
@@ -752,10 +743,7 @@ afs_pioctl(td, args, retval)
 
 #elif defined(AFS_DARWIN_ENV) || defined(AFS_XBSD_ENV)
 int
-afs_pioctl(p, args, retval)
-     struct proc *p;
-     void *args;
-     int *retval;
+afs_pioctl(struct proc *p, void *args, int *retval)
 {
     struct a {
        char *path;
@@ -787,27 +775,27 @@ afs_pioctl(p, args, retval)
 
 int
 #ifdef AFS_SUN5_ENV
-afs_syscall_pioctl(path, com, cmarg, follow, rvp, credp)
-     rval_t *rvp;
-     struct AFS_UCRED *credp;
+afs_syscall_pioctl(char *path, unsigned int com, caddr_t cmarg, int follow, 
+                  rval_t *vvp, AFS_UCRED *credp)
 #else
-#if defined(AFS_DARWIN_ENV) || defined(AFS_XBSD_ENV)
-afs_syscall_pioctl(path, com, cmarg, follow, credp)
-     struct AFS_UCRED *credp;
+#ifdef AFS_DARWIN100_ENV
+afs_syscall64_pioctl(user_addr_t path, unsigned int com, user_addr_t cmarg,
+                  int follow, AFS_UCRED *credp)
+#elif defined(AFS_DARWIN_ENV) || defined(AFS_XBSD_ENV)
+afs_syscall_pioctl(char *path, unsigned int com, caddr_t cmarg, int follow, 
+                  AFS_UCRED *credp)
 #else
-afs_syscall_pioctl(path, com, cmarg, follow)
+afs_syscall_pioctl(char *path, unsigned int com, caddr_t cmarg, int follow)
 #endif
 #endif
-     char *path;
-     unsigned int com;
-     caddr_t cmarg;
-     int follow;
 {
     struct afs_ioctl data;
 #ifdef AFS_NEED_CLIENTCONTEXT
-    struct AFS_UCRED *tmpcred = NULL;
+    AFS_UCRED *tmpcred = NULL;
+#endif
+#if defined(AFS_NEED_CLIENTCONTEXT) || defined(AFS_SUN5_ENV) || defined(AFS_AIX41_ENV) || defined(AFS_LINUX22_ENV) || defined(AFS_DARWIN_ENV) || defined(AFS_XBSD_ENV)
+    AFS_UCRED *foreigncreds = NULL;
 #endif
-    struct AFS_UCRED *foreigncreds = NULL;
     register afs_int32 code = 0;
     struct vnode *vp = NULL;
 #ifdef AFS_AIX41_ENV
@@ -903,11 +891,11 @@ afs_syscall_pioctl(path, com, cmarg, follow)
                       foreigncreds ? foreigncreds : credp);
 #else
 #ifdef AFS_LINUX22_ENV
-       code = gop_lookupname(path, AFS_UIOUSER, follow, &dp);
+       code = gop_lookupname_user(path, AFS_UIOUSER, follow, &dp);
        if (!code)
            vp = (struct vnode *)dp->d_inode;
 #else
-       code = gop_lookupname(path, AFS_UIOUSER, follow, &vp);
+       code = gop_lookupname_user(path, AFS_UIOUSER, follow, &vp);
 #endif /* AFS_LINUX22_ENV */
 #endif /* AFS_AIX41_ENV */
        AFS_GLOCK();
@@ -1018,13 +1006,24 @@ afs_syscall_pioctl(path, com, cmarg, follow)
 #endif
 }
 
+#ifdef AFS_DARWIN100_ENV
+int
+afs_syscall_pioctl(char * path, unsigned int com, caddr_t cmarg,
+                  int follow, AFS_UCRED *credp)
+{
+    return afs_syscall64_pioctl(CAST_USER_ADDR_T(path), com,
+                               CAST_USER_ADDR_T((unsigned int)cmarg), follow,
+                               credp);
+}
+#endif
+
 #define MAXPIOCTLTOKENLEN \
 (3*sizeof(afs_int32)+MAXKTCTICKETLEN+sizeof(struct ClearToken)+MAXKTCREALMLEN)
 
 int
 afs_HandlePioctl(struct vnode *avp, afs_int32 acom,
                 register struct afs_ioctl *ablob, int afollow,
-                struct AFS_UCRED **acred)
+                AFS_UCRED **acred)
 {
     struct vcache *avc;
     struct vrequest treq;
@@ -1032,7 +1031,7 @@ afs_HandlePioctl(struct vnode *avp, afs_int32 acom,
     register afs_int32 function, device;
     afs_int32 inSize, outSize, outSizeMax;
     char *inData, *outData;
-    int (*(*pioctlSw)) ();
+    pioctlFunction *pioctlSw;
     int pioctlSwSize;
     struct afs_fakestat_state fakestate;
 
@@ -1143,12 +1142,12 @@ afs_HandlePioctl(struct vnode *avp, afs_int32 acom,
 }
 
 /*!
- * VIOCETFID (22) - Get file ID quickly
+ * VIOCGETFID (22) - Get file ID quickly
  *
  * \ingroup pioctl
  *
  * \param[in] ain      not in use
- * \param[out] aout    not in use
+ * \param[out] aout    fid of requested file
  *
  * \retval EINVAL      Error if some of the initial arguments aren't set
  *
@@ -1159,7 +1158,7 @@ DECL_PIOCTL(PGetFID)
     AFS_STATCNT(PGetFID);
     if (!avc)
        return EINVAL;
-    memcpy(aout, (char *)&avc->fid, sizeof(struct VenusFid));
+    memcpy(aout, (char *)&avc->f.fid, sizeof(struct VenusFid));
     *aoutSize = sizeof(struct VenusFid);
     return 0;
 }
@@ -1184,7 +1183,7 @@ int dummy_PSetAcl(char *ain, char *aout)
 DECL_PIOCTL(PSetAcl)
 {
     register afs_int32 code;
-    struct conn *tconn;
+    struct afs_conn *tconn;
     struct AFSOpaque acl;
     struct AFSVolSync tsync;
     struct AFSFetchStatus OutStatus;
@@ -1198,29 +1197,31 @@ DECL_PIOCTL(PSetAcl)
 
     acl.AFSOpaque_val = ain;
     do {
-       tconn = afs_Conn(&avc->fid, areq, SHARED_LOCK);
+       tconn = afs_Conn(&avc->f.fid, areq, SHARED_LOCK);
        if (tconn) {
            XSTATS_START_TIME(AFS_STATS_FS_RPCIDX_STOREACL);
            RX_AFS_GUNLOCK();
            code =
-               RXAFS_StoreACL(tconn->id, (struct AFSFid *)&avc->fid.Fid,
+               RXAFS_StoreACL(tconn->id, (struct AFSFid *)&avc->f.fid.Fid,
                               &acl, &OutStatus, &tsync);
            RX_AFS_GLOCK();
            XSTATS_END_TIME;
        } else
            code = -1;
     } while (afs_Analyze
-            (tconn, code, &avc->fid, areq, AFS_STATS_FS_RPCIDX_STOREACL,
+            (tconn, code, &avc->f.fid, areq, AFS_STATS_FS_RPCIDX_STOREACL,
              SHARED_LOCK, NULL));
 
     /* now we've forgotten all of the access info */
     ObtainWriteLock(&afs_xcbhash, 455);
     avc->callback = 0;
     afs_DequeueCallback(avc);
-    avc->states &= ~(CStatd | CUnique);
+    avc->f.states &= ~(CStatd | CUnique);
     ReleaseWriteLock(&afs_xcbhash);
-    if (avc->fid.Fid.Vnode & 1 || (vType(avc) == VDIR))
+    if (avc->f.fid.Fid.Vnode & 1 || (vType(avc) == VDIR))
        osi_dnlc_purgedp(avc);
+
+    /* SXW - Should we flush metadata here? */
     return code;
 }
 
@@ -1313,17 +1314,17 @@ DECL_PIOCTL(PGetAcl)
     struct AFSVolSync tsync;
     struct AFSFetchStatus OutStatus;
     afs_int32 code;
-    struct conn *tconn;
+    struct afs_conn *tconn;
     struct AFSFid Fid;
     XSTATS_DECLS;
 
     AFS_STATCNT(PGetAcl);
     if (!avc)
        return EINVAL;
-    Fid.Volume = avc->fid.Fid.Volume;
-    Fid.Vnode = avc->fid.Fid.Vnode;
-    Fid.Unique = avc->fid.Fid.Unique;
-    if (avc->states & CForeign) {
+    Fid.Volume = avc->f.fid.Fid.Volume;
+    Fid.Vnode = avc->f.fid.Fid.Vnode;
+    Fid.Unique = avc->f.fid.Fid.Unique;
+    if (avc->f.states & CForeign) {
        /*
         * For a dfs xlator acl we have a special hack so that the
         * xlator will distinguish which type of acl will return. So
@@ -1337,7 +1338,7 @@ DECL_PIOCTL(PGetAcl)
     }
     acl.AFSOpaque_val = aout;
     do {
-       tconn = afs_Conn(&avc->fid, areq, SHARED_LOCK);
+       tconn = afs_Conn(&avc->f.fid, areq, SHARED_LOCK);
        if (tconn) {
            *aout = 0;
            XSTATS_START_TIME(AFS_STATS_FS_RPCIDX_FETCHACL);
@@ -1348,7 +1349,7 @@ DECL_PIOCTL(PGetAcl)
        } else
            code = -1;
     } while (afs_Analyze
-            (tconn, code, &avc->fid, areq, AFS_STATS_FS_RPCIDX_FETCHACL,
+            (tconn, code, &avc->f.fid, areq, AFS_STATS_FS_RPCIDX_FETCHACL,
              SHARED_LOCK, NULL));
 
     if (code == 0) {
@@ -1405,7 +1406,7 @@ DECL_PIOCTL(PGetFileCell)
     AFS_STATCNT(PGetFileCell);
     if (!avc)
        return EINVAL;
-    tcell = afs_GetCell(avc->fid.Cell, READ_LOCK);
+    tcell = afs_GetCell(avc->f.fid.Cell, READ_LOCK);
     if (!tcell)
        return ESRCH;
     strcpy(aout, tcell->cellName);
@@ -1563,7 +1564,7 @@ DECL_PIOCTL(PSetTokens)
     i = tcell->cellNum;
     afs_PutCell(tcell, READ_LOCK);
     if (set_parent_pag) {
-       afs_int32 pag;
+       afs_uint32 pag;
 #if defined(AFS_DARWIN_ENV) || defined(AFS_XBSD_ENV)
 #if defined(AFS_DARWIN_ENV)
        struct proc *p = current_proc();        /* XXX */
@@ -1640,7 +1641,7 @@ DECL_PIOCTL(PGetVolumeStatus)
     char volName[32];
     char *offLineMsg = afs_osi_Alloc(256);
     char *motd = afs_osi_Alloc(256);
-    register struct conn *tc;
+    register struct afs_conn *tc;
     register afs_int32 code = 0;
     struct AFSFetchVolumeStatus volstat;
     register char *cp;
@@ -1656,19 +1657,19 @@ DECL_PIOCTL(PGetVolumeStatus)
     OfflineMsg = offLineMsg;
     MOTD = motd;
     do {
-       tc = afs_Conn(&avc->fid, areq, SHARED_LOCK);
+       tc = afs_Conn(&avc->f.fid, areq, SHARED_LOCK);
        if (tc) {
            XSTATS_START_TIME(AFS_STATS_FS_RPCIDX_GETVOLUMESTATUS);
            RX_AFS_GUNLOCK();
            code =
-               RXAFS_GetVolumeStatus(tc->id, avc->fid.Fid.Volume, &volstat,
+               RXAFS_GetVolumeStatus(tc->id, avc->f.fid.Fid.Volume, &volstat,
                                      &Name, &OfflineMsg, &MOTD);
            RX_AFS_GLOCK();
            XSTATS_END_TIME;
        } else
            code = -1;
     } while (afs_Analyze
-            (tc, code, &avc->fid, areq, AFS_STATS_FS_RPCIDX_GETVOLUMESTATUS,
+            (tc, code, &avc->f.fid, areq, AFS_STATS_FS_RPCIDX_GETVOLUMESTATUS,
              SHARED_LOCK, NULL));
 
     if (code)
@@ -1710,7 +1711,7 @@ DECL_PIOCTL(PSetVolumeStatus)
     char volName[32];
     char *offLineMsg = afs_osi_Alloc(256);
     char *motd = afs_osi_Alloc(256);
-    register struct conn *tc;
+    register struct afs_conn *tc;
     register afs_int32 code = 0;
     struct AFSFetchVolumeStatus volstat;
     struct AFSStoreVolumeStatus storeStat;
@@ -1724,7 +1725,7 @@ DECL_PIOCTL(PSetVolumeStatus)
        goto out;
     }
 
-    tvp = afs_GetVolume(&avc->fid, areq, READ_LOCK);
+    tvp = afs_GetVolume(&avc->f.fid, areq, READ_LOCK);
     if (tvp) {
        if (tvp->states & (VRO | VBackup)) {
            afs_PutVolume(tvp, READ_LOCK);
@@ -1767,19 +1768,19 @@ DECL_PIOCTL(PSetVolumeStatus)
        storeStat.Mask |= AFS_SETMAXQUOTA;
     }
     do {
-       tc = afs_Conn(&avc->fid, areq, SHARED_LOCK);
+       tc = afs_Conn(&avc->f.fid, areq, SHARED_LOCK);
        if (tc) {
            XSTATS_START_TIME(AFS_STATS_FS_RPCIDX_SETVOLUMESTATUS);
            RX_AFS_GUNLOCK();
            code =
-               RXAFS_SetVolumeStatus(tc->id, avc->fid.Fid.Volume, &storeStat,
+               RXAFS_SetVolumeStatus(tc->id, avc->f.fid.Fid.Volume, &storeStat,
                                      volName, offLineMsg, motd);
            RX_AFS_GLOCK();
            XSTATS_END_TIME;
        } else
            code = -1;
     } while (afs_Analyze
-            (tc, code, &avc->fid, areq, AFS_STATS_FS_RPCIDX_SETVOLUMESTATUS,
+            (tc, code, &avc->f.fid, areq, AFS_STATS_FS_RPCIDX_SETVOLUMESTATUS,
              SHARED_LOCK, NULL));
 
     if (code)
@@ -1823,17 +1824,7 @@ DECL_PIOCTL(PFlush)
     afs_BozonLock(&avc->pvnLock, avc); /* Since afs_TryToSmush will do a pvn_vptrunc */
 #endif
     ObtainWriteLock(&avc->lock, 225);
-    ObtainWriteLock(&afs_xcbhash, 456);
-    afs_DequeueCallback(avc);
-    avc->states &= ~(CStatd | CDirty); /* next reference will re-stat cache entry */
-    ReleaseWriteLock(&afs_xcbhash);
-    /* now find the disk cache entries */
-    afs_TryToSmush(avc, *acred, 1);
-    osi_dnlc_purgedp(avc);
-    if (avc->linkData && !(avc->states & CCore)) {
-       afs_osi_Free(avc->linkData, strlen(avc->linkData) + 1);
-       avc->linkData = NULL;
-    }
+    afs_ResetVCache(avc, *acred);
     ReleaseWriteLock(&avc->lock);
 #ifdef AFS_BOZONLOCK_ENV
     afs_BozonUnlock(&avc->pvnLock, avc);
@@ -1888,9 +1879,9 @@ DECL_PIOCTL(PNewStatMount)
     if (code) {
        goto out;
     }
-    tfid.Cell = avc->fid.Cell;
-    tfid.Fid.Volume = avc->fid.Fid.Volume;
-    if (!tfid.Fid.Unique && (avc->states & CForeign)) {
+    tfid.Cell = avc->f.fid.Cell;
+    tfid.Fid.Volume = avc->f.fid.Fid.Volume;
+    if (!tfid.Fid.Unique && (avc->f.states & CForeign)) {
        tvc = afs_LookupVCache(&tfid, areq, NULL, avc, bufp);
     } else {
        tvc = afs_GetVCache(&tfid, areq, NULL, NULL);
@@ -1949,7 +1940,7 @@ DECL_PIOCTL(PGetTokens)
     register afs_int32 i;
     register struct unixuser *tu;
     register char *cp;
-    afs_int32 iterator;
+    afs_int32 iterator = 0;
     int newStyle;
 
     AFS_STATCNT(PGetTokens);
@@ -2259,7 +2250,7 @@ DECL_PIOCTL(PCheckAuth)
 {
     int i;
     struct srvAddr *sa;
-    struct conn *tc;
+    struct afs_conn *tc;
     struct unixuser *tu;
     afs_int32 retValue;
 
@@ -2298,8 +2289,8 @@ DECL_PIOCTL(PCheckAuth)
 }
 
 static int
-Prefetch(char *apath, struct afs_ioctl *adata, int afollow,
-        struct AFS_UCRED *acred)
+Prefetch(iparmtype apath, struct afs_ioctl *adata, int afollow,
+        AFS_UCRED *acred)
 {
     register char *tp;
     register afs_int32 code;
@@ -2352,7 +2343,7 @@ DECL_PIOCTL(PFindVolume)
     AFS_STATCNT(PFindVolume);
     if (!avc)
        return EINVAL;
-    tvp = afs_GetVolume(&avc->fid, areq, READ_LOCK);
+    tvp = afs_GetVolume(&avc->f.fid, areq, READ_LOCK);
     if (tvp) {
        cp = aout;
        for (i = 0; i < MAXHOSTS; i++) {
@@ -2407,6 +2398,33 @@ DECL_PIOCTL(PViceAccess)
        return EACCES;
 }
 
+/*!
+ * VIOC_GETPAG (13) - Get PAG value
+ *
+ * \ingroup pioctl
+ *
+ * \param[in] ain      not in use
+ * \param[out] aout    PAG value or NOPAG
+ *
+ * \retval E2BIG       Error not enough space to copy out value
+ *
+ * \post get PAG value for the caller's cred
+ */
+DECL_PIOCTL(PGetPAG)
+{
+    afs_int32 pag;
+
+    if (*aoutSize < sizeof(afs_int32)) {
+       return E2BIG;
+    }
+
+    pag = PagInCred(*acred);
+
+    memcpy(aout, (char *)&pag, sizeof(afs_int32));
+    *aoutSize = sizeof(afs_int32);
+    return 0;
+}
+
 DECL_PIOCTL(PPrecache)
 {
     afs_int32 newValue;
@@ -2543,7 +2561,7 @@ DECL_PIOCTL(PGetCacheSize)
  */
 DECL_PIOCTL(PRemoveCallBack)
 {
-    register struct conn *tc;
+    register struct afs_conn *tc;
     register afs_int32 code = 0;
     struct AFSCallBack CallBacks_Array[1];
     struct AFSCBFids theFids;
@@ -2553,17 +2571,17 @@ DECL_PIOCTL(PRemoveCallBack)
     AFS_STATCNT(PRemoveCallBack);
     if (!avc)
        return EINVAL;
-    if (avc->states & CRO)
+    if (avc->f.states & CRO)
        return 0;               /* read-only-ness can't change */
     ObtainWriteLock(&avc->lock, 229);
     theFids.AFSCBFids_len = 1;
     theCBs.AFSCBs_len = 1;
-    theFids.AFSCBFids_val = (struct AFSFid *)&avc->fid.Fid;
+    theFids.AFSCBFids_val = (struct AFSFid *)&avc->f.fid.Fid;
     theCBs.AFSCBs_val = CallBacks_Array;
     CallBacks_Array[0].CallBackType = CB_DROPPED;
     if (avc->callback) {
        do {
-           tc = afs_Conn(&avc->fid, areq, SHARED_LOCK);
+           tc = afs_Conn(&avc->f.fid, areq, SHARED_LOCK);
            if (tc) {
                XSTATS_START_TIME(AFS_STATS_FS_RPCIDX_GIVEUPCALLBACKS);
                RX_AFS_GUNLOCK();
@@ -2573,15 +2591,15 @@ DECL_PIOCTL(PRemoveCallBack)
            }
            /* don't set code on failure since we wouldn't use it */
        } while (afs_Analyze
-                (tc, code, &avc->fid, areq,
+                (tc, code, &avc->f.fid, areq,
                  AFS_STATS_FS_RPCIDX_GIVEUPCALLBACKS, SHARED_LOCK, NULL));
 
        ObtainWriteLock(&afs_xcbhash, 457);
        afs_DequeueCallback(avc);
        avc->callback = 0;
-       avc->states &= ~(CStatd | CUnique);
+       avc->f.states &= ~(CStatd | CUnique);
        ReleaseWriteLock(&afs_xcbhash);
-       if (avc->fid.Fid.Vnode & 1 || (vType(avc) == VDIR))
+       if (avc->f.fid.Fid.Vnode & 1 || (vType(avc) == VDIR))
            osi_dnlc_purgedp(avc);
     }
     ReleaseWriteLock(&avc->lock);
@@ -2777,7 +2795,7 @@ DECL_PIOCTL(PRemoveMount)
     char *bufp;
     struct sysname_info sysState;
     afs_size_t offset, len;
-    register struct conn *tc;
+    register struct afs_conn *tc;
     register struct dcache *tdc;
     register struct vcache *tvc;
     struct AFSFetchStatus OutDirStatus;
@@ -2811,9 +2829,9 @@ DECL_PIOCTL(PRemoveMount)
        afs_PutDCache(tdc);
        goto out;
     }
-    tfid.Cell = avc->fid.Cell;
-    tfid.Fid.Volume = avc->fid.Fid.Volume;
-    if (!tfid.Fid.Unique && (avc->states & CForeign)) {
+    tfid.Cell = avc->f.fid.Cell;
+    tfid.Fid.Volume = avc->f.fid.Fid.Volume;
+    if (!tfid.Fid.Unique && (avc->f.states & CForeign)) {
        tvc = afs_LookupVCache(&tfid, areq, NULL, avc, bufp);
     } else {
        tvc = afs_GetVCache(&tfid, areq, NULL, NULL);
@@ -2848,19 +2866,19 @@ DECL_PIOCTL(PRemoveMount)
     ObtainWriteLock(&avc->lock, 231);
     osi_dnlc_remove(avc, bufp, tvc);
     do {
-       tc = afs_Conn(&avc->fid, areq, SHARED_LOCK);
+       tc = afs_Conn(&avc->f.fid, areq, SHARED_LOCK);
        if (tc) {
            XSTATS_START_TIME(AFS_STATS_FS_RPCIDX_REMOVEFILE);
            RX_AFS_GUNLOCK();
            code =
-               RXAFS_RemoveFile(tc->id, (struct AFSFid *)&avc->fid.Fid, bufp,
+               RXAFS_RemoveFile(tc->id, (struct AFSFid *)&avc->f.fid.Fid, bufp,
                                 &OutDirStatus, &tsync);
            RX_AFS_GLOCK();
            XSTATS_END_TIME;
        } else
            code = -1;
     } while (afs_Analyze
-            (tc, code, &avc->fid, areq, AFS_STATS_FS_RPCIDX_REMOVEFILE,
+            (tc, code, &avc->f.fid, areq, AFS_STATS_FS_RPCIDX_REMOVEFILE,
              SHARED_LOCK, NULL));
 
     if (code) {
@@ -2883,7 +2901,7 @@ DECL_PIOCTL(PRemoveMount)
        ReleaseWriteLock(&tdc->lock);
        afs_PutDCache(tdc);     /* drop ref count */
     }
-    avc->states &= ~CUnique;   /* For the dfs xlator */
+    avc->f.states &= ~CUnique; /* For the dfs xlator */
     ReleaseWriteLock(&avc->lock);
     code = 0;
   out:
@@ -3006,8 +3024,8 @@ DECL_PIOCTL(PFlushVolumeData)
     if (!afs_resourceinit_flag)        /* afs daemons haven't started yet */
        return EIO;             /* Inappropriate ioctl for device */
 
-    volume = avc->fid.Fid.Volume;      /* who to zap */
-    cell = avc->fid.Cell;
+    volume = avc->f.fid.Fid.Volume;    /* who to zap */
+    cell = avc->f.fid.Cell;
 
     /*
      * Clear stat'd flag from all vnodes from this volume; this will invalidate all
@@ -3015,20 +3033,20 @@ DECL_PIOCTL(PFlushVolumeData)
      */
  loop:
     ObtainReadLock(&afs_xvcache);
-    i = VCHashV(&avc->fid);
+    i = VCHashV(&avc->f.fid);
     for (tq = afs_vhashTV[i].prev; tq != &afs_vhashTV[i]; tq = uq) {
            uq = QPrev(tq);
            tvc = QTOVH(tq);
-           if (tvc->fid.Fid.Volume == volume && tvc->fid.Cell == cell) {
-               if (tvc->states & CVInit) {
+           if (tvc->f.fid.Fid.Volume == volume && tvc->f.fid.Cell == cell) {
+               if (tvc->f.states & CVInit) {
                    ReleaseReadLock(&afs_xvcache);
-                   afs_osi_Sleep(&tvc->states);
+                   afs_osi_Sleep(&tvc->f.states);
                    goto loop;
                }
 #ifdef AFS_DARWIN80_ENV
-               if (tvc->states & CDeadVnode) {
+               if (tvc->f.states & CDeadVnode) {
                    ReleaseReadLock(&afs_xvcache);
-                   afs_osi_Sleep(&tvc->states);
+                   afs_osi_Sleep(&tvc->f.states);
                    goto loop;
                }
 #endif
@@ -3061,9 +3079,9 @@ DECL_PIOCTL(PFlushVolumeData)
 
                ObtainWriteLock(&afs_xcbhash, 458);
                afs_DequeueCallback(tvc);
-               tvc->states &= ~(CStatd | CDirty);
+               tvc->f.states &= ~(CStatd | CDirty);
                ReleaseWriteLock(&afs_xcbhash);
-               if (tvc->fid.Fid.Vnode & 1 || (vType(tvc) == VDIR))
+               if (tvc->f.fid.Fid.Vnode & 1 || (vType(tvc) == VDIR))
                    osi_dnlc_purgedp(tvc);
                afs_TryToSmush(tvc, *acred, 1);
                ReleaseWriteLock(&tvc->lock);
@@ -3159,14 +3177,14 @@ DECL_PIOCTL(PGetVnodeXStatus)
        return EACCES;
 
     memset(&stat, 0, sizeof(struct vcxstat));
-    stat.fid = avc->fid;
-    hset32(stat.DataVersion, hgetlo(avc->m.DataVersion));
+    stat.fid = avc->f.fid;
+    hset32(stat.DataVersion, hgetlo(avc->f.m.DataVersion));
     stat.lock = avc->lock;
-    stat.parentVnode = avc->parentVnode;
-    stat.parentUnique = avc->parentUnique;
+    stat.parentVnode = avc->f.parent.vnode;
+    stat.parentUnique = avc->f.parent.unique;
     hset(stat.flushDV, avc->flushDV);
     hset(stat.mapDV, avc->mapDV);
-    stat.truncPos = avc->truncPos;
+    stat.truncPos = avc->f.truncPos;
     {                          /* just grab the first two - won't break anything... */
        struct axscache *ac;
 
@@ -3177,12 +3195,12 @@ DECL_PIOCTL(PGetVnodeXStatus)
     }
     stat.callback = afs_data_pointer_to_int32(avc->callback);
     stat.cbExpires = avc->cbExpires;
-    stat.anyAccess = avc->anyAccess;
+    stat.anyAccess = avc->f.anyAccess;
     stat.opens = avc->opens;
     stat.execsOrWriters = avc->execsOrWriters;
     stat.flockCount = avc->flockCount;
     stat.mvstat = avc->mvstat;
-    stat.states = avc->states;
+    stat.states = avc->f.states;
     memcpy(aout, (char *)&stat, sizeof(struct vcxstat));
     *aoutSize = sizeof(struct vcxstat);
     return 0;
@@ -3210,7 +3228,7 @@ DECL_PIOCTL(PGetVnodeXStatus2)
     memset(&stat, 0, sizeof(struct vcxstat2));
 
     stat.cbExpires = avc->cbExpires;
-    stat.anyAccess = avc->anyAccess;
+    stat.anyAccess = avc->f.anyAccess;
     stat.mvstat = avc->mvstat;
     stat.callerAccess = afs_GetAccessBits(avc, ~0, areq);
 
@@ -3439,10 +3457,7 @@ ReSortCells(int s, afs_int32 * l, int vlonly)
 
 static int debugsetsp = 0;
 static int
-afs_setsprefs(sp, num, vlonly)
-     struct spref *sp;
-     unsigned int num;
-     unsigned int vlonly;
+afs_setsprefs(struct spref *sp, unsigned int num, unsigned int vlonly)
 {
     struct srvAddr *sa;
     int i, j, k, matches, touchedSize;
@@ -3955,13 +3970,13 @@ DECL_PIOCTL(PSetRxkcrypt)
 #define        PIOCTL_HEADER   6
 static int
 HandleClientContext(struct afs_ioctl *ablob, int *com,
-                   struct AFS_UCRED **acred, struct AFS_UCRED *credp)
+                   AFS_UCRED **acred, AFS_UCRED *credp)
 {
     char *ain, *inData;
     afs_uint32 hostaddr;
     afs_int32 uid, g0, g1, i, code, pag, exporter_type, isroot = 0;
     struct afs_exporter *exporter, *outexporter;
-    struct AFS_UCRED *newcred;
+    AFS_UCRED *newcred;
     struct unixuser *au;
     afs_uint32 comp = *com & 0xff00;
     afs_uint32 h, l;
@@ -4252,9 +4267,9 @@ DECL_PIOCTL(PFlushMount)
     if (code) {
        goto out;
     }
-    tfid.Cell = avc->fid.Cell;
-    tfid.Fid.Volume = avc->fid.Fid.Volume;
-    if (!tfid.Fid.Unique && (avc->states & CForeign)) {
+    tfid.Cell = avc->f.fid.Cell;
+    tfid.Fid.Volume = avc->f.fid.Fid.Volume;
+    if (!tfid.Fid.Unique && (avc->f.states & CForeign)) {
        tvc = afs_LookupVCache(&tfid, areq, NULL, avc, bufp);
     } else {
        tvc = afs_GetVCache(&tfid, areq, NULL, NULL);
@@ -4274,12 +4289,12 @@ DECL_PIOCTL(PFlushMount)
     ObtainWriteLock(&tvc->lock, 649);
     ObtainWriteLock(&afs_xcbhash, 650);
     afs_DequeueCallback(tvc);
-    tvc->states &= ~(CStatd | CDirty); /* next reference will re-stat cache entry */
+    tvc->f.states &= ~(CStatd | CDirty); /* next reference will re-stat cache entry */
     ReleaseWriteLock(&afs_xcbhash);
     /* now find the disk cache entries */
     afs_TryToSmush(tvc, *acred, 1);
     osi_dnlc_purgedp(tvc);
-    if (tvc->linkData && !(tvc->states & CCore)) {
+    if (tvc->linkData && !(tvc->f.states & CCore)) {
        afs_osi_Free(tvc->linkData, strlen(tvc->linkData) + 1);
        tvc->linkData = NULL;
     }
@@ -4389,7 +4404,7 @@ DECL_PIOCTL(PPrefetchFromTape)
 {
     register afs_int32 code, code1;
     afs_int32 bytes;
-    struct conn *tc;
+    struct afs_conn *tc;
     struct rx_call *tcall;
     struct AFSVolSync tsync;
     struct AFSFetchStatus OutStatus;
@@ -4405,8 +4420,8 @@ DECL_PIOCTL(PPrefetchFromTape)
     if (ain && (ainSize == 3 * sizeof(afs_int32)))
        Fid = (struct AFSFid *)ain;
     else
-       Fid = &avc->fid.Fid;
-    tfid.Cell = avc->fid.Cell;
+       Fid = &avc->f.fid.Fid;
+    tfid.Cell = avc->f.fid.Cell;
     tfid.Fid.Volume = Fid->Volume;
     tfid.Fid.Vnode = Fid->Vnode;
     tfid.Fid.Unique = Fid->Unique;
@@ -4414,20 +4429,20 @@ DECL_PIOCTL(PPrefetchFromTape)
     tvc = afs_GetVCache(&tfid, areq, NULL, NULL);
     if (!tvc) {
        afs_Trace3(afs_iclSetp, CM_TRACE_PREFETCHCMD, ICL_TYPE_POINTER, tvc,
-                  ICL_TYPE_FID, &tfid, ICL_TYPE_FID, &avc->fid);
+                  ICL_TYPE_FID, &tfid, ICL_TYPE_FID, &avc->f.fid);
        return ENOENT;
     }
     afs_Trace3(afs_iclSetp, CM_TRACE_PREFETCHCMD, ICL_TYPE_POINTER, tvc,
-              ICL_TYPE_FID, &tfid, ICL_TYPE_FID, &tvc->fid);
+              ICL_TYPE_FID, &tfid, ICL_TYPE_FID, &tvc->f.fid);
 
     do {
-       tc = afs_Conn(&tvc->fid, areq, SHARED_LOCK);
+       tc = afs_Conn(&tvc->f.fid, areq, SHARED_LOCK);
        if (tc) {
 
            RX_AFS_GUNLOCK();
            tcall = rx_NewCall(tc->id);
            code =
-               StartRXAFS_FetchData(tcall, (struct AFSFid *)&tvc->fid.Fid, 0,
+               StartRXAFS_FetchData(tcall, (struct AFSFid *)&tvc->f.fid.Fid, 0,
                                     0);
            if (!code) {
                bytes = rx_Read(tcall, (char *)aout, sizeof(afs_int32));
@@ -4439,7 +4454,7 @@ DECL_PIOCTL(PPrefetchFromTape)
        } else
            code = -1;
     } while (afs_Analyze
-            (tc, code, &tvc->fid, areq, AFS_STATS_FS_RPCIDX_RESIDENCYRPCS,
+            (tc, code, &tvc->f.fid, areq, AFS_STATS_FS_RPCIDX_RESIDENCYRPCS,
              SHARED_LOCK, NULL));
     /* This call is done only to have the callback things handled correctly */
     afs_FetchStatus(tvc, &tfid, areq, &OutStatus);
@@ -4451,28 +4466,28 @@ DECL_PIOCTL(PPrefetchFromTape)
     return code;
 }
 
-DECL_PIOCTL(PResidencyCmd)
+DECL_PIOCTL(PFsCmd)
 {
     register afs_int32 code;
-    struct conn *tc;
+    struct afs_conn *tc;
     struct vcache *tvc;
-    struct ResidencyCmdInputs *Inputs;
-    struct ResidencyCmdOutputs *Outputs;
+    struct FsCmdInputs *Inputs;
+    struct FsCmdOutputs *Outputs;
     struct VenusFid tfid;
     struct AFSFid *Fid;
 
-    Inputs = (struct ResidencyCmdInputs *)ain;
-    Outputs = (struct ResidencyCmdOutputs *)aout;
+    Inputs = (struct FsCmdInputs *)ain;
+    Outputs = (struct FsCmdOutputs *)aout;
     if (!avc)
        return EINVAL;
-    if (!ain || ainSize != sizeof(struct ResidencyCmdInputs))
+    if (!ain || ainSize != sizeof(struct FsCmdInputs))
        return EINVAL;
 
     Fid = &Inputs->fid;
     if (!Fid->Volume)
-       Fid = &avc->fid.Fid;
+       Fid = &avc->f.fid.Fid;
 
-    tfid.Cell = avc->fid.Cell;
+    tfid.Cell = avc->f.fid.Cell;
     tfid.Fid.Volume = Fid->Volume;
     tfid.Fid.Vnode = Fid->Vnode;
     tfid.Fid.Unique = Fid->Unique;
@@ -4485,17 +4500,17 @@ DECL_PIOCTL(PResidencyCmd)
 
     if (Inputs->command) {
        do {
-           tc = afs_Conn(&tvc->fid, areq, SHARED_LOCK);
+           tc = afs_Conn(&tvc->f.fid, areq, SHARED_LOCK);
            if (tc) {
                RX_AFS_GUNLOCK();
                code =
-                   RXAFS_ResidencyCmd(tc->id, Fid, Inputs,
-                                      (struct ResidencyCmdOutputs *)aout);
+                   RXAFS_FsCmd(tc->id, Fid, Inputs, 
+                                       (struct FsCmdOutputs *)aout);
                RX_AFS_GLOCK();
            } else
                code = -1;
        } while (afs_Analyze
-                (tc, code, &tvc->fid, areq,
+                (tc, code, &tvc->f.fid, areq,
                  AFS_STATS_FS_RPCIDX_RESIDENCYRPCS, SHARED_LOCK, NULL));
        /* This call is done to have the callback things handled correctly */
        afs_FetchStatus(tvc, &tfid, areq, &Outputs->status);
@@ -4514,7 +4529,7 @@ DECL_PIOCTL(PResidencyCmd)
     afs_PutVCache(tvc);
 
     if (!code) {
-       *aoutSize = sizeof(struct ResidencyCmdOutputs);
+       *aoutSize = sizeof(struct FsCmdOutputs);
     }
     return code;
 }
@@ -4587,7 +4602,7 @@ DECL_PIOCTL(PCallBackAddr)
     int srvAddrCount;
     struct server *ts;
     struct srvAddr *sa;
-    struct conn *tc;
+    struct afs_conn *tc;
     afs_int32 i, j;
     struct unixuser *tu;
     struct srvAddr **addrs;
@@ -4716,13 +4731,19 @@ DECL_PIOCTL(PDiscon)
            ObtainWriteLock(&afs_discon_lock, 998);
 
            afs_in_sync = 1;
+           afs_MarkAllServersUp();
            code = afs_ResyncDisconFiles(areq, *acred);
            afs_in_sync = 0;
 
            if (code && !force) {
-               printf("Files not synchronized properly, still in discon state. \
-                                               Please retry or use \"force\".\n");
+               printf("Files not synchronized properly, still in discon state. \n"
+                      "Please retry or use \"force\".\n");
+               mode = 0;
            } else {
+               if (force) {
+                   afs_DisconDiscardAll(*acred);
+               }
+               afs_ClearAllStatdFlag();
                afs_is_disconnected = 0;
                afs_is_discon_rw = 0;
                printf("\nSync succeeded. You are back online.\n");
@@ -4739,7 +4760,7 @@ DECL_PIOCTL(PDiscon)
 
     memcpy(aout, &mode, sizeof(afs_int32));
     *aoutSize = sizeof(afs_int32);
-    return 0;
+    return code;
 #else
     return EINVAL;
 #endif
@@ -4747,7 +4768,7 @@ DECL_PIOCTL(PDiscon)
 
 DECL_PIOCTL(PNFSNukeCreds)
 {
-    afs_uint32 addr, code;
+    afs_uint32 addr;
     register afs_int32 i;
     register struct unixuser *tu;