All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v1 0/6] Add Nuvoton NPCM750 support
@ 2022-04-06  7:57 Jim Liu
  2022-04-06  7:57 ` [PATCH v1 1/6] ARM: configs: Add defconfig for Nuvoton NPCM750 Jim Liu
                   ` (6 more replies)
  0 siblings, 7 replies; 14+ messages in thread
From: Jim Liu @ 2022-04-06  7:57 UTC (permalink / raw)
  To: JJLIU0, YSCHU, KWLIU, lukma, seanga2, sjg, sr, trini; +Cc: u-boot

The patch series add basic supoorts for NPCM750, which
is Nuvoton's 3th-generation BMC (Baseboard Management Controller).
Add drivers to support Clock,Timer,Uart for NPCM7xx SoC.

the NPCM750 computing subsystem comprises a dual-core ARM a9
at 800MHz speed with L1/L2 caches

Jim Liu (6):
  ARM: configs: Add defconfig for Nuvoton NPCM750
  ARM: dts: Add Nuvoton NPCM750 device tree
  timer: npcm: Add NPCM timer support
  serial: npcm: Add support for Nuvoton NPCM SoCs
  clk: nuvoton: Add support for NPCM750
  arm: nuvoton: Add support for Nuvoton NPCM750 BMC

 arch/arm/Kconfig                              |    8 +
 arch/arm/Makefile                             |    1 +
 arch/arm/dts/Makefile                         |    1 +
 arch/arm/dts/nuvoton-common-npcm7xx.dtsi      | 1120 +++++++++++++++++
 arch/arm/dts/nuvoton-npcm750-buv-pincfg.dtsi  |  132 ++
 arch/arm/dts/nuvoton-npcm750-buv.dts          |  198 +++
 arch/arm/dts/nuvoton-npcm750.dtsi             |   63 +
 arch/arm/dts/nuvoton-npcm7xx-uboot.dtsi       |  263 ++++
 arch/arm/include/asm/arch-npcm7xx/cpu.h       |   28 +
 arch/arm/include/asm/arch-npcm7xx/gcr.h       |   64 +
 arch/arm/include/asm/arch-npcm7xx/rst.h       |   37 +
 arch/arm/mach-nuvoton/Kconfig                 |   34 +
 arch/arm/mach-nuvoton/Makefile                |    1 +
 arch/arm/mach-nuvoton/npcm7xx/Kconfig         |   18 +
 arch/arm/mach-nuvoton/npcm7xx/Makefile        |    2 +
 arch/arm/mach-nuvoton/npcm7xx/cpu.c           |   67 +
 .../arm/mach-nuvoton/npcm7xx/l2_cache_pl310.c |   30 +
 .../npcm7xx/l2_cache_pl310_init.S             |   89 ++
 arch/arm/mach-nuvoton/npcm7xx/reset.c         |   46 +
 board/nuvoton/poleg/Kconfig                   |   31 +
 board/nuvoton/poleg/MAINTAINERS               |    7 +
 board/nuvoton/poleg/Makefile                  |    1 +
 board/nuvoton/poleg/poleg_evb.c               |   52 +
 configs/PolegRunBMC_defconfig                 |   50 +
 drivers/clk/Makefile                          |    1 +
 drivers/clk/nuvoton/Makefile                  |    1 +
 drivers/clk/nuvoton/clk_npcm7xx.c             |  469 +++++++
 drivers/serial/Kconfig                        |    7 +
 drivers/serial/Makefile                       |    1 +
 drivers/serial/serial_npcm.c                  |  150 +++
 drivers/timer/Kconfig                         |    7 +
 drivers/timer/Makefile                        |    1 +
 drivers/timer/npcm-timer.c                    |  115 ++
 include/configs/poleg.h                       |   77 ++
 .../dt-bindings/clock/nuvoton,npcm7xx-clock.h |   46 +
 .../dt-bindings/reset/nuvoton,npcm7xx-reset.h |   91 ++
 36 files changed, 3309 insertions(+)
 create mode 100644 arch/arm/dts/nuvoton-common-npcm7xx.dtsi
 create mode 100644 arch/arm/dts/nuvoton-npcm750-buv-pincfg.dtsi
 create mode 100644 arch/arm/dts/nuvoton-npcm750-buv.dts
 create mode 100644 arch/arm/dts/nuvoton-npcm750.dtsi
 create mode 100644 arch/arm/dts/nuvoton-npcm7xx-uboot.dtsi
 create mode 100644 arch/arm/include/asm/arch-npcm7xx/cpu.h
 create mode 100644 arch/arm/include/asm/arch-npcm7xx/gcr.h
 create mode 100644 arch/arm/include/asm/arch-npcm7xx/rst.h
 create mode 100644 arch/arm/mach-nuvoton/Kconfig
 create mode 100644 arch/arm/mach-nuvoton/Makefile
 create mode 100644 arch/arm/mach-nuvoton/npcm7xx/Kconfig
 create mode 100644 arch/arm/mach-nuvoton/npcm7xx/Makefile
 create mode 100644 arch/arm/mach-nuvoton/npcm7xx/cpu.c
 create mode 100644 arch/arm/mach-nuvoton/npcm7xx/l2_cache_pl310.c
 create mode 100644 arch/arm/mach-nuvoton/npcm7xx/l2_cache_pl310_init.S
 create mode 100644 arch/arm/mach-nuvoton/npcm7xx/reset.c
 create mode 100644 board/nuvoton/poleg/Kconfig
 create mode 100644 board/nuvoton/poleg/MAINTAINERS
 create mode 100644 board/nuvoton/poleg/Makefile
 create mode 100644 board/nuvoton/poleg/poleg_evb.c
 create mode 100644 configs/PolegRunBMC_defconfig
 create mode 100644 drivers/clk/nuvoton/Makefile
 create mode 100644 drivers/clk/nuvoton/clk_npcm7xx.c
 create mode 100644 drivers/serial/serial_npcm.c
 create mode 100644 drivers/timer/npcm-timer.c
 create mode 100644 include/configs/poleg.h
 create mode 100644 include/dt-bindings/clock/nuvoton,npcm7xx-clock.h
 create mode 100644 include/dt-bindings/reset/nuvoton,npcm7xx-reset.h

-- 
2.17.1


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

* [PATCH v1 1/6] ARM: configs: Add defconfig for Nuvoton NPCM750
  2022-04-06  7:57 [PATCH v1 0/6] Add Nuvoton NPCM750 support Jim Liu
@ 2022-04-06  7:57 ` Jim Liu
  2022-04-06 13:39   ` Tom Rini
  2022-04-06  7:57 ` [PATCH v1 2/6] ARM: dts: Add Nuvoton NPCM750 device tree Jim Liu
                   ` (5 subsequent siblings)
  6 siblings, 1 reply; 14+ messages in thread
From: Jim Liu @ 2022-04-06  7:57 UTC (permalink / raw)
  To: JJLIU0, YSCHU, KWLIU, lukma, seanga2, sjg, sr, trini; +Cc: u-boot

Add defconfig for NPCM750 BUV (Poleg).

Signed-off-by: Jim Liu <JJLIU0@nuvoton.com>
---
 board/nuvoton/poleg/MAINTAINERS |  7 +++++
 configs/PolegRunBMC_defconfig   | 50 +++++++++++++++++++++++++++++++++
 2 files changed, 57 insertions(+)
 create mode 100644 board/nuvoton/poleg/MAINTAINERS
 create mode 100644 configs/PolegRunBMC_defconfig

diff --git a/board/nuvoton/poleg/MAINTAINERS b/board/nuvoton/poleg/MAINTAINERS
new file mode 100644
index 0000000000..bf512a4e6f
--- /dev/null
+++ b/board/nuvoton/poleg/MAINTAINERS
@@ -0,0 +1,7 @@
+Poleg BUV
+M:	Stanley Chu <yschu@nuvoton.com>
+M:	Jim Liu <JJLIU0@nuvoton.com>
+S:	Maintained
+F:	board/nuvoton/poleg/
+F:	include/configs/poleg.h
+F:	configs/PolegRunBMC_defconfig
diff --git a/configs/PolegRunBMC_defconfig b/configs/PolegRunBMC_defconfig
new file mode 100644
index 0000000000..e7b76b6bbf
--- /dev/null
+++ b/configs/PolegRunBMC_defconfig
@@ -0,0 +1,50 @@
+CONFIG_ARM=y
+CONFIG_ARCH_NPCM7xx=y
+CONFIG_TARGET_POLEG=y
+CONFIG_ARCH_NPCM=y
+CONFIG_SYS_ARM_ARCH=7
+CONFIG_SYS_LOAD_ADDR=0x10000000
+CONFIG_SYS_MALLOC_LEN=0x240000
+CONFIG_SYS_MEMTEST_END=0x08000000
+CONFIG_SYS_MEMTEST_START=0
+CONFIG_SYS_PROMPT="U-Boot>"
+CONFIG_SYS_TEXT_BASE=0x8200
+CONFIG_NR_DRAM_BANKS=2
+CONFIG_DEFAULT_DEVICE_TREE="nuvoton-npcm750-buv"
+CONFIG_ENV_IS_IN_SPI_FLASH=y
+CONFIG_ENV_SIZE=0x40000
+CONFIG_ENV_SECT_SIZE=0x4000
+CONFIG_ENV_OFFSET=0x100000
+CONFIG_ENV_ADDR=0x80100000
+CONFIG_SYS_MALLOC_F_LEN=0x1000
+
+CONFIG_DM=y
+CONFIG_DM_SERIAL=y
+CONFIG_NPCM_SERIAL=y
+CONFIG_TIMER=y
+CONFIG_NPCM_TIMER=y
+CONFIG_CLK=y
+CONFIG_CMD_UUID=y
+CONFIG_CMD_SAVEENV=y
+CONFIG_PINCTRL=y
+CONFIG_PINCTRL_NPCM7XX=y
+CONFIG_PINCONF=y
+CONFIG_DM_GPIO=y
+CONFIG_NPCM_GPIO=y
+CONFIG_CMD_GPIO=y
+CONFIG_DM_MMC=y
+CONFIG_DM_ETH=y
+
+CONFIG_SPI=y
+CONFIG_DM_SPI=y
+CONFIG_NPCM_FIU_SPI=y
+CONFIG_SF_DEFAULT_BUS=0
+CONFIG_SF_DEFAULT_CS=0
+CONFIG_DM_SPI_FLASH=y
+CONFIG_SPI_FLASH=y
+CONFIG_SPI_FLASH_MACRONIX=y
+CONFIG_SPI_FLASH_WINBOND=y
+CONFIG_CMD_SF=y
+CONFIG_CMD_MEMORY=y
+CONFIG_CMD_CACHE=y
+CONFIG_CMD_SPI=y
-- 
2.17.1


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

* [PATCH v1 2/6] ARM: dts: Add Nuvoton NPCM750 device tree
  2022-04-06  7:57 [PATCH v1 0/6] Add Nuvoton NPCM750 support Jim Liu
  2022-04-06  7:57 ` [PATCH v1 1/6] ARM: configs: Add defconfig for Nuvoton NPCM750 Jim Liu
@ 2022-04-06  7:57 ` Jim Liu
  2022-04-06 13:38   ` Tom Rini
  2022-04-06  7:57 ` [PATCH v1 3/6] timer: npcm: Add NPCM timer support Jim Liu
                   ` (4 subsequent siblings)
  6 siblings, 1 reply; 14+ messages in thread
From: Jim Liu @ 2022-04-06  7:57 UTC (permalink / raw)
  To: JJLIU0, YSCHU, KWLIU, lukma, seanga2, sjg, sr, trini; +Cc: u-boot

Add a common device tree for all Nuvoton NPCM7xx BMCs and a board
specific device tree for the NPCM750(Poleg) evaluation board.

Signed-off-by: Jim Liu <JJLIU0@nuvoton.com>
---
 arch/arm/dts/Makefile                        |    1 +
 arch/arm/dts/nuvoton-common-npcm7xx.dtsi     | 1120 ++++++++++++++++++
 arch/arm/dts/nuvoton-npcm750-buv-pincfg.dtsi |  132 +++
 arch/arm/dts/nuvoton-npcm750-buv.dts         |  198 ++++
 arch/arm/dts/nuvoton-npcm750.dtsi            |   63 +
 arch/arm/dts/nuvoton-npcm7xx-uboot.dtsi      |  263 ++++
 6 files changed, 1777 insertions(+)
 create mode 100644 arch/arm/dts/nuvoton-common-npcm7xx.dtsi
 create mode 100644 arch/arm/dts/nuvoton-npcm750-buv-pincfg.dtsi
 create mode 100644 arch/arm/dts/nuvoton-npcm750-buv.dts
 create mode 100644 arch/arm/dts/nuvoton-npcm750.dtsi
 create mode 100644 arch/arm/dts/nuvoton-npcm7xx-uboot.dtsi

diff --git a/arch/arm/dts/Makefile b/arch/arm/dts/Makefile
index 644ba961a2..bbacc3c9bd 100644
--- a/arch/arm/dts/Makefile
+++ b/arch/arm/dts/Makefile
@@ -1164,6 +1164,7 @@ dtb-$(CONFIG_ARCH_MEDIATEK) += \
 	mt8516-pumpkin.dtb \
 	mt8518-ap1-emmc.dtb
 
+dtb-$(CONFIG_ARCH_NPCM7xx) += nuvoton-npcm750-buv.dtb
 dtb-$(CONFIG_XEN) += xenguest-arm64.dtb
 
 dtb-$(CONFIG_ARCH_OCTEONTX) += octeontx.dtb
diff --git a/arch/arm/dts/nuvoton-common-npcm7xx.dtsi b/arch/arm/dts/nuvoton-common-npcm7xx.dtsi
new file mode 100644
index 0000000000..9dbc521a8e
--- /dev/null
+++ b/arch/arm/dts/nuvoton-common-npcm7xx.dtsi
@@ -0,0 +1,1120 @@
+// SPDX-License-Identifier: GPL-2.0
+
+#include <dt-bindings/interrupt-controller/arm-gic.h>
+#include <dt-bindings/clock/nuvoton,npcm7xx-clock.h>
+#include <dt-bindings/reset/nuvoton,npcm7xx-reset.h>
+
+/ {
+	#address-cells = <1>;
+	#size-cells = <1>;
+	interrupt-parent = <&gic>;
+
+	/* external reference clock */
+	clk_refclk: clk_refclk {
+		compatible = "fixed-clock";
+		#clock-cells = <0>;
+		clock-frequency = <25000000>;
+		clock-output-names = "refclk";
+	};
+
+	/* external reference clock for cpu. float in normal operation */
+	clk_sysbypck: clk_sysbypck {
+		compatible = "fixed-clock";
+		#clock-cells = <0>;
+		clock-frequency = <800000000>;
+		clock-output-names = "sysbypck";
+	};
+
+	/* external reference clock for MC. float in normal operation */
+	clk_mcbypck: clk_mcbypck {
+		compatible = "fixed-clock";
+		#clock-cells = <0>;
+		clock-frequency = <800000000>;
+		clock-output-names = "mcbypck";
+	};
+
+	 /* external clock signal rg1refck, supplied by the phy */
+	clk_rg1refck: clk_rg1refck {
+		compatible = "fixed-clock";
+		#clock-cells = <0>;
+		clock-frequency = <125000000>;
+		clock-output-names = "clk_rg1refck";
+	};
+
+	 /* external clock signal rg2refck, supplied by the phy */
+	clk_rg2refck: clk_rg2refck {
+		compatible = "fixed-clock";
+		#clock-cells = <0>;
+		clock-frequency = <125000000>;
+		clock-output-names = "clk_rg2refck";
+	};
+
+	clk_xin: clk_xin {
+		compatible = "fixed-clock";
+		#clock-cells = <0>;
+		clock-frequency = <50000000>;
+		clock-output-names = "clk_xin";
+	};
+
+	soc {
+		#address-cells = <1>;
+		#size-cells = <1>;
+		compatible = "simple-bus";
+		interrupt-parent = <&gic>;
+		ranges = <0x0 0xf0000000 0x00900000>;
+
+		scu: scu@3fe000 {
+			compatible = "arm,cortex-a9-scu";
+			reg = <0x3fe000 0x1000>;
+		};
+
+		l2: cache-controller@3fc000 {
+			compatible = "arm,pl310-cache";
+			reg = <0x3fc000 0x1000>;
+			interrupts = <GIC_SPI 21 IRQ_TYPE_LEVEL_HIGH>;
+			cache-unified;
+			cache-level = <2>;
+			clocks = <&clk NPCM7XX_CLK_AXI>;
+			arm,shared-override;
+		};
+
+		gic: interrupt-controller@3ff000 {
+			compatible = "arm,cortex-a9-gic";
+			interrupt-controller;
+			#interrupt-cells = <3>;
+			reg = <0x3ff000 0x1000>,
+				<0x3fe100 0x100>;
+		};
+
+		gcr: gcr@800000 {
+			compatible = "nuvoton,npcm750-gcr", "syscon", "simple-mfd";
+			reg = <0x800000 0x1000>;
+		};
+
+		rst: rst@801000 {
+			compatible = "nuvoton,npcm750-rst", "syscon", "simple-mfd";
+			reg = <0x801000 0x6C>;
+		};
+	};
+
+	ahb {
+		#address-cells = <1>;
+		#size-cells = <1>;
+		compatible = "simple-bus";
+		interrupt-parent = <&gic>;
+		ranges;
+
+		rstc: rstc@f0801000 {
+			compatible = "nuvoton,npcm750-reset";
+			reg = <0xf0801000 0x70>;
+			#reset-cells = <2>;
+		};
+
+		clk: clock-controller@f0801000 {
+			compatible = "nuvoton,npcm750-clk", "syscon";
+			#clock-cells = <1>;
+			clock-controller;
+			reg = <0xf0801000 0x1000>;
+			clock-names = "refclk", "sysbypck", "mcbypck";
+			clocks = <&clk_refclk>, <&clk_sysbypck>, <&clk_mcbypck>;
+		};
+
+		gmac0: eth@f0802000 {
+			device_type = "network";
+			compatible = "nuvoton,npcm-dwmac";
+			reg = <0xf0802000 0x2000>;
+			interrupts = <GIC_SPI 14 IRQ_TYPE_LEVEL_HIGH>;
+			interrupt-names = "macirq";
+			ethernet = <0>;
+			clocks	= <&clk_rg1refck>, <&clk NPCM7XX_CLK_AHB>;
+			clock-names = "stmmaceth", "clk_gmac";
+			pinctrl-names = "default";
+			pinctrl-0 = <&rg1_pins
+					&rg1mdio_pins>;
+			status = "disabled";
+		};
+
+		ehci1: usb@f0806000 {
+			compatible = "nuvoton,npcm750-ehci";
+			reg = <0xf0806000 0x1000>;
+			interrupts = <GIC_SPI 61 IRQ_TYPE_LEVEL_HIGH>;
+			status = "disabled";
+		};
+
+		fiu0: spi@fb000000 {
+			compatible = "nuvoton,npcm750-fiu";
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <0xfb000000 0x1000>;
+			reg-names = "control", "memory";
+			clocks = <&clk NPCM7XX_CLK_SPI0>;
+			clock-names = "clk_spi0";
+			status = "disabled";
+		};
+
+		fiu3: spi@c0000000 {
+			compatible = "nuvoton,npcm750-fiu";
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <0xc0000000 0x1000>;
+			reg-names = "control", "memory";
+			clocks = <&clk NPCM7XX_CLK_SPI3>;
+			clock-names = "clk_spi3";
+			pinctrl-names = "default";
+			pinctrl-0 = <&spi3_pins>;
+			status = "disabled";
+		};
+
+		fiux: spi@fb001000 {
+			compatible = "nuvoton,npcm750-fiu";
+			#address-cells = <1>;
+			#size-cells = <0>;
+			reg = <0xfb001000 0x1000>;
+			reg-names = "control", "memory";
+			clocks = <&clk NPCM7XX_CLK_SPIX>;
+			clock-names = "clk_spix";
+			status = "disabled";
+		};
+
+		apb {
+			#address-cells = <1>;
+			#size-cells = <1>;
+			compatible = "simple-bus";
+			interrupt-parent = <&gic>;
+			ranges = <0x0 0xf0000000 0x00300000>;
+
+			lpc_kcs: lpc_kcs@7000 {
+				compatible = "nuvoton,npcm750-lpc-kcs", "simple-mfd", "syscon";
+				reg = <0x7000 0x40>;
+				reg-io-width = <1>;
+
+				#address-cells = <1>;
+				#size-cells = <1>;
+				ranges = <0x0 0x7000 0x40>;
+
+				kcs1: kcs1@0 {
+					compatible = "nuvoton,npcm750-kcs-bmc";
+					reg = <0x0 0x40>;
+					interrupts = <GIC_SPI 9 IRQ_TYPE_LEVEL_HIGH>;
+					kcs_chan = <1>;
+					status = "disabled";
+				};
+
+				kcs2: kcs2@0 {
+					compatible = "nuvoton,npcm750-kcs-bmc";
+					reg = <0x0 0x40>;
+					interrupts = <GIC_SPI 9 IRQ_TYPE_LEVEL_HIGH>;
+					kcs_chan = <2>;
+					status = "disabled";
+				};
+
+				kcs3: kcs3@0 {
+					compatible = "nuvoton,npcm750-kcs-bmc";
+					reg = <0x0 0x40>;
+					interrupts = <GIC_SPI 9 IRQ_TYPE_LEVEL_HIGH>;
+					kcs_chan = <3>;
+					status = "disabled";
+				};
+			};
+
+			spi0: spi@200000 {
+				compatible = "nuvoton,npcm750-pspi";
+				reg = <0x200000 0x1000>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&pspi1_pins>;
+				#address-cells = <1>;
+				#size-cells = <0>;
+				interrupts = <GIC_SPI 31 IRQ_TYPE_LEVEL_HIGH>;
+				clocks = <&clk NPCM7XX_CLK_APB5>;
+				clock-names = "clk_apb5";
+				resets = <&rstc NPCM7XX_RESET_IPSRST2 NPCM7XX_RESET_PSPI1>;
+				status = "disabled";
+			};
+
+			spi1: spi@201000 {
+				compatible = "nuvoton,npcm750-pspi";
+				reg = <0x201000 0x1000>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&pspi2_pins>;
+				#address-cells = <1>;
+				#size-cells = <0>;
+				interrupts = <GIC_SPI 28 IRQ_TYPE_LEVEL_HIGH>;
+				clocks = <&clk NPCM7XX_CLK_APB5>;
+				clock-names = "clk_apb5";
+				resets = <&rstc NPCM7XX_RESET_IPSRST2 NPCM7XX_RESET_PSPI2>;
+				status = "disabled";
+			};
+
+			timer0: timer@8000 {
+				compatible = "nuvoton,npcm750-timer";
+				interrupts = <GIC_SPI 32 IRQ_TYPE_LEVEL_HIGH>;
+				reg = <0x8000 0x1C>;
+				clocks = <&clk NPCM7XX_CLK_TIMER>;
+			};
+
+			watchdog0: watchdog@801C {
+				compatible = "nuvoton,npcm750-wdt";
+				interrupts = <GIC_SPI 47 IRQ_TYPE_LEVEL_HIGH>;
+				reg = <0x801C 0x4>;
+				status = "disabled";
+				clocks = <&clk NPCM7XX_CLK_TIMER>;
+			};
+
+			watchdog1: watchdog@901C {
+				compatible = "nuvoton,npcm750-wdt";
+				interrupts = <GIC_SPI 48 IRQ_TYPE_LEVEL_HIGH>;
+				reg = <0x901C 0x4>;
+				status = "disabled";
+				clocks = <&clk NPCM7XX_CLK_TIMER>;
+			};
+
+			watchdog2: watchdog@a01C {
+				compatible = "nuvoton,npcm750-wdt";
+				interrupts = <GIC_SPI 49 IRQ_TYPE_LEVEL_HIGH>;
+				reg = <0xa01C 0x4>;
+				status = "disabled";
+				clocks = <&clk NPCM7XX_CLK_TIMER>;
+			};
+
+			serial0: serial@1000 {
+				compatible = "nuvoton,npcm750-uart";
+				reg = <0x1000 0x1000>;
+				clocks = <&clk NPCM7XX_CLK_UART>;
+				interrupts = <GIC_SPI 2 IRQ_TYPE_LEVEL_HIGH>;
+				reg-shift = <2>;
+				status = "disabled";
+			};
+
+			serial1: serial@2000 {
+				compatible = "nuvoton,npcm750-uart";
+				reg = <0x2000 0x1000>;
+				clocks = <&clk NPCM7XX_CLK_UART>;
+				interrupts = <GIC_SPI 3 IRQ_TYPE_LEVEL_HIGH>;
+				reg-shift = <2>;
+				status = "disabled";
+			};
+
+			serial2: serial@3000 {
+				compatible = "nuvoton,npcm750-uart";
+				reg = <0x3000 0x1000>;
+				clocks = <&clk NPCM7XX_CLK_UART>;
+				interrupts = <GIC_SPI 4 IRQ_TYPE_LEVEL_HIGH>;
+				reg-shift = <2>;
+				status = "disabled";
+			};
+
+			serial3: serial@4000 {
+				compatible = "nuvoton,npcm750-uart";
+				reg = <0x4000 0x1000>;
+				clocks = <&clk NPCM7XX_CLK_UART>;
+				interrupts = <GIC_SPI 5 IRQ_TYPE_LEVEL_HIGH>;
+				reg-shift = <2>;
+				status = "disabled";
+			};
+
+			rng: rng@b000 {
+				compatible = "nuvoton,npcm750-rng";
+				reg = <0xb000 0x8>;
+				status = "disabled";
+			};
+
+			adc: adc@c000 {
+				compatible = "nuvoton,npcm750-adc";
+				reg = <0xc000 0x8>;
+				interrupts = <GIC_SPI 0 IRQ_TYPE_LEVEL_HIGH>;
+				clocks = <&clk NPCM7XX_CLK_ADC>;
+				resets = <&rstc NPCM7XX_RESET_IPSRST1 NPCM7XX_RESET_ADC>;
+				status = "disabled";
+			};
+
+			pwm_fan: pwm-fan-controller@103000 {
+				#address-cells = <1>;
+				#size-cells = <0>;
+				compatible = "nuvoton,npcm750-pwm-fan";
+				reg = <0x103000 0x2000>, <0x180000 0x8000>;
+				reg-names = "pwm", "fan";
+				clocks = <&clk NPCM7XX_CLK_APB3>,
+					<&clk NPCM7XX_CLK_APB4>;
+				clock-names = "pwm","fan";
+				interrupts = <GIC_SPI 96 IRQ_TYPE_LEVEL_HIGH>,
+						<GIC_SPI 97 IRQ_TYPE_LEVEL_HIGH>,
+						<GIC_SPI 98 IRQ_TYPE_LEVEL_HIGH>,
+						<GIC_SPI 99 IRQ_TYPE_LEVEL_HIGH>,
+						<GIC_SPI 100 IRQ_TYPE_LEVEL_HIGH>,
+						<GIC_SPI 101 IRQ_TYPE_LEVEL_HIGH>,
+						<GIC_SPI 102 IRQ_TYPE_LEVEL_HIGH>,
+						<GIC_SPI 103 IRQ_TYPE_LEVEL_HIGH>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&pwm0_pins &pwm1_pins
+						&pwm2_pins &pwm3_pins
+						&pwm4_pins &pwm5_pins
+						&pwm6_pins &pwm7_pins
+						&fanin0_pins &fanin1_pins
+						&fanin2_pins &fanin3_pins
+						&fanin4_pins &fanin5_pins
+						&fanin6_pins &fanin7_pins
+						&fanin8_pins &fanin9_pins
+						&fanin10_pins &fanin11_pins
+						&fanin12_pins &fanin13_pins
+						&fanin14_pins &fanin15_pins>;
+				status = "disabled";
+			};
+
+			i2c0: i2c@80000 {
+				reg = <0x80000 0x1000>;
+				compatible = "nuvoton,npcm750-i2c";
+				#address-cells = <1>;
+				#size-cells = <0>;
+				clocks = <&clk NPCM7XX_CLK_APB2>;
+				interrupts = <GIC_SPI 64 IRQ_TYPE_LEVEL_HIGH>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&smb0_pins>;
+				status = "disabled";
+			};
+
+			i2c1: i2c@81000 {
+				reg = <0x81000 0x1000>;
+				compatible = "nuvoton,npcm750-i2c";
+				#address-cells = <1>;
+				#size-cells = <0>;
+				clocks = <&clk NPCM7XX_CLK_APB2>;
+				interrupts = <GIC_SPI 65 IRQ_TYPE_LEVEL_HIGH>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&smb1_pins>;
+				status = "disabled";
+			};
+
+			i2c2: i2c@82000 {
+				reg = <0x82000 0x1000>;
+				compatible = "nuvoton,npcm750-i2c";
+				#address-cells = <1>;
+				#size-cells = <0>;
+				clocks = <&clk NPCM7XX_CLK_APB2>;
+				interrupts = <GIC_SPI 66 IRQ_TYPE_LEVEL_HIGH>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&smb2_pins>;
+				status = "disabled";
+			};
+
+			i2c3: i2c@83000 {
+				reg = <0x83000 0x1000>;
+				compatible = "nuvoton,npcm750-i2c";
+				#address-cells = <1>;
+				#size-cells = <0>;
+				clocks = <&clk NPCM7XX_CLK_APB2>;
+				interrupts = <GIC_SPI 67 IRQ_TYPE_LEVEL_HIGH>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&smb3_pins>;
+				status = "disabled";
+			};
+
+			i2c4: i2c@84000 {
+				reg = <0x84000 0x1000>;
+				compatible = "nuvoton,npcm750-i2c";
+				#address-cells = <1>;
+				#size-cells = <0>;
+				clocks = <&clk NPCM7XX_CLK_APB2>;
+				interrupts = <GIC_SPI 68 IRQ_TYPE_LEVEL_HIGH>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&smb4_pins>;
+				status = "disabled";
+			};
+
+			i2c5: i2c@85000 {
+				reg = <0x85000 0x1000>;
+				compatible = "nuvoton,npcm750-i2c";
+				#address-cells = <1>;
+				#size-cells = <0>;
+				clocks = <&clk NPCM7XX_CLK_APB2>;
+				interrupts = <GIC_SPI 69 IRQ_TYPE_LEVEL_HIGH>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&smb5_pins>;
+				status = "disabled";
+			};
+
+			i2c6: i2c@86000 {
+				reg = <0x86000 0x1000>;
+				compatible = "nuvoton,npcm750-i2c";
+				#address-cells = <1>;
+				#size-cells = <0>;
+				clocks = <&clk NPCM7XX_CLK_APB2>;
+				interrupts = <GIC_SPI 70 IRQ_TYPE_LEVEL_HIGH>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&smb6_pins>;
+				status = "disabled";
+			};
+
+			i2c7: i2c@87000 {
+				reg = <0x87000 0x1000>;
+				compatible = "nuvoton,npcm750-i2c";
+				#address-cells = <1>;
+				#size-cells = <0>;
+				clocks = <&clk NPCM7XX_CLK_APB2>;
+				interrupts = <GIC_SPI 71 IRQ_TYPE_LEVEL_HIGH>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&smb7_pins>;
+				status = "disabled";
+			};
+
+			i2c8: i2c@88000 {
+				reg = <0x88000 0x1000>;
+				compatible = "nuvoton,npcm750-i2c";
+				#address-cells = <1>;
+				#size-cells = <0>;
+				clocks = <&clk NPCM7XX_CLK_APB2>;
+				interrupts = <GIC_SPI 72 IRQ_TYPE_LEVEL_HIGH>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&smb8_pins>;
+				status = "disabled";
+			};
+
+			i2c9: i2c@89000 {
+				reg = <0x89000 0x1000>;
+				compatible = "nuvoton,npcm750-i2c";
+				#address-cells = <1>;
+				#size-cells = <0>;
+				clocks = <&clk NPCM7XX_CLK_APB2>;
+				interrupts = <GIC_SPI 73 IRQ_TYPE_LEVEL_HIGH>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&smb9_pins>;
+				status = "disabled";
+			};
+
+			i2c10: i2c@8a000 {
+				reg = <0x8a000 0x1000>;
+				compatible = "nuvoton,npcm750-i2c";
+				#address-cells = <1>;
+				#size-cells = <0>;
+				clocks = <&clk NPCM7XX_CLK_APB2>;
+				interrupts = <GIC_SPI 74 IRQ_TYPE_LEVEL_HIGH>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&smb10_pins>;
+				status = "disabled";
+			};
+
+			i2c11: i2c@8b000 {
+				reg = <0x8b000 0x1000>;
+				compatible = "nuvoton,npcm750-i2c";
+				#address-cells = <1>;
+				#size-cells = <0>;
+				clocks = <&clk NPCM7XX_CLK_APB2>;
+				interrupts = <GIC_SPI 75 IRQ_TYPE_LEVEL_HIGH>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&smb11_pins>;
+				status = "disabled";
+			};
+
+			i2c12: i2c@8c000 {
+				reg = <0x8c000 0x1000>;
+				compatible = "nuvoton,npcm750-i2c";
+				#address-cells = <1>;
+				#size-cells = <0>;
+				clocks = <&clk NPCM7XX_CLK_APB2>;
+				interrupts = <GIC_SPI 76 IRQ_TYPE_LEVEL_HIGH>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&smb12_pins>;
+				status = "disabled";
+			};
+
+			i2c13: i2c@8d000 {
+				reg = <0x8d000 0x1000>;
+				compatible = "nuvoton,npcm750-i2c";
+				#address-cells = <1>;
+				#size-cells = <0>;
+				clocks = <&clk NPCM7XX_CLK_APB2>;
+				interrupts = <GIC_SPI 77 IRQ_TYPE_LEVEL_HIGH>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&smb13_pins>;
+				status = "disabled";
+			};
+
+			i2c14: i2c@8e000 {
+				reg = <0x8e000 0x1000>;
+				compatible = "nuvoton,npcm750-i2c";
+				#address-cells = <1>;
+				#size-cells = <0>;
+				clocks = <&clk NPCM7XX_CLK_APB2>;
+				interrupts = <GIC_SPI 78 IRQ_TYPE_LEVEL_HIGH>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&smb14_pins>;
+				status = "disabled";
+			};
+
+			i2c15: i2c@8f000 {
+				reg = <0x8f000 0x1000>;
+				compatible = "nuvoton,npcm750-i2c";
+				#address-cells = <1>;
+				#size-cells = <0>;
+				clocks = <&clk NPCM7XX_CLK_APB2>;
+				interrupts = <GIC_SPI 79 IRQ_TYPE_LEVEL_HIGH>;
+				pinctrl-names = "default";
+				pinctrl-0 = <&smb15_pins>;
+				status = "disabled";
+			};
+		};
+	};
+
+	pinctrl: pinctrl@f0800000 {
+		#address-cells = <1>;
+		#size-cells = <1>;
+		compatible = "nuvoton,npcm750-pinctrl", "syscon", "simple-mfd";
+		ranges = <0 0xf0010000 0x8000>;
+		gpio0: gpio@f0010000 {
+			gpio-controller;
+			#gpio-cells = <2>;
+			reg = <0x0 0x80>;
+			interrupts = <GIC_SPI 116 IRQ_TYPE_LEVEL_HIGH>;
+			gpio-ranges = <&pinctrl 0 0 32>;
+		};
+		gpio1: gpio@f0011000 {
+			gpio-controller;
+			#gpio-cells = <2>;
+			reg = <0x1000 0x80>;
+			interrupts = <GIC_SPI 117 IRQ_TYPE_LEVEL_HIGH>;
+			gpio-ranges = <&pinctrl 0 32 32>;
+		};
+		gpio2: gpio@f0012000 {
+			gpio-controller;
+			#gpio-cells = <2>;
+			reg = <0x2000 0x80>;
+			interrupts = <GIC_SPI 118 IRQ_TYPE_LEVEL_HIGH>;
+			gpio-ranges = <&pinctrl 0 64 32>;
+		};
+		gpio3: gpio@f0013000 {
+			gpio-controller;
+			#gpio-cells = <2>;
+			reg = <0x3000 0x80>;
+			interrupts = <GIC_SPI 119 IRQ_TYPE_LEVEL_HIGH>;
+			gpio-ranges = <&pinctrl 0 96 32>;
+		};
+		gpio4: gpio@f0014000 {
+			gpio-controller;
+			#gpio-cells = <2>;
+			reg = <0x4000 0x80>;
+			interrupts = <GIC_SPI 120 IRQ_TYPE_LEVEL_HIGH>;
+			gpio-ranges = <&pinctrl 0 128 32>;
+		};
+		gpio5: gpio@f0015000 {
+			gpio-controller;
+			#gpio-cells = <2>;
+			reg = <0x5000 0x80>;
+			interrupts = <GIC_SPI 121 IRQ_TYPE_LEVEL_HIGH>;
+			gpio-ranges = <&pinctrl 0 160 32>;
+		};
+		gpio6: gpio@f0016000 {
+			gpio-controller;
+			#gpio-cells = <2>;
+			reg = <0x6000 0x80>;
+			interrupts = <GIC_SPI 122 IRQ_TYPE_LEVEL_HIGH>;
+			gpio-ranges = <&pinctrl 0 192 32>;
+		};
+		gpio7: gpio@f0017000 {
+			gpio-controller;
+			#gpio-cells = <2>;
+			reg = <0x7000 0x80>;
+			interrupts = <GIC_SPI 123 IRQ_TYPE_LEVEL_HIGH>;
+			gpio-ranges = <&pinctrl 0 224 32>;
+		};
+
+		iox1_pins: iox1-pins {
+			groups = "iox1";
+			function = "iox1";
+		};
+		iox2_pins: iox2-pins {
+			groups = "iox2";
+			function = "iox2";
+		};
+		smb1d_pins: smb1d-pins {
+			groups = "smb1d";
+			function = "smb1d";
+		};
+		smb2d_pins: smb2d-pins {
+			groups = "smb2d";
+			function = "smb2d";
+		};
+		lkgpo1_pins: lkgpo1-pins {
+			groups = "lkgpo1";
+			function = "lkgpo1";
+		};
+		lkgpo2_pins: lkgpo2-pins {
+			groups = "lkgpo2";
+			function = "lkgpo2";
+		};
+		ioxh_pins: ioxh-pins {
+			groups = "ioxh";
+			function = "ioxh";
+		};
+		gspi_pins: gspi-pins {
+			groups = "gspi";
+			function = "gspi";
+		};
+		smb5b_pins: smb5b-pins {
+			groups = "smb5b";
+			function = "smb5b";
+		};
+		smb5c_pins: smb5c-pins {
+			groups = "smb5c";
+			function = "smb5c";
+		};
+		lkgpo0_pins: lkgpo0-pins {
+			groups = "lkgpo0";
+			function = "lkgpo0";
+		};
+		pspi2_pins: pspi2-pins {
+			groups = "pspi2";
+			function = "pspi2";
+		};
+		smb4den_pins: smb4den-pins {
+			groups = "smb4den";
+			function = "smb4den";
+		};
+		smb4b_pins: smb4b-pins {
+			groups = "smb4b";
+			function = "smb4b";
+		};
+		smb4c_pins: smb4c-pins {
+			groups = "smb4c";
+			function = "smb4c";
+		};
+		smb15_pins: smb15-pins {
+			groups = "smb15";
+			function = "smb15";
+		};
+		smb4d_pins: smb4d-pins {
+			groups = "smb4d";
+			function = "smb4d";
+		};
+		smb14_pins: smb14-pins {
+			groups = "smb14";
+			function = "smb14";
+		};
+		smb5_pins: smb5-pins {
+			groups = "smb5";
+			function = "smb5";
+		};
+		smb4_pins: smb4-pins {
+			groups = "smb4";
+			function = "smb4";
+		};
+		smb3_pins: smb3-pins {
+			groups = "smb3";
+			function = "smb3";
+		};
+		spi0cs1_pins: spi0cs1-pins {
+			groups = "spi0cs1";
+			function = "spi0cs1";
+		};
+		spi0cs2_pins: spi0cs2-pins {
+			groups = "spi0cs2";
+			function = "spi0cs2";
+		};
+		spi0cs3_pins: spi0cs3-pins {
+			groups = "spi0cs3";
+			function = "spi0cs3";
+		};
+		smb3c_pins: smb3c-pins {
+			groups = "smb3c";
+			function = "smb3c";
+		};
+		smb3b_pins: smb3b-pins {
+			groups = "smb3b";
+			function = "smb3b";
+		};
+		bmcuart0a_pins: bmcuart0a-pins {
+			groups = "bmcuart0a";
+			function = "bmcuart0a";
+		};
+		uart1_pins: uart1-pins {
+			groups = "uart1";
+			function = "uart1";
+		};
+		jtag2_pins: jtag2-pins {
+			groups = "jtag2";
+			function = "jtag2";
+		};
+		bmcuart1_pins: bmcuart1-pins {
+			groups = "bmcuart1";
+			function = "bmcuart1";
+		};
+		uart2_pins: uart2-pins {
+			groups = "uart2";
+			function = "uart2";
+		};
+		bmcuart0b_pins: bmcuart0b-pins {
+			groups = "bmcuart0b";
+			function = "bmcuart0b";
+		};
+		r1err_pins: r1err-pins {
+			groups = "r1err";
+			function = "r1err";
+		};
+		r1md_pins: r1md-pins {
+			groups = "r1md";
+			function = "r1md";
+		};
+		smb3d_pins: smb3d-pins {
+			groups = "smb3d";
+			function = "smb3d";
+		};
+		fanin0_pins: fanin0-pins {
+			groups = "fanin0";
+			function = "fanin0";
+		};
+		fanin1_pins: fanin1-pins {
+			groups = "fanin1";
+			function = "fanin1";
+		};
+		fanin2_pins: fanin2-pins {
+			groups = "fanin2";
+			function = "fanin2";
+		};
+		fanin3_pins: fanin3-pins {
+			groups = "fanin3";
+			function = "fanin3";
+		};
+		fanin4_pins: fanin4-pins {
+			groups = "fanin4";
+			function = "fanin4";
+		};
+		fanin5_pins: fanin5-pins {
+			groups = "fanin5";
+			function = "fanin5";
+		};
+		fanin6_pins: fanin6-pins {
+			groups = "fanin6";
+			function = "fanin6";
+		};
+		fanin7_pins: fanin7-pins {
+			groups = "fanin7";
+			function = "fanin7";
+		};
+		fanin8_pins: fanin8-pins {
+			groups = "fanin8";
+			function = "fanin8";
+		};
+		fanin9_pins: fanin9-pins {
+			groups = "fanin9";
+			function = "fanin9";
+		};
+		fanin10_pins: fanin10-pins {
+			groups = "fanin10";
+			function = "fanin10";
+		};
+		fanin11_pins: fanin11-pins {
+			groups = "fanin11";
+			function = "fanin11";
+		};
+		fanin12_pins: fanin12-pins {
+			groups = "fanin12";
+			function = "fanin12";
+		};
+		fanin13_pins: fanin13-pins {
+			groups = "fanin13";
+			function = "fanin13";
+		};
+		fanin14_pins: fanin14-pins {
+			groups = "fanin14";
+			function = "fanin14";
+		};
+		fanin15_pins: fanin15-pins {
+			groups = "fanin15";
+			function = "fanin15";
+		};
+		pwm0_pins: pwm0-pins {
+			groups = "pwm0";
+			function = "pwm0";
+		};
+		pwm1_pins: pwm1-pins {
+			groups = "pwm1";
+			function = "pwm1";
+		};
+		pwm2_pins: pwm2-pins {
+			groups = "pwm2";
+			function = "pwm2";
+		};
+		pwm3_pins: pwm3-pins {
+			groups = "pwm3";
+			function = "pwm3";
+		};
+		r2_pins: r2-pins {
+			groups = "r2";
+			function = "r2";
+		};
+		r2err_pins: r2err-pins {
+			groups = "r2err";
+			function = "r2err";
+		};
+		r2md_pins: r2md-pins {
+			groups = "r2md";
+			function = "r2md";
+		};
+		ga20kbc_pins: ga20kbc-pins {
+			groups = "ga20kbc";
+			function = "ga20kbc";
+		};
+		smb5d_pins: smb5d-pins {
+			groups = "smb5d";
+			function = "smb5d";
+		};
+		lpc_pins: lpc-pins {
+			groups = "lpc";
+			function = "lpc";
+		};
+		espi_pins: espi-pins {
+			groups = "espi";
+			function = "espi";
+		};
+		rg1_pins: rg1-pins {
+			groups = "rg1";
+			function = "rg1";
+		};
+		rg1mdio_pins: rg1mdio-pins {
+			groups = "rg1mdio";
+			function = "rg1mdio";
+		};
+		rg2_pins: rg2-pins {
+			groups = "rg2";
+			function = "rg2";
+		};
+		ddr_pins: ddr-pins {
+			groups = "ddr";
+			function = "ddr";
+		};
+		smb0_pins: smb0-pins {
+			groups = "smb0";
+			function = "smb0";
+		};
+		smb1_pins: smb1-pins {
+			groups = "smb1";
+			function = "smb1";
+		};
+		smb2_pins: smb2-pins {
+			groups = "smb2";
+			function = "smb2";
+		};
+		smb2c_pins: smb2c-pins {
+			groups = "smb2c";
+			function = "smb2c";
+		};
+		smb2b_pins: smb2b-pins {
+			groups = "smb2b";
+			function = "smb2b";
+		};
+		smb1c_pins: smb1c-pins {
+			groups = "smb1c";
+			function = "smb1c";
+		};
+		smb1b_pins: smb1b-pins {
+			groups = "smb1b";
+			function = "smb1b";
+		};
+		smb8_pins: smb8-pins {
+			groups = "smb8";
+			function = "smb8";
+		};
+		smb9_pins: smb9-pins {
+			groups = "smb9";
+			function = "smb9";
+		};
+		smb10_pins: smb10-pins {
+			groups = "smb10";
+			function = "smb10";
+		};
+		smb11_pins: smb11-pins {
+			groups = "smb11";
+			function = "smb11";
+		};
+		sd1_pins: sd1-pins {
+			groups = "sd1";
+			function = "sd1";
+		};
+		sd1pwr_pins: sd1pwr-pins {
+			groups = "sd1pwr";
+			function = "sd1pwr";
+		};
+		pwm4_pins: pwm4-pins {
+			groups = "pwm4";
+			function = "pwm4";
+		};
+		pwm5_pins: pwm5-pins {
+			groups = "pwm5";
+			function = "pwm5";
+		};
+		pwm6_pins: pwm6-pins {
+			groups = "pwm6";
+			function = "pwm6";
+		};
+		pwm7_pins: pwm7-pins {
+			groups = "pwm7";
+			function = "pwm7";
+		};
+		mmc8_pins: mmc8-pins {
+			groups = "mmc8";
+			function = "mmc8";
+		};
+		mmc_pins: mmc-pins {
+			groups = "mmc";
+			function = "mmc";
+		};
+		mmcwp_pins: mmcwp-pins {
+			groups = "mmcwp";
+			function = "mmcwp";
+		};
+		mmccd_pins: mmccd-pins {
+			groups = "mmccd";
+			function = "mmccd";
+		};
+		mmcrst_pins: mmcrst-pins {
+			groups = "mmcrst";
+			function = "mmcrst";
+		};
+		clkout_pins: clkout-pins {
+			groups = "clkout";
+			function = "clkout";
+		};
+		serirq_pins: serirq-pins {
+			groups = "serirq";
+			function = "serirq";
+		};
+		lpcclk_pins: lpcclk-pins {
+			groups = "lpcclk";
+			function = "lpcclk";
+		};
+		scipme_pins: scipme-pins {
+			groups = "scipme";
+			function = "scipme";
+		};
+		sci_pins: sci-pins {
+			groups = "sci";
+			function = "sci";
+		};
+		smb6_pins: smb6-pins {
+			groups = "smb6";
+			function = "smb6";
+		};
+		smb7_pins: smb7-pins {
+			groups = "smb7";
+			function = "smb7";
+		};
+		pspi1_pins: pspi1-pins {
+			groups = "pspi1";
+			function = "pspi1";
+		};
+		faninx_pins: faninx-pins {
+			groups = "faninx";
+			function = "faninx";
+		};
+		r1_pins: r1-pins {
+			groups = "r1";
+			function = "r1";
+		};
+		spi3_pins: spi3-pins {
+			groups = "spi3";
+			function = "spi3";
+		};
+		spi3cs1_pins: spi3cs1-pins {
+			groups = "spi3cs1";
+			function = "spi3cs1";
+		};
+		spi3quad_pins: spi3quad-pins {
+			groups = "spi3quad";
+			function = "spi3quad";
+		};
+		spi3cs2_pins: spi3cs2-pins {
+			groups = "spi3cs2";
+			function = "spi3cs2";
+		};
+		spi3cs3_pins: spi3cs3-pins {
+			groups = "spi3cs3";
+			function = "spi3cs3";
+		};
+		nprd_smi_pins: nprd-smi-pins {
+			groups = "nprd_smi";
+			function = "nprd_smi";
+		};
+		smb0b_pins: smb0b-pins {
+			groups = "smb0b";
+			function = "smb0b";
+		};
+		smb0c_pins: smb0c-pins {
+			groups = "smb0c";
+			function = "smb0c";
+		};
+		smb0den_pins: smb0den-pins {
+			groups = "smb0den";
+			function = "smb0den";
+		};
+		smb0d_pins: smb0d-pins {
+			groups = "smb0d";
+			function = "smb0d";
+		};
+		ddc_pins: ddc-pins {
+			groups = "ddc";
+			function = "ddc";
+		};
+		rg2mdio_pins: rg2mdio-pins {
+			groups = "rg2mdio";
+			function = "rg2mdio";
+		};
+		wdog1_pins: wdog1-pins {
+			groups = "wdog1";
+			function = "wdog1";
+		};
+		wdog2_pins: wdog2-pins {
+			groups = "wdog2";
+			function = "wdog2";
+		};
+		smb12_pins: smb12-pins {
+			groups = "smb12";
+			function = "smb12";
+		};
+		smb13_pins: smb13-pins {
+			groups = "smb13";
+			function = "smb13";
+		};
+		spix_pins: spix-pins {
+			groups = "spix";
+			function = "spix";
+		};
+		spixcs1_pins: spixcs1-pins {
+			groups = "spixcs1";
+			function = "spixcs1";
+		};
+		clkreq_pins: clkreq-pins {
+			groups = "clkreq";
+			function = "clkreq";
+		};
+		hgpio0_pins: hgpio0-pins {
+			groups = "hgpio0";
+			function = "hgpio0";
+		};
+		hgpio1_pins: hgpio1-pins {
+			groups = "hgpio1";
+			function = "hgpio1";
+		};
+		hgpio2_pins: hgpio2-pins {
+			groups = "hgpio2";
+			function = "hgpio2";
+		};
+		hgpio3_pins: hgpio3-pins {
+			groups = "hgpio3";
+			function = "hgpio3";
+		};
+		hgpio4_pins: hgpio4-pins {
+			groups = "hgpio4";
+			function = "hgpio4";
+		};
+		hgpio5_pins: hgpio5-pins {
+			groups = "hgpio5";
+			function = "hgpio5";
+		};
+		hgpio6_pins: hgpio6-pins {
+			groups = "hgpio6";
+			function = "hgpio6";
+		};
+		hgpio7_pins: hgpio7-pins {
+			groups = "hgpio7";
+			function = "hgpio7";
+		};
+	};
+};
diff --git a/arch/arm/dts/nuvoton-npcm750-buv-pincfg.dtsi b/arch/arm/dts/nuvoton-npcm750-buv-pincfg.dtsi
new file mode 100644
index 0000000000..6c0b61aabc
--- /dev/null
+++ b/arch/arm/dts/nuvoton-npcm750-buv-pincfg.dtsi
@@ -0,0 +1,132 @@
+// SPDX-License-Identifier: GPL-2.0+
+// Copyright (c) 2021 Nuvoton Technology tomer.maimon@nuvoton.com
+
+/ {
+	pinctrl: pinctrl@f0800000 {
+		gpio138o_pins: gpio138o-pins {
+			pins = "GPIO138/SD1DT2";
+			output-high;
+		};
+		gpio139o_pins: gpio139o-pins {
+			pins = "GPIO139/SD1DT3";
+			output-high;
+		};
+		gpio89o_pins: gpio89o-pins {
+			pins = "GPIO89/R2CRSDV";
+			output-high;
+		};
+		gpio143o_pins: gpio143o-pins {
+			pins = "GPIO143/SD1CD/SD1PWR";
+			output-high;
+		};
+		gpio9o_pins: gpio9o-pins {
+			pins = "GPIO9/LKGPO2";
+			output-high;
+		};
+		gpio231o_pins: gpio231o-pins {
+			pins = "GPIO231/nCLKREQ";
+			output-high;
+		};
+		gpio140o_pins: gpio140o-pins {
+			pins = "GPIO140/SD1CLK";
+			output-high;
+		};
+		gpio142o_pins: gpio142o-pins {
+			pins = "GPIO142/SD1CMD";
+			output-high;
+		};
+		gpio90o_pins: gpio90o0-pins {
+			pins = "GPIO90/R2RXERR";
+			output-high;
+		};
+		gpio88o_pins: gpio88o-pins {
+			pins = "GPIO88/R2RXD1";
+			output-high;
+		};
+		gpio141o_pins: gpio141o-pins {
+			pins = "GPIO141/SD1WP";
+			output-high;
+		};
+		gpio87o_pins: gpio87o-pins {
+			pins = "GPIO87/R2RXD0";
+			output-high;
+		};
+		gpio11o_pins: gpio11o-pins {
+			pins = "GPIO11/IOXHCK";
+			output-high;
+		};
+		gpio24o_pins: gpio24o-pins {
+			pins = "GPIO24/IOXHDO";
+			output-high;
+		};
+		gpio137o_pins: gpio137o-pins {
+			pins = "GPIO137/SD1DT1";
+			output-high;
+		};
+		gpio25o_pins: gpio25o-pins {
+			pins = "GPIO25/IOXHDI";
+			output-high;
+		};
+		gpio17_pins: gpio17-pins {
+			pins = "GPIO17/PSPI2DI/SMB4DEN";
+			bias-disable;
+			input-enable;
+		};
+		gpio18o_pins: gpio18o-pins {
+			pins = "GPIO18/PSPI2D0/SMB4BSDA";
+			bias-disable;
+			output-high;
+		};
+		gpio19ol_pins: gpio19ol-pins {
+			pins = "GPIO19/PSPI2CK/SMB4BSCL";
+			bias-disable;
+			output-low;
+		};
+		gpio84_pins: gpio84-pins {
+			pins = "GPIO84/R2TXD0";
+			bias-disable;
+			input-enable;
+		};
+		gpio85_pins: gpio85-pins {
+			pins = "GPIO85/R2TXD1";
+			bias-disable;
+			input-enable;
+		};
+		gpio122_pins: gpio122-pins {
+			pins = "GPIO122/SMB2BSDA";
+			bias-disable;
+			input-enable;
+		};
+		gpio124_pins: gpio124-pins {
+			pins = "GPIO124/SMB1CSDA";
+			bias-disable;
+			input-enable;
+		};
+		gpio125_pins: gpio125-pins {
+			pins = "GPIO125/SMB1CSCL";
+			bias-disable;
+			input-enable;
+		};
+		gpio126_pins: gpio126-pins {
+			pins = "GPIO126/SMB1BSDA";
+			bias-disable;
+			input-enable;
+		};
+		gpio4_pins: gpio4-pins {
+			pins = "GPIO4/IOX2DI/SMB1DSDA";
+			slew-rate = <1>;
+		};
+		gpio5_pins: gpio5-pins {
+			pins = "GPIO5/IOX2LD/SMB1DSCL";
+			slew-rate = <1>;
+		};
+		gpio6_pins: gpio6-pins {
+			pins = "GPIO6/IOX2CK/SMB2DSDA";
+			slew-rate = <1>;
+		};
+		gpio7_pins: gpio7o-pins {
+			pins = "GPIO7/IOX2D0/SMB2DSCL";
+			slew-rate = <1>;
+		};
+	};
+};
diff --git a/arch/arm/dts/nuvoton-npcm750-buv.dts b/arch/arm/dts/nuvoton-npcm750-buv.dts
new file mode 100644
index 0000000000..19344ac9a7
--- /dev/null
+++ b/arch/arm/dts/nuvoton-npcm750-buv.dts
@@ -0,0 +1,198 @@
+// SPDX-License-Identifier: GPL-2.0
+/dts-v1/;
+
+#include "nuvoton-npcm750.dtsi"
+#include "nuvoton-npcm750-buv-pincfg.dtsi"
+
+/ {
+	model = "Nuvoton npcm750 Development Board";
+	compatible = "npcm750,runbmc";
+
+	chosen {
+		stdout-path = &serial0;
+		tick-timer = &timer0;
+	};
+
+	aliases {
+		serial0 = &serial0;
+		serial1 = &serial1;
+		serial2 = &serial2;
+		serial3 = &serial3;
+		i2c0 = &i2c0;
+		i2c1 = &i2c1;
+		i2c2 = &i2c2;
+		i2c3 = &i2c3;
+		i2c4 = &i2c4;
+		i2c5 = &i2c5;
+		i2c6 = &i2c6;
+		i2c7 = &i2c7;
+		i2c8 = &i2c8;
+		i2c9 = &i2c9;
+		i2c10 = &i2c10;
+		i2c11 = &i2c11;
+		i2c12 = &i2c12;
+		i2c13 = &i2c13;
+		i2c14 = &i2c14;
+		i2c15 = &i2c15;
+		spi0 = &fiu0;
+		spi1 = &fiu3;
+		spi2 = &fiux;
+		spi3 = &spi0;
+		spi4 = &spi1;
+		mmc0 = &sdhci0;
+		gpio0 = &gpio0;
+		gpio1 = &gpio1;
+		gpio2 = &gpio2;
+		gpio3 = &gpio3;
+		gpio4 = &gpio4;
+		gpio5 = &gpio5;
+		gpio6 = &gpio6;
+		gpio7 = &gpio7;
+		usb0 = &udc0;
+		eth0 = &emc0;
+		eth1 = &gmac0;
+	};
+};
+
+&udc0 {
+	status = "okay";
+	phys = <&usbphy1 0>;
+};
+
+&serial0 {
+	status = "okay";
+	clock-frequency = <24000000>;
+};
+
+&sha {
+	status = "okay";
+};
+
+&aes {
+	status = "okay";
+};
+
+&rng {
+	status = "okay";
+};
+
+&fiu0 {
+	pinctrl-names = "default";
+	pinctrl-0 = <&spi0cs1_pins>;
+	status = "okay";
+	spi_flash@0 {
+		compatible = "jedec,spi-nor";
+		reg = <0>;
+	};
+	spi_flash@1 {
+		compatible = "jedec,spi-nor";
+		reg = <1>;
+	};
+};
+
+&fiu3 {
+	pinctrl-0 = <&spi3_pins>;
+	status = "okay";
+	spi-nor@0 {
+		compatible = "jedec,spi-nor";
+		reg = <0>;
+	};
+};
+
+&i2c0 {
+	status = "okay";
+};
+
+&i2c1 {
+	status = "okay";
+};
+
+&i2c2 {
+	status = "okay";
+};
+
+&i2c3 {
+	status = "okay";
+};
+
+&i2c4 {
+	status = "okay";
+};
+
+&i2c5 {
+	status = "okay";
+};
+
+&i2c6 {
+	status = "okay";
+};
+
+&i2c7 {
+	status = "okay";
+};
+
+&i2c8 {
+	status = "okay";
+};
+
+&i2c9 {
+	status = "okay";
+};
+
+&i2c10 {
+	status = "okay";
+};
+
+&i2c11 {
+	status = "okay";
+};
+
+&i2c12 {
+	status = "okay";
+};
+
+&i2c13 {
+	status = "okay";
+};
+
+&ehci1 {
+	status = "okay";
+	phys = <&usbphy2 3>;
+};
+
+&otp {
+	status = "okay";
+};
+
+&usbphy1 {
+	status = "okay";
+};
+
+&usbphy2 {
+	status = "okay";
+};
+
+&gmac0 {
+	phy-mode = "rgmii-id";
+	snps,eee-force-disable;
+	status = "okay";
+};
+
+&emc0 {
+	status = "okay";
+	pinctrl-names = "default";
+	pinctrl-0 = <&r1_pins
+			&r1err_pins>;
+	fixed-link {
+			speed = <100>;
+			full-dulpex;
+	};
+};
+
+&sdhci0 {
+	status = "okay";
+};
+
+&pinctrl {
+	status = "okay";
+};
diff --git a/arch/arm/dts/nuvoton-npcm750.dtsi b/arch/arm/dts/nuvoton-npcm750.dtsi
new file mode 100644
index 0000000000..9662fca31a
--- /dev/null
+++ b/arch/arm/dts/nuvoton-npcm750.dtsi
@@ -0,0 +1,63 @@
+// SPDX-License-Identifier: GPL-2.0
+// Copyright (c) 2018 Nuvoton Technology tomer.maimon@nuvoton.com
+// Copyright 2018 Google, Inc.
+
+#include "nuvoton-common-npcm7xx.dtsi"
+#include "nuvoton-npcm7xx-uboot.dtsi"
+
+/ {
+	#address-cells = <1>;
+	#size-cells = <1>;
+	interrupt-parent = <&gic>;
+
+	cpus {
+		#address-cells = <1>;
+		#size-cells = <0>;
+		enable-method = "nuvoton,npcm750-smp";
+
+		cpu@0 {
+			device_type = "cpu";
+			compatible = "arm,cortex-a9";
+			clocks = <&clk NPCM7XX_CLK_CPU>;
+			clock-names = "clk_cpu";
+			reg = <0>;
+			next-level-cache = <&l2>;
+		};
+
+		cpu@1 {
+			device_type = "cpu";
+			compatible = "arm,cortex-a9";
+			clocks = <&clk NPCM7XX_CLK_CPU>;
+			clock-names = "clk_cpu";
+			reg = <1>;
+			next-level-cache = <&l2>;
+		};
+	};
+
+	soc {
+		timer@3fe600 {
+			compatible = "arm,cortex-a9-twd-timer";
+			reg = <0x3fe600 0x20>;
+			interrupts = <GIC_PPI 13 (GIC_CPU_MASK_SIMPLE(2) |
+						  IRQ_TYPE_LEVEL_HIGH)>;
+			clocks = <&clk NPCM7XX_CLK_AHB>;
+		};
+	};
+
+	ahb {
+		gmac1: eth@f0804000 {
+			device_type = "network";
+			compatible = "snps,dwmac";
+			reg = <0xf0804000 0x2000>;
+			interrupts = <GIC_SPI 17 IRQ_TYPE_LEVEL_HIGH>;
+			interrupt-names = "macirq";
+			ethernet = <1>;
+			clocks	= <&clk_rg2refck>, <&clk NPCM7XX_CLK_AHB>;
+			clock-names = "stmmaceth", "clk_gmac";
+			pinctrl-names = "default";
+			pinctrl-0 = <&rg2_pins
+					&rg2mdio_pins>;
+			status = "disabled";
+		};
+	};
+};
diff --git a/arch/arm/dts/nuvoton-npcm7xx-uboot.dtsi b/arch/arm/dts/nuvoton-npcm7xx-uboot.dtsi
new file mode 100644
index 0000000000..d41b9b6199
--- /dev/null
+++ b/arch/arm/dts/nuvoton-npcm7xx-uboot.dtsi
@@ -0,0 +1,263 @@
+// SPDX-License-Identifier: GPL-2.0
+
+/ {
+	#address-cells = <1>;
+	#size-cells = <1>;
+	interrupt-parent = <&gic>;
+
+	ahb {
+		udc0:udc@f0830100 {
+			compatible = "nuvoton,npcm750-udc";
+			reg = <0xf0830100 0x200
+			       0xfffd0000 0x800>;
+			interrupts = <GIC_SPI 51 IRQ_TYPE_LEVEL_HIGH>;
+			resets = <&rstc NPCM7XX_RESET_IPSRST3 NPCM7XX_RESET_UDC0>;
+			status = "disabled";
+			clocks = <&clk NPCM7XX_CLK_SU>;
+			clock-names = "clk_usb_bridge";
+		};
+
+		udc1:udc@f0831100 {
+			compatible = "nuvoton,npcm750-udc";
+			reg = <0xf0831100 0x200
+			       0xfffd0800 0x800>;
+			interrupts = <GIC_SPI 52 IRQ_TYPE_LEVEL_HIGH>;
+			status = "disabled";
+			clocks = <&clk NPCM7XX_CLK_SU>;
+			clock-names = "clk_usb_bridge";
+		};
+
+		udc2: udc@f0832100 {
+			compatible = "nuvoton,npcm750-udc";
+			reg = <0xf0832100 0x200
+			       0xfffd1000 0x800>;
+			interrupts = <GIC_SPI 53 IRQ_TYPE_LEVEL_HIGH>;
+			status = "disabled";
+			clocks = <&clk NPCM7XX_CLK_SU>;
+			clock-names = "clk_usb_bridge";
+		};
+
+		udc3: udc@f0833100 {
+			compatible = "nuvoton,npcm750-udc";
+			reg = <0xf0833100 0x200
+			       0xfffd1800 0x800>;
+			interrupts = <GIC_SPI 54 IRQ_TYPE_LEVEL_HIGH>;
+			status = "disabled";
+			clocks = <&clk NPCM7XX_CLK_SU>;
+			clock-names = "clk_usb_bridge";
+		};
+
+		udc4: udc@f0834100 {
+			compatible = "nuvoton,npcm750-udc";
+			reg = <0xf0834100 0x200
+			       0xfffd2000 0x800>;
+			interrupts = <GIC_SPI 55 IRQ_TYPE_LEVEL_HIGH>;
+			status = "disabled";
+			clocks = <&clk NPCM7XX_CLK_SU>;
+			clock-names = "clk_usb_bridge";
+		};
+
+		udc5: udc@f0835100 {
+			compatible = "nuvoton,npcm750-udc";
+			reg = <0xf0835100 0x200
+			       0xfffd2800 0x800>;
+			interrupts = <GIC_SPI 56 IRQ_TYPE_LEVEL_HIGH>;
+			status = "disabled";
+			clocks = <&clk NPCM7XX_CLK_SU>;
+			clock-names = "clk_usb_bridge";
+		};
+
+		udc6: udc@f0836100 {
+			compatible = "nuvoton,npcm750-udc";
+			reg = <0xf0836100 0x200
+			       0xfffd3000 0x800>;
+			interrupts = <GIC_SPI 57 IRQ_TYPE_LEVEL_HIGH>;
+			status = "disabled";
+			clocks = <&clk NPCM7XX_CLK_SU>;
+			clock-names = "clk_usb_bridge";
+		};
+
+		udc7: udc@f0837100 {
+			compatible = "nuvoton,npcm750-udc";
+			reg = <0xf0837100 0x200
+			       0xfffd3800 0x800>;
+			interrupts = <GIC_SPI 58 IRQ_TYPE_LEVEL_HIGH>;
+			status = "disabled";
+			clocks = <&clk NPCM7XX_CLK_SU>;
+			clock-names = "clk_usb_bridge";
+		};
+
+		udc8: udc@f0838100 {
+			compatible = "nuvoton,npcm750-udc";
+			reg = <0xf0838100 0x200
+			       0xfffd4000 0x800>;
+			interrupts = <GIC_SPI 59 IRQ_TYPE_LEVEL_HIGH>;
+			status = "disabled";
+			clocks = <&clk NPCM7XX_CLK_SU>;
+			clock-names = "clk_usb_bridge";
+		};
+
+		udc9: udc@f0839100 {
+			compatible = "nuvoton,npcm750-udc";
+			reg = <0xf0839100 0x200
+			       0xfffd4800 0x800>;
+			interrupts = <GIC_SPI 60 IRQ_TYPE_LEVEL_HIGH>;
+			status = "disabled";
+			clocks = <&clk NPCM7XX_CLK_SU>;
+			clock-names = "clk_usb_bridge";
+		};
+
+		emc0: eth@f0825000 {
+			device_type = "network";
+			compatible = "nuvoton,npcm750-emc";
+			reg = <0xf0825000 0x1000>;
+			phy-mode = "rmii";
+			id = <0>;
+			interrupts = <GIC_SPI 16 IRQ_TYPE_LEVEL_HIGH>,
+					<GIC_SPI 15 IRQ_TYPE_LEVEL_HIGH>;
+			clocks = <&clk NPCM7XX_CLK_AHB>;
+			clock-names = "clk_emc";
+			resets = <&rstc NPCM7XX_RESET_IPSRST1 NPCM7XX_RESET_EMAC1>;
+			pinctrl-names = "default";
+			pinctrl-0 = <&r1_pins
+					&r1md_pins>;
+			status = "disabled";
+		};
+
+		ohci1: ohci@f0807000 {
+			compatible = "nuvoton,npcm750-ohci";
+			reg = <0xf0807000 0x1000>;
+			interrupts = <GIC_SPI 62 IRQ_TYPE_LEVEL_HIGH>;
+			resets = <&rstc NPCM7XX_RESET_IPSRST2 NPCM7XX_RESET_USBH1>;
+			status = "disabled";
+		};
+
+		usbphy {
+			compatible = "simple-bus", "nuvoton,npcm750-usb-phy";
+			#address-cells = <1>;
+			#size-cells = <0>;
+			syscon = <&gcr>;
+			usbphy1: usbphy1 {
+				compatible = "nuvoton,npcm750-usb-phy";
+				#phy-cells = <1>;
+				reg = <1>;
+				resets = <&rstc NPCM7XX_RESET_IPSRST3 NPCM7XX_RESET_USBPHY1>;
+				status = "disabled";
+			};
+			usbphy2: usbphy2 {
+				compatible = "nuvoton,npcm750-usb-phy";
+				#phy-cells = <1>;
+				reg = <2>;
+				resets =<&rstc NPCM7XX_RESET_IPSRST3 NPCM7XX_RESET_USBPHY2>;
+				status = "disabled";
+			};
+		};
+
+		sdhci0: sdhci0@f0842000 {
+			compatible = "nuvoton,npcm750-sdhci-eMMC";
+			reg = <0xf0842000 0x200>;
+			index = <0x0>;
+			bus-width = <0x8>;
+			interrupts = <GIC_SPI 27 IRQ_TYPE_LEVEL_HIGH>;
+			clocks = <&clk NPCM7XX_CLK_SDHC>;
+			clock-frequency = <50000000>;
+			pinctrl-names = "default";
+			pinctrl-0 = <&mmc_pins
+				&mmc8_pins>;
+			status = "disabled";
+		};
+
+		sdhci1: sdhci1@f0840000 {
+			compatible = "nuvoton,npcm750-sdhci-SD";
+			reg = <0xf0840000 0x2000>;
+			index = <0x1>;
+			bus-width = <0x4>;
+			pinctrl-names = "default";
+			pinctrl-0 = <&sd1_pins>;
+			status = "disabled";
+		};
+
+		aes: aes@f0858000 {
+			compatible = "nuvoton,npcm750-aes";
+			reg = <0xf0858000 0x1000>;
+			clocks = <&clk NPCM7XX_CLK_AHB>;
+			clock-names = "clk_ahb";
+			status = "disabled";
+		};
+
+		sha: sha@f085a000 {
+			compatible = "nuvoton,npcm750-sha";
+			reg = <0xf085a000 0x1000>;
+			clocks = <&clk NPCM7XX_CLK_AHB>;
+			clock-names = "clk_ahb";
+			status = "disabled";
+		};
+
+		//ehci1
+		usb@f0806000 {
+			resets = <&rstc NPCM7XX_RESET_IPSRST2 NPCM7XX_RESET_USBH1>;
+		};
+
+		apb {
+			otp:otp@189000 {
+				compatible = "nuvoton,npcm750-otp";
+				reg = <0x189000 0x1000
+					   0x18a000 0x1000>;
+				status = "disabled";
+				clocks = <&clk NPCM7XX_CLK_APB4>;
+				clock-names = "clk_apb4";
+			};
+
+			rng@b000 {
+				clocks = <&clk NPCM7XX_CLK_APB1>;
+			};
+
+			gfxi: gfxi@e000 {
+				compatible = "nuvoton,npcm750-gfxi", "syscon",
+						"simple-mfd";
+				reg = <0xe000 0x100>;
+			};
+
+			gpio@f0010000 {
+				compatible = "nuvoton,npcm-gpio";
+				gpio-bank-name = "gpio0";
+			};
+
+			gpio@f0011000 {
+				compatible = "nuvoton,npcm-gpio";
+				gpio-bank-name = "gpio1";
+			};
+
+			gpio@f0012000 {
+				compatible = "nuvoton,npcm-gpio";
+				gpio-bank-name = "gpio2";
+			};
+
+			gpio@f0013000 {
+				compatible = "nuvoton,npcm-gpio";
+				gpio-bank-name = "gpio3";
+			};
+
+			gpio@f0014000 {
+				compatible = "nuvoton,npcm-gpio";
+				gpio-bank-name = "gpio4";
+			};
+
+			gpio@f0015000 {
+				compatible = "nuvoton,npcm-gpio";
+				gpio-bank-name = "gpio5";
+			};
+
+			gpio@f0016000 {
+				compatible = "nuvoton,npcm-gpio";
+				gpio-bank-name = "gpio6";
+			};
+
+			gpio@f0017000 {
+				compatible = "nuvoton,npcm-gpio";
+				gpio-bank-name = "gpio7";
+			};
+		};
+	};
+};
+
-- 
2.17.1


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

* [PATCH v1 3/6] timer: npcm: Add NPCM timer support
  2022-04-06  7:57 [PATCH v1 0/6] Add Nuvoton NPCM750 support Jim Liu
  2022-04-06  7:57 ` [PATCH v1 1/6] ARM: configs: Add defconfig for Nuvoton NPCM750 Jim Liu
  2022-04-06  7:57 ` [PATCH v1 2/6] ARM: dts: Add Nuvoton NPCM750 device tree Jim Liu
@ 2022-04-06  7:57 ` Jim Liu
  2022-04-06  7:57 ` [PATCH v1 4/6] serial: npcm: Add support for Nuvoton NPCM SoCs Jim Liu
                   ` (3 subsequent siblings)
  6 siblings, 0 replies; 14+ messages in thread
From: Jim Liu @ 2022-04-06  7:57 UTC (permalink / raw)
  To: JJLIU0, YSCHU, KWLIU, lukma, seanga2, sjg, sr, trini; +Cc: u-boot, Stanley Chu

Add Nuvoton BMC NPCM7xx/NPCM8xx timer driver.

Signed-off-by: Jim Liu <JJLIU0@nuvoton.com>
Signed-off-by: Stanley Chu <yschu@nuvoton.com>
Reviewed-by: Simon Glass <sjg@chromium.org>

---
 drivers/timer/Kconfig      |   7 +++
 drivers/timer/Makefile     |   1 +
 drivers/timer/npcm-timer.c | 115 +++++++++++++++++++++++++++++++++++++
 3 files changed, 123 insertions(+)
 create mode 100644 drivers/timer/npcm-timer.c

diff --git a/drivers/timer/Kconfig b/drivers/timer/Kconfig
index 8913142654..19826989fe 100644
--- a/drivers/timer/Kconfig
+++ b/drivers/timer/Kconfig
@@ -143,6 +143,13 @@ config NOMADIK_MTU_TIMER
 	  The MTU provides 4 decrementing free-running timers.
 	  At the moment, only the first timer is used by the driver.
 
+config NPCM_TIMER
+        bool "Nuvoton NPCM timer support"
+        depends on TIMER
+        help
+          Select this to enable support for the timer found on
+          Nuvoton NPCM devices.
+
 config OMAP_TIMER
 	bool "Omap timer support"
 	depends on TIMER
diff --git a/drivers/timer/Makefile b/drivers/timer/Makefile
index e2bd530eb0..a0c5ec4562 100644
--- a/drivers/timer/Makefile
+++ b/drivers/timer/Makefile
@@ -14,6 +14,7 @@ obj-$(CONFIG_CADENCE_TTC_TIMER)	+= cadence-ttc.o
 obj-$(CONFIG_DESIGNWARE_APB_TIMER)	+= dw-apb-timer.o
 obj-$(CONFIG_MPC83XX_TIMER) += mpc83xx_timer.o
 obj-$(CONFIG_NOMADIK_MTU_TIMER)	+= nomadik-mtu-timer.o
+obj-$(CONFIG_NPCM_TIMER)        += npcm-timer.o
 obj-$(CONFIG_OMAP_TIMER)	+= omap-timer.o
 obj-$(CONFIG_RENESAS_OSTM_TIMER) += ostm_timer.o
 obj-$(CONFIG_RISCV_TIMER) += riscv_timer.o
diff --git a/drivers/timer/npcm-timer.c b/drivers/timer/npcm-timer.c
new file mode 100644
index 0000000000..4562a6f231
--- /dev/null
+++ b/drivers/timer/npcm-timer.c
@@ -0,0 +1,115 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * Copyright (c) 2022 Nuvoton Technology Corp.
+ */
+
+#include <common.h>
+#include <clk.h>
+#include <dm.h>
+#include <timer.h>
+#include <asm/io.h>
+
+#define NPCM_TIMER_CLOCK_RATE	1000000UL		/* 1MHz timer */
+#define NPCM_TIMER_INPUT_RATE	25000000UL		/* Rate of input clock */
+#define NPCM_TIMER_TDR_MASK	GENMASK(23, 0)
+#define NPCM_TIMER_MAX_VAL	NPCM_TIMER_TDR_MASK	/* max counter value */
+
+/* Register offsets */
+#define TCR0	0x0	/* Timer Control and Status Register */
+#define TICR0	0x8	/* Timer Initial Count Register */
+#define TDR0	0x10	/* Timer Data Register */
+
+/* TCR fields */
+#define TCR_MODE_PERIODIC	BIT(27)
+#define TCR_EN			BIT(30)
+#define TCR_PRESCALE		(NPCM_TIMER_INPUT_RATE / NPCM_TIMER_CLOCK_RATE - 1)
+
+enum input_clock_type {
+	INPUT_CLOCK_FIXED,	/* input clock rate is fixed */
+	INPUT_CLOCK_NON_FIXED
+};
+
+/**
+ * struct npcm_timer_priv - private data for npcm timer driver
+ * npcm timer is a 24-bits down-counting timer.
+ *
+ * @last_count: last hw counter value
+ * @counter: the value to be returned for get_count ops
+ */
+struct npcm_timer_priv {
+	void __iomem *base;
+	u32 last_count;
+	u64 counter;
+};
+
+static u64 npcm_timer_get_count(struct udevice *dev)
+{
+	struct npcm_timer_priv *priv = dev_get_priv(dev);
+	u32 val;
+
+	/* The timer is counting down */
+	val = readl(priv->base + TDR0) & NPCM_TIMER_TDR_MASK;
+	if (val <= priv->last_count)
+		priv->counter += priv->last_count - val;
+	else
+		priv->counter += priv->last_count + (NPCM_TIMER_MAX_VAL + 1 - val);
+	priv->last_count = val;
+
+	return priv->counter;
+}
+
+static int npcm_timer_probe(struct udevice *dev)
+{
+	struct timer_dev_priv *uc_priv = dev_get_uclass_priv(dev);
+	struct npcm_timer_priv *priv = dev_get_priv(dev);
+	enum input_clock_type type = dev_get_driver_data(dev);
+	struct clk clk;
+	int ret;
+
+	priv->base = dev_read_addr_ptr(dev);
+	if (!priv->base)
+		return -EINVAL;
+	uc_priv->clock_rate = NPCM_TIMER_CLOCK_RATE;
+
+	if (type == INPUT_CLOCK_NON_FIXED) {
+		ret = clk_get_by_index(dev, 0, &clk);
+		if (ret < 0)
+			return ret;
+
+		ret = clk_set_rate(&clk, NPCM_TIMER_INPUT_RATE);
+		if (ret < 0)
+			return ret;
+	}
+
+	/*
+	 * Configure timer and start
+	 * periodic mode
+	 * timer clock rate = input clock / prescale
+	 */
+	writel(0, priv->base + TCR0);
+	writel(NPCM_TIMER_MAX_VAL, priv->base + TICR0);
+	writel(TCR_EN | TCR_MODE_PERIODIC | TCR_PRESCALE,
+	       priv->base + TCR0);
+
+	return 0;
+}
+
+static const struct timer_ops npcm_timer_ops = {
+	.get_count = npcm_timer_get_count,
+};
+
+static const struct udevice_id npcm_timer_ids[] = {
+	{ .compatible = "nuvoton,npcm845-timer", .data = INPUT_CLOCK_FIXED},
+	{ .compatible = "nuvoton,npcm750-timer", .data = INPUT_CLOCK_NON_FIXED},
+	{}
+};
+
+U_BOOT_DRIVER(npcm_timer) = {
+	.name	= "npcm_timer",
+	.id	= UCLASS_TIMER,
+	.of_match = npcm_timer_ids,
+	.priv_auto = sizeof(struct npcm_timer_priv),
+	.probe = npcm_timer_probe,
+	.ops	= &npcm_timer_ops,
+	.flags = DM_FLAG_PRE_RELOC,
+};
-- 
2.17.1


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

* [PATCH v1 4/6] serial: npcm: Add support for Nuvoton NPCM SoCs
  2022-04-06  7:57 [PATCH v1 0/6] Add Nuvoton NPCM750 support Jim Liu
                   ` (2 preceding siblings ...)
  2022-04-06  7:57 ` [PATCH v1 3/6] timer: npcm: Add NPCM timer support Jim Liu
@ 2022-04-06  7:57 ` Jim Liu
  2022-04-06  7:57 ` [PATCH v1 5/6] clk: nuvoton: Add support for NPCM750 Jim Liu
                   ` (2 subsequent siblings)
  6 siblings, 0 replies; 14+ messages in thread
From: Jim Liu @ 2022-04-06  7:57 UTC (permalink / raw)
  To: JJLIU0, YSCHU, KWLIU, lukma, seanga2, sjg, sr, trini; +Cc: u-boot, Stanley Chu

Add Nuvoton BMC NPCM7xx/NPCM8xx uart driver

Signed-off-by: Jim Liu <JJLIU0@nuvoton.com>
Signed-off-by: Stanley Chu <yschu@nuvoton.com>
Reviewed-by: Simon Glass <sjg@chromium.org>
---
 drivers/serial/Kconfig       |   7 ++
 drivers/serial/Makefile      |   1 +
 drivers/serial/serial_npcm.c | 150 +++++++++++++++++++++++++++++++++++
 3 files changed, 158 insertions(+)
 create mode 100644 drivers/serial/serial_npcm.c

diff --git a/drivers/serial/Kconfig b/drivers/serial/Kconfig
index 345d1881f5..77458084d4 100644
--- a/drivers/serial/Kconfig
+++ b/drivers/serial/Kconfig
@@ -928,6 +928,13 @@ config MPC8XX_CONS
 	depends on MPC8xx
 	default y
 
+config NPCM_SERIAL
+        bool "Nuvoton NPCM UART driver"
+        depends on DM_SERIAL
+        help
+          Select this to enable UART support for Nuvoton BMCs
+          (NPCM7xx and NPCM8xx)
+
 config XEN_SERIAL
 	bool "XEN serial support"
 	depends on XEN
diff --git a/drivers/serial/Makefile b/drivers/serial/Makefile
index 52e70aa191..8f12af4779 100644
--- a/drivers/serial/Makefile
+++ b/drivers/serial/Makefile
@@ -67,6 +67,7 @@ obj-$(CONFIG_MSM_GENI_SERIAL) += serial_msm_geni.o
 obj-$(CONFIG_MVEBU_A3700_UART) += serial_mvebu_a3700.o
 obj-$(CONFIG_MPC8XX_CONS) += serial_mpc8xx.o
 obj-$(CONFIG_NULLDEV_SERIAL) += serial_nulldev.o
+obj-$(CONFIG_NPCM_SERIAL) += serial_npcm.o
 obj-$(CONFIG_OCTEON_SERIAL_BOOTCMD) += serial_octeon_bootcmd.o
 obj-$(CONFIG_OCTEON_SERIAL_PCIE_CONSOLE) += serial_octeon_pcie_console.o
 obj-$(CONFIG_OWL_SERIAL) += serial_owl.o
diff --git a/drivers/serial/serial_npcm.c b/drivers/serial/serial_npcm.c
new file mode 100644
index 0000000000..0c6f0410cf
--- /dev/null
+++ b/drivers/serial/serial_npcm.c
@@ -0,0 +1,150 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * Copyright (c) 2021 Nuvoton Technology Corp.
+ */
+
+#include <common.h>
+#include <clk.h>
+#include <dm.h>
+#include <serial.h>
+
+struct npcm_uart {
+	union {
+		u32	rbr;	/* Receive Buffer Register */
+		u32	thr;	/* Transmit Holding Register */
+		u32	dll;	/* Divisor Latch (Low Byte) Register */
+	};
+	union {
+		u32	ier;	/* Interrupt Enable Register */
+		u32	dlm;	/* Divisor Latch (Low Byte) Register */
+	};
+	union {
+		u32	iir;	/* Interrupt Identification Register */
+		u32	fcr;	/* FIFO Control Register */
+	};
+	u32	lcr;		/* Line Control Register */
+	u32	mcr;		/* Modem Control Register */
+	u32	lsr;		/* Line Status Control Register */
+	u32	msr;		/* Modem Status Register */
+	u32	tor;		/* Timeout Register */
+};
+
+#define	LCR_WLS_8BITS	3	/* 8-bit word length select */
+#define	FCR_TFR		BIT(2)	/* TxFIFO reset */
+#define	FCR_RFR		BIT(1)	/* RxFIFO reset */
+#define	FCR_FME		BIT(0)	/* FIFO mode enable */
+#define	LSR_THRE	BIT(5)	/* Status of TxFIFO empty */
+#define	LSR_RFDR	BIT(0)	/* Status of RxFIFO data ready */
+#define	LCR_DLAB	BIT(7)	/* Divisor latch access bit */
+
+struct npcm_serial_plat {
+	struct npcm_uart *reg;
+	u32 uart_clk;		/* frequency of uart clock source */
+};
+
+static int npcm_serial_pending(struct udevice *dev, bool input)
+{
+	struct npcm_serial_plat *plat = dev_get_plat(dev);
+	struct npcm_uart *uart = plat->reg;
+
+	if (input)
+		return readb(&uart->lsr) & LSR_RFDR ? 1 : 0;
+	else
+		return readb(&uart->lsr) & LSR_THRE ? 0 : 1;
+}
+
+static int npcm_serial_putc(struct udevice *dev, const char ch)
+{
+	struct npcm_serial_plat *plat = dev_get_plat(dev);
+	struct npcm_uart *uart = plat->reg;
+
+	if (!(readb(&uart->lsr) & LSR_THRE))
+		return -EAGAIN;
+
+	writeb(ch, &uart->thr);
+
+	return 0;
+}
+
+static int npcm_serial_getc(struct udevice *dev)
+{
+	struct npcm_serial_plat *plat = dev_get_plat(dev);
+	struct npcm_uart *uart = plat->reg;
+
+	if (!(readb(&uart->lsr) & LSR_RFDR))
+		return -EAGAIN;
+
+	return readb(&uart->rbr);
+}
+
+static int npcm_serial_setbrg(struct udevice *dev, int baudrate)
+{
+	struct npcm_serial_plat *plat = dev_get_plat(dev);
+	struct npcm_uart *uart = plat->reg;
+	u16 divisor;
+
+	/* BaudOut = UART Clock / (16 * [Divisor + 2]) */
+	divisor = DIV_ROUND_CLOSEST(plat->uart_clk, 16 * baudrate + 2) - 2;
+
+	setbits_8(&uart->lcr, LCR_DLAB);
+	writeb(divisor & 0xff, &uart->dll);
+	writeb(divisor >> 8, &uart->dlm);
+	clrbits_8(&uart->lcr, LCR_DLAB);
+
+	return 0;
+}
+
+static int npcm_serial_probe(struct udevice *dev)
+{
+	struct npcm_serial_plat *plat = dev_get_plat(dev);
+	struct npcm_uart *uart = plat->reg;
+	struct clk clk;
+	u32 freq;
+	int ret;
+
+	plat->reg = dev_read_addr_ptr(dev);
+	freq = dev_read_u32_default(dev, "clock-frequency", 0);
+
+	ret = clk_get_by_index(dev, 0, &clk);
+	if (ret < 0)
+		return ret;
+
+	ret = clk_set_rate(&clk, freq);
+	if (ret < 0)
+		return ret;
+	plat->uart_clk = ret;
+
+	/* Disable all interrupt */
+	writeb(0, &uart->ier);
+
+	/* Set 8 bit, 1 stop, no parity */
+	writeb(LCR_WLS_8BITS, &uart->lcr);
+
+	/* Reset RX/TX FIFO */
+	writeb(FCR_FME | FCR_RFR | FCR_TFR, &uart->fcr);
+
+	return 0;
+}
+
+static const struct dm_serial_ops npcm_serial_ops = {
+	.getc = npcm_serial_getc,
+	.setbrg = npcm_serial_setbrg,
+	.putc = npcm_serial_putc,
+	.pending = npcm_serial_pending,
+};
+
+static const struct udevice_id npcm_serial_ids[] = {
+	{ .compatible = "nuvoton,npcm750-uart" },
+	{ .compatible = "nuvoton,npcm845-uart" },
+	{ }
+};
+
+U_BOOT_DRIVER(serial_npcm) = {
+	.name	= "serial_npcm",
+	.id	= UCLASS_SERIAL,
+	.of_match = npcm_serial_ids,
+	.plat_auto  = sizeof(struct npcm_serial_plat),
+	.probe = npcm_serial_probe,
+	.ops	= &npcm_serial_ops,
+	.flags = DM_FLAG_PRE_RELOC,
+};
-- 
2.17.1


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

* [PATCH v1 5/6] clk: nuvoton: Add support for NPCM750
  2022-04-06  7:57 [PATCH v1 0/6] Add Nuvoton NPCM750 support Jim Liu
                   ` (3 preceding siblings ...)
  2022-04-06  7:57 ` [PATCH v1 4/6] serial: npcm: Add support for Nuvoton NPCM SoCs Jim Liu
@ 2022-04-06  7:57 ` Jim Liu
  2022-04-06 18:19   ` Sean Anderson
  2022-04-06  7:57 ` [PATCH v1 6/6] arm: nuvoton: Add support for Nuvoton NPCM750 BMC Jim Liu
  2022-04-06 19:45 ` [PATCH v1 0/6] Add Nuvoton NPCM750 support Tom Rini
  6 siblings, 1 reply; 14+ messages in thread
From: Jim Liu @ 2022-04-06  7:57 UTC (permalink / raw)
  To: JJLIU0, YSCHU, KWLIU, lukma, seanga2, sjg, sr, trini; +Cc: u-boot

Add clock controller driver for NPCM750

Signed-off-by: Jim Liu <JJLIU0@nuvoton.com>
---
 drivers/clk/Makefile                          |   1 +
 drivers/clk/nuvoton/Makefile                  |   1 +
 drivers/clk/nuvoton/clk_npcm7xx.c             | 469 ++++++++++++++++++
 .../dt-bindings/clock/nuvoton,npcm7xx-clock.h |  46 ++
 4 files changed, 517 insertions(+)
 create mode 100644 drivers/clk/nuvoton/Makefile
 create mode 100644 drivers/clk/nuvoton/clk_npcm7xx.c
 create mode 100644 include/dt-bindings/clock/nuvoton,npcm7xx-clock.h

diff --git a/drivers/clk/Makefile b/drivers/clk/Makefile
index bb4eee5d99..f5b553172c 100644
--- a/drivers/clk/Makefile
+++ b/drivers/clk/Makefile
@@ -20,6 +20,7 @@ obj-$(CONFIG_ARCH_ASPEED) += aspeed/
 obj-$(CONFIG_ARCH_MEDIATEK) += mediatek/
 obj-$(CONFIG_ARCH_MESON) += meson/
 obj-$(CONFIG_ARCH_MTMIPS) += mtmips/
+obj-$(CONFIG_ARCH_NPCM) += nuvoton/
 obj-$(CONFIG_ARCH_ROCKCHIP) += rockchip/
 obj-$(CONFIG_ARCH_SOCFPGA) += altera/
 obj-$(CONFIG_ARCH_SUNXI) += sunxi/
diff --git a/drivers/clk/nuvoton/Makefile b/drivers/clk/nuvoton/Makefile
new file mode 100644
index 0000000000..4e7b8dfde8
--- /dev/null
+++ b/drivers/clk/nuvoton/Makefile
@@ -0,0 +1 @@
+obj-$(CONFIG_ARCH_NPCM7xx) += clk_npcm7xx.o
diff --git a/drivers/clk/nuvoton/clk_npcm7xx.c b/drivers/clk/nuvoton/clk_npcm7xx.c
new file mode 100644
index 0000000000..a37993eaae
--- /dev/null
+++ b/drivers/clk/nuvoton/clk_npcm7xx.c
@@ -0,0 +1,469 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * Copyright (c) 2021 Nuvoton Technology Corp.
+ */
+
+#include <common.h>
+#include <clk-uclass.h>
+#include <div64.h>
+#include <dm.h>
+#include <asm/io.h>
+#include <linux/bitfield.h>
+#include <linux/log2.h>
+#include <dt-bindings/clock/nuvoton,npcm7xx-clock.h>
+
+/* Register offsets */
+#define CLKSEL		0x04	/* clock source selection */
+#define CLKDIV1		0x08	/* clock divider 1 */
+#define CLKDIV2		0x2C	/* clock divider 2 */
+#define CLKDIV3		0x58	/* clock divider 3 */
+#define PLLCON0		0x0C	/* pll0 control */
+#define PLLCON1		0x10	/* pll1 control */
+#define PLLCON2		0x54	/* pll2 control */
+
+/* PLLCON bit filed */
+#define PLLCON_INDV	GENMASK(5, 0)
+#define PLLCON_OTDV1	GENMASK(10, 8)
+#define PLLCON_OTDV2	GENMASK(15, 13)
+#define PLLCON_FBDV	GENMASK(27, 16)
+
+/* CLKSEL bit filed */
+#define CPUCKSEL	GENMASK(1, 0)
+#define SDCKSEL		GENMASK(7, 6)
+#define UARTCKSEL	GENMASK(9, 8)
+#define TIMCKSEL	GENMASK(15, 14)
+
+/* CLKDIV1 bit filed */
+#define SPI3CKDIV	GENMASK(10, 6)
+#define MMCCKDIV	GENMASK(15, 11)
+#define UARTDIV1	GENMASK(20, 16)
+#define TIMCKDIV	GENMASK(25, 21)
+#define CLK4DIV		GENMASK(27, 26)
+
+/* CLKDIV2 bit filed */
+#define APB5CKDIV	GENMASK(23, 22)
+#define APB2CKDIV	GENMASK(27, 26)
+
+/* CLKDIV3 bit filed */
+#define SPIXCKDIV	GENMASK(5, 1)
+#define SPI0CKDIV	GENMASK(10, 6)
+#define UARTDIV2	GENMASK(15, 11)
+#define SPI1CKDIV	GENMASK(23, 16)
+
+/* Flags */
+#define DIV_TYPE1	BIT(0)	/* div = clkdiv + 1 */
+#define DIV_TYPE2	BIT(1)	/* div = 1 << clkdiv */
+#define PRE_DIV2	BIT(2)	/* Pre divisor = 2 */
+#define POST_DIV2	BIT(3)	/* Post divisor = 2 */
+#define FIXED_PARENT	BIT(4)	/* clock source is fixed */
+
+struct npcm_clk_priv {
+	struct udevice *dev;
+	void __iomem *base;
+};
+
+/* Parameters of PLL configuration */
+struct npcm_clk_pll {
+	const int id;
+	const int parent_id;
+	u32 reg;
+	u32 flags;
+};
+
+/* Parent clock id to clksel mapping */
+struct parent_data {
+	int id;
+	int clksel;
+};
+
+/* Parameters of parent selection */
+struct npcm_clk_select {
+	const int id;
+	const struct parent_data *parents;
+	u32 reg;
+	u32 mask;
+	u8 num_parents;
+	u32 flags;
+};
+
+/* Parameters of clock divider */
+struct npcm_clk_div {
+	const int id;
+	u32 reg;
+	u32 mask;
+	u32 flags;
+};
+
+/* Parent clock map */
+static const struct parent_data pll_parents[] = {
+	{NPCM7XX_CLK_PLL0, 0},
+	{NPCM7XX_CLK_PLL1, 1},
+	{NPCM7XX_CLK_REFCLK, 2},
+	{NPCM7XX_CLK_PLL2DIV2, 3}
+};
+
+static const struct parent_data cpuck_parents[] = {
+	{NPCM7XX_CLK_PLL0, 0},
+	{NPCM7XX_CLK_PLL1, 1},
+	{NPCM7XX_CLK_REFCLK, 2},
+	{NPCM7XX_CLK_PLL2, 7}
+};
+
+static const struct parent_data apb_parent[] = {{NPCM7XX_CLK_AHB, 0}};
+
+static struct npcm_clk_pll npcm7xx_clk_plls[] = {
+	{NPCM7XX_CLK_PLL0, NPCM7XX_CLK_REFCLK, PLLCON0, 0},
+	{NPCM7XX_CLK_PLL1, NPCM7XX_CLK_REFCLK, PLLCON1, 0},
+	{NPCM7XX_CLK_PLL2, NPCM7XX_CLK_REFCLK, PLLCON2, 0},
+	{NPCM7XX_CLK_PLL2DIV2, NPCM7XX_CLK_REFCLK, PLLCON2, POST_DIV2}
+};
+
+static struct npcm_clk_select npcm7xx_clk_selectors[] = {
+	{NPCM7XX_CLK_AHB, cpuck_parents, CLKSEL, CPUCKSEL, 4, 0},
+	{NPCM7XX_CLK_APB2, apb_parent, 0, 0, 1, FIXED_PARENT},
+	{NPCM7XX_CLK_APB5, apb_parent, 0, 0, 1, FIXED_PARENT},
+	{NPCM7XX_CLK_SPI0, apb_parent, 0, 0, 1, FIXED_PARENT},
+	{NPCM7XX_CLK_SPI3, apb_parent, 0, 0, 1, FIXED_PARENT},
+	{NPCM7XX_CLK_SPIX, apb_parent, 0, 0, 1, FIXED_PARENT},
+	{NPCM7XX_CLK_UART, pll_parents, CLKSEL, UARTCKSEL, 4, 0},
+	{NPCM7XX_CLK_TIMER, pll_parents, CLKSEL, TIMCKSEL, 4, 0},
+	{NPCM7XX_CLK_SDHC, pll_parents, CLKSEL, SDCKSEL, 4, 0}
+};
+
+static struct npcm_clk_div npcm7xx_clk_dividers[] = {
+	{NPCM7XX_CLK_AHB, CLKDIV1, CLK4DIV, DIV_TYPE1 | PRE_DIV2},
+	{NPCM7XX_CLK_APB2, CLKDIV2, APB2CKDIV, DIV_TYPE2},
+	{NPCM7XX_CLK_APB5, CLKDIV2, APB5CKDIV, DIV_TYPE2},
+	{NPCM7XX_CLK_SPI0, CLKDIV3, SPI0CKDIV, DIV_TYPE1},
+	{NPCM7XX_CLK_SPI3, CLKDIV1, SPI3CKDIV, DIV_TYPE1},
+	{NPCM7XX_CLK_SPIX, CLKDIV3, SPIXCKDIV, DIV_TYPE1},
+	{NPCM7XX_CLK_UART, CLKDIV1, UARTDIV1, DIV_TYPE1},
+	{NPCM7XX_CLK_TIMER, CLKDIV1, TIMCKDIV, DIV_TYPE2},
+	{NPCM7XX_CLK_SDHC, CLKDIV1, MMCCKDIV, DIV_TYPE1}
+};
+
+static int clkid_to_clksel(struct npcm_clk_select *selector, int id)
+{
+	int i;
+
+	for (i = 0; i < selector->num_parents; i++) {
+		if (selector->parents[i].id == id)
+			return selector->parents[i].clksel;
+	}
+
+	return -EINVAL;
+}
+
+static int clksel_to_clkid(struct npcm_clk_select *selector, int clksel)
+{
+	int i;
+
+	for (i = 0; i < selector->num_parents; i++) {
+		if (selector->parents[i].clksel == clksel)
+			return selector->parents[i].id;
+	}
+
+	return -EINVAL;
+}
+
+static struct npcm_clk_pll *npcm_clk_pll_get(int clk_id)
+{
+	int i;
+
+	for (i = 0; i < ARRAY_SIZE(npcm7xx_clk_plls); i++) {
+		if (npcm7xx_clk_plls[i].id == clk_id)
+			return &npcm7xx_clk_plls[i];
+	}
+
+	return NULL;
+}
+
+static struct npcm_clk_select *npcm_clk_selector_get(int clk_id)
+{
+	int i;
+
+	for (i = 0; i < ARRAY_SIZE(npcm7xx_clk_selectors); i++) {
+		if (npcm7xx_clk_selectors[i].id == clk_id)
+			return &npcm7xx_clk_selectors[i];
+	}
+
+	return NULL;
+}
+
+static struct npcm_clk_div *npcm_clk_divider_get(int clk_id)
+{
+	int i;
+
+	for (i = 0; i < ARRAY_SIZE(npcm7xx_clk_dividers); i++) {
+		if (npcm7xx_clk_dividers[i].id == clk_id)
+			return &npcm7xx_clk_dividers[i];
+	}
+
+	return NULL;
+}
+
+static ulong npcm_clk_get_fin(struct npcm_clk_priv *priv, int id)
+{
+	struct npcm_clk_select *selector;
+	struct clk parent;
+	ulong parent_rate;
+	u32 val, clksel;
+	int ret;
+
+	selector = npcm_clk_selector_get(id);
+	if (!selector)
+		return 0;
+
+	if (selector->flags & FIXED_PARENT) {
+		clksel = 0;
+	} else {
+		val = readl(priv->base + selector->reg);
+		clksel = (val & selector->mask) >> (ffs(selector->mask) - 1);
+	}
+	parent.id = clksel_to_clkid(selector, clksel);
+
+	ret = clk_request(priv->dev, &parent);
+	if (ret)
+		return 0;
+
+	parent_rate = clk_get_rate(&parent);
+
+	debug("fin of clk%d = %lu\n", id, parent_rate);
+	return parent_rate;
+}
+
+static u32 npcm_clk_get_div(struct npcm_clk_priv *priv, int id)
+{
+	struct npcm_clk_div *divider;
+	u32 val, div;
+
+	divider = npcm_clk_divider_get(id);
+	if (!divider)
+		return 0;
+
+	val = readl(priv->base + divider->reg);
+	div = (val & divider->mask) >> (ffs(divider->mask) - 1);
+	if (divider->flags & DIV_TYPE1)
+		div = div + 1;
+	else
+		div = 1 << div;
+
+	if (divider->flags & PRE_DIV2)
+		div = div << 1;
+
+	return div;
+}
+
+static u32 npcm_clk_set_div(struct npcm_clk_priv *priv, int id, u32 div)
+{
+	struct npcm_clk_div *divider;
+	u32 val, clkdiv;
+
+	divider = npcm_clk_divider_get(id);
+	if (!divider)
+		return -EINVAL;
+
+	if (divider->flags & PRE_DIV2)
+		div = div >> 1;
+
+	if (divider->flags & DIV_TYPE1)
+		clkdiv = div - 1;
+	else
+		clkdiv = ilog2(div);
+
+	val = readl(priv->base + divider->reg);
+	val &= ~divider->mask;
+	val |= (clkdiv << (ffs(divider->mask) - 1)) & divider->mask;
+	writel(val, priv->base + divider->reg);
+
+	return 0;
+}
+
+static ulong npcm_clk_get_fout(struct npcm_clk_priv *priv, int id)
+{
+	ulong parent_rate;
+	u32 div;
+
+	parent_rate = npcm_clk_get_fin(priv, id);
+	if (!parent_rate)
+		return -EINVAL;
+
+	div = npcm_clk_get_div(priv, id);
+	if (!div)
+		return -EINVAL;
+
+	debug("fout of clk%d = (%lu / %u)\n", id, parent_rate, div);
+	return (parent_rate / div);
+}
+
+static ulong npcm_clk_set_fout(struct npcm_clk_priv *priv, int id, ulong rate)
+{
+	u32 div;
+	ulong parent_rate;
+	int ret;
+
+	parent_rate = npcm_clk_get_fin(priv, id);
+	if (!parent_rate)
+		return -EINVAL;
+
+	div = DIV_ROUND_UP(parent_rate, rate);
+	ret = npcm_clk_set_div(priv, id, div);
+	if (ret)
+		return ret;
+
+	debug("%s: rate %lu, new rate (%lu / %u)\n", __func__, rate, parent_rate, div);
+	return (parent_rate / div);
+}
+
+static ulong npcm_clk_get_pll_fout(struct npcm_clk_priv *priv, int id)
+{
+	struct npcm_clk_pll *pll;
+	struct clk parent;
+	ulong parent_rate;
+	ulong fbdv, indv, otdv1, otdv2;
+	u32 val;
+	u64 ret;
+
+	pll = npcm_clk_pll_get(id);
+	if (!pll)
+		return -ENODEV;
+
+	parent.id = pll->parent_id;
+	ret = clk_request(priv->dev, &parent);
+	if (ret)
+		return ret;
+
+	parent_rate = clk_get_rate(&parent);
+
+	val = readl(priv->base + pll->reg);
+	indv = FIELD_GET(PLLCON_INDV, val);
+	fbdv = FIELD_GET(PLLCON_FBDV, val);
+	otdv1 = FIELD_GET(PLLCON_OTDV1, val);
+	otdv2 = FIELD_GET(PLLCON_OTDV2, val);
+
+	ret = (u64)parent_rate * fbdv;
+	do_div(ret, indv * otdv1 * otdv2);
+	if (pll->flags & POST_DIV2)
+		do_div(ret, 2);
+
+	debug("fout of pll(id %d) = %llu\n", id, ret);
+	return ret;
+}
+
+static ulong npcm_clk_get_rate(struct clk *clk)
+{
+	struct npcm_clk_priv *priv = dev_get_priv(clk->dev);
+	struct clk refclk;
+	int ret;
+
+	debug("%s: id %lu\n", __func__, clk->id);
+	switch (clk->id) {
+	case NPCM7XX_CLK_TIMER:
+	case NPCM7XX_CLK_REFCLK:
+		ret = clk_get_by_name(priv->dev, "refclk", &refclk);
+		if (!ret)
+			return clk_get_rate(&refclk);
+		else
+			return ret;
+	case NPCM7XX_CLK_PLL0:
+	case NPCM7XX_CLK_PLL1:
+	case NPCM7XX_CLK_PLL2:
+	case NPCM7XX_CLK_PLL2DIV2:
+		return npcm_clk_get_pll_fout(priv, clk->id);
+	case NPCM7XX_CLK_AHB:
+	case NPCM7XX_CLK_APB2:
+	case NPCM7XX_CLK_APB5:
+	case NPCM7XX_CLK_SDHC:
+	case NPCM7XX_CLK_UART:
+	case NPCM7XX_CLK_SPI0:
+	case NPCM7XX_CLK_SPI3:
+	case NPCM7XX_CLK_SPIX:
+		return npcm_clk_get_fout(priv, clk->id);
+	default:
+		return -ENOSYS;
+	}
+}
+
+static ulong npcm_clk_set_rate(struct clk *clk, ulong rate)
+{
+	struct npcm_clk_priv *priv = dev_get_priv(clk->dev);
+
+	debug("%s: id %lu, rate %lu\n", __func__, clk->id, rate);
+	switch (clk->id) {
+	case NPCM7XX_CLK_TIMER:
+	case NPCM7XX_CLK_SDHC:
+	case NPCM7XX_CLK_UART:
+	case NPCM7XX_CLK_SPI0:
+	case NPCM7XX_CLK_SPI3:
+	case NPCM7XX_CLK_SPIX:
+		return  npcm_clk_set_fout(priv, clk->id, rate);
+	default:
+		return -ENOSYS;
+	}
+}
+
+static int npcm_clk_set_parent(struct clk *clk, struct clk *parent)
+{
+	struct npcm_clk_priv *priv = dev_get_priv(clk->dev);
+	struct npcm_clk_select *selector;
+	int clksel;
+	u32 val;
+
+	debug("%s: id %lu, parent %lu\n", __func__, clk->id, parent->id);
+	selector = npcm_clk_selector_get(clk->id);
+	if (!selector)
+		return -EINVAL;
+
+	clksel = clkid_to_clksel(selector, parent->id);
+	if (clksel < 0)
+		return -EINVAL;
+
+	val = readl(priv->base + selector->reg);
+	val &= ~selector->mask;
+	val |= clksel << (ffs(selector->mask) - 1);
+	writel(val, priv->base + selector->reg);
+
+	return 0;
+}
+
+static int npcm_clk_request(struct clk *clk)
+{
+	if (clk->id >= NPCM7XX_NUM_CLOCKS)
+		return -EINVAL;
+
+	return 0;
+}
+
+static struct clk_ops npcm_clk_ops = {
+	.get_rate = npcm_clk_get_rate,
+	.set_rate = npcm_clk_set_rate,
+	.set_parent = npcm_clk_set_parent,
+	.request = npcm_clk_request,
+};
+
+static int npcm_clk_probe(struct udevice *dev)
+{
+	struct npcm_clk_priv *priv = dev_get_priv(dev);
+
+	priv->base = dev_read_addr_ptr(dev);
+	if (!priv->base)
+		return -EINVAL;
+	priv->dev = dev;
+
+	return 0;
+}
+
+static const struct udevice_id npcm_clk_ids[] = {
+	{ .compatible = "nuvoton,npcm750-clk" },
+	{ }
+};
+
+U_BOOT_DRIVER(clk_npcm) = {
+	.name           = "clk_npcm",
+	.id             = UCLASS_CLK,
+	.of_match       = npcm_clk_ids,
+	.ops            = &npcm_clk_ops,
+	.priv_auto	= sizeof(struct npcm_clk_priv),
+	.probe          = npcm_clk_probe,
+	.flags = DM_FLAG_PRE_RELOC,
+};
diff --git a/include/dt-bindings/clock/nuvoton,npcm7xx-clock.h b/include/dt-bindings/clock/nuvoton,npcm7xx-clock.h
new file mode 100644
index 0000000000..65e6bc4eee
--- /dev/null
+++ b/include/dt-bindings/clock/nuvoton,npcm7xx-clock.h
@@ -0,0 +1,46 @@
+/* SPDX-License-Identifier: GPL-2.0 */
+/*
+ * Nuvoton NPCM7xx Clock Generator binding
+ * clock binding number for all clocks supportted by nuvoton,npcm7xx-clk
+ *
+ * Copyright (C) 2018 Nuvoton Technologies tali.perry@nuvoton.com
+ *
+ */
+
+#ifndef __DT_BINDINGS_CLOCK_NPCM7XX_H
+#define __DT_BINDINGS_CLOCK_NPCM7XX_H
+
+#define NPCM7XX_CLK_CPU		0
+#define NPCM7XX_CLK_GFX_PIXEL	1
+#define NPCM7XX_CLK_MC		2
+#define NPCM7XX_CLK_ADC		3
+#define NPCM7XX_CLK_AHB		4
+#define NPCM7XX_CLK_TIMER	5
+#define NPCM7XX_CLK_UART	6
+#define NPCM7XX_CLK_MMC		7
+#define NPCM7XX_CLK_SPI3	8
+#define NPCM7XX_CLK_PCI		9
+#define NPCM7XX_CLK_AXI		10
+#define NPCM7XX_CLK_APB4	11
+#define NPCM7XX_CLK_APB3	12
+#define NPCM7XX_CLK_APB2	13
+#define NPCM7XX_CLK_APB1	14
+#define NPCM7XX_CLK_APB5	15
+#define NPCM7XX_CLK_CLKOUT	16
+#define NPCM7XX_CLK_GFX		17
+#define NPCM7XX_CLK_SU		18
+#define NPCM7XX_CLK_SU48	19
+#define NPCM7XX_CLK_SDHC	20
+#define NPCM7XX_CLK_SPI0	21
+#define NPCM7XX_CLK_SPIX	22
+#define NPCM7XX_CLK_REFCLK	23
+#define NPCM7XX_CLK_SYSBYPCK	24
+#define NPCM7XX_CLK_MCBYPCK	25
+#define NPCM7XX_CLK_PLL0	26
+#define NPCM7XX_CLK_PLL1	27
+#define NPCM7XX_CLK_PLL2	28
+#define NPCM7XX_CLK_PLL2DIV2	29
+#define NPCM7XX_NUM_CLOCKS	(NPCM7XX_CLK_PLL2DIV2 + 1)
+
+#endif
+
-- 
2.17.1


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

* [PATCH v1 6/6] arm: nuvoton: Add support for Nuvoton NPCM750 BMC
  2022-04-06  7:57 [PATCH v1 0/6] Add Nuvoton NPCM750 support Jim Liu
                   ` (4 preceding siblings ...)
  2022-04-06  7:57 ` [PATCH v1 5/6] clk: nuvoton: Add support for NPCM750 Jim Liu
@ 2022-04-06  7:57 ` Jim Liu
  2022-04-06 13:48   ` Tom Rini
  2022-04-06 19:45 ` [PATCH v1 0/6] Add Nuvoton NPCM750 support Tom Rini
  6 siblings, 1 reply; 14+ messages in thread
From: Jim Liu @ 2022-04-06  7:57 UTC (permalink / raw)
  To: JJLIU0, YSCHU, KWLIU, lukma, seanga2, sjg, sr, trini; +Cc: u-boot

Add basic support for the Nuvoton NPCM750 BMC

Signed-off-by: Jim Liu <JJLIU0@nuvoton.com>
---
 arch/arm/Kconfig                              |  8 ++
 arch/arm/Makefile                             |  1 +
 arch/arm/include/asm/arch-npcm7xx/cpu.h       | 28 ++++++
 arch/arm/include/asm/arch-npcm7xx/gcr.h       | 64 +++++++++++++
 arch/arm/include/asm/arch-npcm7xx/rst.h       | 37 ++++++++
 arch/arm/mach-nuvoton/Kconfig                 | 34 +++++++
 arch/arm/mach-nuvoton/Makefile                |  1 +
 arch/arm/mach-nuvoton/npcm7xx/Kconfig         | 18 ++++
 arch/arm/mach-nuvoton/npcm7xx/Makefile        |  2 +
 arch/arm/mach-nuvoton/npcm7xx/cpu.c           | 67 ++++++++++++++
 .../arm/mach-nuvoton/npcm7xx/l2_cache_pl310.c | 30 ++++++
 .../npcm7xx/l2_cache_pl310_init.S             | 89 ++++++++++++++++++
 arch/arm/mach-nuvoton/npcm7xx/reset.c         | 46 ++++++++++
 board/nuvoton/poleg/Kconfig                   | 31 +++++++
 board/nuvoton/poleg/Makefile                  |  1 +
 board/nuvoton/poleg/poleg_evb.c               | 52 +++++++++++
 include/configs/poleg.h                       | 77 ++++++++++++++++
 .../dt-bindings/reset/nuvoton,npcm7xx-reset.h | 91 +++++++++++++++++++
 18 files changed, 677 insertions(+)
 create mode 100644 arch/arm/include/asm/arch-npcm7xx/cpu.h
 create mode 100644 arch/arm/include/asm/arch-npcm7xx/gcr.h
 create mode 100644 arch/arm/include/asm/arch-npcm7xx/rst.h
 create mode 100644 arch/arm/mach-nuvoton/Kconfig
 create mode 100644 arch/arm/mach-nuvoton/Makefile
 create mode 100644 arch/arm/mach-nuvoton/npcm7xx/Kconfig
 create mode 100644 arch/arm/mach-nuvoton/npcm7xx/Makefile
 create mode 100644 arch/arm/mach-nuvoton/npcm7xx/cpu.c
 create mode 100644 arch/arm/mach-nuvoton/npcm7xx/l2_cache_pl310.c
 create mode 100644 arch/arm/mach-nuvoton/npcm7xx/l2_cache_pl310_init.S
 create mode 100644 arch/arm/mach-nuvoton/npcm7xx/reset.c
 create mode 100644 board/nuvoton/poleg/Kconfig
 create mode 100644 board/nuvoton/poleg/Makefile
 create mode 100644 board/nuvoton/poleg/poleg_evb.c
 create mode 100644 include/configs/poleg.h
 create mode 100644 include/dt-bindings/reset/nuvoton,npcm7xx-reset.h

diff --git a/arch/arm/Kconfig b/arch/arm/Kconfig
index 4567c183fb..45ab2793b2 100644
--- a/arch/arm/Kconfig
+++ b/arch/arm/Kconfig
@@ -922,6 +922,12 @@ config ARCH_NEXELL
 	select DM
 	select GPIO_EXTRA_HEADER
 
+config ARCH_NPCM
+        bool "Support Nuvoton SoCs"
+        select DM
+        select OF_CONTROL
+        imply CMD_DM
+
 config ARCH_APPLE
 	bool "Apple SoCs"
 	select ARM64
@@ -2196,6 +2202,8 @@ source "arch/arm/mach-imx/Kconfig"
 
 source "arch/arm/mach-nexell/Kconfig"
 
+source "arch/arm/mach-nuvoton/Kconfig"
+
 source "board/armltd/total_compute/Kconfig"
 
 source "board/bosch/shc/Kconfig"
diff --git a/arch/arm/Makefile b/arch/arm/Makefile
index ad757e982e..ad29f2418e 100644
--- a/arch/arm/Makefile
+++ b/arch/arm/Makefile
@@ -72,6 +72,7 @@ machine-$(CONFIG_ARCH_MEDIATEK)		+= mediatek
 machine-$(CONFIG_ARCH_MESON)		+= meson
 machine-$(CONFIG_ARCH_MVEBU)		+= mvebu
 machine-$(CONFIG_ARCH_NEXELL)		+= nexell
+machine-$(CONFIG_ARCH_NPCM)             += nuvoton
 machine-$(CONFIG_ARCH_OMAP2PLUS)	+= omap2
 machine-$(CONFIG_ARCH_ORION5X)		+= orion5x
 machine-$(CONFIG_ARCH_OWL)		+= owl
diff --git a/arch/arm/include/asm/arch-npcm7xx/cpu.h b/arch/arm/include/asm/arch-npcm7xx/cpu.h
new file mode 100644
index 0000000000..2189ad2fd3
--- /dev/null
+++ b/arch/arm/include/asm/arch-npcm7xx/cpu.h
@@ -0,0 +1,28 @@
+/* SPDX-License-Identifier: GPL-2.0+ */
+/*
+ * Copyright (c) 2021 Nuvoton Technology Corp.
+ */
+
+#ifndef __NPCMX50_CPU_H_
+#define __NPCMX50_CPU_H_
+
+#define NPCM750_GCR_BA			0xF0800000
+#define NPCM750_CLK_BA			0xF0801000
+#define NPCM750_GPIO_BA			0xF0010000
+
+#ifndef __ASSEMBLY__
+
+#define NPCM750_BASE(device, base) \
+static inline unsigned long __attribute__((no_instrument_function)) \
+	npcm_get_base_##device(void) \
+{ \
+	return NPCM750_##base; \
+}
+
+NPCM750_BASE(gcr, GCR_BA)
+NPCM750_BASE(clk, CLK_BA)
+NPCM750_BASE(gpio, GPIO_BA)
+
+#endif
+
+#endif
diff --git a/arch/arm/include/asm/arch-npcm7xx/gcr.h b/arch/arm/include/asm/arch-npcm7xx/gcr.h
new file mode 100644
index 0000000000..cbeca27d77
--- /dev/null
+++ b/arch/arm/include/asm/arch-npcm7xx/gcr.h
@@ -0,0 +1,64 @@
+/* SPDX-License-Identifier: GPL-2.0+ */
+
+#ifndef __NPCM750_GCR_H_
+#define __NPCM750_GCR_H_
+
+/* On-Chip POLEG NPCM750 VERSIONS */
+#define POLEG_Z1                    0x00A92750
+#define POLEG_A1                    0x04A92750
+#define POLEG_NPCM750				0x00000000
+#define POLEG_NPCM730				0x00300395
+#define POLEG_NPCM710				0x00200380
+
+#define PWRON_SECEN                    7         /* STRAP8 */
+
+struct npcm_gcr {
+	unsigned int  pdid;
+	unsigned int  pwron;
+	unsigned char res1[0x4];
+	unsigned int  mfsel1;
+	unsigned int  mfsel2;
+	unsigned int  miscpe;
+	unsigned char res2[0x20];
+	unsigned int  spswc;
+	unsigned int  intcr;
+	unsigned int  intsr;
+	unsigned char res3[0xc];
+	unsigned int  hifcr;
+	unsigned int  sd1irv1;
+	unsigned int  sd1irv2;
+	unsigned char res4[0x4];
+	unsigned int  intcr2;
+	unsigned int  mfsel3;
+	unsigned int  srcnt;
+	unsigned int  ressr;
+	unsigned int  rlockr1;
+	unsigned int  flockr1;
+	unsigned int  dscnt;
+	unsigned int  mdlr;
+	unsigned char res5[0x18];
+	unsigned int  davclvlr;
+	unsigned int  intcr3;
+	unsigned char res6[0xc];
+	unsigned int  vsintr;
+	unsigned int  mfsel4;
+	unsigned int  sd2irv1;
+	unsigned int  sd2irv2;
+	unsigned char res7[0x8];
+	unsigned int  cpbpntr;
+	unsigned char res8[0x8];
+	unsigned int  cpctl;
+	unsigned int  cp2bst;
+	unsigned int  b2cpnt;
+	unsigned int  cppctl;
+	unsigned int  i2csegsel;
+	unsigned int  i2csegctl;
+	unsigned int  vsrcr;
+	unsigned int  mlockr;
+	unsigned char res9[0x4c];
+	unsigned int  scrpad;
+	unsigned int  usb1phyctl;
+	unsigned int  usb2phyctl;
+};
+
+#endif
diff --git a/arch/arm/include/asm/arch-npcm7xx/rst.h b/arch/arm/include/asm/arch-npcm7xx/rst.h
new file mode 100644
index 0000000000..2545d9ed20
--- /dev/null
+++ b/arch/arm/include/asm/arch-npcm7xx/rst.h
@@ -0,0 +1,37 @@
+/* SPDX-License-Identifier: GPL-2.0+ */
+
+#ifndef _NPCM_RST_H_
+#define _NPCM_RST_H_
+
+#define WTCR0_REG       0xF000801C
+#define WTCR_WTR        BIT(0)
+#define WTCR_WTRE       BIT(1)
+#define WTCR_WTE        BIT(7)
+
+enum reset_type {
+	PORST_TYPE    = 0x01,
+	CORST_TYPE    = 0x02,
+	WD0RST_TYPE   = 0x03,
+	SWR1ST_TYPE   = 0x04,
+	SWR2ST_TYPE   = 0x05,
+	SWR3ST_TYPE   = 0x06,
+	SWR4ST_TYPE   = 0x07,
+	WD1RST_TYPE   = 0x08,
+	WD2RST_TYPE   = 0x09,
+	UNKNOWN_TYPE  = 0x10,
+};
+
+#define PORST		BIT(31)
+#define CORST		BIT(30)
+#define WD0RST		BIT(29)
+#define SW1RST		BIT(28)
+#define SW2RST		BIT(27)
+#define SW3RST		BIT(26)
+#define TIPRST		BIT(25)
+#define WD1RST		BIT(24)
+#define WD2RST		BIT(23)
+
+enum reset_type npcm7xx_reset_reason(void);
+
+#endif
+
diff --git a/arch/arm/mach-nuvoton/Kconfig b/arch/arm/mach-nuvoton/Kconfig
new file mode 100644
index 0000000000..5f0128a9ab
--- /dev/null
+++ b/arch/arm/mach-nuvoton/Kconfig
@@ -0,0 +1,34 @@
+if ARCH_NPCM
+
+config SYS_ARCH
+	default "arm"
+
+config SYS_TEXT_BASE
+	default 0x8000
+
+choice
+	prompt "Nuvoton SoC select"
+	default ARCH_NPCM8XX
+
+config ARCH_NPCM8XX
+	bool "Support Nuvoton NPCM8xx SoC"
+	select ARM64
+	help
+	  General support for NPCM8xx BMC (Arbel).
+	  Nuvoton NPCM8xx BMC is based on the Cortex A35.
+
+config ARCH_NPCM7xx
+	bool "Support Nuvoton NPCM7xx SoC"
+	select CPU_V7A
+	select OF_CONTROL
+	select DM
+	help
+	  General support for NPCM7xx BMC (Poleg).
+	  Nuvoton NPCM7xx BMC is based on the Cortex A9.
+
+
+endchoice
+
+source "arch/arm/mach-nuvoton/npcm7xx/Kconfig"
+
+endif
diff --git a/arch/arm/mach-nuvoton/Makefile b/arch/arm/mach-nuvoton/Makefile
new file mode 100644
index 0000000000..8a1572b4f0
--- /dev/null
+++ b/arch/arm/mach-nuvoton/Makefile
@@ -0,0 +1 @@
+obj-$(CONFIG_ARCH_NPCM7xx) += npcm7xx/
diff --git a/arch/arm/mach-nuvoton/npcm7xx/Kconfig b/arch/arm/mach-nuvoton/npcm7xx/Kconfig
new file mode 100644
index 0000000000..6fd37ce367
--- /dev/null
+++ b/arch/arm/mach-nuvoton/npcm7xx/Kconfig
@@ -0,0 +1,18 @@
+if ARCH_NPCM7xx
+
+config SYS_CPU
+        default "armv7"
+
+config SYS_SOC
+	default "npcm7xx"
+
+config TARGET_POLEG
+    bool "NPCM POLEG board"
+
+config SYS_MEM_TOP_HIDE
+	hex "Reserved TOP memory"
+	default 0x03000000
+
+source "board/nuvoton/poleg/Kconfig"
+
+endif
diff --git a/arch/arm/mach-nuvoton/npcm7xx/Makefile b/arch/arm/mach-nuvoton/npcm7xx/Makefile
new file mode 100644
index 0000000000..46e48018a0
--- /dev/null
+++ b/arch/arm/mach-nuvoton/npcm7xx/Makefile
@@ -0,0 +1,2 @@
+obj-y	= reset.o
+obj-$(CONFIG_TARGET_POLEG) += cpu.o l2_cache_pl310_init.o l2_cache_pl310.o
diff --git a/arch/arm/mach-nuvoton/npcm7xx/cpu.c b/arch/arm/mach-nuvoton/npcm7xx/cpu.c
new file mode 100644
index 0000000000..7872695690
--- /dev/null
+++ b/arch/arm/mach-nuvoton/npcm7xx/cpu.c
@@ -0,0 +1,67 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * Copyright (c) 2021 Nuvoton Technology Corp.
+ */
+
+#include <common.h>
+#include <cpu_func.h>
+#include <asm/armv7.h>
+#include <asm/io.h>
+#include <asm/arch/cpu.h>
+#include <asm/arch/gcr.h>
+
+int print_cpuinfo(void)
+{
+	struct npcm_gcr *gcr = (struct npcm_gcr *)npcm_get_base_gcr();
+	unsigned int id, mdlr;
+
+	mdlr = readl(&gcr->mdlr);
+
+	printf("CPU: ");
+
+	switch (mdlr) {
+	case POLEG_NPCM750:
+		printf("NPCM750 ");
+		break;
+	case POLEG_NPCM730:
+		printf("NPCM730 ");
+		break;
+	case POLEG_NPCM710:
+		printf("NPCM710 ");
+		break;
+	default:
+		printf("NPCM7XX ");
+		break;
+	}
+
+	id = readl(&gcr->pdid);
+	switch (id) {
+	case POLEG_Z1:
+		printf("Z1 is no supported! @ ");
+		break;
+	case POLEG_A1:
+		printf("A1 @ ");
+		break;
+	default:
+		printf("Unknown\n");
+		break;
+	}
+
+	return 0;
+}
+
+void s_init(void)
+{
+	/* Invalidate L2 cache in lowlevel_init */
+	v7_outer_cache_inval_all();
+}
+
+void enable_caches(void)
+{
+	dcache_enable();
+}
+
+void disable_caches(void)
+{
+	dcache_disable();
+}
diff --git a/arch/arm/mach-nuvoton/npcm7xx/l2_cache_pl310.c b/arch/arm/mach-nuvoton/npcm7xx/l2_cache_pl310.c
new file mode 100644
index 0000000000..805e13e863
--- /dev/null
+++ b/arch/arm/mach-nuvoton/npcm7xx/l2_cache_pl310.c
@@ -0,0 +1,30 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * Copyright (c) 2021 Nuvoton Technology Corp.
+ */
+
+#include <common.h>
+#include <asm/io.h>
+#include <asm/pl310.h>
+
+void l2_pl310_init(void);
+void set_pl310_ctrl(u32 enable);
+
+void set_pl310_ctrl(u32 enable)
+{
+	struct pl310_regs *const pl310 = (struct pl310_regs *)CONFIG_SYS_PL310_BASE;
+
+	writel(enable, &pl310->pl310_ctrl);
+}
+
+void v7_outer_cache_enable(void)
+{
+	l2_pl310_init();
+
+	set_pl310_ctrl(1);
+}
+
+void v7_outer_cache_disable(void)
+{
+	set_pl310_ctrl(0);
+}
diff --git a/arch/arm/mach-nuvoton/npcm7xx/l2_cache_pl310_init.S b/arch/arm/mach-nuvoton/npcm7xx/l2_cache_pl310_init.S
new file mode 100644
index 0000000000..8f4124b64d
--- /dev/null
+++ b/arch/arm/mach-nuvoton/npcm7xx/l2_cache_pl310_init.S
@@ -0,0 +1,89 @@
+/* SPDX-License-Identifier: GPL-2.0+ */
+/*
+ * Copyright (c) 2021 Nuvoton Technology Corp.
+ */
+
+.align 5
+
+#include <linux/linkage.h>
+
+#ifndef CONFIG_SYS_L2CACHE_OFF
+
+ENTRY(l2_pl310_init)
+
+
+	@------------------------------------------------------------------
+	@ L2CC (PL310) Initialization
+	@------------------------------------------------------------------
+		@ In this example PL310 PA = VA. The memory was marked as Device memory
+		@ in previous stages when defining CORE0 private address space
+		LDR     r0, =0xF03FC000        @ A9_BASE_ADDR
+
+		@ Disable L2 Cache controller just in case it is already on
+		LDR     r1, =0x0
+		STR     r1, [r0,#0x100]
+
+		@ Set aux cntrl
+		@ Way size = 32KB
+        @ Way = 16
+		LDR     r1, =0x02050000
+		ORR	r1, r1, #(1 << 29)	@ Instruction prefetch enable
+		ORR	r1, r1, #(1 << 28)	@ Data prefetch enable
+		ORR	r1, r1, #(1 << 22)	@ cache replacement policy
+		STR     r1, [r0,#0x104]		@ auxilary control reg at offset 0x104
+
+		@ Set tag RAM latency
+		@ 1 cycle RAM write access latency
+		@ 1 cycle RAM read access latency
+		@ 1 cycle RAM setup latency
+		LDR     r1, =0x00000000
+		STR     r1, [r0,#0x108]		@ tag ram control reg at offset 0x108
+
+		@ Set Data RAM latency
+		@ 1 cycle RAM write access latency
+		@ 2 cycles RAM read access latency
+		@ 1 cycle RAM setup latency
+		LDR     r1, =0x00000000
+		STR     r1, [r0,#0x10C]		@ data ram control reg at offset 0x108
+
+		@Cache maintenance - invalidate 16 ways (0xffff) - base offset 0x77C
+		LDR     r1, =0xFFFF
+		STR     r1, [r0,#0x77C]		@ invalidate by way register at offset 0x77C
+	poll_invalidate:
+		LDR     r1, [r0,#0x77C]		@ invalidate by way register at offset 0x77C
+		TST     r1, #1
+		BNE     poll_invalidate
+
+	/*
+		@ Enable Event Counter Control Register. Reset counter 0 and 1 values
+		LDR     r1, =0x007
+		STR     r1, [r0,#0x200]
+
+		@ Counter 1. Count Drhit event
+		LDR     r1, =0x008
+		STR     r1, [r0,#0x204]
+
+		@ Counter 0. Count Dwhit event
+		LDR     r1, =0x010
+		STR     r1, [r0,#0x208]
+	*/
+
+		@ Ensure L2 remains disabled for the time being
+		LDR     r1, =0x0
+		STR     r1, [r0,#0x100]
+
+	MRC     p15, 4, r0, c15, c0, 0     @ Read periph base address
+		@ SCU offset from base of private peripheral space = 0x000
+
+		LDR     r1, [r0, #0x0]             @ Read the SCU Control Register
+		ORR     r1, r1, #0x1               @ Set bit 0 (The Enable bit)
+		STR     r1, [r0, #0x0]             @ Write back modifed value
+
+		BX	lr
+
+
+
+ENDPROC(l2_pl310_init)
+
+
+#endif
diff --git a/arch/arm/mach-nuvoton/npcm7xx/reset.c b/arch/arm/mach-nuvoton/npcm7xx/reset.c
new file mode 100644
index 0000000000..74f925f67b
--- /dev/null
+++ b/arch/arm/mach-nuvoton/npcm7xx/reset.c
@@ -0,0 +1,46 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * Copyright (c) 2021 Nuvoton Technology Corp.
+ */
+
+#include <common.h>
+#include <asm/io.h>
+#include <asm/arch/rst.h>
+#include <asm/arch/gcr.h>
+#include <asm/arch/cpu.h>
+
+void reset_cpu(ulong ignored)
+{
+	/* Generate a watchdog0 reset */
+	writel(WTCR_WTR | WTCR_WTRE | WTCR_WTE, WTCR0_REG);
+	while (1)
+		;
+}
+
+void reset_misc(void)
+{
+	writel(readl(0xf0800060) & ~(1 << 21), 0xf0800060);
+}
+
+enum reset_type npcm7xx_reset_reason(void)
+{
+	struct npcm_gcr *gcr = (struct npcm_gcr *)npcm_get_base_gcr();
+	enum reset_type type = UNKNOWN_TYPE;
+	u32 value = readl(&gcr->ressr);
+
+	if (value == 0)
+		value = ~readl(&gcr->intcr2);
+
+	if (value & CORST)
+		type = CORST_TYPE;
+	if (value & WD0RST)
+		type = WD0RST_TYPE;
+	if (value & WD1RST)
+		type = WD1RST_TYPE;
+	if (value & WD2RST)
+		type = WD2RST_TYPE;
+	if (value & PORST)
+		type = PORST_TYPE;
+
+	return type;
+}
diff --git a/board/nuvoton/poleg/Kconfig b/board/nuvoton/poleg/Kconfig
new file mode 100644
index 0000000000..b1deef774f
--- /dev/null
+++ b/board/nuvoton/poleg/Kconfig
@@ -0,0 +1,31 @@
+if TARGET_POLEG
+
+config SYS_BOARD
+	default "poleg"
+
+config SYS_VENDOR
+	default "nuvoton"
+
+config SYS_CONFIG_NAME
+	default "poleg"
+
+config NIST_VERSION_ADDR
+	hex "Linux NIST version address"
+	default 0x0
+	help
+	  The address of the Linux NIST version, which should be identical
+	  to the u-boot version.
+
+choice
+	prompt "Target board select"
+	default TARGET_POLEG_EVB
+
+config TARGET_POLEG_EVB
+        bool "Poleg EVB"
+
+config TARGET_POLEG_RUNBMC
+	bool "Poleg RunBMC"
+
+endchoice
+
+endif
diff --git a/board/nuvoton/poleg/Makefile b/board/nuvoton/poleg/Makefile
new file mode 100644
index 0000000000..377433d60a
--- /dev/null
+++ b/board/nuvoton/poleg/Makefile
@@ -0,0 +1 @@
+obj-y	:= poleg_evb.o
diff --git a/board/nuvoton/poleg/poleg_evb.c b/board/nuvoton/poleg/poleg_evb.c
new file mode 100644
index 0000000000..4c455be4ad
--- /dev/null
+++ b/board/nuvoton/poleg/poleg_evb.c
@@ -0,0 +1,52 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ *
+ * Copyright (c) 2021 Nuvoton Technology Corp.
+ */
+
+#include <common.h>
+#include <dm.h>
+#include <asm/arch/cpu.h>
+#include <asm/arch/gcr.h>
+#include <asm/io.h>
+#include <asm/mach-types.h>
+
+DECLARE_GLOBAL_DATA_PTR;
+
+int board_init(void)
+{
+	gd->bd->bi_arch_number = CONFIG_MACH_TYPE;
+	gd->bd->bi_boot_params = (PHYS_SDRAM_1 + 0x100UL);
+
+	return 0;
+}
+
+int dram_init(void)
+{
+	struct npcm_gcr *gcr = (struct npcm_gcr *)npcm_get_base_gcr();
+
+	int ramsize = (readl(&gcr->intcr3) >> 8) & 0x7;
+
+	switch (ramsize) {
+	case 0:
+		gd->ram_size = 0x08000000; /* 128 MB. */
+		break;
+	case 1:
+		gd->ram_size = 0x10000000; /* 256 MB. */
+		break;
+	case 2:
+		gd->ram_size = 0x20000000; /* 512 MB. */
+		break;
+	case 3:
+		gd->ram_size = 0x40000000; /* 1024 MB. */
+		break;
+	case 4:
+		gd->ram_size = 0x80000000; /* 2048 MB. */
+		break;
+
+	default:
+	break;
+	}
+
+	return 0;
+}
diff --git a/include/configs/poleg.h b/include/configs/poleg.h
new file mode 100644
index 0000000000..549b198285
--- /dev/null
+++ b/include/configs/poleg.h
@@ -0,0 +1,77 @@
+/* SPDX-License-Identifier: GPL-2.0+ */
+/*
+ * Copyright (c) 2021 Nuvoton Technology Corp.
+ */
+
+#ifndef __CONFIG_POLEG_H
+#define __CONFIG_POLEG_H
+
+#undef  CONFIG_USE_IRQ
+
+#define CONFIG_ARCH_CPU_INIT
+#define CONFIG_ENV_OVERWRITE
+
+#define CONFIG_MACH_TYPE		        MACH_TYPE_NPCMX50
+
+#define CONFIG_SETUP_MEMORY_TAGS
+#define CONFIG_INITRD_TAG
+
+#ifndef CONFIG_SYS_L2CACHE_OFF
+#define CONFIG_SYS_L2_PL310		1
+#define CONFIG_SYS_PL310_BASE	0xF03FC000       /* L2 - Cache Regs Base (4k Space)*/
+#endif
+#undef CONFIG_SYS_CACHELINE_SIZE
+#define CONFIG_SYS_CACHELINE_SIZE      32
+
+#define CONFIG_SYS_MAXARGS              32
+#define CONFIG_SYS_CBSIZE               256
+#define CONFIG_SYS_PBSIZE               (CONFIG_SYS_CBSIZE + sizeof(CONFIG_SYS_PROMPT) + 16)
+#define CONFIG_SYS_PROMPT_HUSH_PS2	    "> "
+
+#define CONFIG_SYS_BOOTMAPSZ            (0x30 << 20)
+#define CONFIG_SYS_SDRAM_BASE           0x0
+#define CONFIG_SYS_INIT_SP_ADDR         (0x00008000 - GENERATED_GBL_DATA_SIZE)
+#define CONFIG_SYS_MONITOR_LEN          (256 << 10) /* Reserve 256 kB for Monitor   */
+#define CONFIG_SYS_MONITOR_BASE	        CONFIG_SYS_TEXT_BASE
+
+#define CONFIG_SYS_MEMTEST_START	CONFIG_SYS_SDRAM_BASE
+#define CONFIG_SYS_MEMTEST_END		(CONFIG_SYS_MEMTEST_START + 0x08000000)
+
+#define CONFIG_STANDALONE_LOAD_ADDR     0x10000000
+
+#ifndef CONFIG_SYS_MEM_TOP_HIDE
+/* 16MB Graphics Memory size to hide + 32MB for VCD ECE DVC. */
+#define CONFIG_SYS_MEM_TOP_HIDE   ((16 << 20) + (32 << 20))
+#endif
+#define PHYS_SDRAM_1			        CONFIG_SYS_SDRAM_BASE
+
+#define CONFIG_BAUDRATE                 115200
+#define CONFIG_SYS_BAUDRATE_TABLE       {115200, 57600, 38400}
+
+#define CONFIG_SYS_HZ                   1000
+
+/* Default environemnt variables */
+#define CONFIG_BOOTCOMMAND "run common_bootargs; run romboot"
+#define CONFIG_SERVERIP                 192.168.0.1
+#define CONFIG_IPADDR                   192.168.0.2
+#define CONFIG_NETMASK                  255.255.255.0
+#define CONFIG_EXTRA_ENV_SETTINGS   "uimage_flash_addr=80200000\0"   \
+		"stdin=serial\0"   \
+		"stdout=serial\0"   \
+		"stderr=serial\0"    \
+		"ethact=eth${eth_num}\0"   \
+		"romboot=echo Booting from flash; echo +++ uimage at 0x${uimage_flash_addr}; " \
+		"echo Using bootargs: ${bootargs};bootm ${uimage_flash_addr}\0" \
+		"autostart=yes\0"   \
+		"eth_num=0\0"    \
+		"ethaddr=00:00:F7:A0:00:FC\0"    \
+		"eth1addr=00:00:F7:A0:00:FD\0"   \
+		"eth2addr=00:00:F7:A0:00:FE\0"    \
+		"eth3addr=00:00:F7:A0:00:FF\0"    \
+		"common_bootargs=setenv bootargs earlycon=${earlycon} root=/dev/ram "   \
+		"console=${console} mem=${mem} ramdisk_size=48000 basemac=${ethaddr}\0"    \
+		"sd_prog=fatload mmc 0 10000000 image-bmc; cp.b 10000000 80000000 ${filesize}\0"  \
+		"sd_run=fatload mmc 0 10000000 image-bmc; bootm 10200000\0"   \
+		"\0"
+
+#endif
diff --git a/include/dt-bindings/reset/nuvoton,npcm7xx-reset.h b/include/dt-bindings/reset/nuvoton,npcm7xx-reset.h
new file mode 100644
index 0000000000..2831918804
--- /dev/null
+++ b/include/dt-bindings/reset/nuvoton,npcm7xx-reset.h
@@ -0,0 +1,91 @@
+/* SPDX-License-Identifier: GPL-2.0 */
+// Copyright (c) 2020 Nuvoton Technology corporation.
+
+#ifndef _DT_BINDINGS_NPCM8XX_RESET_H
+#define _DT_BINDINGS_NPCM8XX_RESET_H
+
+#define NPCM7XX_RESET_IPSRST1		0x20
+#define NPCM7XX_RESET_IPSRST2		0x24
+#define NPCM7XX_RESET_IPSRST3		0x34
+
+/* Reset lines on IP1 reset module (NPCM8XX_RESET_IPSRST1) */
+#define NPCM7XX_RESET_SPI3		1
+#define NPCM7XX_RESET_UDC1		5
+#define NPCM7XX_RESET_EMAC1		6
+#define NPCM7XX_RESET_UART_2_3		7
+#define NPCM7XX_RESET_UDC2		8
+#define NPCM7XX_RESET_PECI		9
+#define NPCM7XX_RESET_AES		10
+#define NPCM7XX_RESET_UART_0_1		11
+#define NPCM7XX_RESET_MC		12
+#define NPCM7XX_RESET_SMB2		13
+#define NPCM7XX_RESET_SMB3		14
+#define NPCM7XX_RESET_SMB4		15
+#define NPCM7XX_RESET_SMB5		16
+#define NPCM7XX_RESET_PWM_M0		18
+#define NPCM7XX_RESET_TIMER_0_4		19
+#define NPCM7XX_RESET_TIMER_5_9		20
+#define NPCM7XX_RESET_EMAC2		21
+#define NPCM7XX_RESET_UDC4		22
+#define NPCM7XX_RESET_UDC5		23
+#define NPCM7XX_RESET_UDC6		24
+#define NPCM7XX_RESET_UDC3		25
+#define NPCM7XX_RESET_ADC		27
+#define NPCM7XX_RESET_SMB6		28
+#define NPCM7XX_RESET_SMB7		29
+#define NPCM7XX_RESET_SMB0		30
+#define NPCM7XX_RESET_SMB1		31
+
+/* Reset lines on IP2 reset module (NPCM8XX_RESET_IPSRST2) */
+#define NPCM7XX_RESET_MFT0		0
+#define NPCM7XX_RESET_MFT1		1
+#define NPCM7XX_RESET_MFT2		2
+#define NPCM7XX_RESET_MFT3		3
+#define NPCM7XX_RESET_MFT4		4
+#define NPCM7XX_RESET_MFT5		5
+#define NPCM7XX_RESET_MFT6		6
+#define NPCM7XX_RESET_MFT7		7
+#define NPCM7XX_RESET_MMC		8
+#define NPCM7XX_RESET_SDHC		9
+#define NPCM7XX_RESET_GFX_SYS		10
+#define NPCM7XX_RESET_AHB_PCIBRG	11
+#define NPCM7XX_RESET_VDMA		12
+#define NPCM7XX_RESET_ECE		13
+#define NPCM7XX_RESET_VCD		14
+#define NPCM7XX_RESET_OTP		16
+#define NPCM7XX_RESET_SIOX1		18
+#define NPCM7XX_RESET_SIOX2		19
+#define NPCM7XX_RESET_3DES		21
+#define NPCM7XX_RESET_PSPI1		22
+#define NPCM7XX_RESET_PSPI2		23
+#define NPCM7XX_RESET_GMAC2		25
+#define NPCM7XX_RESET_USBH1		26
+#define NPCM7XX_RESET_GMAC1		28
+#define NPCM7XX_RESET_CP1		31
+
+/* Reset lines on IP3 reset module (NPCM8XX_RESET_IPSRST3) */
+#define NPCM7XX_RESET_PWM_M1		0
+#define NPCM7XX_RESET_SMB12		1
+#define NPCM7XX_RESET_SPIX		2
+#define NPCM7XX_RESET_SMB13		3
+#define NPCM7XX_RESET_UDC0		4
+#define NPCM7XX_RESET_UDC7		5
+#define NPCM7XX_RESET_UDC8		6
+#define NPCM7XX_RESET_UDC9		7
+#define NPCM7XX_RESET_PCI_MAILBOX	9
+#define NPCM7XX_RESET_SMB14		12
+#define NPCM7XX_RESET_SHA		13
+#define NPCM7XX_RESET_SEC_ECC		14
+#define NPCM7XX_RESET_PCIE_RC		15
+#define NPCM7XX_RESET_TIMER_10_14	16
+#define NPCM7XX_RESET_RNG		17
+#define NPCM7XX_RESET_SMB15		18
+#define NPCM7XX_RESET_SMB8		19
+#define NPCM7XX_RESET_SMB9		20
+#define NPCM7XX_RESET_SMB10		21
+#define NPCM7XX_RESET_SMB11		22
+#define NPCM7XX_RESET_ESPI		23
+#define NPCM7XX_RESET_USBPHY1		24
+#define NPCM7XX_RESET_USBPHY2		25
+
+#endif
-- 
2.17.1


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

* Re: [PATCH v1 2/6] ARM: dts: Add Nuvoton NPCM750 device tree
  2022-04-06  7:57 ` [PATCH v1 2/6] ARM: dts: Add Nuvoton NPCM750 device tree Jim Liu
@ 2022-04-06 13:38   ` Tom Rini
  0 siblings, 0 replies; 14+ messages in thread
From: Tom Rini @ 2022-04-06 13:38 UTC (permalink / raw)
  To: Jim Liu; +Cc: JJLIU0, YSCHU, KWLIU, lukma, seanga2, sjg, sr, u-boot

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

On Wed, Apr 06, 2022 at 03:57:33PM +0800, Jim Liu wrote:

> Add a common device tree for all Nuvoton NPCM7xx BMCs and a board
> specific device tree for the NPCM750(Poleg) evaluation board.
> 
> Signed-off-by: Jim Liu <JJLIU0@nuvoton.com>

Have these been submitted to upstream Linux yet?  And please note:

> ---
>  arch/arm/dts/Makefile                        |    1 +
>  arch/arm/dts/nuvoton-common-npcm7xx.dtsi     | 1120 ++++++++++++++++++
>  arch/arm/dts/nuvoton-npcm750-buv-pincfg.dtsi |  132 +++
>  arch/arm/dts/nuvoton-npcm750-buv.dts         |  198 ++++
>  arch/arm/dts/nuvoton-npcm750.dtsi            |   63 +
>  arch/arm/dts/nuvoton-npcm7xx-uboot.dtsi      |  263 ++++

This should be named nuvoton-npcm7xx-u-boot.dtsi and get automatically
included (see scripts/Makefile.lib for the automatic include logic), and
if there's no way for the automatic include logic to do what you're
wanting, it should still be -u-boot.dtsi for consistency.

Also, this patch along with 1/6 and 6/6 should be combined to a single
patch adding basic support, and then the rest of the patches following
on top of that.  Thanks.

-- 
Tom

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

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

* Re: [PATCH v1 1/6] ARM: configs: Add defconfig for Nuvoton NPCM750
  2022-04-06  7:57 ` [PATCH v1 1/6] ARM: configs: Add defconfig for Nuvoton NPCM750 Jim Liu
@ 2022-04-06 13:39   ` Tom Rini
  0 siblings, 0 replies; 14+ messages in thread
From: Tom Rini @ 2022-04-06 13:39 UTC (permalink / raw)
  To: Jim Liu; +Cc: JJLIU0, YSCHU, KWLIU, lukma, seanga2, sjg, sr, u-boot

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

On Wed, Apr 06, 2022 at 03:57:32PM +0800, Jim Liu wrote:

> Add defconfig for NPCM750 BUV (Poleg).
> 
> Signed-off-by: Jim Liu <JJLIU0@nuvoton.com>
> ---
>  board/nuvoton/poleg/MAINTAINERS |  7 +++++
>  configs/PolegRunBMC_defconfig   | 50 +++++++++++++++++++++++++++++++++

This defconfig was not made with "make savedefconfig", please
re-generate it that way for the next iteration, thanks.

-- 
Tom

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

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

* Re: [PATCH v1 6/6] arm: nuvoton: Add support for Nuvoton NPCM750 BMC
  2022-04-06  7:57 ` [PATCH v1 6/6] arm: nuvoton: Add support for Nuvoton NPCM750 BMC Jim Liu
@ 2022-04-06 13:48   ` Tom Rini
  0 siblings, 0 replies; 14+ messages in thread
From: Tom Rini @ 2022-04-06 13:48 UTC (permalink / raw)
  To: Jim Liu; +Cc: JJLIU0, YSCHU, KWLIU, lukma, seanga2, sjg, sr, u-boot

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

On Wed, Apr 06, 2022 at 03:57:37PM +0800, Jim Liu wrote:

> Add basic support for the Nuvoton NPCM750 BMC
> 
> Signed-off-by: Jim Liu <JJLIU0@nuvoton.com>
[snip]
> diff --git a/arch/arm/Kconfig b/arch/arm/Kconfig
> index 4567c183fb..45ab2793b2 100644
> --- a/arch/arm/Kconfig
> +++ b/arch/arm/Kconfig
> @@ -922,6 +922,12 @@ config ARCH_NEXELL
>  	select DM
>  	select GPIO_EXTRA_HEADER
>  
> +config ARCH_NPCM
> +        bool "Support Nuvoton SoCs"
> +        select DM
> +        select OF_CONTROL
> +        imply CMD_DM

I see this in a lot of your Kconfig changes, the spacing is
wrong/inconsistent, please fix to be a single tab of indentation.

> diff --git a/arch/arm/mach-nuvoton/npcm7xx/reset.c b/arch/arm/mach-nuvoton/npcm7xx/reset.c
> new file mode 100644
> index 0000000000..74f925f67b
> --- /dev/null
> +++ b/arch/arm/mach-nuvoton/npcm7xx/reset.c

I feel this should be doing something under/with drivers/reset/ instead.

> +int board_init(void)
> +{
> +	gd->bd->bi_arch_number = CONFIG_MACH_TYPE;
> +	gd->bd->bi_boot_params = (PHYS_SDRAM_1 + 0x100UL);

Do you really need to support non-DT kernels?  CONFIG_MACH_TYPE should
likely not be used here.

> diff --git a/include/configs/poleg.h b/include/configs/poleg.h
> new file mode 100644
> index 0000000000..549b198285
> --- /dev/null
> +++ b/include/configs/poleg.h
> @@ -0,0 +1,77 @@
> +/* SPDX-License-Identifier: GPL-2.0+ */
> +/*
> + * Copyright (c) 2021 Nuvoton Technology Corp.
> + */
> +
> +#ifndef __CONFIG_POLEG_H
> +#define __CONFIG_POLEG_H
> +
> +#undef  CONFIG_USE_IRQ

Ugh, I see that line made it back in, in another board.  That's not
meaningful.

> +#define CONFIG_ARCH_CPU_INIT
> +#define CONFIG_ENV_OVERWRITE
> +
> +#define CONFIG_MACH_TYPE		        MACH_TYPE_NPCMX50
> +
> +#define CONFIG_SETUP_MEMORY_TAGS
> +#define CONFIG_INITRD_TAG

TAGS are part of Kconfig, if you _really_ need them still.  Please make
use of CI:
https://u-boot.readthedocs.io/en/latest/develop/ci_testing.html
to make sure the series passes there as we have tests to catch things
which need to be in Kconfig not board.h files such as this and some
others that follow.

> +#define CONFIG_SYS_BAUDRATE_TABLE       {115200, 57600, 38400}

Please just use the default baudrate table.

> diff --git a/include/dt-bindings/reset/nuvoton,npcm7xx-reset.h b/include/dt-bindings/reset/nuvoton,npcm7xx-reset.h
> new file mode 100644
> index 0000000000..2831918804
> --- /dev/null
> +++ b/include/dt-bindings/reset/nuvoton,npcm7xx-reset.h

Is this coming in unmodified from Linux?  Thanks!

-- 
Tom

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

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

* Re: [PATCH v1 5/6] clk: nuvoton: Add support for NPCM750
  2022-04-06  7:57 ` [PATCH v1 5/6] clk: nuvoton: Add support for NPCM750 Jim Liu
@ 2022-04-06 18:19   ` Sean Anderson
  2022-04-08  9:12     ` Jim Liu
  0 siblings, 1 reply; 14+ messages in thread
From: Sean Anderson @ 2022-04-06 18:19 UTC (permalink / raw)
  To: Jim Liu, JJLIU0, YSCHU, KWLIU, lukma, sjg, sr, trini; +Cc: u-boot

On 4/6/22 3:57 AM, Jim Liu wrote:
> Add clock controller driver for NPCM750
> 
> Signed-off-by: Jim Liu <JJLIU0@nuvoton.com>

This looks very similar to the NPCM845 driver. Would it be possible to combine them?

--Sean

> ---
>   drivers/clk/Makefile                          |   1 +
>   drivers/clk/nuvoton/Makefile                  |   1 +
>   drivers/clk/nuvoton/clk_npcm7xx.c             | 469 ++++++++++++++++++
>   .../dt-bindings/clock/nuvoton,npcm7xx-clock.h |  46 ++
>   4 files changed, 517 insertions(+)
>   create mode 100644 drivers/clk/nuvoton/Makefile
>   create mode 100644 drivers/clk/nuvoton/clk_npcm7xx.c
>   create mode 100644 include/dt-bindings/clock/nuvoton,npcm7xx-clock.h
> 
> diff --git a/drivers/clk/Makefile b/drivers/clk/Makefile
> index bb4eee5d99..f5b553172c 100644
> --- a/drivers/clk/Makefile
> +++ b/drivers/clk/Makefile
> @@ -20,6 +20,7 @@ obj-$(CONFIG_ARCH_ASPEED) += aspeed/
>   obj-$(CONFIG_ARCH_MEDIATEK) += mediatek/
>   obj-$(CONFIG_ARCH_MESON) += meson/
>   obj-$(CONFIG_ARCH_MTMIPS) += mtmips/
> +obj-$(CONFIG_ARCH_NPCM) += nuvoton/
>   obj-$(CONFIG_ARCH_ROCKCHIP) += rockchip/
>   obj-$(CONFIG_ARCH_SOCFPGA) += altera/
>   obj-$(CONFIG_ARCH_SUNXI) += sunxi/
> diff --git a/drivers/clk/nuvoton/Makefile b/drivers/clk/nuvoton/Makefile
> new file mode 100644
> index 0000000000..4e7b8dfde8
> --- /dev/null
> +++ b/drivers/clk/nuvoton/Makefile
> @@ -0,0 +1 @@
> +obj-$(CONFIG_ARCH_NPCM7xx) += clk_npcm7xx.o
> diff --git a/drivers/clk/nuvoton/clk_npcm7xx.c b/drivers/clk/nuvoton/clk_npcm7xx.c
> new file mode 100644
> index 0000000000..a37993eaae
> --- /dev/null
> +++ b/drivers/clk/nuvoton/clk_npcm7xx.c
> @@ -0,0 +1,469 @@
> +// SPDX-License-Identifier: GPL-2.0+
> +/*
> + * Copyright (c) 2021 Nuvoton Technology Corp.
> + */
> +
> +#include <common.h>
> +#include <clk-uclass.h>
> +#include <div64.h>
> +#include <dm.h>
> +#include <asm/io.h>
> +#include <linux/bitfield.h>
> +#include <linux/log2.h>
> +#include <dt-bindings/clock/nuvoton,npcm7xx-clock.h>
> +
> +/* Register offsets */
> +#define CLKSEL		0x04	/* clock source selection */
> +#define CLKDIV1		0x08	/* clock divider 1 */
> +#define CLKDIV2		0x2C	/* clock divider 2 */
> +#define CLKDIV3		0x58	/* clock divider 3 */
> +#define PLLCON0		0x0C	/* pll0 control */
> +#define PLLCON1		0x10	/* pll1 control */
> +#define PLLCON2		0x54	/* pll2 control */
> +
> +/* PLLCON bit filed */
> +#define PLLCON_INDV	GENMASK(5, 0)
> +#define PLLCON_OTDV1	GENMASK(10, 8)
> +#define PLLCON_OTDV2	GENMASK(15, 13)
> +#define PLLCON_FBDV	GENMASK(27, 16)
> +
> +/* CLKSEL bit filed */
> +#define CPUCKSEL	GENMASK(1, 0)
> +#define SDCKSEL		GENMASK(7, 6)
> +#define UARTCKSEL	GENMASK(9, 8)
> +#define TIMCKSEL	GENMASK(15, 14)
> +
> +/* CLKDIV1 bit filed */
> +#define SPI3CKDIV	GENMASK(10, 6)
> +#define MMCCKDIV	GENMASK(15, 11)
> +#define UARTDIV1	GENMASK(20, 16)
> +#define TIMCKDIV	GENMASK(25, 21)
> +#define CLK4DIV		GENMASK(27, 26)
> +
> +/* CLKDIV2 bit filed */
> +#define APB5CKDIV	GENMASK(23, 22)
> +#define APB2CKDIV	GENMASK(27, 26)
> +
> +/* CLKDIV3 bit filed */
> +#define SPIXCKDIV	GENMASK(5, 1)
> +#define SPI0CKDIV	GENMASK(10, 6)
> +#define UARTDIV2	GENMASK(15, 11)
> +#define SPI1CKDIV	GENMASK(23, 16)
> +
> +/* Flags */
> +#define DIV_TYPE1	BIT(0)	/* div = clkdiv + 1 */
> +#define DIV_TYPE2	BIT(1)	/* div = 1 << clkdiv */
> +#define PRE_DIV2	BIT(2)	/* Pre divisor = 2 */
> +#define POST_DIV2	BIT(3)	/* Post divisor = 2 */
> +#define FIXED_PARENT	BIT(4)	/* clock source is fixed */
> +
> +struct npcm_clk_priv {
> +	struct udevice *dev;
> +	void __iomem *base;
> +};
> +
> +/* Parameters of PLL configuration */
> +struct npcm_clk_pll {
> +	const int id;
> +	const int parent_id;
> +	u32 reg;
> +	u32 flags;
> +};
> +
> +/* Parent clock id to clksel mapping */
> +struct parent_data {
> +	int id;
> +	int clksel;
> +};
> +
> +/* Parameters of parent selection */
> +struct npcm_clk_select {
> +	const int id;
> +	const struct parent_data *parents;
> +	u32 reg;
> +	u32 mask;
> +	u8 num_parents;
> +	u32 flags;
> +};
> +
> +/* Parameters of clock divider */
> +struct npcm_clk_div {
> +	const int id;
> +	u32 reg;
> +	u32 mask;
> +	u32 flags;
> +};
> +
> +/* Parent clock map */
> +static const struct parent_data pll_parents[] = {
> +	{NPCM7XX_CLK_PLL0, 0},
> +	{NPCM7XX_CLK_PLL1, 1},
> +	{NPCM7XX_CLK_REFCLK, 2},
> +	{NPCM7XX_CLK_PLL2DIV2, 3}
> +};
> +
> +static const struct parent_data cpuck_parents[] = {
> +	{NPCM7XX_CLK_PLL0, 0},
> +	{NPCM7XX_CLK_PLL1, 1},
> +	{NPCM7XX_CLK_REFCLK, 2},
> +	{NPCM7XX_CLK_PLL2, 7}
> +};
> +
> +static const struct parent_data apb_parent[] = {{NPCM7XX_CLK_AHB, 0}};
> +
> +static struct npcm_clk_pll npcm7xx_clk_plls[] = {
> +	{NPCM7XX_CLK_PLL0, NPCM7XX_CLK_REFCLK, PLLCON0, 0},
> +	{NPCM7XX_CLK_PLL1, NPCM7XX_CLK_REFCLK, PLLCON1, 0},
> +	{NPCM7XX_CLK_PLL2, NPCM7XX_CLK_REFCLK, PLLCON2, 0},
> +	{NPCM7XX_CLK_PLL2DIV2, NPCM7XX_CLK_REFCLK, PLLCON2, POST_DIV2}
> +};
> +
> +static struct npcm_clk_select npcm7xx_clk_selectors[] = {
> +	{NPCM7XX_CLK_AHB, cpuck_parents, CLKSEL, CPUCKSEL, 4, 0},
> +	{NPCM7XX_CLK_APB2, apb_parent, 0, 0, 1, FIXED_PARENT},
> +	{NPCM7XX_CLK_APB5, apb_parent, 0, 0, 1, FIXED_PARENT},
> +	{NPCM7XX_CLK_SPI0, apb_parent, 0, 0, 1, FIXED_PARENT},
> +	{NPCM7XX_CLK_SPI3, apb_parent, 0, 0, 1, FIXED_PARENT},
> +	{NPCM7XX_CLK_SPIX, apb_parent, 0, 0, 1, FIXED_PARENT},
> +	{NPCM7XX_CLK_UART, pll_parents, CLKSEL, UARTCKSEL, 4, 0},
> +	{NPCM7XX_CLK_TIMER, pll_parents, CLKSEL, TIMCKSEL, 4, 0},
> +	{NPCM7XX_CLK_SDHC, pll_parents, CLKSEL, SDCKSEL, 4, 0}
> +};
> +
> +static struct npcm_clk_div npcm7xx_clk_dividers[] = {
> +	{NPCM7XX_CLK_AHB, CLKDIV1, CLK4DIV, DIV_TYPE1 | PRE_DIV2},
> +	{NPCM7XX_CLK_APB2, CLKDIV2, APB2CKDIV, DIV_TYPE2},
> +	{NPCM7XX_CLK_APB5, CLKDIV2, APB5CKDIV, DIV_TYPE2},
> +	{NPCM7XX_CLK_SPI0, CLKDIV3, SPI0CKDIV, DIV_TYPE1},
> +	{NPCM7XX_CLK_SPI3, CLKDIV1, SPI3CKDIV, DIV_TYPE1},
> +	{NPCM7XX_CLK_SPIX, CLKDIV3, SPIXCKDIV, DIV_TYPE1},
> +	{NPCM7XX_CLK_UART, CLKDIV1, UARTDIV1, DIV_TYPE1},
> +	{NPCM7XX_CLK_TIMER, CLKDIV1, TIMCKDIV, DIV_TYPE2},
> +	{NPCM7XX_CLK_SDHC, CLKDIV1, MMCCKDIV, DIV_TYPE1}
> +};
> +
> +static int clkid_to_clksel(struct npcm_clk_select *selector, int id)
> +{
> +	int i;
> +
> +	for (i = 0; i < selector->num_parents; i++) {
> +		if (selector->parents[i].id == id)
> +			return selector->parents[i].clksel;
> +	}
> +
> +	return -EINVAL;
> +}
> +
> +static int clksel_to_clkid(struct npcm_clk_select *selector, int clksel)
> +{
> +	int i;
> +
> +	for (i = 0; i < selector->num_parents; i++) {
> +		if (selector->parents[i].clksel == clksel)
> +			return selector->parents[i].id;
> +	}
> +
> +	return -EINVAL;
> +}
> +
> +static struct npcm_clk_pll *npcm_clk_pll_get(int clk_id)
> +{
> +	int i;
> +
> +	for (i = 0; i < ARRAY_SIZE(npcm7xx_clk_plls); i++) {
> +		if (npcm7xx_clk_plls[i].id == clk_id)
> +			return &npcm7xx_clk_plls[i];
> +	}
> +
> +	return NULL;
> +}
> +
> +static struct npcm_clk_select *npcm_clk_selector_get(int clk_id)
> +{
> +	int i;
> +
> +	for (i = 0; i < ARRAY_SIZE(npcm7xx_clk_selectors); i++) {
> +		if (npcm7xx_clk_selectors[i].id == clk_id)
> +			return &npcm7xx_clk_selectors[i];
> +	}
> +
> +	return NULL;
> +}
> +
> +static struct npcm_clk_div *npcm_clk_divider_get(int clk_id)
> +{
> +	int i;
> +
> +	for (i = 0; i < ARRAY_SIZE(npcm7xx_clk_dividers); i++) {
> +		if (npcm7xx_clk_dividers[i].id == clk_id)
> +			return &npcm7xx_clk_dividers[i];
> +	}
> +
> +	return NULL;
> +}
> +
> +static ulong npcm_clk_get_fin(struct npcm_clk_priv *priv, int id)
> +{
> +	struct npcm_clk_select *selector;
> +	struct clk parent;
> +	ulong parent_rate;
> +	u32 val, clksel;
> +	int ret;
> +
> +	selector = npcm_clk_selector_get(id);
> +	if (!selector)
> +		return 0;
> +
> +	if (selector->flags & FIXED_PARENT) {
> +		clksel = 0;
> +	} else {
> +		val = readl(priv->base + selector->reg);
> +		clksel = (val & selector->mask) >> (ffs(selector->mask) - 1);
> +	}
> +	parent.id = clksel_to_clkid(selector, clksel);
> +
> +	ret = clk_request(priv->dev, &parent);
> +	if (ret)
> +		return 0;
> +
> +	parent_rate = clk_get_rate(&parent);
> +
> +	debug("fin of clk%d = %lu\n", id, parent_rate);
> +	return parent_rate;
> +}
> +
> +static u32 npcm_clk_get_div(struct npcm_clk_priv *priv, int id)
> +{
> +	struct npcm_clk_div *divider;
> +	u32 val, div;
> +
> +	divider = npcm_clk_divider_get(id);
> +	if (!divider)
> +		return 0;
> +
> +	val = readl(priv->base + divider->reg);
> +	div = (val & divider->mask) >> (ffs(divider->mask) - 1);
> +	if (divider->flags & DIV_TYPE1)
> +		div = div + 1;
> +	else
> +		div = 1 << div;
> +
> +	if (divider->flags & PRE_DIV2)
> +		div = div << 1;
> +
> +	return div;
> +}
> +
> +static u32 npcm_clk_set_div(struct npcm_clk_priv *priv, int id, u32 div)
> +{
> +	struct npcm_clk_div *divider;
> +	u32 val, clkdiv;
> +
> +	divider = npcm_clk_divider_get(id);
> +	if (!divider)
> +		return -EINVAL;
> +
> +	if (divider->flags & PRE_DIV2)
> +		div = div >> 1;
> +
> +	if (divider->flags & DIV_TYPE1)
> +		clkdiv = div - 1;
> +	else
> +		clkdiv = ilog2(div);
> +
> +	val = readl(priv->base + divider->reg);
> +	val &= ~divider->mask;
> +	val |= (clkdiv << (ffs(divider->mask) - 1)) & divider->mask;
> +	writel(val, priv->base + divider->reg);
> +
> +	return 0;
> +}
> +
> +static ulong npcm_clk_get_fout(struct npcm_clk_priv *priv, int id)
> +{
> +	ulong parent_rate;
> +	u32 div;
> +
> +	parent_rate = npcm_clk_get_fin(priv, id);
> +	if (!parent_rate)
> +		return -EINVAL;
> +
> +	div = npcm_clk_get_div(priv, id);
> +	if (!div)
> +		return -EINVAL;
> +
> +	debug("fout of clk%d = (%lu / %u)\n", id, parent_rate, div);
> +	return (parent_rate / div);
> +}
> +
> +static ulong npcm_clk_set_fout(struct npcm_clk_priv *priv, int id, ulong rate)
> +{
> +	u32 div;
> +	ulong parent_rate;
> +	int ret;
> +
> +	parent_rate = npcm_clk_get_fin(priv, id);
> +	if (!parent_rate)
> +		return -EINVAL;
> +
> +	div = DIV_ROUND_UP(parent_rate, rate);
> +	ret = npcm_clk_set_div(priv, id, div);
> +	if (ret)
> +		return ret;
> +
> +	debug("%s: rate %lu, new rate (%lu / %u)\n", __func__, rate, parent_rate, div);
> +	return (parent_rate / div);
> +}
> +
> +static ulong npcm_clk_get_pll_fout(struct npcm_clk_priv *priv, int id)
> +{
> +	struct npcm_clk_pll *pll;
> +	struct clk parent;
> +	ulong parent_rate;
> +	ulong fbdv, indv, otdv1, otdv2;
> +	u32 val;
> +	u64 ret;
> +
> +	pll = npcm_clk_pll_get(id);
> +	if (!pll)
> +		return -ENODEV;
> +
> +	parent.id = pll->parent_id;
> +	ret = clk_request(priv->dev, &parent);
> +	if (ret)
> +		return ret;
> +
> +	parent_rate = clk_get_rate(&parent);
> +
> +	val = readl(priv->base + pll->reg);
> +	indv = FIELD_GET(PLLCON_INDV, val);
> +	fbdv = FIELD_GET(PLLCON_FBDV, val);
> +	otdv1 = FIELD_GET(PLLCON_OTDV1, val);
> +	otdv2 = FIELD_GET(PLLCON_OTDV2, val);
> +
> +	ret = (u64)parent_rate * fbdv;
> +	do_div(ret, indv * otdv1 * otdv2);
> +	if (pll->flags & POST_DIV2)
> +		do_div(ret, 2);
> +
> +	debug("fout of pll(id %d) = %llu\n", id, ret);
> +	return ret;
> +}
> +
> +static ulong npcm_clk_get_rate(struct clk *clk)
> +{
> +	struct npcm_clk_priv *priv = dev_get_priv(clk->dev);
> +	struct clk refclk;
> +	int ret;
> +
> +	debug("%s: id %lu\n", __func__, clk->id);
> +	switch (clk->id) {
> +	case NPCM7XX_CLK_TIMER:
> +	case NPCM7XX_CLK_REFCLK:
> +		ret = clk_get_by_name(priv->dev, "refclk", &refclk);
> +		if (!ret)
> +			return clk_get_rate(&refclk);
> +		else
> +			return ret;
> +	case NPCM7XX_CLK_PLL0:
> +	case NPCM7XX_CLK_PLL1:
> +	case NPCM7XX_CLK_PLL2:
> +	case NPCM7XX_CLK_PLL2DIV2:
> +		return npcm_clk_get_pll_fout(priv, clk->id);
> +	case NPCM7XX_CLK_AHB:
> +	case NPCM7XX_CLK_APB2:
> +	case NPCM7XX_CLK_APB5:
> +	case NPCM7XX_CLK_SDHC:
> +	case NPCM7XX_CLK_UART:
> +	case NPCM7XX_CLK_SPI0:
> +	case NPCM7XX_CLK_SPI3:
> +	case NPCM7XX_CLK_SPIX:
> +		return npcm_clk_get_fout(priv, clk->id);
> +	default:
> +		return -ENOSYS;
> +	}
> +}
> +
> +static ulong npcm_clk_set_rate(struct clk *clk, ulong rate)
> +{
> +	struct npcm_clk_priv *priv = dev_get_priv(clk->dev);
> +
> +	debug("%s: id %lu, rate %lu\n", __func__, clk->id, rate);
> +	switch (clk->id) {
> +	case NPCM7XX_CLK_TIMER:
> +	case NPCM7XX_CLK_SDHC:
> +	case NPCM7XX_CLK_UART:
> +	case NPCM7XX_CLK_SPI0:
> +	case NPCM7XX_CLK_SPI3:
> +	case NPCM7XX_CLK_SPIX:
> +		return  npcm_clk_set_fout(priv, clk->id, rate);
> +	default:
> +		return -ENOSYS;
> +	}
> +}
> +
> +static int npcm_clk_set_parent(struct clk *clk, struct clk *parent)
> +{
> +	struct npcm_clk_priv *priv = dev_get_priv(clk->dev);
> +	struct npcm_clk_select *selector;
> +	int clksel;
> +	u32 val;
> +
> +	debug("%s: id %lu, parent %lu\n", __func__, clk->id, parent->id);
> +	selector = npcm_clk_selector_get(clk->id);
> +	if (!selector)
> +		return -EINVAL;
> +
> +	clksel = clkid_to_clksel(selector, parent->id);
> +	if (clksel < 0)
> +		return -EINVAL;
> +
> +	val = readl(priv->base + selector->reg);
> +	val &= ~selector->mask;
> +	val |= clksel << (ffs(selector->mask) - 1);
> +	writel(val, priv->base + selector->reg);
> +
> +	return 0;
> +}
> +
> +static int npcm_clk_request(struct clk *clk)
> +{
> +	if (clk->id >= NPCM7XX_NUM_CLOCKS)
> +		return -EINVAL;
> +
> +	return 0;
> +}
> +
> +static struct clk_ops npcm_clk_ops = {
> +	.get_rate = npcm_clk_get_rate,
> +	.set_rate = npcm_clk_set_rate,
> +	.set_parent = npcm_clk_set_parent,
> +	.request = npcm_clk_request,
> +};
> +
> +static int npcm_clk_probe(struct udevice *dev)
> +{
> +	struct npcm_clk_priv *priv = dev_get_priv(dev);
> +
> +	priv->base = dev_read_addr_ptr(dev);
> +	if (!priv->base)
> +		return -EINVAL;
> +	priv->dev = dev;
> +
> +	return 0;
> +}
> +
> +static const struct udevice_id npcm_clk_ids[] = {
> +	{ .compatible = "nuvoton,npcm750-clk" },
> +	{ }
> +};
> +
> +U_BOOT_DRIVER(clk_npcm) = {
> +	.name           = "clk_npcm",
> +	.id             = UCLASS_CLK,
> +	.of_match       = npcm_clk_ids,
> +	.ops            = &npcm_clk_ops,
> +	.priv_auto	= sizeof(struct npcm_clk_priv),
> +	.probe          = npcm_clk_probe,
> +	.flags = DM_FLAG_PRE_RELOC,
> +};
> diff --git a/include/dt-bindings/clock/nuvoton,npcm7xx-clock.h b/include/dt-bindings/clock/nuvoton,npcm7xx-clock.h
> new file mode 100644
> index 0000000000..65e6bc4eee
> --- /dev/null
> +++ b/include/dt-bindings/clock/nuvoton,npcm7xx-clock.h
> @@ -0,0 +1,46 @@
> +/* SPDX-License-Identifier: GPL-2.0 */
> +/*
> + * Nuvoton NPCM7xx Clock Generator binding
> + * clock binding number for all clocks supportted by nuvoton,npcm7xx-clk
> + *
> + * Copyright (C) 2018 Nuvoton Technologies tali.perry@nuvoton.com
> + *
> + */
> +
> +#ifndef __DT_BINDINGS_CLOCK_NPCM7XX_H
> +#define __DT_BINDINGS_CLOCK_NPCM7XX_H
> +
> +#define NPCM7XX_CLK_CPU		0
> +#define NPCM7XX_CLK_GFX_PIXEL	1
> +#define NPCM7XX_CLK_MC		2
> +#define NPCM7XX_CLK_ADC		3
> +#define NPCM7XX_CLK_AHB		4
> +#define NPCM7XX_CLK_TIMER	5
> +#define NPCM7XX_CLK_UART	6
> +#define NPCM7XX_CLK_MMC		7
> +#define NPCM7XX_CLK_SPI3	8
> +#define NPCM7XX_CLK_PCI		9
> +#define NPCM7XX_CLK_AXI		10
> +#define NPCM7XX_CLK_APB4	11
> +#define NPCM7XX_CLK_APB3	12
> +#define NPCM7XX_CLK_APB2	13
> +#define NPCM7XX_CLK_APB1	14
> +#define NPCM7XX_CLK_APB5	15
> +#define NPCM7XX_CLK_CLKOUT	16
> +#define NPCM7XX_CLK_GFX		17
> +#define NPCM7XX_CLK_SU		18
> +#define NPCM7XX_CLK_SU48	19
> +#define NPCM7XX_CLK_SDHC	20
> +#define NPCM7XX_CLK_SPI0	21
> +#define NPCM7XX_CLK_SPIX	22
> +#define NPCM7XX_CLK_REFCLK	23
> +#define NPCM7XX_CLK_SYSBYPCK	24
> +#define NPCM7XX_CLK_MCBYPCK	25
> +#define NPCM7XX_CLK_PLL0	26
> +#define NPCM7XX_CLK_PLL1	27
> +#define NPCM7XX_CLK_PLL2	28
> +#define NPCM7XX_CLK_PLL2DIV2	29
> +#define NPCM7XX_NUM_CLOCKS	(NPCM7XX_CLK_PLL2DIV2 + 1)
> +
> +#endif
> +
> 


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

* Re: [PATCH v1 0/6] Add Nuvoton NPCM750 support
  2022-04-06  7:57 [PATCH v1 0/6] Add Nuvoton NPCM750 support Jim Liu
                   ` (5 preceding siblings ...)
  2022-04-06  7:57 ` [PATCH v1 6/6] arm: nuvoton: Add support for Nuvoton NPCM750 BMC Jim Liu
@ 2022-04-06 19:45 ` Tom Rini
  2022-04-08  9:25   ` Jim Liu
  6 siblings, 1 reply; 14+ messages in thread
From: Tom Rini @ 2022-04-06 19:45 UTC (permalink / raw)
  To: Jim Liu; +Cc: JJLIU0, YSCHU, KWLIU, lukma, seanga2, sjg, sr, u-boot

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

On Wed, Apr 06, 2022 at 03:57:31PM +0800, Jim Liu wrote:

> The patch series add basic supoorts for NPCM750, which
> is Nuvoton's 3th-generation BMC (Baseboard Management Controller).
> Add drivers to support Clock,Timer,Uart for NPCM7xx SoC.
> 
> the NPCM750 computing subsystem comprises a dual-core ARM a9
> at 800MHz speed with L1/L2 caches
> 
> Jim Liu (6):
>   ARM: configs: Add defconfig for Nuvoton NPCM750
>   ARM: dts: Add Nuvoton NPCM750 device tree
>   timer: npcm: Add NPCM timer support
>   serial: npcm: Add support for Nuvoton NPCM SoCs
>   clk: nuvoton: Add support for NPCM750
>   arm: nuvoton: Add support for Nuvoton NPCM750 BMC

One last bit of overall feedback is that this, and the NPCM8xx support
need to be coordinated, and sharing as much driver/etc code, pulling SoC
differences from DT, as possible.  Thanks.

-- 
Tom

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

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

* Re: [PATCH v1 5/6] clk: nuvoton: Add support for NPCM750
  2022-04-06 18:19   ` Sean Anderson
@ 2022-04-08  9:12     ` Jim Liu
  0 siblings, 0 replies; 14+ messages in thread
From: Jim Liu @ 2022-04-08  9:12 UTC (permalink / raw)
  To: Sean Anderson; +Cc: Jim Liu, Stanley Chu, KWLIU, lukma, sjg, sr, trini, u-boot

Hi  Sean

thanks for your reply.
i will combine them for version 2


Sean Anderson <seanga2@gmail.com> 於 2022年4月7日 週四 上午2:19寫道:

>
> On 4/6/22 3:57 AM, Jim Liu wrote:
> > Add clock controller driver for NPCM750
> >
> > Signed-off-by: Jim Liu <JJLIU0@nuvoton.com>
>
> This looks very similar to the NPCM845 driver. Would it be possible to combine them?
>
> --Sean
>
> > ---
> >   drivers/clk/Makefile                          |   1 +
> >   drivers/clk/nuvoton/Makefile                  |   1 +
> >   drivers/clk/nuvoton/clk_npcm7xx.c             | 469 ++++++++++++++++++
> >   .../dt-bindings/clock/nuvoton,npcm7xx-clock.h |  46 ++
> >   4 files changed, 517 insertions(+)
> >   create mode 100644 drivers/clk/nuvoton/Makefile
> >   create mode 100644 drivers/clk/nuvoton/clk_npcm7xx.c
> >   create mode 100644 include/dt-bindings/clock/nuvoton,npcm7xx-clock.h
> >
> > diff --git a/drivers/clk/Makefile b/drivers/clk/Makefile
> > index bb4eee5d99..f5b553172c 100644
> > --- a/drivers/clk/Makefile
> > +++ b/drivers/clk/Makefile
> > @@ -20,6 +20,7 @@ obj-$(CONFIG_ARCH_ASPEED) += aspeed/
> >   obj-$(CONFIG_ARCH_MEDIATEK) += mediatek/
> >   obj-$(CONFIG_ARCH_MESON) += meson/
> >   obj-$(CONFIG_ARCH_MTMIPS) += mtmips/
> > +obj-$(CONFIG_ARCH_NPCM) += nuvoton/
> >   obj-$(CONFIG_ARCH_ROCKCHIP) += rockchip/
> >   obj-$(CONFIG_ARCH_SOCFPGA) += altera/
> >   obj-$(CONFIG_ARCH_SUNXI) += sunxi/
> > diff --git a/drivers/clk/nuvoton/Makefile b/drivers/clk/nuvoton/Makefile
> > new file mode 100644
> > index 0000000000..4e7b8dfde8
> > --- /dev/null
> > +++ b/drivers/clk/nuvoton/Makefile
> > @@ -0,0 +1 @@
> > +obj-$(CONFIG_ARCH_NPCM7xx) += clk_npcm7xx.o
> > diff --git a/drivers/clk/nuvoton/clk_npcm7xx.c b/drivers/clk/nuvoton/clk_npcm7xx.c
> > new file mode 100644
> > index 0000000000..a37993eaae
> > --- /dev/null
> > +++ b/drivers/clk/nuvoton/clk_npcm7xx.c
> > @@ -0,0 +1,469 @@
> > +// SPDX-License-Identifier: GPL-2.0+
> > +/*
> > + * Copyright (c) 2021 Nuvoton Technology Corp.
> > + */
> > +
> > +#include <common.h>
> > +#include <clk-uclass.h>
> > +#include <div64.h>
> > +#include <dm.h>
> > +#include <asm/io.h>
> > +#include <linux/bitfield.h>
> > +#include <linux/log2.h>
> > +#include <dt-bindings/clock/nuvoton,npcm7xx-clock.h>
> > +
> > +/* Register offsets */
> > +#define CLKSEL               0x04    /* clock source selection */
> > +#define CLKDIV1              0x08    /* clock divider 1 */
> > +#define CLKDIV2              0x2C    /* clock divider 2 */
> > +#define CLKDIV3              0x58    /* clock divider 3 */
> > +#define PLLCON0              0x0C    /* pll0 control */
> > +#define PLLCON1              0x10    /* pll1 control */
> > +#define PLLCON2              0x54    /* pll2 control */
> > +
> > +/* PLLCON bit filed */
> > +#define PLLCON_INDV  GENMASK(5, 0)
> > +#define PLLCON_OTDV1 GENMASK(10, 8)
> > +#define PLLCON_OTDV2 GENMASK(15, 13)
> > +#define PLLCON_FBDV  GENMASK(27, 16)
> > +
> > +/* CLKSEL bit filed */
> > +#define CPUCKSEL     GENMASK(1, 0)
> > +#define SDCKSEL              GENMASK(7, 6)
> > +#define UARTCKSEL    GENMASK(9, 8)
> > +#define TIMCKSEL     GENMASK(15, 14)
> > +
> > +/* CLKDIV1 bit filed */
> > +#define SPI3CKDIV    GENMASK(10, 6)
> > +#define MMCCKDIV     GENMASK(15, 11)
> > +#define UARTDIV1     GENMASK(20, 16)
> > +#define TIMCKDIV     GENMASK(25, 21)
> > +#define CLK4DIV              GENMASK(27, 26)
> > +
> > +/* CLKDIV2 bit filed */
> > +#define APB5CKDIV    GENMASK(23, 22)
> > +#define APB2CKDIV    GENMASK(27, 26)
> > +
> > +/* CLKDIV3 bit filed */
> > +#define SPIXCKDIV    GENMASK(5, 1)
> > +#define SPI0CKDIV    GENMASK(10, 6)
> > +#define UARTDIV2     GENMASK(15, 11)
> > +#define SPI1CKDIV    GENMASK(23, 16)
> > +
> > +/* Flags */
> > +#define DIV_TYPE1    BIT(0)  /* div = clkdiv + 1 */
> > +#define DIV_TYPE2    BIT(1)  /* div = 1 << clkdiv */
> > +#define PRE_DIV2     BIT(2)  /* Pre divisor = 2 */
> > +#define POST_DIV2    BIT(3)  /* Post divisor = 2 */
> > +#define FIXED_PARENT BIT(4)  /* clock source is fixed */
> > +
> > +struct npcm_clk_priv {
> > +     struct udevice *dev;
> > +     void __iomem *base;
> > +};
> > +
> > +/* Parameters of PLL configuration */
> > +struct npcm_clk_pll {
> > +     const int id;
> > +     const int parent_id;
> > +     u32 reg;
> > +     u32 flags;
> > +};
> > +
> > +/* Parent clock id to clksel mapping */
> > +struct parent_data {
> > +     int id;
> > +     int clksel;
> > +};
> > +
> > +/* Parameters of parent selection */
> > +struct npcm_clk_select {
> > +     const int id;
> > +     const struct parent_data *parents;
> > +     u32 reg;
> > +     u32 mask;
> > +     u8 num_parents;
> > +     u32 flags;
> > +};
> > +
> > +/* Parameters of clock divider */
> > +struct npcm_clk_div {
> > +     const int id;
> > +     u32 reg;
> > +     u32 mask;
> > +     u32 flags;
> > +};
> > +
> > +/* Parent clock map */
> > +static const struct parent_data pll_parents[] = {
> > +     {NPCM7XX_CLK_PLL0, 0},
> > +     {NPCM7XX_CLK_PLL1, 1},
> > +     {NPCM7XX_CLK_REFCLK, 2},
> > +     {NPCM7XX_CLK_PLL2DIV2, 3}
> > +};
> > +
> > +static const struct parent_data cpuck_parents[] = {
> > +     {NPCM7XX_CLK_PLL0, 0},
> > +     {NPCM7XX_CLK_PLL1, 1},
> > +     {NPCM7XX_CLK_REFCLK, 2},
> > +     {NPCM7XX_CLK_PLL2, 7}
> > +};
> > +
> > +static const struct parent_data apb_parent[] = {{NPCM7XX_CLK_AHB, 0}};
> > +
> > +static struct npcm_clk_pll npcm7xx_clk_plls[] = {
> > +     {NPCM7XX_CLK_PLL0, NPCM7XX_CLK_REFCLK, PLLCON0, 0},
> > +     {NPCM7XX_CLK_PLL1, NPCM7XX_CLK_REFCLK, PLLCON1, 0},
> > +     {NPCM7XX_CLK_PLL2, NPCM7XX_CLK_REFCLK, PLLCON2, 0},
> > +     {NPCM7XX_CLK_PLL2DIV2, NPCM7XX_CLK_REFCLK, PLLCON2, POST_DIV2}
> > +};
> > +
> > +static struct npcm_clk_select npcm7xx_clk_selectors[] = {
> > +     {NPCM7XX_CLK_AHB, cpuck_parents, CLKSEL, CPUCKSEL, 4, 0},
> > +     {NPCM7XX_CLK_APB2, apb_parent, 0, 0, 1, FIXED_PARENT},
> > +     {NPCM7XX_CLK_APB5, apb_parent, 0, 0, 1, FIXED_PARENT},
> > +     {NPCM7XX_CLK_SPI0, apb_parent, 0, 0, 1, FIXED_PARENT},
> > +     {NPCM7XX_CLK_SPI3, apb_parent, 0, 0, 1, FIXED_PARENT},
> > +     {NPCM7XX_CLK_SPIX, apb_parent, 0, 0, 1, FIXED_PARENT},
> > +     {NPCM7XX_CLK_UART, pll_parents, CLKSEL, UARTCKSEL, 4, 0},
> > +     {NPCM7XX_CLK_TIMER, pll_parents, CLKSEL, TIMCKSEL, 4, 0},
> > +     {NPCM7XX_CLK_SDHC, pll_parents, CLKSEL, SDCKSEL, 4, 0}
> > +};
> > +
> > +static struct npcm_clk_div npcm7xx_clk_dividers[] = {
> > +     {NPCM7XX_CLK_AHB, CLKDIV1, CLK4DIV, DIV_TYPE1 | PRE_DIV2},
> > +     {NPCM7XX_CLK_APB2, CLKDIV2, APB2CKDIV, DIV_TYPE2},
> > +     {NPCM7XX_CLK_APB5, CLKDIV2, APB5CKDIV, DIV_TYPE2},
> > +     {NPCM7XX_CLK_SPI0, CLKDIV3, SPI0CKDIV, DIV_TYPE1},
> > +     {NPCM7XX_CLK_SPI3, CLKDIV1, SPI3CKDIV, DIV_TYPE1},
> > +     {NPCM7XX_CLK_SPIX, CLKDIV3, SPIXCKDIV, DIV_TYPE1},
> > +     {NPCM7XX_CLK_UART, CLKDIV1, UARTDIV1, DIV_TYPE1},
> > +     {NPCM7XX_CLK_TIMER, CLKDIV1, TIMCKDIV, DIV_TYPE2},
> > +     {NPCM7XX_CLK_SDHC, CLKDIV1, MMCCKDIV, DIV_TYPE1}
> > +};
> > +
> > +static int clkid_to_clksel(struct npcm_clk_select *selector, int id)
> > +{
> > +     int i;
> > +
> > +     for (i = 0; i < selector->num_parents; i++) {
> > +             if (selector->parents[i].id == id)
> > +                     return selector->parents[i].clksel;
> > +     }
> > +
> > +     return -EINVAL;
> > +}
> > +
> > +static int clksel_to_clkid(struct npcm_clk_select *selector, int clksel)
> > +{
> > +     int i;
> > +
> > +     for (i = 0; i < selector->num_parents; i++) {
> > +             if (selector->parents[i].clksel == clksel)
> > +                     return selector->parents[i].id;
> > +     }
> > +
> > +     return -EINVAL;
> > +}
> > +
> > +static struct npcm_clk_pll *npcm_clk_pll_get(int clk_id)
> > +{
> > +     int i;
> > +
> > +     for (i = 0; i < ARRAY_SIZE(npcm7xx_clk_plls); i++) {
> > +             if (npcm7xx_clk_plls[i].id == clk_id)
> > +                     return &npcm7xx_clk_plls[i];
> > +     }
> > +
> > +     return NULL;
> > +}
> > +
> > +static struct npcm_clk_select *npcm_clk_selector_get(int clk_id)
> > +{
> > +     int i;
> > +
> > +     for (i = 0; i < ARRAY_SIZE(npcm7xx_clk_selectors); i++) {
> > +             if (npcm7xx_clk_selectors[i].id == clk_id)
> > +                     return &npcm7xx_clk_selectors[i];
> > +     }
> > +
> > +     return NULL;
> > +}
> > +
> > +static struct npcm_clk_div *npcm_clk_divider_get(int clk_id)
> > +{
> > +     int i;
> > +
> > +     for (i = 0; i < ARRAY_SIZE(npcm7xx_clk_dividers); i++) {
> > +             if (npcm7xx_clk_dividers[i].id == clk_id)
> > +                     return &npcm7xx_clk_dividers[i];
> > +     }
> > +
> > +     return NULL;
> > +}
> > +
> > +static ulong npcm_clk_get_fin(struct npcm_clk_priv *priv, int id)
> > +{
> > +     struct npcm_clk_select *selector;
> > +     struct clk parent;
> > +     ulong parent_rate;
> > +     u32 val, clksel;
> > +     int ret;
> > +
> > +     selector = npcm_clk_selector_get(id);
> > +     if (!selector)
> > +             return 0;
> > +
> > +     if (selector->flags & FIXED_PARENT) {
> > +             clksel = 0;
> > +     } else {
> > +             val = readl(priv->base + selector->reg);
> > +             clksel = (val & selector->mask) >> (ffs(selector->mask) - 1);
> > +     }
> > +     parent.id = clksel_to_clkid(selector, clksel);
> > +
> > +     ret = clk_request(priv->dev, &parent);
> > +     if (ret)
> > +             return 0;
> > +
> > +     parent_rate = clk_get_rate(&parent);
> > +
> > +     debug("fin of clk%d = %lu\n", id, parent_rate);
> > +     return parent_rate;
> > +}
> > +
> > +static u32 npcm_clk_get_div(struct npcm_clk_priv *priv, int id)
> > +{
> > +     struct npcm_clk_div *divider;
> > +     u32 val, div;
> > +
> > +     divider = npcm_clk_divider_get(id);
> > +     if (!divider)
> > +             return 0;
> > +
> > +     val = readl(priv->base + divider->reg);
> > +     div = (val & divider->mask) >> (ffs(divider->mask) - 1);
> > +     if (divider->flags & DIV_TYPE1)
> > +             div = div + 1;
> > +     else
> > +             div = 1 << div;
> > +
> > +     if (divider->flags & PRE_DIV2)
> > +             div = div << 1;
> > +
> > +     return div;
> > +}
> > +
> > +static u32 npcm_clk_set_div(struct npcm_clk_priv *priv, int id, u32 div)
> > +{
> > +     struct npcm_clk_div *divider;
> > +     u32 val, clkdiv;
> > +
> > +     divider = npcm_clk_divider_get(id);
> > +     if (!divider)
> > +             return -EINVAL;
> > +
> > +     if (divider->flags & PRE_DIV2)
> > +             div = div >> 1;
> > +
> > +     if (divider->flags & DIV_TYPE1)
> > +             clkdiv = div - 1;
> > +     else
> > +             clkdiv = ilog2(div);
> > +
> > +     val = readl(priv->base + divider->reg);
> > +     val &= ~divider->mask;
> > +     val |= (clkdiv << (ffs(divider->mask) - 1)) & divider->mask;
> > +     writel(val, priv->base + divider->reg);
> > +
> > +     return 0;
> > +}
> > +
> > +static ulong npcm_clk_get_fout(struct npcm_clk_priv *priv, int id)
> > +{
> > +     ulong parent_rate;
> > +     u32 div;
> > +
> > +     parent_rate = npcm_clk_get_fin(priv, id);
> > +     if (!parent_rate)
> > +             return -EINVAL;
> > +
> > +     div = npcm_clk_get_div(priv, id);
> > +     if (!div)
> > +             return -EINVAL;
> > +
> > +     debug("fout of clk%d = (%lu / %u)\n", id, parent_rate, div);
> > +     return (parent_rate / div);
> > +}
> > +
> > +static ulong npcm_clk_set_fout(struct npcm_clk_priv *priv, int id, ulong rate)
> > +{
> > +     u32 div;
> > +     ulong parent_rate;
> > +     int ret;
> > +
> > +     parent_rate = npcm_clk_get_fin(priv, id);
> > +     if (!parent_rate)
> > +             return -EINVAL;
> > +
> > +     div = DIV_ROUND_UP(parent_rate, rate);
> > +     ret = npcm_clk_set_div(priv, id, div);
> > +     if (ret)
> > +             return ret;
> > +
> > +     debug("%s: rate %lu, new rate (%lu / %u)\n", __func__, rate, parent_rate, div);
> > +     return (parent_rate / div);
> > +}
> > +
> > +static ulong npcm_clk_get_pll_fout(struct npcm_clk_priv *priv, int id)
> > +{
> > +     struct npcm_clk_pll *pll;
> > +     struct clk parent;
> > +     ulong parent_rate;
> > +     ulong fbdv, indv, otdv1, otdv2;
> > +     u32 val;
> > +     u64 ret;
> > +
> > +     pll = npcm_clk_pll_get(id);
> > +     if (!pll)
> > +             return -ENODEV;
> > +
> > +     parent.id = pll->parent_id;
> > +     ret = clk_request(priv->dev, &parent);
> > +     if (ret)
> > +             return ret;
> > +
> > +     parent_rate = clk_get_rate(&parent);
> > +
> > +     val = readl(priv->base + pll->reg);
> > +     indv = FIELD_GET(PLLCON_INDV, val);
> > +     fbdv = FIELD_GET(PLLCON_FBDV, val);
> > +     otdv1 = FIELD_GET(PLLCON_OTDV1, val);
> > +     otdv2 = FIELD_GET(PLLCON_OTDV2, val);
> > +
> > +     ret = (u64)parent_rate * fbdv;
> > +     do_div(ret, indv * otdv1 * otdv2);
> > +     if (pll->flags & POST_DIV2)
> > +             do_div(ret, 2);
> > +
> > +     debug("fout of pll(id %d) = %llu\n", id, ret);
> > +     return ret;
> > +}
> > +
> > +static ulong npcm_clk_get_rate(struct clk *clk)
> > +{
> > +     struct npcm_clk_priv *priv = dev_get_priv(clk->dev);
> > +     struct clk refclk;
> > +     int ret;
> > +
> > +     debug("%s: id %lu\n", __func__, clk->id);
> > +     switch (clk->id) {
> > +     case NPCM7XX_CLK_TIMER:
> > +     case NPCM7XX_CLK_REFCLK:
> > +             ret = clk_get_by_name(priv->dev, "refclk", &refclk);
> > +             if (!ret)
> > +                     return clk_get_rate(&refclk);
> > +             else
> > +                     return ret;
> > +     case NPCM7XX_CLK_PLL0:
> > +     case NPCM7XX_CLK_PLL1:
> > +     case NPCM7XX_CLK_PLL2:
> > +     case NPCM7XX_CLK_PLL2DIV2:
> > +             return npcm_clk_get_pll_fout(priv, clk->id);
> > +     case NPCM7XX_CLK_AHB:
> > +     case NPCM7XX_CLK_APB2:
> > +     case NPCM7XX_CLK_APB5:
> > +     case NPCM7XX_CLK_SDHC:
> > +     case NPCM7XX_CLK_UART:
> > +     case NPCM7XX_CLK_SPI0:
> > +     case NPCM7XX_CLK_SPI3:
> > +     case NPCM7XX_CLK_SPIX:
> > +             return npcm_clk_get_fout(priv, clk->id);
> > +     default:
> > +             return -ENOSYS;
> > +     }
> > +}
> > +
> > +static ulong npcm_clk_set_rate(struct clk *clk, ulong rate)
> > +{
> > +     struct npcm_clk_priv *priv = dev_get_priv(clk->dev);
> > +
> > +     debug("%s: id %lu, rate %lu\n", __func__, clk->id, rate);
> > +     switch (clk->id) {
> > +     case NPCM7XX_CLK_TIMER:
> > +     case NPCM7XX_CLK_SDHC:
> > +     case NPCM7XX_CLK_UART:
> > +     case NPCM7XX_CLK_SPI0:
> > +     case NPCM7XX_CLK_SPI3:
> > +     case NPCM7XX_CLK_SPIX:
> > +             return  npcm_clk_set_fout(priv, clk->id, rate);
> > +     default:
> > +             return -ENOSYS;
> > +     }
> > +}
> > +
> > +static int npcm_clk_set_parent(struct clk *clk, struct clk *parent)
> > +{
> > +     struct npcm_clk_priv *priv = dev_get_priv(clk->dev);
> > +     struct npcm_clk_select *selector;
> > +     int clksel;
> > +     u32 val;
> > +
> > +     debug("%s: id %lu, parent %lu\n", __func__, clk->id, parent->id);
> > +     selector = npcm_clk_selector_get(clk->id);
> > +     if (!selector)
> > +             return -EINVAL;
> > +
> > +     clksel = clkid_to_clksel(selector, parent->id);
> > +     if (clksel < 0)
> > +             return -EINVAL;
> > +
> > +     val = readl(priv->base + selector->reg);
> > +     val &= ~selector->mask;
> > +     val |= clksel << (ffs(selector->mask) - 1);
> > +     writel(val, priv->base + selector->reg);
> > +
> > +     return 0;
> > +}
> > +
> > +static int npcm_clk_request(struct clk *clk)
> > +{
> > +     if (clk->id >= NPCM7XX_NUM_CLOCKS)
> > +             return -EINVAL;
> > +
> > +     return 0;
> > +}
> > +
> > +static struct clk_ops npcm_clk_ops = {
> > +     .get_rate = npcm_clk_get_rate,
> > +     .set_rate = npcm_clk_set_rate,
> > +     .set_parent = npcm_clk_set_parent,
> > +     .request = npcm_clk_request,
> > +};
> > +
> > +static int npcm_clk_probe(struct udevice *dev)
> > +{
> > +     struct npcm_clk_priv *priv = dev_get_priv(dev);
> > +
> > +     priv->base = dev_read_addr_ptr(dev);
> > +     if (!priv->base)
> > +             return -EINVAL;
> > +     priv->dev = dev;
> > +
> > +     return 0;
> > +}
> > +
> > +static const struct udevice_id npcm_clk_ids[] = {
> > +     { .compatible = "nuvoton,npcm750-clk" },
> > +     { }
> > +};
> > +
> > +U_BOOT_DRIVER(clk_npcm) = {
> > +     .name           = "clk_npcm",
> > +     .id             = UCLASS_CLK,
> > +     .of_match       = npcm_clk_ids,
> > +     .ops            = &npcm_clk_ops,
> > +     .priv_auto      = sizeof(struct npcm_clk_priv),
> > +     .probe          = npcm_clk_probe,
> > +     .flags = DM_FLAG_PRE_RELOC,
> > +};
> > diff --git a/include/dt-bindings/clock/nuvoton,npcm7xx-clock.h b/include/dt-bindings/clock/nuvoton,npcm7xx-clock.h
> > new file mode 100644
> > index 0000000000..65e6bc4eee
> > --- /dev/null
> > +++ b/include/dt-bindings/clock/nuvoton,npcm7xx-clock.h
> > @@ -0,0 +1,46 @@
> > +/* SPDX-License-Identifier: GPL-2.0 */
> > +/*
> > + * Nuvoton NPCM7xx Clock Generator binding
> > + * clock binding number for all clocks supportted by nuvoton,npcm7xx-clk
> > + *
> > + * Copyright (C) 2018 Nuvoton Technologies tali.perry@nuvoton.com
> > + *
> > + */
> > +
> > +#ifndef __DT_BINDINGS_CLOCK_NPCM7XX_H
> > +#define __DT_BINDINGS_CLOCK_NPCM7XX_H
> > +
> > +#define NPCM7XX_CLK_CPU              0
> > +#define NPCM7XX_CLK_GFX_PIXEL        1
> > +#define NPCM7XX_CLK_MC               2
> > +#define NPCM7XX_CLK_ADC              3
> > +#define NPCM7XX_CLK_AHB              4
> > +#define NPCM7XX_CLK_TIMER    5
> > +#define NPCM7XX_CLK_UART     6
> > +#define NPCM7XX_CLK_MMC              7
> > +#define NPCM7XX_CLK_SPI3     8
> > +#define NPCM7XX_CLK_PCI              9
> > +#define NPCM7XX_CLK_AXI              10
> > +#define NPCM7XX_CLK_APB4     11
> > +#define NPCM7XX_CLK_APB3     12
> > +#define NPCM7XX_CLK_APB2     13
> > +#define NPCM7XX_CLK_APB1     14
> > +#define NPCM7XX_CLK_APB5     15
> > +#define NPCM7XX_CLK_CLKOUT   16
> > +#define NPCM7XX_CLK_GFX              17
> > +#define NPCM7XX_CLK_SU               18
> > +#define NPCM7XX_CLK_SU48     19
> > +#define NPCM7XX_CLK_SDHC     20
> > +#define NPCM7XX_CLK_SPI0     21
> > +#define NPCM7XX_CLK_SPIX     22
> > +#define NPCM7XX_CLK_REFCLK   23
> > +#define NPCM7XX_CLK_SYSBYPCK 24
> > +#define NPCM7XX_CLK_MCBYPCK  25
> > +#define NPCM7XX_CLK_PLL0     26
> > +#define NPCM7XX_CLK_PLL1     27
> > +#define NPCM7XX_CLK_PLL2     28
> > +#define NPCM7XX_CLK_PLL2DIV2 29
> > +#define NPCM7XX_NUM_CLOCKS   (NPCM7XX_CLK_PLL2DIV2 + 1)
> > +
> > +#endif
> > +
> >
>

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

* Re: [PATCH v1 0/6] Add Nuvoton NPCM750 support
  2022-04-06 19:45 ` [PATCH v1 0/6] Add Nuvoton NPCM750 support Tom Rini
@ 2022-04-08  9:25   ` Jim Liu
  0 siblings, 0 replies; 14+ messages in thread
From: Jim Liu @ 2022-04-08  9:25 UTC (permalink / raw)
  To: Tom Rini
  Cc: Jim Liu, Stanley Chu, KWLIU, lukma, Sean Anderson, sjg, sr, u-boot

Hi Tom

thanks for your reply.
i will followed your suggestion to modify the 1/6 2/6 6/6  patch and
combine 1/6 2/6 6/6 to be a single patch for version 2.

my dts  have  been submitted to upstream, i  will list and describe in
version 2.


Tom Rini <trini@konsulko.com> 於 2022年4月7日 週四 上午3:45寫道:



>
> On Wed, Apr 06, 2022 at 03:57:31PM +0800, Jim Liu wrote:
>
> > The patch series add basic supoorts for NPCM750, which
> > is Nuvoton's 3th-generation BMC (Baseboard Management Controller).
> > Add drivers to support Clock,Timer,Uart for NPCM7xx SoC.
> >
> > the NPCM750 computing subsystem comprises a dual-core ARM a9
> > at 800MHz speed with L1/L2 caches
> >
> > Jim Liu (6):
> >   ARM: configs: Add defconfig for Nuvoton NPCM750
> >   ARM: dts: Add Nuvoton NPCM750 device tree
> >   timer: npcm: Add NPCM timer support
> >   serial: npcm: Add support for Nuvoton NPCM SoCs
> >   clk: nuvoton: Add support for NPCM750
> >   arm: nuvoton: Add support for Nuvoton NPCM750 BMC
>
> One last bit of overall feedback is that this, and the NPCM8xx support
> need to be coordinated, and sharing as much driver/etc code, pulling SoC
> differences from DT, as possible.  Thanks.
>
> --
> Tom

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

end of thread, other threads:[~2022-04-08  9:25 UTC | newest]

Thread overview: 14+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2022-04-06  7:57 [PATCH v1 0/6] Add Nuvoton NPCM750 support Jim Liu
2022-04-06  7:57 ` [PATCH v1 1/6] ARM: configs: Add defconfig for Nuvoton NPCM750 Jim Liu
2022-04-06 13:39   ` Tom Rini
2022-04-06  7:57 ` [PATCH v1 2/6] ARM: dts: Add Nuvoton NPCM750 device tree Jim Liu
2022-04-06 13:38   ` Tom Rini
2022-04-06  7:57 ` [PATCH v1 3/6] timer: npcm: Add NPCM timer support Jim Liu
2022-04-06  7:57 ` [PATCH v1 4/6] serial: npcm: Add support for Nuvoton NPCM SoCs Jim Liu
2022-04-06  7:57 ` [PATCH v1 5/6] clk: nuvoton: Add support for NPCM750 Jim Liu
2022-04-06 18:19   ` Sean Anderson
2022-04-08  9:12     ` Jim Liu
2022-04-06  7:57 ` [PATCH v1 6/6] arm: nuvoton: Add support for Nuvoton NPCM750 BMC Jim Liu
2022-04-06 13:48   ` Tom Rini
2022-04-06 19:45 ` [PATCH v1 0/6] Add Nuvoton NPCM750 support Tom Rini
2022-04-08  9:25   ` Jim Liu

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.