All of lore.kernel.org
 help / color / mirror / Atom feed
From: Liang Hao <haohlliang@gmail.com>
To: linux-gpio@vger.kernel.org
Cc: Liang Hao <haohlliang@gmail.com>,
	Linus Walleij <linusw@kernel.org>,
	Bartosz Golaszewski <brgl@kernel.org>,
	linux-kernel@vger.kernel.org
Subject: [PATCH 1/2] gpiolib: Add irq_set_affinity helper for GPIO line IRQs
Date: Fri, 23 Oct 2026 23:11:04 +0800	[thread overview]
Message-ID: <20261023151209.58772-2-haohlliang@gmail.com> (raw)
In-Reply-To: <20261023151209.58772-1-haohlliang@gmail.com>

GPIO line IRQs need irq_chip->irq_set_affinity so user space can steer
affinity to the upstream controller. Hierarchical domains use
parent_data; chained controllers (parent_handler, no parent_data on the
line) store parent virqs in gpio_irq_chip instead.

Add gpiochip_irq_set_affinity() and GPIOCHIP_IRQ_AFFINITY_HELPERS.
Hierarchical lines delegate via irq_chip_set_affinity_parent().
Chained lines resolve the parent virq and call the parent
irq_chip->irq_set_affinity() directly. Return -EINVAL if the parent
virq cannot be resolved.

Signed-off-by: Liang Hao <haohlliang@gmail.com>
---
 drivers/gpio/gpiolib.c      | 79 +++++++++++++++++++++++++++++++++++++
 include/linux/gpio/driver.h |  5 +++
 2 files changed, 84 insertions(+)

diff --git a/drivers/gpio/gpiolib.c b/drivers/gpio/gpiolib.c
index 2987051d9904..0a4626579963 100644
--- a/drivers/gpio/gpiolib.c
+++ b/drivers/gpio/gpiolib.c
@@ -2104,6 +2104,85 @@ void gpiochip_irq_relres(struct irq_data *d)
 }
 EXPORT_SYMBOL(gpiochip_irq_relres);
 
+static unsigned int gpiochip_chained_parent_virq(struct gpio_chip *gc,
+						 struct irq_data *d)
+{
+	struct gpio_irq_chip *girq = &gc->irq;
+	unsigned int hwirq = irqd_to_hwirq(d);
+	struct irq_desc *desc;
+
+	if (!girq->parent_handler)
+		return 0;
+
+	if (!girq->initialized || !girq->num_parents || !girq->parents)
+		return 0;
+
+	if (girq->num_parents == 1)
+		return girq->parents[0];
+
+	if (girq->map) {
+		if (!gpiochip_irqchip_irq_valid(gc, hwirq))
+			return 0;
+		return girq->map[hwirq];
+	}
+
+	desc = irq_to_desc(d->irq);
+	if (desc && desc->parent_irq)
+		return desc->parent_irq;
+
+	return 0;
+}
+
+/**
+ * gpiochip_irq_set_affinity() - irq_chip set_affinity helper for GPIO lines
+ * @d: Pointer to the GPIO line irq_data
+ * @dest: Affinity mask to set
+ * @force: True to enforce the mask without online CPU checks
+ *
+ * Hierarchical irqdomains with parent_data delegate through
+ * irq_chip_set_affinity_parent(). GPIO irqchips that use a chained parent
+ * handler resolve the parent virq and apply the mask through the parent
+ * irq_chip as described in gpiochip_chained_parent_virq().
+ *
+ * Affinity is programmed on the parent irq, not independently per line. GPIO
+ * lines that share one parent irq also share its affinity; updating one line
+ * replaces the mask for all lines on that parent.
+ *
+ * Return: IRQ_SET_MASK_* on success, or a negative errno on error.
+ */
+int gpiochip_irq_set_affinity(struct irq_data *d,
+			      const struct cpumask *dest, bool force)
+{
+	struct gpio_chip *gc = irq_data_get_irq_chip_data(d);
+	struct irq_data *pdata;
+	unsigned int parent;
+	int ret;
+
+	if (d->parent_data)
+		return irq_chip_set_affinity_parent(d, dest, force);
+
+	parent = gpiochip_chained_parent_virq(gc, d);
+	if (!parent)
+		return -EINVAL;
+
+	pdata = irq_get_irq_data(parent);
+	if (!pdata || !pdata->chip || !pdata->chip->irq_set_affinity)
+		return -EINVAL;
+
+	ret = pdata->chip->irq_set_affinity(pdata, dest, force);
+	switch (ret) {
+	case IRQ_SET_MASK_OK:
+	case IRQ_SET_MASK_OK_NOCOPY:
+	case IRQ_SET_MASK_OK_DONE:
+		irq_data_update_effective_affinity(d,
+			irq_data_get_effective_affinity_mask(pdata));
+		return IRQ_SET_MASK_OK;
+	default:
+		return ret;
+	}
+}
+EXPORT_SYMBOL_GPL(gpiochip_irq_set_affinity);
+
 static void gpiochip_irq_mask(struct irq_data *d)
 {
 	struct gpio_chip *gc = irq_data_get_irq_chip_data(d);
diff --git a/include/linux/gpio/driver.h b/include/linux/gpio/driver.h
index 4077dc678cae..a772bf1707aa 100644
--- a/include/linux/gpio/driver.h
+++ b/include/linux/gpio/driver.h
@@ -658,12 +658,17 @@ void gpiochip_enable_irq(struct gpio_chip *gc, unsigned int offset);
 /* irq_data versions of the above */
 int gpiochip_irq_reqres(struct irq_data *data);
 void gpiochip_irq_relres(struct irq_data *data);
+int gpiochip_irq_set_affinity(struct irq_data *data,
+			      const struct cpumask *dest, bool force);
 
 /* Paste this in your irq_chip structure  */
 #define	GPIOCHIP_IRQ_RESOURCE_HELPERS					\
 		.irq_request_resources  = gpiochip_irq_reqres,		\
 		.irq_release_resources  = gpiochip_irq_relres
 
+#define GPIOCHIP_IRQ_AFFINITY_HELPERS					\
+		.irq_set_affinity = gpiochip_irq_set_affinity
+
 static inline void gpio_irq_chip_set_chip(struct gpio_irq_chip *girq,
 					  const struct irq_chip *chip)
 {
-- 
2.54.0 (Apple Git-157)


  reply	other threads:[~2026-10-23 15:14 UTC|newest]

Thread overview: 7+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-10-23 15:11 [PATCH 0/2] gpiolib: GPIO line irq_set_affinity helper Liang Hao
2026-10-23 15:11 ` Liang Hao [this message]
2026-10-23 15:35   ` [PATCH 1/2] gpiolib: Add irq_set_affinity helper for GPIO line IRQs sashiko-bot
2026-10-24  1:52   ` kernel test robot
2026-10-24  2:58   ` kernel test robot
2026-10-23 15:11 ` [PATCH 2/2] gpio: dwapb: Use gpiolib irq_set_affinity helper Liang Hao
2026-10-23 15:30   ` sashiko-bot

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20261023151209.58772-2-haohlliang@gmail.com \
    --to=haohlliang@gmail.com \
    --cc=brgl@kernel.org \
    --cc=linusw@kernel.org \
    --cc=linux-gpio@vger.kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.