Linux-ARM-Kernel Archive on lore.kernel.org
 help / color / mirror / Atom feed
* Re: [PATCH] [RFC] gpiolib: introduce gpio_name() helper
From: Geert Uytterhoeven @ 2026-06-29 15:29 UTC (permalink / raw)
  To: Arnd Bergmann
  Cc: Linus Walleij, Bartosz Golaszewski, Arnd Bergmann,
	Marcel Holtmann, MyungJoo Ham, Chanwoo Choi, Geert Uytterhoeven,
	Andy Shevchenko, Dmitry Torokhov, Ulf Hansson, linux-bluetooth,
	linux-kernel, linux-gpio, dri-devel, linux-i2c, linux-iio,
	linux-input, linux-mmc, linux-arm-kernel, linux-pm, linux-usb
In-Reply-To: <20260629135917.1308621-1-arnd@kernel.org>

Hi Arnd,

On Mon, 29 Jun 2026 at 15:59, Arnd Bergmann <arnd@kernel.org> wrote:
> From: Arnd Bergmann <arnd@arndb.de>
>
> Most remaining users of desc_to_gpio() only call it for printing debug
> information.
>
> Replace this with a new gpiod_name() helper that returns the
> gpio_desc->name string after checking the gpio_desc pointer.
>
> Signed-off-by: Arnd Bergmann <arnd@arndb.de>

Thanks for your patch!

> Not sure if this the way we want to take this, or if the gpio name is
> an appropriate replacement in debug printk.
>
> Since most of the callers of desc_to_gpio() and gpio_to_desc() are
> otherwise in drivers that already depend on CONFIG_GPIOLIB_LEGACY and
> include linux/gpio/legacy.h, only a handful of instances remain that
> are otherwise in files that otherwise only use the descriptor interfaces:

> --- a/drivers/gpio/gpio-aggregator.c
> +++ b/drivers/gpio/gpio-aggregator.c
> @@ -758,8 +758,8 @@ int gpiochip_fwd_desc_add(struct gpiochip_fwd *fwd, struct gpio_desc *desc,
>
>         fwd->descs[offset] = desc;
>
> -       dev_dbg(chip->parent, "%u => gpio %d irq %d\n", offset,
> -               desc_to_gpio(desc), gpiod_to_irq(desc));
> +       dev_dbg(chip->parent, "%u => gpio %s irq %d\n", offset,
> +               gpiod_name(desc), gpiod_to_irq(desc));
>
>         return 0;
>  }

Before, this printed:

    gpio-aggregator gpio-aggregator.1: 0 => gpio 589 irq 188
    gpio-aggregator gpio-aggregator.1: 1 => gpio 590 irq 189

After, this prints:

    gpio-aggregator gpio-aggregator.1: 0 => gpio (null) irq 188
    gpio-aggregator gpio-aggregator.1: 1 => gpio (null) irq 189

Same results for instantiation using sysfs or configfs[1], although
the latter does have optional support for specifying the name.

[1] Documentation/admin-guide/gpio/gpio-aggregator.rst

Gr{oetje,eeting}s,

                        Geert

-- 
Geert Uytterhoeven -- There's lots of Linux beyond ia32 -- geert@linux-m68k.org

In personal conversations with technical people, I call myself a hacker. But
when I'm talking to journalists I just say "programmer" or something like that.
                                -- Linus Torvalds


^ permalink raw reply

* Re: [PATCH v3 0/5] remoteproc: cleanup shared carveout and resource-table helpers
From: Mathieu Poirier @ 2026-06-29 15:36 UTC (permalink / raw)
  To: Ben Levinsky
  Cc: Bjorn Andersson, linux-remoteproc, Frank Li, Sascha Hauer,
	Pengutronix Kernel Team, Fabio Estevam, Geert Uytterhoeven,
	Magnus Damm, Patrice Chotard, Maxime Coquelin, Alexandre Torgue,
	Arnaud Pouliquen, Daniel Baluta, Tanmay Shah, imx,
	linux-arm-kernel, linux-kernel, linux-renesas-soc, linux-stm32
In-Reply-To: <20260529021637.2077602-1-ben.levinsky@amd.com>

Applied.

Thanks,
Mathieu

On Thu, May 28, 2026 at 07:16:32PM -0700, Ben Levinsky wrote:
> This series is a preparatory remoteproc cleanup split out from review of
> the AMD BRAM-based remoteproc series.
> 
> During review, there was a request to move the duplicated plain
> ioremap_wc()/iounmap() carveout callbacks into common code and to
> factor the "missing resource table is OK" ELF parsing path into a
> common helper as well. There was also a request to send that cleanup as
> its own patchset first, with the AMD BRAM series respun afterwards on
> top once this cleanup is merged.
> 
> This version keeps the same overall cleanup goals as v2, but reworks
> the optional resource-table pieces based on follow-up review:
> 
>   - reshape the optional resource-table helper in patch 4 into the thin
>     parse_fw() wrapper form suggested on the thread
>   - switch the patch 5 clients over to that helper shape directly,
>     without post-helper rproc->table_ptr checks
>   - keep the driver-local parse_fw() wrappers and their existing log
>     messages and severity choices
>   - retain as much of the existing per-driver parse_fw() logic and code
>     placement as possible while moving the missing-table handling
>     through the shared helper
> 
> This series now does that in five patches:
> 
>   1. add common subsystem-private callbacks for the exact-match
>      wc-ioremap carveout case
>   2. switch the in-tree exact-match users over to those callbacks
>   3. mark carveouts mapped through the shared wc-ioremap helper as
>      iomem so the framework uses the proper I/O accessors
>   4. add a common helper for drivers that treat a missing ELF resource
>      table as optional while keeping per-driver logging decisions local
>   5. switch the matching in-tree drivers over to that helper while
>      keeping thin local parse_fw() wrappers
> 
> For the carveout map/unmap cleanup, this series covers the exact-match
> users called out in review: xlnx_r5_remoteproc, rcar_rproc,
> st_remoteproc, stm32_rproc, imx_rproc, and imx_dsp_rproc. The zynqmp R5
> TCM mapping path is left alone because it also clears the mapped memory
> and is not an exact match.
> 
> For the optional resource-table handling, this series converts
> xlnx_r5_remoteproc, rcar_rproc, stm32_rproc, imx_rproc, and
> imx_dsp_rproc. st_remoteproc is intentionally left unchanged because its
> parse_fw() callback also builds carveouts and is therefore not a direct
> match for the helper introduced here.
> 
> Changes in v3:
>   - rework patch 4 so the optional resource-table helper matches the
>     thin-wrapper form suggested in review
>   - note that patch 4 still triggers a checkpatch --strict warning for
>     the flow-control macro form, but that implementation follows the
>     maintainer's review suggestion for the thin parse_fw() wrapper shape
>   - update patch 5 to use that helper shape directly in the client
>     parse_fw() callbacks
>   - drop the post-helper rproc->table_ptr checks from the converted
>     drivers
>   - keep the converted parse_fw() wrappers otherwise close to their
>     existing structure and placement
>   - test xlnx_r5_remoteproc on the latest tree with firmware images
>     both with and without an ELF resource table
> 
> Changes in v2:
>   - split the mem->is_iomem change out into a separate patch
>   - add a common error message on ioremap_wc() failure
>   - drop logging from the optional resource-table helper
>   - keep driver-local parse_fw() wrappers to preserve per-platform
>     missing-resource-table logging policy
> 
> Ben Levinsky (5):
>   remoteproc: add common wc-ioremap carveout callbacks
>   remoteproc: switch exact-match drivers to wc-ioremap callbacks
>   remoteproc: mark wc-ioremap carveouts as iomem
>   remoteproc: add helper for optional ELF resource tables
>   remoteproc: switch drivers to optional resource-table helper
> 
>  drivers/remoteproc/imx_dsp_rproc.c       | 41 +++-----------
>  drivers/remoteproc/imx_rproc.c           | 40 ++------------
>  drivers/remoteproc/rcar_rproc.c          | 41 ++------------
>  drivers/remoteproc/remoteproc_internal.h | 38 +++++++++++++
>  drivers/remoteproc/st_remoteproc.c       | 31 +----------
>  drivers/remoteproc/stm32_rproc.c         | 39 ++-----------
>  drivers/remoteproc/xlnx_r5_remoteproc.c  | 70 +++++-------------------
>  7 files changed, 73 insertions(+), 227 deletions(-)
> 
> -- 
> 2.34.1


^ permalink raw reply

* Re: [PATCH v12 2/2] arm64: dts: imx8ulp: Add MIPI CSI-2 and ISI nodes
From: Frank Li @ 2026-06-29 15:29 UTC (permalink / raw)
  To: Guoniu Zhou
  Cc: Rob Herring, Krzysztof Kozlowski, Conor Dooley, Frank Li,
	Sascha Hauer, Pengutronix Kernel Team, Laurent Pinchart,
	Fabio Estevam, Philipp Zabel, Mauro Carvalho Chehab, Hans Verkuil,
	devicetree, imx, linux-arm-kernel, linux-kernel, linux-media
In-Reply-To: <20260424-csi2_imx8ulp-v12-2-da148eabc035@oss.nxp.com>

On Fri, Apr 24, 2026 at 02:49:51PM +0800, Guoniu Zhou wrote:
> The MIPI CSI-2 in the i.MX8ULP is almost identical to the version present
> in the i.MX8QXP/QM and is routed to the ISI. Add both the MIPI CSI-2 and
> ISI nodes, disabled by default, as they require an attached camera sensor
> to function.
>
> Reviewed-by: Frank Li <Frank.Li@nxp.com>
> Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> Signed-off-by: Guoniu Zhou <guoniu.zhou@oss.nxp.com>
> ---

This part of the previous version patch should be applied. If missed
something, please send new patch, which base on my dt64 branch.

Frank

> Changes in v12:
> - Swap ISI axi and apb clocks to align with dt-binding requirements
> - Update commit message
>
> Changes in v11:
> - Removed #include <dt-bindings/reset/imx8ulp-pcc-reset.h> which was
>   deleted by Rob's dt-bindings cleanup series [2]
> - Replaced reset macros with numeric values and added comments to
>   document the reset indices
>
> Changes in v1-v10:
> - See cover letter
> ---
>  arch/arm64/boot/dts/freescale/imx8ulp.dtsi | 66 ++++++++++++++++++++++++++++++
>  1 file changed, 66 insertions(+)
>
> diff --git a/arch/arm64/boot/dts/freescale/imx8ulp.dtsi b/arch/arm64/boot/dts/freescale/imx8ulp.dtsi
> index 9b5d98766512..c5cae7675ce0 100644
> --- a/arch/arm64/boot/dts/freescale/imx8ulp.dtsi
> +++ b/arch/arm64/boot/dts/freescale/imx8ulp.dtsi
> @@ -859,6 +859,72 @@ spdif: spdif@2dab0000 {
>  				dma-names = "rx", "tx";
>  				status = "disabled";
>  			};
> +
> +			isi: isi@2dac0000 {
> +				compatible = "fsl,imx8ulp-isi";
> +				reg = <0x2dac0000 0x10000>;
> +				interrupts = <GIC_SPI 119 IRQ_TYPE_LEVEL_HIGH>;
> +				clocks = <&cgc2 IMX8ULP_CLK_LPAV_AXI_DIV>,
> +					 <&pcc5 IMX8ULP_CLK_ISI>;
> +				clock-names = "axi", "apb";
> +				power-domains = <&scmi_devpd IMX8ULP_PD_ISI>;
> +				status = "disabled";
> +
> +				ports {
> +					#address-cells = <1>;
> +					#size-cells = <0>;
> +
> +					port@0 {
> +						reg = <0>;
> +						isi_in: endpoint {
> +							remote-endpoint = <&mipi_csi_out>;
> +						};
> +					};
> +				};
> +			};
> +
> +			mipi_csi: csi@2daf0000 {
> +				compatible = "fsl,imx8ulp-mipi-csi2";
> +				reg = <0x2daf0000 0x10000>,
> +				      <0x2dad0000 0x10000>;
> +				clocks = <&pcc5 IMX8ULP_CLK_CSI>,
> +					 <&pcc5 IMX8ULP_CLK_CSI_CLK_ESC>,
> +					 <&pcc5 IMX8ULP_CLK_CSI_CLK_UI>,
> +					 <&pcc5 IMX8ULP_CLK_CSI_REGS>;
> +				clock-names = "core", "esc", "ui", "pclk";
> +				assigned-clocks = <&pcc5 IMX8ULP_CLK_CSI>,
> +						  <&pcc5 IMX8ULP_CLK_CSI_CLK_ESC>,
> +						  <&pcc5 IMX8ULP_CLK_CSI_CLK_UI>,
> +						  <&pcc5 IMX8ULP_CLK_CSI_REGS>;
> +				assigned-clock-parents = <&cgc2 IMX8ULP_CLK_PLL4_PFD1_DIV1>,
> +							 <&cgc2 IMX8ULP_CLK_PLL4_PFD1_DIV2>,
> +							 <&cgc2 IMX8ULP_CLK_PLL4_PFD0_DIV1>;
> +				assigned-clock-rates = <200000000>,
> +						       <80000000>,
> +						       <100000000>,
> +						       <79200000>;
> +				power-domains = <&scmi_devpd IMX8ULP_PD_MIPI_CSI>;
> +				resets = <&pcc5 5>,	/* PCC5_CSI_REGS_SWRST */
> +					 <&pcc5 6>;	/* PCC5_CSI_SWRST> */
> +				status = "disabled";
> +
> +				ports {
> +					#address-cells = <1>;
> +					#size-cells = <0>;
> +
> +					port@0 {
> +						reg = <0>;
> +					};
> +
> +					port@1 {
> +						reg = <1>;
> +
> +						mipi_csi_out: endpoint {
> +							remote-endpoint = <&isi_in>;
> +						};
> +					};
> +				};
> +			};
>  		};
>
>  		gpiod: gpio@2e200000 {
>
> --
> 2.34.1
>


^ permalink raw reply

* [PATCH v2] misc: xilinx_sdfec: validate LDPC code register offsets
From: Yousef Alhouseen @ 2026-06-29 15:28 UTC (permalink / raw)
  To: Derek Kiernan, Dragan Cvetic
  Cc: Arnd Bergmann, Greg Kroah-Hartman, Michal Simek, linux-arm-kernel,
	linux-kernel, Yousef Alhouseen

The LDPC code register helpers check the target MMIO address after
adding code_id * XSDFEC_LDPC_REG_JUMP to the register base. code_id is
supplied through the ioctl path, so the multiplication and addition can
wrap before the bounds check.

Validate the code_id against the register window size before computing
the final address, then write using the checked address.

Signed-off-by: Yousef Alhouseen <alhouseenyousef@gmail.com>
---
Changes in v2:
- Guard against swapped high/base constants before subtracting.
- Preserve debug output and include offset/base/high in the message.

 drivers/misc/xilinx_sdfec.c | 74 +++++++++++++++++--------------------
 1 file changed, 34 insertions(+), 40 deletions(-)

diff --git a/drivers/misc/xilinx_sdfec.c b/drivers/misc/xilinx_sdfec.c
index 3135ba3a58ee..e73a139f3ffc 100644
--- a/drivers/misc/xilinx_sdfec.c
+++ b/drivers/misc/xilinx_sdfec.c
@@ -456,10 +456,25 @@ static int xsdfec_get_turbo(struct xsdfec_dev *xsdfec, void __user *arg)
 	return err;
 }
 
+static int xsdfec_ldpc_reg_addr(struct xsdfec_dev *xsdfec, u32 base, u32 high,
+				u32 offset, u32 *addr)
+{
+	if (high < base || offset > (high - base) / XSDFEC_LDPC_REG_JUMP) {
+		dev_dbg(xsdfec->dev,
+			"LDPC register offset %u outside space 0x%x-0x%x",
+			offset, base, high);
+		return -EINVAL;
+	}
+
+	*addr = base + offset * XSDFEC_LDPC_REG_JUMP;
+	return 0;
+}
+
 static int xsdfec_reg0_write(struct xsdfec_dev *xsdfec, u32 n, u32 k, u32 psize,
 			     u32 offset)
 {
 	u32 wdata;
+	u32 addr;
 
 	if (n < XSDFEC_REG0_N_MIN || n > XSDFEC_REG0_N_MAX || psize == 0 ||
 	    (n > XSDFEC_REG0_N_MUL_P * psize) || n <= k || ((n % psize) != 0)) {
@@ -476,17 +491,11 @@ static int xsdfec_reg0_write(struct xsdfec_dev *xsdfec, u32 n, u32 k, u32 psize,
 	k = k << XSDFEC_REG0_K_LSB;
 	wdata = k | n;
 
-	if (XSDFEC_LDPC_CODE_REG0_ADDR_BASE + (offset * XSDFEC_LDPC_REG_JUMP) >
-	    XSDFEC_LDPC_CODE_REG0_ADDR_HIGH) {
-		dev_dbg(xsdfec->dev, "Writing outside of LDPC reg0 space 0x%x",
-			XSDFEC_LDPC_CODE_REG0_ADDR_BASE +
-				(offset * XSDFEC_LDPC_REG_JUMP));
+	if (xsdfec_ldpc_reg_addr(xsdfec, XSDFEC_LDPC_CODE_REG0_ADDR_BASE,
+				 XSDFEC_LDPC_CODE_REG0_ADDR_HIGH, offset,
+				 &addr))
 		return -EINVAL;
-	}
-	xsdfec_regwrite(xsdfec,
-			XSDFEC_LDPC_CODE_REG0_ADDR_BASE +
-				(offset * XSDFEC_LDPC_REG_JUMP),
-			wdata);
+	xsdfec_regwrite(xsdfec, addr, wdata);
 	return 0;
 }
 
@@ -494,6 +503,7 @@ static int xsdfec_reg1_write(struct xsdfec_dev *xsdfec, u32 psize,
 			     u32 no_packing, u32 nm, u32 offset)
 {
 	u32 wdata;
+	u32 addr;
 
 	if (psize < XSDFEC_REG1_PSIZE_MIN || psize > XSDFEC_REG1_PSIZE_MAX) {
 		dev_dbg(xsdfec->dev, "Psize is not in range");
@@ -510,17 +520,11 @@ static int xsdfec_reg1_write(struct xsdfec_dev *xsdfec, u32 psize,
 	nm = (nm << XSDFEC_REG1_NM_LSB) & XSDFEC_REG1_NM_MASK;
 
 	wdata = nm | no_packing | psize;
-	if (XSDFEC_LDPC_CODE_REG1_ADDR_BASE + (offset * XSDFEC_LDPC_REG_JUMP) >
-	    XSDFEC_LDPC_CODE_REG1_ADDR_HIGH) {
-		dev_dbg(xsdfec->dev, "Writing outside of LDPC reg1 space 0x%x",
-			XSDFEC_LDPC_CODE_REG1_ADDR_BASE +
-				(offset * XSDFEC_LDPC_REG_JUMP));
+	if (xsdfec_ldpc_reg_addr(xsdfec, XSDFEC_LDPC_CODE_REG1_ADDR_BASE,
+				 XSDFEC_LDPC_CODE_REG1_ADDR_HIGH, offset,
+				 &addr))
 		return -EINVAL;
-	}
-	xsdfec_regwrite(xsdfec,
-			XSDFEC_LDPC_CODE_REG1_ADDR_BASE +
-				(offset * XSDFEC_LDPC_REG_JUMP),
-			wdata);
+	xsdfec_regwrite(xsdfec, addr, wdata);
 	return 0;
 }
 
@@ -529,6 +533,7 @@ static int xsdfec_reg2_write(struct xsdfec_dev *xsdfec, u32 nlayers, u32 nmqc,
 			     u32 max_schedule, u32 offset)
 {
 	u32 wdata;
+	u32 addr;
 
 	if (nlayers < XSDFEC_REG2_NLAYERS_MIN ||
 	    nlayers > XSDFEC_REG2_NLAYERS_MAX) {
@@ -563,17 +568,11 @@ static int xsdfec_reg2_write(struct xsdfec_dev *xsdfec, u32 nlayers, u32 nmqc,
 	wdata = (max_schedule | no_final_parity | special_qc | norm_type |
 		 nmqc | nlayers);
 
-	if (XSDFEC_LDPC_CODE_REG2_ADDR_BASE + (offset * XSDFEC_LDPC_REG_JUMP) >
-	    XSDFEC_LDPC_CODE_REG2_ADDR_HIGH) {
-		dev_dbg(xsdfec->dev, "Writing outside of LDPC reg2 space 0x%x",
-			XSDFEC_LDPC_CODE_REG2_ADDR_BASE +
-				(offset * XSDFEC_LDPC_REG_JUMP));
+	if (xsdfec_ldpc_reg_addr(xsdfec, XSDFEC_LDPC_CODE_REG2_ADDR_BASE,
+				 XSDFEC_LDPC_CODE_REG2_ADDR_HIGH, offset,
+				 &addr))
 		return -EINVAL;
-	}
-	xsdfec_regwrite(xsdfec,
-			XSDFEC_LDPC_CODE_REG2_ADDR_BASE +
-				(offset * XSDFEC_LDPC_REG_JUMP),
-			wdata);
+	xsdfec_regwrite(xsdfec, addr, wdata);
 	return 0;
 }
 
@@ -581,20 +580,15 @@ static int xsdfec_reg3_write(struct xsdfec_dev *xsdfec, u8 sc_off, u8 la_off,
 			     u16 qc_off, u32 offset)
 {
 	u32 wdata;
+	u32 addr;
 
 	wdata = ((qc_off << XSDFEC_REG3_QC_OFF_LSB) |
 		 (la_off << XSDFEC_REG3_LA_OFF_LSB) | sc_off);
-	if (XSDFEC_LDPC_CODE_REG3_ADDR_BASE + (offset * XSDFEC_LDPC_REG_JUMP) >
-	    XSDFEC_LDPC_CODE_REG3_ADDR_HIGH) {
-		dev_dbg(xsdfec->dev, "Writing outside of LDPC reg3 space 0x%x",
-			XSDFEC_LDPC_CODE_REG3_ADDR_BASE +
-				(offset * XSDFEC_LDPC_REG_JUMP));
+	if (xsdfec_ldpc_reg_addr(xsdfec, XSDFEC_LDPC_CODE_REG3_ADDR_BASE,
+				 XSDFEC_LDPC_CODE_REG3_ADDR_HIGH, offset,
+				 &addr))
 		return -EINVAL;
-	}
-	xsdfec_regwrite(xsdfec,
-			XSDFEC_LDPC_CODE_REG3_ADDR_BASE +
-				(offset * XSDFEC_LDPC_REG_JUMP),
-			wdata);
+	xsdfec_regwrite(xsdfec, addr, wdata);
 	return 0;
 }
 
-- 
2.54.0


^ permalink raw reply related

* Re: [PATCH 3/5] media: nxp: imx8-isi: Add 16-bit raw Bayer format support
From: Frank Li @ 2026-06-29 14:57 UTC (permalink / raw)
  To: guoniu.zhou
  Cc: Laurent Pinchart, Mauro Carvalho Chehab, Frank Li, Sascha Hauer,
	Pengutronix Kernel Team, Fabio Estevam, Christian Hemp,
	Stefan Riedmueller, Jacopo Mondi, Dong Aisheng, Guoniu Zhou,
	linux-media, imx, linux-arm-kernel, linux-kernel, Laurentiu Palcu
In-Reply-To: <20260629-isi-v1-3-deebfdb1b07b@oss.nxp.com>

On Mon, Jun 29, 2026 at 03:44:57PM +0800, guoniu.zhou@oss.nxp.com wrote:
>
> Add support for 16-bit raw Bayer formats (SBGGR16, SGBRG16, SGRBG16,
> SRGGB16) to both the pipeline subdev and video capture interface.
>
> These formats are commonly used by high-end image sensors that output
> 16-bit raw data, enabling the ISI to process and capture full dynamic
> range from such sensors.
>
> Signed-off-by: Laurentiu Palcu <laurentiu.palcu@oss.nxp.com>
> Signed-off-by: Guoniu Zhou <guoniu.zhou@oss.nxp.com>
> ---

Reviewed-by: Frank Li <Frank.Li@nxp.com>

>  .../media/platform/nxp/imx8-isi/imx8-isi-pipe.c    | 24 +++++++++++++++
>  .../media/platform/nxp/imx8-isi/imx8-isi-video.c   | 36 ++++++++++++++++++++++
>  2 files changed, 60 insertions(+)
>
> diff --git a/drivers/media/platform/nxp/imx8-isi/imx8-isi-pipe.c b/drivers/media/platform/nxp/imx8-isi/imx8-isi-pipe.c
> index 2d0843c86534..e58925d71164 100644
> --- a/drivers/media/platform/nxp/imx8-isi/imx8-isi-pipe.c
> +++ b/drivers/media/platform/nxp/imx8-isi/imx8-isi-pipe.c
> @@ -179,6 +179,30 @@ static const struct mxc_isi_bus_format_info mxc_isi_bus_formats[] = {
>  		.pads		= BIT(MXC_ISI_PIPE_PAD_SINK)
>  				| BIT(MXC_ISI_PIPE_PAD_SOURCE),
>  		.encoding	= MXC_ISI_ENC_RAW,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SBGGR16_1X16,
> +		.output		= MEDIA_BUS_FMT_SBGGR16_1X16,
> +		.pads		= BIT(MXC_ISI_PIPE_PAD_SINK)
> +				| BIT(MXC_ISI_PIPE_PAD_SOURCE),
> +		.encoding	= MXC_ISI_ENC_RAW,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SGBRG16_1X16,
> +		.output		= MEDIA_BUS_FMT_SGBRG16_1X16,
> +		.pads		= BIT(MXC_ISI_PIPE_PAD_SINK)
> +				| BIT(MXC_ISI_PIPE_PAD_SOURCE),
> +		.encoding	= MXC_ISI_ENC_RAW,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SGRBG16_1X16,
> +		.output		= MEDIA_BUS_FMT_SGRBG16_1X16,
> +		.pads		= BIT(MXC_ISI_PIPE_PAD_SINK)
> +				| BIT(MXC_ISI_PIPE_PAD_SOURCE),
> +		.encoding	= MXC_ISI_ENC_RAW,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SRGGB16_1X16,
> +		.output		= MEDIA_BUS_FMT_SRGGB16_1X16,
> +		.pads		= BIT(MXC_ISI_PIPE_PAD_SINK)
> +				| BIT(MXC_ISI_PIPE_PAD_SOURCE),
> +		.encoding	= MXC_ISI_ENC_RAW,
>  	},
>  	/* JPEG */
>  	{
> diff --git a/drivers/media/platform/nxp/imx8-isi/imx8-isi-video.c b/drivers/media/platform/nxp/imx8-isi/imx8-isi-video.c
> index fe4adfa3a1f0..5eb448f4c26f 100644
> --- a/drivers/media/platform/nxp/imx8-isi/imx8-isi-video.c
> +++ b/drivers/media/platform/nxp/imx8-isi/imx8-isi-video.c
> @@ -356,6 +356,42 @@ static const struct mxc_isi_format_info mxc_isi_formats[] = {
>  		.color_planes	= 1,
>  		.depth		= { 16 },
>  		.encoding	= MXC_ISI_ENC_RAW,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SBGGR16_1X16,
> +		.fourcc		= V4L2_PIX_FMT_SBGGR16,
> +		.type		= MXC_ISI_VIDEO_CAP,
> +		.isi_out_format	= CHNL_IMG_CTRL_FORMAT_RAW16,
> +		.mem_planes	= 1,
> +		.color_planes	= 1,
> +		.depth		= { 16 },
> +		.encoding	= MXC_ISI_ENC_RAW,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SGBRG16_1X16,
> +		.fourcc		= V4L2_PIX_FMT_SGBRG16,
> +		.type		= MXC_ISI_VIDEO_CAP,
> +		.isi_out_format	= CHNL_IMG_CTRL_FORMAT_RAW16,
> +		.mem_planes	= 1,
> +		.color_planes	= 1,
> +		.depth		= { 16 },
> +		.encoding	= MXC_ISI_ENC_RAW,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SGRBG16_1X16,
> +		.fourcc		= V4L2_PIX_FMT_SGRBG16,
> +		.type		= MXC_ISI_VIDEO_CAP,
> +		.isi_out_format	= CHNL_IMG_CTRL_FORMAT_RAW16,
> +		.mem_planes	= 1,
> +		.color_planes	= 1,
> +		.depth		= { 16 },
> +		.encoding	= MXC_ISI_ENC_RAW,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SRGGB16_1X16,
> +		.fourcc		= V4L2_PIX_FMT_SRGGB16,
> +		.type		= MXC_ISI_VIDEO_CAP,
> +		.isi_out_format	= CHNL_IMG_CTRL_FORMAT_RAW16,
> +		.mem_planes	= 1,
> +		.color_planes	= 1,
> +		.depth		= { 16 },
> +		.encoding	= MXC_ISI_ENC_RAW,
>  	},
>  	/* JPEG */
>  	{
>
> --
> 2.34.1
>
>


^ permalink raw reply

* [PATCH] Bluetooth: Properly disable remote wakeup for MT7922/MT7925 on Ryzen platform
From: Rong Zhang @ 2026-06-29 15:27 UTC (permalink / raw)
  To: Marcel Holtmann, Luiz Augusto von Dentz, Matthias Brugger,
	AngeloGioacchino Del Regno
  Cc: Luiz Augusto von Dentz, Chris Lu (陸稚泓),
	Will-CY Lee (李政穎),
	SS Wu (巫憲欣), linux-bluetooth, linux-kernel,
	linux-arm-kernel, linux-mediatek, Rong Zhang

It is reported that a remote wakeup could cause MT7922/MT7925's btusb
interface completely unresponsive. Resetting the xHCI root hub doesn't
help at all, and recovering from such a state needs a power cycle.

All reports seen to be relevant to Ryzen-based laptops. These NICs are
usually used as OEM components thanks to some sort of reference designs.

Their popularity on other platforms is unclear. While there is still a
chance that the quirk may exist on other platforms, be cautious and only
apply the quirk on AMD platforms for the time being.

Meanwhile, though device_set_wakeup_capable(false) is the correct fix
for other NICs with fake remote wakeup capabilities, doing so for
MT7922/MT7925 effectively prevents it from being used as wakeup
sources as per userspace requests. Hence, return -EBUSY on runtime
suspend to prevent the interface from being autosuspended while it's
still opened, which has the same effect as
device_set_wakeup_capable(false), since disabling remote wakeup simply
causes the USB core to gate runtime autosuspend as well due to
needs_remote_wakeup == 1. The interface can be safely autosuspended as
long as remote wakeup is disabled, i.e., after closing the HCI device.

Specifically, the interface may still take the advantage of remote
wakeup in order to wake up the system from sleep if userspace has
enabled it as a wakeup source.

Fixes: e31d761628ad ("Bluetooth: btmtk: Disable remote wakeup for MT7922/MT7925")
Signed-off-by: Rong Zhang <i@rong.moe>
---
 drivers/bluetooth/btmtk.c | 10 ---------
 drivers/bluetooth/btusb.c | 57 +++++++++++++++++++++++++++++++++++++++++++----
 2 files changed, 53 insertions(+), 14 deletions(-)

diff --git a/drivers/bluetooth/btmtk.c b/drivers/bluetooth/btmtk.c
index 02a96342e964..4614434dd57b 100644
--- a/drivers/bluetooth/btmtk.c
+++ b/drivers/bluetooth/btmtk.c
@@ -1381,16 +1381,6 @@ int btmtk_usb_setup(struct hci_dev *hdev)
 		break;
 	case 0x7922:
 	case 0x7925:
-		/*
-		 * A remote wakeup could cause the device completely unresponsive, and
-		 * recovering from such a state needs a power cycle.
-		 *
-		 * Since the remote wakeup capability is super broken, just disable it
-		 * to get rid of the troubles. The device can still be autosuspended
-		 * when the bluetooth interface is closed.
-		 */
-		device_set_wakeup_capable(&btmtk_data->udev->dev, false);
-		fallthrough;
 	case 0x7961:
 	case 0x7902:
 	case 0x6639:
diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c
index 08c0a99a62c5..023ae782f41a 100644
--- a/drivers/bluetooth/btusb.c
+++ b/drivers/bluetooth/btusb.c
@@ -6,6 +6,7 @@
  *  Copyright (C) 2005-2008  Marcel Holtmann <marcel@holtmann.org>
  */
 
+#include <linux/cpufeature.h>
 #include <linux/dmi.h>
 #include <linux/module.h>
 #include <linux/usb.h>
@@ -957,6 +958,7 @@ struct qca_dump_info {
 #define BTUSB_USE_ALT3_FOR_WBS	15
 #define BTUSB_ALT6_CONTINUOUS_TX	16
 #define BTUSB_HW_SSR_ACTIVE	17
+#define BTUSB_WAKEUP_BROKEN	18
 
 struct btusb_data {
 	struct hci_dev       *hdev;
@@ -2936,10 +2938,20 @@ static int btusb_send_frame_mtk(struct hci_dev *hdev, struct sk_buff *skb)
 	}
 }
 
+static inline bool platform_is_ryzen(void)
+{
+#ifdef CONFIG_X86
+	return boot_cpu_has(X86_FEATURE_ZEN);
+#else
+	return false;
+#endif
+}
+
 static int btusb_mtk_setup(struct hci_dev *hdev)
 {
 	struct btusb_data *data = hci_get_drvdata(hdev);
 	struct btmtk_data *btmtk_data = hci_get_priv(hdev);
+	int err;
 
 	/* MediaTek WMT vendor cmd requiring below USB resources to
 	 * complete the handshake.
@@ -2956,7 +2968,29 @@ static int btusb_mtk_setup(struct hci_dev *hdev)
 		btusb_mtk_claim_iso_intf(data);
 	}
 
-	return btmtk_usb_setup(hdev);
+	err = btmtk_usb_setup(hdev);
+	if (err)
+		return err;
+
+	switch (btmtk_data->dev_id) {
+	case 0x7922:
+	case 0x7925:
+		/*
+		 * All reports seen to be relevant to Ryzen-based laptops. These
+		 * NICs are usually used as OEM components thanks to some sort
+		 * of reference designs.
+		 *
+		 * Their popularity on other platforms is unclear. While there
+		 * is still a chance that the quirk may exist on other
+		 * platforms, be cautious and only apply the quirk on AMD
+		 * platforms for the time being.
+		 */
+		if (platform_is_ryzen())
+			set_bit(BTUSB_WAKEUP_BROKEN, &data->flags);
+		break;
+	}
+
+	return 0;
 }
 
 static int btusb_mtk_shutdown(struct hci_dev *hdev)
@@ -4532,11 +4566,26 @@ static int btusb_suspend(struct usb_interface *intf, pm_message_t message)
 
 	BT_DBG("intf %p", intf);
 
-	/* Don't auto-suspend if there are connections or discovery in
-	 * progress; external suspend calls shall never fail.
+	/*
+	 * It is reported that remote wakeup events could sometimes cause some
+	 * adapters completely unresponsive. Resetting the xHCI root hub doesn't
+	 * help at all, and recovering from such a state needs a power cycle.
+	 * Since disabling remote wakeup simply causes the USB core to gate
+	 * runtime autosuspend as well due to needs_remote_wakeup == 1, let's do
+	 * this ourselves to make our life easier. The interface can be safely
+	 * autosuspended as long as remote wakeup is disabled, i.e., after
+	 * closing the HCI device.
+	 *
+	 * Don't auto-suspend if there are connections or discovery in progress.
+	 *
+	 * External suspend calls shall never fail. Specifically, a device with
+	 * broken remote wakeup may still take the advantage of remote wakeup in
+	 * order to wake up the system from sleep if userspace has enabled it as
+	 * a wakeup source.
 	 */
 	if (PMSG_IS_AUTO(message) &&
-	    (hci_conn_count(data->hdev) || hci_discovery_active(data->hdev)))
+	    ((test_bit(BTUSB_WAKEUP_BROKEN, &data->flags) && data->intf->needs_remote_wakeup) ||
+	     hci_conn_count(data->hdev) || hci_discovery_active(data->hdev)))
 		return -EBUSY;
 
 	if (data->suspend_count++)

---
base-commit: dc59e4fea9d83f03bad6bddf3fa2e52491777482
change-id: 230ba8c9-btmtk-ryzen-remote-wakeup-055a407682ef

Thanks,
Rong



^ permalink raw reply related

* Re: [PATCH 2/2] arm64: topology: read CPPC FFH feedback counters in one operation
From: Sumit Gupta @ 2026-06-29 15:27 UTC (permalink / raw)
  To: Pengjie Zhang, catalin.marinas, will, rafael, lenb, robert.moore,
	beata.michalska, zhenglifeng1, zhanjie9, cuiyunhui
  Cc: linux-arm-kernel, linux-kernel, linux-acpi, acpica-devel,
	linuxarm, jonathan.cameron, prime.zeng, wanghuiqiang, xuwei5,
	lihuisong, yubowen8, wangzhi12, linux-tegra@vger.kernel.org
In-Reply-To: <20260410094145.4132082-3-zhangpengjie2@huawei.com>


On 10/04/26 15:11, Pengjie Zhang wrote:
> External email: Use caution opening links or attachments
>
>
> arm64 implements CPPC FFH feedback-counter reads using AMU counters.
> Because those counters must be sampled on the target CPU, reading the
> delivered and reference counters separately widens the observation window
> between them.
>
> Implement the paired FFH feedback-counter read hook on arm64 and sample
> both AMU counters together before decoding the requested CPC register
> values.
>
> Also factor the FFH bitfield extraction logic into a helper and reuse
> it from the existing single-counter FFH read path.
>
> Signed-off-by: Pengjie Zhang <zhangpengjie2@huawei.com>
> ---
>   arch/arm64/kernel/topology.c | 75 ++++++++++++++++++++++++++++++++----
>   1 file changed, 67 insertions(+), 8 deletions(-)
>
> diff --git a/arch/arm64/kernel/topology.c b/arch/arm64/kernel/topology.c
> index b32f13358fbb..b90a767b2a1f 100644
> --- a/arch/arm64/kernel/topology.c
> +++ b/arch/arm64/kernel/topology.c
> @@ -50,6 +50,16 @@ struct amu_cntr_sample {
>          unsigned long   last_scale_update;
>   };
>
> +struct amu_ffh_ctrs {
> +       u64 corecnt;
> +       u64 constcnt;
> +};
> +
> +enum cpc_ffh_ctr_id {
> +       CPC_FFH_CTR_CORE  = 0x0,
> +       CPC_FFH_CTR_CONST = 0x1,
> +};
> +
>   static DEFINE_PER_CPU_SHARED_ALIGNED(struct amu_cntr_sample, cpu_amu_samples);
>
>   void update_freq_counters_refs(void)
> @@ -397,7 +407,7 @@ static void cpu_read_constcnt(void *val)
>   }
>
>   static inline
> -int counters_read_on_cpu(int cpu, smp_call_func_t func, u64 *val)
> +int counters_read_on_cpu(int cpu, smp_call_func_t func, void *val)
>   {
>          /*
>           * Abort call on counterless CPU.
> @@ -447,24 +457,73 @@ bool cpc_ffh_supported(void)
>          return true;
>   }
>
> +static void amu_read_core_const_ctrs(void *val)
> +{
> +       struct amu_ffh_ctrs *ctrs = val;
> +
> +       cpu_read_constcnt(&ctrs->constcnt);
> +       cpu_read_corecnt(&ctrs->corecnt);
> +}

Any reason to flip the order?
Harmless as they are read back to back, but better to add a comment
if it's intentional.

Thanks,
Sumit
....




^ permalink raw reply

* Re: [PATCH 3/4] dt-bindings: ipmi: Add optional LPC properties to ASPEED BT devices
From: Conor Dooley @ 2026-06-29 15:26 UTC (permalink / raw)
  To: yc_hsieh
  Cc: Corey Minyard, Rob Herring, Krzysztof Kozlowski, Conor Dooley,
	Joel Stanley, Andrew Jeffery, openipmi-developer, linux-kernel,
	devicetree, linux-arm-kernel, linux-aspeed
In-Reply-To: <20260629-aspeed-bt-bmc-multichannel-v1-3-fc23ee337f7a@aspeedtech.com>

[-- Attachment #1: Type: text/plain, Size: 2563 bytes --]

On Mon, Jun 29, 2026 at 02:49:00PM +0800, Yu-Che Hsieh via B4 Relay wrote:
> From: Yu-Che Hsieh <yc_hsieh@aspeedtech.com>
> 
> Allocating IO and IRQ resources to LPC devices is in-theory an operation
> 
> for the host, however ASPEED systems describe these resources through
> 
> BMC-internal configuration, as already supported by the ASPEED KCS BMC
> 
> binding.
> 
> Add aspeed,lpc-io-reg and aspeed,lpc-interrupts to the ASPEED BT BMC
> 
> binding so firmware can describe the host LPC IO address and SerIRQ
> 
> configuration using the same properties as KCS devices.
> 
> Signed-off-by: Yu-Che Hsieh <yc_hsieh@aspeedtech.com>
> ---
>  .../bindings/ipmi/aspeed,ast2400-ibt-bmc.yaml       | 21 +++++++++++++++++++++
>  1 file changed, 21 insertions(+)
> 
> diff --git a/Documentation/devicetree/bindings/ipmi/aspeed,ast2400-ibt-bmc.yaml b/Documentation/devicetree/bindings/ipmi/aspeed,ast2400-ibt-bmc.yaml
> index c4f7cdbbe16b..1803c6bbae93 100644
> --- a/Documentation/devicetree/bindings/ipmi/aspeed,ast2400-ibt-bmc.yaml
> +++ b/Documentation/devicetree/bindings/ipmi/aspeed,ast2400-ibt-bmc.yaml
> @@ -25,6 +25,24 @@ properties:
>    interrupts:
>      maxItems: 1
>  
> +  aspeed,lpc-io-reg:
> +    $ref: /schemas/types.yaml#/definitions/uint32-array
> +    maxItems: 1
> +    description: |
> +      The host CPU LPC IO address for the BT device.
> +
> +  aspeed,lpc-interrupts:
> +    $ref: /schemas/types.yaml#/definitions/uint32-array
> +    minItems: 2
> +    maxItems: 2
> +    description: |
> +      A 2-cell property expressing the LPC SerIRQ number and the interrupt
> +      level/sense encoding (specified in the standard fashion).
> +
> +      Note that the generated interrupt is issued from the BMC to the host, and
> +      thus the target interrupt controller is not captured by the BMC's
> +      devicetree.

Why can these two properties not just be an additional reg and
interrupts entry?


Cheers,
Conor.

> +
>  required:
>    - compatible
>    - reg
> @@ -35,10 +53,13 @@ additionalProperties: false
>  examples:
>    - |
>      #include <dt-bindings/clock/aspeed-clock.h>
> +    #include <dt-bindings/interrupt-controller/irq.h>
>  
>      bt@1e789140 {
>          compatible = "aspeed,ast2400-ibt-bmc";
>          reg = <0x1e789140 0x18>;
>          interrupts = <8>;
>          clocks = <&syscon ASPEED_CLK_GATE_LCLK>;
> +        aspeed,lpc-io-reg = <0xe4>;
> +        aspeed,lpc-interrupts = <10 IRQ_TYPE_LEVEL_LOW>;
>      };
> 
> -- 
> 2.34.1
> 
> 

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 228 bytes --]

^ permalink raw reply

* Re: (subset) [PATCH v12 0/2] Add i.MX8ULP ISI and CSI-2 support
From: Frank.Li @ 2026-06-29 15:25 UTC (permalink / raw)
  To: Rob Herring, Krzysztof Kozlowski, Conor Dooley, Sascha Hauer,
	Pengutronix Kernel Team, Laurent Pinchart, Fabio Estevam,
	Philipp Zabel, Mauro Carvalho Chehab, Hans Verkuil, Guoniu Zhou
  Cc: Frank Li, devicetree, imx, linux-arm-kernel, linux-kernel,
	linux-media, stable
In-Reply-To: <20260424-csi2_imx8ulp-v12-0-da148eabc035@oss.nxp.com>

From: Frank Li <Frank.Li@nxp.com>


On Fri, 24 Apr 2026 14:49:49 +0800, Guoniu Zhou wrote:
> Add support for the Image Sensing Interface (ISI) and MIPI CSI-2 receiver
> on i.MX8ULP.

Applied, thanks!

[1/2] media: dt-bindings: nxp,imx8-isi: Drop fsl,blk-ctrl requirement for i.MX8ULP
      commit: 2514a04c7455d0bbf41b3b1bfc3af2984ed6a7cc

Best regards,
-- 
Frank Li <Frank.Li@nxp.com>


^ permalink raw reply

* Re: [PATCH v2 3/6] clk: sunxi-ng: sun6i-rtc: Add feature bit for IOSC calibration
From: Chen-Yu Tsai @ 2026-06-29 15:25 UTC (permalink / raw)
  To: Jerome Brunet
  Cc: Junhui Liu, Alexandre Belloni, Rob Herring, Krzysztof Kozlowski,
	Conor Dooley, Jernej Skrabec, Samuel Holland, Michael Turquette,
	Stephen Boyd, Maxime Ripard, linux-rtc, devicetree,
	linux-arm-kernel, linux-sunxi, linux-kernel, linux-clk
In-Reply-To: <20260629-a733-rtc-v2-3-7b72112784f8@baylibre.com>

On Mon, Jun 29, 2026 at 8:42 PM Jerome Brunet <jbrunet@baylibre.com> wrote:
>
> From: Junhui Liu <junhui.liu@pigmoral.tech>
>
> The sun6i-rtc CCU driver currently uses a global static variable to
> denote whether calibration is supported, which makes IOSC operations
> tightly coupled to this file.
>
> Convert this into a feature bit to decouple the logic. This allows the
> IOSC clock code to be moved into a shared module for reuse by other SoCs.
>
> Signed-off-by: Junhui Liu <junhui.liu@pigmoral.tech>
> Signed-off-by: Jerome Brunet<jbrunet@baylibre.com>

Reviewed-by: Chen-Yu Tsai <wens@kernel.org>


^ permalink raw reply

* Re: [PATCH 05/37] drm/display: bridge-connector: split code creating the connector to a subfunction
From: Luca Ceresoli @ 2026-06-29 15:23 UTC (permalink / raw)
  To: Laurent Pinchart, Luca Ceresoli
  Cc: Maxime Ripard, Maarten Lankhorst, Thomas Zimmermann, David Airlie,
	Simona Vetter, Andrzej Hajda, Neil Armstrong, Robert Foss,
	Jonas Karlman, Jernej Skrabec, Inki Dae, Jagan Teki,
	Marek Szyprowski, Marek Vasut, Stefan Agner, Frank Li,
	Sascha Hauer, Pengutronix Kernel Team, Fabio Estevam, Hui Pu,
	Ian Ray, Thomas Petazzoni, dri-devel, linux-kernel, imx,
	linux-arm-kernel
In-Reply-To: <20260629144443.GA3106950@killaraus.ideasonboard.com>

On Mon Jun 29, 2026 at 4:44 PM CEST, Laurent Pinchart wrote:
> On Fri, Jun 26, 2026 at 06:51:14PM +0200, Luca Ceresoli wrote:
>> On Fri Jun 26, 2026 at 4:38 PM CEST, Maxime Ripard wrote:
>> > On Fri, Jun 26, 2026 at 04:16:39PM +0200, Luca Ceresoli wrote:
>> >> On Fri Jun 26, 2026 at 12:09 PM CEST, Maxime Ripard wrote:
>> >> > On Wed, Jun 24, 2026 at 05:47:10PM +0200, Luca Ceresoli wrote:
>> >> >> On Wed Jun 24, 2026 at 1:41 PM CEST, Maxime Ripard wrote:
>> >> >> > On Fri, Jun 12, 2026 at 02:56:24PM +0200, Luca Ceresoli wrote:
>> >> >> >> On Mon Jun 8, 2026 at 1:40 PM CEST, Maxime Ripard wrote:
>> >> >> >> > On Tue, May 19, 2026 at 12:37:22PM +0200, Luca Ceresoli wrote:
>> >> >> >> >> In preparation to introduce bridge hotplug, split out from
>> >> >> >> >> drm_bridge_connector_init() the code adding the drm_connector into a
>> >> >> >> >> dedicated function. This will be needed to be able to add (and re-add) the
>> >> >> >> >> connector from different code paths.
>> >> >> >> >
>> >> >> >> > Same story here, explaining what you need later on that calls for that
>> >> >> >> > change would be nice.
>> >> >> >>
>> >> >> >> Here's a more verbose version:
>> >> >> >>
>> >> >> >>     Currently drm_bridge_connector_init() does two things:
>> >> >> >>
>> >> >> >>      * allocate and initialize the drm_bridge_connector
>> >> >> >>        (which embeds a drm_connector)
>> >> >> >>      * initialize and register the embedded drm_connector
>> >> >> >>
>> >> >> >>     For bridge hotplug we need to separate these two actions:
>> >> >> >>
>> >> >> >>      * the drm_connector needs to be added and removed at any time based on
>> >> >> >>        hotplug events
>> >> >> >>      * the drm_bridge_connector is designated to create and remove the
>> >> >> >>        drm_connector, so it must be persistent for the card lifetime
>> >> >> >>
>> >> >> >>     As the lifetimes of drm_bridge_connector and drm_connector become
>> >> >> >>     different, we need to create them in different moments.
>> >> >> >>
>> >> >> >>     In preparation to support that, split out from
>> >> >> >>     drm_bridge_connector_init() the code adding the drm_connector into a
>> >> >> >>     dedicated function. No functional changes, just moving code around for
>> >> >> >>     now. A future commit will make the drm_connector be created based on
>> >> >> >>     hotplug events.
>> >> >> >>
>> >> >> >> Looks good?
>> >> >> >
>> >> >> > The message itself, yes, thanks.
>> >> >> >
>> >> >> > However, I have questions now :)
>> >> >> >
>> >> >> > Do we really expect drm_bridge_connector to stick around when a bridge
>> >> >> > gets unplugged? If so, how does it cope with having, say, an HDMI
>> >> >> > connector, and then swapping out the hotplugged part for an LVDS one?
>> >> >> > Does the HDMI connector sticks around indefinitely?
>> >> >>
>> >> >> In your example, the HDMI drm_connector would be unregistered and put on
>> >> >> hotunplug. Its allocation will stick around until the last put but that's
>> >> >> quite irrelevant. Then, on plugging the LVDS addon, a new LVDS
>> >> >> drm_connector will be created and registered.
>> >> >>
>> >> >> > *Especially* if we're using overlays for this, I'd expect everything
>> >> >> >  after the first hotplugged bridge to be destroyed, no?
>> >> >>
>> >> >> As said, it would be unregistered immediately but might be freed later on
>> >> >> if still refcounted.
>> >> >>
>> >> >> This is visible in patches 36+15, the path to follow is:
>> >> >>
>> >> >>  drm_bridge_connector_handle_event(event = DRM_BRIDGE_DETACHED) [patch 36]
>> >> >>  -> drm_bridge_connector_dynconn_release()                      [patch 15]
>> >> >>
>> >> >> Does this solve your concern?
>> >> >
>> >> > Not really, I'm talking about drm_bridge_connector. The fact that
>> >> > bridges are destroyed make sense to me. The fact that
>> >> > drm_bridge_connector sticks around doesn't. It's supposed to be a
>> >> > connector for bridges. If you don't have bridges because they got
>> >> > destroyed, and connector, drm_bridge_connector doesn't have a reason to
>> >> > exist anymore, unless it's drm_bridge_hotplug in a trench coat :)
>> >>
>> >> It is not a hotplug-bridge in a trench coat, no :) The code is clear about
>> >> this.
>> >>
>> >> I'd say with this series a "drm_bridge_connector" is just becoming
>> >> something more (perhaps something else too). Somewhat as "a drm_bridge is
>> >> either a bridge or something else". :)
>> >>
>> >>
>> >> But let's leave names aside for a moment. If just looking at the current
>> >> code, the drm_bridge_connector is "a handler, owned by the card/encoder and
>> >> having the same lifetime, which takes care of drm_connector
>> >> creation/destruction at card probe/removal".
>> >>
>> >> What we need now is just the same plug " and on hotplug events" appended.
>> >>
>> >> So in both cases there needs to be "a handler persitent with the card".
>> >>
>> >> Do we agree so far?
>> >
>> > Ish. If we go for that, then we need to update the name.
>>
>> drm_connector_manager?
>> drm_bridge_connector_manager?
>
> I'm fine with a rename. When developing drm_bridge_connector I've always
> envisioned it as code that manages the creation of a connector for a
> chain of bridges. In particular, the drm_bridge_connector object is
> *not* and has never been a bridge.

That's my understanding of the drm_bridge_connector too.

> Ideally all this should move to the DRM core and be transparent to
> drivers. Drivers could set a flag somewhere to opt-in for connectors
> managed by the DRM core.

Not sure I got what you mean.

Currently drivers "opt-in" by:

 1. passing DRM_BRIDGE_ATTACH_NO_CONNECTOR to drm_bridge_attach()
 2. instantiating a drm_bridge_connector via drm_bridge_connector_init()

Do you suggest changing that, so 1 and 2 are done transparently if the
driver sets a new flag?

>> > drm_bridge_connector for something that is neither a bridge or a
>> > connector is not great.
>> >
>> > But even then, I'm not even sure why we need to have that "manager" in
>> > the first place. You want to make bridges be aware if they are the last
>> > in the chain or not.
>
> I don't think bridges should be aware of whether or not they're the last
> one in the chain.

I proposed that, not because I "want" that but because for hotplug we need
a way to know whether a DRM video pipeline is complete in the hardware or
not. This is used in patch 36:

	/* Add the connector if the pipeline is now complete */
	if (drm_bridge_connector_pipeline_is_complete(bridge_connector))
		drm_bridge_connector_add_connector(bridge_connector);

In other words, on a hotplug event (some new hardware was added), check
whether the card is now complete _in the hardware_, and if it is create a
drm_connector.

In this series I proposed implementing it via a new .is_tail callback, that
has been rejected during Dispaly Next Hackfest [0].

The idea that popped up there was that bridge drivers could expose the
fwnode handler to the port@<N>/endpoint pointing to the next bridge. I
liked the idea but then I realized it would hardly fly in complex cases
like bridges with dual-LVDS-or-two-single-LVDS output, e.g. SN65DSI84.

So Maxime proposed [1]:

 ) Thanks for the notes, I think I largely agree with the discussion.
 ) Reading through it, I thought it would be nice for a new callback called
 ) get_next_bridge or something that would return either an error, NULL or a
 ) (refcounted) pointer to the next bridge in the chain. And have some kind
 ) of special error (ENODEV?) when the bridge should be there but isn't
 ) (and thus the chain isn't complete).

To me, "Making bridges aware if they are the last in the chain or not" is
not a goal. It is just a technique to implement
drm_bridge_connector_pipeline_is_complete().  I'm happy to implementing it
in a different way if you have better ideas, but I haven't.

[0] https://lore.kernel.org/lkml/DIXTUCXAU68V.1T7X89LMEUF2F@bootlin.com/
[1] https://lore.kernel.org/lkml/20260624-vagabond-neon-gorilla-cd6487@houat/

Luca

--
Luca Ceresoli, Bootlin
Embedded Linux and Kernel engineering
https://bootlin.com


^ permalink raw reply

* Re: [PATCH 0/2] clocksource/drivers/arm_arch_timer_mmio: Restore support for early init
From: Stephan Gerhold @ 2026-06-29 15:23 UTC (permalink / raw)
  To: Marc Zyngier
  Cc: Mark Rutland, Daniel Lezcano, Thomas Gleixner, Sudeep Holla,
	linux-arm-kernel, linux-kernel, linux-arm-msm, Jack Matthews,
	Konrad Dybcio
In-Reply-To: <87qzmd89ih.wl-maz@kernel.org>

On Thu, Jun 11, 2026 at 02:57:42PM +0100, Marc Zyngier wrote:
> On Thu, 11 Jun 2026 09:47:58 +0100,
> Stephan Gerhold <stephan.gerhold@linaro.org> wrote:
> > 
> > On Thu, Jun 11, 2026 at 08:59:19AM +0100, Marc Zyngier wrote:
> > > On Wed, 10 Jun 2026 18:53:09 +0100,
> > > Stephan Gerhold <stephan.gerhold@linaro.org> wrote:
> > > > 
> > > > Jack reported a regression for some single-core Qualcomm platforms (e.g.
> > > > MDM9625, MDM9607) that no longer boot because no timers can be found during
> > > > early boot [1].
> > > 
> > > Again, this is *not* a regression. These machines were *never*
> > > supported upstream.
> > > 
> > 
> > Sorry, I'll reword this next time. MDM9607 does have all required
> > drivers and compatibles upstream already and is just missing the actual
> > DT so it does feel somewhat supported to me, but I'm fine treating this
> > as a feature extension without stable backporting etc.
> 
> "Supported" has a different definition for me. Cortex-A5 without the
> A9-style TWD was so far never seen in the wild. The Generic MMIO timer
> was introduced way after Cortex-A5 shipped, and was designed to work
> with the CPU timers, making this QCOM contraption a franken-hack.
> 
> So calling this supported is very much pushing the boundaries of what
> was supposed to be put together.
> 

Got it.

> >
> > > > These platforms rely on an obscure timer setup where the
> > > > global Arm MMIO timer (arm,armv7-timer-mem) is used as the only available
> > > > timer for the CPU. This setup used to work fine until commit 0f67b56d84b4
> > > > ("clocksource/drivers/arm_arch_timer_mmio: Switch over to standalone
> > > > driver") when the early timer initialization using TIMER_OF_DECLARE() was
> > > > removed when moving to the standalone MMIO driver.
> > > > 
> > > > There doesn't seem to be any other usable CPU timer on those platforms, so
> > > > this series restores the early timer support using TIMER_OF_DECLARE()
> > > > inside the new standalone arm_arch_timer_mmio driver. This is pretty ugly,
> > > > but I could not think of a better solution so far. I tried to keep the
> > > > ugliness for the two probe paths as limited as possible. :-)
> > > > 
> > > > If someone has a better idea how to solve this, I would be happy to try it.
> > > 
> > > I would suggest finding out what is the latest point in the init
> > > sequence where the timer can be probed without preventing boot.
> > > 
> > 
> > It doesn't get far without having any timer:
> > 
> > [    0.000000] timer_probe: no matching timers found
> > [    0.000000] entering initcall level: console
> > [    0.000000] calling  con_init+0x0/0x354 @ 0
> > [    0.000000] Console: colour dummy device 80x30
> > [    0.000000] initcall con_init+0x0/0x354 returned 0 after 0 usecs
> > [    0.000000] sched_clock: 32 bits at 300 Hz, resolution 3333333ns, wraps every 7158278824300949ns
> > [    0.000000] Calibrating delay loop... 
> > <board hangs>
> >
> 
> This is nothing that "lpj=[some value]" on the command line can't help
> getting past.
> 
> > If you look at start_kernel() in init/main.c it's basically time_init()
> > that would normally probe the TIMER_OF_DECLARE() timers and
> > calibrate_delay() that needs some timer to finish. There is also
> > random_init() that comes directly after time_init(), which already wants
> > to have access to timestamp counters. I don't see any other suitable
> > place to hook into. :-/
> 
> None of that should be a problem. I can boot a hacked arm64 kernel
> without any timer all the way to the point where it is waiting for a
> tick to enter the scheduler and run userspace. There's no reason why
> 32bit can't do something similar. Heck, 32bit doesn't even have a
> standard timer to rely on, so that's very much possible to do.
> 
> Can you at least give it a try?
> 

Thanks for the suggestion and sorry for the delay! I started testing
this, but then ran out of time before my vacation when trying to get the
CP15 timer working on the Cortex-A7.

With lpj=2658304, it proceeds until raid6_select_algo for me with my
current kernel config. I probably don't need the raid6 stuff on this
platform. Also, raid6_select_algo is subsys_initcall() so if I move
arm_arch_timer_mmio to core_initcall() instead of
builtin_platform_driver() (device_initcall()) it does indeed boot
successfully to the userspace login with the lpi= parameter. Nice!

> > 
> > I also don't see any other timer we could use, at least for MDM9625.
> > It's a single-core Cortex-A5 and the downstream kernel defines only the
> > arm,armv7-timer-mem, which seems to be used for everything... (The
> > situation for MDM9607 is a bit different, but not any less messy,
> > unfortunately.)
> 
> MDM9607 appears to be a Cortex-A7, so it *definitely* has all the
> bells and whistles that we need. The DT I found doesn't make describe
> the timer, but it is absolutely part of the CPU.
> 

The CP15 timer is indeed *definitely* there for the Cortex-A7 in
MDM9607, but it's also *definitely* not working for me ... :(

As you saw, it's not documented anywhere for MDM9607. I tried to enable
it a few years ago already, but I couldn't get it working. I tried again
and it's still unusable. The CP15 timer is certainly there and it does
tick just fine. It also signals interrupts (ISTATUS gets set).
But I can't find the interrupts in the GIC:

 - I tried some common options (PPI 13+14+11+10, 2+3+4+1), but it hangs
   in raid6_select_algo like above (no timer interrupts).

 - I created some brute force probing code that fires the timer and then
   scans literally all GIC IRQs using GICD_ISPENDR. Nothing.
   (It finds the correct PPIs on other platforms...)

 - I asked Konrad if he can find something helpful in the chip
   documentation, but apparently there is no clear mention of the CP15
   interrupts there either ....

In other words, it looks like whoever designed this hardware didn't
think it would be useful to hook up the CPU interrupt lines to the GIC.
Or something like that ... Unfortunately, this means that we probably
need the MMIO timer even for the Cortex-A7 in MDM9607. :(


Since you mentioned that we don't need a timer early, I played a bit
with using the CP15 timer only as clocksource (without interrupt). That
seems works quite well actually to bypass the delay calibration problem.
In fact, then it skips the calibration entirely and uses (presumably
more accurate?) timer-based delay loops instead:

[    0.000000] clocksource: jiffies: mask: 0xffffffff max_cycles: 0xffffffff, max_idle_ns: 6370867519511994 ns
[    0.000000] arch_timer: No interrupt available, NOT giving up
[    0.000000] arch_timer: cp15 timer running at 19.20MHz (virt).
[    0.000000] clocksource: arch_sys_counter: mask: 0xffffffffffffff max_cycles: 0x46d987e47, max_idle_ns: 440795202767 ns
[    0.000002] sched_clock: 56 bits at 19MHz, resolution 52ns, wraps every 4398046511078ns
[    0.010688] Switching to timer-based delay loop, resolution 52ns
[    0.019028] Console: colour dummy device 80x30
[    0.024932] Calibrating delay loop (skipped), value calculated using timer frequency.. 38.00 BogoMIPS (lpj=64000)
...

Still need the core_initcall() change, since it looks like that
raid6_select_algo code really wants to have some timer interrupts.

Aside from that it's just a couple of if conditions in the
arm_arch_timer driver to bypass the interrupt handling, but I imagine
you wouldn't be very happy about that kind of butchering either ...? :/

> As for the A5, if we can't get this machine to use the driver as is
> without butchering it and going 15 years back in time, then I'd rather
> hack together a minimal driver that only this contraption will make
> use of, and be done with it.

To be fair, if you look at PATCH 2/2 in this series, the actual MMIO
handling is completely unchanged. It's just some reshuffling of the
init/parsing code. The primary annoyance is probably use of pr_*()
rather than dev_*() logging and some minor manual resource management.
We could duplicate the parsing functions to avoid this reshuffling, but
the actual MMIO code would be still exactly the same. I'm not sure if
we should duplicate that.

Thanks,
Stephan


^ permalink raw reply

* Re: [PATCH] [RFC] gpiolib: introduce gpio_name() helper
From: Andy Shevchenko @ 2026-06-29 15:23 UTC (permalink / raw)
  To: Arnd Bergmann
  Cc: Linus Walleij, Bartosz Golaszewski, Arnd Bergmann,
	Marcel Holtmann, MyungJoo Ham, Chanwoo Choi, Geert Uytterhoeven,
	Andy Shevchenko, Dmitry Torokhov, Ulf Hansson, linux-bluetooth,
	linux-kernel, linux-gpio, dri-devel, linux-i2c, linux-iio,
	linux-input, linux-mmc, linux-arm-kernel, linux-pm, linux-usb
In-Reply-To: <20260629135917.1308621-1-arnd@kernel.org>

On Mon, Jun 29, 2026 at 03:56:29PM +0200, Arnd Bergmann wrote:

> Most remaining users of desc_to_gpio() only call it for printing debug
> information.
> 
> Replace this with a new gpiod_name() helper that returns the
> gpio_desc->name string after checking the gpio_desc pointer.

Oh, that's nice!

...

> +/**
> + * gpiod_name() - get a name to print for a gpio descriptor
> + * @desc: gpio or NULL pointer to query
> + *
> + * Returns:
> + * The desc->name field or a dummy string for unknown GPIOs.
> + */
> +const char *gpiod_name(const struct gpio_desc *desc)
> +{
> +	return desc ? desc->name : "(no gpio)";

Can we get into here with wrong (error pointer descriptor)? Shouldn't you call
one of validate_desc() / VALIDATE_DESC()?

Also not sure if "(no gpio)" is a good choice. "not requested"? "not provided"?

> +}

...

> +static inline const char *gpiod_name(const struct gpio_desc *desc)
> +{
> +	WARN_ON(desc);
> +	return "(no gpio)";

Hmm... This will be a second copy with a slight potential of going apart from
the other case. Perhaps a #define? (Yes, yes, I understand that there are pros
and cons, in particular readability with define is questionable.)

> +}

-- 
With Best Regards,
Andy Shevchenko




^ permalink raw reply

* Re: [PATCH rc v6 4/7] iommu/arm-smmu-v3: Skip EVTQ/PRIQ setup in kdump kernel
From: Pranjal Shrivastava @ 2026-06-29 15:15 UTC (permalink / raw)
  To: Nicolin Chen
  Cc: will, robin.murphy, jgg, joro, kees, baolu.lu, kevin.tian,
	miko.lenczewski, smostafa, linux-arm-kernel, iommu, linux-kernel,
	stable, jamien
In-Reply-To: <1280ac4fdb37f998fd6dcb2bf8f4437283279395.1779265413.git.nicolinc@nvidia.com>

On Wed, May 20, 2026 at 10:03:21AM -0700, Nicolin Chen wrote:
> In kdump cases, the crashed kernel's CDs and page tables can be corrupted,
> which could trigger event spamming. Also, we cannot serve page requests.
> 
> Skip the EVTQ/PRIQ setup entirely rather than enabling then disabling them.
> 
> Also add some inline comments explaining that.
> 
> Fixes: b63b3439b856 ("iommu/arm-smmu-v3: Abort all transactions if SMMU is enabled in kdump kernel")
> Cc: stable@vger.kernel.org # v6.12+
> Suggested-by: Kevin Tian <kevin.tian@intel.com>
> Reviewed-by: Kevin Tian <kevin.tian@intel.com>
> Reviewed-by: Jason Gunthorpe <jgg@nvidia.com>
> Signed-off-by: Nicolin Chen <nicolinc@nvidia.com>
> ---
>  drivers/iommu/arm/arm-smmu-v3/arm-smmu-v3.c | 43 +++++++++++++--------
>  1 file changed, 27 insertions(+), 16 deletions(-)
> 
> diff --git a/drivers/iommu/arm/arm-smmu-v3/arm-smmu-v3.c b/drivers/iommu/arm/arm-smmu-v3/arm-smmu-v3.c
> index e00b28e36f9c4..3f22949391c82 100644
> --- a/drivers/iommu/arm/arm-smmu-v3/arm-smmu-v3.c
> +++ b/drivers/iommu/arm/arm-smmu-v3/arm-smmu-v3.c
> @@ -5161,21 +5161,35 @@ static int arm_smmu_device_reset(struct arm_smmu_device *smmu)
>  	cmd.opcode = CMDQ_OP_TLBI_NSNH_ALL;
>  	arm_smmu_cmdq_issue_cmd_with_sync(smmu, &cmd);
>  
> -	/* Event queue */
> -	writeq_relaxed(smmu->evtq.q.q_base, smmu->base + ARM_SMMU_EVTQ_BASE);
> -	writel_relaxed(smmu->evtq.q.llq.prod, smmu->page1 + ARM_SMMU_EVTQ_PROD);
> -	writel_relaxed(smmu->evtq.q.llq.cons, smmu->page1 + ARM_SMMU_EVTQ_CONS);
> -
> -	enables |= CR0_EVTQEN;
> -	ret = arm_smmu_write_reg_sync(smmu, enables, ARM_SMMU_CR0,
> -				      ARM_SMMU_CR0ACK);
> -	if (ret) {
> -		dev_err(smmu->dev, "failed to enable event queue\n");
> -		return ret;
> +	/*
> +	 * Event queue
> +	 *
> +	 * Do not enable in a kdump case, as the crashed kernel's CDs and page
> +	 * tables might be corrupted, triggering event spamming.
> +	 */
> +	if (!is_kdump_kernel()) {
> +		writeq_relaxed(smmu->evtq.q.q_base,
> +			       smmu->base + ARM_SMMU_EVTQ_BASE);
> +		writel_relaxed(smmu->evtq.q.llq.prod,
> +			       smmu->page1 + ARM_SMMU_EVTQ_PROD);
> +		writel_relaxed(smmu->evtq.q.llq.cons,
> +			       smmu->page1 + ARM_SMMU_EVTQ_CONS);
> +
> +		enables |= CR0_EVTQEN;
> +		ret = arm_smmu_write_reg_sync(smmu, enables, ARM_SMMU_CR0,
> +					      ARM_SMMU_CR0ACK);

Nit:
I believe only the write_reg_sync(CR0) should be under this if condition
do we see any weird behavior if we perform the reg writes in
kdump_kernel?

> +		if (ret) {
> +			dev_err(smmu->dev, "failed to enable event queue\n");
> +			return ret;
> +		}
>  	}
>  
> -	/* PRI queue */
> -	if (smmu->features & ARM_SMMU_FEAT_PRI) {
> +	/*
> +	 * PRI queue
> +	 *
> +	 * Do not enable in a kdump case, as we cannot serve page requests.
> +	 */
> +	if (!is_kdump_kernel() && (smmu->features & ARM_SMMU_FEAT_PRI)) {
>  		writeq_relaxed(smmu->priq.q.q_base,
>  			       smmu->base + ARM_SMMU_PRIQ_BASE);
>  		writel_relaxed(smmu->priq.q.llq.prod,
> @@ -5208,9 +5222,6 @@ static int arm_smmu_device_reset(struct arm_smmu_device *smmu)
>  		return ret;
>  	}
>  
> -	if (is_kdump_kernel())
> -		enables &= ~(CR0_EVTQEN | CR0_PRIQEN);
> -
>  	/* Enable the SMMU interface */
>  	enables |= CR0_SMMUEN;
>  	ret = arm_smmu_write_reg_sync(smmu, enables, ARM_SMMU_CR0,
> -- 
> 2.43.0
> 

Apart from that nit, 

Reviewed-by: Pranjal Shrivastava <praan@google.com>

Thanks,
Praan


^ permalink raw reply

* Re: [PATCH 5/5] media: nxp: imx8-isi: Add additional 32-bit RGB format support
From: Frank Li @ 2026-06-29 15:10 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Laurent Pinchart, Mauro Carvalho Chehab, Frank Li, Sascha Hauer,
	Pengutronix Kernel Team, Fabio Estevam, Christian Hemp,
	Stefan Riedmueller, Jacopo Mondi, Dong Aisheng, Guoniu Zhou,
	linux-media, imx, linux-arm-kernel, linux-kernel, Robert Chiras
In-Reply-To: <20260629-isi-v1-5-deebfdb1b07b@oss.nxp.com>

On Mon, Jun 29, 2026 at 03:44:59PM +0800, Guoniu Zhou wrote:
> Add support for additional 32-bit RGB pixel formats (BGRA32, RGBA32,
> BGRX32, RGBX32, ARGB2101010) and extend existing ABGR32 format with
> full memory-to-memory capabilities to meet Android requirements.
>
> All formats support capture, M2M input, and M2M output operations,
> enabling complete format conversion pipelines.
>
> Signed-off-by: Guoniu Zhou <guoniu.zhou@oss.nxp.com>
> Signed-off-by: Robert Chiras <robert.chiras@nxp.com>
> ---

Reviewed-by: Frank Li <Frank.Li@nxp.com>

>  .../media/platform/nxp/imx8-isi/imx8-isi-video.c   | 59 +++++++++++++++++++++-
>  1 file changed, 58 insertions(+), 1 deletion(-)
>
> diff --git a/drivers/media/platform/nxp/imx8-isi/imx8-isi-video.c b/drivers/media/platform/nxp/imx8-isi/imx8-isi-video.c
> index 05b51b98344b..ef638af350fe 100644
> --- a/drivers/media/platform/nxp/imx8-isi/imx8-isi-video.c
> +++ b/drivers/media/platform/nxp/imx8-isi/imx8-isi-video.c
> @@ -160,12 +160,69 @@ static const struct mxc_isi_format_info mxc_isi_formats[] = {
>  	}, {
>  		.mbus_code	= MEDIA_BUS_FMT_RGB888_1X24,
>  		.fourcc		= V4L2_PIX_FMT_ABGR32,
> -		.type		= MXC_ISI_VIDEO_CAP | MXC_ISI_VIDEO_M2M_CAP,
> +		.type		= MXC_ISI_VIDEO_CAP | MXC_ISI_VIDEO_M2M_OUT
> +				| MXC_ISI_VIDEO_M2M_CAP,
> +		.isi_in_format	= CHNL_MEM_RD_CTRL_IMG_TYPE_XRGB8,
>  		.isi_out_format	= CHNL_IMG_CTRL_FORMAT_ARGB8888,
>  		.mem_planes	= 1,
>  		.color_planes	= 1,
>  		.depth		= { 32 },
>  		.encoding	= MXC_ISI_ENC_RGB,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_RGB888_1X24,
> +		.fourcc		= V4L2_PIX_FMT_BGRA32,
> +		.type		= MXC_ISI_VIDEO_CAP | MXC_ISI_VIDEO_M2M_OUT
> +				| MXC_ISI_VIDEO_M2M_CAP,
> +		.isi_in_format	= CHNL_MEM_RD_CTRL_IMG_TYPE_RGBX8,
> +		.isi_out_format	= CHNL_IMG_CTRL_FORMAT_RGBA8888,
> +		.mem_planes	= 1,
> +		.color_planes	= 1,
> +		.depth		= { 32 },
> +		.encoding	= MXC_ISI_ENC_RGB,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_RGB888_1X24,
> +		.fourcc		= V4L2_PIX_FMT_RGBA32,
> +		.type		= MXC_ISI_VIDEO_CAP | MXC_ISI_VIDEO_M2M_OUT
> +				| MXC_ISI_VIDEO_M2M_CAP,
> +		.isi_in_format	= CHNL_MEM_RD_CTRL_IMG_TYPE_XBGR8,
> +		.isi_out_format	= CHNL_IMG_CTRL_FORMAT_ABGR8888,
> +		.mem_planes	= 1,
> +		.color_planes	= 1,
> +		.depth		= { 32 },
> +		.encoding	= MXC_ISI_ENC_RGB,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_RGB888_1X24,
> +		.fourcc		= V4L2_PIX_FMT_BGRX32,
> +		.type		= MXC_ISI_VIDEO_CAP | MXC_ISI_VIDEO_M2M_OUT
> +				| MXC_ISI_VIDEO_M2M_CAP,
> +		.isi_in_format	= CHNL_MEM_RD_CTRL_IMG_TYPE_RGBX8,
> +		.isi_out_format	= CHNL_IMG_CTRL_FORMAT_RGBX888,
> +		.mem_planes	= 1,
> +		.color_planes	= 1,
> +		.depth		= { 32 },
> +		.encoding	= MXC_ISI_ENC_RGB,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_RGB888_1X24,
> +		.fourcc		= V4L2_PIX_FMT_RGBX32,
> +		.type		= MXC_ISI_VIDEO_CAP | MXC_ISI_VIDEO_M2M_OUT
> +				| MXC_ISI_VIDEO_M2M_CAP,
> +		.isi_in_format	= CHNL_MEM_RD_CTRL_IMG_TYPE_XBGR8,
> +		.isi_out_format	= CHNL_IMG_CTRL_FORMAT_XBGR888,
> +		.mem_planes	= 1,
> +		.color_planes	= 1,
> +		.depth		= { 32 },
> +		.encoding	= MXC_ISI_ENC_RGB,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_RGB888_1X24,
> +		.fourcc		= V4L2_PIX_FMT_ARGB2101010,
> +		.type		= MXC_ISI_VIDEO_CAP | MXC_ISI_VIDEO_M2M_OUT
> +				| MXC_ISI_VIDEO_M2M_CAP,
> +		.isi_in_format	= CHNL_MEM_RD_CTRL_IMG_TYPE_A2RGB10,
> +		.isi_out_format	= CHNL_IMG_CTRL_FORMAT_A2RGB10,
> +		.mem_planes	= 1,
> +		.color_planes	= 1,
> +		.depth		= { 32 },
> +		.encoding	= MXC_ISI_ENC_RGB,
>  	},
>  	/*
>  	 * RAW formats
>
> --
> 2.34.1
>
>


^ permalink raw reply

* Re: [PATCH 2/2] iio: adc: Add Nuvoton MA35D1 EADC driver
From: David Lechner @ 2026-06-29 15:09 UTC (permalink / raw)
  To: Chi-Wen Weng, jic23, robh, krzk+dt, conor+dt
  Cc: nuno.sa, andy, linux-arm-kernel, linux-iio, devicetree,
	linux-kernel, cwweng
In-Reply-To: <5e65eabd-699b-4587-bb38-d8ef5c6d2aaa@gmail.com>

On 6/29/26 2:32 AM, Chi-Wen Weng wrote:
> Hi David,
> 
> Thanks for the detailed review.
> 
> After looking at your comments and the other review feedback, I plan to
> simplify v2 and limit the initial upstream driver to direct raw reads for
> the external single-ended ADC channels.
> 
> In v2, I will drop the triggered buffer support, the device trigger and
> the differential channel support for now. Buffered capture and
> differential inputs can be added later as follow-up patches once the
> scan sequencing, trigger model and differential pair constraints are
> handled properly.

This is a simple/small enough driver that it would be fine to still
keep all of those features in v2. It would still be fine to split
them into separate patches, but you could still send them all as
a single patch series.

> 
> This also means that the scan buffer layout comments will no longer
> apply to v2, since the triggered-buffer path will be removed from the
> initial submission.
> 
> I will address the other driver comments in v2:
> - drop the unused struct device pointer,
> - remove the triggered-buffer and trigger-related Kconfig selects,
> - switch the register access helpers to regmap,
> - avoid forcing the external reference path unconditionally,
> - add optional vref-supply handling,
> - add IIO_CHAN_INFO_SCALE based on the selected reference source,
> - use the internal reference when no vref-supply is provided,
> - add a named macro for the sample-time field,
> - drop the unused channel address field,
> - drop datasheet_name from the initial driver,
> - use device_for_each_child_node_scoped(),
> - use devm_mutex_init(),
> - keep only INDIO_DIRECT_MODE for the initial driver.
> 
> For the firmware-described channels, v2 will only accept the external
> ADC input channels 0 to 7. The internal VBAT channel and differential
> inputs will not be described or exposed by the initial driver.
> 
> Thanks,
> Chi-Wen
> 
> David Lechner 於 2026/6/28 上午 04:52 寫道:
>> On 6/25/26 6:06 AM, Chi-Wen Weng wrote:
>>> From: Chi-Wen Weng <cwweng@nuvoton.com>
>>>
>>> Add an IIO driver for the Nuvoton MA35D1 Enhanced ADC controller.
>>>
For future reference, please don't top-post, but rather put your
reply inline like this and trim any irrelevant context.



^ permalink raw reply

* Re: [PATCH 4/5] media: nxp: imx8-isi: Correct color map between V4L2 and ISI
From: Frank Li @ 2026-06-29 15:08 UTC (permalink / raw)
  To: Guoniu Zhou
  Cc: Laurent Pinchart, Mauro Carvalho Chehab, Frank Li, Sascha Hauer,
	Pengutronix Kernel Team, Fabio Estevam, Christian Hemp,
	Stefan Riedmueller, Jacopo Mondi, Dong Aisheng, Guoniu Zhou,
	linux-media, imx, linux-arm-kernel, linux-kernel, stable
In-Reply-To: <20260629-isi-v1-4-deebfdb1b07b@oss.nxp.com>

On Mon, Jun 29, 2026 at 03:44:58PM +0800, Guoniu Zhou wrote:

Subject: Correct V4L2_PIX_FMT_XBGR32 mapping in m2m mode

> Correct color map between V4L2_PIX_FMT_XBGR32 and ISI input
> format XRGB8 when ISI works at memory to memory mode.

Fix the ISI input format for the color map V4L2_PIX_FMT_XBGR32 in
memory-to-memory mode.

Frank

>
> Fixes: cf21f328fcaf ("media: nxp: Add i.MX8 ISI driver")
> Cc: stable@vger.kernel.org
> Signed-off-by: Guoniu Zhou <guoniu.zhou@nxp.com>
> ---
>  drivers/media/platform/nxp/imx8-isi/imx8-isi-video.c | 2 +-
>  1 file changed, 1 insertion(+), 1 deletion(-)
>
> diff --git a/drivers/media/platform/nxp/imx8-isi/imx8-isi-video.c b/drivers/media/platform/nxp/imx8-isi/imx8-isi-video.c
> index 5eb448f4c26f..05b51b98344b 100644
> --- a/drivers/media/platform/nxp/imx8-isi/imx8-isi-video.c
> +++ b/drivers/media/platform/nxp/imx8-isi/imx8-isi-video.c
> @@ -151,7 +151,7 @@ static const struct mxc_isi_format_info mxc_isi_formats[] = {
>  		.fourcc		= V4L2_PIX_FMT_XBGR32,
>  		.type		= MXC_ISI_VIDEO_CAP | MXC_ISI_VIDEO_M2M_OUT
>  				| MXC_ISI_VIDEO_M2M_CAP,
> -		.isi_in_format	= CHNL_MEM_RD_CTRL_IMG_TYPE_XBGR8,
> +		.isi_in_format	= CHNL_MEM_RD_CTRL_IMG_TYPE_XRGB8,
>  		.isi_out_format	= CHNL_IMG_CTRL_FORMAT_XRGB888,
>  		.mem_planes	= 1,
>  		.color_planes	= 1,
>
> --
> 2.34.1
>
>


^ permalink raw reply

* [PATCH v5 4/4] arm64: escalate smp_send_stop() to an SDEI NMI as a last resort
From: Kiryl Shutsemau @ 2026-06-29 15:07 UTC (permalink / raw)
  To: Catalin Marinas, Will Deacon, James Morse
  Cc: Mark Rutland, Marc Zyngier, Doug Anderson, Petr Mladek,
	Thomas Gleixner, Andrew Morton, Baoquan He, Puranjay Mohan,
	Usama Arif, Breno Leitao, Julien Thierry, Lecopzer Chen,
	Sumit Garg, kernel-team, kexec, linux-arm-kernel, linux-kernel,
	Kiryl Shutsemau (Meta)
In-Reply-To: <cover.1782744912.git.kas@kernel.org>

From: "Kiryl Shutsemau (Meta)" <kas@kernel.org>

A CPU wedged with interrupts masked ignores the stop IPI, and without
pseudo-NMI there is no NMI IPI to escalate to: a reboot proceeds with
the CPU still running, and a kdump misses its registers.

Add a third rung to smp_send_stop(): once the IPI (and pseudo-NMI IPI,
if enabled) rungs have run, signal SDEI event 0 at whatever stayed
online. Firmware delivers it regardless of the target's DAIF, so it
reaches a CPU a plain IPI cannot; the target acks by going offline,
which the caller already polls for.

Fold the stop bookkeeping into one arm64_nmi_cpu_stop(regs,
die_on_crash), shared by the stop IPI handlers, panic_smp_self_stop()
and the SDEI handler, replacing the near-duplicate local_cpu_stop() and
ipi_cpu_crash_stop(). @die_on_crash is the only difference: the IPI
handlers pass true and PSCI CPU_OFF the CPU on a crash stop so a capture
kernel can reclaim it; the SDEI handler and self-stop pass false and
park. The SDEI park is required, not conservative -- its handler runs
inside an SDEI event that is never completed (completing it resumes the
wedged context), and a CPU_OFF from that unfinished-event context wedges
EL3 on some firmware (left as a follow-up). The dump is unaffected; only
re-onlining the CPU in an SMP capture kernel is lost.

Suggested-by: Douglas Anderson <dianders@chromium.org>
Signed-off-by: Kiryl Shutsemau (Meta) <kas@kernel.org>
Reviewed-by: Douglas Anderson <dianders@chromium.org>
---
 arch/arm64/include/asm/nmi.h    |  24 +++++++
 arch/arm64/kernel/smp.c         | 113 +++++++++++++++++++++-----------
 drivers/firmware/Kconfig        |   2 +
 drivers/firmware/arm_sdei_nmi.c |  87 ++++++++++++++++++++++++
 4 files changed, 188 insertions(+), 38 deletions(-)

diff --git a/arch/arm64/include/asm/nmi.h b/arch/arm64/include/asm/nmi.h
index 9366be419d18..2e8974ff8d63 100644
--- a/arch/arm64/include/asm/nmi.h
+++ b/arch/arm64/include/asm/nmi.h
@@ -4,21 +4,45 @@
 
 #include <linux/cpumask.h>
 
+struct pt_regs;
+
 /*
  * Cross-CPU NMI provider hooks, consulted by the arm64 arch code before
  * its regular-IRQ / pseudo-NMI IPI paths. The SDEI provider in
  * drivers/firmware/arm_sdei_nmi.c implements them when active; a future
  * FEAT_NMI provider could slot in here too. The stubs let callers stay
  * unconditional when ARM_SDEI_NMI is off.
+ *
+ * sdei_nmi_active() lets a caller test for the service before committing
+ * to (and waiting on) the SDEI stop rung; sdei_nmi_stop_cpus() then signals
+ * the targets, which ack by going offline.
  */
 #ifdef CONFIG_ARM_SDEI_NMI
 bool sdei_nmi_trigger_cpumask_backtrace(const cpumask_t *mask, int exclude_cpu);
+bool sdei_nmi_active(void);
+void sdei_nmi_stop_cpus(const cpumask_t *mask);
 #else
 static inline bool sdei_nmi_trigger_cpumask_backtrace(const cpumask_t *mask,
 						      int exclude_cpu)
 {
 	return false;
 }
+
+static inline bool sdei_nmi_active(void)
+{
+	return false;
+}
+
+static inline void sdei_nmi_stop_cpus(const cpumask_t *mask) { }
 #endif
 
+/*
+ * The common "stop this CPU" entry every arm64 stop path funnels through:
+ * the regular/pseudo-NMI stop IPI handlers, panic_smp_self_stop(), and the
+ * SDEI cross-CPU NMI handler. @die_on_crash powers the CPU off on the kdump
+ * crash path (IPI handlers) instead of parking it (SDEI / self-stop).
+ * Defined in arch/arm64/kernel/smp.c.
+ */
+void __noreturn arm64_nmi_cpu_stop(struct pt_regs *regs, bool die_on_crash);
+
 #endif /* __ASM_NMI_H */
diff --git a/arch/arm64/kernel/smp.c b/arch/arm64/kernel/smp.c
index a670434a8cae..05c7007a1f4a 100644
--- a/arch/arm64/kernel/smp.c
+++ b/arch/arm64/kernel/smp.c
@@ -33,6 +33,7 @@
 #include <linux/kernel_stat.h>
 #include <linux/kexec.h>
 #include <linux/kgdb.h>
+#include <linux/kprobes.h>
 #include <linux/kvm_host.h>
 #include <linux/nmi.h>
 
@@ -862,14 +863,62 @@ void arch_irq_work_raise(void)
 }
 #endif
 
-static void __noreturn local_cpu_stop(unsigned int cpu)
+/**
+ * arm64_nmi_cpu_stop() - stop the local CPU after it is told to stop.
+ * @regs: register state to record in the vmcore on a crash stop, or NULL for
+ *        panic_smp_self_stop(), which has no interrupted context to save.
+ * @die_on_crash: on the kdump crash path, power the CPU off via PSCI CPU_OFF
+ *                (so a capture kernel can reclaim it) rather than parking it.
+ *
+ * The single point every arm64 stop path funnels through, keeping the
+ * bookkeeping (mask interrupts, save the crash context, mark offline, mask
+ * SDEI, optionally power off) in one place:
+ *
+ *   - the regular IPI_CPU_STOP and pseudo-NMI IPI_CPU_STOP_NMI handlers;
+ *   - panic_smp_self_stop(), a CPU parking itself on a parallel panic();
+ *   - the SDEI cross-CPU NMI handler (drivers/firmware/arm_sdei_nmi.c),
+ *     which reaches CPUs the stop IPIs could not.
+ *
+ * The IPI stop handlers pass @die_on_crash true. The SDEI handler and
+ * panic_smp_self_stop() pass false and only park. For SDEI that is required,
+ * not just conservative: it runs inside an SDEI event that is deliberately
+ * never completed (completing it has firmware resume the wedged context), and
+ * a CPU_OFF from that not-yet-completed context wedges EL3 on some firmware --
+ * a documented follow-up. Parking also matches this path's own fallback when
+ * CPU_OFF is unavailable.
+ */
+void __noreturn arm64_nmi_cpu_stop(struct pt_regs *regs, bool die_on_crash)
 {
+	unsigned int cpu = smp_processor_id();
+	bool crash = IS_ENABLED(CONFIG_KEXEC_CORE) && crash_stop;
+
+	/*
+	 * Use local_daif_mask() instead of local_irq_disable() to make sure
+	 * that pseudo-NMIs are disabled. The "stop" code starts with an IRQ
+	 * and falls back to NMI (which might be pseudo). If the IRQ finally
+	 * goes through right as we're timing out then the NMI could interrupt
+	 * us. It's better to prevent the NMI and let the IRQ finish since the
+	 * pt_regs will be better.
+	 */
+	local_daif_mask();
+
+#ifdef CONFIG_KEXEC_CORE
+	if (crash && regs)
+		crash_save_cpu(regs, cpu);
+#endif
+
+	/* the ack a stop requester (e.g. smp_send_stop()) polls for */
 	set_cpu_online(cpu, false);
 
-	local_daif_mask();
 	sdei_mask_local_cpu();
+
+	if (crash && die_on_crash)
+		__cpu_try_die(cpu);
+
+	/* just in case */
 	cpu_park_loop();
 }
+NOKPROBE_SYMBOL(arm64_nmi_cpu_stop);
 
 /*
  * We need to implement panic_smp_self_stop() for parallel panic() calls, so
@@ -878,36 +927,7 @@ static void __noreturn local_cpu_stop(unsigned int cpu)
  */
 void __noreturn panic_smp_self_stop(void)
 {
-	local_cpu_stop(smp_processor_id());
-}
-
-static void __noreturn ipi_cpu_crash_stop(unsigned int cpu, struct pt_regs *regs)
-{
-#ifdef CONFIG_KEXEC_CORE
-	/*
-	 * Use local_daif_mask() instead of local_irq_disable() to make sure
-	 * that pseudo-NMIs are disabled. The "crash stop" code starts with
-	 * an IRQ and falls back to NMI (which might be pseudo). If the IRQ
-	 * finally goes through right as we're timing out then the NMI could
-	 * interrupt us. It's better to prevent the NMI and let the IRQ
-	 * finish since the pt_regs will be better.
-	 */
-	local_daif_mask();
-
-	crash_save_cpu(regs, cpu);
-
-	set_cpu_online(cpu, false);
-
-	sdei_mask_local_cpu();
-
-	if (IS_ENABLED(CONFIG_HOTPLUG_CPU))
-		__cpu_try_die(cpu);
-
-	/* just in case */
-	cpu_park_loop();
-#else
-	BUG();
-#endif
+	arm64_nmi_cpu_stop(NULL, false);
 }
 
 static void arm64_send_ipi(const cpumask_t *mask, unsigned int nr)
@@ -984,12 +1004,7 @@ static void do_handle_IPI(int ipinr)
 
 	case IPI_CPU_STOP:
 	case IPI_CPU_STOP_NMI:
-		if (IS_ENABLED(CONFIG_KEXEC_CORE) && crash_stop) {
-			ipi_cpu_crash_stop(cpu, get_irq_regs());
-			unreachable();
-		} else {
-			local_cpu_stop(cpu);
-		}
+		arm64_nmi_cpu_stop(get_irq_regs(), true);
 		break;
 
 #ifdef CONFIG_GENERIC_CLOCKEVENTS_BROADCAST
@@ -1263,6 +1278,28 @@ void smp_send_stop(void)
 			udelay(1);
 	}
 
+	/*
+	 * If CPUs are *still* online, try the SDEI cross-CPU NMI. Firmware
+	 * delivers it regardless of the target's DAIF state, so it reaches
+	 * a CPU spinning with interrupts masked, which neither rung above
+	 * could (without pseudo-NMI there is no NMI rung at all). Allow
+	 * 100ms: a firmware round-trip per CPU, with headroom.
+	 */
+	if (num_other_online_cpus() && sdei_nmi_active()) {
+		/* re-snapshot after the rungs above took CPUs offline */
+		smp_rmb();
+		cpumask_copy(&mask, cpu_online_mask);
+		cpumask_clear_cpu(smp_processor_id(), &mask);
+
+		pr_info("SMP: retry stop with SDEI NMI for CPUs %*pbl\n",
+			cpumask_pr_args(&mask));
+
+		sdei_nmi_stop_cpus(&mask);
+		timeout = USEC_PER_MSEC * 100;
+		while (num_other_online_cpus() && timeout--)
+			udelay(1);
+	}
+
 	if (num_other_online_cpus()) {
 		smp_rmb();
 		cpumask_copy(&mask, cpu_online_mask);
diff --git a/drivers/firmware/Kconfig b/drivers/firmware/Kconfig
index dd47584d3b57..b5f502bd2da3 100644
--- a/drivers/firmware/Kconfig
+++ b/drivers/firmware/Kconfig
@@ -46,6 +46,8 @@ config ARM_SDEI_NMI
 	    - arch_trigger_cpumask_backtrace()  (sysrq-l, RCU stalls,
 	      hardlockup_all_cpu_backtrace, soft-lockup secondary dumps,
 	      hung-task auxiliary dumps)
+	    - smp_send_stop() escalation         (reboot/halt and the
+	      panic / kdump crash stop)
 
 	  The driver registers a handler for the SDEI software-signalled
 	  event (event 0) and reaches a target CPU by signalling it with
diff --git a/drivers/firmware/arm_sdei_nmi.c b/drivers/firmware/arm_sdei_nmi.c
index 4047fcda0bc3..038eb79e28ac 100644
--- a/drivers/firmware/arm_sdei_nmi.c
+++ b/drivers/firmware/arm_sdei_nmi.c
@@ -29,6 +29,11 @@
  *     hardlockup_all_cpu_backtrace, soft-lockup/hung-task secondary
  *     dumps all reach interrupt-masked CPUs.
  *
+ *   - sdei_nmi_stop_cpus() — the last rung of smp_send_stop()'s
+ *     escalation (reboot/halt and the panic/kdump crash stop alike),
+ *     reaching CPUs that ignored the stop IPIs; on the kdump path the
+ *     wedged context is captured into the vmcore before the CPU parks.
+ *
  * Delivery uses the standard SDEI software-signalled event (event 0) and
  * SDEI_EVENT_SIGNAL. We register a handler for event 0, enable it, and
  * poke a target CPU with sdei_event_signal(0, mpidr): firmware makes
@@ -59,8 +64,57 @@ static bool sdei_nmi_available;
 
 #define SDEI_NMI_EVENT			0
 
+/*
+ * Backtrace and stop both ride SDEI event 0. That is not a chosen economy:
+ * event 0 is the only architecturally software-signalled event -- the sole
+ * event SDEI_EVENT_SIGNAL can target at an arbitrary PE. Every other event
+ * number is a firmware/platform interrupt-bound event, not something the
+ * kernel can raise cross-CPU, so a dedicated "stop" event would need
+ * firmware to define and bind it -- exactly the firmware dependency this
+ * driver sets out to avoid.
+ *
+ * Sharing one event means the handler must tell a stop apart from a
+ * backtrace. A stop is terminal and system-wide -- sdei_nmi_stop_cpus() is
+ * only reached from smp_send_stop() (reboot/halt/panic/kdump), which never
+ * returns -- so once a stop is requested, every later event-0 fire is a
+ * stop too. A single write-once flag therefore carries as much as a
+ * per-CPU mask would: sdei_nmi_stop_cpus() sets it before signalling, and
+ * the handler reads a set flag as "stop this CPU" and a clear flag as
+ * "backtrace" (handled by nmi_cpu_backtrace(), which self-gates on the
+ * framework's backtrace mask). A backtrace fire that races in after a stop
+ * has begun just stops that CPU instead -- harmless, it is going down.
+ */
+static bool sdei_nmi_stopping;
+
 static int sdei_nmi_handler(u32 event, struct pt_regs *regs, void *arg)
 {
+	/*
+	 * No smp_rmb() pairing sdei_nmi_stop_cpus()'s dsb(ishst): the flag is
+	 * the only shared value, and this handler runs only because firmware
+	 * delivered the event -- a round-trip past that store -- so the read
+	 * cannot be stale and there is no second load for a barrier to order.
+	 */
+	if (READ_ONCE(sdei_nmi_stopping)) {
+		/*
+		 * Never returns, and deliberately never completes the SDEI
+		 * event: SDEI_EVENT_COMPLETE has firmware restore the
+		 * interrupted context, which would land the CPU back in
+		 * the wedged loop (or in do_idle, which BUGs at
+		 * cpuhp_report_idle_dead once it sees itself offline).
+		 * Returning a modified pt_regs doesn't help --
+		 * arch/arm64/kernel/sdei.c::do_sdei_event only honours a PC
+		 * override via its IRQ-state heuristic and otherwise hands
+		 * EL3 its own saved-context slot back.
+		 *
+		 * Trade-off: EL3 retains ~one saved-context slot per parked
+		 * CPU until the next hardware reset (~hundreds of bytes per
+		 * CPU). Recoverability is unchanged versus an IPI-stopped
+		 * CPU: neither comes back without a reset.
+		 */
+		arm64_nmi_cpu_stop(regs, false);
+		/* unreachable */
+	}
+
 	/*
 	 * nmi_cpu_backtrace() no-ops unless this CPU's bit is set in the
 	 * global backtrace mask (driven by nmi_trigger_cpumask_backtrace()),
@@ -122,6 +176,39 @@ bool sdei_nmi_trigger_cpumask_backtrace(const cpumask_t *mask, int exclude_cpu)
 	return true;
 }
 
+bool sdei_nmi_active(void)
+{
+	return sdei_nmi_available;
+}
+
+/*
+ * Last rung of the stop escalation in smp_send_stop() (see
+ * arch/arm64/kernel/smp.c). The caller runs the regular stop IPI (and
+ * the pseudo-NMI stop IPI, where available) first; @mask holds whatever
+ * stayed online through those -- typically CPUs wedged with interrupts
+ * masked, unreachable by an IPI. Mark the stop in progress and signal
+ * event 0 at each target; a target acks by marking itself offline, which
+ * the caller polls for. The caller has already confirmed sdei_nmi_active().
+ */
+void sdei_nmi_stop_cpus(const cpumask_t *mask)
+{
+	unsigned int cpu;
+
+	WRITE_ONCE(sdei_nmi_stopping, true);
+
+	/*
+	 * Publish the flag before signalling. The signal goes out via an SMC
+	 * to firmware, not a memory store, so smp_wmb() ordering is not
+	 * enough: use dsb(ishst) to make the store globally visible before the
+	 * SMC executes, as gic_ipi_send_mask() does for its SGI. The SDEI spec
+	 * does not require the dispatch to order the caller's prior stores.
+	 */
+	dsb(ishst);
+
+	for_each_cpu(cpu, mask)
+		sdei_nmi_fire(cpu);
+}
+
 /*
  * device_initcall (after arch_initcall(sdei_init), so the SDEI subsystem
  * is up): probe the firmware, register the event, and turn on the
-- 
2.54.0



^ permalink raw reply related

* [PATCH v5 2/4] firmware: arm_sdei: add SDEI_EVENT_SIGNAL support
From: Kiryl Shutsemau @ 2026-06-29 15:07 UTC (permalink / raw)
  To: Catalin Marinas, Will Deacon, James Morse
  Cc: Mark Rutland, Marc Zyngier, Doug Anderson, Petr Mladek,
	Thomas Gleixner, Andrew Morton, Baoquan He, Puranjay Mohan,
	Usama Arif, Breno Leitao, Julien Thierry, Lecopzer Chen,
	Sumit Garg, kernel-team, kexec, linux-arm-kernel, linux-kernel,
	Kiryl Shutsemau (Meta)
In-Reply-To: <cover.1782744912.git.kas@kernel.org>

From: "Kiryl Shutsemau (Meta)" <kas@kernel.org>

Add sdei_event_signal(), a thin wrapper over the SDEI_EVENT_SIGNAL call
(DEN0054) that makes the software-signalled event (event 0) pending on a
target PE -- delivered NMI-like even when that PE has interrupts masked.
It takes no locks, so it is safe to call from NMI / crash context.

Signed-off-by: Kiryl Shutsemau (Meta) <kas@kernel.org>
Reviewed-by: Douglas Anderson <dianders@chromium.org>
---
 drivers/firmware/arm_sdei.c   | 12 ++++++++++++
 include/linux/arm_sdei.h      |  6 ++++++
 include/uapi/linux/arm_sdei.h |  1 +
 3 files changed, 19 insertions(+)

diff --git a/drivers/firmware/arm_sdei.c b/drivers/firmware/arm_sdei.c
index c161cf263547..e8dd2f0f3919 100644
--- a/drivers/firmware/arm_sdei.c
+++ b/drivers/firmware/arm_sdei.c
@@ -339,6 +339,18 @@ static void _ipi_unmask_cpu(void *ignored)
 	sdei_unmask_local_cpu();
 }
 
+/*
+ * Signal the software-signalled event (event 0) to @mpidr. Does nothing
+ * but the SMC -- no locks, no event lookup -- so it is safe from NMI /
+ * crash context (e.g. the cross-CPU NMI service).
+ */
+int sdei_event_signal(u32 event_num, u64 mpidr)
+{
+	return invoke_sdei_fn(SDEI_1_0_FN_SDEI_EVENT_SIGNAL, event_num,
+			      mpidr, 0, 0, 0, NULL);
+}
+NOKPROBE_SYMBOL(sdei_event_signal);
+
 /*
  * Was SDEI firmware probed and is it usable?  Lets optional consumers skip
  * registering an event -- and the warning a failed registration emits -- on
diff --git a/include/linux/arm_sdei.h b/include/linux/arm_sdei.h
index b07113eeeff7..b9dc21c241be 100644
--- a/include/linux/arm_sdei.h
+++ b/include/linux/arm_sdei.h
@@ -37,6 +37,12 @@ int sdei_event_unregister(u32 event_num);
 int sdei_event_enable(u32 event_num);
 int sdei_event_disable(u32 event_num);
 
+/*
+ * Signal the software-signalled event (event 0) to another PE, NMI-like.
+ * @mpidr is the target's MPIDR affinity.
+ */
+int sdei_event_signal(u32 event_num, u64 mpidr);
+
 /* Was SDEI firmware probed and usable? */
 bool sdei_is_present(void);
 
diff --git a/include/uapi/linux/arm_sdei.h b/include/uapi/linux/arm_sdei.h
index af0630ba5437..22eb61612673 100644
--- a/include/uapi/linux/arm_sdei.h
+++ b/include/uapi/linux/arm_sdei.h
@@ -22,6 +22,7 @@
 #define SDEI_1_0_FN_SDEI_PE_UNMASK			SDEI_1_0_FN(0x0C)
 #define SDEI_1_0_FN_SDEI_INTERRUPT_BIND			SDEI_1_0_FN(0x0D)
 #define SDEI_1_0_FN_SDEI_INTERRUPT_RELEASE		SDEI_1_0_FN(0x0E)
+#define SDEI_1_0_FN_SDEI_EVENT_SIGNAL			SDEI_1_0_FN(0x0F)
 #define SDEI_1_0_FN_SDEI_PRIVATE_RESET			SDEI_1_0_FN(0x11)
 #define SDEI_1_0_FN_SDEI_SHARED_RESET			SDEI_1_0_FN(0x12)
 
-- 
2.54.0



^ permalink raw reply related

* [PATCH v5 3/4] drivers/firmware: add SDEI cross-CPU NMI service for arm64
From: Kiryl Shutsemau @ 2026-06-29 15:07 UTC (permalink / raw)
  To: Catalin Marinas, Will Deacon, James Morse
  Cc: Mark Rutland, Marc Zyngier, Doug Anderson, Petr Mladek,
	Thomas Gleixner, Andrew Morton, Baoquan He, Puranjay Mohan,
	Usama Arif, Breno Leitao, Julien Thierry, Lecopzer Chen,
	Sumit Garg, kernel-team, kexec, linux-arm-kernel, linux-kernel,
	Kiryl Shutsemau (Meta)
In-Reply-To: <cover.1782744912.git.kas@kernel.org>

From: "Kiryl Shutsemau (Meta)" <kas@kernel.org>

Deliver an NMI-like event to an interrupt-masked arm64 CPU via the
standard SDEI software-signalled event (event 0), without the pseudo-NMI
hot-path cost: register a handler for event 0 and poke a target with
sdei_event_signal(0, mpidr).

First user is arch_trigger_cpumask_backtrace() (sysrq-l, RCU stalls,
hung-task/soft-lockup dumps), which otherwise rides an IPI that can't
reach a masked CPU. Falls back to the IPI path when SDEI is absent; no
watchdog backend yet, so the stock detector is untouched.

Signed-off-by: Kiryl Shutsemau (Meta) <kas@kernel.org>
Reviewed-by: Douglas Anderson <dianders@chromium.org>
---
 MAINTAINERS                     |   2 +-
 arch/arm64/include/asm/nmi.h    |  24 +++++
 arch/arm64/kernel/smp.c         |  11 +++
 drivers/firmware/Kconfig        |  19 ++++
 drivers/firmware/Makefile       |   1 +
 drivers/firmware/arm_sdei_nmi.c | 159 ++++++++++++++++++++++++++++++++
 6 files changed, 215 insertions(+), 1 deletion(-)
 create mode 100644 arch/arm64/include/asm/nmi.h
 create mode 100644 drivers/firmware/arm_sdei_nmi.c

diff --git a/MAINTAINERS b/MAINTAINERS
index c8d4b913f26c..b5ddfb85dce9 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -24797,7 +24797,7 @@ M:	James Morse <james.morse@arm.com>
 L:	linux-arm-kernel@lists.infradead.org (moderated for non-subscribers)
 S:	Maintained
 F:	Documentation/devicetree/bindings/arm/firmware/sdei.txt
-F:	drivers/firmware/arm_sdei.c
+F:	drivers/firmware/arm_sdei*
 F:	include/linux/arm_sdei.h
 F:	include/uapi/linux/arm_sdei.h
 
diff --git a/arch/arm64/include/asm/nmi.h b/arch/arm64/include/asm/nmi.h
new file mode 100644
index 000000000000..9366be419d18
--- /dev/null
+++ b/arch/arm64/include/asm/nmi.h
@@ -0,0 +1,24 @@
+/* SPDX-License-Identifier: GPL-2.0 */
+#ifndef __ASM_NMI_H
+#define __ASM_NMI_H
+
+#include <linux/cpumask.h>
+
+/*
+ * Cross-CPU NMI provider hooks, consulted by the arm64 arch code before
+ * its regular-IRQ / pseudo-NMI IPI paths. The SDEI provider in
+ * drivers/firmware/arm_sdei_nmi.c implements them when active; a future
+ * FEAT_NMI provider could slot in here too. The stubs let callers stay
+ * unconditional when ARM_SDEI_NMI is off.
+ */
+#ifdef CONFIG_ARM_SDEI_NMI
+bool sdei_nmi_trigger_cpumask_backtrace(const cpumask_t *mask, int exclude_cpu);
+#else
+static inline bool sdei_nmi_trigger_cpumask_backtrace(const cpumask_t *mask,
+						      int exclude_cpu)
+{
+	return false;
+}
+#endif
+
+#endif /* __ASM_NMI_H */
diff --git a/arch/arm64/kernel/smp.c b/arch/arm64/kernel/smp.c
index 1aa324104afb..a670434a8cae 100644
--- a/arch/arm64/kernel/smp.c
+++ b/arch/arm64/kernel/smp.c
@@ -45,6 +45,7 @@
 #include <asm/daifflags.h>
 #include <asm/kvm_mmu.h>
 #include <asm/mmu_context.h>
+#include <asm/nmi.h>
 #include <asm/numa.h>
 #include <asm/processor.h>
 #include <asm/smp_plat.h>
@@ -927,6 +928,16 @@ static void arm64_backtrace_ipi(cpumask_t *mask)
 
 void arch_trigger_cpumask_backtrace(const cpumask_t *mask, int exclude_cpu)
 {
+	/*
+	 * Prefer the SDEI cross-CPU NMI provider when active: firmware
+	 * dispatches the event out of EL3 and reaches CPUs that have
+	 * interrupts locally masked, without the per-IRQ-mask cost that
+	 * pseudo-NMI pays for the same reach. The plain IPI path below
+	 * can't reach such a CPU unless pseudo-NMI is enabled.
+	 */
+	if (sdei_nmi_trigger_cpumask_backtrace(mask, exclude_cpu))
+		return;
+
 	/*
 	 * NOTE: though nmi_trigger_cpumask_backtrace() has "nmi_" in the name,
 	 * nothing about it truly needs to be implemented using an NMI, it's
diff --git a/drivers/firmware/Kconfig b/drivers/firmware/Kconfig
index bbd2155d8483..dd47584d3b57 100644
--- a/drivers/firmware/Kconfig
+++ b/drivers/firmware/Kconfig
@@ -36,6 +36,25 @@ config ARM_SDE_INTERFACE
 	  standard for registering callbacks from the platform firmware
 	  into the OS. This is typically used to implement RAS notifications.
 
+config ARM_SDEI_NMI
+	bool "SDEI-based cross-CPU NMI service (arm64)"
+	depends on ARM_SDE_INTERFACE
+	help
+	  Provides SDEI-based cross-CPU NMI delivery for hooks that need
+	  to reach interrupt-masked CPUs on silicon that lacks FEAT_NMI:
+
+	    - arch_trigger_cpumask_backtrace()  (sysrq-l, RCU stalls,
+	      hardlockup_all_cpu_backtrace, soft-lockup secondary dumps,
+	      hung-task auxiliary dumps)
+
+	  The driver registers a handler for the SDEI software-signalled
+	  event (event 0) and reaches a target CPU by signalling it with
+	  SDEI_EVENT_SIGNAL. Firmware delivers the event out of EL3
+	  regardless of the target's PSTATE.DAIF -- forced delivery into a
+	  CPU wedged with interrupts locally masked.
+
+	  If unsure, say N.
+
 config EDD
 	tristate "BIOS Enhanced Disk Drive calls determine boot disk"
 	depends on X86
diff --git a/drivers/firmware/Makefile b/drivers/firmware/Makefile
index 4ddec2820c96..be46f1e1dc77 100644
--- a/drivers/firmware/Makefile
+++ b/drivers/firmware/Makefile
@@ -4,6 +4,7 @@
 #
 obj-$(CONFIG_ARM_SCPI_PROTOCOL)	+= arm_scpi.o
 obj-$(CONFIG_ARM_SDE_INTERFACE)	+= arm_sdei.o
+obj-$(CONFIG_ARM_SDEI_NMI)	+= arm_sdei_nmi.o
 obj-$(CONFIG_DMI)		+= dmi_scan.o
 obj-$(CONFIG_DMI_SYSFS)		+= dmi-sysfs.o
 obj-$(CONFIG_EDD)		+= edd.o
diff --git a/drivers/firmware/arm_sdei_nmi.c b/drivers/firmware/arm_sdei_nmi.c
new file mode 100644
index 000000000000..4047fcda0bc3
--- /dev/null
+++ b/drivers/firmware/arm_sdei_nmi.c
@@ -0,0 +1,159 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * arm64 SDEI-based cross-CPU NMI service.
+ *
+ * Delivering an "NMI-shaped" event to an EL1 context that has locally
+ * masked interrupts, on silicon without FEAT_NMI, can be done two ways:
+ *
+ *   - pseudo-NMI: mask "interrupts" via the GIC priority register
+ *     (ICC_PMR_EL1) instead of PSTATE.DAIF, leaving a high-priority band
+ *     deliverable. Functionally this works -- but it reimplements every
+ *     local_irq_disable()/enable() and exception entry/exit as a PMR
+ *     write plus synchronisation, a cost paid on that hot path forever,
+ *     whether or not an NMI is ever delivered.
+ *
+ *   - SDEI: leave interrupt masking as the cheap PSTATE.DAIF operation
+ *     and have the firmware bounce an EL3-routed Group-0 SGI back to
+ *     NS-EL1 as an event callback. The cost is a firmware round-trip,
+ *     but only at the rare moment delivery is actually needed.
+ *
+ * This driver takes the second path: it keeps the IRQ-mask hot path
+ * free and pays only when it fires, which is what makes cross-CPU NMI
+ * affordable on hardware where the pseudo-NMI tax isn't, until FEAT_NMI
+ * makes NMI masking cheap in the architecture itself.
+ *
+ * Capabilities provided:
+ *
+ *   - sdei_nmi_trigger_cpumask_backtrace() — override for arm64's
+ *     arch_trigger_cpumask_backtrace(), so sysrq-l, RCU stall dumps,
+ *     hardlockup_all_cpu_backtrace, soft-lockup/hung-task secondary
+ *     dumps all reach interrupt-masked CPUs.
+ *
+ * Delivery uses the standard SDEI software-signalled event (event 0) and
+ * SDEI_EVENT_SIGNAL. We register a handler for event 0, enable it, and
+ * poke a target CPU with sdei_event_signal(0, mpidr): firmware makes
+ * event 0 pending on that PE and dispatches the handler NMI-like,
+ * regardless of the target's DAIF.
+ * Availability is simply whether event 0 registers and enables -- if SDEI
+ * and its software-signalled event are present we use it, otherwise the
+ * driver stays inert.
+ */
+
+#define pr_fmt(fmt) "sdei_nmi: " fmt
+
+#include <linux/arm_sdei.h>
+#include <linux/cpumask.h>
+#include <linux/init.h>
+#include <linux/kernel.h>
+#include <linux/kprobes.h>
+#include <linux/nmi.h>
+#include <linux/printk.h>
+#include <linux/ptrace.h>
+#include <linux/smp.h>
+#include <linux/types.h>
+
+#include <asm/nmi.h>
+#include <asm/smp_plat.h>
+
+static bool sdei_nmi_available;
+
+#define SDEI_NMI_EVENT			0
+
+static int sdei_nmi_handler(u32 event, struct pt_regs *regs, void *arg)
+{
+	/*
+	 * nmi_cpu_backtrace() no-ops unless this CPU's bit is set in the
+	 * global backtrace mask (driven by nmi_trigger_cpumask_backtrace()),
+	 * so a fire that reaches a CPU not being backtraced is harmless.
+	 */
+	nmi_cpu_backtrace(regs);
+	return SDEI_EV_HANDLED;
+}
+NOKPROBE_SYMBOL(sdei_nmi_handler);
+
+static void sdei_nmi_fire(unsigned int target_cpu)
+{
+	int err = sdei_event_signal(SDEI_NMI_EVENT, cpu_logical_map(target_cpu));
+
+	if (err)
+		pr_warn("SDEI_EVENT_SIGNAL to CPU %u failed: %d\n",
+			target_cpu, err);
+}
+
+/*
+ * Raise callback for nmi_trigger_cpumask_backtrace(): signal event 0
+ * at every CPU still pending in @mask. The framework excludes the local
+ * CPU from @mask before calling us.
+ */
+static void sdei_nmi_raise_backtrace(cpumask_t *mask)
+{
+	unsigned int cpu;
+
+	/*
+	 * Publish backtrace_mask (set by nmi_trigger_cpumask_backtrace())
+	 * before signalling. As in the stop path, the SMC is not a memory
+	 * store, so dsb(ishst) is needed for the target to observe the mask.
+	 */
+	dsb(ishst);
+
+	for_each_cpu(cpu, mask)
+		sdei_nmi_fire(cpu);
+}
+
+/*
+ * Override hook for arch_trigger_cpumask_backtrace() (see
+ * arch/arm64/kernel/smp.c). Returns true when SDEI handled the request,
+ * which is the case whenever SDEI is active; on a false return the arch
+ * falls back to its regular-IRQ (or pseudo-NMI, if enabled) IPI.
+ *
+ * On a kernel built without paying the pseudo-NMI hot-path cost (the
+ * usual case for this driver's target), the IPI can't reach a CPU that
+ * has interrupts masked -- so the backtrace of the one CPU you care
+ * about comes back empty. SDEI is dispatched out of EL3 and lands
+ * regardless of the target's DAIF, without taxing the IRQ-mask path.
+ */
+bool sdei_nmi_trigger_cpumask_backtrace(const cpumask_t *mask, int exclude_cpu)
+{
+	if (!sdei_nmi_available)
+		return false;
+
+	nmi_trigger_cpumask_backtrace(mask, exclude_cpu,
+				      sdei_nmi_raise_backtrace);
+	return true;
+}
+
+/*
+ * device_initcall (after arch_initcall(sdei_init), so the SDEI subsystem
+ * is up): probe the firmware, register the event, and turn on the
+ * cross-CPU service. If the probe fails the driver stays inert and the
+ * override hooks decline, leaving the arch's own paths in place.
+ */
+static int __init sdei_nmi_init(void)
+{
+	int err;
+
+	if (!sdei_is_present())
+		return 0;
+
+	err = sdei_event_register(SDEI_NMI_EVENT, sdei_nmi_handler, NULL);
+	if (err) {
+		pr_err("sdei_event_register(%u) failed: %d\n",
+		       SDEI_NMI_EVENT, err);
+		return 0;
+	}
+
+	err = sdei_event_enable(SDEI_NMI_EVENT);
+	if (err) {
+		pr_err("sdei_event_enable(%u) failed: %d\n",
+		       SDEI_NMI_EVENT, err);
+		sdei_event_unregister(SDEI_NMI_EVENT);
+		return 0;
+	}
+
+	sdei_nmi_available = true;
+	pr_info("using SDEI cross-CPU NMI (SDEI_EVENT_SIGNAL, event %u)\n",
+		SDEI_NMI_EVENT);
+
+	return 0;
+}
+device_initcall(sdei_nmi_init);
-- 
2.54.0



^ permalink raw reply related

* [PATCH v5 1/4] firmware: arm_sdei: add sdei_is_present()
From: Kiryl Shutsemau @ 2026-06-29 15:07 UTC (permalink / raw)
  To: Catalin Marinas, Will Deacon, James Morse
  Cc: Mark Rutland, Marc Zyngier, Doug Anderson, Petr Mladek,
	Thomas Gleixner, Andrew Morton, Baoquan He, Puranjay Mohan,
	Usama Arif, Breno Leitao, Julien Thierry, Lecopzer Chen,
	Sumit Garg, kernel-team, kexec, linux-arm-kernel, linux-kernel,
	Kiryl Shutsemau (Meta)
In-Reply-To: <cover.1782744912.git.kas@kernel.org>

From: "Kiryl Shutsemau (Meta)" <kas@kernel.org>

invoke_sdei_fn() returns -EIO when no SDEI conduit was probed, and the
core warns ("Failed to create event ...") on any registration that hits
that. An optional consumer that registers an event from an unconditional
initcall would therefore make every boot on a non-SDEI system emit that
warning for what is simply absent firmware.

Expose whether SDEI firmware is present so such a consumer can skip
registration -- and the warning -- when there is nothing to talk to.

Signed-off-by: Kiryl Shutsemau (Meta) <kas@kernel.org>
Reviewed-by: Douglas Anderson <dianders@chromium.org>
---
 drivers/firmware/arm_sdei.c | 10 ++++++++++
 include/linux/arm_sdei.h    |  3 +++
 2 files changed, 13 insertions(+)

diff --git a/drivers/firmware/arm_sdei.c b/drivers/firmware/arm_sdei.c
index f39ed7ba3a38..c161cf263547 100644
--- a/drivers/firmware/arm_sdei.c
+++ b/drivers/firmware/arm_sdei.c
@@ -339,6 +339,16 @@ static void _ipi_unmask_cpu(void *ignored)
 	sdei_unmask_local_cpu();
 }
 
+/*
+ * Was SDEI firmware probed and is it usable?  Lets optional consumers skip
+ * registering an event -- and the warning a failed registration emits -- on
+ * systems with no SDEI.
+ */
+bool sdei_is_present(void)
+{
+	return sdei_firmware_call;
+}
+
 static void _ipi_private_reset(void *ignored)
 {
 	int err;
diff --git a/include/linux/arm_sdei.h b/include/linux/arm_sdei.h
index f652a5028b59..b07113eeeff7 100644
--- a/include/linux/arm_sdei.h
+++ b/include/linux/arm_sdei.h
@@ -37,6 +37,9 @@ int sdei_event_unregister(u32 event_num);
 int sdei_event_enable(u32 event_num);
 int sdei_event_disable(u32 event_num);
 
+/* Was SDEI firmware probed and usable? */
+bool sdei_is_present(void);
+
 /* GHES register/unregister helpers */
 int sdei_register_ghes(struct ghes *ghes, sdei_event_callback *normal_cb,
 		       sdei_event_callback *critical_cb);
-- 
2.54.0



^ permalink raw reply related

* [PATCH v5 0/4] arm64: cross-CPU NMI via SDEI
From: Kiryl Shutsemau @ 2026-06-29 15:07 UTC (permalink / raw)
  To: Catalin Marinas, Will Deacon, James Morse
  Cc: Mark Rutland, Marc Zyngier, Doug Anderson, Petr Mladek,
	Thomas Gleixner, Andrew Morton, Baoquan He, Puranjay Mohan,
	Usama Arif, Breno Leitao, Julien Thierry, Lecopzer Chen,
	Sumit Garg, kernel-team, kexec, linux-arm-kernel, linux-kernel,
	Kiryl Shutsemau (Meta)

From: "Kiryl Shutsemau (Meta)" <kas@kernel.org>

A class of debug/observability features needs to interrupt a CPU that has
its interrupts locally masked: the all-CPU backtrace behind sysrq-l /
RCU-stall / hung-task / hard-lockup dumps, and crash_smp_send_stop()
capturing a stuck CPU's state into the vmcore. On arm64 these need a
mechanism that reaches a CPU spinning with DAIF masked, which a normal IPI
cannot.

arm64 has two such mechanisms today:

  - GICv3 pseudo-NMI (interrupt priority masking). The cost lands on the
    interrupt mask/unmask hot path: local_irq_enable() becomes an
    ICC_PMR_EL1 write, and exception entry/exit save and restore the PMR,
    paid on every CPU whether or not an NMI is ever delivered.

    Measured on Grace (Neoverse V2; ICC_CTLR_EL1.PMHE=0, so the PMR-sync
    DSB is already patched to a NOP), pseudo_nmi=0 vs pseudo_nmi=1:

        gettid() loop:              178 -> 253 ns/call  (+42%, ~74 ns)
        will-it-scale sched_yield:  0.705x throughput, flat from 1 to 72 cores
        will-it-scale page_fault1:  within ~5%

    The ~74 ns is a fixed per-syscall entry/exit tax -- it reproduces at
    +73.5 ns on Neoverse N2 -- so the hit tracks syscall/exception density
    and is unacceptable on syscall-bound fleet workloads, which therefore
    run with pseudo-NMI disabled.

  - FEAT_NMI (Armv8.8) -- the architectural fix, but absent from deployed
    silicon and from most of the fleet for years to come.

For deployments that do not run pseudo-NMI, the backtrace and crash paths
are degraded: a plain IPI can't reach the masked CPU, so the backtrace of
the CPU you care about comes back empty and the kdump is missing the
culprit's registers. The hard-lockup detector on these systems is the
software buddy detector (HARDLOCKUP_DETECTOR_BUDDY): it detects a stall
from a neighbour CPU, but it cannot itself interrupt the wedged CPU, so
its report has no stack for the culprit and (with hardlockup_panic) the
panic runs on the bystander.

This series adds a third delivery backend that costs nothing on the hot
path: SDEI. Firmware delivers an SDEI event into a CPU regardless of its
DAIF state, so interrupt masking stays the cheap PSTATE.DAIF operation and
the firmware round-trip is paid only at the rare moment a CPU must be
interrupted.

It does not add a hard-lockup detector. Detection stays with the buddy
detector (CONFIG_HARDLOCKUP_DETECTOR_PREFER_BUDDY); this series gives the
backtrace and crash-stop paths -- including the buddy detector's
backtrace of the stalled CPU -- a way to actually reach a masked CPU.

Mechanism
=========

It uses the standard SDEI software-signalled event (event 0) and the
SDEI_EVENT_SIGNAL call (DEN0054) -- a spec-defined cross-PE signal, not a
vendor extension. The driver registers a handler for event 0 and pokes a
target CPU with sdei_event_signal(0, target_mpidr); firmware makes event 0
pending on that PE and dispatches the handler NMI-like.

No firmware change is required beyond SDEI being enabled, which
firmware-first RAS (APEI/GHES) deployments already have; the only
SDEI-core addition is a thin sdei_event_signal() wrapper over the standard
call.

Prior SDEI watchdog work
========================

Out-of-tree SDEI hard-lockup watchdogs exist (e.g. in the openEuler and
Anolis kernels). They bind the secure physical timer as an SDEI event, so
firmware delivers a periodic self-CPU tick that drives a detector. That
requires a new SDEI interrupt-binding API, pushes the watchdog period into
firmware, and adds secure-timer EOI handling on the kexec path. This
series instead uses only the standard software-signalled event 0, keeps
all timing in the kernel (the buddy detector), and the same delivery
primitive serves the backtrace and crash-stop users, not just lockup
reporting.

Not included / follow-ups
=========================

  - No SDEI hard-lockup-detector backend. v1 had one; it is dropped here.
    The buddy detector plus this series' backtrace already cover the
    no-pseudo-NMI case, and a dedicated SDEI backend duplicated the
    perf-NMI detector it had to compile-exclude. Run PREFER_BUDDY.

  - A CPU stopped by the SDEI rung is parked, not powered off via PSCI
    CPU_OFF. Reaching and dumping the wedged CPU -- the point of the
    series -- works, and it matches the shared stop path's own park
    fallback when CPU_OFF is unavailable. The consequence is that an SMP
    crash-capture kernel cannot re-online such a CPU (it stays "already
    on"); the capture kernel boots and runs on the remaining CPUs.
    Powering the stopped CPU off so a capture kernel can reclaim it would
    need CPU_OFF from the SDEI stop context, which does not work in
    practice (see the v4 discussion); left as a follow-up and does not
    affect the dump's contents.

Testing
=======

Developed on QEMU 'virt' (Trusted Firmware-A with SDEI enabled) and
validated on NVIDIA Grace (Neoverse V2) hardware, under
irqchip.gicv3_pseudo_nmi=0 with HARDLOCKUP_DETECTOR_PREFER_BUDDY=y:

  - sysrq-l backtrace of an interrupt-masked CPU returns its real stack,
    pstate showing DAIF set -- proof SDEI delivered into the masked CPU;
  - buddy detector catches a hard lockup (LKDTM) and the wedged CPU's
    stack is fetched via the SDEI backtrace;
  - reboot/halt and the panic/kdump crash stop reach a wedged CPU via the
    SDEI rung ("SMP: retry stop with SDEI NMI for CPUs N"), and the kdump
    captures the wedged CPU's registers in the vmcore;
  - with SDEI absent (plain QEMU 'virt', no firmware support) the driver
    stays inert: no event registration and no boot-time warning.

Changes since v4
================

  - Strengthen the publish barrier from smp_wmb() to dsb(ishst) on the
    stop path, and add the missing one on the backtrace path; the SMC is
    not a memory store, so ordering alone is not enough (Catalin Marinas).
  - Drop the redundant ARM64 Kconfig dependency, already implied by
    ARM_SDE_INTERFACE (Julian Braha).
  - Reviewed-by from Douglas Anderson now on all four patches.
  - Replaced the stale perf numbers in this cover with fresh, reproducible
    measurements (Catalin Marinas, Marc Zyngier).

Changes since v3
================

  - New sdei_is_present() patch; the NMI initcall now skips registration
    (and its boot warning) on non-SDEI systems (Puranjay Mohan).
  - Fixed a NULL deref on a parallel-panic crash stop and the
    CONFIG_KEXEC_CORE=n build (Puranjay Mohan).
  - kernel-doc + barrier comments on the stop path; reordered the two
    arm_sdei core patches (Doug Anderson).

Changes since v2
================

  - Unified the CPU-stop paths into one arm64_nmi_cpu_stop(regs,
    die_on_crash), dropping local_cpu_stop()/ipi_cpu_crash_stop().
  - SDEI rung tests sdei_nmi_active() first; sdei_nmi_stop_cpus() is void.
  - Replaced the per-CPU stop cpumask with a write-once flag.
  - Commented the SDEI-park / no-CPU_OFF rationale.

Changes since v1
================

  - Dropped the SDEI hard-lockup-detector patch; use the buddy detector.
  - Reworked crash-stop into a third rung of smp_send_stop().
  - Renamed the driver to arm_sdei_nmi.c; widened the MAINTAINERS glob.

v4: https://lore.kernel.org/all/cover.1781709543.git.kas@kernel.org
v3: https://lore.kernel.org/all/cover.1781490440.git.kas@kernel.org
v2: https://lore.kernel.org/all/cover.1781082212.git.kas@kernel.org
v1: https://lore.kernel.org/all/cover.1780496779.git.kas@kernel.org

Also available at:

  git://git.kernel.org/pub/scm/linux/kernel/git/kas/linux.git sdei-nmi/v5

Kiryl Shutsemau (Meta) (4):
  firmware: arm_sdei: add sdei_is_present()
  firmware: arm_sdei: add SDEI_EVENT_SIGNAL support
  drivers/firmware: add SDEI cross-CPU NMI service for arm64
  arm64: escalate smp_send_stop() to an SDEI NMI as a last resort

 MAINTAINERS                     |   2 +-
 arch/arm64/include/asm/nmi.h    |  48 +++++++
 arch/arm64/kernel/smp.c         | 124 +++++++++++-----
 drivers/firmware/Kconfig        |  21 +++
 drivers/firmware/Makefile       |   1 +
 drivers/firmware/arm_sdei.c     |  22 +++
 drivers/firmware/arm_sdei_nmi.c | 246 ++++++++++++++++++++++++++++++++
 include/linux/arm_sdei.h        |   9 ++
 include/uapi/linux/arm_sdei.h   |   1 +
 9 files changed, 435 insertions(+), 39 deletions(-)
 create mode 100644 arch/arm64/include/asm/nmi.h
 create mode 100644 drivers/firmware/arm_sdei_nmi.c


base-commit: 8cd9520d35a6c38db6567e97dd93b1f11f185dc6
--
2.54.0


^ permalink raw reply

* Re: [PATCH v15 08/11] arm64/ptrace: Define and use _TIF_SYSCALL_EXIT_WORK
From: Ada Couprie Diaz @ 2026-06-29 15:05 UTC (permalink / raw)
  To: Jinjie Ruan
  Cc: mark.rutland, peterz, catalin.marinas, ldv, song, will, kees,
	thuth, ryan.roberts, anshuman.khandual, kevin.brodsky, pengcan,
	broonie, luto, linux-arm-kernel, wad, yeoreum.yun, oleg,
	linux-kernel, james.morse, tglx, liqiang01, linusw
In-Reply-To: <a1f5cfdc-ea1c-421c-a5bb-675406ca3311@huawei.com>

On 25/06/2026 12:41, Jinjie Ruan wrote:
> On 6/24/2026 10:53 PM, Ada Couprie Diaz wrote:
>> On 11/05/2026 10:21, Jinjie Ruan wrote:
>>> Introduce _TIF_SYSCALL_EXIT_WORK to filter out entry-only flags
>>> during the syscall exit path. This aligns arm64 with the generic
>>> entry framework's SYSCALL_WORK_EXIT semantics.
>>>
>>> [Rationale]
>>> The current syscall exit path uses _TIF_SYSCALL_WORK to decide whether
>>> to invoke syscall_exit_work(). However, _TIF_SYSCALL_WORK includes
>>> flags that are only relevant during syscall entry:
>>>
>>> 1. _TIF_SECCOMP: Seccomp filtering (__secure_computing) only runs
>>>     on entry. There is no seccomp callback for syscall exit.
>>>
>>> 2. _TIF_SYSCALL_EMU: In PTRACE_SYSEMU mode, the syscall is
>>>     intercepted and skipped on entry. Since the syscall is never
>>>     executed, reporting a syscall exit stop is unnecessary.
>>>
>>> [Changes]
>>> - Define _TIF_SYSCALL_EXIT_WORK: A new mask containing only flags
>>>     requiring exit processing: _TIF_SYSCALL_TRACE, _TIF_SYSCALL_AUDIT,
>>>     and _TIF_SYSCALL_TRACEPOINT.
>>>
>>> - Update exit path: Use _TIF_SYSCALL_EXIT_WORK in
>>>     syscall_exit_to_user_mode_work() to avoid redundant calls to
>>>     audit and ptrace reporting when only entry-flags are set.
>>>
>>> - Cleanup: Remove the has_syscall_work() helper as it is no longer
>>>     needed. Direct flag comparison is now used to distinguish between
>>>     entry and exit work requirements.
>>>
>>> [Impact]
>>> audit_syscall_exit() and report_syscall_exit() will no longer be
>>> triggered for seccomp-only or emu-only syscalls. This matches the
>>> generic entry behavior and improves efficiency by skipping unnecessary
>>> exit processing.
>>>
>>> Cc: Mark Rutland <mark.rutland@arm.com>
>>> Cc: Will Deacon <will@kernel.org>
>>> Cc: Catalin Marinas <catalin.marinas@arm.com>
>>> Reviewed-by: Linus Walleij <linusw@kernel.org>
>>> Reviewed-by: Yeoreum Yun <yeoreum.yun@arm.com>
>>> Signed-off-by: Jinjie Ruan <ruanjinjie@huawei.com>
>>> ---
>> Reviewed-by: Ada Couprie Diaz <ada.coupriediaz@arm.com>
>>
>> Definitely not related to this series, but it feels like this brings us
>> quite close to being able to switch to generic TIF flags as well :
>> only TIF_FOREIGN_PSTATE and TIF_MTE_ASYNC_FAULT
>> would need to be moved to the upper 16 bits,
>> with TIF_RESTORE_SIGMASK and TIF_MEMDIE freeing two slots there.
>>
>> Not sure how important the bit number changes would be and if any
>> of the extra generic bits require any arch support (TIF_POLLING_NRFLAG,
>> TIF_USER_RETURN_NOTIFY, TIF_RSEQ, TIF_HRTIMER_REARM)...
>>
>> But again, just thinking out loud !
> Hi Ada,
>
> You have incredible foresight! You are absolutely right that this series
> lays the perfect groundwork for switching arm64 to generic TIF flags
> (HAVE_GENERIC_TIF_BITS).
>
> I am happy to share that I have already implemented exactly what you
> described—including migrating the architecture-specific flags to the
> upper 16 bits and enabling the generic TIF infrastructure—in a separate,
> dedicated patch series.
>
> You can find the implementation and discussion here:
>
> https://lore.kernel.org/all/20260320104222.1381274-1-ruanjinjie@huawei.com/
>
> Since that series directly builds on top of the cleanups and
> infrastructure introduced here, I plan to actively push it forward right
> after we get this core generic entry conversion landed.
>
> Thanks again for looking so far ahead and validating the direction!
>
> Best regards,
> Jinjie

Hi Jinjie,

Oh, neat, I evidently missed this series ;
glad you confirmed I was on the right track !

I am looking forward to seeing both those works merged then :)

Kind regards,
Ada



^ permalink raw reply

* Re: [PATCH v20 01/14] dmaengine: constify struct dma_descriptor_metadata_ops
From: Pandey, Radhey Shyam @ 2026-06-29 15:04 UTC (permalink / raw)
  To: Bartosz Golaszewski, Vinod Koul, Jonathan Corbet, Thara Gopinath,
	Herbert Xu, David S. Miller, Udit Tiwari, Md Sadre Alam,
	Dmitry Baryshkov, Manivannan Sadhasivam, Stephan Gerhold,
	Bjorn Andersson, Peter Ujfalusi, Michal Simek, Frank Li,
	Andy Gross, Neil Armstrong
  Cc: dmaengine, linux-doc, linux-kernel, linux-arm-msm, linux-crypto,
	linux-arm-kernel, brgl, Bartosz Golaszewski
In-Reply-To: <20260629-qcom-qce-cmd-descr-v20-1-56f67da84c05@oss.qualcomm.com>

> There's no reason for the instances of this struct to be modifiable.
> Constify the pointer in struct dma_async_tx_descriptor and all drivers
> currently using it.
> 
> Reviewed-by: Manivannan Sadhasivam <mani@kernel.org>
> Signed-off-by: Bartosz Golaszewski <bartosz.golaszewski@oss.qualcomm.com>

Reviewed-by: Radhey Shyam Pandey <radhey.shyam.pandey@amd.com>
Thanks!

> ---
>   drivers/dma/ti/k3-udma.c        | 2 +-
>   drivers/dma/xilinx/xilinx_dma.c | 2 +-
>   include/linux/dmaengine.h       | 2 +-
>   3 files changed, 3 insertions(+), 3 deletions(-)
> 
> diff --git a/drivers/dma/ti/k3-udma.c b/drivers/dma/ti/k3-udma.c
> index 1cf158eb7bdb541c4e7f4f79f65ab70be4311fad..fb21e0df5ab7b20e4e16777b5ff7f61d2ae67b2b 100644
> --- a/drivers/dma/ti/k3-udma.c
> +++ b/drivers/dma/ti/k3-udma.c
> @@ -3408,7 +3408,7 @@ static int udma_set_metadata_len(struct dma_async_tx_descriptor *desc,
>   	return 0;
>   }
>   
> -static struct dma_descriptor_metadata_ops metadata_ops = {
> +static const struct dma_descriptor_metadata_ops metadata_ops = {
>   	.attach = udma_attach_metadata,
>   	.get_ptr = udma_get_metadata_ptr,
>   	.set_len = udma_set_metadata_len,
> diff --git a/drivers/dma/xilinx/xilinx_dma.c b/drivers/dma/xilinx/xilinx_dma.c
> index 404235c1735384635597e88edc25c67c7d250647..165b11a7c776abc6a8d66d631e19da669644577d 100644
> --- a/drivers/dma/xilinx/xilinx_dma.c
> +++ b/drivers/dma/xilinx/xilinx_dma.c
> @@ -653,7 +653,7 @@ static void *xilinx_dma_get_metadata_ptr(struct dma_async_tx_descriptor *tx,
>   	return seg->hw.app;
>   }
>   
> -static struct dma_descriptor_metadata_ops xilinx_dma_metadata_ops = {
> +static const struct dma_descriptor_metadata_ops xilinx_dma_metadata_ops = {
>   	.get_ptr = xilinx_dma_get_metadata_ptr,
>   };
>   
> diff --git a/include/linux/dmaengine.h b/include/linux/dmaengine.h
> index b3d251c9734e95e1b75cf6763d4d2c3a1c6a9910..5244edb90e7e7510bf4460b6a74ee2a7f91c1ccc 100644
> --- a/include/linux/dmaengine.h
> +++ b/include/linux/dmaengine.h
> @@ -623,7 +623,7 @@ struct dma_async_tx_descriptor {
>   	void *callback_param;
>   	struct dmaengine_unmap_data *unmap;
>   	enum dma_desc_metadata_mode desc_metadata_mode;
> -	struct dma_descriptor_metadata_ops *metadata_ops;
> +	const struct dma_descriptor_metadata_ops *metadata_ops;
>   #ifdef CONFIG_ASYNC_TX_ENABLE_CHANNEL_SWITCH
>   	struct dma_async_tx_descriptor *next;
>   	struct dma_async_tx_descriptor *parent;
> 



^ permalink raw reply

* Re: [PATCH 1/2] dt-bindings: iio: adc: Add Nuvoton MA35D1 EADC
From: David Lechner @ 2026-06-29 15:04 UTC (permalink / raw)
  To: Chi-Wen Weng, jic23, robh, krzk+dt, conor+dt
  Cc: nuno.sa, andy, linux-arm-kernel, linux-iio, devicetree,
	linux-kernel, cwweng
In-Reply-To: <7e96cc1a-eb60-4eeb-937d-64e83bc35279@gmail.com>

On 6/29/26 2:11 AM, Chi-Wen Weng wrote:


>> Should there be a dmas property? Datasheet says it supports PDMA transfer.
> 
> The hardware does support PDMA, but DMA support is intentionally not
> included in this initial upstream version. The initial driver will only
> support interrupt-driven direct raw reads, and the MA35D1 PDMA provider
> is not upstream yet.
> 
> I would prefer to leave dmas/dma-names out of the initial binding and
> add them later together with DMA support. Please let me know if you
> would prefer optional DMA properties to be described now.

We always want the devicetree to be as complete as possible even
if the drier doesn't use all of the information.

So for trivial/well-known bindings like dmas, we should be able to
add it now.

> 
>> I assume 8 is for the internal batter voltage channel? Often, we don't
>> include fixed internal channels like this in the devicetree since they
>> are always the same and don't depend on external wiring.
> 
> Correct. Channels 0 to 7 are the external ADC input pins, while channel
> 8 is the internal VBAT input. I will limit the DT child channel nodes to
> external channels 0 to 7.
> 
> If VBAT support is added later, it can be exposed by the driver as a
> fixed internal channel rather than being described by devicetree.
> 
>> adc.yaml already specifies minItems and maxItems, so we don't need to
>> repeat it.
> 
> Since I plan to simplify v2 and drop differential channel support from
> the initial submission, I will remove diff-channels from the initial
> binding.

Same reasoning as above, we want the binding to be as complete as
possible, so we should not omit diff-channels since we know what
the bindings should look like already.

> 
> Differential input support can be added later once the fixed hardware
> pair constraints and signed output handling are implemented in the
> driver.
> 


^ permalink raw reply


This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox