[irqchip:,irq/irqchip-next] irqchip/loongson-htvec: Add suspend/resume support

Message ID 166946967944.4906.6915919359278946026.tip-bot2@tip-bot2
State New
Headers
Series [irqchip:,irq/irqchip-next] irqchip/loongson-htvec: Add suspend/resume support |

Commit Message

tip-bot2 for Thomas Gleixner Nov. 26, 2022, 1:34 p.m. UTC
  The following commit has been merged into the irq/irqchip-next branch of irqchip:

Commit-ID:     1be356c9326d68c9b0161ca004a41f203864d7ee
Gitweb:        https://git.kernel.org/pub/scm/linux/kernel/git/maz/arm-platforms/1be356c9326d68c9b0161ca004a41f203864d7ee
Author:        Huacai Chen <chenhuacai@loongson.cn>
AuthorDate:    Thu, 20 Oct 2022 15:35:24 +08:00
Committer:     Marc Zyngier <maz@kernel.org>
CommitterDate: Sat, 26 Nov 2022 13:09:25 

irqchip/loongson-htvec: Add suspend/resume support

Add suspend/resume support for HTVEC irqchip, which is needed for
upcoming suspend/hibernation.

Signed-off-by: Huacai Chen <chenhuacai@loongson.cn>
Signed-off-by: Marc Zyngier <maz@kernel.org>
Link: https://lore.kernel.org/r/20221020073527.541845-2-chenhuacai@loongson.cn
---
 drivers/irqchip/irq-loongson-htvec.c | 27 +++++++++++++++++++++++++++-
 1 file changed, 27 insertions(+)
  

Patch

diff --git a/drivers/irqchip/irq-loongson-htvec.c b/drivers/irqchip/irq-loongson-htvec.c
index 8b06082..fc8bf1f 100644
--- a/drivers/irqchip/irq-loongson-htvec.c
+++ b/drivers/irqchip/irq-loongson-htvec.c
@@ -16,6 +16,7 @@ 
 #include <linux/of_address.h>
 #include <linux/of_irq.h>
 #include <linux/of_platform.h>
+#include <linux/syscore_ops.h>
 
 /* Registers */
 #define HTVEC_EN_OFF		0x20
@@ -29,6 +30,7 @@  struct htvec {
 	void __iomem		*base;
 	struct irq_domain	*htvec_domain;
 	raw_spinlock_t		htvec_lock;
+	u32			saved_vec_en[HTVEC_MAX_PARENT_IRQ];
 };
 
 static struct htvec *htvec_priv;
@@ -156,6 +158,29 @@  static void htvec_reset(struct htvec *priv)
 	}
 }
 
+static int htvec_suspend(void)
+{
+	int i;
+
+	for (i = 0; i < htvec_priv->num_parents; i++)
+		htvec_priv->saved_vec_en[i] = readl(htvec_priv->base + HTVEC_EN_OFF + 4 * i);
+
+	return 0;
+}
+
+static void htvec_resume(void)
+{
+	int i;
+
+	for (i = 0; i < htvec_priv->num_parents; i++)
+		writel(htvec_priv->saved_vec_en[i], htvec_priv->base + HTVEC_EN_OFF + 4 * i);
+}
+
+static struct syscore_ops htvec_syscore_ops = {
+	.suspend = htvec_suspend,
+	.resume = htvec_resume,
+};
+
 static int htvec_init(phys_addr_t addr, unsigned long size,
 		int num_parents, int parent_irq[], struct fwnode_handle *domain_handle)
 {
@@ -188,6 +213,8 @@  static int htvec_init(phys_addr_t addr, unsigned long size,
 
 	htvec_priv = priv;
 
+	register_syscore_ops(&htvec_syscore_ops);
+
 	return 0;
 
 iounmap_base: