Linux Input/HID development
 help / color / mirror / Atom feed
* [PATCH v2] Documentation: input: expand INPUT_PROP_HAPTIC_TOUCHPAD to all pressure pads
From: Peter Hutterer @ 2025-10-31  4:12 UTC (permalink / raw)
  To: Jonathan Denose, Jiri Kosina, Benjamin Tissoires, Dmitry Torokhov,
	Jonathan Corbet, Henrik Rydberg
  Cc: linux-input, linux-kernel, linux-doc, Angela Czubak,
	Sean O'Brien, Randy Dunlap
In-Reply-To: <20251030011735.GA969565@quokka>

Definition: "pressure pad" used here as all touchpads that use physical
pressure to convert to click without physical hinges. Also called haptic
touchpads in general parlance, Synaptics calls them ForcePads.

Most (all?) pressure pads are currently advertised as
INPUT_PROP_BUTTONPAD. The suggestion to identify them as pressure pads
by defining the resolution on ABS_MT_PRESSURE has been in the docs since
commit 20ccc8dd38a3 ("Documentation: input: define
ABS_PRESSURE/ABS_MT_PRESSURE resolution as grams") but few devices
provide this information.

In userspace it's thus impossible to determine whether a device is a
true pressure pad (pressure equals pressure) or a normal clickpad with
(pressure equals finger size).

Commit 7075ae4ac9db ("Input: add INPUT_PROP_HAPTIC_TOUCHPAD") introduces
INPUT_PROP_HAPTIC_TOUCHPAD but restricted it to those touchpads that
have support for userspace-controlled effects. Let's expand that
definition to include all haptic touchpads (pressure pads) since those
that do support FF effects can be identified by the presence of the
FF_HAPTIC bit.

This means:
- clickpad: INPUT_PROP_BUTTONPAD
- pressurepad: INPUT_PROP_BUTTONPAD + INPUT_PROP_HAPTIC_TOUCHPAD
- pressurepad with haptics:
  INPUT_PROP_BUTTONPAD + INPUT_PROP_HAPTIC_TOUCHPAD + FF_HAPTIC

Signed-off-by: Peter Hutterer <peter.hutterer@who-t.net>
Tested-by: Randy Dunlap <rdunlap@infradead.org>
---
Changes to v1: extra empty lines to render the lists as lists
Link to v1: https://lore.kernel.org/linux-input/20251030011735.GA969565@quokka/T/#u

Side-note: typo in my v1 comment, the HID usage ID that tells us whether
it's a clickpad or pressurepad is 0x59, not 0x55.

 Documentation/input/event-codes.rst | 21 ++++++++++++++++-----
 1 file changed, 16 insertions(+), 5 deletions(-)

diff --git ./Documentation/input/event-codes.rst ../Documentation/input/event-codes.rst
index 1ead9bb8d9c6..bb4c68871e94 100644
--- a/Documentation/input/event-codes.rst
+++ b/Documentation/input/event-codes.rst
@@ -403,16 +403,27 @@ regular directional axes and accelerometer axes on the same event node.
 INPUT_PROP_HAPTIC_TOUCHPAD
 --------------------------
 
-The INPUT_PROP_HAPTIC_TOUCHPAD property indicates that device:
-- supports simple haptic auto and manual triggering
+The INPUT_PROP_HAPTIC_TOUCHPAD property indicates that the device provides
+simulated haptic feedback (e.g. a vibrator motor situated below the surface)
+instead of physical haptic feedback (e.g. a hinge). This property is only set
+if the device:
+
 - can differentiate between at least 5 fingers
 - uses correct resolution for the X/Y (units and value)
-- reports correct force per touch, and correct units for them (newtons or grams)
 - follows the MT protocol type B
 
+If the simulated haptic feedback is controllable by userspace the device must:
+
+- support simple haptic auto and manual triggering, and
+- report correct force per touch, and correct units for them (newtons or grams), and
+- provide the EV_FF FF_HAPTIC force feedback effect.
+
 Summing up, such devices follow the MS spec for input devices in
-Win8 and Win8.1, and in addition support the Simple haptic controller HID table,
-and report correct units for the pressure.
+Win8 and Win8.1, and in addition may support the Simple haptic controller HID
+table, and report correct units for the pressure.
+
+Where applicable, this property is set in addition to INPUT_PROP_BUTTONPAD, it
+does not replace that property.
 
 Guidelines
 ==========
-- 
2.51.0


^ permalink raw reply related

* [PATCH] Input: xpad - add support for the ZD O+ Excellence controller
From: Philippos Boon Alexaki @ 2025-10-30 22:56 UTC (permalink / raw)
  To: Dmitry Torokhov, linux-input; +Cc: linux-kernel, Philippos Boon Alexaki

Adds support for the ZD O+ Excellence controller.
Tested with a wired connection.

Signed-off-by: Philippos Boon Alexaki <palexaki@xs4all.nl>
---
 drivers/input/joystick/xpad.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/drivers/input/joystick/xpad.c b/drivers/input/joystick/xpad.c
index 4c94297e17e6..3805780d5be3 100644
--- a/drivers/input/joystick/xpad.c
+++ b/drivers/input/joystick/xpad.c
@@ -296,6 +296,7 @@ static const struct xpad_device {
 	{ 0x10f5, 0x7005, "Turtle Beach Recon Controller", 0, XTYPE_XBOXONE },
 	{ 0x10f5, 0x7008, "Turtle Beach Recon Controller", MAP_SHARE_BUTTON, XTYPE_XBOXONE },
 	{ 0x10f5, 0x7073, "Turtle Beach Stealth Ultra Controller", MAP_SHARE_BUTTON, XTYPE_XBOXONE },
+	{ 0x11c0, 0x5505, "ZD O+ Excellence", 0, XTYPE_XBOX360 },
 	{ 0x11c9, 0x55f0, "Nacon GC-100XF", 0, XTYPE_XBOX360 },
 	{ 0x11ff, 0x0511, "PXN V900", 0, XTYPE_XBOX360 },
 	{ 0x1209, 0x2882, "Ardwiino Controller", 0, XTYPE_XBOX360 },
@@ -541,6 +542,7 @@ static const struct usb_device_id xpad_table[] = {
 	XPAD_XBOXONE_VENDOR(0x0f0d),		/* Hori controllers */
 	XPAD_XBOX360_VENDOR(0x1038),		/* SteelSeries controllers */
 	XPAD_XBOXONE_VENDOR(0x10f5),		/* Turtle Beach Controllers */
+	XPAD_XBOXONE_VENDOR(0x11c0),		/* ZD O+ Excellence */
 	XPAD_XBOX360_VENDOR(0x11c9),		/* Nacon GC100XF */
 	XPAD_XBOX360_VENDOR(0x11ff),		/* PXN V900 */
 	XPAD_XBOX360_VENDOR(0x1209),		/* Ardwiino Controllers */
-- 
2.43.0


^ permalink raw reply related

* Re: [PATCH 08/10] arm64: dts: add description for solidrun imx8mp hummingboard-iiot
From: Josua Mayer @ 2025-10-30 20:52 UTC (permalink / raw)
  To: Rob Herring, Krzysztof Kozlowski, Conor Dooley, Shawn Guo,
	Neil Armstrong, Jessica Zhang, David Airlie, Simona Vetter,
	Maarten Lankhorst, Maxime Ripard, Thomas Zimmermann,
	Dmitry Torokhov, Sascha Hauer, Pengutronix Kernel Team,
	Fabio Estevam
  Cc: Jon Nettleton, Mikhail Anikin, Yazan Shhady,
	devicetree@vger.kernel.org, linux-kernel@vger.kernel.org,
	dri-devel@lists.freedesktop.org, linux-input@vger.kernel.org,
	imx@lists.linux.dev, linux-arm-kernel@lists.infradead.org
In-Reply-To: <20251027-imx8mp-hb-iiot-v1-8-683f86357818@solid-run.com>

Am 27.10.25 um 18:48 schrieb Josua Mayer:
> Add description for the SolidRun i.MX8MP HummingBoard IIoT.
> The board is a new design around the i.MX8MP System on Module, not
> sharing much with previous HummingBoards.
>
> It comes with some common features:
> - 3x USB-3.0 Type A connector
> - 2x 1Gbps RJ45 Ethernet
> - USB Type-C Console Port
> - microSD connector
> - RTC with backup battery
> - RGB Status LED
> - 1x M.2 M-Key connector with PCI-E Gen. 3 x1
> - 1x M.2 B-Key connector with USB-2.0/3.0 + SIM card holder
> - 1x LVDS Display Connector
> - 1x DSI Display Connector
> - GPIO header
> - 2x RS232/RS485 ports (configurable)
> - 2x CAN
>
> In addition there is a board-to-board expansion connector to support
> custom daughter boards with access to SPI, a range of GPIOs and -
> notably - CAN and UART. Both 2x CAN and 2x UART can be muxed either
> to this b2b connector, or a termianl block connector on the base board.
>
> The routing choice for UART and CAN is expressed through gpio
> mux-controllers in DT and can be changed by applying dtb addons.
>
> Four dtb addons are provided:
>
> - dsi panel Winstar WJ70N3TYJHMNG0
> - lvds panel Winstar WF70A8SYJHLNGA
> - RS485 on UART port "A" (default rs232)
> - RS485 on UART port "B" (default rs232)
>
> Signed-off-by: Josua Mayer <josua@solid-run.com>
> ---
>  arch/arm64/boot/dts/freescale/Makefile             |   6 +
>  ...hummingboard-iiot-panel-dsi-WJ70N3TYJHMNG0.dtso |  70 ++
>  ...ummingboard-iiot-panel-lvds-WF70A8SYJHLNGA.dtso | 105 +++
>  .../imx8mp-hummingboard-iiot-rs485-a.dtso          |  18 +
>  .../imx8mp-hummingboard-iiot-rs485-b.dtso          |  18 +
>  .../dts/freescale/imx8mp-hummingboard-iiot.dts     | 710 +++++++++++++++++++++
>  6 files changed, 927 insertions(+)
>
> diff --git a/arch/arm64/boot/dts/freescale/Makefile b/arch/arm64/boot/dts/freescale/Makefile
> index 8bda6fb0ff9c1..d414d0efe5e74 100644
> --- a/arch/arm64/boot/dts/freescale/Makefile
> +++ b/arch/arm64/boot/dts/freescale/Makefile
> @@ -207,6 +207,12 @@ dtb-$(CONFIG_ARCH_MXC) += imx8mp-dhcom-pdk3.dtb
>  dtb-$(CONFIG_ARCH_MXC) += imx8mp-dhcom-picoitx.dtb
>  dtb-$(CONFIG_ARCH_MXC) += imx8mp-edm-g-wb.dtb
>  dtb-$(CONFIG_ARCH_MXC) += imx8mp-evk.dtb
> +dtb-$(CONFIG_ARCH_MXC) += imx8mp-hummingboard-iiot.dtb
> +DTC_FLAGS_imx8mp-hummingboard-iiot := -@
> +dtb-$(CONFIG_ARCH_MXC) += imx8mp-hummingboard-iiot-panel-dsi-WJ70N3TYJHMNG0.dtbo
> +dtb-$(CONFIG_ARCH_MXC) += imx8mp-hummingboard-iiot-panel-lvds-WF70A8SYJHLNGA.dtbo
> +dtb-$(CONFIG_ARCH_MXC) += imx8mp-hummingboard-iiot-rs485-a.dtbo
> +dtb-$(CONFIG_ARCH_MXC) += imx8mp-hummingboard-iiot-rs485-b.dtbo
>  dtb-$(CONFIG_ARCH_MXC) += imx8mp-hummingboard-mate.dtb
>  DTC_FLAGS_imx8mp-hummingboard-mate := -@
>  dtb-$(CONFIG_ARCH_MXC) += imx8mp-hummingboard-pro.dtb
> diff --git a/arch/arm64/boot/dts/freescale/imx8mp-hummingboard-iiot-panel-dsi-WJ70N3TYJHMNG0.dtso b/arch/arm64/boot/dts/freescale/imx8mp-hummingboard-iiot-panel-dsi-WJ70N3TYJHMNG0.dtso
> new file mode 100644
> index 0000000000000..b3cf66837c577
> --- /dev/null
> +++ b/arch/arm64/boot/dts/freescale/imx8mp-hummingboard-iiot-panel-dsi-WJ70N3TYJHMNG0.dtso
> @@ -0,0 +1,70 @@
> +// SPDX-License-Identifier: (GPL-2.0+ OR MIT)
> +/*
> + * Copyright 2025 Josua Mayer <josua@solid-run.com>
> + *
> + * Overlay for enabling HummingBoard IIoT MIPI-DSI connector
> + * with Winstar WJ70N3TYJHMNG0 panel.
> + */
> +
> +/dts-v1/;
> +/plugin/;
> +
> +#include <dt-bindings/gpio/gpio.h>
> +#include <dt-bindings/interrupt-controller/irq.h>
> +
> +&{/} {
> +	dsi_backlight: dsi-backlight {
> +		compatible = "gpio-backlight";
> +		gpios = <&tca6408_u48 3 GPIO_ACTIVE_LOW>;
> +	};
> +};
> +
> +&i2c_dsi {
> +	#address-cells = <1>;
> +	#size-cells = <0>;
> +
> +	touchscreen@41 {
> +		compatible = "ilitek,ili2130";
> +		reg = <0x41>;
> +		reset-gpios = <&tca6408_u48 6 GPIO_ACTIVE_LOW>;
> +		interrupts-extended = <&tca6416_u21 13 IRQ_TYPE_LEVEL_LOW>;
> +	};
> +};
> +
> +&lcdif1 {
> +	status = "okay";
> +};
> +
> +&mipi_dsi {
> +	samsung,esc-clock-frequency = <10000000>;
> +	#address-cells = <1>;
> +	#size-cells = <0>;
> +	status = "okay";
> +
> +	panel@0 {
> +		/* This is a Winstar panel, but the ronbo panel uses same controls. */
> +		compatible = "ronbo,rb070d30";
> +		reg = <0>;
> +		vcc-lcd-supply = <&reg_dsi_panel>;
> +		power-gpios = <&tca6408_u48 2 GPIO_ACTIVE_HIGH>;
> +		/* reset is active-low but driver inverts it internally */
> +		reset-gpios = <&tca6408_u48 1 GPIO_ACTIVE_HIGH>;
> +		updn-gpios = <&tca6408_u48 5 GPIO_ACTIVE_HIGH>;
> +		shlr-gpios = <&tca6408_u48 4 GPIO_ACTIVE_LOW>;
> +		backlight = <&dsi_backlight>;
> +
> +		port {
> +			panel_from_dsim: endpoint {
> +				data-lanes = <1 2 3 4>;
> +				remote-endpoint = <&dsim_to_panel>;
> +			};
> +		};
> +	};
> +
> +	port@1 {
> +		dsim_to_panel: endpoint {
> +			remote-endpoint = <&panel_from_dsim>;
> +			attach-bridge;
> +		};
> +	};
> +};
> diff --git a/arch/arm64/boot/dts/freescale/imx8mp-hummingboard-iiot-panel-lvds-WF70A8SYJHLNGA.dtso b/arch/arm64/boot/dts/freescale/imx8mp-hummingboard-iiot-panel-lvds-WF70A8SYJHLNGA.dtso
> new file mode 100644
> index 0000000000000..90674f9871020
> --- /dev/null
> +++ b/arch/arm64/boot/dts/freescale/imx8mp-hummingboard-iiot-panel-lvds-WF70A8SYJHLNGA.dtso
> @@ -0,0 +1,105 @@
> +// SPDX-License-Identifier: (GPL-2.0+ OR MIT)
> +/*
> + * Copyright 2025 Josua Mayer <josua@solid-run.com>
> + *
> + * Overlay for enabling HummingBoard IIoT LVDS connector
> + * with Winstar WF70A8SYJHLNGA panel.
> + */
> +
> +/dts-v1/;
> +/plugin/;
> +
> +#include <dt-bindings/gpio/gpio.h>
> +#include <dt-bindings/interrupt-controller/irq.h>
> +
> +&{/} {
> +	lvds_backlight: lvds-backlight {
> +		compatible = "gpio-backlight";
> +		gpios = <&tca6408_u37 3 GPIO_ACTIVE_LOW>;
> +	};
> +
> +	panel-lvds {
> +		compatible = "panel-lvds";
> +		backlight = <&lvds_backlight>;
> +		power-supply = <&reg_dsi_panel>;
> +		enable-gpios = <&tca6408_u37 2 GPIO_ACTIVE_HIGH>;
> +		reset-gpios = <&tca6408_u37 1 GPIO_ACTIVE_HIGH>;
> +		data-mapping = "vesa-24";
> +		width-mm = <154>;
> +		height-mm = <86>;
> +
> +		panel-timing {
> +			/*
> +			 * Note: NXP BSP hard-codes 74MHz clock in ldb driver:
> +			 * drivers/gpu/drm/imx/imx8mp-ldb.c
> +			 * SolidRun BSP carries patch.
> +			 */
> +			clock-frequency = <49500000>;
> +			hactive = <1024>;
> +			vactive = <600>;
> +			hfront-porch = <40>;
> +			hback-porch = <144>;
> +			hsync-len = <104>;
> +			hsync-active = <0>;
> +			vfront-porch = <3>;
> +			vback-porch = <11>;
> +			vsync-len = <10>;
> +			vsync-active = <1>;
> +			de-active = <1>;
> +		};
> +
> +		port {
> +			panel_from_lvds: endpoint {
> +				remote-endpoint = <&lvds_ch0_out>;
> +			};
> +		};
> +	};
> +};
> +
> +&i2c_lvds {
> +	#address-cells = <1>;
> +	#size-cells = <0>;
> +
> +	touchscreen@41 {
> +		compatible = "ilitek,ili2130";
> +		reg = <0x41>;
> +		reset-gpios = <&tca6408_u37 6 GPIO_ACTIVE_LOW>;
> +		interrupts-extended = <&tca6416_u21 13 IRQ_TYPE_LEVEL_LOW>;
> +	};
> +};
> +
> +&lcdif2 {
> +	status = "okay";
> +};
> +
> +&lvds_bridge {
> +	status = "okay";
> +
> +	ports {
> +		#address-cells = <1>;
> +		#size-cells = <0>;
> +		status = "okay";
> +
> +		port@1 {
> +			lvds_ch0_out: endpoint {
> +				remote-endpoint = <&panel_from_lvds>;
> +			};
> +		};
> +	};
> +};
> +
> +&tca6408_u37 {
> +	lvds-lr-hog {
> +		gpio-hog;
> +		gpios = <4 GPIO_ACTIVE_HIGH>;
> +		output-high;
> +		line-name = "lvds-l/r";
> +	};
> +
> +	lvds-ud-hog {
> +		gpio-hog;
> +		gpios = <5 GPIO_ACTIVE_HIGH>;
> +		output-high;
> +		line-name = "lvds-u/d";
> +	};
> +};
Because I have not added any Makefile targets applying the dbo's to dtb,
make dtbs_check is not checking them ...

There are some failing checks that I will resolve:

/opt/workspace/linux/arch/arm64/boot/dts/freescale/imx8mp-hummingboard-iiot-panel-dsi-WJ70N3TYJHMNG0.dtb: panel@0: port:endpoint: Unevaluated properties are not allowed ('data-lanes' was unexpected)
        from schema $id: http://devicetree.org/schemas/display/panel/ronbo,rb070d30.yaml#
/opt/workspace/linux/arch/arm64/boot/dts/freescale/imx8mp-hummingboard-iiot-panel-lvds-WF70A8SYJHLNGA.dtb: panel-lvds: compatible:0: 'panel-lvds' is not one of ['admatec,9904379', 'ampire,amp19201200b5tzqw-t03', 'auo,b101ew05', 'auo,g084sn05', 'chunghwa,claa070wp03xg', 'edt,etml0700z8dha', 'edt,etml0700z9ndha', 'hannstar,hsd101pww2', 'hydis,hv070wx2-1e0', 'jenson,bl-jt60050-01a', 'tbs,a711-panel']
        from schema $id: http://devicetree.org/schemas/display/panel/panel-lvds.yaml#
/opt/workspace/linux/arch/arm64/boot/dts/freescale/imx8mp-hummingboard-iiot-panel-lvds-WF70A8SYJHLNGA.dtb: panel-lvds: compatible: ['panel-lvds'] is too short
        from schema $id: http://devicetree.org/schemas/display/panel/panel-lvds.yaml#
/opt/workspace/linux/arch/arm64/boot/dts/freescale/imx8mp-hummingboard-iiot-panel-lvds-WF70A8SYJHLNGA.dtb: panel-lvds: Unevaluated properties are not allowed ('compatible' was unexpected)
        from schema $id: http://devicetree.org/schemas/display/panel/panel-lvds.yaml#


^ permalink raw reply

* Re: [PATCH v2 1/3] dt-bindings: mfd: twl: enable power button also for twl603x
From: Conor Dooley @ 2025-10-30 19:59 UTC (permalink / raw)
  To: akemnade
  Cc: Lee Jones, Rob Herring, Krzysztof Kozlowski, Conor Dooley,
	Andreas Kemnade, Dmitry Torokhov, Tony Lindgren, Kevin Hilman,
	devicetree, linux-kernel, linux-input, linux-omap
In-Reply-To: <20251030-twl6030-button-v2-1-09653d05a2b1@kernel.org>

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

On Thu, Oct 30, 2025 at 08:10:34PM +0100, akemnade@kernel.org wrote:
> From: Andreas Kemnade <andreas@kemnade.info>
> 
> TWL603x has also a power button function, so add the corresponding subnode.
> As not in all cases there is a power button connected to the corresponding
> pad of the TWL603x, the functionality can be disabled by
> status = "disabled" or simply not adding the subnode.
> To keep things simple, follow the established design pattern of using const
> interrupts as used also by the other subdevices.
> 
> Signed-off-by: Andreas Kemnade <andreas@kemnade.info>

> @@ -225,12 +248,8 @@ properties:
>      additionalProperties: false
>  
>      properties:
> -      compatible:
> -        const: ti,twl4030-pwrbutton
> -      interrupts:
> -        items:
> -          - items:
> -              const: 8
> +      compatible: true
> +      interrupts: true

I think this should be
    properties:
      compatible:
        enum:
          - ti,twl4030-pwrbutton
          - ti,twl6030-pwrbutton
      interrupts:
        maxItems: 1
since we want to keep the widest constraints that apply at the outer
level, rather than removing the constraints entirely.

pw-bot: changes-requested

Cheers,
Conor.

>  
>    watchdog:
>      type: object
> @@ -459,6 +478,11 @@ examples:
>            #io-channel-cells = <1>;
>          };
>  
> +        pwrbutton {
> +          compatible = "ti,twl6030-pwrbutton";
> +          interrupts = <0>;
> +        };
> +
>          rtc {
>            compatible = "ti,twl4030-rtc";
>            interrupts = <8>;
> 
> -- 
> 2.47.3
> 

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

^ permalink raw reply

* [PATCH v6 4/6] Input: mc13783-pwrbutton: enable other mc13xxx PMIC
From: Alexander Kurz @ 2025-10-30 19:56 UTC (permalink / raw)
  To: Rob Herring, Krzysztof Kozlowski, Conor Dooley, Shawn Guo,
	Sascha Hauer, Pengutronix Kernel Team, Fabio Estevam,
	Dmitry Torokhov, Lee Jones, Dzmitry Sankouski,
	Griffin Kroah-Hartman, Mathieu Dubois-Briand, Heiko Stuebner,
	Dr . David Alan Gilbert, Job Sava, Alexandre Belloni,
	Uwe Kleine-König
  Cc: devicetree, imx, linux-arm-kernel, linux-kernel, linux-input,
	Alexander Kurz
In-Reply-To: <20251030195654.20142-1-akurz@blala.de>

All three mc13xxx types feature two common power buttons referred in
the datasheets as ONOFD[12] (mc13783) and PWRON[12] (mc13892/mc34708).
A third button is available on the mc13783 and mc13892 models, which
however uses distinct interrupt register bits.

Add support for mc13892/mc34708 to support all available power buttons
in the mc13xxx series.

Signed-off-by: Alexander Kurz <akurz@blala.de>
---
 drivers/input/misc/Kconfig             |   4 +-
 drivers/input/misc/mc13783-pwrbutton.c | 131 +++++++++++--------------
 drivers/mfd/mc13xxx-core.c             |  22 ++++-
 include/linux/mfd/mc13783.h            |   4 +-
 include/linux/mfd/mc13892.h            |   1 +
 include/linux/mfd/mc13xxx.h            |   2 +
 6 files changed, 84 insertions(+), 80 deletions(-)

diff --git a/drivers/input/misc/Kconfig b/drivers/input/misc/Kconfig
index cc2558630797..c967daa0388a 100644
--- a/drivers/input/misc/Kconfig
+++ b/drivers/input/misc/Kconfig
@@ -297,8 +297,8 @@ config INPUT_MC13783_PWRBUTTON
 	tristate "MC13783 ON buttons"
 	depends on MFD_MC13XXX
 	help
-	  Support the ON buttons of MC13783 PMIC as an input device
-	  reporting power button status.
+	  Support the ON buttons of MC13783/MC13892/MC34708 PMIC as an input
+	  device reporting power button status.
 
 	  To compile this driver as a module, choose M here: the module
 	  will be called mc13783-pwrbutton.
diff --git a/drivers/input/misc/mc13783-pwrbutton.c b/drivers/input/misc/mc13783-pwrbutton.c
index 2ee115d77b1c..08618c59197f 100644
--- a/drivers/input/misc/mc13783-pwrbutton.c
+++ b/drivers/input/misc/mc13783-pwrbutton.c
@@ -30,9 +30,16 @@
 #include <linux/sched.h>
 #include <linux/slab.h>
 
+struct mc13xxx_button_devtype {
+	int button_id_max;
+	const char *irq_name[3];
+	int irq_sense_reg[3];
+};
+
 struct mc13783_pwrb {
 	struct input_dev *pwr;
 	struct mc13xxx *mc13783;
+	const struct mc13xxx_button_devtype *devtype;
 	int flags;
 	unsigned short keymap[3];
 	int irq[3];
@@ -43,9 +50,6 @@ struct mc13783_pwrb {
 #define MC13783_PWRB_B3_POL_INVERT	(1 << 2)
 
 #define MC13783_REG_INTERRUPT_SENSE_1		5
-#define MC13783_IRQSENSE1_ONOFD1S		(1 << 3)
-#define MC13783_IRQSENSE1_ONOFD2S		(1 << 4)
-#define MC13783_IRQSENSE1_ONOFD3S		(1 << 5)
 
 #define MC13783_REG_POWER_CONTROL_2		15
 #define MC13783_POWER_CONTROL_2_ON1BDBNC	4
@@ -63,17 +67,17 @@ static irqreturn_t button_irq(int irq, void *_priv)
 	mc13xxx_reg_read(priv->mc13783, MC13783_REG_INTERRUPT_SENSE_1, &val);
 
 	if (irq == priv->irq[0]) {
-		val = val & MC13783_IRQSENSE1_ONOFD1S ? 1 : 0;
+		val = val & (1 << priv->devtype->irq_sense_reg[0]) ? 1 : 0;
 		if (priv->flags & MC13783_PWRB_B1_POL_INVERT)
 			val ^= 1;
 		input_report_key(priv->pwr, priv->keymap[0], val);
 	} else if (irq == priv->irq[1]) {
-		val = val & MC13783_IRQSENSE1_ONOFD2S ? 1 : 0;
+		val = val & (1 << priv->devtype->irq_sense_reg[1]) ? 1 : 0;
 		if (priv->flags & MC13783_PWRB_B2_POL_INVERT)
 			val ^= 1;
 		input_report_key(priv->pwr, priv->keymap[1], val);
-	} else if (irq == priv->irq[2]) {
-		val = val & MC13783_IRQSENSE1_ONOFD3S ? 1 : 0;
+	} else if (irq == priv->irq[2] && priv->devtype->button_id_max >= 2) {
+		val = val & (1 << priv->devtype->irq_sense_reg[2]) ? 1 : 0;
 		if (priv->flags & MC13783_PWRB_B3_POL_INVERT)
 			val ^= 1;
 		input_report_key(priv->pwr, priv->keymap[2], val);
@@ -88,6 +92,8 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 {
 	const struct mc13xxx_buttons_platform_data *pdata;
 	struct mc13xxx *mc13783 = dev_get_drvdata(pdev->dev.parent);
+	struct mc13xxx_button_devtype *devtype =
+		(struct mc13xxx_button_devtype *)pdev->id_entry->driver_data;
 	struct input_dev *pwr;
 	struct mc13783_pwrb *priv;
 	int err = 0;
@@ -108,54 +114,36 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 	if (!priv)
 		return -ENOMEM;
 
+	if (devtype->button_id_max < 2 && pdata->b_on_flags[2] & 0x3) {
+		dev_err(&pdev->dev, "button not supported\n");
+		return -ENODEV;
+	}
+
 	reg |= (pdata->b_on_flags[0] & 0x3) << MC13783_POWER_CONTROL_2_ON1BDBNC;
 	reg |= (pdata->b_on_flags[1] & 0x3) << MC13783_POWER_CONTROL_2_ON2BDBNC;
 	reg |= (pdata->b_on_flags[2] & 0x3) << MC13783_POWER_CONTROL_2_ON3BDBNC;
 
 	priv->pwr = pwr;
 	priv->mc13783 = mc13783;
+	priv->devtype = devtype;
 
 	mc13xxx_lock(mc13783);
 
-	if (pdata->b_on_flags[0] & MC13783_BUTTON_ENABLE) {
-		priv->keymap[0] = pdata->b_on_key[0];
-		if (pdata->b_on_key[0] != KEY_RESERVED)
-			__set_bit(pdata->b_on_key[0], pwr->keybit);
+	for (int i = 0; i < devtype->button_id_max; i++) {
+		if ((pdata->b_on_flags[i] & MC13783_BUTTON_ENABLE) == 0)
+			continue;
 
-		if (pdata->b_on_flags[0] & MC13783_BUTTON_POL_INVERT)
-			priv->flags |= MC13783_PWRB_B1_POL_INVERT;
+		priv->keymap[i] = pdata->b_on_key[i];
+		if (pdata->b_on_key[i] != KEY_RESERVED)
+			__set_bit(pdata->b_on_key[i], pwr->keybit);
 
-		if (pdata->b_on_flags[0] & MC13783_BUTTON_RESET_EN)
-			reg |= MC13783_POWER_CONTROL_2_ON1BRSTEN;
+		if (pdata->b_on_flags[i] & MC13783_BUTTON_POL_INVERT)
+			priv->flags |= (MC13783_PWRB_B1_POL_INVERT << i);
 
-		irq = platform_get_irq_byname(pdev, "b1on");
+		if (pdata->b_on_flags[i] & MC13783_BUTTON_RESET_EN)
+			reg |= (MC13783_POWER_CONTROL_2_ON1BRSTEN << i);
 
-		if (irq < 0) {
-			dev_dbg(&pdev->dev, "Can't request irq\n");
-			goto free_mc13xxx_lock;
-		}
-
-		err = devm_request_any_context_irq(&pdev->dev, irq, button_irq,
-						   IRQF_ONESHOT, "b1on",
-						   priv);
-		if (err < 0)
-			goto free_mc13xxx_lock;
-
-		priv->irq[0] = irq;
-	}
-
-	if (pdata->b_on_flags[1] & MC13783_BUTTON_ENABLE) {
-		priv->keymap[1] = pdata->b_on_key[1];
-		if (pdata->b_on_key[1] != KEY_RESERVED)
-			__set_bit(pdata->b_on_key[1], pwr->keybit);
-
-		if (pdata->b_on_flags[1] & MC13783_BUTTON_POL_INVERT)
-			priv->flags |= MC13783_PWRB_B2_POL_INVERT;
-
-		if (pdata->b_on_flags[1] & MC13783_BUTTON_RESET_EN)
-			reg |= MC13783_POWER_CONTROL_2_ON2BRSTEN;
-
-		irq = platform_get_irq_byname(pdev, "b2on");
+		irq = platform_get_irq_byname(pdev, devtype->irq_name[i]);
 
 		if (irq < 0) {
 			dev_dbg(&pdev->dev, "Can't request irq\n");
@@ -163,39 +151,12 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 		}
 
 		err = devm_request_any_context_irq(&pdev->dev, irq, button_irq,
-						   IRQF_ONESHOT, "b2on",
-						   priv);
+					   IRQF_ONESHOT, devtype->irq_name[i],
+					   priv);
 		if (err < 0)
 			goto free_mc13xxx_lock;
 
-		priv->irq[1] = irq;
-	}
-
-	if (pdata->b_on_flags[2] & MC13783_BUTTON_ENABLE) {
-		priv->keymap[2] = pdata->b_on_key[2];
-		if (pdata->b_on_key[2] != KEY_RESERVED)
-			__set_bit(pdata->b_on_key[2], pwr->keybit);
-
-		if (pdata->b_on_flags[2] & MC13783_BUTTON_POL_INVERT)
-			priv->flags |= MC13783_PWRB_B3_POL_INVERT;
-
-		if (pdata->b_on_flags[2] & MC13783_BUTTON_RESET_EN)
-			reg |= MC13783_POWER_CONTROL_2_ON3BRSTEN;
-
-		irq = platform_get_irq_byname(pdev, "b3on");
-
-		if (irq < 0) {
-			dev_dbg(&pdev->dev, "Can't request irq: %d\n", err);
-			goto free_mc13xxx_lock;
-		}
-
-		err = devm_request_any_context_irq(&pdev->dev, irq, button_irq,
-						   IRQF_ONESHOT, "b3on",
-						   priv);
-		if (err < 0)
-			goto free_mc13xxx_lock;
-
-		priv->irq[2] = irq;
+		priv->irq[i] = irq;
 	}
 
 	mc13xxx_reg_rmw(mc13783, MC13783_REG_POWER_CONTROL_2, 0x3FE, reg);
@@ -226,7 +187,33 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 	return err;
 }
 
+static const struct mc13xxx_button_devtype mc13783_button_devtype = {
+	.button_id_max	= 2,
+	.irq_name = { "b1on", "b2on", "b3on" },
+	.irq_sense_reg = { 3, 4, 5 },
+};
+
+static const struct mc13xxx_button_devtype mc13892_button_devtype = {
+	.button_id_max	= 2,
+	.irq_name = { "b1on", "b2on", "b3on" },
+	.irq_sense_reg = { 3, 4, 2 },
+};
+
+static const struct mc13xxx_button_devtype mc34708_button_devtype = {
+	.button_id_max	= 1,
+	.irq_name = { "b1on", "b2on" },
+	.irq_sense_reg = { 3, 4 },
+};
+
+static const struct platform_device_id mc13xxx_pwrbutton_idtable[] = {
+	{ "mc13783-pwrbutton", (kernel_ulong_t)&mc13783_button_devtype },
+	{ "mc13892-pwrbutton", (kernel_ulong_t)&mc13892_button_devtype },
+	{ "mc34708-pwrbutton", (kernel_ulong_t)&mc34708_button_devtype },
+	{ /* sentinel */ }
+};
+
 static struct platform_driver mc13783_pwrbutton_driver = {
+	.id_table	= mc13xxx_pwrbutton_idtable,
 	.probe		= mc13783_pwrbutton_probe,
 	.driver		= {
 		.name	= "mc13783-pwrbutton",
diff --git a/drivers/mfd/mc13xxx-core.c b/drivers/mfd/mc13xxx-core.c
index 1756c8d47d5e..c29974722704 100644
--- a/drivers/mfd/mc13xxx-core.c
+++ b/drivers/mfd/mc13xxx-core.c
@@ -14,6 +14,7 @@
 #include <linux/platform_device.h>
 #include <linux/mfd/core.h>
 #include <linux/mfd/mc13783.h>
+#include <linux/mfd/mc13892.h>
 
 #include "mc13xxx.h"
 
@@ -48,11 +49,22 @@
 #define MC13XXX_ADC2		45
 
 static const struct resource mc13783_button_resources[] = {
-	DEFINE_RES_IRQ_NAMED(MC13783_IRQ_ONOFD1, "b1on"),
-	DEFINE_RES_IRQ_NAMED(MC13783_IRQ_ONOFD2, "b2on"),
+	DEFINE_RES_IRQ_NAMED(MC13XXX_IRQ_PWRON1, "b1on"),
+	DEFINE_RES_IRQ_NAMED(MC13XXX_IRQ_PWRON2, "b2on"),
 	DEFINE_RES_IRQ_NAMED(MC13783_IRQ_ONOFD3, "b3on"),
 };
 
+static const struct resource mc13892_button_resources[] = {
+	DEFINE_RES_IRQ_NAMED(MC13XXX_IRQ_PWRON1, "b1on"),
+	DEFINE_RES_IRQ_NAMED(MC13XXX_IRQ_PWRON2, "b2on"),
+	DEFINE_RES_IRQ_NAMED(MC13892_IRQ_PWRON3, "b3on"),
+};
+
+static const struct resource mc34708_button_resources[] = {
+	DEFINE_RES_IRQ_NAMED(MC13XXX_IRQ_PWRON1, "b1on"),
+	DEFINE_RES_IRQ_NAMED(MC13XXX_IRQ_PWRON2, "b2on"),
+};
+
 void mc13xxx_lock(struct mc13xxx *mc13xxx)
 {
 	if (!mutex_trylock(&mc13xxx->lock)) {
@@ -216,14 +228,16 @@ EXPORT_SYMBOL_GPL(mc13xxx_variant_mc13783);
 
 struct mc13xxx_variant mc13xxx_variant_mc13892 = {
 	.name = "mc13892",
-	.button_resources_size = 0,
+	.button_resources = mc13892_button_resources,
+	.button_resources_size = ARRAY_SIZE(mc13892_button_resources),
 	.print_revision = mc13xxx_print_revision,
 };
 EXPORT_SYMBOL_GPL(mc13xxx_variant_mc13892);
 
 struct mc13xxx_variant mc13xxx_variant_mc34708 = {
 	.name = "mc34708",
-	.button_resources_size = 0,
+	.button_resources = mc34708_button_resources,
+	.button_resources_size = ARRAY_SIZE(mc34708_button_resources),
 	.print_revision = mc34708_print_revision,
 };
 EXPORT_SYMBOL_GPL(mc13xxx_variant_mc34708);
diff --git a/include/linux/mfd/mc13783.h b/include/linux/mfd/mc13783.h
index c25b1676741b..ab6db774e1fa 100644
--- a/include/linux/mfd/mc13783.h
+++ b/include/linux/mfd/mc13783.h
@@ -65,8 +65,8 @@
 #define MC13783_IRQ_UDM		23
 #define MC13783_IRQ_1HZ		MC13XXX_IRQ_1HZ
 #define MC13783_IRQ_TODA	MC13XXX_IRQ_TODA
-#define MC13783_IRQ_ONOFD1	27
-#define MC13783_IRQ_ONOFD2	28
+#define MC13783_IRQ_ONOFD1	MC13XXX_IRQ_PWRON1
+#define MC13783_IRQ_ONOFD2	MC13XXX_IRQ_PWRON2
 #define MC13783_IRQ_ONOFD3	29
 #define MC13783_IRQ_SYSRST	MC13XXX_IRQ_SYSRST
 #define MC13783_IRQ_RTCRST	MC13XXX_IRQ_RTCRST
diff --git a/include/linux/mfd/mc13892.h b/include/linux/mfd/mc13892.h
index 880cd949d12a..567d527825df 100644
--- a/include/linux/mfd/mc13892.h
+++ b/include/linux/mfd/mc13892.h
@@ -33,4 +33,5 @@
 #define MC13892_PWGT2SPI	22
 #define MC13892_VCOINCELL	23
 
+#define MC13892_IRQ_PWRON3	26
 #endif
diff --git a/include/linux/mfd/mc13xxx.h b/include/linux/mfd/mc13xxx.h
index 4437ab80fcf8..71c7d3614d4c 100644
--- a/include/linux/mfd/mc13xxx.h
+++ b/include/linux/mfd/mc13xxx.h
@@ -61,6 +61,8 @@ int mc13xxx_irq_unmask(struct mc13xxx *mc13xxx, int irq);
 #define MC13XXX_IRQ_LOBATH	14
 #define MC13XXX_IRQ_1HZ		24
 #define MC13XXX_IRQ_TODA	25
+#define MC13XXX_IRQ_PWRON1	27
+#define MC13XXX_IRQ_PWRON2	28
 #define MC13XXX_IRQ_SYSRST	30
 #define MC13XXX_IRQ_RTCRST	31
 #define MC13XXX_IRQ_PC		32
-- 
2.39.5


^ permalink raw reply related

* [PATCH v6 0/6] Fix, extend and support OF to mc13xxx pwrbutton
From: Alexander Kurz @ 2025-10-30 19:56 UTC (permalink / raw)
  To: Rob Herring, Krzysztof Kozlowski, Conor Dooley, Shawn Guo,
	Sascha Hauer, Pengutronix Kernel Team, Fabio Estevam,
	Dmitry Torokhov, Lee Jones, Dzmitry Sankouski,
	Griffin Kroah-Hartman, Mathieu Dubois-Briand, Heiko Stuebner,
	Dr . David Alan Gilbert, Job Sava, Alexandre Belloni,
	Uwe Kleine-König
  Cc: devicetree, imx, linux-arm-kernel, linux-kernel, linux-input,
	Alexander Kurz

Goal of this patch series is to make mx13xxx power buttons usable
on DT based systems.
A ten-year-old IRQ issue needed a fix, mc13783-pwrbutton had to be
extended to the other to mc13xxx PMIC as well and adding OF support.
The implementation has been tested with PWRON1 on mc13892 found e.g.
in amazon kindle D01100/D01200/EY21 readers and also in on mc34708
in the imx53-qsrb "i.MX53 Quick start board".

Changes in v6:
- Link to v5: https://lore.kernel.org/linux-input/20251008064401.13863-1-akurz@blala.de/
- Rebase to v6.18-rc1
- Add a imx53-qsrb dts patch to enable the "power" button on the
  i.MX53 Quick start board.

Changes in v5:
- Link to v4: https://lore.kernel.org/linux-input/20250914193723.10544-1-akurz@blala.de/
- Rebase to current to include already merged dt-schema patches and
  a different mc13xxx related patch.
- Drop patch to use devm_mfd_add_devices and devm_regmap_add_irq_chip -
  won't like to do the proposed mutex-cleanup now.
- While adding OF support, remove the platform_data configuration
  interface as proposed by Dmitry Torokhov. Also drop the change
  to use module_platform_driver_probe.

Changes in v4:
- Link to v3: https://lore.kernel.org/linux-input/20250829201517.15374-1-akurz@blala.de/
- Rebase to git://git.kernel.org/pub/scm/linux/kernel/git/lee/mfd.git
  tags/ib-mfd-input-rtc-v6.18 in order to include a different mc13xxx
  related patch (sorry for that).
- Re-ordered commits since dt-bindings changes already go reviewes by
  Rob Herring.
- Following Dmitrys suggestions, resources for irq are now passed from
  mfd to input allowing a more simple implementation. Work on other mfd
  cells with irq usage might still be a future project.
- Input-related differences between the mc13xxx variants are encoded
  in data structures, making the implementation of mc13892 PWRON3 a
  simple task.

Changes in v3:
- Link to v2: https://lore.kernel.org/linux-input/20250823144441.12654-1-akurz@blala.de/
- Undo all changes to led-control (rename to fsl,led-control), thanks Rob
- Restructured the new buttons node for unevaluatedProperties: false
- Various other remarks from Rob
- Rebase to current state

Changes in v2:
- Link to v1: https://lore.kernel.org/linux-input/20250817102751.29709-1-akurz@blala.de/
- Convert dt-bindings from txt to fsl,mc13xxx.yaml and add vendor prefix
  to led-control property, causing changes in dts and driver.
- Change node name from pwrbuttons to buttons
- Change property debounce-delay-value to debounce-delay-ms
- Fixed a section mismatch error
- Fixed https://lore.kernel.org/r/202508210551.VzAtE5re-lkp@intel.com/
  (wrong index used when converting to array access)
- Usage of generic device properties API in mc13783-pwrbutton.c
- Provide chip-specific max button id via platform_device_id, therefore
  swap patches 3 and 4.

Alexander Kurz (6):
  Input: mc13783-pwrbutton: use managed resources
  Input: mc13783-pwrbutton: fix irq mixup and use resources
  Input: mc13783-pwrbutton: convert pdata members to array
  Input: mc13783-pwrbutton: enable other mc13xxx PMIC
  Input: mc13783-pwrbutton: add OF support and drop platform_data
  ARM: dts: imx53: add imx53-qsrb PMIC power button

 arch/arm/boot/dts/nxp/imx/imx53-qsrb.dts |  12 +
 drivers/input/misc/Kconfig               |   4 +-
 drivers/input/misc/mc13783-pwrbutton.c   | 278 +++++++++++++----------
 drivers/mfd/mc13xxx-core.c               |  49 +++-
 drivers/mfd/mc13xxx.h                    |   2 +
 include/linux/mfd/mc13783.h              |   4 +-
 include/linux/mfd/mc13892.h              |   1 +
 include/linux/mfd/mc13xxx.h              |  20 +-
 8 files changed, 219 insertions(+), 151 deletions(-)

-- 
2.39.5


^ permalink raw reply

* [PATCH v6 2/6] Input: mc13783-pwrbutton: fix irq mixup and use resources
From: Alexander Kurz @ 2025-10-30 19:56 UTC (permalink / raw)
  To: Rob Herring, Krzysztof Kozlowski, Conor Dooley, Shawn Guo,
	Sascha Hauer, Pengutronix Kernel Team, Fabio Estevam,
	Dmitry Torokhov, Lee Jones, Dzmitry Sankouski,
	Griffin Kroah-Hartman, Mathieu Dubois-Briand, Heiko Stuebner,
	Dr . David Alan Gilbert, Job Sava, Alexandre Belloni,
	Uwe Kleine-König
  Cc: devicetree, imx, linux-arm-kernel, linux-kernel, linux-input,
	Alexander Kurz
In-Reply-To: <20251030195654.20142-1-akurz@blala.de>

The mfd mc13xxx interrupt handling was migrated to regmap with commit
10f9edaeaa30 ("mfd: mc13xxx: Use regmap irq framework for interrupts").
As a consequence, button_irq() got get called with virtual irq instead
of chip-internal irq.

Make use of mfd_cell resources to pass interrupts from mfd so that
platform_get_irq_byname() can be used in mc13783-pwrbutton. The
amount of required interrupt related cleanup can be reduced this way.

Note, that mc13783-pwrbutton is still considered to support only the
model mc13783.

Signed-off-by: Alexander Kurz <akurz@blala.de>
---
 drivers/input/misc/mc13783-pwrbutton.c | 103 +++++++++++--------------
 drivers/mfd/mc13xxx-core.c             |  39 ++++++++--
 drivers/mfd/mc13xxx.h                  |   2 +
 3 files changed, 79 insertions(+), 65 deletions(-)

diff --git a/drivers/input/misc/mc13783-pwrbutton.c b/drivers/input/misc/mc13783-pwrbutton.c
index 82434ea9cca5..20f68aab6edf 100644
--- a/drivers/input/misc/mc13783-pwrbutton.c
+++ b/drivers/input/misc/mc13783-pwrbutton.c
@@ -33,13 +33,15 @@
 struct mc13783_pwrb {
 	struct input_dev *pwr;
 	struct mc13xxx *mc13783;
-#define MC13783_PWRB_B1_POL_INVERT	(1 << 0)
-#define MC13783_PWRB_B2_POL_INVERT	(1 << 1)
-#define MC13783_PWRB_B3_POL_INVERT	(1 << 2)
 	int flags;
 	unsigned short keymap[3];
+	int irq[3];
 };
 
+#define MC13783_PWRB_B1_POL_INVERT	(1 << 0)
+#define MC13783_PWRB_B2_POL_INVERT	(1 << 1)
+#define MC13783_PWRB_B3_POL_INVERT	(1 << 2)
+
 #define MC13783_REG_INTERRUPT_SENSE_1		5
 #define MC13783_IRQSENSE1_ONOFD1S		(1 << 3)
 #define MC13783_IRQSENSE1_ONOFD2S		(1 << 4)
@@ -60,27 +62,21 @@ static irqreturn_t button_irq(int irq, void *_priv)
 
 	mc13xxx_reg_read(priv->mc13783, MC13783_REG_INTERRUPT_SENSE_1, &val);
 
-	switch (irq) {
-	case MC13783_IRQ_ONOFD1:
+	if (irq == priv->irq[0]) {
 		val = val & MC13783_IRQSENSE1_ONOFD1S ? 1 : 0;
 		if (priv->flags & MC13783_PWRB_B1_POL_INVERT)
 			val ^= 1;
 		input_report_key(priv->pwr, priv->keymap[0], val);
-		break;
-
-	case MC13783_IRQ_ONOFD2:
+	} else if (irq == priv->irq[1]) {
 		val = val & MC13783_IRQSENSE1_ONOFD2S ? 1 : 0;
 		if (priv->flags & MC13783_PWRB_B2_POL_INVERT)
 			val ^= 1;
 		input_report_key(priv->pwr, priv->keymap[1], val);
-		break;
-
-	case MC13783_IRQ_ONOFD3:
+	} else if (irq == priv->irq[2]) {
 		val = val & MC13783_IRQSENSE1_ONOFD3S ? 1 : 0;
 		if (priv->flags & MC13783_PWRB_B3_POL_INVERT)
 			val ^= 1;
 		input_report_key(priv->pwr, priv->keymap[2], val);
-		break;
 	}
 
 	input_sync(priv->pwr);
@@ -96,6 +92,7 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 	struct mc13783_pwrb *priv;
 	int err = 0;
 	int reg = 0;
+	int irq = 0;
 
 	pdata = dev_get_platdata(&pdev->dev);
 	if (!pdata) {
@@ -131,12 +128,20 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 		if (pdata->b1on_flags & MC13783_BUTTON_RESET_EN)
 			reg |= MC13783_POWER_CONTROL_2_ON1BRSTEN;
 
-		err = mc13xxx_irq_request(mc13783, MC13783_IRQ_ONOFD1,
-					  button_irq, "b1on", priv);
-		if (err) {
+		irq = platform_get_irq_byname(pdev, "b1on");
+
+		if (irq < 0) {
 			dev_dbg(&pdev->dev, "Can't request irq\n");
 			goto free_mc13xxx_lock;
 		}
+
+		err = devm_request_any_context_irq(&pdev->dev, irq, button_irq,
+						   IRQF_ONESHOT, "b1on",
+						   priv);
+		if (err < 0)
+			goto free_mc13xxx_lock;
+
+		priv->irq[0] = irq;
 	}
 
 	if (pdata->b2on_flags & MC13783_BUTTON_ENABLE) {
@@ -150,12 +155,20 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 		if (pdata->b2on_flags & MC13783_BUTTON_RESET_EN)
 			reg |= MC13783_POWER_CONTROL_2_ON2BRSTEN;
 
-		err = mc13xxx_irq_request(mc13783, MC13783_IRQ_ONOFD2,
-					  button_irq, "b2on", priv);
-		if (err) {
+		irq = platform_get_irq_byname(pdev, "b2on");
+
+		if (irq < 0) {
 			dev_dbg(&pdev->dev, "Can't request irq\n");
-			goto free_irq_b1;
+			goto free_mc13xxx_lock;
 		}
+
+		err = devm_request_any_context_irq(&pdev->dev, irq, button_irq,
+						   IRQF_ONESHOT, "b2on",
+						   priv);
+		if (err < 0)
+			goto free_mc13xxx_lock;
+
+		priv->irq[1] = irq;
 	}
 
 	if (pdata->b3on_flags & MC13783_BUTTON_ENABLE) {
@@ -169,12 +182,20 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 		if (pdata->b3on_flags & MC13783_BUTTON_RESET_EN)
 			reg |= MC13783_POWER_CONTROL_2_ON3BRSTEN;
 
-		err = mc13xxx_irq_request(mc13783, MC13783_IRQ_ONOFD3,
-					  button_irq, "b3on", priv);
-		if (err) {
+		irq = platform_get_irq_byname(pdev, "b3on");
+
+		if (irq < 0) {
 			dev_dbg(&pdev->dev, "Can't request irq: %d\n", err);
-			goto free_irq_b2;
+			goto free_mc13xxx_lock;
 		}
+
+		err = devm_request_any_context_irq(&pdev->dev, irq, button_irq,
+						   IRQF_ONESHOT, "b3on",
+						   priv);
+		if (err < 0)
+			goto free_mc13xxx_lock;
+
+		priv->irq[2] = irq;
 	}
 
 	mc13xxx_reg_rmw(mc13783, MC13783_REG_POWER_CONTROL_2, 0x3FE, reg);
@@ -192,55 +213,21 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 	err = input_register_device(pwr);
 	if (err) {
 		dev_dbg(&pdev->dev, "Can't register power button: %d\n", err);
-		goto free_irq;
+		return err;
 	}
 
 	platform_set_drvdata(pdev, priv);
 
 	return 0;
 
-free_irq:
-	mc13xxx_lock(mc13783);
-
-	if (pdata->b3on_flags & MC13783_BUTTON_ENABLE)
-		mc13xxx_irq_free(mc13783, MC13783_IRQ_ONOFD3, priv);
-
-free_irq_b2:
-	if (pdata->b2on_flags & MC13783_BUTTON_ENABLE)
-		mc13xxx_irq_free(mc13783, MC13783_IRQ_ONOFD2, priv);
-
-free_irq_b1:
-	if (pdata->b1on_flags & MC13783_BUTTON_ENABLE)
-		mc13xxx_irq_free(mc13783, MC13783_IRQ_ONOFD1, priv);
-
 free_mc13xxx_lock:
 	mc13xxx_unlock(mc13783);
 
 	return err;
 }
 
-static void mc13783_pwrbutton_remove(struct platform_device *pdev)
-{
-	struct mc13783_pwrb *priv = platform_get_drvdata(pdev);
-	const struct mc13xxx_buttons_platform_data *pdata;
-
-	pdata = dev_get_platdata(&pdev->dev);
-
-	mc13xxx_lock(priv->mc13783);
-
-	if (pdata->b3on_flags & MC13783_BUTTON_ENABLE)
-		mc13xxx_irq_free(priv->mc13783, MC13783_IRQ_ONOFD3, priv);
-	if (pdata->b2on_flags & MC13783_BUTTON_ENABLE)
-		mc13xxx_irq_free(priv->mc13783, MC13783_IRQ_ONOFD2, priv);
-	if (pdata->b1on_flags & MC13783_BUTTON_ENABLE)
-		mc13xxx_irq_free(priv->mc13783, MC13783_IRQ_ONOFD1, priv);
-
-	mc13xxx_unlock(priv->mc13783);
-}
-
 static struct platform_driver mc13783_pwrbutton_driver = {
 	.probe		= mc13783_pwrbutton_probe,
-	.remove		= mc13783_pwrbutton_remove,
 	.driver		= {
 		.name	= "mc13783-pwrbutton",
 	},
diff --git a/drivers/mfd/mc13xxx-core.c b/drivers/mfd/mc13xxx-core.c
index 920797b806ce..1756c8d47d5e 100644
--- a/drivers/mfd/mc13xxx-core.c
+++ b/drivers/mfd/mc13xxx-core.c
@@ -13,6 +13,7 @@
 #include <linux/of_device.h>
 #include <linux/platform_device.h>
 #include <linux/mfd/core.h>
+#include <linux/mfd/mc13783.h>
 
 #include "mc13xxx.h"
 
@@ -46,6 +47,12 @@
 
 #define MC13XXX_ADC2		45
 
+static const struct resource mc13783_button_resources[] = {
+	DEFINE_RES_IRQ_NAMED(MC13783_IRQ_ONOFD1, "b1on"),
+	DEFINE_RES_IRQ_NAMED(MC13783_IRQ_ONOFD2, "b2on"),
+	DEFINE_RES_IRQ_NAMED(MC13783_IRQ_ONOFD3, "b3on"),
+};
+
 void mc13xxx_lock(struct mc13xxx *mc13xxx)
 {
 	if (!mutex_trylock(&mc13xxx->lock)) {
@@ -201,18 +208,22 @@ static void mc34708_print_revision(struct mc13xxx *mc13xxx, u32 revision)
 /* These are only exported for mc13xxx-i2c and mc13xxx-spi */
 struct mc13xxx_variant mc13xxx_variant_mc13783 = {
 	.name = "mc13783",
+	.button_resources = mc13783_button_resources,
+	.button_resources_size = ARRAY_SIZE(mc13783_button_resources),
 	.print_revision = mc13xxx_print_revision,
 };
 EXPORT_SYMBOL_GPL(mc13xxx_variant_mc13783);
 
 struct mc13xxx_variant mc13xxx_variant_mc13892 = {
 	.name = "mc13892",
+	.button_resources_size = 0,
 	.print_revision = mc13xxx_print_revision,
 };
 EXPORT_SYMBOL_GPL(mc13xxx_variant_mc13892);
 
 struct mc13xxx_variant mc13xxx_variant_mc34708 = {
 	.name = "mc34708",
+	.button_resources_size = 0,
 	.print_revision = mc34708_print_revision,
 };
 EXPORT_SYMBOL_GPL(mc13xxx_variant_mc34708);
@@ -362,15 +373,18 @@ int mc13xxx_adc_do_conversion(struct mc13xxx *mc13xxx, unsigned int mode,
 }
 EXPORT_SYMBOL_GPL(mc13xxx_adc_do_conversion);
 
-static int mc13xxx_add_subdevice_pdata(struct mc13xxx *mc13xxx,
-		const char *format, void *pdata, size_t pdata_size)
+static int mc13xxx_add_subdevice_pdata_res(struct mc13xxx *mc13xxx,
+		const char *format, void *pdata, size_t pdata_size,
+		const struct resource *resources, int num_resources)
 {
 	char buf[30];
 	const char *name = mc13xxx_get_chipname(mc13xxx);
 
 	struct mfd_cell cell = {
-		.platform_data = pdata,
-		.pdata_size = pdata_size,
+		.platform_data	= pdata,
+		.pdata_size	= pdata_size,
+		.resources	= resources,
+		.num_resources	= num_resources,
 	};
 
 	/* there is no asnprintf in the kernel :-( */
@@ -385,6 +399,12 @@ static int mc13xxx_add_subdevice_pdata(struct mc13xxx *mc13xxx,
 			       regmap_irq_get_domain(mc13xxx->irq_data));
 }
 
+static int mc13xxx_add_subdevice_pdata(struct mc13xxx *mc13xxx,
+		const char *format, void *pdata, size_t pdata_size)
+{
+	return mc13xxx_add_subdevice_pdata_res(mc13xxx, format, pdata, pdata_size, NULL, 0);
+}
+
 static int mc13xxx_add_subdevice(struct mc13xxx *mc13xxx, const char *format)
 {
 	return mc13xxx_add_subdevice_pdata(mc13xxx, format, NULL, 0);
@@ -470,8 +490,10 @@ int mc13xxx_common_init(struct device *dev)
 			&pdata->regulators, sizeof(pdata->regulators));
 		mc13xxx_add_subdevice_pdata(mc13xxx, "%s-led",
 				pdata->leds, sizeof(*pdata->leds));
-		mc13xxx_add_subdevice_pdata(mc13xxx, "%s-pwrbutton",
-				pdata->buttons, sizeof(*pdata->buttons));
+		mc13xxx_add_subdevice_pdata_res(mc13xxx, "%s-pwrbutton",
+				pdata->buttons, sizeof(*pdata->buttons),
+				mc13xxx->variant->button_resources,
+				mc13xxx->variant->button_resources_size);
 		if (mc13xxx->flags & MC13XXX_USE_CODEC)
 			mc13xxx_add_subdevice_pdata(mc13xxx, "%s-codec",
 				pdata->codec, sizeof(*pdata->codec));
@@ -481,7 +503,10 @@ int mc13xxx_common_init(struct device *dev)
 	} else {
 		mc13xxx_add_subdevice(mc13xxx, "%s-regulator");
 		mc13xxx_add_subdevice(mc13xxx, "%s-led");
-		mc13xxx_add_subdevice(mc13xxx, "%s-pwrbutton");
+		mc13xxx_add_subdevice_pdata_res(mc13xxx, "%s-pwrbutton",
+				NULL, 0,
+				mc13xxx->variant->button_resources,
+				mc13xxx->variant->button_resources_size);
 		if (mc13xxx->flags & MC13XXX_USE_CODEC)
 			mc13xxx_add_subdevice(mc13xxx, "%s-codec");
 		if (mc13xxx->flags & MC13XXX_USE_TOUCHSCREEN)
diff --git a/drivers/mfd/mc13xxx.h b/drivers/mfd/mc13xxx.h
index bd5ba9a0e14f..b13ae652f4ec 100644
--- a/drivers/mfd/mc13xxx.h
+++ b/drivers/mfd/mc13xxx.h
@@ -18,6 +18,8 @@ struct mc13xxx;
 
 struct mc13xxx_variant {
 	const char *name;
+	const struct resource *button_resources;
+	int button_resources_size;
 	void (*print_revision)(struct mc13xxx *mc13xxx, u32 revision);
 };
 
-- 
2.39.5


^ permalink raw reply related

* [PATCH v6 3/6] Input: mc13783-pwrbutton: convert pdata members to array
From: Alexander Kurz @ 2025-10-30 19:56 UTC (permalink / raw)
  To: Rob Herring, Krzysztof Kozlowski, Conor Dooley, Shawn Guo,
	Sascha Hauer, Pengutronix Kernel Team, Fabio Estevam,
	Dmitry Torokhov, Lee Jones, Dzmitry Sankouski,
	Griffin Kroah-Hartman, Mathieu Dubois-Briand, Heiko Stuebner,
	Dr . David Alan Gilbert, Job Sava, Alexandre Belloni,
	Uwe Kleine-König
  Cc: devicetree, imx, linux-arm-kernel, linux-kernel, linux-input,
	Alexander Kurz
In-Reply-To: <20251030195654.20142-1-akurz@blala.de>

As preparation for the extension of support for all three mc13xxx
variants, convert the members of mc13xxx_buttons_platform_data to
arrays to allow index access within the next commit.

Signed-off-by: Alexander Kurz <akurz@blala.de>
---
 drivers/input/misc/mc13783-pwrbutton.c | 42 +++++++++++++-------------
 include/linux/mfd/mc13xxx.h            |  8 ++---
 2 files changed, 23 insertions(+), 27 deletions(-)

diff --git a/drivers/input/misc/mc13783-pwrbutton.c b/drivers/input/misc/mc13783-pwrbutton.c
index 20f68aab6edf..2ee115d77b1c 100644
--- a/drivers/input/misc/mc13783-pwrbutton.c
+++ b/drivers/input/misc/mc13783-pwrbutton.c
@@ -108,24 +108,24 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 	if (!priv)
 		return -ENOMEM;
 
-	reg |= (pdata->b1on_flags & 0x3) << MC13783_POWER_CONTROL_2_ON1BDBNC;
-	reg |= (pdata->b2on_flags & 0x3) << MC13783_POWER_CONTROL_2_ON2BDBNC;
-	reg |= (pdata->b3on_flags & 0x3) << MC13783_POWER_CONTROL_2_ON3BDBNC;
+	reg |= (pdata->b_on_flags[0] & 0x3) << MC13783_POWER_CONTROL_2_ON1BDBNC;
+	reg |= (pdata->b_on_flags[1] & 0x3) << MC13783_POWER_CONTROL_2_ON2BDBNC;
+	reg |= (pdata->b_on_flags[2] & 0x3) << MC13783_POWER_CONTROL_2_ON3BDBNC;
 
 	priv->pwr = pwr;
 	priv->mc13783 = mc13783;
 
 	mc13xxx_lock(mc13783);
 
-	if (pdata->b1on_flags & MC13783_BUTTON_ENABLE) {
-		priv->keymap[0] = pdata->b1on_key;
-		if (pdata->b1on_key != KEY_RESERVED)
-			__set_bit(pdata->b1on_key, pwr->keybit);
+	if (pdata->b_on_flags[0] & MC13783_BUTTON_ENABLE) {
+		priv->keymap[0] = pdata->b_on_key[0];
+		if (pdata->b_on_key[0] != KEY_RESERVED)
+			__set_bit(pdata->b_on_key[0], pwr->keybit);
 
-		if (pdata->b1on_flags & MC13783_BUTTON_POL_INVERT)
+		if (pdata->b_on_flags[0] & MC13783_BUTTON_POL_INVERT)
 			priv->flags |= MC13783_PWRB_B1_POL_INVERT;
 
-		if (pdata->b1on_flags & MC13783_BUTTON_RESET_EN)
+		if (pdata->b_on_flags[0] & MC13783_BUTTON_RESET_EN)
 			reg |= MC13783_POWER_CONTROL_2_ON1BRSTEN;
 
 		irq = platform_get_irq_byname(pdev, "b1on");
@@ -144,15 +144,15 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 		priv->irq[0] = irq;
 	}
 
-	if (pdata->b2on_flags & MC13783_BUTTON_ENABLE) {
-		priv->keymap[1] = pdata->b2on_key;
-		if (pdata->b2on_key != KEY_RESERVED)
-			__set_bit(pdata->b2on_key, pwr->keybit);
+	if (pdata->b_on_flags[1] & MC13783_BUTTON_ENABLE) {
+		priv->keymap[1] = pdata->b_on_key[1];
+		if (pdata->b_on_key[1] != KEY_RESERVED)
+			__set_bit(pdata->b_on_key[1], pwr->keybit);
 
-		if (pdata->b2on_flags & MC13783_BUTTON_POL_INVERT)
+		if (pdata->b_on_flags[1] & MC13783_BUTTON_POL_INVERT)
 			priv->flags |= MC13783_PWRB_B2_POL_INVERT;
 
-		if (pdata->b2on_flags & MC13783_BUTTON_RESET_EN)
+		if (pdata->b_on_flags[1] & MC13783_BUTTON_RESET_EN)
 			reg |= MC13783_POWER_CONTROL_2_ON2BRSTEN;
 
 		irq = platform_get_irq_byname(pdev, "b2on");
@@ -171,15 +171,15 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 		priv->irq[1] = irq;
 	}
 
-	if (pdata->b3on_flags & MC13783_BUTTON_ENABLE) {
-		priv->keymap[2] = pdata->b3on_key;
-		if (pdata->b3on_key != KEY_RESERVED)
-			__set_bit(pdata->b3on_key, pwr->keybit);
+	if (pdata->b_on_flags[2] & MC13783_BUTTON_ENABLE) {
+		priv->keymap[2] = pdata->b_on_key[2];
+		if (pdata->b_on_key[2] != KEY_RESERVED)
+			__set_bit(pdata->b_on_key[2], pwr->keybit);
 
-		if (pdata->b3on_flags & MC13783_BUTTON_POL_INVERT)
+		if (pdata->b_on_flags[2] & MC13783_BUTTON_POL_INVERT)
 			priv->flags |= MC13783_PWRB_B3_POL_INVERT;
 
-		if (pdata->b3on_flags & MC13783_BUTTON_RESET_EN)
+		if (pdata->b_on_flags[2] & MC13783_BUTTON_RESET_EN)
 			reg |= MC13783_POWER_CONTROL_2_ON3BRSTEN;
 
 		irq = platform_get_irq_byname(pdev, "b3on");
diff --git a/include/linux/mfd/mc13xxx.h b/include/linux/mfd/mc13xxx.h
index dd46fe424a80..4437ab80fcf8 100644
--- a/include/linux/mfd/mc13xxx.h
+++ b/include/linux/mfd/mc13xxx.h
@@ -181,12 +181,8 @@ struct mc13xxx_leds_platform_data {
 #define MC13783_BUTTON_RESET_EN		(1 << 4)
 
 struct mc13xxx_buttons_platform_data {
-	int b1on_flags;
-	unsigned short b1on_key;
-	int b2on_flags;
-	unsigned short b2on_key;
-	int b3on_flags;
-	unsigned short b3on_key;
+	int b_on_flags[3];
+	unsigned int b_on_key[3];
 };
 
 #define MC13783_TS_ATO_FIRST	false
-- 
2.39.5


^ permalink raw reply related

* [PATCH v6 5/6] Input: mc13783-pwrbutton: add OF support and drop platform_data
From: Alexander Kurz @ 2025-10-30 19:56 UTC (permalink / raw)
  To: Rob Herring, Krzysztof Kozlowski, Conor Dooley, Shawn Guo,
	Sascha Hauer, Pengutronix Kernel Team, Fabio Estevam,
	Dmitry Torokhov, Lee Jones, Dzmitry Sankouski,
	Griffin Kroah-Hartman, Mathieu Dubois-Briand, Heiko Stuebner,
	Dr . David Alan Gilbert, Job Sava, Alexandre Belloni,
	Uwe Kleine-König
  Cc: devicetree, imx, linux-arm-kernel, linux-kernel, linux-input,
	Alexander Kurz
In-Reply-To: <20251030195654.20142-1-akurz@blala.de>

Add OF support for the mc13783-pwrbutton so that it can be used with
modern DT based systems, dropping support for platform_data.

Signed-off-by: Alexander Kurz <akurz@blala.de>
---
 drivers/input/misc/mc13783-pwrbutton.c | 104 +++++++++++++++++++++----
 drivers/mfd/mc13xxx-core.c             |   4 -
 include/linux/mfd/mc13xxx.h            |  14 ----
 3 files changed, 88 insertions(+), 34 deletions(-)

diff --git a/drivers/input/misc/mc13783-pwrbutton.c b/drivers/input/misc/mc13783-pwrbutton.c
index 08618c59197f..0fa630adff19 100644
--- a/drivers/input/misc/mc13783-pwrbutton.c
+++ b/drivers/input/misc/mc13783-pwrbutton.c
@@ -27,6 +27,7 @@
 #include <linux/interrupt.h>
 #include <linux/platform_device.h>
 #include <linux/mfd/mc13783.h>
+#include <linux/property.h>
 #include <linux/sched.h>
 #include <linux/slab.h>
 
@@ -41,10 +42,20 @@ struct mc13783_pwrb {
 	struct mc13xxx *mc13783;
 	const struct mc13xxx_button_devtype *devtype;
 	int flags;
+	int b_on_flags[3];
+	unsigned int b_on_key[3];
 	unsigned short keymap[3];
 	int irq[3];
 };
 
+#define MC13783_BUTTON_DBNC_0MS         0
+#define MC13783_BUTTON_DBNC_30MS        1
+#define MC13783_BUTTON_DBNC_150MS       2
+#define MC13783_BUTTON_DBNC_750MS       3
+#define MC13783_BUTTON_ENABLE           (1 << 2)
+#define MC13783_BUTTON_POL_INVERT       (1 << 3)
+#define MC13783_BUTTON_RESET_EN         (1 << 4)
+
 #define MC13783_PWRB_B1_POL_INVERT	(1 << 0)
 #define MC13783_PWRB_B2_POL_INVERT	(1 << 1)
 #define MC13783_PWRB_B3_POL_INVERT	(1 << 2)
@@ -88,9 +99,69 @@ static irqreturn_t button_irq(int irq, void *_priv)
 	return IRQ_HANDLED;
 }
 
+static int mc13xxx_pwrbutton_parse_properties(struct platform_device *pdev,
+					      struct mc13783_pwrb *priv)
+{
+	struct fwnode_handle *child;
+	struct device *dev = &pdev->dev;
+	struct mc13xxx_button_devtype *devtype =
+		(struct mc13xxx_button_devtype *)platform_get_device_id(pdev)->driver_data;
+
+	struct fwnode_handle *parent __free(fwnode_handle) =
+		device_get_named_child_node(dev->parent, "buttons");
+	if (!parent)
+		return -ENODATA;
+
+	fwnode_for_each_named_child_node(parent, child, "onkey") {
+		u32 idx;
+		u8 dbnc = MC13783_BUTTON_DBNC_30MS;
+		u16 dbnc_ms;
+
+		if (fwnode_property_read_u32(child, "reg", &idx))
+			continue;
+
+		if (idx > devtype->button_id_max) {
+			dev_warn(dev, "reg out of range\n");
+			continue;
+		}
+
+		fwnode_property_read_u16(child, "debounce-delay-ms", &dbnc_ms);
+		switch (dbnc_ms) {
+		case 0:
+			dbnc = MC13783_BUTTON_DBNC_0MS;
+			break;
+		case 30:
+			dbnc = MC13783_BUTTON_DBNC_30MS;
+			break;
+		case 150:
+			dbnc = MC13783_BUTTON_DBNC_150MS;
+			break;
+		case 750:
+			dbnc = MC13783_BUTTON_DBNC_750MS;
+			break;
+		default:
+			dev_warn(dev, "invalid debounce-delay-ms value\n");
+			continue;
+		}
+
+		if (fwnode_property_read_u32(child, "linux,code", &priv->b_on_key[idx]))
+			continue;
+
+		if (fwnode_property_read_bool(child, "active-low"))
+			priv->b_on_flags[idx] |= MC13783_BUTTON_POL_INVERT;
+
+		if (fwnode_property_read_bool(child, "fsl,enable-reset"))
+			priv->b_on_flags[idx] |= MC13783_BUTTON_RESET_EN;
+
+		priv->b_on_flags[idx] |= MC13783_BUTTON_ENABLE | dbnc;
+	}
+
+	return 0;
+}
+
 static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 {
-	const struct mc13xxx_buttons_platform_data *pdata;
+	struct device *dev = &pdev->dev;
 	struct mc13xxx *mc13783 = dev_get_drvdata(pdev->dev.parent);
 	struct mc13xxx_button_devtype *devtype =
 		(struct mc13xxx_button_devtype *)pdev->id_entry->driver_data;
@@ -100,11 +171,8 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 	int reg = 0;
 	int irq = 0;
 
-	pdata = dev_get_platdata(&pdev->dev);
-	if (!pdata) {
-		dev_err(&pdev->dev, "missing platform data\n");
-		return -ENODEV;
-	}
+	if (!dev->parent->of_node)
+		return -ENODATA;
 
 	pwr = devm_input_allocate_device(&pdev->dev);
 	if (!pwr)
@@ -114,14 +182,18 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 	if (!priv)
 		return -ENOMEM;
 
-	if (devtype->button_id_max < 2 && pdata->b_on_flags[2] & 0x3) {
+	err = mc13xxx_pwrbutton_parse_properties(pdev, priv);
+	if (err)
+		return err;
+
+	if (devtype->button_id_max < 2 && priv->b_on_flags[2] & 0x3) {
 		dev_err(&pdev->dev, "button not supported\n");
 		return -ENODEV;
 	}
 
-	reg |= (pdata->b_on_flags[0] & 0x3) << MC13783_POWER_CONTROL_2_ON1BDBNC;
-	reg |= (pdata->b_on_flags[1] & 0x3) << MC13783_POWER_CONTROL_2_ON2BDBNC;
-	reg |= (pdata->b_on_flags[2] & 0x3) << MC13783_POWER_CONTROL_2_ON3BDBNC;
+	reg |= (priv->b_on_flags[0] & 0x3) << MC13783_POWER_CONTROL_2_ON1BDBNC;
+	reg |= (priv->b_on_flags[1] & 0x3) << MC13783_POWER_CONTROL_2_ON2BDBNC;
+	reg |= (priv->b_on_flags[2] & 0x3) << MC13783_POWER_CONTROL_2_ON3BDBNC;
 
 	priv->pwr = pwr;
 	priv->mc13783 = mc13783;
@@ -130,17 +202,17 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 	mc13xxx_lock(mc13783);
 
 	for (int i = 0; i < devtype->button_id_max; i++) {
-		if ((pdata->b_on_flags[i] & MC13783_BUTTON_ENABLE) == 0)
+		if ((priv->b_on_flags[i] & MC13783_BUTTON_ENABLE) == 0)
 			continue;
 
-		priv->keymap[i] = pdata->b_on_key[i];
-		if (pdata->b_on_key[i] != KEY_RESERVED)
-			__set_bit(pdata->b_on_key[i], pwr->keybit);
+		priv->keymap[i] = priv->b_on_key[i];
+		if (priv->b_on_key[i] != KEY_RESERVED)
+			__set_bit(priv->b_on_key[i], pwr->keybit);
 
-		if (pdata->b_on_flags[i] & MC13783_BUTTON_POL_INVERT)
+		if (priv->b_on_flags[i] & MC13783_BUTTON_POL_INVERT)
 			priv->flags |= (MC13783_PWRB_B1_POL_INVERT << i);
 
-		if (pdata->b_on_flags[i] & MC13783_BUTTON_RESET_EN)
+		if (priv->b_on_flags[i] & MC13783_BUTTON_RESET_EN)
 			reg |= (MC13783_POWER_CONTROL_2_ON1BRSTEN << i);
 
 		irq = platform_get_irq_byname(pdev, devtype->irq_name[i]);
diff --git a/drivers/mfd/mc13xxx-core.c b/drivers/mfd/mc13xxx-core.c
index c29974722704..9512136e821b 100644
--- a/drivers/mfd/mc13xxx-core.c
+++ b/drivers/mfd/mc13xxx-core.c
@@ -504,10 +504,6 @@ int mc13xxx_common_init(struct device *dev)
 			&pdata->regulators, sizeof(pdata->regulators));
 		mc13xxx_add_subdevice_pdata(mc13xxx, "%s-led",
 				pdata->leds, sizeof(*pdata->leds));
-		mc13xxx_add_subdevice_pdata_res(mc13xxx, "%s-pwrbutton",
-				pdata->buttons, sizeof(*pdata->buttons),
-				mc13xxx->variant->button_resources,
-				mc13xxx->variant->button_resources_size);
 		if (mc13xxx->flags & MC13XXX_USE_CODEC)
 			mc13xxx_add_subdevice_pdata(mc13xxx, "%s-codec",
 				pdata->codec, sizeof(*pdata->codec));
diff --git a/include/linux/mfd/mc13xxx.h b/include/linux/mfd/mc13xxx.h
index 71c7d3614d4c..ac3765df341d 100644
--- a/include/linux/mfd/mc13xxx.h
+++ b/include/linux/mfd/mc13xxx.h
@@ -174,19 +174,6 @@ struct mc13xxx_leds_platform_data {
 	u32 led_control[MAX_LED_CONTROL_REGS];
 };
 
-#define MC13783_BUTTON_DBNC_0MS		0
-#define MC13783_BUTTON_DBNC_30MS	1
-#define MC13783_BUTTON_DBNC_150MS	2
-#define MC13783_BUTTON_DBNC_750MS	3
-#define MC13783_BUTTON_ENABLE		(1 << 2)
-#define MC13783_BUTTON_POL_INVERT	(1 << 3)
-#define MC13783_BUTTON_RESET_EN		(1 << 4)
-
-struct mc13xxx_buttons_platform_data {
-	int b_on_flags[3];
-	unsigned int b_on_key[3];
-};
-
 #define MC13783_TS_ATO_FIRST	false
 #define MC13783_TS_ATO_EACH	true
 
@@ -219,7 +206,6 @@ struct mc13xxx_platform_data {
 
 	struct mc13xxx_regulator_platform_data regulators;
 	struct mc13xxx_leds_platform_data *leds;
-	struct mc13xxx_buttons_platform_data *buttons;
 	struct mc13xxx_ts_platform_data touch;
 	struct mc13xxx_codec_platform_data *codec;
 };
-- 
2.39.5


^ permalink raw reply related

* [PATCH v6 6/6] ARM: dts: imx53: add imx53-qsrb PMIC power button
From: Alexander Kurz @ 2025-10-30 19:56 UTC (permalink / raw)
  To: Rob Herring, Krzysztof Kozlowski, Conor Dooley, Shawn Guo,
	Sascha Hauer, Pengutronix Kernel Team, Fabio Estevam,
	Dmitry Torokhov, Lee Jones, Dzmitry Sankouski,
	Griffin Kroah-Hartman, Mathieu Dubois-Briand, Heiko Stuebner,
	Dr . David Alan Gilbert, Job Sava, Alexandre Belloni,
	Uwe Kleine-König
  Cc: devicetree, imx, linux-arm-kernel, linux-kernel, linux-input,
	Alexander Kurz
In-Reply-To: <20251030195654.20142-1-akurz@blala.de>

As described in the board hardware user guide IMX53RQSBRM-R.pdf, the
mc34708 pin PWRON1 is connected to a button "SW6"/"POWER", connecting
this line to GND.
Add support for the imx53-qsrb "POWER" button.

Signed-off-by: Alexander Kurz <akurz@blala.de>
---
 arch/arm/boot/dts/nxp/imx/imx53-qsrb.dts | 12 ++++++++++++
 1 file changed, 12 insertions(+)

diff --git a/arch/arm/boot/dts/nxp/imx/imx53-qsrb.dts b/arch/arm/boot/dts/nxp/imx/imx53-qsrb.dts
index 2f06ad61a766..2a6d28e9e8f8 100644
--- a/arch/arm/boot/dts/nxp/imx/imx53-qsrb.dts
+++ b/arch/arm/boot/dts/nxp/imx/imx53-qsrb.dts
@@ -139,6 +139,18 @@ vgen2_reg: vgen2 {
 				regulator-always-on;
 			};
 		};
+
+		buttons {
+			#address-cells = <1>;
+			#size-cells = <0>;
+			onkey@0 {
+				reg = <0>;
+				linux,code = <KEY_POWER>;
+				debounce-delay-ms = <30>;
+				active-low;
+				fsl,enable-reset;
+			};
+		};
 	};
 };
 
-- 
2.39.5


^ permalink raw reply related

* [PATCH v6 1/6] Input: mc13783-pwrbutton: use managed resources
From: Alexander Kurz @ 2025-10-30 19:56 UTC (permalink / raw)
  To: Rob Herring, Krzysztof Kozlowski, Conor Dooley, Shawn Guo,
	Sascha Hauer, Pengutronix Kernel Team, Fabio Estevam,
	Dmitry Torokhov, Lee Jones, Dzmitry Sankouski,
	Griffin Kroah-Hartman, Mathieu Dubois-Briand, Heiko Stuebner,
	Dr . David Alan Gilbert, Job Sava, Alexandre Belloni,
	Uwe Kleine-König
  Cc: devicetree, imx, linux-arm-kernel, linux-kernel, linux-input,
	Alexander Kurz
In-Reply-To: <20251030195654.20142-1-akurz@blala.de>

Use devres functionality to simplify resource freeing, dev.parent will
be set by devm_input_allocate_device().

Signed-off-by: Alexander Kurz <akurz@blala.de>
---
 drivers/input/misc/mc13783-pwrbutton.c | 28 ++++++++------------------
 1 file changed, 8 insertions(+), 20 deletions(-)

diff --git a/drivers/input/misc/mc13783-pwrbutton.c b/drivers/input/misc/mc13783-pwrbutton.c
index b83d762ae2e9..82434ea9cca5 100644
--- a/drivers/input/misc/mc13783-pwrbutton.c
+++ b/drivers/input/misc/mc13783-pwrbutton.c
@@ -21,6 +21,7 @@
 
 #include <linux/module.h>
 #include <linux/kernel.h>
+#include <linux/device.h>
 #include <linux/errno.h>
 #include <linux/input.h>
 #include <linux/interrupt.h>
@@ -102,18 +103,13 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 		return -ENODEV;
 	}
 
-	pwr = input_allocate_device();
-	if (!pwr) {
-		dev_dbg(&pdev->dev, "Can't allocate power button\n");
+	pwr = devm_input_allocate_device(&pdev->dev);
+	if (!pwr)
 		return -ENOMEM;
-	}
 
-	priv = kzalloc(sizeof(*priv), GFP_KERNEL);
-	if (!priv) {
-		err = -ENOMEM;
-		dev_dbg(&pdev->dev, "Can't allocate power button\n");
-		goto free_input_dev;
-	}
+	priv = devm_kzalloc(&pdev->dev, sizeof(*priv), GFP_KERNEL);
+	if (!priv)
+		return -ENOMEM;
 
 	reg |= (pdata->b1on_flags & 0x3) << MC13783_POWER_CONTROL_2_ON1BDBNC;
 	reg |= (pdata->b2on_flags & 0x3) << MC13783_POWER_CONTROL_2_ON2BDBNC;
@@ -139,7 +135,7 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 					  button_irq, "b1on", priv);
 		if (err) {
 			dev_dbg(&pdev->dev, "Can't request irq\n");
-			goto free_priv;
+			goto free_mc13xxx_lock;
 		}
 	}
 
@@ -187,7 +183,6 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 
 	pwr->name = "mc13783_pwrbutton";
 	pwr->phys = "mc13783_pwrbutton/input0";
-	pwr->dev.parent = &pdev->dev;
 
 	pwr->keycode = priv->keymap;
 	pwr->keycodemax = ARRAY_SIZE(priv->keymap);
@@ -218,12 +213,8 @@ static int mc13783_pwrbutton_probe(struct platform_device *pdev)
 	if (pdata->b1on_flags & MC13783_BUTTON_ENABLE)
 		mc13xxx_irq_free(mc13783, MC13783_IRQ_ONOFD1, priv);
 
-free_priv:
+free_mc13xxx_lock:
 	mc13xxx_unlock(mc13783);
-	kfree(priv);
-
-free_input_dev:
-	input_free_device(pwr);
 
 	return err;
 }
@@ -245,9 +236,6 @@ static void mc13783_pwrbutton_remove(struct platform_device *pdev)
 		mc13xxx_irq_free(priv->mc13783, MC13783_IRQ_ONOFD1, priv);
 
 	mc13xxx_unlock(priv->mc13783);
-
-	input_unregister_device(priv->pwr);
-	kfree(priv);
 }
 
 static struct platform_driver mc13783_pwrbutton_driver = {
-- 
2.39.5


^ permalink raw reply related

* [PATCH v2 3/3] ARM: dts: ti/omap: omap4-epson-embt2ws: add powerbutton
From: akemnade @ 2025-10-30 19:10 UTC (permalink / raw)
  To: Lee Jones, Rob Herring, Krzysztof Kozlowski, Conor Dooley,
	Andreas Kemnade, Dmitry Torokhov, Tony Lindgren, Kevin Hilman
  Cc: devicetree, linux-kernel, linux-input, linux-omap,
	Andreas Kemnade
In-Reply-To: <20251030-twl6030-button-v2-0-09653d05a2b1@kernel.org>

From: Andreas Kemnade <andreas@kemnade.info>

There is a power button connected to the PMIC, so describe it to be able
to power off the device in a convenient manner.

Signed-off-by: Andreas Kemnade <andreas@kemnade.info>
---
 arch/arm/boot/dts/ti/omap/omap4-epson-embt2ws.dts | 5 +++++
 1 file changed, 5 insertions(+)

diff --git a/arch/arm/boot/dts/ti/omap/omap4-epson-embt2ws.dts b/arch/arm/boot/dts/ti/omap/omap4-epson-embt2ws.dts
index c90f43cc2fae..673df1b693f2 100644
--- a/arch/arm/boot/dts/ti/omap/omap4-epson-embt2ws.dts
+++ b/arch/arm/boot/dts/ti/omap/omap4-epson-embt2ws.dts
@@ -229,6 +229,11 @@ rtc {
 			interrupts = <11>;
 		};
 
+		pwrbutton {
+			compatible = "ti,twl6030-pwrbutton";
+			interrupts = <0>;
+		};
+
 		ldo2: regulator-ldo2 {
 			compatible = "ti,twl6032-ldo2";
 			regulator-min-microvolt = <1000000>;

-- 
2.47.3


^ permalink raw reply related

* [PATCH v2 2/3] Input: twl4030 - add TWL603x power button
From: akemnade @ 2025-10-30 19:10 UTC (permalink / raw)
  To: Lee Jones, Rob Herring, Krzysztof Kozlowski, Conor Dooley,
	Andreas Kemnade, Dmitry Torokhov, Tony Lindgren, Kevin Hilman
  Cc: devicetree, linux-kernel, linux-input, linux-omap,
	Andreas Kemnade
In-Reply-To: <20251030-twl6030-button-v2-0-09653d05a2b1@kernel.org>

From: Andreas Kemnade <andreas@kemnade.info>

Like the TWL4030, these PMICs also have a power button feature, so extend
the TWL4030 power button driver. As the irqchip of the TWL6030 mfd driver
does not provide mask, unmask finctions, do it manually.

Signed-off-by: Andreas Kemnade <andreas@kemnade.info>
---
 drivers/input/misc/twl4030-pwrbutton.c | 61 +++++++++++++++++++++++++++++++---
 1 file changed, 57 insertions(+), 4 deletions(-)

diff --git a/drivers/input/misc/twl4030-pwrbutton.c b/drivers/input/misc/twl4030-pwrbutton.c
index f85cc289c053..f8c337f62393 100644
--- a/drivers/input/misc/twl4030-pwrbutton.c
+++ b/drivers/input/misc/twl4030-pwrbutton.c
@@ -25,22 +25,40 @@
 #include <linux/kernel.h>
 #include <linux/errno.h>
 #include <linux/input.h>
+#include <linux/bits.h>
 #include <linux/interrupt.h>
 #include <linux/of.h>
 #include <linux/platform_device.h>
 #include <linux/mfd/twl.h>
 
-#define PWR_PWRON_IRQ (1 << 0)
+#define PWR_PWRON_IRQ BIT(0)
 
-#define STS_HW_CONDITIONS 0xf
+#define STS_HW_CONDITIONS_4030 0xf
+#define STS_HW_CONDITIONS_6030 0x2
+
+struct twl_pwrbutton_chipdata {
+	u8 status_reg;
+	bool need_manual_irq;
+};
+
+struct twl_pwrbutton_chipdata twl4030_chipdata = {
+	STS_HW_CONDITIONS_4030,
+	false,
+};
+
+struct twl_pwrbutton_chipdata twl6030_chipdata = {
+	STS_HW_CONDITIONS_6030,
+	true,
+};
 
 static irqreturn_t powerbutton_irq(int irq, void *_pwr)
 {
 	struct input_dev *pwr = _pwr;
+	const struct twl_pwrbutton_chipdata *pdata = dev_get_drvdata(pwr->dev.parent);
 	int err;
 	u8 value;
 
-	err = twl_i2c_read_u8(TWL_MODULE_PM_MASTER, &value, STS_HW_CONDITIONS);
+	err = twl_i2c_read_u8(TWL_MODULE_PM_MASTER, &value, pdata->status_reg);
 	if (!err)  {
 		pm_wakeup_event(pwr->dev.parent, 0);
 		input_report_key(pwr, KEY_POWER, value & PWR_PWRON_IRQ);
@@ -55,10 +73,17 @@ static irqreturn_t powerbutton_irq(int irq, void *_pwr)
 
 static int twl4030_pwrbutton_probe(struct platform_device *pdev)
 {
+	const struct twl_pwrbutton_chipdata *pdata;
 	struct input_dev *pwr;
 	int irq = platform_get_irq(pdev, 0);
 	int err;
 
+	pdata = device_get_match_data(&pdev->dev);
+	if (!pdata)
+		return -EINVAL;
+
+	platform_set_drvdata(pdev, (void *)pdata);
+
 	pwr = devm_input_allocate_device(&pdev->dev);
 	if (!pwr) {
 		dev_err(&pdev->dev, "Can't allocate power button\n");
@@ -85,14 +110,41 @@ static int twl4030_pwrbutton_probe(struct platform_device *pdev)
 		return err;
 	}
 
+	if (pdata->need_manual_irq) {
+		err = twl6030_interrupt_unmask(0x01, REG_INT_MSK_LINE_A);
+		if (err < 0)
+			return err;
+
+		err = twl6030_interrupt_unmask(0x01, REG_INT_MSK_STS_A);
+		if (err < 0)
+			return err;
+	}
+
 	device_init_wakeup(&pdev->dev, true);
 
 	return 0;
 }
 
+static void twl4030_pwrbutton_remove(struct platform_device *pdev)
+{
+	const struct twl_pwrbutton_chipdata *pdata = platform_get_drvdata(pdev);
+
+	if (pdata->need_manual_irq) {
+		twl6030_interrupt_mask(0x01, REG_INT_MSK_LINE_A);
+		twl6030_interrupt_mask(0x01, REG_INT_MSK_STS_A);
+	}
+}
+
 #ifdef CONFIG_OF
 static const struct of_device_id twl4030_pwrbutton_dt_match_table[] = {
-       { .compatible = "ti,twl4030-pwrbutton" },
+	{
+		.compatible = "ti,twl4030-pwrbutton",
+		.data = &twl4030_chipdata,
+	},
+	{
+		.compatible = "ti,twl6030-pwrbutton",
+		.data = &twl6030_chipdata,
+	},
        {},
 };
 MODULE_DEVICE_TABLE(of, twl4030_pwrbutton_dt_match_table);
@@ -100,6 +152,7 @@ MODULE_DEVICE_TABLE(of, twl4030_pwrbutton_dt_match_table);
 
 static struct platform_driver twl4030_pwrbutton_driver = {
 	.probe		= twl4030_pwrbutton_probe,
+	.remove		= twl4030_pwrbutton_remove,
 	.driver		= {
 		.name	= "twl4030_pwrbutton",
 		.of_match_table = of_match_ptr(twl4030_pwrbutton_dt_match_table),

-- 
2.47.3


^ permalink raw reply related

* [PATCH v2 1/3] dt-bindings: mfd: twl: enable power button also for twl603x
From: akemnade @ 2025-10-30 19:10 UTC (permalink / raw)
  To: Lee Jones, Rob Herring, Krzysztof Kozlowski, Conor Dooley,
	Andreas Kemnade, Dmitry Torokhov, Tony Lindgren, Kevin Hilman
  Cc: devicetree, linux-kernel, linux-input, linux-omap,
	Andreas Kemnade
In-Reply-To: <20251030-twl6030-button-v2-0-09653d05a2b1@kernel.org>

From: Andreas Kemnade <andreas@kemnade.info>

TWL603x has also a power button function, so add the corresponding subnode.
As not in all cases there is a power button connected to the corresponding
pad of the TWL603x, the functionality can be disabled by
status = "disabled" or simply not adding the subnode.
To keep things simple, follow the established design pattern of using const
interrupts as used also by the other subdevices.

Signed-off-by: Andreas Kemnade <andreas@kemnade.info>
---
 Documentation/devicetree/bindings/mfd/ti,twl.yaml | 40 ++++++++++++++++++-----
 1 file changed, 32 insertions(+), 8 deletions(-)

diff --git a/Documentation/devicetree/bindings/mfd/ti,twl.yaml b/Documentation/devicetree/bindings/mfd/ti,twl.yaml
index 776b04e182cb..3527fee32cb0 100644
--- a/Documentation/devicetree/bindings/mfd/ti,twl.yaml
+++ b/Documentation/devicetree/bindings/mfd/ti,twl.yaml
@@ -55,6 +55,15 @@ allOf:
 
         gpadc: false
 
+        pwrbutton:
+          properties:
+            compatible:
+              const: ti,twl4030-pwrbutton
+            interrupts:
+              items:
+                - items:
+                    const: 8
+
         usb-comparator: false
 
   - if:
@@ -95,7 +104,14 @@ allOf:
             compatible:
               const: ti,twl6030-gpadc
 
-        pwrbutton: false
+        pwrbutton:
+          properties:
+            compatible:
+              const: ti,twl6030-pwrbutton
+            interrupts:
+              items:
+                - items:
+                    const: 0
 
         madc: false
 
@@ -146,7 +162,14 @@ allOf:
             compatible:
               const: ti,twl6032-gpadc
 
-        pwrbutton: false
+        pwrbutton:
+          properties:
+            compatible:
+              const: ti,twl6030-pwrbutton
+            interrupts:
+              items:
+                - items:
+                    const: 0
 
         madc: false
 
@@ -225,12 +248,8 @@ properties:
     additionalProperties: false
 
     properties:
-      compatible:
-        const: ti,twl4030-pwrbutton
-      interrupts:
-        items:
-          - items:
-              const: 8
+      compatible: true
+      interrupts: true
 
   watchdog:
     type: object
@@ -459,6 +478,11 @@ examples:
           #io-channel-cells = <1>;
         };
 
+        pwrbutton {
+          compatible = "ti,twl6030-pwrbutton";
+          interrupts = <0>;
+        };
+
         rtc {
           compatible = "ti,twl4030-rtc";
           interrupts = <8>;

-- 
2.47.3


^ permalink raw reply related

* [PATCH v2 0/3] mfd: twl603x: add power button
From: akemnade @ 2025-10-30 19:10 UTC (permalink / raw)
  To: Lee Jones, Rob Herring, Krzysztof Kozlowski, Conor Dooley,
	Andreas Kemnade, Dmitry Torokhov, Tony Lindgren, Kevin Hilman
  Cc: devicetree, linux-kernel, linux-input, linux-omap,
	Andreas Kemnade

Like the TWL4030, the TWL603x also has a power button feature,
so extend the TWL4030 power button driver to support TWL603x.

Signed-off-by: Andreas Kemnade <akemnade@kernel.org>
---
Changes in v2:
- integrate driver into existing TWL4030 driver
- improve commit messages
- Link to v1: https://lore.kernel.org/r/20251020-twl6030-button-v1-0-93e4644ac974@kernel.org

---
Andreas Kemnade (3):
      dt-bindings: mfd: twl: enable power button also for twl603x
      Input: twl4030 - add TWL603x power button
      ARM: dts: ti/omap: omap4-epson-embt2ws: add powerbutton

 Documentation/devicetree/bindings/mfd/ti,twl.yaml | 40 ++++++++++++---
 arch/arm/boot/dts/ti/omap/omap4-epson-embt2ws.dts |  5 ++
 drivers/input/misc/twl4030-pwrbutton.c            | 61 +++++++++++++++++++++--
 3 files changed, 94 insertions(+), 12 deletions(-)
---
base-commit: 3a8660878839faadb4f1a6dd72c3179c1df56787
change-id: 20251020-twl6030-button-83d759b060e6

Best regards,
--  
Andreas Kemnade <akemnade@kernel.org>


^ permalink raw reply

* Re: [PATCH] HID: nintendo: Reduce JC_SUBCMD_RATE_MAX_ATTEMPTS
From: Daniel Ogorchock @ 2025-10-30 17:44 UTC (permalink / raw)
  To: Willy Huang; +Cc: Jiri Kosina, Benjamin Tissoires, linux-input, linux-kernel
In-Reply-To: <20251030063704.903998-1-willyhuang@google.com>

Hi Willy,

On Thu, Oct 30, 2025 at 2:37 AM Willy Huang <willyhuang@google.com> wrote:
>
> The JC_SUBCMD_RATE_MAX_ATTEMPTS constant is currently set to 500.
> In a worst-case scenario where all attempts consistently fail, this could
> cause the loop to block for up to 60000 ms (500 * 60ms * 2, including the
> additional retry after a timeout).
>
> This change lowers the maximum potential blocking time to 3000 ms
> (25 * 60ms * 2), improving system responsiveness and efficiency.
>
> Signed-off-by: Willy Huang <willyhuang@google.com>
> ---
>  drivers/hid/hid-nintendo.c | 2 +-
>  1 file changed, 1 insertion(+), 1 deletion(-)
>
> diff --git a/drivers/hid/hid-nintendo.c b/drivers/hid/hid-nintendo.c
> index c2849a541f65..342cd6893502 100644
> --- a/drivers/hid/hid-nintendo.c
> +++ b/drivers/hid/hid-nintendo.c
> @@ -819,7 +819,7 @@ static void joycon_wait_for_input_report(struct joycon_ctlr *ctlr)
>  #define JC_INPUT_REPORT_MAX_DELTA      17
>  #define JC_SUBCMD_TX_OFFSET_MS         4
>  #define JC_SUBCMD_VALID_DELTA_REQ      3
> -#define JC_SUBCMD_RATE_MAX_ATTEMPTS    500
> +#define JC_SUBCMD_RATE_MAX_ATTEMPTS    25
>  #define JC_SUBCMD_RATE_LIMITER_USB_MS  20
>  #define JC_SUBCMD_RATE_LIMITER_BT_MS   60
>  #define JC_SUBCMD_RATE_LIMITER_MS(ctlr)        ((ctlr)->hdev->bus == BUS_USB ? JC_SUBCMD_RATE_LIMITER_USB_MS : JC_SUBCMD_RATE_LIMITER_BT_MS)
> --
> 2.51.1.851.g4ebd6896fd-goog
>

Thanks for the patch. Seems like a good change.

Reviewed-by: Daniel J. Ogorchock <djogorchock@gmail.com>

- Daniel

^ permalink raw reply

* Re: [PATCH 02/10] dt-bindings: display: panel: ronbo,rb070d30: add port property
From: Josua Mayer @ 2025-10-30 16:57 UTC (permalink / raw)
  To: Krzysztof Kozlowski
  Cc: Rob Herring, Krzysztof Kozlowski, Conor Dooley, Shawn Guo,
	Neil Armstrong, Jessica Zhang, David Airlie, Simona Vetter,
	Maarten Lankhorst, Maxime Ripard, Thomas Zimmermann,
	Dmitry Torokhov, Sascha Hauer, Pengutronix Kernel Team,
	Fabio Estevam, Jon Nettleton, Mikhail Anikin, Yazan Shhady,
	devicetree@vger.kernel.org, linux-kernel@vger.kernel.org,
	dri-devel@lists.freedesktop.org, linux-input@vger.kernel.org,
	imx@lists.linux.dev, linux-arm-kernel@lists.infradead.org
In-Reply-To: <a5e9f1ec-69f0-4f91-9dd1-387b3e4ace5b@kernel.org>

Am 28.10.25 um 17:23 schrieb Krzysztof Kozlowski:

> On 28/10/2025 13:01, Josua Mayer wrote:
>> Am 28.10.25 um 10:03 schrieb Krzysztof Kozlowski:
>>> On Mon, Oct 27, 2025 at 06:48:11PM +0100, Josua Mayer wrote:
>>>> port property is used for linking dsi ports with dsi panels.
>>>> Add port property to ronbo dsi panel binding.
>>>>
>>>> Signed-off-by: Josua Mayer <josua@solid-run.com>
>>>> ---
>>>>  Documentation/devicetree/bindings/display/panel/ronbo,rb070d30.yaml | 1 +
>>>>  1 file changed, 1 insertion(+)
>>>>
>>>> diff --git a/Documentation/devicetree/bindings/display/panel/ronbo,rb070d30.yaml b/Documentation/devicetree/bindings/display/panel/ronbo,rb070d30.yaml
>>>> index 04f86e0cbac91..a2dc67a87fa3b 100644
>>>> --- a/Documentation/devicetree/bindings/display/panel/ronbo,rb070d30.yaml
>>>> +++ b/Documentation/devicetree/bindings/display/panel/ronbo,rb070d30.yaml
>>>> @@ -13,6 +13,7 @@ properties:
>>>>    compatible:
>>>>      const: ronbo,rb070d30
>>>>  
>>>> +  port: true
>>> Port is never the second property. Please look at other bindings.
>> Some places did that ...., e.g.:
> Yes, finding few outliers is not a good argument. Especially binding
> from 2020 where many conventions did not exist.
>
> Look at the most of the bindings or the recently reviewed.
>
>> Documentation/devicetree/bindings/display/panel/mantix,mlaf057we51-x.yaml-  compatible:
>> Documentation/devicetree/bindings/display/panel/mantix,mlaf057we51-x.yaml-    enum:
>> Documentation/devicetree/bindings/display/panel/mantix,mlaf057we51-x.yaml-      - mantix,mlaf057we51-x
>> Documentation/devicetree/bindings/display/panel/mantix,mlaf057we51-x.yaml-      - ys,ys57pss36bh5gq
>> Documentation/devicetree/bindings/display/panel/mantix,mlaf057we51-x.yaml-
>> Documentation/devicetree/bindings/display/panel/mantix,mlaf057we51-x.yaml:  port: true
>> Documentation/devicetree/bindings/display/panel/mantix,mlaf057we51-x.yaml-  reg:
>>
>>> Also, missing blank line
>> Okay
>>>  and missing top-level ref for panel-common.
>> Does this impact which properties are considered required / valid?
>>
>> Ronbo panel has different gpios / names from panel-common:
>>
>> power-gpios: similar to panel-common enable-gpios
>> reset-gpios: common to panel-common
>> shlr-gpios: special to ronbo
>> updn-gpios: special to ronbo
>> vcc-lcd-supply: similar to panel-common power-supply
>> backlight: common to panel-common
>>
>> There are some other gpios in panel-common that ronbo panel does not use.
> Just use the properties from the common schema where applicable.
>
>> Is the above relevant?
>> Would it be correct adding the below?:
>>
>>  maintainers:
>>    - Maxime Ripard <mripard@kernel.org>
>>  
>> +allOf:
>> +  - $ref: panel-common.yaml#
>> +
>>  properties:
>>    compatible:
>>      const: ronbo,rb070d30
>>
>> @@ -48,5 +50,6 @@ required:
>>    - shlr-gpios
>>    - updn-gpios
>>    - vcc-lcd-supply
>> +  - port
>>  
>>  additionalProperties: false
> unevaluatedProperties:false now.
Does this mean to have both additionalProperties and unevaluatedProperties,
or just the latter?

^ permalink raw reply

* Re: [PATCH 10/10] arm64: dts: add description for solidrun i.mx8mm som and evb
From: Josua Mayer @ 2025-10-30 16:47 UTC (permalink / raw)
  To: Rob Herring, Krzysztof Kozlowski, Conor Dooley, Shawn Guo,
	Neil Armstrong, Jessica Zhang, David Airlie, Simona Vetter,
	Maarten Lankhorst, Maxime Ripard, Thomas Zimmermann,
	Dmitry Torokhov, Sascha Hauer, Pengutronix Kernel Team,
	Fabio Estevam
  Cc: Jon Nettleton, Mikhail Anikin, Yazan Shhady,
	devicetree@vger.kernel.org, linux-kernel@vger.kernel.org,
	dri-devel@lists.freedesktop.org, linux-input@vger.kernel.org,
	imx@lists.linux.dev, linux-arm-kernel@lists.infradead.org
In-Reply-To: <20251027-imx8mp-hb-iiot-v1-10-683f86357818@solid-run.com>

Am 27.10.25 um 18:48 schrieb Josua Mayer:
> Add description for the SolidRun i.MX8M Mini SoM on HummingBoard Ripple.
>
> The SoM features:
> - 1Gbps Ethernet with PHY
> - eMMC
> - 1/2GB DDR
> - NPU (assembly option)
> - WiFi + Bluetooth
>
> The HummingBoard Ripple features:
> - 2x USB-2.0 Type-A connector
> - 1Gbps RJ45 Ethernet with PoE
> - microSD connector
> - microHDMI connector
> - mpcie connector with USB-2.0 interface + SIM card holder
> - microUSB connector for console (using fdtdi chip)
> - RTC with backup battery
>
> Signed-off-by: Josua Mayer <josua@solid-run.com>
> ---
>  arch/arm64/boot/dts/freescale/Makefile             |   2 +
>  .../dts/freescale/imx8mm-hummingboard-ripple.dts   | 335 +++++++++++++++++
>  arch/arm64/boot/dts/freescale/imx8mm-sr-som.dtsi   | 395 +++++++++++++++++++++
>  3 files changed, 732 insertions(+)
>
> diff --git a/arch/arm64/boot/dts/freescale/Makefile b/arch/arm64/boot/dts/freescale/Makefile
> index c56137097da3b..3fbc8a1a1bf6e 100644
> --- a/arch/arm64/boot/dts/freescale/Makefile
> +++ b/arch/arm64/boot/dts/freescale/Makefile
> @@ -124,6 +124,8 @@ imx8mm-evk-pcie-ep-dtbs += imx8mm-evk.dtb imx-pcie0-ep.dtbo
>  imx8mm-evkb-pcie-ep-dtbs += imx8mm-evkb.dtb imx-pcie0-ep.dtbo
>  dtb-$(CONFIG_ARCH_MXC) += imx8mm-evk-pcie-ep.dtb imx8mm-evkb-pcie-ep.dtb
>  
> +dtb-$(CONFIG_ARCH_MXC) += imx8mm-hummingboard-ripple.dtb
> +DTC_FLAGS_imx8mm-hummingboard-ripple += -@
>  dtb-$(CONFIG_ARCH_MXC) += imx8mm-icore-mx8mm-ctouch2.dtb
>  dtb-$(CONFIG_ARCH_MXC) += imx8mm-icore-mx8mm-edimm2.2.dtb
>  dtb-$(CONFIG_ARCH_MXC) += imx8mm-iot-gateway.dtb
> diff --git a/arch/arm64/boot/dts/freescale/imx8mm-hummingboard-ripple.dts b/arch/arm64/boot/dts/freescale/imx8mm-hummingboard-ripple.dts
> new file mode 100644
> index 0000000000000..110e7ff1ff135
> --- /dev/null
> +++ b/arch/arm64/boot/dts/freescale/imx8mm-hummingboard-ripple.dts
cut
> +&usbotg2 {
> +	status = "okay";
> +	dr_mode = "host";
> +	vbus-supply = <&vbus1>;
> +	#address-cells = <1>;
> +	#size-cells = <0>;
> +	pinctrl-names = "default";
> +	pinctrl-0 = <&usb_hub_pins>;
> +
> +	hub_2_0: hub@1 {
> +		compatible = "usb4b4,6502", "usb4b4,6506";
> +		reg = <1>;
> +		peer-hub = <&hub_3_0>;
> +		reset-gpios = <&gpio4 30 GPIO_ACTIVE_LOW>;
> +		vdd-supply = <&v_1_2>;
> +		vdd2-supply = <&v_3_3>;
> +	};
> +
> +	/* this device is not visible because host supports 2.0 only */
> +	hub_3_0: hub@2 {
> +		compatible = "usb4b4,6500", "usb4b4,6504";
> +		reg = <2>;
> +		peer-hub = <&hub_2_0>;
> +		reset-gpios = <&gpio4 30 GPIO_ACTIVE_LOW>;
> +		vdd-supply = <&v_1_2>;
> +		vdd2-supply = <&v_3_3>;
> +	};
> +};
Is it correct to specify both usb-2.0 and usb-3.0 instances of the
hub even though the host is usb-2.0 only?

^ permalink raw reply

* Re: [PATCH 08/10] arm64: dts: add description for solidrun imx8mp hummingboard-iiot
From: Josua Mayer @ 2025-10-30 16:44 UTC (permalink / raw)
  To: Rob Herring, Krzysztof Kozlowski, Conor Dooley, Shawn Guo,
	Neil Armstrong, Jessica Zhang, David Airlie, Simona Vetter,
	Maarten Lankhorst, Maxime Ripard, Thomas Zimmermann,
	Dmitry Torokhov, Sascha Hauer, Pengutronix Kernel Team,
	Fabio Estevam, Jon Nettleton, Mikhail Anikin, Yazan Shhady,
	devicetree@vger.kernel.org, linux-kernel@vger.kernel.org,
	dri-devel@lists.freedesktop.org, linux-input@vger.kernel.org,
	imx@lists.linux.dev, linux-arm-kernel@lists.infradead.org,
	linux-leds@vger.kernel.org
In-Reply-To: <20251029-jittery-ambiguity-14e03ad2f0df@thorsis.com>

Hi Alex,

Am 29.10.25 um 10:23 schrieb Alexander Dahl:
> Hello Josua,
>
> Am Tue, Oct 28, 2025 at 12:24:36PM +0000 schrieb Josua Mayer:
>> Am 27.10.25 um 18:48 schrieb Josua Mayer:
>>
>>> Add description for the SolidRun i.MX8MP HummingBoard IIoT.
>>> The board is a new design around the i.MX8MP System on Module, not
>>> sharing much with previous HummingBoards.
>>>
>>> It comes with some common features:
>>> - 3x USB-3.0 Type A connector
>>> - 2x 1Gbps RJ45 Ethernet
>>> - USB Type-C Console Port
>>> - microSD connector
>>> - RTC with backup battery
>>> - RGB Status LED
>>> - 1x M.2 M-Key connector with PCI-E Gen. 3 x1
>>> - 1x M.2 B-Key connector with USB-2.0/3.0 + SIM card holder
>>> - 1x LVDS Display Connector
>>> - 1x DSI Display Connector
>>> - GPIO header
>>> - 2x RS232/RS485 ports (configurable)
>>> - 2x CAN
>>>
>>> In addition there is a board-to-board expansion connector to support
>>> custom daughter boards with access to SPI, a range of GPIOs and -
>>> notably - CAN and UART. Both 2x CAN and 2x UART can be muxed either
>>> to this b2b connector, or a termianl block connector on the base board.
>>>
>>> The routing choice for UART and CAN is expressed through gpio
>>> mux-controllers in DT and can be changed by applying dtb addons.
>>>
>>> Four dtb addons are provided:
>>>
>>> - dsi panel Winstar WJ70N3TYJHMNG0
>>> - lvds panel Winstar WF70A8SYJHLNGA
>>> - RS485 on UART port "A" (default rs232)
>>> - RS485 on UART port "B" (default rs232)
>>>
>>> Signed-off-by: Josua Mayer <josua@solid-run.com>
>>> ---
>>>  arch/arm64/boot/dts/freescale/Makefile             |   6 +
>>>  ...hummingboard-iiot-panel-dsi-WJ70N3TYJHMNG0.dtso |  70 ++
>>>  ...ummingboard-iiot-panel-lvds-WF70A8SYJHLNGA.dtso | 105 +++
>>>  .../imx8mp-hummingboard-iiot-rs485-a.dtso          |  18 +
>>>  .../imx8mp-hummingboard-iiot-rs485-b.dtso          |  18 +
>>>  .../dts/freescale/imx8mp-hummingboard-iiot.dts     | 710 +++++++++++++++++++++
>>>  6 files changed, 927 insertions(+)
>> cut
>>> diff --git a/arch/arm64/boot/dts/freescale/imx8mp-hummingboard-iiot.dts b/arch/arm64/boot/dts/freescale/imx8mp-hummingboard-iiot.dts
>>> new file mode 100644
>>> index 0000000000000..2e4cb676bc9da
>>> --- /dev/null
>>> +++ b/arch/arm64/boot/dts/freescale/imx8mp-hummingboard-iiot.dts
>> cut
>>> +	led-controller@30 {
>>> +		compatible = "ti,lp5562";
>>> +		reg = <0x30>;
>>> +		/* use internal clock, could use external generated by rtc */
>>> +		clock-mode = /bits/ 8 <1>;
>>> +		#address-cells = <1>;
>>> +		#size-cells = <0>;
>>> +
>>> +		multi-led@0 {
>>> +			reg = <0x0>;
>>> +			color = <LED_COLOR_ID_RGB>;
>>> +			#address-cells = <1>;
>>> +			#size-cells = <0>;
>>> +
>>> +			led@0 {
>>> +				reg = <0x0>;
>>> +				color = <LED_COLOR_ID_RED>;
>>> +				led-cur = /bits/ 8 <0x32>;
>>> +				max-cur = /bits/ 8 <0x64>;
>>> +			};
>>> +
>>> +			led@1 {
>>> +				reg = <0x1>;
>>> +				color = <LED_COLOR_ID_GREEN>;
>>> +				led-cur = /bits/ 8 <0x19>;
>>> +				max-cur = /bits/ 8 <0x32>;
>>> +			};
>>> +
>>> +			led@2 {
>>> +				reg = <0x2>;
>>> +				color = <LED_COLOR_ID_BLUE>;
>>> +				led-cur = /bits/ 8 <0x19>;
>>> +				max-cur = /bits/ 8 <0x32>;
>>> +			};
>>> +		};
>>> +
>>> +		led@3 {
>>> +			reg = <3>;
>>> +			chan-name = "D8";
>> chan-name gives the led the name D6 in sysfs.
>>
>> The bindings do not allow however setting chan-name on
>> the multi-led, and it has an auto-generated name in sysfs.
>>
>> Am I missing something? Can multi-leds have a custom name?
> The sysfs names are auto-generated based on the attributes "color",
> "function", and "label" with the last being discouraged for new
> designs.
Thank you for reminding me of this one!
> If the "ti,lp5562" driver does nothing special,you could
> add "function" to the multi-led node and see if that fits your needs.
The board is not a complete product by itself so we have not chosen
a specific function for each led.
Therefore only color and label are actually applicable.

After testing on v6.18-rc1 I can state that leds-lp5562 driver does
something special - function and label properties do not have any
impact on the names in sysfs.

However I could set label on both LEDs regardless?

>
> Adding linux-leds to Cc, because this is a LED related question.
>
> Greets
> Alex
>
>> In v6.6 leds-lp5562 driver if I set in each multi-led led@[0-2] sub-node
>> chan-name to the same string "D7" - then the sysfs name becomes D7.
>>
>>> +			color = <LED_COLOR_ID_GREEN>;
>>> +			led-cur = /bits/ 8 <0x19>;
>>> +			max-cur = /bits/ 8 <0x64>;
>>> +		};
>>> +	};

^ permalink raw reply

* [PATCH] HID: hid-input: Extend Elan ignore battery quirk to USB
From: Mario Limonciello (AMD) @ 2025-10-30 16:06 UTC (permalink / raw)
  To: mario.limonciello, jikos, bentiss
  Cc: Mario Limonciello (AMD), Hans de Goede, André Barata,
	linux-input

USB Elan devices have the same problem as the I2C ones with a fake
battery device showing up.

Reviewed-by: Hans de Goede <hansg@kernel.org>
Reported-by: André Barata <andretiagob@protonmail.com>
Closes: https://bugzilla.kernel.org/show_bug.cgi?id=220722
Signed-off-by: Mario Limonciello (AMD) <superm1@kernel.org>
---
 drivers/hid/hid-input.c | 5 +++--
 1 file changed, 3 insertions(+), 2 deletions(-)

diff --git a/drivers/hid/hid-input.c b/drivers/hid/hid-input.c
index e56e7de532799..2bbb645c2ff41 100644
--- a/drivers/hid/hid-input.c
+++ b/drivers/hid/hid-input.c
@@ -399,10 +399,11 @@ static const struct hid_device_id hid_battery_quirks[] = {
 	{ HID_I2C_DEVICE(USB_VENDOR_ID_ELAN, I2C_DEVICE_ID_CHROMEBOOK_TROGDOR_POMPOM),
 	  HID_BATTERY_QUIRK_AVOID_QUERY },
 	/*
-	 * Elan I2C-HID touchscreens seem to all report a non present battery,
-	 * set HID_BATTERY_QUIRK_IGNORE for all Elan I2C-HID devices.
+	 * Elan HID touchscreens seem to all report a non present battery,
+	 * set HID_BATTERY_QUIRK_IGNORE for all Elan I2C and USB HID devices.
 	 */
 	{ HID_I2C_DEVICE(USB_VENDOR_ID_ELAN, HID_ANY_ID), HID_BATTERY_QUIRK_IGNORE },
+	{ HID_USB_DEVICE(USB_VENDOR_ID_ELAN, HID_ANY_ID), HID_BATTERY_QUIRK_IGNORE },
 	{}
 };
 
-- 
2.43.0


^ permalink raw reply related

* [PATCH 2/2] HID: multitouch: Toggle touch surface on Elan touchpad on lid event
From: Jonathan Denose @ 2025-10-30 14:10 UTC (permalink / raw)
  To: Dmitry Torokhov, Jiri Kosina, Benjamin Tissoires
  Cc: linux-input, linux-kernel, Jonathan Denose
In-Reply-To: <20251030-lid-switch-notifier-v1-0-c58dc9b1439d@google.com>

Many touchpad modules have a pin which is expected to be connected to the
lid angle sensor in laptops. The pin sends a signal to the touchpad module
about the lid state and each touchpad vendor handles this notification in
their firmware.

The Elan touchpad with VID 323b does not always have this aforementioned
pin, which then causes interference between the lid and the touchpad when
the lid is closed. This interference causes a few seconds delay before the
touchpad works again, or it causes it to be come completely unresponsive.
To circumvent this hardware issue in software, implement a device quirk
which will allow the hid-multitouch driver to register a notifier_block
to listen for lid switch events and turn the touchpad surface on and off
triggering a recalibration of the touchpad. This recalibration resolves
interference issues when the lid is closed.

Signed-off-by: Jonathan Denose <jdenose@google.com>
---
 drivers/hid/hid-multitouch.c | 32 +++++++++++++++++++++++++++++++-
 1 file changed, 31 insertions(+), 1 deletion(-)

diff --git a/drivers/hid/hid-multitouch.c b/drivers/hid/hid-multitouch.c
index 2879e65cf303b1456311ac06115adda5a78a2600..feb0a0b65b6355cc412fcf8ea88132dc5bdc6a26 100644
--- a/drivers/hid/hid-multitouch.c
+++ b/drivers/hid/hid-multitouch.c
@@ -35,6 +35,7 @@
 #include <linux/device.h>
 #include <linux/hid.h>
 #include <linux/module.h>
+#include <linux/notifier.h>
 #include <linux/slab.h>
 #include <linux/input/mt.h>
 #include <linux/jiffies.h>
@@ -76,6 +77,7 @@ MODULE_LICENSE("GPL");
 #define MT_QUIRK_DISABLE_WAKEUP		BIT(21)
 #define MT_QUIRK_ORIENTATION_INVERT	BIT(22)
 #define MT_QUIRK_APPLE_TOUCHBAR		BIT(23)
+#define MT_QUIRK_REGISTER_INPUT_NOTIFIER BIT(24)
 
 #define MT_INPUTMODE_TOUCHSCREEN	0x02
 #define MT_INPUTMODE_TOUCHPAD		0x03
@@ -183,6 +185,8 @@ struct mt_device {
 	struct list_head reports;
 };
 
+static struct hid_device *lid_notify_hdev;
+
 static void mt_post_parse_default_settings(struct mt_device *td,
 					   struct mt_application *app);
 static void mt_post_parse(struct mt_device *td, struct mt_application *app);
@@ -227,6 +231,7 @@ static void mt_post_parse(struct mt_device *td, struct mt_application *app);
 #define MT_CLS_SMART_TECH			0x0113
 #define MT_CLS_APPLE_TOUCHBAR			0x0114
 #define MT_CLS_SIS				0x0457
+#define MT_CLS_REGISTER_INPUT_NOTIFIER 0x0115
 
 #define MT_DEFAULT_MAXCONTACT	10
 #define MT_MAX_MAXCONTACT	250
@@ -327,7 +332,9 @@ static const struct mt_class mt_classes[] = {
 			MT_QUIRK_CONTACT_CNT_ACCURATE |
 			MT_QUIRK_WIN8_PTP_BUTTONS,
 		.export_all_inputs = true },
-
+	{ .name = MT_CLS_REGISTER_INPUT_NOTIFIER,
+		.quirks = MT_QUIRK_REGISTER_INPUT_NOTIFIER,
+		.export_all_inputs = true },
 	/*
 	 * vendor specific classes
 	 */
@@ -1840,6 +1847,20 @@ static void mt_expired_timeout(struct timer_list *t)
 	clear_bit_unlock(MT_IO_FLAGS_RUNNING, &td->mt_io_flags);
 }
 
+static int mt_input_notifier(struct notifier_block *nb, unsigned long action, void *dev)
+{
+	if (action == LID_SWITCH_CLOSE)
+		mt_set_modes(lid_notify_hdev, HID_LATENCY_NORMAL, TOUCHPAD_REPORT_NONE);
+	else if (action == LID_SWITCH_OPEN)
+		mt_set_modes(lid_notify_hdev, HID_LATENCY_NORMAL, TOUCHPAD_REPORT_ALL);
+
+	return 0;
+}
+
+static struct notifier_block mt_notifier_block = {
+	.notifier_call = mt_input_notifier
+};
+
 static int mt_probe(struct hid_device *hdev, const struct hid_device_id *id)
 {
 	int ret, i;
@@ -1920,6 +1941,11 @@ static int mt_probe(struct hid_device *hdev, const struct hid_device_id *id)
 	if (hdev->vendor == USB_VENDOR_ID_SIS_TOUCH)
 		hdev->quirks |= HID_QUIRK_NOGET;
 
+	if (mtclass->quirks & MT_CLS_REGISTER_INPUT_NOTIFIER) {
+		lid_notify_hdev = hdev;
+		register_input_notifier(&mt_notifier_block);
+	}
+
 	ret = hid_hw_start(hdev, HID_CONNECT_DEFAULT);
 	if (ret)
 		return ret;
@@ -2150,6 +2176,10 @@ static const struct hid_device_id mt_devices[] = {
 		HID_DEVICE(BUS_I2C, HID_GROUP_MULTITOUCH_WIN_8,
 			USB_VENDOR_ID_ELAN, 0x32ae) },
 
+	{ .driver_data = MT_CLS_REGISTER_INPUT_NOTIFIER,
+		HID_DEVICE(BUS_I2C, HID_GROUP_MULTITOUCH_WIN_8,
+			USB_VENDOR_ID_ELAN, 0x323b) },
+
 	/* Elitegroup panel */
 	{ .driver_data = MT_CLS_SERIAL,
 		MT_USB_DEVICE(USB_VENDOR_ID_ELITEGROUP,

-- 
2.51.1.851.g4ebd6896fd-goog


^ permalink raw reply related

* [PATCH 1/2] Input: Create input notifier chain in input.c
From: Jonathan Denose @ 2025-10-30 14:10 UTC (permalink / raw)
  To: Dmitry Torokhov, Jiri Kosina, Benjamin Tissoires
  Cc: linux-input, linux-kernel, Jonathan Denose
In-Reply-To: <20251030-lid-switch-notifier-v1-0-c58dc9b1439d@google.com>

To expose input events to other kernel modules, add a blocking notifier
chain. Publish LID_SWITCH_OPEN/LID_SWITCH_CLOSE events through this
notifier chain when input_handle_event detects events signaling the lid
switch has opened or closed.

Additionally, export a function which allows other kernel modules to
register notifier_block structs against this notifier chain.

Signed-off-by: Jonathan Denose <jdenose@google.com>
---
 drivers/input/input.c | 13 +++++++++++++
 include/linux/input.h |  7 +++++++
 2 files changed, 20 insertions(+)

diff --git a/drivers/input/input.c b/drivers/input/input.c
index a500e1e276c211d1146dbfea421a3402084007f8..b342b1ff138ccc58d4623edcf1152bd85d7054bf 100644
--- a/drivers/input/input.c
+++ b/drivers/input/input.c
@@ -26,6 +26,7 @@
 #include <linux/kstrtox.h>
 #include <linux/mutex.h>
 #include <linux/rcupdate.h>
+#include <linux/notifier.h>
 #include "input-compat.h"
 #include "input-core-private.h"
 #include "input-poller.h"
@@ -62,6 +63,8 @@ static const unsigned int input_max_code[EV_CNT] = {
 	[EV_FF] = FF_MAX,
 };
 
+static struct blocking_notifier_head input_notifier_head;
+
 static inline int is_event_supported(unsigned int code,
 				     unsigned long *bm, unsigned int max)
 {
@@ -367,10 +370,20 @@ void input_handle_event(struct input_dev *dev,
 		if (type != EV_SYN)
 			add_input_randomness(type, code, value);
 
+		if (type == EV_SW && code == SW_LID && !value)
+			blocking_notifier_call_chain(&input_notifier_head, value ?
+				LID_SWITCH_CLOSE : LID_SWITCH_OPEN, dev);
+
 		input_event_dispose(dev, disposition, type, code, value);
 	}
 }
 
+int register_input_notifier(struct notifier_block *notifier)
+{
+	return blocking_notifier_chain_register(&input_notifier_head, notifier);
+}
+EXPORT_SYMBOL(register_input_notifier);
+
 /**
  * input_event() - report new input event
  * @dev: device that generated the event
diff --git a/include/linux/input.h b/include/linux/input.h
index 7d7cb0593a63e93c4906c49cde430188db2d1ab5..e940aff8843a0afc693c60a252d6b0dbcb3476c4 100644
--- a/include/linux/input.h
+++ b/include/linux/input.h
@@ -42,6 +42,11 @@ enum input_clock_type {
 	INPUT_CLK_MAX
 };
 
+enum input_notify_event_type {
+	LID_SWITCH_OPEN,
+	LID_SWITCH_CLOSE
+};
+
 /**
  * struct input_dev - represents an input device
  * @name: name of the device
@@ -431,6 +436,8 @@ int input_flush_device(struct input_handle *handle, struct file *file);
 void input_set_timestamp(struct input_dev *dev, ktime_t timestamp);
 ktime_t *input_get_timestamp(struct input_dev *dev);
 
+int register_input_notifier(struct notifier_block *notifier);
+
 void input_event(struct input_dev *dev, unsigned int type, unsigned int code, int value);
 void input_inject_event(struct input_handle *handle, unsigned int type, unsigned int code, int value);
 

-- 
2.51.1.851.g4ebd6896fd-goog


^ permalink raw reply related

* [PATCH 0/2] Implement notifier chain for lid switch events
From: Jonathan Denose @ 2025-10-30 14:10 UTC (permalink / raw)
  To: Dmitry Torokhov, Jiri Kosina, Benjamin Tissoires
  Cc: linux-input, linux-kernel, Jonathan Denose

To circumvent a hardware issue where the touchpad is not physically
connected to the lid angle sensor, implement a notifier chain which
broadcasts lid switch events and a notifier_block which can be enabled
via a quirk to listen for those events turning the touchpad surface
on or off based on if the lid is open or closed. This will prevent
issues resulting from interference between the laptop lid and the
touchpad.

Signed-off-by: Jonathan Denose <jdenose@google.com>
---
Jonathan Denose (2):
      Input: Create input notifier chain in input.c
      HID: multitouch: Toggle touch surface on Elan touchpad on lid event

 drivers/hid/hid-multitouch.c | 32 +++++++++++++++++++++++++++++++-
 drivers/input/input.c        | 13 +++++++++++++
 include/linux/input.h        |  7 +++++++
 3 files changed, 51 insertions(+), 1 deletion(-)
---
base-commit: 3a8660878839faadb4f1a6dd72c3179c1df56787
change-id: 20251014-lid-switch-notifier-1cb9918d675d

Best regards,
-- 
Jonathan Denose <jdenose@google.com>


^ permalink raw reply

* [PATCH] input: elan_i2c: Add newline to sysfs attribute outputs
From: Zhongqiu Han @ 2025-10-30 12:34 UTC (permalink / raw)
  To: dmitry.torokhov, krzk; +Cc: linux-input, linux-kernel, zhongqiu.han

Append newline characters to sysfs_emit() outputs in func min_show() and
max_show(). This aligns with common kernel conventions and improves
readability for userspace tools that expect newline-terminated values.

Signed-off-by: Zhongqiu Han <zhongqiu.han@oss.qualcomm.com>
---
 drivers/input/mouse/elan_i2c_core.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/input/mouse/elan_i2c_core.c b/drivers/input/mouse/elan_i2c_core.c
index fee1796da3d0..14b6cfd7a6de 100644
--- a/drivers/input/mouse/elan_i2c_core.c
+++ b/drivers/input/mouse/elan_i2c_core.c
@@ -861,7 +861,7 @@ static ssize_t min_show(struct device *dev,
 		if (!data->baseline_ready)
 			return -ENODATA;
 
-		return sysfs_emit(buf, "%d", data->min_baseline);
+		return sysfs_emit(buf, "%d\n", data->min_baseline);
 	}
 
 	return -EINTR;
@@ -877,7 +877,7 @@ static ssize_t max_show(struct device *dev,
 		if (!data->baseline_ready)
 			return -ENODATA;
 
-		return sysfs_emit(buf, "%d", data->max_baseline);
+		return sysfs_emit(buf, "%d\n", data->max_baseline);
 	}
 
 	return -EINTR;
-- 
2.43.0


^ permalink raw reply related

* Re: [PATCH] HID: amd_sfh: Stop sensor before starting
From: Jiri Kosina @ 2025-10-30 10:59 UTC (permalink / raw)
  To: Mario Limonciello (AMD)
  Cc: mario.limonciello, basavaraj.natikar, bentiss, stable, Titas,
	linux-input
In-Reply-To: <20251020155101.3905957-1-superm1@kernel.org>

On Mon, 20 Oct 2025, Mario Limonciello (AMD) wrote:

> Titas reports that the accelerometer sensor on their laptop only
> works after a warm boot or unloading/reloading the amd-sfh kernel
> module.
> 
> Presumably the sensor is in a bad state on cold boot and failing to
> start, so explicitly stop it before starting.
> 
> Cc: stable@vger.kernel.org
> Fixes: 93ce5e0231d79 ("HID: amd_sfh: Implement SFH1.1 functionality")
> Reported-by: Titas <novatitas366@gmail.com>
> Closes: https://bugzilla.kernel.org/show_bug.cgi?id=220670
> Tested-by: Titas <novatitas366@gmail.com>
> Signed-off-by: Mario Limonciello (AMD) <superm1@kernel.org>

Applied, thanks.

-- 
Jiri Kosina
SUSE Labs


^ permalink raw reply


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