From nobody Fri Oct 3 23:09:37 2025 Received: from smtpout1.mo533.mail-out.ovh.net (smtpout1.mo533.mail-out.ovh.net [51.210.94.138]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id D1F403054F0 for ; Fri, 22 Aug 2025 14:06:37 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=51.210.94.138 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1755871599; cv=none; b=Xzwj8CjhKeuFBUo97pTt1vQgRXyfe+eCz/MVd1PnYrRWnl7iJZWA5ZNbdZFdjdZhJBKAYSfSFFp0wXimIeWia6aW0hrf6hbx3o6uJAIbpbFB+jmpxvXnFZI7o0Mv20XRTNoW6I56oF9sYK2C3PjU/bWPYo6KPh6t0QNNGatcyL4= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1755871599; c=relaxed/simple; bh=mobexwaFEPKvRq4c5TjJBbvqTGgsSTcXHU8meTu5HVE=; h=From:To:Cc:Subject:Date:Message-Id:In-Reply-To:References: MIME-Version; b=OHp3CcfyTUI57u4GDn96dsA8u15ql1zeQMUdGgrLLZXYDgmnAgGYSlvNMsZN7fsBrBbWVfYRk/P+AH/tjfV1wjOO5cwPn8hqmva3h7DDwrAHpxwSuopT1Vwsw+PQg7dWuHl+y7D++pKK6f7+PrLbjS8k3NOqUch9YjkRuHZqNTU= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=orca.pet; spf=pass smtp.mailfrom=orca.pet; dkim=pass (2048-bit key) header.d=orca.pet header.i=@orca.pet header.b=DDJTRhKr; arc=none smtp.client-ip=51.210.94.138 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=orca.pet Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=orca.pet Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=orca.pet header.i=@orca.pet header.b="DDJTRhKr" Received: from director1.derp.mail-out.ovh.net (director1.derp.mail-out.ovh.net [51.68.80.175]) by mo533.mail-out.ovh.net (Postfix) with ESMTPS id 4c7hcD03b7z5wtK; Fri, 22 Aug 2025 13:58:35 +0000 (UTC) Received: from director1.derp.mail-out.ovh.net (director1.derp.mail-out.ovh.net. [127.0.0.1]) by director1.derp.mail-out.ovh.net (inspect_sender_mail_agent) with SMTP for ; Fri, 22 Aug 2025 13:58:35 +0000 (UTC) Received: from mta2.priv.ovhmail-u1.ea.mail.ovh.net (unknown [10.110.96.172]) by director1.derp.mail-out.ovh.net (Postfix) with ESMTPS id 4c7hcC4Vprz5wH3; Fri, 22 Aug 2025 13:58:35 +0000 (UTC) Received: from orca.pet (unknown [10.1.6.4]) by mta2.priv.ovhmail-u1.ea.mail.ovh.net (Postfix) with ESMTPSA id 9340A3E32CF; Fri, 22 Aug 2025 13:58:34 +0000 (UTC) Authentication-Results: garm.ovh; auth=pass (GARM-95G001eea4ffed-c7f3-48b3-b59a-bca0aebd966c, ADC0680FE15BB91110492B9A34CE42AA242C155A) smtp.auth=marcos@orca.pet X-OVh-ClientIp: 147.156.42.5 From: Marcos Del Sol Vives To: linux-kernel@vger.kernel.org Cc: Marcos Del Sol Vives , Linus Walleij , Bartosz Golaszewski , Michael Walle , Lee Jones , Bjorn Helgaas , linux-gpio@vger.kernel.org, linux-pci@vger.kernel.org Subject: [PATCH v4 1/3] gpio: gpio-regmap: add flag to set direction before value Date: Fri, 22 Aug 2025 15:58:11 +0200 Message-Id: <20250822135816.739582-2-marcos@orca.pet> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20250822135816.739582-1-marcos@orca.pet> References: <20250822135816.739582-1-marcos@orca.pet> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Ovh-Tracer-Id: 8613978715448366694 X-VR-SPAMSTATE: OK X-VR-SPAMSCORE: -100 X-VR-SPAMCAUSE: gggruggvucftvghtrhhoucdtuddrgeeffedrtdefgdduieefleegucetufdoteggodetrfdotffvucfrrhhofhhilhgvmecuqfggjfdpvefjgfevmfevgfenuceurghilhhouhhtmecuhedttdenucesvcftvggtihhpihgvnhhtshculddquddttddmnecujfgurhephffvvefufffkofgjfhgggfestdekredtredttdenucfhrhhomhepofgrrhgtohhsucffvghlucfuohhlucggihhvvghsuceomhgrrhgtohhssehorhgtrgdrphgvtheqnecuggftrfgrthhtvghrnhepudffudeutdejudeffeeugeehveevgfefiefgueejueejheevtefgtdffvddukeelnecukfhppeduvdejrddtrddtrddupddugeejrdduheeirdegvddrheenucevlhhushhtvghrufhiiigvpedtnecurfgrrhgrmhepihhnvghtpeduvdejrddtrddtrddupdhmrghilhhfrhhomhepmhgrrhgtohhssehorhgtrgdrphgvthdpnhgspghrtghpthhtohepledprhgtphhtthhopegsrhhglhessghguggvvhdrphhlpdhrtghpthhtohepsghhvghlghgrrghssehgohhoghhlvgdrtghomhdprhgtphhtthhopehlvggvsehkvghrnhgvlhdrohhrghdprhgtphhtthhopehmfigrlhhlvgeskhgvrhhnvghlrdhorhhgpdhrtghpthhtoheplhhinhhushdrfigrlhhlvghijheslhhinhgrrhhordhorhhgpdhrtghpthhtohepmhgrrhgtohhssehorhgtrgdrphgvthdprhgtphhtthhopehlihhnuhigqdhgphhiohesvhhgvghrrdhkvghrnhgvlhdroh hrghdprhgtphhtthhopehlihhnuhigqdhkvghrnhgvlhesvhhgvghrrdhkvghrnhgvlhdrohhrghdprhgtphhtthhopehlihhnuhigqdhptghisehvghgvrhdrkhgvrhhnvghlrdhorhhg DKIM-Signature: a=rsa-sha256; bh=WB97LK5wYLYtJExCAYyxWF9h54DDMHBADVZKaBy4Blo=; c=relaxed/relaxed; d=orca.pet; h=From; s=ovhmo-selector-1; t=1755871116; v=1; b=DDJTRhKrm5FrqTz0tw0XqnuRdt10sI6bgEEagIH3DovTIhju9RaMVSt69Hn/QKpcJjJ5evIf r1chFJNf7OlCcCuHyQi3QZ2vvysQ7EelDLZqqaaDS7H4UGWX8mtGEoCxm3RSmAK9Js7oLf6nbkG 4hH5+mn2MpvOy5RcZsoh+vX6dlM3l6AL603oQ62dXqZdnWXwl48xGxh6X6oDaRxN5E6CPGDyw1A ESjrgMEAWtWTs/LJMqIveAo5haoKddS4UjRrRSe0OcthvX1KP1jh81G7IxsFDdsDsZ/ZjaPpoTS IBRimZx0jnmJrgGGMH0OWNLw/E89MFYYEGxoYwzxhaCiQ== Content-Type: text/plain; charset="utf-8" When configuring a pin as an output, by default the gpio-regmap driver writes first the value and then configures the direction. The Vortex86 family of SoCs, however, need the direction set before the value, else writes to the data ports are ignored. This commit adds a new "flags" field plus a flag to reverse that order, allowing the direction to be set before the value. Also, added a missing error check in gpio_regmap_direction_output(). Signed-off-by: Marcos Del Sol Vives --- drivers/gpio/gpio-regmap.c | 17 ++++++++++++++++- include/linux/gpio/regmap.h | 18 ++++++++++++++++++ 2 files changed, 34 insertions(+), 1 deletion(-) diff --git a/drivers/gpio/gpio-regmap.c b/drivers/gpio/gpio-regmap.c index e8a32dfebdcb..24cefbd57637 100644 --- a/drivers/gpio/gpio-regmap.c +++ b/drivers/gpio/gpio-regmap.c @@ -31,6 +31,7 @@ struct gpio_regmap { unsigned int reg_clr_base; unsigned int reg_dir_in_base; unsigned int reg_dir_out_base; + unsigned int flags; =20 int (*reg_mask_xlate)(struct gpio_regmap *gpio, unsigned int base, unsigned int offset, unsigned int *reg, @@ -196,7 +197,20 @@ static int gpio_regmap_direction_input(struct gpio_chi= p *chip, static int gpio_regmap_direction_output(struct gpio_chip *chip, unsigned int offset, int value) { - gpio_regmap_set(chip, offset, value); + struct gpio_regmap *gpio =3D gpiochip_get_data(chip); + int ret; + + if (gpio->flags & GPIO_REGMAP_DIR_BEFORE_SET) { + ret =3D gpio_regmap_set_direction(chip, offset, true); + if (ret) + return ret; + + return gpio_regmap_set(chip, offset, value); + } + + ret =3D gpio_regmap_set(chip, offset, value); + if (ret) + return ret; =20 return gpio_regmap_set_direction(chip, offset, true); } @@ -247,6 +261,7 @@ struct gpio_regmap *gpio_regmap_register(const struct g= pio_regmap_config *config gpio->reg_clr_base =3D config->reg_clr_base; gpio->reg_dir_in_base =3D config->reg_dir_in_base; gpio->reg_dir_out_base =3D config->reg_dir_out_base; + gpio->flags =3D config->flags; =20 chip =3D &gpio->gpio_chip; chip->parent =3D config->parent; diff --git a/include/linux/gpio/regmap.h b/include/linux/gpio/regmap.h index c722c67668c6..a2257a1288a8 100644 --- a/include/linux/gpio/regmap.h +++ b/include/linux/gpio/regmap.h @@ -3,6 +3,8 @@ #ifndef _LINUX_GPIO_REGMAP_H #define _LINUX_GPIO_REGMAP_H =20 +#include + struct device; struct fwnode_handle; struct gpio_regmap; @@ -12,6 +14,19 @@ struct regmap; #define GPIO_REGMAP_ADDR_ZERO ((unsigned int)(-1)) #define GPIO_REGMAP_ADDR(addr) ((addr) ? : GPIO_REGMAP_ADDR_ZERO) =20 +/** + * enum gpio_regmap_flags - flags to control GPIO operation + */ +enum gpio_regmap_flags { + /** + * @GPIO_REGMAP_DIR_BEFORE_SET: when setting a pin as an output, set + * its direction before the value. The output value will be undefined + * for a short time which may have unwanted side effects, but some + * hardware requires this. + */ + GPIO_REGMAP_DIR_BEFORE_SET =3D BIT(0), +}; + /** * struct gpio_regmap_config - Description of a generic regmap gpio_chip. * @parent: The parent device @@ -23,6 +38,8 @@ struct regmap; * If not given, the name of the device is used. * @ngpio: (Optional) Number of GPIOs * @names: (Optional) Array of names for gpios + * @flags: (Optional) A bitmask of flags from + * &enum gpio_regmap_flags * @reg_dat_base: (Optional) (in) register base address * @reg_set_base: (Optional) set register base address * @reg_clr_base: (Optional) clear register base address @@ -68,6 +85,7 @@ struct gpio_regmap_config { const char *label; int ngpio; const char *const *names; + unsigned int flags; =20 unsigned int reg_dat_base; unsigned int reg_set_base; --=20 2.34.1 From nobody Fri Oct 3 23:09:37 2025 Received: from 10.mo534.mail-out.ovh.net (10.mo534.mail-out.ovh.net [46.105.32.219]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 8B8D430E0E3 for ; Fri, 22 Aug 2025 13:58:47 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=46.105.32.219 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1755871130; cv=none; b=YeggN3LTSUjNrLH/1BHI+cDZWmtAMD60JBlFIE2MEMNi4BA5u9Q7qjwpzhiwQD0mKGlEODGdj+ssd4lr7bdNCZ1dCTQbHs1D2cxjvBqnHrMvwLds2h8iQaFY60ZpAEbQ0SWLaisFhruiV6mT1OEOiv5xxQEllHTFGMbCNAiBcvk= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1755871130; c=relaxed/simple; bh=I2+ooCH66VdkjAu2Ze3eP4vpjnffGHDacRvjoxxTVaY=; h=From:To:Cc:Subject:Date:Message-Id:In-Reply-To:References: MIME-Version; b=rbwHHlB98GubaDh/5JootQB/NK0TQtb6W/9umVNBC/Ef2SbjB3xeTwaYprhmwL8dy4b/6hVy4gWNChchI5lXr5ByHv/HN4e7dn+j2VeGSaCv8ZKQcSemYD+29yV6J2xOkoKFQx1DKng6+7R9w0bYneRvomv7DC3QmckDH31AJFk= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=orca.pet; spf=pass smtp.mailfrom=orca.pet; dkim=pass (2048-bit key) header.d=orca.pet header.i=@orca.pet header.b=X1ZFhVeg; arc=none smtp.client-ip=46.105.32.219 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=orca.pet Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=orca.pet Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=orca.pet header.i=@orca.pet header.b="X1ZFhVeg" Received: from director4.derp.mail-out.ovh.net (director4.derp.mail-out.ovh.net [79.137.60.37]) by mo534.mail-out.ovh.net (Postfix) with ESMTPS id 4c7hcH3ybvz6ByC; Fri, 22 Aug 2025 13:58:39 +0000 (UTC) Received: from director4.derp.mail-out.ovh.net (director4.derp.mail-out.ovh.net. [127.0.0.1]) by director4.derp.mail-out.ovh.net (inspect_sender_mail_agent) with SMTP for ; Fri, 22 Aug 2025 13:58:39 +0000 (UTC) Received: from mta2.priv.ovhmail-u1.ea.mail.ovh.net (unknown [10.110.164.55]) by director4.derp.mail-out.ovh.net (Postfix) with ESMTPS id 4c7hcH2WNbz1yGR; Fri, 22 Aug 2025 13:58:39 +0000 (UTC) Received: from orca.pet (unknown [10.1.6.4]) by mta2.priv.ovhmail-u1.ea.mail.ovh.net (Postfix) with ESMTPSA id 5F0633E32CF; Fri, 22 Aug 2025 13:58:38 +0000 (UTC) Authentication-Results: garm.ovh; auth=pass (GARM-95G00193c9e7f0-3e02-4c96-8053-d7a721d83764, ADC0680FE15BB91110492B9A34CE42AA242C155A) smtp.auth=marcos@orca.pet X-OVh-ClientIp: 147.156.42.5 From: Marcos Del Sol Vives To: linux-kernel@vger.kernel.org Cc: Marcos Del Sol Vives , Linus Walleij , Bartosz Golaszewski , Michael Walle , Lee Jones , Bjorn Helgaas , linux-gpio@vger.kernel.org, linux-pci@vger.kernel.org Subject: [PATCH v4 2/3] gpio: vortex: add new GPIO device driver Date: Fri, 22 Aug 2025 15:58:12 +0200 Message-Id: <20250822135816.739582-3-marcos@orca.pet> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20250822135816.739582-1-marcos@orca.pet> References: <20250822135816.739582-1-marcos@orca.pet> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Ovh-Tracer-Id: 8615104614398383718 X-VR-SPAMSTATE: OK X-VR-SPAMSCORE: -100 X-VR-SPAMCAUSE: gggruggvucftvghtrhhoucdtuddrgeeffedrtdefgdduieefleegucetufdoteggodetrfdotffvucfrrhhofhhilhgvmecuqfggjfdpvefjgfevmfevgfenuceurghilhhouhhtmecuhedttdenucesvcftvggtihhpihgvnhhtshculddquddttddmnecujfgurhephffvvefufffkofgjfhgggfestdekredtredttdenucfhrhhomhepofgrrhgtohhsucffvghlucfuohhlucggihhvvghsuceomhgrrhgtohhssehorhgtrgdrphgvtheqnecuggftrfgrthhtvghrnhepjefhtddukedtjedttdejhfekgeetgeetudelheeghfduffeiveekgfehhfekjedunecuffhomhgrihhnpehvohhrthgvgiekiedrtghomhenucfkphepuddvjedrtddrtddruddpudegjedrudehiedrgedvrdehnecuvehluhhsthgvrhfuihiivgeptdenucfrrghrrghmpehinhgvthepuddvjedrtddrtddruddpmhgrihhlfhhrohhmpehmrghrtghoshesohhrtggrrdhpvghtpdhnsggprhgtphhtthhopeelpdhrtghpthhtohepsghrghhlsegsghguvghvrdhplhdprhgtphhtthhopegshhgvlhhgrggrshesghhoohhglhgvrdgtohhmpdhrtghpthhtoheplhgvvgeskhgvrhhnvghlrdhorhhgpdhrtghpthhtohepmhifrghllhgvsehkvghrnhgvlhdrohhrghdprhgtphhtthhopehlihhnuhhsrdifrghllhgvihhjsehlihhnrghrohdrohhrghdprhgtphhtthhopehmrghrtghoshesohhrtggrrdhpvghtpdhrtghpthhtoheplhhinh hugidqghhpihhosehvghgvrhdrkhgvrhhnvghlrdhorhhgpdhrtghpthhtoheplhhinhhugidqkhgvrhhnvghlsehvghgvrhdrkhgvrhhnvghlrdhorhhgpdhrtghpthhtoheplhhinhhugidqphgtihesvhhgvghrrdhkvghrnhgvlhdrohhrgh DKIM-Signature: a=rsa-sha256; bh=+ddC6/C+4PiskoWM7HBtyuAMn3NQyUw8QTC7ohXcGxA=; c=relaxed/relaxed; d=orca.pet; h=From; s=ovhmo-selector-1; t=1755871119; v=1; b=X1ZFhVegygBtdgZiV99FaouYtYLuwjtKIrOkVUEtuOUnB9ihybHA9Hi1l2anmGBanr1BSFxn 8nmIwv8uYRphhQ1P8uzBf8GdkLxPW62NC75kYlA/K9Ep8aoPaAI1YZkdSxQWZiCY1/vT0RiGryI FqF1raZoOuSEAt9ba//Rx+Lokp+tG0PohRm5Kh9xjZIS9chFnnOjbioOF3hLuvHtrM3oYfvnY9z JaPd1lEGa/0zFFQqLX81wmIOcMNSZdvSaZG35EoseUV3lYLevJh1IlvaTQCx0ubU1mEysp/fT5d zuKpaD1A7D8nN4x49+E1XLK/x3Ir1xnzr2PSKLRfXhPmA== Content-Type: text/plain; charset="utf-8" Add a new simple GPIO device driver for most DM&P Vortex86 SoCs, implemented according to their programming reference manuals [1][2][3]. Vortex86EX/EX2 use a radically different mechanism of GPIO control and are not supported by this driver. This is required for detecting the status of the poweroff button and performing the poweroff sequence on ICOP eBox computers. IRQs are not implemented, as they are only available for ports 0 and 1, none which are accessible on my test machine (an EBOX-3352-GLW). [1]: https://www.vortex86.com/downloadsStart?serial=3DVortex86SX/DX/MXPLUS [2]: https://www.vortex86.com/downloadsStart?serial=3DVortex86DX2 [3]: https://www.vortex86.com/downloadsStart?serial=3DVortex86DX3 Signed-off-by: Marcos Del Sol Vives Acked-by: William Breathitt Gray --- MAINTAINERS | 5 ++ drivers/gpio/Kconfig | 13 +++ drivers/gpio/Makefile | 1 + drivers/gpio/gpio-vortex.c | 170 +++++++++++++++++++++++++++++++++++++ 4 files changed, 189 insertions(+) create mode 100644 drivers/gpio/gpio-vortex.c diff --git a/MAINTAINERS b/MAINTAINERS index 2720544cd91f..afa88f446630 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -26953,6 +26953,11 @@ VOLTAGE AND CURRENT REGULATOR IRQ HELPERS R: Matti Vaittinen F: drivers/regulator/irq_helpers.c =20 +VORTEX HARDWARE SUPPORT +R: Marcos Del Sol Vives +S: Maintained +F: drivers/gpio/gpio-vortex.c + VRF M: David Ahern L: netdev@vger.kernel.org diff --git a/drivers/gpio/Kconfig b/drivers/gpio/Kconfig index e43abb322fa6..dd5b24843b41 100644 --- a/drivers/gpio/Kconfig +++ b/drivers/gpio/Kconfig @@ -1077,6 +1077,19 @@ config GPIO_TS5500 blocks of the TS-5500: DIO1, DIO2 and the LCD port, and the TS-5600 LCD port. =20 +config GPIO_VORTEX + tristate "Vortex SoC GPIO support" + select REGMAP_MMIO + select GPIO_REGMAP + help + Driver to access the 8-bit bidirectional GPIO ports present on DM&P + Vortex86SX/MX/MX+/DX/DX2/DX3 SoCs. + + Vortex86EX-series parts are not supported. + + To compile this driver as a module, choose M here: the module will + be called gpio-vortex. + config GPIO_WINBOND tristate "Winbond Super I/O GPIO support" select ISA_BUS_API diff --git a/drivers/gpio/Makefile b/drivers/gpio/Makefile index 379f55e9ed1e..7b8626c9bd75 100644 --- a/drivers/gpio/Makefile +++ b/drivers/gpio/Makefile @@ -197,6 +197,7 @@ obj-$(CONFIG_GPIO_VIPERBOARD) +=3D gpio-viperboard.o obj-$(CONFIG_GPIO_VIRTUSER) +=3D gpio-virtuser.o obj-$(CONFIG_GPIO_VIRTIO) +=3D gpio-virtio.o obj-$(CONFIG_GPIO_VISCONTI) +=3D gpio-visconti.o +obj-$(CONFIG_GPIO_VORTEX) +=3D gpio-vortex.o obj-$(CONFIG_GPIO_VX855) +=3D gpio-vx855.o obj-$(CONFIG_GPIO_WCD934X) +=3D gpio-wcd934x.o obj-$(CONFIG_GPIO_WHISKEY_COVE) +=3D gpio-wcove.o diff --git a/drivers/gpio/gpio-vortex.c b/drivers/gpio/gpio-vortex.c new file mode 100644 index 000000000000..edac919a5799 --- /dev/null +++ b/drivers/gpio/gpio-vortex.c @@ -0,0 +1,170 @@ +// SPDX-License-Identifier: GPL-2.0-only +/* + * GPIO driver for Vortex86 SoCs + * + * Vortex SoCs may have either a single set (DX/MX/SX) of data/direction p= orts, + * or two non-contiguous sets (DX2/DX3). + * + * Because gpio-regmap is not designed to handle ranges with holes of arbi= trary + * sizes in them, this driver reports a virtual layout where ports 0..n-1 = are + * data ports, and n..n*2-1 are direction ports. The xlate function then m= aps + * these virtual ports back to the real hardware registers relative to the + * requested I/O window. + * + * Author: Marcos Del Sol Vives + */ + +#include +#include +#include +#include +#include +#include +#include +#include + +struct vortex_gpio { + struct regmap_range ranges[4]; + struct regmap_access_table access_table; + struct device *dev; +}; + +static int vortex_gpio_xlate(struct gpio_regmap *gpio, unsigned int base, + unsigned int offset, unsigned int *reg, + unsigned int *mask) +{ + struct vortex_gpio *priv =3D gpio_regmap_get_drvdata(gpio); + unsigned int virtual_port, r_min, r_size; + int i; + + virtual_port =3D base + offset / 8; + + for (i =3D 0; i < priv->access_table.n_yes_ranges; i++) { + r_min =3D priv->ranges[i].range_min; + r_size =3D priv->ranges[i].range_max - r_min + 1; + + if (virtual_port < r_size) { + *reg =3D virtual_port + r_min; + *mask =3D BIT(offset % 8); + return 0; + } + virtual_port -=3D r_size; + } + + /* should never happen */ + dev_err(priv->dev, "tried to translate an out-of-bounds virtual port: %u\= n", + base + offset / 8); + return -EINVAL; +} + +static int vortex_gpio_add_range(struct vortex_gpio *priv, + struct platform_device *pdev, + const char *res_name) +{ + struct resource *res; + + res =3D platform_get_resource_byname(pdev, IORESOURCE_IO, res_name); + if (!res) + return 0; + + priv->ranges[priv->access_table.n_yes_ranges].range_min =3D res->start; + priv->ranges[priv->access_table.n_yes_ranges].range_max =3D res->end; + priv->access_table.n_yes_ranges++; + + return resource_size(res); +} + +static int vortex_gpio_probe(struct platform_device *pdev) +{ + struct gpio_regmap_config gpiocfg =3D {}; + struct device *dev =3D &pdev->dev; + struct regmap_config rmcfg =3D {}; + unsigned long io_min, io_max; + struct vortex_gpio *priv; + int i, dat_len, dir_len; + struct regmap *map; + void __iomem *regs; + + /* Initialize private data */ + priv =3D devm_kzalloc(dev, sizeof(struct vortex_gpio), + GFP_KERNEL); + if (unlikely(!priv)) + return -ENOMEM; + priv->dev =3D dev; + priv->access_table.yes_ranges =3D priv->ranges; + + /* Add I/O ports from platform data to ranges */ + dat_len =3D vortex_gpio_add_range(priv, pdev, "dat1"); + if (unlikely(!dat_len)) { + dev_err(dev, "failed to get data register\n"); + return -ENODEV; + } + dat_len +=3D vortex_gpio_add_range(priv, pdev, "dat2"); + + dir_len =3D vortex_gpio_add_range(priv, pdev, "dir1"); + if (unlikely(!dir_len)) { + dev_err(dev, "failed to get direction register\n"); + return -ENODEV; + } + dir_len +=3D vortex_gpio_add_range(priv, pdev, "dir2"); + + if (unlikely(dat_len !=3D dir_len)) { + dev_err(dev, "data and direction size mismatch (%d vs %d)\n", + dat_len, dir_len); + return -EINVAL; + } + + /* Request smallest I/O window that covers all registers */ + io_min =3D priv->ranges[0].range_min; + io_max =3D priv->ranges[0].range_max; + for (i =3D 1; i < priv->access_table.n_yes_ranges; i++) { + io_min =3D min(io_min, priv->ranges[i].range_min); + io_max =3D max(io_max, priv->ranges[i].range_max); + } + + regs =3D devm_ioport_map(dev, io_min, io_max - io_min + 1); + if (unlikely(!regs)) + return -ENOMEM; + + /* Subtract io_min to make them relative to the window */ + for (i =3D 0; i < priv->access_table.n_yes_ranges; i++) { + priv->ranges[i].range_min -=3D io_min; + priv->ranges[i].range_max -=3D io_min; + } + + rmcfg.reg_bits =3D 8; + rmcfg.val_bits =3D 8; + rmcfg.io_port =3D true; + rmcfg.wr_table =3D &priv->access_table; + rmcfg.rd_table =3D &priv->access_table; + + map =3D devm_regmap_init_mmio(dev, regs, &rmcfg); + if (IS_ERR(map)) + return dev_err_probe(dev, PTR_ERR(map), + "Unable to initialize register map\n"); + + gpiocfg.parent =3D dev; + gpiocfg.regmap =3D map; + gpiocfg.drvdata =3D priv; + gpiocfg.ngpio =3D 8 * dat_len; + gpiocfg.ngpio_per_reg =3D 8; + gpiocfg.reg_dat_base =3D GPIO_REGMAP_ADDR(0); + gpiocfg.reg_set_base =3D GPIO_REGMAP_ADDR(0); + gpiocfg.reg_dir_out_base =3D GPIO_REGMAP_ADDR(dat_len); + gpiocfg.flags =3D GPIO_REGMAP_DIR_BEFORE_SET; + gpiocfg.reg_mask_xlate =3D vortex_gpio_xlate; + + return PTR_ERR_OR_ZERO(devm_gpio_regmap_register(dev, &gpiocfg)); +} + +static struct platform_driver vortex_gpio_driver =3D { + .driver.name =3D "vortex-gpio", + .probe =3D vortex_gpio_probe, +}; + +module_platform_driver(vortex_gpio_driver); + +MODULE_AUTHOR("Marcos Del Sol Vives "); +MODULE_DESCRIPTION("GPIO driver for Vortex86 SoCs"); +MODULE_LICENSE("GPL"); +MODULE_ALIAS("platform:vortex-gpio"); --=20 2.34.1 From nobody Fri Oct 3 23:09:37 2025 Received: from 5.mo534.mail-out.ovh.net (5.mo534.mail-out.ovh.net [54.36.140.176]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 5FDF4303CBE; Fri, 22 Aug 2025 13:58:45 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=54.36.140.176 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1755871128; cv=none; b=fKhZg03kbmkqdxUSM2MtgsKbzX2qUVB8ZawgcWpvi+6wwVWJL0EeXVvcO0WFByntegj1kRKy2StMAheCiT6mriW2S4MqEADwxE3Q/9ddqbf6NeCc9chrFBbJqF9zEdeoofYb2/SncfjRYXL51ETKwagIw64cWUg2g6Lodu7Rr7I= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1755871128; c=relaxed/simple; bh=1nFot461mH2AXNOy+OXg4eZ75foA2HBvx3TjV+cwST4=; h=From:To:Cc:Subject:Date:Message-Id:In-Reply-To:References: MIME-Version; b=d6hv+8YfIMR4FqwPK5gsPGcKzRLmyW8jop4gIojd4CclzPRxL8x2qKdF9VrwHWK/AOZ9Ldk68/KIaiotje+tKmdp9gL72fMK6SarU5zxDmGY2PM4kXc6E0jgiHWcI0J4zY0qIKRC9+uVeRRzeZVZcDawesbshUa5lIyOP603Pmw= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=orca.pet; spf=pass smtp.mailfrom=orca.pet; dkim=pass (2048-bit key) header.d=orca.pet header.i=@orca.pet header.b=U7uMZGgh; arc=none smtp.client-ip=54.36.140.176 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=orca.pet Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=orca.pet Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=orca.pet header.i=@orca.pet header.b="U7uMZGgh" Received: from director4.derp.mail-out.ovh.net (director4.derp.mail-out.ovh.net [79.137.60.37]) by mo534.mail-out.ovh.net (Postfix) with ESMTPS id 4c7hcM1W1rz6D5x; Fri, 22 Aug 2025 13:58:43 +0000 (UTC) Received: from director4.derp.mail-out.ovh.net (director4.derp.mail-out.ovh.net. [127.0.0.1]) by director4.derp.mail-out.ovh.net (inspect_sender_mail_agent) with SMTP for ; Fri, 22 Aug 2025 13:58:43 +0000 (UTC) Received: from mta2.priv.ovhmail-u1.ea.mail.ovh.net (unknown [10.110.168.168]) by director4.derp.mail-out.ovh.net (Postfix) with ESMTPS id 4c7hcM0F12z1yGZ; Fri, 22 Aug 2025 13:58:43 +0000 (UTC) Received: from orca.pet (unknown [10.1.6.4]) by mta2.priv.ovhmail-u1.ea.mail.ovh.net (Postfix) with ESMTPSA id 1AEDF3E32D0; Fri, 22 Aug 2025 13:58:42 +0000 (UTC) Authentication-Results: garm.ovh; auth=pass (GARM-95G0016ef2d7ab-2360-4703-861c-5b60f28993d5, ADC0680FE15BB91110492B9A34CE42AA242C155A) smtp.auth=marcos@orca.pet X-OVh-ClientIp: 147.156.42.5 From: Marcos Del Sol Vives To: linux-kernel@vger.kernel.org Cc: Marcos Del Sol Vives , Linus Walleij , Bartosz Golaszewski , Michael Walle , Lee Jones , Bjorn Helgaas , linux-gpio@vger.kernel.org, linux-pci@vger.kernel.org Subject: [PATCH v4 3/3] mfd: vortex: implement new driver for Vortex southbridges Date: Fri, 22 Aug 2025 15:58:13 +0200 Message-Id: <20250822135816.739582-4-marcos@orca.pet> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20250822135816.739582-1-marcos@orca.pet> References: <20250822135816.739582-1-marcos@orca.pet> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Ovh-Tracer-Id: 8616230514139223654 X-VR-SPAMSTATE: OK X-VR-SPAMSCORE: -100 X-VR-SPAMCAUSE: gggruggvucftvghtrhhoucdtuddrgeeffedrtdefgdduieefleegucetufdoteggodetrfdotffvucfrrhhofhhilhgvmecuqfggjfdpvefjgfevmfevgfenuceurghilhhouhhtmecuhedttdenucesvcftvggtihhpihgvnhhtshculddquddttddmnecujfgurhephffvvefufffkofgjfhgggfestdekredtredttdenucfhrhhomhepofgrrhgtohhsucffvghlucfuohhlucggihhvvghsuceomhgrrhgtohhssehorhgtrgdrphgvtheqnecuggftrfgrthhtvghrnhepudffudeutdejudeffeeugeehveevgfefiefgueejueejheevtefgtdffvddukeelnecukfhppeduvdejrddtrddtrddupddugeejrdduheeirdegvddrheenucevlhhushhtvghrufhiiigvpedtnecurfgrrhgrmhepihhnvghtpeduvdejrddtrddtrddupdhmrghilhhfrhhomhepmhgrrhgtohhssehorhgtrgdrphgvthdpnhgspghrtghpthhtohepledprhgtphhtthhopegsrhhglhessghguggvvhdrphhlpdhrtghpthhtohepsghhvghlghgrrghssehgohhoghhlvgdrtghomhdprhgtphhtthhopehlvggvsehkvghrnhgvlhdrohhrghdprhgtphhtthhopehmfigrlhhlvgeskhgvrhhnvghlrdhorhhgpdhrtghpthhtoheplhhinhhushdrfigrlhhlvghijheslhhinhgrrhhordhorhhgpdhrtghpthhtohepmhgrrhgtohhssehorhgtrgdrphgvthdprhgtphhtthhopehlihhnuhigqdhgphhiohesvhhgvghrrdhkvghrnhgvlhdroh hrghdprhgtphhtthhopehlihhnuhigqdhkvghrnhgvlhesvhhgvghrrdhkvghrnhgvlhdrohhrghdprhgtphhtthhopehlihhnuhigqdhptghisehvghgvrhdrkhgvrhhnvghlrdhorhhg DKIM-Signature: a=rsa-sha256; bh=qUWhGzunPuC1HDyNVxUC9O9rEFAp/6tcqWTBpQ5k3nI=; c=relaxed/relaxed; d=orca.pet; h=From; s=ovhmo-selector-1; t=1755871123; v=1; b=U7uMZGghJg4ldSfCih9aDGX5RIqWjR0vS1G13sbYsAyHSwTAaR16gVZU0QT4isByk+vpXPKH cmL0Salw29gSHg6sHfvEPbi1tBZrFg7Ga/XnG8hxnjQKppsMDSIbgFFFlcbXxpWV3Ej07r/XtfV ERLinKufx77j4bgjqy1gx6LnlgPnQ+ObmgPqZ/GJcLly3R/O8w30FDUb0cTUeCOZZFansMrbqIh xLKVUDWzddwilTgv48OmHexde26VfAM/vG/yztggoeJyqQjYiVhsIGkMVsduFjJjHmcn4XlWzWa JB79lGhxkmIIq1c2lnuTFMahQwov4XIvOzpRwDlR82p2A== Content-Type: text/plain; charset="utf-8" This new driver loads resources related to southbridges available in DM&P Vortex devices, currently only the GPIO pins. Signed-off-by: Marcos Del Sol Vives --- MAINTAINERS | 1 + drivers/mfd/Kconfig | 9 +++ drivers/mfd/Makefile | 1 + drivers/mfd/vortex-sb.c | 135 ++++++++++++++++++++++++++++++++++++++++ include/linux/pci_ids.h | 3 + 5 files changed, 149 insertions(+) create mode 100644 drivers/mfd/vortex-sb.c diff --git a/MAINTAINERS b/MAINTAINERS index afa88f446630..63e410e23e95 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -26957,6 +26957,7 @@ VORTEX HARDWARE SUPPORT R: Marcos Del Sol Vives S: Maintained F: drivers/gpio/gpio-vortex.c +F: drivers/mfd/vortex-sb.c =20 VRF M: David Ahern diff --git a/drivers/mfd/Kconfig b/drivers/mfd/Kconfig index 425c5fba6cb1..fe54bb22687d 100644 --- a/drivers/mfd/Kconfig +++ b/drivers/mfd/Kconfig @@ -2008,6 +2008,15 @@ config MFD_VX855 VIA VX855/VX875 south bridge. You will need to enable the vx855_spi and/or vx855_gpio drivers for this to do anything useful. =20 +config MFD_VORTEX_SB + tristate "Vortex southbridge" + select MFD_CORE + depends on PCI + help + Say yes here if you want to have support for the southbridge + present on Vortex SoCs. You will need to enable the vortex-gpio + driver for this to do anything useful. + config MFD_ARIZONA select REGMAP select REGMAP_IRQ diff --git a/drivers/mfd/Makefile b/drivers/mfd/Makefile index f7bdedd5a66d..2504ba311f1a 100644 --- a/drivers/mfd/Makefile +++ b/drivers/mfd/Makefile @@ -202,6 +202,7 @@ obj-$(CONFIG_MFD_JANZ_CMODIO) +=3D janz-cmodio.o obj-$(CONFIG_MFD_TPS6586X) +=3D tps6586x.o obj-$(CONFIG_MFD_VX855) +=3D vx855.o obj-$(CONFIG_MFD_WL1273_CORE) +=3D wl1273-core.o +obj-$(CONFIG_MFD_VORTEX_SB) +=3D vortex-sb.o =20 si476x-core-y :=3D si476x-cmd.o si476x-prop.o si476x-i2c.o obj-$(CONFIG_MFD_SI476X_CORE) +=3D si476x-core.o diff --git a/drivers/mfd/vortex-sb.c b/drivers/mfd/vortex-sb.c new file mode 100644 index 000000000000..141fa19773e2 --- /dev/null +++ b/drivers/mfd/vortex-sb.c @@ -0,0 +1,135 @@ +// SPDX-License-Identifier: GPL-2.0-or-later +/* + * MFD southbridge driver for Vortex SoCs + * + * Author: Marcos Del Sol Vives + * + * Based on the RDC321x MFD driver by Florian Fainelli and Bernhard Loos + */ + +#include +#include +#include +#include +#include + +struct vortex_southbridge { + const struct mfd_cell *cells; + int n_cells; +}; + +/* Layout for Vortex86DX/MX */ +static const struct resource vortex_dx_gpio_resources[] =3D { + { + .name =3D "dat1", + .start =3D 0x78, + .end =3D 0x7C, + .flags =3D IORESOURCE_IO, + }, { + .name =3D "dir1", + .start =3D 0x98, + .end =3D 0x9C, + .flags =3D IORESOURCE_IO, + } +}; + +static const struct mfd_cell vortex_dx_sb_cells[] =3D { + { + .name =3D "vortex-gpio", + .resources =3D vortex_dx_gpio_resources, + .num_resources =3D ARRAY_SIZE(vortex_dx_gpio_resources), + }, +}; + +static const struct vortex_southbridge vortex_dx_sb =3D { + .cells =3D vortex_dx_sb_cells, + .n_cells =3D ARRAY_SIZE(vortex_dx_sb_cells), +}; + +/* Layout for Vortex86DX2/DX3 */ +static const struct resource vortex_dx2_gpio_resources[] =3D { + { + .name =3D "dat1", + .start =3D 0x78, + .end =3D 0x7C, + .flags =3D IORESOURCE_IO, + }, { + .name =3D "dat2", + .start =3D 0x100, + .end =3D 0x105, + .flags =3D IORESOURCE_IO, + }, { + .name =3D "dir1", + .start =3D 0x98, + .end =3D 0x9D, + .flags =3D IORESOURCE_IO, + }, { + .name =3D "dir2", + .start =3D 0x93, + .end =3D 0x97, + .flags =3D IORESOURCE_IO, + } +}; + +static const struct mfd_cell vortex_dx2_sb_cells[] =3D { + { + .name =3D "vortex-gpio", + .resources =3D vortex_dx2_gpio_resources, + .num_resources =3D ARRAY_SIZE(vortex_dx2_gpio_resources), + }, +}; + +static const struct vortex_southbridge vortex_dx2_sb =3D { + .cells =3D vortex_dx2_sb_cells, + .n_cells =3D ARRAY_SIZE(vortex_dx2_sb_cells), +}; + +static int vortex_sb_probe(struct pci_dev *pdev, + const struct pci_device_id *ent) +{ + struct vortex_southbridge *priv =3D (struct vortex_southbridge *) ent->dr= iver_data; + int err; + + /* + * In the Vortex86DX3, the southbridge appears twice (on both 00:07.0 + * and 00:07.1). Register only once for .0. + * + * Other Vortex boards (eg Vortex86MX+) have the southbridge exposed + * only once, also at 00:07.0. + */ + if (PCI_FUNC(pdev->devfn) !=3D 0) + return -ENODEV; + + err =3D pci_enable_device(pdev); + if (err) { + dev_err(&pdev->dev, "failed to enable device\n"); + return err; + } + + return devm_mfd_add_devices(&pdev->dev, PLATFORM_DEVID_NONE, + priv->cells, priv->n_cells, + NULL, 0, NULL); +} + +static const struct pci_device_id vortex_sb_table[] =3D { + /* Vortex86DX */ + { PCI_DEVICE_DATA(RDC, R6031, &vortex_dx_sb) }, + /* Vortex86DX2/DX3 */ + { PCI_DEVICE_DATA(RDC, R6035, &vortex_dx2_sb) }, + /* Vortex86MX */ + { PCI_DEVICE_DATA(RDC, R6036, &vortex_dx_sb) }, + {} +}; +MODULE_DEVICE_TABLE(pci, vortex_sb_table); + +static struct pci_driver vortex_sb_driver =3D { + .name =3D "vortex-sb", + .id_table =3D vortex_sb_table, + .probe =3D vortex_sb_probe, +}; + +module_pci_driver(vortex_sb_driver); + +MODULE_AUTHOR("Marcos Del Sol Vives "); +MODULE_LICENSE("GPL"); +MODULE_DESCRIPTION("Vortex MFD southbridge driver"); diff --git a/include/linux/pci_ids.h b/include/linux/pci_ids.h index 92ffc4373f6d..2c7afebd94ea 100644 --- a/include/linux/pci_ids.h +++ b/include/linux/pci_ids.h @@ -2412,6 +2412,9 @@ #define PCI_VENDOR_ID_RDC 0x17f3 #define PCI_DEVICE_ID_RDC_R6020 0x6020 #define PCI_DEVICE_ID_RDC_R6030 0x6030 +#define PCI_DEVICE_ID_RDC_R6031 0x6031 +#define PCI_DEVICE_ID_RDC_R6035 0x6035 +#define PCI_DEVICE_ID_RDC_R6036 0x6036 #define PCI_DEVICE_ID_RDC_R6040 0x6040 #define PCI_DEVICE_ID_RDC_R6060 0x6060 #define PCI_DEVICE_ID_RDC_R6061 0x6061 --=20 2.34.1