Skip to content

Commit e6478da

Browse files
calebsanderkawasaki
authored andcommitted
block: don't merge bios with different app_tags
nvme_set_app_tag() uses the app_tag value from the bio_integrity_payload of the struct request's first bio. This assumes all the request's bios have the same app_tag. However, it is possible for bios with different app_tag values to be merged into a single request. Add a check in blk_integrity_merge_{bio,rq}() to prevent the merging of bios/requests with different app_tag values if BIP_CHECK_APPTAG is set. Signed-off-by: Caleb Sander Mateos <[email protected]> Fixes: 3d8b5a2 ("block: add support to pass user meta buffer")
1 parent f962a4d commit e6478da

File tree

1 file changed

+18
-5
lines changed

1 file changed

+18
-5
lines changed

block/blk-integrity.c

Lines changed: 18 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -140,14 +140,21 @@ EXPORT_SYMBOL_GPL(blk_rq_integrity_map_user);
140140
bool blk_integrity_merge_rq(struct request_queue *q, struct request *req,
141141
struct request *next)
142142
{
143+
struct bio_integrity_payload *bip, *bip_next;
144+
143145
if (blk_integrity_rq(req) == 0 && blk_integrity_rq(next) == 0)
144146
return true;
145147

146148
if (blk_integrity_rq(req) == 0 || blk_integrity_rq(next) == 0)
147149
return false;
148150

149-
if (bio_integrity(req->bio)->bip_flags !=
150-
bio_integrity(next->bio)->bip_flags)
151+
bip = bio_integrity(req->bio);
152+
bip_next = bio_integrity(next->bio);
153+
if (bip->bip_flags != bip_next->bip_flags)
154+
return false;
155+
156+
if (bip->bip_flags & BIP_CHECK_APPTAG &&
157+
bip->app_tag != bip_next->app_tag)
151158
return false;
152159

153160
if (req->nr_integrity_segments + next->nr_integrity_segments >
@@ -163,15 +170,21 @@ bool blk_integrity_merge_rq(struct request_queue *q, struct request *req,
163170
bool blk_integrity_merge_bio(struct request_queue *q, struct request *req,
164171
struct bio *bio)
165172
{
173+
struct bio_integrity_payload *bip, *bip_bio = bio_integrity(bio);
166174
int nr_integrity_segs;
167175

168-
if (blk_integrity_rq(req) == 0 && bio_integrity(bio) == NULL)
176+
if (blk_integrity_rq(req) == 0 && bip_bio == NULL)
169177
return true;
170178

171-
if (blk_integrity_rq(req) == 0 || bio_integrity(bio) == NULL)
179+
if (blk_integrity_rq(req) == 0 || bip_bio == NULL)
180+
return false;
181+
182+
bip = bio_integrity(req->bio);
183+
if (bip->bip_flags != bip_bio->bip_flags)
172184
return false;
173185

174-
if (bio_integrity(req->bio)->bip_flags != bio_integrity(bio)->bip_flags)
186+
if (bip->bip_flags & BIP_CHECK_APPTAG &&
187+
bip->app_tag != bip_bio->app_tag)
175188
return false;
176189

177190
nr_integrity_segs = blk_rq_count_integrity_sg(q, bio);

0 commit comments

Comments
 (0)