linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH 0/2] net: wwan: t7xx: Fix Runtime PM implementation
@ 2023-01-26 13:25 Kornel Dulęba
  2023-01-26 13:25 ` [PATCH 1/2] net: wwan: t7xx: Fix Runtime PM resume sequence Kornel Dulęba
                   ` (2 more replies)
  0 siblings, 3 replies; 4+ messages in thread
From: Kornel Dulęba @ 2023-01-26 13:25 UTC (permalink / raw)
  To: netdev, linux-kernel
  Cc: Chandrashekar Devegowda, Intel Corporation, Chiranjeevi Rapolu,
	Liu Haijun, M Chetan Kumar, Ricardo Martinez, Loic Poulain,
	Sergey Ryazanov, Johannes Berg, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, rad, mw, upstream,
	Kornel Dulęba

d10b3a695ba0 ("net: wwan: t7xx: Runtime PM") introduced support for
Runtime PM for this driver, but due to a bug in the initialization logic
the usage refcount would never reach 0, leaving the feature unused.
This patchset addresses that, together with a bug found after runtime
suspend was enabled.

Kornel Dulęba (2):
  net: wwan: t7xx: Fix Runtime PM resume sequence
  net: wwan: t7xx: Fix Runtime PM initialization

 drivers/net/wwan/t7xx/t7xx_hif_dpmaif.c    | 11 +++++++-
 drivers/net/wwan/t7xx/t7xx_hif_dpmaif_rx.c | 29 +++++++++++++++-------
 drivers/net/wwan/t7xx/t7xx_netdev.c        | 16 +++++++++++-
 drivers/net/wwan/t7xx/t7xx_pci.c           |  2 ++
 4 files changed, 47 insertions(+), 11 deletions(-)

-- 
2.39.1.456.gfc5497dd1b-goog


^ permalink raw reply	[flat|nested] 4+ messages in thread

* [PATCH 1/2] net: wwan: t7xx: Fix Runtime PM resume sequence
  2023-01-26 13:25 [PATCH 0/2] net: wwan: t7xx: Fix Runtime PM implementation Kornel Dulęba
@ 2023-01-26 13:25 ` Kornel Dulęba
  2023-01-26 13:25 ` [PATCH 2/2] net: wwan: t7xx: Fix Runtime PM initialization Kornel Dulęba
  2023-01-28 13:50 ` [PATCH 0/2] net: wwan: t7xx: Fix Runtime PM implementation patchwork-bot+netdevbpf
  2 siblings, 0 replies; 4+ messages in thread
From: Kornel Dulęba @ 2023-01-26 13:25 UTC (permalink / raw)
  To: netdev, linux-kernel
  Cc: Chandrashekar Devegowda, Intel Corporation, Chiranjeevi Rapolu,
	Liu Haijun, M Chetan Kumar, Ricardo Martinez, Loic Poulain,
	Sergey Ryazanov, Johannes Berg, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, rad, mw, upstream,
	Kornel Dulęba

Resume device before calling napi_schedule, instead of doing in the napi
poll routine. Polling is done in softrq context. We can't call the PM
resume logic from there as it's blocking and not irq safe.
In order to make it work modify the interrupt handler to be run from irq
handler thread.

Fixes: 5545b7b9f294 ("net: wwan: t7xx: Add NAPI support")
Signed-off-by: Kornel Dulęba <mindal@semihalf.com>
---
 drivers/net/wwan/t7xx/t7xx_hif_dpmaif.c    | 11 +++++++-
 drivers/net/wwan/t7xx/t7xx_hif_dpmaif_rx.c | 29 +++++++++++++++-------
 drivers/net/wwan/t7xx/t7xx_netdev.c        | 16 +++++++++++-
 3 files changed, 45 insertions(+), 11 deletions(-)

diff --git a/drivers/net/wwan/t7xx/t7xx_hif_dpmaif.c b/drivers/net/wwan/t7xx/t7xx_hif_dpmaif.c
index 7eff3531b9a5..7ff33c1d6ac7 100644
--- a/drivers/net/wwan/t7xx/t7xx_hif_dpmaif.c
+++ b/drivers/net/wwan/t7xx/t7xx_hif_dpmaif.c
@@ -152,6 +152,15 @@ static irqreturn_t t7xx_dpmaif_isr_handler(int irq, void *data)
 	}
 
 	t7xx_pcie_mac_clear_int(dpmaif_ctrl->t7xx_dev, isr_para->pcie_int);
+
+	return IRQ_WAKE_THREAD;
+}
+
+static irqreturn_t t7xx_dpmaif_isr_thread(int irq, void *data)
+{
+	struct dpmaif_isr_para *isr_para = data;
+	struct dpmaif_ctrl *dpmaif_ctrl = isr_para->dpmaif_ctrl;
+
 	t7xx_dpmaif_irq_cb(isr_para);
 	t7xx_pcie_mac_set_int(dpmaif_ctrl->t7xx_dev, isr_para->pcie_int);
 	return IRQ_HANDLED;
@@ -188,7 +197,7 @@ static void t7xx_dpmaif_register_pcie_irq(struct dpmaif_ctrl *dpmaif_ctrl)
 		t7xx_pcie_mac_clear_int(t7xx_dev, int_type);
 
 		t7xx_dev->intr_handler[int_type] = t7xx_dpmaif_isr_handler;
-		t7xx_dev->intr_thread[int_type] = NULL;
+		t7xx_dev->intr_thread[int_type] = t7xx_dpmaif_isr_thread;
 		t7xx_dev->callback_param[int_type] = isr_para;
 
 		t7xx_pcie_mac_clear_int_status(t7xx_dev, int_type);
diff --git a/drivers/net/wwan/t7xx/t7xx_hif_dpmaif_rx.c b/drivers/net/wwan/t7xx/t7xx_hif_dpmaif_rx.c
index aa2174a10437..f4ff2198b5ef 100644
--- a/drivers/net/wwan/t7xx/t7xx_hif_dpmaif_rx.c
+++ b/drivers/net/wwan/t7xx/t7xx_hif_dpmaif_rx.c
@@ -840,14 +840,13 @@ int t7xx_dpmaif_napi_rx_poll(struct napi_struct *napi, const int budget)
 
 	if (!rxq->que_started) {
 		atomic_set(&rxq->rx_processing, 0);
+		pm_runtime_put_autosuspend(rxq->dpmaif_ctrl->dev);
 		dev_err(rxq->dpmaif_ctrl->dev, "Work RXQ: %d has not been started\n", rxq->index);
 		return work_done;
 	}
 
-	if (!rxq->sleep_lock_pending) {
-		pm_runtime_get_noresume(rxq->dpmaif_ctrl->dev);
+	if (!rxq->sleep_lock_pending)
 		t7xx_pci_disable_sleep(t7xx_dev);
-	}
 
 	ret = try_wait_for_completion(&t7xx_dev->sleep_lock_acquire);
 	if (!ret) {
@@ -876,22 +875,22 @@ int t7xx_dpmaif_napi_rx_poll(struct napi_struct *napi, const int budget)
 		napi_complete_done(napi, work_done);
 		t7xx_dpmaif_clr_ip_busy_sts(&rxq->dpmaif_ctrl->hw_info);
 		t7xx_dpmaif_dlq_unmask_rx_done(&rxq->dpmaif_ctrl->hw_info, rxq->index);
+		t7xx_pci_enable_sleep(rxq->dpmaif_ctrl->t7xx_dev);
+		pm_runtime_mark_last_busy(rxq->dpmaif_ctrl->dev);
+		pm_runtime_put_autosuspend(rxq->dpmaif_ctrl->dev);
+		atomic_set(&rxq->rx_processing, 0);
 	} else {
 		t7xx_dpmaif_clr_ip_busy_sts(&rxq->dpmaif_ctrl->hw_info);
 	}
 
-	t7xx_pci_enable_sleep(rxq->dpmaif_ctrl->t7xx_dev);
-	pm_runtime_mark_last_busy(rxq->dpmaif_ctrl->dev);
-	pm_runtime_put_noidle(rxq->dpmaif_ctrl->dev);
-	atomic_set(&rxq->rx_processing, 0);
-
 	return work_done;
 }
 
 void t7xx_dpmaif_irq_rx_done(struct dpmaif_ctrl *dpmaif_ctrl, const unsigned int que_mask)
 {
 	struct dpmaif_rx_queue *rxq;
-	int qno;
+	struct dpmaif_ctrl *ctrl;
+	int qno, ret;
 
 	qno = ffs(que_mask) - 1;
 	if (qno < 0 || qno > DPMAIF_RXQ_NUM - 1) {
@@ -900,6 +899,18 @@ void t7xx_dpmaif_irq_rx_done(struct dpmaif_ctrl *dpmaif_ctrl, const unsigned int
 	}
 
 	rxq = &dpmaif_ctrl->rxq[qno];
+	ctrl = rxq->dpmaif_ctrl;
+	/* We need to make sure that the modem has been resumed before
+	 * calling napi. This can't be done inside the polling function
+	 * as we could be blocked waiting for device to be resumed,
+	 * which can't be done from softirq context the poll function
+	 * is running in.
+	 */
+	ret = pm_runtime_resume_and_get(ctrl->dev);
+	if (ret < 0 && ret != -EACCES) {
+		dev_err(ctrl->dev, "Failed to resume device: %d\n", ret);
+		return;
+	}
 	napi_schedule(&rxq->napi);
 }
 
diff --git a/drivers/net/wwan/t7xx/t7xx_netdev.c b/drivers/net/wwan/t7xx/t7xx_netdev.c
index 494a28e386a3..3ef4a8a4f8fd 100644
--- a/drivers/net/wwan/t7xx/t7xx_netdev.c
+++ b/drivers/net/wwan/t7xx/t7xx_netdev.c
@@ -27,6 +27,7 @@
 #include <linux/list.h>
 #include <linux/netdev_features.h>
 #include <linux/netdevice.h>
+#include <linux/pm_runtime.h>
 #include <linux/skbuff.h>
 #include <linux/types.h>
 #include <linux/wwan.h>
@@ -45,12 +46,25 @@
 
 static void t7xx_ccmni_enable_napi(struct t7xx_ccmni_ctrl *ctlb)
 {
-	int i;
+	struct dpmaif_ctrl *ctrl;
+	int i, ret;
+
+	ctrl =  ctlb->hif_ctrl;
 
 	if (ctlb->is_napi_en)
 		return;
 
 	for (i = 0; i < RXQ_NUM; i++) {
+		/* The usage count has to be bumped every time before calling
+		 * napi_schedule. It will be decresed in the poll routine,
+		 * right after napi_complete_done is called.
+		 */
+		ret = pm_runtime_resume_and_get(ctrl->dev);
+		if (ret < 0) {
+			dev_err(ctrl->dev, "Failed to resume device: %d\n",
+				ret);
+			return;
+		}
 		napi_enable(ctlb->napi[i]);
 		napi_schedule(ctlb->napi[i]);
 	}
-- 
2.39.1.456.gfc5497dd1b-goog


^ permalink raw reply related	[flat|nested] 4+ messages in thread

* [PATCH 2/2] net: wwan: t7xx: Fix Runtime PM initialization
  2023-01-26 13:25 [PATCH 0/2] net: wwan: t7xx: Fix Runtime PM implementation Kornel Dulęba
  2023-01-26 13:25 ` [PATCH 1/2] net: wwan: t7xx: Fix Runtime PM resume sequence Kornel Dulęba
@ 2023-01-26 13:25 ` Kornel Dulęba
  2023-01-28 13:50 ` [PATCH 0/2] net: wwan: t7xx: Fix Runtime PM implementation patchwork-bot+netdevbpf
  2 siblings, 0 replies; 4+ messages in thread
From: Kornel Dulęba @ 2023-01-26 13:25 UTC (permalink / raw)
  To: netdev, linux-kernel
  Cc: Chandrashekar Devegowda, Intel Corporation, Chiranjeevi Rapolu,
	Liu Haijun, M Chetan Kumar, Ricardo Martinez, Loic Poulain,
	Sergey Ryazanov, Johannes Berg, David S. Miller, Eric Dumazet,
	Jakub Kicinski, Paolo Abeni, rad, mw, upstream,
	Kornel Dulęba

For PCI devices the Runtime PM refcount is incremented twice:
1. During device enumeration with a call to pm_runtime_forbid.
2. Just before a driver probe logic is called.
Because of that in order to enable Runtime PM on a given device
we have to call both pm_runtime_allow and pm_runtime_put_noidle,
once it's ready to be runtime suspended.
The former was missing causing the pm refcount to never reach 0.

Fixes: d10b3a695ba0 ("net: wwan: t7xx: Runtime PM")
Signed-off-by: Kornel Dulęba <mindal@semihalf.com>
---
 drivers/net/wwan/t7xx/t7xx_pci.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/drivers/net/wwan/t7xx/t7xx_pci.c b/drivers/net/wwan/t7xx/t7xx_pci.c
index 871f2a27a398..226fc1703e90 100644
--- a/drivers/net/wwan/t7xx/t7xx_pci.c
+++ b/drivers/net/wwan/t7xx/t7xx_pci.c
@@ -121,6 +121,8 @@ void t7xx_pci_pm_init_late(struct t7xx_pci_dev *t7xx_dev)
 	iowrite32(T7XX_L1_BIT(0), IREG_BASE(t7xx_dev) + ENABLE_ASPM_LOWPWR);
 	atomic_set(&t7xx_dev->md_pm_state, MTK_PM_RESUMED);
 
+	pm_runtime_mark_last_busy(&t7xx_dev->pdev->dev);
+	pm_runtime_allow(&t7xx_dev->pdev->dev);
 	pm_runtime_put_noidle(&t7xx_dev->pdev->dev);
 }
 
-- 
2.39.1.456.gfc5497dd1b-goog


^ permalink raw reply related	[flat|nested] 4+ messages in thread

* Re: [PATCH 0/2] net: wwan: t7xx: Fix Runtime PM implementation
  2023-01-26 13:25 [PATCH 0/2] net: wwan: t7xx: Fix Runtime PM implementation Kornel Dulęba
  2023-01-26 13:25 ` [PATCH 1/2] net: wwan: t7xx: Fix Runtime PM resume sequence Kornel Dulęba
  2023-01-26 13:25 ` [PATCH 2/2] net: wwan: t7xx: Fix Runtime PM initialization Kornel Dulęba
@ 2023-01-28 13:50 ` patchwork-bot+netdevbpf
  2 siblings, 0 replies; 4+ messages in thread
From: patchwork-bot+netdevbpf @ 2023-01-28 13:50 UTC (permalink / raw)
  To: =?utf-8?q?Kornel_Dul=C4=99ba_=3Cmindal=40semihalf=2Ecom=3E?=
  Cc: netdev, linux-kernel, chandrashekar.devegowda, linuxwwan,
	chiranjeevi.rapolu, haijun.liu, m.chetan.kumar, ricardo.martinez,
	loic.poulain, ryazanov.s.a, johannes, davem, edumazet, kuba,
	pabeni, rad, mw, upstream

Hello:

This series was applied to netdev/net.git (master)
by David S. Miller <davem@davemloft.net>:

On Thu, 26 Jan 2023 13:25:33 +0000 you wrote:
> d10b3a695ba0 ("net: wwan: t7xx: Runtime PM") introduced support for
> Runtime PM for this driver, but due to a bug in the initialization logic
> the usage refcount would never reach 0, leaving the feature unused.
> This patchset addresses that, together with a bug found after runtime
> suspend was enabled.
> 
> Kornel Dulęba (2):
>   net: wwan: t7xx: Fix Runtime PM resume sequence
>   net: wwan: t7xx: Fix Runtime PM initialization
> 
> [...]

Here is the summary with links:
  - [1/2] net: wwan: t7xx: Fix Runtime PM resume sequence
    https://git.kernel.org/netdev/net/c/364d0221f178
  - [2/2] net: wwan: t7xx: Fix Runtime PM initialization
    https://git.kernel.org/netdev/net/c/e3d6d152a1cb

You are awesome, thank you!
-- 
Deet-doot-dot, I am a bot.
https://korg.docs.kernel.org/patchwork/pwbot.html



^ permalink raw reply	[flat|nested] 4+ messages in thread

end of thread, other threads:[~2023-01-28 13:50 UTC | newest]

Thread overview: 4+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2023-01-26 13:25 [PATCH 0/2] net: wwan: t7xx: Fix Runtime PM implementation Kornel Dulęba
2023-01-26 13:25 ` [PATCH 1/2] net: wwan: t7xx: Fix Runtime PM resume sequence Kornel Dulęba
2023-01-26 13:25 ` [PATCH 2/2] net: wwan: t7xx: Fix Runtime PM initialization Kornel Dulęba
2023-01-28 13:50 ` [PATCH 0/2] net: wwan: t7xx: Fix Runtime PM implementation patchwork-bot+netdevbpf

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).