Whamcloud - gitweb
LU-13729 osd-ldiskfs: race access to iam_formats during setup 13/39213/2
authorWang Shilong <wshilong@ddn.com>
Tue, 30 Jun 2020 01:12:48 +0000 (09:12 +0800)
committerOleg Drokin <green@whamcloud.com>
Fri, 10 Jul 2020 16:53:13 +0000 (16:53 +0000)
It might be possible during OST mounting, two targets reach
iam_format_guess() at the same time, if @initialized is 0,
they both access iam_lxx_format_init(), however list operation
inside is not protected by any locking which cause list corruptions
finally.

We could fix this by doing formats registration in module init,
since there are only two formats, just remove pointless list.

Signed-off-by: Wang Shilong <wshilong@ddn.com>
Change-Id: I6dd5a4d1297792b47fb4b94052465a7e0f9123aa
Reviewed-on: https://review.whamcloud.com/39213
Tested-by: jenkins <devops@whamcloud.com>
Reviewed-by: Andreas Dilger <adilger@whamcloud.com>
Reviewed-by: John L. Hammond <jhammond@whamcloud.com>
Reviewed-by: Yingjin Qian <qian@ddn.com>
Tested-by: Maloo <maloo@whamcloud.com>
Reviewed-by: Oleg Drokin <green@whamcloud.com>
lustre/osd-ldiskfs/osd_iam.c
lustre/osd-ldiskfs/osd_iam.h
lustre/osd-ldiskfs/osd_iam_lfix.c
lustre/osd-ldiskfs/osd_iam_lvar.c

index a699f02..56881d6 100644 (file)
 
 #include <ldiskfs/acl.h>
 
-/*
- * List of all registered formats.
- *
- * No locking. Callers synchronize.
- */
-static LIST_HEAD(iam_formats);
-
-void iam_format_register(struct iam_format *fmt)
-{
-       list_add(&fmt->if_linkage, &iam_formats);
-}
-
 static struct buffer_head *
 iam_load_idle_blocks(struct iam_container *c, iam_ptr_t blk)
 {
@@ -205,27 +193,10 @@ iam_load_idle_blocks(struct iam_container *c, iam_ptr_t blk)
 static int iam_format_guess(struct iam_container *c)
 {
        int result;
-       struct iam_format *fmt;
-
-       /*
-        * XXX temporary initialization hook.
-        */
-       {
-               static int initialized = 0;
-
-               if (!initialized) {
-                       iam_lvar_format_init();
-                       iam_lfix_format_init();
-                       initialized = 1;
-               }
-       }
 
-       result = -ENOENT;
-       list_for_each_entry(fmt, &iam_formats, if_linkage) {
-               result = fmt->if_guess(c);
-               if (result == 0)
-                       break;
-       }
+       result = iam_lvar_guess(c);
+       if (result)
+               result = iam_lfix_guess(c);
 
        if (result == 0) {
                struct buffer_head *bh;
index b4ee34d..15d3ede 100644 (file)
@@ -1069,31 +1069,12 @@ struct iam_leaf_operations *iam_leaf_ops(const struct iam_leaf *leaf);
 int iam_node_read(struct iam_container *c, iam_ptr_t ptr,
                   handle_t *h, struct buffer_head **bh);
 
-/*
- * Container format.
- */
-struct iam_format {
-        /*
-         * Method called to recognize container format. Should return true iff
-         * container @c conforms to this format. This method may do IO to read
-         * container pages.
-         *
-         * If container is recognized, this method sets operation vectors
-         * ->id_ops and ->id_leaf_ops in container description (c->ic_descr),
-         * and fills other description fields.
-         */
-        int (*if_guess)(struct iam_container *c);
-        /*
-         * Linkage into global list of container formats.
-         */
-       struct list_head if_linkage;
-};
-
-void iam_format_register(struct iam_format *fmt);
 int iam_root_limit(int rootgap, int blocksize, int size);
 
 void iam_lfix_format_init(void);
 void iam_lvar_format_init(void);
+int iam_lfix_guess(struct iam_container *c);
+int iam_lvar_guess(struct iam_container *c);
 void iam_htree_format_init(void);
 
 int iam_lfix_create(struct inode *obj,
index ef1906b..c6a73cf 100644 (file)
@@ -672,7 +672,7 @@ static struct iam_operations iam_lfix_ops = {
        .id_name        = "lfix"
 };
 
-static int iam_lfix_guess(struct iam_container *c)
+int iam_lfix_guess(struct iam_container *c)
 {
        int result;
        struct buffer_head *bh;
@@ -704,15 +704,6 @@ static int iam_lfix_guess(struct iam_container *c)
        return result;
 }
 
-static struct iam_format iam_lfix_format = {
-       .if_guess = iam_lfix_guess
-};
-
-void iam_lfix_format_init(void)
-{
-       iam_format_register(&iam_lfix_format);
-}
-
 /*
  * Debugging aid.
  */
index 1612f20..2636934 100644 (file)
@@ -1057,7 +1057,7 @@ static struct iam_operations lvar_ops = {
        .id_name        = "lvar"
 };
 
-static int lvar_guess(struct iam_container *c)
+int iam_lvar_guess(struct iam_container *c)
 {
        int result;
        struct buffer_head *bh;
@@ -1089,13 +1089,3 @@ static int lvar_guess(struct iam_container *c)
        }
        return result;
 }
-
-static struct iam_format lvar_format = {
-       .if_guess = lvar_guess
-};
-
-void iam_lvar_format_init(void)
-{
-       iam_format_register(&lvar_format);
-}
-