Whamcloud - gitweb
Branch HEAD
[fs/lustre-release.git] / lustre / osc / osc_create.c
index d79be2f..99dd705 100644 (file)
@@ -81,8 +81,14 @@ static int osc_interpret_create(struct ptlrpc_request *req, void *data, int rc)
                 spin_unlock(&oscc->oscc_lock);
                 break;
         }
+        case -EAGAIN:
+                /* valid race delorphan vs create, or somthing after resend */
+                spin_unlock(&oscc->oscc_lock);
+                DEBUG_REQ(D_INODE, req, "Got EGAIN - resend \n");
+                break;
         case -ENOSPC:
-        case -EROFS: {
+        case -EROFS: 
+        case -EFBIG: {
                 oscc->oscc_flags |= OSCC_FLAG_NOSPC;
                 if (body && rc == -ENOSPC) {
                         oscc->oscc_grow_count = OST_MIN_PRECREATE;
@@ -125,9 +131,16 @@ static int oscc_internal_create(struct osc_creator *oscc)
         int size[] = { sizeof(struct ptlrpc_body), sizeof(*body) };
         ENTRY;
 
-        spin_lock(&oscc->oscc_lock);
+        LASSERT_SPIN_LOCKED(&oscc->oscc_lock);
+
+        if (oscc->oscc_flags & OSCC_FLAG_CREATING ||
+            oscc->oscc_flags & OSCC_FLAG_RECOVERING) {
+                spin_unlock(&oscc->oscc_lock);
+                RETURN(0);
+        }
+
         if (oscc->oscc_grow_count < OST_MAX_PRECREATE &&
-            !(oscc->oscc_flags & (OSCC_FLAG_LOW | OSCC_FLAG_RECOVERING)) &&
+            ((oscc->oscc_flags & OSCC_FLAG_LOW) == 0) &&
             (__s64)(oscc->oscc_last_id - oscc->oscc_next_id) <=
                    (oscc->oscc_grow_count / 4 + 1)) {
                 oscc->oscc_flags |= OSCC_FLAG_LOW;
@@ -137,11 +150,6 @@ static int oscc_internal_create(struct osc_creator *oscc)
         if (oscc->oscc_grow_count > OST_MAX_PRECREATE / 2)
                 oscc->oscc_grow_count = OST_MAX_PRECREATE / 2;
 
-        if (oscc->oscc_flags & OSCC_FLAG_CREATING ||
-            oscc->oscc_flags & OSCC_FLAG_RECOVERING) {
-                spin_unlock(&oscc->oscc_lock);
-                RETURN(0);
-        }
         oscc->oscc_flags |= OSCC_FLAG_CREATING;
         spin_unlock(&oscc->oscc_lock);
 
@@ -181,10 +189,12 @@ static int oscc_has_objects(struct osc_creator *oscc, int count)
         int have_objs;
         spin_lock(&oscc->oscc_lock);
         have_objs = ((__s64)(oscc->oscc_last_id - oscc->oscc_next_id) >= count);
-        spin_unlock(&oscc->oscc_lock);
 
-        if (!have_objs)
+        if (!have_objs) {
                 oscc_internal_create(oscc);
+        } else {
+                spin_unlock(&oscc->oscc_lock);
+        }
 
         return have_objs;
 }
@@ -248,7 +258,7 @@ int oscc_recovering(struct osc_creator *oscc)
             a potentially very long time
      1000 : unusable
  */
-int osc_precreate(struct obd_export *exp, int need_create)
+int osc_precreate(struct obd_export *exp)
 {
         struct osc_creator *oscc = &exp->exp_obd->u.cli.cl_oscc;
         struct obd_import *imp = exp->exp_imp_reverse;
@@ -272,13 +282,11 @@ int osc_precreate(struct obd_export *exp, int need_create)
                         spin_unlock(&oscc->oscc_lock);
                         RETURN(2);
                 }
-                spin_unlock(&oscc->oscc_lock);
-
-                if (oscc->oscc_flags & OSCC_FLAG_CREATING)
-                        RETURN(1);
 
-                if (!need_create)
+                if (oscc->oscc_flags & OSCC_FLAG_CREATING) {
+                        spin_unlock(&oscc->oscc_lock);
                         RETURN(1);
+                }
 
                 oscc_internal_create(oscc);
                 RETURN(1);
@@ -320,6 +328,9 @@ int osc_create(struct obd_export *exp, struct obdo *oa,
                         RETURN(0);
                 }
                 oscc->oscc_flags |= OSCC_FLAG_SYNC_IN_PROGRESS;
+                /* seting flag LOW we prevent extra grow precreate size
+                 * and enforce use last assigned size */
+                oscc->oscc_flags |= OSCC_FLAG_LOW;
                 spin_unlock(&oscc->oscc_lock);
                 CDEBUG(D_HA, "%s: oscc recovery started - delete to "LPU64"\n",
                        oscc->oscc_obd->obd_name, oscc->oscc_next_id - 1);