Linux-ARM-Kernel Archive on lore.kernel.org
 help / color / mirror / Atom feed
* Re: [PATCH v20 04/10] firmware: psci: Introduce command-based reset in psci_sys_reset
From: Lorenzo Pieralisi @ 2026-03-27 14:07 UTC (permalink / raw)
  To: Shivendra Pratap
  Cc: Arnd Bergmann, Bjorn Andersson, Sebastian Reichel, Rob Herring,
	Souvik Chakravarty, Krzysztof Kozlowski, Andy Yan,
	Matthias Brugger, Mark Rutland, Conor Dooley, Konrad Dybcio,
	John Stultz, Moritz Fischer, Bartosz Golaszewski, Sudeep Holla,
	Florian Fainelli, Krzysztof Kozlowski, Dmitry Baryshkov,
	Mukesh Ojha, Andre Draszik, Kathiravan Thirumoorthy, linux-pm,
	linux-kernel, linux-arm-kernel, linux-arm-msm, devicetree,
	Srinivas Kandagatla
In-Reply-To: <20260304-arm-psci-system_reset2-vendor-reboots-v20-4-cf7d346b8372@oss.qualcomm.com>

On Wed, Mar 04, 2026 at 11:33:04PM +0530, Shivendra Pratap wrote:
> PSCI currently supports only COLD reset and ARCH WARM reset based on the
> Linux reboot_mode variable. The PSCI specification now includes
> SYSTEM_RESET2 for vendor-specific resets, but there's no mechanism to
> issue these through psci_sys_reset.
> 
> Add a command-based reset mechanism that allows external drivers to set
> the psci reset command via a new psci_set_reset_cmd() function.
> 
> The psci command-based reset is disabled by default and the
> psci_sys_reset follows its original flow until a psci_reset command is
> set. In kernel panic path, psci_reset command is ignored.

If it is function calls you should add parenthesis (eg psci_sys_reset ->
psci_sys_reset()).

You must explain why the kernel panic path requires separate handling
here AND in the code - think about looking at this years down the line
and figure out why kernel panics are special here.

> Signed-off-by: Shivendra Pratap <shivendra.pratap@oss.qualcomm.com>
> ---
>  drivers/firmware/psci/psci.c | 45 ++++++++++++++++++++++++++++++++++++++++++--
>  include/linux/psci.h         |  2 ++
>  2 files changed, 45 insertions(+), 2 deletions(-)
> 
> diff --git a/drivers/firmware/psci/psci.c b/drivers/firmware/psci/psci.c
> index 38ca190d4a22d6e7e0f06420e8478a2b0ec2fe6f..ae6f7a0aead913d740070080d4b2a3da15b29485 100644
> --- a/drivers/firmware/psci/psci.c
> +++ b/drivers/firmware/psci/psci.c
> @@ -51,6 +51,15 @@ static int resident_cpu = -1;
>  struct psci_operations psci_ops;
>  static enum arm_smccc_conduit psci_conduit = SMCCC_CONDUIT_NONE;
>  
> +struct psci_sys_reset_params {
> +	u32 system_reset;
> +	u32 reset_type;
> +	u32 cookie;
> +	bool cmd;
> +};
> +
> +static struct psci_sys_reset_params psci_reset;
> +
>  bool psci_tos_resident_on(int cpu)
>  {
>  	return cpu == resident_cpu;
> @@ -80,6 +89,28 @@ static u32 psci_cpu_suspend_feature;
>  static bool psci_system_reset2_supported;
>  static bool psci_system_off2_hibernate_supported;
>  
> +/**
> + * psci_set_reset_cmd - Sets the psci_reset_cmd for command-based
> + * reset which will be used in psci_sys_reset call.
> + *
> + * @cmd_sys_rst2: Set to true for SYSTEM_RESET2 based resets.
> + * @cmd_reset_type: Set the reset_type argument for psci_sys_reset.
> + * @cmd_cookie: Set the cookie argument for psci_sys_reset.
> + */
> +void psci_set_reset_cmd(bool cmd_sys_rst2, u32 cmd_reset_type, u32 cmd_cookie)
> +{

I don't think cmd_sys_rst2 is needed, as a replied in a different thread.

> +	if (cmd_sys_rst2 && psci_system_reset2_supported) {
> +		psci_reset.system_reset = PSCI_FN_NATIVE(1_1, SYSTEM_RESET2);
> +		psci_reset.reset_type = cmd_reset_type;
> +		psci_reset.cookie = cmd_cookie;
> +	} else {
> +		psci_reset.system_reset = PSCI_0_2_FN_SYSTEM_RESET;
> +		psci_reset.reset_type = 0;
> +		psci_reset.cookie = 0;
> +	}
> +	psci_reset.cmd = true;
> +}
> +
>  static inline bool psci_has_ext_power_state(void)
>  {
>  	return psci_cpu_suspend_feature &
> @@ -309,14 +340,24 @@ static int get_set_conduit_method(const struct device_node *np)
>  static int psci_sys_reset(struct notifier_block *nb, unsigned long action,
>  			  void *data)
>  {
> -	if ((reboot_mode == REBOOT_WARM || reboot_mode == REBOOT_SOFT) &&
> -	    psci_system_reset2_supported) {
> +	if (((reboot_mode == REBOOT_WARM || reboot_mode == REBOOT_SOFT) &&
> +	     psci_system_reset2_supported) && (panic_in_progress() || !psci_reset.cmd)) {
>  		/*
>  		 * reset_type[31] = 0 (architectural)
>  		 * reset_type[30:0] = 0 (SYSTEM_WARM_RESET)
>  		 * cookie = 0 (ignored by the implementation)
>  		 */
>  		invoke_psci_fn(PSCI_FN_NATIVE(1_1, SYSTEM_RESET2), 0, 0, 0);
> +	} else if (!panic_in_progress() && psci_reset.cmd) {
> +		/*
> +		 * Commands are being set in psci_set_reset_cmd
> +		 * This issues, SYSTEM_RESET2 arch warm reset or
> +		 * SYSTEM_RESET2 vendor-specific reset or
> +		 * a SYSTEM_RESET cold reset in accordance with
> +		 * the reboot-mode command.
> +		 */
> +		invoke_psci_fn(psci_reset.system_reset, psci_reset.reset_type,
> +			       psci_reset.cookie, 0);
>  	} else {
>  		invoke_psci_fn(PSCI_0_2_FN_SYSTEM_RESET, 0, 0, 0);

This is very hard to parse. IMO, what you should do is:

- Split this into two different paths: reboot_mode vs psci_reset.cmd == true.
- Document very clearly why a panic needs separate handling.

Something like:

if (psci_reset.cmd)
	handle_reset_cmd();
else
	handle_reboot_mode();

I don't think we are far from converging but I want to be able to maintain
this code going forward.

Thanks,
Lorenzo

>  	}
> diff --git a/include/linux/psci.h b/include/linux/psci.h
> index 4ca0060a3fc42ba1ca751c7862fb4ad8dda35a4c..d13ceca88eab8932894051e7c86e806c2ad8a73a 100644
> --- a/include/linux/psci.h
> +++ b/include/linux/psci.h
> @@ -45,8 +45,10 @@ struct psci_0_1_function_ids get_psci_0_1_function_ids(void);
>  
>  #if defined(CONFIG_ARM_PSCI_FW)
>  int __init psci_dt_init(void);
> +void psci_set_reset_cmd(bool cmd_sys_rst2, u32 cmd_reset_type, u32 cmd_cookie);
>  #else
>  static inline int psci_dt_init(void) { return 0; }
> +static inline void psci_set_reset_cmd(bool cmd_sys_rst2, u32 cmd_reset_type, u32 cmd_cookie) { }
>  #endif
>  
>  #if defined(CONFIG_ARM_PSCI_FW) && defined(CONFIG_ACPI)
> 
> -- 
> 2.34.1
> 


^ permalink raw reply

* Re: [PATCH v20 06/10] power: reset: Add psci-reboot-mode driver
From: Lorenzo Pieralisi @ 2026-03-27 14:08 UTC (permalink / raw)
  To: Bartosz Golaszewski
  Cc: Shivendra Pratap, Florian Fainelli, Krzysztof Kozlowski,
	Dmitry Baryshkov, Mukesh Ojha, Andre Draszik,
	Kathiravan Thirumoorthy, linux-pm, linux-kernel, linux-arm-kernel,
	linux-arm-msm, devicetree, Srinivas Kandagatla, Arnd Bergmann,
	Bjorn Andersson, Sebastian Reichel, Rob Herring,
	Souvik Chakravarty, Krzysztof Kozlowski, Andy Yan,
	Matthias Brugger, Mark Rutland, Conor Dooley, Konrad Dybcio,
	John Stultz, Moritz Fischer, Sudeep Holla
In-Reply-To: <CAMRc=McUdboG0ziWmUf+h9mUiuGesaFk2v27z_Opbw-AF33C0g@mail.gmail.com>

On Fri, Mar 06, 2026 at 02:32:46PM +0100, Bartosz Golaszewski wrote:
> On Thu, Mar 5, 2026 at 6:07 PM Shivendra Pratap
> <shivendra.pratap@oss.qualcomm.com> wrote:
> >
> > >
> > > You should pass the address of this function in faux_device_ops instead of
> > > calling it directly.
> >
> > In last patch, we were using a probe function. As faux_device_create,
> > calls the probe from its internal operations, "of_node" can only be
> > assigned from inside of faux device probe.
> >
> > As our primary requirement is to assign reboot-mode of_node to the faux
> > device, thought to make it this way. (As we did not want to assign it
> > inside the faux device probe).
> >
> 
> TBH This sounds like a limitation of the faux device API. I'll Cc you
> on a patch proposing to extend it with the ability of using a firmware
> node to describe the device. If it works for you, you can integrate it
> into your series and use it.

What's the status on this matter ?

Thanks,
Lorenzo


^ permalink raw reply

* Re: [PATCH v20 06/10] power: reset: Add psci-reboot-mode driver
From: Bartosz Golaszewski @ 2026-03-27 14:09 UTC (permalink / raw)
  To: Lorenzo Pieralisi
  Cc: Shivendra Pratap, Florian Fainelli, Krzysztof Kozlowski,
	Dmitry Baryshkov, Mukesh Ojha, Andre Draszik,
	Kathiravan Thirumoorthy, linux-pm, linux-kernel, linux-arm-kernel,
	linux-arm-msm, devicetree, Srinivas Kandagatla, Arnd Bergmann,
	Bjorn Andersson, Sebastian Reichel, Rob Herring,
	Souvik Chakravarty, Krzysztof Kozlowski, Andy Yan,
	Matthias Brugger, Mark Rutland, Conor Dooley, Konrad Dybcio,
	John Stultz, Moritz Fischer, Sudeep Holla
In-Reply-To: <acaPSW6VeYceoMnO@lpieralisi>

On Fri, Mar 27, 2026 at 3:08 PM Lorenzo Pieralisi <lpieralisi@kernel.org> wrote:
>
> On Fri, Mar 06, 2026 at 02:32:46PM +0100, Bartosz Golaszewski wrote:
> > On Thu, Mar 5, 2026 at 6:07 PM Shivendra Pratap
> > <shivendra.pratap@oss.qualcomm.com> wrote:
> > >
> > > >
> > > > You should pass the address of this function in faux_device_ops instead of
> > > > calling it directly.
> > >
> > > In last patch, we were using a probe function. As faux_device_create,
> > > calls the probe from its internal operations, "of_node" can only be
> > > assigned from inside of faux device probe.
> > >
> > > As our primary requirement is to assign reboot-mode of_node to the faux
> > > device, thought to make it this way. (As we did not want to assign it
> > > inside the faux device probe).
> > >
> >
> > TBH This sounds like a limitation of the faux device API. I'll Cc you
> > on a patch proposing to extend it with the ability of using a firmware
> > node to describe the device. If it works for you, you can integrate it
> > into your series and use it.
>
> What's the status on this matter ?
>

I looked around and didn't find any good reason for adding this after
all so I dropped it.

Bart


^ permalink raw reply

* Re: [PATCH v2] i2c: rk3x: add support for SCL OE debounce and slave hold recovery
From: Andi Shyti @ 2026-03-27 14:13 UTC (permalink / raw)
  To: Anand Moon
  Cc: Heiko Stuebner, moderated list:ARM/Rockchip SoC support,
	open list:ARM/Rockchip SoC support,
	open list:I2C SUBSYSTEM HOST DRIVERS, open list, David Wu
In-Reply-To: <20260321105146.7419-1-linux.amoon@gmail.com>

Hi Anand,

...

> @@ -1125,6 +1141,17 @@ static int rk3x_i2c_xfer_common(struct i2c_adapter *adap,
>  		}
>  	}
>  
> +	/*
> +	 * If a timeout occurred and the slave is holding SCL,
> +	 * re-apply the timings/dividers to attempt recovery.
> +	 */
> +	if (ret == -ETIMEDOUT && i2c->soc_data->has_scl_oe_debounce) {
> +		if (ipd & REG_INT_SLV_HDSCL) {
> +			dev_err(i2c->dev, "SCL hold by slave detected, resetting timings.\n");
> +			rk3x_i2c_adapt_div(i2c, clk_get_rate(i2c->clk));

argh! this nests i2c->lock. rk3x_i2c_xfer_common() already holds
it when calling rk3x_i2c_adapt_div().
Andi

> +		}
> +	}
> +


^ permalink raw reply

* Re: [PATCH v20 06/10] power: reset: Add psci-reboot-mode driver
From: Lorenzo Pieralisi @ 2026-03-27 14:14 UTC (permalink / raw)
  To: Shivendra Pratap
  Cc: Arnd Bergmann, Bjorn Andersson, Sebastian Reichel, Rob Herring,
	Souvik Chakravarty, Krzysztof Kozlowski, Andy Yan,
	Matthias Brugger, Mark Rutland, Conor Dooley, Konrad Dybcio,
	John Stultz, Moritz Fischer, Bartosz Golaszewski, Sudeep Holla,
	Florian Fainelli, Krzysztof Kozlowski, Dmitry Baryshkov,
	Mukesh Ojha, Andre Draszik, Kathiravan Thirumoorthy, linux-pm,
	linux-kernel, linux-arm-kernel, linux-arm-msm, devicetree,
	Srinivas Kandagatla
In-Reply-To: <20260304-arm-psci-system_reset2-vendor-reboots-v20-6-cf7d346b8372@oss.qualcomm.com>

On Wed, Mar 04, 2026 at 11:33:06PM +0530, Shivendra Pratap wrote:
> PSCI supports different types of resets like COLD reset, ARCH WARM
> reset, vendor-specific resets. Currently there is no common driver that
> handles all supported psci resets at one place. Additionally, there is
> no common mechanism to issue the supported psci resets from userspace.
> 
> Add a PSCI reboot mode driver and define two types of PSCI resets in the
> driver as reboot-modes: predefined resets controlled by Linux
> reboot_mode and customizable resets defined by SoC vendors in their
> device tree under the psci:reboot-mode node.
> 
> Register the driver with the reboot-mode framework to interface these
> resets to userspace. When userspace initiates a supported command, pass
> the reset arguments to the PSCI driver to enable command-based reset.
> 
> This change allows userspace to issue supported PSCI reset commands
> using the standard reboot system calls while enabling SoC vendors to
> define their specific resets for PSCI.
> 
> Signed-off-by: Shivendra Pratap <shivendra.pratap@oss.qualcomm.com>
> ---
>  drivers/power/reset/Kconfig            |  10 +++
>  drivers/power/reset/Makefile           |   1 +
>  drivers/power/reset/psci-reboot-mode.c | 119 +++++++++++++++++++++++++++++++++

Add an entry into MAINTAINERS.POWER STATE COORDINATION INTERFACE for this
specific file because I'd like to keep an eye on it, if you don't mind.

Creating a MAINTAINER entry just for this seems overkill to me, it
does not look like it is done for other reboot mode drivers.

Thanks,
Lorenzo

>  3 files changed, 130 insertions(+)
> 
> diff --git a/drivers/power/reset/Kconfig b/drivers/power/reset/Kconfig
> index f6c1bcbb57deff3568d6b1b326454add3b3bbf06..529d6c7d3555601f7b7e6199acd29838030fcef2 100644
> --- a/drivers/power/reset/Kconfig
> +++ b/drivers/power/reset/Kconfig
> @@ -348,6 +348,16 @@ config NVMEM_REBOOT_MODE
>  	  then the bootloader can read it and take different
>  	  action according to the mode.
>  
> +config PSCI_REBOOT_MODE
> +	bool "PSCI reboot mode driver"
> +	depends on OF && ARM_PSCI_FW
> +	select REBOOT_MODE
> +	help
> +	  Say y here will enable PSCI reboot mode driver. This gets
> +          the PSCI reboot mode arguments and passes them to psci
> +	  driver. psci driver uses these arguments for issuing
> +	  device reset into different boot states.
> +
>  config POWER_MLXBF
>  	tristate "Mellanox BlueField power handling driver"
>  	depends on (GPIO_MLXBF2 || GPIO_MLXBF3) && ACPI
> diff --git a/drivers/power/reset/Makefile b/drivers/power/reset/Makefile
> index 0e4ae6f6b5c55729cf60846d47e6fe0fec24f3cc..49774b42cdf61fd57a5b70f286c65c9d66bbc0cb 100644
> --- a/drivers/power/reset/Makefile
> +++ b/drivers/power/reset/Makefile
> @@ -40,4 +40,5 @@ obj-$(CONFIG_REBOOT_MODE) += reboot-mode.o
>  obj-$(CONFIG_SYSCON_REBOOT_MODE) += syscon-reboot-mode.o
>  obj-$(CONFIG_POWER_RESET_SC27XX) += sc27xx-poweroff.o
>  obj-$(CONFIG_NVMEM_REBOOT_MODE) += nvmem-reboot-mode.o
> +obj-$(CONFIG_PSCI_REBOOT_MODE) += psci-reboot-mode.o
>  obj-$(CONFIG_POWER_MLXBF) += pwr-mlxbf.o
> diff --git a/drivers/power/reset/psci-reboot-mode.c b/drivers/power/reset/psci-reboot-mode.c
> new file mode 100644
> index 0000000000000000000000000000000000000000..86bef195228b0924704c2936b99f6801c14ff1b1
> --- /dev/null
> +++ b/drivers/power/reset/psci-reboot-mode.c
> @@ -0,0 +1,119 @@
> +// SPDX-License-Identifier: GPL-2.0-only
> +/*
> + * Copyright (c) Qualcomm Technologies, Inc. and/or its subsidiaries.
> + */
> +
> +#include <linux/device/faux.h>
> +#include <linux/device.h>
> +#include <linux/err.h>
> +#include <linux/of.h>
> +#include <linux/psci.h>
> +#include <linux/reboot.h>
> +#include <linux/reboot-mode.h>
> +#include <linux/types.h>
> +
> +/*
> + * Predefined reboot-modes are defined as per the values
> + * of enum reboot_mode defined in the kernel: reboot.c.
> + */
> +static struct mode_info psci_resets[] = {
> +	{ .mode = "warm", .magic = REBOOT_WARM},
> +	{ .mode = "soft", .magic = REBOOT_SOFT},
> +	{ .mode = "cold", .magic = REBOOT_COLD},
> +};
> +
> +static void psci_reboot_mode_set_predefined_modes(struct reboot_mode_driver *reboot)
> +{
> +	INIT_LIST_HEAD(&reboot->predefined_modes);
> +	for (u32 i = 0; i < ARRAY_SIZE(psci_resets); i++) {
> +		/* Prepare the magic with arg1 as 0 and arg2 as per pre-defined mode */
> +		psci_resets[i].magic = REBOOT_MODE_MAGIC(0, psci_resets[i].magic);
> +		INIT_LIST_HEAD(&psci_resets[i].list);
> +		list_add_tail(&psci_resets[i].list, &reboot->predefined_modes);
> +	}
> +}
> +
> +/*
> + * arg1 is reset_type(Low 32 bit of magic).
> + * arg2 is cookie(High 32 bit of magic).
> + * If reset_type is 0, cookie will be used to decide the reset command.
> + */
> +static int psci_reboot_mode_write(struct reboot_mode_driver *reboot, u64 magic)
> +{
> +	u32 reset_type = REBOOT_MODE_ARG1(magic);
> +	u32 cookie = REBOOT_MODE_ARG2(magic);
> +
> +	if (reset_type == 0) {
> +		if (cookie == REBOOT_WARM || cookie == REBOOT_SOFT)
> +			psci_set_reset_cmd(true, 0, 0);
> +		else
> +			psci_set_reset_cmd(false, 0, 0);
> +	} else {
> +		psci_set_reset_cmd(true, reset_type, cookie);
> +	}
> +
> +	return NOTIFY_DONE;
> +}
> +
> +static int psci_reboot_mode_register_device(struct faux_device *fdev)
> +{
> +	struct reboot_mode_driver *reboot;
> +	int ret;
> +
> +	reboot = devm_kzalloc(&fdev->dev, sizeof(*reboot), GFP_KERNEL);
> +	if (!reboot)
> +		return -ENOMEM;
> +
> +	psci_reboot_mode_set_predefined_modes(reboot);
> +	reboot->write = psci_reboot_mode_write;
> +	reboot->dev = &fdev->dev;
> +
> +	ret = devm_reboot_mode_register(&fdev->dev, reboot);
> +	if (ret) {
> +		dev_err_probe(&fdev->dev, ret, "devm_reboot_mode_register failed %d\n", ret);
> +		return ret;
> +	}
> +
> +	return 0;
> +}
> +
> +static int __init psci_reboot_mode_init(void)
> +{
> +	struct device_node *psci_np;
> +	struct faux_device *fdev;
> +	struct device_node *np;
> +	int ret;
> +
> +	psci_np = of_find_compatible_node(NULL, NULL, "arm,psci-1.0");
> +	if (!psci_np)
> +		return -ENODEV;
> +	/*
> +	 * Look for reboot-mode in the psci node. Even if the reboot-mode
> +	 * node is not defined in psci, continue to register with the
> +	 * reboot-mode driver and let the dev.ofnode be set as NULL.
> +	 */
> +	np = of_find_node_by_name(psci_np, "reboot-mode");
> +
> +	fdev = faux_device_create("psci-reboot-mode", NULL, NULL);
> +	if (!fdev) {
> +		ret = -ENODEV;
> +		goto error;
> +	}
> +
> +	device_set_node(&fdev->dev, of_fwnode_handle(np));
> +	ret = psci_reboot_mode_register_device(fdev);
> +	if (ret)
> +		goto error;
> +
> +	return 0;
> +
> +error:
> +	of_node_put(np);
> +	if (fdev) {
> +		device_set_node(&fdev->dev, NULL);
> +		faux_device_destroy(fdev);
> +	}
> +
> +	return ret;
> +}
> +device_initcall(psci_reboot_mode_init);
> 
> -- 
> 2.34.1
> 


^ permalink raw reply

* Re: [PATCH 6/9] dt-bindings: i2c: apple,i2c: Add t8122 compatible
From: Andi Shyti @ 2026-03-27 14:15 UTC (permalink / raw)
  To: Janne Grunau
  Cc: Rob Herring, Krzysztof Kozlowski, Conor Dooley, Lorenzo Pieralisi,
	Sven Peter, Neal Gompa, Wim Van Sebroeck, Guenter Roeck,
	Linus Walleij, Mark Kettenis, Uwe Kleine-König,
	Sasha Finkelstein, devicetree, linux-kernel, asahi,
	linux-arm-kernel, linux-watchdog, linux-gpio, linux-i2c,
	linux-pwm
In-Reply-To: <20260320-apple-m3-initial-devicetrees-v1-6-5842e1e393a8@jannau.net>

Hi Janne,

On Fri, Mar 20, 2026 at 01:23:24PM +0100, Janne Grunau wrote:
> The i2c block on the Apple silicon t8122 (M3) SoC is compatible with the
> existing driver. Add "apple,t8122-i2c" as SoC specific compatible under
> "apple,t8103-i2c" used by the deriver.
> 
> Signed-off-by: Janne Grunau <j@jannau.net>

Acked-by: Andi Shyti <andi.shyti@kernel.org>

Thanks,
Andi


^ permalink raw reply

* [PATCH 0/2] arm64: dts: ti: k3-pinctrl: some minor cleanup
From: Rasmus Villemoes @ 2026-03-27 14:15 UTC (permalink / raw)
  To: Nishanth Menon, Vignesh Raghavendra, Tero Kristo
  Cc: linux-arm-kernel, Rasmus Villemoes

I stumbled on a few things one might want to clean up. No functional change.

Rasmus Villemoes (2):
  arm64: dts: ti: k3-pinctrl: consistently use tabs for alignment
  arm64: dts: ti: k3-pinctrl: sort shift values numerically

 arch/arm64/boot/dts/ti/k3-pinctrl.h | 82 ++++++++++++++---------------
 1 file changed, 41 insertions(+), 41 deletions(-)

-- 
2.53.0



^ permalink raw reply

* [PATCH 1/2] arm64: dts: ti: k3-pinctrl: consistently use tabs for alignment
From: Rasmus Villemoes @ 2026-03-27 14:15 UTC (permalink / raw)
  To: Nishanth Menon, Vignesh Raghavendra, Tero Kristo
  Cc: linux-arm-kernel, Rasmus Villemoes
In-Reply-To: <20260327141513.1250499-1-linux@rasmusvillemoes.dk>

Currently, there's a mix of spaces and tabs used for aligning the
bodies of the macros, even within the same block. Use tabs throughout
for consistency.

No functional change; 'git diff -w' produces no output.

Signed-off-by: Rasmus Villemoes <linux@rasmusvillemoes.dk>
---
 arch/arm64/boot/dts/ti/k3-pinctrl.h | 78 ++++++++++++++---------------
 1 file changed, 39 insertions(+), 39 deletions(-)

diff --git a/arch/arm64/boot/dts/ti/k3-pinctrl.h b/arch/arm64/boot/dts/ti/k3-pinctrl.h
index dc8e03ae74c8..bdccb153e089 100644
--- a/arch/arm64/boot/dts/ti/k3-pinctrl.h
+++ b/arch/arm64/boot/dts/ti/k3-pinctrl.h
@@ -8,15 +8,15 @@
 #ifndef DTS_ARM64_TI_K3_PINCTRL_H
 #define DTS_ARM64_TI_K3_PINCTRL_H
 
-#define WKUP_LVL_EN_SHIFT       (7)
-#define WKUP_LVL_POL_SHIFT      (8)
+#define WKUP_LVL_EN_SHIFT	(7)
+#define WKUP_LVL_POL_SHIFT	(8)
 #define ST_EN_SHIFT		(14)
 #define PULLUDEN_SHIFT		(16)
 #define PULLTYPESEL_SHIFT	(17)
 #define RXACTIVE_SHIFT		(18)
-#define DRV_STR_SHIFT           (19)
-#define ISO_OVERRIDE_EN_SHIFT   (22)
-#define ISO_BYPASS_EN_SHIFT     (23)
+#define DRV_STR_SHIFT		(19)
+#define ISO_OVERRIDE_EN_SHIFT	(22)
+#define ISO_BYPASS_EN_SHIFT	(23)
 #define DEBOUNCE_SHIFT		(11)
 #define FORCE_DS_EN_SHIFT	(15)
 #define DS_EN_SHIFT		(24)
@@ -24,7 +24,7 @@
 #define DS_OUT_VAL_SHIFT	(26)
 #define DS_PULLUD_EN_SHIFT	(27)
 #define DS_PULLTYPE_SEL_SHIFT	(28)
-#define WKUP_EN_SHIFT           (29)
+#define WKUP_EN_SHIFT		(29)
 
 /* Schmitt trigger configuration */
 #define ST_DISABLE		(0 << ST_EN_SHIFT)
@@ -39,28 +39,28 @@
 #define INPUT_EN		(1 << RXACTIVE_SHIFT)
 #define INPUT_DISABLE		(0 << RXACTIVE_SHIFT)
 
-#define DS_PULL_DISABLE         (1 << DS_PULLUD_EN_SHIFT)
-#define DS_PULL_ENABLE          (0 << DS_PULLUD_EN_SHIFT)
+#define DS_PULL_DISABLE		(1 << DS_PULLUD_EN_SHIFT)
+#define DS_PULL_ENABLE		(0 << DS_PULLUD_EN_SHIFT)
 
-#define DS_PULL_UP              (1 << DS_PULLTYPE_SEL_SHIFT | DS_PULL_ENABLE)
-#define DS_PULL_DOWN            (0 << DS_PULLTYPE_SEL_SHIFT | DS_PULL_ENABLE)
+#define DS_PULL_UP		(1 << DS_PULLTYPE_SEL_SHIFT | DS_PULL_ENABLE)
+#define DS_PULL_DOWN		(0 << DS_PULLTYPE_SEL_SHIFT | DS_PULL_ENABLE)
 
-#define DS_STATE_EN             (1 << DS_EN_SHIFT)
-#define DS_STATE_DISABLE        (0 << DS_EN_SHIFT)
+#define DS_STATE_EN		(1 << DS_EN_SHIFT)
+#define DS_STATE_DISABLE	(0 << DS_EN_SHIFT)
 
-#define DS_INPUT_EN             (1 << DS_OUT_DIS_SHIFT | DS_STATE_EN)
-#define DS_INPUT_DISABLE        (0 << DS_OUT_DIS_SHIFT | DS_STATE_EN)
+#define DS_INPUT_EN		(1 << DS_OUT_DIS_SHIFT | DS_STATE_EN)
+#define DS_INPUT_DISABLE	(0 << DS_OUT_DIS_SHIFT | DS_STATE_EN)
 
-#define DS_OUT_VALUE_ZERO       (0 << DS_OUT_VAL_SHIFT)
-#define DS_OUT_VALUE_ONE        (1 << DS_OUT_VAL_SHIFT)
+#define DS_OUT_VALUE_ZERO	(0 << DS_OUT_VAL_SHIFT)
+#define DS_OUT_VALUE_ONE	(1 << DS_OUT_VAL_SHIFT)
 
 /* Configuration to enable wake-up on pin activity */
-#define WKUP_ENABLE             (1 << WKUP_EN_SHIFT)
-#define WKUP_DISABLE            (0 << WKUP_EN_SHIFT)
-#define WKUP_ON_LEVEL           (1 << WKUP_LVL_EN_SHIFT)
-#define WKUP_ON_EDGE            (0 << WKUP_LVL_EN_SHIFT)
-#define WKUP_LEVEL_LOW          (0 << WKUP_LVL_POL_SHIFT)
-#define WKUP_LEVEL_HIGH         (1 << WKUP_LVL_POL_SHIFT)
+#define WKUP_ENABLE		(1 << WKUP_EN_SHIFT)
+#define WKUP_DISABLE		(0 << WKUP_EN_SHIFT)
+#define WKUP_ON_LEVEL		(1 << WKUP_LVL_EN_SHIFT)
+#define WKUP_ON_EDGE		(0 << WKUP_LVL_EN_SHIFT)
+#define WKUP_LEVEL_LOW		(0 << WKUP_LVL_POL_SHIFT)
+#define WKUP_LEVEL_HIGH		(1 << WKUP_LVL_POL_SHIFT)
 
 /* Only these macros are expected be used directly in device tree files */
 #define PIN_OUTPUT		(INPUT_DISABLE | PULL_DISABLE)
@@ -82,14 +82,14 @@
 #define PIN_DEBOUNCE_CONF5	(5 << DEBOUNCE_SHIFT)
 #define PIN_DEBOUNCE_CONF6	(6 << DEBOUNCE_SHIFT)
 
-#define PIN_DRIVE_STRENGTH_NOMINAL      (0 << DRV_STR_SHIFT)
-#define PIN_DRIVE_STRENGTH_SLOW         (1 << DRV_STR_SHIFT)
-#define PIN_DRIVE_STRENGTH_FAST         (2 << DRV_STR_SHIFT)
+#define PIN_DRIVE_STRENGTH_NOMINAL	(0 << DRV_STR_SHIFT)
+#define PIN_DRIVE_STRENGTH_SLOW		(1 << DRV_STR_SHIFT)
+#define PIN_DRIVE_STRENGTH_FAST		(2 << DRV_STR_SHIFT)
 
 #define PIN_DS_FORCE_DISABLE		(0 << FORCE_DS_EN_SHIFT)
 #define PIN_DS_FORCE_ENABLE		(1 << FORCE_DS_EN_SHIFT)
-#define PIN_DS_ISO_OVERRIDE_DISABLE     (0 << ISO_OVERRIDE_EN_SHIFT)
-#define PIN_DS_ISO_OVERRIDE_ENABLE      (1 << ISO_OVERRIDE_EN_SHIFT)
+#define PIN_DS_ISO_OVERRIDE_DISABLE	(0 << ISO_OVERRIDE_EN_SHIFT)
+#define PIN_DS_ISO_OVERRIDE_ENABLE	(1 << ISO_OVERRIDE_EN_SHIFT)
 #define PIN_DS_OUT_ENABLE		(0 << DS_OUT_DIS_SHIFT)
 #define PIN_DS_OUT_DISABLE		(1 << DS_OUT_DIS_SHIFT)
 #define PIN_DS_OUT_VALUE_ZERO		(0 << DS_OUT_VAL_SHIFT)
@@ -98,18 +98,18 @@
 #define PIN_DS_PULLUD_DISABLE		(1 << DS_PULLUD_EN_SHIFT)
 #define PIN_DS_PULL_DOWN		(0 << DS_PULLTYPE_SEL_SHIFT)
 #define PIN_DS_PULL_UP			(1 << DS_PULLTYPE_SEL_SHIFT)
-#define PIN_DS_ISO_BYPASS               (1 << ISO_BYPASS_EN_SHIFT)
-#define PIN_DS_ISO_BYPASS_DISABLE       (0 << ISO_BYPASS_EN_SHIFT)
-
-#define PIN_DS_OUTPUT_LOW               (DS_INPUT_DISABLE | DS_OUT_VALUE_ZERO)
-#define PIN_DS_OUTPUT_HIGH              (DS_INPUT_DISABLE | DS_OUT_VALUE_ONE)
-#define PIN_DS_INPUT                    (DS_INPUT_EN | DS_PULL_DISABLE)
-#define PIN_DS_INPUT_PULLUP             (DS_INPUT_EN | DS_PULL_UP)
-#define PIN_DS_INPUT_PULLDOWN           (DS_INPUT_EN | DS_PULL_DOWN)
-
-#define PIN_WKUP_EN_LEVEL_LOW           (WKUP_ENABLE | WKUP_ON_LEVEL | WKUP_LEVEL_LOW)
-#define PIN_WKUP_EN_LEVEL_HIGH          (WKUP_ENABLE | WKUP_ON_LEVEL | WKUP_LEVEL_HIGH)
-#define PIN_WKUP_EN                     (WKUP_ENABLE | WKUP_ON_EDGE)
+#define PIN_DS_ISO_BYPASS		(1 << ISO_BYPASS_EN_SHIFT)
+#define PIN_DS_ISO_BYPASS_DISABLE	(0 << ISO_BYPASS_EN_SHIFT)
+
+#define PIN_DS_OUTPUT_LOW		(DS_INPUT_DISABLE | DS_OUT_VALUE_ZERO)
+#define PIN_DS_OUTPUT_HIGH		(DS_INPUT_DISABLE | DS_OUT_VALUE_ONE)
+#define PIN_DS_INPUT			(DS_INPUT_EN | DS_PULL_DISABLE)
+#define PIN_DS_INPUT_PULLUP		(DS_INPUT_EN | DS_PULL_UP)
+#define PIN_DS_INPUT_PULLDOWN		(DS_INPUT_EN | DS_PULL_DOWN)
+
+#define PIN_WKUP_EN_LEVEL_LOW		(WKUP_ENABLE | WKUP_ON_LEVEL | WKUP_LEVEL_LOW)
+#define PIN_WKUP_EN_LEVEL_HIGH		(WKUP_ENABLE | WKUP_ON_LEVEL | WKUP_LEVEL_HIGH)
+#define PIN_WKUP_EN			(WKUP_ENABLE | WKUP_ON_EDGE)
 
 /* Default mux configuration for gpio-ranges to use with pinctrl */
 #define PIN_GPIO_RANGE_IOPAD	(PIN_INPUT | 7)
-- 
2.53.0



^ permalink raw reply related

* [PATCH 2/2] arm64: dts: ti: k3-pinctrl: sort shift values numerically
From: Rasmus Villemoes @ 2026-03-27 14:15 UTC (permalink / raw)
  To: Nishanth Menon, Vignesh Raghavendra, Tero Kristo
  Cc: linux-arm-kernel, Rasmus Villemoes
In-Reply-To: <20260327141513.1250499-1-linux@rasmusvillemoes.dk>

The macros are easier to read when the values are sorted numerically.

Signed-off-by: Rasmus Villemoes <linux@rasmusvillemoes.dk>
---
 arch/arm64/boot/dts/ti/k3-pinctrl.h | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/arch/arm64/boot/dts/ti/k3-pinctrl.h b/arch/arm64/boot/dts/ti/k3-pinctrl.h
index bdccb153e089..4491898d8294 100644
--- a/arch/arm64/boot/dts/ti/k3-pinctrl.h
+++ b/arch/arm64/boot/dts/ti/k3-pinctrl.h
@@ -10,15 +10,15 @@
 
 #define WKUP_LVL_EN_SHIFT	(7)
 #define WKUP_LVL_POL_SHIFT	(8)
+#define DEBOUNCE_SHIFT		(11)
 #define ST_EN_SHIFT		(14)
+#define FORCE_DS_EN_SHIFT	(15)
 #define PULLUDEN_SHIFT		(16)
 #define PULLTYPESEL_SHIFT	(17)
 #define RXACTIVE_SHIFT		(18)
 #define DRV_STR_SHIFT		(19)
 #define ISO_OVERRIDE_EN_SHIFT	(22)
 #define ISO_BYPASS_EN_SHIFT	(23)
-#define DEBOUNCE_SHIFT		(11)
-#define FORCE_DS_EN_SHIFT	(15)
 #define DS_EN_SHIFT		(24)
 #define DS_OUT_DIS_SHIFT	(25)
 #define DS_OUT_VAL_SHIFT	(26)
-- 
2.53.0



^ permalink raw reply related

* [PATCH] MAINTAINERS: Add Rockchip keyword matching
From: Sebastian Reichel @ 2026-03-27 14:21 UTC (permalink / raw)
  To: Heiko Stuebner
  Cc: linux-kernel, linux-arm-kernel, linux-rockchip, Sebastian Reichel

Add keyword based matching for 'ARM/Rockchip SoC support'. This will
match rockchip, Rockchip, RockChip and ROCKCHIP separated by any
whitespace character or underscores.

The goal is to match arm64 defconfig patches, which should go through
the Rockchip tree as they right now only match the LKML and thus are
easily lost. The keyword matching is quite good for this, since it
also applies to the commit message and the config options itself might
not give any hint about being relevant for Rockchip.

Signed-off-by: Sebastian Reichel <sebastian.reichel@collabora.com>
---
This is not perfect (people need to write good commit messages), but
should improve the current situation quite a bit.
---
 MAINTAINERS | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/MAINTAINERS b/MAINTAINERS
index 55af015174a5..9f036f812823 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -3416,6 +3416,8 @@ F:	drivers/i2c/busses/i2c-rk3x.c
 F:	drivers/net/ethernet/stmicro/stmmac/dwmac-rk.c
 F:	sound/soc/rockchip/
 N:	rockchip
+K:	\b[Rr]ock[Cc]hip\b
+K:	(?:\b|_)ROCKCHIP(?:\b|_)
 
 ARM/SAMSUNG S3C, S5P AND EXYNOS ARM ARCHITECTURES
 M:	Krzysztof Kozlowski <krzk@kernel.org>

---
base-commit: 2e930174c99bf75c71f898779f3ce777d7db6fd1
change-id: 20260327-maintainers-rockchip-keyword-a805c1523f43

Best regards,
-- 
Sebastian Reichel <sebastian.reichel@collabora.com>



^ permalink raw reply related

* Re: [RFT PATCH v3] ARM: omap1: enable real software node lookup of GPIOs on Nokia 770
From: Bartosz Golaszewski @ 2026-03-27 14:22 UTC (permalink / raw)
  To: Aaro Koskinen
  Cc: Janusz Krzysztofik, Arnd Bergmann, Bartosz Golaszewski,
	Tony Lindgren, Russell King, Dmitry Torokhov, Hans de Goede,
	Linux-OMAP, linux-arm-kernel, linux-kernel, Kevin Hilman
In-Reply-To: <acaOlGcGQEZHQ_mJ@darkstar.musicnaut.iki.fi>

On Fri, Mar 27, 2026 at 3:05 PM Aaro Koskinen <aaro.koskinen@iki.fi> wrote:
>
> Hi,
>
> On Thu, Mar 26, 2026 at 09:57:31AM +0100, Bartosz Golaszewski wrote:
> > On Mon, Mar 16, 2026 at 9:50 AM Bartosz Golaszewski <brgl@kernel.org> wrote:
> > > On Fri, Mar 6, 2026 at 1:31 AM Kevin Hilman <khilman@kernel.org> wrote:
> > > > Bartosz Golaszewski <brgl@kernel.org> writes:
> > > > > On Thu, Feb 12, 2026 at 12:46 PM Arnd Bergmann <arnd@kernel.org> wrote:
> > > > >> On Thu, Feb 12, 2026, at 12:25, Bartosz Golaszewski wrote:
> > > > >> > Currently the board file for Nokia 770 creates dummy software nodes not
> > > > >> > attached in any way to the actual GPIO controller devices and uses the
> > > > >> > fact that GPIOLIB matching swnode's name to the GPIO chip's label during
> > > > >> > software node lookup. This behavior is wrong and we want to remove it.
> > > > >> > To that end, we need to first convert all existing users to creating
> > > > >> > actual fwnode links.
> > > > >> >
> > > > >> > Create real software nodes for GPIO controllers on OMAP16xx and
> > > > >> > reference them from the software nodes in the nokia board file.
> > > > >> >
> > > > >> > Signed-off-by: Bartosz Golaszewski <bartosz.golaszewski@oss.qualcomm.com>
> > > > >>
> > > > >> Acked-by: Arnd Bergmann <arnd@arndb.de>
> > > > >
> > > > > Aaro, Janusz: Can you please pick it up for v7.1?
> > > >
> > > > I can take this via the OMAP tree once I have confirmation from
> > > > Aaro/Janusz that they've tested.
> >
> > Hi again! Any chance we could get this queued? Janusz, Aaro: any objections?
>
> Unfortunately the patch doesn't work - 770 just dies silently. This
> means that e.g. CBUS GPIOs are not working as those are needed to keep
> the device powered. I'll try to figure out how to debug this...
>
> A.

Hmm, I'm wondering if there's a race with consumers already requesting
the GPIOs after the controller device is registered but before the
software node is added. I'll send a version with software nodes being
registered first, then passes as firmware nodes to the platform device
API before the device is registered.

Bart


^ permalink raw reply

* Re: [PATCH v2 00/12] arm64: dts: imx8mp: Correct PAD settings for PMIC_nINT
From: Frank Li @ 2026-03-27 14:32 UTC (permalink / raw)
  To: Peng Fan (OSS)
  Cc: Rob Herring, Krzysztof Kozlowski, Conor Dooley, Sascha Hauer,
	Pengutronix Kernel Team, Fabio Estevam, Laurent Pinchart,
	Shawn Guo, Daniel Scally, Marco Felsch, Gilles Talis,
	Viorel Suman, Shengjiu Wang, Jagan Teki, Manoj Sai, Matteo Lisi,
	Ray Chang, Richard Hu, Heiko Schocher, Martyn Welch, Josua Mayer,
	Goran Rađenović, Börge Strümpfel,
	Christoph Niedermaier, Marek Vasut, devicetree, imx,
	linux-arm-kernel, linux-kernel, kernel, Peng Fan, Kieran Bingham
In-Reply-To: <20260326-imx8mp-dts-fix-v2-v2-0-62c4ce727448@nxp.com>

On Thu, Mar 26, 2026 at 03:28:04PM +0800, Peng Fan (OSS) wrote:
> As reported in [1], there is interrupt storm for i.MX8MP DEBIX Model A.
> Per schematic, there is no on board PULL-UP resistors for GPIO1_IO03,
> so need to set PAD PUE and PU together to make pull up work properly.
>
> DEBIX Model SOM also has same issue as reported in [2].
>
> I gave a check on current i.MX8MP based boards, most boards have wrong
> PAD settings with PMIC_nINT. It is low level triggered interrupt.
> many boards only set PU, but PUE not set, so pull up not work properly.
>
> Patch 1 and 2 are to fix issue that confirmed by Laurent and  Kieran.
>
> I checked AB2 and NAVQ schematic, so these two boards are also having
> same issue.
>
> For other boards, I not able to find any public schematics. For per
> the DT settings(interrupt is configured LOW LEVEL trigger), so PMIC_nINT
> should be configured as PULL UP, per NXP reference design, there is no
> on-board resistors for PMIC_nINT, it counts on SoC internal PULL. So I think
> these boards are also having issues. But I use phase "there might be" in
> commit log.
>
> The last two patches, I think the PAD settings are wrong, but not sure
> they have interrupt storm issues, so just correct the settings.
>
> For imx8mp-skov-reva.dtsi, I am not sure whether it needs same fix, so
> not touch it.
>
> [1] https://lore.kernel.org/all/20260323105858.GA2185714@killaraus.ideasonboard.com/
> [2] https://lore.kernel.org/all/20260324194353.GB2352505@killaraus.ideasonboard.com/
>
> Signed-off-by: Peng Fan <peng.fan@nxp.com>
> ---
> Changes in V2:
>  - Fix more boards
>  - Drop preceding zero
>  - Link to v1: https://lore.kernel.org/all/20260324-imx8mp-dts-fix-v1-1-df0eb2f62543@nxp.com/
>
> ---
> Peng Fan (12):
>       arm64: dts: imx8mp-debix-model-a: Correct PAD settings for PMIC_nINT
>       arm64: dts: imx8mp-debix-som-a: Correct PAD settings for PMIC_nINT
>       arm64: dts: imx8mp-navqp: Correct PAD settings for PMIC_nINT
>       arm64: dts: imx8mp-ab2: Correct PAD settings for PMIC_nINT

This one squash to 7adad1a52c420 ("arm64: dts: imx8mp-ab2: add support for NXP i.MX8MP audio board (version 2)")
because it is still in my tree.

>       arm64: dts: imx8mp-icore-mx8mp: Correct PAD settings for PMIC_nINT
>       arm64: dts: imx8mp-edm-g: Correct PAD settings for PMIC_nINT
>       arm64: dts: imx8mp-aristainetos3a-som-v1: Correct PAD settings for PMIC_nINT
>       arm64: dts: imx8mp-nitrogen-som: Correct PAD settings for PMIC_nINT
>       arm64: dts: imx8mp-sr-som: Correct PAD settings for PMIC_nINT
>       arm64: dts: imx8mp-ultra-mach-sbc: Correct PAD settings for PMIC_nINT
>       arm64: dts: imx8mp-dhcom-som: Correct PAD settings for PMIC_nINT
>       arm64: dts: imx8mp-data-modul-edm-sbc: Correct PAD settings for PMIC_nINT

Other apply to 7.0 fixes branch. Thanks

Frank
>
>  arch/arm64/boot/dts/freescale/imx8mp-ab2.dts                    | 2 +-
>  arch/arm64/boot/dts/freescale/imx8mp-aristainetos3a-som-v1.dtsi | 2 +-
>  arch/arm64/boot/dts/freescale/imx8mp-data-modul-edm-sbc.dts     | 2 +-
>  arch/arm64/boot/dts/freescale/imx8mp-debix-model-a.dts          | 2 +-
>  arch/arm64/boot/dts/freescale/imx8mp-debix-som-a-bmb-08.dts     | 2 +-
>  arch/arm64/boot/dts/freescale/imx8mp-debix-som-a.dtsi           | 2 +-
>  arch/arm64/boot/dts/freescale/imx8mp-dhcom-som.dtsi             | 2 +-
>  arch/arm64/boot/dts/freescale/imx8mp-edm-g.dtsi                 | 2 +-
>  arch/arm64/boot/dts/freescale/imx8mp-icore-mx8mp.dtsi           | 2 +-
>  arch/arm64/boot/dts/freescale/imx8mp-navqp.dts                  | 2 +-
>  arch/arm64/boot/dts/freescale/imx8mp-nitrogen-som.dtsi          | 2 +-
>  arch/arm64/boot/dts/freescale/imx8mp-sr-som.dtsi                | 4 ++--
>  arch/arm64/boot/dts/freescale/imx8mp-ultra-mach-sbc.dts         | 4 ++--
>  13 files changed, 15 insertions(+), 15 deletions(-)
> ---
> base-commit: 66ba480978ce390e631e870b740a3406e3eb6b01
> change-id: 20260326-imx8mp-dts-fix-v2-89ede7320c6a
>
> Best regards,
> --
> Peng Fan <peng.fan@nxp.com>
>


^ permalink raw reply

* Re: [PATCH] arm64/kvm: Enable eager hugepage splitting if HDBSS is available
From: Leonardo Bras @ 2026-03-27 14:37 UTC (permalink / raw)
  To: Tian Zheng
  Cc: Leonardo Bras, maz, oupton, catalin.marinas, corbet, pbonzini,
	will, yuzenghui, wangzhou1, liuyonglong, Jonathan.Cameron,
	yezhenyu2, linuxarm, joey.gouly, kvmarm, kvm, linux-arm-kernel,
	linux-doc, linux-kernel, skhan, suzuki.poulose
In-Reply-To: <6cce203f-89d9-4e9d-8b28-9629eb53b180@huawei.com>

On Fri, Mar 27, 2026 at 03:40:30PM +0800, Tian Zheng wrote:
> 
> On 3/26/2026 2:20 AM, Leonardo Bras wrote:
> > FEAT_HDBSS speeds up guest memory dirty tracking by avoiding a page fault
> > and saving the entry in a tracking structure.
> > 
> > That may be a problem when we have guest memory backed by hugepages or
> > transparent huge pages, as it's not possible to do on-demand hugepage
> > splitting, relying only on eager hugepage splitting.
> > 
> > So, at stage2 initialization, enable eager hugepage splitting with
> > chunk = PAGE_SIZE if the system supports HDBSS.
> > 
> > Signed-off-by: Leonardo Bras <leo.bras@arm.com>
> > ---
> >   arch/arm64/kvm/mmu.c | 8 ++++++--
> >   1 file changed, 6 insertions(+), 2 deletions(-)
> > 
> > diff --git a/arch/arm64/kvm/mmu.c b/arch/arm64/kvm/mmu.c
> > index 070a01e53fcb..bdfa72b7c073 100644
> > --- a/arch/arm64/kvm/mmu.c
> > +++ b/arch/arm64/kvm/mmu.c
> > @@ -993,22 +993,26 @@ int kvm_init_stage2_mmu(struct kvm *kvm, struct kvm_s2_mmu *mmu, unsigned long t
> >   	mmu->last_vcpu_ran = alloc_percpu(typeof(*mmu->last_vcpu_ran));
> >   	if (!mmu->last_vcpu_ran) {
> >   		err = -ENOMEM;
> >   		goto out_destroy_pgtable;
> >   	}
> >   	for_each_possible_cpu(cpu)
> >   		*per_cpu_ptr(mmu->last_vcpu_ran, cpu) = -1;
> > -	 /* The eager page splitting is disabled by default */
> > -	mmu->split_page_chunk_size = KVM_ARM_EAGER_SPLIT_CHUNK_SIZE_DEFAULT;
> > +	 /* The eager page splitting is disabled by default if system has no HDBSS */
> > +	if (system_supports_hacdbs())
> > +		mmu->split_page_chunk_size = PAGE_SIZE;
> > +	else
> > +		mmu->split_page_chunk_size = KVM_ARM_EAGER_SPLIT_CHUNK_SIZE_DEFAULT;
> > +
> >   	mmu->split_page_cache.gfp_zero = __GFP_ZERO;
> >   	mmu->pgd_phys = __pa(pgt->pgd);
> >   	if (kvm_is_nested_s2_mmu(kvm, mmu))
> >   		kvm_init_nested_s2_mmu(mmu);
> >   	return 0;
> >   out_destroy_pgtable:
> 
> 
> Thanks again for sending this patch. I'll integrate it into the next version
> and run some tests.
> 
> 

Awesome, thanks!
Leo


^ permalink raw reply

* Re: [PATCH v2 0/2] media: staging: imx: fix multiple video input
From: Frank Li @ 2026-03-27 14:42 UTC (permalink / raw)
  To: Michael Tretter, Steve Longerbeam, Philipp Zabel,
	Mauro Carvalho Chehab, Pengutronix Kernel Team, Fabio Estevam,
	Hans Verkuil, linux-media, imx, linux-arm-kernel, stable,
	Michael Tretter, Laurent Pinchart
In-Reply-To: <aXPNRbXBt2PRdFe4@lizhi-Precision-Tower-5810>

On Fri, Jan 23, 2026 at 02:34:29PM -0500, Frank Li wrote:
> On Fri, Jan 23, 2026 at 05:58:57PM +0100, Michael Tretter wrote:
> > On Thu, 18 Dec 2025 10:09:07 +0100, Michael Tretter wrote:
> > > On Fri, 07 Nov 2025 11:34:32 +0100, Michael Tretter wrote:
> > > > If the IMX media pipeline is configured to receive multiple video
> > > > inputs, the second input stream may be broken on start. This happens if
> > > > the IMX CSI hardware has to be reconfigured for the second stream, while
> > > > the first stream is already running.
> > > >
> > > > The IMX CSI driver configures the IMX CSI in the link_validate callback.
> > > > The media pipeline is only validated on the first start. Thus, any later
> > > > start of the media pipeline skips the validation and directly starts
> > > > streaming. This may leave the hardware in an inconsistent state compared
> > > > to the driver configuration. Moving the hardware configuration to the
> > > > stream start to make sure that the hardware is configured correctly.
> > > >
> > > > Patch 1 removes the caching of the upstream mbus_config in
> > > > csi_link_validate and explicitly request the mbus_config in csi_start,
> > > > to get rid of this implicit dependency.
> > > >
> > > > Patch 2 actually moves the hardware register setting from
> > > > csi_link_validate to csi_start to fix the skipped hardware
> > > > reconfiguration.
> > >
> > > Gentle ping.
> >
> > Is there anything still missing to get these patches applied?
>

Applied, it should be media-committers/next branch, I have not permission
to change patchwork stage.

Frank

> Add Laurent Pinchart.
>
> Frank
>
> >
> > Michael
> >
> > > >
> > > > Signed-off-by: Michael Tretter <michael.tretter@pengutronix.de>
> > > > ---
> > > > Changes in v2:
> > > > - Document changed locking in commit message
> > > > - Link to v1: https://lore.kernel.org/r/20251105-media-imx-fixes-v1-0-99e48b4f5cbc@pengutronix.de
> > > >
> > > > ---
> > > > Michael Tretter (2):
> > > >       media: staging: imx: request mbus_config in csi_start
> > > >       media: staging: imx: configure src_mux in csi_start
> > > >
> > > >  drivers/staging/media/imx/imx-media-csi.c | 84 ++++++++++++++++++-------------
> > > >  1 file changed, 48 insertions(+), 36 deletions(-)
> > > > ---
> > > > base-commit: 27afd6e066cfd80ddbe22a4a11b99174ac89cced
> > > > change-id: 20251105-media-imx-fixes-acef77c7ba12


^ permalink raw reply

* Re: [PATCH 4/5] xor/arm64: Use shared NEON intrinsics implementation from 32-bit ARM
From: Ard Biesheuvel @ 2026-03-27 14:45 UTC (permalink / raw)
  To: Christoph Hellwig, Ard Biesheuvel
  Cc: linux-raid, linux-arm-kernel, linux-crypto, Russell King,
	Arnd Bergmann, Eric Biggers
In-Reply-To: <20260327135051.GA739@lst.de>

On Fri, 27 Mar 2026, at 14:50, Christoph Hellwig wrote:
> On Fri, Mar 27, 2026 at 12:30:52PM +0100, Ard Biesheuvel wrote:
>> From: Ard Biesheuvel <ardb@kernel.org>
>> 
>> Tweak the arm64 code so that the pure NEON intrinsics implementation of
>> XOR is shared between arm64 and ARM.
>
> Instead of hiding the implementation in a header, just split xor-neon.c
> into two .c files, one of which could be built by arm32 as well.

That is what patch 3/5 does. This patch wires up that version into arm64, and drops the copy that has become redundant as a result.

> probably
> in the arm/ instead of the arm64/ subdirectory, but we can also add a
> new arm-common one if that's what the arm maintainers prefer.

Having the shared pure NEON version in arm/ is perfectly fine.

Building it as a separate compilation unit for arm64 should also be straight-forward, the only issue is that the 2-way NEON version needs to be shared with the EOR3 compilation unit.




^ permalink raw reply

* Re: [PATCH] staging: media: imx: fix style issues
From: Frank Li @ 2026-03-27 14:47 UTC (permalink / raw)
  To: vivek yadav
  Cc: slongerbeam, p.zabel, mchehab, gregkh, shawnguo, s.hauer, kernel,
	festevam, linux-media, linux-staging, imx, linux-arm-kernel,
	linux-kernel
In-Reply-To: <20251202161413.92230-1-y9.vivek@gmail.com>

On Tue, Dec 02, 2025 at 09:44:13PM +0530, vivek yadav wrote:
> Applied checkpatch.pl recommendations:
> - corrected whitespace
> - fixed line length
> - adjusted indentation
>
> Signed-off-by: vivek yadav <y9.vivek@gmail.com>
> ---

Applied, thanks! It should be in media-committers/next.

Frank

> --
> 2.43.0
>


^ permalink raw reply

* Re: [PATCH v2 21/30] KVM: arm64: Kill topup_memcache from kvm_s2_fault
From: Marc Zyngier @ 2026-03-27 14:49 UTC (permalink / raw)
  To: kvmarm, linux-arm-kernel, kvm
  Cc: Joey Gouly, Suzuki K Poulose, Oliver Upton, Zenghui Yu,
	Fuad Tabba, Will Deacon, Quentin Perret
In-Reply-To: <20260327113618.4051534-22-maz@kernel.org>

On Fri, 27 Mar 2026 11:36:09 +0000,
Marc Zyngier <maz@kernel.org> wrote:
> 
> The topup_memcache field can be easily replaced by the equivalent
> conditions, and the resulting code is not much worse.
> 
> Tested-by: Fuad Tabba <tabba@google.com>
> Reviewed-by: Fuad Tabba <tabba@google.com>
> Reviewed-by: Suzuki K Poulose <suzuki.poulose@arm.com>
> Signed-off-by: Marc Zyngier <maz@kernel.org>
> ---
>  arch/arm64/kvm/mmu.c | 12 ++++++------
>  1 file changed, 6 insertions(+), 6 deletions(-)
> 
> diff --git a/arch/arm64/kvm/mmu.c b/arch/arm64/kvm/mmu.c
> index e8bda71e862b2..5b05caecdbd92 100644
> --- a/arch/arm64/kvm/mmu.c
> +++ b/arch/arm64/kvm/mmu.c
> @@ -1712,7 +1712,6 @@ static short kvm_s2_resolve_vma_size(const struct kvm_s2_fault_desc *s2fd,
>  
>  struct kvm_s2_fault {
>  	bool writable;
> -	bool topup_memcache;
>  	bool mte_allowed;
>  	bool is_vma_cacheable;
>  	bool s2_force_noncacheable;
> @@ -1983,9 +1982,8 @@ static int user_mem_abort(const struct kvm_s2_fault_desc *s2fd)
>  		.logging_active = logging_active,
>  		.force_pte = logging_active,
>  		.prot = KVM_PGTABLE_PROT_R,
> -		.topup_memcache = !perm_fault || (logging_active && kvm_is_write_fault(s2fd->vcpu)),
>  	};
> -	void *memcache;
> +	void *memcache = NULL;
>  	int ret;
>  
>  	/*
> @@ -1994,9 +1992,11 @@ static int user_mem_abort(const struct kvm_s2_fault_desc *s2fd)
>  	 * only exception to this is when dirty logging is enabled at runtime
>  	 * and a write fault needs to collapse a block entry into a table.
>  	 */
> -	ret = prepare_mmu_memcache(s2fd->vcpu, fault.topup_memcache, &memcache);
> -	if (ret)
> -		return ret;
> +	if (!perm_fault || (logging_active && kvm_is_write_fault(s2fd->vcpu))) {
> +		ret = prepare_mmu_memcache(s2fd->vcpu, true, &memcache);
> +		if (ret)
> +			return ret;
> +	}
>  
>  	/*
>  	 * Let's check if we will get back a huge page backed by hugetlbfs, or

Sashiko has spotted [1] an interesting corner case here, which is that the
original code always initialises memcache to its correct value, while
we now only do it in a limited number of cases.

I'm proposing to restore the original behaviour by folding the
following change into this patch, splitting the retrieval of the
memcache pointer from the top-up and avoiding the ugly pointer
indirection:

diff --git a/arch/arm64/kvm/mmu.c b/arch/arm64/kvm/mmu.c
index 1fe7182be45ac..03e1f389339c7 100644
--- a/arch/arm64/kvm/mmu.c
+++ b/arch/arm64/kvm/mmu.c
@@ -1513,25 +1513,22 @@ static bool kvm_vma_is_cacheable(struct vm_area_struct *vma)
 	}
 }
 
-static int prepare_mmu_memcache(struct kvm_vcpu *vcpu, bool topup_memcache,
-				void **memcache)
+static void *get_mmu_memcache(struct kvm_vcpu *vcpu)
 {
-	int min_pages;
-
 	if (!is_protected_kvm_enabled())
-		*memcache = &vcpu->arch.mmu_page_cache;
+		return &vcpu->arch.mmu_page_cache;
 	else
-		*memcache = &vcpu->arch.pkvm_memcache;
-
-	if (!topup_memcache)
-		return 0;
+		return &vcpu->arch.pkvm_memcache;
+}
 
-	min_pages = kvm_mmu_cache_min_pages(vcpu->arch.hw_mmu);
+static int topup_mmu_memcache(struct kvm_vcpu *vcpu, void *memcache)
+{
+	int min_pages = kvm_mmu_cache_min_pages(vcpu->arch.hw_mmu);
 
 	if (!is_protected_kvm_enabled())
-		return kvm_mmu_topup_memory_cache(*memcache, min_pages);
+		return kvm_mmu_topup_memory_cache(memcache, min_pages);
 
-	return topup_hyp_memcache(*memcache, min_pages);
+	return topup_hyp_memcache(memcache, min_pages);
 }
 
 /*
@@ -1589,7 +1586,8 @@ static int gmem_abort(const struct kvm_s2_fault_desc *s2fd)
 	gfn_t gfn;
 	int ret;
 
-	ret = prepare_mmu_memcache(s2fd->vcpu, true, &memcache);
+	memcache = get_mmu_memcache(s2fd->vcpu);
+	ret = topup_mmu_memcache(s2fd->vcpu, memcache);
 	if (ret)
 		return ret;
 
@@ -1993,7 +1991,7 @@ static int user_mem_abort(const struct kvm_s2_fault_desc *s2fd)
 	bool perm_fault = kvm_vcpu_trap_is_permission_fault(s2fd->vcpu);
 	struct kvm_s2_fault_vma_info s2vi = {};
 	enum kvm_pgtable_prot prot;
-	void *memcache = NULL;
+	void *memcache;
 	int ret;
 
 	/*
@@ -2002,9 +2000,10 @@ static int user_mem_abort(const struct kvm_s2_fault_desc *s2fd)
 	 * only exception to this is when dirty logging is enabled at runtime
 	 * and a write fault needs to collapse a block entry into a table.
 	 */
+	memcache = get_mmu_memcache(s2fd->vcpu);
 	if (!perm_fault || (memslot_is_logging(s2fd->memslot) &&
 			    kvm_is_write_fault(s2fd->vcpu))) {
-		ret = prepare_mmu_memcache(s2fd->vcpu, true, &memcache);
+		ret = topup_mmu_memcache(s2fd->vcpu, memcache);
 		if (ret)
 			return ret;
 	}

The bot has also pointed out a couple of cases where memcache and
permission faults interact badly. I'll look into them separately, as
they predate this rework.

Thanks,

	M.

[1] https://sashiko.dev/#/patchset/20260327113618.4051534-1-maz%40kernel.org?patch=12134

-- 
Without deviation from the norm, progress is not possible.


^ permalink raw reply related

* Re: [PATCH] staging: media: Remove unnecessary braces from if statement
From: Frank Li @ 2026-03-27 14:49 UTC (permalink / raw)
  To: Ayush Kumar
  Cc: slongerbeam, p.zabel, mchehab, gregkh, shawnguo, s.hauer, kernel,
	festevam, linux-media, linux-staging, imx, linux-arm-kernel,
	linux-kernel, kernel-newbies
In-Reply-To: <aSYcZYDUsJ3jy8cR@lizhi-Precision-Tower-5810>

On Tue, Nov 25, 2025 at 04:15:17PM -0500, Frank Li wrote:
> On Tue, Nov 25, 2025 at 08:23:31PM +0000, Ayush Kumar wrote:
> > Adhering to Linux kernel coding style guidelines (Chapter 3: Indentation).
> >
> > Signed-off-by: Ayush Kumar <ayushkr0s@gmail.com>
> > ---
>
> Reviewed-by: Frank Li <Frank.Li@nxp.com>

Applied, thank! It should be in media-committers/next branch

Frank

>
> >  drivers/staging/media/imx/imx-media-of.c | 3 +--
> >  1 file changed, 1 insertion(+), 2 deletions(-)
> >
> > diff --git a/drivers/staging/media/imx/imx-media-of.c b/drivers/staging/media/imx/imx-media-of.c
> > index bb28daa4d713..7413551052ae 100644
> > --- a/drivers/staging/media/imx/imx-media-of.c
> > +++ b/drivers/staging/media/imx/imx-media-of.c
> > @@ -57,9 +57,8 @@ int imx_media_add_of_subdevs(struct imx_media_dev *imxmd,
> >  		of_node_put(csi_np);
> >  		if (ret) {
> >  			/* unavailable or already added is not an error */
> > -			if (ret == -ENODEV || ret == -EEXIST) {
> > +			if (ret == -ENODEV || ret == -EEXIST)
> >  				continue;
> > -			}
> >
> >  			/* other error, can't continue */
> >  			return ret;
> > --
> > 2.43.0
> >


^ permalink raw reply

* Re: [RFC PATCH] dmaengine: xilinx_dma: Fix per-channel direction reporting via device_caps
From: Marek Vasut @ 2026-03-27 14:51 UTC (permalink / raw)
  To: Rahul Navale, Folker Schwesinger
  Cc: Rahul Navale, dmaengine, linux-arm-kernel, linux-kernel, vkoul,
	Frank.Li, michal.simek, suraj.gupta2, thomas.gessler,
	radhey.shyam.pandey, tomi.valkeinen, Michal Simek
In-Reply-To: <20260318123524.4959-1-rahulnavale04@gmail.com>

On 3/18/26 1:35 PM, Rahul Navale wrote:

Hello Rahul,

>> If yes,make sure you only test these three
> I have confirmed no other pathes applied on xilinx dma driver.
> I have applied only three patches provided by you.
> and tested audio but facing same issue.

Can you please add [1] to the patch stack and let me know whether that 
improves the behavior ?

Thank you

[1] 
https://lore.kernel.org/linux-sound/20260327143014.54867-1-marex@nabladev.com/


^ permalink raw reply

* Re: [PATCH v3 4/5] KVM: arm64: Enable HDBSS support and handle HDBSSF events
From: Leonardo Bras @ 2026-03-27 15:00 UTC (permalink / raw)
  To: Tian Zheng
  Cc: Leonardo Bras, maz, oupton, catalin.marinas, corbet, pbonzini,
	will, yuzenghui, wangzhou1, liuyonglong, Jonathan.Cameron,
	yezhenyu2, linuxarm, joey.gouly, kvmarm, kvm, linux-arm-kernel,
	linux-doc, linux-kernel, skhan, suzuki.poulose
In-Reply-To: <e3253959-0340-4c13-a980-a599e090a6de@huawei.com>

On Fri, Mar 27, 2026 at 03:35:29PM +0800, Tian Zheng wrote:
> 
> On 3/26/2026 2:05 AM, Leonardo Bras wrote:
> > Hello Tian,
> > 
> > I am currently working on HACDBS enablement(which will be rebased on top of
> > this patchset) and due to the fact HACDBS and HDBSS are kind of
> > complementary I will sometimes come with some questions for issues I have
> > faced myself on that part. :)
> > 
> > (see below)
> 
> 
> Of course! Happy to exchange ideas and learn together.

:)

> 
> 
> > 
> > On Wed, Feb 25, 2026 at 12:04:20PM +0800, Tian Zheng wrote:
> > > From: eillon <yezhenyu2@huawei.com>
> > > 
> > > HDBSS is enabled via an ioctl from userspace (e.g. QEMU) at the start of
> > > migration. This feature is only supported in VHE mode.
> > > 
> > > Initially, S2 PTEs doesn't contain the DBM attribute. During migration,
> > > write faults are handled by user_mem_abort, which relaxes permissions
> > > and adds the DBM bit when HDBSS is active. Once DBM is set, subsequent
> > > writes no longer trap, as the hardware automatically transitions the page
> > > from writable-clean to writable-dirty.
> > > 
> > > KVM does not scan S2 page tables to consume DBM. Instead, when HDBSS is
> > > enabled, the hardware observes the clean->dirty transition and records
> > > the corresponding page into the HDBSS buffer.
> > > 
> > > During sync_dirty_log, KVM kicks all vCPUs to force VM-Exit, ensuring
> > > that check_vcpu_requests flushes the HDBSS buffer and propagates the
> > > accumulated dirty information into the userspace-visible dirty bitmap.
> > > 
> > > Add fault handling for HDBSS including buffer full, external abort, and
> > > general protection fault (GPF).
> > > 
> > > Signed-off-by: eillon <yezhenyu2@huawei.com>
> > > Signed-off-by: Tian Zheng <zhengtian10@huawei.com>
> > > ---
> > >   arch/arm64/include/asm/esr.h      |   5 ++
> > >   arch/arm64/include/asm/kvm_host.h |  17 +++++
> > >   arch/arm64/include/asm/kvm_mmu.h  |   1 +
> > >   arch/arm64/include/asm/sysreg.h   |  11 ++++
> > >   arch/arm64/kvm/arm.c              | 102 ++++++++++++++++++++++++++++++
> > >   arch/arm64/kvm/hyp/vhe/switch.c   |  19 ++++++
> > >   arch/arm64/kvm/mmu.c              |  70 ++++++++++++++++++++
> > >   arch/arm64/kvm/reset.c            |   3 +
> > >   8 files changed, 228 insertions(+)
> > > 
> > > diff --git a/arch/arm64/include/asm/esr.h b/arch/arm64/include/asm/esr.h
> > > index 81c17320a588..2e6b679b5908 100644
> > > --- a/arch/arm64/include/asm/esr.h
> > > +++ b/arch/arm64/include/asm/esr.h
> > > @@ -437,6 +437,11 @@
> > >   #ifndef __ASSEMBLER__
> > >   #include <asm/types.h>
> > > 
> > > +static inline bool esr_iss2_is_hdbssf(unsigned long esr)
> > > +{
> > > +	return ESR_ELx_ISS2(esr) & ESR_ELx_HDBSSF;
> > > +}
> > > +
> > >   static inline unsigned long esr_brk_comment(unsigned long esr)
> > >   {
> > >   	return esr & ESR_ELx_BRK64_ISS_COMMENT_MASK;
> > > diff --git a/arch/arm64/include/asm/kvm_host.h b/arch/arm64/include/asm/kvm_host.h
> > > index 5d5a3bbdb95e..57ee6b53e061 100644
> > > --- a/arch/arm64/include/asm/kvm_host.h
> > > +++ b/arch/arm64/include/asm/kvm_host.h
> > > @@ -55,12 +55,17 @@
> > >   #define KVM_REQ_GUEST_HYP_IRQ_PENDING	KVM_ARCH_REQ(9)
> > >   #define KVM_REQ_MAP_L1_VNCR_EL2		KVM_ARCH_REQ(10)
> > >   #define KVM_REQ_VGIC_PROCESS_UPDATE	KVM_ARCH_REQ(11)
> > > +#define KVM_REQ_FLUSH_HDBSS			KVM_ARCH_REQ(12)
> > > 
> > >   #define KVM_DIRTY_LOG_MANUAL_CAPS   (KVM_DIRTY_LOG_MANUAL_PROTECT_ENABLE | \
> > >   				     KVM_DIRTY_LOG_INITIALLY_SET)
> > > 
> > >   #define KVM_HAVE_MMU_RWLOCK
> > > 
> > > +/* HDBSS entry field definitions */
> > > +#define HDBSS_ENTRY_VALID BIT(0)
> > > +#define HDBSS_ENTRY_IPA GENMASK_ULL(55, 12)
> > > +
> > >   /*
> > >    * Mode of operation configurable with kvm-arm.mode early param.
> > >    * See Documentation/admin-guide/kernel-parameters.txt for more information.
> > > @@ -84,6 +89,7 @@ int __init kvm_arm_init_sve(void);
> > >   u32 __attribute_const__ kvm_target_cpu(void);
> > >   void kvm_reset_vcpu(struct kvm_vcpu *vcpu);
> > >   void kvm_arm_vcpu_destroy(struct kvm_vcpu *vcpu);
> > > +void kvm_arm_vcpu_free_hdbss(struct kvm_vcpu *vcpu);
> > > 
> > >   struct kvm_hyp_memcache {
> > >   	phys_addr_t head;
> > > @@ -405,6 +411,8 @@ struct kvm_arch {
> > >   	 * the associated pKVM instance in the hypervisor.
> > >   	 */
> > >   	struct kvm_protected_vm pkvm;
> > > +
> > > +	bool enable_hdbss;
> > >   };
> > > 
> > >   struct kvm_vcpu_fault_info {
> > > @@ -816,6 +824,12 @@ struct vcpu_reset_state {
> > >   	bool		reset;
> > >   };
> > > 
> > > +struct vcpu_hdbss_state {
> > > +	phys_addr_t base_phys;
> > > +	u32 size;
> > > +	u32 next_index;
> > > +};
> > > +
> > >   struct vncr_tlb;
> > > 
> > >   struct kvm_vcpu_arch {
> > > @@ -920,6 +934,9 @@ struct kvm_vcpu_arch {
> > > 
> > >   	/* Per-vcpu TLB for VNCR_EL2 -- NULL when !NV */
> > >   	struct vncr_tlb	*vncr_tlb;
> > > +
> > > +	/* HDBSS registers info */
> > > +	struct vcpu_hdbss_state hdbss;
> > >   };
> > > 
> > >   /*
> > > diff --git a/arch/arm64/include/asm/kvm_mmu.h b/arch/arm64/include/asm/kvm_mmu.h
> > > index d968aca0461a..3fea8cfe8869 100644
> > > --- a/arch/arm64/include/asm/kvm_mmu.h
> > > +++ b/arch/arm64/include/asm/kvm_mmu.h
> > > @@ -183,6 +183,7 @@ int kvm_phys_addr_ioremap(struct kvm *kvm, phys_addr_t guest_ipa,
> > > 
> > >   int kvm_handle_guest_sea(struct kvm_vcpu *vcpu);
> > >   int kvm_handle_guest_abort(struct kvm_vcpu *vcpu);
> > > +void kvm_flush_hdbss_buffer(struct kvm_vcpu *vcpu);
> > > 
> > >   phys_addr_t kvm_mmu_get_httbr(void);
> > >   phys_addr_t kvm_get_idmap_vector(void);
> > > diff --git a/arch/arm64/include/asm/sysreg.h b/arch/arm64/include/asm/sysreg.h
> > > index f4436ecc630c..d11f4d0dd4e7 100644
> > > --- a/arch/arm64/include/asm/sysreg.h
> > > +++ b/arch/arm64/include/asm/sysreg.h
> > > @@ -1039,6 +1039,17 @@
> > > 
> > >   #define GCS_CAP(x)	((((unsigned long)x) & GCS_CAP_ADDR_MASK) | \
> > >   					       GCS_CAP_VALID_TOKEN)
> > > +
> > > +/*
> > > + * Definitions for the HDBSS feature
> > > + */
> > > +#define HDBSS_MAX_SIZE		HDBSSBR_EL2_SZ_2MB
> > > +
> > > +#define HDBSSBR_EL2(baddr, sz)	(((baddr) & GENMASK(55, 12 + sz)) | \
> > > +				 FIELD_PREP(HDBSSBR_EL2_SZ_MASK, sz))
> > > +
> > > +#define HDBSSPROD_IDX(prod)	FIELD_GET(HDBSSPROD_EL2_INDEX_MASK, prod)
> > > +
> > >   /*
> > >    * Definitions for GICv5 instructions]
> > >    */
> > > diff --git a/arch/arm64/kvm/arm.c b/arch/arm64/kvm/arm.c
> > > index 29f0326f7e00..d64da05e25c4 100644
> > > --- a/arch/arm64/kvm/arm.c
> > > +++ b/arch/arm64/kvm/arm.c
> > > @@ -125,6 +125,87 @@ int kvm_arch_vcpu_should_kick(struct kvm_vcpu *vcpu)
> > >   	return kvm_vcpu_exiting_guest_mode(vcpu) == IN_GUEST_MODE;
> > >   }
> > > 
> > > +void kvm_arm_vcpu_free_hdbss(struct kvm_vcpu *vcpu)
> > > +{
> > > +	struct page *hdbss_pg;
> > > +
> > > +	hdbss_pg = phys_to_page(vcpu->arch.hdbss.base_phys);
> > > +	if (hdbss_pg)
> > > +		__free_pages(hdbss_pg, vcpu->arch.hdbss.size);
> > > +
> > > +	vcpu->arch.hdbss.size = 0;
> > > +}
> > > +
> > > +static int kvm_cap_arm_enable_hdbss(struct kvm *kvm,
> > > +				    struct kvm_enable_cap *cap)
> > > +{
> > > +	unsigned long i;
> > > +	struct kvm_vcpu *vcpu;
> > > +	struct page *hdbss_pg = NULL;
> > > +	__u64 size = cap->args[0];
> > > +	bool enable = cap->args[1] ? true : false;
> > > +
> > > +	if (!system_supports_hdbss())
> > > +		return -EINVAL;
> > > +
> > > +	if (size > HDBSS_MAX_SIZE)
> > > +		return -EINVAL;
> > > +
> > > +	if (!enable && !kvm->arch.enable_hdbss) /* Already Off */
> > > +		return 0;
> > > +
> > > +	if (enable && kvm->arch.enable_hdbss) /* Already On, can't set size */
> > > +		return -EINVAL;
> > > +
> > > +	if (!enable) { /* Turn it off */
> > > +		kvm->arch.mmu.vtcr &= ~(VTCR_EL2_HD | VTCR_EL2_HDBSS | VTCR_EL2_HA);
> > > +
> > > +		kvm_for_each_vcpu(i, vcpu, kvm) {
> > > +			/* Kick vcpus to flush hdbss buffer. */
> > > +			kvm_vcpu_kick(vcpu);
> > > +
> > > +			kvm_arm_vcpu_free_hdbss(vcpu);
> > > +		}
> > > +
> > > +		kvm->arch.enable_hdbss = false;
> > > +
> > > +		return 0;
> > > +	}
> > > +
> > > +	/* Turn it on */
> > > +	kvm_for_each_vcpu(i, vcpu, kvm) {
> > > +		hdbss_pg = alloc_pages(GFP_KERNEL_ACCOUNT, size);
> > > +		if (!hdbss_pg)
> > > +			goto error_alloc;
> > > +
> > > +		vcpu->arch.hdbss = (struct vcpu_hdbss_state) {
> > > +			.base_phys = page_to_phys(hdbss_pg),
> > > +			.size = size,
> > > +			.next_index = 0,
> > > +		};
> > > +	}
> > > +
> > > +	kvm->arch.enable_hdbss = true;
> > > +	kvm->arch.mmu.vtcr |= VTCR_EL2_HD | VTCR_EL2_HDBSS | VTCR_EL2_HA;
> > > +
> > > +	/*
> > > +	 * We should kick vcpus out of guest mode here to load new
> > > +	 * vtcr value to vtcr_el2 register when re-enter guest mode.
> > > +	 */
> > > +	kvm_for_each_vcpu(i, vcpu, kvm)
> > > +		kvm_vcpu_kick(vcpu);
> > > +
> > > +	return 0;
> > > +
> > > +error_alloc:
> > > +	kvm_for_each_vcpu(i, vcpu, kvm) {
> > > +		if (vcpu->arch.hdbss.base_phys)
> > > +			kvm_arm_vcpu_free_hdbss(vcpu);
> > > +	}
> > > +
> > > +	return -ENOMEM;
> > > +}
> > > +
> > >   int kvm_vm_ioctl_enable_cap(struct kvm *kvm,
> > >   			    struct kvm_enable_cap *cap)
> > >   {
> > > @@ -182,6 +263,11 @@ int kvm_vm_ioctl_enable_cap(struct kvm *kvm,
> > >   		r = 0;
> > >   		set_bit(KVM_ARCH_FLAG_EXIT_SEA, &kvm->arch.flags);
> > >   		break;
> > > +	case KVM_CAP_ARM_HW_DIRTY_STATE_TRACK:
> > > +		mutex_lock(&kvm->lock);
> > > +		r = kvm_cap_arm_enable_hdbss(kvm, cap);
> > > +		mutex_unlock(&kvm->lock);
> > > +		break;
> > >   	default:
> > >   		break;
> > >   	}
> > > @@ -471,6 +557,9 @@ int kvm_vm_ioctl_check_extension(struct kvm *kvm, long ext)
> > >   			r = kvm_supports_cacheable_pfnmap();
> > >   		break;
> > > 
> > > +	case KVM_CAP_ARM_HW_DIRTY_STATE_TRACK:
> > > +		r = system_supports_hdbss();
> > > +		break;
> > >   	default:
> > >   		r = 0;
> > >   	}
> > > @@ -1120,6 +1209,9 @@ static int check_vcpu_requests(struct kvm_vcpu *vcpu)
> > >   		if (kvm_dirty_ring_check_request(vcpu))
> > >   			return 0;
> > > 
> > > +		if (kvm_check_request(KVM_REQ_FLUSH_HDBSS, vcpu))
> > > +			kvm_flush_hdbss_buffer(vcpu);
> > > +
> > >   		check_nested_vcpu_requests(vcpu);
> > >   	}
> > > 
> > > @@ -1898,7 +1990,17 @@ long kvm_arch_vcpu_unlocked_ioctl(struct file *filp, unsigned int ioctl,
> > > 
> > >   void kvm_arch_sync_dirty_log(struct kvm *kvm, struct kvm_memory_slot *memslot)
> > >   {
> > > +	/*
> > > +	 * Flush all CPUs' dirty log buffers to the dirty_bitmap.  Called
> > > +	 * before reporting dirty_bitmap to userspace. Send a request with
> > > +	 * KVM_REQUEST_WAIT to flush buffer synchronously.
> > > +	 */
> > > +	struct kvm_vcpu *vcpu;
> > > +
> > > +	if (!kvm->arch.enable_hdbss)
> > > +		return;
> > > 
> > > +	kvm_make_all_cpus_request(kvm, KVM_REQ_FLUSH_HDBSS);
> > >   }
> > > 
> > >   static int kvm_vm_ioctl_set_device_addr(struct kvm *kvm,
> > > diff --git a/arch/arm64/kvm/hyp/vhe/switch.c b/arch/arm64/kvm/hyp/vhe/switch.c
> > > index 9db3f11a4754..600cbc4f8ae9 100644
> > > --- a/arch/arm64/kvm/hyp/vhe/switch.c
> > > +++ b/arch/arm64/kvm/hyp/vhe/switch.c
> > > @@ -213,6 +213,23 @@ static void __vcpu_put_deactivate_traps(struct kvm_vcpu *vcpu)
> > >   	local_irq_restore(flags);
> > >   }
> > > 
> > > +static void __load_hdbss(struct kvm_vcpu *vcpu)
> > > +{
> > > +	struct kvm *kvm = vcpu->kvm;
> > > +	u64 br_el2, prod_el2;
> > > +
> > > +	if (!kvm->arch.enable_hdbss)
> > > +		return;
> > > +
> > > +	br_el2 = HDBSSBR_EL2(vcpu->arch.hdbss.base_phys, vcpu->arch.hdbss.size);
> > > +	prod_el2 = vcpu->arch.hdbss.next_index;
> > > +
> > > +	write_sysreg_s(br_el2, SYS_HDBSSBR_EL2);
> > > +	write_sysreg_s(prod_el2, SYS_HDBSSPROD_EL2);
> > > +
> > > +	isb();
> > > +}
> > > +
> > I see in the code below you trust that the tracking will happen with
> > PAGE_SIZE granularity (you track with PAGE_SHIFT).
> > 
> > That may be a problem when we have guest memory backed by hugepages or
> > transparent huge pages.
> > 
> > When we are using HDBSS, there is no fault happening, so we have no way of
> > doing on-demand block splitting, so we need to make use of eager block
> > splitting, _before_ we start to track anything, or else we may have
> > different-sized pages in the HDBSS buffer, which is harder to deal with.
> > 
> > Suggestion: do the eager splitting before we enable HDBSS.
> > 
> > For this to happen, we have to enable the EAGER_SPLIT_CHUNK_SIZE
> > capability, which can only be enabled when all memslots are empty.
> > 
> > I suggest doing that at kvm_init_stage2_mmu(), and checking if HDBSS is
> > in which case we set mmu->split_page_chunk_size to PAGESIZE.
> > 
> > I will send a patch you can put before this one to make sure it works :)
> > 
> > Thanks!
> > Leo
> 
> Hi Leo,
> 
> Thanks for the helpful suggestion. I had previously traced the
> hugepage-splitting path
> 
> during live migration and found that when migration starts, enabling dirty
> logging
> 
> triggers the splitting path. I also tested HDBSS with traditional hugepages
> and haven't
> 
> observed any issues yet.
> 
> 
> However, your concern is valid — there may be cases not covered, especially
> when the
> 
> VMM uses transparent hugepages. I'll integrate your patch into the next
> version and
> 
> run some tests.
> 
> 
> For reference, here's the path I traced:
> 
> ```
> 
> - userspace, e.g., QEMU
> 
> kvm_log_start
> +-> kvm_section_update_flags
>     +-> kvm_slot_update_flags
>         |
>         | // For each memory region, QEMU issues a
> KVM_SET_USER_MEMORY_REGION ioctl.
>         | // Before issuing it, flags are updated to include
> KVM_MEM_LOG_DIRTY_PAGES.
>         +-> kvm_mem_flags
>         +-> kvm_set_user_memory_region   // ioctl that enables dirty logging
> on the memslot
> 
> - KVM
> 
> KVM_SET_USER_MEMORY_REGION
> +-> kvm_vm_ioctl_set_memory_region
>     +-> kvm_set_memory_region / __kvm_set_memory_region
>         +-> kvm_set_memslot
>             +-> kvm_commit_memory_region
>                 +-> kvm_arch_commit_memory_region
>                     +-> kvm_mmu_split_memory_region
>                         // Splits Stage-2 hugepages/contiguous mappings into
> 4KB PTEs.

Right, except on a case we have dirty_log_manual_protect and init_set, when 
it returns before splitting pages:

```
if (kvm_dirty_log_manual_protect_and_init_set(kvm))
	return;
```

IIUC, that's desired to avoid holding the lock for a long time while it 
cleans every page in the beginning, and instead do it in a per dirty-page
basis. I guess it may benefit guests with very little dirty pages, as it 
does not have to split/dirty everything at the start. 
(Its a pain for my HACDBS routines, though)

>                         +-> kvm_mmu_split_huge_pages

Other important point here:
You can see in this function it skips splitting if chunk_size == 0.
This value is set by a capability that configures EAGER_SPLIT, meaning 
splitting before the guest have write faults, which is nice as the 
write-fault is faster.

Two points in this capability:
- It's optional, if it's not set, only on-demand splitting (on fault) will 
  happen, and since HDBSS removes the write-fault, we have no splitting
- It can be set to any valid block size, not only 4K, nor PAGE_SIZE, it can
  be set to PMD_SIZE, PUD_SIZE, and so on, which will depend on the 
  PAGE_SIZE the kernel was compiled to.
 
That's only some points to keep in mind :)

		if (kvm_dirty_log_manual_protect_and_init_set(kvm))
			return;

>                             +-> kvm_pgtable_stage2_split
> 
> ```
> 
> Thanks again for the detailed explanation and for sending the patch.
> 

Thank you for the collaboration on this!
Leo

> > >   void kvm_vcpu_load_vhe(struct kvm_vcpu *vcpu)
> > >   {
> > >   	host_data_ptr(host_ctxt)->__hyp_running_vcpu = vcpu;
> > > @@ -220,10 +237,12 @@ void kvm_vcpu_load_vhe(struct kvm_vcpu *vcpu)
> > >   	__vcpu_load_switch_sysregs(vcpu);
> > >   	__vcpu_load_activate_traps(vcpu);
> > >   	__load_stage2(vcpu->arch.hw_mmu, vcpu->arch.hw_mmu->arch);
> > > +	__load_hdbss(vcpu);
> > >   }
> > > 
> > >   void kvm_vcpu_put_vhe(struct kvm_vcpu *vcpu)
> > >   {
> > > +	kvm_flush_hdbss_buffer(vcpu);
> > >   	__vcpu_put_deactivate_traps(vcpu);
> > >   	__vcpu_put_switch_sysregs(vcpu);
> > > 
> > > diff --git a/arch/arm64/kvm/mmu.c b/arch/arm64/kvm/mmu.c
> > > index 070a01e53fcb..42b0710a16ce 100644
> > > --- a/arch/arm64/kvm/mmu.c
> > > +++ b/arch/arm64/kvm/mmu.c
> > > @@ -1896,6 +1896,9 @@ static int user_mem_abort(struct kvm_vcpu *vcpu, phys_addr_t fault_ipa,
> > >   	if (writable)
> > >   		prot |= KVM_PGTABLE_PROT_W;
> > > 
> > > +	if (writable && kvm->arch.enable_hdbss && logging_active)
> > > +		prot |= KVM_PGTABLE_PROT_DBM;
> > > +
> > >   	if (exec_fault)
> > >   		prot |= KVM_PGTABLE_PROT_X;
> > > 
> > > @@ -2033,6 +2036,70 @@ int kvm_handle_guest_sea(struct kvm_vcpu *vcpu)
> > >   	return 0;
> > >   }
> > > 
> > > +void kvm_flush_hdbss_buffer(struct kvm_vcpu *vcpu)
> > > +{
> > > +	int idx, curr_idx;
> > > +	u64 br_el2;
> > > +	u64 *hdbss_buf;
> > > +	struct kvm *kvm = vcpu->kvm;
> > > +
> > > +	if (!kvm->arch.enable_hdbss)
> > > +		return;
> > > +
> > > +	curr_idx = HDBSSPROD_IDX(read_sysreg_s(SYS_HDBSSPROD_EL2));
> > > +	br_el2 = HDBSSBR_EL2(vcpu->arch.hdbss.base_phys, vcpu->arch.hdbss.size);
> > > +
> > > +	/* Do nothing if HDBSS buffer is empty or br_el2 is NULL */
> > > +	if (curr_idx == 0 || br_el2 == 0)
> > > +		return;
> > > +
> > > +	hdbss_buf = page_address(phys_to_page(vcpu->arch.hdbss.base_phys));
> > > +	if (!hdbss_buf)
> > > +		return;
> > > +
> > > +	guard(write_lock_irqsave)(&vcpu->kvm->mmu_lock);
> > > +	for (idx = 0; idx < curr_idx; idx++) {
> > > +		u64 gpa;
> > > +
> > > +		gpa = hdbss_buf[idx];
> > > +		if (!(gpa & HDBSS_ENTRY_VALID))
> > > +			continue;
> > > +
> > > +		gpa &= HDBSS_ENTRY_IPA;
> > > +		kvm_vcpu_mark_page_dirty(vcpu, gpa >> PAGE_SHIFT);
> > > +	}
> > Here ^
> 
> Thanks!
> 
> Tian
> 
> 
> > 
> > > +
> > > +	/* reset HDBSS index */
> > > +	write_sysreg_s(0, SYS_HDBSSPROD_EL2);
> > > +	vcpu->arch.hdbss.next_index = 0;
> > > +	isb();
> > > +}
> > > +
> > > +static int kvm_handle_hdbss_fault(struct kvm_vcpu *vcpu)
> > > +{
> > > +	u64 prod;
> > > +	u64 fsc;
> > > +
> > > +	prod = read_sysreg_s(SYS_HDBSSPROD_EL2);
> > > +	fsc = FIELD_GET(HDBSSPROD_EL2_FSC_MASK, prod);
> > > +
> > > +	switch (fsc) {
> > > +	case HDBSSPROD_EL2_FSC_OK:
> > > +		/* Buffer full, which is reported as permission fault. */
> > > +		kvm_flush_hdbss_buffer(vcpu);
> > > +		return 1;
> > > +	case HDBSSPROD_EL2_FSC_ExternalAbort:
> > > +	case HDBSSPROD_EL2_FSC_GPF:
> > > +		return -EFAULT;
> > > +	default:
> > > +		/* Unknown fault. */
> > > +		WARN_ONCE(1,
> > > +				"Unexpected HDBSS fault type, FSC: 0x%llx (prod=0x%llx, vcpu=%d)\n",
> > > +				fsc, prod, vcpu->vcpu_id);
> > > +		return -EFAULT;
> > > +	}
> > > +}
> > > +
> > >   /**
> > >    * kvm_handle_guest_abort - handles all 2nd stage aborts
> > >    * @vcpu:	the VCPU pointer
> > > @@ -2071,6 +2138,9 @@ int kvm_handle_guest_abort(struct kvm_vcpu *vcpu)
> > > 
> > >   	is_iabt = kvm_vcpu_trap_is_iabt(vcpu);
> > > 
> > > +	if (esr_iss2_is_hdbssf(esr))
> > > +		return kvm_handle_hdbss_fault(vcpu);
> > > +
> > >   	if (esr_fsc_is_translation_fault(esr)) {
> > >   		/* Beyond sanitised PARange (which is the IPA limit) */
> > >   		if (fault_ipa >= BIT_ULL(get_kvm_ipa_limit())) {
> > > diff --git a/arch/arm64/kvm/reset.c b/arch/arm64/kvm/reset.c
> > > index 959532422d3a..c03a4b310b53 100644
> > > --- a/arch/arm64/kvm/reset.c
> > > +++ b/arch/arm64/kvm/reset.c
> > > @@ -161,6 +161,9 @@ void kvm_arm_vcpu_destroy(struct kvm_vcpu *vcpu)
> > >   	free_page((unsigned long)vcpu->arch.ctxt.vncr_array);
> > >   	kfree(vcpu->arch.vncr_tlb);
> > >   	kfree(vcpu->arch.ccsidr);
> > > +
> > > +	if (vcpu->kvm->arch.enable_hdbss)
> > > +		kvm_arm_vcpu_free_hdbss(vcpu);
> > >   }
> > > 
> > >   static void kvm_vcpu_reset_sve(struct kvm_vcpu *vcpu)
> > > --
> > > 2.33.0
> > > 


^ permalink raw reply

* [PATCH v3] mailbox: remove superfluous internal header
From: Wolfram Sang @ 2026-03-27 15:10 UTC (permalink / raw)
  To: linux-renesas-soc
  Cc: Wolfram Sang, Sudeep Holla, Daniel Baluta, Peter Chen,
	Fugang Duan, CIX Linux Kernel Upstream Group, Jassi Brar,
	Frank Li, Sascha Hauer, Pengutronix Kernel Team, Fabio Estevam,
	Thierry Reding, Jonathan Hunter, linux-kernel, linux-arm-kernel,
	imx, linux-acpi, linux-tegra

Quite some controller drivers use the defines from the internal header
already. This prevents controller drivers outside the mailbox directory.
Move the defines to the public controller header to allow this again as
the defines are not strictly internal anyhow.

Signed-off-by: Wolfram Sang <wsa+renesas@sang-engineering.com>
Reviewed-by: Sudeep Holla <sudeep.holla@kernel.org>
Reviewed-by: Daniel Baluta <daniel.baluta@nxp.com>
---

Changes since v2:
* rebased to 7.0-rc5
* add tag (Thanks, Daniel!)

 drivers/mailbox/cix-mailbox.c      |  2 --
 drivers/mailbox/hi3660-mailbox.c   |  2 --
 drivers/mailbox/imx-mailbox.c      |  2 --
 drivers/mailbox/mailbox-sti.c      |  2 --
 drivers/mailbox/mailbox.c          |  2 --
 drivers/mailbox/mailbox.h          | 12 ------------
 drivers/mailbox/omap-mailbox.c     |  2 --
 drivers/mailbox/pcc.c              |  2 --
 drivers/mailbox/tegra-hsp.c        |  2 --
 include/linux/mailbox_controller.h |  5 +++++
 10 files changed, 5 insertions(+), 28 deletions(-)
 delete mode 100644 drivers/mailbox/mailbox.h

diff --git a/drivers/mailbox/cix-mailbox.c b/drivers/mailbox/cix-mailbox.c
index 443620e8ae37..864f98f21fc3 100644
--- a/drivers/mailbox/cix-mailbox.c
+++ b/drivers/mailbox/cix-mailbox.c
@@ -12,8 +12,6 @@
 #include <linux/module.h>
 #include <linux/platform_device.h>
 
-#include "mailbox.h"
-
 /*
  * The maximum transmission size is 32 words or 128 bytes.
  */
diff --git a/drivers/mailbox/hi3660-mailbox.c b/drivers/mailbox/hi3660-mailbox.c
index 17c29e960fbf..9b727a2b54a5 100644
--- a/drivers/mailbox/hi3660-mailbox.c
+++ b/drivers/mailbox/hi3660-mailbox.c
@@ -15,8 +15,6 @@
 #include <linux/platform_device.h>
 #include <linux/slab.h>
 
-#include "mailbox.h"
-
 #define MBOX_CHAN_MAX			32
 
 #define MBOX_RX				0x0
diff --git a/drivers/mailbox/imx-mailbox.c b/drivers/mailbox/imx-mailbox.c
index 003f9236c35e..22331b579489 100644
--- a/drivers/mailbox/imx-mailbox.c
+++ b/drivers/mailbox/imx-mailbox.c
@@ -23,8 +23,6 @@
 #include <linux/slab.h>
 #include <linux/workqueue.h>
 
-#include "mailbox.h"
-
 #define IMX_MU_CHANS		24
 /* TX0/RX0/RXDB[0-3] */
 #define IMX_MU_SCU_CHANS	6
diff --git a/drivers/mailbox/mailbox-sti.c b/drivers/mailbox/mailbox-sti.c
index b4b5bdd503cf..b6c9ecbbc8ec 100644
--- a/drivers/mailbox/mailbox-sti.c
+++ b/drivers/mailbox/mailbox-sti.c
@@ -21,8 +21,6 @@
 #include <linux/property.h>
 #include <linux/slab.h>
 
-#include "mailbox.h"
-
 #define STI_MBOX_INST_MAX	4      /* RAM saving: Max supported instances */
 #define STI_MBOX_CHAN_MAX	20     /* RAM saving: Max supported channels  */
 
diff --git a/drivers/mailbox/mailbox.c b/drivers/mailbox/mailbox.c
index e63b2292ee7a..9d41a1ab9018 100644
--- a/drivers/mailbox/mailbox.c
+++ b/drivers/mailbox/mailbox.c
@@ -18,8 +18,6 @@
 #include <linux/property.h>
 #include <linux/spinlock.h>
 
-#include "mailbox.h"
-
 static LIST_HEAD(mbox_cons);
 static DEFINE_MUTEX(con_mutex);
 
diff --git a/drivers/mailbox/mailbox.h b/drivers/mailbox/mailbox.h
deleted file mode 100644
index e1ec4efab693..000000000000
--- a/drivers/mailbox/mailbox.h
+++ /dev/null
@@ -1,12 +0,0 @@
-/* SPDX-License-Identifier: GPL-2.0-only */
-
-#ifndef __MAILBOX_H
-#define __MAILBOX_H
-
-#include <linux/bits.h>
-
-#define TXDONE_BY_IRQ	BIT(0) /* controller has remote RTR irq */
-#define TXDONE_BY_POLL	BIT(1) /* controller can read status of last TX */
-#define TXDONE_BY_ACK	BIT(2) /* S/W ACK received by Client ticks the TX */
-
-#endif /* __MAILBOX_H */
diff --git a/drivers/mailbox/omap-mailbox.c b/drivers/mailbox/omap-mailbox.c
index d9f100c18895..5772c6b9886a 100644
--- a/drivers/mailbox/omap-mailbox.c
+++ b/drivers/mailbox/omap-mailbox.c
@@ -22,8 +22,6 @@
 #include <linux/pm_runtime.h>
 #include <linux/mailbox_controller.h>
 
-#include "mailbox.h"
-
 #define MAILBOX_REVISION		0x000
 #define MAILBOX_MESSAGE(m)		(0x040 + 4 * (m))
 #define MAILBOX_FIFOSTATUS(m)		(0x080 + 4 * (m))
diff --git a/drivers/mailbox/pcc.c b/drivers/mailbox/pcc.c
index 22e70af1ae5d..636879ae1db7 100644
--- a/drivers/mailbox/pcc.c
+++ b/drivers/mailbox/pcc.c
@@ -59,8 +59,6 @@
 #include <linux/io-64-nonatomic-lo-hi.h>
 #include <acpi/pcc.h>
 
-#include "mailbox.h"
-
 #define MBOX_IRQ_NAME		"pcc-mbox"
 
 /**
diff --git a/drivers/mailbox/tegra-hsp.c b/drivers/mailbox/tegra-hsp.c
index ed9a0bb2bcd8..2231050bb5a9 100644
--- a/drivers/mailbox/tegra-hsp.c
+++ b/drivers/mailbox/tegra-hsp.c
@@ -16,8 +16,6 @@
 
 #include <dt-bindings/mailbox/tegra186-hsp.h>
 
-#include "mailbox.h"
-
 #define HSP_INT_IE(x)		(0x100 + ((x) * 4))
 #define HSP_INT_IV		0x300
 #define HSP_INT_IR		0x304
diff --git a/include/linux/mailbox_controller.h b/include/linux/mailbox_controller.h
index 80a427c7ca29..16fef421c30c 100644
--- a/include/linux/mailbox_controller.h
+++ b/include/linux/mailbox_controller.h
@@ -3,6 +3,7 @@
 #ifndef __MAILBOX_CONTROLLER_H
 #define __MAILBOX_CONTROLLER_H
 
+#include <linux/bits.h>
 #include <linux/completion.h>
 #include <linux/device.h>
 #include <linux/hrtimer.h>
@@ -11,6 +12,10 @@
 
 struct mbox_chan;
 
+#define TXDONE_BY_IRQ	BIT(0) /* controller has remote RTR irq */
+#define TXDONE_BY_POLL	BIT(1) /* controller can read status of last TX */
+#define TXDONE_BY_ACK	BIT(2) /* S/W ACK received by Client ticks the TX */
+
 /**
  * struct mbox_chan_ops - methods to control mailbox channels
  * @send_data:	The API asks the MBOX controller driver, in atomic
-- 
2.51.0



^ permalink raw reply related

* [PATCH v2] mailbox: exynos: drop superfluous mbox setting per channel
From: Wolfram Sang @ 2026-03-27 15:12 UTC (permalink / raw)
  To: linux-renesas-soc
  Cc: Wolfram Sang, Tudor Ambarus, Jassi Brar, Krzysztof Kozlowski,
	Alim Akhtar, linux-kernel, linux-samsung-soc, linux-arm-kernel

The core initializes the 'mbox' field exactly like this, so don't
duplicate it in the driver.

Signed-off-by: Wolfram Sang <wsa+renesas@sang-engineering.com>
Reviewed-by: Tudor Ambarus <tudor.ambarus@linaro.org>
Tested-by: Tudor Ambarus <tudor.ambarus@linaro.org>
---
Changes since v1:
* rebased to 7.0-rc5
* add tags (Thanks, Tudor!) and dropped RFT

 drivers/mailbox/exynos-mailbox.c | 4 ----
 1 file changed, 4 deletions(-)

diff --git a/drivers/mailbox/exynos-mailbox.c b/drivers/mailbox/exynos-mailbox.c
index 5f2d3b81c1db..d2355b128ba4 100644
--- a/drivers/mailbox/exynos-mailbox.c
+++ b/drivers/mailbox/exynos-mailbox.c
@@ -99,7 +99,6 @@ static int exynos_mbox_probe(struct platform_device *pdev)
 	struct mbox_controller *mbox;
 	struct mbox_chan *chans;
 	struct clk *pclk;
-	int i;
 
 	exynos_mbox = devm_kzalloc(dev, sizeof(*exynos_mbox), GFP_KERNEL);
 	if (!exynos_mbox)
@@ -129,9 +128,6 @@ static int exynos_mbox_probe(struct platform_device *pdev)
 	mbox->ops = &exynos_mbox_chan_ops;
 	mbox->of_xlate = exynos_mbox_of_xlate;
 
-	for (i = 0; i < EXYNOS_MBOX_CHAN_COUNT; i++)
-		chans[i].mbox = mbox;
-
 	exynos_mbox->mbox = mbox;
 
 	platform_set_drvdata(pdev, exynos_mbox);
-- 
2.51.0



^ permalink raw reply related

* [PATCH 0/4] media: rkvdec: Switch to using a bitwriter
From: Detlev Casanova @ 2026-03-27 15:15 UTC (permalink / raw)
  To: Ezequiel Garcia, Mauro Carvalho Chehab, Heiko Stuebner,
	Nathan Chancellor, Nick Desaulniers, Bill Wendling, Justin Stitt,
	Jonas Karlman, Nicolas Dufresne
  Cc: linux-kernel, linux-media, linux-rockchip, linux-arm-kernel, llvm,
	kernel, Detlev Casanova

Using bitfields in large structures where fields are mostly unaligned can
be hard on the compiler.

Issues have been reported with clang ([1], [2]) and, even though those
issues are addressed by clang devs, some setup can't or won't update clang
just to compile a driver.

Even when fixed, the compiler still might have to allocate a bigger stack
frame to manage misalignement. Coupled with other features like KASAN, the
stack becomes larger than the kernel's maximum [3].

To avoid this, let's drop the bitfield implementation and switch to a
bitwriter. There is already one for the older variants, so make it global
and use it in other variants.

Note that only buffer structures are switched to the bitwriter. The
registers representation structures are kept with bitfields, as they are
properly aligned every 32 bits and don't require heavy stack overhead.

Also note that the VDPU381 SPS and PPS structs are kept with bitfields,
for the same reason that they are small and aligned enough not to require
heavy stack overhead.

[1]: https://lore.kernel.org/oe-kbuild-all/202601211924.rqKS2Ihm-lkp@intel.com/
[2]: https://github.com/llvm/llvm-project/issues/178535
[3]: https://yhbt.net/lore/llvm/20260121230406.GA2625738@ax162/T/#mad878ec24a8224e1387ef5e73cb77b9ada55e3f2

Signed-off-by: Detlev Casanova <detlev.casanova@collabora.com>
---
Detlev Casanova (4):
      media: rkvdec: Introduce a global bitwriter helper
      media: rkvdec: Use the global bitwriter instead of local one
      media: rkvdec: common: Drop bitfields for the bitwriter
      media: rkvdec: vdpu383: Drop bitfields for the bitwriter

 drivers/media/platform/rockchip/rkvdec/Makefile    |   1 +
 .../platform/rockchip/rkvdec/rkvdec-bitwriter.c    |  30 ++
 .../platform/rockchip/rkvdec/rkvdec-bitwriter.h    |  25 +
 .../platform/rockchip/rkvdec/rkvdec-h264-common.c  |  51 +--
 .../platform/rockchip/rkvdec/rkvdec-h264-common.h  |  40 +-
 .../media/platform/rockchip/rkvdec/rkvdec-h264.c   | 109 ++---
 .../platform/rockchip/rkvdec/rkvdec-hevc-common.c  |  92 +---
 .../platform/rockchip/rkvdec/rkvdec-hevc-common.h  |  57 +--
 .../media/platform/rockchip/rkvdec/rkvdec-hevc.c   | 171 +++----
 .../platform/rockchip/rkvdec/rkvdec-vdpu383-h264.c | 351 ++++++--------
 .../platform/rockchip/rkvdec/rkvdec-vdpu383-hevc.c | 502 +++++++++------------
 11 files changed, 578 insertions(+), 851 deletions(-)
---
base-commit: bbeb83d3182abe0d245318e274e8531e5dd7a948
change-id: 20260327-rkvdec-use-bitwriter-f1d149b3cf7c

Best regards,
--  
Detlev Casanova <detlev.casanova@collabora.com>



^ permalink raw reply

* [PATCH 1/4] media: rkvdec: Introduce a global bitwriter helper
From: Detlev Casanova @ 2026-03-27 15:16 UTC (permalink / raw)
  To: Ezequiel Garcia, Mauro Carvalho Chehab, Heiko Stuebner,
	Nathan Chancellor, Nick Desaulniers, Bill Wendling, Justin Stitt,
	Jonas Karlman, Nicolas Dufresne
  Cc: linux-kernel, linux-media, linux-rockchip, linux-arm-kernel, llvm,
	kernel, Detlev Casanova
In-Reply-To: <20260327-rkvdec-use-bitwriter-v1-0-982cf872b590@collabora.com>

The use of structures with bitfields is good when the values are
somewhat aligned.
More mis-alignement means that compilers need to do more gymanstics
to edit the fields values.

Some cases have been reported with CLang on specific architectures
like armhf and hexagon, where the compiler would allocate a bigger
local stack than needed or even completely freeze during compilation.

Some fixes have been provided to ease the issues, but the real fix
here is to use a bitwriter instead of heavily unaligned bitfields.

This is a preparation commit to provide a global bitwriter interface
for the whole driver.

Signed-off-by: Detlev Casanova <detlev.casanova@collabora.com>
---
 drivers/media/platform/rockchip/rkvdec/Makefile    |  1 +
 .../platform/rockchip/rkvdec/rkvdec-bitwriter.c    | 30 ++++++++++++++++++++++
 .../platform/rockchip/rkvdec/rkvdec-bitwriter.h    | 25 ++++++++++++++++++
 3 files changed, 56 insertions(+)

diff --git a/drivers/media/platform/rockchip/rkvdec/Makefile b/drivers/media/platform/rockchip/rkvdec/Makefile
index e629d571e4d8..11e2122bcbbf 100644
--- a/drivers/media/platform/rockchip/rkvdec/Makefile
+++ b/drivers/media/platform/rockchip/rkvdec/Makefile
@@ -2,6 +2,7 @@ obj-$(CONFIG_VIDEO_ROCKCHIP_VDEC) += rockchip-vdec.o
 
 rockchip-vdec-y += \
 		   rkvdec.o \
+		   rkvdec-bitwriter.o \
 		   rkvdec-cabac.o \
 		   rkvdec-h264.o \
 		   rkvdec-h264-common.o \
diff --git a/drivers/media/platform/rockchip/rkvdec/rkvdec-bitwriter.c b/drivers/media/platform/rockchip/rkvdec/rkvdec-bitwriter.c
new file mode 100644
index 000000000000..673ebb89002b
--- /dev/null
+++ b/drivers/media/platform/rockchip/rkvdec/rkvdec-bitwriter.c
@@ -0,0 +1,30 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * Rockchip Video Decoder bit writer
+ *
+ * Copyright (C) 2026 Collabora, Ltd.
+ *      Detlev Casanova <detlev.casanova@collabora.com>
+ * Copyright (C) 2019 Collabora, Ltd.
+ *	Boris Brezillon <boris.brezillon@collabora.com>
+ */
+
+#include <linux/types.h>
+#include <linux/bits.h>
+
+#include "rkvdec-bitwriter.h"
+
+void rkvdec_set_bw_field(u32 *buf, struct rkvdec_bw_field field, u32 value)
+{
+	u8 bit = field.offset % 32;
+	u16 word = field.offset / 32;
+	u64 mask = GENMASK_ULL(bit + field.len - 1, bit);
+	u64 val = ((u64)value << bit) & mask;
+
+	buf[word] &= ~mask;
+	buf[word] |= val;
+	if (bit + field.len > 32) {
+		buf[word + 1] &= ~(mask >> 32);
+		buf[word + 1] |= val >> 32;
+	}
+}
+
diff --git a/drivers/media/platform/rockchip/rkvdec/rkvdec-bitwriter.h b/drivers/media/platform/rockchip/rkvdec/rkvdec-bitwriter.h
new file mode 100644
index 000000000000..44154f1ebc65
--- /dev/null
+++ b/drivers/media/platform/rockchip/rkvdec/rkvdec-bitwriter.h
@@ -0,0 +1,25 @@
+/* SPDX-License-Identifier: GPL-2.0 */
+/*
+ * Rockchip Video Decoder bit writer
+ *
+ * Copyright (C) 2026 Collabora, Ltd.
+ *      Detlev Casanova <detlev.casanova@collabora.com>
+ * Copyright (C) 2019 Collabora, Ltd.
+ *	Boris Brezillon <boris.brezillon@collabora.com>
+ */
+
+#ifndef RKVDEC_BIT_WRITER_H_
+#define RKVDEC_BIT_WRITER_H_
+
+#include <linux/types.h>
+
+struct rkvdec_bw_field {
+	u16 offset;
+	u8 len;
+};
+
+#define BW_FIELD(_offset, _len) ((struct rkvdec_bw_field){ _offset, _len })
+
+void rkvdec_set_bw_field(u32 *buf, struct rkvdec_bw_field field, u32 value);
+
+#endif /* RKVDEC_BIT_WRITER_H_ */

-- 
2.53.0



^ permalink raw reply related

* [PATCH 2/4] media: rkvdec: Use the global bitwriter instead of local one
From: Detlev Casanova @ 2026-03-27 15:16 UTC (permalink / raw)
  To: Ezequiel Garcia, Mauro Carvalho Chehab, Heiko Stuebner,
	Nathan Chancellor, Nick Desaulniers, Bill Wendling, Justin Stitt,
	Jonas Karlman, Nicolas Dufresne
  Cc: linux-kernel, linux-media, linux-rockchip, linux-arm-kernel, llvm,
	kernel, Detlev Casanova
In-Reply-To: <20260327-rkvdec-use-bitwriter-v1-0-982cf872b590@collabora.com>

Both rkvdec-h264.c and rkvdec-hevc.c use their own bitwriter
function and macros.

Move to using the global one introduced before.

Signed-off-by: Detlev Casanova <detlev.casanova@collabora.com>
---
 .../media/platform/rockchip/rkvdec/rkvdec-h264.c   | 109 ++++++-------
 .../media/platform/rockchip/rkvdec/rkvdec-hevc.c   | 171 +++++++++------------
 2 files changed, 119 insertions(+), 161 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkvdec/rkvdec-h264.c b/drivers/media/platform/rockchip/rkvdec/rkvdec-h264.c
index d3202cecb988..ffa606038192 100644
--- a/drivers/media/platform/rockchip/rkvdec/rkvdec-h264.c
+++ b/drivers/media/platform/rockchip/rkvdec/rkvdec-h264.c
@@ -16,6 +16,7 @@
 #include "rkvdec-regs.h"
 #include "rkvdec-cabac.h"
 #include "rkvdec-h264-common.h"
+#include "rkvdec-bitwriter.h"
 
 /* Size with u32 units. */
 #define RKV_CABAC_INIT_BUFFER_SIZE	(3680 + 128)
@@ -25,56 +26,48 @@ struct rkvdec_sps_pps_packet {
 	u32 info[8];
 };
 
-struct rkvdec_ps_field {
-	u16 offset;
-	u8 len;
-};
-
-#define PS_FIELD(_offset, _len) \
-	((struct rkvdec_ps_field){ _offset, _len })
-
-#define SEQ_PARAMETER_SET_ID				PS_FIELD(0, 4)
-#define PROFILE_IDC					PS_FIELD(4, 8)
-#define CONSTRAINT_SET3_FLAG				PS_FIELD(12, 1)
-#define CHROMA_FORMAT_IDC				PS_FIELD(13, 2)
-#define BIT_DEPTH_LUMA					PS_FIELD(15, 3)
-#define BIT_DEPTH_CHROMA				PS_FIELD(18, 3)
-#define QPPRIME_Y_ZERO_TRANSFORM_BYPASS_FLAG		PS_FIELD(21, 1)
-#define LOG2_MAX_FRAME_NUM_MINUS4			PS_FIELD(22, 4)
-#define MAX_NUM_REF_FRAMES				PS_FIELD(26, 5)
-#define PIC_ORDER_CNT_TYPE				PS_FIELD(31, 2)
-#define LOG2_MAX_PIC_ORDER_CNT_LSB_MINUS4		PS_FIELD(33, 4)
-#define DELTA_PIC_ORDER_ALWAYS_ZERO_FLAG		PS_FIELD(37, 1)
-#define PIC_WIDTH_IN_MBS				PS_FIELD(38, 9)
-#define PIC_HEIGHT_IN_MBS				PS_FIELD(47, 9)
-#define FRAME_MBS_ONLY_FLAG				PS_FIELD(56, 1)
-#define MB_ADAPTIVE_FRAME_FIELD_FLAG			PS_FIELD(57, 1)
-#define DIRECT_8X8_INFERENCE_FLAG			PS_FIELD(58, 1)
-#define MVC_EXTENSION_ENABLE				PS_FIELD(59, 1)
-#define NUM_VIEWS					PS_FIELD(60, 2)
-#define VIEW_ID(i)					PS_FIELD(62 + ((i) * 10), 10)
-#define NUM_ANCHOR_REFS_L(i)				PS_FIELD(82 + ((i) * 11), 1)
-#define ANCHOR_REF_L(i)				PS_FIELD(83 + ((i) * 11), 10)
-#define NUM_NON_ANCHOR_REFS_L(i)			PS_FIELD(104 + ((i) * 11), 1)
-#define NON_ANCHOR_REFS_L(i)				PS_FIELD(105 + ((i) * 11), 10)
-#define PIC_PARAMETER_SET_ID				PS_FIELD(128, 8)
-#define PPS_SEQ_PARAMETER_SET_ID			PS_FIELD(136, 5)
-#define ENTROPY_CODING_MODE_FLAG			PS_FIELD(141, 1)
-#define BOTTOM_FIELD_PIC_ORDER_IN_FRAME_PRESENT_FLAG	PS_FIELD(142, 1)
-#define NUM_REF_IDX_L_DEFAULT_ACTIVE_MINUS1(i)		PS_FIELD(143 + ((i) * 5), 5)
-#define WEIGHTED_PRED_FLAG				PS_FIELD(153, 1)
-#define WEIGHTED_BIPRED_IDC				PS_FIELD(154, 2)
-#define PIC_INIT_QP_MINUS26				PS_FIELD(156, 7)
-#define PIC_INIT_QS_MINUS26				PS_FIELD(163, 6)
-#define CHROMA_QP_INDEX_OFFSET				PS_FIELD(169, 5)
-#define DEBLOCKING_FILTER_CONTROL_PRESENT_FLAG		PS_FIELD(174, 1)
-#define CONSTRAINED_INTRA_PRED_FLAG			PS_FIELD(175, 1)
-#define REDUNDANT_PIC_CNT_PRESENT			PS_FIELD(176, 1)
-#define TRANSFORM_8X8_MODE_FLAG			PS_FIELD(177, 1)
-#define SECOND_CHROMA_QP_INDEX_OFFSET			PS_FIELD(178, 5)
-#define SCALING_LIST_ENABLE_FLAG			PS_FIELD(183, 1)
-#define SCALING_LIST_ADDRESS				PS_FIELD(184, 32)
-#define IS_LONG_TERM(i)				PS_FIELD(216 + (i), 1)
+#define SEQ_PARAMETER_SET_ID				BW_FIELD(0, 4)
+#define PROFILE_IDC					BW_FIELD(4, 8)
+#define CONSTRAINT_SET3_FLAG				BW_FIELD(12, 1)
+#define CHROMA_FORMAT_IDC				BW_FIELD(13, 2)
+#define BIT_DEPTH_LUMA					BW_FIELD(15, 3)
+#define BIT_DEPTH_CHROMA				BW_FIELD(18, 3)
+#define QPPRIME_Y_ZERO_TRANSFORM_BYPASS_FLAG		BW_FIELD(21, 1)
+#define LOG2_MAX_FRAME_NUM_MINUS4			BW_FIELD(22, 4)
+#define MAX_NUM_REF_FRAMES				BW_FIELD(26, 5)
+#define PIC_ORDER_CNT_TYPE				BW_FIELD(31, 2)
+#define LOG2_MAX_PIC_ORDER_CNT_LSB_MINUS4		BW_FIELD(33, 4)
+#define DELTA_PIC_ORDER_ALWAYS_ZERO_FLAG		BW_FIELD(37, 1)
+#define PIC_WIDTH_IN_MBS				BW_FIELD(38, 9)
+#define PIC_HEIGHT_IN_MBS				BW_FIELD(47, 9)
+#define FRAME_MBS_ONLY_FLAG				BW_FIELD(56, 1)
+#define MB_ADAPTIVE_FRAME_FIELD_FLAG			BW_FIELD(57, 1)
+#define DIRECT_8X8_INFERENCE_FLAG			BW_FIELD(58, 1)
+#define MVC_EXTENSION_ENABLE				BW_FIELD(59, 1)
+#define NUM_VIEWS					BW_FIELD(60, 2)
+#define VIEW_ID(i)					BW_FIELD(62 + ((i) * 10), 10)
+#define NUM_ANCHOR_REFS_L(i)				BW_FIELD(82 + ((i) * 11), 1)
+#define ANCHOR_REF_L(i)				BW_FIELD(83 + ((i) * 11), 10)
+#define NUM_NON_ANCHOR_REFS_L(i)			BW_FIELD(104 + ((i) * 11), 1)
+#define NON_ANCHOR_REFS_L(i)				BW_FIELD(105 + ((i) * 11), 10)
+#define PIC_PARAMETER_SET_ID				BW_FIELD(128, 8)
+#define PPS_SEQ_PARAMETER_SET_ID			BW_FIELD(136, 5)
+#define ENTROPY_CODING_MODE_FLAG			BW_FIELD(141, 1)
+#define BOTTOM_FIELD_PIC_ORDER_IN_FRAME_PRESENT_FLAG	BW_FIELD(142, 1)
+#define NUM_REF_IDX_L_DEFAULT_ACTIVE_MINUS1(i)		BW_FIELD(143 + ((i) * 5), 5)
+#define WEIGHTED_PRED_FLAG				BW_FIELD(153, 1)
+#define WEIGHTED_BIPRED_IDC				BW_FIELD(154, 2)
+#define PIC_INIT_QP_MINUS26				BW_FIELD(156, 7)
+#define PIC_INIT_QS_MINUS26				BW_FIELD(163, 6)
+#define CHROMA_QP_INDEX_OFFSET				BW_FIELD(169, 5)
+#define DEBLOCKING_FILTER_CONTROL_PRESENT_FLAG		BW_FIELD(174, 1)
+#define CONSTRAINED_INTRA_PRED_FLAG			BW_FIELD(175, 1)
+#define REDUNDANT_PIC_CNT_PRESENT			BW_FIELD(176, 1)
+#define TRANSFORM_8X8_MODE_FLAG			BW_FIELD(177, 1)
+#define SECOND_CHROMA_QP_INDEX_OFFSET			BW_FIELD(178, 5)
+#define SCALING_LIST_ENABLE_FLAG			BW_FIELD(183, 1)
+#define SCALING_LIST_ADDRESS				BW_FIELD(184, 32)
+#define IS_LONG_TERM(i)				BW_FIELD(216 + (i), 1)
 
 /* Data structure describing auxiliary buffer format. */
 struct rkvdec_h264_priv_tbl {
@@ -91,20 +84,6 @@ struct rkvdec_h264_ctx {
 	struct rkvdec_regs regs;
 };
 
-static void set_ps_field(u32 *buf, struct rkvdec_ps_field field, u32 value)
-{
-	u8 bit = field.offset % 32, word = field.offset / 32;
-	u64 mask = GENMASK_ULL(bit + field.len - 1, bit);
-	u64 val = ((u64)value << bit) & mask;
-
-	buf[word] &= ~mask;
-	buf[word] |= val;
-	if (bit + field.len > 32) {
-		buf[word + 1] &= ~(mask >> 32);
-		buf[word + 1] |= val >> 32;
-	}
-}
-
 static void assemble_hw_pps(struct rkvdec_ctx *ctx,
 			    struct rkvdec_h264_run *run)
 {
@@ -128,7 +107,7 @@ static void assemble_hw_pps(struct rkvdec_ctx *ctx,
 	hw_ps = &priv_tbl->param_set[pps->pic_parameter_set_id];
 	memset(hw_ps, 0, sizeof(*hw_ps));
 
-#define WRITE_PPS(value, field) set_ps_field(hw_ps->info, field, value)
+#define WRITE_PPS(value, field) rkvdec_set_bw_field(hw_ps->info, field, value)
 	/* write sps */
 	WRITE_PPS(sps->seq_parameter_set_id, SEQ_PARAMETER_SET_ID);
 	WRITE_PPS(sps->profile_idc, PROFILE_IDC);
diff --git a/drivers/media/platform/rockchip/rkvdec/rkvdec-hevc.c b/drivers/media/platform/rockchip/rkvdec/rkvdec-hevc.c
index ac8b825d080a..6d367bfcdd13 100644
--- a/drivers/media/platform/rockchip/rkvdec/rkvdec-hevc.c
+++ b/drivers/media/platform/rockchip/rkvdec/rkvdec-hevc.c
@@ -18,6 +18,7 @@
 #include "rkvdec-regs.h"
 #include "rkvdec-cabac.h"
 #include "rkvdec-hevc-common.h"
+#include "rkvdec-bitwriter.h"
 
 /* Size in u8/u32 units. */
 #define RKV_SCALING_LIST_SIZE		1360
@@ -34,80 +35,72 @@ struct rkvdec_rps_packet {
 	u32 info[RKV_RPS_SIZE];
 };
 
-struct rkvdec_ps_field {
-	u16 offset;
-	u8 len;
-};
-
-#define PS_FIELD(_offset, _len) \
-	((struct rkvdec_ps_field){ _offset, _len })
-
 /* SPS */
-#define VIDEO_PARAMETER_SET_ID				PS_FIELD(0, 4)
-#define SEQ_PARAMETER_SET_ID				PS_FIELD(4, 4)
-#define CHROMA_FORMAT_IDC				PS_FIELD(8, 2)
-#define PIC_WIDTH_IN_LUMA_SAMPLES			PS_FIELD(10, 13)
-#define PIC_HEIGHT_IN_LUMA_SAMPLES			PS_FIELD(23, 13)
-#define BIT_DEPTH_LUMA					PS_FIELD(36, 4)
-#define BIT_DEPTH_CHROMA				PS_FIELD(40, 4)
-#define LOG2_MAX_PIC_ORDER_CNT_LSB			PS_FIELD(44, 5)
-#define LOG2_DIFF_MAX_MIN_LUMA_CODING_BLOCK_SIZE	PS_FIELD(49, 2)
-#define LOG2_MIN_LUMA_CODING_BLOCK_SIZE			PS_FIELD(51, 3)
-#define LOG2_MIN_TRANSFORM_BLOCK_SIZE			PS_FIELD(54, 3)
-#define LOG2_DIFF_MAX_MIN_LUMA_TRANSFORM_BLOCK_SIZE	PS_FIELD(57, 2)
-#define MAX_TRANSFORM_HIERARCHY_DEPTH_INTER		PS_FIELD(59, 3)
-#define MAX_TRANSFORM_HIERARCHY_DEPTH_INTRA		PS_FIELD(62, 3)
-#define SCALING_LIST_ENABLED_FLAG			PS_FIELD(65, 1)
-#define AMP_ENABLED_FLAG				PS_FIELD(66, 1)
-#define SAMPLE_ADAPTIVE_OFFSET_ENABLED_FLAG		PS_FIELD(67, 1)
-#define PCM_ENABLED_FLAG				PS_FIELD(68, 1)
-#define PCM_SAMPLE_BIT_DEPTH_LUMA			PS_FIELD(69, 4)
-#define PCM_SAMPLE_BIT_DEPTH_CHROMA			PS_FIELD(73, 4)
-#define PCM_LOOP_FILTER_DISABLED_FLAG			PS_FIELD(77, 1)
-#define LOG2_DIFF_MAX_MIN_PCM_LUMA_CODING_BLOCK_SIZE	PS_FIELD(78, 3)
-#define LOG2_MIN_PCM_LUMA_CODING_BLOCK_SIZE		PS_FIELD(81, 3)
-#define NUM_SHORT_TERM_REF_PIC_SETS			PS_FIELD(84, 7)
-#define LONG_TERM_REF_PICS_PRESENT_FLAG			PS_FIELD(91, 1)
-#define NUM_LONG_TERM_REF_PICS_SPS			PS_FIELD(92, 6)
-#define SPS_TEMPORAL_MVP_ENABLED_FLAG			PS_FIELD(98, 1)
-#define STRONG_INTRA_SMOOTHING_ENABLED_FLAG		PS_FIELD(99, 1)
+#define VIDEO_PARAMETER_SET_ID				BW_FIELD(0, 4)
+#define SEQ_PARAMETER_SET_ID				BW_FIELD(4, 4)
+#define CHROMA_FORMAT_IDC				BW_FIELD(8, 2)
+#define PIC_WIDTH_IN_LUMA_SAMPLES			BW_FIELD(10, 13)
+#define PIC_HEIGHT_IN_LUMA_SAMPLES			BW_FIELD(23, 13)
+#define BIT_DEPTH_LUMA					BW_FIELD(36, 4)
+#define BIT_DEPTH_CHROMA				BW_FIELD(40, 4)
+#define LOG2_MAX_PIC_ORDER_CNT_LSB			BW_FIELD(44, 5)
+#define LOG2_DIFF_MAX_MIN_LUMA_CODING_BLOCK_SIZE	BW_FIELD(49, 2)
+#define LOG2_MIN_LUMA_CODING_BLOCK_SIZE			BW_FIELD(51, 3)
+#define LOG2_MIN_TRANSFORM_BLOCK_SIZE			BW_FIELD(54, 3)
+#define LOG2_DIFF_MAX_MIN_LUMA_TRANSFORM_BLOCK_SIZE	BW_FIELD(57, 2)
+#define MAX_TRANSFORM_HIERARCHY_DEPTH_INTER		BW_FIELD(59, 3)
+#define MAX_TRANSFORM_HIERARCHY_DEPTH_INTRA		BW_FIELD(62, 3)
+#define SCALING_LIST_ENABLED_FLAG			BW_FIELD(65, 1)
+#define AMP_ENABLED_FLAG				BW_FIELD(66, 1)
+#define SAMPLE_ADAPTIVE_OFFSET_ENABLED_FLAG		BW_FIELD(67, 1)
+#define PCM_ENABLED_FLAG				BW_FIELD(68, 1)
+#define PCM_SAMPLE_BIT_DEPTH_LUMA			BW_FIELD(69, 4)
+#define PCM_SAMPLE_BIT_DEPTH_CHROMA			BW_FIELD(73, 4)
+#define PCM_LOOP_FILTER_DISABLED_FLAG			BW_FIELD(77, 1)
+#define LOG2_DIFF_MAX_MIN_PCM_LUMA_CODING_BLOCK_SIZE	BW_FIELD(78, 3)
+#define LOG2_MIN_PCM_LUMA_CODING_BLOCK_SIZE		BW_FIELD(81, 3)
+#define NUM_SHORT_TERM_REF_PIC_SETS			BW_FIELD(84, 7)
+#define LONG_TERM_REF_PICS_PRESENT_FLAG			BW_FIELD(91, 1)
+#define NUM_LONG_TERM_REF_PICS_SPS			BW_FIELD(92, 6)
+#define SPS_TEMPORAL_MVP_ENABLED_FLAG			BW_FIELD(98, 1)
+#define STRONG_INTRA_SMOOTHING_ENABLED_FLAG		BW_FIELD(99, 1)
 /* PPS */
-#define PIC_PARAMETER_SET_ID				PS_FIELD(128, 6)
-#define PPS_SEQ_PARAMETER_SET_ID			PS_FIELD(134, 4)
-#define DEPENDENT_SLICE_SEGMENTS_ENABLED_FLAG		PS_FIELD(138, 1)
-#define OUTPUT_FLAG_PRESENT_FLAG			PS_FIELD(139, 1)
-#define NUM_EXTRA_SLICE_HEADER_BITS			PS_FIELD(140, 13)
-#define SIGN_DATA_HIDING_ENABLED_FLAG			PS_FIELD(153, 1)
-#define CABAC_INIT_PRESENT_FLAG				PS_FIELD(154, 1)
-#define NUM_REF_IDX_L0_DEFAULT_ACTIVE			PS_FIELD(155, 4)
-#define NUM_REF_IDX_L1_DEFAULT_ACTIVE			PS_FIELD(159, 4)
-#define INIT_QP_MINUS26					PS_FIELD(163, 7)
-#define CONSTRAINED_INTRA_PRED_FLAG			PS_FIELD(170, 1)
-#define TRANSFORM_SKIP_ENABLED_FLAG			PS_FIELD(171, 1)
-#define CU_QP_DELTA_ENABLED_FLAG			PS_FIELD(172, 1)
-#define LOG2_MIN_CU_QP_DELTA_SIZE			PS_FIELD(173, 3)
-#define PPS_CB_QP_OFFSET				PS_FIELD(176, 5)
-#define PPS_CR_QP_OFFSET				PS_FIELD(181, 5)
-#define PPS_SLICE_CHROMA_QP_OFFSETS_PRESENT_FLAG	PS_FIELD(186, 1)
-#define WEIGHTED_PRED_FLAG				PS_FIELD(187, 1)
-#define WEIGHTED_BIPRED_FLAG				PS_FIELD(188, 1)
-#define TRANSQUANT_BYPASS_ENABLED_FLAG			PS_FIELD(189, 1)
-#define TILES_ENABLED_FLAG				PS_FIELD(190, 1)
-#define ENTROPY_CODING_SYNC_ENABLED_FLAG		PS_FIELD(191, 1)
-#define PPS_LOOP_FILTER_ACROSS_SLICES_ENABLED_FLAG	PS_FIELD(192, 1)
-#define LOOP_FILTER_ACROSS_TILES_ENABLED_FLAG		PS_FIELD(193, 1)
-#define DEBLOCKING_FILTER_OVERRIDE_ENABLED_FLAG		PS_FIELD(194, 1)
-#define PPS_DEBLOCKING_FILTER_DISABLED_FLAG		PS_FIELD(195, 1)
-#define PPS_BETA_OFFSET_DIV2				PS_FIELD(196, 4)
-#define PPS_TC_OFFSET_DIV2				PS_FIELD(200, 4)
-#define LISTS_MODIFICATION_PRESENT_FLAG			PS_FIELD(204, 1)
-#define LOG2_PARALLEL_MERGE_LEVEL			PS_FIELD(205, 3)
-#define SLICE_SEGMENT_HEADER_EXTENSION_PRESENT_FLAG	PS_FIELD(208, 1)
-#define NUM_TILE_COLUMNS				PS_FIELD(212, 5)
-#define NUM_TILE_ROWS					PS_FIELD(217, 5)
-#define COLUMN_WIDTH(i)					PS_FIELD(256 + ((i) * 8), 8)
-#define ROW_HEIGHT(i)					PS_FIELD(416 + ((i) * 8), 8)
-#define SCALING_LIST_ADDRESS				PS_FIELD(592, 32)
+#define PIC_PARAMETER_SET_ID				BW_FIELD(128, 6)
+#define PPS_SEQ_PARAMETER_SET_ID			BW_FIELD(134, 4)
+#define DEPENDENT_SLICE_SEGMENTS_ENABLED_FLAG		BW_FIELD(138, 1)
+#define OUTPUT_FLAG_PRESENT_FLAG			BW_FIELD(139, 1)
+#define NUM_EXTRA_SLICE_HEADER_BITS			BW_FIELD(140, 13)
+#define SIGN_DATA_HIDING_ENABLED_FLAG			BW_FIELD(153, 1)
+#define CABAC_INIT_PRESENT_FLAG				BW_FIELD(154, 1)
+#define NUM_REF_IDX_L0_DEFAULT_ACTIVE			BW_FIELD(155, 4)
+#define NUM_REF_IDX_L1_DEFAULT_ACTIVE			BW_FIELD(159, 4)
+#define INIT_QP_MINUS26					BW_FIELD(163, 7)
+#define CONSTRAINED_INTRA_PRED_FLAG			BW_FIELD(170, 1)
+#define TRANSFORM_SKIP_ENABLED_FLAG			BW_FIELD(171, 1)
+#define CU_QP_DELTA_ENABLED_FLAG			BW_FIELD(172, 1)
+#define LOG2_MIN_CU_QP_DELTA_SIZE			BW_FIELD(173, 3)
+#define PPS_CB_QP_OFFSET				BW_FIELD(176, 5)
+#define PPS_CR_QP_OFFSET				BW_FIELD(181, 5)
+#define PPS_SLICE_CHROMA_QP_OFFSETS_PRESENT_FLAG	BW_FIELD(186, 1)
+#define WEIGHTED_PRED_FLAG				BW_FIELD(187, 1)
+#define WEIGHTED_BIPRED_FLAG				BW_FIELD(188, 1)
+#define TRANSQUANT_BYPASS_ENABLED_FLAG			BW_FIELD(189, 1)
+#define TILES_ENABLED_FLAG				BW_FIELD(190, 1)
+#define ENTROPY_CODING_SYNC_ENABLED_FLAG		BW_FIELD(191, 1)
+#define PPS_LOOP_FILTER_ACROSS_SLICES_ENABLED_FLAG	BW_FIELD(192, 1)
+#define LOOP_FILTER_ACROSS_TILES_ENABLED_FLAG		BW_FIELD(193, 1)
+#define DEBLOCKING_FILTER_OVERRIDE_ENABLED_FLAG		BW_FIELD(194, 1)
+#define PPS_DEBLOCKING_FILTER_DISABLED_FLAG		BW_FIELD(195, 1)
+#define PPS_BETA_OFFSET_DIV2				BW_FIELD(196, 4)
+#define PPS_TC_OFFSET_DIV2				BW_FIELD(200, 4)
+#define LISTS_MODIFICATION_PRESENT_FLAG			BW_FIELD(204, 1)
+#define LOG2_PARALLEL_MERGE_LEVEL			BW_FIELD(205, 3)
+#define SLICE_SEGMENT_HEADER_EXTENSION_PRESENT_FLAG	BW_FIELD(208, 1)
+#define NUM_TILE_COLUMNS				BW_FIELD(212, 5)
+#define NUM_TILE_ROWS					BW_FIELD(217, 5)
+#define COLUMN_WIDTH(i)					BW_FIELD(256 + ((i) * 8), 8)
+#define ROW_HEIGHT(i)					BW_FIELD(416 + ((i) * 8), 8)
+#define SCALING_LIST_ADDRESS				BW_FIELD(592, 32)
 
 /* Data structure describing auxiliary buffer format. */
 struct rkvdec_hevc_priv_tbl {
@@ -123,20 +116,6 @@ struct rkvdec_hevc_ctx {
 	struct rkvdec_regs regs;
 };
 
-static void set_ps_field(u32 *buf, struct rkvdec_ps_field field, u32 value)
-{
-	u8 bit = field.offset % 32, word = field.offset / 32;
-	u64 mask = GENMASK_ULL(bit + field.len - 1, bit);
-	u64 val = ((u64)value << bit) & mask;
-
-	buf[word] &= ~mask;
-	buf[word] |= val;
-	if (bit + field.len > 32) {
-		buf[word + 1] &= ~(mask >> 32);
-		buf[word + 1] |= val >> 32;
-	}
-}
-
 static void assemble_hw_pps(struct rkvdec_ctx *ctx,
 			    struct rkvdec_hevc_run *run)
 {
@@ -159,7 +138,7 @@ static void assemble_hw_pps(struct rkvdec_ctx *ctx,
 	hw_ps = &priv_tbl->param_set[pps->pic_parameter_set_id];
 	memset(hw_ps, 0, sizeof(*hw_ps));
 
-#define WRITE_PPS(value, field) set_ps_field(hw_ps->info, field, value)
+#define WRITE_PPS(value, field) rkvdec_set_bw_field(hw_ps->info, field, value)
 	/* write sps */
 	WRITE_PPS(sps->video_parameter_set_id, VIDEO_PARAMETER_SET_ID);
 	WRITE_PPS(sps->seq_parameter_set_id, SEQ_PARAMETER_SET_ID);
@@ -321,17 +300,17 @@ static void assemble_sw_rps(struct rkvdec_ctx *ctx,
 	int i, j;
 	unsigned int lowdelay;
 
-#define WRITE_RPS(value, field) set_ps_field(hw_ps->info, field, value)
+#define WRITE_RPS(value, field) rkvdec_set_bw_field(hw_ps->info, field, value)
 
-#define REF_PIC_LONG_TERM_L0(i)			PS_FIELD((i) * 5, 1)
-#define REF_PIC_IDX_L0(i)			PS_FIELD(1 + ((i) * 5), 4)
-#define REF_PIC_LONG_TERM_L1(i)			PS_FIELD(((i) < 5 ? 75 : 132) + ((i) * 5), 1)
-#define REF_PIC_IDX_L1(i)			PS_FIELD(((i) < 4 ? 76 : 128) + ((i) * 5), 4)
+#define REF_PIC_LONG_TERM_L0(i)			BW_FIELD((i) * 5, 1)
+#define REF_PIC_IDX_L0(i)			BW_FIELD(1 + ((i) * 5), 4)
+#define REF_PIC_LONG_TERM_L1(i)			BW_FIELD(((i) < 5 ? 75 : 132) + ((i) * 5), 1)
+#define REF_PIC_IDX_L1(i)			BW_FIELD(((i) < 4 ? 76 : 128) + ((i) * 5), 4)
 
-#define LOWDELAY				PS_FIELD(182, 1)
-#define LONG_TERM_RPS_BIT_OFFSET		PS_FIELD(183, 10)
-#define SHORT_TERM_RPS_BIT_OFFSET		PS_FIELD(193, 9)
-#define NUM_RPS_POC				PS_FIELD(202, 4)
+#define LOWDELAY				BW_FIELD(182, 1)
+#define LONG_TERM_RPS_BIT_OFFSET		BW_FIELD(183, 10)
+#define SHORT_TERM_RPS_BIT_OFFSET		BW_FIELD(193, 9)
+#define NUM_RPS_POC				BW_FIELD(202, 4)
 
 	for (j = 0; j < run->num_slices; j++) {
 		uint st_bit_offset = 0;

-- 
2.53.0



^ permalink raw reply related


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