You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@subversion.apache.org by bl...@apache.org on 2011/02/01 23:34:46 UTC

svn commit: r1066249 - /subversion/trunk/subversion/libsvn_subr/io.c

Author: blair
Date: Tue Feb  1 22:34:45 2011
New Revision: 1066249

URL: http://svn.apache.org/viewvc?rev=1066249&view=rev
Log:
Getting a lock on a file using fcntl(F_SETLKW) may also return an
EINTR, so in addition to retrying with sleeps if a EDEADLK is
returned, retry without sleeps if an EINTR is returned.

* subversion/libsvn_subr/io.c
  (RETRY_LOOP):
    Add another argument, a test if apr_sleep() should be called.
  (FILE_LOCK_RETRY_LOOP):
    Renamed from EDEADLK_RETRY_LOOP.
    Now always define FILE_LOCK_RETRY_LOOP that will retry and only
      define different versions of EDEADLK is available.
    Update all callers.
  (WIN32_RETRY_LOOP):
    Pass 1 as the new sleep test argument to RETRY_LOOP.

Modified:
    subversion/trunk/subversion/libsvn_subr/io.c

Modified: subversion/trunk/subversion/libsvn_subr/io.c
URL: http://svn.apache.org/viewvc/subversion/trunk/subversion/libsvn_subr/io.c?rev=1066249&r1=1066248&r2=1066249&view=diff
==============================================================================
--- subversion/trunk/subversion/libsvn_subr/io.c (original)
+++ subversion/trunk/subversion/libsvn_subr/io.c Tue Feb  1 22:34:45 2011
@@ -85,29 +85,38 @@
 #define RETRY_INITIAL_SLEEP 1000
 #define RETRY_MAX_SLEEP 128000
 
-#define RETRY_LOOP(err, expr, test)                                        \
+#define RETRY_LOOP(err, expr, retry_test, sleep_test)                      \
   do                                                                       \
     {                                                                      \
       apr_status_t os_err = APR_TO_OS_ERROR(err);                          \
       int sleep_count = RETRY_INITIAL_SLEEP;                               \
       int retries;                                                         \
       for (retries = 0;                                                    \
-           retries < RETRY_MAX_ATTEMPTS && (test);                         \
+           retries < RETRY_MAX_ATTEMPTS && (retry_test);                   \
            ++retries, os_err = APR_TO_OS_ERROR(err))                       \
         {                                                                  \
-          apr_sleep(sleep_count);                                          \
-          if (sleep_count < RETRY_MAX_SLEEP)                               \
-            sleep_count *= 2;                                              \
+          if (sleep_test)                                                  \
+            {                                                              \
+              apr_sleep(sleep_count);                                      \
+              if (sleep_count < RETRY_MAX_SLEEP)                           \
+                sleep_count *= 2;                                          \
+            }                                                              \
           (err) = (expr);                                                  \
         }                                                                  \
     }                                                                      \
   while (0)
 
 #if defined(EDEADLK) && APR_HAS_THREADS
-#define EDEADLK_RETRY_LOOP(err, expr)                                      \
-  RETRY_LOOP(err, expr, (os_err == EDEADLK))
+#define FILE_LOCK_RETRY_LOOP(err, expr)                                    \
+  RETRY_LOOP(err,                                                          \
+             expr,                                                         \
+             (APR_STATUS_IS_EINTR(err) || os_err == EDEADLK),              \
+             (!APR_STATUS_IS_EINTR(err)))
 #else
-#define EDEADLK_RETRY_LOOP(err, expr) ((void)0)
+  RETRY_LOOP(err,                                                          \
+             expr,                                                         \
+             (APR_STATUS_IS_EINTR(err)),                                   \
+             0)
 #endif
 
 #ifndef WIN32_RETRY_LOOP
@@ -115,7 +124,8 @@
 #define WIN32_RETRY_LOOP(err, expr)                                        \
   RETRY_LOOP(err, expr, (os_err == ERROR_ACCESS_DENIED                     \
                          || os_err == ERROR_SHARING_VIOLATION              \
-                         || os_err == ERROR_DIR_NOT_EMPTY))
+                         || os_err == ERROR_DIR_NOT_EMPTY),                \
+             1)
 #else
 #define WIN32_RETRY_LOOP(err, expr) ((void)0)
 #endif
@@ -1718,7 +1728,7 @@ svn_io_file_lock2(const char *lock_file,
      thread 2: try to get lock in B *** deadlock ***
 
      Retry for a while for the deadlock to clear. */
-  EDEADLK_RETRY_LOOP(apr_err, apr_file_lock(lockfile_handle, locktype));
+  FILE_LOCK_RETRY_LOOP(apr_err, apr_file_lock(lockfile_handle, locktype));
 
   if (apr_err)
     {