Skip to content

Commit 003fb0a

Browse files
cloehlestorulf
authored andcommitted
mmc: block: ensure error propagation for non-blk
Requests to the mmc layer usually come through a block device IO. The exceptions are the ioctl interface, RPMB chardev ioctl and debugfs, which issue their own blk_mq requests through blk_execute_rq and do not query the BLK_STS error but the mmcblk-internal drv_op_result. This patch ensures that drv_op_result defaults to an error and has to be overwritten by the operation to be considered successful. The behavior leads to a bug where the request never propagates the error, e.g. by directly erroring out at mmc_blk_mq_issue_rq if mmc_blk_part_switch fails. The ioctl caller of the rpmb chardev then can never see an error (BLK_STS_IOERR, but drv_op_result is unchanged) and thus may assume that their call executed successfully when it did not. While always checking the blk_execute_rq return value would be advised, let's eliminate the error by always setting drv_op_result as -EIO to be overwritten on success (or other error) Fixes: 614f038 ("mmc: block: move single ioctl() commands to block requests") Signed-off-by: Christian Loehle <[email protected]> Acked-by: Adrian Hunter <[email protected]> Cc: [email protected] Link: https://lore.kernel.org/r/[email protected] Signed-off-by: Ulf Hansson <[email protected]>
1 parent ac9a786 commit 003fb0a

File tree

1 file changed

+5
-0
lines changed

1 file changed

+5
-0
lines changed

drivers/mmc/core/block.c

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -264,6 +264,7 @@ static ssize_t power_ro_lock_store(struct device *dev,
264264
goto out_put;
265265
}
266266
req_to_mmc_queue_req(req)->drv_op = MMC_DRV_OP_BOOT_WP;
267+
req_to_mmc_queue_req(req)->drv_op_result = -EIO;
267268
blk_execute_rq(req, false);
268269
ret = req_to_mmc_queue_req(req)->drv_op_result;
269270
blk_mq_free_request(req);
@@ -651,6 +652,7 @@ static int mmc_blk_ioctl_cmd(struct mmc_blk_data *md,
651652
idatas[0] = idata;
652653
req_to_mmc_queue_req(req)->drv_op =
653654
rpmb ? MMC_DRV_OP_IOCTL_RPMB : MMC_DRV_OP_IOCTL;
655+
req_to_mmc_queue_req(req)->drv_op_result = -EIO;
654656
req_to_mmc_queue_req(req)->drv_op_data = idatas;
655657
req_to_mmc_queue_req(req)->ioc_count = 1;
656658
blk_execute_rq(req, false);
@@ -722,6 +724,7 @@ static int mmc_blk_ioctl_multi_cmd(struct mmc_blk_data *md,
722724
}
723725
req_to_mmc_queue_req(req)->drv_op =
724726
rpmb ? MMC_DRV_OP_IOCTL_RPMB : MMC_DRV_OP_IOCTL;
727+
req_to_mmc_queue_req(req)->drv_op_result = -EIO;
725728
req_to_mmc_queue_req(req)->drv_op_data = idata;
726729
req_to_mmc_queue_req(req)->ioc_count = n;
727730
blk_execute_rq(req, false);
@@ -2806,6 +2809,7 @@ static int mmc_dbg_card_status_get(void *data, u64 *val)
28062809
if (IS_ERR(req))
28072810
return PTR_ERR(req);
28082811
req_to_mmc_queue_req(req)->drv_op = MMC_DRV_OP_GET_CARD_STATUS;
2812+
req_to_mmc_queue_req(req)->drv_op_result = -EIO;
28092813
blk_execute_rq(req, false);
28102814
ret = req_to_mmc_queue_req(req)->drv_op_result;
28112815
if (ret >= 0) {
@@ -2844,6 +2848,7 @@ static int mmc_ext_csd_open(struct inode *inode, struct file *filp)
28442848
goto out_free;
28452849
}
28462850
req_to_mmc_queue_req(req)->drv_op = MMC_DRV_OP_GET_EXT_CSD;
2851+
req_to_mmc_queue_req(req)->drv_op_result = -EIO;
28472852
req_to_mmc_queue_req(req)->drv_op_data = &ext_csd;
28482853
blk_execute_rq(req, false);
28492854
err = req_to_mmc_queue_req(req)->drv_op_result;

0 commit comments

Comments
 (0)