Commit 2f18d466 authored by Ilya Dryomov's avatar Ilya Dryomov

rbd: refactor rbd_wait_state_locked()

In preparation for lock_timeout option, make rbd_wait_state_locked()
return error codes.
Signed-off-by: default avatarIlya Dryomov <idryomov@gmail.com>
parent 60cc43fc
...@@ -3533,9 +3533,21 @@ static int rbd_obj_method_sync(struct rbd_device *rbd_dev, ...@@ -3533,9 +3533,21 @@ static int rbd_obj_method_sync(struct rbd_device *rbd_dev,
/* /*
* lock_rwsem must be held for read * lock_rwsem must be held for read
*/ */
static void rbd_wait_state_locked(struct rbd_device *rbd_dev) static int rbd_wait_state_locked(struct rbd_device *rbd_dev, bool may_acquire)
{ {
DEFINE_WAIT(wait); DEFINE_WAIT(wait);
int ret = 0;
if (test_bit(RBD_DEV_FLAG_BLACKLISTED, &rbd_dev->flags))
return -EBLACKLISTED;
if (rbd_dev->lock_state == RBD_LOCK_STATE_LOCKED)
return 0;
if (!may_acquire) {
rbd_warn(rbd_dev, "exclusive lock required");
return -EROFS;
}
do { do {
/* /*
...@@ -3549,10 +3561,14 @@ static void rbd_wait_state_locked(struct rbd_device *rbd_dev) ...@@ -3549,10 +3561,14 @@ static void rbd_wait_state_locked(struct rbd_device *rbd_dev)
up_read(&rbd_dev->lock_rwsem); up_read(&rbd_dev->lock_rwsem);
schedule(); schedule();
down_read(&rbd_dev->lock_rwsem); down_read(&rbd_dev->lock_rwsem);
} while (rbd_dev->lock_state != RBD_LOCK_STATE_LOCKED && if (test_bit(RBD_DEV_FLAG_BLACKLISTED, &rbd_dev->flags)) {
!test_bit(RBD_DEV_FLAG_BLACKLISTED, &rbd_dev->flags)); ret = -EBLACKLISTED;
break;
}
} while (rbd_dev->lock_state != RBD_LOCK_STATE_LOCKED);
finish_wait(&rbd_dev->lock_waitq, &wait); finish_wait(&rbd_dev->lock_waitq, &wait);
return ret;
} }
static void rbd_queue_workfn(struct work_struct *work) static void rbd_queue_workfn(struct work_struct *work)
...@@ -3638,19 +3654,10 @@ static void rbd_queue_workfn(struct work_struct *work) ...@@ -3638,19 +3654,10 @@ static void rbd_queue_workfn(struct work_struct *work)
(op_type != OBJ_OP_READ || rbd_dev->opts->lock_on_read); (op_type != OBJ_OP_READ || rbd_dev->opts->lock_on_read);
if (must_be_locked) { if (must_be_locked) {
down_read(&rbd_dev->lock_rwsem); down_read(&rbd_dev->lock_rwsem);
if (rbd_dev->lock_state != RBD_LOCK_STATE_LOCKED && result = rbd_wait_state_locked(rbd_dev,
!test_bit(RBD_DEV_FLAG_BLACKLISTED, &rbd_dev->flags)) { !rbd_dev->opts->exclusive);
if (rbd_dev->opts->exclusive) { if (result)
rbd_warn(rbd_dev, "exclusive lock required");
result = -EROFS;
goto err_unlock;
}
rbd_wait_state_locked(rbd_dev);
}
if (test_bit(RBD_DEV_FLAG_BLACKLISTED, &rbd_dev->flags)) {
result = -EBLACKLISTED;
goto err_unlock; goto err_unlock;
}
} }
img_request = rbd_img_request_create(rbd_dev, op_type, snapc); img_request = rbd_img_request_create(rbd_dev, op_type, snapc);
...@@ -5216,6 +5223,8 @@ static void rbd_dev_image_unlock(struct rbd_device *rbd_dev) ...@@ -5216,6 +5223,8 @@ static void rbd_dev_image_unlock(struct rbd_device *rbd_dev)
static int rbd_add_acquire_lock(struct rbd_device *rbd_dev) static int rbd_add_acquire_lock(struct rbd_device *rbd_dev)
{ {
int ret;
if (!(rbd_dev->header.features & RBD_FEATURE_EXCLUSIVE_LOCK)) { if (!(rbd_dev->header.features & RBD_FEATURE_EXCLUSIVE_LOCK)) {
rbd_warn(rbd_dev, "exclusive-lock feature is not enabled"); rbd_warn(rbd_dev, "exclusive-lock feature is not enabled");
return -EINVAL; return -EINVAL;
...@@ -5223,9 +5232,9 @@ static int rbd_add_acquire_lock(struct rbd_device *rbd_dev) ...@@ -5223,9 +5232,9 @@ static int rbd_add_acquire_lock(struct rbd_device *rbd_dev)
/* FIXME: "rbd map --exclusive" should be in interruptible */ /* FIXME: "rbd map --exclusive" should be in interruptible */
down_read(&rbd_dev->lock_rwsem); down_read(&rbd_dev->lock_rwsem);
rbd_wait_state_locked(rbd_dev); ret = rbd_wait_state_locked(rbd_dev, true);
up_read(&rbd_dev->lock_rwsem); up_read(&rbd_dev->lock_rwsem);
if (test_bit(RBD_DEV_FLAG_BLACKLISTED, &rbd_dev->flags)) { if (ret) {
rbd_warn(rbd_dev, "failed to acquire exclusive lock"); rbd_warn(rbd_dev, "failed to acquire exclusive lock");
return -EROFS; return -EROFS;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment