Whamcloud - gitweb
LU-2482 layout: introduce new layout for released files
[fs/lustre-release.git] / lustre / lov / lov_object.c
index 07ed284..e1f5b5d 100644 (file)
@@ -258,10 +258,25 @@ out:
         RETURN(result);
 }
 
+static int lov_init_released(const struct lu_env *env,
+                       struct lov_device *dev, struct lov_object *lov,
+                       const struct cl_object_conf *conf,
+                       union  lov_layout_state *state)
+{
+       struct lov_stripe_md *lsm = conf->u.coc_md->lsm;
+
+       LASSERT(lsm != NULL);
+       LASSERT(lsm_is_released(lsm));
+       LASSERT(lov->lo_lsm == NULL);
+
+       lov->lo_lsm = lsm_addref(lsm);
+       return 0;
+}
+
 static int lov_delete_empty(const struct lu_env *env, struct lov_object *lov,
                            union lov_layout_state *state)
 {
-       LASSERT(lov->lo_type == LLT_EMPTY);
+       LASSERT(lov->lo_type == LLT_EMPTY || lov->lo_type == LLT_RELEASED);
 
        lov_layout_wait(env, lov);
 
@@ -349,7 +364,7 @@ static int lov_delete_raid0(const struct lu_env *env, struct lov_object *lov,
 static void lov_fini_empty(const struct lu_env *env, struct lov_object *lov,
                            union lov_layout_state *state)
 {
-        LASSERT(lov->lo_type == LLT_EMPTY);
+       LASSERT(lov->lo_type == LLT_EMPTY || lov->lo_type == LLT_RELEASED);
 }
 
 static void lov_fini_raid0(const struct lu_env *env, struct lov_object *lov,
@@ -369,6 +384,15 @@ static void lov_fini_raid0(const struct lu_env *env, struct lov_object *lov,
        EXIT;
 }
 
+static void lov_fini_released(const struct lu_env *env, struct lov_object *lov,
+                               union lov_layout_state *state)
+{
+       ENTRY;
+       dump_lsm(D_INODE, lov->lo_lsm);
+       lov_free_memmd(&lov->lo_lsm);
+       EXIT;
+}
+
 static int lov_print_empty(const struct lu_env *env, void *cookie,
                            lu_printer_t p, const struct lu_object *o)
 {
@@ -400,6 +424,13 @@ static int lov_print_raid0(const struct lu_env *env, void *cookie,
         return 0;
 }
 
+static int lov_print_released(const struct lu_env *env, void *cookie,
+                               lu_printer_t p, const struct lu_object *o)
+{
+       (*p)(env, cookie, "released\n");
+       return 0;
+}
+
 /**
  * Implements cl_object_operations::coo_attr_get() method for an object
  * without stripes (LLT_EMPTY layout type).
@@ -503,10 +534,20 @@ const static struct lov_layout_operations lov_dispatch[] = {
                 .llo_lock_init = lov_lock_init_raid0,
                 .llo_io_init   = lov_io_init_raid0,
                 .llo_getattr   = lov_attr_get_raid0
+       },
+        [LLT_RELEASED] = {
+                .llo_init      = lov_init_released,
+                .llo_delete    = lov_delete_empty,
+                .llo_fini      = lov_fini_released,
+                .llo_install   = lov_install_empty,
+                .llo_print     = lov_print_released,
+                .llo_page_init = lov_page_init_empty,
+                .llo_lock_init = lov_lock_init_empty,
+                .llo_io_init   = lov_io_init_released,
+                .llo_getattr   = lov_attr_get_empty
         }
 };
 
-
 /**
  * Performs a double-dispatch based on the layout type of an object.
  */
@@ -520,6 +561,18 @@ const static struct lov_layout_operations lov_dispatch[] = {
         lov_dispatch[__llt].op(__VA_ARGS__);                            \
 })
 
+/**
+ * Return lov_layout_type associated with a given lsm
+ */
+enum lov_layout_type lov_type(struct lov_stripe_md *lsm)
+{
+       if (lsm == NULL)
+               return LLT_EMPTY;
+       if (lsm_is_released(lsm))
+               return LLT_RELEASED;
+       return LLT_RAID0;
+}
+
 static inline void lov_conf_freeze(struct lov_object *lov)
 {
        if (lov->lo_owner != cfs_current())
@@ -612,8 +665,8 @@ static int lov_layout_change(const struct lu_env *unused,
 
        LASSERT(0 <= lov->lo_type && lov->lo_type < ARRAY_SIZE(lov_dispatch));
 
-       if (conf->u.coc_md != NULL && conf->u.coc_md->lsm != NULL)
-               llt = LLT_RAID0; /* only raid0 is supported. */
+       if (conf->u.coc_md != NULL)
+               llt = lov_type(conf->u.coc_md->lsm);
        LASSERT(0 <= llt && llt < ARRAY_SIZE(lov_dispatch));
 
        cookie = cl_env_reenter();
@@ -658,7 +711,6 @@ static int lov_layout_change(const struct lu_env *unused,
  * Lov object operations.
  *
  */
-
 int lov_object_init(const struct lu_env *env, struct lu_object *obj,
                     const struct lu_object_conf *conf)
 {
@@ -677,7 +729,7 @@ int lov_object_init(const struct lu_env *env, struct lu_object *obj,
        cl_object_page_init(lu2cl(obj), sizeof(struct lov_page));
 
         /* no locking is necessary, as object is being created */
-        lov->lo_type = cconf->u.coc_md->lsm != NULL ? LLT_RAID0 : LLT_EMPTY;
+       lov->lo_type = lov_type(cconf->u.coc_md->lsm);
         ops = &lov_dispatch[lov->lo_type];
         result = ops->llo_init(env, dev, lov, cconf, set);
         if (result == 0)
@@ -688,9 +740,9 @@ int lov_object_init(const struct lu_env *env, struct lu_object *obj,
 static int lov_conf_set(const struct lu_env *env, struct cl_object *obj,
                         const struct cl_object_conf *conf)
 {
-       struct lov_stripe_md *lsm = NULL;
-       struct lov_object *lov = cl2lov(obj);
-       int result = 0;
+       struct lov_stripe_md    *lsm = NULL;
+       struct lov_object       *lov = cl2lov(obj);
+       int                      result = 0;
        ENTRY;
 
        lov_conf_lock(lov);
@@ -928,6 +980,7 @@ int lov_read_and_clear_async_rc(struct cl_object *clob)
                                loi->loi_ar.ar_rc = 0;
                        }
                }
+               case LLT_RELEASED:
                case LLT_EMPTY:
                        break;
                default: