scsi: ufs: core: Add helpers to pause and resume command processing

In preparation for supporting TX Equalization refreshing, introduce helper
functions to safely pause and resume command processing.

ufshcd_pause_command_processing() ensures the host is in a quiescent state
by stopping the block layer tagset, acquiring the necessary locks
(scan_mutex and clk_scaling_lock), and waiting for any in-flight commands
to complete within a specified timeout.

ufshcd_resume_command_processing() restores the host to its previous
operational state by reversing these steps in the correct order.

Reviewed-by: Bean Huo <beanhuo@micron.com>
Reviewed-by: Bart Van Assche <bvanassche@acm.org>
Signed-off-by: Can Guo <can.guo@oss.qualcomm.com>
Reviewed-by: Peter Wang <peter.wang@mediatek.com>
Link: https://patch.msgid.link/20260325152154.1604082-7-can.guo@oss.qualcomm.com
Signed-off-by: Martin K. Petersen <martin.petersen@oracle.com>
This commit is contained in:
Can Guo
2026-03-27 17:20:29 -04:00
committed by Martin K. Petersen
parent 10c40143f3
commit dc5dcac532
2 changed files with 44 additions and 0 deletions
+2
View File
@@ -78,6 +78,8 @@ int ufshcd_mcq_sq_cleanup(struct ufs_hba *hba, int task_tag);
int ufshcd_mcq_abort(struct scsi_cmnd *cmd);
int ufshcd_try_to_abort_task(struct ufs_hba *hba, int tag);
void ufshcd_release_scsi_cmd(struct ufs_hba *hba, struct scsi_cmnd *cmd);
int ufshcd_pause_command_processing(struct ufs_hba *hba, u64 timeout_us);
void ufshcd_resume_command_processing(struct ufs_hba *hba);
/**
* enum ufs_descr_fmt - UFS string descriptor format
+42
View File
@@ -1363,6 +1363,48 @@ out:
return ret;
}
/**
* ufshcd_pause_command_processing - Pause command processing
* @hba: per-adapter instance
* @timeout_us: timeout in microseconds to wait for pending commands to finish
*
* This function stops new command submissions and waits for existing commands
* to complete.
*
* Return: 0 on success, %-EBUSY if commands did not finish within @timeout_us.
* On failure, all acquired locks are released and the tagset is unquiesced.
*/
int ufshcd_pause_command_processing(struct ufs_hba *hba, u64 timeout_us)
{
int ret = 0;
mutex_lock(&hba->host->scan_mutex);
blk_mq_quiesce_tagset(&hba->host->tag_set);
down_write(&hba->clk_scaling_lock);
if (ufshcd_wait_for_pending_cmds(hba, timeout_us)) {
ret = -EBUSY;
up_write(&hba->clk_scaling_lock);
blk_mq_unquiesce_tagset(&hba->host->tag_set);
mutex_unlock(&hba->host->scan_mutex);
}
return ret;
}
/**
* ufshcd_resume_command_processing - Resume command processing
* @hba: per-adapter instance
*
* This function resumes command submissions.
*/
void ufshcd_resume_command_processing(struct ufs_hba *hba)
{
up_write(&hba->clk_scaling_lock);
blk_mq_unquiesce_tagset(&hba->host->tag_set);
mutex_unlock(&hba->host->scan_mutex);
}
/**
* ufshcd_scale_gear - scale up/down UFS gear
* @hba: per adapter instance