summaryrefslogtreecommitdiffstats
path: root/drivers/md/dm-cache-metadata.c
diff options
context:
space:
mode:
authorMike Snitzer <snitzer@redhat.com>2017-05-05 14:40:13 -0400
committerMike Snitzer <snitzer@redhat.com>2017-05-05 14:40:13 -0400
commit10add84e276432d9dd8044679a1028dd4084117e (patch)
tree6ea92feaba250f9751bfae9d0cdc64a5d55cafb4 /drivers/md/dm-cache-metadata.c
parent7ab84db64f119e03b2c42ed919dfee7d6cf0dc3c (diff)
dm cache metadata: fail operations if fail_io mode has been established
Otherwise it is possible to trigger crashes due to the metadata being inaccessible yet these methods don't safely account for that possibility without these checks. Cc: stable@vger.kernel.org Reported-by: Mikulas Patocka <mpatocka@redhat.com> Signed-off-by: Mike Snitzer <snitzer@redhat.com>
Diffstat (limited to 'drivers/md/dm-cache-metadata.c')
-rw-r--r--drivers/md/dm-cache-metadata.c12
1 files changed, 8 insertions, 4 deletions
diff --git a/drivers/md/dm-cache-metadata.c b/drivers/md/dm-cache-metadata.c
index 8568dbd50ba4..4a4e9c75fc4c 100644
--- a/drivers/md/dm-cache-metadata.c
+++ b/drivers/md/dm-cache-metadata.c
@@ -1624,17 +1624,19 @@ void dm_cache_metadata_set_stats(struct dm_cache_metadata *cmd,
1624 1624
1625int dm_cache_commit(struct dm_cache_metadata *cmd, bool clean_shutdown) 1625int dm_cache_commit(struct dm_cache_metadata *cmd, bool clean_shutdown)
1626{ 1626{
1627 int r; 1627 int r = -EINVAL;
1628 flags_mutator mutator = (clean_shutdown ? set_clean_shutdown : 1628 flags_mutator mutator = (clean_shutdown ? set_clean_shutdown :
1629 clear_clean_shutdown); 1629 clear_clean_shutdown);
1630 1630
1631 WRITE_LOCK(cmd); 1631 WRITE_LOCK(cmd);
1632 if (cmd->fail_io)
1633 goto out;
1634
1632 r = __commit_transaction(cmd, mutator); 1635 r = __commit_transaction(cmd, mutator);
1633 if (r) 1636 if (r)
1634 goto out; 1637 goto out;
1635 1638
1636 r = __begin_transaction(cmd); 1639 r = __begin_transaction(cmd);
1637
1638out: 1640out:
1639 WRITE_UNLOCK(cmd); 1641 WRITE_UNLOCK(cmd);
1640 return r; 1642 return r;
@@ -1646,7 +1648,8 @@ int dm_cache_get_free_metadata_block_count(struct dm_cache_metadata *cmd,
1646 int r = -EINVAL; 1648 int r = -EINVAL;
1647 1649
1648 READ_LOCK(cmd); 1650 READ_LOCK(cmd);
1649 r = dm_sm_get_nr_free(cmd->metadata_sm, result); 1651 if (!cmd->fail_io)
1652 r = dm_sm_get_nr_free(cmd->metadata_sm, result);
1650 READ_UNLOCK(cmd); 1653 READ_UNLOCK(cmd);
1651 1654
1652 return r; 1655 return r;
@@ -1658,7 +1661,8 @@ int dm_cache_get_metadata_dev_size(struct dm_cache_metadata *cmd,
1658 int r = -EINVAL; 1661 int r = -EINVAL;
1659 1662
1660 READ_LOCK(cmd); 1663 READ_LOCK(cmd);
1661 r = dm_sm_get_nr_blocks(cmd->metadata_sm, result); 1664 if (!cmd->fail_io)
1665 r = dm_sm_get_nr_blocks(cmd->metadata_sm, result);
1662 READ_UNLOCK(cmd); 1666 READ_UNLOCK(cmd);
1663 1667
1664 return r; 1668 return r;