Windows: Treat invalid AFSFetchStatus as VBUSY
authorJeffrey Altman <jaltman@your-file-system.com>
Thu, 8 Nov 2012 16:29:20 +0000 (11:29 -0500)
committerJeffrey Altman <jaltman@your-file-system.com>
Fri, 9 Nov 2012 04:40:27 +0000 (20:40 -0800)
Modify cm_Analyze() to accept an AFSFetchStatus parameter which
when set is verified for validity.  If the status info is invalid,
then consider the response equivalent to VBUSY and attempt to
query an alternate file server (if any.)   Log the invalid status
info to the Windows Application Event Log as a Warning.

When cm_Analyze() is processing the response of an RPC that returns
multiple AFSFetchStatus structures, pass in the one that corresponds
with the source object.

Change-Id: I84be22f332ff6fd7bc9620347f958538a3412380
Reviewed-on: http://gerrit.openafs.org/8404
Tested-by: BuildBot <buildbot@rampaginggeek.com>
Reviewed-by: Jeffrey Altman <jaltman@your-file-system.com>

src/WINNT/afsd/afsd_eventlog.c
src/WINNT/afsd/afsd_eventmessages.mc
src/WINNT/afsd/cm_callback.c
src/WINNT/afsd/cm_conn.c
src/WINNT/afsd/cm_conn.h
src/WINNT/afsd/cm_dcache.c
src/WINNT/afsd/cm_ioctl.c
src/WINNT/afsd/cm_vnodeops.c
src/WINNT/afsd/cm_volume.c
src/WINNT/afsrdr/user/RDRFunction.c

index 3b9d974..8b68e9d 100644 (file)
@@ -254,6 +254,7 @@ LogEvent(WORD wEventType, DWORD dwEventID, ...)
     case MSG_SERVER_REPORTS_VIO:
     case MSG_SERVER_REPORTS_VBUSY:
     case MSG_SERVER_REPORTS_VRESTARTING:
+    case MSG_SERVER_REPLIED_BAD_STATUS:
        wNumArgs = 3;
        lpArgs[0] = va_arg(listArgs, LPTSTR);
        StringCbPrintf(lpStrings[1],STRLEN,"%d",va_arg(listArgs,afs_int32));
index ba84be2..348da60 100644 (file)
@@ -454,4 +454,12 @@ Language=English
 Idle dead timeout when communicating with server %1.
 .
 
+MessageId=
+Severity=Warning
+Facility=System
+SymbolicName=MSG_SERVER_REPLIED_BAD_STATUS
+Language=English
+Server %1 replied with bad status info when accessing volume %2 in cell %3.  Data discarded by cache manager.
+.
+
 ;#endif /* __AFSD_EVENTMESSAGES_H_ 1 */
index 036fe89..9e23278 100644 (file)
@@ -1865,7 +1865,7 @@ long cm_GetCallback(cm_scache_t *scp, struct cm_user *userp,
                                      &afsStatus, &callback, &volSync);
             rx_PutConnection(rxconnp);
 
-        } while (cm_Analyze(connp, userp, reqp, &sfid, NULL, 0, &volSync, NULL,
+        } while (cm_Analyze(connp, userp, reqp, &sfid, NULL, 0, &afsStatus, &volSync, NULL,
                             &cbr, code));
         code = cm_MapRPCError(code, reqp);
         if (code)
index 195c4e1..0df8b37 100644 (file)
@@ -301,6 +301,7 @@ cm_Analyze(cm_conn_t *connp,
            struct cm_fid *fidp,
            cm_cell_t *cellp,
            afs_uint32 storeOp,
+           AFSFetchStatus *statusp,
            AFSVolSync *volSyncp,
            cm_serverRef_t * serversp,
            cm_callbackRequest_t *cbrp,
@@ -324,6 +325,7 @@ cm_Analyze(cm_conn_t *connp,
     int location_updated = 0;
     char *format;
     DWORD msgID;
+    int invalid_status = 0;
 
     osi_Log2(afsd_logp, "cm_Analyze connp 0x%p, code 0x%x",
              connp, errorCode);
@@ -359,6 +361,18 @@ cm_Analyze(cm_conn_t *connp,
     else
         timeLeft = 0x0FFFFFFF;
 
+    /*
+     * Similar to the UNIX cache manager, if the AFSFetchStatus info
+     * returned by the file server is invalid, consider the response
+     * as being equivalent to VBUSY so that another file server can
+     * be queried if there is one.  If there is no replica, then the
+     * request will fail.
+     */
+    if (errorCode == 0 && statusp && !cm_IsStatusValid(statusp)) {
+        invalid_status = 1;
+        errorCode = VBUSY;
+    }
+
     /* get a pointer to the cell */
     if (errorCode) {
         if (cellp == NULL && serverp)
@@ -601,8 +615,13 @@ cm_Analyze(cm_conn_t *connp,
 
             switch ( errorCode ) {
             case VBUSY:
-                msgID = MSG_SERVER_REPORTS_VBUSY;
-                format = "Server %s reported busy when accessing volume %d in cell %s.";
+                if (invalid_status) {
+                    msgID = MSG_SERVER_REPLIED_BAD_STATUS;
+                    format = "Server %s replied with bad status info when accessing volume %d in cell %s.  Data discarded by cache manager.";
+                } else {
+                    msgID = MSG_SERVER_REPORTS_VBUSY;
+                    format = "Server %s reported busy when accessing volume %d in cell %s.";
+                }
                 break;
             case VRESTARTING:
                 msgID = MSG_SERVER_REPORTS_VRESTARTING;
index 4a1a6ad..96bb098 100644 (file)
@@ -140,6 +140,7 @@ extern void cm_InitReq(cm_req_t *reqp);
 extern int cm_Analyze(cm_conn_t *connp, struct cm_user *up, struct cm_req *reqp,
                       struct cm_fid *fidp, struct cm_cell *cellp,
                       afs_uint32 storeOp,
+                      struct AFSFetchStatus *statusp,
                       struct AFSVolSync *volInfop,
                       cm_serverRef_t * serversp,
                       struct cm_callbackRequest *cbrp, long code);
index 6140240..4eb0085 100644 (file)
@@ -375,7 +375,7 @@ long cm_BufWrite(void *vscp, osi_hyper_t *offsetp, long length, long flags,
             osi_Log2(afsd_logp, "rx_EndCall converted 0x%x to 0x%x", code, code1);
             code = code1;
         }
-    } while (cm_Analyze(connp, userp, reqp, &scp->fid, NULL, 1, &volSync, NULL, NULL, code));
+    } while (cm_Analyze(connp, userp, reqp, &scp->fid, NULL, 1, &outStatus, &volSync, NULL, NULL, code));
 
     code = cm_MapRPCError(code, reqp);
 
@@ -564,7 +564,7 @@ long cm_StoreMini(cm_scache_t *scp, cm_user_t *userp, cm_req_t *reqp)
         /* prefer StoreData error over rx_EndCall error */
         if (code == 0 && code1 != 0)
             code = code1;
-    } while (cm_Analyze(connp, userp, reqp, &scp->fid, NULL, 1, &volSync, NULL, NULL, code));
+    } while (cm_Analyze(connp, userp, reqp, &scp->fid, NULL, 1, &outStatus, &volSync, NULL, NULL, code));
     code = cm_MapRPCError(code, reqp);
 
     /* now, clean up our state */
@@ -2174,7 +2174,7 @@ long cm_GetBuffer(cm_scache_t *scp, cm_buf_t *bufp, int *cpffp, cm_user_t *userp
             code = code1;
         osi_Log0(afsd_logp, "CALL FetchData DONE");
 
-    } while (cm_Analyze(connp, userp, reqp, &scp->fid, NULL, 0, &volSync, NULL, NULL, code));
+    } while (cm_Analyze(connp, userp, reqp, &scp->fid, NULL, 0, &afsStatus, &volSync, NULL, NULL, code));
 
   fetchingcompleted:
     code = cm_MapRPCError(code, reqp);
@@ -2558,7 +2558,7 @@ long cm_GetData(cm_scache_t *scp, osi_hyper_t *offsetp, char *datap, int data_le
             code = code1;
         osi_Log0(afsd_logp, "CALL FetchData DONE");
 
-    } while (cm_Analyze(connp, userp, reqp, &scp->fid, NULL, 0, &volSync, NULL, NULL, code));
+    } while (cm_Analyze(connp, userp, reqp, &scp->fid, NULL, 0, &afsStatus, &volSync, NULL, NULL, code));
 
   fetchingcompleted:
     code = cm_MapRPCError(code, reqp);
@@ -2782,7 +2782,7 @@ cm_VerifyStoreData(cm_bulkIO_t *biod, cm_scache_t *savedScp)
             code = code1;
         osi_Log0(afsd_logp, "CALL FetchData DONE");
 
-    } while (cm_Analyze(connp, userp, reqp, &scp->fid, NULL, 0, &volSync, NULL, NULL, code));
+    } while (cm_Analyze(connp, userp, reqp, &scp->fid, NULL, 0, &afsStatus, &volSync, NULL, NULL, code));
 
   fetchingcompleted:
     code = cm_MapRPCError(code, reqp);
index 4614a7f..55a4f73 100644 (file)
@@ -439,7 +439,7 @@ cm_IoctlGetACL(cm_ioctl_t *ioctlp, cm_user_t *userp, cm_scache_t *scp, cm_req_t
             code = RXAFS_FetchACL(rxconnp, &afid, &acl, &fileStatus, &volSync);
             rx_PutConnection(rxconnp);
 
-        } while (cm_Analyze(connp, userp, reqp, &scp->fid, NULL, 0, &volSync, NULL, NULL, code));
+        } while (cm_Analyze(connp, userp, reqp, &scp->fid, NULL, 0, &fileStatus, &volSync, NULL, NULL, code));
         code = cm_MapRPCError(code, reqp);
 
         if (code)
@@ -537,7 +537,7 @@ cm_IoctlSetACL(struct cm_ioctl *ioctlp, struct cm_user *userp, cm_scache_t *scp,
             code = RXAFS_StoreACL(rxconnp, &fid, &acl, &fileStatus, &volSync);
             rx_PutConnection(rxconnp);
 
-        } while (cm_Analyze(connp, userp, reqp, &scp->fid, NULL, 1, &volSync, NULL, NULL, code));
+        } while (cm_Analyze(connp, userp, reqp, &scp->fid, NULL, 1, &fileStatus, &volSync, NULL, NULL, code));
         code = cm_MapRPCError(code, reqp);
 
         /* invalidate cache info, since we just trashed the ACL cache */
@@ -710,7 +710,7 @@ cm_IoctlSetVolumeStatus(struct cm_ioctl *ioctlp, struct cm_user *userp, cm_scach
                                          &storeStat, volName, offLineMsg, motd);
             rx_PutConnection(rxconnp);
 
-        } while (cm_Analyze(tcp, userp, reqp, &scp->fid, NULL, 1, NULL, NULL, NULL, code));
+        } while (cm_Analyze(tcp, userp, reqp, &scp->fid, NULL, 1, NULL, NULL, NULL, NULL, code));
         code = cm_MapRPCError(code, reqp);
     }
 
@@ -801,7 +801,7 @@ cm_IoctlGetVolumeStatus(struct cm_ioctl *ioctlp, struct cm_user *userp, cm_scach
                                          &volStat, &Name, &OfflineMsg, &MOTD);
             rx_PutConnection(rxconnp);
 
-        } while (cm_Analyze(connp, userp, reqp, &vfid, NULL, 0, NULL, NULL, NULL, code));
+        } while (cm_Analyze(connp, userp, reqp, &vfid, NULL, 0, NULL, NULL, NULL, NULL, code));
         code = cm_MapRPCError(code, reqp);
 
         lock_ObtainWrite(&vscp->rw);
index eb12ee5..a5c3d6e 100644 (file)
@@ -1692,7 +1692,7 @@ long cm_Unlink(cm_scache_t *dscp, fschar_t *fnamep, clientchar_t * cnamep,
                                 &newDirStatus, &volSync);
         rx_PutConnection(rxconnp);
 
-    } while (cm_Analyze(connp, userp, reqp, &dscp->fid, NULL, 1, &volSync, NULL, NULL, code));
+    } while (cm_Analyze(connp, userp, reqp, &dscp->fid, NULL, 1, &newDirStatus, &volSync, NULL, NULL, code));
     code = cm_MapRPCError(code, reqp);
 
     if (code)
@@ -2496,7 +2496,7 @@ cm_TryBulkStatRPC(cm_scache_t *dscp, cm_bulkStat_t *bbp, cm_user_t *userp, cm_re
                         code = (&bbp->stats[0])->errorCode;
                 }
             }
-        } while (cm_Analyze(connp, userp, reqp, &tfid, NULL, 0, &volSync, NULL, &cbReq, code));
+        } while (cm_Analyze(connp, userp, reqp, &tfid, NULL, 0, &bbp->stats[0], &volSync, NULL, &cbReq, code));
         code = cm_MapRPCError(code, reqp);
 
         /*
@@ -2527,7 +2527,8 @@ cm_TryBulkStatRPC(cm_scache_t *dscp, cm_bulkStat_t *bbp, cm_user_t *userp, cm_re
 
             if (inlinebulk && (&bbp->stats[j])->errorCode) {
                 cm_req_t treq = *reqp;
-                cm_Analyze(NULL, userp, &treq, &tfid, NULL, 0, &volSync, NULL, &cbReq, (&bbp->stats[j])->errorCode);
+                cm_Analyze(NULL, userp, &treq, &tfid, NULL, 0, &bbp->stats[j], &volSync,
+                           NULL, &cbReq, (&bbp->stats[j])->errorCode);
                 switch ((&bbp->stats[j])->errorCode) {
                 case EACCES:
                 case UAEACCES:
@@ -2727,7 +2728,7 @@ cm_IsSpaceAvailable(cm_fid_t * fidp, osi_hyper_t *sizep, cm_user_t *userp, cm_re
                                              &volStat, &Name, &OfflineMsg, &MOTD);
                 rx_PutConnection(rxconnp);
 
-            } while (cm_Analyze(connp, userp, reqp, &vfid, NULL, 0, NULL, NULL, NULL, code));
+            } while (cm_Analyze(connp, userp, reqp, &vfid, NULL, 0, NULL, NULL, NULL, NULL, code));
             code = cm_MapRPCError(code, reqp);
         }
 
@@ -2917,7 +2918,7 @@ long cm_SetAttr(cm_scache_t *scp, cm_attr_t *attrp, cm_user_t *userp,
         rx_PutConnection(rxconnp);
 
     } while (cm_Analyze(connp, userp, reqp,
-                         &scp->fid, NULL, 1, &volSync, NULL, NULL, code));
+                         &scp->fid, NULL, 1, &afsOutStatus, &volSync, NULL, NULL, code));
     code = cm_MapRPCError(code, reqp);
 
     if (code)
@@ -3029,7 +3030,7 @@ long cm_Create(cm_scache_t *dscp, clientchar_t *cnamep, long flags, cm_attr_t *a
         rx_PutConnection(rxconnp);
 
     } while (cm_Analyze(connp, userp, reqp,
-                         &dscp->fid, NULL, 1, &volSync, NULL, &cbReq, code));
+                         &dscp->fid, NULL, 1, &updatedDirStatus, &volSync, NULL, &cbReq, code));
     code = cm_MapRPCError(code, reqp);
 
     if (code)
@@ -3221,7 +3222,7 @@ long cm_MakeDir(cm_scache_t *dscp, clientchar_t *cnamep, long flags, cm_attr_t *
         rx_PutConnection(rxconnp);
 
     } while (cm_Analyze(connp, userp, reqp,
-                        &dscp->fid, NULL, 1, &volSync, NULL, &cbReq, code));
+                        &dscp->fid, NULL, 1, &updatedDirStatus, &volSync, NULL, &cbReq, code));
     code = cm_MapRPCError(code, reqp);
 
     if (code)
@@ -3352,7 +3353,7 @@ long cm_Link(cm_scache_t *dscp, clientchar_t *cnamep, cm_scache_t *sscp, long fl
         rx_PutConnection(rxconnp);
         osi_Log1(afsd_logp,"  RXAFS_Link returns 0x%x", code);
 
-    } while (cm_Analyze(connp, userp, reqp, &dscp->fid, NULL, 1, &volSync, NULL, NULL, code));
+    } while (cm_Analyze(connp, userp, reqp, &dscp->fid, NULL, 1, &updatedDirStatus, &volSync, NULL, NULL, code));
 
     code = cm_MapRPCError(code, reqp);
 
@@ -3468,7 +3469,7 @@ long cm_SymLink(cm_scache_t *dscp, clientchar_t *cnamep, fschar_t *contentsp, lo
         rx_PutConnection(rxconnp);
 
     } while (cm_Analyze(connp, userp, reqp,
-                         &dscp->fid, NULL, 1, &volSync, NULL, NULL, code));
+                         &dscp->fid, NULL, 1, &updatedDirStatus, &volSync, NULL, NULL, code));
     code = cm_MapRPCError(code, reqp);
 
     if (code)
@@ -3625,7 +3626,7 @@ long cm_RemoveDir(cm_scache_t *dscp, fschar_t *fnamep, clientchar_t *cnamep, cm_
         rx_PutConnection(rxconnp);
 
     } while (cm_Analyze(connp, userp, reqp,
-                        &dscp->fid, NULL, 1, &volSync, NULL, NULL, code));
+                        &dscp->fid, NULL, 1, &updatedDirStatus, &volSync, NULL, NULL, code));
     code = cm_MapRPCErrorRmdir(code, reqp);
 
     if (code)
@@ -3971,7 +3972,7 @@ long cm_Rename(cm_scache_t *oldDscp, fschar_t *oldNamep, clientchar_t *cOldNamep
         rx_PutConnection(rxconnp);
 
     } while (cm_Analyze(connp, userp, reqp, &oldDscp->fid, NULL, 1,
-                         &volSync, NULL, NULL, code));
+                        &updatedOldDirStatus, &volSync, NULL, NULL, code));
     code = cm_MapRPCError(code, reqp);
 
     if (code)
@@ -4672,7 +4673,7 @@ long cm_IntSetLock(cm_scache_t * scp, cm_user_t * userp, int lockType,
                              &volSync);
         rx_PutConnection(rxconnp);
 
-    } while (cm_Analyze(connp, userp, reqp, &cfid, NULL, 1, &volSync,
+    } while (cm_Analyze(connp, userp, reqp, &cfid, NULL, 1, NULL, &volSync,
                         NULL, NULL, code));
 
     code = cm_MapRPCError(code, reqp);
@@ -4734,7 +4735,7 @@ long cm_IntReleaseLock(cm_scache_t * scp, cm_user_t * userp,
         code = RXAFS_ReleaseLock(rxconnp, &tfid, &volSync);
         rx_PutConnection(rxconnp);
 
-    } while (cm_Analyze(connp, userp, reqp, &cfid, NULL, 1, &volSync,
+    } while (cm_Analyze(connp, userp, reqp, &cfid, NULL, 1, NULL, &volSync,
                         NULL, NULL, code));
     code = cm_MapRPCError(code, reqp);
     if (code)
@@ -5728,7 +5729,7 @@ void cm_CheckLocks()
                         osi_Log1(afsd_logp, "   ExtendLock returns %d", code);
 
                     } while (cm_Analyze(connp, userp, &req,
-                                        &cfid, NULL, 1, &volSync, NULL, NULL,
+                                        &cfid, NULL, 1, NULL, &volSync, NULL, NULL,
                                         code));
 
                     code = cm_MapRPCError(code, &req);
index a63bd8f..45deb1a 100644 (file)
@@ -203,7 +203,7 @@ cm_GetEntryByName( struct cm_cell *cellp, const char *name,
             *methodp = 0;
         }
         rx_PutConnection(rxconnp);
-    } while (cm_Analyze(connp, userp, reqp, NULL, cellp, 0, NULL, cellp->vlServersp, NULL, code));
+    } while (cm_Analyze(connp, userp, reqp, NULL, cellp, 0, NULL, NULL, cellp->vlServersp, NULL, code));
     code = cm_MapVLRPCError(code, reqp);
     if ( code )
         osi_Log3(afsd_logp, "CALL VL_GetEntryByName{UNO} name %s:%s FAILURE, code 0x%x",
@@ -447,7 +447,7 @@ long cm_UpdateVolumeLocation(struct cm_cell *cellp, cm_user_t *userp, cm_req_t *
                         rxconnp = cm_GetRxConn(connp);
                         code = VL_GetAddrsU(rxconnp, &attrs, &uuid, &unique, &nentries, &addrs);
                         rx_PutConnection(rxconnp);
-                    } while (cm_Analyze(connp, userp, reqp, NULL, cellp, 0, NULL, cellp->vlServersp, NULL, code));
+                    } while (cm_Analyze(connp, userp, reqp, NULL, cellp, 0, NULL, NULL, cellp->vlServersp, NULL, code));
 
                     if ( code ) {
                         code = cm_MapVLRPCError(code, reqp);
@@ -1352,7 +1352,7 @@ cm_CheckOfflineVolumeState(cm_volume_t *volp, cm_vol_state_t *statep, afs_uint32
                             code = RXAFS_GetVolumeStatus(rxconnp, statep->ID,
                                                          &volStat, &Name, &OfflineMsg, &MOTD);
                             rx_PutConnection(rxconnp);
-                        } while (cm_Analyze(connp, cm_rootUserp, &req, &vfid, NULL, 0, NULL, NULL, NULL, code));
+                        } while (cm_Analyze(connp, cm_rootUserp, &req, &vfid, NULL, 0, NULL, NULL, NULL, NULL, code));
                         code = cm_MapRPCError(code, &req);
                     }
 
index 0c12007..d39bc96 100644 (file)
@@ -5046,7 +5046,7 @@ RDR_GetVolumeInfo( IN cm_user_t     *userp,
                                               &volStat, &Name, &OfflineMsg, &MOTD);
                 rx_PutConnection(rxconnp);
 
-            } while (cm_Analyze(connp, userp, &req, &scp->fid, NULL, 0, NULL, NULL, NULL, code));
+            } while (cm_Analyze(connp, userp, &req, &scp->fid, NULL, 0, NULL, NULL, NULL, NULL, code));
             code = cm_MapRPCError(code, &req);
         }
 
@@ -5222,7 +5222,7 @@ RDR_GetVolumeSizeInfo( IN cm_user_t     *userp,
                                               &volStat, &Name, &OfflineMsg, &MOTD);
                 rx_PutConnection(rxconnp);
 
-            } while (cm_Analyze(connp, userp, &req, &scp->fid, NULL, 0, NULL, NULL, NULL, code));
+            } while (cm_Analyze(connp, userp, &req, &scp->fid, NULL, 0, NULL, NULL, NULL, NULL, code));
             code = cm_MapRPCError(code, &req);
         }