All of lore.kernel.org
 help / color / mirror / Atom feed
* [U-Boot] [PATCH 00/37] convert GE boards to DM
@ 2019-10-15 15:53 Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 01/37] configs: bx50v3: Fix boot hang with video Robert Beckett
                   ` (36 more replies)
  0 siblings, 37 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

This patch series converts GE boards to use DM features.
Most of the patches are GE board specific to modify the board code to
use the DM drivers, or modify the device tree.

There are a few new features:

patch 11 & 12: Add i2c_eeprom partitioning via device tree

patch 16 & 17: Add an i2c chip addr offset overflow mask to allow offsets to
effectively steal chip addresses. This handles a common i2c addressing
mode used on various devices.

patch 18: Add i2c eeprom bootcount driver

patch 36 & 37: add da9063 pmic and regulators

Denis Zalevskiy (2):
  configs: ppd: DM for USB and regulators PPD
  board: ge: bx50v3: Enable DM for PCI and ethernet

Ian Ray (8):
  configs: bx50v3: Fix boot hang with video
  board: ge: bx50v3: Fix run-time warning
  board: ge: bx50v3: Fix message output to video console
  board: ge: pass rtc_status via device tree
  board: ge: mx53ppd: move uart initialisation to own function
  board: ge: mx53ppd: enable DM_VIDEO
  rtc: s35392a: encode command correctly
  board: ge: mx53ppd: fix RTC compatible definition

Robert Beckett (27):
  board: ge: bx50v3: use imx wdt
  board: ge: mx53ppd: use imx wdt
  board: ge: bx50v3: Add i2c bus description
  board: ge: mx53ppd: Add i2c bus descritpion
  misc: i2c_eeprom: add fixed partitions support
  misc: i2c_eeprom: add size query
  board: ge: bx50v3: use DM I2C
  board: ge: mx53ppd: use DM I2C
  board: ge: convert vpd to use i2c eeprom
  i2c: add support for offset overflow in to address
  misc: i2c_eeprom: set offset len and chip addr offset mask
  bootcount: add a DM i2c eeprom backing store for bootcount
  board: ge: bx50v3: add i2c eeprom bootcount storage
  board: ge: mx53ppd: add i2c eeprom bootcount storage
  rtc: rx8010sj: fix DM initialization
  board: ge: bx50v3, mx53ppd: use DM rtc
  board: ge: bx50v3: use DM i2c for PMIC initialization
  board: ge: mx53ppd: remove redundant power config
  board: ge: bx50v3, mx53ppd: disable I2C compatibility API
  board: ge: bx50v3: Enable DM PWM for backlight
  board: ge: mx53ppd: clean up DM PWM video and backlight
  board: ge: mx53ppd: Use DM for ethernet
  board: ge: bx50v3: use DM for uart
  serial: mxc: add imx53 and imx21 compatible string
  board: ge: mx53ppd: use DM for uart
  dm: pmic: add da9063 PMIC driver and regulators
  board: ge: bx50v3: use DM PMIC driver

 arch/arm/dts/imx53-ppd.dts       | 317 ++++++++++++++++++
 arch/arm/dts/imx6q-bx50v3.dts    | 529 +++++++++++++++++++++++++++++++
 board/ge/bx50v3/Kconfig          |   2 -
 board/ge/bx50v3/bx50v3.c         | 291 ++++-------------
 board/ge/common/Kconfig          |  14 -
 board/ge/common/ge_common.c      |  33 +-
 board/ge/common/vpd_reader.c     |  37 ++-
 board/ge/mx53ppd/Kconfig         |   2 -
 board/ge/mx53ppd/Makefile        |   2 +-
 board/ge/mx53ppd/mx53ppd.c       |  75 +----
 board/ge/mx53ppd/mx53ppd_video.c | 125 +++-----
 board/ge/mx53ppd/ppd_gpio.h      |   8 -
 configs/ge_bx50v3_defconfig      |  40 ++-
 configs/mx53ppd_defconfig        |  35 +-
 drivers/bootcount/Kconfig        |  10 +
 drivers/bootcount/Makefile       |   1 +
 drivers/bootcount/i2c-eeprom.c   |  95 ++++++
 drivers/i2c/i2c-uclass.c         |  32 +-
 drivers/misc/i2c_eeprom.c        | 278 ++++++++++++++--
 drivers/power/pmic/Kconfig       |   8 +
 drivers/power/pmic/Makefile      |   1 +
 drivers/power/pmic/da9063.c      | 270 ++++++++++++++++
 drivers/power/regulator/Kconfig  |   7 +
 drivers/power/regulator/Makefile |   1 +
 drivers/power/regulator/da9063.c | 320 +++++++++++++++++++
 drivers/rtc/rx8010sj.c           |   2 +-
 drivers/rtc/s35392a.c            |  27 +-
 drivers/serial/serial_mxc.c      |   2 +
 include/configs/ge_bx50v3.h      |  64 +---
 include/configs/mx53ppd.h        |  69 +---
 include/i2c.h                    |  24 ++
 include/i2c_eeprom.h             |  12 +
 include/power/da9063_pmic.h      | 303 ++++++++++++++++++
 33 files changed, 2430 insertions(+), 606 deletions(-)
 delete mode 100644 board/ge/common/Kconfig
 create mode 100644 drivers/bootcount/i2c-eeprom.c
 create mode 100644 drivers/power/pmic/da9063.c
 create mode 100644 drivers/power/regulator/da9063.c
 create mode 100644 include/power/da9063_pmic.h

-- 
2.20.1

^ permalink raw reply	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 01/37] configs: bx50v3: Fix boot hang with video
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 02/37] board: ge: bx50v3: Fix run-time warning Robert Beckett
                   ` (35 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

From: Ian Ray <ian.ray@ge.com>

Fixes commit: 0b09f7b15052bb419e318e38da453be46e5a13e5, which converted
to DM_VIDEO, but requires more memory.

[Inspired by 9002e735e71754a90adbb9676c0ffb1964dbc288]

Signed-off-by: Ian Ray <ian.ray@ge.com>
Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 configs/ge_bx50v3_defconfig | 1 +
 1 file changed, 1 insertion(+)

diff --git a/configs/ge_bx50v3_defconfig b/configs/ge_bx50v3_defconfig
index 75fdbf7e72..7e9da38f20 100644
--- a/configs/ge_bx50v3_defconfig
+++ b/configs/ge_bx50v3_defconfig
@@ -64,3 +64,4 @@ CONFIG_VIDEO_IPUV3=y
 CONFIG_WATCHDOG_TIMEOUT_MSECS=6000
 CONFIG_IMX_WATCHDOG=y
 # CONFIG_EFI_LOADER is not set
+CONFIG_SYS_MALLOC_F_LEN=0x4000
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 02/37] board: ge: bx50v3: Fix run-time warning
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 01/37] configs: bx50v3: Fix boot hang with video Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 03/37] board: ge: bx50v3: Fix message output to video console Robert Beckett
                   ` (34 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

From: Ian Ray <ian.ray@ge.com>

Fix GPIO reservation warning on code paths that do not need LVDS power.

Signed-off-by: Ian Ray <ian.ray@ge.com>
Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 board/ge/bx50v3/bx50v3.c | 23 +++++++++++++----------
 1 file changed, 13 insertions(+), 10 deletions(-)

diff --git a/board/ge/bx50v3/bx50v3.c b/board/ge/bx50v3/bx50v3.c
index 917ecc4c18..499dcb3a61 100644
--- a/board/ge/bx50v3/bx50v3.c
+++ b/board/ge/bx50v3/bx50v3.c
@@ -704,20 +704,23 @@ int ft_board_setup(void *blob, bd_t *bd)
 static int do_backlight_enable(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
 {
 #ifdef CONFIG_VIDEO_IPUV3
-	/* We need at least 200ms between power on and backlight on
-	 * as per specifications from CHI MEI */
-	mdelay(250);
+	if (!is_b850v3()) {
+		/* We need at least 200ms between power on and backlight on
+		 * as per specifications from CHI MEI
+		 */
+		mdelay(250);
 
-	/* enable backlight PWM 1 */
-	pwm_init(0, 0, 0);
+		/* enable backlight PWM 1 */
+		pwm_init(0, 0, 0);
 
-	/* duty cycle 5000000ns, period: 5000000ns */
-	pwm_config(0, 5000000, 5000000);
+		/* duty cycle 5000000ns, period: 5000000ns */
+		pwm_config(0, 5000000, 5000000);
 
-	/* Backlight Power */
-	gpio_direction_output(LVDS_BACKLIGHT_GP, 1);
+		/* Backlight Power */
+		gpio_direction_output(LVDS_BACKLIGHT_GP, 1);
 
-	pwm_enable(0);
+		pwm_enable(0);
+	}
 #endif
 
 	return 0;
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 03/37] board: ge: bx50v3: Fix message output to video console
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 01/37] configs: bx50v3: Fix boot hang with video Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 02/37] board: ge: bx50v3: Fix run-time warning Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 04/37] configs: ppd: DM for USB and regulators PPD Robert Beckett
                   ` (33 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

From: Ian Ray <ian.ray@ge.com>

Use vidconsole for output to the LCD, now that DM_VIDEO is used.  Write
white text on a black background, like before migrating to DM_VIDEO.

Signed-off-by: Ian Ray <ian.ray@ge.com>
Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 board/ge/bx50v3/bx50v3.c    | 21 ++++++++++++++-------
 configs/ge_bx50v3_defconfig |  1 +
 include/configs/ge_bx50v3.h |  9 ++++-----
 3 files changed, 19 insertions(+), 12 deletions(-)

diff --git a/board/ge/bx50v3/bx50v3.c b/board/ge/bx50v3/bx50v3.c
index 499dcb3a61..55fbcbcc81 100644
--- a/board/ge/bx50v3/bx50v3.c
+++ b/board/ge/bx50v3/bx50v3.c
@@ -217,13 +217,6 @@ static void do_enable_hdmi(struct display_info_t const *dev)
 	imx_enable_hdmi_phy();
 }
 
-int board_cfb_skip(void)
-{
-	gpio_direction_output(LVDS_POWER_GP, 1);
-
-	return 0;
-}
-
 static int is_b850v3(void)
 {
 	return confidx == 3;
@@ -703,8 +696,14 @@ int ft_board_setup(void *blob, bd_t *bd)
 
 static int do_backlight_enable(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
 {
+#if CONFIG_IS_ENABLED(DM_VIDEO)
+	int ret;
+	struct udevice *dev;
+
 #ifdef CONFIG_VIDEO_IPUV3
 	if (!is_b850v3()) {
+		gpio_direction_output(LVDS_POWER_GP, 1);
+
 		/* We need at least 200ms between power on and backlight on
 		 * as per specifications from CHI MEI
 		 */
@@ -723,6 +722,14 @@ static int do_backlight_enable(cmd_tbl_t *cmdtp, int flag, int argc, char * cons
 	}
 #endif
 
+	/* Probe, to find a video device to be used to show a message on
+	 * the vidconsole.
+	 */
+	ret = uclass_get_device(UCLASS_VIDEO, 0, &dev);
+	if (ret)
+		return ret;
+#endif
+
 	return 0;
 }
 
diff --git a/configs/ge_bx50v3_defconfig b/configs/ge_bx50v3_defconfig
index 7e9da38f20..0b45105134 100644
--- a/configs/ge_bx50v3_defconfig
+++ b/configs/ge_bx50v3_defconfig
@@ -65,3 +65,4 @@ CONFIG_WATCHDOG_TIMEOUT_MSECS=6000
 CONFIG_IMX_WATCHDOG=y
 # CONFIG_EFI_LOADER is not set
 CONFIG_SYS_MALLOC_F_LEN=0x4000
+CONFIG_SYS_WHITE_ON_BLACK=y
diff --git a/include/configs/ge_bx50v3.h b/include/configs/ge_bx50v3.h
index 6de5119d7f..92a927bb82 100644
--- a/include/configs/ge_bx50v3.h
+++ b/include/configs/ge_bx50v3.h
@@ -114,12 +114,11 @@
 	"swappartitions=" \
 		"setexpr partnum 3 - ${partnum}\0" \
 	"failbootcmd=" \
+		"echo reached failbootcmd; " \
 		"bx50_backlight_enable; " \
-		"msg=\"Monitor failed to start.  Try again, or contact GE Service for support.\"; " \
-		"echo $msg; " \
-		"setenv stdout vga; " \
-		"echo \"\n\n\n\n    \" $msg; " \
-		"setenv stdout serial; " \
+		"setcurs 5 4; " \
+		"lcdputs \"Monitor failed to start. " \
+		"Try again, or contact GE Service for support.\"; " \
 		"mw.b 0x7000A000 0xbc; " \
 		"mw.b 0x7000A001 0x00; " \
 		"ext4write ${dev} ${devnum}:5 0x7000A000 /boot/failures 2\0" \
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 04/37] configs: ppd: DM for USB and regulators PPD
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (2 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 03/37] board: ge: bx50v3: Fix message output to video console Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 05/37] board: ge: bx50v3: Enable DM for PCI and ethernet Robert Beckett
                   ` (32 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

From: Denis Zalevskiy <denis.zalevskiy@ge.com>

DM should be used for USB since 2019.07, it also requires DM for
regulators.

Signed-off-by: Denis Zalevskiy <denis.zalevskiy@ge.com>
Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 configs/mx53ppd_defconfig | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/configs/mx53ppd_defconfig b/configs/mx53ppd_defconfig
index 7f293c8e9a..e1992e91ad 100644
--- a/configs/mx53ppd_defconfig
+++ b/configs/mx53ppd_defconfig
@@ -52,3 +52,5 @@ CONFIG_VIDEO=y
 # CONFIG_VIDEO_SW_CURSOR is not set
 CONFIG_WATCHDOG_TIMEOUT_MSECS=8000
 CONFIG_IMX_WATCHDOG=y
+CONFIG_DM_REGULATOR=y
+CONFIG_DM_USB=y
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 05/37] board: ge: bx50v3: Enable DM for PCI and ethernet
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (3 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 04/37] configs: ppd: DM for USB and regulators PPD Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 06/37] board: ge: pass rtc_status via device tree Robert Beckett
                   ` (31 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

From: Denis Zalevskiy <denis.zalevskiy@ge.com>

DM for PCI pulls DM for ethernet that also needs other changes described
below to build u-boot and keep existing functionality - ability to update
MAC addresses of FEC ethernet adapter and I210 adapter connected to the
Marvell switch.

- fec_mxc driver with DM needs PHYLIB;

- configuration items are moved from ge_bx50v3.h to ge_bx50v3_defconfig;

- FEC is marked as eth0 because it is always present, so indices changed:
  I210 are still probed in the same order;

- board_eth_init() was used by legacy ethernet, setup for enet iomux and
  pcie is moved to the board_late_init();

- pci_init() is called from the board_late_init() to initiate PCI bus
  probing, so I210 devices are propagated to the device tree;

Signed-off-by: Denis Zalevskiy <denis.zalevskiy@ge.com>
[Describe PHY reset in device tree]
Signed-off-by: Ian Ray <ian.ray@ge.com>
Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 arch/arm/dts/imx6q-bx50v3.dts | 54 +++++++++++++++++++++++++
 board/ge/bx50v3/bx50v3.c      | 75 ++++++-----------------------------
 configs/ge_bx50v3_defconfig   |  8 ++++
 include/configs/ge_bx50v3.h   | 12 ------
 4 files changed, 75 insertions(+), 74 deletions(-)

diff --git a/arch/arm/dts/imx6q-bx50v3.dts b/arch/arm/dts/imx6q-bx50v3.dts
index deaec63509..28a35394f0 100644
--- a/arch/arm/dts/imx6q-bx50v3.dts
+++ b/arch/arm/dts/imx6q-bx50v3.dts
@@ -13,6 +13,11 @@
 / {
 	model = "General Electric Bx50v3";
 	compatible = "ge,imx6q-bx50v3", "advantech,imx6q-ba16", "fsl,imx6q";
+
+	aliases {
+		ethernet0 = &fec;
+	};
+
 };
 
 &iomuxc {
@@ -48,6 +53,30 @@
 			MX6QDL_PAD_SD3_RST__SD3_RESET   0x170F9
 		>;
 	};
+
+	pinctrl_enet: enetgrp {
+		fsl,pins = <
+			MX6QDL_PAD_ENET_MDIO__ENET_MDIO       0x100b0
+			MX6QDL_PAD_ENET_MDC__ENET_MDC         0x100b0
+			MX6QDL_PAD_RGMII_TXC__RGMII_TXC       0x10030
+			MX6QDL_PAD_RGMII_TD0__RGMII_TD0       0x10030
+			MX6QDL_PAD_RGMII_TD1__RGMII_TD1       0x10030
+			MX6QDL_PAD_RGMII_TD2__RGMII_TD2       0x10030
+			MX6QDL_PAD_RGMII_TD3__RGMII_TD3       0x10030
+			MX6QDL_PAD_RGMII_TX_CTL__RGMII_TX_CTL 0x10030
+			MX6QDL_PAD_ENET_REF_CLK__ENET_TX_CLK  0x100b0
+			MX6QDL_PAD_RGMII_RXC__RGMII_RXC       0x1b030
+			MX6QDL_PAD_RGMII_RD0__RGMII_RD0       0x1b030
+			MX6QDL_PAD_RGMII_RD1__RGMII_RD1       0x1b030
+			MX6QDL_PAD_RGMII_RD2__RGMII_RD2       0x1b030
+			MX6QDL_PAD_RGMII_RD3__RGMII_RD3       0x1b030
+			MX6QDL_PAD_RGMII_RX_CTL__RGMII_RX_CTL 0x1b030
+			/* FEC Reset */
+			MX6QDL_PAD_ENET_TX_EN__GPIO1_IO28     0x1b0b0
+			/* AR8033 Interrupt */
+			MX6QDL_PAD_GPIO_19__GPIO4_IO05        0x1b0b0
+		>;
+	};
 };
 
 &usdhc1 {
@@ -87,3 +116,28 @@
 		reg = <0>;
 	};
 };
+
+&fec {
+	reg = <0x02188000 0x4000>;
+	pinctrl-names = "default";
+	pinctrl-0 = <&pinctrl_enet>;
+	phy-mode = "rgmii";
+	status = "okay";
+	phy-reset-gpios = <&gpio1 28 GPIO_ACTIVE_LOW>;
+	phy-reset-duration = <10>;
+	phy-reset-post-delay = <1>;
+
+	mdio {
+		#address-cells = <1>;
+		#size-cells = <0>;
+
+		ethphy0: ethernet-phy at 4 {
+			compatible = "ethernet-phy-ieee802.3-c22";
+			reg = <4>;
+		};
+	};
+};
+
+&pcie {
+	status = "okay";
+};
diff --git a/board/ge/bx50v3/bx50v3.c b/board/ge/bx50v3/bx50v3.c
index 55fbcbcc81..87e34cf1c9 100644
--- a/board/ge/bx50v3/bx50v3.c
+++ b/board/ge/bx50v3/bx50v3.c
@@ -34,6 +34,8 @@
 #include "../common/ge_common.h"
 #include "../common/vpd_reader.h"
 #include "../../../drivers/net/e1000.h"
+#include <pci.h>
+
 DECLARE_GLOBAL_DATA_PTR;
 
 static int confidx = 3;  /* Default to b850v3. */
@@ -81,38 +83,6 @@ static iomux_v3_cfg_t const uart4_pads[] = {
 	MX6_PAD_KEY_ROW0__UART4_RX_DATA | MUX_PAD_CTRL(UART_PAD_CTRL),
 };
 
-static iomux_v3_cfg_t const enet_pads[] = {
-	MX6_PAD_ENET_MDIO__ENET_MDIO | MUX_PAD_CTRL(ENET_PAD_CTRL),
-	MX6_PAD_ENET_MDC__ENET_MDC   | MUX_PAD_CTRL(ENET_PAD_CTRL),
-	MX6_PAD_RGMII_TXC__RGMII_TXC | MUX_PAD_CTRL(ENET_PAD_CTRL),
-	MX6_PAD_RGMII_TD0__RGMII_TD0 | MUX_PAD_CTRL(ENET_PAD_CTRL),
-	MX6_PAD_RGMII_TD1__RGMII_TD1 | MUX_PAD_CTRL(ENET_PAD_CTRL),
-	MX6_PAD_RGMII_TD2__RGMII_TD2 | MUX_PAD_CTRL(ENET_PAD_CTRL),
-	MX6_PAD_RGMII_TD3__RGMII_TD3 | MUX_PAD_CTRL(ENET_PAD_CTRL),
-	MX6_PAD_RGMII_TX_CTL__RGMII_TX_CTL | MUX_PAD_CTRL(ENET_PAD_CTRL),
-	MX6_PAD_ENET_REF_CLK__ENET_TX_CLK  | MUX_PAD_CTRL(ENET_CLK_PAD_CTRL),
-	MX6_PAD_RGMII_RXC__RGMII_RXC | MUX_PAD_CTRL(ENET_RX_PAD_CTRL),
-	MX6_PAD_RGMII_RD0__RGMII_RD0 | MUX_PAD_CTRL(ENET_RX_PAD_CTRL),
-	MX6_PAD_RGMII_RD1__RGMII_RD1 | MUX_PAD_CTRL(ENET_RX_PAD_CTRL),
-	MX6_PAD_RGMII_RD2__RGMII_RD2 | MUX_PAD_CTRL(ENET_RX_PAD_CTRL),
-	MX6_PAD_RGMII_RD3__RGMII_RD3 | MUX_PAD_CTRL(ENET_RX_PAD_CTRL),
-	MX6_PAD_RGMII_RX_CTL__RGMII_RX_CTL | MUX_PAD_CTRL(ENET_RX_PAD_CTRL),
-	/* AR8033 PHY Reset */
-	MX6_PAD_ENET_TX_EN__GPIO1_IO28 | MUX_PAD_CTRL(NO_PAD_CTRL),
-};
-
-static void setup_iomux_enet(void)
-{
-	imx_iomux_v3_setup_multiple_pads(enet_pads, ARRAY_SIZE(enet_pads));
-
-	/* Reset AR8033 PHY */
-	gpio_request(IMX_GPIO_NR(1, 28), "fec_rst");
-	gpio_direction_output(IMX_GPIO_NR(1, 28), 0);
-	mdelay(10);
-	gpio_set_value(IMX_GPIO_NR(1, 28), 1);
-	mdelay(1);
-}
-
 static struct i2c_pads_info i2c_pad_info1 = {
 	.scl = {
 		.i2c_mode = MX6_PAD_CSI0_DAT9__I2C1_SCL | I2C_PAD,
@@ -152,16 +122,6 @@ static struct i2c_pads_info i2c_pad_info3 = {
 	}
 };
 
-static iomux_v3_cfg_t const pcie_pads[] = {
-	MX6_PAD_GPIO_5__GPIO1_IO05 | MUX_PAD_CTRL(NO_PAD_CTRL),
-	MX6_PAD_GPIO_17__GPIO7_IO12 | MUX_PAD_CTRL(NO_PAD_CTRL),
-};
-
-static void setup_pcie(void)
-{
-	imx_iomux_v3_setup_multiple_pads(pcie_pads, ARRAY_SIZE(pcie_pads));
-}
-
 static void setup_iomux_uart(void)
 {
 	imx_iomux_v3_setup_multiple_pads(uart3_pads, ARRAY_SIZE(uart3_pads));
@@ -453,7 +413,7 @@ static int vpd_callback(struct vpd_cache *vpd, u8 id, u8 version, u8 type,
 
 static void process_vpd(struct vpd_cache *vpd)
 {
-	int fec_index = -1;
+	int fec_index = 0;
 	int i210_index = -1;
 
 	if (!vpd->is_read) {
@@ -461,41 +421,30 @@ static void process_vpd(struct vpd_cache *vpd)
 		return;
 	}
 
+	if (vpd->has & VPD_HAS_MAC1)
+		eth_env_set_enetaddr_by_index("eth", fec_index, vpd->mac1);
+
+	env_set("ethact", "eth0");
+
 	switch (vpd->product_id) {
 	case VPD_PRODUCT_B450:
 		env_set("confidx", "1");
-		i210_index = 0;
-		fec_index = 1;
+		i210_index = 1;
 		break;
 	case VPD_PRODUCT_B650:
 		env_set("confidx", "2");
-		i210_index = 0;
-		fec_index = 1;
+		i210_index = 1;
 		break;
 	case VPD_PRODUCT_B850:
 		env_set("confidx", "3");
-		i210_index = 1;
-		fec_index = 2;
+		i210_index = 2;
 		break;
 	}
 
-	if (fec_index >= 0 && (vpd->has & VPD_HAS_MAC1))
-		eth_env_set_enetaddr_by_index("eth", fec_index, vpd->mac1);
-
 	if (i210_index >= 0 && (vpd->has & VPD_HAS_MAC2))
 		eth_env_set_enetaddr_by_index("eth", i210_index, vpd->mac2);
 }
 
-int board_eth_init(bd_t *bis)
-{
-	setup_iomux_enet();
-	setup_pcie();
-
-	e1000_initialize(bis);
-
-	return cpu_eth_init(bis);
-}
-
 static iomux_v3_cfg_t const misc_pads[] = {
 	MX6_PAD_KEY_ROW2__GPIO4_IO11	| MUX_PAD_CTRL(NO_PAD_CTRL),
 	MX6_PAD_EIM_A25__GPIO5_IO02	| MUX_PAD_CTRL(NC_PAD_CTRL),
@@ -649,6 +598,8 @@ int board_late_init(void)
 
 	check_time();
 
+	pci_init();
+
 	return 0;
 }
 
diff --git a/configs/ge_bx50v3_defconfig b/configs/ge_bx50v3_defconfig
index 0b45105134..cd0bf5bab5 100644
--- a/configs/ge_bx50v3_defconfig
+++ b/configs/ge_bx50v3_defconfig
@@ -66,3 +66,11 @@ CONFIG_IMX_WATCHDOG=y
 # CONFIG_EFI_LOADER is not set
 CONFIG_SYS_MALLOC_F_LEN=0x4000
 CONFIG_SYS_WHITE_ON_BLACK=y
+CONFIG_PCI=y
+CONFIG_DM_PCI=y
+CONFIG_PCI_PNP=y
+CONFIG_DM_ETH=y
+CONFIG_PHYLIB=y
+CONFIG_PHY_ATHEROS=y
+CONFIG_FEC_MXC=y
+CONFIG_ETHPRIME="FEC"
diff --git a/include/configs/ge_bx50v3.h b/include/configs/ge_bx50v3.h
index 92a927bb82..d572424831 100644
--- a/include/configs/ge_bx50v3.h
+++ b/include/configs/ge_bx50v3.h
@@ -49,16 +49,6 @@
 #define CONFIG_USB_GADGET_MASS_STORAGE
 #endif
 
-/* Networking Configs */
-#ifdef CONFIG_NET
-#define CONFIG_FEC_MXC
-#define IMX_FEC_BASE			ENET_BASE_ADDR
-#define CONFIG_FEC_XCV_TYPE		RGMII
-#define CONFIG_ETHPRIME		"FEC"
-#define CONFIG_FEC_MXC_PHYADDR		4
-#define CONFIG_PHY_ATHEROS
-#endif
-
 /* Serial Flash */
 
 /* allow to overwrite serial and ethaddr */
@@ -197,8 +187,6 @@
 
 #define CONFIG_IMX6_PWM_PER_CLK	66000000
 
-#define CONFIG_PCI
-#define CONFIG_PCI_PNP
 #define CONFIG_PCI_SCAN_SHOW
 #define CONFIG_PCIE_IMX
 #define CONFIG_PCIE_IMX_PERST_GPIO	IMX_GPIO_NR(7, 12)
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 06/37] board: ge: pass rtc_status via device tree
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (4 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 05/37] board: ge: bx50v3: Enable DM for PCI and ethernet Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 07/37] board: ge: bx50v3: use imx wdt Robert Beckett
                   ` (30 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

From: Ian Ray <ian.ray@ge.com>

Pass rtc_status via the device tree, instead of on kernel command line.
Additionally, the 2038 mitigation is reported, if applied successfully.

Signed-off-by: Ian Ray <ian.ray@ge.com>
Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 board/ge/bx50v3/bx50v3.c    |  7 ++++++-
 board/ge/common/ge_common.c | 20 +++++++++++++-------
 board/ge/mx53ppd/mx53ppd.c  |  7 ++++++-
 include/configs/ge_bx50v3.h |  2 +-
 include/configs/mx53ppd.h   |  2 +-
 5 files changed, 27 insertions(+), 11 deletions(-)

diff --git a/board/ge/bx50v3/bx50v3.c b/board/ge/bx50v3/bx50v3.c
index 87e34cf1c9..c29ac5b611 100644
--- a/board/ge/bx50v3/bx50v3.c
+++ b/board/ge/bx50v3/bx50v3.c
@@ -639,8 +639,13 @@ int checkboard(void)
 #ifdef CONFIG_OF_BOARD_SETUP
 int ft_board_setup(void *blob, bd_t *bd)
 {
+	char *rtc_status = env_get("rtc_status");
+
 	fdt_setprop(blob, 0, "ge,boot-ver", version_string,
-	                                    strlen(version_string) + 1);
+		    strlen(version_string) + 1);
+
+	fdt_setprop(blob, 0, "ge,rtc-status", rtc_status,
+		    strlen(rtc_status) + 1);
 	return 0;
 }
 #endif
diff --git a/board/ge/common/ge_common.c b/board/ge/common/ge_common.c
index 501c8b2daf..d7e21deca7 100644
--- a/board/ge/common/ge_common.c
+++ b/board/ge/common/ge_common.c
@@ -17,8 +17,10 @@ void check_time(void)
 	unsigned int current_i2c_bus = i2c_get_bus_num();
 
 	ret = i2c_set_bus_num(CONFIG_SYS_RTC_BUS_NUM);
-	if (ret < 0)
+	if (ret < 0) {
+		env_set("rtc_status", "FAIL");
 		return;
+	}
 
 	rtc_init();
 
@@ -28,10 +30,7 @@ void check_time(void)
 			break;
 	}
 
-	if (ret < 0)
-		env_set("rtc_status", "RTC_ERROR");
-
-	if (tm.tm_year > 2037) {
+	if (!ret && tm.tm_year > 2037) {
 		tm.tm_sec  = 0;
 		tm.tm_min  = 0;
 		tm.tm_hour = 0;
@@ -46,10 +45,17 @@ void check_time(void)
 				break;
 		}
 
-		if (ret < 0)
-			env_set("rtc_status", "RTC_ERROR");
+		if (ret >= 0)
+			ret = 2038;
 	}
 
+	if (ret < 0)
+		env_set("rtc_status", "FAIL");
+	else if (ret == 2038)
+		env_set("rtc_status", "2038");
+	else
+		env_set("rtc_status", "OK");
+
 	i2c_set_bus_num(current_i2c_bus);
 }
 
diff --git a/board/ge/mx53ppd/mx53ppd.c b/board/ge/mx53ppd/mx53ppd.c
index 5448567298..b4d08a11ee 100644
--- a/board/ge/mx53ppd/mx53ppd.c
+++ b/board/ge/mx53ppd/mx53ppd.c
@@ -313,8 +313,13 @@ int checkboard(void)
 #ifdef CONFIG_OF_BOARD_SETUP
 int ft_board_setup(void *blob, bd_t *bd)
 {
+	char *rtc_status = env_get("rtc_status");
+
 	fdt_setprop(blob, 0, "ge,boot-ver", version_string,
-	                                    strlen(version_string) + 1);
+		    strlen(version_string) + 1);
+
+	fdt_setprop(blob, 0, "ge,rtc-status", rtc_status,
+		    strlen(rtc_status) + 1);
 	return 0;
 }
 #endif
diff --git a/include/configs/ge_bx50v3.h b/include/configs/ge_bx50v3.h
index d572424831..7c26608aa7 100644
--- a/include/configs/ge_bx50v3.h
+++ b/include/configs/ge_bx50v3.h
@@ -93,7 +93,7 @@
 	"setargs=setenv bootargs root=/dev/${rootdev}${partnum} " \
 		"ro rootwait cma=128M " \
 		"bootcause=${bootcause} " \
-		"${quiet} console=${console} ${rtc_status} " \
+		"${quiet} console=${console} " \
 		"${videoargs}" "\0" \
 	"doquiet=" \
 		"if ext2load ${dev} ${devnum}:5 0x7000A000 /boot/console; " \
diff --git a/include/configs/mx53ppd.h b/include/configs/mx53ppd.h
index 59988efc9b..26e4b729bb 100644
--- a/include/configs/mx53ppd.h
+++ b/include/configs/mx53ppd.h
@@ -101,7 +101,7 @@
 	"lvds=ldb\0" \
 	"setargs=setenv bootargs ${lvds} jtag=on mem=2G " \
 		"vt.global_cursor_default=0 bootcause=${bootcause} ${quiet} " \
-		"console=${console} ${rtc_status}\0" \
+		"console=${console}\0" \
 	"bootargs_emmc=setenv bootargs root=/dev/${rootdev}${partnum} ro " \
 		"rootwait ${bootargs}\0" \
 	"doquiet=if ext2load ${dev} ${devnum}:5 0x7000A000 /boot/console; " \
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 07/37] board: ge: bx50v3: use imx wdt
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (5 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 06/37] board: ge: pass rtc_status via device tree Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 08/37] board: ge: mx53ppd: " Robert Beckett
                   ` (29 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Enable DM imx WDT
Enable SYSRESET_WATCHDOG to maintain WDT based reset ability

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 arch/arm/dts/imx6q-bx50v3.dts | 4 ++++
 configs/ge_bx50v3_defconfig   | 3 +++
 2 files changed, 7 insertions(+)

diff --git a/arch/arm/dts/imx6q-bx50v3.dts b/arch/arm/dts/imx6q-bx50v3.dts
index 28a35394f0..2e2e3bbc24 100644
--- a/arch/arm/dts/imx6q-bx50v3.dts
+++ b/arch/arm/dts/imx6q-bx50v3.dts
@@ -18,6 +18,10 @@
 		ethernet0 = &fec;
 	};
 
+	wdt-reboot {
+		compatible = "wdt-reboot";
+		wdt = <&wdog1>;
+	};
 };
 
 &iomuxc {
diff --git a/configs/ge_bx50v3_defconfig b/configs/ge_bx50v3_defconfig
index cd0bf5bab5..cddc558484 100644
--- a/configs/ge_bx50v3_defconfig
+++ b/configs/ge_bx50v3_defconfig
@@ -63,6 +63,9 @@ CONFIG_DM_VIDEO=y
 CONFIG_VIDEO_IPUV3=y
 CONFIG_WATCHDOG_TIMEOUT_MSECS=6000
 CONFIG_IMX_WATCHDOG=y
+CONFIG_WDT=y
+CONFIG_SYSRESET=y
+CONFIG_SYSRESET_WATCHDOG=y
 # CONFIG_EFI_LOADER is not set
 CONFIG_SYS_MALLOC_F_LEN=0x4000
 CONFIG_SYS_WHITE_ON_BLACK=y
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 08/37] board: ge: mx53ppd: use imx wdt
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (6 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 07/37] board: ge: bx50v3: use imx wdt Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 09/37] board: ge: bx50v3: Add i2c bus description Robert Beckett
                   ` (28 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Enable DM imx WDT
Enable SYSRESET_WATCHDOG to maintain WDT based reset ability

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 arch/arm/dts/imx53-ppd.dts | 5 +++++
 board/ge/mx53ppd/mx53ppd.c | 1 -
 configs/mx53ppd_defconfig  | 3 +++
 3 files changed, 8 insertions(+), 1 deletion(-)

diff --git a/arch/arm/dts/imx53-ppd.dts b/arch/arm/dts/imx53-ppd.dts
index f89d6f4672..909a76731b 100644
--- a/arch/arm/dts/imx53-ppd.dts
+++ b/arch/arm/dts/imx53-ppd.dts
@@ -11,6 +11,11 @@
 / {
 	model = "General Electric CS ONE";
 	compatible = "ge,imx53-cpuvo", "fsl,imx53";
+
+	wdt-reboot {
+		compatible = "wdt-reboot";
+		wdt = <&wdog1>;
+	};
 };
 
 &iomuxc {
diff --git a/board/ge/mx53ppd/mx53ppd.c b/board/ge/mx53ppd/mx53ppd.c
index b4d08a11ee..ad37995624 100644
--- a/board/ge/mx53ppd/mx53ppd.c
+++ b/board/ge/mx53ppd/mx53ppd.c
@@ -296,7 +296,6 @@ int board_late_init(void)
 		return res;
 
 	print_cpuinfo();
-	hw_watchdog_init();
 
 	check_time();
 
diff --git a/configs/mx53ppd_defconfig b/configs/mx53ppd_defconfig
index e1992e91ad..8822b74864 100644
--- a/configs/mx53ppd_defconfig
+++ b/configs/mx53ppd_defconfig
@@ -52,5 +52,8 @@ CONFIG_VIDEO=y
 # CONFIG_VIDEO_SW_CURSOR is not set
 CONFIG_WATCHDOG_TIMEOUT_MSECS=8000
 CONFIG_IMX_WATCHDOG=y
+CONFIG_WDT=y
+CONFIG_SYSRESET=y
+CONFIG_SYSRESET_WATCHDOG=y
 CONFIG_DM_REGULATOR=y
 CONFIG_DM_USB=y
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 09/37] board: ge: bx50v3: Add i2c bus description
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (7 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 08/37] board: ge: mx53ppd: " Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 10/37] board: ge: mx53ppd: Add i2c bus descritpion Robert Beckett
                   ` (27 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Add i2c bus devicetree description

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 arch/arm/dts/imx6q-bx50v3.dts | 351 ++++++++++++++++++++++++++++++++++
 1 file changed, 351 insertions(+)

diff --git a/arch/arm/dts/imx6q-bx50v3.dts b/arch/arm/dts/imx6q-bx50v3.dts
index 2e2e3bbc24..4dd2ce3038 100644
--- a/arch/arm/dts/imx6q-bx50v3.dts
+++ b/arch/arm/dts/imx6q-bx50v3.dts
@@ -81,6 +81,61 @@
 			MX6QDL_PAD_GPIO_19__GPIO4_IO05        0x1b0b0
 		>;
 	};
+
+	pinctrl_i2c1: i2c1grp {
+		fsl,pins = <
+			MX6QDL_PAD_CSI0_DAT8__I2C1_SDA	0x4001b8b1
+			MX6QDL_PAD_CSI0_DAT9__I2C1_SCL	0x4001b8b1
+		>;
+	};
+
+	pinctrl_i2c2: i2c2grp {
+		fsl,pins = <
+			MX6QDL_PAD_KEY_COL3__I2C2_SCL	0x4001b8b1
+			MX6QDL_PAD_KEY_ROW3__I2C2_SDA	0x4001b8b1
+		>;
+	};
+
+	pinctrl_i2c3: i2c3grp {
+		fsl,pins = <
+			MX6QDL_PAD_GPIO_3__I2C3_SCL	0x4001b8b1
+			MX6QDL_PAD_GPIO_6__I2C3_SDA	0x4001b8b1
+		>;
+	};
+	pinctrl_i2c1_gpio: i2c1gpiogrp {
+		fsl,pins = <
+			MX6QDL_PAD_CSI0_DAT8__GPIO5_IO26	0x1b0b0
+			MX6QDL_PAD_CSI0_DAT9__GPIO5_IO27	0x1b0b0
+		>;
+	};
+
+	pinctrl_i2c2_gpio: i2c2gpiogrp {
+		fsl,pins = <
+			MX6QDL_PAD_KEY_COL3__GPIO4_IO12	0x1b0b0
+			MX6QDL_PAD_KEY_ROW3__GPIO4_IO13	0x1b0b0
+		>;
+	};
+
+	pinctrl_i2c3_gpio: i2c3gpiogrp {
+		fsl,pins = <
+			MX6QDL_PAD_GPIO_3__GPIO1_IO03	0x1b0b0
+			MX6QDL_PAD_GPIO_6__GPIO1_IO06	0x1b0b0
+		>;
+	};
+
+	pinctrl_pmic: pmicgrp {
+		fsl,pins = <
+			/* PMIC Interrupt */
+			MX6QDL_PAD_GPIO_18__GPIO7_IO13	0x1b0b0
+		>;
+	};
+
+	pinctrl_rtc: rtcgrp {
+		fsl,pins = <
+			/* RTC_INT */
+			MX6QDL_PAD_KEY_COL2__GPIO4_IO10	0x1b0b0
+		>;
+	};
 };
 
 &usdhc1 {
@@ -145,3 +200,299 @@
 &pcie {
 	status = "okay";
 };
+
+/* I2C */
+&i2c1 {
+	clock-frequency = <100000>;
+	pinctrl-names = "default", "gpio";
+	pinctrl-0 = <&pinctrl_i2c1>;
+	pinctrl-1 = <&pinctrl_i2c1_gpio>;
+	sda-gpios = <&gpio5 26 GPIO_ACTIVE_HIGH>;
+	scl-gpios = <&gpio5 27 GPIO_ACTIVE_HIGH>;
+	status = "okay";
+
+	pca9547: mux at 70 {
+		compatible = "nxp,pca9547";
+		reg = <0x70>;
+		#address-cells = <1>;
+		#size-cells = <0>;
+
+		mux1_i2c1: i2c at 0 {
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <0x0>;
+
+			ads7830: ads7830 at 48 {
+				compatible = "ti,ads7830";
+				reg = <0x48>;
+			};
+
+			mma8453: mma8453 at 1c {
+				compatible = "fsl,mma8453";
+				reg = <0x1c>;
+			};
+		};
+
+		mux1_i2c2: i2c at 1 {
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <0x1>;
+
+			eeprom: eeprom at 50 {
+				compatible = "atmel,24c08";
+				reg = <0x50>;
+
+				partitions {
+					compatible = "fixed-partitions";
+
+					vpd {
+						offset = <0>;
+						size = <1022>;
+					};
+
+					bootcount {
+						offset = <1022>;
+						size = <2>;
+					};
+				};
+			};
+
+			mpl3115: mpl3115 at 60 {
+				compatible = "fsl,mpl3115";
+				reg = <0x60>;
+			};
+		};
+
+		mux1_i2c3: i2c at 2 {
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <0x2>;
+		};
+
+		mux1_i2c4: i2c at 3 {
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <0x3>;
+
+		};
+
+		mux1_i2c5: i2c at 4 {
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <0x4>;
+
+			pca9539: pca9539 at 74 {
+				compatible = "nxp,pca9539";
+				reg = <0x74>;
+				gpio-controller;
+				#gpio-cells = <2>;
+				interrupt-controller;
+				interrupt-parent = <&gpio2>;
+				interrupts = <3 IRQ_TYPE_LEVEL_LOW>;
+
+				P12 {
+					gpio-hog;
+					gpios = <10 0>;
+					output-low;
+					line-name = "PCA9539-P12";
+				};
+
+				P13 {
+					gpio-hog;
+					gpios = <11 0>;
+					output-low;
+					line-name = "PCA9539-P13";
+				};
+
+				P14 {
+					gpio-hog;
+					gpios = <12 0>;
+					output-low;
+					line-name = "PCA9539-P14";
+				};
+
+				P15 {
+					gpio-hog;
+					gpios = <13 0>;
+					output-low;
+					line-name = "PCA9539-P15";
+				};
+
+				P16 {
+					gpio-hog;
+					gpios = <14 0>;
+					output-low;
+					line-name = "PCA9539-P16";
+				};
+
+				P17 {
+					gpio-hog;
+					gpios = <15 0>;
+					output-low;
+					line-name = "PCA9539-P17";
+				};
+			};
+		};
+
+		mux1_i2c6: i2c at 5 {
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <0x5>;
+		};
+
+		mux1_i2c7: i2c at 6 {
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <0x6>;
+		};
+
+		mux1_i2c8: i2c at 7 {
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <0x7>;
+		};
+	};
+};
+
+&i2c2 {
+	clock-frequency = <100000>;
+	pinctrl-names = "default", "gpio";
+	pinctrl-0 = <&pinctrl_i2c2>;
+	pinctrl-1 = <&pinctrl_i2c2_gpio>;
+	sda-gpios = <&gpio4 13 GPIO_ACTIVE_HIGH>;
+	scl-gpios = <&gpio4 12 GPIO_ACTIVE_HIGH>;
+	status = "okay";
+};
+
+&i2c3 {
+	clock-frequency = <100000>;
+	pinctrl-names = "default", "gpio";
+	pinctrl-0 = <&pinctrl_i2c3>;
+	pinctrl-1 = <&pinctrl_i2c3_gpio>;
+	sda-gpios = <&gpio1 6 GPIO_ACTIVE_HIGH>;
+	scl-gpios = <&gpio1 3 GPIO_ACTIVE_HIGH>;
+	status = "okay";
+
+	pmic at 58 {
+		compatible = "dlg,da9063";
+		reg = <0x58>;
+		pinctrl-names = "default";
+		pinctrl-0 = <&pinctrl_pmic>;
+		interrupt-parent = <&gpio7>;
+		interrupts = <13 IRQ_TYPE_LEVEL_LOW>;
+
+		onkey {
+			compatible = "dlg,da9063-onkey";
+		};
+
+		regulators {
+			vdd_bcore1: bcore1 {
+				regulator-min-microvolt = <1420000>;
+				regulator-max-microvolt = <1420000>;
+				regulator-always-on;
+				regulator-boot-on;
+			};
+
+			vdd_bcore2: bcore2 {
+				regulator-min-microvolt = <1420000>;
+				regulator-max-microvolt = <1420000>;
+				regulator-always-on;
+				regulator-boot-on;
+			};
+
+			vdd_bpro: bpro {
+				regulator-min-microvolt = <1500000>;
+				regulator-max-microvolt = <1500000>;
+				regulator-always-on;
+				regulator-boot-on;
+			};
+
+			vdd_bmem: bmem {
+				regulator-min-microvolt = <1800000>;
+				regulator-max-microvolt = <1800000>;
+				regulator-always-on;
+				regulator-boot-on;
+			};
+
+			vdd_bio: bio {
+				regulator-min-microvolt = <1800000>;
+				regulator-max-microvolt = <1800000>;
+				regulator-always-on;
+				regulator-boot-on;
+			};
+
+			vdd_bperi: bperi {
+				regulator-min-microvolt = <3300000>;
+				regulator-max-microvolt = <3300000>;
+				regulator-always-on;
+				regulator-boot-on;
+			};
+
+			vdd_ldo1: ldo1 {
+				regulator-min-microvolt = <600000>;
+				regulator-max-microvolt = <1860000>;
+			};
+
+			vdd_ldo2: ldo2 {
+				regulator-min-microvolt = <600000>;
+				regulator-max-microvolt = <1860000>;
+			};
+
+			vdd_ldo3: ldo3 {
+				regulator-min-microvolt = <900000>;
+				regulator-max-microvolt = <3440000>;
+			};
+
+			vdd_ldo4: ldo4 {
+				regulator-min-microvolt = <900000>;
+				regulator-max-microvolt = <3440000>;
+			};
+
+			vdd_ldo5: ldo5 {
+				regulator-min-microvolt = <900000>;
+				regulator-max-microvolt = <3600000>;
+			};
+
+			vdd_ldo6: ldo6 {
+				regulator-min-microvolt = <900000>;
+				regulator-max-microvolt = <3600000>;
+			};
+
+			vdd_ldo7: ldo7 {
+				regulator-min-microvolt = <900000>;
+				regulator-max-microvolt = <3600000>;
+			};
+
+			vdd_ldo8: ldo8 {
+				regulator-min-microvolt = <900000>;
+				regulator-max-microvolt = <3600000>;
+			};
+
+			vdd_ldo9: ldo9 {
+				regulator-min-microvolt = <950000>;
+				regulator-max-microvolt = <3600000>;
+			};
+
+			vdd_ldo10: ldo10 {
+				regulator-min-microvolt = <900000>;
+				regulator-max-microvolt = <3600000>;
+			};
+
+			vdd_ldo11: ldo11 {
+				regulator-min-microvolt = <900000>;
+				regulator-max-microvolt = <3600000>;
+				regulator-always-on;
+				regulator-boot-on;
+			};
+		};
+	};
+
+	rtc at 32 {
+		compatible = "epson,rx8010";
+		pinctrl-names = "default";
+		pinctrl-0 = <&pinctrl_rtc>;
+		reg = <0x32>;
+		interrupt-parent = <&gpio4>;
+		interrupts = <10 IRQ_TYPE_LEVEL_HIGH>;
+	};
+};
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 10/37] board: ge: mx53ppd: Add i2c bus descritpion
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (8 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 09/37] board: ge: bx50v3: Add i2c bus description Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 11/37] misc: i2c_eeprom: add fixed partitions support Robert Beckett
                   ` (26 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Add i2c bus devicetree description

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 arch/arm/dts/imx53-ppd.dts | 176 +++++++++++++++++++++++++++++++++++++
 1 file changed, 176 insertions(+)

diff --git a/arch/arm/dts/imx53-ppd.dts b/arch/arm/dts/imx53-ppd.dts
index 909a76731b..84b20cdc55 100644
--- a/arch/arm/dts/imx53-ppd.dts
+++ b/arch/arm/dts/imx53-ppd.dts
@@ -35,6 +35,48 @@
 			MX53_PAD_PATA_IORDY__ESDHC3_CLK         0x1d5
 		>;
 	};
+
+	pinctrl_i2c1: i2c1grp {
+		fsl,pins = <
+			MX53_PAD_EIM_D21__I2C1_SCL		0x400001e4
+			MX53_PAD_EIM_D28__I2C1_SDA		0x400001e4
+		>;
+	};
+
+	pinctrl_i2c1_gpio: i2c1gpiogrp {
+		fsl,pins = <
+			MX53_PAD_EIM_D28__GPIO3_28		0x1e4
+			MX53_PAD_EIM_D21__GPIO3_21		0x1e4
+		>;
+	};
+
+	pinctrl_i2c2: i2c2grp {
+		fsl,pins = <
+			MX53_PAD_EIM_EB2__I2C2_SCL		0x400001e4
+			MX53_PAD_EIM_D16__I2C2_SDA		0x400001e4
+		>;
+	};
+
+	pinctrl_i2c2_gpio: i2c2gpiogrp {
+		fsl,pins = <
+			MX53_PAD_EIM_D16__GPIO3_16		0x1e4
+			MX53_PAD_EIM_EB2__GPIO2_30		0x1e4
+		>;
+	};
+
+	pinctrl_i2c3: i2c3grp {
+		fsl,pins = <
+			MX53_PAD_EIM_D17__I2C3_SCL		0x400001e4
+			MX53_PAD_EIM_D18__I2C3_SDA		0x400001e4
+		>;
+	};
+
+	pinctrl_i2c3_gpio: i2c3gpiogrp {
+		fsl,pins = <
+			MX53_PAD_EIM_D18__GPIO3_18		0x1e4
+			MX53_PAD_EIM_D17__GPIO3_17		0x1e4
+		>;
+	};
 };
 
 /* eMMC */
@@ -46,3 +88,137 @@
 	non-removable;
 	status = "okay";
 };
+
+/* I2C */
+&i2c1 {
+	pinctrl-names = "default", "gpio";
+	pinctrl-0 = <&pinctrl_i2c1>;
+	pinctrl-1 = <&pinctrl_i2c1_gpio>;
+	sda-gpios = <&gpio3 28 GPIO_ACTIVE_HIGH>;
+	scl-gpios = <&gpio3 21 GPIO_ACTIVE_HIGH>;
+	status = "okay";
+
+	i2c-switch at 70 {
+		compatible = "nxp,pca9547";
+		#address-cells = <1>;
+		#size-cells = <0>;
+		reg = <0x70>;
+		reset-gpios = <&gpio2 18 GPIO_ACTIVE_LOW>;
+
+		i2c4: i2c at 0 {
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <0>;
+		};
+
+		i2c5: i2c at 1 {
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <1>;
+
+			rtc at 30 {
+			       compatible = "sii,s35390a";
+			       reg = <0x30>;
+			};
+
+			temp at 48 {
+				compatible = "ti,tmp112";
+				reg = <0x48>;
+			};
+
+			mma8453q: accelerometer at 1c {
+				compatible = "fsl,mma8453";
+				reg = <0x1c>;
+				interrupt-parent = <&gpio1>;
+				interrupts = <6 IRQ_TYPE_NONE>;
+				interrupt-names = "INT1";
+			};
+
+			mpl3115: pressure-sensor at 60 {
+				compatible = "fsl,mpl3115";
+				reg = <0x60>;
+			};
+
+			eeprom: eeprom at 50 {
+				compatible = "atmel,24c08";
+				reg = <0x50>;
+
+				partitions {
+					compatible = "fixed-partitions";
+
+					vpd {
+						offset = <0>;
+						size = <1022>;
+					};
+
+					bootcount_eeprom: bootcount {
+						offset = <1022>;
+						size = <2>;
+					};
+				};
+			};
+		};
+
+		i2c6: i2c at 2 {
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <2>;
+		};
+
+		i2c7: i2c at 3 {
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <3>;
+		};
+
+		i2c8: i2c at 4 {
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <4>;
+		};
+
+		i2c9: i2c at 5 {
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <5>;
+		};
+
+		i2c10: i2c at 6 {
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <6>;
+		};
+
+		i2c11: i2c at 7 {
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <7>;
+		};
+	};
+};
+
+&i2c2 {
+	pinctrl-names = "default", "gpio";
+	pinctrl-0 = <&pinctrl_i2c2>;
+	pinctrl-1 = <&pinctrl_i2c2_gpio>;
+	sda-gpios = <&gpio3 16 GPIO_ACTIVE_HIGH>;
+	scl-gpios = <&gpio2 30 GPIO_ACTIVE_HIGH>;
+	status = "okay";
+
+	touchscreen at 4b {
+		compatible = "atmel,maxtouch";
+		reset-gpio = <&gpio5 19 GPIO_ACTIVE_HIGH>;
+		reg = <0x4b>;
+		interrupt-parent = <&gpio5>;
+		interrupts = <4 IRQ_TYPE_LEVEL_LOW>;
+	};
+};
+
+&i2c3 {
+	pinctrl-names = "default", "gpio";
+	pinctrl-0 = <&pinctrl_i2c3>;
+	pinctrl-1 = <&pinctrl_i2c3_gpio>;
+	sda-gpios = <&gpio3 18 GPIO_ACTIVE_HIGH>;
+	scl-gpios = <&gpio3 17 GPIO_ACTIVE_HIGH>;
+	status = "okay";
+};
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 11/37] misc: i2c_eeprom: add fixed partitions support
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (9 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 10/37] board: ge: mx53ppd: Add i2c bus descritpion Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 12/37] misc: i2c_eeprom: add size query Robert Beckett
                   ` (25 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Add ability to partition eeprom via devicetree bindings

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 drivers/misc/i2c_eeprom.c | 98 +++++++++++++++++++++++++++++++++++++++
 1 file changed, 98 insertions(+)

diff --git a/drivers/misc/i2c_eeprom.c b/drivers/misc/i2c_eeprom.c
index 8f2349ad5a..7add8fcc0f 100644
--- a/drivers/misc/i2c_eeprom.c
+++ b/drivers/misc/i2c_eeprom.c
@@ -7,6 +7,7 @@
 #include <linux/err.h>
 #include <linux/kernel.h>
 #include <dm.h>
+#include <dm/device-internal.h>
 #include <i2c.h>
 #include <i2c_eeprom.h>
 
@@ -82,6 +83,29 @@ static int i2c_eeprom_std_ofdata_to_platdata(struct udevice *dev)
 	return 0;
 }
 
+static int i2c_eeprom_std_bind(struct udevice *dev)
+{
+	ofnode partitions = ofnode_find_subnode(dev_ofnode(dev), "partitions");
+	ofnode partition;
+	const char *name;
+
+	if (!ofnode_valid(partitions))
+		return 0;
+	if (!ofnode_device_is_compatible(partitions, "fixed-partitions"))
+		return -ENOTSUPP;
+
+	ofnode_for_each_subnode(partition, partitions) {
+		name = ofnode_get_name(partition);
+		if (!name)
+			continue;
+
+		device_bind_ofnode(dev, DM_GET_DRIVER(i2c_eeprom_partition),
+				   name, NULL, partition, NULL);
+	}
+
+	return 0;
+}
+
 static int i2c_eeprom_std_probe(struct udevice *dev)
 {
 	u8 test_byte;
@@ -117,12 +141,86 @@ U_BOOT_DRIVER(i2c_eeprom_std) = {
 	.name			= "i2c_eeprom",
 	.id			= UCLASS_I2C_EEPROM,
 	.of_match		= i2c_eeprom_std_ids,
+	.bind			= i2c_eeprom_std_bind,
 	.probe			= i2c_eeprom_std_probe,
 	.ofdata_to_platdata	= i2c_eeprom_std_ofdata_to_platdata,
 	.priv_auto_alloc_size	= sizeof(struct i2c_eeprom),
 	.ops			= &i2c_eeprom_std_ops,
 };
 
+struct i2c_eeprom_partition {
+	u32 offset;
+	u32 size;
+};
+
+static int i2c_eeprom_partition_probe(struct udevice *dev)
+{
+	return 0;
+}
+
+static int i2c_eeprom_partition_ofdata_to_platdata(struct udevice *dev)
+{
+	struct i2c_eeprom_partition *priv = dev_get_priv(dev);
+	u32 offset, size;
+	int ret;
+
+	ret = dev_read_u32(dev, "offset", &offset);
+	if (ret)
+		return ret;
+
+	ret = dev_read_u32(dev, "size", &size);
+	if (ret)
+		return ret;
+
+	priv->offset = offset;
+	priv->size = size;
+
+	return 0;
+}
+
+static int i2c_eeprom_partition_read(struct udevice *dev, int offset,
+				     u8 *buf, int size)
+{
+	struct i2c_eeprom_partition *priv = dev_get_priv(dev);
+	struct udevice *parent = dev_get_parent(dev);
+
+	if (!parent)
+		return -ENODEV;
+	if (offset + size > priv->size)
+		return -EINVAL;
+
+	return i2c_eeprom_read(parent, offset + priv->offset, buf, size);
+}
+
+static int i2c_eeprom_partition_write(struct udevice *dev, int offset,
+				      const u8 *buf, int size)
+{
+	struct i2c_eeprom_partition *priv = dev_get_priv(dev);
+	struct udevice *parent = dev_get_parent(dev);
+
+	if (!parent)
+		return -ENODEV;
+	if (offset + size > priv->size)
+		return -EINVAL;
+
+	return i2c_eeprom_write(parent, offset + priv->offset, (uint8_t *)buf,
+				size);
+}
+
+static const struct i2c_eeprom_ops i2c_eeprom_partition_ops = {
+	.read	= i2c_eeprom_partition_read,
+	.write	= i2c_eeprom_partition_write,
+};
+
+U_BOOT_DRIVER(i2c_eeprom_partition) = {
+	.name			= "i2c_eeprom_partition",
+	.id			= UCLASS_I2C_EEPROM,
+	.probe			= i2c_eeprom_partition_probe,
+	.ofdata_to_platdata	= i2c_eeprom_partition_ofdata_to_platdata,
+	.priv_auto_alloc_size	= sizeof(struct i2c_eeprom_partition),
+	.ops			= &i2c_eeprom_partition_ops,
+};
+
 UCLASS_DRIVER(i2c_eeprom) = {
 	.id		= UCLASS_I2C_EEPROM,
 	.name		= "i2c_eeprom",
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 12/37] misc: i2c_eeprom: add size query
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (10 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 11/37] misc: i2c_eeprom: add fixed partitions support Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 13/37] board: ge: bx50v3: use DM I2C Robert Beckett
                   ` (24 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Add ability to query size of eeprom device and partitions

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 drivers/misc/i2c_eeprom.c | 145 +++++++++++++++++++++++++++++++++-----
 include/i2c_eeprom.h      |  12 ++++
 2 files changed, 138 insertions(+), 19 deletions(-)

diff --git a/drivers/misc/i2c_eeprom.c b/drivers/misc/i2c_eeprom.c
index 7add8fcc0f..c948ed937a 100644
--- a/drivers/misc/i2c_eeprom.c
+++ b/drivers/misc/i2c_eeprom.c
@@ -11,6 +11,11 @@
 #include <i2c.h>
 #include <i2c_eeprom.h>
 
+struct i2c_eeprom_drv_data {
+	u32 size; /* size in bytes */
+	u32 pagewidth; /* pagesize = 2^pagewidth */
+};
+
 int i2c_eeprom_read(struct udevice *dev, int offset, uint8_t *buf, int size)
 {
 	const struct i2c_eeprom_ops *ops = device_get_ops(dev);
@@ -31,6 +36,16 @@ int i2c_eeprom_write(struct udevice *dev, int offset, uint8_t *buf, int size)
 	return ops->write(dev, offset, buf, size);
 }
 
+int i2c_eeprom_size(struct udevice *dev)
+{
+	const struct i2c_eeprom_ops *ops = device_get_ops(dev);
+
+	if (!ops->size)
+		return -ENOSYS;
+
+	return ops->size(dev);
+}
+
 static int i2c_eeprom_std_read(struct udevice *dev, int offset, uint8_t *buf,
 			       int size)
 {
@@ -60,25 +75,39 @@ static int i2c_eeprom_std_write(struct udevice *dev, int offset,
 	return 0;
 }
 
+static int i2c_eeprom_std_size(struct udevice *dev)
+{
+	struct i2c_eeprom *priv = dev_get_priv(dev);
+
+	return priv->size;
+}
+
 static const struct i2c_eeprom_ops i2c_eeprom_std_ops = {
 	.read	= i2c_eeprom_std_read,
 	.write	= i2c_eeprom_std_write,
+	.size	= i2c_eeprom_std_size,
 };
 
 static int i2c_eeprom_std_ofdata_to_platdata(struct udevice *dev)
 {
 	struct i2c_eeprom *priv = dev_get_priv(dev);
-	u64 data = dev_get_driver_data(dev);
+	struct i2c_eeprom_drv_data *data =
+		(struct i2c_eeprom_drv_data *)dev_get_driver_data(dev);
 	u32 pagesize;
+	u32 size;
 
 	if (dev_read_u32(dev, "pagesize", &pagesize) == 0) {
 		priv->pagesize = pagesize;
-		return 0;
+	} else {
+		/* 6 bit -> page size of up to 2^63 (should be sufficient) */
+		priv->pagewidth = data->pagewidth;
+		priv->pagesize = (1 << priv->pagewidth);
 	}
 
-	/* 6 bit -> page size of up to 2^63 (should be sufficient) */
-	priv->pagewidth = data & 0x3F;
-	priv->pagesize = (1 << priv->pagewidth);
+	if (dev_read_u32(dev, "size", &size) == 0)
+		priv->size = size;
+	else
+		priv->size = data->size;
 
 	return 0;
 }
@@ -119,21 +148,91 @@ static int i2c_eeprom_std_probe(struct udevice *dev)
 	return 0;
 }
 
+static const struct i2c_eeprom_drv_data eeprom_data = {
+	.size = 0,
+	.pagewidth = 0,
+};
+
+static const struct i2c_eeprom_drv_data mc24aa02e48_data = {
+	.size = 256,
+	.pagewidth = 3,
+};
+
+static const struct i2c_eeprom_drv_data atmel24c01a_data = {
+	.size = 128,
+	.pagewidth = 3,
+};
+
+static const struct i2c_eeprom_drv_data atmel24c02_data = {
+	.size = 256,
+	.pagewidth = 3,
+};
+
+static const struct i2c_eeprom_drv_data atmel24c04_data = {
+	.size = 512,
+	.pagewidth = 4,
+};
+
+static const struct i2c_eeprom_drv_data atmel24c08_data = {
+	.size = 1024,
+	.pagewidth = 4,
+};
+
+static const struct i2c_eeprom_drv_data atmel24c08a_data = {
+	.size = 1024,
+	.pagewidth = 4,
+};
+
+static const struct i2c_eeprom_drv_data atmel24c16a_data = {
+	.size = 2048,
+	.pagewidth = 4,
+};
+
+static const struct i2c_eeprom_drv_data atmel24mac402_data = {
+	.size = 256,
+	.pagewidth = 4,
+};
+
+static const struct i2c_eeprom_drv_data atmel24c32_data = {
+	.size = 4096,
+	.pagewidth = 5,
+};
+
+static const struct i2c_eeprom_drv_data atmel24c64_data = {
+	.size = 8192,
+	.pagewidth = 5,
+};
+
+static const struct i2c_eeprom_drv_data atmel24c128_data = {
+	.size = 16384,
+	.pagewidth = 6,
+};
+
+static const struct i2c_eeprom_drv_data atmel24c256_data = {
+	.size = 32768,
+	.pagewidth = 6,
+};
+
+static const struct i2c_eeprom_drv_data atmel24c512_data = {
+	.size = 65536,
+	.pagewidth = 6,
+};
+
 static const struct udevice_id i2c_eeprom_std_ids[] = {
-	{ .compatible = "i2c-eeprom", .data = 0 },
-	{ .compatible = "microchip,24aa02e48", .data = 3 },
-	{ .compatible = "atmel,24c01a", .data = 3 },
-	{ .compatible = "atmel,24c02", .data = 3 },
-	{ .compatible = "atmel,24c04", .data = 4 },
-	{ .compatible = "atmel,24c08", .data = 4 },
-	{ .compatible = "atmel,24c08a", .data = 4 },
-	{ .compatible = "atmel,24c16a", .data = 4 },
-	{ .compatible = "atmel,24mac402", .data = 4 },
-	{ .compatible = "atmel,24c32", .data = 5 },
-	{ .compatible = "atmel,24c64", .data = 5 },
-	{ .compatible = "atmel,24c128", .data = 6 },
-	{ .compatible = "atmel,24c256", .data = 6 },
-	{ .compatible = "atmel,24c512", .data = 6 },
+	{ .compatible = "i2c-eeprom", (ulong)&eeprom_data },
+	{ .compatible = "microchip,24aa02e48", (ulong)&mc24aa02e48_data },
+	{ .compatible = "atmel,24c01a", (ulong)&atmel24c01a_data },
+	{ .compatible = "atmel,24c02", (ulong)&atmel24c02_data },
+	{ .compatible = "atmel,24c04", (ulong)&atmel24c04_data },
+	{ .compatible = "atmel,24c08", (ulong)&atmel24c08_data },
+	{ .compatible = "atmel,24c08a", (ulong)&atmel24c08a_data },
+	{ .compatible = "atmel,24c16a", (ulong)&atmel24c16a_data },
+	{ .compatible = "atmel,24mac402", (ulong)&atmel24mac402_data },
+	{ .compatible = "atmel,24c32", (ulong)&atmel24c32_data },
+	{ .compatible = "atmel,24c64", (ulong)&atmel24c64_data },
+	{ .compatible = "atmel,24c128", (ulong)&atmel24c128_data },
+	{ .compatible = "atmel,24c256", (ulong)&atmel24c256_data },
+	{ .compatible = "atmel,24c512", (ulong)&atmel24c512_data },
 	{ }
 };
 
@@ -207,9 +306,17 @@ static int i2c_eeprom_partition_write(struct udevice *dev, int offset,
 				size);
 }
 
+static int i2c_eeprom_partition_size(struct udevice *dev)
+{
+	struct i2c_eeprom_partition *priv = dev_get_priv(dev);
+
+	return priv->size;
+}
+
 static const struct i2c_eeprom_ops i2c_eeprom_partition_ops = {
 	.read	= i2c_eeprom_partition_read,
 	.write	= i2c_eeprom_partition_write,
+	.size	= i2c_eeprom_partition_size,
 };
 
 U_BOOT_DRIVER(i2c_eeprom_partition) = {
diff --git a/include/i2c_eeprom.h b/include/i2c_eeprom.h
index 0fcdf3831b..b96254ae79 100644
--- a/include/i2c_eeprom.h
+++ b/include/i2c_eeprom.h
@@ -10,6 +10,7 @@ struct i2c_eeprom_ops {
 	int (*read)(struct udevice *dev, int offset, uint8_t *buf, int size);
 	int (*write)(struct udevice *dev, int offset, const uint8_t *buf,
 		     int size);
+	int (*size)(struct udevice *dev);
 };
 
 struct i2c_eeprom {
@@ -17,6 +18,8 @@ struct i2c_eeprom {
 	unsigned long pagesize;
 	/* The EEPROM's page width in bits (pagesize = 2^pagewidth) */
 	unsigned pagewidth;
+	/* The EEPROM's capacity in bytes */
+	unsigned long size;
 };
 
 /*
@@ -43,4 +46,13 @@ int i2c_eeprom_read(struct udevice *dev, int offset, uint8_t *buf, int size);
  */
 int i2c_eeprom_write(struct udevice *dev, int offset, uint8_t *buf, int size);
 
+/*
+ * i2c_eeprom_size() - get size of I2C EEPROM chip
+ *
+ * @dev:	Chip to query
+ *
+ * @return +ve size in bytes on success, -ve on failure
+ */
+int i2c_eeprom_size(struct udevice *dev);
+
 #endif
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 13/37] board: ge: bx50v3: use DM I2C
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (11 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 12/37] misc: i2c_eeprom: add size query Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 14/37] board: ge: mx53ppd: " Robert Beckett
                   ` (23 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Remove old (pre-DM) i2c setup code.
Enable DM i2c.
Enable compat i2c api while we migrate other i2c devices to DM i2c.

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 board/ge/bx50v3/bx50v3.c    | 43 -------------------------------------
 configs/ge_bx50v3_defconfig |  5 +++++
 include/configs/ge_bx50v3.h | 23 --------------------
 3 files changed, 5 insertions(+), 66 deletions(-)

diff --git a/board/ge/bx50v3/bx50v3.c b/board/ge/bx50v3/bx50v3.c
index c29ac5b611..dce76808d7 100644
--- a/board/ge/bx50v3/bx50v3.c
+++ b/board/ge/bx50v3/bx50v3.c
@@ -83,45 +83,6 @@ static iomux_v3_cfg_t const uart4_pads[] = {
 	MX6_PAD_KEY_ROW0__UART4_RX_DATA | MUX_PAD_CTRL(UART_PAD_CTRL),
 };
 
-static struct i2c_pads_info i2c_pad_info1 = {
-	.scl = {
-		.i2c_mode = MX6_PAD_CSI0_DAT9__I2C1_SCL | I2C_PAD,
-		.gpio_mode = MX6_PAD_CSI0_DAT9__GPIO5_IO27 | I2C_PAD,
-		.gp = IMX_GPIO_NR(5, 27)
-	},
-	.sda = {
-		.i2c_mode = MX6_PAD_CSI0_DAT8__I2C1_SDA | I2C_PAD,
-		.gpio_mode = MX6_PAD_CSI0_DAT8__GPIO5_IO26 | I2C_PAD,
-		.gp = IMX_GPIO_NR(5, 26)
-	}
-};
-
-static struct i2c_pads_info i2c_pad_info2 = {
-	.scl = {
-		.i2c_mode = MX6_PAD_KEY_COL3__I2C2_SCL | I2C_PAD,
-		.gpio_mode = MX6_PAD_KEY_COL3__GPIO4_IO12 | I2C_PAD,
-		.gp = IMX_GPIO_NR(4, 12)
-	},
-	.sda = {
-		.i2c_mode = MX6_PAD_KEY_ROW3__I2C2_SDA | I2C_PAD,
-		.gpio_mode = MX6_PAD_KEY_ROW3__GPIO4_IO13 | I2C_PAD,
-		.gp = IMX_GPIO_NR(4, 13)
-	}
-};
-
-static struct i2c_pads_info i2c_pad_info3 = {
-	.scl = {
-		.i2c_mode = MX6_PAD_GPIO_3__I2C3_SCL | I2C_PAD,
-		.gpio_mode = MX6_PAD_GPIO_3__GPIO1_IO03 | I2C_PAD,
-		.gp = IMX_GPIO_NR(1, 3)
-	},
-	.sda = {
-		.i2c_mode = MX6_PAD_GPIO_6__I2C3_SDA | I2C_PAD,
-		.gpio_mode = MX6_PAD_GPIO_6__GPIO1_IO06 | I2C_PAD,
-		.gp = IMX_GPIO_NR(1, 6)
-	}
-};
-
 static void setup_iomux_uart(void)
 {
 	imx_iomux_v3_setup_multiple_pads(uart3_pads, ARRAY_SIZE(uart3_pads));
@@ -489,10 +450,6 @@ static void set_confidx(const struct vpd_cache* vpd)
 
 int board_init(void)
 {
-	setup_i2c(0, CONFIG_SYS_I2C_SPEED, 0x7f, &i2c_pad_info1);
-	setup_i2c(1, CONFIG_SYS_I2C_SPEED, 0x7f, &i2c_pad_info2);
-	setup_i2c(2, CONFIG_SYS_I2C_SPEED, 0x7f, &i2c_pad_info3);
-
 	if (!read_vpd(&vpd, vpd_callback)) {
 		vpd.is_read = true;
 		set_confidx(&vpd);
diff --git a/configs/ge_bx50v3_defconfig b/configs/ge_bx50v3_defconfig
index cddc558484..ff16b2c4f0 100644
--- a/configs/ge_bx50v3_defconfig
+++ b/configs/ge_bx50v3_defconfig
@@ -41,6 +41,11 @@ CONFIG_BOOTCOUNT_EXT=y
 CONFIG_BOOTCOUNT_BOOTLIMIT=10
 CONFIG_SYS_BOOTCOUNT_EXT_DEVPART="1:5"
 CONFIG_DM_GPIO=y
+CONFIG_DM_I2C=y
+CONFIG_DM_I2C_COMPAT=y
+CONFIG_SYS_I2C_MXC=y
+CONFIG_I2C_MUX=y
+CONFIG_I2C_MUX_PCA954x=y
 CONFIG_DM_MMC=y
 CONFIG_SUPPORT_EMMC_BOOT=y
 CONFIG_FSL_USDHC=y
diff --git a/include/configs/ge_bx50v3.h b/include/configs/ge_bx50v3.h
index 7c26608aa7..f5e11aa465 100644
--- a/include/configs/ge_bx50v3.h
+++ b/include/configs/ge_bx50v3.h
@@ -196,29 +196,6 @@
 #define CONFIG_SYS_RTC_BUS_NUM 2
 #define CONFIG_SYS_I2C_RTC_ADDR	0x32
 
-/* I2C Configs */
-#define CONFIG_SYS_I2C
-#define CONFIG_SYS_I2C_MXC
-#define CONFIG_SYS_I2C_SPEED		  100000
-#define CONFIG_SYS_I2C_MXC_I2C1
-#define CONFIG_SYS_I2C_MXC_I2C2
-#define CONFIG_SYS_I2C_MXC_I2C3
-
-#define CONFIG_SYS_NUM_I2C_BUSES        11
-#define CONFIG_SYS_I2C_MAX_HOPS         1
-#define CONFIG_SYS_I2C_BUSES	{	{0, {I2C_NULL_HOP} }, \
-					{1, {I2C_NULL_HOP} }, \
-					{2, {I2C_NULL_HOP} }, \
-					{0, {{I2C_MUX_PCA9547, 0x70, 0} } }, \
-					{0, {{I2C_MUX_PCA9547, 0x70, 1} } }, \
-					{0, {{I2C_MUX_PCA9547, 0x70, 2} } }, \
-					{0, {{I2C_MUX_PCA9547, 0x70, 3} } }, \
-					{0, {{I2C_MUX_PCA9547, 0x70, 4} } }, \
-					{0, {{I2C_MUX_PCA9547, 0x70, 5} } }, \
-					{0, {{I2C_MUX_PCA9547, 0x70, 6} } }, \
-					{0, {{I2C_MUX_PCA9547, 0x70, 7} } }, \
-				}
-
 #define CONFIG_BCH
 
 #endif	/* __GE_BX50V3_CONFIG_H */
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 14/37] board: ge: mx53ppd: use DM I2C
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (12 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 13/37] board: ge: bx50v3: use DM I2C Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 15/37] board: ge: convert vpd to use i2c eeprom Robert Beckett
                   ` (22 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Remove old (pre-DM) i2c setup code. The old iomux setup was setting up
the wrong pins.
Enable DM i2c.
Enable MXC DM i2c driver.
Enable compat i2c api while we migrate other i2c devices to DM i2c.
Define CONFIG_SYS_MALLOC_F_LEN so that DM is available in pre-reloc.
Make GPIO banks available during preloc, since initialisation is done
in board_early_init_f().
Add gpio_request() calls to satisfy the DM_GPIO compatibility API.

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
Signed-off-by: Ian Ray <ian.ray@ge.com>
---
 arch/arm/dts/imx53-ppd.dts       | 20 ++++++++++++++++++
 board/ge/mx53ppd/mx53ppd.c       | 35 +++-----------------------------
 board/ge/mx53ppd/mx53ppd_video.c |  1 +
 configs/mx53ppd_defconfig        |  7 +++++++
 include/configs/mx53ppd.h        | 23 ---------------------
 5 files changed, 31 insertions(+), 55 deletions(-)

diff --git a/arch/arm/dts/imx53-ppd.dts b/arch/arm/dts/imx53-ppd.dts
index 84b20cdc55..18022796e7 100644
--- a/arch/arm/dts/imx53-ppd.dts
+++ b/arch/arm/dts/imx53-ppd.dts
@@ -222,3 +222,23 @@
 	scl-gpios = <&gpio3 17 GPIO_ACTIVE_HIGH>;
 	status = "okay";
 };
+
+&gpio1 {
+	u-boot,dm-pre-reloc;
+};
+
+&gpio2 {
+	u-boot,dm-pre-reloc;
+};
+
+&gpio3 {
+	u-boot,dm-pre-reloc;
+};
+
+&gpio4 {
+	u-boot,dm-pre-reloc;
+};
+
+&gpio5 {
+	u-boot,dm-pre-reloc;
+};
diff --git a/board/ge/mx53ppd/mx53ppd.c b/board/ge/mx53ppd/mx53ppd.c
index ad37995624..c923478809 100644
--- a/board/ge/mx53ppd/mx53ppd.c
+++ b/board/ge/mx53ppd/mx53ppd.c
@@ -124,34 +124,6 @@ static void setup_iomux_fec(void)
 	imx_iomux_v3_setup_multiple_pads(fec_pads, ARRAY_SIZE(fec_pads));
 }
 
-#define I2C_PAD_CTRL	(PAD_CTL_SRE_FAST | PAD_CTL_DSE_HIGH | \
-			 PAD_CTL_PUS_100K_UP | PAD_CTL_ODE)
-
-static void setup_iomux_i2c(void)
-{
-	static const iomux_v3_cfg_t i2c1_pads[] = {
-		NEW_PAD_CTRL(MX53_PAD_CSI0_DAT8__I2C1_SDA, I2C_PAD_CTRL),
-		NEW_PAD_CTRL(MX53_PAD_CSI0_DAT9__I2C1_SCL, I2C_PAD_CTRL),
-	};
-
-	imx_iomux_v3_setup_multiple_pads(i2c1_pads, ARRAY_SIZE(i2c1_pads));
-}
-
-#define I2C_PAD MUX_PAD_CTRL(I2C_PAD_CTRL)
-
-static struct i2c_pads_info i2c_pad_info1 = {
-	.scl = {
-		.i2c_mode = MX53_PAD_EIM_D21__I2C1_SCL | I2C_PAD,
-		.gpio_mode = MX53_PAD_EIM_D28__GPIO3_28 | I2C_PAD,
-		.gp = IMX_GPIO_NR(3, 28)
-	},
-	.sda = {
-		.i2c_mode = MX53_PAD_EIM_D28__I2C1_SDA | I2C_PAD,
-		.gpio_mode = MX53_PAD_EIM_D21__GPIO3_21 | I2C_PAD,
-		.gp = IMX_GPIO_NR(3, 21)
-	}
-};
-
 static int clock_1GHz(void)
 {
 	int ret;
@@ -181,8 +153,10 @@ void ppd_gpio_init(void)
 	int i;
 
 	imx_iomux_v3_setup_multiple_pads(ppd_pads, ARRAY_SIZE(ppd_pads));
-	for (i = 0; i < ARRAY_SIZE(ppd_gpios); ++i)
+	for (i = 0; i < ARRAY_SIZE(ppd_gpios); ++i) {
+		gpio_request(ppd_gpios[i].gpio, "request");
 		gpio_direction_output(ppd_gpios[i].gpio, ppd_gpios[i].value);
+	}
 }
 
 int board_early_init_f(void)
@@ -255,9 +229,6 @@ int board_init(void)
 	gd->bd->bi_boot_params = PHYS_SDRAM_1 + 0x100;
 
 	mxc_set_sata_internal_clock();
-	setup_iomux_i2c();
-
-	setup_i2c(1, CONFIG_SYS_I2C_SPEED, 0x7f, &i2c_pad_info1);
 
 	return 0;
 }
diff --git a/board/ge/mx53ppd/mx53ppd_video.c b/board/ge/mx53ppd/mx53ppd_video.c
index 394dcd6801..9dd9f0c98d 100644
--- a/board/ge/mx53ppd/mx53ppd_video.c
+++ b/board/ge/mx53ppd/mx53ppd_video.c
@@ -104,6 +104,7 @@ static void lcd_enable(void)
 	pwm_config(1, 5000000, 5000000);
 
 	/* Backlight Power */
+	gpio_request(BACKLIGHT_ENABLE, "BACKLIGHT_ENABLE");
 	gpio_direction_output(BACKLIGHT_ENABLE, 1);
 
 	pwm_enable(1);
diff --git a/configs/mx53ppd_defconfig b/configs/mx53ppd_defconfig
index 8822b74864..b8cb599491 100644
--- a/configs/mx53ppd_defconfig
+++ b/configs/mx53ppd_defconfig
@@ -38,6 +38,12 @@ CONFIG_BOOTCOUNT_LIMIT=y
 CONFIG_BOOTCOUNT_EXT=y
 CONFIG_BOOTCOUNT_BOOTLIMIT=10
 CONFIG_SYS_BOOTCOUNT_EXT_DEVPART="0:5"
+CONFIG_DM_GPIO=y
+CONFIG_DM_I2C=y
+CONFIG_DM_I2C_COMPAT=y
+CONFIG_SYS_I2C_MXC=y
+CONFIG_I2C_MUX=y
+CONFIG_I2C_MUX_PCA954x=y
 CONFIG_DM_MMC=y
 CONFIG_FSL_ESDHC_IMX=y
 CONFIG_MII=y
@@ -57,3 +63,4 @@ CONFIG_SYSRESET=y
 CONFIG_SYSRESET_WATCHDOG=y
 CONFIG_DM_REGULATOR=y
 CONFIG_DM_USB=y
+CONFIG_SYS_MALLOC_F_LEN=0x4000
diff --git a/include/configs/mx53ppd.h b/include/configs/mx53ppd.h
index 26e4b729bb..be4336e3a9 100644
--- a/include/configs/mx53ppd.h
+++ b/include/configs/mx53ppd.h
@@ -46,13 +46,6 @@
 #define CONFIG_SYS_RTC_BUS_NUM		2
 #define CONFIG_SYS_I2C_RTC_ADDR	0x30
 
-/* I2C Configs */
-#define CONFIG_SYS_I2C
-#define CONFIG_SYS_I2C_MXC
-#define CONFIG_SYS_I2C_MXC_I2C1		/* enable I2C bus 1 */
-#define CONFIG_SYS_I2C_MXC_I2C2		/* enable I2C bus 2 */
-#define CONFIG_SYS_I2C_MXC_I2C3		/* enable I2C bus 3 */
-
 /* PMIC Controller */
 #define CONFIG_POWER
 #define CONFIG_POWER_I2C
@@ -190,22 +183,6 @@
 #define CONFIG_CMD_FUSE
 #define CONFIG_FSL_IIM
 
-#define CONFIG_SYS_I2C_SPEED	100000
-
-/* I2C1 */
-#define CONFIG_SYS_NUM_I2C_BUSES	9
-#define CONFIG_SYS_I2C_MAX_HOPS		1
-#define CONFIG_SYS_I2C_BUSES	{	{0, {I2C_NULL_HOP} }, \
-					{0, {{I2C_MUX_PCA9547, 0x70, 0} } }, \
-					{0, {{I2C_MUX_PCA9547, 0x70, 1} } }, \
-					{0, {{I2C_MUX_PCA9547, 0x70, 2} } }, \
-					{0, {{I2C_MUX_PCA9547, 0x70, 3} } }, \
-					{0, {{I2C_MUX_PCA9547, 0x70, 4} } }, \
-					{0, {{I2C_MUX_PCA9547, 0x70, 5} } }, \
-					{0, {{I2C_MUX_PCA9547, 0x70, 6} } }, \
-					{0, {{I2C_MUX_PCA9547, 0x70, 7} } }, \
-				}
-
 #define CONFIG_BCH
 
 /* Backlight Control */
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 15/37] board: ge: convert vpd to use i2c eeprom
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (13 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 14/37] board: ge: mx53ppd: " Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 16/37] i2c: add support for offset overflow in to address Robert Beckett
                   ` (21 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

convert vpd reader to use DM i2c eeprom driver.
remove old VPD definitions.

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 board/ge/bx50v3/Kconfig      |  2 --
 board/ge/common/Kconfig      | 14 --------------
 board/ge/common/vpd_reader.c | 37 ++++++++++++++++++++++--------------
 board/ge/mx53ppd/Kconfig     |  2 --
 configs/ge_bx50v3_defconfig  |  5 ++---
 configs/mx53ppd_defconfig    |  3 ---
 6 files changed, 25 insertions(+), 38 deletions(-)
 delete mode 100644 board/ge/common/Kconfig

diff --git a/board/ge/bx50v3/Kconfig b/board/ge/bx50v3/Kconfig
index 05938560ab..993b055930 100644
--- a/board/ge/bx50v3/Kconfig
+++ b/board/ge/bx50v3/Kconfig
@@ -15,6 +15,4 @@ config SYS_SOC
 config SYS_CONFIG_NAME
 	default "ge_bx50v3"
 
-source "board/ge/common/Kconfig"
-
 endif
diff --git a/board/ge/common/Kconfig b/board/ge/common/Kconfig
deleted file mode 100644
index 637b264954..0000000000
--- a/board/ge/common/Kconfig
+++ /dev/null
@@ -1,14 +0,0 @@
-config SYS_VPD_EEPROM_I2C_ADDR
-	hex "I2C address of the EEPROM device used for VPD"
-	help
-	  VPD = Vital Product Data
-
-config SYS_VPD_EEPROM_I2C_BUS
-	int "I2C bus of the EEPROM device used for VPD."
-
-config SYS_VPD_EEPROM_SIZE
-	int "Size in bytes of the EEPROM device used for VPD"
-
-config SYS_VPD_EEPROM_I2C_ADDR_LEN
-	int "Number of bytes to use for VPD EEPROM address"
-	default 1
diff --git a/board/ge/common/vpd_reader.c b/board/ge/common/vpd_reader.c
index 12410d9b71..4df411cf10 100644
--- a/board/ge/common/vpd_reader.c
+++ b/board/ge/common/vpd_reader.c
@@ -8,6 +8,9 @@
 #include <i2c.h>
 #include <linux/bch.h>
 #include <stdlib.h>
+#include <dm/uclass.h>
+#include <i2c_eeprom.h>
+#include <hexdump.h>
 
 /* BCH configuration */
 
@@ -200,28 +203,34 @@ int read_vpd(struct vpd_cache *cache,
 	     int (*process_block)(struct vpd_cache *, u8 id, u8 version,
 				  u8 type, size_t size, u8 const *data))
 {
-	static const size_t size = CONFIG_SYS_VPD_EEPROM_SIZE;
-
-	int res;
+	struct udevice *dev;
+	int ret;
 	u8 *data;
-	unsigned int current_i2c_bus = i2c_get_bus_num();
+	int size;
+
+	ret = uclass_get_device_by_name(UCLASS_I2C_EEPROM, "vpd", &dev);
+	if (ret)
+		return ret;
 
-	res = i2c_set_bus_num(CONFIG_SYS_VPD_EEPROM_I2C_BUS);
-	if (res < 0)
-		return res;
+	size = i2c_eeprom_size(dev);
+	if (size < 0) {
+		printf("Unable to get size of eeprom: %d\n", ret);
+		return ret;
+	}
 
 	data = malloc(size);
 	if (!data)
 		return -ENOMEM;
 
-	res = i2c_read(CONFIG_SYS_VPD_EEPROM_I2C_ADDR, 0,
-		       CONFIG_SYS_VPD_EEPROM_I2C_ADDR_LEN,
-		       data, size);
-	if (res == 0)
-		res = vpd_reader(size, data, cache, process_block);
+	ret = i2c_eeprom_read(dev, 0, data, size);
+	if (ret) {
+		free(data);
+		return ret;
+	}
+
+	ret = vpd_reader(size, data, cache, process_block);
 
 	free(data);
 
-	i2c_set_bus_num(current_i2c_bus);
-	return res;
+	return ret;
 }
diff --git a/board/ge/mx53ppd/Kconfig b/board/ge/mx53ppd/Kconfig
index bebb2fab01..6dc3818cb7 100644
--- a/board/ge/mx53ppd/Kconfig
+++ b/board/ge/mx53ppd/Kconfig
@@ -13,6 +13,4 @@ config SYS_SOC
 config SYS_CONFIG_NAME
 	default "mx53ppd"
 
-source "board/ge/common/Kconfig"
-
 endif
diff --git a/configs/ge_bx50v3_defconfig b/configs/ge_bx50v3_defconfig
index ff16b2c4f0..937b6af9fa 100644
--- a/configs/ge_bx50v3_defconfig
+++ b/configs/ge_bx50v3_defconfig
@@ -1,9 +1,6 @@
 CONFIG_ARM=y
 CONFIG_ARCH_MX6=y
 CONFIG_SYS_TEXT_BASE=0x17800000
-CONFIG_SYS_VPD_EEPROM_I2C_ADDR=0x50
-CONFIG_SYS_VPD_EEPROM_I2C_BUS=4
-CONFIG_SYS_VPD_EEPROM_SIZE=1024
 CONFIG_TARGET_GE_BX50V3=y
 CONFIG_NR_DRAM_BANKS=1
 CONFIG_SYS_BOOTCOUNT_ADDR=0x7000A000
@@ -46,6 +43,8 @@ CONFIG_DM_I2C_COMPAT=y
 CONFIG_SYS_I2C_MXC=y
 CONFIG_I2C_MUX=y
 CONFIG_I2C_MUX_PCA954x=y
+CONFIG_MISC=y
+CONFIG_I2C_EEPROM=y
 CONFIG_DM_MMC=y
 CONFIG_SUPPORT_EMMC_BOOT=y
 CONFIG_FSL_USDHC=y
diff --git a/configs/mx53ppd_defconfig b/configs/mx53ppd_defconfig
index b8cb599491..1de43b7126 100644
--- a/configs/mx53ppd_defconfig
+++ b/configs/mx53ppd_defconfig
@@ -2,9 +2,6 @@ CONFIG_ARM=y
 CONFIG_ARCH_MX5=y
 CONFIG_SYS_TEXT_BASE=0x77800000
 CONFIG_TARGET_MX53PPD=y
-CONFIG_SYS_VPD_EEPROM_I2C_ADDR=0x50
-CONFIG_SYS_VPD_EEPROM_I2C_BUS=2
-CONFIG_SYS_VPD_EEPROM_SIZE=1024
 CONFIG_NR_DRAM_BANKS=2
 CONFIG_SYS_BOOTCOUNT_ADDR=0x7000A000
 CONFIG_FIT=y
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 16/37] i2c: add support for offset overflow in to address
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (14 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 15/37] board: ge: convert vpd to use i2c eeprom Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-16  3:40   ` Simon Glass
  2019-10-15 15:53 ` [U-Boot] [PATCH 17/37] misc: i2c_eeprom: set offset len and chip addr offset mask Robert Beckett
                   ` (20 subsequent siblings)
  36 siblings, 1 reply; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Some devices (2 wire eeproms for example) use some bits from the chip
address to represent the high bits of the offset instead of or as well
as using multiple bytes for the offset, effectively stealing chip
addresses on the bus.

Add a chip offset mask that can be set for any i2c chip which gets
filled with the offset overflow during offset setup.

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
Signed-off-by: Ian Ray <ian.ray@ge.com>
---
 drivers/i2c/i2c-uclass.c | 32 ++++++++++++++++++++++++++------
 include/i2c.h            | 24 ++++++++++++++++++++++++
 2 files changed, 50 insertions(+), 6 deletions(-)

diff --git a/drivers/i2c/i2c-uclass.c b/drivers/i2c/i2c-uclass.c
index e47abf1833..7580867dc1 100644
--- a/drivers/i2c/i2c-uclass.c
+++ b/drivers/i2c/i2c-uclass.c
@@ -52,16 +52,19 @@ void i2c_dump_msgs(struct i2c_msg *msg, int nmsgs)
 static int i2c_setup_offset(struct dm_i2c_chip *chip, uint offset,
 			    uint8_t offset_buf[], struct i2c_msg *msg)
 {
-	int offset_len;
+	int offset_len = chip->offset_len;
 
 	msg->addr = chip->chip_addr;
+	if (chip->chip_addr_offset_mask)
+		msg->addr |= (offset >> (8 * offset_len)) &
+			chip->chip_addr_offset_mask;
 	msg->flags = chip->flags & DM_I2C_CHIP_10BIT ? I2C_M_TEN : 0;
 	msg->len = chip->offset_len;
 	msg->buf = offset_buf;
-	if (!chip->offset_len)
+	if (!offset_len)
 		return -EADDRNOTAVAIL;
-	assert(chip->offset_len <= I2C_MAX_OFFSET_LEN);
-	offset_len = chip->offset_len;
+	assert(offset_len <= I2C_MAX_OFFSET_LEN);
+
 	while (offset_len--)
 		*offset_buf++ = offset >> (8 * offset_len);
 
@@ -83,7 +86,7 @@ static int i2c_read_bytewise(struct udevice *dev, uint offset,
 		if (i2c_setup_offset(chip, offset + i, offset_buf, msg))
 			return -EINVAL;
 		ptr = msg + 1;
-		ptr->addr = chip->chip_addr;
+		ptr->addr = msg->addr;
 		ptr->flags = msg->flags | I2C_M_RD;
 		ptr->len = 1;
 		ptr->buf = &buffer[i];
@@ -132,6 +135,7 @@ int dm_i2c_read(struct udevice *dev, uint offset, uint8_t *buffer, int len)
 
 	if (!ops->xfer)
 		return -ENOSYS;
+
 	if (chip->flags & DM_I2C_CHIP_RD_ADDRESS)
 		return i2c_read_bytewise(dev, offset, buffer, len);
 	ptr = msg;
@@ -139,7 +143,7 @@ int dm_i2c_read(struct udevice *dev, uint offset, uint8_t *buffer, int len)
 		ptr++;
 
 	if (len) {
-		ptr->addr = chip->chip_addr;
+		ptr->addr = msg->addr;
 		ptr->flags = chip->flags & DM_I2C_CHIP_10BIT ? I2C_M_TEN : 0;
 		ptr->flags |= I2C_M_RD;
 		ptr->len = len;
@@ -465,6 +469,22 @@ int i2c_get_chip_offset_len(struct udevice *dev)
 	return chip->offset_len;
 }
 
+int i2c_set_chip_addr_offset_mask(struct udevice *dev, uint mask)
+{
+	struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
+
+	chip->chip_addr_offset_mask = mask;
+
+	return 0;
+}
+
+uint i2c_get_chip_addr_offset_mask(struct udevice *dev)
+{
+	struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
+
+	return chip->chip_addr_offset_mask;
+}
+
 #ifdef CONFIG_DM_GPIO
 static void i2c_gpio_set_pin(struct gpio_desc *pin, int bit)
 {
diff --git a/include/i2c.h b/include/i2c.h
index 33570f5404..3c927340da 100644
--- a/include/i2c.h
+++ b/include/i2c.h
@@ -45,12 +45,17 @@ struct udevice;
  *		represent up to 256 bytes. A value larger than 1 may be
  *		needed for larger devices.
  * @flags:	Flags for this chip (dm_i2c_chip_flags)
+ * @chip_addr_offset_mask: Mask of offset bits within chip_addr. Used for
+ *			   devices which steal addresses as part of offset.
+ *			   If offset_len is zero, then the offset is encoded
+ *			   completely within the chip address itself.
  * @emul: Emulator for this chip address (only used for emulation)
  */
 struct dm_i2c_chip {
 	uint chip_addr;
 	uint offset_len;
 	uint flags;
+	uint chip_addr_offset_mask;
 #ifdef CONFIG_SANDBOX
 	struct udevice *emul;
 	bool test_mode;
@@ -261,6 +266,25 @@ int i2c_set_chip_offset_len(struct udevice *dev, uint offset_len);
  */
 int i2c_get_chip_offset_len(struct udevice *dev);
 
+/**
+ * i2c_set_chip_addr_offset_mask() - set mask of address bits usable by offset
+ *
+ * Some devices listen on multiple chip addresses to achieve larger offsets
+ * than their single or multiple byte offsets would allow for. You can use this
+ * function to set the bits that are valid to be used for offset overflow.
+ *
+ * @mask: The mask to be used for high offset bits within address
+ * @return 0 if OK, other -ve value on error
+ */
+int i2c_set_chip_addr_offset_mask(struct udevice *dev, uint mask);
+
+/*
+ * i2c_get_chip_addr_offset_mask() - get mask of address bits usable by offset
+ *
+ * @return current chip addr offset mask
+ */
+uint i2c_get_chip_addr_offset_mask(struct udevice *dev);
+
 /**
  * i2c_deblock() - recover a bus that is in an unknown state
  *
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 17/37] misc: i2c_eeprom: set offset len and chip addr offset mask
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (15 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 16/37] i2c: add support for offset overflow in to address Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 18/37] bootcount: add a DM i2c eeprom backing store for bootcount Robert Beckett
                   ` (19 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Set the correct offset length and chip address offset mask for each
device to allow correct access to total capacity of the devices.

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 drivers/misc/i2c_eeprom.c | 35 +++++++++++++++++++++++++++++++++++
 1 file changed, 35 insertions(+)

diff --git a/drivers/misc/i2c_eeprom.c b/drivers/misc/i2c_eeprom.c
index c948ed937a..9ce4757b30 100644
--- a/drivers/misc/i2c_eeprom.c
+++ b/drivers/misc/i2c_eeprom.c
@@ -14,6 +14,8 @@
 struct i2c_eeprom_drv_data {
 	u32 size; /* size in bytes */
 	u32 pagewidth; /* pagesize = 2^pagewidth */
+	u32 addr_offset_mask; /* bits in addr used for offset overflow */
+	u32 offset_len; /* size in bytes of offset */
 };
 
 int i2c_eeprom_read(struct udevice *dev, int offset, uint8_t *buf, int size)
@@ -139,6 +141,11 @@ static int i2c_eeprom_std_probe(struct udevice *dev)
 {
 	u8 test_byte;
 	int ret;
+	struct i2c_eeprom_drv_data *data =
+		(struct i2c_eeprom_drv_data *)dev_get_driver_data(dev);
+
+	i2c_set_chip_offset_len(dev, data->offset_len);
+	i2c_set_chip_addr_offset_mask(dev, data->addr_offset_mask);
 
 	/* Verify that the chip is functional */
 	ret = i2c_eeprom_read(dev, 0, &test_byte, 1);
@@ -151,71 +158,99 @@ static int i2c_eeprom_std_probe(struct udevice *dev)
 static const struct i2c_eeprom_drv_data eeprom_data = {
 	.size = 0,
 	.pagewidth = 0,
+	.addr_offset_mask = 0,
+	.offset_len = 1,
 };
 
 static const struct i2c_eeprom_drv_data mc24aa02e48_data = {
 	.size = 256,
 	.pagewidth = 3,
+	.addr_offset_mask = 0,
+	.offset_len = 1,
 };
 
 static const struct i2c_eeprom_drv_data atmel24c01a_data = {
 	.size = 128,
 	.pagewidth = 3,
+	.addr_offset_mask = 0,
+	.offset_len = 1,
 };
 
 static const struct i2c_eeprom_drv_data atmel24c02_data = {
 	.size = 256,
 	.pagewidth = 3,
+	.addr_offset_mask = 0,
+	.offset_len = 1,
 };
 
 static const struct i2c_eeprom_drv_data atmel24c04_data = {
 	.size = 512,
 	.pagewidth = 4,
+	.addr_offset_mask = 0x1,
+	.offset_len = 1,
 };
 
 static const struct i2c_eeprom_drv_data atmel24c08_data = {
 	.size = 1024,
 	.pagewidth = 4,
+	.addr_offset_mask = 0x3,
+	.offset_len = 1,
 };
 
 static const struct i2c_eeprom_drv_data atmel24c08a_data = {
 	.size = 1024,
 	.pagewidth = 4,
+	.addr_offset_mask = 0x3,
+	.offset_len = 1,
 };
 
 static const struct i2c_eeprom_drv_data atmel24c16a_data = {
 	.size = 2048,
 	.pagewidth = 4,
+	.addr_offset_mask = 0x7,
+	.offset_len = 1,
 };
 
 static const struct i2c_eeprom_drv_data atmel24mac402_data = {
 	.size = 256,
 	.pagewidth = 4,
+	.addr_offset_mask = 0,
+	.offset_len = 1,
 };
 
 static const struct i2c_eeprom_drv_data atmel24c32_data = {
 	.size = 4096,
 	.pagewidth = 5,
+	.addr_offset_mask = 0,
+	.offset_len = 2,
 };
 
 static const struct i2c_eeprom_drv_data atmel24c64_data = {
 	.size = 8192,
 	.pagewidth = 5,
+	.addr_offset_mask = 0,
+	.offset_len = 2,
 };
 
 static const struct i2c_eeprom_drv_data atmel24c128_data = {
 	.size = 16384,
 	.pagewidth = 6,
+	.addr_offset_mask = 0,
+	.offset_len = 2,
 };
 
 static const struct i2c_eeprom_drv_data atmel24c256_data = {
 	.size = 32768,
 	.pagewidth = 6,
+	.addr_offset_mask = 0,
+	.offset_len = 2,
 };
 
 static const struct i2c_eeprom_drv_data atmel24c512_data = {
 	.size = 65536,
 	.pagewidth = 6,
+	.addr_offset_mask = 0,
+	.offset_len = 2,
 };
 
 static const struct udevice_id i2c_eeprom_std_ids[] = {
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 18/37] bootcount: add a DM i2c eeprom backing store for bootcount
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (16 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 17/37] misc: i2c_eeprom: set offset len and chip addr offset mask Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 19/37] board: ge: bx50v3: add i2c eeprom bootcount storage Robert Beckett
                   ` (18 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

This driver allows the use of i2c eeprom device or partition as backing
store for boot counter values with DM enabled.

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 drivers/bootcount/Kconfig      | 10 ++++
 drivers/bootcount/Makefile     |  1 +
 drivers/bootcount/i2c-eeprom.c | 95 ++++++++++++++++++++++++++++++++++
 3 files changed, 106 insertions(+)
 create mode 100644 drivers/bootcount/i2c-eeprom.c

diff --git a/drivers/bootcount/Kconfig b/drivers/bootcount/Kconfig
index b7c29f2fd3..0e506c9ea2 100644
--- a/drivers/bootcount/Kconfig
+++ b/drivers/bootcount/Kconfig
@@ -96,6 +96,16 @@ config DM_BOOTCOUNT_RTC
 	  Accesses to the backing store are performed using the write16
 	  and read16 ops of DM RTC devices.
 
+config DM_BOOTCOUNT_I2C_EEPROM
+	bool "Support i2c eeprom devices as a backing store for bootcount"
+	depends on I2C_EEPROM
+	help
+	  Enabled reading/writing the bootcount in a DM i2c eeprom device.
+	  The wrapper device is to be specified with the compatible string
+	  'u-boot,bootcount-i2c-eeprom' and the 'i2c-eeprom'-property (a phandle
+	  pointing to the underlying i2c eeprom device) and an optional 'offset'
+	  property are supported.
+
 endmenu
 
 endif
diff --git a/drivers/bootcount/Makefile b/drivers/bootcount/Makefile
index f9841d8615..73ccfb5a08 100644
--- a/drivers/bootcount/Makefile
+++ b/drivers/bootcount/Makefile
@@ -10,3 +10,4 @@ obj-$(CONFIG_BOOTCOUNT_EXT)	+= bootcount_ext.o
 
 obj-$(CONFIG_DM_BOOTCOUNT)      += bootcount-uclass.o
 obj-$(CONFIG_DM_BOOTCOUNT_RTC)  += rtc.o
+obj-$(CONFIG_DM_BOOTCOUNT_I2C_EEPROM)	+= i2c-eeprom.o
diff --git a/drivers/bootcount/i2c-eeprom.c b/drivers/bootcount/i2c-eeprom.c
new file mode 100644
index 0000000000..ee760a2742
--- /dev/null
+++ b/drivers/bootcount/i2c-eeprom.c
@@ -0,0 +1,95 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * (C) Copyright 2019 Collabora
+ * (C) Copyright 2019 GE
+ */
+
+#include <common.h>
+#include <bootcount.h>
+#include <dm.h>
+#include <i2c_eeprom.h>
+
+static const u8 bootcount_magic = 0xbc;
+
+struct bootcount_i2c_eeprom_priv {
+	struct udevice *i2c_eeprom;
+	u32 offset;
+};
+
+static int bootcount_i2c_eeprom_set(struct udevice *dev, const u32 a)
+{
+	struct bootcount_i2c_eeprom_priv *priv = dev_get_priv(dev);
+	const u16 val = bootcount_magic << 8 | (a & 0xff);
+
+	if (i2c_eeprom_write(priv->i2c_eeprom, priv->offset,
+			     (uint8_t *)&val, 2) < 0) {
+		debug("%s: write failed\n", __func__);
+		return -EIO;
+	}
+
+	return 0;
+}
+
+static int bootcount_i2c_eeprom_get(struct udevice *dev, u32 *a)
+{
+	struct bootcount_i2c_eeprom_priv *priv = dev_get_priv(dev);
+	u16 val;
+
+	if (i2c_eeprom_read(priv->i2c_eeprom, priv->offset,
+			    (uint8_t *)&val, 2) < 0) {
+		debug("%s: read failed\n", __func__);
+		return -EIO;
+	}
+
+	if (val >> 8 == bootcount_magic) {
+		*a = val & 0xff;
+		return 0;
+	}
+
+	debug("%s: bootcount magic does not match on %04x\n", __func__, val);
+	return -EIO;
+}
+
+static int bootcount_i2c_eeprom_probe(struct udevice *dev)
+{
+	struct ofnode_phandle_args phandle_args;
+	struct bootcount_i2c_eeprom_priv *priv = dev_get_priv(dev);
+	struct udevice *i2c_eeprom;
+
+	if (dev_read_phandle_with_args(dev, "i2c-eeprom", NULL, 0, 0,
+				       &phandle_args)) {
+		debug("%s: i2c-eeprom backing device not specified\n",
+		      dev->name);
+		return -ENOENT;
+	}
+
+	if (uclass_get_device_by_ofnode(UCLASS_I2C_EEPROM, phandle_args.node,
+					&i2c_eeprom)) {
+		debug("%s: could not get backing device\n", dev->name);
+		return -ENODEV;
+	}
+
+	priv->i2c_eeprom = i2c_eeprom;
+	priv->offset = dev_read_u32_default(dev, "offset", 0);
+
+	return 0;
+}
+
+static const struct bootcount_ops bootcount_i2c_eeprom_ops = {
+	.get = bootcount_i2c_eeprom_get,
+	.set = bootcount_i2c_eeprom_set,
+};
+
+static const struct udevice_id bootcount_i2c_eeprom_ids[] = {
+	{ .compatible = "u-boot,bootcount-i2c-eeprom" },
+	{ }
+};
+
+U_BOOT_DRIVER(bootcount_spi_flash) = {
+	.name	= "bootcount-i2c-eeprom",
+	.id	= UCLASS_BOOTCOUNT,
+	.priv_auto_alloc_size = sizeof(struct bootcount_i2c_eeprom_priv),
+	.probe	= bootcount_i2c_eeprom_probe,
+	.of_match = bootcount_i2c_eeprom_ids,
+	.ops	= &bootcount_i2c_eeprom_ops,
+};
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 19/37] board: ge: bx50v3: add i2c eeprom bootcount storage
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (17 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 18/37] bootcount: add a DM i2c eeprom backing store for bootcount Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 20/37] board: ge: mx53ppd: " Robert Beckett
                   ` (17 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Add bootcount node, linking to i2c eeprom "bootcount" partitions for
storage.
Enable i2c eeprom bootcount backend storage.
Enable bootcount command and use it for failbootcmd.

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 arch/arm/dts/imx6q-bx50v3.dts | 7 ++++++-
 configs/ge_bx50v3_defconfig   | 6 +++---
 include/configs/ge_bx50v3.h   | 4 +---
 3 files changed, 10 insertions(+), 7 deletions(-)

diff --git a/arch/arm/dts/imx6q-bx50v3.dts b/arch/arm/dts/imx6q-bx50v3.dts
index 4dd2ce3038..4d40980254 100644
--- a/arch/arm/dts/imx6q-bx50v3.dts
+++ b/arch/arm/dts/imx6q-bx50v3.dts
@@ -18,6 +18,11 @@
 		ethernet0 = &fec;
 	};
 
+	bootcount {
+		compatible = "u-boot,bootcount-i2c-eeprom";
+		i2c-eeprom = <&bootcount_eeprom>;
+	};
+
 	wdt-reboot {
 		compatible = "wdt-reboot";
 		wdt = <&wdog1>;
@@ -250,7 +255,7 @@
 						size = <1022>;
 					};
 
-					bootcount {
+					bootcount_eeprom: bootcount {
 						offset = <1022>;
 						size = <2>;
 					};
diff --git a/configs/ge_bx50v3_defconfig b/configs/ge_bx50v3_defconfig
index 937b6af9fa..519b3e1bb1 100644
--- a/configs/ge_bx50v3_defconfig
+++ b/configs/ge_bx50v3_defconfig
@@ -3,7 +3,6 @@ CONFIG_ARCH_MX6=y
 CONFIG_SYS_TEXT_BASE=0x17800000
 CONFIG_TARGET_GE_BX50V3=y
 CONFIG_NR_DRAM_BANKS=1
-CONFIG_SYS_BOOTCOUNT_ADDR=0x7000A000
 # CONFIG_SYS_MALLOC_CLEAR_ON_INIT is not set
 CONFIG_FIT=y
 CONFIG_OF_BOARD_SETUP=y
@@ -23,6 +22,7 @@ CONFIG_CMD_MMC=y
 CONFIG_CMD_PCI=y
 CONFIG_CMD_SF=y
 # CONFIG_CMD_NFS is not set
+CONFIG_CMD_BOOTCOUNT=y
 CONFIG_CMD_CACHE=y
 CONFIG_CMD_EXT2=y
 CONFIG_CMD_EXT4=y
@@ -34,9 +34,9 @@ CONFIG_DEFAULT_DEVICE_TREE="imx6q-bx50v3"
 CONFIG_ENV_IS_IN_SPI_FLASH=y
 CONFIG_DM=y
 CONFIG_BOOTCOUNT_LIMIT=y
-CONFIG_BOOTCOUNT_EXT=y
+CONFIG_DM_BOOTCOUNT=y
+CONFIG_DM_BOOTCOUNT_I2C_EEPROM=y
 CONFIG_BOOTCOUNT_BOOTLIMIT=10
-CONFIG_SYS_BOOTCOUNT_EXT_DEVPART="1:5"
 CONFIG_DM_GPIO=y
 CONFIG_DM_I2C=y
 CONFIG_DM_I2C_COMPAT=y
diff --git a/include/configs/ge_bx50v3.h b/include/configs/ge_bx50v3.h
index f5e11aa465..b2c114409d 100644
--- a/include/configs/ge_bx50v3.h
+++ b/include/configs/ge_bx50v3.h
@@ -109,9 +109,7 @@
 		"setcurs 5 4; " \
 		"lcdputs \"Monitor failed to start. " \
 		"Try again, or contact GE Service for support.\"; " \
-		"mw.b 0x7000A000 0xbc; " \
-		"mw.b 0x7000A001 0x00; " \
-		"ext4write ${dev} ${devnum}:5 0x7000A000 /boot/failures 2\0" \
+		"bootcount reset; \0" \
 	"altbootcmd=" \
 		"run doquiet; " \
 		"setenv partnum 1; run hasfirstboot || setenv partnum 2; " \
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 20/37] board: ge: mx53ppd: add i2c eeprom bootcount storage
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (18 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 19/37] board: ge: bx50v3: add i2c eeprom bootcount storage Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 21/37] rtc: rx8010sj: fix DM initialization Robert Beckett
                   ` (16 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Add bootcount node, linking to i2c eeprom "bootcount" partitions for
storage.
Enable i2c eeprom bootcount backend storage.
Enable bootcount command and use it for failbootcmd.

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 arch/arm/dts/imx53-ppd.dts | 5 +++++
 configs/mx53ppd_defconfig  | 8 +++++---
 include/configs/mx53ppd.h  | 4 +---
 3 files changed, 11 insertions(+), 6 deletions(-)

diff --git a/arch/arm/dts/imx53-ppd.dts b/arch/arm/dts/imx53-ppd.dts
index 18022796e7..3a3192d5e8 100644
--- a/arch/arm/dts/imx53-ppd.dts
+++ b/arch/arm/dts/imx53-ppd.dts
@@ -16,6 +16,11 @@
 		compatible = "wdt-reboot";
 		wdt = <&wdog1>;
 	};
+
+	bootcount {
+		compatible = "u-boot,bootcount-i2c-eeprom";
+		i2c-eeprom = <&bootcount_eeprom>;
+	};
 };
 
 &iomuxc {
diff --git a/configs/mx53ppd_defconfig b/configs/mx53ppd_defconfig
index 1de43b7126..db00481266 100644
--- a/configs/mx53ppd_defconfig
+++ b/configs/mx53ppd_defconfig
@@ -3,7 +3,6 @@ CONFIG_ARCH_MX5=y
 CONFIG_SYS_TEXT_BASE=0x77800000
 CONFIG_TARGET_MX53PPD=y
 CONFIG_NR_DRAM_BANKS=2
-CONFIG_SYS_BOOTCOUNT_ADDR=0x7000A000
 CONFIG_FIT=y
 CONFIG_OF_BOARD_SETUP=y
 CONFIG_SYS_EXTRA_OPTIONS="IMX_CONFIG=board/ge/mx53ppd/imximage.cfg"
@@ -20,6 +19,7 @@ CONFIG_CMD_I2C=y
 CONFIG_CMD_MMC=y
 CONFIG_CMD_USB=y
 CONFIG_CMD_DHCP=y
+CONFIG_CMD_BOOTCOUNT=y
 CONFIG_CMD_MII=y
 CONFIG_CMD_PING=y
 CONFIG_CMD_EXT2=y
@@ -32,15 +32,17 @@ CONFIG_DEFAULT_DEVICE_TREE="imx53-ppd"
 CONFIG_ENV_IS_IN_MMC=y
 CONFIG_DM=y
 CONFIG_BOOTCOUNT_LIMIT=y
-CONFIG_BOOTCOUNT_EXT=y
+CONFIG_DM_BOOTCOUNT=y
+CONFIG_DM_BOOTCOUNT_I2C_EEPROM=y
 CONFIG_BOOTCOUNT_BOOTLIMIT=10
-CONFIG_SYS_BOOTCOUNT_EXT_DEVPART="0:5"
 CONFIG_DM_GPIO=y
 CONFIG_DM_I2C=y
 CONFIG_DM_I2C_COMPAT=y
 CONFIG_SYS_I2C_MXC=y
 CONFIG_I2C_MUX=y
 CONFIG_I2C_MUX_PCA954x=y
+CONFIG_MISC=y
+CONFIG_I2C_EEPROM=y
 CONFIG_DM_MMC=y
 CONFIG_FSL_ESDHC_IMX=y
 CONFIG_MII=y
diff --git a/include/configs/mx53ppd.h b/include/configs/mx53ppd.h
index be4336e3a9..b21235dd57 100644
--- a/include/configs/mx53ppd.h
+++ b/include/configs/mx53ppd.h
@@ -110,9 +110,7 @@
 		"setenv stdout vga; " \
 		"echo \"\n\n\n\n    \" $msg; " \
 		"setenv stdout serial; " \
-		"mw.b 0x7000A000 0xbc; " \
-		"mw.b 0x7000A001 0x00; " \
-		"ext4write ${dev} ${devnum}:5 0x7000A000 /boot/failures 2\0" \
+		"bootcount reset; \0" \
 	"altbootcmd=" \
 		"run doquiet; " \
 		"setenv partnum 1; run hasfirstboot || setenv partnum 2; " \
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 21/37] rtc: rx8010sj: fix DM initialization
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (19 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 20/37] board: ge: mx53ppd: " Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 22/37] board: ge: bx50v3, mx53ppd: use DM rtc Robert Beckett
                   ` (15 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

pass the udevice by reference instead of double ref

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 drivers/rtc/rx8010sj.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/rtc/rx8010sj.c b/drivers/rtc/rx8010sj.c
index 81560e16ce..2876692a37 100644
--- a/drivers/rtc/rx8010sj.c
+++ b/drivers/rtc/rx8010sj.c
@@ -349,7 +349,7 @@ void rtc_init(void)
 
 static int rx8010sj_probe(struct udevice *dev)
 {
-	rx8010sj_rtc_init(&dev);
+	rx8010sj_rtc_init(dev);
 
 	return 0;
 }
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 22/37] board: ge: bx50v3, mx53ppd: use DM rtc
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (20 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 21/37] rtc: rx8010sj: fix DM initialization Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 23/37] board: ge: bx50v3: use DM i2c for PMIC initialization Robert Beckett
                   ` (14 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Convert common code to use DM rtc.
Remove old (pre-DM) rtc defines and config.
Add uboot specific devicetree binding name for bx50v3 rtc

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 arch/arm/dts/imx6q-bx50v3.dts |  2 +-
 board/ge/common/ge_common.c   | 17 ++++++-----------
 configs/ge_bx50v3_defconfig   |  2 ++
 configs/mx53ppd_defconfig     |  1 +
 include/configs/ge_bx50v3.h   |  4 ----
 include/configs/mx53ppd.h     |  3 ---
 6 files changed, 10 insertions(+), 19 deletions(-)

diff --git a/arch/arm/dts/imx6q-bx50v3.dts b/arch/arm/dts/imx6q-bx50v3.dts
index 4d40980254..0f27c32db6 100644
--- a/arch/arm/dts/imx6q-bx50v3.dts
+++ b/arch/arm/dts/imx6q-bx50v3.dts
@@ -493,7 +493,7 @@
 	};
 
 	rtc at 32 {
-		compatible = "epson,rx8010";
+		compatible = "epson,rx8010sj-rtc", "epson,rx8010";
 		pinctrl-names = "default";
 		pinctrl-0 = <&pinctrl_rtc>;
 		reg = <0x32>;
diff --git a/board/ge/common/ge_common.c b/board/ge/common/ge_common.c
index d7e21deca7..48c3778046 100644
--- a/board/ge/common/ge_common.c
+++ b/board/ge/common/ge_common.c
@@ -5,27 +5,24 @@
 
 #include <common.h>
 #include <env.h>
-#include <i2c.h>
+#include <dm/uclass.h>
 #include <rtc.h>
 
 void check_time(void)
 {
+	struct udevice *dev;
 	int ret, i;
 	struct rtc_time tm;
 	u8 retry = 3;
 
-	unsigned int current_i2c_bus = i2c_get_bus_num();
-
-	ret = i2c_set_bus_num(CONFIG_SYS_RTC_BUS_NUM);
-	if (ret < 0) {
+	ret = uclass_get_device(UCLASS_RTC, 0, &dev);
+	if (ret) {
 		env_set("rtc_status", "FAIL");
 		return;
 	}
 
-	rtc_init();
-
 	for (i = 0; i < retry; i++) {
-		ret = rtc_get(&tm);
+		ret = dm_rtc_get(dev, &tm);
 		if (!ret || ret == -EINVAL)
 			break;
 	}
@@ -40,7 +37,7 @@ void check_time(void)
 		tm.tm_year = 2036;
 
 		for (i = 0; i < retry; i++) {
-			ret = rtc_set(&tm);
+			ret = dm_rtc_set(dev, &tm);
 			if (!ret)
 				break;
 		}
@@ -55,7 +52,5 @@ void check_time(void)
 		env_set("rtc_status", "2038");
 	else
 		env_set("rtc_status", "OK");
-
-	i2c_set_bus_num(current_i2c_bus);
 }
 
diff --git a/configs/ge_bx50v3_defconfig b/configs/ge_bx50v3_defconfig
index 519b3e1bb1..5768757573 100644
--- a/configs/ge_bx50v3_defconfig
+++ b/configs/ge_bx50v3_defconfig
@@ -60,6 +60,8 @@ CONFIG_MII=y
 CONFIG_PINCTRL=y
 CONFIG_PINCTRL_IMX6=y
 CONFIG_PWM_IMX=y
+CONFIG_DM_RTC=y
+CONFIG_RTC_RX8010SJ=y
 CONFIG_SPI=y
 CONFIG_DM_SPI=y
 CONFIG_MXC_SPI=y
diff --git a/configs/mx53ppd_defconfig b/configs/mx53ppd_defconfig
index db00481266..9fd6280825 100644
--- a/configs/mx53ppd_defconfig
+++ b/configs/mx53ppd_defconfig
@@ -49,6 +49,7 @@ CONFIG_MII=y
 CONFIG_PINCTRL=y
 CONFIG_PINCTRL_IMX5=y
 CONFIG_PWM_IMX=y
+CONFIG_DM_RTC=y
 CONFIG_RTC_S35392A=y
 CONFIG_USB=y
 CONFIG_USB_EHCI_MX5=y
diff --git a/include/configs/ge_bx50v3.h b/include/configs/ge_bx50v3.h
index b2c114409d..fd23cbe507 100644
--- a/include/configs/ge_bx50v3.h
+++ b/include/configs/ge_bx50v3.h
@@ -190,10 +190,6 @@
 #define CONFIG_PCIE_IMX_PERST_GPIO	IMX_GPIO_NR(7, 12)
 #define CONFIG_PCIE_IMX_POWER_GPIO	IMX_GPIO_NR(1, 5)
 
-#define CONFIG_RTC_RX8010SJ
-#define CONFIG_SYS_RTC_BUS_NUM 2
-#define CONFIG_SYS_I2C_RTC_ADDR	0x32
-
 #define CONFIG_BCH
 
 #endif	/* __GE_BX50V3_CONFIG_H */
diff --git a/include/configs/mx53ppd.h b/include/configs/mx53ppd.h
index b21235dd57..65b8a56f7a 100644
--- a/include/configs/mx53ppd.h
+++ b/include/configs/mx53ppd.h
@@ -43,9 +43,6 @@
 #define CONFIG_MXC_USB_PORTSC	(PORT_PTS_UTMI | PORT_PTS_PTW)
 #define CONFIG_MXC_USB_FLAGS	0
 
-#define CONFIG_SYS_RTC_BUS_NUM		2
-#define CONFIG_SYS_I2C_RTC_ADDR	0x30
-
 /* PMIC Controller */
 #define CONFIG_POWER
 #define CONFIG_POWER_I2C
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 23/37] board: ge: bx50v3: use DM i2c for PMIC initialization
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (21 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 22/37] board: ge: bx50v3, mx53ppd: use DM rtc Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 24/37] board: ge: mx53ppd: remove redundant power config Robert Beckett
                   ` (13 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Use DM i2c for PMIC dc-dc buck converter initialization.

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 board/ge/bx50v3/bx50v3.c | 40 ++++++++++++++++++++++++++--------------
 1 file changed, 26 insertions(+), 14 deletions(-)

diff --git a/board/ge/bx50v3/bx50v3.c b/board/ge/bx50v3/bx50v3.c
index dce76808d7..c1a71e1c9a 100644
--- a/board/ge/bx50v3/bx50v3.c
+++ b/board/ge/bx50v3/bx50v3.c
@@ -488,7 +488,6 @@ static const struct boot_mode board_boot_modes[] = {
 
 void pmic_init(void)
 {
-#define I2C_PMIC                0x2
 #define DA9063_I2C_ADDR         0x58
 #define DA9063_REG_BCORE2_CFG   0x9D
 #define DA9063_REG_BCORE1_CFG   0x9E
@@ -503,38 +502,51 @@ void pmic_init(void)
 #define DA9063_BUCK_MODE_AUTO   0xC0
 
 	uchar val;
+	struct udevice *dev, *bus;
+	int ret;
+
+	// TODO: Add a da9063 DM PMIC driver and use that.
+	ret = uclass_get_device_by_name(UCLASS_I2C, "i2c at 21a8000", &bus);
+	if (ret) {
+		printf("%s: Unable to get I2C bus: %d\n", __func__, ret);
+		return;
+	}
 
-	i2c_set_bus_num(I2C_PMIC);
+	ret = dm_i2c_probe(bus, DA9063_I2C_ADDR, 0, &dev);
+	if (ret) {
+		printf("%s: Unable to get PMIC device: %d\n", __func__, ret);
+		return;
+	}
 
-	i2c_read(DA9063_I2C_ADDR, DA9063_REG_BCORE2_CFG, 1, &val, 1);
+	dm_i2c_read(dev, DA9063_REG_BCORE2_CFG, &val, 1);
 	val &= ~DA9063_BUCK_MODE_MASK;
 	val |= DA9063_BUCK_MODE_SYNC;
-	i2c_write(DA9063_I2C_ADDR, DA9063_REG_BCORE2_CFG, 1, &val, 1);
+	dm_i2c_write(dev, DA9063_REG_BCORE2_CFG, &val, 1);
 
-	i2c_read(DA9063_I2C_ADDR, DA9063_REG_BCORE1_CFG, 1, &val, 1);
+	dm_i2c_read(dev, DA9063_REG_BCORE1_CFG, &val, 1);
 	val &= ~DA9063_BUCK_MODE_MASK;
 	val |= DA9063_BUCK_MODE_SYNC;
-	i2c_write(DA9063_I2C_ADDR, DA9063_REG_BCORE1_CFG, 1, &val, 1);
+	dm_i2c_write(dev, DA9063_REG_BCORE1_CFG, &val, 1);
 
-	i2c_read(DA9063_I2C_ADDR, DA9063_REG_BPRO_CFG, 1, &val, 1);
+	dm_i2c_read(dev, DA9063_REG_BPRO_CFG, &val, 1);
 	val &= ~DA9063_BUCK_MODE_MASK;
 	val |= DA9063_BUCK_MODE_SYNC;
-	i2c_write(DA9063_I2C_ADDR, DA9063_REG_BPRO_CFG, 1, &val, 1);
+	dm_i2c_write(dev, DA9063_REG_BPRO_CFG, &val, 1);
 
-	i2c_read(DA9063_I2C_ADDR, DA9063_REG_BIO_CFG, 1, &val, 1);
+	dm_i2c_read(dev, DA9063_REG_BIO_CFG, &val, 1);
 	val &= ~DA9063_BUCK_MODE_MASK;
 	val |= DA9063_BUCK_MODE_SYNC;
-	i2c_write(DA9063_I2C_ADDR, DA9063_REG_BIO_CFG, 1, &val, 1);
+	dm_i2c_write(dev, DA9063_REG_BIO_CFG, &val, 1);
 
-	i2c_read(DA9063_I2C_ADDR, DA9063_REG_BMEM_CFG, 1, &val, 1);
+	dm_i2c_read(dev, DA9063_REG_BMEM_CFG, &val, 1);
 	val &= ~DA9063_BUCK_MODE_MASK;
 	val |= DA9063_BUCK_MODE_SYNC;
-	i2c_write(DA9063_I2C_ADDR, DA9063_REG_BMEM_CFG, 1, &val, 1);
+	dm_i2c_write(dev, DA9063_REG_BMEM_CFG, &val, 1);
 
-	i2c_read(DA9063_I2C_ADDR, DA9063_REG_BPERI_CFG, 1, &val, 1);
+	dm_i2c_read(dev, DA9063_REG_BPERI_CFG, &val, 1);
 	val &= ~DA9063_BUCK_MODE_MASK;
 	val |= DA9063_BUCK_MODE_SYNC;
-	i2c_write(DA9063_I2C_ADDR, DA9063_REG_BPERI_CFG, 1, &val, 1);
+	dm_i2c_write(dev, DA9063_REG_BPERI_CFG, &val, 1);
 }
 
 int board_late_init(void)
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 24/37] board: ge: mx53ppd: remove redundant power config
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (22 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 23/37] board: ge: bx50v3: use DM i2c for PMIC initialization Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 25/37] board: ge: bx50v3, mx53ppd: disable I2C compatibility API Robert Beckett
                   ` (12 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Remove unused power configuration.
The code never calls pmic_init, so this was not being used, and stops
the build if left enabled when CONFIG_DM_I2C_COMPAT is diabled.

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 include/configs/mx53ppd.h | 9 ---------
 1 file changed, 9 deletions(-)

diff --git a/include/configs/mx53ppd.h b/include/configs/mx53ppd.h
index 65b8a56f7a..941b8c00cc 100644
--- a/include/configs/mx53ppd.h
+++ b/include/configs/mx53ppd.h
@@ -43,15 +43,6 @@
 #define CONFIG_MXC_USB_PORTSC	(PORT_PTS_UTMI | PORT_PTS_PTW)
 #define CONFIG_MXC_USB_FLAGS	0
 
-/* PMIC Controller */
-#define CONFIG_POWER
-#define CONFIG_POWER_I2C
-#define CONFIG_DIALOG_POWER
-#define CONFIG_POWER_FSL
-#define CONFIG_POWER_FSL_MC13892
-#define CONFIG_SYS_DIALOG_PMIC_I2C_ADDR	0x48
-#define CONFIG_SYS_FSL_PMIC_I2C_ADDR	0x8
-
 /* allow to overwrite serial and ethaddr */
 #define CONFIG_ENV_OVERWRITE
 #define CONFIG_BAUDRATE			115200
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 25/37] board: ge: bx50v3, mx53ppd: disable I2C compatibility API
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (23 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 24/37] board: ge: mx53ppd: remove redundant power config Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 26/37] board: ge: mx53ppd: move uart initialisation to own function Robert Beckett
                   ` (11 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Now that all i2c drivers are using DM i2c, we can disable the
compatibility api.

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 configs/ge_bx50v3_defconfig | 1 -
 configs/mx53ppd_defconfig   | 1 -
 2 files changed, 2 deletions(-)

diff --git a/configs/ge_bx50v3_defconfig b/configs/ge_bx50v3_defconfig
index 5768757573..769e093261 100644
--- a/configs/ge_bx50v3_defconfig
+++ b/configs/ge_bx50v3_defconfig
@@ -39,7 +39,6 @@ CONFIG_DM_BOOTCOUNT_I2C_EEPROM=y
 CONFIG_BOOTCOUNT_BOOTLIMIT=10
 CONFIG_DM_GPIO=y
 CONFIG_DM_I2C=y
-CONFIG_DM_I2C_COMPAT=y
 CONFIG_SYS_I2C_MXC=y
 CONFIG_I2C_MUX=y
 CONFIG_I2C_MUX_PCA954x=y
diff --git a/configs/mx53ppd_defconfig b/configs/mx53ppd_defconfig
index 9fd6280825..51d79f602a 100644
--- a/configs/mx53ppd_defconfig
+++ b/configs/mx53ppd_defconfig
@@ -37,7 +37,6 @@ CONFIG_DM_BOOTCOUNT_I2C_EEPROM=y
 CONFIG_BOOTCOUNT_BOOTLIMIT=10
 CONFIG_DM_GPIO=y
 CONFIG_DM_I2C=y
-CONFIG_DM_I2C_COMPAT=y
 CONFIG_SYS_I2C_MXC=y
 CONFIG_I2C_MUX=y
 CONFIG_I2C_MUX_PCA954x=y
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 26/37] board: ge: mx53ppd: move uart initialisation to own function
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (24 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 25/37] board: ge: bx50v3, mx53ppd: disable I2C compatibility API Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 27/37] board: ge: mx53ppd: enable DM_VIDEO Robert Beckett
                   ` (10 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

From: Ian Ray <ian.ray@ge.com>

Move UART initialisation to a stand-alone function for consistency with
other boards.

Drop PPD_UART_PAD_CTRL since it matches defaults.

Signed-off-by: Ian Ray <ian.ray@ge.com>
Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 board/ge/mx53ppd/mx53ppd.c  | 11 +++++++++++
 board/ge/mx53ppd/ppd_gpio.h |  6 ------
 2 files changed, 11 insertions(+), 6 deletions(-)

diff --git a/board/ge/mx53ppd/mx53ppd.c b/board/ge/mx53ppd/mx53ppd.c
index c923478809..2586daddf3 100644
--- a/board/ge/mx53ppd/mx53ppd.c
+++ b/board/ge/mx53ppd/mx53ppd.c
@@ -81,6 +81,16 @@ int dram_init_banksize(void)
 	return 0;
 }
 
+static void setup_iomux_uart(void)
+{
+	static const iomux_v3_cfg_t uart_pads[] = {
+		MX53_PAD_PATA_DMACK__UART1_RXD_MUX,
+		MX53_PAD_PATA_DIOW__UART1_TXD_MUX,
+	};
+
+	imx_iomux_v3_setup_multiple_pads(uart_pads, ARRAY_SIZE(uart_pads));
+}
+
 u32 get_board_rev(void)
 {
 	return get_cpu_rev() & ~(0xF << 8);
@@ -161,6 +171,7 @@ void ppd_gpio_init(void)
 
 int board_early_init_f(void)
 {
+	setup_iomux_uart();
 	setup_iomux_fec();
 	setup_iomux_lcd();
 	ppd_gpio_init();
diff --git a/board/ge/mx53ppd/ppd_gpio.h b/board/ge/mx53ppd/ppd_gpio.h
index ba2d1baf37..12bb389629 100644
--- a/board/ge/mx53ppd/ppd_gpio.h
+++ b/board/ge/mx53ppd/ppd_gpio.h
@@ -9,15 +9,9 @@
 #include <asm/arch/iomux-mx53.h>
 #include <asm/gpio.h>
 
-#define PPD_UART_PAD_CTRL (PAD_CTL_HYS | PAD_CTL_DSE_HIGH |	\
-			   PAD_CTL_PUS_100K_UP)
-
 static const iomux_v3_cfg_t ppd_pads[] = {
 	/* FEC */
 	MX53_PAD_EIM_A22__GPIO2_16,
-	/* UART */
-	NEW_PAD_CTRL(MX53_PAD_PATA_DMACK__UART1_RXD_MUX, PPD_UART_PAD_CTRL),
-	NEW_PAD_CTRL(MX53_PAD_PATA_DIOW__UART1_TXD_MUX, PPD_UART_PAD_CTRL),
 	/* Video */
 	MX53_PAD_CSI0_DATA_EN__GPIO5_20, /* LR_SCAN_CTRL */
 	MX53_PAD_CSI0_VSYNC__GPIO5_21,	 /* UD_SCAN_CTRL */
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 27/37] board: ge: mx53ppd: enable DM_VIDEO
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (25 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 26/37] board: ge: mx53ppd: move uart initialisation to own function Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 28/37] rtc: s35392a: encode command correctly Robert Beckett
                   ` (9 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

From: Ian Ray <ian.ray@ge.com>

Enable DM_VIDEO for mx53ppd.  This also requires DM_REGULATOR_FIXED and
DM_PWM for the backlight, and `failbootcmd' is changed to use lcdputs.

Remove unused MX53PPD_LCD_POWER.

Signed-off-by: Ian Ray <ian.ray@ge.com>
Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 arch/arm/dts/imx53-ppd.dts       | 70 +++++++++++++++++++++++
 board/ge/mx53ppd/Makefile        |  2 +-
 board/ge/mx53ppd/mx53ppd.c       |  2 -
 board/ge/mx53ppd/mx53ppd_video.c | 96 ++++++++++++++++++--------------
 board/ge/mx53ppd/ppd_gpio.h      |  2 -
 configs/mx53ppd_defconfig        |  5 +-
 include/configs/mx53ppd.h        | 11 ++--
 7 files changed, 133 insertions(+), 55 deletions(-)

diff --git a/arch/arm/dts/imx53-ppd.dts b/arch/arm/dts/imx53-ppd.dts
index 3a3192d5e8..947d75b05d 100644
--- a/arch/arm/dts/imx53-ppd.dts
+++ b/arch/arm/dts/imx53-ppd.dts
@@ -7,6 +7,7 @@
 /dts-v1/;
 
 #include "imx53.dtsi"
+#include <dt-bindings/gpio/gpio.h>
 
 / {
 	model = "General Electric CS ONE";
@@ -21,6 +22,69 @@
 		compatible = "u-boot,bootcount-i2c-eeprom";
 		i2c-eeprom = <&bootcount_eeprom>;
 	};
+
+	reg_3v3: regulator-3v3 {
+		/* TPS54320 */
+		compatible = "regulator-fixed";
+		regulator-name = "3V3";
+		regulator-min-microvolt = <3300000>;
+		regulator-max-microvolt = <3300000>;
+		regulator-always-on;
+	};
+
+	reg_3v3_lcd: regulator-3v3-lcd {
+		/* MIC2009 */
+		compatible = "regulator-fixed";
+		regulator-name = "LCD_3V3";
+		vin-supply = <&reg_3v3>;
+		regulator-min-microvolt = <3300000>;
+		regulator-max-microvolt = <3300000>;
+		regulator-always-on;
+	};
+
+	pwm_bl: backlight {
+		compatible = "pwm-backlight";
+		pwms = <&pwm2 0 50000>;
+		brightness-levels = <0 2 5 7 10 12 15 17 20 22 25 28 30 33 35
+				     38 40 43 45 48 51 53 56 58 61 63 66 68 71
+				     73 76 79 81 84 86 89 91 94 96 99 102 104
+				     107 109 112 114 117 119 122 124 127 130
+				     132 135 137 140 142 145 147 150 153 155
+				     158 160 163 165 168 170 173 175 178 181
+				     183 186 188 191 193 196 198 201 204 206
+				     209 211 214 216 219 221 224 226 229 232
+				     234 237 239 242 244 247 249 252 255>;
+		default-brightness-level = <0>;
+		enable-gpios = <&gpio5 29 GPIO_ACTIVE_HIGH>;
+		power-supply = <&reg_3v3_lcd>;
+	};
+
+	panel-lvds0 {
+		compatible = "simple-panel";
+		backlight = <&pwm_bl>;
+		power-supply = <&reg_3v3_lcd>;
+
+		port {
+			panel_in_lvds0: endpoint {
+				remote-endpoint = <&lvds0_out>;
+			};
+		};
+	};
+};
+
+&ldb {
+	status = "okay";
+
+	lvds0: lvds-channel at 0 {
+		status = "okay";
+
+		port at 2 {
+			reg = <2>;
+			lvds0_out: endpoint {
+				remote-endpoint = <&panel_in_lvds0>;
+			};
+		};
+	};
 };
 
 &iomuxc {
@@ -41,6 +105,12 @@
 		>;
 	};
 
+	pinctrl_pwm2: pwm2grp {
+		fsl,pins = <
+		MX53_PAD_DISP0_DAT9__PWM2_PWMO		0x5
+		>;
+	};
+
 	pinctrl_i2c1: i2c1grp {
 		fsl,pins = <
 			MX53_PAD_EIM_D21__I2C1_SCL		0x400001e4
diff --git a/board/ge/mx53ppd/Makefile b/board/ge/mx53ppd/Makefile
index 9fae414399..f423e80cae 100644
--- a/board/ge/mx53ppd/Makefile
+++ b/board/ge/mx53ppd/Makefile
@@ -7,4 +7,4 @@
 # Jason Liu <r64343@freescale.com>
 
 obj-y			+= mx53ppd.o
-obj-$(CONFIG_VIDEO)	+= mx53ppd_video.o
+obj-$(CONFIG_DM_VIDEO)	+= mx53ppd_video.o
diff --git a/board/ge/mx53ppd/mx53ppd.c b/board/ge/mx53ppd/mx53ppd.c
index 2586daddf3..17ba3a87dd 100644
--- a/board/ge/mx53ppd/mx53ppd.c
+++ b/board/ge/mx53ppd/mx53ppd.c
@@ -38,8 +38,6 @@
 #include "../../ge/common/ge_common.h"
 #include "../../ge/common/vpd_reader.h"
 
-#define MX53PPD_LCD_POWER		IMX_GPIO_NR(3, 24)
-
 DECLARE_GLOBAL_DATA_PTR;
 
 static u32 mx53_dram_size[2];
diff --git a/board/ge/mx53ppd/mx53ppd_video.c b/board/ge/mx53ppd/mx53ppd_video.c
index 9dd9f0c98d..c386dc29de 100644
--- a/board/ge/mx53ppd/mx53ppd_video.c
+++ b/board/ge/mx53ppd/mx53ppd_video.c
@@ -9,35 +9,49 @@
  */
 
 #include <common.h>
+#include <dm.h>
 #include <linux/list.h>
-#include <asm/gpio.h>
 #include <asm/arch/iomux-mx53.h>
+#include <asm/mach-imx/video.h>
 #include <linux/fb.h>
 #include <ipu_pixfmt.h>
 #include <asm/arch/crm_regs.h>
 #include <asm/arch/imx-regs.h>
 #include <asm/io.h>
-#include <pwm.h>
-#include "ppd_gpio.h"
-
-#define MX53PPD_LCD_POWER		IMX_GPIO_NR(3, 24)
-
-static struct fb_videomode const nv_spwg = {
-	.name		= "NV-SPWGRGB888",
-	.refresh	= 60,
-	.xres		= 800,
-	.yres		= 480,
-	.pixclock	= 15384,
-	.left_margin	= 16,
-	.right_margin	= 210,
-	.upper_margin	= 10,
-	.lower_margin	= 22,
-	.hsync_len	= 30,
-	.vsync_len	= 13,
-	.sync		= FB_SYNC_EXT,
-	.vmode		= FB_VMODE_NONINTERLACED
+#include <panel.h>
+
+static int detect_lcd(struct display_info_t const *dev)
+{
+	return 1;
+}
+
+struct display_info_t const displays[] = {
+	{
+		.bus	= -1,
+		.addr	= -1,
+		.pixfmt	= IPU_PIX_FMT_RGB24,
+		.detect	= detect_lcd,
+		.enable	= NULL,
+		.mode = {
+			.name		= "NV-SPWGRGB888",
+			.refresh	= 60,
+			.xres		= 800,
+			.yres		= 480,
+			.pixclock	= 15384,
+			.left_margin	= 16,
+			.right_margin	= 210,
+			.upper_margin	= 10,
+			.lower_margin	= 22,
+			.hsync_len	= 30,
+			.vsync_len	= 13,
+			.sync		= FB_SYNC_EXT,
+			.vmode		= FB_VMODE_NONINTERLACED
+		}
+	}
 };
 
+size_t display_count = ARRAY_SIZE(displays);
+
 void setup_iomux_lcd(void)
 {
 	static const iomux_v3_cfg_t lcd_pads[] = {
@@ -96,24 +110,31 @@ static void lcd_enable(void)
 		IOMUXC_GPR2_DATA_WIDTH_CH0_24BIT |
 		IOMUXC_GPR2_LVDS_CH0_MODE_ENABLED_DI0,
 		&iomux->gpr[2]);
-
-	/* Enable backlights  */
-	pwm_init(1, 0, 0);
-
-	/* duty cycle 5000000ns, period: 5000000ns */
-	pwm_config(1, 5000000, 5000000);
-
-	/* Backlight Power */
-	gpio_request(BACKLIGHT_ENABLE, "BACKLIGHT_ENABLE");
-	gpio_direction_output(BACKLIGHT_ENABLE, 1);
-
-	pwm_enable(1);
 }
 
 static int do_lcd_enable(cmd_tbl_t *cmdtp, int flag, int argc,
 			 char * const argv[])
 {
 	lcd_enable();
+
+	int ret;
+	struct udevice *panel;
+	struct udevice *dev;
+
+	ret = uclass_get_device(UCLASS_PANEL, 0, &panel);
+	if (ret)
+		return ret;
+
+	panel_set_backlight(panel, 100);
+	panel_enable_backlight(panel);
+
+	/* Probe, to find a video device to be used to show a message on
+	 * the vidconsole.
+	 */
+	ret = uclass_get_device(UCLASS_VIDEO, 0, &dev);
+	if (ret)
+		return ret;
+
 	return 0;
 }
 
@@ -122,14 +143,3 @@ U_BOOT_CMD(
 	"enable PPD LCD",
 	"no parameters"
 );
-
-int board_video_skip(void)
-{
-	int ret;
-
-	ret = ipuv3_fb_init(&nv_spwg, 0, IPU_PIX_FMT_RGB24);
-	if (ret)
-		printf("Display cannot be configured: %d\n", ret);
-
-	return ret;
-}
diff --git a/board/ge/mx53ppd/ppd_gpio.h b/board/ge/mx53ppd/ppd_gpio.h
index 12bb389629..98c41d4d67 100644
--- a/board/ge/mx53ppd/ppd_gpio.h
+++ b/board/ge/mx53ppd/ppd_gpio.h
@@ -51,7 +51,6 @@ struct gpio_cfg {
 #define POWER_DOWN_LVDS0_DESERIALIZER_N IMX_GPIO_NR(2, 22)
 #define POWER_DOWN_LVDS1_DESERIALIZER_N IMX_GPIO_NR(2, 27)
 #define ENABLE_PWR_TO_LCD_AND_UI_INTERFACE IMX_GPIO_NR(2, 17)
-#define BACKLIGHT_ENABLE IMX_GPIO_NR(5, 29)
 #define RESET_I2C1_BUS_SEGMENT_MUX_N IMX_GPIO_NR(2, 18)
 #define ECSPI1_CS0 IMX_GPIO_NR(5, 17)
 #define ECSPI1_CS1 IMX_GPIO_NR(4, 10)
@@ -81,7 +80,6 @@ static const struct gpio_cfg ppd_gpios[] = {
 	{ POWER_DOWN_LVDS0_DESERIALIZER_N, 1 },
 	{ POWER_DOWN_LVDS1_DESERIALIZER_N, 1 },
 	{ ENABLE_PWR_TO_LCD_AND_UI_INTERFACE, 1 },
-	{ BACKLIGHT_ENABLE, 0 },
 	{ RESET_I2C1_BUS_SEGMENT_MUX_N, 1 },
 	{ ECSPI1_CS0, 1 },
 	{ ECSPI1_CS1, 1 },
diff --git a/configs/mx53ppd_defconfig b/configs/mx53ppd_defconfig
index 51d79f602a..4d4f93614f 100644
--- a/configs/mx53ppd_defconfig
+++ b/configs/mx53ppd_defconfig
@@ -53,7 +53,6 @@ CONFIG_RTC_S35392A=y
 CONFIG_USB=y
 CONFIG_USB_EHCI_MX5=y
 CONFIG_VIDEO_IPUV3=y
-CONFIG_VIDEO=y
 # CONFIG_VIDEO_SW_CURSOR is not set
 CONFIG_WATCHDOG_TIMEOUT_MSECS=8000
 CONFIG_IMX_WATCHDOG=y
@@ -61,5 +60,9 @@ CONFIG_WDT=y
 CONFIG_SYSRESET=y
 CONFIG_SYSRESET_WATCHDOG=y
 CONFIG_DM_REGULATOR=y
+CONFIG_DM_REGULATOR_FIXED=y
 CONFIG_DM_USB=y
 CONFIG_SYS_MALLOC_F_LEN=0x4000
+CONFIG_DM_VIDEO=y
+CONFIG_SYS_WHITE_ON_BLACK=y
+CONFIG_DM_PWM=y
diff --git a/include/configs/mx53ppd.h b/include/configs/mx53ppd.h
index 941b8c00cc..c7414213a7 100644
--- a/include/configs/mx53ppd.h
+++ b/include/configs/mx53ppd.h
@@ -92,12 +92,9 @@
 	"swappartitions=setexpr partnum 3 - ${partnum}\0" \
 	"failbootcmd=" \
 		"ppd_lcd_enable; " \
-		"msg=\"Monitor failed to start.  " \
-			"Try again, or contact GE Service for support.\"; " \
-		"echo $msg; " \
-		"setenv stdout vga; " \
-		"echo \"\n\n\n\n    \" $msg; " \
-		"setenv stdout serial; " \
+		"setcurs 5 4; " \
+		"lcdputs \"Monitor failed to start. " \
+		"Try again, or contact GE Service for support.\"; " \
 		"bootcount reset; \0" \
 	"altbootcmd=" \
 		"run doquiet; " \
@@ -174,4 +171,6 @@
 /* Backlight Control */
 #define CONFIG_IMX6_PWM_PER_CLK 66666000
 
+#define CONFIG_IMX_VIDEO_SKIP
+
 #endif				/* __CONFIG_H */
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 28/37] rtc: s35392a: encode command correctly
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (26 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 27/37] board: ge: mx53ppd: enable DM_VIDEO Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 29/37] board: ge: mx53ppd: fix RTC compatible definition Robert Beckett
                   ` (8 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

From: Ian Ray <ian.ray@ge.com>

The 3-bit "command", or register, is encoded within the device address.
Configure the device accordingly, and pass command in DM I2C read/write
calls correctly.

Signed-off-by: Ian Ray <ian.ray@ge.com>
Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 drivers/rtc/s35392a.c | 27 ++++++++++++++++-----------
 1 file changed, 16 insertions(+), 11 deletions(-)

diff --git a/drivers/rtc/s35392a.c b/drivers/rtc/s35392a.c
index 844f1b72c7..53cd590e69 100644
--- a/drivers/rtc/s35392a.c
+++ b/drivers/rtc/s35392a.c
@@ -24,11 +24,13 @@
 #include <linux/bitrev.h>
 #include <rtc.h>
 
-#define S35390A_CMD_STATUS1		0x30
-#define S35390A_CMD_STATUS2		0x31
-#define S35390A_CMD_TIME1		0x32
-#define S35390A_CMD_TIME2		0x33
-#define S35390A_CMD_INT2_REG1	0x35
+#define S35390A_CHIP_ADDR	0x30
+
+#define S35390A_CMD_STATUS1	0x0
+#define S35390A_CMD_STATUS2	0x1
+#define S35390A_CMD_TIME1	0x2
+#define S35390A_CMD_TIME2	0x3
+#define S35390A_CMD_INT2_REG1	0x5
 
 #define S35390A_BYTE_YEAR	0
 #define S35390A_BYTE_MONTH	1
@@ -85,11 +87,10 @@ static int s35392a_rtc_read(DEV_TYPE *dev, u8 reg, u8 *buf, int len)
 	int ret;
 
 #ifdef CONFIG_DM_RTC
-	/* TODO: we need to tweak the chip address to reg */
-	ret = dm_i2c_read(dev, 0, buf, len);
+	ret = dm_i2c_read(dev, reg, buf, len);
 #else
 	(void)dev;
-	ret = i2c_read(reg, 0, -1, buf, len);
+	ret = i2c_read(S35390A_CHIP_ADDR | reg, 0, -1, buf, len);
 #endif
 
 	return ret;
@@ -100,11 +101,10 @@ static int s35392a_rtc_write(DEV_TYPE *dev, u8 reg, u8 *buf, int len)
 	int ret;
 
 #ifdef CONFIG_DM_RTC
-	/* TODO: we need to tweak the chip address to reg */
-	ret = dm_i2c_write(dev, 0, buf, 1);
+	ret = dm_i2c_write(dev, reg, buf, len);
 #else
 	(void)dev;
-	ret = i2c_write(reg, 0, 0, buf, len);
+	ret = i2c_write(S35390A_CHIP_ADDR | reg, 0, 0, buf, len);
 #endif
 
 	return ret;
@@ -336,6 +336,11 @@ void rtc_init(void)
 
 static int s35392a_probe(struct udevice *dev)
 {
+	/* 3-bit "command", or register, is encoded within the device address.
+	 */
+	i2c_set_chip_offset_len(dev, 0);
+	i2c_set_chip_addr_offset_mask(dev, 0x7);
+
 	s35392a_rtc_init(dev);
 	return 0;
 }
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 29/37] board: ge: mx53ppd: fix RTC compatible definition
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (27 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 28/37] rtc: s35392a: encode command correctly Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 30/37] board: ge: bx50v3: Enable DM PWM for backlight Robert Beckett
                   ` (7 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

From: Ian Ray <ian.ray@ge.com>

Fix RTC compatible definition.

Signed-off-by: Ian Ray <ian.ray@ge.com>
Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 arch/arm/dts/imx53-ppd.dts | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/arch/arm/dts/imx53-ppd.dts b/arch/arm/dts/imx53-ppd.dts
index 947d75b05d..484447af10 100644
--- a/arch/arm/dts/imx53-ppd.dts
+++ b/arch/arm/dts/imx53-ppd.dts
@@ -192,7 +192,7 @@
 			reg = <1>;
 
 			rtc at 30 {
-			       compatible = "sii,s35390a";
+			       compatible = "sii,s35392a-rtc";
 			       reg = <0x30>;
 			};
 
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 30/37] board: ge: bx50v3: Enable DM PWM for backlight
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (28 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 29/37] board: ge: mx53ppd: fix RTC compatible definition Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 31/37] board: ge: mx53ppd: clean up DM PWM video and backlight Robert Beckett
                   ` (6 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Add backlight and panel devicetree definitions
Use UCLASS_PANEL to enable backlight via display enable handler
Remove old explicit gpio code for handling backlight
Use cls command to initiate display in HW agnostic manner
Enable DM regulator and pwm

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 arch/arm/dts/imx6q-bx50v3.dts | 95 +++++++++++++++++++++++++++++++++++
 board/ge/bx50v3/bx50v3.c      | 81 ++++++-----------------------
 configs/ge_bx50v3_defconfig   |  4 ++
 include/configs/ge_bx50v3.h   |  2 +-
 4 files changed, 116 insertions(+), 66 deletions(-)

diff --git a/arch/arm/dts/imx6q-bx50v3.dts b/arch/arm/dts/imx6q-bx50v3.dts
index 0f27c32db6..e9aaca4a78 100644
--- a/arch/arm/dts/imx6q-bx50v3.dts
+++ b/arch/arm/dts/imx6q-bx50v3.dts
@@ -27,6 +27,84 @@
 		compatible = "wdt-reboot";
 		wdt = <&wdog1>;
 	};
+
+	backlight_lvds: backlight {
+		compatible = "pwm-backlight";
+		pinctrl-names = "default";
+		pinctrl-0 = <&pinctrl_display>;
+		pwms = <&pwm1 0 5000000>;
+		brightness-levels = <  0   1   2   3   4   5   6   7   8   9
+				      10  11  12  13  14  15  16  17  18  19
+				      20  21  22  23  24  25  26  27  28  29
+				      30  31  32  33  34  35  36  37  38  39
+				      40  41  42  43  44  45  46  47  48  49
+				      50  51  52  53  54  55  56  57  58  59
+				      60  61  62  63  64  65  66  67  68  69
+				      70  71  72  73  74  75  76  77  78  79
+				      80  81  82  83  84  85  86  87  88  89
+				      90  91  92  93  94  95  96  97  98  99
+				     100 101 102 103 104 105 106 107 108 109
+				     110 111 112 113 114 115 116 117 118 119
+				     120 121 122 123 124 125 126 127 128 129
+				     130 131 132 133 134 135 136 137 138 139
+				     140 141 142 143 144 145 146 147 148 149
+				     150 151 152 153 154 155 156 157 158 159
+				     160 161 162 163 164 165 166 167 168 169
+				     170 171 172 173 174 175 176 177 178 179
+				     180 181 182 183 184 185 186 187 188 189
+				     190 191 192 193 194 195 196 197 198 199
+				     200 201 202 203 204 205 206 207 208 209
+				     210 211 212 213 214 215 216 217 218 219
+				     220 221 222 223 224 225 226 227 228 229
+				     230 231 232 233 234 235 236 237 238 239
+				     240 241 242 243 244 245 246 247 248 249
+				     250 251 252 253 254 255>;
+		default-brightness-level = <255>;
+		enable-gpios = <&gpio1 0 GPIO_ACTIVE_HIGH>;
+	};
+
+	reg_lvds: regulator-lvds {
+		compatible = "regulator-fixed";
+		regulator-name = "lvds_ppen";
+		regulator-min-microvolt = <3300000>;
+		regulator-max-microvolt = <3300000>;
+		regulator-boot-on;
+		gpio = <&gpio3 22 GPIO_ACTIVE_HIGH>;
+		enable-active-high;
+	};
+
+	panel-lvds0 {
+		compatible = "simple-panel";
+		backlight = <&backlight_lvds>;
+		power-supply = <&reg_lvds>;
+
+		port {
+			panel_in_lvds0: endpoint {
+				remote-endpoint = <&lvds0_out>;
+			};
+		};
+	};
+};
+
+&ldb {
+	status = "okay";
+
+	lvds0: lvds-channel at 0 {
+		status = "okay";
+
+		port at 2 {
+			reg = <2>;
+			lvds0_out: endpoint {
+				remote-endpoint = <&panel_in_lvds0>;
+			};
+		};
+	};
+};
+
+&pwm1 {
+	pinctrl-names = "default";
+	pinctrl-0 = <&pinctrl_pwm1>;
+	status = "okay";
 };
 
 &iomuxc {
@@ -141,6 +219,23 @@
 			MX6QDL_PAD_KEY_COL2__GPIO4_IO10	0x1b0b0
 		>;
 	};
+
+	pinctrl_display: dispgrp {
+		fsl,pins = <
+			/* Backlight enable for LVDS display */
+			MX6QDL_PAD_GPIO_0__GPIO1_IO00    0x1b0b0
+			/* Power for LVDS Display */
+			MX6QDL_PAD_EIM_D22__GPIO3_IO22   0x1b0b0
+			/* backlight PWM brightness control */
+			MX6QDL_PAD_GPIO_18__GPIO7_IO13	0x1b0b0
+		>;
+	};
+
+	pinctrl_pwm1: pwm1grp {
+		fsl,pins = <
+			MX6QDL_PAD_SD1_DAT3__PWM1_OUT	0x1b0b1
+		>;
+	};
 };
 
 &usdhc1 {
diff --git a/board/ge/bx50v3/bx50v3.c b/board/ge/bx50v3/bx50v3.c
index c1a71e1c9a..2e11697af0 100644
--- a/board/ge/bx50v3/bx50v3.c
+++ b/board/ge/bx50v3/bx50v3.c
@@ -35,6 +35,7 @@
 #include "../common/vpd_reader.h"
 #include "../../../drivers/net/e1000.h"
 #include <pci.h>
+#include <panel.h>
 
 DECLARE_GLOBAL_DATA_PTR;
 
@@ -122,16 +123,20 @@ int board_phy_config(struct phy_device *phydev)
 }
 
 #if defined(CONFIG_VIDEO_IPUV3)
-static iomux_v3_cfg_t const backlight_pads[] = {
-	/* Power for LVDS Display */
-	MX6_PAD_EIM_D22__GPIO3_IO22 | MUX_PAD_CTRL(NO_PAD_CTRL),
-#define LVDS_POWER_GP IMX_GPIO_NR(3, 22)
-	/* Backlight enable for LVDS display */
-	MX6_PAD_GPIO_0__GPIO1_IO00 | MUX_PAD_CTRL(NO_PAD_CTRL),
-#define LVDS_BACKLIGHT_GP IMX_GPIO_NR(1, 0)
-	/* backlight PWM brightness control */
-	MX6_PAD_SD1_DAT3__PWM1_OUT | MUX_PAD_CTRL(NO_PAD_CTRL),
-};
+static void do_enable_backlight(struct display_info_t const *dev)
+{
+	struct udevice *panel;
+	int ret;
+
+	ret = uclass_get_device(UCLASS_PANEL, 0, &panel);
+	if (ret) {
+		printf("Could not find panel: %d\n", ret);
+		return;
+	}
+
+	panel_set_backlight(panel, 100);
+	panel_enable_backlight(panel);
+}
 
 static void do_enable_hdmi(struct display_info_t const *dev)
 {
@@ -153,7 +158,7 @@ struct display_info_t const displays[] = {{
 	.addr	= -1,
 	.pixfmt	= IPU_PIX_FMT_RGB24,
 	.detect	= detect_lcd,
-	.enable	= NULL,
+	.enable	= do_enable_backlight,
 	.mode	= {
 		.name           = "G121X1-L03",
 		.refresh        = 60,
@@ -312,12 +317,6 @@ static void setup_display_bx50v3(void)
 			IOMUXC_GPR3_LVDS0_MUX_CTL_MASK,
 		       (IOMUXC_GPR3_MUX_SRC_IPU1_DI0 <<
 			IOMUXC_GPR3_LVDS0_MUX_CTL_OFFSET));
-
-	/* backlights off until needed */
-	imx_iomux_v3_setup_multiple_pads(backlight_pads,
-					 ARRAY_SIZE(backlight_pads));
-	gpio_request(LVDS_POWER_GP, "lvds_power");
-	gpio_direction_input(LVDS_POWER_GP);
 }
 #endif /* CONFIG_VIDEO_IPUV3 */
 
@@ -466,9 +465,6 @@ int board_init(void)
 		setup_display_b850v3();
 	else
 		setup_display_bx50v3();
-
-	gpio_request(LVDS_BACKLIGHT_GP, "lvds_backlight");
-	gpio_direction_input(LVDS_BACKLIGHT_GP);
 #endif
 
 	/* address of boot parameters */
@@ -618,48 +614,3 @@ int ft_board_setup(void *blob, bd_t *bd)
 	return 0;
 }
 #endif
-
-static int do_backlight_enable(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
-{
-#if CONFIG_IS_ENABLED(DM_VIDEO)
-	int ret;
-	struct udevice *dev;
-
-#ifdef CONFIG_VIDEO_IPUV3
-	if (!is_b850v3()) {
-		gpio_direction_output(LVDS_POWER_GP, 1);
-
-		/* We need@least 200ms between power on and backlight on
-		 * as per specifications from CHI MEI
-		 */
-		mdelay(250);
-
-		/* enable backlight PWM 1 */
-		pwm_init(0, 0, 0);
-
-		/* duty cycle 5000000ns, period: 5000000ns */
-		pwm_config(0, 5000000, 5000000);
-
-		/* Backlight Power */
-		gpio_direction_output(LVDS_BACKLIGHT_GP, 1);
-
-		pwm_enable(0);
-	}
-#endif
-
-	/* Probe, to find a video device to be used to show a message on
-	 * the vidconsole.
-	 */
-	ret = uclass_get_device(UCLASS_VIDEO, 0, &dev);
-	if (ret)
-		return ret;
-#endif
-
-	return 0;
-}
-
-U_BOOT_CMD(
-       bx50_backlight_enable, 1,      1,      do_backlight_enable,
-       "enable Bx50 backlight",
-       ""
-);
diff --git a/configs/ge_bx50v3_defconfig b/configs/ge_bx50v3_defconfig
index 769e093261..977aac41f6 100644
--- a/configs/ge_bx50v3_defconfig
+++ b/configs/ge_bx50v3_defconfig
@@ -24,6 +24,7 @@ CONFIG_CMD_SF=y
 # CONFIG_CMD_NFS is not set
 CONFIG_CMD_BOOTCOUNT=y
 CONFIG_CMD_CACHE=y
+CONFIG_CMD_CLS=y
 CONFIG_CMD_EXT2=y
 CONFIG_CMD_EXT4=y
 CONFIG_CMD_EXT4_WRITE=y
@@ -59,6 +60,9 @@ CONFIG_MII=y
 CONFIG_PINCTRL=y
 CONFIG_PINCTRL_IMX6=y
 CONFIG_PWM_IMX=y
+CONFIG_DM_PWM=y
+CONFIG_DM_REGULATOR=y
+CONFIG_DM_REGULATOR_FIXED=y
 CONFIG_DM_RTC=y
 CONFIG_RTC_RX8010SJ=y
 CONFIG_SPI=y
diff --git a/include/configs/ge_bx50v3.h b/include/configs/ge_bx50v3.h
index fd23cbe507..6ca43c3cf7 100644
--- a/include/configs/ge_bx50v3.h
+++ b/include/configs/ge_bx50v3.h
@@ -105,7 +105,7 @@
 		"setexpr partnum 3 - ${partnum}\0" \
 	"failbootcmd=" \
 		"echo reached failbootcmd; " \
-		"bx50_backlight_enable; " \
+		"cls; " \
 		"setcurs 5 4; " \
 		"lcdputs \"Monitor failed to start. " \
 		"Try again, or contact GE Service for support.\"; " \
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 31/37] board: ge: mx53ppd: clean up DM PWM video and backlight
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (29 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 30/37] board: ge: bx50v3: Enable DM PWM for backlight Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 32/37] board: ge: mx53ppd: Use DM for ethernet Robert Beckett
                   ` (5 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Remove old (incorrect) setup_iomux_lcd.
Enable backlight via display enable handler.
Use cls command to initiate display in HW agnostic manner.

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 board/ge/mx53ppd/mx53ppd.c       |   1 -
 board/ge/mx53ppd/mx53ppd_video.c | 118 +++++++++----------------------
 configs/mx53ppd_defconfig        |   1 +
 include/configs/mx53ppd.h        |   2 +-
 4 files changed, 36 insertions(+), 86 deletions(-)

diff --git a/board/ge/mx53ppd/mx53ppd.c b/board/ge/mx53ppd/mx53ppd.c
index 17ba3a87dd..57bf03f659 100644
--- a/board/ge/mx53ppd/mx53ppd.c
+++ b/board/ge/mx53ppd/mx53ppd.c
@@ -171,7 +171,6 @@ int board_early_init_f(void)
 {
 	setup_iomux_uart();
 	setup_iomux_fec();
-	setup_iomux_lcd();
 	ppd_gpio_init();
 
 	return 0;
diff --git a/board/ge/mx53ppd/mx53ppd_video.c b/board/ge/mx53ppd/mx53ppd_video.c
index c386dc29de..3240ed62ae 100644
--- a/board/ge/mx53ppd/mx53ppd_video.c
+++ b/board/ge/mx53ppd/mx53ppd_video.c
@@ -25,69 +25,6 @@ static int detect_lcd(struct display_info_t const *dev)
 	return 1;
 }
 
-struct display_info_t const displays[] = {
-	{
-		.bus	= -1,
-		.addr	= -1,
-		.pixfmt	= IPU_PIX_FMT_RGB24,
-		.detect	= detect_lcd,
-		.enable	= NULL,
-		.mode = {
-			.name		= "NV-SPWGRGB888",
-			.refresh	= 60,
-			.xres		= 800,
-			.yres		= 480,
-			.pixclock	= 15384,
-			.left_margin	= 16,
-			.right_margin	= 210,
-			.upper_margin	= 10,
-			.lower_margin	= 22,
-			.hsync_len	= 30,
-			.vsync_len	= 13,
-			.sync		= FB_SYNC_EXT,
-			.vmode		= FB_VMODE_NONINTERLACED
-		}
-	}
-};
-
-size_t display_count = ARRAY_SIZE(displays);
-
-void setup_iomux_lcd(void)
-{
-	static const iomux_v3_cfg_t lcd_pads[] = {
-		MX53_PAD_DI0_DISP_CLK__IPU_DI0_DISP_CLK,
-		MX53_PAD_DI0_PIN15__IPU_DI0_PIN15,
-		MX53_PAD_DI0_PIN2__IPU_DI0_PIN2,
-		MX53_PAD_DI0_PIN3__IPU_DI0_PIN3,
-		MX53_PAD_DISP0_DAT0__IPU_DISP0_DAT_0,
-		MX53_PAD_DISP0_DAT1__IPU_DISP0_DAT_1,
-		MX53_PAD_DISP0_DAT2__IPU_DISP0_DAT_2,
-		MX53_PAD_DISP0_DAT3__IPU_DISP0_DAT_3,
-		MX53_PAD_DISP0_DAT4__IPU_DISP0_DAT_4,
-		MX53_PAD_DISP0_DAT5__IPU_DISP0_DAT_5,
-		MX53_PAD_DISP0_DAT6__IPU_DISP0_DAT_6,
-		MX53_PAD_DISP0_DAT7__IPU_DISP0_DAT_7,
-		MX53_PAD_DISP0_DAT8__IPU_DISP0_DAT_8,
-		MX53_PAD_DISP0_DAT9__IPU_DISP0_DAT_9,
-		MX53_PAD_DISP0_DAT10__IPU_DISP0_DAT_10,
-		MX53_PAD_DISP0_DAT11__IPU_DISP0_DAT_11,
-		MX53_PAD_DISP0_DAT12__IPU_DISP0_DAT_12,
-		MX53_PAD_DISP0_DAT13__IPU_DISP0_DAT_13,
-		MX53_PAD_DISP0_DAT14__IPU_DISP0_DAT_14,
-		MX53_PAD_DISP0_DAT15__IPU_DISP0_DAT_15,
-		MX53_PAD_DISP0_DAT16__IPU_DISP0_DAT_16,
-		MX53_PAD_DISP0_DAT17__IPU_DISP0_DAT_17,
-		MX53_PAD_DISP0_DAT18__IPU_DISP0_DAT_18,
-		MX53_PAD_DISP0_DAT19__IPU_DISP0_DAT_19,
-		MX53_PAD_DISP0_DAT20__IPU_DISP0_DAT_20,
-		MX53_PAD_DISP0_DAT21__IPU_DISP0_DAT_21,
-		MX53_PAD_DISP0_DAT22__IPU_DISP0_DAT_22,
-		MX53_PAD_DISP0_DAT23__IPU_DISP0_DAT_23,
-	};
-
-	imx_iomux_v3_setup_multiple_pads(lcd_pads, ARRAY_SIZE(lcd_pads));
-}
-
 static void lcd_enable(void)
 {
 	struct mxc_ccm_reg *mxc_ccm = (struct mxc_ccm_reg *)CCM_BASE_ADDR;
@@ -112,34 +49,47 @@ static void lcd_enable(void)
 		&iomux->gpr[2]);
 }
 
-static int do_lcd_enable(cmd_tbl_t *cmdtp, int flag, int argc,
-			 char * const argv[])
+static void do_enable_backlight(struct display_info_t const *dev)
 {
-	lcd_enable();
-
-	int ret;
 	struct udevice *panel;
-	struct udevice *dev;
+	int ret;
+
+	lcd_enable();
 
 	ret = uclass_get_device(UCLASS_PANEL, 0, &panel);
-	if (ret)
-		return ret;
+	if (ret) {
+		printf("Could not find panel: %d\n", ret);
+		return;
+	}
 
 	panel_set_backlight(panel, 100);
 	panel_enable_backlight(panel);
+}
 
-	/* Probe, to find a video device to be used to show a message on
-	 * the vidconsole.
-	 */
-	ret = uclass_get_device(UCLASS_VIDEO, 0, &dev);
-	if (ret)
-		return ret;
+struct display_info_t const displays[] = {
+	{
+		.bus	= -1,
+		.addr	= -1,
+		.pixfmt	= IPU_PIX_FMT_RGB24,
+		.detect	= detect_lcd,
+		.enable	= do_enable_backlight,
+		.mode = {
+			.name		= "NV-SPWGRGB888",
+			.refresh	= 60,
+			.xres		= 800,
+			.yres		= 480,
+			.pixclock	= 15384,
+			.left_margin	= 16,
+			.right_margin	= 210,
+			.upper_margin	= 10,
+			.lower_margin	= 22,
+			.hsync_len	= 30,
+			.vsync_len	= 13,
+			.sync		= FB_SYNC_EXT,
+			.vmode		= FB_VMODE_NONINTERLACED
+		}
+	}
+};
 
-	return 0;
-}
+size_t display_count = ARRAY_SIZE(displays);
 
-U_BOOT_CMD(
-	ppd_lcd_enable,	1,	1,	do_lcd_enable,
-	"enable PPD LCD",
-	"no parameters"
-);
diff --git a/configs/mx53ppd_defconfig b/configs/mx53ppd_defconfig
index 4d4f93614f..2094e74c7d 100644
--- a/configs/mx53ppd_defconfig
+++ b/configs/mx53ppd_defconfig
@@ -22,6 +22,7 @@ CONFIG_CMD_DHCP=y
 CONFIG_CMD_BOOTCOUNT=y
 CONFIG_CMD_MII=y
 CONFIG_CMD_PING=y
+CONFIG_CMD_CLS=y
 CONFIG_CMD_EXT2=y
 CONFIG_CMD_EXT4=y
 CONFIG_CMD_EXT4_WRITE=y
diff --git a/include/configs/mx53ppd.h b/include/configs/mx53ppd.h
index c7414213a7..3b1615338c 100644
--- a/include/configs/mx53ppd.h
+++ b/include/configs/mx53ppd.h
@@ -91,7 +91,7 @@
 		"/boot/bootcause/firstboot\0" \
 	"swappartitions=setexpr partnum 3 - ${partnum}\0" \
 	"failbootcmd=" \
-		"ppd_lcd_enable; " \
+		"cls; " \
 		"setcurs 5 4; " \
 		"lcdputs \"Monitor failed to start. " \
 		"Try again, or contact GE Service for support.\"; " \
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 32/37] board: ge: mx53ppd: Use DM for ethernet
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (30 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 31/37] board: ge: mx53ppd: clean up DM PWM video and backlight Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 33/37] board: ge: bx50v3: use DM for uart Robert Beckett
                   ` (4 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Add fec ethernet and pinctrl DT config.
Remove legacy iomux setup for fec.
Enable phylib and DM fec.
Use Kconfig for enabling fec.

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 arch/arm/dts/imx53-ppd.dts | 24 ++++++++++++++++++++++++
 board/ge/mx53ppd/mx53ppd.c | 26 --------------------------
 configs/mx53ppd_defconfig  |  3 +++
 include/configs/mx53ppd.h  |  8 --------
 4 files changed, 27 insertions(+), 34 deletions(-)

diff --git a/arch/arm/dts/imx53-ppd.dts b/arch/arm/dts/imx53-ppd.dts
index 484447af10..d308abc09c 100644
--- a/arch/arm/dts/imx53-ppd.dts
+++ b/arch/arm/dts/imx53-ppd.dts
@@ -152,6 +152,21 @@
 			MX53_PAD_EIM_D17__GPIO3_17		0x1e4
 		>;
 	};
+
+	pinctrl_fec: fecgrp {
+		fsl,pins = <
+			MX53_PAD_FEC_MDC__FEC_MDC		0x0
+			MX53_PAD_FEC_MDIO__FEC_MDIO		0x0
+			MX53_PAD_FEC_REF_CLK__FEC_TX_CLK	0x0
+			MX53_PAD_FEC_RX_ER__FEC_RX_ER		0x0
+			MX53_PAD_FEC_CRS_DV__FEC_RX_DV		0x0
+			MX53_PAD_FEC_RXD1__FEC_RDATA_1		0x0
+			MX53_PAD_FEC_RXD0__FEC_RDATA_0		0x0
+			MX53_PAD_FEC_TX_EN__FEC_TX_EN		0x0
+			MX53_PAD_FEC_TXD1__FEC_TDATA_1		0x0
+			MX53_PAD_FEC_TXD0__FEC_TDATA_0		0x0
+		>;
+	};
 };
 
 /* eMMC */
@@ -317,3 +332,12 @@
 &gpio5 {
 	u-boot,dm-pre-reloc;
 };
+
+&fec {
+	pinctrl-names = "default";
+	pinctrl-0 = <&pinctrl_fec>;
+	phy-supply = <&reg_3v3>;
+	phy-mode = "rmii";
+	phy-reset-gpios = <&gpio2 16 GPIO_ACTIVE_LOW>;
+	status = "okay";
+};
diff --git a/board/ge/mx53ppd/mx53ppd.c b/board/ge/mx53ppd/mx53ppd.c
index 57bf03f659..486ef6d374 100644
--- a/board/ge/mx53ppd/mx53ppd.c
+++ b/board/ge/mx53ppd/mx53ppd.c
@@ -107,31 +107,6 @@ int board_ehci_hcd_init(int port)
 }
 #endif
 
-static void setup_iomux_fec(void)
-{
-	static const iomux_v3_cfg_t fec_pads[] = {
-		NEW_PAD_CTRL(MX53_PAD_FEC_MDIO__FEC_MDIO, PAD_CTL_HYS |
-			     PAD_CTL_DSE_HIGH | PAD_CTL_PUS_22K_UP |
-			     PAD_CTL_ODE),
-		NEW_PAD_CTRL(MX53_PAD_FEC_MDC__FEC_MDC, PAD_CTL_DSE_HIGH),
-		NEW_PAD_CTRL(MX53_PAD_FEC_RXD1__FEC_RDATA_1,
-			     PAD_CTL_HYS | PAD_CTL_PKE),
-		NEW_PAD_CTRL(MX53_PAD_FEC_RXD0__FEC_RDATA_0,
-			     PAD_CTL_HYS | PAD_CTL_PKE),
-		NEW_PAD_CTRL(MX53_PAD_FEC_TXD1__FEC_TDATA_1, PAD_CTL_DSE_HIGH),
-		NEW_PAD_CTRL(MX53_PAD_FEC_TXD0__FEC_TDATA_0, PAD_CTL_DSE_HIGH),
-		NEW_PAD_CTRL(MX53_PAD_FEC_TX_EN__FEC_TX_EN, PAD_CTL_DSE_HIGH),
-		NEW_PAD_CTRL(MX53_PAD_FEC_REF_CLK__FEC_TX_CLK,
-			     PAD_CTL_HYS | PAD_CTL_PKE),
-		NEW_PAD_CTRL(MX53_PAD_FEC_RX_ER__FEC_RX_ER,
-			     PAD_CTL_HYS | PAD_CTL_PKE),
-		NEW_PAD_CTRL(MX53_PAD_FEC_CRS_DV__FEC_RX_DV,
-			     PAD_CTL_HYS | PAD_CTL_PKE),
-	};
-
-	imx_iomux_v3_setup_multiple_pads(fec_pads, ARRAY_SIZE(fec_pads));
-}
-
 static int clock_1GHz(void)
 {
 	int ret;
@@ -170,7 +145,6 @@ void ppd_gpio_init(void)
 int board_early_init_f(void)
 {
 	setup_iomux_uart();
-	setup_iomux_fec();
 	ppd_gpio_init();
 
 	return 0;
diff --git a/configs/mx53ppd_defconfig b/configs/mx53ppd_defconfig
index 2094e74c7d..1fa9715850 100644
--- a/configs/mx53ppd_defconfig
+++ b/configs/mx53ppd_defconfig
@@ -45,6 +45,9 @@ CONFIG_MISC=y
 CONFIG_I2C_EEPROM=y
 CONFIG_DM_MMC=y
 CONFIG_FSL_ESDHC_IMX=y
+CONFIG_PHYLIB=y
+CONFIG_DM_ETH=y
+CONFIG_FEC_MXC=y
 CONFIG_MII=y
 CONFIG_PINCTRL=y
 CONFIG_PINCTRL_IMX5=y
diff --git a/include/configs/mx53ppd.h b/include/configs/mx53ppd.h
index 3b1615338c..5b1c467554 100644
--- a/include/configs/mx53ppd.h
+++ b/include/configs/mx53ppd.h
@@ -28,12 +28,6 @@
 #define CONFIG_MXC_UART
 #define CONFIG_MXC_UART_BASE	UART1_BASE
 
-/* Eth Configs */
-
-#define CONFIG_FEC_MXC
-#define IMX_FEC_BASE	FEC_BASE_ADDR
-#define CONFIG_FEC_MXC_PHYADDR	0x1F
-
 /* USB Configs */
 #define CONFIG_USB_HOST_ETHER
 #define CONFIG_USB_ETHER_ASIX
@@ -49,8 +43,6 @@
 
 /* Command definition */
 
-#define CONFIG_ETHPRIME		"FEC0"
-
 #define CONFIG_LOADADDR		0x72000000	/* loadaddr env var */
 
 #define PPD_CONFIG_NFS \
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 33/37] board: ge: bx50v3: use DM for uart
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (31 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 32/37] board: ge: mx53ppd: Use DM for ethernet Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 34/37] serial: mxc: add imx53 and imx21 compatible string Robert Beckett
                   ` (3 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Set chosen stdout-path in DT
Add uart3 and associated pinctrl definitions in DT
Remove legacy uart pad and iomux code
Enable DM serial and mxc uart

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 arch/arm/dts/imx6q-bx50v3.dts | 20 ++++++++++++++++++++
 board/ge/bx50v3/bx50v3.c      | 24 ------------------------
 configs/ge_bx50v3_defconfig   |  3 +++
 include/configs/ge_bx50v3.h   | 10 ++--------
 4 files changed, 25 insertions(+), 32 deletions(-)

diff --git a/arch/arm/dts/imx6q-bx50v3.dts b/arch/arm/dts/imx6q-bx50v3.dts
index e9aaca4a78..7b5fe3b5de 100644
--- a/arch/arm/dts/imx6q-bx50v3.dts
+++ b/arch/arm/dts/imx6q-bx50v3.dts
@@ -14,6 +14,10 @@
 	model = "General Electric Bx50v3";
 	compatible = "ge,imx6q-bx50v3", "advantech,imx6q-ba16", "fsl,imx6q";
 
+	chosen {
+		stdout-path = &uart3;
+	};
+
 	aliases {
 		ethernet0 = &fec;
 	};
@@ -236,6 +240,15 @@
 			MX6QDL_PAD_SD1_DAT3__PWM1_OUT	0x1b0b1
 		>;
 	};
+
+	pinctrl_uart3: uart3grp {
+		fsl,pins = <
+			MX6QDL_PAD_EIM_D25__UART3_RX_DATA 0x1b0b1
+			MX6QDL_PAD_EIM_D24__UART3_TX_DATA 0x1b0b1
+			MX6QDL_PAD_EIM_D23__UART3_CTS_B   0x1b0b1
+			MX6QDL_PAD_EIM_D31__UART3_RTS_B   0x1b0b1
+		>;
+	};
 };
 
 &usdhc1 {
@@ -596,3 +609,10 @@
 		interrupts = <10 IRQ_TYPE_LEVEL_HIGH>;
 	};
 };
+
+&uart3 {
+	pinctrl-names = "default";
+	pinctrl-0 = <&pinctrl_uart3>;
+	uart-has-rtscts;
+	status = "okay";
+};
diff --git a/board/ge/bx50v3/bx50v3.c b/board/ge/bx50v3/bx50v3.c
index 2e11697af0..aa4a3598c6 100644
--- a/board/ge/bx50v3/bx50v3.c
+++ b/board/ge/bx50v3/bx50v3.c
@@ -46,10 +46,6 @@ static struct vpd_cache vpd;
 	PAD_CTL_SPEED_MED | PAD_CTL_DSE_40ohm |	\
 	PAD_CTL_HYS)
 
-#define UART_PAD_CTRL  (PAD_CTL_PUS_100K_UP |			\
-	PAD_CTL_SPEED_MED | PAD_CTL_DSE_40ohm |			\
-	PAD_CTL_SRE_FAST  | PAD_CTL_HYS)
-
 #define ENET_PAD_CTRL  (PAD_CTL_PUS_100K_UP | PAD_CTL_PUE |	\
 	PAD_CTL_SPEED_HIGH | PAD_CTL_DSE_48ohm | PAD_CTL_SRE_FAST)
 
@@ -72,24 +68,6 @@ int dram_init(void)
 	return 0;
 }
 
-static iomux_v3_cfg_t const uart3_pads[] = {
-	MX6_PAD_EIM_D31__UART3_RTS_B | MUX_PAD_CTRL(UART_PAD_CTRL),
-	MX6_PAD_EIM_D23__UART3_CTS_B | MUX_PAD_CTRL(UART_PAD_CTRL),
-	MX6_PAD_EIM_D24__UART3_TX_DATA | MUX_PAD_CTRL(UART_PAD_CTRL),
-	MX6_PAD_EIM_D25__UART3_RX_DATA | MUX_PAD_CTRL(UART_PAD_CTRL),
-};
-
-static iomux_v3_cfg_t const uart4_pads[] = {
-	MX6_PAD_KEY_COL0__UART4_TX_DATA | MUX_PAD_CTRL(UART_PAD_CTRL),
-	MX6_PAD_KEY_ROW0__UART4_RX_DATA | MUX_PAD_CTRL(UART_PAD_CTRL),
-};
-
-static void setup_iomux_uart(void)
-{
-	imx_iomux_v3_setup_multiple_pads(uart3_pads, ARRAY_SIZE(uart3_pads));
-	imx_iomux_v3_setup_multiple_pads(uart4_pads, ARRAY_SIZE(uart4_pads));
-}
-
 static int mx6_rgmii_rework(struct phy_device *phydev)
 {
 	/* Configure AR8033 to ouput a 125MHz clk from CLK_25M */
@@ -423,8 +401,6 @@ int board_early_init_f(void)
 	imx_iomux_v3_setup_multiple_pads(misc_pads,
 					 ARRAY_SIZE(misc_pads));
 
-	setup_iomux_uart();
-
 #if defined(CONFIG_VIDEO_IPUV3)
 	/* Set LDB clock to Video PLL */
 	select_ldb_di_clock_source(MXC_PLL5_CLK);
diff --git a/configs/ge_bx50v3_defconfig b/configs/ge_bx50v3_defconfig
index 977aac41f6..8acb41c046 100644
--- a/configs/ge_bx50v3_defconfig
+++ b/configs/ge_bx50v3_defconfig
@@ -65,6 +65,9 @@ CONFIG_DM_REGULATOR=y
 CONFIG_DM_REGULATOR_FIXED=y
 CONFIG_DM_RTC=y
 CONFIG_RTC_RX8010SJ=y
+# CONFIG_REQUIRE_SERIAL_CONSOLE is not set
+CONFIG_DM_SERIAL=y
+CONFIG_MXC_UART=y
 CONFIG_SPI=y
 CONFIG_DM_SPI=y
 CONFIG_MXC_SPI=y
diff --git a/include/configs/ge_bx50v3.h b/include/configs/ge_bx50v3.h
index 6ca43c3cf7..d59a965792 100644
--- a/include/configs/ge_bx50v3.h
+++ b/include/configs/ge_bx50v3.h
@@ -16,9 +16,6 @@
 
 #define CONFIG_BOARD_NAME	"General Electric Bx50v3"
 
-#define CONFIG_MXC_UART_BASE	UART3_BASE
-#define CONSOLE_DEV	"ttymxc2"
-
 #include "mx6_common.h"
 #include <linux/sizes.h>
 
@@ -28,8 +25,6 @@
 #define CONFIG_REVISION_TAG
 #define CONFIG_SYS_MALLOC_LEN		(10 * SZ_1M)
 
-#define CONFIG_MXC_UART
-
 /* SATA Configs */
 #ifdef CONFIG_CMD_SATA
 #define CONFIG_SYS_SATA_MAX_DEVICE	1
@@ -64,7 +59,7 @@
                 "setenv netmask 255.255.255.0; setenv ethaddr ca:fe:de:ca:f0:11; " \
                 "setenv bootargs root=/dev/nfs nfsroot=${nfsserver}:/srv/nfs/,v3,tcp rw rootwait" \
                 "setenv bootargs $bootargs ip=${ipaddr}:${nfsserver}:${gatewayip}:${netmask}::eth0:off " \
-                "setenv bootargs $bootargs cma=128M bootcause=POR console=${console} ${videoargs} " \
+                "setenv bootargs $bootargs cma=128M bootcause=POR ${videoargs} " \
                 "setenv bootargs $bootargs systemd.mask=helix-network-defaults.service " \
                 "setenv bootargs $bootargs watchdog.handle_boot_enabled=1\0" \
         "networkboot=" \
@@ -89,11 +84,10 @@
 	"devnum=2\0" \
 	"rootdev=mmcblk0p\0" \
 	"quiet=quiet loglevel=0\0" \
-	"console=" CONSOLE_DEV "\0" \
 	"setargs=setenv bootargs root=/dev/${rootdev}${partnum} " \
 		"ro rootwait cma=128M " \
 		"bootcause=${bootcause} " \
-		"${quiet} console=${console} " \
+		"${quiet} " \
 		"${videoargs}" "\0" \
 	"doquiet=" \
 		"if ext2load ${dev} ${devnum}:5 0x7000A000 /boot/console; " \
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 34/37] serial: mxc: add imx53 and imx21 compatible string
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (32 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 33/37] board: ge: bx50v3: use DM for uart Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 35/37] board: ge: mx53ppd: use DM for uart Robert Beckett
                   ` (2 subsequent siblings)
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Add compatible string for imx53 and imx21.

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 drivers/serial/serial_mxc.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/drivers/serial/serial_mxc.c b/drivers/serial/serial_mxc.c
index 42abb96a26..8e19a89151 100644
--- a/drivers/serial/serial_mxc.c
+++ b/drivers/serial/serial_mxc.c
@@ -348,6 +348,8 @@ static const struct udevice_id mxc_serial_ids[] = {
 	{ .compatible = "fsl,imx6ul-uart" },
 	{ .compatible = "fsl,imx7d-uart" },
 	{ .compatible = "fsl,imx6q-uart" },
+	{ .compatible = "fsl,imx53-uart" },
+	{ .compatible = "fsl,imx21-uart" },
 	{ }
 };
 #endif
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 35/37] board: ge: mx53ppd: use DM for uart
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (33 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 34/37] serial: mxc: add imx53 and imx21 compatible string Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 36/37] dm: pmic: add da9063 PMIC driver and regulators Robert Beckett
  2019-10-15 15:53 ` [U-Boot] [PATCH 37/37] board: ge: bx50v3: use DM PMIC driver Robert Beckett
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Set chose stdout-path in DT
Add uart1 and associated pinctrl definitions in DT
Remove legacy uart pad and iomux code
Enable DM serial and mxc uart

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 arch/arm/dts/imx53-ppd.dts | 17 +++++++++++++++++
 board/ge/mx53ppd/mx53ppd.c | 14 --------------
 configs/mx53ppd_defconfig  |  3 +++
 include/configs/mx53ppd.h  |  9 +--------
 4 files changed, 21 insertions(+), 22 deletions(-)

diff --git a/arch/arm/dts/imx53-ppd.dts b/arch/arm/dts/imx53-ppd.dts
index d308abc09c..681bc89331 100644
--- a/arch/arm/dts/imx53-ppd.dts
+++ b/arch/arm/dts/imx53-ppd.dts
@@ -13,6 +13,10 @@
 	model = "General Electric CS ONE";
 	compatible = "ge,imx53-cpuvo", "fsl,imx53";
 
+	chosen {
+		stdout-path = "serial0:115200n8";
+	};
+
 	wdt-reboot {
 		compatible = "wdt-reboot";
 		wdt = <&wdog1>;
@@ -167,6 +171,13 @@
 			MX53_PAD_FEC_TXD0__FEC_TDATA_0		0x0
 		>;
 	};
+
+	pinctrl_uart1: uart1grp {
+		fsl,pins = <
+			MX53_PAD_PATA_DIOW__UART1_TXD_MUX	0x1e4
+			MX53_PAD_PATA_DMACK__UART1_RXD_MUX	0x1e4
+		>;
+	};
 };
 
 /* eMMC */
@@ -341,3 +352,9 @@
 	phy-reset-gpios = <&gpio2 16 GPIO_ACTIVE_LOW>;
 	status = "okay";
 };
+
+&uart1 {
+	pinctrl-names = "default";
+	pinctrl-0 = <&pinctrl_uart1>;
+	status = "okay";
+};
diff --git a/board/ge/mx53ppd/mx53ppd.c b/board/ge/mx53ppd/mx53ppd.c
index 486ef6d374..a8d4bf363e 100644
--- a/board/ge/mx53ppd/mx53ppd.c
+++ b/board/ge/mx53ppd/mx53ppd.c
@@ -79,24 +79,11 @@ int dram_init_banksize(void)
 	return 0;
 }
 
-static void setup_iomux_uart(void)
-{
-	static const iomux_v3_cfg_t uart_pads[] = {
-		MX53_PAD_PATA_DMACK__UART1_RXD_MUX,
-		MX53_PAD_PATA_DIOW__UART1_TXD_MUX,
-	};
-
-	imx_iomux_v3_setup_multiple_pads(uart_pads, ARRAY_SIZE(uart_pads));
-}
-
 u32 get_board_rev(void)
 {
 	return get_cpu_rev() & ~(0xF << 8);
 }
 
-#define UART_PAD_CTRL	(PAD_CTL_HYS | PAD_CTL_DSE_HIGH | \
-			 PAD_CTL_PUS_100K_UP | PAD_CTL_ODE)
-
 #ifdef CONFIG_USB_EHCI_MX5
 int board_ehci_hcd_init(int port)
 {
@@ -144,7 +131,6 @@ void ppd_gpio_init(void)
 
 int board_early_init_f(void)
 {
-	setup_iomux_uart();
 	ppd_gpio_init();
 
 	return 0;
diff --git a/configs/mx53ppd_defconfig b/configs/mx53ppd_defconfig
index 1fa9715850..ac1b701e69 100644
--- a/configs/mx53ppd_defconfig
+++ b/configs/mx53ppd_defconfig
@@ -54,6 +54,9 @@ CONFIG_PINCTRL_IMX5=y
 CONFIG_PWM_IMX=y
 CONFIG_DM_RTC=y
 CONFIG_RTC_S35392A=y
+# CONFIG_REQUIRE_SERIAL_CONSOLE is not set
+CONFIG_DM_SERIAL=y
+CONFIG_MXC_UART=y
 CONFIG_USB=y
 CONFIG_USB_EHCI_MX5=y
 CONFIG_VIDEO_IPUV3=y
diff --git a/include/configs/mx53ppd.h b/include/configs/mx53ppd.h
index 5b1c467554..7bbb0f8dfd 100644
--- a/include/configs/mx53ppd.h
+++ b/include/configs/mx53ppd.h
@@ -11,8 +11,6 @@
 
 #include <asm/arch/imx-regs.h>
 
-#define CONSOLE_DEV	"ttymxc0"
-
 #define CONFIG_CMDLINE_TAG
 #define CONFIG_SETUP_MEMORY_TAGS
 #define CONFIG_INITRD_TAG
@@ -25,9 +23,6 @@
 #define CONFIG_BOARD_LATE_INIT
 #define CONFIG_REVISION_TAG
 
-#define CONFIG_MXC_UART
-#define CONFIG_MXC_UART_BASE	UART1_BASE
-
 /* USB Configs */
 #define CONFIG_USB_HOST_ETHER
 #define CONFIG_USB_ETHER_ASIX
@@ -70,11 +65,9 @@
 	"devnum=2\0" \
 	"rootdev=mmcblk0p\0" \
 	"quiet=quiet loglevel=0\0" \
-	"console=" CONSOLE_DEV "\0" \
 	"lvds=ldb\0" \
 	"setargs=setenv bootargs ${lvds} jtag=on mem=2G " \
-		"vt.global_cursor_default=0 bootcause=${bootcause} ${quiet} " \
-		"console=${console}\0" \
+		"vt.global_cursor_default=0 bootcause=${bootcause} ${quiet}\0" \
 	"bootargs_emmc=setenv bootargs root=/dev/${rootdev}${partnum} ro " \
 		"rootwait ${bootargs}\0" \
 	"doquiet=if ext2load ${dev} ${devnum}:5 0x7000A000 /boot/console; " \
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 36/37] dm: pmic: add da9063 PMIC driver and regulators
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (34 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 35/37] board: ge: mx53ppd: use DM for uart Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  2019-10-16  7:24   ` Schrempf Frieder
  2019-10-15 15:53 ` [U-Boot] [PATCH 37/37] board: ge: bx50v3: use DM PMIC driver Robert Beckett
  36 siblings, 1 reply; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Add DM driver to support Dialog DA9063.
Currently it support binding regulator children.

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 drivers/power/pmic/Kconfig       |   8 +
 drivers/power/pmic/Makefile      |   1 +
 drivers/power/pmic/da9063.c      | 270 ++++++++++++++++++++++++++
 drivers/power/regulator/Kconfig  |   7 +
 drivers/power/regulator/Makefile |   1 +
 drivers/power/regulator/da9063.c | 320 +++++++++++++++++++++++++++++++
 include/power/da9063_pmic.h      | 303 +++++++++++++++++++++++++++++
 7 files changed, 910 insertions(+)
 create mode 100644 drivers/power/pmic/da9063.c
 create mode 100644 drivers/power/regulator/da9063.c
 create mode 100644 include/power/da9063_pmic.h

diff --git a/drivers/power/pmic/Kconfig b/drivers/power/pmic/Kconfig
index 586772fdec..6dd7b1bf76 100644
--- a/drivers/power/pmic/Kconfig
+++ b/drivers/power/pmic/Kconfig
@@ -267,3 +267,11 @@ config SPL_PMIC_LP87565
 	help
 	The LP87565 is a PMIC containing a bunch of SMPS.
 	This driver binds the pmic children in SPL.
+
+config DM_PMIC_DA9063
+	bool "Enable support for Dialog DA9063 PMIC"
+	depends on DM_PMIC && (DM_I2C || DM_SPI)
+	help
+	The DA9063 is a PMIC providing 6 BUCK converters and 11 LDO regulators.
+	It can be accessed via I2C or SPI.
+	This driver binds the pmic children.
diff --git a/drivers/power/pmic/Makefile b/drivers/power/pmic/Makefile
index 888dbb2857..9be9d5d9a0 100644
--- a/drivers/power/pmic/Makefile
+++ b/drivers/power/pmic/Makefile
@@ -25,6 +25,7 @@ obj-$(CONFIG_$(SPL_)PMIC_PALMAS) += palmas.o
 obj-$(CONFIG_$(SPL_)PMIC_LP873X) += lp873x.o
 obj-$(CONFIG_$(SPL_)PMIC_LP87565) += lp87565.o
 obj-$(CONFIG_PMIC_STPMIC1) += stpmic1.o
+obj-$(CONFIG_DM_PMIC_DA9063) += da9063.o
 
 obj-$(CONFIG_POWER_LTC3676) += pmic_ltc3676.o
 obj-$(CONFIG_POWER_MAX77696) += pmic_max77696.o
diff --git a/drivers/power/pmic/da9063.c b/drivers/power/pmic/da9063.c
new file mode 100644
index 0000000000..81a7803b09
--- /dev/null
+++ b/drivers/power/pmic/da9063.c
@@ -0,0 +1,270 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * (C) Copyright 2019 Collabora
+ * (C) Copyright 2019 GE
+ */
+
+#define DEBUG 1
+#include <common.h>
+#include <fdtdec.h>
+#include <errno.h>
+#include <dm.h>
+#include <i2c.h>
+#include <spi.h>
+#include <linux/bitfield.h>
+#include <power/pmic.h>
+#include <power/regulator.h>
+#include <power/da9063_pmic.h>
+
+static const struct pmic_child_info pmic_children_info[] = {
+	{ .prefix = "bcore", .driver = DA9063_BUCK_DRIVER },
+	{ .prefix = "bpro", .driver = DA9063_BUCK_DRIVER },
+	{ .prefix = "bmem", .driver = DA9063_BUCK_DRIVER },
+	{ .prefix = "bio", .driver = DA9063_BUCK_DRIVER },
+	{ .prefix = "bperi", .driver = DA9063_BUCK_DRIVER },
+	{ .prefix = "ldo", .driver = DA9063_LDO_DRIVER },
+	{ },
+};
+
+static int da9063_reg_count(struct udevice *dev)
+{
+	return DA9063_NUM_OF_REGS;
+}
+
+#if defined(CONFIG_DM_I2C)
+static int da9063_i2c_read(struct udevice *dev, uint reg, uint8_t *buff,
+			   int len)
+{
+	int ret;
+
+	/* only support single reg accesses */
+	if (len != 1)
+		return -EINVAL;
+
+	ret = dm_i2c_read(dev, reg, buff, len);
+	if (ret) {
+		pr_err("%s: unable to read reg %#x: %d\n", __func__, reg, ret);
+		return ret;
+	}
+
+	return 0;
+}
+
+static int da9063_i2c_write(struct udevice *dev, uint reg, const uint8_t *buff,
+			    int len)
+{
+	int ret;
+
+	/* only support single reg accesses */
+	if (len != 1)
+		return -EINVAL;
+
+	ret = dm_i2c_write(dev, reg, buff, len);
+	if (ret) {
+		pr_err("%s: unable to write reg %#x: %d\n", __func__, reg, ret);
+		return ret;
+	}
+
+	return 0;
+}
+#endif
+
+#if defined(CONFIG_DM_SPI)
+static int da9063_spi_read(struct udevice *dev, uint reg, uint8_t *buff,
+			   int len)
+{
+	u8 page;
+	u8 data[2];
+	int ret;
+
+	/* only support single reg accesses */
+	if (len != 1)
+		return -EINVAL;
+
+	page = FIELD_GET(DA9063_REG_PAGE_MASK, reg);
+	reg = FIELD_GET(DA9063_REG_ADDR_MASK, reg);
+
+	ret = dm_spi_claim_bus(dev);
+	if (ret)
+		return ret;
+	/* set page */
+	data[0] = FIELD_PREP(DA9063_PROTO_ADDR_MASK, DA9063_PAGE_CON) |
+		  FIELD_PREP(DA9063_PROTO_RW_MASK, DA9063_PROTO_WRITE);
+	data[1] = FIELD_PREP(DA9063_PAGE_CON_PAGE, page);
+	ret = dm_spi_xfer(dev, DA9063_PROTO_LEN, data, NULL, SPI_XFER_ONCE);
+	if (ret) {
+		pr_err("%s: unable to set page: %d\n", __func__, ret);
+		goto err_page;
+	}
+
+	/* set target reg */
+	data[0] = FIELD_PREP(DA9063_PROTO_ADDR_MASK, reg) |
+		  FIELD_PREP(DA9063_PROTO_RW_MASK, DA9063_PROTO_READ);
+	data[1] = 0;
+	ret = dm_spi_xfer(dev, DA9063_PROTO_LEN, data, data, SPI_XFER_ONCE);
+	if (ret) {
+		pr_err("%s: unable to read reg %#x: %d\n", __func__, reg, ret);
+		goto err_reg;
+	}
+	dm_spi_release_bus(dev);
+
+	*buff = data[1];
+
+	return 0;
+
+err_page:
+err_reg:
+	dm_spi_release_bus(dev);
+
+	return ret;
+}
+
+static int da9063_spi_write(struct udevice *dev, uint reg, const uint8_t *buff,
+			    int len)
+{
+	u8 page;
+	u8 data[2];
+	int ret;
+
+	/* only support single reg accesses */
+	if (len != 1)
+		return -EINVAL;
+
+	page = FIELD_GET(DA9063_REG_PAGE_MASK, reg);
+	reg = FIELD_GET(DA9063_REG_ADDR_MASK, reg);
+
+	ret = dm_spi_claim_bus(dev);
+	if (ret)
+		return ret;
+	/* set page */
+	data[0] = FIELD_PREP(DA9063_PROTO_ADDR_MASK, DA9063_PAGE_CON) |
+		  FIELD_PREP(DA9063_PROTO_RW_MASK, DA9063_PROTO_WRITE);
+	data[1] = FIELD_PREP(DA9063_PAGE_CON_PAGE, page);
+	ret = dm_spi_xfer(dev, DA9063_PROTO_LEN, data, NULL, SPI_XFER_ONCE);
+	if (ret) {
+		pr_err("%s: unable to set page: %d\n", __func__, ret);
+		goto err_page;
+	}
+
+	/* set target reg */
+	data[0] = FIELD_PREP(DA9063_PROTO_ADDR_MASK, reg) |
+		  FIELD_PREP(DA9063_PROTO_RW_MASK, DA9063_PROTO_WRITE);
+	data[1] = *buff;
+	ret = dm_spi_xfer(dev, DA9063_PROTO_LEN, data, NULL, SPI_XFER_ONCE);
+	if (ret) {
+		pr_err("%s: unable to write reg %#x: %d\n", __func__, reg, ret);
+		goto err_reg;
+	}
+	dm_spi_release_bus(dev);
+
+	return 0;
+
+err_page:
+err_reg:
+	dm_spi_release_bus(dev);
+
+	return ret;
+}
+#endif
+
+struct da9063_priv {
+	int (*read)(struct udevice *dev, uint reg, uint8_t *buffer, int len);
+	int (*write)(struct udevice *dev, uint reg, const uint8_t *buffer,
+		     int len);
+};
+
+static int da9063_read(struct udevice *dev, uint reg, uint8_t *buff, int len)
+{
+	struct da9063_priv *priv = dev_get_priv(dev);
+
+	return priv->read(dev, reg, buff, len);
+}
+
+static int da9063_write(struct udevice *dev, uint reg, const uint8_t *buff,
+			int len)
+{
+	struct da9063_priv *priv = dev_get_priv(dev);
+
+	return priv->write(dev, reg, buff, len);
+}
+
+static struct dm_pmic_ops da9063_ops = {
+	.reg_count = da9063_reg_count,
+	.read = da9063_read,
+	.write = da9063_write,
+};
+
+static int da9063_bind(struct udevice *dev)
+{
+	ofnode regulators_node;
+	int children;
+
+	regulators_node = dev_read_subnode(dev, "regulators");
+	if (!ofnode_valid(regulators_node)) {
+		pr_debug("%s: %s regulators subnode not found!\n", __func__,
+			 dev->name);
+		return -ENXIO;
+	}
+
+	pr_debug("%s: '%s' - found regulators subnode\n", __func__, dev->name);
+
+	children = pmic_bind_children(dev, regulators_node, pmic_children_info);
+	if (!children)
+		pr_debug("%s: %s - no child found\n", __func__, dev->name);
+
+	return 0;
+}
+
+static int da9063_probe(struct udevice *dev)
+{
+	struct da9063_priv *priv = dev_get_priv(dev);
+	int ret;
+
+	if (device_get_uclass_id(dev->parent) == UCLASS_I2C) {
+#if defined(CONFIG_DM_I2C)
+		i2c_set_chip_addr_offset_mask(dev, 0x1);
+		priv->read = da9063_i2c_read;
+		priv->write = da9063_i2c_write;
+#else
+		return -ENODEV;
+#endif
+	} else if (device_get_uclass_id(dev->parent) == UCLASS_SPI) {
+#if defined(CONFIG_DM_SPI)
+		priv->read = da9063_spi_read;
+		priv->write = da9063_spi_write;
+#else
+		return -ENODEV;
+#endif
+	} else {
+		pr_err("%s: invalid bus\n", __func__);
+		return -ENODEV;
+	}
+
+	ret = pmic_reg_read(dev, DA9063_CHIP_ID);
+	if (ret < 0) {
+		pr_debug("%s: unable to read chip id: %d\n", __func__, ret);
+		return ret;
+	}
+
+	if (ret != DA9063_CHIP_ID_DA9063) {
+		pr_debug("%s: unknown chip id: %#x\n", __func__, ret);
+		return -ENODEV;
+	}
+
+	return 0;
+}
+
+static const struct udevice_id da9063_ids[] = {
+	{ .compatible = "dlg,da9063" },
+	{ }
+};
+
+U_BOOT_DRIVER(pmic_da9063) = {
+	.name = "da9063_pmic",
+	.id = UCLASS_PMIC,
+	.of_match = da9063_ids,
+	.bind = da9063_bind,
+	.ops = &da9063_ops,
+	.priv_auto_alloc_size = sizeof(struct da9063_priv),
+	.probe = da9063_probe,
+};
diff --git a/drivers/power/regulator/Kconfig b/drivers/power/regulator/Kconfig
index 9aa00fad42..e87cccdb82 100644
--- a/drivers/power/regulator/Kconfig
+++ b/drivers/power/regulator/Kconfig
@@ -313,3 +313,10 @@ config SPL_DM_REGULATOR_LP873X
 	This enables implementation of driver-model regulator uclass
 	features for REGULATOR LP873X and the family of LP873X PMICs.
 	The driver implements get/set api for: value and enable in SPL.
+
+config DM_REGULATOR_DA9063
+	bool "Enable support for DA9063 regulators"
+	help
+	Enable support the regulator functions of the DA9063 PMIC.
+	The driver support voltage set/get and enable/disable for LDOs and
+	BUCKs, and mode get/set for BUCKs.
diff --git a/drivers/power/regulator/Makefile b/drivers/power/regulator/Makefile
index 6a3d4bbee4..f0926614cb 100644
--- a/drivers/power/regulator/Makefile
+++ b/drivers/power/regulator/Makefile
@@ -27,3 +27,4 @@ obj-$(CONFIG_$(SPL_)DM_REGULATOR_LP87565) += lp87565_regulator.o
 obj-$(CONFIG_$(SPL_)DM_REGULATOR_STM32_VREFBUF) += stm32-vrefbuf.o
 obj-$(CONFIG_DM_REGULATOR_TPS65910) += tps65910_regulator.o
 obj-$(CONFIG_$(SPL_)DM_REGULATOR_STPMIC1) += stpmic1.o
+obj-$(CONFIG_DM_REGULATOR_DA9063) += da9063.o
diff --git a/drivers/power/regulator/da9063.c b/drivers/power/regulator/da9063.c
new file mode 100644
index 0000000000..68036a3951
--- /dev/null
+++ b/drivers/power/regulator/da9063.c
@@ -0,0 +1,320 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * (C) Copyright 2019 Collabora
+ * (C) Copyright 2019 GE
+ */
+
+#include <common.h>
+#include <fdtdec.h>
+#include <dm.h>
+#include <linux/bitfield.h>
+#include <power/pmic.h>
+#include <power/regulator.h>
+#include <power/da9063_pmic.h>
+
+enum {
+	DA9063_ID_BCORE1 = 0,
+	DA9063_ID_BCORE2,
+	DA9063_ID_BPRO,
+	DA9063_ID_BMEM,
+	DA9063_ID_BIO,
+	DA9063_ID_BPERI,
+};
+
+struct buck_info {
+	int min_uV;
+	int max_uV;
+	int step_uV;
+	int ctrl_reg;
+	int volt_reg;
+	int mode_reg;
+};
+
+#define to_buck_info(dev) (struct buck_info *)dev->driver_data
+
+#define DA9063_BUCK(name, min_mV, max_mV, step_mV) \
+{ \
+	.min_uV = min_mV * 1000, \
+	.max_uV = max_mV * 1000, \
+	.step_uV = step_mV * 1000, \
+	.ctrl_reg = DA9063_##name##_CONT, \
+	.volt_reg = DA9063_V##name##_A, \
+	.mode_reg = DA9063_##name##_CFG, \
+}
+
+static const struct buck_info da9063_buck_info[] = {
+	[DA9063_ID_BCORE1] = DA9063_BUCK(BCORE1, 300, 1570, 10),
+	[DA9063_ID_BCORE2] = DA9063_BUCK(BCORE2, 300, 1570, 10),
+	[DA9063_ID_BPRO]   = DA9063_BUCK(BPRO, 530, 1800, 10),
+	[DA9063_ID_BMEM]   = DA9063_BUCK(BMEM, 800, 3340, 20),
+	[DA9063_ID_BIO]    = DA9063_BUCK(BIO, 800, 3340, 20),
+	[DA9063_ID_BPERI]  = DA9063_BUCK(BPERI, 800, 3340, 20),
+};
+
+/* Buck converters can either be in auto mode or sync mode.
+ * Auto uses PWM or PFM depending on load current.
+ * Sync mode uses PFM unless output voltage is < 0.7V.
+ */
+static struct dm_regulator_mode da9063_buck_modes[] = {
+	{
+		.id = DA9063_OPMODE_AUTO,
+		.register_value = DA9063_BUCK_MODE_AUTO,
+		.name = "AUTO",
+	},
+	{
+		.id = DA9063_OPMODE_SYNC,
+		.register_value = DA9063_BUCK_MODE_SYNC,
+		.name = "SYNC",
+	},
+};
+
+static int da9063_buck_get_mode(struct udevice *dev)
+{
+	struct buck_info *info = to_buck_info(dev);
+	int mode = pmic_reg_read(dev_get_parent(dev), info->mode_reg);
+
+	if (mode < 0)
+		return mode;
+
+	mode = FIELD_GET(DA9063_BUCK_MODE, mode);
+
+	switch (mode) {
+	case DA9063_BUCK_MODE_AUTO:
+		return DA9063_OPMODE_AUTO;
+	case DA9063_BUCK_MODE_SYNC:
+		return DA9063_OPMODE_SYNC;
+	default:
+		return -EINVAL;
+	}
+}
+
+static int da9063_buck_set_mode(struct udevice *dev, int rmode)
+{
+	struct buck_info *info = to_buck_info(dev);
+	int mode = pmic_reg_read(dev_get_parent(dev), info->mode_reg);
+
+	mode &= ~DA9063_BUCK_MODE;
+
+	switch (rmode) {
+	case DA9063_OPMODE_AUTO:
+		mode |= FIELD_PREP(DA9063_BUCK_MODE, DA9063_BUCK_MODE_AUTO);
+		break;
+	case DA9063_OPMODE_SYNC:
+		mode |= FIELD_PREP(DA9063_BUCK_MODE, DA9063_BUCK_MODE_SYNC);
+		break;
+	default:
+		return -EINVAL;
+	}
+
+	return pmic_reg_write(dev_get_parent(dev), info->mode_reg, mode);
+}
+
+static int da9063_buck_get_value(struct udevice *dev)
+{
+	struct buck_info *info = to_buck_info(dev);
+	int sel = pmic_reg_read(dev_get_parent(dev), info->volt_reg);
+
+	if (sel < 0)
+		return sel;
+	sel = FIELD_GET(DA9063_BUCK_VSEL, sel);
+	return info->min_uV + (info->step_uV * sel);
+}
+
+static int da9063_buck_set_value(struct udevice *dev, int uV)
+{
+	struct buck_info *info = to_buck_info(dev);
+	int sel = pmic_reg_read(dev_get_parent(dev), info->volt_reg);
+
+	if (sel < 0)
+		return sel;
+	sel &= ~DA9063_BUCK_VSEL;
+	sel |= FIELD_PREP(DA9063_BUCK_VSEL,
+			  DIV_ROUND_UP(uV - info->min_uV, info->step_uV));
+
+	return pmic_reg_write(dev_get_parent(dev), info->volt_reg, sel);
+}
+
+static int da9063_buck_get_enable(struct udevice *dev)
+{
+	struct buck_info *info = to_buck_info(dev);
+	int cont = pmic_reg_read(dev_get_parent(dev), info->ctrl_reg);
+
+	if (cont < 0)
+		return cont;
+
+	return FIELD_GET(DA9063_BUCK_ENABLE, cont);
+}
+
+static int da9063_buck_set_enable(struct udevice *dev, bool enable)
+{
+	struct buck_info *info = to_buck_info(dev);
+	int cont = pmic_reg_read(dev_get_parent(dev), info->ctrl_reg);
+
+	if (cont < 0)
+		return cont;
+
+	cont &= ~DA9063_BUCK_ENABLE;
+	cont |= FIELD_PREP(DA9063_BUCK_ENABLE, enable);
+
+	return pmic_reg_write(dev_get_parent(dev), info->ctrl_reg, cont);
+}
+
+static int da9063_buck_probe(struct udevice *dev)
+{
+	struct dm_regulator_uclass_platdata *uc_pdata;
+
+	uc_pdata = dev_get_uclass_platdata(dev);
+
+	if (!strcmp(uc_pdata->name, "bcore1"))
+		dev->driver_data = (ulong)&da9063_buck_info[DA9063_ID_BCORE1];
+	else if (!strcmp(uc_pdata->name, "bcore2"))
+		dev->driver_data = (ulong)&da9063_buck_info[DA9063_ID_BCORE2];
+	else if (!strcmp(uc_pdata->name, "bpro"))
+		dev->driver_data = (ulong)&da9063_buck_info[DA9063_ID_BPRO];
+	else if (!strcmp(uc_pdata->name, "bmem"))
+		dev->driver_data = (ulong)&da9063_buck_info[DA9063_ID_BMEM];
+	else if (!strcmp(uc_pdata->name, "bio"))
+		dev->driver_data = (ulong)&da9063_buck_info[DA9063_ID_BIO];
+	else if (!strcmp(uc_pdata->name, "bperi"))
+		dev->driver_data = (ulong)&da9063_buck_info[DA9063_ID_BPERI];
+	else
+		return -ENODEV;
+
+	uc_pdata->type = REGULATOR_TYPE_BUCK;
+	uc_pdata->mode_count = ARRAY_SIZE(da9063_buck_modes);
+	uc_pdata->mode = da9063_buck_modes;
+
+	return 0;
+}
+
+static const struct dm_regulator_ops da9063_buck_ops = {
+	.get_value  = da9063_buck_get_value,
+	.set_value  = da9063_buck_set_value,
+	.get_enable = da9063_buck_get_enable,
+	.set_enable = da9063_buck_set_enable,
+	.get_mode   = da9063_buck_get_mode,
+	.set_mode   = da9063_buck_set_mode,
+};
+
+U_BOOT_DRIVER(da9063_buck) = {
+	.name  = DA9063_BUCK_DRIVER,
+	.id    = UCLASS_REGULATOR,
+	.ops   = &da9063_buck_ops,
+	.probe = da9063_buck_probe,
+};
+
+struct ldo_info {
+	int min_uV;
+	int max_uV;
+	int step_uV;
+	int ctrl_reg;
+	int volt_reg;
+};
+
+#define to_ldo_info(dev) (struct ldo_info *)dev->driver_data
+
+#define DA9063_LDO(idx, min_mV, max_mV, step_mV) \
+{ \
+	.min_uV = min_mV * 1000, \
+	.max_uV = max_mV * 1000, \
+	.step_uV = step_mV * 1000, \
+	.ctrl_reg = DA9063_LDO##idx##_CONT, \
+	.volt_reg = DA9063_VLDO##idx##_A, \
+}
+
+static const struct ldo_info da9063_ldo_info[] = {
+	DA9063_LDO(1, 600, 1860, 20),
+	DA9063_LDO(2, 600, 1860, 20),
+	DA9063_LDO(3, 900, 3440, 20),
+	DA9063_LDO(4, 900, 3440, 20),
+	DA9063_LDO(5, 900, 3600, 50),
+	DA9063_LDO(6, 900, 3600, 50),
+	DA9063_LDO(7, 900, 3600, 50),
+	DA9063_LDO(8, 900, 3600, 50),
+	DA9063_LDO(9, 950, 3600, 50),
+	DA9063_LDO(10, 900, 3600, 50),
+	DA9063_LDO(11, 900, 3600, 50),
+};
+
+static int da9063_ldo_get_value(struct udevice *dev)
+{
+	struct ldo_info *info = to_ldo_info(dev);
+	int sel;
+
+	sel = pmic_reg_read(dev_get_parent(dev), info->volt_reg);
+	if (sel < 0)
+		return sel;
+	sel = FIELD_GET(DA9063_LDO_VSEL, sel);
+	return info->min_uV + (info->step_uV * sel);
+}
+
+static int da9063_ldo_set_value(struct udevice *dev, int uV)
+{
+	struct ldo_info *info = to_ldo_info(dev);
+	int sel;
+
+	sel = pmic_reg_read(dev_get_parent(dev), info->volt_reg);
+	if (sel < 0)
+		return sel;
+	sel &= ~DA9063_LDO_VSEL;
+	sel |= FIELD_PREP(DA9063_LDO_VSEL,
+			  DIV_ROUND_UP(uV - info->min_uV, info->step_uV));
+
+	return pmic_reg_write(dev_get_parent(dev), info->volt_reg, sel);
+}
+
+static int da9063_ldo_get_enable(struct udevice *dev)
+{
+	struct ldo_info *info = to_ldo_info(dev);
+	int cont = pmic_reg_read(dev_get_parent(dev), info->ctrl_reg);
+
+	if (cont < 0)
+		return cont;
+
+	return FIELD_GET(DA9063_LDO_ENABLE, cont);
+}
+
+static int da9063_ldo_set_enable(struct udevice *dev, bool enable)
+{
+	struct ldo_info *info = to_ldo_info(dev);
+	int cont = pmic_reg_read(dev_get_parent(dev), info->ctrl_reg);
+
+	if (cont < 0)
+		return cont;
+
+	cont &= ~DA9063_LDO_ENABLE;
+	cont |= FIELD_PREP(DA9063_LDO_ENABLE, enable);
+
+	return pmic_reg_write(dev_get_parent(dev), info->ctrl_reg, cont);
+}
+
+static int da9063_ldo_probe(struct udevice *dev)
+{
+	struct dm_regulator_uclass_platdata *uc_pdata;
+
+	if (dev->driver_data < 1 ||
+	    dev->driver_data > ARRAY_SIZE(da9063_ldo_info))
+		return -EINVAL;
+
+	uc_pdata = dev_get_uclass_platdata(dev);
+
+	dev->driver_data = (ulong)&da9063_ldo_info[dev->driver_data - 1];
+	uc_pdata->type = REGULATOR_TYPE_LDO;
+	uc_pdata->mode_count = 0;
+
+	return 0;
+}
+
+static const struct dm_regulator_ops da9063_ldo_ops = {
+	.get_value = da9063_ldo_get_value,
+	.set_value = da9063_ldo_set_value,
+	.get_enable = da9063_ldo_get_enable,
+	.set_enable = da9063_ldo_set_enable,
+};
+
+U_BOOT_DRIVER(da9063_ldo) = {
+	.name = DA9063_LDO_DRIVER,
+	.id = UCLASS_REGULATOR,
+	.ops = &da9063_ldo_ops,
+	.probe = da9063_ldo_probe,
+};
diff --git a/include/power/da9063_pmic.h b/include/power/da9063_pmic.h
new file mode 100644
index 0000000000..7258987ae3
--- /dev/null
+++ b/include/power/da9063_pmic.h
@@ -0,0 +1,303 @@
+/* SPDX-License-Identifier: GPL-2.0+ */
+/*
+ * (C) Copyright 2019 Collabora
+ * (C) Copyright 2019 GE
+ */
+
+#ifndef __DA9063_PMIC_H_
+#define __DA9063_PMIC_H_
+
+#include <linux/bitops.h>
+#include <power/pmic.h>
+
+enum {
+	DA9063_PAGE_CON			= 0x0,
+
+	/* System Control and Event Registers */
+	DA9063_STATUS_A,
+	DA9063_STATUS_B,
+	DA9063_STATUS_C,
+	DA9063_STATUS_D,
+	DA9063_FAULT_LOG,
+	DA9063_EVENT_A,
+	DA9063_EVENT_B,
+	DA9063_EVENT_C,
+	DA9063_EVENT_D,
+	DA9063_IRQ_MASK_A,
+	DA9063_IRQ_MASK_B,
+	DA9063_IRQ_MASK_C,
+	DA9063_IRQ_MASK_D,
+	DA9063_CONTROL_A,
+	DA9063_CONTROL_B,
+	DA9063_CONTROL_C,
+	DA9063_CONTROL_D,
+	DA9063_CONTROL_E,
+	DA9063_CONTROL_F,
+	DA9063_PD_DIS,
+
+	/* GPIO Control Registers */
+	DA9063_GPIO_0_1,
+	DA9063_GPIO_2_3,
+	DA9063_GPIO_4_5,
+	DA9063_GPIO_6_7,
+	DA9063_GPIO_8_9,
+	DA9063_GPIO_10_11,
+	DA9063_GPIO_12_13,
+	DA9063_GPIO_14_15,
+	DA9063_GPIO_MODE0_7,
+	DA9063_GPIO_MODE8_15,
+	DA9063_SWITCH_CONT,
+
+	/* Regulator Control Registers */
+	DA9063_BCORE2_CONT,
+	DA9063_BCORE1_CONT,
+	DA9063_BPRO_CONT,
+	DA9063_BMEM_CONT,
+	DA9063_BIO_CONT,
+	DA9063_BPERI_CONT,
+	DA9063_LDO1_CONT,
+	DA9063_LDO2_CONT,
+	DA9063_LDO3_CONT,
+	DA9063_LDO4_CONT,
+	DA9063_LDO5_CONT,
+	DA9063_LDO6_CONT,
+	DA9063_LDO7_CONT,
+	DA9063_LDO8_CONT,
+	DA9063_LDO9_CONT,
+	DA9063_LDO10_CONT,
+	DA9063_LDO11_CONT,
+	DA9063_SUPPLIES,
+	DA9063_DVC_1,
+	DA9063_DVC_2,
+
+	/* GP-ADC Control Registers */
+	DA9063_ADC_MAN,
+	DA9063_ADC_CONT,
+	DA9063_VSYS_MON,
+	DA9063_ADC_RES_L,
+	DA9063_ADC_RES_H,
+	DA9063_VSYS_RES,
+	DA9063_ADCIN1_RES,
+	DA9063_ADCIN2_RES,
+	DA9063_ADCIN3_RES,
+	DA9063_MON_A8_RES,
+	DA9063_MON_A9_RES,
+	DA9063_MON_A10_RES,
+
+	/* RTC Calendar and Alarm Registers */
+	DA9063_COUNT_S,
+	DA9063_COUNT_MI,
+	DA9063_COUNT_H,
+	DA9063_COUNT_D,
+	DA9063_COUNT_MO,
+	DA9063_COUNT_Y,
+
+	DA9063_ALARM_S,
+	DA9063_ALARM_MI,
+	DA9063_ALARM_H,
+	DA9063_ALARM_D,
+	DA9063_ALARM_MO,
+	DA9063_ALARM_Y,
+	DA9063_SECOND_A,
+	DA9063_SECOND_B,
+	DA9063_SECOND_C,
+	DA9063_SECOND_D,
+
+	/* Sequencer Control Registers */
+	DA9063_SEQ			= 0x81,
+	DA9063_SEQ_TIMER,
+	DA9063_ID_2_1,
+	DA9063_ID_4_3,
+	DA9063_ID_6_5,
+	DA9063_ID_8_7,
+	DA9063_ID_10_9,
+	DA9063_ID_12_11,
+	DA9063_ID_14_13,
+	DA9063_ID_16_15,
+	DA9063_ID_18_17,
+	DA9063_ID_20_19,
+	DA9063_ID_22_21,
+	DA9063_ID_24_23,
+	DA9063_ID_26_25,
+	DA9063_ID_28_27,
+	DA9063_ID_30_29,
+	DA9063_ID_32_31,
+	DA9063_SEQ_A,
+	DA9063_SEQ_B,
+	DA9063_WAIT,
+	DA9063_EN_32K,
+	DA9063_RESET,
+
+	/* Regulator Setting Registers */
+	DA9063_BUCK_ILIM_A,
+	DA9063_BUCK_ILIM_B,
+	DA9063_BUCK_ILIM_C,
+	DA9063_BCORE2_CFG,
+	DA9063_BCORE1_CFG,
+	DA9063_BPRO_CFG,
+	DA9063_BIO_CFG,
+	DA9063_BMEM_CFG,
+	DA9063_BPERI_CFG,
+	DA9063_VBCORE2_A,
+	DA9063_VBCORE1_A,
+	DA9063_VBPRO_A,
+	DA9063_VBMEM_A,
+	DA9063_VBIO_A,
+	DA9063_VBPERI_A,
+	DA9063_VLDO1_A,
+	DA9063_VLDO2_A,
+	DA9063_VLDO3_A,
+	DA9063_VLDO4_A,
+	DA9063_VLDO5_A,
+	DA9063_VLDO6_A,
+	DA9063_VLDO7_A,
+	DA9063_VLDO8_A,
+	DA9063_VLDO9_A,
+	DA9063_VLDO10_A,
+	DA9063_VLDO11_A,
+	DA9063_VBCORE2_B,
+	DA9063_VBCORE1_B,
+	DA9063_VBPRO_B,
+	DA9063_VBMEM_B,
+	DA9063_VBIO_B,
+	DA9063_VBPERI_B,
+	DA9063_VLDO1_B,
+	DA9063_VLDO2_B,
+	DA9063_VLDO3_B,
+	DA9063_VLDO4_B,
+	DA9063_VLDO5_B,
+	DA9063_VLDO6_B,
+	DA9063_VLDO7_B,
+	DA9063_VLDO8_B,
+	DA9063_VLDO9_B,
+	DA9063_VLDO10_B,
+	DA9063_VLDO11_B,
+
+	/* Backup Battery Charger Control Register */
+	DA9063_BBAT_CONT,
+
+	/* GPIO PWM (LED) */
+	DA9063_GPO11_LED,
+	DA9063_GPO14_LED,
+	DA9063_GPO15_LED,
+
+	/* GP-ADC Threshold Registers */
+	DA9063_ADC_CFG,
+	DA9063_AUTO1_HIGH,
+	DA9063_AUTO1_LOW,
+	DA9063_AUTO2_HIGH,
+	DA9063_AUTO2_LOW,
+	DA9063_AUTO3_HIGH,
+	DA9063_AUTO3_LOW,
+
+	/* DA9063 Configuration registers */
+	/* OTP */
+	DA9063_OTP_CONT			= 0x101,
+	DA9063_OTP_ADDR,
+	DA9063_OTP_DATA,
+
+	/* Customer Trim and Configuration */
+	DA9063_T_OFFSET,
+	DA9063_INTERFACE,
+	DA9063_CONFIG_A,
+	DA9063_CONFIG_B,
+	DA9063_CONFIG_C,
+	DA9063_CONFIG_D,
+	DA9063_CONFIG_E,
+	DA9063_CONFIG_F,
+	DA9063_CONFIG_G,
+	DA9063_CONFIG_H,
+	DA9063_CONFIG_I,
+	DA9063_CONFIG_J,
+	DA9063_CONFIG_K,
+	DA9063_CONFIG_L,
+
+	DA9063_CONFIG_M,
+	DA9063_CONFIG_N,
+
+	DA9063_MON_REG_1,
+	DA9063_MON_REG_2,
+	DA9063_MON_REG_3,
+	DA9063_MON_REG_4,
+	DA9063_MON_REG_5		= 0x11E,
+	DA9063_MON_REG_6,
+	DA9063_TRIM_CLDR,
+	/* General Purpose Registers */
+	DA9063_GP_ID_0,
+	DA9063_GP_ID_1,
+	DA9063_GP_ID_2,
+	DA9063_GP_ID_3,
+	DA9063_GP_ID_4,
+	DA9063_GP_ID_5,
+	DA9063_GP_ID_6,
+	DA9063_GP_ID_7,
+	DA9063_GP_ID_8,
+	DA9063_GP_ID_9,
+	DA9063_GP_ID_10,
+	DA9063_GP_ID_11,
+	DA9063_GP_ID_12,
+	DA9063_GP_ID_13,
+	DA9063_GP_ID_14,
+	DA9063_GP_ID_15,
+	DA9063_GP_ID_16,
+	DA9063_GP_ID_17,
+	DA9063_GP_ID_18,
+	DA9063_GP_ID_19,
+
+	/* Chip ID and variant */
+	DA9063_CHIP_ID			= 0x181,
+	DA9063_CHIP_VARIANT,
+
+	DA9063_NUM_OF_REGS,
+};
+
+#define DA9063_REG_PAGE_MASK		GENMASK(8, 7)
+#define DA9063_REG_ADDR_MASK		GENMASK(6, 0)
+
+#define DA9063_PROTO_ADDR_MASK		GENMASK(7, 1)
+#define DA9063_PROTO_RW_MASK		BIT(0)
+#define DA9063_PROTO_READ		1
+#define DA9063_PROTO_WRITE		0
+#define DA9063_PROTO_LEN		16
+
+/* DA9063_PAGE_CON - 0x0 */
+#define DA9063_PAGE_CON_PAGE			GENMASK(2, 0)
+#define DA9063_PAGE_CON_WRITE_MODE		BIT(6)
+#define DA9063_PAGE_CON_WRITE_MODE_PAGE		0
+#define DA9063_PAGE_CON_WRITE_MODE_REPEAT	1
+#define DA9063_PAGE_CON_REVERT			BIT(7)
+
+/* DA9063_B<x>_CONT - 0x20 - 0x25 */
+#define DA9063_BUCK_ENABLE	BIT(0)
+
+/* DA9063_LDO<x>_CONT - 0x26 - 0x30 */
+#define DA9063_LDO_ENABLE	BIT(0)
+
+/* DA9063_B<x>_CFG - 0x9D - 0xA2 */
+#define DA9063_BUCK_MODE	GENMASK(7, 6)
+#define DA9063_BUCK_MODE_MANUAL	0
+#define DA9063_BUCK_MODE_SLEEP	1
+#define DA9063_BUCK_MODE_SYNC	2
+#define DA9063_BUCK_MODE_AUTO	3
+
+/* DA9063_VB<x>_A - 0xA3 - 0xA8 */
+#define DA9063_BUCK_VSEL	GENMASK(6, 0)
+
+/* DA9063_VLDO<x>_A - 0xA9 - 0xB3 */
+#define DA9063_LDO_VSEL		GENMASK(5, 0)
+
+/* DA9063_CHIP_ID - 0x181 */
+#define DA9063_CHIP_ID_DA9063	0x61
+
+/* regulator operating modes */
+enum {
+	DA9063_OPMODE_AUTO,
+	DA9063_OPMODE_SYNC,
+};
+
+/* Drivers name */
+#define DA9063_LDO_DRIVER	"da9063_ldo"
+#define DA9063_BUCK_DRIVER	"da9063_buck"
+
+#endif /* __DA9063_PMIC_H_ */
+
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 37/37] board: ge: bx50v3: use DM PMIC driver
  2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
                   ` (35 preceding siblings ...)
  2019-10-15 15:53 ` [U-Boot] [PATCH 36/37] dm: pmic: add da9063 PMIC driver and regulators Robert Beckett
@ 2019-10-15 15:53 ` Robert Beckett
  36 siblings, 0 replies; 44+ messages in thread
From: Robert Beckett @ 2019-10-15 15:53 UTC (permalink / raw)
  To: u-boot

Convert the generic i2c PMIC init code to use the new da9063 driver.

Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
---
 board/ge/bx50v3/bx50v3.c    | 81 ++++++++++---------------------------
 configs/ge_bx50v3_defconfig |  3 ++
 2 files changed, 24 insertions(+), 60 deletions(-)

diff --git a/board/ge/bx50v3/bx50v3.c b/board/ge/bx50v3/bx50v3.c
index aa4a3598c6..69057ede19 100644
--- a/board/ge/bx50v3/bx50v3.c
+++ b/board/ge/bx50v3/bx50v3.c
@@ -13,7 +13,6 @@
 #include <linux/errno.h>
 #include <linux/libfdt.h>
 #include <asm/gpio.h>
-#include <asm/mach-imx/mxc_i2c.h>
 #include <asm/mach-imx/iomux-v3.h>
 #include <asm/mach-imx/boot_mode.h>
 #include <asm/mach-imx/video.h>
@@ -26,7 +25,8 @@
 #include <asm/arch/crm_regs.h>
 #include <asm/io.h>
 #include <asm/arch/sys_proto.h>
-#include <i2c.h>
+#include <power/regulator.h>
+#include <power/da9063_pmic.h>
 #include <input.h>
 #include <pwm.h>
 #include <version.h>
@@ -460,65 +460,26 @@ static const struct boot_mode board_boot_modes[] = {
 
 void pmic_init(void)
 {
-#define DA9063_I2C_ADDR         0x58
-#define DA9063_REG_BCORE2_CFG   0x9D
-#define DA9063_REG_BCORE1_CFG   0x9E
-#define DA9063_REG_BPRO_CFG     0x9F
-#define DA9063_REG_BIO_CFG      0xA0
-#define DA9063_REG_BMEM_CFG     0xA1
-#define DA9063_REG_BPERI_CFG    0xA2
-#define DA9063_BUCK_MODE_MASK   0xC0
-#define DA9063_BUCK_MODE_MANUAL 0x00
-#define DA9063_BUCK_MODE_SLEEP  0x40
-#define DA9063_BUCK_MODE_SYNC   0x80
-#define DA9063_BUCK_MODE_AUTO   0xC0
-
-	uchar val;
-	struct udevice *dev, *bus;
-	int ret;
-
-	// TODO: Add a da9063 DM PMIC driver and use that.
-	ret = uclass_get_device_by_name(UCLASS_I2C, "i2c at 21a8000", &bus);
-	if (ret) {
-		printf("%s: Unable to get I2C bus: %d\n", __func__, ret);
-		return;
-	}
-
-	ret = dm_i2c_probe(bus, DA9063_I2C_ADDR, 0, &dev);
-	if (ret) {
-		printf("%s: Unable to get PMIC device: %d\n", __func__, ret);
-		return;
+	struct udevice *reg;
+	int ret, i;
+	static const char * const bucks[] = {
+		"bcore1",
+		"bcore2",
+		"bpro",
+		"bmem",
+		"bio",
+		"bperi",
+	};
+
+	for (i = 0; i < ARRAY_SIZE(bucks); i++) {
+		ret = regulator_get_by_devname(bucks[i], &reg);
+		if (reg < 0) {
+			printf("%s(): Unable to get regulator %s: %d\n",
+			       __func__, bucks[i], ret);
+			continue;
+		}
+		regulator_set_mode(reg, DA9063_OPMODE_SYNC);
 	}
-
-	dm_i2c_read(dev, DA9063_REG_BCORE2_CFG, &val, 1);
-	val &= ~DA9063_BUCK_MODE_MASK;
-	val |= DA9063_BUCK_MODE_SYNC;
-	dm_i2c_write(dev, DA9063_REG_BCORE2_CFG, &val, 1);
-
-	dm_i2c_read(dev, DA9063_REG_BCORE1_CFG, &val, 1);
-	val &= ~DA9063_BUCK_MODE_MASK;
-	val |= DA9063_BUCK_MODE_SYNC;
-	dm_i2c_write(dev, DA9063_REG_BCORE1_CFG, &val, 1);
-
-	dm_i2c_read(dev, DA9063_REG_BPRO_CFG, &val, 1);
-	val &= ~DA9063_BUCK_MODE_MASK;
-	val |= DA9063_BUCK_MODE_SYNC;
-	dm_i2c_write(dev, DA9063_REG_BPRO_CFG, &val, 1);
-
-	dm_i2c_read(dev, DA9063_REG_BIO_CFG, &val, 1);
-	val &= ~DA9063_BUCK_MODE_MASK;
-	val |= DA9063_BUCK_MODE_SYNC;
-	dm_i2c_write(dev, DA9063_REG_BIO_CFG, &val, 1);
-
-	dm_i2c_read(dev, DA9063_REG_BMEM_CFG, &val, 1);
-	val &= ~DA9063_BUCK_MODE_MASK;
-	val |= DA9063_BUCK_MODE_SYNC;
-	dm_i2c_write(dev, DA9063_REG_BMEM_CFG, &val, 1);
-
-	dm_i2c_read(dev, DA9063_REG_BPERI_CFG, &val, 1);
-	val &= ~DA9063_BUCK_MODE_MASK;
-	val |= DA9063_BUCK_MODE_SYNC;
-	dm_i2c_write(dev, DA9063_REG_BPERI_CFG, &val, 1);
 }
 
 int board_late_init(void)
diff --git a/configs/ge_bx50v3_defconfig b/configs/ge_bx50v3_defconfig
index 8acb41c046..e9ef2de24f 100644
--- a/configs/ge_bx50v3_defconfig
+++ b/configs/ge_bx50v3_defconfig
@@ -61,8 +61,11 @@ CONFIG_PINCTRL=y
 CONFIG_PINCTRL_IMX6=y
 CONFIG_PWM_IMX=y
 CONFIG_DM_PWM=y
+CONFIG_DM_PMIC=y
+CONFIG_DM_PMIC_DA9063=y
 CONFIG_DM_REGULATOR=y
 CONFIG_DM_REGULATOR_FIXED=y
+CONFIG_DM_REGULATOR_DA9063=y
 CONFIG_DM_RTC=y
 CONFIG_RTC_RX8010SJ=y
 # CONFIG_REQUIRE_SERIAL_CONSOLE is not set
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 16/37] i2c: add support for offset overflow in to address
  2019-10-15 15:53 ` [U-Boot] [PATCH 16/37] i2c: add support for offset overflow in to address Robert Beckett
@ 2019-10-16  3:40   ` Simon Glass
  2019-10-17 14:35     ` Robert Beckett
  0 siblings, 1 reply; 44+ messages in thread
From: Simon Glass @ 2019-10-16  3:40 UTC (permalink / raw)
  To: u-boot

Hi Robert,

On Tue, 15 Oct 2019 at 09:55, Robert Beckett <bob.beckett@collabora.com> wrote:
>
> Some devices (2 wire eeproms for example) use some bits from the chip
> address to represent the high bits of the offset instead of or as well
> as using multiple bytes for the offset, effectively stealing chip
> addresses on the bus.
>
> Add a chip offset mask that can be set for any i2c chip which gets
> filled with the offset overflow during offset setup.
>
> Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
> Signed-off-by: Ian Ray <ian.ray@ge.com>
> ---
>  drivers/i2c/i2c-uclass.c | 32 ++++++++++++++++++++++++++------
>  include/i2c.h            | 24 ++++++++++++++++++++++++
>  2 files changed, 50 insertions(+), 6 deletions(-)

Please can you update the i2c tests to cover this new feature?

>
> diff --git a/drivers/i2c/i2c-uclass.c b/drivers/i2c/i2c-uclass.c
> index e47abf1833..7580867dc1 100644
> --- a/drivers/i2c/i2c-uclass.c
> +++ b/drivers/i2c/i2c-uclass.c
> @@ -52,16 +52,19 @@ void i2c_dump_msgs(struct i2c_msg *msg, int nmsgs)
>  static int i2c_setup_offset(struct dm_i2c_chip *chip, uint offset,
>                             uint8_t offset_buf[], struct i2c_msg *msg)
>  {
> -       int offset_len;
> +       int offset_len = chip->offset_len;
>
>         msg->addr = chip->chip_addr;
> +       if (chip->chip_addr_offset_mask)
> +               msg->addr |= (offset >> (8 * offset_len)) &
> +                       chip->chip_addr_offset_mask;
>         msg->flags = chip->flags & DM_I2C_CHIP_10BIT ? I2C_M_TEN : 0;
>         msg->len = chip->offset_len;
>         msg->buf = offset_buf;
> -       if (!chip->offset_len)
> +       if (!offset_len)
>                 return -EADDRNOTAVAIL;
> -       assert(chip->offset_len <= I2C_MAX_OFFSET_LEN);
> -       offset_len = chip->offset_len;
> +       assert(offset_len <= I2C_MAX_OFFSET_LEN);
> +
>         while (offset_len--)
>                 *offset_buf++ = offset >> (8 * offset_len);
>
> @@ -83,7 +86,7 @@ static int i2c_read_bytewise(struct udevice *dev, uint offset,
>                 if (i2c_setup_offset(chip, offset + i, offset_buf, msg))
>                         return -EINVAL;
>                 ptr = msg + 1;
> -               ptr->addr = chip->chip_addr;
> +               ptr->addr = msg->addr;
>                 ptr->flags = msg->flags | I2C_M_RD;
>                 ptr->len = 1;
>                 ptr->buf = &buffer[i];
> @@ -132,6 +135,7 @@ int dm_i2c_read(struct udevice *dev, uint offset, uint8_t *buffer, int len)
>
>         if (!ops->xfer)
>                 return -ENOSYS;
> +

Unrelated change

>         if (chip->flags & DM_I2C_CHIP_RD_ADDRESS)
>                 return i2c_read_bytewise(dev, offset, buffer, len);
>         ptr = msg;
> @@ -139,7 +143,7 @@ int dm_i2c_read(struct udevice *dev, uint offset, uint8_t *buffer, int len)
>                 ptr++;
>
>         if (len) {
> -               ptr->addr = chip->chip_addr;
> +               ptr->addr = msg->addr;
>                 ptr->flags = chip->flags & DM_I2C_CHIP_10BIT ? I2C_M_TEN : 0;
>                 ptr->flags |= I2C_M_RD;
>                 ptr->len = len;
> @@ -465,6 +469,22 @@ int i2c_get_chip_offset_len(struct udevice *dev)
>         return chip->offset_len;
>  }
>
> +int i2c_set_chip_addr_offset_mask(struct udevice *dev, uint mask)
> +{
> +       struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
> +
> +       chip->chip_addr_offset_mask = mask;
> +
> +       return 0;
> +}
> +
> +uint i2c_get_chip_addr_offset_mask(struct udevice *dev)
> +{
> +       struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
> +
> +       return chip->chip_addr_offset_mask;
> +}
> +
>  #ifdef CONFIG_DM_GPIO
>  static void i2c_gpio_set_pin(struct gpio_desc *pin, int bit)
>  {
> diff --git a/include/i2c.h b/include/i2c.h
> index 33570f5404..3c927340da 100644
> --- a/include/i2c.h
> +++ b/include/i2c.h
> @@ -45,12 +45,17 @@ struct udevice;
>   *             represent up to 256 bytes. A value larger than 1 may be
>   *             needed for larger devices.
>   * @flags:     Flags for this chip (dm_i2c_chip_flags)
> + * @chip_addr_offset_mask: Mask of offset bits within chip_addr. Used for
> + *                        devices which steal addresses as part of offset.
> + *                        If offset_len is zero, then the offset is encoded
> + *                        completely within the chip address itself.

Can you add an example value here, or point to some documentation on
this? There is not enough info here to figure out what is going on.


>   * @emul: Emulator for this chip address (only used for emulation)
>   */
>  struct dm_i2c_chip {
>         uint chip_addr;
>         uint offset_len;
>         uint flags;
> +       uint chip_addr_offset_mask;
>  #ifdef CONFIG_SANDBOX
>         struct udevice *emul;
>         bool test_mode;
> @@ -261,6 +266,25 @@ int i2c_set_chip_offset_len(struct udevice *dev, uint offset_len);
>   */
>  int i2c_get_chip_offset_len(struct udevice *dev);
>
> +/**
> + * i2c_set_chip_addr_offset_mask() - set mask of address bits usable by offset
> + *
> + * Some devices listen on multiple chip addresses to achieve larger offsets
> + * than their single or multiple byte offsets would allow for. You can use this
> + * function to set the bits that are valid to be used for offset overflow.
> + *
> + * @mask: The mask to be used for high offset bits within address
> + * @return 0 if OK, other -ve value on error
> + */
> +int i2c_set_chip_addr_offset_mask(struct udevice *dev, uint mask);
> +
> +/*
> + * i2c_get_chip_addr_offset_mask() - get mask of address bits usable by offset
> + *
> + * @return current chip addr offset mask
> + */
> +uint i2c_get_chip_addr_offset_mask(struct udevice *dev);
> +
>  /**
>   * i2c_deblock() - recover a bus that is in an unknown state
>   *
> --
> 2.20.1
>

^ permalink raw reply	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 36/37] dm: pmic: add da9063 PMIC driver and regulators
  2019-10-15 15:53 ` [U-Boot] [PATCH 36/37] dm: pmic: add da9063 PMIC driver and regulators Robert Beckett
@ 2019-10-16  7:24   ` Schrempf Frieder
  2019-10-16 11:11     ` Robert Beckett
  0 siblings, 1 reply; 44+ messages in thread
From: Schrempf Frieder @ 2019-10-16  7:24 UTC (permalink / raw)
  To: u-boot

Hi Robert,

On 15.10.19 17:53, Robert Beckett wrote:
> Add DM driver to support Dialog DA9063.
> Currently it support binding regulator children.
> 
> Signed-off-by: Robert Beckett <bob.beckett@collabora.com>

I also have a board with DA9063 and was looking for support in U-Boot. I 
found patches from Martin Fuzzey [1] and pulled them in almost as is and 
found them to work just fine.

Unfortunately I didn't have time to resend them yet, but you can find 
the rebased patches here: [2].

On a first glance your implementation looks different, so it seems you 
didn't use Martin's patches. Though the resulting features probably will 
be similar.

I only had a very quick look and one difference seems to be that your 
regulator implementation supports the AUTO and SYNC mode, while Martin's 
version supports AUTO, SYNC and SLEEP. There might be other differences.

What do you think? Which version would be better?

Also find a few comments below, though I didn't do a full review, yet.

Thanks,
Frieder

[1] https://patchwork.ozlabs.org/cover/979346/
[2] https://github.com/fschrempf/u-boot/commits/da9063

> ---
>   drivers/power/pmic/Kconfig       |   8 +
>   drivers/power/pmic/Makefile      |   1 +
>   drivers/power/pmic/da9063.c      | 270 ++++++++++++++++++++++++++
>   drivers/power/regulator/Kconfig  |   7 +
>   drivers/power/regulator/Makefile |   1 +
>   drivers/power/regulator/da9063.c | 320 +++++++++++++++++++++++++++++++
>   include/power/da9063_pmic.h      | 303 +++++++++++++++++++++++++++++
>   7 files changed, 910 insertions(+)
>   create mode 100644 drivers/power/pmic/da9063.c
>   create mode 100644 drivers/power/regulator/da9063.c
>   create mode 100644 include/power/da9063_pmic.h
> 
> diff --git a/drivers/power/pmic/Kconfig b/drivers/power/pmic/Kconfig
> index 586772fdec..6dd7b1bf76 100644
> --- a/drivers/power/pmic/Kconfig
> +++ b/drivers/power/pmic/Kconfig
> @@ -267,3 +267,11 @@ config SPL_PMIC_LP87565
>   	help
>   	The LP87565 is a PMIC containing a bunch of SMPS.
>   	This driver binds the pmic children in SPL.
> +
> +config DM_PMIC_DA9063
> +	bool "Enable support for Dialog DA9063 PMIC"
> +	depends on DM_PMIC && (DM_I2C || DM_SPI)
> +	help
> +	The DA9063 is a PMIC providing 6 BUCK converters and 11 LDO regulators.
> +	It can be accessed via I2C or SPI.
> +	This driver binds the pmic children.
> diff --git a/drivers/power/pmic/Makefile b/drivers/power/pmic/Makefile
> index 888dbb2857..9be9d5d9a0 100644
> --- a/drivers/power/pmic/Makefile
> +++ b/drivers/power/pmic/Makefile
> @@ -25,6 +25,7 @@ obj-$(CONFIG_$(SPL_)PMIC_PALMAS) += palmas.o
>   obj-$(CONFIG_$(SPL_)PMIC_LP873X) += lp873x.o
>   obj-$(CONFIG_$(SPL_)PMIC_LP87565) += lp87565.o
>   obj-$(CONFIG_PMIC_STPMIC1) += stpmic1.o
> +obj-$(CONFIG_DM_PMIC_DA9063) += da9063.o

It would be good to be able to enable the driver for U-Boot proper and 
SPL separately. So this should be CONFIG_$(SPL_)DM_PMIC_DA9063.

>   
>   obj-$(CONFIG_POWER_LTC3676) += pmic_ltc3676.o
>   obj-$(CONFIG_POWER_MAX77696) += pmic_max77696.o
> diff --git a/drivers/power/pmic/da9063.c b/drivers/power/pmic/da9063.c
> new file mode 100644
> index 0000000000..81a7803b09
> --- /dev/null
> +++ b/drivers/power/pmic/da9063.c
> @@ -0,0 +1,270 @@
> +// SPDX-License-Identifier: GPL-2.0+
> +/*
> + * (C) Copyright 2019 Collabora
> + * (C) Copyright 2019 GE
> + */
> +
> +#define DEBUG 1

This should not be here.

> +#include <common.h>
> +#include <fdtdec.h>
> +#include <errno.h>
> +#include <dm.h>
> +#include <i2c.h>
> +#include <spi.h>
> +#include <linux/bitfield.h>
> +#include <power/pmic.h>
> +#include <power/regulator.h>
> +#include <power/da9063_pmic.h>
> +
> +static const struct pmic_child_info pmic_children_info[] = {
> +	{ .prefix = "bcore", .driver = DA9063_BUCK_DRIVER },
> +	{ .prefix = "bpro", .driver = DA9063_BUCK_DRIVER },
> +	{ .prefix = "bmem", .driver = DA9063_BUCK_DRIVER },
> +	{ .prefix = "bio", .driver = DA9063_BUCK_DRIVER },
> +	{ .prefix = "bperi", .driver = DA9063_BUCK_DRIVER },
> +	{ .prefix = "ldo", .driver = DA9063_LDO_DRIVER },
> +	{ },
> +};
> +
> +static int da9063_reg_count(struct udevice *dev)
> +{
> +	return DA9063_NUM_OF_REGS;
> +}
> +
> +#if defined(CONFIG_DM_I2C)
> +static int da9063_i2c_read(struct udevice *dev, uint reg, uint8_t *buff,
> +			   int len)
> +{
> +	int ret;
> +
> +	/* only support single reg accesses */
> +	if (len != 1)
> +		return -EINVAL;
> +
> +	ret = dm_i2c_read(dev, reg, buff, len);
> +	if (ret) {
> +		pr_err("%s: unable to read reg %#x: %d\n", __func__, reg, ret);
> +		return ret;
> +	}
> +
> +	return 0;
> +}
> +
> +static int da9063_i2c_write(struct udevice *dev, uint reg, const uint8_t *buff,
> +			    int len)
> +{
> +	int ret;
> +
> +	/* only support single reg accesses */
> +	if (len != 1)
> +		return -EINVAL;
> +
> +	ret = dm_i2c_write(dev, reg, buff, len);
> +	if (ret) {
> +		pr_err("%s: unable to write reg %#x: %d\n", __func__, reg, ret);
> +		return ret;
> +	}
> +
> +	return 0;
> +}
> +#endif
> +
> +#if defined(CONFIG_DM_SPI)
> +static int da9063_spi_read(struct udevice *dev, uint reg, uint8_t *buff,
> +			   int len)
> +{
> +	u8 page;
> +	u8 data[2];
> +	int ret;
> +
> +	/* only support single reg accesses */
> +	if (len != 1)
> +		return -EINVAL;
> +
> +	page = FIELD_GET(DA9063_REG_PAGE_MASK, reg);
> +	reg = FIELD_GET(DA9063_REG_ADDR_MASK, reg);
> +
> +	ret = dm_spi_claim_bus(dev);
> +	if (ret)
> +		return ret;
> +	/* set page */
> +	data[0] = FIELD_PREP(DA9063_PROTO_ADDR_MASK, DA9063_PAGE_CON) |
> +		  FIELD_PREP(DA9063_PROTO_RW_MASK, DA9063_PROTO_WRITE);
> +	data[1] = FIELD_PREP(DA9063_PAGE_CON_PAGE, page);
> +	ret = dm_spi_xfer(dev, DA9063_PROTO_LEN, data, NULL, SPI_XFER_ONCE);
> +	if (ret) {
> +		pr_err("%s: unable to set page: %d\n", __func__, ret);
> +		goto err_page;
> +	}
> +
> +	/* set target reg */
> +	data[0] = FIELD_PREP(DA9063_PROTO_ADDR_MASK, reg) |
> +		  FIELD_PREP(DA9063_PROTO_RW_MASK, DA9063_PROTO_READ);
> +	data[1] = 0;
> +	ret = dm_spi_xfer(dev, DA9063_PROTO_LEN, data, data, SPI_XFER_ONCE);
> +	if (ret) {
> +		pr_err("%s: unable to read reg %#x: %d\n", __func__, reg, ret);
> +		goto err_reg;
> +	}
> +	dm_spi_release_bus(dev);
> +
> +	*buff = data[1];
> +
> +	return 0;
> +
> +err_page:
> +err_reg:
> +	dm_spi_release_bus(dev);
> +
> +	return ret;
> +}
> +
> +static int da9063_spi_write(struct udevice *dev, uint reg, const uint8_t *buff,
> +			    int len)
> +{
> +	u8 page;
> +	u8 data[2];
> +	int ret;
> +
> +	/* only support single reg accesses */
> +	if (len != 1)
> +		return -EINVAL;
> +
> +	page = FIELD_GET(DA9063_REG_PAGE_MASK, reg);
> +	reg = FIELD_GET(DA9063_REG_ADDR_MASK, reg);
> +
> +	ret = dm_spi_claim_bus(dev);
> +	if (ret)
> +		return ret;
> +	/* set page */
> +	data[0] = FIELD_PREP(DA9063_PROTO_ADDR_MASK, DA9063_PAGE_CON) |
> +		  FIELD_PREP(DA9063_PROTO_RW_MASK, DA9063_PROTO_WRITE);
> +	data[1] = FIELD_PREP(DA9063_PAGE_CON_PAGE, page);
> +	ret = dm_spi_xfer(dev, DA9063_PROTO_LEN, data, NULL, SPI_XFER_ONCE);
> +	if (ret) {
> +		pr_err("%s: unable to set page: %d\n", __func__, ret);
> +		goto err_page;
> +	}
> +
> +	/* set target reg */
> +	data[0] = FIELD_PREP(DA9063_PROTO_ADDR_MASK, reg) |
> +		  FIELD_PREP(DA9063_PROTO_RW_MASK, DA9063_PROTO_WRITE);
> +	data[1] = *buff;
> +	ret = dm_spi_xfer(dev, DA9063_PROTO_LEN, data, NULL, SPI_XFER_ONCE);
> +	if (ret) {
> +		pr_err("%s: unable to write reg %#x: %d\n", __func__, reg, ret);
> +		goto err_reg;
> +	}
> +	dm_spi_release_bus(dev);
> +
> +	return 0;
> +
> +err_page:
> +err_reg:
> +	dm_spi_release_bus(dev);
> +
> +	return ret;
> +}
> +#endif
> +
> +struct da9063_priv {
> +	int (*read)(struct udevice *dev, uint reg, uint8_t *buffer, int len);
> +	int (*write)(struct udevice *dev, uint reg, const uint8_t *buffer,
> +		     int len);
> +};
> +
> +static int da9063_read(struct udevice *dev, uint reg, uint8_t *buff, int len)
> +{
> +	struct da9063_priv *priv = dev_get_priv(dev);
> +
> +	return priv->read(dev, reg, buff, len);
> +}
> +
> +static int da9063_write(struct udevice *dev, uint reg, const uint8_t *buff,
> +			int len)
> +{
> +	struct da9063_priv *priv = dev_get_priv(dev);
> +
> +	return priv->write(dev, reg, buff, len);
> +}
> +
> +static struct dm_pmic_ops da9063_ops = {
> +	.reg_count = da9063_reg_count,
> +	.read = da9063_read,
> +	.write = da9063_write,
> +};
> +
> +static int da9063_bind(struct udevice *dev)
> +{
> +	ofnode regulators_node;
> +	int children;
> +
> +	regulators_node = dev_read_subnode(dev, "regulators");
> +	if (!ofnode_valid(regulators_node)) {
> +		pr_debug("%s: %s regulators subnode not found!\n", __func__,
> +			 dev->name);
> +		return -ENXIO;
> +	}
> +
> +	pr_debug("%s: '%s' - found regulators subnode\n", __func__, dev->name);
> +
> +	children = pmic_bind_children(dev, regulators_node, pmic_children_info);
> +	if (!children)
> +		pr_debug("%s: %s - no child found\n", __func__, dev->name);
> +
> +	return 0;
> +}
> +
> +static int da9063_probe(struct udevice *dev)
> +{
> +	struct da9063_priv *priv = dev_get_priv(dev);
> +	int ret;
> +
> +	if (device_get_uclass_id(dev->parent) == UCLASS_I2C) {
> +#if defined(CONFIG_DM_I2C)
> +		i2c_set_chip_addr_offset_mask(dev, 0x1);
> +		priv->read = da9063_i2c_read;
> +		priv->write = da9063_i2c_write;
> +#else
> +		return -ENODEV;
> +#endif
> +	} else if (device_get_uclass_id(dev->parent) == UCLASS_SPI) {
> +#if defined(CONFIG_DM_SPI)
> +		priv->read = da9063_spi_read;
> +		priv->write = da9063_spi_write;
> +#else
> +		return -ENODEV;
> +#endif
> +	} else {
> +		pr_err("%s: invalid bus\n", __func__);
> +		return -ENODEV;
> +	}
> +
> +	ret = pmic_reg_read(dev, DA9063_CHIP_ID);
> +	if (ret < 0) {
> +		pr_debug("%s: unable to read chip id: %d\n", __func__, ret);
> +		return ret;
> +	}
> +
> +	if (ret != DA9063_CHIP_ID_DA9063) {
> +		pr_debug("%s: unknown chip id: %#x\n", __func__, ret);
> +		return -ENODEV;
> +	}
> +
> +	return 0;
> +}
> +
> +static const struct udevice_id da9063_ids[] = {
> +	{ .compatible = "dlg,da9063" },
> +	{ }
> +};
> +
> +U_BOOT_DRIVER(pmic_da9063) = {
> +	.name = "da9063_pmic",
> +	.id = UCLASS_PMIC,
> +	.of_match = da9063_ids,
> +	.bind = da9063_bind,
> +	.ops = &da9063_ops,
> +	.priv_auto_alloc_size = sizeof(struct da9063_priv),
> +	.probe = da9063_probe,
> +};
> diff --git a/drivers/power/regulator/Kconfig b/drivers/power/regulator/Kconfig
> index 9aa00fad42..e87cccdb82 100644
> --- a/drivers/power/regulator/Kconfig
> +++ b/drivers/power/regulator/Kconfig
> @@ -313,3 +313,10 @@ config SPL_DM_REGULATOR_LP873X
>   	This enables implementation of driver-model regulator uclass
>   	features for REGULATOR LP873X and the family of LP873X PMICs.
>   	The driver implements get/set api for: value and enable in SPL.
> +
> +config DM_REGULATOR_DA9063
> +	bool "Enable support for DA9063 regulators"
> +	help
> +	Enable support the regulator functions of the DA9063 PMIC.
> +	The driver support voltage set/get and enable/disable for LDOs and
> +	BUCKs, and mode get/set for BUCKs.
> diff --git a/drivers/power/regulator/Makefile b/drivers/power/regulator/Makefile
> index 6a3d4bbee4..f0926614cb 100644
> --- a/drivers/power/regulator/Makefile
> +++ b/drivers/power/regulator/Makefile
> @@ -27,3 +27,4 @@ obj-$(CONFIG_$(SPL_)DM_REGULATOR_LP87565) += lp87565_regulator.o
>   obj-$(CONFIG_$(SPL_)DM_REGULATOR_STM32_VREFBUF) += stm32-vrefbuf.o
>   obj-$(CONFIG_DM_REGULATOR_TPS65910) += tps65910_regulator.o
>   obj-$(CONFIG_$(SPL_)DM_REGULATOR_STPMIC1) += stpmic1.o
> +obj-$(CONFIG_DM_REGULATOR_DA9063) += da9063.o

It would be good to be able to enable the driver for U-Boot proper and 
SPL separately. So this should be CONFIG_$(SPL_)DM_REGULATOR_DA9063.

> diff --git a/drivers/power/regulator/da9063.c b/drivers/power/regulator/da9063.c
> new file mode 100644
> index 0000000000..68036a3951
> --- /dev/null
> +++ b/drivers/power/regulator/da9063.c
> @@ -0,0 +1,320 @@
> +// SPDX-License-Identifier: GPL-2.0+
> +/*
> + * (C) Copyright 2019 Collabora
> + * (C) Copyright 2019 GE
> + */
> +
> +#include <common.h>
> +#include <fdtdec.h>
> +#include <dm.h>
> +#include <linux/bitfield.h>
> +#include <power/pmic.h>
> +#include <power/regulator.h>
> +#include <power/da9063_pmic.h>
> +
> +enum {
> +	DA9063_ID_BCORE1 = 0,
> +	DA9063_ID_BCORE2,
> +	DA9063_ID_BPRO,
> +	DA9063_ID_BMEM,
> +	DA9063_ID_BIO,
> +	DA9063_ID_BPERI,
> +};
> +
> +struct buck_info {
> +	int min_uV;
> +	int max_uV;
> +	int step_uV;
> +	int ctrl_reg;
> +	int volt_reg;
> +	int mode_reg;
> +};
> +
> +#define to_buck_info(dev) (struct buck_info *)dev->driver_data
> +
> +#define DA9063_BUCK(name, min_mV, max_mV, step_mV) \
> +{ \
> +	.min_uV = min_mV * 1000, \
> +	.max_uV = max_mV * 1000, \
> +	.step_uV = step_mV * 1000, \
> +	.ctrl_reg = DA9063_##name##_CONT, \
> +	.volt_reg = DA9063_V##name##_A, \
> +	.mode_reg = DA9063_##name##_CFG, \
> +}
> +
> +static const struct buck_info da9063_buck_info[] = {
> +	[DA9063_ID_BCORE1] = DA9063_BUCK(BCORE1, 300, 1570, 10),
> +	[DA9063_ID_BCORE2] = DA9063_BUCK(BCORE2, 300, 1570, 10),
> +	[DA9063_ID_BPRO]   = DA9063_BUCK(BPRO, 530, 1800, 10),
> +	[DA9063_ID_BMEM]   = DA9063_BUCK(BMEM, 800, 3340, 20),
> +	[DA9063_ID_BIO]    = DA9063_BUCK(BIO, 800, 3340, 20),
> +	[DA9063_ID_BPERI]  = DA9063_BUCK(BPERI, 800, 3340, 20),
> +};
> +
> +/* Buck converters can either be in auto mode or sync mode.
> + * Auto uses PWM or PFM depending on load current.
> + * Sync mode uses PFM unless output voltage is < 0.7V.
> + */
> +static struct dm_regulator_mode da9063_buck_modes[] = {
> +	{
> +		.id = DA9063_OPMODE_AUTO,
> +		.register_value = DA9063_BUCK_MODE_AUTO,
> +		.name = "AUTO",
> +	},
> +	{
> +		.id = DA9063_OPMODE_SYNC,
> +		.register_value = DA9063_BUCK_MODE_SYNC,
> +		.name = "SYNC",
> +	},
> +};
> +
> +static int da9063_buck_get_mode(struct udevice *dev)
> +{
> +	struct buck_info *info = to_buck_info(dev);
> +	int mode = pmic_reg_read(dev_get_parent(dev), info->mode_reg);
> +
> +	if (mode < 0)
> +		return mode;
> +
> +	mode = FIELD_GET(DA9063_BUCK_MODE, mode);
> +
> +	switch (mode) {
> +	case DA9063_BUCK_MODE_AUTO:
> +		return DA9063_OPMODE_AUTO;
> +	case DA9063_BUCK_MODE_SYNC:
> +		return DA9063_OPMODE_SYNC;
> +	default:
> +		return -EINVAL;
> +	}
> +}
> +
> +static int da9063_buck_set_mode(struct udevice *dev, int rmode)
> +{
> +	struct buck_info *info = to_buck_info(dev);
> +	int mode = pmic_reg_read(dev_get_parent(dev), info->mode_reg);
> +
> +	mode &= ~DA9063_BUCK_MODE;
> +
> +	switch (rmode) {
> +	case DA9063_OPMODE_AUTO:
> +		mode |= FIELD_PREP(DA9063_BUCK_MODE, DA9063_BUCK_MODE_AUTO);
> +		break;
> +	case DA9063_OPMODE_SYNC:
> +		mode |= FIELD_PREP(DA9063_BUCK_MODE, DA9063_BUCK_MODE_SYNC);
> +		break;
> +	default:
> +		return -EINVAL;
> +	}
> +
> +	return pmic_reg_write(dev_get_parent(dev), info->mode_reg, mode);
> +}
> +
> +static int da9063_buck_get_value(struct udevice *dev)
> +{
> +	struct buck_info *info = to_buck_info(dev);
> +	int sel = pmic_reg_read(dev_get_parent(dev), info->volt_reg);
> +
> +	if (sel < 0)
> +		return sel;
> +	sel = FIELD_GET(DA9063_BUCK_VSEL, sel);
> +	return info->min_uV + (info->step_uV * sel);
> +}
> +
> +static int da9063_buck_set_value(struct udevice *dev, int uV)
> +{
> +	struct buck_info *info = to_buck_info(dev);
> +	int sel = pmic_reg_read(dev_get_parent(dev), info->volt_reg);
> +
> +	if (sel < 0)
> +		return sel;
> +	sel &= ~DA9063_BUCK_VSEL;
> +	sel |= FIELD_PREP(DA9063_BUCK_VSEL,
> +			  DIV_ROUND_UP(uV - info->min_uV, info->step_uV));
> +
> +	return pmic_reg_write(dev_get_parent(dev), info->volt_reg, sel);
> +}
> +
> +static int da9063_buck_get_enable(struct udevice *dev)
> +{
> +	struct buck_info *info = to_buck_info(dev);
> +	int cont = pmic_reg_read(dev_get_parent(dev), info->ctrl_reg);
> +
> +	if (cont < 0)
> +		return cont;
> +
> +	return FIELD_GET(DA9063_BUCK_ENABLE, cont);
> +}
> +
> +static int da9063_buck_set_enable(struct udevice *dev, bool enable)
> +{
> +	struct buck_info *info = to_buck_info(dev);
> +	int cont = pmic_reg_read(dev_get_parent(dev), info->ctrl_reg);
> +
> +	if (cont < 0)
> +		return cont;
> +
> +	cont &= ~DA9063_BUCK_ENABLE;
> +	cont |= FIELD_PREP(DA9063_BUCK_ENABLE, enable);
> +
> +	return pmic_reg_write(dev_get_parent(dev), info->ctrl_reg, cont);
> +}
> +
> +static int da9063_buck_probe(struct udevice *dev)
> +{
> +	struct dm_regulator_uclass_platdata *uc_pdata;
> +
> +	uc_pdata = dev_get_uclass_platdata(dev);
> +
> +	if (!strcmp(uc_pdata->name, "bcore1"))
> +		dev->driver_data = (ulong)&da9063_buck_info[DA9063_ID_BCORE1];
> +	else if (!strcmp(uc_pdata->name, "bcore2"))
> +		dev->driver_data = (ulong)&da9063_buck_info[DA9063_ID_BCORE2];
> +	else if (!strcmp(uc_pdata->name, "bpro"))
> +		dev->driver_data = (ulong)&da9063_buck_info[DA9063_ID_BPRO];
> +	else if (!strcmp(uc_pdata->name, "bmem"))
> +		dev->driver_data = (ulong)&da9063_buck_info[DA9063_ID_BMEM];
> +	else if (!strcmp(uc_pdata->name, "bio"))
> +		dev->driver_data = (ulong)&da9063_buck_info[DA9063_ID_BIO];
> +	else if (!strcmp(uc_pdata->name, "bperi"))
> +		dev->driver_data = (ulong)&da9063_buck_info[DA9063_ID_BPERI];
> +	else
> +		return -ENODEV;
> +
> +	uc_pdata->type = REGULATOR_TYPE_BUCK;
> +	uc_pdata->mode_count = ARRAY_SIZE(da9063_buck_modes);
> +	uc_pdata->mode = da9063_buck_modes;
> +
> +	return 0;
> +}
> +
> +static const struct dm_regulator_ops da9063_buck_ops = {
> +	.get_value  = da9063_buck_get_value,
> +	.set_value  = da9063_buck_set_value,
> +	.get_enable = da9063_buck_get_enable,
> +	.set_enable = da9063_buck_set_enable,
> +	.get_mode   = da9063_buck_get_mode,
> +	.set_mode   = da9063_buck_set_mode,
> +};
> +
> +U_BOOT_DRIVER(da9063_buck) = {
> +	.name  = DA9063_BUCK_DRIVER,
> +	.id    = UCLASS_REGULATOR,
> +	.ops   = &da9063_buck_ops,
> +	.probe = da9063_buck_probe,
> +};
> +
> +struct ldo_info {
> +	int min_uV;
> +	int max_uV;
> +	int step_uV;
> +	int ctrl_reg;
> +	int volt_reg;
> +};
> +
> +#define to_ldo_info(dev) (struct ldo_info *)dev->driver_data
> +
> +#define DA9063_LDO(idx, min_mV, max_mV, step_mV) \
> +{ \
> +	.min_uV = min_mV * 1000, \
> +	.max_uV = max_mV * 1000, \
> +	.step_uV = step_mV * 1000, \
> +	.ctrl_reg = DA9063_LDO##idx##_CONT, \
> +	.volt_reg = DA9063_VLDO##idx##_A, \
> +}
> +
> +static const struct ldo_info da9063_ldo_info[] = {
> +	DA9063_LDO(1, 600, 1860, 20),
> +	DA9063_LDO(2, 600, 1860, 20),
> +	DA9063_LDO(3, 900, 3440, 20),
> +	DA9063_LDO(4, 900, 3440, 20),
> +	DA9063_LDO(5, 900, 3600, 50),
> +	DA9063_LDO(6, 900, 3600, 50),
> +	DA9063_LDO(7, 900, 3600, 50),
> +	DA9063_LDO(8, 900, 3600, 50),
> +	DA9063_LDO(9, 950, 3600, 50),
> +	DA9063_LDO(10, 900, 3600, 50),
> +	DA9063_LDO(11, 900, 3600, 50),
> +};
> +
> +static int da9063_ldo_get_value(struct udevice *dev)
> +{
> +	struct ldo_info *info = to_ldo_info(dev);
> +	int sel;
> +
> +	sel = pmic_reg_read(dev_get_parent(dev), info->volt_reg);
> +	if (sel < 0)
> +		return sel;
> +	sel = FIELD_GET(DA9063_LDO_VSEL, sel);
> +	return info->min_uV + (info->step_uV * sel);
> +}
> +
> +static int da9063_ldo_set_value(struct udevice *dev, int uV)
> +{
> +	struct ldo_info *info = to_ldo_info(dev);
> +	int sel;
> +
> +	sel = pmic_reg_read(dev_get_parent(dev), info->volt_reg);
> +	if (sel < 0)
> +		return sel;
> +	sel &= ~DA9063_LDO_VSEL;
> +	sel |= FIELD_PREP(DA9063_LDO_VSEL,
> +			  DIV_ROUND_UP(uV - info->min_uV, info->step_uV));
> +
> +	return pmic_reg_write(dev_get_parent(dev), info->volt_reg, sel);
> +}
> +
> +static int da9063_ldo_get_enable(struct udevice *dev)
> +{
> +	struct ldo_info *info = to_ldo_info(dev);
> +	int cont = pmic_reg_read(dev_get_parent(dev), info->ctrl_reg);
> +
> +	if (cont < 0)
> +		return cont;
> +
> +	return FIELD_GET(DA9063_LDO_ENABLE, cont);
> +}
> +
> +static int da9063_ldo_set_enable(struct udevice *dev, bool enable)
> +{
> +	struct ldo_info *info = to_ldo_info(dev);
> +	int cont = pmic_reg_read(dev_get_parent(dev), info->ctrl_reg);
> +
> +	if (cont < 0)
> +		return cont;
> +
> +	cont &= ~DA9063_LDO_ENABLE;
> +	cont |= FIELD_PREP(DA9063_LDO_ENABLE, enable);
> +
> +	return pmic_reg_write(dev_get_parent(dev), info->ctrl_reg, cont);
> +}
> +
> +static int da9063_ldo_probe(struct udevice *dev)
> +{
> +	struct dm_regulator_uclass_platdata *uc_pdata;
> +
> +	if (dev->driver_data < 1 ||
> +	    dev->driver_data > ARRAY_SIZE(da9063_ldo_info))
> +		return -EINVAL;
> +
> +	uc_pdata = dev_get_uclass_platdata(dev);
> +
> +	dev->driver_data = (ulong)&da9063_ldo_info[dev->driver_data - 1];
> +	uc_pdata->type = REGULATOR_TYPE_LDO;
> +	uc_pdata->mode_count = 0;
> +
> +	return 0;
> +}
> +
> +static const struct dm_regulator_ops da9063_ldo_ops = {
> +	.get_value = da9063_ldo_get_value,
> +	.set_value = da9063_ldo_set_value,
> +	.get_enable = da9063_ldo_get_enable,
> +	.set_enable = da9063_ldo_set_enable,
> +};
> +
> +U_BOOT_DRIVER(da9063_ldo) = {
> +	.name = DA9063_LDO_DRIVER,
> +	.id = UCLASS_REGULATOR,
> +	.ops = &da9063_ldo_ops,
> +	.probe = da9063_ldo_probe,
> +};
> diff --git a/include/power/da9063_pmic.h b/include/power/da9063_pmic.h
> new file mode 100644
> index 0000000000..7258987ae3
> --- /dev/null
> +++ b/include/power/da9063_pmic.h
> @@ -0,0 +1,303 @@
> +/* SPDX-License-Identifier: GPL-2.0+ */
> +/*
> + * (C) Copyright 2019 Collabora
> + * (C) Copyright 2019 GE
> + */
> +
> +#ifndef __DA9063_PMIC_H_
> +#define __DA9063_PMIC_H_
> +
> +#include <linux/bitops.h>
> +#include <power/pmic.h>
> +
> +enum {
> +	DA9063_PAGE_CON			= 0x0,
> +
> +	/* System Control and Event Registers */
> +	DA9063_STATUS_A,
> +	DA9063_STATUS_B,
> +	DA9063_STATUS_C,
> +	DA9063_STATUS_D,
> +	DA9063_FAULT_LOG,
> +	DA9063_EVENT_A,
> +	DA9063_EVENT_B,
> +	DA9063_EVENT_C,
> +	DA9063_EVENT_D,
> +	DA9063_IRQ_MASK_A,
> +	DA9063_IRQ_MASK_B,
> +	DA9063_IRQ_MASK_C,
> +	DA9063_IRQ_MASK_D,
> +	DA9063_CONTROL_A,
> +	DA9063_CONTROL_B,
> +	DA9063_CONTROL_C,
> +	DA9063_CONTROL_D,
> +	DA9063_CONTROL_E,
> +	DA9063_CONTROL_F,
> +	DA9063_PD_DIS,
> +
> +	/* GPIO Control Registers */
> +	DA9063_GPIO_0_1,
> +	DA9063_GPIO_2_3,
> +	DA9063_GPIO_4_5,
> +	DA9063_GPIO_6_7,
> +	DA9063_GPIO_8_9,
> +	DA9063_GPIO_10_11,
> +	DA9063_GPIO_12_13,
> +	DA9063_GPIO_14_15,
> +	DA9063_GPIO_MODE0_7,
> +	DA9063_GPIO_MODE8_15,
> +	DA9063_SWITCH_CONT,
> +
> +	/* Regulator Control Registers */
> +	DA9063_BCORE2_CONT,
> +	DA9063_BCORE1_CONT,
> +	DA9063_BPRO_CONT,
> +	DA9063_BMEM_CONT,
> +	DA9063_BIO_CONT,
> +	DA9063_BPERI_CONT,
> +	DA9063_LDO1_CONT,
> +	DA9063_LDO2_CONT,
> +	DA9063_LDO3_CONT,
> +	DA9063_LDO4_CONT,
> +	DA9063_LDO5_CONT,
> +	DA9063_LDO6_CONT,
> +	DA9063_LDO7_CONT,
> +	DA9063_LDO8_CONT,
> +	DA9063_LDO9_CONT,
> +	DA9063_LDO10_CONT,
> +	DA9063_LDO11_CONT,
> +	DA9063_SUPPLIES,
> +	DA9063_DVC_1,
> +	DA9063_DVC_2,
> +
> +	/* GP-ADC Control Registers */
> +	DA9063_ADC_MAN,
> +	DA9063_ADC_CONT,
> +	DA9063_VSYS_MON,
> +	DA9063_ADC_RES_L,
> +	DA9063_ADC_RES_H,
> +	DA9063_VSYS_RES,
> +	DA9063_ADCIN1_RES,
> +	DA9063_ADCIN2_RES,
> +	DA9063_ADCIN3_RES,
> +	DA9063_MON_A8_RES,
> +	DA9063_MON_A9_RES,
> +	DA9063_MON_A10_RES,
> +
> +	/* RTC Calendar and Alarm Registers */
> +	DA9063_COUNT_S,
> +	DA9063_COUNT_MI,
> +	DA9063_COUNT_H,
> +	DA9063_COUNT_D,
> +	DA9063_COUNT_MO,
> +	DA9063_COUNT_Y,
> +
> +	DA9063_ALARM_S,
> +	DA9063_ALARM_MI,
> +	DA9063_ALARM_H,
> +	DA9063_ALARM_D,
> +	DA9063_ALARM_MO,
> +	DA9063_ALARM_Y,
> +	DA9063_SECOND_A,
> +	DA9063_SECOND_B,
> +	DA9063_SECOND_C,
> +	DA9063_SECOND_D,
> +
> +	/* Sequencer Control Registers */
> +	DA9063_SEQ			= 0x81,
> +	DA9063_SEQ_TIMER,
> +	DA9063_ID_2_1,
> +	DA9063_ID_4_3,
> +	DA9063_ID_6_5,
> +	DA9063_ID_8_7,
> +	DA9063_ID_10_9,
> +	DA9063_ID_12_11,
> +	DA9063_ID_14_13,
> +	DA9063_ID_16_15,
> +	DA9063_ID_18_17,
> +	DA9063_ID_20_19,
> +	DA9063_ID_22_21,
> +	DA9063_ID_24_23,
> +	DA9063_ID_26_25,
> +	DA9063_ID_28_27,
> +	DA9063_ID_30_29,
> +	DA9063_ID_32_31,
> +	DA9063_SEQ_A,
> +	DA9063_SEQ_B,
> +	DA9063_WAIT,
> +	DA9063_EN_32K,
> +	DA9063_RESET,
> +
> +	/* Regulator Setting Registers */
> +	DA9063_BUCK_ILIM_A,
> +	DA9063_BUCK_ILIM_B,
> +	DA9063_BUCK_ILIM_C,
> +	DA9063_BCORE2_CFG,
> +	DA9063_BCORE1_CFG,
> +	DA9063_BPRO_CFG,
> +	DA9063_BIO_CFG,
> +	DA9063_BMEM_CFG,
> +	DA9063_BPERI_CFG,
> +	DA9063_VBCORE2_A,
> +	DA9063_VBCORE1_A,
> +	DA9063_VBPRO_A,
> +	DA9063_VBMEM_A,
> +	DA9063_VBIO_A,
> +	DA9063_VBPERI_A,
> +	DA9063_VLDO1_A,
> +	DA9063_VLDO2_A,
> +	DA9063_VLDO3_A,
> +	DA9063_VLDO4_A,
> +	DA9063_VLDO5_A,
> +	DA9063_VLDO6_A,
> +	DA9063_VLDO7_A,
> +	DA9063_VLDO8_A,
> +	DA9063_VLDO9_A,
> +	DA9063_VLDO10_A,
> +	DA9063_VLDO11_A,
> +	DA9063_VBCORE2_B,
> +	DA9063_VBCORE1_B,
> +	DA9063_VBPRO_B,
> +	DA9063_VBMEM_B,
> +	DA9063_VBIO_B,
> +	DA9063_VBPERI_B,
> +	DA9063_VLDO1_B,
> +	DA9063_VLDO2_B,
> +	DA9063_VLDO3_B,
> +	DA9063_VLDO4_B,
> +	DA9063_VLDO5_B,
> +	DA9063_VLDO6_B,
> +	DA9063_VLDO7_B,
> +	DA9063_VLDO8_B,
> +	DA9063_VLDO9_B,
> +	DA9063_VLDO10_B,
> +	DA9063_VLDO11_B,
> +
> +	/* Backup Battery Charger Control Register */
> +	DA9063_BBAT_CONT,
> +
> +	/* GPIO PWM (LED) */
> +	DA9063_GPO11_LED,
> +	DA9063_GPO14_LED,
> +	DA9063_GPO15_LED,
> +
> +	/* GP-ADC Threshold Registers */
> +	DA9063_ADC_CFG,
> +	DA9063_AUTO1_HIGH,
> +	DA9063_AUTO1_LOW,
> +	DA9063_AUTO2_HIGH,
> +	DA9063_AUTO2_LOW,
> +	DA9063_AUTO3_HIGH,
> +	DA9063_AUTO3_LOW,
> +
> +	/* DA9063 Configuration registers */
> +	/* OTP */
> +	DA9063_OTP_CONT			= 0x101,
> +	DA9063_OTP_ADDR,
> +	DA9063_OTP_DATA,
> +
> +	/* Customer Trim and Configuration */
> +	DA9063_T_OFFSET,
> +	DA9063_INTERFACE,
> +	DA9063_CONFIG_A,
> +	DA9063_CONFIG_B,
> +	DA9063_CONFIG_C,
> +	DA9063_CONFIG_D,
> +	DA9063_CONFIG_E,
> +	DA9063_CONFIG_F,
> +	DA9063_CONFIG_G,
> +	DA9063_CONFIG_H,
> +	DA9063_CONFIG_I,
> +	DA9063_CONFIG_J,
> +	DA9063_CONFIG_K,
> +	DA9063_CONFIG_L,
> +
> +	DA9063_CONFIG_M,
> +	DA9063_CONFIG_N,
> +
> +	DA9063_MON_REG_1,
> +	DA9063_MON_REG_2,
> +	DA9063_MON_REG_3,
> +	DA9063_MON_REG_4,
> +	DA9063_MON_REG_5		= 0x11E,
> +	DA9063_MON_REG_6,
> +	DA9063_TRIM_CLDR,
> +	/* General Purpose Registers */
> +	DA9063_GP_ID_0,
> +	DA9063_GP_ID_1,
> +	DA9063_GP_ID_2,
> +	DA9063_GP_ID_3,
> +	DA9063_GP_ID_4,
> +	DA9063_GP_ID_5,
> +	DA9063_GP_ID_6,
> +	DA9063_GP_ID_7,
> +	DA9063_GP_ID_8,
> +	DA9063_GP_ID_9,
> +	DA9063_GP_ID_10,
> +	DA9063_GP_ID_11,
> +	DA9063_GP_ID_12,
> +	DA9063_GP_ID_13,
> +	DA9063_GP_ID_14,
> +	DA9063_GP_ID_15,
> +	DA9063_GP_ID_16,
> +	DA9063_GP_ID_17,
> +	DA9063_GP_ID_18,
> +	DA9063_GP_ID_19,
> +
> +	/* Chip ID and variant */
> +	DA9063_CHIP_ID			= 0x181,
> +	DA9063_CHIP_VARIANT,
> +
> +	DA9063_NUM_OF_REGS,
> +};
> +
> +#define DA9063_REG_PAGE_MASK		GENMASK(8, 7)
> +#define DA9063_REG_ADDR_MASK		GENMASK(6, 0)
> +
> +#define DA9063_PROTO_ADDR_MASK		GENMASK(7, 1)
> +#define DA9063_PROTO_RW_MASK		BIT(0)
> +#define DA9063_PROTO_READ		1
> +#define DA9063_PROTO_WRITE		0
> +#define DA9063_PROTO_LEN		16
> +
> +/* DA9063_PAGE_CON - 0x0 */
> +#define DA9063_PAGE_CON_PAGE			GENMASK(2, 0)
> +#define DA9063_PAGE_CON_WRITE_MODE		BIT(6)
> +#define DA9063_PAGE_CON_WRITE_MODE_PAGE		0
> +#define DA9063_PAGE_CON_WRITE_MODE_REPEAT	1
> +#define DA9063_PAGE_CON_REVERT			BIT(7)
> +
> +/* DA9063_B<x>_CONT - 0x20 - 0x25 */
> +#define DA9063_BUCK_ENABLE	BIT(0)
> +
> +/* DA9063_LDO<x>_CONT - 0x26 - 0x30 */
> +#define DA9063_LDO_ENABLE	BIT(0)
> +
> +/* DA9063_B<x>_CFG - 0x9D - 0xA2 */
> +#define DA9063_BUCK_MODE	GENMASK(7, 6)
> +#define DA9063_BUCK_MODE_MANUAL	0
> +#define DA9063_BUCK_MODE_SLEEP	1
> +#define DA9063_BUCK_MODE_SYNC	2
> +#define DA9063_BUCK_MODE_AUTO	3
> +
> +/* DA9063_VB<x>_A - 0xA3 - 0xA8 */
> +#define DA9063_BUCK_VSEL	GENMASK(6, 0)
> +
> +/* DA9063_VLDO<x>_A - 0xA9 - 0xB3 */
> +#define DA9063_LDO_VSEL		GENMASK(5, 0)
> +
> +/* DA9063_CHIP_ID - 0x181 */
> +#define DA9063_CHIP_ID_DA9063	0x61
> +
> +/* regulator operating modes */
> +enum {
> +	DA9063_OPMODE_AUTO,
> +	DA9063_OPMODE_SYNC,
> +};
> +
> +/* Drivers name */
> +#define DA9063_LDO_DRIVER	"da9063_ldo"
> +#define DA9063_BUCK_DRIVER	"da9063_buck"
> +
> +#endif /* __DA9063_PMIC_H_ */
> +
> 

^ permalink raw reply	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 36/37] dm: pmic: add da9063 PMIC driver and regulators
  2019-10-16  7:24   ` Schrempf Frieder
@ 2019-10-16 11:11     ` Robert Beckett
  2019-10-16 12:06       ` Martin Fuzzey
  0 siblings, 1 reply; 44+ messages in thread
From: Robert Beckett @ 2019-10-16 11:11 UTC (permalink / raw)
  To: u-boot

On Wed, 2019-10-16 at 07:24 +0000, Schrempf Frieder wrote:
> Hi Robert,
> 
> On 15.10.19 17:53, Robert Beckett wrote:
> > Add DM driver to support Dialog DA9063.
> > Currently it support binding regulator children.
> > 
> > Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
> 
> I also have a board with DA9063 and was looking for support in U-
> Boot. I 
> found patches from Martin Fuzzey [1] and pulled them in almost as is
> and 
> found them to work just fine.
> 
> Unfortunately I didn't have time to resend them yet, but you can
> find 
> the rebased patches here: [2].
> 
> On a first glance your implementation looks different, so it seems
> you 
> didn't use Martin's patches. Though the resulting features probably
> will 
> be similar.
> 
> I only had a very quick look and one difference seems to be that
> your 
> regulator implementation supports the AUTO and SYNC mode, while
> Martin's 
> version supports AUTO, SYNC and SLEEP. There might be other
> differences.
> 
> What do you think? Which version would be better?

(+cc Martin Fuzzey)

Huh, I had not seen that.
Martin's versions looks more complete than mine, so I would say go with
that one.

Martin: any objections to including your patches in here? I dont mind
pushing it through and handling any review comments etc. I am keen to
get get this upstreamed.

> 
> Also find a few comments below, though I didn't do a full review,
> yet.
> 
> Thanks,
> Frieder
> 
> [1] https://patchwork.ozlabs.org/cover/979346/
> [2] https://github.com/fschrempf/u-boot/commits/da9063
> 
> > ---
> >   drivers/power/pmic/Kconfig       |   8 +
> >   drivers/power/pmic/Makefile      |   1 +
> >   drivers/power/pmic/da9063.c      | 270 ++++++++++++++++++++++++++
> >   drivers/power/regulator/Kconfig  |   7 +
> >   drivers/power/regulator/Makefile |   1 +
> >   drivers/power/regulator/da9063.c | 320
> > +++++++++++++++++++++++++++++++
> >   include/power/da9063_pmic.h      | 303
> > +++++++++++++++++++++++++++++
> >   7 files changed, 910 insertions(+)
> >   create mode 100644 drivers/power/pmic/da9063.c
> >   create mode 100644 drivers/power/regulator/da9063.c
> >   create mode 100644 include/power/da9063_pmic.h
> > 
> > diff --git a/drivers/power/pmic/Kconfig
> > b/drivers/power/pmic/Kconfig
> > index 586772fdec..6dd7b1bf76 100644
> > --- a/drivers/power/pmic/Kconfig
> > +++ b/drivers/power/pmic/Kconfig
> > @@ -267,3 +267,11 @@ config SPL_PMIC_LP87565
> >   	help
> >   	The LP87565 is a PMIC containing a bunch of SMPS.
> >   	This driver binds the pmic children in SPL.
> > +
> > +config DM_PMIC_DA9063
> > +	bool "Enable support for Dialog DA9063 PMIC"
> > +	depends on DM_PMIC && (DM_I2C || DM_SPI)
> > +	help
> > +	The DA9063 is a PMIC providing 6 BUCK converters and 11 LDO
> > regulators.
> > +	It can be accessed via I2C or SPI.
> > +	This driver binds the pmic children.
> > diff --git a/drivers/power/pmic/Makefile
> > b/drivers/power/pmic/Makefile
> > index 888dbb2857..9be9d5d9a0 100644
> > --- a/drivers/power/pmic/Makefile
> > +++ b/drivers/power/pmic/Makefile
> > @@ -25,6 +25,7 @@ obj-$(CONFIG_$(SPL_)PMIC_PALMAS) += palmas.o
> >   obj-$(CONFIG_$(SPL_)PMIC_LP873X) += lp873x.o
> >   obj-$(CONFIG_$(SPL_)PMIC_LP87565) += lp87565.o
> >   obj-$(CONFIG_PMIC_STPMIC1) += stpmic1.o
> > +obj-$(CONFIG_DM_PMIC_DA9063) += da9063.o
> 
> It would be good to be able to enable the driver for U-Boot proper
> and 
> SPL separately. So this should be CONFIG_$(SPL_)DM_PMIC_DA9063.
> 
> >   
> >   obj-$(CONFIG_POWER_LTC3676) += pmic_ltc3676.o
> >   obj-$(CONFIG_POWER_MAX77696) += pmic_max77696.o
> > diff --git a/drivers/power/pmic/da9063.c
> > b/drivers/power/pmic/da9063.c
> > new file mode 100644
> > index 0000000000..81a7803b09
> > --- /dev/null
> > +++ b/drivers/power/pmic/da9063.c
> > @@ -0,0 +1,270 @@
> > +// SPDX-License-Identifier: GPL-2.0+
> > +/*
> > + * (C) Copyright 2019 Collabora
> > + * (C) Copyright 2019 GE
> > + */
> > +
> > +#define DEBUG 1
> 
> This should not be here.
> 
> > +#include <common.h>
> > +#include <fdtdec.h>
> > +#include <errno.h>
> > +#include <dm.h>
> > +#include <i2c.h>
> > +#include <spi.h>
> > +#include <linux/bitfield.h>
> > +#include <power/pmic.h>
> > +#include <power/regulator.h>
> > +#include <power/da9063_pmic.h>
> > +
> > +static const struct pmic_child_info pmic_children_info[] = {
> > +	{ .prefix = "bcore", .driver = DA9063_BUCK_DRIVER },
> > +	{ .prefix = "bpro", .driver = DA9063_BUCK_DRIVER },
> > +	{ .prefix = "bmem", .driver = DA9063_BUCK_DRIVER },
> > +	{ .prefix = "bio", .driver = DA9063_BUCK_DRIVER },
> > +	{ .prefix = "bperi", .driver = DA9063_BUCK_DRIVER },
> > +	{ .prefix = "ldo", .driver = DA9063_LDO_DRIVER },
> > +	{ },
> > +};
> > +
> > +static int da9063_reg_count(struct udevice *dev)
> > +{
> > +	return DA9063_NUM_OF_REGS;
> > +}
> > +
> > +#if defined(CONFIG_DM_I2C)
> > +static int da9063_i2c_read(struct udevice *dev, uint reg, uint8_t
> > *buff,
> > +			   int len)
> > +{
> > +	int ret;
> > +
> > +	/* only support single reg accesses */
> > +	if (len != 1)
> > +		return -EINVAL;
> > +
> > +	ret = dm_i2c_read(dev, reg, buff, len);
> > +	if (ret) {
> > +		pr_err("%s: unable to read reg %#x: %d\n", __func__,
> > reg, ret);
> > +		return ret;
> > +	}
> > +
> > +	return 0;
> > +}
> > +
> > +static int da9063_i2c_write(struct udevice *dev, uint reg, const
> > uint8_t *buff,
> > +			    int len)
> > +{
> > +	int ret;
> > +
> > +	/* only support single reg accesses */
> > +	if (len != 1)
> > +		return -EINVAL;
> > +
> > +	ret = dm_i2c_write(dev, reg, buff, len);
> > +	if (ret) {
> > +		pr_err("%s: unable to write reg %#x: %d\n", __func__,
> > reg, ret);
> > +		return ret;
> > +	}
> > +
> > +	return 0;
> > +}
> > +#endif
> > +
> > +#if defined(CONFIG_DM_SPI)
> > +static int da9063_spi_read(struct udevice *dev, uint reg, uint8_t
> > *buff,
> > +			   int len)
> > +{
> > +	u8 page;
> > +	u8 data[2];
> > +	int ret;
> > +
> > +	/* only support single reg accesses */
> > +	if (len != 1)
> > +		return -EINVAL;
> > +
> > +	page = FIELD_GET(DA9063_REG_PAGE_MASK, reg);
> > +	reg = FIELD_GET(DA9063_REG_ADDR_MASK, reg);
> > +
> > +	ret = dm_spi_claim_bus(dev);
> > +	if (ret)
> > +		return ret;
> > +	/* set page */
> > +	data[0] = FIELD_PREP(DA9063_PROTO_ADDR_MASK, DA9063_PAGE_CON) |
> > +		  FIELD_PREP(DA9063_PROTO_RW_MASK, DA9063_PROTO_WRITE);
> > +	data[1] = FIELD_PREP(DA9063_PAGE_CON_PAGE, page);
> > +	ret = dm_spi_xfer(dev, DA9063_PROTO_LEN, data, NULL,
> > SPI_XFER_ONCE);
> > +	if (ret) {
> > +		pr_err("%s: unable to set page: %d\n", __func__, ret);
> > +		goto err_page;
> > +	}
> > +
> > +	/* set target reg */
> > +	data[0] = FIELD_PREP(DA9063_PROTO_ADDR_MASK, reg) |
> > +		  FIELD_PREP(DA9063_PROTO_RW_MASK, DA9063_PROTO_READ);
> > +	data[1] = 0;
> > +	ret = dm_spi_xfer(dev, DA9063_PROTO_LEN, data, data,
> > SPI_XFER_ONCE);
> > +	if (ret) {
> > +		pr_err("%s: unable to read reg %#x: %d\n", __func__,
> > reg, ret);
> > +		goto err_reg;
> > +	}
> > +	dm_spi_release_bus(dev);
> > +
> > +	*buff = data[1];
> > +
> > +	return 0;
> > +
> > +err_page:
> > +err_reg:
> > +	dm_spi_release_bus(dev);
> > +
> > +	return ret;
> > +}
> > +
> > +static int da9063_spi_write(struct udevice *dev, uint reg, const
> > uint8_t *buff,
> > +			    int len)
> > +{
> > +	u8 page;
> > +	u8 data[2];
> > +	int ret;
> > +
> > +	/* only support single reg accesses */
> > +	if (len != 1)
> > +		return -EINVAL;
> > +
> > +	page = FIELD_GET(DA9063_REG_PAGE_MASK, reg);
> > +	reg = FIELD_GET(DA9063_REG_ADDR_MASK, reg);
> > +
> > +	ret = dm_spi_claim_bus(dev);
> > +	if (ret)
> > +		return ret;
> > +	/* set page */
> > +	data[0] = FIELD_PREP(DA9063_PROTO_ADDR_MASK, DA9063_PAGE_CON) |
> > +		  FIELD_PREP(DA9063_PROTO_RW_MASK, DA9063_PROTO_WRITE);
> > +	data[1] = FIELD_PREP(DA9063_PAGE_CON_PAGE, page);
> > +	ret = dm_spi_xfer(dev, DA9063_PROTO_LEN, data, NULL,
> > SPI_XFER_ONCE);
> > +	if (ret) {
> > +		pr_err("%s: unable to set page: %d\n", __func__, ret);
> > +		goto err_page;
> > +	}
> > +
> > +	/* set target reg */
> > +	data[0] = FIELD_PREP(DA9063_PROTO_ADDR_MASK, reg) |
> > +		  FIELD_PREP(DA9063_PROTO_RW_MASK, DA9063_PROTO_WRITE);
> > +	data[1] = *buff;
> > +	ret = dm_spi_xfer(dev, DA9063_PROTO_LEN, data, NULL,
> > SPI_XFER_ONCE);
> > +	if (ret) {
> > +		pr_err("%s: unable to write reg %#x: %d\n", __func__,
> > reg, ret);
> > +		goto err_reg;
> > +	}
> > +	dm_spi_release_bus(dev);
> > +
> > +	return 0;
> > +
> > +err_page:
> > +err_reg:
> > +	dm_spi_release_bus(dev);
> > +
> > +	return ret;
> > +}
> > +#endif
> > +
> > +struct da9063_priv {
> > +	int (*read)(struct udevice *dev, uint reg, uint8_t *buffer, int
> > len);
> > +	int (*write)(struct udevice *dev, uint reg, const uint8_t
> > *buffer,
> > +		     int len);
> > +};
> > +
> > +static int da9063_read(struct udevice *dev, uint reg, uint8_t
> > *buff, int len)
> > +{
> > +	struct da9063_priv *priv = dev_get_priv(dev);
> > +
> > +	return priv->read(dev, reg, buff, len);
> > +}
> > +
> > +static int da9063_write(struct udevice *dev, uint reg, const
> > uint8_t *buff,
> > +			int len)
> > +{
> > +	struct da9063_priv *priv = dev_get_priv(dev);
> > +
> > +	return priv->write(dev, reg, buff, len);
> > +}
> > +
> > +static struct dm_pmic_ops da9063_ops = {
> > +	.reg_count = da9063_reg_count,
> > +	.read = da9063_read,
> > +	.write = da9063_write,
> > +};
> > +
> > +static int da9063_bind(struct udevice *dev)
> > +{
> > +	ofnode regulators_node;
> > +	int children;
> > +
> > +	regulators_node = dev_read_subnode(dev, "regulators");
> > +	if (!ofnode_valid(regulators_node)) {
> > +		pr_debug("%s: %s regulators subnode not found!\n",
> > __func__,
> > +			 dev->name);
> > +		return -ENXIO;
> > +	}
> > +
> > +	pr_debug("%s: '%s' - found regulators subnode\n", __func__,
> > dev->name);
> > +
> > +	children = pmic_bind_children(dev, regulators_node,
> > pmic_children_info);
> > +	if (!children)
> > +		pr_debug("%s: %s - no child found\n", __func__, dev-
> > >name);
> > +
> > +	return 0;
> > +}
> > +
> > +static int da9063_probe(struct udevice *dev)
> > +{
> > +	struct da9063_priv *priv = dev_get_priv(dev);
> > +	int ret;
> > +
> > +	if (device_get_uclass_id(dev->parent) == UCLASS_I2C) {
> > +#if defined(CONFIG_DM_I2C)
> > +		i2c_set_chip_addr_offset_mask(dev, 0x1);
> > +		priv->read = da9063_i2c_read;
> > +		priv->write = da9063_i2c_write;
> > +#else
> > +		return -ENODEV;
> > +#endif
> > +	} else if (device_get_uclass_id(dev->parent) == UCLASS_SPI) {
> > +#if defined(CONFIG_DM_SPI)
> > +		priv->read = da9063_spi_read;
> > +		priv->write = da9063_spi_write;
> > +#else
> > +		return -ENODEV;
> > +#endif
> > +	} else {
> > +		pr_err("%s: invalid bus\n", __func__);
> > +		return -ENODEV;
> > +	}
> > +
> > +	ret = pmic_reg_read(dev, DA9063_CHIP_ID);
> > +	if (ret < 0) {
> > +		pr_debug("%s: unable to read chip id: %d\n", __func__,
> > ret);
> > +		return ret;
> > +	}
> > +
> > +	if (ret != DA9063_CHIP_ID_DA9063) {
> > +		pr_debug("%s: unknown chip id: %#x\n", __func__, ret);
> > +		return -ENODEV;
> > +	}
> > +
> > +	return 0;
> > +}
> > +
> > +static const struct udevice_id da9063_ids[] = {
> > +	{ .compatible = "dlg,da9063" },
> > +	{ }
> > +};
> > +
> > +U_BOOT_DRIVER(pmic_da9063) = {
> > +	.name = "da9063_pmic",
> > +	.id = UCLASS_PMIC,
> > +	.of_match = da9063_ids,
> > +	.bind = da9063_bind,
> > +	.ops = &da9063_ops,
> > +	.priv_auto_alloc_size = sizeof(struct da9063_priv),
> > +	.probe = da9063_probe,
> > +};
> > diff --git a/drivers/power/regulator/Kconfig
> > b/drivers/power/regulator/Kconfig
> > index 9aa00fad42..e87cccdb82 100644
> > --- a/drivers/power/regulator/Kconfig
> > +++ b/drivers/power/regulator/Kconfig
> > @@ -313,3 +313,10 @@ config SPL_DM_REGULATOR_LP873X
> >   	This enables implementation of driver-model regulator uclass
> >   	features for REGULATOR LP873X and the family of LP873X PMICs.
> >   	The driver implements get/set api for: value and enable in SPL.
> > +
> > +config DM_REGULATOR_DA9063
> > +	bool "Enable support for DA9063 regulators"
> > +	help
> > +	Enable support the regulator functions of the DA9063 PMIC.
> > +	The driver support voltage set/get and enable/disable for LDOs
> > and
> > +	BUCKs, and mode get/set for BUCKs.
> > diff --git a/drivers/power/regulator/Makefile
> > b/drivers/power/regulator/Makefile
> > index 6a3d4bbee4..f0926614cb 100644
> > --- a/drivers/power/regulator/Makefile
> > +++ b/drivers/power/regulator/Makefile
> > @@ -27,3 +27,4 @@ obj-$(CONFIG_$(SPL_)DM_REGULATOR_LP87565) +=
> > lp87565_regulator.o
> >   obj-$(CONFIG_$(SPL_)DM_REGULATOR_STM32_VREFBUF) += stm32-
> > vrefbuf.o
> >   obj-$(CONFIG_DM_REGULATOR_TPS65910) += tps65910_regulator.o
> >   obj-$(CONFIG_$(SPL_)DM_REGULATOR_STPMIC1) += stpmic1.o
> > +obj-$(CONFIG_DM_REGULATOR_DA9063) += da9063.o
> 
> It would be good to be able to enable the driver for U-Boot proper
> and 
> SPL separately. So this should be CONFIG_$(SPL_)DM_REGULATOR_DA9063.
> 
> > diff --git a/drivers/power/regulator/da9063.c
> > b/drivers/power/regulator/da9063.c
> > new file mode 100644
> > index 0000000000..68036a3951
> > --- /dev/null
> > +++ b/drivers/power/regulator/da9063.c
> > @@ -0,0 +1,320 @@
> > +// SPDX-License-Identifier: GPL-2.0+
> > +/*
> > + * (C) Copyright 2019 Collabora
> > + * (C) Copyright 2019 GE
> > + */
> > +
> > +#include <common.h>
> > +#include <fdtdec.h>
> > +#include <dm.h>
> > +#include <linux/bitfield.h>
> > +#include <power/pmic.h>
> > +#include <power/regulator.h>
> > +#include <power/da9063_pmic.h>
> > +
> > +enum {
> > +	DA9063_ID_BCORE1 = 0,
> > +	DA9063_ID_BCORE2,
> > +	DA9063_ID_BPRO,
> > +	DA9063_ID_BMEM,
> > +	DA9063_ID_BIO,
> > +	DA9063_ID_BPERI,
> > +};
> > +
> > +struct buck_info {
> > +	int min_uV;
> > +	int max_uV;
> > +	int step_uV;
> > +	int ctrl_reg;
> > +	int volt_reg;
> > +	int mode_reg;
> > +};
> > +
> > +#define to_buck_info(dev) (struct buck_info *)dev->driver_data
> > +
> > +#define DA9063_BUCK(name, min_mV, max_mV, step_mV) \
> > +{ \
> > +	.min_uV = min_mV * 1000, \
> > +	.max_uV = max_mV * 1000, \
> > +	.step_uV = step_mV * 1000, \
> > +	.ctrl_reg = DA9063_##name##_CONT, \
> > +	.volt_reg = DA9063_V##name##_A, \
> > +	.mode_reg = DA9063_##name##_CFG, \
> > +}
> > +
> > +static const struct buck_info da9063_buck_info[] = {
> > +	[DA9063_ID_BCORE1] = DA9063_BUCK(BCORE1, 300, 1570, 10),
> > +	[DA9063_ID_BCORE2] = DA9063_BUCK(BCORE2, 300, 1570, 10),
> > +	[DA9063_ID_BPRO]   = DA9063_BUCK(BPRO, 530, 1800, 10),
> > +	[DA9063_ID_BMEM]   = DA9063_BUCK(BMEM, 800, 3340, 20),
> > +	[DA9063_ID_BIO]    = DA9063_BUCK(BIO, 800, 3340, 20),
> > +	[DA9063_ID_BPERI]  = DA9063_BUCK(BPERI, 800, 3340, 20),
> > +};
> > +
> > +/* Buck converters can either be in auto mode or sync mode.
> > + * Auto uses PWM or PFM depending on load current.
> > + * Sync mode uses PFM unless output voltage is < 0.7V.
> > + */
> > +static struct dm_regulator_mode da9063_buck_modes[] = {
> > +	{
> > +		.id = DA9063_OPMODE_AUTO,
> > +		.register_value = DA9063_BUCK_MODE_AUTO,
> > +		.name = "AUTO",
> > +	},
> > +	{
> > +		.id = DA9063_OPMODE_SYNC,
> > +		.register_value = DA9063_BUCK_MODE_SYNC,
> > +		.name = "SYNC",
> > +	},
> > +};
> > +
> > +static int da9063_buck_get_mode(struct udevice *dev)
> > +{
> > +	struct buck_info *info = to_buck_info(dev);
> > +	int mode = pmic_reg_read(dev_get_parent(dev), info->mode_reg);
> > +
> > +	if (mode < 0)
> > +		return mode;
> > +
> > +	mode = FIELD_GET(DA9063_BUCK_MODE, mode);
> > +
> > +	switch (mode) {
> > +	case DA9063_BUCK_MODE_AUTO:
> > +		return DA9063_OPMODE_AUTO;
> > +	case DA9063_BUCK_MODE_SYNC:
> > +		return DA9063_OPMODE_SYNC;
> > +	default:
> > +		return -EINVAL;
> > +	}
> > +}
> > +
> > +static int da9063_buck_set_mode(struct udevice *dev, int rmode)
> > +{
> > +	struct buck_info *info = to_buck_info(dev);
> > +	int mode = pmic_reg_read(dev_get_parent(dev), info->mode_reg);
> > +
> > +	mode &= ~DA9063_BUCK_MODE;
> > +
> > +	switch (rmode) {
> > +	case DA9063_OPMODE_AUTO:
> > +		mode |= FIELD_PREP(DA9063_BUCK_MODE,
> > DA9063_BUCK_MODE_AUTO);
> > +		break;
> > +	case DA9063_OPMODE_SYNC:
> > +		mode |= FIELD_PREP(DA9063_BUCK_MODE,
> > DA9063_BUCK_MODE_SYNC);
> > +		break;
> > +	default:
> > +		return -EINVAL;
> > +	}
> > +
> > +	return pmic_reg_write(dev_get_parent(dev), info->mode_reg,
> > mode);
> > +}
> > +
> > +static int da9063_buck_get_value(struct udevice *dev)
> > +{
> > +	struct buck_info *info = to_buck_info(dev);
> > +	int sel = pmic_reg_read(dev_get_parent(dev), info->volt_reg);
> > +
> > +	if (sel < 0)
> > +		return sel;
> > +	sel = FIELD_GET(DA9063_BUCK_VSEL, sel);
> > +	return info->min_uV + (info->step_uV * sel);
> > +}
> > +
> > +static int da9063_buck_set_value(struct udevice *dev, int uV)
> > +{
> > +	struct buck_info *info = to_buck_info(dev);
> > +	int sel = pmic_reg_read(dev_get_parent(dev), info->volt_reg);
> > +
> > +	if (sel < 0)
> > +		return sel;
> > +	sel &= ~DA9063_BUCK_VSEL;
> > +	sel |= FIELD_PREP(DA9063_BUCK_VSEL,
> > +			  DIV_ROUND_UP(uV - info->min_uV, info-
> > >step_uV));
> > +
> > +	return pmic_reg_write(dev_get_parent(dev), info->volt_reg,
> > sel);
> > +}
> > +
> > +static int da9063_buck_get_enable(struct udevice *dev)
> > +{
> > +	struct buck_info *info = to_buck_info(dev);
> > +	int cont = pmic_reg_read(dev_get_parent(dev), info->ctrl_reg);
> > +
> > +	if (cont < 0)
> > +		return cont;
> > +
> > +	return FIELD_GET(DA9063_BUCK_ENABLE, cont);
> > +}
> > +
> > +static int da9063_buck_set_enable(struct udevice *dev, bool
> > enable)
> > +{
> > +	struct buck_info *info = to_buck_info(dev);
> > +	int cont = pmic_reg_read(dev_get_parent(dev), info->ctrl_reg);
> > +
> > +	if (cont < 0)
> > +		return cont;
> > +
> > +	cont &= ~DA9063_BUCK_ENABLE;
> > +	cont |= FIELD_PREP(DA9063_BUCK_ENABLE, enable);
> > +
> > +	return pmic_reg_write(dev_get_parent(dev), info->ctrl_reg,
> > cont);
> > +}
> > +
> > +static int da9063_buck_probe(struct udevice *dev)
> > +{
> > +	struct dm_regulator_uclass_platdata *uc_pdata;
> > +
> > +	uc_pdata = dev_get_uclass_platdata(dev);
> > +
> > +	if (!strcmp(uc_pdata->name, "bcore1"))
> > +		dev->driver_data =
> > (ulong)&da9063_buck_info[DA9063_ID_BCORE1];
> > +	else if (!strcmp(uc_pdata->name, "bcore2"))
> > +		dev->driver_data =
> > (ulong)&da9063_buck_info[DA9063_ID_BCORE2];
> > +	else if (!strcmp(uc_pdata->name, "bpro"))
> > +		dev->driver_data =
> > (ulong)&da9063_buck_info[DA9063_ID_BPRO];
> > +	else if (!strcmp(uc_pdata->name, "bmem"))
> > +		dev->driver_data =
> > (ulong)&da9063_buck_info[DA9063_ID_BMEM];
> > +	else if (!strcmp(uc_pdata->name, "bio"))
> > +		dev->driver_data =
> > (ulong)&da9063_buck_info[DA9063_ID_BIO];
> > +	else if (!strcmp(uc_pdata->name, "bperi"))
> > +		dev->driver_data =
> > (ulong)&da9063_buck_info[DA9063_ID_BPERI];
> > +	else
> > +		return -ENODEV;
> > +
> > +	uc_pdata->type = REGULATOR_TYPE_BUCK;
> > +	uc_pdata->mode_count = ARRAY_SIZE(da9063_buck_modes);
> > +	uc_pdata->mode = da9063_buck_modes;
> > +
> > +	return 0;
> > +}
> > +
> > +static const struct dm_regulator_ops da9063_buck_ops = {
> > +	.get_value  = da9063_buck_get_value,
> > +	.set_value  = da9063_buck_set_value,
> > +	.get_enable = da9063_buck_get_enable,
> > +	.set_enable = da9063_buck_set_enable,
> > +	.get_mode   = da9063_buck_get_mode,
> > +	.set_mode   = da9063_buck_set_mode,
> > +};
> > +
> > +U_BOOT_DRIVER(da9063_buck) = {
> > +	.name  = DA9063_BUCK_DRIVER,
> > +	.id    = UCLASS_REGULATOR,
> > +	.ops   = &da9063_buck_ops,
> > +	.probe = da9063_buck_probe,
> > +};
> > +
> > +struct ldo_info {
> > +	int min_uV;
> > +	int max_uV;
> > +	int step_uV;
> > +	int ctrl_reg;
> > +	int volt_reg;
> > +};
> > +
> > +#define to_ldo_info(dev) (struct ldo_info *)dev->driver_data
> > +
> > +#define DA9063_LDO(idx, min_mV, max_mV, step_mV) \
> > +{ \
> > +	.min_uV = min_mV * 1000, \
> > +	.max_uV = max_mV * 1000, \
> > +	.step_uV = step_mV * 1000, \
> > +	.ctrl_reg = DA9063_LDO##idx##_CONT, \
> > +	.volt_reg = DA9063_VLDO##idx##_A, \
> > +}
> > +
> > +static const struct ldo_info da9063_ldo_info[] = {
> > +	DA9063_LDO(1, 600, 1860, 20),
> > +	DA9063_LDO(2, 600, 1860, 20),
> > +	DA9063_LDO(3, 900, 3440, 20),
> > +	DA9063_LDO(4, 900, 3440, 20),
> > +	DA9063_LDO(5, 900, 3600, 50),
> > +	DA9063_LDO(6, 900, 3600, 50),
> > +	DA9063_LDO(7, 900, 3600, 50),
> > +	DA9063_LDO(8, 900, 3600, 50),
> > +	DA9063_LDO(9, 950, 3600, 50),
> > +	DA9063_LDO(10, 900, 3600, 50),
> > +	DA9063_LDO(11, 900, 3600, 50),
> > +};
> > +
> > +static int da9063_ldo_get_value(struct udevice *dev)
> > +{
> > +	struct ldo_info *info = to_ldo_info(dev);
> > +	int sel;
> > +
> > +	sel = pmic_reg_read(dev_get_parent(dev), info->volt_reg);
> > +	if (sel < 0)
> > +		return sel;
> > +	sel = FIELD_GET(DA9063_LDO_VSEL, sel);
> > +	return info->min_uV + (info->step_uV * sel);
> > +}
> > +
> > +static int da9063_ldo_set_value(struct udevice *dev, int uV)
> > +{
> > +	struct ldo_info *info = to_ldo_info(dev);
> > +	int sel;
> > +
> > +	sel = pmic_reg_read(dev_get_parent(dev), info->volt_reg);
> > +	if (sel < 0)
> > +		return sel;
> > +	sel &= ~DA9063_LDO_VSEL;
> > +	sel |= FIELD_PREP(DA9063_LDO_VSEL,
> > +			  DIV_ROUND_UP(uV - info->min_uV, info-
> > >step_uV));
> > +
> > +	return pmic_reg_write(dev_get_parent(dev), info->volt_reg,
> > sel);
> > +}
> > +
> > +static int da9063_ldo_get_enable(struct udevice *dev)
> > +{
> > +	struct ldo_info *info = to_ldo_info(dev);
> > +	int cont = pmic_reg_read(dev_get_parent(dev), info->ctrl_reg);
> > +
> > +	if (cont < 0)
> > +		return cont;
> > +
> > +	return FIELD_GET(DA9063_LDO_ENABLE, cont);
> > +}
> > +
> > +static int da9063_ldo_set_enable(struct udevice *dev, bool enable)
> > +{
> > +	struct ldo_info *info = to_ldo_info(dev);
> > +	int cont = pmic_reg_read(dev_get_parent(dev), info->ctrl_reg);
> > +
> > +	if (cont < 0)
> > +		return cont;
> > +
> > +	cont &= ~DA9063_LDO_ENABLE;
> > +	cont |= FIELD_PREP(DA9063_LDO_ENABLE, enable);
> > +
> > +	return pmic_reg_write(dev_get_parent(dev), info->ctrl_reg,
> > cont);
> > +}
> > +
> > +static int da9063_ldo_probe(struct udevice *dev)
> > +{
> > +	struct dm_regulator_uclass_platdata *uc_pdata;
> > +
> > +	if (dev->driver_data < 1 ||
> > +	    dev->driver_data > ARRAY_SIZE(da9063_ldo_info))
> > +		return -EINVAL;
> > +
> > +	uc_pdata = dev_get_uclass_platdata(dev);
> > +
> > +	dev->driver_data = (ulong)&da9063_ldo_info[dev->driver_data -
> > 1];
> > +	uc_pdata->type = REGULATOR_TYPE_LDO;
> > +	uc_pdata->mode_count = 0;
> > +
> > +	return 0;
> > +}
> > +
> > +static const struct dm_regulator_ops da9063_ldo_ops = {
> > +	.get_value = da9063_ldo_get_value,
> > +	.set_value = da9063_ldo_set_value,
> > +	.get_enable = da9063_ldo_get_enable,
> > +	.set_enable = da9063_ldo_set_enable,
> > +};
> > +
> > +U_BOOT_DRIVER(da9063_ldo) = {
> > +	.name = DA9063_LDO_DRIVER,
> > +	.id = UCLASS_REGULATOR,
> > +	.ops = &da9063_ldo_ops,
> > +	.probe = da9063_ldo_probe,
> > +};
> > diff --git a/include/power/da9063_pmic.h
> > b/include/power/da9063_pmic.h
> > new file mode 100644
> > index 0000000000..7258987ae3
> > --- /dev/null
> > +++ b/include/power/da9063_pmic.h
> > @@ -0,0 +1,303 @@
> > +/* SPDX-License-Identifier: GPL-2.0+ */
> > +/*
> > + * (C) Copyright 2019 Collabora
> > + * (C) Copyright 2019 GE
> > + */
> > +
> > +#ifndef __DA9063_PMIC_H_
> > +#define __DA9063_PMIC_H_
> > +
> > +#include <linux/bitops.h>
> > +#include <power/pmic.h>
> > +
> > +enum {
> > +	DA9063_PAGE_CON			= 0x0,
> > +
> > +	/* System Control and Event Registers */
> > +	DA9063_STATUS_A,
> > +	DA9063_STATUS_B,
> > +	DA9063_STATUS_C,
> > +	DA9063_STATUS_D,
> > +	DA9063_FAULT_LOG,
> > +	DA9063_EVENT_A,
> > +	DA9063_EVENT_B,
> > +	DA9063_EVENT_C,
> > +	DA9063_EVENT_D,
> > +	DA9063_IRQ_MASK_A,
> > +	DA9063_IRQ_MASK_B,
> > +	DA9063_IRQ_MASK_C,
> > +	DA9063_IRQ_MASK_D,
> > +	DA9063_CONTROL_A,
> > +	DA9063_CONTROL_B,
> > +	DA9063_CONTROL_C,
> > +	DA9063_CONTROL_D,
> > +	DA9063_CONTROL_E,
> > +	DA9063_CONTROL_F,
> > +	DA9063_PD_DIS,
> > +
> > +	/* GPIO Control Registers */
> > +	DA9063_GPIO_0_1,
> > +	DA9063_GPIO_2_3,
> > +	DA9063_GPIO_4_5,
> > +	DA9063_GPIO_6_7,
> > +	DA9063_GPIO_8_9,
> > +	DA9063_GPIO_10_11,
> > +	DA9063_GPIO_12_13,
> > +	DA9063_GPIO_14_15,
> > +	DA9063_GPIO_MODE0_7,
> > +	DA9063_GPIO_MODE8_15,
> > +	DA9063_SWITCH_CONT,
> > +
> > +	/* Regulator Control Registers */
> > +	DA9063_BCORE2_CONT,
> > +	DA9063_BCORE1_CONT,
> > +	DA9063_BPRO_CONT,
> > +	DA9063_BMEM_CONT,
> > +	DA9063_BIO_CONT,
> > +	DA9063_BPERI_CONT,
> > +	DA9063_LDO1_CONT,
> > +	DA9063_LDO2_CONT,
> > +	DA9063_LDO3_CONT,
> > +	DA9063_LDO4_CONT,
> > +	DA9063_LDO5_CONT,
> > +	DA9063_LDO6_CONT,
> > +	DA9063_LDO7_CONT,
> > +	DA9063_LDO8_CONT,
> > +	DA9063_LDO9_CONT,
> > +	DA9063_LDO10_CONT,
> > +	DA9063_LDO11_CONT,
> > +	DA9063_SUPPLIES,
> > +	DA9063_DVC_1,
> > +	DA9063_DVC_2,
> > +
> > +	/* GP-ADC Control Registers */
> > +	DA9063_ADC_MAN,
> > +	DA9063_ADC_CONT,
> > +	DA9063_VSYS_MON,
> > +	DA9063_ADC_RES_L,
> > +	DA9063_ADC_RES_H,
> > +	DA9063_VSYS_RES,
> > +	DA9063_ADCIN1_RES,
> > +	DA9063_ADCIN2_RES,
> > +	DA9063_ADCIN3_RES,
> > +	DA9063_MON_A8_RES,
> > +	DA9063_MON_A9_RES,
> > +	DA9063_MON_A10_RES,
> > +
> > +	/* RTC Calendar and Alarm Registers */
> > +	DA9063_COUNT_S,
> > +	DA9063_COUNT_MI,
> > +	DA9063_COUNT_H,
> > +	DA9063_COUNT_D,
> > +	DA9063_COUNT_MO,
> > +	DA9063_COUNT_Y,
> > +
> > +	DA9063_ALARM_S,
> > +	DA9063_ALARM_MI,
> > +	DA9063_ALARM_H,
> > +	DA9063_ALARM_D,
> > +	DA9063_ALARM_MO,
> > +	DA9063_ALARM_Y,
> > +	DA9063_SECOND_A,
> > +	DA9063_SECOND_B,
> > +	DA9063_SECOND_C,
> > +	DA9063_SECOND_D,
> > +
> > +	/* Sequencer Control Registers */
> > +	DA9063_SEQ			= 0x81,
> > +	DA9063_SEQ_TIMER,
> > +	DA9063_ID_2_1,
> > +	DA9063_ID_4_3,
> > +	DA9063_ID_6_5,
> > +	DA9063_ID_8_7,
> > +	DA9063_ID_10_9,
> > +	DA9063_ID_12_11,
> > +	DA9063_ID_14_13,
> > +	DA9063_ID_16_15,
> > +	DA9063_ID_18_17,
> > +	DA9063_ID_20_19,
> > +	DA9063_ID_22_21,
> > +	DA9063_ID_24_23,
> > +	DA9063_ID_26_25,
> > +	DA9063_ID_28_27,
> > +	DA9063_ID_30_29,
> > +	DA9063_ID_32_31,
> > +	DA9063_SEQ_A,
> > +	DA9063_SEQ_B,
> > +	DA9063_WAIT,
> > +	DA9063_EN_32K,
> > +	DA9063_RESET,
> > +
> > +	/* Regulator Setting Registers */
> > +	DA9063_BUCK_ILIM_A,
> > +	DA9063_BUCK_ILIM_B,
> > +	DA9063_BUCK_ILIM_C,
> > +	DA9063_BCORE2_CFG,
> > +	DA9063_BCORE1_CFG,
> > +	DA9063_BPRO_CFG,
> > +	DA9063_BIO_CFG,
> > +	DA9063_BMEM_CFG,
> > +	DA9063_BPERI_CFG,
> > +	DA9063_VBCORE2_A,
> > +	DA9063_VBCORE1_A,
> > +	DA9063_VBPRO_A,
> > +	DA9063_VBMEM_A,
> > +	DA9063_VBIO_A,
> > +	DA9063_VBPERI_A,
> > +	DA9063_VLDO1_A,
> > +	DA9063_VLDO2_A,
> > +	DA9063_VLDO3_A,
> > +	DA9063_VLDO4_A,
> > +	DA9063_VLDO5_A,
> > +	DA9063_VLDO6_A,
> > +	DA9063_VLDO7_A,
> > +	DA9063_VLDO8_A,
> > +	DA9063_VLDO9_A,
> > +	DA9063_VLDO10_A,
> > +	DA9063_VLDO11_A,
> > +	DA9063_VBCORE2_B,
> > +	DA9063_VBCORE1_B,
> > +	DA9063_VBPRO_B,
> > +	DA9063_VBMEM_B,
> > +	DA9063_VBIO_B,
> > +	DA9063_VBPERI_B,
> > +	DA9063_VLDO1_B,
> > +	DA9063_VLDO2_B,
> > +	DA9063_VLDO3_B,
> > +	DA9063_VLDO4_B,
> > +	DA9063_VLDO5_B,
> > +	DA9063_VLDO6_B,
> > +	DA9063_VLDO7_B,
> > +	DA9063_VLDO8_B,
> > +	DA9063_VLDO9_B,
> > +	DA9063_VLDO10_B,
> > +	DA9063_VLDO11_B,
> > +
> > +	/* Backup Battery Charger Control Register */
> > +	DA9063_BBAT_CONT,
> > +
> > +	/* GPIO PWM (LED) */
> > +	DA9063_GPO11_LED,
> > +	DA9063_GPO14_LED,
> > +	DA9063_GPO15_LED,
> > +
> > +	/* GP-ADC Threshold Registers */
> > +	DA9063_ADC_CFG,
> > +	DA9063_AUTO1_HIGH,
> > +	DA9063_AUTO1_LOW,
> > +	DA9063_AUTO2_HIGH,
> > +	DA9063_AUTO2_LOW,
> > +	DA9063_AUTO3_HIGH,
> > +	DA9063_AUTO3_LOW,
> > +
> > +	/* DA9063 Configuration registers */
> > +	/* OTP */
> > +	DA9063_OTP_CONT			= 0x101,
> > +	DA9063_OTP_ADDR,
> > +	DA9063_OTP_DATA,
> > +
> > +	/* Customer Trim and Configuration */
> > +	DA9063_T_OFFSET,
> > +	DA9063_INTERFACE,
> > +	DA9063_CONFIG_A,
> > +	DA9063_CONFIG_B,
> > +	DA9063_CONFIG_C,
> > +	DA9063_CONFIG_D,
> > +	DA9063_CONFIG_E,
> > +	DA9063_CONFIG_F,
> > +	DA9063_CONFIG_G,
> > +	DA9063_CONFIG_H,
> > +	DA9063_CONFIG_I,
> > +	DA9063_CONFIG_J,
> > +	DA9063_CONFIG_K,
> > +	DA9063_CONFIG_L,
> > +
> > +	DA9063_CONFIG_M,
> > +	DA9063_CONFIG_N,
> > +
> > +	DA9063_MON_REG_1,
> > +	DA9063_MON_REG_2,
> > +	DA9063_MON_REG_3,
> > +	DA9063_MON_REG_4,
> > +	DA9063_MON_REG_5		= 0x11E,
> > +	DA9063_MON_REG_6,
> > +	DA9063_TRIM_CLDR,
> > +	/* General Purpose Registers */
> > +	DA9063_GP_ID_0,
> > +	DA9063_GP_ID_1,
> > +	DA9063_GP_ID_2,
> > +	DA9063_GP_ID_3,
> > +	DA9063_GP_ID_4,
> > +	DA9063_GP_ID_5,
> > +	DA9063_GP_ID_6,
> > +	DA9063_GP_ID_7,
> > +	DA9063_GP_ID_8,
> > +	DA9063_GP_ID_9,
> > +	DA9063_GP_ID_10,
> > +	DA9063_GP_ID_11,
> > +	DA9063_GP_ID_12,
> > +	DA9063_GP_ID_13,
> > +	DA9063_GP_ID_14,
> > +	DA9063_GP_ID_15,
> > +	DA9063_GP_ID_16,
> > +	DA9063_GP_ID_17,
> > +	DA9063_GP_ID_18,
> > +	DA9063_GP_ID_19,
> > +
> > +	/* Chip ID and variant */
> > +	DA9063_CHIP_ID			= 0x181,
> > +	DA9063_CHIP_VARIANT,
> > +
> > +	DA9063_NUM_OF_REGS,
> > +};
> > +
> > +#define DA9063_REG_PAGE_MASK		GENMASK(8, 7)
> > +#define DA9063_REG_ADDR_MASK		GENMASK(6, 0)
> > +
> > +#define DA9063_PROTO_ADDR_MASK		GENMASK(7, 1)
> > +#define DA9063_PROTO_RW_MASK		BIT(0)
> > +#define DA9063_PROTO_READ		1
> > +#define DA9063_PROTO_WRITE		0
> > +#define DA9063_PROTO_LEN		16
> > +
> > +/* DA9063_PAGE_CON - 0x0 */
> > +#define DA9063_PAGE_CON_PAGE			GENMASK(2, 0)
> > +#define DA9063_PAGE_CON_WRITE_MODE		BIT(6)
> > +#define DA9063_PAGE_CON_WRITE_MODE_PAGE		0
> > +#define DA9063_PAGE_CON_WRITE_MODE_REPEAT	1
> > +#define DA9063_PAGE_CON_REVERT			BIT(7)
> > +
> > +/* DA9063_B<x>_CONT - 0x20 - 0x25 */
> > +#define DA9063_BUCK_ENABLE	BIT(0)
> > +
> > +/* DA9063_LDO<x>_CONT - 0x26 - 0x30 */
> > +#define DA9063_LDO_ENABLE	BIT(0)
> > +
> > +/* DA9063_B<x>_CFG - 0x9D - 0xA2 */
> > +#define DA9063_BUCK_MODE	GENMASK(7, 6)
> > +#define DA9063_BUCK_MODE_MANUAL	0
> > +#define DA9063_BUCK_MODE_SLEEP	1
> > +#define DA9063_BUCK_MODE_SYNC	2
> > +#define DA9063_BUCK_MODE_AUTO	3
> > +
> > +/* DA9063_VB<x>_A - 0xA3 - 0xA8 */
> > +#define DA9063_BUCK_VSEL	GENMASK(6, 0)
> > +
> > +/* DA9063_VLDO<x>_A - 0xA9 - 0xB3 */
> > +#define DA9063_LDO_VSEL		GENMASK(5, 0)
> > +
> > +/* DA9063_CHIP_ID - 0x181 */
> > +#define DA9063_CHIP_ID_DA9063	0x61
> > +
> > +/* regulator operating modes */
> > +enum {
> > +	DA9063_OPMODE_AUTO,
> > +	DA9063_OPMODE_SYNC,
> > +};
> > +
> > +/* Drivers name */
> > +#define DA9063_LDO_DRIVER	"da9063_ldo"
> > +#define DA9063_BUCK_DRIVER	"da9063_buck"
> > +
> > +#endif /* __DA9063_PMIC_H_ */
> > +

^ permalink raw reply	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 36/37] dm: pmic: add da9063 PMIC driver and regulators
  2019-10-16 11:11     ` Robert Beckett
@ 2019-10-16 12:06       ` Martin Fuzzey
  0 siblings, 0 replies; 44+ messages in thread
From: Martin Fuzzey @ 2019-10-16 12:06 UTC (permalink / raw)
  To: u-boot

Hi Robert,

On 16/10/2019 13:11, Robert Beckett wrote:
>
> Huh, I had not seen that.
> Martin's versions looks more complete than mine, so I would say go with
> that one.
>
> Martin: any objections to including your patches in here? I dont mind
> pushing it through and handling any review comments etc. I am keen to
> get get this upstreamed.
>

No that's fine by me. It would be good to get them upstream.

Regards,


Martin

^ permalink raw reply	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 16/37] i2c: add support for offset overflow in to address
  2019-10-16  3:40   ` Simon Glass
@ 2019-10-17 14:35     ` Robert Beckett
  2019-10-21 23:47       ` Simon Glass
  0 siblings, 1 reply; 44+ messages in thread
From: Robert Beckett @ 2019-10-17 14:35 UTC (permalink / raw)
  To: u-boot

On Tue, 2019-10-15 at 21:40 -0600, Simon Glass wrote:
> Hi Robert,
> 
> On Tue, 15 Oct 2019 at 09:55, Robert Beckett <
> bob.beckett at collabora.com> wrote:
> > Some devices (2 wire eeproms for example) use some bits from the
> > chip
> > address to represent the high bits of the offset instead of or as
> > well
> > as using multiple bytes for the offset, effectively stealing chip
> > addresses on the bus.
> > 
> > Add a chip offset mask that can be set for any i2c chip which gets
> > filled with the offset overflow during offset setup.
> > 
> > Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
> > Signed-off-by: Ian Ray <ian.ray@ge.com>
> > ---
> >  drivers/i2c/i2c-uclass.c | 32 ++++++++++++++++++++++++++------
> >  include/i2c.h            | 24 ++++++++++++++++++++++++
> >  2 files changed, 50 insertions(+), 6 deletions(-)
> 
> Please can you update the i2c tests to cover this new feature?

Sure, will do.
Having looked at the i2c testing available in test/dm/i2c.c, I'm
struggling to see how the current tests are valid.
The changes in offset leng for 3 and 4 byte offsets don't set the
correct offset length in dm_test_i2c_offset.

Also, there is no visibility of the effect under test to verify the
correct behaviour. It seems to be relying on predictable offset mapping
in to an assumed 256 byte storage in drivers/misc/i2c_eeprom_emul.c,
but as long as the mapping is consistent between read and write, it
could be all sorts of wrong and the test would not show any issue.

Also there appears to be a bug in the loop for offset mapping, I think
it should be ">=", rather than ">". Currently wouldn't it overflow the
storage if an offset of 256 is used?

Am I missing something in how it is meant to work? If not, I can modify
the tests while I'm adding a new one for the new addressing mode, I
just wanted to check first.

Thanks for the review, Ill fix the rest up for v2.

> 
> > diff --git a/drivers/i2c/i2c-uclass.c b/drivers/i2c/i2c-uclass.c
> > index e47abf1833..7580867dc1 100644
> > --- a/drivers/i2c/i2c-uclass.c
> > +++ b/drivers/i2c/i2c-uclass.c
> > @@ -52,16 +52,19 @@ void i2c_dump_msgs(struct i2c_msg *msg, int
> > nmsgs)
> >  static int i2c_setup_offset(struct dm_i2c_chip *chip, uint offset,
> >                             uint8_t offset_buf[], struct i2c_msg
> > *msg)
> >  {
> > -       int offset_len;
> > +       int offset_len = chip->offset_len;
> > 
> >         msg->addr = chip->chip_addr;
> > +       if (chip->chip_addr_offset_mask)
> > +               msg->addr |= (offset >> (8 * offset_len)) &
> > +                       chip->chip_addr_offset_mask;
> >         msg->flags = chip->flags & DM_I2C_CHIP_10BIT ? I2C_M_TEN :
> > 0;
> >         msg->len = chip->offset_len;
> >         msg->buf = offset_buf;
> > -       if (!chip->offset_len)
> > +       if (!offset_len)
> >                 return -EADDRNOTAVAIL;
> > -       assert(chip->offset_len <= I2C_MAX_OFFSET_LEN);
> > -       offset_len = chip->offset_len;
> > +       assert(offset_len <= I2C_MAX_OFFSET_LEN);
> > +
> >         while (offset_len--)
> >                 *offset_buf++ = offset >> (8 * offset_len);
> > 
> > @@ -83,7 +86,7 @@ static int i2c_read_bytewise(struct udevice *dev,
> > uint offset,
> >                 if (i2c_setup_offset(chip, offset + i, offset_buf,
> > msg))
> >                         return -EINVAL;
> >                 ptr = msg + 1;
> > -               ptr->addr = chip->chip_addr;
> > +               ptr->addr = msg->addr;
> >                 ptr->flags = msg->flags | I2C_M_RD;
> >                 ptr->len = 1;
> >                 ptr->buf = &buffer[i];
> > @@ -132,6 +135,7 @@ int dm_i2c_read(struct udevice *dev, uint
> > offset, uint8_t *buffer, int len)
> > 
> >         if (!ops->xfer)
> >                 return -ENOSYS;
> > +
> 
> Unrelated change
> 
> >         if (chip->flags & DM_I2C_CHIP_RD_ADDRESS)
> >                 return i2c_read_bytewise(dev, offset, buffer, len);
> >         ptr = msg;
> > @@ -139,7 +143,7 @@ int dm_i2c_read(struct udevice *dev, uint
> > offset, uint8_t *buffer, int len)
> >                 ptr++;
> > 
> >         if (len) {
> > -               ptr->addr = chip->chip_addr;
> > +               ptr->addr = msg->addr;
> >                 ptr->flags = chip->flags & DM_I2C_CHIP_10BIT ?
> > I2C_M_TEN : 0;
> >                 ptr->flags |= I2C_M_RD;
> >                 ptr->len = len;
> > @@ -465,6 +469,22 @@ int i2c_get_chip_offset_len(struct udevice
> > *dev)
> >         return chip->offset_len;
> >  }
> > 
> > +int i2c_set_chip_addr_offset_mask(struct udevice *dev, uint mask)
> > +{
> > +       struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
> > +
> > +       chip->chip_addr_offset_mask = mask;
> > +
> > +       return 0;
> > +}
> > +
> > +uint i2c_get_chip_addr_offset_mask(struct udevice *dev)
> > +{
> > +       struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
> > +
> > +       return chip->chip_addr_offset_mask;
> > +}
> > +
> >  #ifdef CONFIG_DM_GPIO
> >  static void i2c_gpio_set_pin(struct gpio_desc *pin, int bit)
> >  {
> > diff --git a/include/i2c.h b/include/i2c.h
> > index 33570f5404..3c927340da 100644
> > --- a/include/i2c.h
> > +++ b/include/i2c.h
> > @@ -45,12 +45,17 @@ struct udevice;
> >   *             represent up to 256 bytes. A value larger than 1
> > may be
> >   *             needed for larger devices.
> >   * @flags:     Flags for this chip (dm_i2c_chip_flags)
> > + * @chip_addr_offset_mask: Mask of offset bits within chip_addr.
> > Used for
> > + *                        devices which steal addresses as part of
> > offset.
> > + *                        If offset_len is zero, then the offset
> > is encoded
> > + *                        completely within the chip address
> > itself.
> 
> Can you add an example value here, or point to some documentation on
> this? There is not enough info here to figure out what is going on.
> 
> 
> >   * @emul: Emulator for this chip address (only used for emulation)
> >   */
> >  struct dm_i2c_chip {
> >         uint chip_addr;
> >         uint offset_len;
> >         uint flags;
> > +       uint chip_addr_offset_mask;
> >  #ifdef CONFIG_SANDBOX
> >         struct udevice *emul;
> >         bool test_mode;
> > @@ -261,6 +266,25 @@ int i2c_set_chip_offset_len(struct udevice
> > *dev, uint offset_len);
> >   */
> >  int i2c_get_chip_offset_len(struct udevice *dev);
> > 
> > +/**
> > + * i2c_set_chip_addr_offset_mask() - set mask of address bits
> > usable by offset
> > + *
> > + * Some devices listen on multiple chip addresses to achieve
> > larger offsets
> > + * than their single or multiple byte offsets would allow for. You
> > can use this
> > + * function to set the bits that are valid to be used for offset
> > overflow.
> > + *
> > + * @mask: The mask to be used for high offset bits within address
> > + * @return 0 if OK, other -ve value on error
> > + */
> > +int i2c_set_chip_addr_offset_mask(struct udevice *dev, uint mask);
> > +
> > +/*
> > + * i2c_get_chip_addr_offset_mask() - get mask of address bits
> > usable by offset
> > + *
> > + * @return current chip addr offset mask
> > + */
> > +uint i2c_get_chip_addr_offset_mask(struct udevice *dev);
> > +
> >  /**
> >   * i2c_deblock() - recover a bus that is in an unknown state
> >   *
> > --
> > 2.20.1
> > 

^ permalink raw reply	[flat|nested] 44+ messages in thread

* [U-Boot] [PATCH 16/37] i2c: add support for offset overflow in to address
  2019-10-17 14:35     ` Robert Beckett
@ 2019-10-21 23:47       ` Simon Glass
  0 siblings, 0 replies; 44+ messages in thread
From: Simon Glass @ 2019-10-21 23:47 UTC (permalink / raw)
  To: u-boot

Hi Robert,

On Thu, 17 Oct 2019 at 08:35, Robert Beckett <bob.beckett@collabora.com> wrote:
>
> On Tue, 2019-10-15 at 21:40 -0600, Simon Glass wrote:
> > Hi Robert,
> >
> > On Tue, 15 Oct 2019 at 09:55, Robert Beckett <
> > bob.beckett at collabora.com> wrote:
> > > Some devices (2 wire eeproms for example) use some bits from the
> > > chip
> > > address to represent the high bits of the offset instead of or as
> > > well
> > > as using multiple bytes for the offset, effectively stealing chip
> > > addresses on the bus.
> > >
> > > Add a chip offset mask that can be set for any i2c chip which gets
> > > filled with the offset overflow during offset setup.
> > >
> > > Signed-off-by: Robert Beckett <bob.beckett@collabora.com>
> > > Signed-off-by: Ian Ray <ian.ray@ge.com>
> > > ---
> > >  drivers/i2c/i2c-uclass.c | 32 ++++++++++++++++++++++++++------
> > >  include/i2c.h            | 24 ++++++++++++++++++++++++
> > >  2 files changed, 50 insertions(+), 6 deletions(-)
> >
> > Please can you update the i2c tests to cover this new feature?
>
> Sure, will do.
> Having looked at the i2c testing available in test/dm/i2c.c, I'm
> struggling to see how the current tests are valid.
> The changes in offset leng for 3 and 4 byte offsets don't set the
> correct offset length in dm_test_i2c_offset.
>
> Also, there is no visibility of the effect under test to verify the
> correct behaviour. It seems to be relying on predictable offset mapping
> in to an assumed 256 byte storage in drivers/misc/i2c_eeprom_emul.c,
> but as long as the mapping is consistent between read and write, it
> could be all sorts of wrong and the test would not show any issue.
>
> Also there appears to be a bug in the loop for offset mapping, I think
> it should be ">=", rather than ">". Currently wouldn't it overflow the
> storage if an offset of 256 is used?
>
> Am I missing something in how it is meant to work? If not, I can modify
> the tests while I'm adding a new one for the new addressing mode, I
> just wanted to check first.

I think the best approach is to modify the tests in a separate patch,
then add your new patch.

> Thanks for the review, Ill fix the rest up for v2.

Regards,
Simon

^ permalink raw reply	[flat|nested] 44+ messages in thread

end of thread, other threads:[~2019-10-21 23:47 UTC | newest]

Thread overview: 44+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2019-10-15 15:53 [U-Boot] [PATCH 00/37] convert GE boards to DM Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 01/37] configs: bx50v3: Fix boot hang with video Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 02/37] board: ge: bx50v3: Fix run-time warning Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 03/37] board: ge: bx50v3: Fix message output to video console Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 04/37] configs: ppd: DM for USB and regulators PPD Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 05/37] board: ge: bx50v3: Enable DM for PCI and ethernet Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 06/37] board: ge: pass rtc_status via device tree Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 07/37] board: ge: bx50v3: use imx wdt Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 08/37] board: ge: mx53ppd: " Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 09/37] board: ge: bx50v3: Add i2c bus description Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 10/37] board: ge: mx53ppd: Add i2c bus descritpion Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 11/37] misc: i2c_eeprom: add fixed partitions support Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 12/37] misc: i2c_eeprom: add size query Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 13/37] board: ge: bx50v3: use DM I2C Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 14/37] board: ge: mx53ppd: " Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 15/37] board: ge: convert vpd to use i2c eeprom Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 16/37] i2c: add support for offset overflow in to address Robert Beckett
2019-10-16  3:40   ` Simon Glass
2019-10-17 14:35     ` Robert Beckett
2019-10-21 23:47       ` Simon Glass
2019-10-15 15:53 ` [U-Boot] [PATCH 17/37] misc: i2c_eeprom: set offset len and chip addr offset mask Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 18/37] bootcount: add a DM i2c eeprom backing store for bootcount Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 19/37] board: ge: bx50v3: add i2c eeprom bootcount storage Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 20/37] board: ge: mx53ppd: " Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 21/37] rtc: rx8010sj: fix DM initialization Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 22/37] board: ge: bx50v3, mx53ppd: use DM rtc Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 23/37] board: ge: bx50v3: use DM i2c for PMIC initialization Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 24/37] board: ge: mx53ppd: remove redundant power config Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 25/37] board: ge: bx50v3, mx53ppd: disable I2C compatibility API Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 26/37] board: ge: mx53ppd: move uart initialisation to own function Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 27/37] board: ge: mx53ppd: enable DM_VIDEO Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 28/37] rtc: s35392a: encode command correctly Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 29/37] board: ge: mx53ppd: fix RTC compatible definition Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 30/37] board: ge: bx50v3: Enable DM PWM for backlight Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 31/37] board: ge: mx53ppd: clean up DM PWM video and backlight Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 32/37] board: ge: mx53ppd: Use DM for ethernet Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 33/37] board: ge: bx50v3: use DM for uart Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 34/37] serial: mxc: add imx53 and imx21 compatible string Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 35/37] board: ge: mx53ppd: use DM for uart Robert Beckett
2019-10-15 15:53 ` [U-Boot] [PATCH 36/37] dm: pmic: add da9063 PMIC driver and regulators Robert Beckett
2019-10-16  7:24   ` Schrempf Frieder
2019-10-16 11:11     ` Robert Beckett
2019-10-16 12:06       ` Martin Fuzzey
2019-10-15 15:53 ` [U-Boot] [PATCH 37/37] board: ge: bx50v3: use DM PMIC driver Robert Beckett

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.