Received: by 2002:a05:6a10:206:0:0:0:0 with SMTP id 6csp5428454pxj; Wed, 23 Jun 2021 00:41:34 -0700 (PDT) X-Google-Smtp-Source: ABdhPJwzdCtTHznxTyOatcWN/uCvVuMgiPY+jY0KH+XiLbSoqUAzrbuyr0PYGaxEvFNsx2mTCzVO X-Received: by 2002:a17:906:698a:: with SMTP id i10mr8527863ejr.499.1624434094175; Wed, 23 Jun 2021 00:41:34 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1624434094; cv=none; d=google.com; s=arc-20160816; b=z8oO2nqUl78DLL9CpTYADQ6ogHDatjrNg2VFWtbRJF4tfOHN7qpVjkzy3W9A9yXfQq iDTq1v8rxxPveZojV809Z9ljvFaKItWD3LeIKFHUpRmvWnO4T7yX0efTqnqapMm63jEW qQb2obc5Hn5qx6LW1DSLnNjbEYBZ+lq+wxRIN6mK29fuEvjPIPirtfAxUW5P21cBl5N5 Sus6wA581/7PtZMie48QbWLdJm4zvU6Vo0jb1xrejjkDol3EU4zzXstMnFTiUyhPiObT NQZMpC85BPKkB4yVp2QX9gpIgzf9WBY5jBPUeTBDJAZSCVQngFoiIkQE1/6TaJUII1hl 6wxg== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:references:in-reply-to:message-id:date:subject :cc:to:from:ironport-sdr; bh=yfavllGP4YBkPWeddRH5c+V25qM/wdVdDAcpssh5yq8=; b=KbupDqiBBYEpXe3038zFnnbfmPDJtmyc/W//QmA6wPPt4wU28Olkw7uA/tEeiErfff 7M0PymByVK/ZintYHFp8i5yiojlmvJ7aff+jiiZd9x0vOkk2ZHXRVGeTcyX9iD7ZjrLN eqDCCZuFLVB7pi+TrjK4qYLcC/lFYGaN7fBRS/cnPDdn/UwzT58QxaiNeKahQPnF9AY9 m4WrpDyYt9C2k6lzNqdTp+7wNbdqRvKaGRhDI0sjdKjix+6N1lt0rBA/Xg9B0bsO1DVE W3IIMTMcxjeHYwFS2RZQ1NL7gtF0u9P5ytHhxRiGRuWNsGSfkL+EluTnSO5hw6LsIfuT eqUg== ARC-Authentication-Results: i=1; mx.google.com; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.18 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org Return-Path: Received: from vger.kernel.org (vger.kernel.org. [23.128.96.18]) by mx.google.com with ESMTP id e29si5619256ejl.202.2021.06.23.00.41.12; Wed, 23 Jun 2021 00:41:34 -0700 (PDT) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.18 as permitted sender) client-ip=23.128.96.18; Authentication-Results: mx.google.com; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.18 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S231261AbhFWHkG (ORCPT + 99 others); Wed, 23 Jun 2021 03:40:06 -0400 Received: from labrats.qualcomm.com ([199.106.110.90]:1666 "EHLO labrats.qualcomm.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S230239AbhFWHjj (ORCPT ); Wed, 23 Jun 2021 03:39:39 -0400 IronPort-SDR: gxr3rinUnZwqhDdvoPSRL3vJPIPKMfWgnZxn3KTf+6ceJ/uPEtNRQLo7c4+cgAZ/VJjjaCaRZK 4hetoaFwvUTjqYQthpw+igVHNe96ts1DoJEhPg5EKnryoN/4a4bDpdiSPcw7v5kjXuFmsLxGY0 5buz/q0xuKhWTdo+4fghNnlusBHXVxAit8gexCVBTmNum1dop7bBPRBTz8mhJV1LLV605VrkWS rrsbuJ/ne/ptgMtLuEH4friErVigXmi8xJROLWfzbldzPwshRd7RfChmoub1RjD+nBjiNiWTUc BwA= X-IronPort-AV: E=Sophos;i="5.83,293,1616482800"; d="scan'208";a="29780823" Received: from unknown (HELO ironmsg04-sd.qualcomm.com) ([10.53.140.144]) by labrats.qualcomm.com with ESMTP; 23 Jun 2021 00:37:18 -0700 X-QCInternal: smtphost Received: from stor-presley.qualcomm.com ([192.168.140.85]) by ironmsg04-sd.qualcomm.com with ESMTP; 23 Jun 2021 00:37:18 -0700 Received: by stor-presley.qualcomm.com (Postfix, from userid 359480) id 1ABA121BC1; Wed, 23 Jun 2021 00:37:18 -0700 (PDT) From: Can Guo To: asutoshd@codeaurora.org, nguyenb@codeaurora.org, hongwus@codeaurora.org, ziqichen@codeaurora.org, linux-scsi@vger.kernel.org, kernel-team@android.com, cang@codeaurora.org Cc: Alim Akhtar , Avri Altman , "James E.J. Bottomley" , "Martin K. Petersen" , Stanley Chu , Bean Huo , Jaegeuk Kim , linux-kernel@vger.kernel.org (open list) Subject: [PATCH v4 08/10] scsi: ufs: Update ufshcd_recover_pm_error() Date: Wed, 23 Jun 2021 00:35:08 -0700 Message-Id: <1624433711-9339-10-git-send-email-cang@codeaurora.org> X-Mailer: git-send-email 2.7.4 In-Reply-To: <1624433711-9339-1-git-send-email-cang@codeaurora.org> References: <1624433711-9339-1-git-send-email-cang@codeaurora.org> Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org After error handler performs a successful reset and restore, all the LUs become active, forcibly set the runtime PM status of the scsi devices (and their request queues) underneath hba to ACTIVE to reflect the change. By doing so, dev->power.runtime_error (if any) can also be cleared, such that runtime PM can get back to work on them, otherwise the device(s) may be left either runtime active or runtime suspended permanently. Signed-off-by: Can Guo --- drivers/scsi/ufs/ufshcd.c | 49 ++++++++++++++++++++--------------------------- 1 file changed, 21 insertions(+), 28 deletions(-) diff --git a/drivers/scsi/ufs/ufshcd.c b/drivers/scsi/ufs/ufshcd.c index 379c6a0..d739401 100644 --- a/drivers/scsi/ufs/ufshcd.c +++ b/drivers/scsi/ufs/ufshcd.c @@ -243,6 +243,7 @@ static irqreturn_t ufshcd_intr(int irq, void *__hba); static int ufshcd_change_power_mode(struct ufs_hba *hba, struct ufs_pa_layer_attr *pwr_mode); static void ufshcd_schedule_eh_work(struct ufs_hba *hba); +static void ufshcd_recover_pm_error(struct ufs_hba *hba); static int ufshcd_setup_hba_vreg(struct ufs_hba *hba, bool on); static int ufshcd_setup_vreg(struct ufs_hba *hba, bool on); static inline int ufshcd_config_vreg_hpm(struct ufs_hba *hba, @@ -5946,13 +5947,15 @@ static int ufshcd_err_handling_prepare(struct ufs_hba *hba) return 0; } -static void ufshcd_err_handling_unprepare(struct ufs_hba *hba) +static void ufshcd_err_handling_unprepare(struct ufs_hba *hba, int reset_err) { ufshcd_clear_eh_in_progress(hba); ufshcd_scsi_unblock_requests(hba); ufshcd_release(hba); if (ufshcd_is_clkscaling_supported(hba)) ufshcd_clk_scaling_suspend(hba, false); + if (!reset_err) + ufshcd_recover_pm_error(hba); ufshcd_clear_ua_wluns(hba); ufshcd_rpm_put(hba); pm_runtime_put(hba->dev); @@ -5972,34 +5975,26 @@ static inline bool ufshcd_err_handling_should_stop(struct ufs_hba *hba) static void ufshcd_recover_pm_error(struct ufs_hba *hba) { struct Scsi_Host *shost = hba->host; - struct scsi_device *sdev; - struct request_queue *q; + struct scsi_device *sdev = hba->sdev_ufs_device; + struct scsi_target *starget = sdev->sdev_target; int ret; hba->is_wlu_sys_suspended = false; - /* - * Set RPM status of wlun device to RPM_ACTIVE, - * this also clears its runtime error. - */ - ret = pm_runtime_set_active(&hba->sdev_ufs_device->sdev_gendev); - /* hba device might have a runtime error otherwise */ - if (ret) - ret = pm_runtime_set_active(hba->dev); - /* - * If wlun device had runtime error, we also need to resume those - * consumer scsi devices in case any of them has failed to be - * resumed due to supplier runtime resume failure. This is to unblock - * blk_queue_enter in case there are bios waiting inside it. - */ - if (!ret) { - shost_for_each_device(sdev, shost) { - q = sdev->request_queue; - if (q->dev && (q->rpm_status == RPM_SUSPENDED || - q->rpm_status == RPM_SUSPENDING)) - pm_request_resume(q->dev); - } + /* Resume parent/target to clear path for pm_runtime_set_active() */ + pm_runtime_get_sync(&starget->dev); + shost_for_each_device(sdev, shost) { + struct device *dev = &sdev->sdev_gendev; + + pm_runtime_get_sync(dev); + /* Clear dev->power.runtime_error */ + ret = pm_runtime_set_active(dev); + if (!ret) + /* runtime_error cleared, kick blk_queue_enter() */ + blk_set_runtime_active(sdev->request_queue); + pm_runtime_put(dev); } + pm_runtime_put(&starget->dev); } #else static inline void ufshcd_recover_pm_error(struct ufs_hba *hba) @@ -6033,7 +6028,7 @@ static void ufshcd_err_handler(struct work_struct *work) unsigned long flags; bool err_xfer = false; bool err_tm = false; - int err = 0, pmc_err; + int err = -1, pmc_err; int tag; bool needs_reset = false, needs_restore = false; @@ -6185,8 +6180,6 @@ static void ufshcd_err_handler(struct work_struct *work) if (err) dev_err(hba->dev, "%s: reset and restore failed with err %d\n", __func__, err); - else - ufshcd_recover_pm_error(hba); spin_lock_irqsave(hba->host->host_lock, flags); } @@ -6199,7 +6192,7 @@ static void ufshcd_err_handler(struct work_struct *work) __func__, hba->saved_err, hba->saved_uic_err); } spin_unlock_irqrestore(hba->host->host_lock, flags); - ufshcd_err_handling_unprepare(hba); + ufshcd_err_handling_unprepare(hba, err); up(&hba->host_sem); } -- Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum, a Linux Foundation Collaborative Project.