blk-mq: bitmap tag: fix races in bt_get() function
This update fixes few issues in bt_get() function: - list_empty(&wait.task_list) check is not protected; - was_empty check is always true which results in *every* thread entering the loop resets bt_wait_state::wait_cnt counter rather than every bt->wake_cnt'th thread; - 'bt_wait_state::wait_cnt' counter update is redundant, since it also gets reset in bt_clear_tag() function; Cc: Christoph Hellwig <hch@infradead.org> Cc: Ming Lei <tom.leiming@gmail.com> Cc: Jens Axboe <axboe@kernel.dk> Signed-off-by: Alexander Gordeev <agordeev@redhat.com> Signed-off-by: Jens Axboe <axboe@fb.com>
This commit is contained in:
parent
2971c35f35
commit
86fb5c56cf
|
@ -248,18 +248,12 @@ static int bt_get(struct blk_mq_alloc_data *data,
|
|||
|
||||
bs = bt_wait_ptr(bt, hctx);
|
||||
do {
|
||||
bool was_empty;
|
||||
|
||||
was_empty = list_empty(&wait.task_list);
|
||||
prepare_to_wait(&bs->wait, &wait, TASK_UNINTERRUPTIBLE);
|
||||
|
||||
tag = __bt_get(hctx, bt, last_tag);
|
||||
if (tag != -1)
|
||||
break;
|
||||
|
||||
if (was_empty)
|
||||
atomic_set(&bs->wait_cnt, bt->wake_cnt);
|
||||
|
||||
blk_mq_put_ctx(data->ctx);
|
||||
|
||||
io_schedule();
|
||||
|
@ -519,10 +513,13 @@ static int bt_alloc(struct blk_mq_bitmap_tags *bt, unsigned int depth,
|
|||
return -ENOMEM;
|
||||
}
|
||||
|
||||
for (i = 0; i < BT_WAIT_QUEUES; i++)
|
||||
init_waitqueue_head(&bt->bs[i].wait);
|
||||
|
||||
bt_update_count(bt, depth);
|
||||
|
||||
for (i = 0; i < BT_WAIT_QUEUES; i++) {
|
||||
init_waitqueue_head(&bt->bs[i].wait);
|
||||
atomic_set(&bt->bs[i].wait_cnt, bt->wake_cnt);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue