diff options
-rw-r--r-- | drivers/md/dm-mpath.c | 11 | ||||
-rw-r--r-- | drivers/md/dm.c | 11 | ||||
-rw-r--r-- | include/linux/device-mapper.h | 3 |
3 files changed, 23 insertions, 2 deletions
diff --git a/drivers/md/dm-mpath.c b/drivers/md/dm-mpath.c index 075747e25f77..e08be94959fd 100644 --- a/drivers/md/dm-mpath.c +++ b/drivers/md/dm-mpath.c | |||
@@ -1299,8 +1299,17 @@ static int do_end_io(struct multipath *m, struct request *clone, | |||
1299 | if (!error && !clone->errors) | 1299 | if (!error && !clone->errors) |
1300 | return 0; /* I/O complete */ | 1300 | return 0; /* I/O complete */ |
1301 | 1301 | ||
1302 | if (noretry_error(error)) | 1302 | if (noretry_error(error)) { |
1303 | if ((clone->cmd_flags & REQ_WRITE_SAME) && | ||
1304 | !clone->q->limits.max_write_same_sectors) { | ||
1305 | struct queue_limits *limits; | ||
1306 | |||
1307 | /* device doesn't really support WRITE SAME, disable it */ | ||
1308 | limits = dm_get_queue_limits(dm_table_get_md(m->ti->table)); | ||
1309 | limits->max_write_same_sectors = 0; | ||
1310 | } | ||
1303 | return error; | 1311 | return error; |
1312 | } | ||
1304 | 1313 | ||
1305 | if (mpio->pgpath) | 1314 | if (mpio->pgpath) |
1306 | fail_path(mpio->pgpath); | 1315 | fail_path(mpio->pgpath); |
diff --git a/drivers/md/dm.c b/drivers/md/dm.c index 6a5e9ed2fcc3..7b0ccdc5d65c 100644 --- a/drivers/md/dm.c +++ b/drivers/md/dm.c | |||
@@ -2278,6 +2278,17 @@ struct target_type *dm_get_immutable_target_type(struct mapped_device *md) | |||
2278 | } | 2278 | } |
2279 | 2279 | ||
2280 | /* | 2280 | /* |
2281 | * The queue_limits are only valid as long as you have a reference | ||
2282 | * count on 'md'. | ||
2283 | */ | ||
2284 | struct queue_limits *dm_get_queue_limits(struct mapped_device *md) | ||
2285 | { | ||
2286 | BUG_ON(!atomic_read(&md->holders)); | ||
2287 | return &md->queue->limits; | ||
2288 | } | ||
2289 | EXPORT_SYMBOL_GPL(dm_get_queue_limits); | ||
2290 | |||
2291 | /* | ||
2281 | * Fully initialize a request-based queue (->elevator, ->request_fn, etc). | 2292 | * Fully initialize a request-based queue (->elevator, ->request_fn, etc). |
2282 | */ | 2293 | */ |
2283 | static int dm_init_request_based_queue(struct mapped_device *md) | 2294 | static int dm_init_request_based_queue(struct mapped_device *md) |
diff --git a/include/linux/device-mapper.h b/include/linux/device-mapper.h index 653073de09e3..ed419c62dde1 100644 --- a/include/linux/device-mapper.h +++ b/include/linux/device-mapper.h | |||
@@ -406,13 +406,14 @@ int dm_noflush_suspending(struct dm_target *ti); | |||
406 | union map_info *dm_get_mapinfo(struct bio *bio); | 406 | union map_info *dm_get_mapinfo(struct bio *bio); |
407 | union map_info *dm_get_rq_mapinfo(struct request *rq); | 407 | union map_info *dm_get_rq_mapinfo(struct request *rq); |
408 | 408 | ||
409 | struct queue_limits *dm_get_queue_limits(struct mapped_device *md); | ||
410 | |||
409 | /* | 411 | /* |
410 | * Geometry functions. | 412 | * Geometry functions. |
411 | */ | 413 | */ |
412 | int dm_get_geometry(struct mapped_device *md, struct hd_geometry *geo); | 414 | int dm_get_geometry(struct mapped_device *md, struct hd_geometry *geo); |
413 | int dm_set_geometry(struct mapped_device *md, struct hd_geometry *geo); | 415 | int dm_set_geometry(struct mapped_device *md, struct hd_geometry *geo); |
414 | 416 | ||
415 | |||
416 | /*----------------------------------------------------------------- | 417 | /*----------------------------------------------------------------- |
417 | * Functions for manipulating device-mapper tables. | 418 | * Functions for manipulating device-mapper tables. |
418 | *---------------------------------------------------------------*/ | 419 | *---------------------------------------------------------------*/ |