Skip to content

Commit 4b6c093

Browse files
committed
Merge tag 'block-5.9-2020-08-14' of git://git.kernel.dk/linux-block
Pull block fixes from Jens Axboe: "A few fixes on the block side of things: - Discard granularity fix (Coly) - rnbd cleanups (Guoqing) - md error handling fix (Dan) - md sysfs fix (Junxiao) - Fix flush request accounting, which caused an IO slowdown for some configurations (Ming) - Properly propagate loop flag for partition scanning (Lennart)" * tag 'block-5.9-2020-08-14' of git://git.kernel.dk/linux-block: block: fix double account of flush request's driver tag loop: unset GENHD_FL_NO_PART_SCAN on LOOP_CONFIGURE rnbd: no need to set bi_end_io in rnbd_bio_map_kern rnbd: remove rnbd_dev_submit_io md-cluster: Fix potential error pointer dereference in resize_bitmaps() block: check queue's limits.discard_granularity in __blkdev_issue_discard() md: get sysfs entry after redundancy attr group create
2 parents d84835b + c1e2b84 commit 4b6c093

File tree

8 files changed

+62
-66
lines changed

8 files changed

+62
-66
lines changed

block/blk-flush.c

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -308,9 +308,16 @@ static void blk_kick_flush(struct request_queue *q, struct blk_flush_queue *fq,
308308
flush_rq->mq_ctx = first_rq->mq_ctx;
309309
flush_rq->mq_hctx = first_rq->mq_hctx;
310310

311-
if (!q->elevator)
311+
if (!q->elevator) {
312312
flush_rq->tag = first_rq->tag;
313-
else
313+
314+
/*
315+
* We borrow data request's driver tag, so have to mark
316+
* this flush request as INFLIGHT for avoiding double
317+
* account of this driver tag
318+
*/
319+
flush_rq->rq_flags |= RQF_MQ_INFLIGHT;
320+
} else
314321
flush_rq->internal_tag = first_rq->internal_tag;
315322

316323
flush_rq->cmd_flags = REQ_OP_FLUSH | REQ_PREFLUSH;

block/blk-lib.c

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,15 @@ int __blkdev_issue_discard(struct block_device *bdev, sector_t sector,
4747
op = REQ_OP_DISCARD;
4848
}
4949

50+
/* In case the discard granularity isn't set by buggy device driver */
51+
if (WARN_ON_ONCE(!q->limits.discard_granularity)) {
52+
char dev_name[BDEVNAME_SIZE];
53+
54+
bdevname(bdev, dev_name);
55+
pr_err_ratelimited("%s: Error: discard_granularity is 0.\n", dev_name);
56+
return -EOPNOTSUPP;
57+
}
58+
5059
bs_mask = (bdev_logical_block_size(bdev) >> 9) - 1;
5160
if ((sector | nr_sects) & bs_mask)
5261
return -EINVAL;

drivers/block/loop.c

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1171,6 +1171,8 @@ static int loop_configure(struct loop_device *lo, fmode_t mode,
11711171
if (part_shift)
11721172
lo->lo_flags |= LO_FLAGS_PARTSCAN;
11731173
partscan = lo->lo_flags & LO_FLAGS_PARTSCAN;
1174+
if (partscan)
1175+
lo->lo_disk->flags &= ~GENHD_FL_NO_PART_SCAN;
11741176

11751177
/* Grab the block_device to prevent its destruction after we
11761178
* put /dev/loopXX inode. Later in __loop_clr_fd() we bdput(bdev).

drivers/block/rnbd/rnbd-srv-dev.c

Lines changed: 3 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -45,7 +45,7 @@ void rnbd_dev_close(struct rnbd_dev *dev)
4545
kfree(dev);
4646
}
4747

48-
static void rnbd_dev_bi_end_io(struct bio *bio)
48+
void rnbd_dev_bi_end_io(struct bio *bio)
4949
{
5050
struct rnbd_dev_blk_io *io = bio->bi_private;
5151

@@ -63,8 +63,8 @@ static void rnbd_dev_bi_end_io(struct bio *bio)
6363
* Map the kernel address into a bio suitable for io to a block
6464
* device. Returns an error pointer in case of error.
6565
*/
66-
static struct bio *rnbd_bio_map_kern(void *data, struct bio_set *bs,
67-
unsigned int len, gfp_t gfp_mask)
66+
struct bio *rnbd_bio_map_kern(void *data, struct bio_set *bs,
67+
unsigned int len, gfp_t gfp_mask)
6868
{
6969
unsigned long kaddr = (unsigned long)data;
7070
unsigned long end = (kaddr + len + PAGE_SIZE - 1) >> PAGE_SHIFT;
@@ -99,36 +99,5 @@ static struct bio *rnbd_bio_map_kern(void *data, struct bio_set *bs,
9999
offset = 0;
100100
}
101101

102-
bio->bi_end_io = bio_put;
103102
return bio;
104103
}
105-
106-
int rnbd_dev_submit_io(struct rnbd_dev *dev, sector_t sector, void *data,
107-
size_t len, u32 bi_size, enum rnbd_io_flags flags,
108-
short prio, void *priv)
109-
{
110-
struct rnbd_dev_blk_io *io;
111-
struct bio *bio;
112-
113-
/* Generate bio with pages pointing to the rdma buffer */
114-
bio = rnbd_bio_map_kern(data, dev->ibd_bio_set, len, GFP_KERNEL);
115-
if (IS_ERR(bio))
116-
return PTR_ERR(bio);
117-
118-
io = container_of(bio, struct rnbd_dev_blk_io, bio);
119-
120-
io->dev = dev;
121-
io->priv = priv;
122-
123-
bio->bi_end_io = rnbd_dev_bi_end_io;
124-
bio->bi_private = io;
125-
bio->bi_opf = rnbd_to_bio_flags(flags);
126-
bio->bi_iter.bi_sector = sector;
127-
bio->bi_iter.bi_size = bi_size;
128-
bio_set_prio(bio, prio);
129-
bio_set_dev(bio, dev->bdev);
130-
131-
submit_bio(bio);
132-
133-
return 0;
134-
}

drivers/block/rnbd/rnbd-srv-dev.h

Lines changed: 5 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,11 @@ void rnbd_dev_close(struct rnbd_dev *dev);
4141

4242
void rnbd_endio(void *priv, int error);
4343

44+
void rnbd_dev_bi_end_io(struct bio *bio);
45+
46+
struct bio *rnbd_bio_map_kern(void *data, struct bio_set *bs,
47+
unsigned int len, gfp_t gfp_mask);
48+
4449
static inline int rnbd_dev_get_max_segs(const struct rnbd_dev *dev)
4550
{
4651
return queue_max_segments(bdev_get_queue(dev->bdev));
@@ -75,18 +80,4 @@ static inline int rnbd_dev_get_discard_alignment(const struct rnbd_dev *dev)
7580
return bdev_get_queue(dev->bdev)->limits.discard_alignment;
7681
}
7782

78-
/**
79-
* rnbd_dev_submit_io() - Submit an I/O to the disk
80-
* @dev: device to that the I/O is submitted
81-
* @sector: address to read/write data to
82-
* @data: I/O data to write or buffer to read I/O date into
83-
* @len: length of @data
84-
* @bi_size: Amount of data that will be read/written
85-
* @prio: IO priority
86-
* @priv: private data passed to @io_fn
87-
*/
88-
int rnbd_dev_submit_io(struct rnbd_dev *dev, sector_t sector, void *data,
89-
size_t len, u32 bi_size, enum rnbd_io_flags flags,
90-
short prio, void *priv);
91-
9283
#endif /* RNBD_SRV_DEV_H */

drivers/block/rnbd/rnbd-srv.c

Lines changed: 23 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -124,6 +124,9 @@ static int process_rdma(struct rtrs_srv *sess,
124124
struct rnbd_srv_sess_dev *sess_dev;
125125
u32 dev_id;
126126
int err;
127+
struct rnbd_dev_blk_io *io;
128+
struct bio *bio;
129+
short prio;
127130

128131
priv = kmalloc(sizeof(*priv), GFP_KERNEL);
129132
if (!priv)
@@ -142,18 +145,29 @@ static int process_rdma(struct rtrs_srv *sess,
142145
priv->sess_dev = sess_dev;
143146
priv->id = id;
144147

145-
err = rnbd_dev_submit_io(sess_dev->rnbd_dev, le64_to_cpu(msg->sector),
146-
data, datalen, le32_to_cpu(msg->bi_size),
147-
le32_to_cpu(msg->rw),
148-
srv_sess->ver < RNBD_PROTO_VER_MAJOR ||
149-
usrlen < sizeof(*msg) ?
150-
0 : le16_to_cpu(msg->prio), priv);
151-
if (unlikely(err)) {
152-
rnbd_srv_err(sess_dev, "Submitting I/O to device failed, err: %d\n",
153-
err);
148+
/* Generate bio with pages pointing to the rdma buffer */
149+
bio = rnbd_bio_map_kern(data, sess_dev->rnbd_dev->ibd_bio_set, datalen, GFP_KERNEL);
150+
if (IS_ERR(bio)) {
151+
rnbd_srv_err(sess_dev, "Failed to generate bio, err: %ld\n", PTR_ERR(bio));
154152
goto sess_dev_put;
155153
}
156154

155+
io = container_of(bio, struct rnbd_dev_blk_io, bio);
156+
io->dev = sess_dev->rnbd_dev;
157+
io->priv = priv;
158+
159+
bio->bi_end_io = rnbd_dev_bi_end_io;
160+
bio->bi_private = io;
161+
bio->bi_opf = rnbd_to_bio_flags(le32_to_cpu(msg->rw));
162+
bio->bi_iter.bi_sector = le64_to_cpu(msg->sector);
163+
bio->bi_iter.bi_size = le32_to_cpu(msg->bi_size);
164+
prio = srv_sess->ver < RNBD_PROTO_VER_MAJOR ||
165+
usrlen < sizeof(*msg) ? 0 : le16_to_cpu(msg->prio);
166+
bio_set_prio(bio, prio);
167+
bio_set_dev(bio, sess_dev->rnbd_dev->bdev);
168+
169+
submit_bio(bio);
170+
157171
return 0;
158172

159173
sess_dev_put:

drivers/md/md-cluster.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1139,6 +1139,7 @@ static int resize_bitmaps(struct mddev *mddev, sector_t newsize, sector_t oldsiz
11391139
bitmap = get_bitmap_from_slot(mddev, i);
11401140
if (IS_ERR(bitmap)) {
11411141
pr_err("can't get bitmap from slot %d\n", i);
1142+
bitmap = NULL;
11421143
goto out;
11431144
}
11441145
counts = &bitmap->counts;

drivers/md/md.c

Lines changed: 10 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -850,7 +850,13 @@ void mddev_unlock(struct mddev *mddev)
850850
sysfs_remove_group(&mddev->kobj, &md_redundancy_group);
851851
if (mddev->sysfs_action)
852852
sysfs_put(mddev->sysfs_action);
853+
if (mddev->sysfs_completed)
854+
sysfs_put(mddev->sysfs_completed);
855+
if (mddev->sysfs_degraded)
856+
sysfs_put(mddev->sysfs_degraded);
853857
mddev->sysfs_action = NULL;
858+
mddev->sysfs_completed = NULL;
859+
mddev->sysfs_degraded = NULL;
854860
}
855861
}
856862
mddev->sysfs_active = 0;
@@ -4068,6 +4074,8 @@ level_store(struct mddev *mddev, const char *buf, size_t len)
40684074
pr_warn("md: cannot register extra attributes for %s\n",
40694075
mdname(mddev));
40704076
mddev->sysfs_action = sysfs_get_dirent(mddev->kobj.sd, "sync_action");
4077+
mddev->sysfs_completed = sysfs_get_dirent_safe(mddev->kobj.sd, "sync_completed");
4078+
mddev->sysfs_degraded = sysfs_get_dirent_safe(mddev->kobj.sd, "degraded");
40714079
}
40724080
if (oldpers->sync_request != NULL &&
40734081
pers->sync_request == NULL) {
@@ -5582,14 +5590,9 @@ static void md_free(struct kobject *ko)
55825590

55835591
if (mddev->sysfs_state)
55845592
sysfs_put(mddev->sysfs_state);
5585-
if (mddev->sysfs_completed)
5586-
sysfs_put(mddev->sysfs_completed);
5587-
if (mddev->sysfs_degraded)
5588-
sysfs_put(mddev->sysfs_degraded);
55895593
if (mddev->sysfs_level)
55905594
sysfs_put(mddev->sysfs_level);
55915595

5592-
55935596
if (mddev->gendisk)
55945597
del_gendisk(mddev->gendisk);
55955598
if (mddev->queue)
@@ -5757,8 +5760,6 @@ static int md_alloc(dev_t dev, char *name)
57575760
if (!error && mddev->kobj.sd) {
57585761
kobject_uevent(&mddev->kobj, KOBJ_ADD);
57595762
mddev->sysfs_state = sysfs_get_dirent_safe(mddev->kobj.sd, "array_state");
5760-
mddev->sysfs_completed = sysfs_get_dirent_safe(mddev->kobj.sd, "sync_completed");
5761-
mddev->sysfs_degraded = sysfs_get_dirent_safe(mddev->kobj.sd, "degraded");
57625763
mddev->sysfs_level = sysfs_get_dirent_safe(mddev->kobj.sd, "level");
57635764
}
57645765
mddev_put(mddev);
@@ -6036,6 +6037,8 @@ int md_run(struct mddev *mddev)
60366037
pr_warn("md: cannot register extra attributes for %s\n",
60376038
mdname(mddev));
60386039
mddev->sysfs_action = sysfs_get_dirent_safe(mddev->kobj.sd, "sync_action");
6040+
mddev->sysfs_completed = sysfs_get_dirent_safe(mddev->kobj.sd, "sync_completed");
6041+
mddev->sysfs_degraded = sysfs_get_dirent_safe(mddev->kobj.sd, "degraded");
60396042
} else if (mddev->ro == 2) /* auto-readonly not meaningful */
60406043
mddev->ro = 0;
60416044

0 commit comments

Comments
 (0)