block/rnbd-srv: Remove force_close file after holding a lock
authorGioh Kim <gi-oh.kim@cloud.ionos.com>
Mon, 19 Apr 2021 07:37:13 +0000 (09:37 +0200)
committerJens Axboe <axboe@kernel.dk>
Tue, 20 Apr 2021 14:59:04 +0000 (08:59 -0600)
We changed the rnbd_srv_sess_dev_force_close to use try-lock
because rnbd_srv_sess_dev_force_close and process_msg_close
can generate a deadlock.

Now rnbd_srv_sess_dev_force_close would do nothing
if it fails to get the lock. So removing the force_close
file should be moved to after the lock. Or the force_close
file is removed but the others are not removed.

Signed-off-by: Gioh Kim <gi-oh.kim@ionos.com>
Signed-off-by: Md Haris Iqbal <haris.iqbal@ionos.com>
Signed-off-by: Jack Wang <jinpu.wang@ionos.com>
Link: https://lore.kernel.org/r/20210419073722.15351-11-gi-oh.kim@ionos.com
Signed-off-by: Jens Axboe <axboe@kernel.dk>
drivers/block/rnbd/rnbd-srv-sysfs.c
drivers/block/rnbd/rnbd-srv.c
drivers/block/rnbd/rnbd-srv.h

index 05ffe48..acf5fce 100644 (file)
@@ -147,10 +147,7 @@ static ssize_t rnbd_srv_dev_session_force_close_store(struct kobject *kobj,
        }
 
        rnbd_srv_info(sess_dev, "force close requested\n");
-
-       /* first remove sysfs itself to avoid deadlock */
-       sysfs_remove_file_self(&sess_dev->kobj, &attr->attr);
-       rnbd_srv_sess_dev_force_close(sess_dev);
+       rnbd_srv_sess_dev_force_close(sess_dev, attr);
 
        return count;
 }
index 1549a63..a9bb414 100644 (file)
@@ -329,7 +329,8 @@ static int rnbd_srv_link_ev(struct rtrs_srv *rtrs,
        }
 }
 
-void rnbd_srv_sess_dev_force_close(struct rnbd_srv_sess_dev *sess_dev)
+void rnbd_srv_sess_dev_force_close(struct rnbd_srv_sess_dev *sess_dev,
+                                  struct kobj_attribute *attr)
 {
        struct rnbd_srv_session *sess = sess_dev->sess;
 
@@ -337,6 +338,8 @@ void rnbd_srv_sess_dev_force_close(struct rnbd_srv_sess_dev *sess_dev)
        /* It is already started to close by client's close message. */
        if (!mutex_trylock(&sess->lock))
                return;
+       /* first remove sysfs itself to avoid deadlock */
+       sysfs_remove_file_self(&sess_dev->kobj, &attr->attr);
        rnbd_srv_destroy_dev_session_sysfs(sess_dev);
        mutex_unlock(&sess->lock);
 }
index b157371..98ddc31 100644 (file)
@@ -64,7 +64,8 @@ struct rnbd_srv_sess_dev {
        enum rnbd_access_mode           access_mode;
 };
 
-void rnbd_srv_sess_dev_force_close(struct rnbd_srv_sess_dev *sess_dev);
+void rnbd_srv_sess_dev_force_close(struct rnbd_srv_sess_dev *sess_dev,
+                                  struct kobj_attribute *attr);
 /* rnbd-srv-sysfs.c */
 
 int rnbd_srv_create_dev_sysfs(struct rnbd_srv_dev *dev,