From 23137e72f0e8f406a42b6dc0ef0c90e866789798 Mon Sep 17 00:00:00 2001 From: Paul Kocialkowski Date: Tue, 5 Aug 2025 19:48:21 +0200 Subject: [PATCH 001/112] sunxi: Switch V3/V3s device-tree source to OF_UPSTREAM There is nothing special for u-boot in the V3/V3s device-tree files, they are just copies of the upstream ones. Remove the copies and switch to OF_UPSTREAM for supported boards. Signed-off-by: Paul Kocialkowski Reviewed-by: Andre Przywara --- arch/arm/dts/Makefile | 5 - arch/arm/dts/sun8i-s3-elimo-impetus.dtsi | 44 -- arch/arm/dts/sun8i-s3-elimo-initium.dts | 29 - arch/arm/dts/sun8i-s3-lichee-zero-plus.dts | 53 -- arch/arm/dts/sun8i-s3-pinecube.dts | 228 ------ arch/arm/dts/sun8i-v3-sl631-imx179.dts | 12 - arch/arm/dts/sun8i-v3-sl631.dtsi | 138 ---- arch/arm/dts/sun8i-v3.dtsi | 63 -- arch/arm/dts/sun8i-v3s-anbernic-rg-nano.dts | 276 -------- arch/arm/dts/sun8i-v3s-licheepi-zero-dock.dts | 105 --- arch/arm/dts/sun8i-v3s-licheepi-zero.dts | 101 --- arch/arm/dts/sun8i-v3s.dtsi | 656 ------------------ arch/arm/mach-sunxi/Kconfig | 1 + configs/LicheePi_Zero_defconfig | 2 +- configs/pinecube_defconfig | 2 +- 15 files changed, 3 insertions(+), 1712 deletions(-) delete mode 100644 arch/arm/dts/sun8i-s3-elimo-impetus.dtsi delete mode 100644 arch/arm/dts/sun8i-s3-elimo-initium.dts delete mode 100644 arch/arm/dts/sun8i-s3-lichee-zero-plus.dts delete mode 100644 arch/arm/dts/sun8i-s3-pinecube.dts delete mode 100644 arch/arm/dts/sun8i-v3-sl631-imx179.dts delete mode 100644 arch/arm/dts/sun8i-v3-sl631.dtsi delete mode 100644 arch/arm/dts/sun8i-v3.dtsi delete mode 100644 arch/arm/dts/sun8i-v3s-anbernic-rg-nano.dts delete mode 100644 arch/arm/dts/sun8i-v3s-licheepi-zero-dock.dts delete mode 100644 arch/arm/dts/sun8i-v3s-licheepi-zero.dts delete mode 100644 arch/arm/dts/sun8i-v3s.dtsi diff --git a/arch/arm/dts/Makefile b/arch/arm/dts/Makefile index eece3bdcdce..ff8f1ed1ac0 100644 --- a/arch/arm/dts/Makefile +++ b/arch/arm/dts/Makefile @@ -648,11 +648,6 @@ dtb-$(CONFIG_MACH_SUN8I_R40) += \ sun8i-r40-oka40i-c.dtb \ sun8i-t3-cqa3t-bv3.dtb \ sun8i-v40-bananapi-m2-berry.dtb -dtb-$(CONFIG_MACH_SUN8I_V3S) += \ - sun8i-s3-elimo-initium.dtb \ - sun8i-s3-pinecube.dtb \ - sun8i-v3-sl631-imx179.dtb \ - sun8i-v3s-licheepi-zero.dtb dtb-$(CONFIG_MACH_SUN8I_R528) += \ sun8i-t113s-mangopi-mq-r-t113.dtb dtb-$(CONFIG_MACH_SUN50I_H5) += \ diff --git a/arch/arm/dts/sun8i-s3-elimo-impetus.dtsi b/arch/arm/dts/sun8i-s3-elimo-impetus.dtsi deleted file mode 100644 index 052b010a560..00000000000 --- a/arch/arm/dts/sun8i-s3-elimo-impetus.dtsi +++ /dev/null @@ -1,44 +0,0 @@ -// SPDX-License-Identifier: (GPL-2.0+ OR MIT) -/* - * Copyright (C) 2020 Matteo Scordino - */ - -/dts-v1/; -#include "sun8i-v3.dtsi" -#include "sunxi-common-regulators.dtsi" - -/ { - model = "Elimo Impetus SoM"; - compatible = "elimo,impetus", "sochip,s3", "allwinner,sun8i-v3"; - - aliases { - serial0 = &uart0; - }; - - chosen { - stdout-path = "serial0:115200n8"; - }; -}; - -&mmc0 { - broken-cd; - bus-width = <4>; - vmmc-supply = <®_vcc3v3>; - status = "okay"; -}; - -&uart0 { - pinctrl-0 = <&uart0_pb_pins>; - pinctrl-names = "default"; - status = "okay"; -}; - -&usb_otg { - dr_mode = "otg"; - status = "okay"; -}; - -&usbphy { - usb0_id_det-gpios = <&pio 5 6 GPIO_ACTIVE_HIGH>; - status = "okay"; -}; diff --git a/arch/arm/dts/sun8i-s3-elimo-initium.dts b/arch/arm/dts/sun8i-s3-elimo-initium.dts deleted file mode 100644 index 039677c2cc6..00000000000 --- a/arch/arm/dts/sun8i-s3-elimo-initium.dts +++ /dev/null @@ -1,29 +0,0 @@ -// SPDX-License-Identifier: (GPL-2.0+ OR MIT) -/* - * Copyright (C) 2020 Matteo Scordino - */ - -/dts-v1/; -#include "sun8i-s3-elimo-impetus.dtsi" - -/ { - model = "Elimo Initium"; - compatible = "elimo,initium", "elimo,impetus", "sochip,s3", - "allwinner,sun8i-v3"; - - aliases { - serial1 = &uart1; - }; -}; - -&uart1 { - pinctrl-0 = <&uart1_pg_pins>; - pinctrl-names = "default"; - status = "okay"; -}; - -&emac { - phy-handle = <&int_mii_phy>; - phy-mode = "mii"; - status = "okay"; -}; diff --git a/arch/arm/dts/sun8i-s3-lichee-zero-plus.dts b/arch/arm/dts/sun8i-s3-lichee-zero-plus.dts deleted file mode 100644 index d18192d51d1..00000000000 --- a/arch/arm/dts/sun8i-s3-lichee-zero-plus.dts +++ /dev/null @@ -1,53 +0,0 @@ -// SPDX-License-Identifier: (GPL-2.0+ OR MIT) -/* - * Copyright (C) 2019 Icenowy Zheng - */ - -/dts-v1/; -#include "sun8i-v3.dtsi" - -#include - -/ { - model = "Sipeed Lichee Zero Plus"; - compatible = "sipeed,lichee-zero-plus", "sochip,s3", - "allwinner,sun8i-v3"; - - aliases { - serial0 = &uart0; - }; - - chosen { - stdout-path = "serial0:115200n8"; - }; - - reg_vcc3v3: vcc3v3 { - compatible = "regulator-fixed"; - regulator-name = "vcc3v3"; - regulator-min-microvolt = <3300000>; - regulator-max-microvolt = <3300000>; - }; -}; - -&mmc0 { - broken-cd; - bus-width = <4>; - vmmc-supply = <®_vcc3v3>; - status = "okay"; -}; - -&uart0 { - pinctrl-0 = <&uart0_pb_pins>; - pinctrl-names = "default"; - status = "okay"; -}; - -&usb_otg { - dr_mode = "peripheral"; - status = "okay"; -}; - -&usbphy { - usb0_id_det-gpios = <&pio 5 6 GPIO_ACTIVE_HIGH>; - status = "okay"; -}; diff --git a/arch/arm/dts/sun8i-s3-pinecube.dts b/arch/arm/dts/sun8i-s3-pinecube.dts deleted file mode 100644 index e0d4404b595..00000000000 --- a/arch/arm/dts/sun8i-s3-pinecube.dts +++ /dev/null @@ -1,228 +0,0 @@ -// SPDX-License-Identifier: (GPL-2.0+ OR X11) -/* - * Copyright 2019 Icenowy Zheng - */ - -/dts-v1/; -#include "sun8i-v3.dtsi" -#include -#include - -/ { - model = "PineCube IP Camera"; - compatible = "pine64,pinecube", "sochip,s3", "allwinner,sun8i-v3"; - - aliases { - serial0 = &uart2; - }; - - chosen { - stdout-path = "serial0:115200n8"; - }; - - leds { - compatible = "gpio-leds"; - - led1 { - label = "pine64:ir:led1"; - gpios = <&pio 1 10 GPIO_ACTIVE_LOW>; /* PB10 */ - }; - - led2 { - label = "pine64:ir:led2"; - gpios = <&pio 1 12 GPIO_ACTIVE_LOW>; /* PB12 */ - }; - }; - - reg_vcc5v0: vcc5v0 { - compatible = "regulator-fixed"; - regulator-name = "vcc5v0"; - regulator-min-microvolt = <5000000>; - regulator-max-microvolt = <5000000>; - }; - - reg_vcc_wifi: vcc-wifi { - compatible = "regulator-fixed"; - regulator-name = "vcc-wifi"; - regulator-min-microvolt = <3300000>; - regulator-max-microvolt = <3300000>; - gpio = <&pio 1 2 GPIO_ACTIVE_LOW>; /* PB2 WIFI-EN */ - vin-supply = <®_dcdc3>; - startup-delay-us = <200000>; - }; - - wifi_pwrseq: pwrseq { - compatible = "mmc-pwrseq-simple"; - reset-gpios = <&pio 1 3 GPIO_ACTIVE_LOW>; /* PB3 WIFI-RST */ - post-power-on-delay-ms = <200>; - }; -}; - -&csi1 { - pinctrl-names = "default"; - pinctrl-0 = <&csi1_8bit_pins>; - status = "okay"; - - port { - csi1_ep: endpoint { - remote-endpoint = <&ov5640_ep>; - bus-width = <8>; - hsync-active = <1>; /* Active high */ - vsync-active = <0>; /* Active low */ - data-active = <1>; /* Active high */ - pclk-sample = <1>; /* Rising */ - }; - }; -}; - -&emac { - phy-handle = <&int_mii_phy>; - phy-mode = "mii"; - status = "okay"; -}; - -&i2c0 { - status = "okay"; - - axp209: pmic@34 { - reg = <0x34>; - interrupt-parent = <&nmi_intc>; - interrupts = <0 IRQ_TYPE_LEVEL_LOW>; - }; -}; - -&i2c1 { - pinctrl-names = "default"; - pinctrl-0 = <&i2c1_pe_pins>; - status = "okay"; - - ov5640: camera@3c { - compatible = "ovti,ov5640"; - reg = <0x3c>; - pinctrl-names = "default"; - pinctrl-0 = <&csi1_mclk_pin>; - clocks = <&ccu CLK_CSI1_MCLK>; - clock-names = "xclk"; - - AVDD-supply = <®_ldo3>; - DOVDD-supply = <®_ldo3>; - DVDD-supply = <®_ldo4>; - reset-gpios = <&pio 4 23 GPIO_ACTIVE_LOW>; /* PE23 */ - powerdown-gpios = <&pio 4 24 GPIO_ACTIVE_HIGH>; /* PE24 */ - - port { - ov5640_ep: endpoint { - remote-endpoint = <&csi1_ep>; - bus-width = <8>; - hsync-active = <1>; /* Active high */ - vsync-active = <0>; /* Active low */ - data-active = <1>; /* Active high */ - pclk-sample = <1>; /* Rising */ - }; - }; - }; -}; - -&lradc { - vref-supply = <®_ldo2>; - status = "okay"; - - button-200 { - label = "Setup"; - linux,code = ; - channel = <0>; - voltage = <190000>; - }; -}; - -&mmc0 { - vmmc-supply = <®_dcdc3>; - bus-width = <4>; - cd-gpios = <&pio 5 6 GPIO_ACTIVE_LOW>; - status = "okay"; -}; - -&mmc1 { - vmmc-supply = <®_vcc_wifi>; - vqmmc-supply = <®_dcdc3>; - mmc-pwrseq = <&wifi_pwrseq>; - bus-width = <4>; - non-removable; - status = "okay"; -}; - -&pio { - vcc-pd-supply = <®_dcdc3>; - vcc-pe-supply = <®_ldo3>; -}; - -#include "axp209.dtsi" - -&ac_power_supply { - status = "okay"; -}; - -®_dcdc2 { - regulator-always-on; - regulator-min-microvolt = <1250000>; - regulator-max-microvolt = <1250000>; - regulator-name = "vdd-sys-cpu-ephy"; -}; - -®_dcdc3 { - regulator-always-on; - regulator-min-microvolt = <3300000>; - regulator-max-microvolt = <3300000>; - regulator-name = "vcc-3v3"; -}; - -®_ldo1 { - regulator-name = "vdd-rtc"; -}; - -®_ldo2 { - regulator-always-on; - regulator-min-microvolt = <3000000>; - regulator-max-microvolt = <3000000>; - regulator-name = "avcc"; -}; - -®_ldo3 { - regulator-min-microvolt = <2800000>; - regulator-max-microvolt = <2800000>; - regulator-name = "avdd-dovdd-2v8-csi"; - regulator-soft-start; - regulator-ramp-delay = <1600>; -}; - -®_ldo4 { - regulator-min-microvolt = <1800000>; - regulator-max-microvolt = <1800000>; - regulator-name = "dvdd-1v8-csi"; -}; - -&spi0 { - status = "okay"; - - flash@0 { - #address-cells = <1>; - #size-cells = <1>; - compatible = "winbond,w25q128", "jedec,spi-nor"; - reg = <0>; - spi-max-frequency = <40000000>; - }; -}; - -&uart2 { - status = "okay"; -}; - -&usb_otg { - dr_mode = "host"; - status = "okay"; -}; - -&usbphy { - usb0_vbus-supply = <®_vcc5v0>; - status = "okay"; -}; diff --git a/arch/arm/dts/sun8i-v3-sl631-imx179.dts b/arch/arm/dts/sun8i-v3-sl631-imx179.dts deleted file mode 100644 index 117aeece4e5..00000000000 --- a/arch/arm/dts/sun8i-v3-sl631-imx179.dts +++ /dev/null @@ -1,12 +0,0 @@ -// SPDX-License-Identifier: (GPL-2.0+ OR X11) -/* - * Copyright 2020 Paul Kocialkowski - */ - -#include "sun8i-v3-sl631.dtsi" - -/ { - model = "SL631 Action Camera with IMX179"; - compatible = "allwinner,sl631-imx179", "allwinner,sl631", - "allwinner,sun8i-v3"; -}; diff --git a/arch/arm/dts/sun8i-v3-sl631.dtsi b/arch/arm/dts/sun8i-v3-sl631.dtsi deleted file mode 100644 index 6f93f8c49f8..00000000000 --- a/arch/arm/dts/sun8i-v3-sl631.dtsi +++ /dev/null @@ -1,138 +0,0 @@ -// SPDX-License-Identifier: (GPL-2.0+ OR X11) -/* - * Copyright 2020 Paul Kocialkowski - */ - -/dts-v1/; - -#include "sun8i-v3.dtsi" - -#include -#include - -/ { - model = "SL631 Action Camera"; - compatible = "allwinner,sl631", "allwinner,sun8i-v3"; - - aliases { - serial0 = &uart1; - }; - - chosen { - stdout-path = "serial0:115200n8"; - }; -}; - -&i2c0 { - status = "okay"; - - axp209: pmic@34 { - reg = <0x34>; - interrupt-parent = <&nmi_intc>; - interrupts = <0 IRQ_TYPE_LEVEL_LOW>; - }; -}; - -&i2c1 { - pinctrl-names = "default"; - pinctrl-0 = <&i2c1_pb_pins>; - status = "okay"; -}; - -&lradc { - vref-supply = <®_ldo2>; - status = "okay"; - - button-174 { - label = "Down"; - linux,code = ; - channel = <0>; - voltage = <174603>; - }; - - button-384 { - label = "Up"; - linux,code = ; - channel = <0>; - voltage = <384126>; - }; - - button-593 { - label = "OK"; - linux,code = ; - channel = <0>; - voltage = <593650>; - }; -}; - -&mmc0 { - cd-gpios = <&pio 5 6 GPIO_ACTIVE_LOW>; /* PF6 */ - bus-width = <4>; - vmmc-supply = <®_dcdc3>; - status = "okay"; -}; - -&pio { - vcc-pd-supply = <®_dcdc3>; - vcc-pe-supply = <®_dcdc3>; -}; - -#include "axp209.dtsi" - -&ac_power_supply { - status = "okay"; -}; - -&battery_power_supply { - status = "okay"; -}; - -®_dcdc2 { - regulator-always-on; - regulator-min-microvolt = <1250000>; - regulator-max-microvolt = <1250000>; - regulator-name = "vdd-sys-cpu"; -}; - -®_dcdc3 { - regulator-always-on; - regulator-min-microvolt = <3300000>; - regulator-max-microvolt = <3300000>; - regulator-name = "vdd-3v3"; -}; - -®_ldo1 { - regulator-name = "vdd-rtc"; -}; - -®_ldo2 { - regulator-always-on; - regulator-min-microvolt = <3000000>; - regulator-max-microvolt = <3000000>; - regulator-name = "avcc"; -}; - -&spi0 { - status = "okay"; - - flash@0 { - reg = <0>; - compatible = "jedec,spi-nor"; - spi-max-frequency = <50000000>; - }; -}; - -&uart1 { - pinctrl-0 = <&uart1_pg_pins>; - pinctrl-names = "default"; - status = "okay"; -}; - -&usb_otg { - dr_mode = "peripheral"; - status = "okay"; -}; - -&usbphy { - status = "okay"; -}; diff --git a/arch/arm/dts/sun8i-v3.dtsi b/arch/arm/dts/sun8i-v3.dtsi deleted file mode 100644 index 186c30cbe6e..00000000000 --- a/arch/arm/dts/sun8i-v3.dtsi +++ /dev/null @@ -1,63 +0,0 @@ -// SPDX-License-Identifier: (GPL-2.0+ OR MIT) -/* - * Copyright (C) 2019 Icenowy Zheng - * Copyright (C) 2021 Tobias Schramm - */ - -#include "sun8i-v3s.dtsi" - -/ { - soc { - i2s0: i2s@1c22000 { - #sound-dai-cells = <0>; - compatible = "allwinner,sun8i-v3-i2s", - "allwinner,sun8i-h3-i2s"; - reg = <0x01c22000 0x400>; - interrupts = ; - clocks = <&ccu CLK_BUS_I2S0>, <&ccu CLK_I2S0>; - clock-names = "apb", "mod"; - dmas = <&dma 3>, <&dma 3>; - dma-names = "rx", "tx"; - pinctrl-names = "default"; - pinctrl-0 = <&i2s0_pins>; - resets = <&ccu RST_BUS_I2S0>; - status = "disabled"; - }; - }; -}; - -&ccu { - compatible = "allwinner,sun8i-v3-ccu"; -}; - -&codec_analog { - compatible = "allwinner,sun8i-v3-codec-analog", - "allwinner,sun8i-h3-codec-analog"; -}; - -&emac { - /delete-property/ phy-handle; - /delete-property/ phy-mode; -}; - -&mdio_mux { - external_mdio: mdio@2 { - reg = <2>; - #address-cells = <1>; - #size-cells = <0>; - }; -}; - -&pio { - compatible = "allwinner,sun8i-v3-pinctrl"; - - i2s0_pins: i2s0-pins { - pins = "PG10", "PG11", "PG12", "PG13"; - function = "i2s"; - }; - - uart1_pg_pins: uart1-pg-pins { - pins = "PG6", "PG7"; - function = "uart1"; - }; -}; diff --git a/arch/arm/dts/sun8i-v3s-anbernic-rg-nano.dts b/arch/arm/dts/sun8i-v3s-anbernic-rg-nano.dts deleted file mode 100644 index f34dfdf1566..00000000000 --- a/arch/arm/dts/sun8i-v3s-anbernic-rg-nano.dts +++ /dev/null @@ -1,276 +0,0 @@ -// SPDX-License-Identifier: (GPL-2.0+ OR MIT) - -/dts-v1/; -#include -#include "sun8i-v3s.dtsi" -#include "sunxi-common-regulators.dtsi" - -/ { - model = "Anbernic RG Nano"; - compatible = "anbernic,rg-nano", "allwinner,sun8i-v3s"; - - aliases { - rtc0 = &pcf8563; - rtc1 = &rtc; - serial0 = &uart0; - }; - - backlight: backlight { - compatible = "pwm-backlight"; - brightness-levels = <0 1 2 3 8 14 21 32 46 60 80 100>; - default-brightness-level = <11>; - power-supply = <®_vcc5v0>; - pwms = <&pwm 0 40000 1>; - }; - - chosen { - stdout-path = "serial0:115200n8"; - }; - - gpio_keys: gpio-keys { - compatible = "gpio-keys"; - - button-a { - gpios = <&gpio_expander 12 (GPIO_ACTIVE_LOW | GPIO_PULL_UP)>; - label = "BTN-A"; - linux,code = ; - }; - - button-b { - gpios = <&gpio_expander 14 (GPIO_ACTIVE_LOW | GPIO_PULL_UP)>; - label = "BTN-B"; - linux,code = ; - }; - - button-down { - gpios = <&gpio_expander 1 (GPIO_ACTIVE_LOW | GPIO_PULL_UP)>; - label = "DPAD-DOWN"; - linux,code = ; - }; - - button-left { - gpios = <&gpio_expander 4 (GPIO_ACTIVE_LOW | GPIO_PULL_UP)>; - label = "DPAD-LEFT"; - linux,code = ; - }; - - button-right { - gpios = <&gpio_expander 0 (GPIO_ACTIVE_LOW | GPIO_PULL_UP)>; - label = "DPAD-RIGHT"; - linux,code = ; - }; - - button-se { - gpios = <&gpio_expander 7 (GPIO_ACTIVE_LOW | GPIO_PULL_UP)>; - label = "BTN-SELECT"; - linux,code = ; - }; - - button-st { - gpios = <&gpio_expander 6 (GPIO_ACTIVE_LOW | GPIO_PULL_UP)>; - label = "BTN-START"; - linux,code = ; - }; - - button-tl { - gpios = <&gpio_expander 2 (GPIO_ACTIVE_LOW | GPIO_PULL_UP)>; - label = "BTN-L"; - linux,code = ; - }; - - button-tr { - gpios = <&gpio_expander 15 (GPIO_ACTIVE_LOW | GPIO_PULL_UP)>; - label = "BTN-R"; - linux,code = ; - }; - - button-up { - gpios = <&gpio_expander 3 (GPIO_ACTIVE_LOW | GPIO_PULL_UP)>; - label = "DPAD-UP"; - linux,code = ; - }; - - button-x { - gpios = <&gpio_expander 11 (GPIO_ACTIVE_LOW | GPIO_PULL_UP)>; - label = "BTN-X"; - linux,code = ; - }; - - button-y { - gpios = <&gpio_expander 13 (GPIO_ACTIVE_LOW | GPIO_PULL_UP)>; - label = "BTN-Y"; - linux,code = ; - }; - }; -}; - -&codec { - allwinner,audio-routing = "Speaker", "HP", - "MIC1", "Mic", - "Mic", "HBIAS"; - allwinner,pa-gpios = <&pio 5 6 (GPIO_ACTIVE_HIGH | GPIO_PULL_UP)>; /* PF6 */ - status = "okay"; -}; - -&ehci { - status = "okay"; -}; - -&i2c0 { - status = "okay"; - - gpio_expander: gpio@20 { - compatible = "nxp,pcal6416"; - reg = <0x20>; - gpio-controller; - #gpio-cells = <2>; - #interrupt-cells = <2>; - interrupt-controller; - interrupt-parent = <&pio>; - interrupts = <1 3 IRQ_TYPE_EDGE_BOTH>; /* PB3/EINT3 */ - vcc-supply = <®_vcc3v3>; - }; - - axp209: pmic@34 { - reg = <0x34>; - interrupt-parent = <&pio>; - interrupts = <1 5 IRQ_TYPE_EDGE_FALLING>; /* PB5/EINT5 */ - }; - - pcf8563: rtc@51 { - compatible = "nxp,pcf8563"; - reg = <0x51>; - }; -}; - -#include "axp209.dtsi" - -&battery_power_supply { - status = "okay"; -}; - -&mmc0 { - broken-cd; - bus-width = <4>; - disable-wp; - vmmc-supply = <®_vcc3v3>; - vqmmc-supply = <®_vcc3v3>; - status = "okay"; -}; - -&ohci { - status = "okay"; -}; - -&pio { - vcc-pb-supply = <®_vcc3v3>; - vcc-pc-supply = <®_vcc3v3>; - vcc-pf-supply = <®_vcc3v3>; - vcc-pg-supply = <®_vcc3v3>; - - spi0_no_miso_pins: spi0-no-miso-pins { - pins = "PC1", "PC2", "PC3"; - function = "spi0"; - }; -}; - -&pwm { - pinctrl-0 = <&pwm0_pin>; - pinctrl-names = "default"; - status = "okay"; -}; - -/* DCDC2 wired into vdd-cpu, vdd-sys, and vdd-ephy. */ -®_dcdc2 { - regulator-always-on; - regulator-max-microvolt = <1250000>; - regulator-min-microvolt = <1250000>; - regulator-name = "vdd-cpu"; -}; - -/* DCDC3 wired into every 3.3v input that isn't the RTC. */ -®_dcdc3 { - regulator-always-on; - regulator-max-microvolt = <3300000>; - regulator-min-microvolt = <3300000>; - regulator-name = "vcc-io"; -}; - -/* LDO1 wired into RTC, voltage is hard-wired at 3.3v. */ -®_ldo1 { - regulator-always-on; - regulator-name = "vcc-rtc"; -}; - -/* LDO2 wired into VCC-PLL and audio codec. */ -®_ldo2 { - regulator-always-on; - regulator-max-microvolt = <3000000>; - regulator-min-microvolt = <3000000>; - regulator-name = "vcc-pll"; -}; - -/* LDO3, LDO4, and LDO5 unused. */ -®_ldo3 { - status = "disabled"; -}; - -®_ldo4 { - status = "disabled"; -}; - -/* RTC uses internal oscillator */ -&rtc { - /delete-property/ clocks; -}; - -&spi0 { - pinctrl-0 = <&spi0_no_miso_pins>; - pinctrl-names = "default"; - status = "okay"; - - display@0 { - compatible = "saef,sftc154b", "panel-mipi-dbi-spi"; - reg = <0>; - backlight = <&backlight>; - dc-gpios = <&pio 2 0 GPIO_ACTIVE_HIGH>; /* PC0 */ - reset-gpios = <&pio 1 2 GPIO_ACTIVE_HIGH>; /* PB2 */ - spi-max-frequency = <100000000>; - - height-mm = <39>; - width-mm = <39>; - - /* Set hb-porch to compensate for non-visible area */ - panel-timing { - hactive = <240>; - vactive = <240>; - hback-porch = <80>; - vback-porch = <0>; - clock-frequency = <0>; - hfront-porch = <0>; - hsync-len = <0>; - vfront-porch = <0>; - vsync-len = <0>; - }; - }; -}; - -&uart0 { - pinctrl-0 = <&uart0_pb_pins>; - pinctrl-names = "default"; - status = "okay"; -}; - -&usb_otg { - dr_mode = "otg"; - status = "okay"; -}; - -&usb_power_supply { - status = "okay"; -}; - -&usbphy { - usb0_id_det-gpios = <&pio 6 5 (GPIO_ACTIVE_LOW | GPIO_PULL_UP)>; /* PG5 */ - status = "okay"; -}; diff --git a/arch/arm/dts/sun8i-v3s-licheepi-zero-dock.dts b/arch/arm/dts/sun8i-v3s-licheepi-zero-dock.dts deleted file mode 100644 index 752ad05c8f8..00000000000 --- a/arch/arm/dts/sun8i-v3s-licheepi-zero-dock.dts +++ /dev/null @@ -1,105 +0,0 @@ -/* - * Copyright (C) 2016 Icenowy Zheng - * - * This file is dual-licensed: you can use it either under the terms - * of the GPL or the X11 license, at your option. Note that this dual - * licensing only applies to this file, and not this project as a - * whole. - * - * a) This file is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License as - * published by the Free Software Foundation; either version 2 of the - * License, or (at your option) any later version. - * - * This file is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * Or, alternatively, - * - * b) Permission is hereby granted, free of charge, to any person - * obtaining a copy of this software and associated documentation - * files (the "Software"), to deal in the Software without - * restriction, including without limitation the rights to use, - * copy, modify, merge, publish, distribute, sublicense, and/or - * sell copies of the Software, and to permit persons to whom the - * Software is furnished to do so, subject to the following - * conditions: - * - * The above copyright notice and this permission notice shall be - * included in all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, - * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES - * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND - * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT - * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, - * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING - * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR - * OTHER DEALINGS IN THE SOFTWARE. - */ - -#include "sun8i-v3s-licheepi-zero.dts" - -#include - -/ { - model = "Lichee Pi Zero with Dock"; - compatible = "licheepi,licheepi-zero-dock", "licheepi,licheepi-zero", - "allwinner,sun8i-v3s"; - - aliases { - ethernet0 = &emac; - }; - - leds { - /* The LEDs use PG0~2 pins, which conflict with MMC1 */ - status = "disabled"; - }; -}; - -&emac { - allwinner,leds-active-low; - status = "okay"; -}; - -&lradc { - vref-supply = <®_vcc3v0>; - status = "okay"; - - button-200 { - label = "Volume Up"; - linux,code = ; - channel = <0>; - voltage = <200000>; - }; - - button-400 { - label = "Volume Down"; - linux,code = ; - channel = <0>; - voltage = <400000>; - }; - - button-600 { - label = "Select"; - linux,code = ; - channel = <0>; - voltage = <600000>; - }; - - button-800 { - label = "Start"; - linux,code = ; - channel = <0>; - voltage = <800000>; - }; -}; - -&mmc1 { - broken-cd; - bus-width = <4>; - vmmc-supply = <®_vcc3v3>; - status = "okay"; -}; diff --git a/arch/arm/dts/sun8i-v3s-licheepi-zero.dts b/arch/arm/dts/sun8i-v3s-licheepi-zero.dts deleted file mode 100644 index 2e4587d26ce..00000000000 --- a/arch/arm/dts/sun8i-v3s-licheepi-zero.dts +++ /dev/null @@ -1,101 +0,0 @@ -/* - * Copyright (C) 2016 Icenowy Zheng - * - * This file is dual-licensed: you can use it either under the terms - * of the GPL or the X11 license, at your option. Note that this dual - * licensing only applies to this file, and not this project as a - * whole. - * - * a) This file is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License as - * published by the Free Software Foundation; either version 2 of the - * License, or (at your option) any later version. - * - * This file is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * Or, alternatively, - * - * b) Permission is hereby granted, free of charge, to any person - * obtaining a copy of this software and associated documentation - * files (the "Software"), to deal in the Software without - * restriction, including without limitation the rights to use, - * copy, modify, merge, publish, distribute, sublicense, and/or - * sell copies of the Software, and to permit persons to whom the - * Software is furnished to do so, subject to the following - * conditions: - * - * The above copyright notice and this permission notice shall be - * included in all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, - * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES - * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND - * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT - * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, - * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING - * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR - * OTHER DEALINGS IN THE SOFTWARE. - */ - -/dts-v1/; -#include "sun8i-v3s.dtsi" -#include "sunxi-common-regulators.dtsi" - -/ { - model = "Lichee Pi Zero"; - compatible = "licheepi,licheepi-zero", "allwinner,sun8i-v3s"; - - aliases { - serial0 = &uart0; - }; - - chosen { - stdout-path = "serial0:115200n8"; - }; - - leds { - compatible = "gpio-leds"; - - blue_led { - label = "licheepi:blue:usr"; - gpios = <&pio 6 1 GPIO_ACTIVE_LOW>; /* PG1 */ - }; - - green_led { - label = "licheepi:green:usr"; - gpios = <&pio 6 0 GPIO_ACTIVE_LOW>; /* PG0 */ - default-state = "on"; - }; - - red_led { - label = "licheepi:red:usr"; - gpios = <&pio 6 2 GPIO_ACTIVE_LOW>; /* PG2 */ - }; - }; -}; - -&mmc0 { - broken-cd; - bus-width = <4>; - vmmc-supply = <®_vcc3v3>; - status = "okay"; -}; - -&uart0 { - pinctrl-0 = <&uart0_pb_pins>; - pinctrl-names = "default"; - status = "okay"; -}; - -&usb_otg { - dr_mode = "otg"; - status = "okay"; -}; - -&usbphy { - usb0_id_det-gpios = <&pio 5 6 GPIO_ACTIVE_HIGH>; - status = "okay"; -}; diff --git a/arch/arm/dts/sun8i-v3s.dtsi b/arch/arm/dts/sun8i-v3s.dtsi deleted file mode 100644 index b3a32534762..00000000000 --- a/arch/arm/dts/sun8i-v3s.dtsi +++ /dev/null @@ -1,656 +0,0 @@ -/* - * Copyright (C) 2016 Icenowy Zheng - * Copyright (C) 2021 Tobias Schramm - * - * This file is dual-licensed: you can use it either under the terms - * of the GPL or the X11 license, at your option. Note that this dual - * licensing only applies to this file, and not this project as a - * whole. - * - * a) This file is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License as - * published by the Free Software Foundation; either version 2 of the - * License, or (at your option) any later version. - * - * This file is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * Or, alternatively, - * - * b) Permission is hereby granted, free of charge, to any person - * obtaining a copy of this software and associated documentation - * files (the "Software"), to deal in the Software without - * restriction, including without limitation the rights to use, - * copy, modify, merge, publish, distribute, sublicense, and/or - * sell copies of the Software, and to permit persons to whom the - * Software is furnished to do so, subject to the following - * conditions: - * - * The above copyright notice and this permission notice shall be - * included in all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, - * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES - * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND - * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT - * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, - * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING - * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR - * OTHER DEALINGS IN THE SOFTWARE. - */ - -#include -#include -#include -#include -#include - -/ { - #address-cells = <1>; - #size-cells = <1>; - interrupt-parent = <&gic>; - - chosen { - #address-cells = <1>; - #size-cells = <1>; - ranges; - - framebuffer-lcd { - compatible = "allwinner,simple-framebuffer", - "simple-framebuffer"; - allwinner,pipeline = "mixer0-lcd0"; - clocks = <&display_clocks CLK_MIXER0>, - <&ccu CLK_TCON0>; - status = "disabled"; - }; - }; - - cpus { - #address-cells = <1>; - #size-cells = <0>; - - cpu@0 { - compatible = "arm,cortex-a7"; - device_type = "cpu"; - reg = <0>; - clocks = <&ccu CLK_CPU>; - }; - }; - - de: display-engine { - compatible = "allwinner,sun8i-v3s-display-engine"; - allwinner,pipelines = <&mixer0>; - status = "disabled"; - }; - - timer { - compatible = "arm,armv7-timer"; - interrupts = , - , - , - ; - }; - - clocks { - #address-cells = <1>; - #size-cells = <1>; - ranges; - - osc24M: osc24M-clk { - #clock-cells = <0>; - compatible = "fixed-clock"; - clock-frequency = <24000000>; - clock-accuracy = <50000>; - clock-output-names = "osc24M"; - }; - - osc32k: osc32k-clk { - #clock-cells = <0>; - compatible = "fixed-clock"; - clock-frequency = <32768>; - clock-accuracy = <50000>; - clock-output-names = "ext-osc32k"; - }; - }; - - soc { - compatible = "simple-bus"; - #address-cells = <1>; - #size-cells = <1>; - ranges; - - display_clocks: clock@1000000 { - compatible = "allwinner,sun8i-v3s-de2-clk"; - reg = <0x01000000 0x10000>; - clocks = <&ccu CLK_BUS_DE>, - <&ccu CLK_DE>; - clock-names = "bus", - "mod"; - resets = <&ccu RST_BUS_DE>; - #clock-cells = <1>; - #reset-cells = <1>; - }; - - mixer0: mixer@1100000 { - compatible = "allwinner,sun8i-v3s-de2-mixer"; - reg = <0x01100000 0x100000>; - clocks = <&display_clocks 0>, - <&display_clocks 6>; - clock-names = "bus", - "mod"; - resets = <&display_clocks 0>; - - ports { - #address-cells = <1>; - #size-cells = <0>; - - mixer0_out: port@1 { - reg = <1>; - - mixer0_out_tcon0: endpoint { - remote-endpoint = <&tcon0_in_mixer0>; - }; - }; - }; - }; - - syscon: system-control@1c00000 { - compatible = "allwinner,sun8i-v3s-system-control", - "allwinner,sun8i-h3-system-control"; - reg = <0x01c00000 0xd0>; - #address-cells = <1>; - #size-cells = <1>; - ranges; - }; - - nmi_intc: interrupt-controller@1c000d0 { - compatible = "allwinner,sun8i-v3s-nmi", - "allwinner,sun9i-a80-nmi"; - interrupt-controller; - #interrupt-cells = <2>; - reg = <0x01c000d0 0x0c>; - interrupts = ; - }; - - dma: dma-controller@1c02000 { - compatible = "allwinner,sun8i-v3s-dma"; - reg = <0x01c02000 0x1000>; - interrupts = ; - clocks = <&ccu CLK_BUS_DMA>; - resets = <&ccu RST_BUS_DMA>; - #dma-cells = <1>; - }; - - tcon0: lcd-controller@1c0c000 { - compatible = "allwinner,sun8i-v3s-tcon"; - reg = <0x01c0c000 0x1000>; - interrupts = ; - clocks = <&ccu CLK_BUS_TCON0>, - <&ccu CLK_TCON0>; - clock-names = "ahb", - "tcon-ch0"; - clock-output-names = "tcon-data-clock"; - #clock-cells = <0>; - resets = <&ccu RST_BUS_TCON0>; - reset-names = "lcd"; - status = "disabled"; - - ports { - #address-cells = <1>; - #size-cells = <0>; - - tcon0_in: port@0 { - reg = <0>; - - tcon0_in_mixer0: endpoint { - remote-endpoint = <&mixer0_out_tcon0>; - }; - }; - - tcon0_out: port@1 { - #address-cells = <1>; - #size-cells = <0>; - reg = <1>; - }; - }; - }; - - - mmc0: mmc@1c0f000 { - compatible = "allwinner,sun7i-a20-mmc"; - reg = <0x01c0f000 0x1000>; - clocks = <&ccu CLK_BUS_MMC0>, - <&ccu CLK_MMC0>, - <&ccu CLK_MMC0_OUTPUT>, - <&ccu CLK_MMC0_SAMPLE>; - clock-names = "ahb", - "mmc", - "output", - "sample"; - resets = <&ccu RST_BUS_MMC0>; - reset-names = "ahb"; - interrupts = ; - pinctrl-names = "default"; - pinctrl-0 = <&mmc0_pins>; - status = "disabled"; - #address-cells = <1>; - #size-cells = <0>; - }; - - mmc1: mmc@1c10000 { - compatible = "allwinner,sun7i-a20-mmc"; - reg = <0x01c10000 0x1000>; - clocks = <&ccu CLK_BUS_MMC1>, - <&ccu CLK_MMC1>, - <&ccu CLK_MMC1_OUTPUT>, - <&ccu CLK_MMC1_SAMPLE>; - clock-names = "ahb", - "mmc", - "output", - "sample"; - resets = <&ccu RST_BUS_MMC1>; - reset-names = "ahb"; - interrupts = ; - pinctrl-names = "default"; - pinctrl-0 = <&mmc1_pins>; - status = "disabled"; - #address-cells = <1>; - #size-cells = <0>; - }; - - mmc2: mmc@1c11000 { - compatible = "allwinner,sun7i-a20-mmc"; - reg = <0x01c11000 0x1000>; - clocks = <&ccu CLK_BUS_MMC2>, - <&ccu CLK_MMC2>, - <&ccu CLK_MMC2_OUTPUT>, - <&ccu CLK_MMC2_SAMPLE>; - clock-names = "ahb", - "mmc", - "output", - "sample"; - resets = <&ccu RST_BUS_MMC2>; - reset-names = "ahb"; - interrupts = ; - status = "disabled"; - #address-cells = <1>; - #size-cells = <0>; - }; - - crypto@1c15000 { - compatible = "allwinner,sun8i-v3s-crypto", - "allwinner,sun8i-a33-crypto"; - reg = <0x01c15000 0x1000>; - interrupts = ; - clocks = <&ccu CLK_BUS_CE>, <&ccu CLK_CE>; - clock-names = "ahb", "mod"; - dmas = <&dma 16>, <&dma 16>; - dma-names = "rx", "tx"; - resets = <&ccu RST_BUS_CE>; - reset-names = "ahb"; - }; - - usb_otg: usb@1c19000 { - compatible = "allwinner,sun8i-h3-musb"; - reg = <0x01c19000 0x0400>; - clocks = <&ccu CLK_BUS_OTG>; - resets = <&ccu RST_BUS_OTG>; - interrupts = ; - interrupt-names = "mc"; - phys = <&usbphy 0>; - phy-names = "usb"; - extcon = <&usbphy 0>; - status = "disabled"; - }; - - usbphy: phy@1c19400 { - compatible = "allwinner,sun8i-v3s-usb-phy"; - reg = <0x01c19400 0x2c>, - <0x01c1a800 0x4>; - reg-names = "phy_ctrl", - "pmu0"; - clocks = <&ccu CLK_USB_PHY0>; - clock-names = "usb0_phy"; - resets = <&ccu RST_USB_PHY0>; - reset-names = "usb0_reset"; - status = "disabled"; - #phy-cells = <1>; - }; - - ehci: usb@1c1a000 { - compatible = "allwinner,sun8i-v3s-ehci", "generic-ehci"; - reg = <0x01c1a000 0x100>; - interrupts = ; - clocks = <&ccu CLK_BUS_EHCI0>, <&ccu CLK_BUS_OHCI0>; - resets = <&ccu RST_BUS_EHCI0>, <&ccu RST_BUS_OHCI0>; - phys = <&usbphy 0>; - phy-names = "usb"; - status = "disabled"; - }; - - ohci: usb@1c1a400 { - compatible = "allwinner,sun8i-v3s-ohci", "generic-ohci"; - reg = <0x01c1a400 0x100>; - interrupts = ; - clocks = <&ccu CLK_BUS_EHCI0>, <&ccu CLK_BUS_OHCI0>, - <&ccu CLK_USB_OHCI0>; - resets = <&ccu RST_BUS_EHCI0>, <&ccu RST_BUS_OHCI0>; - phys = <&usbphy 0>; - phy-names = "usb"; - status = "disabled"; - }; - - ccu: clock@1c20000 { - compatible = "allwinner,sun8i-v3s-ccu"; - reg = <0x01c20000 0x400>; - clocks = <&osc24M>, <&rtc CLK_OSC32K>; - clock-names = "hosc", "losc"; - #clock-cells = <1>; - #reset-cells = <1>; - }; - - rtc: rtc@1c20400 { - #clock-cells = <1>; - compatible = "allwinner,sun8i-v3-rtc"; - reg = <0x01c20400 0x54>; - interrupts = , - ; - clocks = <&osc32k>; - clock-output-names = "osc32k", "osc32k-out"; - }; - - pio: pinctrl@1c20800 { - compatible = "allwinner,sun8i-v3s-pinctrl"; - reg = <0x01c20800 0x400>; - interrupts = , - ; - clocks = <&ccu CLK_BUS_PIO>, <&osc24M>, - <&rtc CLK_OSC32K>; - clock-names = "apb", "hosc", "losc"; - gpio-controller; - #gpio-cells = <3>; - interrupt-controller; - #interrupt-cells = <3>; - - /omit-if-no-ref/ - csi0_mclk_pin: csi0-mclk-pin { - pins = "PE20"; - function = "csi_mipi"; - }; - - /omit-if-no-ref/ - csi1_8bit_pins: csi1-8bit-pins { - pins = "PE0", "PE2", "PE3", "PE8", "PE9", - "PE10", "PE11", "PE12", "PE13", "PE14", - "PE15"; - function = "csi"; - }; - - /omit-if-no-ref/ - csi1_mclk_pin: csi1-mclk-pin { - pins = "PE1"; - function = "csi"; - }; - - i2c0_pins: i2c0-pins { - pins = "PB6", "PB7"; - function = "i2c0"; - }; - - /omit-if-no-ref/ - i2c1_pb_pins: i2c1-pb-pins { - pins = "PB8", "PB9"; - function = "i2c1"; - }; - - /omit-if-no-ref/ - i2c1_pe_pins: i2c1-pe-pins { - pins = "PE21", "PE22"; - function = "i2c1"; - }; - - uart0_pb_pins: uart0-pb-pins { - pins = "PB8", "PB9"; - function = "uart0"; - }; - - uart2_pins: uart2-pins { - pins = "PB0", "PB1"; - function = "uart2"; - }; - - mmc0_pins: mmc0-pins { - pins = "PF0", "PF1", "PF2", "PF3", - "PF4", "PF5"; - function = "mmc0"; - drive-strength = <30>; - bias-pull-up; - }; - - mmc1_pins: mmc1-pins { - pins = "PG0", "PG1", "PG2", "PG3", - "PG4", "PG5"; - function = "mmc1"; - drive-strength = <30>; - bias-pull-up; - }; - - /omit-if-no-ref/ - pwm0_pin: pwm0-pin { - pins = "PB4"; - function = "pwm0"; - }; - - /omit-if-no-ref/ - pwm1_pin: pwm1-pin { - pins = "PB5"; - function = "pwm1"; - }; - - spi0_pins: spi0-pins { - pins = "PC0", "PC1", "PC2", "PC3"; - function = "spi0"; - }; - }; - - timer@1c20c00 { - compatible = "allwinner,sun8i-v3s-timer"; - reg = <0x01c20c00 0xa0>; - interrupts = , - , - ; - clocks = <&osc24M>; - }; - - wdt0: watchdog@1c20ca0 { - compatible = "allwinner,sun6i-a31-wdt"; - reg = <0x01c20ca0 0x20>; - interrupts = ; - clocks = <&osc24M>; - }; - - pwm: pwm@1c21400 { - compatible = "allwinner,sun8i-v3s-pwm", - "allwinner,sun7i-a20-pwm"; - reg = <0x01c21400 0xc>; - clocks = <&osc24M>; - #pwm-cells = <3>; - status = "disabled"; - }; - - lradc: lradc@1c22800 { - compatible = "allwinner,sun4i-a10-lradc-keys"; - reg = <0x01c22800 0x400>; - interrupts = ; - status = "disabled"; - }; - - codec: codec@1c22c00 { - #sound-dai-cells = <0>; - compatible = "allwinner,sun8i-v3s-codec"; - reg = <0x01c22c00 0x400>; - interrupts = ; - clocks = <&ccu CLK_BUS_CODEC>, <&ccu CLK_AC_DIG>; - clock-names = "apb", "codec"; - resets = <&ccu RST_BUS_CODEC>; - dmas = <&dma 15>, <&dma 15>; - dma-names = "rx", "tx"; - allwinner,codec-analog-controls = <&codec_analog>; - status = "disabled"; - }; - - codec_analog: codec-analog@1c23000 { - compatible = "allwinner,sun8i-v3s-codec-analog"; - reg = <0x01c23000 0x4>; - }; - - uart0: serial@1c28000 { - compatible = "snps,dw-apb-uart"; - reg = <0x01c28000 0x400>; - interrupts = ; - reg-shift = <2>; - reg-io-width = <4>; - clocks = <&ccu CLK_BUS_UART0>; - dmas = <&dma 6>, <&dma 6>; - dma-names = "tx", "rx"; - resets = <&ccu RST_BUS_UART0>; - status = "disabled"; - }; - - uart1: serial@1c28400 { - compatible = "snps,dw-apb-uart"; - reg = <0x01c28400 0x400>; - interrupts = ; - reg-shift = <2>; - reg-io-width = <4>; - clocks = <&ccu CLK_BUS_UART1>; - dmas = <&dma 7>, <&dma 7>; - dma-names = "tx", "rx"; - resets = <&ccu RST_BUS_UART1>; - status = "disabled"; - }; - - uart2: serial@1c28800 { - compatible = "snps,dw-apb-uart"; - reg = <0x01c28800 0x400>; - interrupts = ; - reg-shift = <2>; - reg-io-width = <4>; - clocks = <&ccu CLK_BUS_UART2>; - dmas = <&dma 8>, <&dma 8>; - dma-names = "tx", "rx"; - resets = <&ccu RST_BUS_UART2>; - pinctrl-0 = <&uart2_pins>; - pinctrl-names = "default"; - status = "disabled"; - }; - - i2c0: i2c@1c2ac00 { - compatible = "allwinner,sun6i-a31-i2c"; - reg = <0x01c2ac00 0x400>; - interrupts = ; - clocks = <&ccu CLK_BUS_I2C0>; - resets = <&ccu RST_BUS_I2C0>; - pinctrl-names = "default"; - pinctrl-0 = <&i2c0_pins>; - status = "disabled"; - #address-cells = <1>; - #size-cells = <0>; - }; - - i2c1: i2c@1c2b000 { - compatible = "allwinner,sun6i-a31-i2c"; - reg = <0x01c2b000 0x400>; - interrupts = ; - clocks = <&ccu CLK_BUS_I2C1>; - resets = <&ccu RST_BUS_I2C1>; - status = "disabled"; - #address-cells = <1>; - #size-cells = <0>; - }; - - emac: ethernet@1c30000 { - compatible = "allwinner,sun8i-v3s-emac"; - syscon = <&syscon>; - reg = <0x01c30000 0x10000>; - interrupts = ; - interrupt-names = "macirq"; - resets = <&ccu RST_BUS_EMAC>; - reset-names = "stmmaceth"; - clocks = <&ccu CLK_BUS_EMAC>; - clock-names = "stmmaceth"; - phy-handle = <&int_mii_phy>; - phy-mode = "mii"; - status = "disabled"; - - mdio: mdio { - #address-cells = <1>; - #size-cells = <0>; - compatible = "snps,dwmac-mdio"; - }; - - mdio_mux: mdio-mux { - compatible = "allwinner,sun8i-h3-mdio-mux"; - #address-cells = <1>; - #size-cells = <0>; - - mdio-parent-bus = <&mdio>; - /* Only one MDIO is usable at the time */ - internal_mdio: mdio@1 { - compatible = "allwinner,sun8i-h3-mdio-internal"; - reg = <1>; - #address-cells = <1>; - #size-cells = <0>; - - int_mii_phy: ethernet-phy@1 { - compatible = "ethernet-phy-ieee802.3-c22"; - reg = <1>; - clocks = <&ccu CLK_BUS_EPHY>; - resets = <&ccu RST_BUS_EPHY>; - }; - }; - }; - }; - - spi0: spi@1c68000 { - compatible = "allwinner,sun8i-h3-spi"; - reg = <0x01c68000 0x1000>; - interrupts = ; - clocks = <&ccu CLK_BUS_SPI0>, <&ccu CLK_SPI0>; - clock-names = "ahb", "mod"; - dmas = <&dma 23>, <&dma 23>; - dma-names = "rx", "tx"; - pinctrl-names = "default"; - pinctrl-0 = <&spi0_pins>; - resets = <&ccu RST_BUS_SPI0>; - status = "disabled"; - #address-cells = <1>; - #size-cells = <0>; - }; - - gic: interrupt-controller@1c81000 { - compatible = "arm,gic-400"; - reg = <0x01c81000 0x1000>, - <0x01c82000 0x2000>, - <0x01c84000 0x2000>, - <0x01c86000 0x2000>; - interrupt-controller; - #interrupt-cells = <3>; - interrupts = ; - }; - - csi1: camera@1cb4000 { - compatible = "allwinner,sun8i-v3s-csi"; - reg = <0x01cb4000 0x3000>; - interrupts = ; - clocks = <&ccu CLK_BUS_CSI>, - <&ccu CLK_CSI_SCLK>, - <&ccu CLK_DRAM_CSI>; - clock-names = "bus", "mod", "ram"; - resets = <&ccu RST_BUS_CSI>; - status = "disabled"; - }; - }; -}; diff --git a/arch/arm/mach-sunxi/Kconfig b/arch/arm/mach-sunxi/Kconfig index 6a511c4fd39..5f128e73709 100644 --- a/arch/arm/mach-sunxi/Kconfig +++ b/arch/arm/mach-sunxi/Kconfig @@ -487,6 +487,7 @@ config MACH_SUN8I_V3S select SUNXI_DRAM_DW_16BIT select SUPPORT_SPL select ARMV7_BOOT_SEC_DEFAULT if OLD_SUNXI_KERNEL_COMPAT + imply OF_UPSTREAM config MACH_SUN9I bool "sun9i (Allwinner A80)" diff --git a/configs/LicheePi_Zero_defconfig b/configs/LicheePi_Zero_defconfig index c37c49ccbb1..baea0477798 100644 --- a/configs/LicheePi_Zero_defconfig +++ b/configs/LicheePi_Zero_defconfig @@ -1,6 +1,6 @@ CONFIG_ARM=y CONFIG_ARCH_SUNXI=y -CONFIG_DEFAULT_DEVICE_TREE="sun8i-v3s-licheepi-zero" +CONFIG_DEFAULT_DEVICE_TREE="allwinner/sun8i-v3s-licheepi-zero" CONFIG_SPL=y CONFIG_MACH_SUN8I_V3S=y CONFIG_DRAM_CLK=360 diff --git a/configs/pinecube_defconfig b/configs/pinecube_defconfig index 7567a6aa739..de092424611 100644 --- a/configs/pinecube_defconfig +++ b/configs/pinecube_defconfig @@ -1,6 +1,6 @@ CONFIG_ARM=y CONFIG_ARCH_SUNXI=y -CONFIG_DEFAULT_DEVICE_TREE="sun8i-s3-pinecube" +CONFIG_DEFAULT_DEVICE_TREE="allwinner/sun8i-s3-pinecube" CONFIG_SPL=y CONFIG_MACH_SUN8I_V3S=y CONFIG_SUNXI_DRAM_DDR3_1333=y From e706ea63b93d3443830467ab4c711988f5cc44be Mon Sep 17 00:00:00 2001 From: Paul Kocialkowski Date: Tue, 5 Aug 2025 19:48:17 +0200 Subject: [PATCH 002/112] sunxi: Kconfig: Fix default order for V3s DRAM clock The V3s (using co-packaged DRAM) runs at 360 MHz, which is specified in the common platform Kconfig file. However the value for MACH_SUN8I will be picked up instead due to ordering. Re-order the defaults to have MACH_SUN8I_V3S before MACH_SUN8I and let it select the correct default. Also update the LicheePi Zero Dock defconfig to remove the value, which is now correctly selected. Signed-off-by: Paul Kocialkowski Reviewed-by: Andre Przywara --- arch/arm/mach-sunxi/Kconfig | 2 +- configs/LicheePi_Zero_defconfig | 1 - 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/arch/arm/mach-sunxi/Kconfig b/arch/arm/mach-sunxi/Kconfig index 5f128e73709..b04ec671696 100644 --- a/arch/arm/mach-sunxi/Kconfig +++ b/arch/arm/mach-sunxi/Kconfig @@ -719,9 +719,9 @@ config DRAM_CLK int "sunxi dram clock speed" default 792 if MACH_SUN9I default 648 if MACH_SUN8I_R40 - default 312 if MACH_SUN6I || MACH_SUN8I default 360 if MACH_SUN4I || MACH_SUN5I || MACH_SUN7I || \ MACH_SUN8I_V3S + default 312 if MACH_SUN6I || MACH_SUN8I default 672 if MACH_SUN50I default 744 if MACH_SUN50I_H6 default 720 if MACH_SUN50I_H616 || MACH_SUN50I_A133 diff --git a/configs/LicheePi_Zero_defconfig b/configs/LicheePi_Zero_defconfig index baea0477798..7460548461d 100644 --- a/configs/LicheePi_Zero_defconfig +++ b/configs/LicheePi_Zero_defconfig @@ -3,6 +3,5 @@ CONFIG_ARCH_SUNXI=y CONFIG_DEFAULT_DEVICE_TREE="allwinner/sun8i-v3s-licheepi-zero" CONFIG_SPL=y CONFIG_MACH_SUN8I_V3S=y -CONFIG_DRAM_CLK=360 # CONFIG_HAS_ARMV7_SECURE_BASE is not set CONFIG_NO_NET=y From 06b18e1ed512a3c312f9f04ae25b7966cf9eb909 Mon Sep 17 00:00:00 2001 From: Andre Przywara Date: Wed, 30 Jul 2025 23:38:52 +0100 Subject: [PATCH 003/112] pinctrl: sunxi: a523: change Ethernet pin function name The name of the pin function was changed last minute in the DT, from emac0 to gmac0. Adjust the name we use in the pinctrl driver accordingly. Signed-off-by: Andre Przywara Reviewed-by: Jernej Skrabec --- drivers/pinctrl/sunxi/pinctrl-sunxi.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/pinctrl/sunxi/pinctrl-sunxi.c b/drivers/pinctrl/sunxi/pinctrl-sunxi.c index 03cfe23aaf8..fd357ab0d4e 100644 --- a/drivers/pinctrl/sunxi/pinctrl-sunxi.c +++ b/drivers/pinctrl/sunxi/pinctrl-sunxi.c @@ -760,7 +760,7 @@ static const struct sunxi_pinctrl_desc __maybe_unused sun50i_h616_pinctrl_desc = }; static const struct sunxi_pinctrl_function sun55i_a523_pinctrl_functions[] = { - { "emac0", 5 }, /* PI0-PI16 */ + { "gmac0", 5 }, /* PI0-PI16 */ { "gpio_in", 0 }, { "gpio_out", 1 }, { "mmc0", 2 }, /* PF0-PF5 */ From 50dfe957c622addf3f4a70cbdc760af8aee565dd Mon Sep 17 00:00:00 2001 From: Andre Przywara Date: Tue, 29 Jul 2025 00:24:52 +0100 Subject: [PATCH 004/112] sunxi: a527: radxa/avaota: enable Ethernet The first of the two Ethernet controllers in the Allwinner A527/T527 is compatible to the MAC from the previous SoCs. Consequently the recent DT update brought use the MAC node, using the A64 compatible string as the fallback, which works out of the box. Enable the sun8i-emac Ethernet driver in the defconfig for the Radxa and the Avaota boards, so that kernels and other data can be loaded via TFTP. Please note that only one of the Ethernet sockets will work, the second MAC is not compatible, and needs a new U-Boot driver. The X96QPro+ TV box unfortunately uses only this second EMAC, so Ethernet cannot be used there at the moment. Signed-off-by: Andre Przywara Reviewed-by: Jernej Skrabec --- configs/avaota-a1_defconfig | 2 ++ configs/radxa-cubie-a5e_defconfig | 2 ++ 2 files changed, 4 insertions(+) diff --git a/configs/avaota-a1_defconfig b/configs/avaota-a1_defconfig index 55457edd3b3..a4582c00d5b 100644 --- a/configs/avaota-a1_defconfig +++ b/configs/avaota-a1_defconfig @@ -22,6 +22,8 @@ CONFIG_SYS_I2C_MVTWSI=y CONFIG_SYS_I2C_SLAVE=0x7f CONFIG_SYS_I2C_SPEED=400000 CONFIG_SUPPORT_EMMC_BOOT=y +CONFIG_PHY_REALTEK=y +CONFIG_SUN8I_EMAC=y CONFIG_REGULATOR_AXP=y CONFIG_AXP717_POWER=y CONFIG_AXP_I2C_ADDRESS=0x35 diff --git a/configs/radxa-cubie-a5e_defconfig b/configs/radxa-cubie-a5e_defconfig index 88019acf576..9d204ef5548 100644 --- a/configs/radxa-cubie-a5e_defconfig +++ b/configs/radxa-cubie-a5e_defconfig @@ -22,6 +22,8 @@ CONFIG_SYS_I2C_MVTWSI=y CONFIG_SYS_I2C_SLAVE=0x7f CONFIG_SYS_I2C_SPEED=400000 CONFIG_SUPPORT_EMMC_BOOT=y +CONFIG_PHY_REALTEK=y +CONFIG_SUN8I_EMAC=y CONFIG_REGULATOR_AXP=y CONFIG_AXP717_POWER=y CONFIG_AXP_DCDC2_VOLT=920 From cef5636d5ab6a4d8a553840a4a706ab86ca61291 Mon Sep 17 00:00:00 2001 From: Andre Przywara Date: Sat, 19 Jul 2025 00:58:34 +0100 Subject: [PATCH 005/112] sunxi: a133: dram: fix data type for address variable Variables holding addresses are typically using the "long" C type in U-Boot, to be easily compatible with both 32-bit and 64-bit builds. The A133 DRAM driver is typically compiled for AArch64, so u64 is the same type as unsigned long, but that breaks when compiling the DRAM driver in AArch32 (for some experiments). Fix the type to make the code more portable. Signed-off-by: Andre Przywara Reviewed-by: Jernej Skrabec --- arch/arm/mach-sunxi/dram_sun50i_a133.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/arm/mach-sunxi/dram_sun50i_a133.c b/arch/arm/mach-sunxi/dram_sun50i_a133.c index 3a231141168..1496f99624d 100644 --- a/arch/arm/mach-sunxi/dram_sun50i_a133.c +++ b/arch/arm/mach-sunxi/dram_sun50i_a133.c @@ -416,7 +416,7 @@ static void mctl_com_init(const struct dram_para *para, static void mctl_drive_odt_config(const struct dram_para *para) { u32 val; - u64 base; + ulong base; u32 i; /* DX drive */ From b26eea99b1a61a9216efc56c40ba1e27ab2ea8c6 Mon Sep 17 00:00:00 2001 From: Paul Kocialkowski Date: Tue, 5 Aug 2025 19:48:24 +0200 Subject: [PATCH 006/112] sunxi: pinecube: Enable EMAC and network support The pinecube has an ethernet connector which uses the EMAC and internal PHY of the chip. Enable it in the config. Reviewed-by: Andre Przywara Signed-off-by: Paul Kocialkowski --- configs/pinecube_defconfig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/configs/pinecube_defconfig b/configs/pinecube_defconfig index de092424611..5c81ced4956 100644 --- a/configs/pinecube_defconfig +++ b/configs/pinecube_defconfig @@ -9,13 +9,13 @@ CONFIG_DRAM_ODT_EN=y CONFIG_I2C0_ENABLE=y # CONFIG_HAS_ARMV7_SECURE_BASE is not set CONFIG_SPL_I2C=y -CONFIG_NO_NET=y CONFIG_SPL_SYS_I2C_LEGACY=y CONFIG_SYS_I2C_MVTWSI=y CONFIG_SYS_I2C_SLAVE=0x7f CONFIG_SYS_I2C_SPEED=400000 CONFIG_MTD=y CONFIG_SPI_FLASH_WINBOND=y +CONFIG_SUN8I_EMAC=y CONFIG_AXP209_POWER=y CONFIG_AXP_DCDC2_VOLT=1250 CONFIG_AXP_DCDC3_VOLT=3300 From 4b8405b54780e824cae9893c6b9b42bae2b08f63 Mon Sep 17 00:00:00 2001 From: Andre Przywara Date: Sun, 20 Jul 2025 16:29:19 +0100 Subject: [PATCH 007/112] sunxi: spl: initialise timer before clocks Recent changes in the H6 clock code added delay() calls into the SPL clock setup routine, which requires the timers to work. When compiling for AArch64, we are always using the Arm Generic Timer (aka. arch timer), which does not require further setup, hence having an empty timer_init() routine. However for 32-bit SoCs we use the Allwinner timers, which require some setup routine, and hence we need timer_init() to be called before clock_init(). Swap the order of the two calls, to be more robust when compiling the H6 clock code for AArch32 or when using the Allwinner timers for whatever reason. Signed-off-by: Andre Przywara Reviewed-by: Jernej Skrabec --- arch/arm/mach-sunxi/board.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/arm/mach-sunxi/board.c b/arch/arm/mach-sunxi/board.c index fb4837c2082..432b1c10f92 100644 --- a/arch/arm/mach-sunxi/board.c +++ b/arch/arm/mach-sunxi/board.c @@ -476,8 +476,8 @@ void board_init_f(ulong dummy) /* Enable non-secure access to some peripherals */ tzpc_init(); - clock_init(); timer_init(); + clock_init(); gpio_init(); spl_init(); From 7161a5f6861ee620f97d1c622a2281dfbba6fd4b Mon Sep 17 00:00:00 2001 From: Eric Anderson Date: Sat, 12 Jul 2025 17:27:41 -0700 Subject: [PATCH 008/112] sunxi: Enable SPL/SPI boot for OLinuXino Lime2 58e9502e6 "arm: sunxi: Enable SPL/SPI boot for Olinuxino Lime2-eMMC boards" enabled SPI boot for the eMMC variant. Olimex offers the "s16MB" variant with SPI flash populated but without eMMC populated. Tested on board rev L. Signed-off-by: Eric Anderson Signed-off-by: Andre Przywara --- configs/A20-OLinuXino-Lime2_defconfig | 1 + 1 file changed, 1 insertion(+) diff --git a/configs/A20-OLinuXino-Lime2_defconfig b/configs/A20-OLinuXino-Lime2_defconfig index f885fc01e6e..da0bb6683d0 100644 --- a/configs/A20-OLinuXino-Lime2_defconfig +++ b/configs/A20-OLinuXino-Lime2_defconfig @@ -5,6 +5,7 @@ CONFIG_SPL=y CONFIG_MACH_SUN7I=y CONFIG_DRAM_CLK=384 CONFIG_I2C1_ENABLE=y +CONFIG_SPL_SPI_SUNXI=y CONFIG_AHCI=y # CONFIG_SYS_MALLOC_CLEAR_ON_INIT is not set CONFIG_SPL_I2C=y From c453a80cc3b999ad515ed7fcfcf3062e8de1f696 Mon Sep 17 00:00:00 2001 From: Andre Przywara Date: Sun, 27 Jul 2025 14:04:09 +0100 Subject: [PATCH 009/112] sunxi: H616: dram: fix LPDDR3 mode register settings The JEDEC LPDDR3 spec defines mode register 0 (MR0) as being read-only, so there is no point in trying to set its value. Also the H616 memory controller encodes the mode register index to be written starting from bit 8 in MRCTRL1 (for LPDDR3 and LPDDR4 chips), so we need to OR in that number to tell the controller which MR to program. On top of that, the mode registers between DDR3 and LPDDR3 are completely different, so writing values crafted for DDR3 into a LPDDR3 chip is just wrong. Due to the above mentioned bugs the writes for MR0-MR2 did not have any effect (as they were all trying to set the read-only MR0), so the mode registers just stayed unchanged. Looking at the LPDDR3 spec and the BSP code, let's write the proper MR values into LPDDR3 chips, using the proper addressing mode. Use the opportunity to document the LPDDR3 mode register bits written. Signed-off-by: Andre Przywara Reviewed-by: Jernej Skrabec --- arch/arm/mach-sunxi/dram_sun50i_h616.c | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/arch/arm/mach-sunxi/dram_sun50i_h616.c b/arch/arm/mach-sunxi/dram_sun50i_h616.c index 877181016f3..3345c9b8e82 100644 --- a/arch/arm/mach-sunxi/dram_sun50i_h616.c +++ b/arch/arm/mach-sunxi/dram_sun50i_h616.c @@ -1078,18 +1078,18 @@ static bool mctl_phy_init(const struct dram_para *para, mctl_await_completion(&mctl_ctl->mrctrl0, BIT(31), 0); break; case SUNXI_DRAM_TYPE_LPDDR3: - writel(mr0, &mctl_ctl->mrctrl1); + /* MR0 is read-only */ + /* MR1: nWR=14, BL8 */ + writel(0x183, &mctl_ctl->mrctrl1); writel(0x800000f0, &mctl_ctl->mrctrl0); mctl_await_completion(&mctl_ctl->mrctrl0, BIT(31), 0); - writel(4, &mctl_ctl->mrctrl1); - writel(0x800000f0, &mctl_ctl->mrctrl0); - mctl_await_completion(&mctl_ctl->mrctrl0, BIT(31), 0); - - writel(mr2, &mctl_ctl->mrctrl1); + /* MR2: no WR leveling, WL set A, use nWR>9, nRL=14/nWL=8 */ + writel(0x21c, &mctl_ctl->mrctrl1); writel(0x800000f0, &mctl_ctl->mrctrl0); mctl_await_completion(&mctl_ctl->mrctrl0, BIT(31), 0); + /* MR3: 34.3 Ohm pull-up/pull-down resistor */ writel(0x301, &mctl_ctl->mrctrl1); writel(0x800000f0, &mctl_ctl->mrctrl0); mctl_await_completion(&mctl_ctl->mrctrl0, BIT(31), 0); From fda7bee6468ee5a701e268162aaa7645d98b85f0 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Wed, 6 Aug 2025 17:55:04 +0100 Subject: [PATCH 010/112] phy: qcom: Fix ret is uninitialised In qcom_snps_eusb2_phy_probe after the call to devm_clk_get if an error is found then ret is printed but has not been assigned to by the code. Decode the error from the pointer and assign it to ret. This issue was found by Smatch. Signed-off-by: Andrew Goodbody Reviewed-by: Sumit Garg Link: https://lore.kernel.org/r/20250806-phy_qcom_snps-v1-1-5cda830026c7@linaro.org Signed-off-by: Casey Connolly --- drivers/phy/qcom/phy-qcom-snps-eusb2.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/drivers/phy/qcom/phy-qcom-snps-eusb2.c b/drivers/phy/qcom/phy-qcom-snps-eusb2.c index b2655ac007c..28502c46f67 100644 --- a/drivers/phy/qcom/phy-qcom-snps-eusb2.c +++ b/drivers/phy/qcom/phy-qcom-snps-eusb2.c @@ -331,8 +331,9 @@ static int qcom_snps_eusb2_phy_probe(struct udevice *dev) qcom_snps_eusb2->ref_clk = devm_clk_get(dev, "ref"); if (IS_ERR(qcom_snps_eusb2->ref_clk)) { + ret = PTR_ERR(qcom_snps_eusb2->ref_clk); printf("%s: failed to get ref clk %d\n", __func__, ret); - return PTR_ERR(qcom_snps_eusb2->ref_clk); + return ret; } ret = reset_get_bulk(dev, &qcom_snps_eusb2->resets); From 23e1a11f4e8e3333ddcbff3bf88763c711340fe2 Mon Sep 17 00:00:00 2001 From: Casey Connolly Date: Mon, 11 Aug 2025 12:45:13 +0200 Subject: [PATCH 011/112] mach-snapdragon: fix erroneous lmb allocations In commit 6e4675b8e5d8 ("lmb: replace the lmb_alloc() and lmb_alloc_base() API's") an additional allocation was mistakenly introduced resulting in ${kernel_comp_size} containing the address of a second 64mb region rather than the actual value of KERNEL_COMP_SIZE. Additionally, in commit b40d7b8f72f1 ("Merge patch series "lmb: use a single API for all allocations"") merge conflict resulted in an additional 128mb allocation for ${loadaddr} when CONFIG_FASTBOOT is enabled, where it should actually be set to the same value as ${fastboot_addr_r} to respect size constraints (and since it doesn't seem to interfer with any bootflows). Fixup both of these, freeing up 192mb of memory. Fixes: 6e4675b8e5d8 ("lmb: replace the lmb_alloc() and lmb_alloc_base() API's") Fixes: b40d7b8f72f1 ("Merge patch series "lmb: use a single API for all allocations"") Link: https://lore.kernel.org/r/20250811104710.1896382-1-casey.connolly@linaro.org Signed-off-by: Casey Connolly --- arch/arm/mach-snapdragon/board.c | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) diff --git a/arch/arm/mach-snapdragon/board.c b/arch/arm/mach-snapdragon/board.c index fc921a4be26..5fb3240acc5 100644 --- a/arch/arm/mach-snapdragon/board.c +++ b/arch/arm/mach-snapdragon/board.c @@ -534,8 +534,7 @@ int board_late_init(void) env_set_hex("ramdisk_addr_r", addr) : 1; status |= !lmb_alloc(KERNEL_COMP_SIZE, &addr) ? env_set_hex("kernel_comp_addr_r", addr) : 1; - status |= !lmb_alloc(KERNEL_COMP_SIZE, &addr) ? - env_set_hex("kernel_comp_size", addr) : 1; + status |= env_set_hex("kernel_comp_size", KERNEL_COMP_SIZE); status |= !lmb_alloc(SZ_4M, &addr) ? env_set_hex("scriptaddr", addr) : 1; status |= !lmb_alloc(SZ_4M, &addr) ? @@ -544,9 +543,13 @@ int board_late_init(void) if (IS_ENABLED(CONFIG_FASTBOOT)) { status |= !lmb_alloc(FASTBOOT_BUF_SIZE, &addr) ? env_set_hex("fastboot_addr_r", addr) : 1; - /* override loadaddr for memory rich soc */ - status |= !lmb_alloc(SZ_128M, &addr) ? - env_set_hex("loadaddr", addr) : 1; + /* + * Override loadaddr for memory rich soc since ${loadaddr} and + * ${kernel_addr_r} need to be different for the Android boot image + * flow. It's typically safe for ${loadaddr} to be the same address + * as the fastboot buffer. + */ + status |= env_set_hex("loadaddr", addr); } fdt_status |= !lmb_alloc(SZ_2M, &addr) ? From f236451cb426fc3edaf756dac6346cd6273179b8 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Mon, 11 Aug 2025 18:03:39 +0100 Subject: [PATCH 012/112] serial: msm-geni: Detect error from get_clk_div_rate In msm_serial_setbrg if the call to get_clk_div_rate fails then there will not have been an assignment to clk_div which will lead to the call to geni_serial_baud using an uninitialised value. Check for an error from get_clk_div_rate and return an error code if so. This issue was found by Smatch. Signed-off-by: Andrew Goodbody Reviewed-by: Casey Connolly Link: https://lore.kernel.org/r/20250811-serial_msm_geni-v1-1-4499179491bc@linaro.org Signed-off-by: Casey Connolly --- drivers/serial/serial_msm_geni.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/drivers/serial/serial_msm_geni.c b/drivers/serial/serial_msm_geni.c index cb6c09fdd09..33016f0cb53 100644 --- a/drivers/serial/serial_msm_geni.c +++ b/drivers/serial/serial_msm_geni.c @@ -252,6 +252,10 @@ static int msm_serial_setbrg(struct udevice *dev, int baud) priv->baud = baud; clk_rate = get_clk_div_rate(baud, priv->oversampling, &clk_div); + if (!clk_rate) { + pr_err("%s: Couldn't get clock division rate\n", __func__); + return -EINVAL; + } ret = geni_serial_set_clock_rate(dev, clk_rate); if (ret < 0) { pr_err("%s: Couldn't set clock rate: %d\n", __func__, ret); From 10e65926a37d06831fc913221f9eb930c4194060 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Mon, 11 Aug 2025 18:03:40 +0100 Subject: [PATCH 013/112] serial: msm-geni: No need to NULL check priv The NULL check for priv in qcom_geni_serial_poll_bit serves no useful prupose as too much other code surrounding it relies on priv being valid. Remove the NULL check for priv and other related code. This issue was found by Smatch. Signed-off-by: Andrew Goodbody Link: https://lore.kernel.org/r/20250811-serial_msm_geni-v1-2-4499179491bc@linaro.org Signed-off-by: Casey Connolly --- drivers/serial/serial_msm_geni.c | 28 ++++++++++++---------------- 1 file changed, 12 insertions(+), 16 deletions(-) diff --git a/drivers/serial/serial_msm_geni.c b/drivers/serial/serial_msm_geni.c index 33016f0cb53..0eb90f82a34 100644 --- a/drivers/serial/serial_msm_geni.c +++ b/drivers/serial/serial_msm_geni.c @@ -288,23 +288,19 @@ static bool qcom_geni_serial_poll_bit(const struct udevice *dev, int offset, unsigned int tx_fifo_depth; unsigned int tx_fifo_width; unsigned int fifo_bits; - unsigned long timeout_us = 10000; + unsigned long timeout_us; - baud = 115200; - - if (priv) { - baud = priv->baud; - if (!baud) - baud = 115200; - tx_fifo_depth = geni_se_get_tx_fifo_depth(priv->base); - tx_fifo_width = geni_se_get_tx_fifo_width(priv->base); - fifo_bits = tx_fifo_depth * tx_fifo_width; - /* - * Total polling iterations based on FIFO worth of bytes to be - * sent at current baud. Add a little fluff to the wait. - */ - timeout_us = ((fifo_bits * USEC_PER_SEC) / baud) + 500; - } + baud = priv->baud; + if (!baud) + baud = 115200; + tx_fifo_depth = geni_se_get_tx_fifo_depth(priv->base); + tx_fifo_width = geni_se_get_tx_fifo_width(priv->base); + fifo_bits = tx_fifo_depth * tx_fifo_width; + /* + * Total polling iterations based on FIFO worth of bytes to be + * sent at current baud. Add a little fluff to the wait. + */ + timeout_us = ((fifo_bits * USEC_PER_SEC) / baud) + 500; timeout_us = DIV_ROUND_UP(timeout_us, 10) * 10; while (timeout_us) { From 8a0bb0b176069989d645e1edca2737d46770a530 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Wed, 23 Jul 2025 11:58:04 +0100 Subject: [PATCH 014/112] button: qcom-pmic: Fix dereference of uninitialised pointer The pointer 'label' is declared and later dereferenced without ever having a value assigned to it. Add an assignment to this pointer so it will be valid later when dereferenced. This issue was found by Smatch. Signed-off-by: Andrew Goodbody Reviewed-by: Casey Connolly Link: https://lore.kernel.org/r/20250723-button-qcom-pmic-v1-1-9c317ac71167@linaro.org Signed-off-by: Casey Connolly --- drivers/button/button-qcom-pmic.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/drivers/button/button-qcom-pmic.c b/drivers/button/button-qcom-pmic.c index 85addfe32a2..b823490d6d5 100644 --- a/drivers/button/button-qcom-pmic.c +++ b/drivers/button/button-qcom-pmic.c @@ -195,8 +195,9 @@ static int button_qcom_pmic_bind(struct udevice *parent) continue; } + label = ofnode_get_name(node); ret = device_bind_driver_to_node(parent, "qcom_pwrkey", - ofnode_get_name(node), + label, node, &dev); if (ret) { printf("Failed to bind %s! %d\n", label, ret); From be12b6e158a06580437f2e4756eb6021cf0cbfbe Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Thu, 7 Aug 2025 12:20:01 +0100 Subject: [PATCH 015/112] pinctrl: qcom: sa8775: Limit check for array index not correct In sa8775p_get_pin_name the limit check for the index into msm_special_pins_data allows for more elements than exist. Add code to ensure the array index remains in bounds. This issue was found by Smatch. Signed-off-by: Andrew Goodbody Link: https://lore.kernel.org/r/20250807-pinctrl_qcom-v1-1-42fac6707fd5@linaro.org Signed-off-by: Casey Connolly --- drivers/pinctrl/qcom/pinctrl-sa8775p.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/drivers/pinctrl/qcom/pinctrl-sa8775p.c b/drivers/pinctrl/qcom/pinctrl-sa8775p.c index cb2496ff1fb..d4acae15d55 100644 --- a/drivers/pinctrl/qcom/pinctrl-sa8775p.c +++ b/drivers/pinctrl/qcom/pinctrl-sa8775p.c @@ -516,7 +516,9 @@ static const char *sa8775p_get_function_name(struct udevice *dev, static const char *sa8775p_get_pin_name(struct udevice *dev, unsigned int selector) { - if (selector >= 149 && selector <= 155) + if (selector > 153) + strcpy(pin_name, "unknown"); + else if (selector >= 149) snprintf(pin_name, MAX_PIN_NAME_LEN, msm_special_pins_data[selector - 149].name); else From d9fbc1d70bc9d5e7665c9fc1ed71d25e04faba54 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Thu, 7 Aug 2025 12:20:02 +0100 Subject: [PATCH 016/112] pinctrl: qcom: sdm845: Limit check off by 1 The driver specifies 154 pins so should have a maximum selector of 153 to ensure that the index into the array special_pins_names does not overflow. This issue was found by Smatch. Signed-off-by: Andrew Goodbody Link: https://lore.kernel.org/r/20250807-pinctrl_qcom-v1-2-42fac6707fd5@linaro.org Signed-off-by: Casey Connolly --- drivers/pinctrl/qcom/pinctrl-sdm845.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/pinctrl/qcom/pinctrl-sdm845.c b/drivers/pinctrl/qcom/pinctrl-sdm845.c index 3f55fc81c8e..24b42e94c7a 100644 --- a/drivers/pinctrl/qcom/pinctrl-sdm845.c +++ b/drivers/pinctrl/qcom/pinctrl-sdm845.c @@ -72,7 +72,7 @@ static const char *sdm845_get_pin_name(struct udevice *dev, "sdc2_data", }; - if (selector >= 150 && selector <= 154) + if (selector >= 150 && selector <= 153) snprintf(pin_name, MAX_PIN_NAME_LEN, special_pins_names[selector - 150]); else snprintf(pin_name, MAX_PIN_NAME_LEN, "gpio%u", selector); From c64fc632a86a58e343cb3f181cd8d5642a28894a Mon Sep 17 00:00:00 2001 From: Michal Simek Date: Thu, 17 Jul 2025 08:26:15 +0200 Subject: [PATCH 017/112] riscv: cpu: Use CONFIG_IS_ENABLED(CPU) instead of plain ifdef ifdef CONFIG_CPU only works in U-Boot proper but macro is not working when XPL phases are used. In this case CONFIG_SPL_CPU is also defined and can be disabled which is causing compilation error. Signed-off-by: Michal Simek Reviewed-by: Leo Yu-Chi Liang --- arch/riscv/cpu/cpu.c | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/arch/riscv/cpu/cpu.c b/arch/riscv/cpu/cpu.c index 15c4e14599d..d5123e4b7d9 100644 --- a/arch/riscv/cpu/cpu.c +++ b/arch/riscv/cpu/cpu.c @@ -608,14 +608,14 @@ static inline bool supports_extension(char ext) static int riscv_cpu_probe(void) { -#ifdef CONFIG_CPU - int ret; + if (CONFIG_IS_ENABLED(CPU)) { + int ret; - /* probe cpus so that RISC-V timer can be bound */ - ret = cpu_probe_all(); - if (ret) - return log_msg_ret("RISC-V cpus probe failed\n", ret); -#endif + /* probe cpus so that RISC-V timer can be bound */ + ret = cpu_probe_all(); + if (ret) + return log_msg_ret("RISC-V cpus probe failed\n", ret); + } return 0; } From 4da366de5d754097d1ed94cd8e722c39a8865f6f Mon Sep 17 00:00:00 2001 From: Martin Herren Date: Sat, 19 Jul 2025 23:46:32 +0200 Subject: [PATCH 018/112] riscv: Set SYS_BOOTM_LEN explicitly to 0x800000 For all riscv defconfigs that use the current default value. This is done in provision of changing the default value to the most common used value of 0x4000000. Signed-off-by: Martin Herren Acked-by: Michal Simek # xilinx_mbv Reviewed-by: Leo Yu-Chi Liang --- configs/k230_canmv_defconfig | 1 + configs/microchip_mpfs_icicle_defconfig | 1 + configs/sipeed_maix_bitm_defconfig | 1 + configs/sipeed_maix_smode_defconfig | 1 + configs/xilinx_mbv32_defconfig | 1 + configs/xilinx_mbv32_smode_defconfig | 1 + configs/xilinx_mbv64_defconfig | 1 + configs/xilinx_mbv64_smode_defconfig | 1 + 8 files changed, 8 insertions(+) diff --git a/configs/k230_canmv_defconfig b/configs/k230_canmv_defconfig index a43412f0290..8781c12d3fd 100644 --- a/configs/k230_canmv_defconfig +++ b/configs/k230_canmv_defconfig @@ -4,6 +4,7 @@ CONFIG_NR_DRAM_BANKS=1 CONFIG_HAS_CUSTOM_SYS_INIT_SP_ADDR=y CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0x80400000 CONFIG_DEFAULT_DEVICE_TREE="k230-canmv" +CONFIG_SYS_BOOTM_LEN=0x800000 CONFIG_SYS_LOAD_ADDR=0xc000000 CONFIG_TARGET_K230_CANMV=y CONFIG_ARCH_RV64I=y diff --git a/configs/microchip_mpfs_icicle_defconfig b/configs/microchip_mpfs_icicle_defconfig index 6937aa224a1..99df10dc4c2 100644 --- a/configs/microchip_mpfs_icicle_defconfig +++ b/configs/microchip_mpfs_icicle_defconfig @@ -5,6 +5,7 @@ CONFIG_HAS_CUSTOM_SYS_INIT_SP_ADDR=y CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0x80200000 CONFIG_ENV_SIZE=0x2000 CONFIG_DEFAULT_DEVICE_TREE="microchip/mpfs-icicle-kit" +CONFIG_SYS_BOOTM_LEN=0x800000 CONFIG_SYS_LOAD_ADDR=0x80200000 CONFIG_SYS_MEM_TOP_HIDE=0x400000 # CONFIG_DEBUG_UART is not set diff --git a/configs/sipeed_maix_bitm_defconfig b/configs/sipeed_maix_bitm_defconfig index 9fcdfb4a8fe..bb9e7f7d903 100644 --- a/configs/sipeed_maix_bitm_defconfig +++ b/configs/sipeed_maix_bitm_defconfig @@ -5,6 +5,7 @@ CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0x803fffff CONFIG_ENV_SIZE=0x1000 CONFIG_ENV_OFFSET=0xfff000 CONFIG_ENV_SECT_SIZE=0x1000 +CONFIG_SYS_BOOTM_LEN=0x800000 CONFIG_SYS_LOAD_ADDR=0x80000000 CONFIG_SF_DEFAULT_BUS=3 CONFIG_TARGET_SIPEED_MAIX=y diff --git a/configs/sipeed_maix_smode_defconfig b/configs/sipeed_maix_smode_defconfig index 11d78688780..aadadbcab3f 100644 --- a/configs/sipeed_maix_smode_defconfig +++ b/configs/sipeed_maix_smode_defconfig @@ -6,6 +6,7 @@ CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0x803fffff CONFIG_ENV_SIZE=0x1000 CONFIG_ENV_OFFSET=0xfff000 CONFIG_ENV_SECT_SIZE=0x1000 +CONFIG_SYS_BOOTM_LEN=0x800000 CONFIG_SYS_LOAD_ADDR=0x80000000 CONFIG_SF_DEFAULT_BUS=3 CONFIG_TARGET_SIPEED_MAIX=y diff --git a/configs/xilinx_mbv32_defconfig b/configs/xilinx_mbv32_defconfig index 92f7aa04ec0..a6268dd1dde 100644 --- a/configs/xilinx_mbv32_defconfig +++ b/configs/xilinx_mbv32_defconfig @@ -8,6 +8,7 @@ CONFIG_DEFAULT_DEVICE_TREE="xilinx-mbv32" CONFIG_SPL_STACK=0x80200000 CONFIG_SPL_BSS_START_ADDR=0x84000000 CONFIG_SPL_BSS_MAX_SIZE=0x80000 +CONFIG_SYS_BOOTM_LEN=0x800000 CONFIG_SYS_LOAD_ADDR=0x80200000 CONFIG_SPL_SIZE_LIMIT=0x40000 CONFIG_SPL=y diff --git a/configs/xilinx_mbv32_smode_defconfig b/configs/xilinx_mbv32_smode_defconfig index b61ec90d096..2073bc71092 100644 --- a/configs/xilinx_mbv32_smode_defconfig +++ b/configs/xilinx_mbv32_smode_defconfig @@ -8,6 +8,7 @@ CONFIG_DEFAULT_DEVICE_TREE="xilinx-mbv32" CONFIG_SPL_STACK=0x80200000 CONFIG_SPL_BSS_START_ADDR=0x84000000 CONFIG_SPL_BSS_MAX_SIZE=0x80000 +CONFIG_SYS_BOOTM_LEN=0x800000 CONFIG_SYS_LOAD_ADDR=0x80200000 CONFIG_SPL_SIZE_LIMIT=0x40000 CONFIG_SPL=y diff --git a/configs/xilinx_mbv64_defconfig b/configs/xilinx_mbv64_defconfig index c4d458370b6..3bedec95b77 100644 --- a/configs/xilinx_mbv64_defconfig +++ b/configs/xilinx_mbv64_defconfig @@ -8,6 +8,7 @@ CONFIG_DEFAULT_DEVICE_TREE="xilinx-mbv64" CONFIG_SPL_STACK=0x80200000 CONFIG_SPL_BSS_START_ADDR=0x84000000 CONFIG_SPL_BSS_MAX_SIZE=0x80000 +CONFIG_SYS_BOOTM_LEN=0x800000 CONFIG_SYS_LOAD_ADDR=0x80200000 CONFIG_SPL_SIZE_LIMIT=0x40000 CONFIG_SPL=y diff --git a/configs/xilinx_mbv64_smode_defconfig b/configs/xilinx_mbv64_smode_defconfig index 2d7227c9e33..e45e4e638bb 100644 --- a/configs/xilinx_mbv64_smode_defconfig +++ b/configs/xilinx_mbv64_smode_defconfig @@ -8,6 +8,7 @@ CONFIG_DEFAULT_DEVICE_TREE="xilinx-mbv64" CONFIG_SPL_STACK=0x80200000 CONFIG_SPL_BSS_START_ADDR=0x84000000 CONFIG_SPL_BSS_MAX_SIZE=0x80000 +CONFIG_SYS_BOOTM_LEN=0x800000 CONFIG_SYS_LOAD_ADDR=0x80200000 CONFIG_SPL_SIZE_LIMIT=0x40000 CONFIG_SPL=y From b8e140c1f23b8dd93c62946734cbed8b218450b3 Mon Sep 17 00:00:00 2001 From: Martin Herren Date: Sat, 19 Jul 2025 23:46:33 +0200 Subject: [PATCH 019/112] riscv: Set SYS_BOOTM_LEN default to 0x4000000 This changes the default value to the most commonly used one among existing defconfigs. Signed-off-by: Martin Herren Acked-by: Michal Simek # xilinx_mbv Reviewed-by: Leo Yu-Chi Liang Reviewed-by: Mattijs Korpershoek --- boot/Kconfig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/boot/Kconfig b/boot/Kconfig index 2ff6f003738..54ef7052c5c 100644 --- a/boot/Kconfig +++ b/boot/Kconfig @@ -1057,7 +1057,7 @@ config SYS_BOOTM_LEN hex "Maximum size of a decompresed OS image" depends on CMD_BOOTM || CMD_BOOTI || CMD_BOOTZ || \ LEGACY_IMAGE_FORMAT || SPL_LEGACY_IMAGE_FORMAT - default 0x4000000 if PPC || ARM64 + default 0x4000000 if PPC || ARM64 || RISCV default 0x1000000 if X86 || ARCH_MX6 || ARCH_MX7 default 0x800000 help From 2fd48ef2d71d9666b81726c16332db0f14dcd28e Mon Sep 17 00:00:00 2001 From: Martin Herren Date: Sat, 19 Jul 2025 23:46:34 +0200 Subject: [PATCH 020/112] riscv: Remove default SYS_BOOTM_LEN from defconfig Remove CONFIG_SYS_BOOTM_LEN from all riscv defconfigs where the new default value is used. Signed-off-by: Martin Herren Acked-by: Michal Simek # xilinx_mbv Reviewed-by: Leo Yu-Chi Liang --- configs/ae350_rv32_defconfig | 1 - configs/ae350_rv32_falcon_defconfig | 1 - configs/ae350_rv32_falcon_xip_defconfig | 1 - configs/ae350_rv32_spl_defconfig | 1 - configs/ae350_rv32_spl_xip_defconfig | 1 - configs/ae350_rv32_xip_defconfig | 1 - configs/ae350_rv64_defconfig | 1 - configs/ae350_rv64_falcon_defconfig | 1 - configs/ae350_rv64_falcon_xip_defconfig | 1 - configs/ae350_rv64_spl_defconfig | 1 - configs/ae350_rv64_spl_xip_defconfig | 1 - configs/ae350_rv64_xip_defconfig | 1 - configs/ibex-ast2700_defconfig | 1 - configs/milkv_duo_defconfig | 1 - configs/qemu-riscv32_defconfig | 1 - configs/qemu-riscv32_smode_defconfig | 1 - configs/qemu-riscv32_spl_defconfig | 1 - configs/qemu-riscv64_defconfig | 1 - configs/qemu-riscv64_smode_defconfig | 1 - configs/qemu-riscv64_spl_defconfig | 1 - configs/sifive_unleashed_defconfig | 1 - configs/sifive_unmatched_defconfig | 1 - configs/sipeed_licheerv_nano_defconfig | 1 - configs/starfive_visionfive2_defconfig | 1 - configs/th1520_lpi4a_defconfig | 1 - 25 files changed, 25 deletions(-) diff --git a/configs/ae350_rv32_defconfig b/configs/ae350_rv32_defconfig index 467d61d73df..e87782005f1 100644 --- a/configs/ae350_rv32_defconfig +++ b/configs/ae350_rv32_defconfig @@ -7,7 +7,6 @@ CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0xfffe80 CONFIG_ENV_SECT_SIZE=0x1000 CONFIG_DEFAULT_DEVICE_TREE="ae350_32" CONFIG_SYS_MONITOR_LEN=786432 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x100000 CONFIG_TARGET_ANDES_AE350=y CONFIG_SYS_MONITOR_BASE=0x88000000 diff --git a/configs/ae350_rv32_falcon_defconfig b/configs/ae350_rv32_falcon_defconfig index 66b809d2376..f1d88f8560f 100644 --- a/configs/ae350_rv32_falcon_defconfig +++ b/configs/ae350_rv32_falcon_defconfig @@ -9,7 +9,6 @@ CONFIG_DEFAULT_DEVICE_TREE="ae350_32" CONFIG_SYS_MONITOR_LEN=786432 CONFIG_SPL_SYS_MALLOC_F_LEN=0x2000000 CONFIG_SPL_BSS_START_ADDR=0x400000 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x100000 CONFIG_SPL=y CONFIG_TARGET_ANDES_AE350=y diff --git a/configs/ae350_rv32_falcon_xip_defconfig b/configs/ae350_rv32_falcon_xip_defconfig index a2f8d4cd236..2355bac5019 100644 --- a/configs/ae350_rv32_falcon_xip_defconfig +++ b/configs/ae350_rv32_falcon_xip_defconfig @@ -10,7 +10,6 @@ CONFIG_SYS_MONITOR_LEN=786432 CONFIG_SPL_SYS_MALLOC_F_LEN=0x2000000 CONFIG_SPL_TEXT_BASE=0x80000000 CONFIG_SPL_BSS_START_ADDR=0x400000 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x100000 CONFIG_SPL=y CONFIG_TARGET_ANDES_AE350=y diff --git a/configs/ae350_rv32_spl_defconfig b/configs/ae350_rv32_spl_defconfig index 098cf7686d6..6655cbd4a96 100644 --- a/configs/ae350_rv32_spl_defconfig +++ b/configs/ae350_rv32_spl_defconfig @@ -9,7 +9,6 @@ CONFIG_DEFAULT_DEVICE_TREE="ae350_32" CONFIG_SYS_MONITOR_LEN=786432 CONFIG_SPL_SYS_MALLOC_F_LEN=0x2000000 CONFIG_SPL_BSS_START_ADDR=0x400000 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x100000 CONFIG_SPL=y CONFIG_TARGET_ANDES_AE350=y diff --git a/configs/ae350_rv32_spl_xip_defconfig b/configs/ae350_rv32_spl_xip_defconfig index 23927888c87..44a6b6534b8 100644 --- a/configs/ae350_rv32_spl_xip_defconfig +++ b/configs/ae350_rv32_spl_xip_defconfig @@ -10,7 +10,6 @@ CONFIG_SYS_MONITOR_LEN=786432 CONFIG_SPL_SYS_MALLOC_F_LEN=0x2000000 CONFIG_SPL_TEXT_BASE=0x80000000 CONFIG_SPL_BSS_START_ADDR=0x400000 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x100000 CONFIG_SPL=y CONFIG_TARGET_ANDES_AE350=y diff --git a/configs/ae350_rv32_xip_defconfig b/configs/ae350_rv32_xip_defconfig index 75eb0618454..15f3b5c378b 100644 --- a/configs/ae350_rv32_xip_defconfig +++ b/configs/ae350_rv32_xip_defconfig @@ -7,7 +7,6 @@ CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0xfffe80 CONFIG_ENV_SECT_SIZE=0x1000 CONFIG_DEFAULT_DEVICE_TREE="ae350_32" CONFIG_SYS_MONITOR_LEN=786432 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x100000 CONFIG_TARGET_ANDES_AE350=y CONFIG_XIP=y diff --git a/configs/ae350_rv64_defconfig b/configs/ae350_rv64_defconfig index 932739e5dec..78b9fc439ac 100644 --- a/configs/ae350_rv64_defconfig +++ b/configs/ae350_rv64_defconfig @@ -6,7 +6,6 @@ CONFIG_HAS_CUSTOM_SYS_INIT_SP_ADDR=y CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0xfffd70 CONFIG_ENV_SECT_SIZE=0x1000 CONFIG_DEFAULT_DEVICE_TREE="ae350_64" -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x100000 CONFIG_TARGET_ANDES_AE350=y CONFIG_ARCH_RV64I=y diff --git a/configs/ae350_rv64_falcon_defconfig b/configs/ae350_rv64_falcon_defconfig index c9417175ce7..81bebb1a1d4 100644 --- a/configs/ae350_rv64_falcon_defconfig +++ b/configs/ae350_rv64_falcon_defconfig @@ -8,7 +8,6 @@ CONFIG_ENV_SECT_SIZE=0x1000 CONFIG_DEFAULT_DEVICE_TREE="ae350_64" CONFIG_SPL_SYS_MALLOC_F_LEN=0x2000000 CONFIG_SPL_BSS_START_ADDR=0x400000 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x100000 CONFIG_SPL=y CONFIG_TARGET_ANDES_AE350=y diff --git a/configs/ae350_rv64_falcon_xip_defconfig b/configs/ae350_rv64_falcon_xip_defconfig index e072f7c2ae9..8e1b8e20052 100644 --- a/configs/ae350_rv64_falcon_xip_defconfig +++ b/configs/ae350_rv64_falcon_xip_defconfig @@ -9,7 +9,6 @@ CONFIG_DEFAULT_DEVICE_TREE="ae350_64" CONFIG_SPL_SYS_MALLOC_F_LEN=0x2000000 CONFIG_SPL_TEXT_BASE=0x80000000 CONFIG_SPL_BSS_START_ADDR=0x400000 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x100000 CONFIG_SPL=y CONFIG_TARGET_ANDES_AE350=y diff --git a/configs/ae350_rv64_spl_defconfig b/configs/ae350_rv64_spl_defconfig index 83ce28077f0..7950074642e 100644 --- a/configs/ae350_rv64_spl_defconfig +++ b/configs/ae350_rv64_spl_defconfig @@ -8,7 +8,6 @@ CONFIG_ENV_SECT_SIZE=0x1000 CONFIG_DEFAULT_DEVICE_TREE="ae350_64" CONFIG_SPL_SYS_MALLOC_F_LEN=0x2000000 CONFIG_SPL_BSS_START_ADDR=0x400000 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x100000 CONFIG_SPL=y CONFIG_TARGET_ANDES_AE350=y diff --git a/configs/ae350_rv64_spl_xip_defconfig b/configs/ae350_rv64_spl_xip_defconfig index 5ad1751686c..d5882af1de1 100644 --- a/configs/ae350_rv64_spl_xip_defconfig +++ b/configs/ae350_rv64_spl_xip_defconfig @@ -9,7 +9,6 @@ CONFIG_DEFAULT_DEVICE_TREE="ae350_64" CONFIG_SPL_SYS_MALLOC_F_LEN=0x2000000 CONFIG_SPL_TEXT_BASE=0x80000000 CONFIG_SPL_BSS_START_ADDR=0x400000 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x100000 CONFIG_SPL=y CONFIG_TARGET_ANDES_AE350=y diff --git a/configs/ae350_rv64_xip_defconfig b/configs/ae350_rv64_xip_defconfig index 5ec2cba670b..46ce063c484 100644 --- a/configs/ae350_rv64_xip_defconfig +++ b/configs/ae350_rv64_xip_defconfig @@ -6,7 +6,6 @@ CONFIG_HAS_CUSTOM_SYS_INIT_SP_ADDR=y CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0xfffd70 CONFIG_ENV_SECT_SIZE=0x1000 CONFIG_DEFAULT_DEVICE_TREE="ae350_64" -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x100000 CONFIG_TARGET_ANDES_AE350=y CONFIG_ARCH_RV64I=y diff --git a/configs/ibex-ast2700_defconfig b/configs/ibex-ast2700_defconfig index f088aec8716..8e8259f291d 100644 --- a/configs/ibex-ast2700_defconfig +++ b/configs/ibex-ast2700_defconfig @@ -15,7 +15,6 @@ CONFIG_DM_RESET=y CONFIG_SPL_TEXT_BASE=0x14bc0080 CONFIG_SPL_BSS_START_ADDR=0x14bd7800 CONFIG_SPL_BSS_MAX_SIZE=0x800 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x83000000 CONFIG_SPL_SIZE_LIMIT=0x16000 CONFIG_SPL=y diff --git a/configs/milkv_duo_defconfig b/configs/milkv_duo_defconfig index 70393de5736..f1f3930564b 100644 --- a/configs/milkv_duo_defconfig +++ b/configs/milkv_duo_defconfig @@ -5,7 +5,6 @@ CONFIG_NR_DRAM_BANKS=1 CONFIG_HAS_CUSTOM_SYS_INIT_SP_ADDR=y CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0x82300000 CONFIG_DEFAULT_DEVICE_TREE="cv1800b-milkv-duo" -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x80080000 CONFIG_IDENT_STRING="milkv_duo" CONFIG_TARGET_MILKV_DUO=y diff --git a/configs/qemu-riscv32_defconfig b/configs/qemu-riscv32_defconfig index bf39a1da723..e22585a705a 100644 --- a/configs/qemu-riscv32_defconfig +++ b/configs/qemu-riscv32_defconfig @@ -5,7 +5,6 @@ CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0x80200000 CONFIG_ENV_SIZE=0x20000 CONFIG_DEFAULT_DEVICE_TREE="qemu-virt32" CONFIG_SYS_MONITOR_LEN=786432 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x80200000 CONFIG_TARGET_QEMU_VIRT=y CONFIG_FIT=y diff --git a/configs/qemu-riscv32_smode_defconfig b/configs/qemu-riscv32_smode_defconfig index 2a876aefecd..c588d01a676 100644 --- a/configs/qemu-riscv32_smode_defconfig +++ b/configs/qemu-riscv32_smode_defconfig @@ -5,7 +5,6 @@ CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0x80200000 CONFIG_ENV_SIZE=0x20000 CONFIG_DEFAULT_DEVICE_TREE="qemu-virt32" CONFIG_SYS_MONITOR_LEN=786432 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x80200000 CONFIG_TARGET_QEMU_VIRT=y CONFIG_RISCV_SMODE=y diff --git a/configs/qemu-riscv32_spl_defconfig b/configs/qemu-riscv32_spl_defconfig index 36f8b457586..d1c43575c2a 100644 --- a/configs/qemu-riscv32_spl_defconfig +++ b/configs/qemu-riscv32_spl_defconfig @@ -6,7 +6,6 @@ CONFIG_ENV_SIZE=0x20000 CONFIG_DEFAULT_DEVICE_TREE="qemu-virt32" CONFIG_SYS_MONITOR_LEN=786432 CONFIG_SPL_BSS_START_ADDR=0x84000000 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x80200000 CONFIG_SPL=y CONFIG_TARGET_QEMU_VIRT=y diff --git a/configs/qemu-riscv64_defconfig b/configs/qemu-riscv64_defconfig index a9ff831be91..cb91dfd9432 100644 --- a/configs/qemu-riscv64_defconfig +++ b/configs/qemu-riscv64_defconfig @@ -4,7 +4,6 @@ CONFIG_HAS_CUSTOM_SYS_INIT_SP_ADDR=y CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0x80200000 CONFIG_ENV_SIZE=0x20000 CONFIG_DEFAULT_DEVICE_TREE="qemu-virt64" -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x80200000 CONFIG_TARGET_QEMU_VIRT=y CONFIG_ARCH_RV64I=y diff --git a/configs/qemu-riscv64_smode_defconfig b/configs/qemu-riscv64_smode_defconfig index 8384fe78a31..2ef67d40269 100644 --- a/configs/qemu-riscv64_smode_defconfig +++ b/configs/qemu-riscv64_smode_defconfig @@ -4,7 +4,6 @@ CONFIG_HAS_CUSTOM_SYS_INIT_SP_ADDR=y CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0x80200000 CONFIG_ENV_SIZE=0x20000 CONFIG_DEFAULT_DEVICE_TREE="qemu-virt64" -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x80200000 CONFIG_TARGET_QEMU_VIRT=y CONFIG_ARCH_RV64I=y diff --git a/configs/qemu-riscv64_spl_defconfig b/configs/qemu-riscv64_spl_defconfig index 34e14b8f8df..04dec72ceac 100644 --- a/configs/qemu-riscv64_spl_defconfig +++ b/configs/qemu-riscv64_spl_defconfig @@ -5,7 +5,6 @@ CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0x80200000 CONFIG_ENV_SIZE=0x20000 CONFIG_DEFAULT_DEVICE_TREE="qemu-virt64" CONFIG_SPL_BSS_START_ADDR=0x84000000 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x80200000 CONFIG_SPL=y CONFIG_TARGET_QEMU_VIRT=y diff --git a/configs/sifive_unleashed_defconfig b/configs/sifive_unleashed_defconfig index 01963a4e54e..f341e3e0735 100644 --- a/configs/sifive_unleashed_defconfig +++ b/configs/sifive_unleashed_defconfig @@ -11,7 +11,6 @@ CONFIG_DM_RESET=y CONFIG_SPL_MMC=y CONFIG_SPL_STACK=0x81cfe70 CONFIG_SPL_BSS_START_ADDR=0x85000000 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x80200000 CONFIG_SPL=y CONFIG_SPL_SPI_FLASH_SUPPORT=y diff --git a/configs/sifive_unmatched_defconfig b/configs/sifive_unmatched_defconfig index acbea7fe1bb..0a736f2ba95 100644 --- a/configs/sifive_unmatched_defconfig +++ b/configs/sifive_unmatched_defconfig @@ -12,7 +12,6 @@ CONFIG_DM_RESET=y CONFIG_SPL_MMC=y CONFIG_SPL_STACK=0x81cfe60 CONFIG_SPL_BSS_START_ADDR=0x85000000 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x80200000 CONFIG_SPL=y CONFIG_SPL_SPI_FLASH_SUPPORT=y diff --git a/configs/sipeed_licheerv_nano_defconfig b/configs/sipeed_licheerv_nano_defconfig index fc7f82e878a..9aa3ede10c5 100644 --- a/configs/sipeed_licheerv_nano_defconfig +++ b/configs/sipeed_licheerv_nano_defconfig @@ -5,7 +5,6 @@ CONFIG_NR_DRAM_BANKS=1 CONFIG_HAS_CUSTOM_SYS_INIT_SP_ADDR=y CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0x82300000 CONFIG_DEFAULT_DEVICE_TREE="sg2002-licheerv-nano-b" -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x80080000 CONFIG_IDENT_STRING="licheerv_nano" CONFIG_TARGET_LICHEERV_NANO=y diff --git a/configs/starfive_visionfive2_defconfig b/configs/starfive_visionfive2_defconfig index 3e34e4a87f8..544140c03f7 100644 --- a/configs/starfive_visionfive2_defconfig +++ b/configs/starfive_visionfive2_defconfig @@ -18,7 +18,6 @@ CONFIG_SPL_STACK=0x8180000 CONFIG_SPL_TEXT_BASE=0x8000000 CONFIG_SPL_BSS_START_ADDR=0x8040000 CONFIG_SPL_BSS_MAX_SIZE=0x10000 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x82000000 CONFIG_SPL=y CONFIG_SPL_SPI_FLASH_SUPPORT=y diff --git a/configs/th1520_lpi4a_defconfig b/configs/th1520_lpi4a_defconfig index 2763cbb428a..48cd8991591 100644 --- a/configs/th1520_lpi4a_defconfig +++ b/configs/th1520_lpi4a_defconfig @@ -10,7 +10,6 @@ CONFIG_DEFAULT_DEVICE_TREE="th1520-lichee-pi-4a" CONFIG_SPL_STACK=0xffe0170000 CONFIG_SPL_BSS_START_ADDR=0xffe0160000 CONFIG_SPL_BSS_MAX_SIZE=0x10000 -CONFIG_SYS_BOOTM_LEN=0x4000000 CONFIG_SYS_LOAD_ADDR=0x80200000 CONFIG_SPL=y CONFIG_TARGET_TH1520_LPI4A=y From 4bd206a423e1ced02445acaaaac2508f9c1f29b2 Mon Sep 17 00:00:00 2001 From: Martin Herren Date: Sat, 19 Jul 2025 23:46:35 +0200 Subject: [PATCH 021/112] riscv: Increase Microchip Icicle's SYS_BOOTM_LEN Increase Icicle's SYS_BOOTM_LEN to 0x4000000 which is the new default value. Done on Conor Dooley's request. Signed-off-by: Martin Herren Reviewed-by: Leo Yu-Chi Liang --- configs/microchip_mpfs_icicle_defconfig | 1 - 1 file changed, 1 deletion(-) diff --git a/configs/microchip_mpfs_icicle_defconfig b/configs/microchip_mpfs_icicle_defconfig index 99df10dc4c2..6937aa224a1 100644 --- a/configs/microchip_mpfs_icicle_defconfig +++ b/configs/microchip_mpfs_icicle_defconfig @@ -5,7 +5,6 @@ CONFIG_HAS_CUSTOM_SYS_INIT_SP_ADDR=y CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0x80200000 CONFIG_ENV_SIZE=0x2000 CONFIG_DEFAULT_DEVICE_TREE="microchip/mpfs-icicle-kit" -CONFIG_SYS_BOOTM_LEN=0x800000 CONFIG_SYS_LOAD_ADDR=0x80200000 CONFIG_SYS_MEM_TOP_HIDE=0x400000 # CONFIG_DEBUG_UART is not set From 5f5bba72c2f6f444cabff459ad3927fdc86dbdb3 Mon Sep 17 00:00:00 2001 From: Michal Simek Date: Tue, 22 Jul 2025 13:03:43 +0200 Subject: [PATCH 022/112] xilinx: mbv: Disable OF_HAS_PRIOR_STAGE There is no reason to use OF_BOARD for MBV because reduced DT is used by SPL and full DT is passed via u-boot.img or u-boot.itb. There is no reason to pick up DTB from certain address. Signed-off-by: Michal Simek Reviewed-by: Leo Yu-Chi Liang --- board/xilinx/mbv/Kconfig | 1 - 1 file changed, 1 deletion(-) diff --git a/board/xilinx/mbv/Kconfig b/board/xilinx/mbv/Kconfig index c52ba1870b0..68acd8955ae 100644 --- a/board/xilinx/mbv/Kconfig +++ b/board/xilinx/mbv/Kconfig @@ -28,7 +28,6 @@ config BOARD_SPECIFIC_OPTIONS imply SPL_RAM_DEVICE imply CMD_SBI imply CMD_PING - imply OF_HAS_PRIOR_STAGE source "board/xilinx/Kconfig" From 441ac0814216a0b29df675aec03c6de5b45ffbd6 Mon Sep 17 00:00:00 2001 From: Michal Simek Date: Tue, 22 Jul 2025 13:03:44 +0200 Subject: [PATCH 023/112] xilinx: mbv: Add missing mmu-type cpu property OpenSBI expects mmu-type to be present in DT that's why add it. Without it OpenSBI disable CPU node which ends up in not working boot. Signed-off-by: Michal Simek Reviewed-by: Leo Yu-Chi Liang --- arch/riscv/dts/xilinx-mbv32.dts | 3 ++- arch/riscv/dts/xilinx-mbv64.dts | 3 ++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/arch/riscv/dts/xilinx-mbv32.dts b/arch/riscv/dts/xilinx-mbv32.dts index 4050ce2f051..96e42806244 100644 --- a/arch/riscv/dts/xilinx-mbv32.dts +++ b/arch/riscv/dts/xilinx-mbv32.dts @@ -2,7 +2,7 @@ /* * dts file for AMD MicroBlaze V * - * (C) Copyright 2023, Advanced Micro Devices, Inc. + * (C) Copyright 2023 - 2025, Advanced Micro Devices, Inc. * * Michal Simek */ @@ -26,6 +26,7 @@ device_type = "cpu"; reg = <0>; riscv,isa = "rv32imafdc"; + mmu-type = "riscv,sv39"; i-cache-size = <32768>; d-cache-size = <32768>; clock-frequency = <100000000>; diff --git a/arch/riscv/dts/xilinx-mbv64.dts b/arch/riscv/dts/xilinx-mbv64.dts index 4d65d338ecb..5a989c1697e 100644 --- a/arch/riscv/dts/xilinx-mbv64.dts +++ b/arch/riscv/dts/xilinx-mbv64.dts @@ -2,7 +2,7 @@ /* * dts file for AMD MicroBlaze V * - * (C) Copyright 2023 - 2024, Advanced Micro Devices, Inc. + * (C) Copyright 2023 - 2025, Advanced Micro Devices, Inc. * * Michal Simek */ @@ -26,6 +26,7 @@ device_type = "cpu"; reg = <0>; riscv,isa = "rv64imafdc"; + mmu-type = "riscv,sv39"; i-cache-size = <32768>; d-cache-size = <32768>; clock-frequency = <100000000>; From 5fe8b532092ff7e7d822db7ef03b501547d22e56 Mon Sep 17 00:00:00 2001 From: Michal Simek Date: Tue, 22 Jul 2025 13:03:45 +0200 Subject: [PATCH 024/112] xilinx: mbv: Fix dt properties in interrupt controller node Properties didn't match dt binding that's why should be fixed. Signed-off-by: Michal Simek Reviewed-by: Leo Yu-Chi Liang --- arch/riscv/dts/xilinx-mbv32.dts | 3 ++- arch/riscv/dts/xilinx-mbv64.dts | 3 ++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/arch/riscv/dts/xilinx-mbv32.dts b/arch/riscv/dts/xilinx-mbv32.dts index 96e42806244..b426510f343 100644 --- a/arch/riscv/dts/xilinx-mbv32.dts +++ b/arch/riscv/dts/xilinx-mbv32.dts @@ -71,7 +71,8 @@ interrupt-controller; interrupt-parent = <&cpu0_intc>; #interrupt-cells = <2>; - kind-of-intr = <0>; + xlnx,num-intr-inputs = <2>; + xlnx,kind-of-intr = <0>; }; xlnx_timer0: timer@41c00000 { diff --git a/arch/riscv/dts/xilinx-mbv64.dts b/arch/riscv/dts/xilinx-mbv64.dts index 5a989c1697e..3762def29f9 100644 --- a/arch/riscv/dts/xilinx-mbv64.dts +++ b/arch/riscv/dts/xilinx-mbv64.dts @@ -71,7 +71,8 @@ interrupt-controller; interrupt-parent = <&cpu0_intc>; #interrupt-cells = <2>; - kind-of-intr = <0>; + xlnx,num-intr-inputs = <2>; + xlnx,kind-of-intr = <0>; }; xlnx_timer0: timer@41c00000 { From 87bd5806e608b555ea4f84ae217e44d50525f968 Mon Sep 17 00:00:00 2001 From: Michal Simek Date: Tue, 22 Jul 2025 13:03:46 +0200 Subject: [PATCH 025/112] xilinx: mbv: Use separate DTB for binman nodes The commit d92fdb60677b ("binman: Add option for pointing to separate description") added support for separating binman description to own file not the be the part of DT for OS. The main reason is that binman is not passing dt schema validation that's why want to keep it separated. Signed-off-by: Michal Simek Acked-by: Leo Yu-Chi Liang --- arch/riscv/dts/Makefile | 1 + arch/riscv/dts/xilinx-binman.dts | 12 ++++++++++++ arch/riscv/dts/xilinx-mbv32.dts | 2 -- arch/riscv/dts/xilinx-mbv64.dts | 2 -- configs/xilinx_mbv32_defconfig | 1 + configs/xilinx_mbv32_smode_defconfig | 1 + configs/xilinx_mbv64_defconfig | 1 + configs/xilinx_mbv64_smode_defconfig | 1 + 8 files changed, 17 insertions(+), 4 deletions(-) create mode 100644 arch/riscv/dts/xilinx-binman.dts diff --git a/arch/riscv/dts/Makefile b/arch/riscv/dts/Makefile index 2b10c2d6c01..68dfe9ce56d 100644 --- a/arch/riscv/dts/Makefile +++ b/arch/riscv/dts/Makefile @@ -14,6 +14,7 @@ dtb-$(CONFIG_TARGET_SIPEED_MAIX) += k210-maix-bit.dtb dtb-$(CONFIG_TARGET_TH1520_LPI4A) += th1520-lichee-pi-4a.dtb dtb-$(CONFIG_TARGET_XILINX_MBV) += xilinx-mbv32.dtb dtb-$(CONFIG_TARGET_XILINX_MBV) += xilinx-mbv64.dtb +dtb-$(CONFIG_TARGET_XILINX_MBV) += xilinx-binman.dtb dtb-$(CONFIG_TARGET_ASPEED_AST2700_IBEX) += ast2700-ibex.dtb include $(srctree)/scripts/Makefile.dts diff --git a/arch/riscv/dts/xilinx-binman.dts b/arch/riscv/dts/xilinx-binman.dts new file mode 100644 index 00000000000..715080ed763 --- /dev/null +++ b/arch/riscv/dts/xilinx-binman.dts @@ -0,0 +1,12 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * binman file for AMD MicroBlaze V + * + * (C) Copyright 2025, Advanced Micro Devices, Inc. + * + * Michal Simek + */ + +/dts-v1/; + +#include "binman.dtsi" diff --git a/arch/riscv/dts/xilinx-mbv32.dts b/arch/riscv/dts/xilinx-mbv32.dts index b426510f343..f7a3e076fd5 100644 --- a/arch/riscv/dts/xilinx-mbv32.dts +++ b/arch/riscv/dts/xilinx-mbv32.dts @@ -9,8 +9,6 @@ /dts-v1/; -#include "binman.dtsi" - / { #address-cells = <1>; #size-cells = <1>; diff --git a/arch/riscv/dts/xilinx-mbv64.dts b/arch/riscv/dts/xilinx-mbv64.dts index 3762def29f9..e6235ed2f52 100644 --- a/arch/riscv/dts/xilinx-mbv64.dts +++ b/arch/riscv/dts/xilinx-mbv64.dts @@ -9,8 +9,6 @@ /dts-v1/; -#include "binman.dtsi" - / { #address-cells = <2>; #size-cells = <2>; diff --git a/configs/xilinx_mbv32_defconfig b/configs/xilinx_mbv32_defconfig index a6268dd1dde..e3341179a68 100644 --- a/configs/xilinx_mbv32_defconfig +++ b/configs/xilinx_mbv32_defconfig @@ -41,5 +41,6 @@ CONFIG_DEBUG_UART_SKIP_INIT=y CONFIG_XILINX_UARTLITE=y CONFIG_XILINX_TIMER=y # CONFIG_BINMAN_FDT is not set +CONFIG_BINMAN_DTB="./arch/riscv/dts/xilinx-binman.dtb" CONFIG_PANIC_HANG=y CONFIG_SPL_GZIP=y diff --git a/configs/xilinx_mbv32_smode_defconfig b/configs/xilinx_mbv32_smode_defconfig index 2073bc71092..c95b4497395 100644 --- a/configs/xilinx_mbv32_smode_defconfig +++ b/configs/xilinx_mbv32_smode_defconfig @@ -45,5 +45,6 @@ CONFIG_XILINX_UARTLITE=y # CONFIG_RISCV_TIMER is not set CONFIG_XILINX_TIMER=y # CONFIG_BINMAN_FDT is not set +CONFIG_BINMAN_DTB="./arch/riscv/dts/xilinx-binman.dtb" CONFIG_PANIC_HANG=y CONFIG_SPL_GZIP=y diff --git a/configs/xilinx_mbv64_defconfig b/configs/xilinx_mbv64_defconfig index 3bedec95b77..a3cc1a5669e 100644 --- a/configs/xilinx_mbv64_defconfig +++ b/configs/xilinx_mbv64_defconfig @@ -42,5 +42,6 @@ CONFIG_DEBUG_UART_SKIP_INIT=y CONFIG_XILINX_UARTLITE=y CONFIG_XILINX_TIMER=y # CONFIG_BINMAN_FDT is not set +CONFIG_BINMAN_DTB="./arch/riscv/dts/xilinx-binman.dtb" CONFIG_PANIC_HANG=y CONFIG_SPL_GZIP=y diff --git a/configs/xilinx_mbv64_smode_defconfig b/configs/xilinx_mbv64_smode_defconfig index e45e4e638bb..3d49670c60c 100644 --- a/configs/xilinx_mbv64_smode_defconfig +++ b/configs/xilinx_mbv64_smode_defconfig @@ -46,5 +46,6 @@ CONFIG_XILINX_UARTLITE=y # CONFIG_RISCV_TIMER is not set CONFIG_XILINX_TIMER=y # CONFIG_BINMAN_FDT is not set +CONFIG_BINMAN_DTB="./arch/riscv/dts/xilinx-binman.dtb" CONFIG_PANIC_HANG=y CONFIG_SPL_GZIP=y From c22c40546be90fc94511011122e7a3cde3704fc5 Mon Sep 17 00:00:00 2001 From: Jamie Gibbons Date: Fri, 1 Aug 2025 13:36:21 +0100 Subject: [PATCH 026/112] configs: microchip_mpfs_icicle: enable CONFIG_OF_BOARD_SETUP Enable CONFIG_OF_BOARD_SETUP and other dependencies to allow the use of the ft_board_setup() function to replace fdt set in boot scripts for Microchip's MPFS Icicle kit. Signed-off-by: Jamie Gibbons Reviewed-by: Leo Yu-Chi Liang --- configs/microchip_mpfs_icicle_defconfig | 3 +++ 1 file changed, 3 insertions(+) diff --git a/configs/microchip_mpfs_icicle_defconfig b/configs/microchip_mpfs_icicle_defconfig index 6937aa224a1..9f933592c9d 100644 --- a/configs/microchip_mpfs_icicle_defconfig +++ b/configs/microchip_mpfs_icicle_defconfig @@ -5,6 +5,7 @@ CONFIG_HAS_CUSTOM_SYS_INIT_SP_ADDR=y CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0x80200000 CONFIG_ENV_SIZE=0x2000 CONFIG_DEFAULT_DEVICE_TREE="microchip/mpfs-icicle-kit" +CONFIG_OF_LIBFDT_OVERLAY=y CONFIG_SYS_LOAD_ADDR=0x80200000 CONFIG_SYS_MEM_TOP_HIDE=0x400000 # CONFIG_DEBUG_UART is not set @@ -13,6 +14,7 @@ CONFIG_ARCH_RV64I=y CONFIG_RISCV_SMODE=y CONFIG_FIT=y CONFIG_DISTRO_DEFAULTS=y +CONFIG_OF_BOARD_SETUP=y CONFIG_DEFAULT_FDT_FILE="microchip/mpfs-icicle-kit.dtb" CONFIG_SYS_CBSIZE=256 CONFIG_SYS_PBSIZE=282 @@ -20,6 +22,7 @@ CONFIG_DISPLAY_CPUINFO=y CONFIG_DISPLAY_BOARDINFO=y CONFIG_SYS_PROMPT="RISC-V # " CONFIG_OF_UPSTREAM=y +CONFIG_ENV_OVERWRITE_ETHADDR_ONCE=y CONFIG_ENV_RELOC_GD_ENV_ADDR=y CONFIG_BOOTP_SEND_HOSTNAME=y CONFIG_DM_MTD=y From 69539ef2f1e0406dcdcf41929c8f8e0d3a20f158 Mon Sep 17 00:00:00 2001 From: Jamie Gibbons Date: Fri, 1 Aug 2025 13:36:22 +0100 Subject: [PATCH 027/112] board: microchip: mpfs_icicle: make use of ft_board_setup() Move ethernet mac address setting to ft_board_setup() to remove the need for fdt set in custom boot script. Signed-off-by: Jamie Gibbons Acked-by: Leo Yu-Chi Liang --- board/microchip/mpfs_icicle/mpfs_icicle.c | 53 ++++++++++++----------- 1 file changed, 27 insertions(+), 26 deletions(-) diff --git a/board/microchip/mpfs_icicle/mpfs_icicle.c b/board/microchip/mpfs_icicle/mpfs_icicle.c index ba622e38ee5..19acbbba42b 100644 --- a/board/microchip/mpfs_icicle/mpfs_icicle.c +++ b/board/microchip/mpfs_icicle/mpfs_icicle.c @@ -22,6 +22,8 @@ DECLARE_GLOBAL_DATA_PTR; #define SERVICE_CR_REQ 0x1u #define SERVICE_SR_BUSY 0x2u +static unsigned char mac_addr[6]; + static void read_device_serial_number(u8 *response, u8 response_size) { u8 idx; @@ -145,10 +147,7 @@ int board_late_init(void) { u32 ret; int node; - u8 idx; - u8 device_serial_number[16] = { 0 }; - unsigned char mac_addr[6]; - char icicle_mac_addr[20]; + u8 device_serial_number[16] = {0}; void *blob = (void *)gd->fdt_blob; read_device_serial_number(device_serial_number, 16); @@ -170,19 +169,6 @@ int board_late_init(void) } } - icicle_mac_addr[0] = '['; - - sprintf(&icicle_mac_addr[1], "%pM", mac_addr); - - icicle_mac_addr[18] = ']'; - icicle_mac_addr[19] = '\0'; - - for (idx = 0; idx < 20; idx++) { - if (icicle_mac_addr[idx] == ':') - icicle_mac_addr[idx] = ' '; - } - env_set("icicle_mac_addr0", icicle_mac_addr); - mac_addr[5] = device_serial_number[0] + 1; node = fdt_path_offset(blob, "/soc/ethernet@20110000"); @@ -194,18 +180,33 @@ int board_late_init(void) } } - icicle_mac_addr[0] = '['; + return 0; +} - sprintf(&icicle_mac_addr[1], "%pM", mac_addr); +int ft_board_setup(void *blob, struct bd_info *bd) +{ + u32 ret; + int node; - icicle_mac_addr[18] = ']'; - icicle_mac_addr[19] = '\0'; - - for (idx = 0; idx < 20; idx++) { - if (icicle_mac_addr[idx] == ':') - icicle_mac_addr[idx] = ' '; + node = fdt_path_offset(blob, "/soc/ethernet@20110000"); + if (node >= 0) { + ret = fdt_setprop(blob, node, "local-mac-address", mac_addr, 6); + if (ret) { + printf("Error setting local-mac-address property for ethernet@20110000\n"); + return -ENODEV; + } + } + + mac_addr[5] -= 1; + + node = fdt_path_offset(blob, "/soc/ethernet@20112000"); + if (node >= 0) { + ret = fdt_setprop(blob, node, "local-mac-address", mac_addr, 6); + if (ret) { + printf("Error setting local-mac-address property for ethernet@20112000\n"); + return -ENODEV; + } } - env_set("icicle_mac_addr1", icicle_mac_addr); return 0; } From 111e9bf6a5acc8187c4849cbf4e7516e37496059 Mon Sep 17 00:00:00 2001 From: Jamie Gibbons Date: Fri, 1 Aug 2025 13:36:23 +0100 Subject: [PATCH 028/112] mailbox: add PolarFire SoC mailbox driver This driver adds support for the single mailbox channel of the MSS system controller on the Microchip PolarFire SoC. Signed-off-by: Jamie Gibbons Acked-by: Leo Yu-Chi Liang --- drivers/mailbox/Kconfig | 7 ++ drivers/mailbox/Makefile | 1 + drivers/mailbox/mpfs-mbox.c | 177 ++++++++++++++++++++++++++++++++++++ include/mpfs-mailbox.h | 66 ++++++++++++++ 4 files changed, 251 insertions(+) create mode 100644 drivers/mailbox/mpfs-mbox.c create mode 100644 include/mpfs-mailbox.h diff --git a/drivers/mailbox/Kconfig b/drivers/mailbox/Kconfig index 4d9f004ebad..f9531c1627c 100644 --- a/drivers/mailbox/Kconfig +++ b/drivers/mailbox/Kconfig @@ -28,6 +28,13 @@ config IMX_MU_MBOX Enable support for i.MX Messaging Unit for communication with other processors on the SoC using mailbox interface +config MPFS_MBOX + bool "Enable MPFS system controller support" + depends on DM_MAILBOX && ARCH_RV64I + help + Enable support for the mailboxes that provide a communication + channel with the system controller integrated on PolarFire SoC. + config SANDBOX_MBOX bool "Enable the sandbox mailbox test driver" depends on DM_MAILBOX && SANDBOX diff --git a/drivers/mailbox/Makefile b/drivers/mailbox/Makefile index e8c745f7d79..b54fbdfff15 100644 --- a/drivers/mailbox/Makefile +++ b/drivers/mailbox/Makefile @@ -6,6 +6,7 @@ obj-$(CONFIG_$(PHASE_)DM_MAILBOX) += mailbox-uclass.o obj-$(CONFIG_APPLE_MBOX) += apple-mbox.o obj-$(CONFIG_IMX_MU_MBOX) += imx-mailbox.o +obj-$(CONFIG_MPFS_MBOX) += mpfs-mbox.o obj-$(CONFIG_SANDBOX_MBOX) += sandbox-mbox.o obj-$(CONFIG_SANDBOX_MBOX) += sandbox-mbox-test.o obj-$(CONFIG_STM32_IPCC) += stm32-ipcc.o diff --git a/drivers/mailbox/mpfs-mbox.c b/drivers/mailbox/mpfs-mbox.c new file mode 100644 index 00000000000..55238847ecd --- /dev/null +++ b/drivers/mailbox/mpfs-mbox.c @@ -0,0 +1,177 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Microchip's PolarFire SoC (MPFS) Mailbox Driver + * + * Copyright (C) 2024 Microchip Technology Inc. All rights reserved. + * + * Author: Jamie Gibbons + * + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define SERVICES_CR_OFFSET 0x50u +#define SERVICES_SR_OFFSET 0x54u + +#define SERVICE_CR_REQ_MASK 0x1u +#define SERVICE_SR_BUSY_MASK 0x2u +#define SERVICE_SR_STATUS_SHIFT 16 +#define SERVICE_CR_COMMAND_SHIFT 16 +#define MASK_8BIT 0xFF + +struct mpfs_mbox { + struct udevice *dev; + void __iomem *ctrl_base; + void __iomem *mbox_base; + struct mbox_chan *chan; +}; + +static bool mpfs_mbox_busy(struct mbox_chan *chan) +{ + struct mpfs_mbox *mbox = dev_get_priv(chan->dev); + uint16_t status; + + status = readl(mbox->ctrl_base + SERVICES_SR_OFFSET); + + return status & SERVICE_SR_BUSY_MASK; +} + +static int mpfs_mbox_send(struct mbox_chan *chan, const void *data) +{ + struct mpfs_mbox *mbox = dev_get_priv(chan->dev); + struct mpfs_mss_msg *msg = (struct mpfs_mss_msg *)data; + u32 mailbox_val, cmd_shifted, value; + u8 *byte_buf; + u8 idx, byte_idx, byte_offset; + + u32 *word_buf = (u32 *)msg->cmd_data; + + if (mpfs_mbox_busy(chan)) + return -EBUSY; + + for (idx = 0; idx < (msg->cmd_data_size / BYTES_4); idx++) + writel(word_buf[idx], mbox->mbox_base + msg->mbox_offset + idx * BYTES_4); + + if ((msg->cmd_data_size % BYTES_4) > 0) { + byte_offset = (msg->cmd_data_size / BYTES_4) * BYTES_4; + byte_buf = (u8 *)(msg->cmd_data + byte_offset); + mailbox_val = readl(mbox->mbox_base + msg->mbox_offset + idx * BYTES_4); + + for (byte_idx = 0; byte_idx < (msg->cmd_data_size % BYTES_4); byte_idx++) { + mailbox_val &= ~(MASK_8BIT << (byte_idx * 0x8u)); + mailbox_val |= (u32)byte_buf[byte_idx] << (byte_idx * 0x8u); + } + writel(mailbox_val, mbox->mbox_base + msg->mbox_offset + idx * BYTES_4); + } + + cmd_shifted = msg->cmd_opcode << SERVICE_CR_COMMAND_SHIFT; + cmd_shifted |= SERVICE_CR_REQ_MASK; + writel(cmd_shifted, mbox->ctrl_base + SERVICES_CR_OFFSET); + + do { + value = readl(mbox->ctrl_base + SERVICES_CR_OFFSET); + } while (SERVICE_CR_REQ_MASK == (value & SERVICE_CR_REQ_MASK)); + + do { + value = readl(mbox->ctrl_base + SERVICES_SR_OFFSET); + } while (SERVICE_SR_BUSY_MASK == (value & SERVICE_SR_BUSY_MASK)); + + msg->response->resp_status = (value >> SERVICE_SR_STATUS_SHIFT); + if (msg->response->resp_status) + return -EBADMSG; + + return 0; +} + +static int mpfs_mbox_recv(struct mbox_chan *chan, void *data) +{ + struct mpfs_mbox *mbox = dev_get_priv(chan->dev); + struct mpfs_mss_msg *msg = data; + struct mpfs_mss_response *response = msg->response; + u8 idx; + + if (!response->resp_msg) { + dev_err(chan->dev, "failed to assign memory for response %d\n", -ENOMEM); + return -EINVAL; + } + + if (mpfs_mbox_busy(chan)) { + dev_err(chan->dev, "mailbox is busy\n"); + response->resp_status = 0xDEAD; + return -EINVAL; + } + + for (idx = 0; idx < response->resp_size; idx++) + *((u8 *)(response->resp_msg) + idx) = readb(mbox->mbox_base + msg->resp_offset + idx); + + return 0; +} + +static const struct mbox_ops mpfs_mbox_ops = { + .send = mpfs_mbox_send, + .recv = mpfs_mbox_recv, +}; + +static int mpfs_mbox_probe(struct udevice *dev) +{ + struct mpfs_mbox *mbox; + struct resource regs; + ofnode node; + int ret; + + node = dev_ofnode(dev); + + mbox = devm_kzalloc(dev, sizeof(*mbox), GFP_KERNEL); + if (!mbox) + return -ENOMEM; + + ret = ofnode_read_resource(node, 0, ®s); + if (ret) { + dev_err(dev, "No reg property for controller base\n"); + return ret; + }; + + mbox->ctrl_base = devm_ioremap(dev, regs.start, regs.start - regs.end); + + ret = ofnode_read_resource(node, 2, ®s); + if (ret) { + dev_err(dev, "No reg property for mailbox base\n"); + return ret; + }; + + mbox->mbox_base = devm_ioremap(dev, regs.start, regs.start - regs.end); + + mbox->dev = dev; + dev_set_priv(dev, mbox); + mbox->chan->con_priv = mbox; + + return 0; +} + +static const struct udevice_id mpfs_mbox_ids[] = { + {.compatible = "microchip,mpfs-mailbox"}, + { } +}; + +U_BOOT_DRIVER(mpfs_mbox) = { + .name = "mpfs-mbox", + .id = UCLASS_MAILBOX, + .of_match = mpfs_mbox_ids, + .probe = mpfs_mbox_probe, + .priv_auto = sizeof(struct mpfs_mbox), + .ops = &mpfs_mbox_ops, +}; diff --git a/include/mpfs-mailbox.h b/include/mpfs-mailbox.h new file mode 100644 index 00000000000..c0ff327a4ce --- /dev/null +++ b/include/mpfs-mailbox.h @@ -0,0 +1,66 @@ +/* SPDX-License-Identifier: GPL-2.0 */ +/* + * + * Microchip PolarFire SoC (MPFS) + * + * Copyright (c) 2020 Microchip Corporation. All rights reserved. + * + * + */ + +#ifndef _MPFS_MAILBOX_H__ +#define _MPFS_MAILBOX_H__ + +#include + +#define BYTES_4 4 + +struct udevice; + +/** + * struct mpfs_mss_msg - PolarFire SoC message structure + * @cmd_opcode: Command opcode + * @cmd_data_size: Size of the command data. + * @response: Pointer to the response data. + * @cmd_data: Pointer to the command data. + * @mbox_offset: Mailbox offset + * @resp_offset: Response offset + * + */ +struct mpfs_mss_msg { + u8 cmd_opcode; + u16 cmd_data_size; + struct mpfs_mss_response *response; + u8 *cmd_data; + u16 mbox_offset; + u16 resp_offset; +}; + +/** + * struct mpfs_mss_response - PolarFire SoC response structure + * @resp_status: Response status + * @resp_msg: Pointer to response message. + * @resp_size: Size of the response message. + * + */ +struct mpfs_mss_response { + u32 resp_status; + u32 *resp_msg; + u16 resp_size; +}; + +struct mpfs_syscontroller_priv; + +struct mpfs_sys_serv { + struct udevice *dev; + struct mpfs_syscontroller_priv *sys_controller; + struct mpfs_mss_msg *msg; +}; + +int mpfs_syscontroller_run_service(struct mpfs_syscontroller_priv *sys_controller, struct mpfs_mss_msg *msg); +int mpfs_syscontroller_read_sernum(struct mpfs_sys_serv *sys_serv_priv, u8 *device_serial_number); +void mpfs_syscontroller_process_dtbo(struct mpfs_sys_serv *sys_serv_priv); +struct mpfs_syscontroller_priv *mpfs_syscontroller_get(struct udevice *dev); + +#endif /* __MPFS_MAILBOX_H__ */ + From b7a0ad16f9114a7fe648d94e67d943772b8119ab Mon Sep 17 00:00:00 2001 From: Jamie Gibbons Date: Fri, 1 Aug 2025 13:36:24 +0100 Subject: [PATCH 029/112] misc: add PolarFire SoC system controller This driver provides an interface to access the functions of the system controller on the Microchip PolarFire SoC. This driver includes functions to use the system controller to read the device serial number. Signed-off-by: Jamie Gibbons Acked-by: Leo Yu-Chi Liang --- drivers/misc/Kconfig | 9 ++ drivers/misc/Makefile | 1 + drivers/misc/mpfs_syscontroller.c | 156 ++++++++++++++++++++++++++++++ 3 files changed, 166 insertions(+) create mode 100644 drivers/misc/mpfs_syscontroller.c diff --git a/drivers/misc/Kconfig b/drivers/misc/Kconfig index 0f753b9dbb9..29b84430ff5 100644 --- a/drivers/misc/Kconfig +++ b/drivers/misc/Kconfig @@ -658,6 +658,15 @@ config MICROCHIP_FLEXCOM Only one function can be used at a time and is chosen at boot time according to the device tree. +config MPFS_SYSCONTROLLER + bool "Enable Microchip PolarFire SoC (MPFS) System Services support" + depends on MISC + depends on MPFS_MBOX + help + This driver adds support for the PolarFire SoC (MPFS) system controller. + + If unsure, say N. + config K3_AVS0 depends on ARCH_K3 && SPL_DM_REGULATOR bool "AVS class 0 support for K3 devices" diff --git a/drivers/misc/Makefile b/drivers/misc/Makefile index f7422c8e95a..dc5eb3af19c 100644 --- a/drivers/misc/Makefile +++ b/drivers/misc/Makefile @@ -86,6 +86,7 @@ obj-$(CONFIG_VEXPRESS_CONFIG) += vexpress_config.o obj-$(CONFIG_WINBOND_W83627) += winbond_w83627.o obj-$(CONFIG_JZ4780_EFUSE) += jz4780_efuse.o obj-$(CONFIG_MICROCHIP_FLEXCOM) += microchip_flexcom.o +obj-$(CONFIG_MPFS_SYSCONTROLLER) += mpfs_syscontroller.o obj-$(CONFIG_K3_AVS0) += k3_avs.o obj-$(CONFIG_ESM_K3) += k3_esm.o obj-$(CONFIG_K3_BIST) += k3_bist.o diff --git a/drivers/misc/mpfs_syscontroller.c b/drivers/misc/mpfs_syscontroller.c new file mode 100644 index 00000000000..41e80815ab5 --- /dev/null +++ b/drivers/misc/mpfs_syscontroller.c @@ -0,0 +1,156 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* + * Microchip's PolarFire SoC (MPFS) System Controller Driver + * + * Copyright (C) 2024 Microchip Technology Inc. All rights reserved. + * + * Author: Jamie Gibbons + * + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/* Descriptor table */ +#define CMD_OPCODE 0x0u +#define CMD_DATA_SIZE 0U +#define CMD_DATA NULL +#define MBOX_OFFSET 0x0 +#define RESP_OFFSET 0x0 +#define RESP_BYTES 16U + +/** + * struct mpfs_syscontroller_priv - Structure representing System Controller data. + * @chan: Mailbox channel + * @c: Completion signal + */ +struct mpfs_syscontroller_priv { + struct mbox_chan chan; + struct completion c; +}; + +/** + * mpfs_syscontroller_run_service() - Run the MPFS system service + * @sys_controller: corresponding MPFS system service device + * @msg: Message to send + * + * Return: 0 if all goes good, else appropriate error message. + */ +int mpfs_syscontroller_run_service(struct mpfs_syscontroller_priv *sys_controller, struct mpfs_mss_msg *msg) +{ + int ret; + + reinit_completion(&sys_controller->c); + + /* Run the System Service Request */ + ret = mbox_send(&sys_controller->chan, msg); + if (ret < 0) + dev_warn(sys_controller->chan.dev, "MPFS sys controller service timeout\n"); + + debug("%s: Service successful %s\n", + __func__, sys_controller->chan.dev->name); + + return ret; +} +EXPORT_SYMBOL_GPL(mpfs_syscontroller_run_service); + +/** + * mpfs_syscontroller_read_sernum() - Use system service to read the device serial number + * @sys_serv_priv: system service private data + * @device_serial_number: device serial number + * + * Return: 0 if all went ok, else return appropriate error + */ +int mpfs_syscontroller_read_sernum(struct mpfs_sys_serv *sys_serv_priv, u8 *device_serial_number) +{ + unsigned long timeoutsecs = 300; + int ret; + + struct mpfs_mss_response response = { + .resp_status = 0U, + .resp_msg = (u32 *)device_serial_number, + .resp_size = RESP_BYTES}; + struct mpfs_mss_msg msg = { + .cmd_opcode = CMD_OPCODE, + .cmd_data_size = CMD_DATA_SIZE, + .response = &response, + .cmd_data = CMD_DATA, + .mbox_offset = MBOX_OFFSET, + .resp_offset = RESP_OFFSET}; + + ret = mpfs_syscontroller_run_service(sys_serv_priv->sys_controller, &msg); + if (ret) { + dev_err(sys_serv_priv->sys_controller->chan.dev, "Service failed: %d, abort\n", ret); + return ret; + } + + /* Receive the response */ + ret = mbox_recv(&sys_serv_priv->sys_controller->chan, &msg, timeoutsecs); + if (ret) { + dev_err(sys_serv_priv->sys_controller->chan.dev, "Service failed: %d, abort. Failure: %u\n", ret, msg.response->resp_status); + return ret; + } + + debug("%s: Read successful %s\n", + __func__, sys_serv_priv->sys_controller->chan.dev->name); + + return 0; +} +EXPORT_SYMBOL(mpfs_syscontroller_read_sernum); + +static int mpfs_syscontroller_probe(struct udevice *dev) +{ + struct mpfs_syscontroller_priv *sys_controller = dev_get_priv(dev); + int ret; + + ret = mbox_get_by_index(dev, 0, &sys_controller->chan); + if (ret) { + dev_err(dev, "%s: Acquiring mailbox channel failed. ret = %d\n", + __func__, ret); + return ret; + } + + init_completion(&sys_controller->c); + dev_info(dev, "Registered MPFS system controller\n"); + + return 0; +} + +static const struct udevice_id mpfs_syscontroller_ids[] = { + { .compatible = "microchip,mpfs-sys-controller" }, + { } +}; + +struct mpfs_syscontroller_priv *mpfs_syscontroller_get(struct udevice *dev) +{ + struct mpfs_syscontroller_priv *sys_controller; + + sys_controller = dev_get_priv(dev); + if (!sys_controller) { + debug("%s: MPFS system controller found but could not register as a sub device %p\n", + __func__, sys_controller); + return ERR_PTR(-EPROBE_DEFER); + } + + return sys_controller; +} +EXPORT_SYMBOL(mpfs_syscontroller_get); + +U_BOOT_DRIVER(mpfs_syscontroller) = { + .name = "mpfs_syscontroller", + .id = UCLASS_MISC, + .of_match = mpfs_syscontroller_ids, + .probe = mpfs_syscontroller_probe, + .priv_auto = sizeof(struct mpfs_syscontroller_priv), +}; From c93a93e4f2361c014ac30badc0d78c85ca02c438 Mon Sep 17 00:00:00 2001 From: Jamie Gibbons Date: Fri, 1 Aug 2025 13:36:25 +0100 Subject: [PATCH 030/112] board: microchip: mpfs_icicle: enable new driver configs Enable the MPFS mailbox and system controller drivers for use with the Icicle kit. These functions are crucial for the board setup functions that run in the Icicle board file - mpfs_icicle.c. Signed-off-by: Jamie Gibbons Acked-by: Leo Yu-Chi Liang --- board/microchip/mpfs_icicle/Kconfig | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/board/microchip/mpfs_icicle/Kconfig b/board/microchip/mpfs_icicle/Kconfig index 6e8c479e955..760dffc488b 100644 --- a/board/microchip/mpfs_icicle/Kconfig +++ b/board/microchip/mpfs_icicle/Kconfig @@ -59,5 +59,9 @@ config BOARD_SPECIFIC_OPTIONS # dummy imply MTD_SPI_NAND imply CMD_MTD imply CMD_MTDPARTS + imply DM_MAILBOX + imply MPFS_MBOX + imply MISC + imply MPFS_SYSCONTROLLER endif From f6da31b6340b0fecf681fb4782911121c7f3a1c3 Mon Sep 17 00:00:00 2001 From: Jamie Gibbons Date: Fri, 1 Aug 2025 13:36:26 +0100 Subject: [PATCH 031/112] board: microchip: mpfs_icicle: update to use system controller A new system controller driver has been created to make code modular and improve and clean code. Update and remove functions to account for these additional drivers. Signed-off-by: Jamie Gibbons Reviewed-by: Leo Yu-Chi Liang --- board/microchip/mpfs_icicle/mpfs_icicle.c | 72 ++++++++++------------- 1 file changed, 32 insertions(+), 40 deletions(-) diff --git a/board/microchip/mpfs_icicle/mpfs_icicle.c b/board/microchip/mpfs_icicle/mpfs_icicle.c index 19acbbba42b..739a9b6cd76 100644 --- a/board/microchip/mpfs_icicle/mpfs_icicle.c +++ b/board/microchip/mpfs_icicle/mpfs_icicle.c @@ -4,55 +4,22 @@ * Padmarao Begari */ -#include -#include -#include #include #include #include +#include +#include +#include +#include +#include DECLARE_GLOBAL_DATA_PTR; -#define MPFS_SYSREG_SOFT_RESET ((unsigned int *)0x20002088) -#define MPFS_SYS_SERVICE_CR ((unsigned int *)0x37020050) -#define MPFS_SYS_SERVICE_SR ((unsigned int *)0x37020054) -#define MPFS_SYS_SERVICE_MAILBOX ((unsigned char *)0x37020800) - +#define MPFS_SYSREG_SOFT_RESET ((unsigned int *)0x20002088) #define PERIPH_RESET_VALUE 0x1e8u -#define SERVICE_CR_REQ 0x1u -#define SERVICE_SR_BUSY 0x2u static unsigned char mac_addr[6]; -static void read_device_serial_number(u8 *response, u8 response_size) -{ - u8 idx; - u8 *response_buf; - unsigned int val; - - response_buf = (u8 *)response; - - writel(SERVICE_CR_REQ, MPFS_SYS_SERVICE_CR); - /* - * REQ bit will remain set till the system controller starts - * processing. - */ - do { - val = readl(MPFS_SYS_SERVICE_CR); - } while (SERVICE_CR_REQ == (val & SERVICE_CR_REQ)); - - /* - * Once system controller starts processing the busy bit will - * go high and service is completed when busy bit is gone low - */ - do { - val = readl(MPFS_SYS_SERVICE_SR); - } while (SERVICE_SR_BUSY == (val & SERVICE_SR_BUSY)); - - for (idx = 0; idx < response_size; idx++) - response_buf[idx] = readb(MPFS_SYS_SERVICE_MAILBOX + idx); -} - #if defined(CONFIG_MULTI_DTB_FIT) int board_fit_config_name_match(const char *name) { @@ -149,8 +116,33 @@ int board_late_init(void) int node; u8 device_serial_number[16] = {0}; void *blob = (void *)gd->fdt_blob; + struct udevice *dev; + struct mpfs_sys_serv *sys_serv_priv; - read_device_serial_number(device_serial_number, 16); + ret = uclass_get_device_by_name(UCLASS_MISC, "syscontroller", &dev); + if (ret) { + debug("%s: system controller setup failed\n", __func__); + return ret; + } + + sys_serv_priv = kzalloc(sizeof(*sys_serv_priv), GFP_KERNEL); + if (!sys_serv_priv) + return -ENOMEM; + + sys_serv_priv->dev = dev; + + sys_serv_priv->sys_controller = mpfs_syscontroller_get(dev); + ret = IS_ERR(sys_serv_priv->sys_controller); + if (ret) { + debug("%s: Failed to register system controller sub device ret=%d\n", __func__, ret); + return -ENODEV; + } + + ret = mpfs_syscontroller_read_sernum(sys_serv_priv, device_serial_number); + if (ret) { + printf("Cannot read device serial number\n"); + return -EINVAL; + } /* Update MAC address with device serial number */ mac_addr[0] = 0x00; From 89e4154431ea34bfbbe095100543b27560271f4e Mon Sep 17 00:00:00 2001 From: Leo Yu-Chi Liang Date: Wed, 13 Aug 2025 14:01:04 +0800 Subject: [PATCH 032/112] common: spl: fix compilation warning Explicitly specify the type by replacing macro with variable to fix the possible compilation warning. Signed-off-by: Leo Yu-Chi Liang --- common/spl/spl.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/common/spl/spl.c b/common/spl/spl.c index ed443c645a7..55ad497c86d 100644 --- a/common/spl/spl.c +++ b/common/spl/spl.c @@ -278,8 +278,8 @@ void spl_set_header_raw_uboot(struct spl_image_info *spl_image) } else { spl_image->entry_point = CONFIG_SYS_UBOOT_START; spl_image->load_addr = CONFIG_TEXT_BASE; - log_debug("Default load addr %x (u_boot_pos=%lx)\n", - CONFIG_TEXT_BASE, u_boot_pos); + log_debug("Default load addr %lx (u_boot_pos=%lx)\n", + spl_image->load_addr, u_boot_pos); } spl_image->os = IH_OS_U_BOOT; spl_image->name = xpl_name(xpl_next_phase()); From 87f98d92257db0e72b4d2c2684aec492e93b6e01 Mon Sep 17 00:00:00 2001 From: Leo Yu-Chi Liang Date: Thu, 7 Aug 2025 19:38:07 +0800 Subject: [PATCH 033/112] riscv: board: Add Andes Voyager board Kconfig support The Voyager is Andes' first RISC-V development board. It is built around Qilai SoC, which includes Andes AX45MP quad-core cluster. Introduce the Kconfig entry for the Voyager board. Signed-off-by: Randolph Sheng-Kai Lin Signed-off-by: Leo Yu-Chi Liang --- arch/riscv/Kconfig | 4 +++ board/andestech/voyager/Kconfig | 44 +++++++++++++++++++++++++++++++++ 2 files changed, 48 insertions(+) create mode 100644 board/andestech/voyager/Kconfig diff --git a/arch/riscv/Kconfig b/arch/riscv/Kconfig index 8c6feae5735..04eb0e6f23c 100644 --- a/arch/riscv/Kconfig +++ b/arch/riscv/Kconfig @@ -11,6 +11,9 @@ choice config TARGET_ANDES_AE350 bool "Support Andes ae350" +config TARGET_ANDES_VOYAGER + bool "Support Andes Voyager Board" + config TARGET_BANANAPI_F3 bool "Support BananaPi F3 Board" @@ -101,6 +104,7 @@ config SPL_ZERO_MEM_BEFORE_USE # board-specific options below source "board/andestech/ae350/Kconfig" +source "board/andestech/voyager/Kconfig" source "board/aspeed/ibex_ast2700/Kconfig" source "board/canaan/k230_canmv/Kconfig" source "board/emulation/qemu-riscv/Kconfig" diff --git a/board/andestech/voyager/Kconfig b/board/andestech/voyager/Kconfig new file mode 100644 index 00000000000..b2e212c3fee --- /dev/null +++ b/board/andestech/voyager/Kconfig @@ -0,0 +1,44 @@ +if TARGET_ANDES_VOYAGER + +config SYS_CPU + default "andes" + +config SYS_BOARD + default "voyager" + +config SYS_VENDOR + default "andestech" + +config SYS_SOC + default "qilai" + +config SYS_CONFIG_NAME + default "voyager" + +config ENV_SIZE + default 0x2000 if ENV_IS_IN_SPI_FLASH + +config ENV_OFFSET + default 0x1F0000 if ENV_IS_IN_SPI_FLASH + +config SPL_TEXT_BASE + default 0x400800000 + +config SPL_OPENSBI_LOAD_ADDR + default 0x400000000 + +config SYS_FDT_BASE + hex + default 0x81E0000 if OF_SEPARATE + +config BOARD_SPECIFIC_OPTIONS # dummy + def_bool y + select RISCV_ANDES + select SUPPORT_SPL + select BINMAN if SPL + imply SMP + imply SPL_RAM_SUPPORT + imply SPL_RAM_DEVICE + imply OF_HAS_PRIOR_STAGE + +endif From a25e1aacdbed4d80d05ea85a13cc944a8657d473 Mon Sep 17 00:00:00 2001 From: Leo Yu-Chi Liang Date: Thu, 7 Aug 2025 19:38:17 +0800 Subject: [PATCH 034/112] riscv: dts: andes: Add Voyager device tree Introduce the initial device tree support for Andes Voyager board. We will convert to OF_UPSTREAM once the patch series for kernel is merged. Signed-off-by: Randolph Sheng-Kai Lin Signed-off-by: Leo Yu-Chi Liang --- arch/riscv/dts/Makefile | 1 + arch/riscv/dts/qilai-voyager.dts | 227 +++++++++++++++++++++++++++++ arch/riscv/dts/voyager-u-boot.dtsi | 52 +++++++ 3 files changed, 280 insertions(+) create mode 100644 arch/riscv/dts/qilai-voyager.dts create mode 100644 arch/riscv/dts/voyager-u-boot.dtsi diff --git a/arch/riscv/dts/Makefile b/arch/riscv/dts/Makefile index 68dfe9ce56d..a637727b76b 100644 --- a/arch/riscv/dts/Makefile +++ b/arch/riscv/dts/Makefile @@ -1,6 +1,7 @@ # SPDX-License-Identifier: GPL-2.0+ dtb-$(CONFIG_TARGET_ANDES_AE350) += ae350_32.dtb ae350_64.dtb +dtb-$(CONFIG_TARGET_ANDES_VOYAGER) += qilai-voyager.dtb dtb-$(CONFIG_TARGET_BANANAPI_F3) += k1-bananapi-f3.dtb dtb-$(CONFIG_TARGET_K230_CANMV) += k230-canmv.dtb dtb-$(CONFIG_TARGET_MICROCHIP_ICICLE) += mpfs-icicle-kit.dtb diff --git a/arch/riscv/dts/qilai-voyager.dts b/arch/riscv/dts/qilai-voyager.dts new file mode 100644 index 00000000000..44933529f89 --- /dev/null +++ b/arch/riscv/dts/qilai-voyager.dts @@ -0,0 +1,227 @@ +// SPDX-License-Identifier: (GPL-2.0 OR MIT) + +/dts-v1/; + +#include "binman.dtsi" +#include "voyager-u-boot.dtsi" + +/ { + #address-cells = <0x2>; + #size-cells = <0x2>; + compatible = "andestech,voyager", "andestech,qilai"; + model = "Voyager"; + + aliases { + uart0 = &serial0; + spi0 = &spi; + }; + + chosen { + bootargs = "console=ttyS0,115200n8 earlycon=sbi debug loglevel=7"; + stdout-path = "uart0:115200n8"; + }; + + cpus { + #address-cells = <0x1>; + #size-cells = <0x0>; + timebase-frequency = <0x3938700>; + + CPU0: cpu@0 { + device_type = "cpu"; + reg = <0x0>; + status = "okay"; + compatible = "riscv"; + riscv,isa = "rv64imafdc"; + riscv,priv-major = <0x1>; + riscv,priv-minor = <0xa>; + mmu-type = "riscv,sv39"; + clock-frequency = <0x3938700>; + i-cache-size = <0x8000>; + i-cache-line-size = <0x20>; + d-cache-size = <0x8000>; + d-cache-line-size = <0x20>; + next-level-cache = <&L2>; + + CPU0_intc: interrupt-controller { + #interrupt-cells = <0x1>; + interrupt-controller; + compatible = "riscv,cpu-intc"; + }; + }; + + CPU1: cpu@1 { + device_type = "cpu"; + reg = <0x1>; + status = "okay"; + compatible = "riscv"; + riscv,isa = "rv64imafdc"; + riscv,priv-major = <0x1>; + riscv,priv-minor = <0xa>; + mmu-type = "riscv,sv39"; + clock-frequency = <0x3938700>; + i-cache-size = <0x8000>; + i-cache-line-size = <0x20>; + d-cache-size = <0x8000>; + d-cache-line-size = <0x20>; + next-level-cache = <&L2>; + + CPU1_intc: interrupt-controller { + #interrupt-cells = <0x1>; + interrupt-controller; + compatible = "riscv,cpu-intc"; + }; + }; + + CPU2: cpu@2 { + device_type = "cpu"; + reg = <0x2>; + status = "okay"; + compatible = "riscv"; + riscv,isa = "rv64imafdc"; + riscv,priv-major = <0x1>; + riscv,priv-minor = <0xa>; + mmu-type = "riscv,sv39"; + clock-frequency = <0x3938700>; + i-cache-size = <0x8000>; + i-cache-line-size = <0x20>; + d-cache-size = <0x8000>; + d-cache-line-size = <0x20>; + next-level-cache = <&L2>; + + CPU2_intc: interrupt-controller { + #interrupt-cells = <0x1>; + interrupt-controller; + compatible = "riscv,cpu-intc"; + }; + }; + + CPU3: cpu@3 { + device_type = "cpu"; + reg = <0x3>; + status = "okay"; + compatible = "riscv"; + riscv,isa = "rv64imafdc"; + riscv,priv-major = <0x1>; + riscv,priv-minor = <0xa>; + mmu-type = "riscv,sv39"; + clock-frequency = <0x3938700>; + i-cache-size = <0x8000>; + i-cache-line-size = <0x20>; + d-cache-size = <0x8000>; + d-cache-line-size = <0x20>; + next-level-cache = <&L2>; + + CPU3_intc: interrupt-controller { + #interrupt-cells = <0x1>; + interrupt-controller; + compatible = "riscv,cpu-intc"; + }; + }; + }; + + L2: l2-cache@200000 { + compatible = "cache"; + cache-level = <0x2>; + cache-size = <0x40000>; + reg = <0x0 0x00200000 0x0 0x100000>; + andes,inst-prefetch = <0x3>; + andes,data-prefetch = <0x3>; + andes,tag-ram-ctl = <0x0 0x0>; + andes,data-ram-ctl = <0x0 0x0>; + }; + + memory@400000000 { + device_type = "memory"; + reg = <0x04 0x00000000 0x0 0x40000000>; + }; + + soc { + #address-cells = <0x2>; + #size-cells = <0x2>; + compatible = "simple-bus"; + ranges; + + plic0: interrupt-controller@2000000 { + compatible = "riscv,plic0"; + #address-cells = <0x2>; + #interrupt-cells = <0x2>; + interrupt-controller; + reg = <0x0 0x02000000 0x0 0x2000000>; + riscv,ndev = <0x47>; + interrupts-extended = <&CPU0_intc 11 &CPU0_intc 9 + &CPU1_intc 11 &CPU1_intc 9 + &CPU2_intc 11 &CPU2_intc 9 + &CPU3_intc 11 &CPU3_intc 9>; + }; + + plic1: interrupt-controller@400000 { + compatible = "andestech,plicsw"; + #address-cells = <0x2>; + #interrupt-cells = <0x2>; + interrupt-controller; + reg = <0x0 0x00400000 0x0 0x400000>; + riscv,ndev = <0x1>; + interrupts-extended = <&CPU0_intc 3 + &CPU1_intc 3 + &CPU2_intc 3 + &CPU3_intc 3>; + }; + + plmt0@100000 { + compatible = "andestech,plmt0"; + reg = <0x0 0x00100000 0x0 0x100000>; + interrupts-extended = <&CPU0_intc 7 + &CPU1_intc 7 + &CPU2_intc 7 + &CPU3_intc 7>; + }; + }; + + spiclk: virt_100mhz { + #clock-cells = <0x0>; + compatible = "fixed-clock"; + clock-frequency = <0x5f5e100>; + }; + + serial0: serial@30300000 { + compatible = "andestech,uart16550", "ns16550a"; + reg = <0x0 0x30300000 0x0 0x1000>; + interrupts = <0x9 0x4>; + clock-frequency = <0x12c0000>; + reg-shift = <0x2>; + reg-offset = <0x20>; + no-loopback-test = <0x1>; + interrupt-parent = <&plic0>; + }; + + mmc0: mmc@30c00000 { + compatible = "andestech,atfsdc010"; + max-frequency = <0x5f5e100>; + clock-freq-min-max = <0x61a80 0x5f5e100>; + fifo-depth = <0x10>; + reg = <0x0 0x30c00000 0x0 0x1000>; + interrupts = <0x12 0x4>; + cap-sd-highspeed; + interrupt-parent = <&plic0>; + dma-coherent; + }; + + spi: spi@30900000 { + compatible = "andestech,atcspi200"; + reg = <0x0 0x30900000 0x0 0x100000>; + #address-cells = <0x1>; + #size-cells = <0x0>; + num-cs = <0x1>; + clocks = <&spiclk>; + interrupts = <0x4 0x4>; + interrupt-parent = <&plic0>; + + flash@0 { + compatible = "mx25u1635e", "jedec,spi-nor"; + spi-max-frequency = <0x2faf080>; + reg = <0x0>; + spi-cpol; + spi-cpha; + }; + }; +}; diff --git a/arch/riscv/dts/voyager-u-boot.dtsi b/arch/riscv/dts/voyager-u-boot.dtsi new file mode 100644 index 00000000000..cef0aa08b37 --- /dev/null +++ b/arch/riscv/dts/voyager-u-boot.dtsi @@ -0,0 +1,52 @@ +// SPDX-License-Identifier: (GPL-2.0 OR MIT) + +/ { + cpus { + bootph-pre-ram; + CPU0: cpu@0 { + bootph-pre-ram; + CPU0_intc: interrupt-controller { + bootph-pre-ram; + }; + }; + CPU1: cpu@1 { + bootph-pre-ram; + CPU1_intc: interrupt-controller { + bootph-pre-ram; + }; + }; + CPU2: cpu@2 { + bootph-pre-ram; + CPU2_intc: interrupt-controller { + bootph-pre-ram; + }; + }; + CPU3: cpu@3 { + bootph-pre-ram; + CPU3_intc: interrupt-controller { + bootph-pre-ram; + }; + }; + }; + + memory@0 { + bootph-pre-ram; + }; + + soc { + bootph-pre-ram; + + plic1: interrupt-controller@400000 { + bootph-pre-ram; + }; + + plmt0@100000 { + bootph-pre-ram; + }; + }; + + serial0: serial@30300000 { + bootph-pre-ram; + }; + +}; From 35995f7ebf04a95864a116f76ba8f89c94b6d475 Mon Sep 17 00:00:00 2001 From: Leo Yu-Chi Liang Date: Thu, 7 Aug 2025 19:38:32 +0800 Subject: [PATCH 035/112] board: andestech: Add Voyager board support Introduce Voyager board specific code, including - dram info - shared cache enabling Signed-off-by: Randolph Sheng-Kai Lin Signed-off-by: Leo Yu-Chi Liang --- board/andestech/voyager/Makefile | 6 +++ board/andestech/voyager/voyager.c | 70 +++++++++++++++++++++++++++++++ include/configs/voyager.h | 40 ++++++++++++++++++ 3 files changed, 116 insertions(+) create mode 100644 board/andestech/voyager/Makefile create mode 100644 board/andestech/voyager/voyager.c create mode 100644 include/configs/voyager.h diff --git a/board/andestech/voyager/Makefile b/board/andestech/voyager/Makefile new file mode 100644 index 00000000000..d293e3e2d89 --- /dev/null +++ b/board/andestech/voyager/Makefile @@ -0,0 +1,6 @@ +# SPDX-License-Identifier: GPL-2.0+ +# +# Copyright (C) 2025 Andes Technology Corporation. +# Randolph Lin, Andes Technology Corporation + +obj-y := voyager.o diff --git a/board/andestech/voyager/voyager.c b/board/andestech/voyager/voyager.c new file mode 100644 index 00000000000..dc8f1347775 --- /dev/null +++ b/board/andestech/voyager/voyager.c @@ -0,0 +1,70 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* + * Copyright (C) 2025 Andes Technology Corporation + * Randolph Lin, Andes Technology Corporation + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +DECLARE_GLOBAL_DATA_PTR; + +int dram_init(void) +{ + return fdtdec_setup_mem_size_base(); +} + +int dram_init_banksize(void) +{ + return fdtdec_setup_memory_banksize(); +} + +#ifdef CONFIG_SPL_BOARD_INIT +void spl_board_init(void) +{ + /* enable andes-l2 cache */ + if (!CONFIG_IS_ENABLED(SYS_DCACHE_OFF)) + enable_caches(); +} +#endif + +#ifdef CONFIG_BOARD_EARLY_INIT_R +int board_early_init_r(void) +{ + /* enable andes-l2 cache */ + if (!CONFIG_IS_ENABLED(SYS_DCACHE_OFF)) + enable_caches(); + + return 0; +} +#endif + +#ifdef CONFIG_SPL +void board_boot_order(u32 *spl_boot_list) +{ + u8 i; + u32 boot_devices[] = { +#ifdef CONFIG_SPL_RAM_SUPPORT + BOOT_DEVICE_RAM, +#endif +#ifdef CONFIG_SPL_MMC + BOOT_DEVICE_MMC1, +#endif + }; + + for (i = 0; i < ARRAY_SIZE(boot_devices); i++) + spl_boot_list[i] = boot_devices[i]; +} +#endif diff --git a/include/configs/voyager.h b/include/configs/voyager.h new file mode 100644 index 00000000000..f6630b07ec9 --- /dev/null +++ b/include/configs/voyager.h @@ -0,0 +1,40 @@ +/* SPDX-License-Identifier: GPL-2.0+ */ +/* + * Copyright (C) 2025 Andes Technology Corporation + * Randolph Lin, Andes Technology Corporation + */ + +#ifndef __CONFIG_H +#define __CONFIG_H + +#define RISCV_MMODE_TIMERBASE 0xe6000000 +#define RISCV_MMODE_TIMER_FREQ 60000000 + +#define RISCV_SMODE_TIMER_FREQ 60000000 + +/* support JEDEC */ +#define PHYS_FLASH_1 0x8000000 /* BANK 0 */ +#define CFG_SYS_FLASH_BASE PHYS_FLASH_1 +#define CFG_SYS_FLASH_BANKS_LIST { PHYS_FLASH_1, } +#define CFG_SYS_FLASH_BANKS_SIZES { 0x4000000 } + +/* Enable distro boot */ +#define BOOT_TARGET_DEVICES(func) \ + func(MMC, mmc, 0) \ + func(DHCP, dhcp, na) + +#include + +#define CFG_EXTRA_ENV_SETTINGS \ + "fdt_high=0xffffffffffffffff\0" \ + "initrd_high=0xffffffffffffffff\0" \ + "kernel_addr_r=0x400600000\0" \ + "kernel_comp_addr_r=0x404600000\0" \ + "kernel_comp_size=0x04000000\0" \ + "pxefile_addr_r=0x408600000\0" \ + "scriptaddr=0x408700000\0" \ + "fdt_addr_r=0x408800000\0" \ + "ramdisk_addr_r=0x408900000\0" \ + BOOTENV + +#endif /* __CONFIG_H */ From 3239ef494c7f3a9b6c95a40817cc121a97302874 Mon Sep 17 00:00:00 2001 From: Leo Yu-Chi Liang Date: Thu, 7 Aug 2025 19:40:40 +0800 Subject: [PATCH 036/112] configs: andes: add Voyager board defconfig Add default configuration file for Voyager board. Signed-off-by: Randolph Sheng-Kai Lin Signed-off-by: Leo Yu-Chi Liang --- configs/voyager_spl_defconfig | 65 +++++++++++++++++++++++++++++++++++ 1 file changed, 65 insertions(+) create mode 100644 configs/voyager_spl_defconfig diff --git a/configs/voyager_spl_defconfig b/configs/voyager_spl_defconfig new file mode 100644 index 00000000000..f7390405dac --- /dev/null +++ b/configs/voyager_spl_defconfig @@ -0,0 +1,65 @@ +CONFIG_RISCV=y +CONFIG_TEXT_BASE=0x401800000 +CONFIG_SYS_MALLOC_LEN=0x80000 +CONFIG_NR_DRAM_BANKS=2 +CONFIG_HAS_CUSTOM_SYS_INIT_SP_ADDR=y +CONFIG_CUSTOM_SYS_INIT_SP_ADDR=0x410000000 +CONFIG_ENV_SIZE=0x20000 +CONFIG_ENV_SECT_SIZE=0x1000 +CONFIG_DEFAULT_DEVICE_TREE="qilai-voyager" +CONFIG_SPL_BSS_START_ADDR=0x400400000 +CONFIG_SYS_LOAD_ADDR=0x400100000 +CONFIG_SPL=y +CONFIG_TARGET_ANDES_VOYAGER=y +CONFIG_NR_CPUS=4 +CONFIG_ARCH_RV64I=y +CONFIG_RISCV_SMODE=y +# CONFIG_AVAILABLE_HARTS is not set +CONFIG_SYS_MONITOR_BASE=0x88000000 +CONFIG_FIT=y +CONFIG_SPL_LOAD_FIT_ADDRESS=0x410000000 +CONFIG_DISTRO_DEFAULTS=y +CONFIG_BOOTDELAY=3 +CONFIG_CONSOLE_RECORD=y +CONFIG_CONSOLE_RECORD_OUT_SIZE_F=0x2000 +CONFIG_SYS_PBSIZE=1050 +CONFIG_DISPLAY_CPUINFO=y +CONFIG_DISPLAY_BOARDINFO=y +# CONFIG_SPL_CYCLIC is not set +CONFIG_BOARD_EARLY_INIT_R=y +# CONFIG_BOARD_INIT is not set +CONFIG_SPL_MAX_SIZE=0x40000 +CONFIG_SPL_BOARD_INIT=y +CONFIG_SPL_CACHE=y +CONFIG_SYS_PROMPT="RISC-V # " +CONFIG_CMD_IMLS=y +CONFIG_CMD_MMC=y +CONFIG_CMD_SF_TEST=y +CONFIG_CMD_WDT=y +# CONFIG_CMD_SETEXPR is not set +CONFIG_BOOTP_PREFER_SERVERIP=y +CONFIG_CMD_CACHE=y +CONFIG_ENV_OVERWRITE=y +CONFIG_ENV_IS_IN_SPI_FLASH=y +CONFIG_NET_RETRY_COUNT=50 +CONFIG_BOOTP_SEND_HOSTNAME=y +CONFIG_NET_RANDOM_ETHADDR=y +CONFIG_MMC=y +CONFIG_FTSDC010=y +CONFIG_FTSDC010_SDIO=y +CONFIG_MTD_NOR_FLASH=y +CONFIG_FLASH_CFI_DRIVER=y +CONFIG_SYS_FLASH_CFI_WIDTH_16BIT=y +CONFIG_FLASH_SHOW_PROGRESS=0 +CONFIG_SYS_CFI_FLASH_STATUS_POLL=y +CONFIG_SYS_FLASH_USE_BUFFER_WRITE=y +CONFIG_SYS_FLASH_CFI=y +CONFIG_SPI_FLASH_MACRONIX=y +CONFIG_FTMAC100=y +CONFIG_SYS_NS16550=y +CONFIG_SPI=y +CONFIG_ATCSPI200_SPI=y +# CONFIG_WATCHDOG_AUTOSTART is not set +CONFIG_WDT=y +CONFIG_WDT_ATCWDT200=y +# CONFIG_BINMAN_FDT is not set From 2da685378ff3738ab5614b9f70627af73b8db958 Mon Sep 17 00:00:00 2001 From: Leo Yu-Chi Liang Date: Thu, 7 Aug 2025 19:40:55 +0800 Subject: [PATCH 037/112] doc: board: voyager: Add documentation for Voyager Add documentation for Voyager board. Signed-off-by: Randolph Sheng-Kai Lin Signed-off-by: Leo Yu-Chi Liang --- doc/board/andestech/index.rst | 1 + doc/board/andestech/voyager.rst | 81 +++++++++++++++++++++++++++++++++ 2 files changed, 82 insertions(+) create mode 100644 doc/board/andestech/voyager.rst diff --git a/doc/board/andestech/index.rst b/doc/board/andestech/index.rst index cacc5791a91..5ef93308b49 100644 --- a/doc/board/andestech/index.rst +++ b/doc/board/andestech/index.rst @@ -8,3 +8,4 @@ Andes Tech adp-ag101p ae350 + voyager diff --git a/doc/board/andestech/voyager.rst b/doc/board/andestech/voyager.rst new file mode 100644 index 00000000000..63553216d60 --- /dev/null +++ b/doc/board/andestech/voyager.rst @@ -0,0 +1,81 @@ +.. SPDX-License-Identifier: GPL-2.0+ + +Voyager +======= + +Qilai RISC-V SoC +---------------- +The QiLai SoC chip is Andes' first RISC-V SoC. It includes high performance +quad-core Andes AX45MP cluster and one NX27V vector processor. + +The Voyager development platform is based on Qilai and capable of running Linux. + +Mainline support +---------------- + +The support for following drivers are already enabled: + +1. UART driver +2. MMC driver +3. SPI driver + +Building +~~~~~~~~ + +How to build U-Boot SPL +~~~~~~~~~~~~~~~~~~~~~~~ +Before building U-Boot SPL, OpenSBI must be build first. +OpenSBI can be cloned and build for Voyager as below: + +1. Get the RISC-V toolchain. +2. Setup cross compilation environment variable. + +.. code-block:: none + + git clone https://github.com/riscv-software-src/opensbi.git + cd opensbi + make PLATFORM=generic + +Copy OpenSBI FW_DYNAMIC image (build/platform/generic/firmware/fw_dynamic.bin) +into U-Boot root directory, then + +.. code-block:: console + + export CROSS_COMPILE=riscv64-linux-gnu- + cd + cp fw_dynamic.bin . + make voyager_spl_defconfig + make + +Booting +~~~~~~~ + +Currently, we rely on vendor ROM code to initialize the DDR +and load the u-boot image, then boot from it. + +Sample boot log from Voyager board +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +.. code-block:: none + + U-Boot SPL 2025.10-rc1-00130-ga28bcbba4778-dirty (Aug 06 2025 - 17:46:10 +0800) + Trying to boot from RAM + + U-Boot 2025.10-rc1-00130-ga28bcbba4778-dirty (Aug 06 2025 - 17:46:10 +0800) + + CPU: riscv + Model: andestech,ax45 + DRAM: 16 GiB + Core: 25 devices, 14 uclasses, devicetree: board + MMC: mmc@30c00000: 0 + Loading Environment from SPIFlash... SF: Detected mx25u1635e with page size 256 Bytes, erase size 4 KiB, total 2 MiB + *** Warning - bad CRC, using default environment + + In: serial@30300000 + Out: serial@30300000 + Err: serial@30300000 + Net: No ethernet found. + Hit any key to stop autoboot: 0 + No ethernet found. + No ethernet found. + RISC-V # From 3856d93ea331f462a9bebf072390a66d104a1a93 Mon Sep 17 00:00:00 2001 From: Leo Yu-Chi Liang Date: Thu, 7 Aug 2025 19:38:27 +0800 Subject: [PATCH 038/112] board: MAINTAINERS: Add Voyager board maintainer Add Voyager board maintainer. Signed-off-by: Randolph Sheng-Kai Lin Signed-off-by: Leo Yu-Chi Liang --- board/andestech/voyager/MAINTAINERS | 8 ++++++++ 1 file changed, 8 insertions(+) create mode 100644 board/andestech/voyager/MAINTAINERS diff --git a/board/andestech/voyager/MAINTAINERS b/board/andestech/voyager/MAINTAINERS new file mode 100644 index 00000000000..b87026ee383 --- /dev/null +++ b/board/andestech/voyager/MAINTAINERS @@ -0,0 +1,8 @@ +Andestech Voyager BOARD +M: Randolph +S: Maintained +F: board/andestech/voyager/ +F: configs/voyager_spl_defconfig +F: doc/board/andestech/voyager.rst +F: include/configs/qilai.h + From 909ceacf4a8ac5360c25588f9db7b6dbd19c5c06 Mon Sep 17 00:00:00 2001 From: Heinrich Schuchardt Date: Sat, 9 Aug 2025 10:21:55 +0200 Subject: [PATCH 039/112] starfive: fix return code of `mac write_eeprom` When writing the EEPROM fails, the command usage help text is displayed after the error message. We should only display the error message instead. If writing the EEPROM fails, return CMD_RET_FAILURE (1) instead of CMD_RET_USAGE (-1). Fixes: aea1bd95b61e ("eeprom: starfive: Enable ID EEPROM configuration") Signed-off-by: Heinrich Schuchardt Acked-by: E Shattow --- board/starfive/visionfive2/visionfive2-i2c-eeprom.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/board/starfive/visionfive2/visionfive2-i2c-eeprom.c b/board/starfive/visionfive2/visionfive2-i2c-eeprom.c index 010e386e64d..17a44020bcf 100644 --- a/board/starfive/visionfive2/visionfive2-i2c-eeprom.c +++ b/board/starfive/visionfive2/visionfive2-i2c-eeprom.c @@ -275,7 +275,7 @@ static int prog_eeprom(unsigned int size) if (is_match_magic()) { printf("MAGIC ERROR, Please check the data@%p.\n", pbuf.buf); - return -1; + return CMD_RET_FAILURE; } ret = i2c_get_chip_for_busnum(CONFIG_SYS_EEPROM_BUS_NUM, @@ -285,7 +285,7 @@ static int prog_eeprom(unsigned int size) if (ret) { printf("Get i2c bus:%d addr:%d fail.\n", CONFIG_SYS_EEPROM_BUS_NUM, CONFIG_SYS_I2C_EEPROM_ADDR); - return ret; + return CMD_RET_FAILURE; } for (i = 0, p = (u8 *)pbuf.buf; i < size; ) { @@ -314,11 +314,11 @@ static int prog_eeprom(unsigned int size) if (ret) { has_been_read = -1; printf("Programming failed.\n"); - return -1; + return CMD_RET_FAILURE; } printf("Programming passed.\n"); - return 0; + return CMD_RET_SUCCESS; } /** From 35d6caad6de93b3a5545df7bcdc6d322a4edb93c Mon Sep 17 00:00:00 2001 From: Ben Dooks Date: Thu, 7 Aug 2025 17:49:33 +0100 Subject: [PATCH 040/112] arch/riscv/lib: update memmove and memcpy for big-endian Change the shift patterns for the unaligned memory move and copy code to deal with big-endian by definign macros to change the shfit left and right to go the opposite way. Signed-off-by: Ben Dooks Reviewed-by: Leo Yu-Chi Liang --- arch/riscv/lib/memcpy.S | 12 ++++++++++-- arch/riscv/lib/memmove.S | 12 ++++++++++-- 2 files changed, 20 insertions(+), 4 deletions(-) diff --git a/arch/riscv/lib/memcpy.S b/arch/riscv/lib/memcpy.S index 9884077c933..e5479bbe84e 100644 --- a/arch/riscv/lib/memcpy.S +++ b/arch/riscv/lib/memcpy.S @@ -125,6 +125,14 @@ WEAK(memcpy) .copy_end: ret +#if __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__ +#define M_SLL sll +#define M_SRL srl +#else +#define M_SLL srl +#define M_SRL sll +#endif + .Lmisaligned_word_copy: /* * Misaligned word-wise copy. @@ -144,10 +152,10 @@ WEAK(memcpy) addi t0, t0, -(SZREG-1) /* At least one iteration will be executed here, no check */ 1: - srl a4, a5, t3 + M_SRL a4, a5, t3 REG_L a5, SZREG(a1) addi a1, a1, SZREG - sll a2, a5, t4 + M_SLL a2, a5, t4 or a2, a2, a4 REG_S a2, 0(a0) addi a0, a0, SZREG diff --git a/arch/riscv/lib/memmove.S b/arch/riscv/lib/memmove.S index fbe6701dbe4..b2c1c736713 100644 --- a/arch/riscv/lib/memmove.S +++ b/arch/riscv/lib/memmove.S @@ -91,6 +91,14 @@ WEAK(memmove) mv a0, t0 ret +#if __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__ +#define M_SLL sll +#define M_SRL srl +#else +#define M_SLL srl +#define M_SRL sll +#endif + .Lmisaligned_word_copy: /* * Misaligned word-wise copy. @@ -110,10 +118,10 @@ WEAK(memmove) addi t0, t0, SZREG-1 /* At least one iteration will be executed here, no check */ 1: - sll a4, a5, t4 + M_SLL a4, a5, t4 addi a1, a1, -SZREG REG_L a5, 0(a1) - srl a2, a5, t3 + M_SRL a2, a5, t3 or a2, a2, a4 addi a0, a0, -SZREG REG_S a2, 0(a0) From 6531aeed374f0818d7259eaa401b92b976723fb2 Mon Sep 17 00:00:00 2001 From: Tom Rini Date: Tue, 12 Aug 2025 11:31:09 -0600 Subject: [PATCH 041/112] env: Correct Kconfig type for ENV_MMC_SW_PARTITION As part of renaming environment related Kconfig options, ENV_MMC_SW_PARTITION was inadvertently changed from a string to a bool. Correct this. Fixes: ffc4914703a2 ("env: Rename ENV_MMC_PARTITION to ENV_MMC_SW_PARTITION") Reviewed-by: Marek Vasut Signed-off-by: Tom Rini --- env/Kconfig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/env/Kconfig b/env/Kconfig index 1df7ebd547e..03c189b7266 100644 --- a/env/Kconfig +++ b/env/Kconfig @@ -732,7 +732,7 @@ config ENV_MMC_USE_SW_PARTITION depends on ENV_IS_IN_MMC config ENV_MMC_SW_PARTITION - bool "SD/MMC environment software partition name" + string "SD/MMC environment software partition name" depends on ENV_MMC_USE_SW_PARTITION help SD/MMC software partition name used to save environment variables. From 0c558bbad9e7581808b358091d1fd979f860e8ac Mon Sep 17 00:00:00 2001 From: Martin Schwan Date: Tue, 12 Aug 2025 14:38:34 +0200 Subject: [PATCH 042/112] bootstd: rauc: Change global method to check any partition The bootmeth rauc should scan all partitions, in particular whole devices, and not be a global method. There may exist multiple RAUC systems on different devices and they should all be detected. This also fixes a bug, where both a global bootflow and one using an actual, complete device would be detected at the same time, when scanning for valid bootflows. Signed-off-by: Martin Schwan Tested-by: Wadim Egorov --- boot/bootmeth_rauc.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/boot/bootmeth_rauc.c b/boot/bootmeth_rauc.c index cc6180221ed..7c1a895139e 100644 --- a/boot/bootmeth_rauc.c +++ b/boot/bootmeth_rauc.c @@ -410,7 +410,7 @@ static int distro_rauc_bootmeth_bind(struct udevice *dev) struct bootmeth_uc_plat *plat = dev_get_uclass_plat(dev); plat->desc = "RAUC distro boot from MMC"; - plat->flags = BOOTMETHF_GLOBAL; + plat->flags = BOOTMETHF_ANY_PART; return 0; } From 93297f1f9bb5e21149fc344aaddf7cf2b7e1fb8f Mon Sep 17 00:00:00 2001 From: Marek Vasut Date: Wed, 6 Aug 2025 21:23:54 +0200 Subject: [PATCH 043/112] pci: pcie-rcar-gen4: Fix PHY initialization R-Car V4H Reference Manual R19UH0186EJ0130 Rev.1.30 Apr. 21, 2025 page 4581 Figure 104.3b Initial Setting of PCIEC(example) middle of the figure indicates that fourth write into register 0x148 [2:0] is 0x3 or GENMASK(1, 0). The current code writes GENMASK(11, 0) which is a typo. Fix the typo. Fixes: be3dd0dc2fd9 ("pci: pcie-rcar-gen4: Add Renesas R-Car Gen4 DW PCIe controller driver") Signed-off-by: Marek Vasut --- drivers/pci/pci-rcar-gen4.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/pci/pci-rcar-gen4.c b/drivers/pci/pci-rcar-gen4.c index 87cd69f989d..41f0d958447 100644 --- a/drivers/pci/pci-rcar-gen4.c +++ b/drivers/pci/pci-rcar-gen4.c @@ -235,7 +235,7 @@ static int rcar_gen4_pcie_ltssm_control(struct rcar_gen4_pcie *rcar, bool enable clrsetbits_le32(rcar->phy_base + 0x148, GENMASK(23, 22), BIT(22)); clrsetbits_le32(rcar->phy_base + 0x148, GENMASK(18, 16), GENMASK(17, 16)); clrsetbits_le32(rcar->phy_base + 0x148, GENMASK(7, 6), BIT(6)); - clrsetbits_le32(rcar->phy_base + 0x148, GENMASK(2, 0), GENMASK(11, 0)); + clrsetbits_le32(rcar->phy_base + 0x148, GENMASK(2, 0), GENMASK(1, 0)); clrsetbits_le32(rcar->phy_base + 0x1d4, GENMASK(16, 15), GENMASK(16, 15)); clrsetbits_le32(rcar->phy_base + 0x514, BIT(26), BIT(26)); clrsetbits_le32(rcar->phy_base + 0x0f8, BIT(16), 0); From e394ef09bc7389089b410e81fb660ad6ce18223a Mon Sep 17 00:00:00 2001 From: Marek Vasut Date: Wed, 6 Aug 2025 02:56:15 +0200 Subject: [PATCH 044/112] arm64: renesas: r8a779g3: Disable MicroSD UHS modes on Retronix R-Car V4H Sparrow Hawk EVTA1 The Retronix R-Car V4H Sparrow Hawk old revision EVTA1 does not have MicroSD voltage switch populated on the board, therefore the board supports only 3V3 and non-UHS MicroSD cards. While the EVTB1 board is populated with Winbond W77Q51NW SPI NOR, the EVTA1 board is populated with Spansion S25FS512S SPI NOR, those those SPI NOR IDs to discern the two board revisions and apply the MicroSD related DT changes. The MicroSD related DT changes modify the regulator node, which is now a regulator-fixed and supplies only 3V3, and remove sd-uhs-sdr50 and sd-uhs-sdr104 properties from the MicroSD slot controller node. The MicroSD related DT changes cannot be applied as DTO, because the base DT contains nodes which have to be removed in case of EVTA1, but have to be present in case of EVTB1 and newer revisions of the board. Because the EVTA1 is an old revision of the board that is not generally available, it is better to special case it and keep the base DT compatible with EVTB1 and newer revisions of the board which are actually available. Signed-off-by: Marek Vasut --- board/renesas/sparrowhawk/sparrowhawk.c | 114 ++++++++++++++++++++++++ 1 file changed, 114 insertions(+) diff --git a/board/renesas/sparrowhawk/sparrowhawk.c b/board/renesas/sparrowhawk/sparrowhawk.c index 8e72b5424d1..871dad8172a 100644 --- a/board/renesas/sparrowhawk/sparrowhawk.c +++ b/board/renesas/sparrowhawk/sparrowhawk.c @@ -6,8 +6,12 @@ #include #include #include +#include +#include #include +#include "../../../drivers/mtd/spi/sf_internal.h" + #if defined(CONFIG_XPL_BUILD) static const struct renesas_dbsc5_board_config @@ -118,6 +122,116 @@ dbsc5_get_board_data(struct udevice *dev, const u32 modemr0) return &renesas_v4h_sparrowhawk_8g_6400_dbsc5_board_config; } +static bool renesas_v4h_sparrowhawk_is_evta1 = false; + +unsigned int spl_spi_get_uboot_offs(struct spi_flash *flash) +{ + const u8 sf_ids_evta1[6] = { 0x01, 0x02, 0x20, 0x4d, 0x00, 0x81 }; + + renesas_v4h_sparrowhawk_is_evta1 = !memcmp(sf_ids_evta1, flash->info->id, + sizeof(sf_ids_evta1)); + + return CONFIG_SYS_SPI_U_BOOT_OFFS; +} + +void spl_perform_fixups(struct spl_image_info *spl_image) +{ + void *blob = spl_image_fdt_addr(spl_image); + int err, offs; + u32 size; + + if (!renesas_v4h_sparrowhawk_is_evta1) + return; + + printf("EVTA1 board detected\n"); + + /* + * MicroSD voltage switch is not populated on Sparrow Hawk EVTA1, + * rewrite MicroSD slot regulator to only support 3V3 and disable + * UHS modes in MicroSD slot node. + */ + if (!blob) + return; + + err = fdt_check_header(blob); + if (err < 0) { + printf("Invalid FDT header: %s\n", fdt_strerror(err)); + return; + } + + size = fdt_totalsize(blob); + err = fdt_open_into(blob, blob, size + 64); + if (err < 0) { + printf("Failed to expand DT\n"); + return; + } + + offs = fdt_path_offset(blob, "/regulator-vcc-sdhi"); + if (offs < 0) { + printf("Failed to locate MicroSD regulator node: %d\n", offs); + return; + } + + err = fdt_setprop_string(blob, offs, "compatible", "regulator-fixed"); + if (err < 0) { + printf("Failed to set fixed MicroSD regulator: %d\n", err); + return; + } + + err = fdt_setprop_u32(blob, offs, "regulator-min-microvolt", 3300000); + if (err < 0) { + printf("Failed to set MicroSD regulator minimum voltage: %d\n", err); + return; + } + + err = fdt_nop_property(blob, offs, "gpios"); + if (err < 0) { + printf("Failed to remove MicroSD regulator gpios: %d\n", err); + return; + } + + err = fdt_nop_property(blob, offs, "gpios-states"); + if (err < 0) { + printf("Failed to remove MicroSD regulator gpio states: %d\n", err); + return; + } + + err = fdt_nop_property(blob, offs, "states"); + if (err < 0) { + printf("Failed to remove MicroSD regulator states: %d\n", err); + return; + } + + offs = fdt_path_offset(blob, "/soc/mmc@ee140000"); + if (offs < 0) { + printf("Failed to locate MicroSD device node: %d\n", offs); + return; + } + + err = fdt_nop_property(blob, offs, "sd-uhs-sdr50"); + if (err < 0) { + printf("Failed to disable SDR50 mode in MicroSD node: %d\n", err); + return; + } + + err = fdt_nop_property(blob, offs, "sd-uhs-sdr104"); + if (err < 0) { + printf("Failed to disable SDR104 mode in MicroSD node: %d\n", err); + return; + } + + err = fdt_setprop_string(blob, offs, "pinctrl-names", "default"); + if (err < 0) { + printf("Failed to set fixed MicroSD pin names: %d\n", err); + return; + } + + err = fdt_nop_property(blob, offs, "pinctrl-1"); + if (err < 0) { + printf("Failed to disable UHS pins in MicroSD node: %d\n", err); + return; + } +} #endif #define RST_MODEMR0 0xe6160000 From 47148dfd8f7a70afa134723da7940f7c80b47329 Mon Sep 17 00:00:00 2001 From: Marek Vasut Date: Wed, 6 Aug 2025 02:57:14 +0200 Subject: [PATCH 045/112] arm64: renesas: r8a779g3: Disable dual-rank DRAM on Retronix R-Car V4H ES2 Sparrow Hawk The R-Car V4H SoC before rev.3.0 can not support dual-rank LPDDR5 DRAM. This affects 16 GiB dual-rank DRAM configuration of Retronix R-Car V4H Sparrow Hawk board. Fall back to 8 GiB single-rank DRAM configuration on such systems instead. Signed-off-by: Marek Vasut --- board/renesas/sparrowhawk/sparrowhawk.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/board/renesas/sparrowhawk/sparrowhawk.c b/board/renesas/sparrowhawk/sparrowhawk.c index 871dad8172a..1fd7a63d2fa 100644 --- a/board/renesas/sparrowhawk/sparrowhawk.c +++ b/board/renesas/sparrowhawk/sparrowhawk.c @@ -116,7 +116,7 @@ dbsc5_get_board_data(struct udevice *dev, const u32 modemr0) * Use MD[19] setting to discern 8 GiB and 16 GiB DRAM Sparrow Hawk * board variants from each other automatically. */ - if (modemr0 & BIT(19)) + if ((renesas_get_cpu_rev_integer() >= 3) && (modemr0 & BIT(19))) return &renesas_v4h_sparrowhawk_16g_5500_dbsc5_board_config; else return &renesas_v4h_sparrowhawk_8g_6400_dbsc5_board_config; @@ -244,7 +244,7 @@ void renesas_dram_init_banksize(void) int bank; /* 8 GiB device, do nothing. */ - if (!(modemr0 & BIT(19))) + if (!((renesas_get_cpu_rev_integer() >= 3) && (modemr0 & BIT(19)))) return; /* 16 GiB device, adjust memory map. */ From c818fd0594840266f0986d8beea94bda0fce1d49 Mon Sep 17 00:00:00 2001 From: Marek Vasut Date: Wed, 6 Aug 2025 02:58:30 +0200 Subject: [PATCH 046/112] arm64: renesas: r8a779g3: Enable xHCI USB on Retronix R-Car V4H Sparrow Hawk board Enable support for PCIe based xHCI USB 3.0 driver and USB mass storage support on Retronix R-Car V4H Sparrow Hawk board . Signed-off-by: Marek Vasut --- configs/r8a779g3_sparrowhawk_defconfig | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/configs/r8a779g3_sparrowhawk_defconfig b/configs/r8a779g3_sparrowhawk_defconfig index bb8d110dc0d..9cee4d287ef 100644 --- a/configs/r8a779g3_sparrowhawk_defconfig +++ b/configs/r8a779g3_sparrowhawk_defconfig @@ -25,6 +25,7 @@ CONFIG_GPIO_HOG=y CONFIG_REMOTEPROC_RENESAS_APMU=y CONFIG_BITBANGMII=y CONFIG_CMD_PCI=y +CONFIG_CMD_USB=y CONFIG_NET_RANDOM_ETHADDR=y CONFIG_NVME_PCI=y CONFIG_PCI=y @@ -34,6 +35,14 @@ CONFIG_PHY_MICREL=y CONFIG_PHY_MICREL_KSZ90X1=y CONFIG_RENESAS_RAVB=y CONFIG_SPI_FLASH_WINBOND=y +CONFIG_USB=y +CONFIG_USB_EHCI_GENERIC=y +CONFIG_USB_EHCI_HCD=y +CONFIG_USB_STORAGE=y +CONFIG_USB_XHCI_GENERIC=y +CONFIG_USB_XHCI_HCD=y +CONFIG_USB_XHCI_PCI=y +# CONFIG_USB_XHCI_RCAR is not set # CONFIG_SPL_SHARES_INIT_SP_ADDR is not set CONFIG_SPL_HAVE_INIT_STACK=y From 74bc80190c48dce43a59cbae1975ccf10f671bc2 Mon Sep 17 00:00:00 2001 From: Marek Vasut Date: Wed, 13 Aug 2025 23:26:27 +0200 Subject: [PATCH 047/112] arm64: dts: renesas: r8a779g3: Invert microSD voltage selector on Retronix R-Car V4H Sparrow Hawk EVTB1 Invert the polarity of microSD voltage selector on Retronix R-Car V4H Sparrow Hawk board. The voltage selector was not populated on prototype EVTA1 boards, and is implemented slightly different on EVTB1 boards. As the EVTA1 boards are from a limited run and generally not available, update the DT to make it compatible with EVTB1 microSD voltage selector. Signed-off-by: Marek Vasut --- arch/arm/dts/r8a779g3-sparrow-hawk-u-boot.dtsi | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/arch/arm/dts/r8a779g3-sparrow-hawk-u-boot.dtsi b/arch/arm/dts/r8a779g3-sparrow-hawk-u-boot.dtsi index c9f302799f1..c8c24d661ac 100644 --- a/arch/arm/dts/r8a779g3-sparrow-hawk-u-boot.dtsi +++ b/arch/arm/dts/r8a779g3-sparrow-hawk-u-boot.dtsi @@ -48,3 +48,7 @@ spi-rx-bus-width = <1>; }; }; + +&vcc_sdhi { + states = <1800000 0>, <3300000 1>; +}; From 1df2880e9512f4760f615668e5d06aa5f44b778a Mon Sep 17 00:00:00 2001 From: Marek Vasut Date: Wed, 13 Aug 2025 23:26:59 +0200 Subject: [PATCH 048/112] arm64: dts: renesas: r8a779g3: Set VDDQ18_25_AVB voltage on Retronix R-Car V4H Sparrow Hawk EVTB1 The Retronix R-Car V4H Sparrow Hawk EVTB1 uses 1V8 IO voltage supply for VDDQ18_25_AVB power rail. Update the AVB0 pinmux to reflect the change in IO voltage. Since the VDDQ18_25_AVB power rail is shared, all four AVB0, AVB1, AVB2, TSN0 PFC/GPIO POC[7..4] registers have to be configured the same way. Correct the voltage for EVTA1 boards accordingly by patching the U-Boot control DT in SPL. Signed-off-by: Marek Vasut --- arch/arm/dts/r8a779g3-sparrow-hawk-u-boot.dtsi | 7 +++++++ board/renesas/sparrowhawk/sparrowhawk.c | 12 ++++++++++++ 2 files changed, 19 insertions(+) diff --git a/arch/arm/dts/r8a779g3-sparrow-hawk-u-boot.dtsi b/arch/arm/dts/r8a779g3-sparrow-hawk-u-boot.dtsi index c8c24d661ac..cdf5c9cdd64 100644 --- a/arch/arm/dts/r8a779g3-sparrow-hawk-u-boot.dtsi +++ b/arch/arm/dts/r8a779g3-sparrow-hawk-u-boot.dtsi @@ -7,6 +7,13 @@ #include "r8a779g0-u-boot.dtsi" +&avb0_pins { + pins-vddq18-25-avb { + pins = "PIN_VDDQ_AVB0", "PIN_VDDQ_AVB1", "PIN_VDDQ_AVB2", "PIN_VDDQ_TSN0"; + power-source = <1800>; + }; +}; + /* Page 31 / FAN */ &gpio1 { pwm-fan-hog { diff --git a/board/renesas/sparrowhawk/sparrowhawk.c b/board/renesas/sparrowhawk/sparrowhawk.c index 1fd7a63d2fa..58de7f25cbd 100644 --- a/board/renesas/sparrowhawk/sparrowhawk.c +++ b/board/renesas/sparrowhawk/sparrowhawk.c @@ -231,6 +231,18 @@ void spl_perform_fixups(struct spl_image_info *spl_image) printf("Failed to disable UHS pins in MicroSD node: %d\n", err); return; } + + offs = fdt_path_offset(blob, "/soc/pinctrl@e6050000/avb0/pins-vddq18-25-avb"); + if (offs < 0) { + printf("Failed to locate AVB pinctrl node: %d\n", offs); + return; + } + + err = fdt_setprop_u32(blob, offs, "power-source", 2500); + if (err < 0) { + printf("Failed to set AVB IO voltage: %d\n", err); + return; + } } #endif From 797255d897d635799fbb878262b7491e07ceac9e Mon Sep 17 00:00:00 2001 From: Marek Vasut Date: Wed, 13 Aug 2025 23:25:56 +0200 Subject: [PATCH 049/112] arm64: dts: renesas: r8a779g3: Describe generic SPI NOR support on Retronix R-Car V4H Sparrow Hawk board Retronix R-Car V4H Sparrow Hawk EVTA1 is populated with Spansion S25FS512S, EVTB1 is populated with Winbond W77Q51NW. Describe the SPI NOR using generic "jedec,spi-nor" compatible, because both flashes can be auto-detected based on their built-in IDs. Signed-off-by: Marek Vasut --- arch/arm/dts/r8a779g3-sparrow-hawk-u-boot.dtsi | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/arch/arm/dts/r8a779g3-sparrow-hawk-u-boot.dtsi b/arch/arm/dts/r8a779g3-sparrow-hawk-u-boot.dtsi index cdf5c9cdd64..dff0355150d 100644 --- a/arch/arm/dts/r8a779g3-sparrow-hawk-u-boot.dtsi +++ b/arch/arm/dts/r8a779g3-sparrow-hawk-u-boot.dtsi @@ -51,6 +51,11 @@ &rpc { flash@0 { + /* + * EVTA1 is populated with Spansion S25FS512S + * EVTB1 is populated with Winbond W77Q51NW + */ + compatible = "jedec,spi-nor"; spi-tx-bus-width = <1>; spi-rx-bus-width = <1>; }; From c797d8bac9921208253242251b855e97107fba22 Mon Sep 17 00:00:00 2001 From: Lad Prabhakar Date: Wed, 23 Jul 2025 09:10:15 +0100 Subject: [PATCH 050/112] configs: Remove redundant CONFIG_TEXT_BASE assignments for Renesas defconfigs The Renesas board defconfigs explicitly set CONFIG_TEXT_BASE=0x50000000, however U-Boot's POSITION_INDEPENDENT=y build default already places text at 0x0. These hardcoded overrides are therefore unnecessary and will be pruned automatically in upcoming resyncs. Remove the CONFIG_TEXT_BASE lines from the following defconfigs: - hihope_rzg2_defconfig - r8a77970_eagle_defconfig - r8a77970_v3msk_defconfig - r8a77990_ebisu_defconfig - r8a77995_draak_defconfig - r8a779a0_falcon_defconfig - renesas_rzg2l_smarc_defconfig - rz2_beacon_defconfig - silinux_ek874_defconfig Signed-off-by: Lad Prabhakar Reviewed-by: Tom Rini Reviewed-by: Marek Vasut --- configs/hihope_rzg2_defconfig | 1 - configs/r8a77970_eagle_defconfig | 1 - configs/r8a77970_v3msk_defconfig | 1 - configs/r8a77990_ebisu_defconfig | 1 - configs/r8a77995_draak_defconfig | 1 - configs/r8a779a0_falcon_defconfig | 1 - configs/renesas_rzg2l_smarc_defconfig | 1 - configs/rzg2_beacon_defconfig | 1 - configs/silinux_ek874_defconfig | 1 - 9 files changed, 9 deletions(-) diff --git a/configs/hihope_rzg2_defconfig b/configs/hihope_rzg2_defconfig index f5bb28cb0c7..19fb14887c6 100644 --- a/configs/hihope_rzg2_defconfig +++ b/configs/hihope_rzg2_defconfig @@ -5,7 +5,6 @@ CONFIG_ARCH_RENESAS=y CONFIG_RCAR_GEN3=y CONFIG_COUNTER_FREQUENCY=16666666 CONFIG_ARCH_CPU_INIT=y -CONFIG_TEXT_BASE=0x50000000 CONFIG_ENV_SIZE=0x20000 CONFIG_ENV_OFFSET=0xFFFE0000 CONFIG_DEFAULT_DEVICE_TREE="renesas/r8a774a1-hihope-rzg2m-ex" diff --git a/configs/r8a77970_eagle_defconfig b/configs/r8a77970_eagle_defconfig index 4ab362f0d43..3734836fa61 100644 --- a/configs/r8a77970_eagle_defconfig +++ b/configs/r8a77970_eagle_defconfig @@ -5,7 +5,6 @@ CONFIG_ARCH_RENESAS=y CONFIG_RCAR_GEN3=y CONFIG_COUNTER_FREQUENCY=16666666 CONFIG_ARCH_CPU_INIT=y -CONFIG_TEXT_BASE=0x50000000 CONFIG_SYS_MALLOC_F_LEN=0x2000 CONFIG_ENV_SIZE=0x40000 CONFIG_ENV_OFFSET=0x700000 diff --git a/configs/r8a77970_v3msk_defconfig b/configs/r8a77970_v3msk_defconfig index 5ef81682caa..d3df0fd0baf 100644 --- a/configs/r8a77970_v3msk_defconfig +++ b/configs/r8a77970_v3msk_defconfig @@ -5,7 +5,6 @@ CONFIG_ARCH_RENESAS=y CONFIG_RCAR_GEN3=y CONFIG_COUNTER_FREQUENCY=16666666 CONFIG_ARCH_CPU_INIT=y -CONFIG_TEXT_BASE=0x50000000 CONFIG_SYS_MALLOC_F_LEN=0x2000 CONFIG_ENV_SIZE=0x40000 CONFIG_ENV_OFFSET=0x700000 diff --git a/configs/r8a77990_ebisu_defconfig b/configs/r8a77990_ebisu_defconfig index 414bfdebab1..7405f207612 100644 --- a/configs/r8a77990_ebisu_defconfig +++ b/configs/r8a77990_ebisu_defconfig @@ -5,7 +5,6 @@ CONFIG_ARCH_RENESAS=y CONFIG_RCAR_GEN3=y CONFIG_COUNTER_FREQUENCY=16666666 CONFIG_ARCH_CPU_INIT=y -CONFIG_TEXT_BASE=0x50000000 CONFIG_SYS_MALLOC_F_LEN=0x2000 CONFIG_ENV_SIZE=0x20000 CONFIG_ENV_OFFSET=0xFFFE0000 diff --git a/configs/r8a77995_draak_defconfig b/configs/r8a77995_draak_defconfig index 12d92067de5..2d487722677 100644 --- a/configs/r8a77995_draak_defconfig +++ b/configs/r8a77995_draak_defconfig @@ -5,7 +5,6 @@ CONFIG_ARCH_RENESAS=y CONFIG_RCAR_GEN3=y CONFIG_COUNTER_FREQUENCY=16666666 CONFIG_ARCH_CPU_INIT=y -CONFIG_TEXT_BASE=0x50000000 CONFIG_SYS_MALLOC_F_LEN=0x2000 CONFIG_ENV_SIZE=0x20000 CONFIG_ENV_OFFSET=0xFFFE0000 diff --git a/configs/r8a779a0_falcon_defconfig b/configs/r8a779a0_falcon_defconfig index f4f5c57451f..1b99ba1f02b 100644 --- a/configs/r8a779a0_falcon_defconfig +++ b/configs/r8a779a0_falcon_defconfig @@ -4,7 +4,6 @@ CONFIG_ARM=y CONFIG_ARCH_RENESAS=y CONFIG_RCAR_GEN4=y CONFIG_COUNTER_FREQUENCY=16666666 -CONFIG_TEXT_BASE=0x50000000 CONFIG_ENV_SIZE=0x40000 CONFIG_ENV_OFFSET=0xC00000 CONFIG_ENV_SECT_SIZE=0x40000 diff --git a/configs/renesas_rzg2l_smarc_defconfig b/configs/renesas_rzg2l_smarc_defconfig index c2bdc521018..401e237a816 100644 --- a/configs/renesas_rzg2l_smarc_defconfig +++ b/configs/renesas_rzg2l_smarc_defconfig @@ -3,7 +3,6 @@ CONFIG_COUNTER_FREQUENCY=16666666 CONFIG_SYS_INIT_SP_BSS_OFFSET=1048576 CONFIG_ARCH_CPU_INIT=y CONFIG_ARCH_RENESAS=y -CONFIG_TEXT_BASE=0x50000000 CONFIG_SYS_MALLOC_LEN=0x4000000 CONFIG_SYS_MALLOC_F_LEN=0x80000 CONFIG_ENV_SIZE=0x20000 diff --git a/configs/rzg2_beacon_defconfig b/configs/rzg2_beacon_defconfig index 0b91337b17b..d3f7061f04d 100644 --- a/configs/rzg2_beacon_defconfig +++ b/configs/rzg2_beacon_defconfig @@ -3,7 +3,6 @@ CONFIG_ARM=y CONFIG_ARCH_RENESAS=y CONFIG_RCAR_GEN3=y -CONFIG_TEXT_BASE=0x50000000 CONFIG_SYS_MALLOC_F_LEN=0x2000 CONFIG_ENV_SIZE=0x2000 CONFIG_ENV_OFFSET=0xFFFFE000 diff --git a/configs/silinux_ek874_defconfig b/configs/silinux_ek874_defconfig index acdd1ad5205..af462d2086f 100644 --- a/configs/silinux_ek874_defconfig +++ b/configs/silinux_ek874_defconfig @@ -5,7 +5,6 @@ CONFIG_ARCH_RENESAS=y CONFIG_RCAR_GEN3=y CONFIG_COUNTER_FREQUENCY=16666666 CONFIG_ARCH_CPU_INIT=y -CONFIG_TEXT_BASE=0x50000000 CONFIG_SYS_MALLOC_F_LEN=0x2000 CONFIG_ENV_SIZE=0x10000 CONFIG_ENV_OFFSET=0x3F0000 From 45eedb7b8097793242c542b68bc5d37b298808b7 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Tue, 5 Aug 2025 16:45:47 +0100 Subject: [PATCH 051/112] net: octeontx: Remove unneeded code In nicvf_rcv_pkt_handler there is no need to initialise err as it is assigned to immediately after. Also the test for !pkt will return if true meaning that pkt is guaranteed to be true after that code block and so no need to test for it and the redundant test can be removed. This issue was found by Smatch. Signed-off-by: Andrew Goodbody --- drivers/net/octeontx/nicvf_main.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/drivers/net/octeontx/nicvf_main.c b/drivers/net/octeontx/nicvf_main.c index 27d0327c88a..8021cd752b5 100644 --- a/drivers/net/octeontx/nicvf_main.c +++ b/drivers/net/octeontx/nicvf_main.c @@ -232,7 +232,7 @@ static int nicvf_rcv_pkt_handler(struct nicvf *nic, size_t pkt_len; struct cqe_rx_t *cqe_rx = (struct cqe_rx_t *)cq_desc; - int err = 0; + int err; /* Check for errors */ err = nicvf_check_cqe_rx_errs(nic, cq, cq_desc); @@ -245,8 +245,7 @@ static int nicvf_rcv_pkt_handler(struct nicvf *nic, return -1; } - if (pkt) - *ppkt = pkt; + *ppkt = pkt; return pkt_len; } From 62b4a482b943bc8173ac10a6c783e84d939b88bf Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Tue, 5 Aug 2025 16:45:48 +0100 Subject: [PATCH 052/112] net: octeontx: Remove unneeded test In nicvf_cq_handler there is a test for !cqe_count which will return if true so it is guaranteed that cqe_count will true after that point. This makes the later test for cqe_count redundant so it can be removed. This issue was found by Smatch. Signed-off-by: Andrew Goodbody --- drivers/net/octeontx/nicvf_main.c | 44 +++++++++++++++---------------- 1 file changed, 21 insertions(+), 23 deletions(-) diff --git a/drivers/net/octeontx/nicvf_main.c b/drivers/net/octeontx/nicvf_main.c index 8021cd752b5..94e5d827614 100644 --- a/drivers/net/octeontx/nicvf_main.c +++ b/drivers/net/octeontx/nicvf_main.c @@ -273,31 +273,29 @@ int nicvf_cq_handler(struct nicvf *nic, void **ppkt, int *pkt_len) cqe_head >>= 9; cqe_head &= 0xFFFF; - if (cqe_count) { - /* Get the CQ descriptor */ - cq_desc = (struct cqe_rx_t *)GET_CQ_DESC(cq, cqe_head); - cqe_head++; - cqe_head &= (cq->dmem.q_len - 1); + /* Get the CQ descriptor */ + cq_desc = (struct cqe_rx_t *)GET_CQ_DESC(cq, cqe_head); + cqe_head++; + cqe_head &= (cq->dmem.q_len - 1); - switch (cq_desc->cqe_type) { - case CQE_TYPE_RX: - debug("%s: Got Rx CQE\n", nic->dev->name); - *pkt_len = nicvf_rcv_pkt_handler(nic, cq, cq_desc, - ppkt, CQE_TYPE_RX); - processed_rq_cqe++; - break; - case CQE_TYPE_SEND: - debug("%s: Got Tx CQE\n", nic->dev->name); - nicvf_snd_pkt_handler(nic, cq, cq_desc, CQE_TYPE_SEND); - processed_sq_cqe++; - break; - default: - debug("%s: Got CQ type %u\n", nic->dev->name, - cq_desc->cqe_type); - break; - } - processed_cqe++; + switch (cq_desc->cqe_type) { + case CQE_TYPE_RX: + debug("%s: Got Rx CQE\n", nic->dev->name); + *pkt_len = nicvf_rcv_pkt_handler(nic, cq, cq_desc, + ppkt, CQE_TYPE_RX); + processed_rq_cqe++; + break; + case CQE_TYPE_SEND: + debug("%s: Got Tx CQE\n", nic->dev->name); + nicvf_snd_pkt_handler(nic, cq, cq_desc, CQE_TYPE_SEND); + processed_sq_cqe++; + break; + default: + debug("%s: Got CQ type %u\n", nic->dev->name, + cq_desc->cqe_type); + break; } + processed_cqe++; /* Dequeue CQE */ nicvf_queue_reg_write(nic, NIC_QSET_CQ_0_7_DOOR, From 0ce7fef9e2154d188bd50ae687fb666faac8fe7b Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Tue, 5 Aug 2025 16:45:49 +0100 Subject: [PATCH 053/112] net: octeontx: Free allocated memory on error In octeontx_smi_probe if an error is detected then memory that was allocated is not freed. Small refactor of the code to use a common return and free memory. Also return -ENOMEM for an allocation failure. This issue was found by Smatch. Signed-off-by: Andrew Goodbody --- drivers/net/octeontx/smi.c | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/drivers/net/octeontx/smi.c b/drivers/net/octeontx/smi.c index 233c26f7319..217bcac2ce2 100644 --- a/drivers/net/octeontx/smi.c +++ b/drivers/net/octeontx/smi.c @@ -338,7 +338,8 @@ int octeontx_smi_probe(struct udevice *dev) if (!bus || !priv) { printf("Failed to allocate OcteonTX MDIO bus # %u\n", dev_seq(dev)); - return -1; + ret = -ENOMEM; + goto error_ret; } bus->read = octeontx_phy_read; @@ -355,9 +356,16 @@ int octeontx_smi_probe(struct udevice *dev) ret = mdio_register(bus); if (ret) - return ret; + goto error_ret; } return 0; + +error_ret: + if (bus) + free(bus); + if (priv) + free(priv); + return ret; } static const struct udevice_id octeontx_smi_ids[] = { From 4b2d64f3885a83fd001993785f74f70cc6045acc Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Wed, 6 Aug 2025 10:37:26 +0100 Subject: [PATCH 054/112] net: phy: vitesse: Fix incorrect test for timeout In vsc8514_config there is a while loop for detecting a config failure using a timeout counter with a post-decrement. In the case of a timeout this will result in the loop exiting with timeout == -1 so use that as the test below the loop to detect that the timeout occurred. This issue was found by Smatch. Signed-off-by: Andrew Goodbody Reviewed-by: Quentin Schulz --- drivers/net/phy/vitesse.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/phy/vitesse.c b/drivers/net/phy/vitesse.c index 4867d1931b4..821d3878236 100644 --- a/drivers/net/phy/vitesse.c +++ b/drivers/net/phy/vitesse.c @@ -239,7 +239,7 @@ static int vsc8514_config(struct phy_device *phydev) while ((val & MIIM_VSC8514_18G_CMDSTAT) && timeout--) val = phy_read(phydev, MDIO_DEVAD_NONE, MIIM_VSC8514_GENERAL18); - if (0 == timeout) { + if (timeout == -1) { printf("PHY 8514 config failed\n"); return -1; } From a75c8a4b883108edf19127fca3e6c6c590f9ba8c Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Wed, 6 Aug 2025 17:43:24 +0100 Subject: [PATCH 055/112] phy: marvell: Fix off by 1 limit checks The limit checks in get_speed_string and get_type_string are off by 1 as they do not account for the maximum index into an array that can be used is 1 less than the number of elements in that array. Adjust the limit checks to allow for this. This issue was found by Smatch. Signed-off-by: Andrew Goodbody Reviewed-by: Stefan Roese --- drivers/phy/marvell/comphy_core.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/phy/marvell/comphy_core.c b/drivers/phy/marvell/comphy_core.c index a666a4e794e..a4121423873 100644 --- a/drivers/phy/marvell/comphy_core.c +++ b/drivers/phy/marvell/comphy_core.c @@ -28,7 +28,7 @@ static const char *get_speed_string(u32 speed) "10.3125 Gbps" }; - if (speed < 0 || speed > COMPHY_SPEED_MAX) + if (speed < 0 || speed >= COMPHY_SPEED_MAX) return "invalid"; return speed_strings[speed]; @@ -44,7 +44,7 @@ static const char *get_type_string(u32 type) "IGNORE" }; - if (type < 0 || type > COMPHY_TYPE_MAX) + if (type < 0 || type >= COMPHY_TYPE_MAX) return "invalid"; return type_strings[type]; From 2e9155cb9f366a6b9191af0850efad1948b4c785 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Wed, 6 Aug 2025 17:43:25 +0100 Subject: [PATCH 056/112] phy: marvell: Cannot test unsigned field to be negative In comphy_cp110_init_serdes_map in comphy_cp110.c there are two fields in cfg, comphy_lanes_count and comphy_mux_bitcount, which are fetched from the FDT blob with fdtdec_get_int which returns an int. These two fields are then tested for being negative. However the fields are declared as unsigned so those tests must always fail. Change the declaration of those fields to be int instead of u32 and the code will work as expected. This issue was found by Smatch. Signed-off-by: Andrew Goodbody Reviewed-by: Stefan Roese --- drivers/phy/marvell/comphy_core.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/phy/marvell/comphy_core.h b/drivers/phy/marvell/comphy_core.h index f3d04939387..086a4d82f26 100644 --- a/drivers/phy/marvell/comphy_core.h +++ b/drivers/phy/marvell/comphy_core.h @@ -47,8 +47,8 @@ struct chip_serdes_phy_config { int (*rx_training)(struct chip_serdes_phy_config *, u32); void __iomem *comphy_base_addr; void __iomem *hpipe3_base_addr; - u32 comphy_lanes_count; - u32 comphy_mux_bitcount; + int comphy_lanes_count; + int comphy_mux_bitcount; const fdt32_t *comphy_mux_lane_order; u32 cp_index; struct comphy_map comphy_map_data[MAX_LANE_OPTIONS]; From 59ec495f6c645c80d934034ffe48adb2ea75839a Mon Sep 17 00:00:00 2001 From: Jim Liu Date: Thu, 7 Aug 2025 13:28:32 +0800 Subject: [PATCH 057/112] net: designware: Fix get_timer value overflow get_timer returns a ulong value representing system time in ms. On a 64-bit system, this ulong value is 64 bits long. However, the driver stores it in a 32-bit unsigned integer, which overflows after 49 days up time, causing the driver to get an incorrect time. Replace the unsigned int variable with a ulong type to properly store the value returned by get_timer. Signed-off-by: Stanley Chu Signed-off-by: Jim Liu --- drivers/net/designware.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/net/designware.c b/drivers/net/designware.c index fce3ef910cb..7ecedc3d7f0 100644 --- a/drivers/net/designware.c +++ b/drivers/net/designware.c @@ -486,7 +486,7 @@ static int dw_adjust_link(struct dw_eth_dev *priv, struct eth_mac_regs *mac_p, #ifdef CONFIG_ARCH_NPCM8XX if (phydev->interface == PHY_INTERFACE_MODE_SGMII) { - unsigned int start; + ulong start; /* Indirect access to VR_MII_MMD registers */ writew((VR_MII_MMD >> 9), PCS_BA + PCS_IND_AC); @@ -532,7 +532,7 @@ int designware_eth_init(struct dw_eth_dev *priv, u8 *enetaddr) { struct eth_mac_regs *mac_p = priv->mac_regs_p; struct eth_dma_regs *dma_p = priv->dma_regs_p; - unsigned int start; + ulong start; int ret; writel(readl(&dma_p->busmode) | DMAMAC_SRST, &dma_p->busmode); From 0cabbe3235ba91f84495095a7bec693338b3c521 Mon Sep 17 00:00:00 2001 From: Jim Liu Date: Thu, 7 Aug 2025 13:29:31 +0800 Subject: [PATCH 058/112] net: phy: broadcom: add support for BCM54612E It's Broadcom PHY simply described as single-port RGMII 10/100/1000BASE-T PHY. Signed-off-by: Jim Liu --- drivers/net/phy/broadcom.c | 37 +++++++++++++++++++++++++++++++++++++ 1 file changed, 37 insertions(+) diff --git a/drivers/net/phy/broadcom.c b/drivers/net/phy/broadcom.c index 0a49015eb89..1c02e3efedc 100644 --- a/drivers/net/phy/broadcom.c +++ b/drivers/net/phy/broadcom.c @@ -134,6 +134,33 @@ static void bcm_phy_write_misc(struct phy_device *phydev, phy_write(phydev, MDIO_DEVAD_NONE, MIIM_BCM54XX_EXP_DATA, value); } +/* Broadcom BCM54612E */ +static int bcm54612e_config(struct phy_device *phydev) +{ + u32 reg = 0; + + genphy_config_aneg(phydev); + + phy_reset(phydev); + + /* 125Mhz Clock Output Enable */ + reg = phy_read(phydev, MDIO_DEVAD_NONE, MIIM_BCM54XX_EXP_SEL); + reg |= 0xD34; + phy_write(phydev, MDIO_DEVAD_NONE, MIIM_BCM54XX_EXP_SEL, reg); + + reg = phy_read(phydev, MDIO_DEVAD_NONE, MIIM_BCM54XX_EXP_DATA); + reg |= (1 << 1); + phy_write(phydev, MDIO_DEVAD_NONE, MIIM_BCM54XX_EXP_DATA, reg); + + reg = phy_read(phydev, MDIO_DEVAD_NONE, MIIM_BCM54XX_EXP_SEL); + reg &= 0xfffff000; + phy_write(phydev, MDIO_DEVAD_NONE, MIIM_BCM54XX_EXP_SEL, reg); + + genphy_restart_aneg(phydev); + + return 0; +} + /* Broadcom BCM5461S */ static int bcm5461_config(struct phy_device *phydev) { @@ -434,6 +461,16 @@ U_BOOT_PHY_DRIVER(bcm5461s) = { .shutdown = &genphy_shutdown, }; +U_BOOT_PHY_DRIVER(bcm54612e) = { + .name = "Broadcom BCM54612E", + .uid = 0x03625e6a, + .mask = 0xfffff0, + .features = PHY_GBIT_FEATURES, + .config = &bcm54612e_config, + .startup = &bcm54xx_startup, + .shutdown = &genphy_shutdown, +}; + U_BOOT_PHY_DRIVER(bcm5464s) = { .name = "Broadcom BCM5464S", .uid = 0x2060b0, From fbd79b493d943a2f41a78408cc99ca4ee4392b07 Mon Sep 17 00:00:00 2001 From: Jerome Forissier Date: Tue, 12 Aug 2025 14:43:18 +0200 Subject: [PATCH 059/112] lwip: icmp: allow reporting ICMP destination unreachable Allow reporting ICMP destination unreachable messages via a user-defined callback. Signed-off-by: Jerome Forissier --- lib/lwip/lwip/src/core/ipv4/icmp.c | 17 +++++++++++++---- 1 file changed, 13 insertions(+), 4 deletions(-) diff --git a/lib/lwip/lwip/src/core/ipv4/icmp.c b/lib/lwip/lwip/src/core/ipv4/icmp.c index 9a82a67aa93..6d588349c4a 100644 --- a/lib/lwip/lwip/src/core/ipv4/icmp.c +++ b/lib/lwip/lwip/src/core/ipv4/icmp.c @@ -80,9 +80,9 @@ void icmp_input(struct pbuf *p, struct netif *inp) { u8_t type; -#ifdef LWIP_DEBUG +#if defined(LWIP_DEBUG) || defined(ICMP_DEST_UNREACH_CB) u8_t code; -#endif /* LWIP_DEBUG */ +#endif struct icmp_echo_hdr *iecho; const struct ip_hdr *iphdr_in; u16_t hlen; @@ -103,11 +103,11 @@ icmp_input(struct pbuf *p, struct netif *inp) } type = *((u8_t *)p->payload); -#ifdef LWIP_DEBUG +#if defined(LWIP_DEBUG) || defined(ICMP_DEST_UNREACH_CB) code = *(((u8_t *)p->payload) + 1); /* if debug is enabled but debug statement below is somehow disabled: */ LWIP_UNUSED_ARG(code); -#endif /* LWIP_DEBUG */ +#endif switch (type) { case ICMP_ER: /* This is OK, echo reply might have been parsed by a raw PCB @@ -257,6 +257,15 @@ icmp_input(struct pbuf *p, struct netif *inp) default: if (type == ICMP_DUR) { MIB2_STATS_INC(mib2.icmpindestunreachs); +#ifdef ICMP_DEST_UNREACH_CB + /* + * The callback receives the IP packet (not the ICMP message) so that + * it can extract the source address for example + */ + pbuf_add_header(p, IP_HLEN); + ICMP_DEST_UNREACH_CB(code, p); + pbuf_remove_header(p, IP_HLEN); +#endif } else if (type == ICMP_TE) { MIB2_STATS_INC(mib2.icmpintimeexcds); } else if (type == ICMP_PP) { From 6b914d5596d947ebea4e8697004e210df1abe61e Mon Sep 17 00:00:00 2001 From: Jerome Forissier Date: Tue, 12 Aug 2025 14:43:19 +0200 Subject: [PATCH 060/112] net: lwip: add Kconfig option to show ICMP unreachable errors Add Kconfig symbol LWIP_ICMP_SHOW_UNREACH which, when enabled, prints a message to the console upon reception of ICMP unreachable messages. For example: $ make qemu_arm64_lwip_defconfig $ qemu-system-aarch64 -M virt -cpu max -nographic -bios u-boot.bin [...] => dhcp DHCP client bound to address 10.0.2.15 (0 ms) => tftp 192.168.0.100:69:Image Using virtio-net#32 device TFTP from server 192.168.0.100; our IP address is 10.0.2.15 Filename 'Image'. Load address: 0x40200000 Loading: ICMP destination unreachable (host unreachable) from 192.168.0.16 Timeout! => tftp 192.168.0.16:69:Image Using virtio-net#32 device TFTP from server 192.168.0.16; our IP address is 10.0.2.15 Filename 'Image'. Load address: 0x40200000 Loading: ICMP destination unreachable (port unreachable) from 192.168.0.16 Timeout! => Submitted upstream as https://github.com/lwip-tcpip/lwip/pull/73. Signed-off-by: Jerome Forissier --- lib/lwip/u-boot/arch/cc.h | 7 +++++++ lib/lwip/u-boot/lwipopts.h | 4 ++++ net/lwip/Kconfig | 13 +++++++++++++ net/lwip/Makefile | 1 + net/lwip/icmp_unreach.c | 38 ++++++++++++++++++++++++++++++++++++++ 5 files changed, 63 insertions(+) create mode 100644 net/lwip/icmp_unreach.c diff --git a/lib/lwip/u-boot/arch/cc.h b/lib/lwip/u-boot/arch/cc.h index 04ab94d6b70..849c79c5a8d 100644 --- a/lib/lwip/u-boot/arch/cc.h +++ b/lib/lwip/u-boot/arch/cc.h @@ -56,4 +56,11 @@ static inline const char *sntp_format_time(time_t t) } #define sntp_format_time sntp_format_time + +#ifdef CONFIG_LWIP_ICMP_SHOW_UNREACH +struct pbuf; +void net_lwip_icmp_dest_unreach(int code, struct pbuf *p); + +#define ICMP_DEST_UNREACH_CB(_c, _p) net_lwip_icmp_dest_unreach(_c, _p) +#endif #endif /* LWIP_ARCH_CC_H */ diff --git a/lib/lwip/u-boot/lwipopts.h b/lib/lwip/u-boot/lwipopts.h index 46af91f9410..80b93ea172d 100644 --- a/lib/lwip/u-boot/lwipopts.h +++ b/lib/lwip/u-boot/lwipopts.h @@ -80,7 +80,11 @@ #define IP_DEFAULT_TTL 255 +#if defined(CONFIG_PROT_ICMP_LWIP) +#define LWIP_ICMP 1 +#else #define LWIP_ICMP 0 +#endif #if defined(CONFIG_PROT_RAW_LWIP) #define LWIP_RAW 1 diff --git a/net/lwip/Kconfig b/net/lwip/Kconfig index d28a8a7df94..5789766fe62 100644 --- a/net/lwip/Kconfig +++ b/net/lwip/Kconfig @@ -4,6 +4,16 @@ if NET_LWIP +config LWIP_ICMP_SHOW_UNREACH + bool "Print ICMP Destination Unreachable messages" + default y + depends on CMD_TFTPBOOT || CMD_SNTP + select PROT_ICMP_LWIP + help + Prints a message whenever an ICMP Destination Unreachable message is + received while running a network command that sends requests via UDP. + Enabling this can make troubleshooting easier. + config LWIP_DEBUG bool "Enable debug traces in the lwIP library" help @@ -31,6 +41,9 @@ config PROT_DNS_LWIP bool select PROT_UDP_LWIP +config PROT_ICMP_LWIP + bool + config PROT_RAW_LWIP bool diff --git a/net/lwip/Makefile b/net/lwip/Makefile index 97299d9b542..09c3b3511a4 100644 --- a/net/lwip/Makefile +++ b/net/lwip/Makefile @@ -2,6 +2,7 @@ ccflags-y += -I$(srctree)/lib/lwip/lwip/src/include -I$(srctree)/lib/lwip/u-boot obj-$(CONFIG_$(PHASE_)DM_ETH) += net-lwip.o obj-$(CONFIG_CMD_DHCP) += dhcp.o +obj-$(CONFIG_LWIP_ICMP_SHOW_UNREACH) += icmp_unreach.o obj-$(CONFIG_CMD_TFTPBOOT) += tftp.o obj-$(CONFIG_WGET) += wget.o diff --git a/net/lwip/icmp_unreach.c b/net/lwip/icmp_unreach.c new file mode 100644 index 00000000000..9e8a05f5717 --- /dev/null +++ b/net/lwip/icmp_unreach.c @@ -0,0 +1,38 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* Copyright (C) 2025 Linaro Ltd. */ + +#include +#include +#include +#include + +static const char *code_to_str(int code) +{ + switch (code) { + case ICMP_DUR_NET: + return "network unreachable"; + case ICMP_DUR_HOST: + return "host unreachable"; + case ICMP_DUR_PROTO: + return "protocol unreachable"; + case ICMP_DUR_PORT: + return "port unreachable"; + case ICMP_DUR_FRAG: + return "fragmentation needed and DF set"; + case ICMP_DUR_SR: + return "source route failed"; + default: + break; + } + return "unknown cause"; +} + +void net_lwip_icmp_dest_unreach(int code, struct pbuf *p) +{ + struct ip_hdr *iphdr = (struct ip_hdr *)p->payload; + ip4_addr_t src; + + ip4_addr_copy(src, iphdr->src); + printf("ICMP destination unreachable (%s) from %s\n", + code_to_str(code), ip4addr_ntoa(&src)); +} From 4800a6a0b3fa9d00f1ec40233a0e16464987c24f Mon Sep 17 00:00:00 2001 From: Max Merchel Date: Thu, 14 Aug 2025 14:03:52 +0200 Subject: [PATCH 061/112] net: add missing SPDX-License-Identifier for files originating from LiMon The header of LiMon imported files reference a License file which does not exist in U-Boot. Some files were forgotten when adding the SPDX-License-Identifier. The LiMon files were originally licensed under GPLv2 as can be seen in commit [2ea91039]. Based on this commit, add the correct SPDX license identifier. While at it drop the reference to the non-existing License file from all LiMon files and update the SPDX-License-Identifier to SPDX version 3. Signed-off-by: Max Merchel --- include/net-legacy.h | 3 +-- include/net/tftp.h | 2 +- net/arp.c | 3 +-- net/arp.h | 3 +-- net/bootp.c | 2 +- net/bootp.h | 2 +- net/cdp.c | 3 +-- net/cdp.h | 3 +-- net/net.c | 3 +-- net/net_rand.h | 2 +- net/ping.c | 3 +-- net/ping.h | 3 +-- 12 files changed, 12 insertions(+), 20 deletions(-) diff --git a/include/net-legacy.h b/include/net-legacy.h index a7dbcec1506..050fc352920 100644 --- a/include/net-legacy.h +++ b/include/net-legacy.h @@ -1,9 +1,8 @@ -/* SPDX-License-Identifier: GPL-2.0 */ +/* SPDX-License-Identifier: GPL-2.0-only */ /* * LiMon Monitor (LiMon) - Network. * * Copyright 1994 - 2000 Neil Russell. - * (See License) * * History * 9/16/00 bor adapted to TQM823L/STK8xxL board, RARP/TFTP boot added diff --git a/include/net/tftp.h b/include/net/tftp.h index c411c9b2e65..c7e14817280 100644 --- a/include/net/tftp.h +++ b/include/net/tftp.h @@ -1,10 +1,10 @@ +/* SPDX-License-Identifier: GPL-2.0-only */ /* * LiMon - BOOTP/TFTP. * * Copyright 1994, 1995, 2000 Neil Russell. * Copyright 2011 Comelit Group SpA * Luca Ceresoli - * (See License) */ #ifndef __TFTP_H__ diff --git a/net/arp.c b/net/arp.c index bc1e25f941f..4801dca6213 100644 --- a/net/arp.c +++ b/net/arp.c @@ -1,9 +1,8 @@ -// SPDX-License-Identifier: GPL-2.0 +// SPDX-License-Identifier: GPL-2.0-only /* * Copied from Linux Monitor (LiMon) - Networking. * * Copyright 1994 - 2000 Neil Russell. - * (See License) * Copyright 2000 Roland Borde * Copyright 2000 Paolo Scaffardi * Copyright 2000-2002 Wolfgang Denk, wd@denx.de diff --git a/net/arp.h b/net/arp.h index c50885fb9a5..882f3ec31fc 100644 --- a/net/arp.h +++ b/net/arp.h @@ -1,9 +1,8 @@ -/* SPDX-License-Identifier: GPL-2.0 */ +/* SPDX-License-Identifier: GPL-2.0-only */ /* * Copied from Linux Monitor (LiMon) - Networking. * * Copyright 1994 - 2000 Neil Russell. - * (See License) * Copyright 2000 Roland Borde * Copyright 2000 Paolo Scaffardi * Copyright 2000-2002 Wolfgang Denk, wd@denx.de diff --git a/net/bootp.c b/net/bootp.c index 95d906e3b2d..19e7453daed 100644 --- a/net/bootp.c +++ b/net/bootp.c @@ -1,8 +1,8 @@ +/* SPDX-License-Identifier: GPL-2.0-only */ /* * Based on LiMon - BOOTP. * * Copyright 1994, 1995, 2000 Neil Russell. - * (See License) * Copyright 2000 Roland Borde * Copyright 2000 Paolo Scaffardi * Copyright 2000-2004 Wolfgang Denk, wd@denx.de diff --git a/net/bootp.h b/net/bootp.h index 68320bf66cf..47c743479e7 100644 --- a/net/bootp.h +++ b/net/bootp.h @@ -1,8 +1,8 @@ +/* SPDX-License-Identifier: GPL-2.0-only */ /* * Copied from LiMon - BOOTP. * * Copyright 1994, 1995, 2000 Neil Russell. - * (See License) * Copyright 2000 Paolo Scaffardi */ diff --git a/net/cdp.c b/net/cdp.c index d4cfc587ee3..6e404981d4a 100644 --- a/net/cdp.c +++ b/net/cdp.c @@ -1,9 +1,8 @@ -// SPDX-License-Identifier: GPL-2.0 +// SPDX-License-Identifier: GPL-2.0-only /* * Copied from Linux Monitor (LiMon) - Networking. * * Copyright 1994 - 2000 Neil Russell. - * (See License) * Copyright 2000 Roland Borde * Copyright 2000 Paolo Scaffardi * Copyright 2000-2002 Wolfgang Denk, wd@denx.de diff --git a/net/cdp.h b/net/cdp.h index 16ccbf4b59e..606fabba957 100644 --- a/net/cdp.h +++ b/net/cdp.h @@ -1,9 +1,8 @@ -/* SPDX-License-Identifier: GPL-2.0 */ +/* SPDX-License-Identifier: GPL-2.0-only */ /* * Copied from Linux Monitor (LiMon) - Networking. * * Copyright 1994 - 2000 Neil Russell. - * (See License) * Copyright 2000 Roland Borde * Copyright 2000 Paolo Scaffardi * Copyright 2000-2002 Wolfgang Denk, wd@denx.de diff --git a/net/net.c b/net/net.c index 5219367e391..ac9b65c0ca4 100644 --- a/net/net.c +++ b/net/net.c @@ -1,9 +1,8 @@ -// SPDX-License-Identifier: GPL-2.0 +// SPDX-License-Identifier: GPL-2.0-only /* * Copied from Linux Monitor (LiMon) - Networking. * * Copyright 1994 - 2000 Neil Russell. - * (See License) * Copyright 2000 Roland Borde * Copyright 2000 Paolo Scaffardi * Copyright 2000-2002 Wolfgang Denk, wd@denx.de diff --git a/net/net_rand.h b/net/net_rand.h index 686e85f2b53..e21dff8569b 100644 --- a/net/net_rand.h +++ b/net/net_rand.h @@ -1,8 +1,8 @@ +/* SPDX-License-Identifier: GPL-2.0-only */ /* * Copied from LiMon - BOOTP. * * Copyright 1994, 1995, 2000 Neil Russell. - * (See License) * Copyright 2000 Paolo Scaffardi */ diff --git a/net/ping.c b/net/ping.c index 075df3663fe..fb981f62084 100644 --- a/net/ping.c +++ b/net/ping.c @@ -1,9 +1,8 @@ -// SPDX-License-Identifier: GPL-2.0 +// SPDX-License-Identifier: GPL-2.0-only /* * Copied from Linux Monitor (LiMon) - Networking. * * Copyright 1994 - 2000 Neil Russell. - * (See License) * Copyright 2000 Roland Borde * Copyright 2000 Paolo Scaffardi * Copyright 2000-2002 Wolfgang Denk, wd@denx.de diff --git a/net/ping.h b/net/ping.h index 76ac225fc07..739f128408e 100644 --- a/net/ping.h +++ b/net/ping.h @@ -1,9 +1,8 @@ -/* SPDX-License-Identifier: GPL-2.0 */ +/* SPDX-License-Identifier: GPL-2.0-only */ /* * Copied from Linux Monitor (LiMon) - Networking. * * Copyright 1994 - 2000 Neil Russell. - * (See License) * Copyright 2000 Roland Borde * Copyright 2000 Paolo Scaffardi * Copyright 2000-2002 Wolfgang Denk, wd@denx.de From ed3b08874f4c47e287a1f0eb36fc61ff7d778cc9 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Tue, 5 Aug 2025 11:52:00 +0100 Subject: [PATCH 062/112] net: ldpaa_eth: Fix buffer overflow in memset In ldpaa_eth_open a memset is used to initialise a struct to 0 but the size passed is that of a different struct. Correct to pass the sizeof the struct that is being initialised. This issue was found by Smatch. Signed-off-by: Andrew Goodbody --- drivers/net/ldpaa_eth/ldpaa_eth.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/ldpaa_eth/ldpaa_eth.c b/drivers/net/ldpaa_eth/ldpaa_eth.c index b72198ca530..94e62748239 100644 --- a/drivers/net/ldpaa_eth/ldpaa_eth.c +++ b/drivers/net/ldpaa_eth/ldpaa_eth.c @@ -458,7 +458,7 @@ static int ldpaa_eth_open(struct udevice *dev) link_state.up == 1 ? printf("up\n") : printf("error state\n"); #endif - memset(&d_queue, 0, sizeof(struct dpni_queue)); + memset(&d_queue, 0, sizeof(struct dpni_queue_id)); err = dpni_get_queue(dflt_mc_io, MC_CMD_NO_FLAGS, dflt_dpni->dpni_handle, DPNI_QUEUE_RX, 0, 0, &d_queue_cfg, &d_queue); From ff36afe346777f60c461964de1ab00aa6b2edb95 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Tue, 5 Aug 2025 12:04:00 +0100 Subject: [PATCH 063/112] net: mediatek: Use correct variable for return In mtk_eth_of_to_plat, the last error check has the value in 'priv->phy_addr' but returns ret. Correct to return 'priv->phy_addr' instead. This issue was found by Smatch. Signed-off-by: Andrew Goodbody --- drivers/net/mtk_eth/mtk_eth.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/mtk_eth/mtk_eth.c b/drivers/net/mtk_eth/mtk_eth.c index 5d6a42bceb4..b172838ba3a 100644 --- a/drivers/net/mtk_eth/mtk_eth.c +++ b/drivers/net/mtk_eth/mtk_eth.c @@ -1461,7 +1461,7 @@ static int mtk_eth_of_to_plat(struct udevice *dev) priv->phy_addr = ofnode_read_s32_default(args.node, "reg", -1); if (priv->phy_addr < 0) { printf("error: phy address is not specified\n"); - return ret; + return priv->phy_addr; } } From 34bc71f2db6bcd83b718ac9c28c39bd7d788a356 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Tue, 5 Aug 2025 12:14:14 +0100 Subject: [PATCH 064/112] net: mv88e6xxx: Fix logical operator instead of bitwise In mv88e6xxx_port_enable when attempting to mask out the previous settings of two bits a logical operator was used instead of a bitwise operator. Fix this. This issue was found by Smatch. Signed-off-by: Andrew Goodbody --- drivers/net/mv88e6xxx.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/mv88e6xxx.c b/drivers/net/mv88e6xxx.c index 557b6b2c8f6..f06c73c20f8 100644 --- a/drivers/net/mv88e6xxx.c +++ b/drivers/net/mv88e6xxx.c @@ -631,7 +631,7 @@ static int mv88e6xxx_port_enable(struct udevice *dev, int port, struct phy_devic dev_dbg(dev, "configure internal RGMII delays\n"); /* RGMII delays */ - val &= ~(PORT_REG_PHYS_CTRL_RGMII_DELAY_RXCLK || + val &= ~(PORT_REG_PHYS_CTRL_RGMII_DELAY_RXCLK | PORT_REG_PHYS_CTRL_RGMII_DELAY_TXCLK); if (phy->interface == PHY_INTERFACE_MODE_RGMII_ID || phy->interface == PHY_INTERFACE_MODE_RGMII_RXID) From b24c89affd9063c3f9f3ca99db075bd3bb1fc4b2 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Tue, 5 Aug 2025 15:18:16 +0100 Subject: [PATCH 065/112] net: mvpp2: Fix impossible test You cannot test an unsigned char to be >= 256. Instead make the variables start and end to be ints. This issue was found by Smatch. Signed-off-by: Andrew Goodbody --- drivers/net/mvpp2.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/net/mvpp2.c b/drivers/net/mvpp2.c index 184c1f9a46a..c0328345973 100644 --- a/drivers/net/mvpp2.c +++ b/drivers/net/mvpp2.c @@ -1722,8 +1722,7 @@ static struct mvpp2_prs_entry *mvpp2_prs_flow_find(struct mvpp2 *priv, int flow) } /* Return first free tcam index, seeking from start to end */ -static int mvpp2_prs_tcam_first_free(struct mvpp2 *priv, unsigned char start, - unsigned char end) +static int mvpp2_prs_tcam_first_free(struct mvpp2 *priv, int start, int end) { int tid; From 6781b90f89b427ec9445c43f8102ebe0a4330e54 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Tue, 5 Aug 2025 15:18:17 +0100 Subject: [PATCH 066/112] net: mvpp2: Return -ENOMEM for failed alloc Instead of returning -1 on a failed alloc, return -ENOMEM. This issue was found by Smatch. Signed-off-by: Andrew Goodbody --- drivers/net/mvpp2.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/mvpp2.c b/drivers/net/mvpp2.c index c0328345973..b68d305a0dc 100644 --- a/drivers/net/mvpp2.c +++ b/drivers/net/mvpp2.c @@ -2329,7 +2329,7 @@ static int mvpp2_prs_mac_da_accept(struct mvpp2 *priv, int port, pe = kzalloc(sizeof(*pe), GFP_KERNEL); if (!pe) - return -1; + return -ENOMEM; mvpp2_prs_tcam_lu_set(pe, MVPP2_PRS_LU_MAC); pe->index = tid; From 3aa3d37282414ea5c19ea415f46d214f4c80d8b6 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Tue, 5 Aug 2025 15:18:18 +0100 Subject: [PATCH 067/112] net: mvpp2: Cannot test unsigned variable to be negative In phy_info_parse all uses of the variable phyaddr are as an int so declaring as u32 is not useful and prevents the test for an error return from fdtdec_get_int ever detecting an error. Change phyaddr to be an int. This issue was found by Smatch. Signed-off-by: Andrew Goodbody --- drivers/net/mvpp2.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/mvpp2.c b/drivers/net/mvpp2.c index b68d305a0dc..3a3510f603a 100644 --- a/drivers/net/mvpp2.c +++ b/drivers/net/mvpp2.c @@ -4734,7 +4734,7 @@ static int phy_info_parse(struct udevice *dev, struct mvpp2_port *port) int port_node = dev_of_offset(dev); int phy_node; u32 id; - u32 phyaddr = 0; + int phyaddr = 0; int fixed_link = 0; int ret; From c6561a467c9f9a77717ddc2ef296866a4d8a6843 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Tue, 5 Aug 2025 15:18:19 +0100 Subject: [PATCH 068/112] net: mvpp2: Use field just assigned in error test In mvpp2_probe the code attempts to get a value for "gop-port-id" and assigns it to port->gop_id but it then tests port->id for being equal to -1. That is an impossible test as port->id is a field of type u8 so cannot be negative. Change the test to port->gop_id. This issue was found by Smatch. Signed-off-by: Andrew Goodbody --- drivers/net/mvpp2.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/mvpp2.c b/drivers/net/mvpp2.c index 3a3510f603a..f9e979c4d58 100644 --- a/drivers/net/mvpp2.c +++ b/drivers/net/mvpp2.c @@ -5353,7 +5353,7 @@ static int mvpp2_probe(struct udevice *dev) } else { port->gop_id = fdtdec_get_int(gd->fdt_blob, dev_of_offset(dev), "gop-port-id", -1); - if (port->id == -1) { + if (port->gop_id == -1) { dev_err(dev, "missing gop-port-id value\n"); return -EINVAL; } From 6bc6fec3b33f3c14f14493783db9258ac9938062 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Tue, 5 Aug 2025 15:53:34 +0100 Subject: [PATCH 069/112] net: octeontx2: Restore default value for err In nix_lf_setup there is a default value assigned to err in case an error is detected. However this default value will be overwritten in the for loop so that later code does not return an error code from the function. Add a new assignment to restore err to the default error code. This issue was found by Smatch. Signed-off-by: Andrew Goodbody --- drivers/net/octeontx2/nix.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/drivers/net/octeontx2/nix.c b/drivers/net/octeontx2/nix.c index f596b6bca87..87d1f7a5dbf 100644 --- a/drivers/net/octeontx2/nix.c +++ b/drivers/net/octeontx2/nix.c @@ -298,6 +298,8 @@ int nix_lf_setup(struct nix *nix) goto error; } + err = -1; + /* Alloc memory for Qints HW contexts */ nix->qint_base = nix_memalloc(nix_af->qints, nix_af->qint_ctx_sz, "Qint CTX"); From 425f9839f3c2922a36efaefa53833f0abe681be0 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Tue, 5 Aug 2025 15:53:35 +0100 Subject: [PATCH 070/112] net: octeontx2: NULL check before dereference In rvu_af_init if the code fails to allocate memory for nix_af it will take the error path with nix_af == NULL which will dereference nix_af. Add the appropriate NULL check. This issue was found by Smatch. Signed-off-by: Andrew Goodbody --- drivers/net/octeontx2/rvu_af.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/octeontx2/rvu_af.c b/drivers/net/octeontx2/rvu_af.c index 0d3a9ffe9ee..7bdfbc52e3b 100644 --- a/drivers/net/octeontx2/rvu_af.c +++ b/drivers/net/octeontx2/rvu_af.c @@ -114,7 +114,7 @@ struct nix_af *rvu_af_init(struct rvu_af *rvu_af) return nix_af; error: - if (nix_af->npa_af) { + if (nix_af && nix_af->npa_af) { free(nix_af->npa_af); memset(nix_af, 0, sizeof(*nix_af)); } From 512be8979666a9c62e5ffb8f331d6cd3052623a4 Mon Sep 17 00:00:00 2001 From: Jerome Forissier Date: Fri, 18 Jul 2025 12:48:48 +0200 Subject: [PATCH 071/112] net: introduce CONFIG_DNS Introduce the DNS Kconfig symbol so that various network commands may use host names without the dns command (CMD_DNS) being selected. Signed-off-by: Jerome Forissier CC: E Shattow --- cmd/Kconfig | 2 +- cmd/lwip/dns.c | 108 --------------------------------------- doc/usage/cmd/sntp.rst | 8 +-- doc/usage/cmd/wget.rst | 2 +- include/net-legacy.h | 2 +- net/Kconfig | 8 ++- net/Makefile | 2 +- net/lwip/Makefile | 1 + net/lwip/dns.c | 113 +++++++++++++++++++++++++++++++++++++++++ net/lwip/net-lwip.c | 6 +-- net/net.c | 10 ++-- net/wget.c | 2 +- 12 files changed, 138 insertions(+), 126 deletions(-) create mode 100644 net/lwip/dns.c diff --git a/cmd/Kconfig b/cmd/Kconfig index 1a7dba2a27d..29de857ba7c 100644 --- a/cmd/Kconfig +++ b/cmd/Kconfig @@ -2117,7 +2117,7 @@ config CMD_DHCP config CMD_DNS bool "dns" - select PROT_DNS_LWIP if NET_LWIP + select DNS help Lookup the IP of a hostname diff --git a/cmd/lwip/dns.c b/cmd/lwip/dns.c index b5fccc7433e..3eb698b3f82 100644 --- a/cmd/lwip/dns.c +++ b/cmd/lwip/dns.c @@ -2,115 +2,7 @@ /* Copyright (C) 2024 Linaro Ltd. */ #include -#include -#include -#include -#include #include -#include U_BOOT_CMD(dns, 3, 1, do_dns, "lookup the IP of a hostname", "hostname [envvar]"); - -#define DNS_RESEND_MS 1000 -#define DNS_TIMEOUT_MS 10000 - -struct dns_cb_arg { - ip_addr_t host_ipaddr; - const char *var; - bool done; -}; - -static void do_dns_tmr(void *arg) -{ - dns_tmr(); -} - -static void dns_cb(const char *name, const ip_addr_t *ipaddr, void *arg) -{ - struct dns_cb_arg *dns_cb_arg = arg; - char *ipstr = ip4addr_ntoa(ipaddr); - - dns_cb_arg->done = true; - - if (!ipaddr) { - printf("DNS: host not found\n"); - dns_cb_arg->host_ipaddr.addr = 0; - return; - } - - dns_cb_arg->host_ipaddr.addr = ipaddr->addr; - - if (dns_cb_arg->var) - env_set(dns_cb_arg->var, ipstr); -} - -static int dns_loop(struct udevice *udev, const char *name, const char *var) -{ - struct dns_cb_arg dns_cb_arg = { }; - struct netif *netif; - ip_addr_t ipaddr; - ulong start; - int ret; - - dns_cb_arg.var = var; - - netif = net_lwip_new_netif(udev); - if (!netif) - return CMD_RET_FAILURE; - - if (net_lwip_dns_init()) { - net_lwip_remove_netif(netif); - return CMD_RET_FAILURE; - } - - dns_cb_arg.done = false; - - ret = dns_gethostbyname(name, &ipaddr, dns_cb, &dns_cb_arg); - - if (ret == ERR_OK) { - dns_cb(name, &ipaddr, &dns_cb_arg); - } else if (ret == ERR_INPROGRESS) { - start = get_timer(0); - sys_timeout(DNS_RESEND_MS, do_dns_tmr, NULL); - do { - net_lwip_rx(udev, netif); - if (dns_cb_arg.done) - break; - if (ctrlc()) { - printf("\nAbort\n"); - break; - } - } while (get_timer(start) < DNS_TIMEOUT_MS); - sys_untimeout(do_dns_tmr, NULL); - } - - net_lwip_remove_netif(netif); - - if (dns_cb_arg.done && dns_cb_arg.host_ipaddr.addr != 0) { - if (!var) - printf("%s\n", ipaddr_ntoa(&ipaddr)); - return CMD_RET_SUCCESS; - } - - return CMD_RET_FAILURE; -} - -int do_dns(struct cmd_tbl *cmdtp, int flag, int argc, char *const argv[]) -{ - char *name; - char *var = NULL; - - if (argc == 1 || argc > 3) - return CMD_RET_USAGE; - - name = argv[1]; - - if (argc == 3) - var = argv[2]; - - if (net_lwip_eth_start() < 0) - return CMD_RET_FAILURE; - - return dns_loop(eth_get_dev(), name, var); -} diff --git a/doc/usage/cmd/sntp.rst b/doc/usage/cmd/sntp.rst index d97f83053f7..2046828130d 100644 --- a/doc/usage/cmd/sntp.rst +++ b/doc/usage/cmd/sntp.rst @@ -12,7 +12,7 @@ Synopsis :: sntp [serverip] - sntp [servername] # NET_LWIP=y && CMD_DNS=y only + sntp [servername] # NET_LWIP=y && DNS=y only Description @@ -27,8 +27,8 @@ The address of the NTP server does not need to be given if the DHCP server provides one. The legacy network stack (`CONFIG_NET=y`) can only use the first NTP server provided in the `ntp-servers` DHCP option. -When the network stack is lwIP (`CONFIG_NET_LWIP=y`) and the dns command -is enabled (`CONFIG_CMD_DNS=y`), then the sntp command accepts a server +When the network stack is lwIP (`CONFIG_NET_LWIP=y`) and DNS resolution +is enabled (`CONFIG_DNS=y`), then the sntp command accepts a server name as an argument. The network time is sent as UTC. So, if you want to set the RTC to any local @@ -61,7 +61,7 @@ Examples => date Date: 2025-06-16 (Monday) Time: 17:19:57 -With `CONFIG_NET_LWIP=y` and `CONFIG_CMD_DNS=y`: +With `CONFIG_NET_LWIP=y` and `CONFIG_DNS=y`: :: diff --git a/doc/usage/cmd/wget.rst b/doc/usage/cmd/wget.rst index 06df2842549..8feda0248b2 100644 --- a/doc/usage/cmd/wget.rst +++ b/doc/usage/cmd/wget.rst @@ -38,7 +38,7 @@ address memory address for the data downloaded host - IP address (or host name if `CONFIG_CMD_DNS` is enabled) of the HTTP + IP address (or host name if `CONFIG_DNS` is enabled) of the HTTP server, defaults to the value of environment variable *serverip*. path diff --git a/include/net-legacy.h b/include/net-legacy.h index 050fc352920..9564e97d238 100644 --- a/include/net-legacy.h +++ b/include/net-legacy.h @@ -315,7 +315,7 @@ extern u32 net_boot_file_size; /* Boot file size in blocks as reported by the DHCP server */ extern u32 net_boot_file_expected_size_in_blocks; -#if defined(CONFIG_CMD_DNS) +#if defined(CONFIG_DNS) extern char *net_dns_resolve; /* The host to resolve */ extern char *net_dns_env_var; /* the env var to put the ip into */ #endif diff --git a/net/Kconfig b/net/Kconfig index 24508026200..40ec6bbce76 100644 --- a/net/Kconfig +++ b/net/Kconfig @@ -244,11 +244,17 @@ config NET_RANDOM_ETHADDR generated. It will be saved to the appropriate environment variable, too. +config DNS + bool "Enable DNS resolutions" + select PROT_DNS_LWIP if NET_LWIP + help + Selecting this will allow the network stack to use server names + in addition to IP addresses. + config WGET bool "Enable wget" select PROT_TCP if NET select PROT_TCP_LWIP if NET_LWIP - select PROT_DNS_LWIP if NET_LWIP help Selecting this will enable wget, an interface to send HTTP requests via the network stack. diff --git a/net/Makefile b/net/Makefile index d63f62b7c8a..468820186cf 100644 --- a/net/Makefile +++ b/net/Makefile @@ -10,7 +10,7 @@ ifeq ($(CONFIG_NET),y) obj-$(CONFIG_NET) += arp.o obj-$(CONFIG_CMD_BOOTP) += bootp.o obj-$(CONFIG_CMD_CDP) += cdp.o -obj-$(CONFIG_CMD_DNS) += dns.o +obj-$(CONFIG_DNS) += dns.o obj-$(CONFIG_CMD_LINK_LOCAL) += link_local.o obj-$(CONFIG_IPV6) += ndisc.o obj-$(CONFIG_$(PHASE_)DM_ETH) += net.o diff --git a/net/lwip/Makefile b/net/lwip/Makefile index 09c3b3511a4..1b48ae4d508 100644 --- a/net/lwip/Makefile +++ b/net/lwip/Makefile @@ -2,6 +2,7 @@ ccflags-y += -I$(srctree)/lib/lwip/lwip/src/include -I$(srctree)/lib/lwip/u-boot obj-$(CONFIG_$(PHASE_)DM_ETH) += net-lwip.o obj-$(CONFIG_CMD_DHCP) += dhcp.o +obj-$(CONFIG_DNS) += dns.o obj-$(CONFIG_LWIP_ICMP_SHOW_UNREACH) += icmp_unreach.o obj-$(CONFIG_CMD_TFTPBOOT) += tftp.o obj-$(CONFIG_WGET) += wget.o diff --git a/net/lwip/dns.c b/net/lwip/dns.c new file mode 100644 index 00000000000..9964003195f --- /dev/null +++ b/net/lwip/dns.c @@ -0,0 +1,113 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* Copyright (C) 2024 Linaro Ltd. */ + +#include +#include +#include +#include +#include +#include +#include + +#define DNS_RESEND_MS 1000 +#define DNS_TIMEOUT_MS 10000 + +struct dns_cb_arg { + ip_addr_t host_ipaddr; + const char *var; + bool done; +}; + +static void do_dns_tmr(void *arg) +{ + dns_tmr(); +} + +static void dns_cb(const char *name, const ip_addr_t *ipaddr, void *arg) +{ + struct dns_cb_arg *dns_cb_arg = arg; + char *ipstr = ip4addr_ntoa(ipaddr); + + dns_cb_arg->done = true; + + if (!ipaddr) { + printf("DNS: host not found\n"); + dns_cb_arg->host_ipaddr.addr = 0; + return; + } + + dns_cb_arg->host_ipaddr.addr = ipaddr->addr; + + if (dns_cb_arg->var) + env_set(dns_cb_arg->var, ipstr); +} + +static int dns_loop(struct udevice *udev, const char *name, const char *var) +{ + struct dns_cb_arg dns_cb_arg = { }; + struct netif *netif; + ip_addr_t ipaddr; + ulong start; + int ret; + + dns_cb_arg.var = var; + + netif = net_lwip_new_netif(udev); + if (!netif) + return CMD_RET_FAILURE; + + if (net_lwip_dns_init()) { + net_lwip_remove_netif(netif); + return CMD_RET_FAILURE; + } + + dns_cb_arg.done = false; + + ret = dns_gethostbyname(name, &ipaddr, dns_cb, &dns_cb_arg); + + if (ret == ERR_OK) { + dns_cb(name, &ipaddr, &dns_cb_arg); + } else if (ret == ERR_INPROGRESS) { + start = get_timer(0); + sys_timeout(DNS_RESEND_MS, do_dns_tmr, NULL); + do { + net_lwip_rx(udev, netif); + if (dns_cb_arg.done) + break; + if (ctrlc()) { + printf("\nAbort\n"); + break; + } + } while (get_timer(start) < DNS_TIMEOUT_MS); + sys_untimeout(do_dns_tmr, NULL); + } + + net_lwip_remove_netif(netif); + + if (dns_cb_arg.done && dns_cb_arg.host_ipaddr.addr != 0) { + if (!var) + printf("%s\n", ipaddr_ntoa(&ipaddr)); + return CMD_RET_SUCCESS; + } + + return CMD_RET_FAILURE; +} + +int do_dns(struct cmd_tbl *cmdtp, int flag, int argc, char *const argv[]) +{ + char *name; + char *var = NULL; + + if (argc == 1 || argc > 3) + return CMD_RET_USAGE; + + name = argv[1]; + + if (argc == 3) + var = argv[2]; + + if (net_lwip_eth_start() < 0) + return CMD_RET_FAILURE; + + return dns_loop(eth_get_dev(), name, var); +} diff --git a/net/lwip/net-lwip.c b/net/lwip/net-lwip.c index 660ceb10cbe..74cbc7e4bf5 100644 --- a/net/lwip/net-lwip.c +++ b/net/lwip/net-lwip.c @@ -147,7 +147,7 @@ static int get_udev_ipv4_info(struct udevice *dev, ip4_addr_t *ip, */ int net_lwip_dns_init(void) { -#if CONFIG_IS_ENABLED(CMD_DNS) +#if CONFIG_IS_ENABLED(DNS) bool has_server = false; ip_addr_t ns; char *nsenv; @@ -364,7 +364,7 @@ int net_lwip_rx(struct udevice *udev, struct netif *netif) */ int net_lwip_dns_resolve(char *name_or_ip, ip_addr_t *ip) { -#if defined(CONFIG_CMD_DNS) +#if defined(CONFIG_DNS) char *var = "_dnsres"; char *argv[] = { "dns", name_or_ip, var, NULL }; int argc = ARRAY_SIZE(argv) - 1; @@ -373,7 +373,7 @@ int net_lwip_dns_resolve(char *name_or_ip, ip_addr_t *ip) if (ipaddr_aton(name_or_ip, ip)) return 0; -#if defined(CONFIG_CMD_DNS) +#if defined(CONFIG_DNS) if (do_dns(NULL, 0, argc, argv) != CMD_RET_SUCCESS) return -1; diff --git a/net/net.c b/net/net.c index ac9b65c0ca4..f579f6ac5bc 100644 --- a/net/net.c +++ b/net/net.c @@ -114,7 +114,7 @@ #include "bootp.h" #include "cdp.h" #include "dhcpv6.h" -#if defined(CONFIG_CMD_DNS) +#if defined(CONFIG_DNS) #include "dns.h" #endif #include "link_local.h" @@ -287,7 +287,7 @@ static int on_vlan(const char *name, const char *value, enum env_op op, } U_BOOT_ENV_CALLBACK(vlan, on_vlan); -#if defined(CONFIG_CMD_DNS) +#if defined(CONFIG_DNS) static int on_dnsip(const char *name, const char *value, enum env_op op, int flags) { @@ -581,7 +581,7 @@ restart: nc_start(); break; #endif -#if defined(CONFIG_CMD_DNS) +#if defined(CONFIG_DNS) case DNS: dns_start(); break; @@ -1506,7 +1506,7 @@ static int net_check_prereq(enum proto_t protocol) } goto common; #endif -#if defined(CONFIG_CMD_DNS) +#if defined(CONFIG_DNS) case DNS: if (net_dns_server.s_addr == 0) { puts("*** ERROR: DNS server address not given\n"); @@ -1539,7 +1539,7 @@ static int net_check_prereq(enum proto_t protocol) return 1; } #if defined(CONFIG_CMD_PING) || \ - defined(CONFIG_CMD_DNS) || defined(CONFIG_PROT_UDP) + defined(CONFIG_DNS) || defined(CONFIG_PROT_UDP) common: #endif /* Fall through */ diff --git a/net/wget.c b/net/wget.c index 428ee072330..d3642958bf0 100644 --- a/net/wget.c +++ b/net/wget.c @@ -393,7 +393,7 @@ int wget_do_request(ulong dst_addr, char *uri) if (string_to_ip(host_name).s_addr) { s = host_name; } else { -#if IS_ENABLED(CONFIG_CMD_DNS) +#if IS_ENABLED(CONFIG_DNS) net_dns_resolve = host_name; net_dns_env_var = "httpserverip"; if (net_loop(DNS) < 0) { From 46fc56559933777051bcc7b58d06424f1f4af504 Mon Sep 17 00:00:00 2001 From: Jerome Forissier Date: Thu, 24 Jul 2025 18:08:24 +0200 Subject: [PATCH 072/112] lwip: tftp: resend initial request The TFTP implementation does not resend the initial request if there is no response from the server. Since TFTP is based on UDP, there should be a mechanism to deal with unreliable transmissions at this point, similar to what we have for data packets. Therefore, introduce request retransmission. Signed-off-by: Jerome Forissier CC: Venkatesh Abbarapu CC: Michal Simek CC: Ilias Apalodimas --- lib/lwip/lwip/src/apps/tftp/tftp.c | 74 +++++++++++++++++++++++++++++- 1 file changed, 72 insertions(+), 2 deletions(-) diff --git a/lib/lwip/lwip/src/apps/tftp/tftp.c b/lib/lwip/lwip/src/apps/tftp/tftp.c index 63b1e0e0e20..ecb6c55ae11 100644 --- a/lib/lwip/lwip/src/apps/tftp/tftp.c +++ b/lib/lwip/lwip/src/apps/tftp/tftp.c @@ -79,6 +79,14 @@ enum tftp_error { #include +struct tftp_req { + ip_addr_t addr; + u16_t port; + u16_t opcode; + enum tftp_transfer_mode mode; + char* fname; +}; + struct tftp_state { const struct tftp_context *ctx; void *handle; @@ -97,14 +105,33 @@ struct tftp_state { }; static struct tftp_state tftp_state; +static struct tftp_req tftp_req; static void tftp_tmr(void *arg); +static void tftp_req_tmr(void *arg); +static const char *mode_to_string(enum tftp_transfer_mode mode); + +static void +clear_req(void) +{ + ip_addr_set_any(0, &tftp_req.addr); + tftp_req.port = 0; + tftp_req.opcode = 0; + free(tftp_req.fname); + tftp_req.fname = NULL; + tftp_req.mode = 0; + + sys_untimeout(tftp_req_tmr, NULL); +} static void close_handle(void) { + clear_req(); + tftp_state.port = 0; ip_addr_set_any(0, &tftp_state.addr); + tftp_state.retries = 0; if (tftp_state.last_data != NULL) { pbuf_free(tftp_state.last_data); @@ -209,6 +236,12 @@ send_ack(const ip_addr_t *addr, u16_t port, u16_t blknum) return ret; } +static err_t +resend_request(void) +{ + return send_request(&tftp_req.addr, tftp_req.port, tftp_req.opcode, tftp_req.fname, mode_to_string(tftp_req.mode)); +} + static err_t resend_data(const ip_addr_t *addr, u16_t port) { @@ -336,6 +369,9 @@ tftp_recv(void *arg, struct udp_pcb *upcb, struct pbuf *p, const ip_addr_t *addr tftp_state.last_pkt = tftp_state.timer; tftp_state.retries = 0; + if (tftp_req.fname) + clear_req(); + switch (opcode) { case PP_HTONS(TFTP_RRQ): /* fall through */ case PP_HTONS(TFTP_WRQ): { @@ -542,6 +578,26 @@ tftp_tmr(void *arg) } } +static void +tftp_req_tmr(void *arg) +{ + if (tftp_state.handle == NULL) { + return; + } + + sys_timeout(TFTP_TIMER_MSECS, tftp_req_tmr, NULL); + + if (tftp_state.retries < TFTP_MAX_RETRIES) { + LWIP_DEBUGF(TFTP_DEBUG | LWIP_DBG_STATE, ("tftp: req timeout, retrying\n")); + resend_request(); + tftp_state.retries++; + } else { + LWIP_DEBUGF(TFTP_DEBUG | LWIP_DBG_STATE, ("tftp: req timeout\n")); + tftp_state.ctx->error(tftp_state.handle, -1, "Request timeout", strlen("Request timeout")); + close_handle(); + } +} + /** * Initialize TFTP client/server. * @param mode TFTP mode (client/server) @@ -637,6 +693,20 @@ mode_to_string(enum tftp_transfer_mode mode) return NULL; } +err_t +start_send_requests(const ip_addr_t *addr, u16_t port, u16_t opcode, const char* fname, enum tftp_transfer_mode mode) +{ + tftp_req.addr = *addr; + tftp_req.port = port; + tftp_req.opcode = opcode; + tftp_req.fname = strdup(fname); + tftp_req.mode = mode; + if (!tftp_req.fname) + return ERR_MEM; + sys_timeout(TFTP_TIMER_MSECS, tftp_req_tmr, NULL); + return resend_request(); +} + err_t tftp_get(void* handle, const ip_addr_t *addr, u16_t port, const char* fname, enum tftp_transfer_mode mode) { @@ -647,7 +717,7 @@ tftp_get(void* handle, const ip_addr_t *addr, u16_t port, const char* fname, enu tftp_state.handle = handle; tftp_state.blknum = 1; tftp_state.mode_write = 1; /* We want to receive data */ - return send_request(addr, port, TFTP_RRQ, fname, mode_to_string(mode)); + return start_send_requests(addr, port, TFTP_RRQ, fname, mode); } err_t @@ -660,7 +730,7 @@ tftp_put(void* handle, const ip_addr_t *addr, u16_t port, const char* fname, enu tftp_state.handle = handle; tftp_state.blknum = 1; tftp_state.mode_write = 0; /* We want to send data */ - return send_request(addr, port, TFTP_WRQ, fname, mode_to_string(mode)); + return start_send_requests(addr, port, TFTP_WRQ, fname, mode); } #endif /* LWIP_UDP */ From 8f80e305792419000e141828cef7539eb3180fc9 Mon Sep 17 00:00:00 2001 From: Jerome Forissier Date: Fri, 1 Aug 2025 10:12:20 +0200 Subject: [PATCH 073/112] lwip: sntp: remove redundant sys_check_timeouts() Now that sys_check_timeouts() is called in net_lwip_rx(), there is no need to call it from the SNTP receive loop. Remove the redundant call. Signed-off-by: Jerome Forissier --- cmd/lwip/sntp.c | 1 - 1 file changed, 1 deletion(-) diff --git a/cmd/lwip/sntp.c b/cmd/lwip/sntp.c index ae02bb11040..608345c873b 100644 --- a/cmd/lwip/sntp.c +++ b/cmd/lwip/sntp.c @@ -79,7 +79,6 @@ static int sntp_loop(struct udevice *udev, ip_addr_t *srvip) sys_timeout(SNTP_TIMEOUT, no_response, NULL); while (sntp_state == NOT_DONE) { net_lwip_rx(udev, netif); - sys_check_timeouts(); if (ctrlc()) { printf("\nAbort\n"); sntp_state = ABORTED; From 2cb9fef65bbb7535c1e27cef3122bb0b43e38b68 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Fri, 1 Aug 2025 12:59:40 +0100 Subject: [PATCH 074/112] net: cortina_ni: Fix typo accessing wrong phy In ca_phy_probe when checking for an external phy it uses a field from the internal phy due to what is assumed to be a copy/paste typo. Make the obvious fix to use the field from the external phy. This issue was found by Smatch. Signed-off-by: Andrew Goodbody --- drivers/net/cortina_ni.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/cortina_ni.c b/drivers/net/cortina_ni.c index 79026882800..21b7089176c 100644 --- a/drivers/net/cortina_ni.c +++ b/drivers/net/cortina_ni.c @@ -499,7 +499,7 @@ static int ca_phy_probe(struct udevice *dev) dev, priv->phy_interface); if (ext_phydev) { ext_phydev->supported &= PHY_GBIT_FEATURES; - ext_phydev->advertising = int_phydev->supported; + ext_phydev->advertising = ext_phydev->supported; phy_config(ext_phydev); } else { printf("CA NI %s: There is no external phy device\n", __func__); From 90c05f68fcab57d669233033d34e52b8d55d57dd Mon Sep 17 00:00:00 2001 From: Jerome Forissier Date: Mon, 4 Aug 2025 14:51:01 +0200 Subject: [PATCH 075/112] net: lwip: ping: set net_try_count to 1 The legacy network stack sets net_try_count to 1 at the beginning of the net_loop() function. This is required for net_start_again() to work properly. Therefore, set the variable accordingly in the do_ping() function when NET_LWIP=y. This fixes an issue where a ping to an unreachable destination would run twice on the same network device. For example with qemu_arm64_lwip_defconfig: => dhcp DHCP client bound to address 10.0.2.15 (3 ms) => ping 10.0.0.1 Using virtio-net#32 device ping failed; host 10.0.0.1 is not alive Using virtio-net#32 device ping failed; host 10.0.0.1 is not alive => QEMU: Terminated Signed-off-by: Jerome Forissier --- cmd/lwip/ping.c | 1 + include/net-lwip.h | 2 ++ net/lwip/net-lwip.c | 2 +- 3 files changed, 4 insertions(+), 1 deletion(-) diff --git a/cmd/lwip/ping.c b/cmd/lwip/ping.c index 87f8e958e48..6d090fc530d 100644 --- a/cmd/lwip/ping.c +++ b/cmd/lwip/ping.c @@ -170,6 +170,7 @@ int do_ping(struct cmd_tbl *cmdtp, int flag, int argc, char *const argv[]) if (net_lwip_dns_resolve(argv[1], &addr)) return CMD_RET_USAGE; + net_try_count = 1; restart: if (net_lwip_eth_start() < 0 || ping_loop(eth_get_dev(), &addr) < 0) { if (net_start_again() == 0) diff --git a/include/net-lwip.h b/include/net-lwip.h index f54f23471f1..e88e2186635 100644 --- a/include/net-lwip.h +++ b/include/net-lwip.h @@ -18,6 +18,8 @@ extern size_t cacert_size; extern enum auth_mode cacert_auth_mode; extern bool cacert_initialized; +extern int net_try_count; + int set_cacert_builtin(void); enum proto_t { diff --git a/net/lwip/net-lwip.c b/net/lwip/net-lwip.c index 74cbc7e4bf5..1a70cedfb58 100644 --- a/net/lwip/net-lwip.c +++ b/net/lwip/net-lwip.c @@ -27,7 +27,7 @@ #if defined(CONFIG_API) || defined(CONFIG_EFI_LOADER) void (*push_packet)(void *, int len) = 0; #endif -static int net_try_count; +int net_try_count; static int net_restarted; int net_restart_wrap; static uchar net_pkt_buf[(PKTBUFSRX) * PKTSIZE_ALIGN + PKTALIGN]; From 5deb50f749659746233e08060b457c9cf9986f9c Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Tue, 5 Aug 2025 11:34:29 +0100 Subject: [PATCH 076/112] net: ks8851_mll: Remove unreachable code In ks8851_mll_detect_chip the if..else code detects the case of (val & 0xfff0) != CIDER_ID and returns if found. So testing for this again will always fail and the code is unreachable. Just remove the test and code block. This issue was found by Smatch. Signed-off-by: Andrew Goodbody --- drivers/net/ks8851_mll.c | 5 ----- 1 file changed, 5 deletions(-) diff --git a/drivers/net/ks8851_mll.c b/drivers/net/ks8851_mll.c index cc2e826257a..2c956154d09 100644 --- a/drivers/net/ks8851_mll.c +++ b/drivers/net/ks8851_mll.c @@ -347,11 +347,6 @@ static int ks8851_mll_detect_chip(struct ks_net *ks) debug("Read back KS8851 id 0x%x\n", val); - if ((val & 0xfff0) != CIDER_ID) { - printf(DRIVERNAME ": Unknown chip ID %04x\n", val); - return -1; - } - return 0; } From 783ea37c7b52ae088e8c64581fbe412b5dc9a878 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Mon, 18 Aug 2025 11:44:28 +0100 Subject: [PATCH 077/112] phy: cadence: sierra: Remove variable that is not assigned to In cdns_sierra_pll_bind_of_clocks the variable 'i' is declared but never assigned to before its value is used in a dev_err. Replace clk_names[i] by the name passed to device_bind(), i.e., "pll_mux_clk". With that, the clk_names[] array is unused and can therefore be removed. This issue was found by Smatch. Signed-off-by: Andrew Goodbody [jf: update description] Signed-off-by: Jerome Forissier --- drivers/phy/cadence/phy-cadence-sierra.c | 13 +++---------- 1 file changed, 3 insertions(+), 10 deletions(-) diff --git a/drivers/phy/cadence/phy-cadence-sierra.c b/drivers/phy/cadence/phy-cadence-sierra.c index 2c9d5a12127..bd7ab9d1b77 100644 --- a/drivers/phy/cadence/phy-cadence-sierra.c +++ b/drivers/phy/cadence/phy-cadence-sierra.c @@ -225,11 +225,6 @@ static const struct reg_field pllctrl_lock = static const struct reg_field phy_iso_link_ctrl_1 = REG_FIELD(SIERRA_PHY_ISO_LINK_CTRL, 1, 1); -static const char * const clk_names[] = { - [CDNS_SIERRA_PLL_CMNLC] = "pll_cmnlc", - [CDNS_SIERRA_PLL_CMNLC1] = "pll_cmnlc1", -}; - enum cdns_sierra_cmn_plllc { CMN_PLLLC, CMN_PLLLC1, @@ -602,7 +597,7 @@ static int cdns_sierra_pll_bind_of_clocks(struct cdns_sierra_phy *sp) struct udevice *dev = sp->dev; struct driver *cdns_sierra_clk_drv; struct cdns_sierra_pll_mux_sel *data = pll_clk_mux_sel; - int i, rc; + int rc; cdns_sierra_clk_drv = lists_driver_lookup_name("cdns_sierra_mux_clk"); if (!cdns_sierra_clk_drv) { @@ -612,10 +607,8 @@ static int cdns_sierra_pll_bind_of_clocks(struct cdns_sierra_phy *sp) rc = device_bind(dev, cdns_sierra_clk_drv, "pll_mux_clk", data, dev_ofnode(dev), NULL); - if (rc) { - dev_err(dev, "cannot bind driver for clock %s\n", - clk_names[i]); - } + if (rc) + dev_err(dev, "cannot bind driver for clock pll_mux_clk\n"); return 0; } From c4526c390a3c4ea1c4f244b6436ebbb74902769a Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Mon, 18 Aug 2025 11:44:29 +0100 Subject: [PATCH 078/112] phy: cadence: torrent: Set an error code for return In cdns_torrent_phy_probe the test for too many lanes configured does not set an error code before taking the error path. This could lead to a silent failure if the calling code does not detect the error. Add the code to return -EINVAL in this case. This issue was found by Smatch. Signed-off-by: Andrew Goodbody --- drivers/phy/cadence/phy-cadence-torrent.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/phy/cadence/phy-cadence-torrent.c b/drivers/phy/cadence/phy-cadence-torrent.c index 1f566d082f9..28fe026223c 100644 --- a/drivers/phy/cadence/phy-cadence-torrent.c +++ b/drivers/phy/cadence/phy-cadence-torrent.c @@ -719,6 +719,7 @@ static int cdns_torrent_phy_probe(struct udevice *dev) if (total_num_lanes > MAX_NUM_LANES) { dev_err(dev, "Invalid lane configuration\n"); + ret = -EINVAL; goto put_lnk_rst; } From b34b18a2c936c02c42c1c66bee274fcc96e25c57 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Fri, 8 Aug 2025 12:32:36 +0100 Subject: [PATCH 079/112] ram: renesas: dbsc5: Fix off by 1 errors In dbsc5_read_vref_training the arrays dvw_min_byte0_table and dvw_min_byte1_table have 128 elements per channel. The variable vref_stop_index is limited to be a maximum of 128. This means that the index used to access the arrays must use a test of '< vref_stop_index' rather than '<= vref_stop_index' in order to prevent out of bounds accesses to the arrays. This issue was found by Smatch. Signed-off-by: Andrew Goodbody Reviewed-by: Marek Vasut Tested-by: Marek Vasut --- drivers/ram/renesas/dbsc5/dram.c | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/drivers/ram/renesas/dbsc5/dram.c b/drivers/ram/renesas/dbsc5/dram.c index ca8a7fb4783..3ed02e11f9e 100644 --- a/drivers/ram/renesas/dbsc5/dram.c +++ b/drivers/ram/renesas/dbsc5/dram.c @@ -3735,7 +3735,7 @@ static u32 dbsc5_read_vref_training(struct udevice *dev) if (vref_stop_index > 0x80) return 0; - for (i = 0; i <= vref_stop_index; i++) { + for (i = 0; i < vref_stop_index; i++) { r_foreach_vch(dev, ch) { reg = dbsc5_ddr_getval_slice(dev, ch, 0, PHY_PAD_VREF_CTRL_DQ); reg &= 0xF << 10; @@ -3819,7 +3819,7 @@ static u32 dbsc5_read_vref_training(struct udevice *dev) best_vref_byte0_index = 0; best_dvw_min_byte0 = dvw_min_byte0_table[ch][0]; - for (i = 0; i <= vref_stop_index; i++) { + for (i = 0; i < vref_stop_index; i++) { if (best_dvw_min_byte0 >= dvw_min_byte0_table[ch][i]) continue; @@ -3858,7 +3858,7 @@ static u32 dbsc5_read_vref_training(struct udevice *dev) vref_outlier = dbsc5_ddr_getval_slice(dev, ch, 0, PHY_RDLVL_VREF_OUTLIER); best_upper_vref = best_vref_byte0; outlier_cnt = vref_outlier; - for (i = best_vref_byte0_index; i <= vref_stop_index; i++) { + for (i = best_vref_byte0_index; i < vref_stop_index; i++) { if (dvw_min_byte0_table[ch][i] <= 0) break; @@ -3879,7 +3879,7 @@ static u32 dbsc5_read_vref_training(struct udevice *dev) best_vref_byte1 = vref_start; best_vref_byte1_index = 0; best_dvw_min_byte1 = dvw_min_byte1_table[ch][0]; - for (i = 0; i <= vref_stop_index; i++) { + for (i = 0; i < vref_stop_index; i++) { if (best_dvw_min_byte1 >= dvw_min_byte1_table[ch][i]) continue; @@ -3918,7 +3918,7 @@ static u32 dbsc5_read_vref_training(struct udevice *dev) vref_outlier = dbsc5_ddr_getval_slice(dev, ch, 1, PHY_RDLVL_VREF_OUTLIER); best_upper_vref = best_vref_byte1; outlier_cnt = vref_outlier; - for (i = best_vref_byte1_index; i <= vref_stop_index; i++) { + for (i = best_vref_byte1_index; i < vref_stop_index; i++) { if (dvw_min_byte1_table[ch][i] <= 0) break; From 074066790c7f726f149c1974e01b8b3f75738c73 Mon Sep 17 00:00:00 2001 From: Martin Schwan Date: Wed, 13 Aug 2025 13:54:05 +0200 Subject: [PATCH 080/112] bootstd: rauc: Fix segfault when cleaning up slots Fix a segfault when cleaning up the slots from the private struct. This fault was generated by accessing a member of a null pointer. Signed-off-by: Martin Schwan Tested-by: Wadim Egorov --- boot/bootmeth_rauc.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/boot/bootmeth_rauc.c b/boot/bootmeth_rauc.c index cc6180221ed..a27c85c4ff0 100644 --- a/boot/bootmeth_rauc.c +++ b/boot/bootmeth_rauc.c @@ -187,7 +187,7 @@ static int distro_rauc_read_bootflow(struct udevice *dev, struct bootflow *bflow ret = distro_rauc_scan_parts(bflow); if (ret < 0) { - for (i = 0; priv->slots[i]->name; i++) { + for (i = 0; priv->slots[i]; i++) { free(priv->slots[i]->name); free(priv->slots[i]); } From b389967f9a624b35c163767c34919cbdcd4e0917 Mon Sep 17 00:00:00 2001 From: Martin Schwan Date: Wed, 13 Aug 2025 13:54:06 +0200 Subject: [PATCH 081/112] bootstd: rauc: Don't null bootflow->bootmeth_priv Don't null bootflow->bootmeth_priv, as the private struct is freed later on by the bootflow. Signed-off-by: Martin Schwan Tested-by: Wadim Egorov --- boot/bootmeth_rauc.c | 1 - 1 file changed, 1 deletion(-) diff --git a/boot/bootmeth_rauc.c b/boot/bootmeth_rauc.c index a27c85c4ff0..c8efdce75b9 100644 --- a/boot/bootmeth_rauc.c +++ b/boot/bootmeth_rauc.c @@ -193,7 +193,6 @@ static int distro_rauc_read_bootflow(struct udevice *dev, struct bootflow *bflow } free(priv); free(boot_order_copy); - bflow->bootmeth_priv = NULL; return ret; } From 302830499d9f0ebec42fe62254429a4d8db6b36c Mon Sep 17 00:00:00 2001 From: Martin Schwan Date: Wed, 13 Aug 2025 13:54:07 +0200 Subject: [PATCH 082/112] bootstd: rauc: Move freeing private struct to its own function Move freeing a distro_rauc_priv struct to a new, separate function for better reuse. Signed-off-by: Martin Schwan Tested-by: Wadim Egorov --- boot/bootmeth_rauc.c | 18 +++++++++++++----- 1 file changed, 13 insertions(+), 5 deletions(-) diff --git a/boot/bootmeth_rauc.c b/boot/bootmeth_rauc.c index c8efdce75b9..f781a7fc0b5 100644 --- a/boot/bootmeth_rauc.c +++ b/boot/bootmeth_rauc.c @@ -52,6 +52,18 @@ struct distro_rauc_priv { struct distro_rauc_slot **slots; }; +static void distro_rauc_priv_free(struct distro_rauc_priv *priv) +{ + int i; + + for (i = 0; priv->slots[i]; i++) { + free(priv->slots[i]->name); + free(priv->slots[i]); + } + free(priv->slots); + free(priv); +} + static struct distro_rauc_slot *get_slot(struct distro_rauc_priv *priv, const char *slot_name) { @@ -187,11 +199,7 @@ static int distro_rauc_read_bootflow(struct udevice *dev, struct bootflow *bflow ret = distro_rauc_scan_parts(bflow); if (ret < 0) { - for (i = 0; priv->slots[i]; i++) { - free(priv->slots[i]->name); - free(priv->slots[i]); - } - free(priv); + distro_rauc_priv_free(priv); free(boot_order_copy); return ret; } From 498e423457a0360c01d976aa21a218995a1bdef8 Mon Sep 17 00:00:00 2001 From: Martin Schwan Date: Wed, 13 Aug 2025 13:54:08 +0200 Subject: [PATCH 083/112] bootstd: rauc: Free private data when booting The private data struct can be freed when loading the boot script, as we don't need the slot information anymore at this point. Signed-off-by: Martin Schwan Tested-by: Wadim Egorov --- boot/bootmeth_rauc.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/boot/bootmeth_rauc.c b/boot/bootmeth_rauc.c index f781a7fc0b5..9c082dabd2b 100644 --- a/boot/bootmeth_rauc.c +++ b/boot/bootmeth_rauc.c @@ -409,6 +409,8 @@ static int distro_rauc_boot(struct udevice *dev, struct bootflow *bflow) if (ret) return log_msg_ret("boot", ret); + distro_rauc_priv_free(priv); + return 0; } From a20dbbb0711ef144703848105dd0500b16ba7eae Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o=20Paulo=20Gon=C3=A7alves?= Date: Mon, 11 Aug 2025 09:57:50 -0300 Subject: [PATCH 084/112] arm: imx: imx9: soc: Fix env location when booting from USB MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit On i.MX9 platforms, when booting from USB, the U-Boot environment is always assumed to be in RAM. However, this causes the boot to hang when `CONFIG_ENV_IS_NOWHERE` is not enabled. The boot also hangs even if the environment is present in another storage media (for example, eMMC). Fix the issue by correctly handling the U-Boot environment's location when booting from USB. Also for i.MX95, set the environment location based on the ENV config and not solely based on the boot device type. Suggested-by: Frieder Schrempf Signed-off-by: João Paulo Gonçalves --- arch/arm/mach-imx/imx9/scmi/soc.c | 13 ++++++++++--- arch/arm/mach-imx/imx9/soc.c | 8 +++++++- 2 files changed, 17 insertions(+), 4 deletions(-) diff --git a/arch/arm/mach-imx/imx9/scmi/soc.c b/arch/arm/mach-imx/imx9/scmi/soc.c index 13f13ca7d10..f973652d0cb 100644 --- a/arch/arm/mach-imx/imx9/scmi/soc.c +++ b/arch/arm/mach-imx/imx9/scmi/soc.c @@ -635,7 +635,8 @@ enum env_location env_get_location(enum env_operation op, int prio) switch (dev) { case QSPI_BOOT: - env_loc = ENVL_SPI_FLASH; + if (IS_ENABLED(CONFIG_ENV_IS_IN_SPI_FLASH)) + env_loc = ENVL_SPI_FLASH; break; case SD1_BOOT: case SD2_BOOT: @@ -643,10 +644,16 @@ enum env_location env_get_location(enum env_operation op, int prio) case MMC1_BOOT: case MMC2_BOOT: case MMC3_BOOT: - env_loc = ENVL_MMC; + if (IS_ENABLED(CONFIG_ENV_IS_IN_MMC)) + env_loc = ENVL_MMC; break; default: - env_loc = ENVL_NOWHERE; + if (IS_ENABLED(CONFIG_ENV_IS_NOWHERE)) + env_loc = ENVL_NOWHERE; + else if (IS_ENABLED(CONFIG_ENV_IS_IN_SPI_FLASH)) + env_loc = ENVL_SPI_FLASH; + else if (IS_ENABLED(CONFIG_ENV_IS_IN_MMC)) + env_loc = ENVL_MMC; break; } diff --git a/arch/arm/mach-imx/imx9/soc.c b/arch/arm/mach-imx/imx9/soc.c index 9fb82644f12..3f7dafdcce5 100644 --- a/arch/arm/mach-imx/imx9/soc.c +++ b/arch/arm/mach-imx/imx9/soc.c @@ -809,7 +809,13 @@ enum env_location env_get_location(enum env_operation op, int prio) return ENVL_FAT; return ENVL_NOWHERE; default: - return ENVL_NOWHERE; + if (IS_ENABLED(CONFIG_ENV_IS_NOWHERE)) + return ENVL_NOWHERE; + else if (IS_ENABLED(CONFIG_ENV_IS_IN_SPI_FLASH)) + return ENVL_SPI_FLASH; + else if (IS_ENABLED(CONFIG_ENV_IS_IN_MMC)) + return ENVL_MMC; + return ENVL_UNKNOWN; } } From a7528da151489d87582d70f2628256f4d59e2740 Mon Sep 17 00:00:00 2001 From: Primoz Fiser Date: Tue, 19 Aug 2025 07:39:41 +0200 Subject: [PATCH 085/112] board: phytec: phycore-imx93: Fix EEPROM bus mismatch in SPL Fix PHYTEC EEPROM bus mismatch between SPL and U-Boot proper by enabling CONFIG_SPL_DM_SEQ_ALIAS=y on phyCORE-i.MX93 boards. This way, both the SPL and U-Boot proper will respect the device-tree aliases for I2C devs and use the same I2C bus number for phytec_eeprom_data_setup() function calls. This makes code less confusing and more robust. Fixes an issue apparent since commit 79f3e77133bd ("Subtree merge tag 'v6.16-dts' of dts repo [1] into dts/upstream") where SPL would spew the following error: phytec_eeprom_read: i2c EEPROM not found: -110. phytec_eeprom_data_setup: EEPROM data init failed While later in U-Boot proper, EEPROM would be successfully read out. This happens because Linux device-tree for phyBOARD-Segin-i.MX93 since aforementioned commit enables I2C bus 2 (lpi2c2 is used for audio codec and RTC) which breaks SPL I2C bus number ordering and I2C EEPROM bus is shifted by +1. Now, lets prevent this from happening again by utilizing device-tree aliases also in the SPL. Signed-off-by: Primoz Fiser --- board/phytec/phycore_imx93/spl.c | 3 +-- configs/imx93-phycore_defconfig | 1 + 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/board/phytec/phycore_imx93/spl.c b/board/phytec/phycore_imx93/spl.c index 7b5d38d438f..beaa536c600 100644 --- a/board/phytec/phycore_imx93/spl.c +++ b/board/phytec/phycore_imx93/spl.c @@ -52,8 +52,7 @@ void spl_dram_init(void) int ret; enum phytec_imx93_ddr_eeprom_code ddr_opt = PHYTEC_IMX93_DDR_INVALID; - /* NOTE: In SPL lpi2c3 is mapped to bus 0 */ - ret = phytec_eeprom_data_setup(NULL, 0, EEPROM_ADDR); + ret = phytec_eeprom_data_setup(NULL, 2, EEPROM_ADDR); if (ret && !IS_ENABLED(CONFIG_PHYCORE_IMX93_RAM_TYPE_FIX)) goto out; diff --git a/configs/imx93-phycore_defconfig b/configs/imx93-phycore_defconfig index 6210be64672..af149128ed4 100644 --- a/configs/imx93-phycore_defconfig +++ b/configs/imx93-phycore_defconfig @@ -92,6 +92,7 @@ CONFIG_USE_ETHPRIME=y CONFIG_ETHPRIME="eth1" CONFIG_NET_RANDOM_ETHADDR=y CONFIG_SPL_DM=y +CONFIG_SPL_DM_SEQ_ALIAS=y CONFIG_SPL_CLK_IMX93=y CONFIG_CLK_IMX93=y CONFIG_DFU_MMC=y From cb5f3e4f5288f27c44753503ca6c75bd17d8a1f8 Mon Sep 17 00:00:00 2001 From: Ye Li Date: Wed, 20 Aug 2025 15:08:51 +0200 Subject: [PATCH 086/112] imx: imx93_{evk, frdm, qsb}: Fix conflict SPL early malloc address MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Because the early malloc pool size is set to 0x18000, so using this start address may cause conflict with ATF, then corrupt the heap data. So we delete the definition to use the default early malloc pool from CONFIG_SPL_STACK to avoid any conflict Signed-off-by: Ye Li Cherry picked from nxp-imx/uboot-imx commit 1ba675df122627a19debe1d807877052705372c6 Jérémie Dautheribes: applied the same patch to the frdm and qsb imx93-based boards Signed-off-by: Jérémie Dautheribes --- include/configs/imx93_evk.h | 4 ---- include/configs/imx93_frdm.h | 4 ---- include/configs/imx93_qsb.h | 4 ---- 3 files changed, 12 deletions(-) diff --git a/include/configs/imx93_evk.h b/include/configs/imx93_evk.h index e7db0161126..ffd72a38bcb 100644 --- a/include/configs/imx93_evk.h +++ b/include/configs/imx93_evk.h @@ -11,10 +11,6 @@ #define CFG_SYS_UBOOT_BASE \ (QSPI0_AMBA_BASE + CONFIG_SYS_MMCSD_RAW_MODE_U_BOOT_SECTOR * 512) -#ifdef CONFIG_XPL_BUILD -#define CFG_MALLOC_F_ADDR 0x204D0000 -#endif - #ifdef CONFIG_ENV_MMC_DEVICE_INDEX #define IMX93_EVK_MMC_ENV_DEV CONFIG_ENV_MMC_DEVICE_INDEX #else diff --git a/include/configs/imx93_frdm.h b/include/configs/imx93_frdm.h index 987fcacb999..c98c10774cb 100644 --- a/include/configs/imx93_frdm.h +++ b/include/configs/imx93_frdm.h @@ -11,10 +11,6 @@ #define CFG_SYS_UBOOT_BASE \ (QSPI0_AMBA_BASE + CONFIG_SYS_MMCSD_RAW_MODE_U_BOOT_SECTOR * 512) -#ifdef CONFIG_XPL_BUILD -#define CFG_MALLOC_F_ADDR 0x204D0000 -#endif - /* Link Definitions */ #define CFG_SYS_INIT_RAM_ADDR 0x80000000 diff --git a/include/configs/imx93_qsb.h b/include/configs/imx93_qsb.h index 5ddc191d17c..a7b94f7ab57 100644 --- a/include/configs/imx93_qsb.h +++ b/include/configs/imx93_qsb.h @@ -9,10 +9,6 @@ #define CFG_SYS_UBOOT_BASE \ (QSPI0_AMBA_BASE + CONFIG_SYS_MMCSD_RAW_MODE_U_BOOT_SECTOR * 512) -#ifdef CONFIG_SPL_BUILD -#define CFG_MALLOC_F_ADDR 0x204D0000 -#endif - #define CFG_SYS_INIT_RAM_ADDR 0x80000000 #define CFG_SYS_INIT_RAM_SIZE 0x200000 From 5d542302230fec4edf6443aac25a442b3245306a Mon Sep 17 00:00:00 2001 From: Dinesh Maniyam Date: Tue, 19 Aug 2025 16:35:09 +0800 Subject: [PATCH 087/112] mtd: nand: cadence: Fix device assignment to avoid warm reset issue MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The driver currently does: mtd->dev->parent = cadence->dev; This works in Linux because `struct mtd_info` embeds a `struct device`, so `mtd->dev` is always valid and its `.parent` can be set. In U-Boot, however, `mtd->dev` is only a pointer to a `struct udevice`. Dereferencing it before assignment is invalid, which breaks the device hierarchy. As a result, consumers relying on `mtd->dev` (e.g. partition parser, reset and re-init paths) operate on a dangling pointer. This leads to failures during warm reset when the NAND device is accessed again. Fix by assigning the device pointer directly: mtd->dev = cadence->dev; This matches U-Boot’s device model, preserves a valid hierarchy, and resolves the warm reset issue on Cadence NAND. Fixes: ebc41cad ("drivers: mtd: nand: Add driver for Cadence Nand") Signed-off-by: Dinesh Maniyam Signed-off-by: Michael Trimarchi --- drivers/mtd/nand/raw/cadence_nand.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/mtd/nand/raw/cadence_nand.c b/drivers/mtd/nand/raw/cadence_nand.c index 27aa7f97a45..4771440d1de 100644 --- a/drivers/mtd/nand/raw/cadence_nand.c +++ b/drivers/mtd/nand/raw/cadence_nand.c @@ -2196,7 +2196,7 @@ static int cadence_nand_chip_init(struct cadence_nand_info *cadence, ofnode node chip->controller = &cadence->controller; nand_set_flash_node(chip, node); mtd = nand_to_mtd(chip); - mtd->dev->parent = cadence->dev; + mtd->dev = cadence->dev; chip->options |= NAND_BUSWIDTH_AUTO; chip->select_chip = cadence_nand_select_chip; From 590c28b378ff76022b910accfb8ff7c56095f4f8 Mon Sep 17 00:00:00 2001 From: david regan Date: Thu, 14 Aug 2025 11:04:55 -0700 Subject: [PATCH 088/112] cmd: nand: bug fix MTD_OOB_AUTO to MTD_OPS_AUTO_OOB bug fix MTD_OOB_AUTO to MTD_OPS_AUTO_OOB since MTD_OOB_AUTO does not exist Fixes: dfe64e2c8973 ("mtd: resync with Linux-3.7.1") Signed-off-by: david regan Signed-off-by: Michael Trimarchi --- cmd/nand.c | 2 +- env/nand.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/cmd/nand.c b/cmd/nand.c index 2f785deeb7f..e09e145bc2d 100644 --- a/cmd/nand.c +++ b/cmd/nand.c @@ -412,7 +412,7 @@ int do_nand_env_oob(struct cmd_tbl *cmdtp, int argc, char *const argv[]) } ops.datbuf = NULL; - ops.mode = MTD_OOB_AUTO; + ops.mode = MTD_OPS_AUTO_OOB; ops.ooboffs = 0; ops.ooblen = ENV_OFFSET_SIZE; ops.oobbuf = (void *) oob_buf; diff --git a/env/nand.c b/env/nand.c index fdaa903cd61..709f8411eb6 100644 --- a/env/nand.c +++ b/env/nand.c @@ -275,7 +275,7 @@ int get_nand_env_oob(struct mtd_info *mtd, unsigned long *result) int ret; ops.datbuf = NULL; - ops.mode = MTD_OOB_AUTO; + ops.mode = MTD_OPS_AUTO_OOB; ops.ooboffs = 0; ops.ooblen = ENV_OFFSET_SIZE; ops.oobbuf = (void *)oob_buf; From 7ec4e91b2f3782530157766a9fc46d0eb27fae3a Mon Sep 17 00:00:00 2001 From: david regan Date: Thu, 14 Aug 2025 11:04:56 -0700 Subject: [PATCH 089/112] cmd: nand: more descriptive help info nand read/write raw change 'count' to 'pages' since count is ambiguous Signed-off-by: david regan Signed-off-by: Michael Trimarchi --- cmd/nand.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/cmd/nand.c b/cmd/nand.c index e09e145bc2d..cb2a61a2e57 100644 --- a/cmd/nand.c +++ b/cmd/nand.c @@ -1026,8 +1026,8 @@ U_BOOT_LONGHELP(nand, "nand write - addr off|partition size\n" " read/write 'size' bytes starting at offset 'off'\n" " to/from memory address 'addr', skipping bad blocks.\n" - "nand read.raw - addr off|partition [count]\n" - "nand write.raw[.noverify] - addr off|partition [count]\n" + "nand read.raw - addr off|partition [pages]\n" + "nand write.raw[.noverify] - addr off|partition [pages]\n" " Use read.raw/write.raw to avoid ECC and access the flash as-is.\n" #ifdef CONFIG_CMD_NAND_TRIMFFS "nand write.trimffs - addr off|partition size\n" From b5ce63e1350f94b51986765e8bd56f45d16af650 Mon Sep 17 00:00:00 2001 From: david regan Date: Thu, 14 Aug 2025 11:04:57 -0700 Subject: [PATCH 090/112] cmd: nand: nand dump display update show characters with nand dump similar to md along with offset into NAND Signed-off-by: david regan Signed-off-by: Michael Trimarchi --- cmd/nand.c | 25 +++++++------------------ 1 file changed, 7 insertions(+), 18 deletions(-) diff --git a/cmd/nand.c b/cmd/nand.c index cb2a61a2e57..832e990108c 100644 --- a/cmd/nand.c +++ b/cmd/nand.c @@ -37,6 +37,7 @@ #include #include #include +#include #include "legacy-mtd-utils.h" @@ -198,30 +199,18 @@ static int nand_dump(struct mtd_info *mtd, ulong off, int only_oob, ret = 1; goto free_all; } - printf("Page %08lx dump:\n", off); + printf("\nPage at offset %08lx dump:\n", off); if (!only_oob) { - i = mtd->writesize >> 4; + i = mtd->writesize; p = datbuf; - - while (i--) { - printf("\t%02x %02x %02x %02x %02x %02x %02x %02x" - " %02x %02x %02x %02x %02x %02x %02x %02x\n", - p[0], p[1], p[2], p[3], p[4], p[5], p[6], p[7], - p[8], p[9], p[10], p[11], p[12], p[13], p[14], - p[15]); - p += 16; - } + print_buffer(off, p, 1, i, 16); } - puts("OOB:\n"); - i = mtd->oobsize >> 3; + puts("\nOOB:\n"); + i = mtd->oobsize; p = oobbuf; - while (i--) { - printf("\t%02x %02x %02x %02x %02x %02x %02x %02x\n", - p[0], p[1], p[2], p[3], p[4], p[5], p[6], p[7]); - p += 8; - } + print_buffer(0, p, 1, i, 8); free_all: free(oobbuf); From bb5d3a7a1c83cca588b5795630bf8fb3db950e5e Mon Sep 17 00:00:00 2001 From: david regan Date: Thu, 14 Aug 2025 11:04:58 -0700 Subject: [PATCH 091/112] cmd: nand: nand dump with ecc option option to show nand dump data ecc corrected as opposed to just raw Signed-off-by: david regan Signed-off-by: Michael Trimarchi --- cmd/nand.c | 25 ++++++++++++++++++------- 1 file changed, 18 insertions(+), 7 deletions(-) diff --git a/cmd/nand.c b/cmd/nand.c index 832e990108c..b5678b0a008 100644 --- a/cmd/nand.c +++ b/cmd/nand.c @@ -160,7 +160,7 @@ free_memory: } static int nand_dump(struct mtd_info *mtd, ulong off, int only_oob, - int repeat) + int ecc, int repeat) { int i; u_char *datbuf, *oobbuf, *p; @@ -192,12 +192,16 @@ static int nand_dump(struct mtd_info *mtd, ulong off, int only_oob, ops.oobbuf = oobbuf; ops.len = mtd->writesize; ops.ooblen = mtd->oobsize; - ops.mode = MTD_OPS_RAW; + if (ecc) + ops.mode = MTD_OPS_PLACE_OOB; + else + ops.mode = MTD_OPS_RAW; i = mtd_read_oob(mtd, addr, &ops); if (i < 0) { - printf("Error (%d) reading page %08lx\n", i, off); + printf("Error reading page at offset %08lx, %d %s\n", + off, i, i == -EUCLEAN ? "correctable" : + "uncorrectable, dumping raw data"); ret = 1; - goto free_all; } printf("\nPage at offset %08lx dump:\n", off); @@ -212,7 +216,6 @@ static int nand_dump(struct mtd_info *mtd, ulong off, int only_oob, p = oobbuf; print_buffer(0, p, 1, i, 8); -free_all: free(oobbuf); free_dat: free(datbuf); @@ -697,11 +700,19 @@ static int do_nand(struct cmd_tbl *cmdtp, int flag, int argc, } if (strncmp(cmd, "dump", 4) == 0) { + int only_oob, ecc; + if (argc < 3) goto usage; + only_oob = !strcmp(&cmd[4], ".oob") || !strcmp(&cmd[4], ".ecc.oob") || + !strcmp(&cmd[4], ".oob.ecc"); + + ecc = !strcmp(&cmd[4], ".ecc") || !strcmp(&cmd[4], ".ecc.oob") || + !strcmp(&cmd[4], ".oob.ecc"); + off = (int)hextoul(argv[2], NULL); - ret = nand_dump(mtd, off, !strcmp(&cmd[4], ".oob"), repeat); + ret = nand_dump(mtd, off, only_oob, ecc, repeat); return ret == 0 ? 1 : 0; } @@ -1031,7 +1042,7 @@ U_BOOT_LONGHELP(nand, "nand erase.part [clean] partition - erase entire mtd partition'\n" "nand erase.chip [clean] - erase entire chip'\n" "nand bad - show bad blocks\n" - "nand dump[.oob] off - dump page\n" + "nand dump[.oob][.ecc] off - dump raw (default) or ecc corrected page at offset\n" #ifdef CONFIG_CMD_NAND_WATCH "nand watch - check an area for bitflips\n" "nand watch.part - check a partition for bitflips\n" From d246e70cf81d0a0d7cc49abd520c93df59d42e16 Mon Sep 17 00:00:00 2001 From: Miquel Raynal Date: Mon, 4 Aug 2025 11:21:37 +0200 Subject: [PATCH 092/112] cmd: mtd: Enable speed benchmarking Linux features a flash_speed speed test from the mtd-utils suite, U-Boot does not. Benchmarks are useful for speed improvement developments as well as troubleshooting or regression testing sometimes. Enable a benchmark option to enable this feature. Example of output on a Nuvoton platform: MA35D1> mtd read nor0 0x81000000 0 0x10000 Reading 65536 byte(s) at offset 0x00000000 MA35D1> mtd read.benchmark nor0 0x81000000 0 0x10000 Reading 65536 byte(s) at offset 0x00000000 Read speed: 3752kiB/s Signed-off-by: Miquel Raynal Signed-off-by: Michael Trimarchi --- cmd/mtd.c | 15 ++++++++++++++- 1 file changed, 14 insertions(+), 1 deletion(-) diff --git a/cmd/mtd.c b/cmd/mtd.c index c25997cfb24..2520b89eed2 100644 --- a/cmd/mtd.c +++ b/cmd/mtd.c @@ -17,6 +17,7 @@ #include #include #include +#include #include #include @@ -466,8 +467,9 @@ static int mtd_special_write_oob(struct mtd_info *mtd, u64 off, static int do_mtd_io(struct cmd_tbl *cmdtp, int flag, int argc, char *const argv[]) { - bool dump, read, raw, woob, write_empty_pages, has_pages = false; + bool dump, read, raw, woob, benchmark, write_empty_pages, has_pages = false; u64 start_off, off, len, remaining, default_len; + unsigned long bench_start, bench_end; struct mtd_oob_ops io_op = {}; uint user_addr = 0, npages; const char *cmd = argv[0]; @@ -490,6 +492,7 @@ static int do_mtd_io(struct cmd_tbl *cmdtp, int flag, int argc, read = dump || !strncmp(cmd, "read", 4); raw = strstr(cmd, ".raw"); woob = strstr(cmd, ".oob"); + benchmark = strstr(cmd, ".benchmark"); write_empty_pages = !has_pages || strstr(cmd, ".dontskipff"); argc -= 2; @@ -559,6 +562,9 @@ static int do_mtd_io(struct cmd_tbl *cmdtp, int flag, int argc, led_activity_blink(); + if (benchmark) + bench_start = timer_get_us(); + /* Loop over the pages to do the actual read/write */ while (remaining) { /* Skip the block if it is bad */ @@ -586,6 +592,13 @@ static int do_mtd_io(struct cmd_tbl *cmdtp, int flag, int argc, io_op.oobbuf += io_op.oobretlen; } + if (benchmark && bench_start) { + bench_end = timer_get_us(); + printf("%s speed: %lukiB/s\n", + read ? "Read" : "Write", + ((io_op.len * 1000000) / (bench_end - bench_start)) / 1024); + } + led_activity_off(); if (!ret && dump) From 6b156c62ced25d3f8aed64c81e471353b56d0f2c Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Thu, 31 Jul 2025 17:21:32 +0100 Subject: [PATCH 093/112] mtd: nand: Do not dereference before NULL check In nanddev_init mtd and memorg are assigned values that dereference nand but this happens before a NULL check for nand. Move the assignments after the NULL check. This issue was found by Smatch. Signed-off-by: Andrew Goodbody Signed-off-by: Michael Trimarchi --- drivers/mtd/nand/core.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/drivers/mtd/nand/core.c b/drivers/mtd/nand/core.c index 472ad0bdefb..01ff6e3befa 100644 --- a/drivers/mtd/nand/core.c +++ b/drivers/mtd/nand/core.c @@ -201,8 +201,8 @@ EXPORT_SYMBOL_GPL(nanddev_mtd_erase); int nanddev_init(struct nand_device *nand, const struct nand_ops *ops, struct module *owner) { - struct mtd_info *mtd = nanddev_to_mtd(nand); - struct nand_memory_organization *memorg = nanddev_get_memorg(nand); + struct mtd_info *mtd; + struct nand_memory_organization *memorg; if (!nand || !ops) return -EINVAL; @@ -210,6 +210,9 @@ int nanddev_init(struct nand_device *nand, const struct nand_ops *ops, if (!ops->erase || !ops->markbad || !ops->isbad) return -EINVAL; + mtd = nanddev_to_mtd(nand); + memorg = nanddev_get_memorg(nand); + if (!memorg->bits_per_cell || !memorg->pagesize || !memorg->pages_per_eraseblock || !memorg->eraseblocks_per_lun || !memorg->planes_per_lun || !memorg->luns_per_target || From edbcf8e3590fb640b4709841605b0a58ef8aa7f1 Mon Sep 17 00:00:00 2001 From: Tim Harvey Date: Wed, 9 Jul 2025 08:24:08 -0700 Subject: [PATCH 094/112] phy: phy-imx8mq-usb: Add support for i.MX95 USB3 PHY Add initial support for i.MX95 USB.30 PHY, which is similar to the i.MX8MQ and i.MX8MP USB PHY. The i.MX95 USB3 PHY has a Type-C Assist block (TCA) consisting of two functional blocks (XBar assist and VBus assist) and is documented in the i.MX95 RM Chapter 163.3.8 Type-C assist (TCA) block. Instead of relying on an external MUX for Type-C plug orientation the XBar can handle the flip internally. Add initial support for i.MX95 by: - allowing the driver to be enabled i.MX95 - resetting the XBar - configuring the TCA in System Configuration mode (which was determined to be necessary to enable the PHY in device-mode) Follow-on support will need to be added to steer the XBar based on either board design (if only one pair is brought out) or if used with a Type-C controller. Signed-off-by: Tim Harvey Tested-by: Alice Guo --- drivers/phy/Kconfig | 6 +-- drivers/phy/phy-imx8mq-usb.c | 91 +++++++++++++++++++++++++++++++++++- 2 files changed, 93 insertions(+), 4 deletions(-) diff --git a/drivers/phy/Kconfig b/drivers/phy/Kconfig index c297fa03ea7..d36a5f00ef8 100644 --- a/drivers/phy/Kconfig +++ b/drivers/phy/Kconfig @@ -289,11 +289,11 @@ config PHY_NPCM_USB Support the USB PHY in NPCM SoCs config PHY_IMX8MQ_USB - bool "NXP i.MX8MQ/i.MX8MP USB PHY Driver" + bool "NXP i.MX8MQ/i.MX8MP/i.MX95 USB PHY Driver" depends on PHY - depends on IMX8MQ || IMX8MP + depends on IMX8MQ || IMX8MP || IMX95 help - Support the USB3.0 PHY in NXP i.MX8MQ or i.MX8MP SoC + Support the USB3.0 PHY in NXP i.MX8MQ, i.MX8MP, and i.MX95 SoC config PHY_IMX8M_PCIE bool "NXP i.MX8MM/i.MX8MP PCIe PHY Driver" diff --git a/drivers/phy/phy-imx8mq-usb.c b/drivers/phy/phy-imx8mq-usb.c index 75763046adc..387db843c50 100644 --- a/drivers/phy/phy-imx8mq-usb.c +++ b/drivers/phy/phy-imx8mq-usb.c @@ -71,9 +71,57 @@ #define PHY_STS0_FSVPLUS BIT(3) #define PHY_STS0_FSVMINUS BIT(2) +#define TCA_CLK_RST 0x00 +#define TCA_CLK_RST_SW BIT(9) +#define TCA_CLK_RST_REF_CLK_EN BIT(1) +#define TCA_CLK_RST_SUSPEND_CLK_EN BIT(0) + +#define TCA_INTR_EN 0x04 +#define TCA_INTR_STS 0x08 + +#define TCA_GCFG 0x10 +#define TCA_GCFG_ROLE_HSTDEV BIT(4) +#define TCA_GCFG_OP_MODE GENMASK(1, 0) +#define TCA_GCFG_OP_MODE_SYSMODE 0 +#define TCA_GCFG_OP_MODE_SYNCMODE 1 + +#define TCA_TCPC 0x14 +#define TCA_TCPC_VALID BIT(4) +#define TCA_TCPC_LOW_POWER_EN BIT(3) +#define TCA_TCPC_ORIENTATION_NORMAL BIT(2) +#define TCA_TCPC_MUX_CONTRL GENMASK(1, 0) +#define TCA_TCPC_MUX_CONTRL_NO_CONN 0 +#define TCA_TCPC_MUX_CONTRL_USB_CONN 1 + +#define TCA_SYSMODE_CFG 0x18 +#define TCA_SYSMODE_TCPC_DISABLE BIT(3) +#define TCA_SYSMODE_TCPC_FLIP BIT(2) + +#define TCA_CTRLSYNCMODE_CFG0 0x20 +#define TCA_CTRLSYNCMODE_CFG1 0x20 + +#define TCA_PSTATE 0x30 +#define TCA_PSTATE_CM_STS BIT(4) +#define TCA_PSTATE_TX_STS BIT(3) +#define TCA_PSTATE_RX_PLL_STS BIT(2) +#define TCA_PSTATE_PIPE0_POWER_DOWN GENMASK(1, 0) + +#define TCA_GEN_STATUS 0x34 +#define TCA_GEN_DEV_POR BIT(12) +#define TCA_GEN_REF_CLK_SEL BIT(8) +#define TCA_GEN_TYPEC_FLIP_INVERT BIT(4) +#define TCA_GEN_PHY_TYPEC_DISABLE BIT(3) +#define TCA_GEN_PHY_TYPEC_FLIP BIT(2) + +#define TCA_VBUS_CTRL 0x40 +#define TCA_VBUS_STATUS 0x44 + +#define TCA_INFO 0xfc + enum imx8mpq_phy_type { IMX8MQ_PHY, IMX8MP_PHY, + IMX95_PHY, }; struct imx8mq_usb_phy { @@ -81,14 +129,49 @@ struct imx8mq_usb_phy { void __iomem *base; enum imx8mpq_phy_type type; struct udevice *vbus_supply; + void __iomem *tca_base; }; static const struct udevice_id imx8mq_usb_phy_of_match[] = { { .compatible = "fsl,imx8mq-usb-phy", .data = IMX8MQ_PHY }, { .compatible = "fsl,imx8mp-usb-phy", .data = IMX8MP_PHY }, + { .compatible = "fsl,imx95-usb-phy", .data = IMX95_PHY }, {}, }; +static void tca_blk_init(struct phy *usb_phy) +{ + struct udevice *dev = usb_phy->dev; + struct imx8mq_usb_phy *imx_phy = dev_get_priv(dev); + void __iomem *base = imx_phy->tca_base; + u32 val; + + /* reset XBar block */ + val = readl(base + TCA_CLK_RST); + val &= ~TCA_CLK_RST_SW; + writel(val, base + TCA_CLK_RST); + + udelay(100); + + /* clear reset */ + val |= TCA_CLK_RST_SW; + writel(val, base + TCA_CLK_RST); + + /* + * use Controller Synced Mode for TCA low power enable and + * put PHY to USB safe state. + */ + val = FIELD_PREP(TCA_GCFG_OP_MODE, TCA_GCFG_OP_MODE_SYNCMODE); + writel(val, base + TCA_GCFG); + + val = TCA_TCPC_VALID | TCA_TCPC_LOW_POWER_EN; + writel(val, base + TCA_TCPC); + + /* use System Configuration Mode for TCA mux control. */ + val = FIELD_PREP(TCA_GCFG_OP_MODE, TCA_GCFG_OP_MODE_SYSMODE); + writel(val, base + TCA_GCFG); +} + static int imx8mq_usb_phy_init(struct phy *usb_phy) { struct udevice *dev = usb_phy->dev; @@ -154,6 +237,9 @@ static int imx8mp_usb_phy_init(struct phy *usb_phy) value &= ~(PHY_CTRL1_RESET | PHY_CTRL1_ATERESET); writel(value, imx_phy->base + PHY_CTRL1); + if (imx_phy->tca_base) + tca_blk_init(usb_phy); + return 0; } @@ -162,7 +248,7 @@ static int imx8mpq_usb_phy_init(struct phy *usb_phy) struct udevice *dev = usb_phy->dev; struct imx8mq_usb_phy *imx_phy = dev_get_priv(dev); - if (imx_phy->type == IMX8MP_PHY) + if (imx_phy->type == IMX8MP_PHY || imx_phy->type == IMX95_PHY) return imx8mp_usb_phy_init(usb_phy); else return imx8mq_usb_phy_init(usb_phy); @@ -264,6 +350,9 @@ int imx8mq_usb_phy_probe(struct udevice *dev) } } + if (priv->type == IMX95_PHY) + priv->tca_base = dev_read_addr_index_ptr(dev, 1); + return 0; } From 445aad45f47a19860eff5b09c4c570285265318a Mon Sep 17 00:00:00 2001 From: Tim Harvey Date: Mon, 21 Jul 2025 11:02:05 -0700 Subject: [PATCH 095/112] usb: ehci-mx6: Add i.MX95 OTG support When the usb node is defined dr_mode="otg" ehci_usb_phy_mode() is called to determine the mode from status registers. The IMX95RM does not currently define the USBNC STATUS register but it is assumed to be an omission as the first three registers are defined. It has been expirimentally verified that the USBNC_PHY_STATUS register at offset 0x23C bit4 (USBNC_PHYSTATUS_ID_DIG) reads 0 when USB_ID is GND and 1 when floating. Use is_imx9() as this driver works for i.MX91, i.MX93 and i.MX95 and all of these determine the role based on the USBNC_PHY_STATUS register. Fixes: 801b5fafd35d "(usb: ehci-mx6: Add i.MX95 support") Signed-off-by: Tim Harvey Reviewed-by: Alice Guo Reviewed-by: Peng Fan Reviewed-by: Fabio Estevam --- drivers/usb/host/ehci-mx6.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/usb/host/ehci-mx6.c b/drivers/usb/host/ehci-mx6.c index a8748cef7ad..25907f22612 100644 --- a/drivers/usb/host/ehci-mx6.c +++ b/drivers/usb/host/ehci-mx6.c @@ -537,7 +537,7 @@ static int ehci_usb_phy_mode(struct udevice *dev) plat->init_type = USB_INIT_DEVICE; else plat->init_type = USB_INIT_HOST; - } else if (is_mx7() || is_imx8mm() || is_imx8mn() || is_imx93()) { + } else if (is_mx7() || is_imx8mm() || is_imx8mn() || is_imx9()) { phy_status = (void __iomem *)(addr + USBNC_PHY_STATUS_OFFSET); val = readl(phy_status); From 332714b905923d9e97a2cc7590dfc41e49980d35 Mon Sep 17 00:00:00 2001 From: Patrick Delaunay Date: Wed, 23 Jul 2025 17:09:16 +0200 Subject: [PATCH 096/112] usb: dwc2: fix reset logic in dwc2_core_reset Use GUSBCFG_FORCEHOSTMODE to detected the HOST forced mode as it is done in the Linux driver drivers/usb/dwc2/core.c:dwc2_core_reset(). The host polling must be executed only if the current mode is host, either due to the force HOST mode (which persists after core reset) or the connector id pin. The GUSBCFG_FORCEDEVMODE bits is used to force the device mode (for example used on STM32MP1x platform) and when it is activated the DWC2 reset failed with the trace: "dwc2_core_reset: Waiting for GINTSTS_CURMODE_HOST timeout" Fixes: c5d685b8993c ("usb: dwc2: Unify flush and reset logic with v4.20a support") Signed-off-by: Patrick Delaunay Reviewed-by: Junhui Liu Tested-by: Patrice Chotard Reviewed-by: Marek Vasut --- drivers/usb/common/dwc2_core.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/usb/common/dwc2_core.c b/drivers/usb/common/dwc2_core.c index 63062d5cc94..37007134e5b 100644 --- a/drivers/usb/common/dwc2_core.c +++ b/drivers/usb/common/dwc2_core.c @@ -17,7 +17,7 @@ int dwc2_core_reset(struct dwc2_core_regs *regs) bool host_mode = false; if (!(readl(®s->global_regs.gotgctl) & GOTGCTL_CONID_B) || - (readl(®s->global_regs.gusbcfg) & GUSBCFG_FORCEDEVMODE)) + (readl(®s->global_regs.gusbcfg) & GUSBCFG_FORCEHOSTMODE)) host_mode = true; /* Core Soft Reset */ From 0d1c4fd514c13fbda3b3016cfa9ce00b01e42bf9 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Mon, 28 Jul 2025 16:47:09 +0100 Subject: [PATCH 097/112] mailbox: zynqmp: Fix off by 1 errors Use resource_size to correctly calculate the size to pass to devm_ioremap and avoid the off by 1 errors previously present. This issue was found by Smatch. Signed-off-by: Andrew Goodbody Link: https://lore.kernel.org/r/20250728-zynqmp-ipi-v1-1-b2bd144a9521@linaro.org Signed-off-by: Michal Simek --- drivers/mailbox/zynqmp-ipi.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/drivers/mailbox/zynqmp-ipi.c b/drivers/mailbox/zynqmp-ipi.c index 851aa737c03..f62277385fb 100644 --- a/drivers/mailbox/zynqmp-ipi.c +++ b/drivers/mailbox/zynqmp-ipi.c @@ -188,7 +188,7 @@ static int zynqmp_ipi_dest_probe(struct udevice *dev) return -EINVAL; }; zynqmp->local_req_regs = devm_ioremap(dev, res.start, - (res.start - res.end)); + resource_size(&res)); if (!zynqmp->local_req_regs) return -EINVAL; @@ -197,7 +197,7 @@ static int zynqmp_ipi_dest_probe(struct udevice *dev) return -EINVAL; }; zynqmp->local_res_regs = devm_ioremap(dev, res.start, - (res.start - res.end)); + resource_size(&res)); if (!zynqmp->local_res_regs) return -EINVAL; @@ -206,7 +206,7 @@ static int zynqmp_ipi_dest_probe(struct udevice *dev) return -EINVAL; }; zynqmp->remote_req_regs = devm_ioremap(dev, res.start, - (res.start - res.end)); + resource_size(&res)); if (!zynqmp->remote_req_regs) return -EINVAL; @@ -215,7 +215,7 @@ static int zynqmp_ipi_dest_probe(struct udevice *dev) return -EINVAL; }; zynqmp->remote_res_regs = devm_ioremap(dev, res.start, - (res.start - res.end)); + resource_size(&res)); if (!zynqmp->remote_res_regs) return -EINVAL; From 7aac8439445793baa9313a7d5139b77f968b2885 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Thu, 7 Aug 2025 11:04:04 +0100 Subject: [PATCH 098/112] pinctrl: zynqmp: Ensure ret is initialised In zynqmp_pinctrl_prepare_func_groups if called with func->ngroups == 0 then ret will not be assigned to before its value is returned on exit. Initialise ret to ensure it is always valid. This issue was found by Smatch. Signed-off-by: Andrew Goodbody Link: https://lore.kernel.org/r/20250807-pinctrl_misc-v1-3-eeb564a1b032@linaro.org Signed-off-by: Michal Simek --- drivers/pinctrl/pinctrl-zynqmp.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/pinctrl/pinctrl-zynqmp.c b/drivers/pinctrl/pinctrl-zynqmp.c index 6fa203a3b86..27dadbff8ca 100644 --- a/drivers/pinctrl/pinctrl-zynqmp.c +++ b/drivers/pinctrl/pinctrl-zynqmp.c @@ -204,7 +204,7 @@ static int zynqmp_pinctrl_prepare_func_groups(u32 fid, const char **fgroups; char name[MAX_GROUP_NAME_LEN]; u16 resp[NUM_GROUPS_PER_RESP] = {0}; - int ret, index, i; + int ret = 0, index, i; fgroups = kcalloc(func->ngroups, sizeof(*fgroups), GFP_KERNEL); if (!fgroups) From 6ce599f513172147362e8a2f7424837a2dd60e90 Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Thu, 7 Aug 2025 11:04:05 +0100 Subject: [PATCH 099/112] pinctrl: zynqmp: Avoid using uninitialised variable In zynqmp_pinconf_set if param is PIN_CFG_IOSTANDARD or PIN_CONFIG_POWER_SOURCE and zynqmp_pm_pinctrl_get_config returns an error then value will not be assigned to when its value is tested to be not equal to arg. Add code to only test value not equal to arg if ret is false. This issue was found by Smatch. Signed-off-by: Andrew Goodbody Link: https://lore.kernel.org/r/20250807-pinctrl_misc-v1-4-eeb564a1b032@linaro.org Signed-off-by: Michal Simek --- drivers/pinctrl/pinctrl-zynqmp.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/pinctrl/pinctrl-zynqmp.c b/drivers/pinctrl/pinctrl-zynqmp.c index 27dadbff8ca..665b76a7d4d 100644 --- a/drivers/pinctrl/pinctrl-zynqmp.c +++ b/drivers/pinctrl/pinctrl-zynqmp.c @@ -460,14 +460,14 @@ static int zynqmp_pinconf_set(struct udevice *dev, unsigned int pin, case PIN_CFG_IOSTANDARD: param = PM_PINCTRL_CONFIG_VOLTAGE_STATUS; ret = zynqmp_pm_pinctrl_get_config(pin, param, &value); - if (arg != value) + if (!ret && arg != value) dev_warn(dev, "Invalid IO Standard requested for pin %d\n", pin); break; case PIN_CONFIG_POWER_SOURCE: param = PM_PINCTRL_CONFIG_VOLTAGE_STATUS; ret = zynqmp_pm_pinctrl_get_config(pin, param, &value); - if (arg != value) + if (!ret && arg != value) dev_warn(dev, "Invalid IO Standard requested for pin %d\n", pin); break; From 3b765ae05005249b91a737cd620e0577a8d5b9ba Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Frank=20B=C3=B6wingloh?= Date: Fri, 8 Aug 2025 14:31:34 +0200 Subject: [PATCH 100/112] soc: xilinx: zynqmp: Fix zu1cg device detection MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Currently u-boot displayed a zu1cg soc as "Chip: zu1eg". A value of 0468_8093h in the IDCODE (CSU) Register defines a ZU1 soc not only for the EG family but also for the CG family as described in the Xilinx Zynq UltraScale+ UG1085 documentation in Table 1-2. Signed-off-by: Frank Böwingloh Cc: Michal Simek Link: https://lore.kernel.org/r/20250808123134.636-1-f.boewingloh@beckhoff.com Signed-off-by: Michal Simek --- drivers/soc/soc_xilinx_zynqmp.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/soc/soc_xilinx_zynqmp.c b/drivers/soc/soc_xilinx_zynqmp.c index 0c45c781fef..4b69ff3de13 100644 --- a/drivers/soc/soc_xilinx_zynqmp.c +++ b/drivers/soc/soc_xilinx_zynqmp.c @@ -63,7 +63,7 @@ static const struct zynqmp_device zynqmp_devices[] = { { .id = 0x04688093, .device = 1, - .variants = ZYNQMP_VARIANT_EG, + .variants = ZYNQMP_VARIANT_EG | ZYNQMP_VARIANT_CG, }, { .id = 0x04689093, From 818f6002e1429aa42f7efda06d3fe742ebf65e93 Mon Sep 17 00:00:00 2001 From: Alexander Dahl Date: Mon, 4 Aug 2025 11:08:16 +0200 Subject: [PATCH 101/112] fpga: cyclon2: Remove message never printed else branch is never reached. Print "Done." anyways to keep behaviour. Addresses-Coverity-ID: 583148 Link: https://lore.kernel.org/u-boot/20250725132645.GA1807455@bill-the-cat/ Fixes: f0ff4692ff33 ("Add FPGA Altera Cyclone 2 support Patch by Heiko Schocher, 15 Aug 2006") Signed-off-by: Alexander Dahl Link: https://lore.kernel.org/r/20250804090816.42603-1-ada@thorsis.com Signed-off-by: Michal Simek --- drivers/fpga/cyclon2.c | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/drivers/fpga/cyclon2.c b/drivers/fpga/cyclon2.c index 7e78d6e2d6c..1c464c1e912 100644 --- a/drivers/fpga/cyclon2.c +++ b/drivers/fpga/cyclon2.c @@ -174,10 +174,7 @@ static int CYC2_ps_load(Altera_desc *desc, const void *buf, size_t bsize) ret_val = FPGA_SUCCESS; #ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK - if (ret_val == FPGA_SUCCESS) - puts("Done.\n"); - else - puts("Fail.\n"); + puts("Done.\n"); #endif /* From 7fc04c9a82e858a1d042d8c7b008831c28d5965e Mon Sep 17 00:00:00 2001 From: Michal Simek Date: Mon, 28 Jul 2025 09:07:52 +0200 Subject: [PATCH 102/112] fpga: xilinx: Check valid desc structure FPGA validation can fail and return value needs to be checked. Addresses-Coverity-ID: CID 583150: Null pointer dereferences (NULL_RETURNS) Signed-off-by: Michal Simek Link: https://lore.kernel.org/r/876b6f8dbc99ca305460183dbd18635a35ccc989.1753686468.git.michal.simek@amd.com --- drivers/fpga/xilinx.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/fpga/xilinx.c b/drivers/fpga/xilinx.c index 28c68faba55..25b348648ef 100644 --- a/drivers/fpga/xilinx.c +++ b/drivers/fpga/xilinx.c @@ -50,6 +50,9 @@ int fpga_loadbitstream(int devnum, char *fpgadata, size_t size, dataptr = (unsigned char *)fpgadata; /* Find out fpga_description */ desc = fpga_validate(devnum, dataptr, 0); + if (!desc) + return FPGA_FAIL; + /* Assign xilinx device description */ xdesc = desc->devdesc; From 0870281a415d33b20ca4a2ff072ab55c1b71bcb5 Mon Sep 17 00:00:00 2001 From: Michal Simek Date: Mon, 28 Jul 2025 09:07:53 +0200 Subject: [PATCH 103/112] fpga: Remove ancient ACEX1K support Coverity (CID 583149) reports issue on code which is not enabled by any real platform that's why remove it completely. Acked-by: Alexander Dahl Signed-off-by: Michal Simek Link: https://lore.kernel.org/r/20fe425910b6266a2bf0555bda67f60c1dd3aa61.1753686468.git.michal.simek@amd.com --- configs/sandbox_defconfig | 1 - drivers/fpga/ACEX1K.c | 245 -------------------------------------- drivers/fpga/Kconfig | 6 - drivers/fpga/Makefile | 1 - drivers/fpga/altera.c | 5 +- include/ACEX1K.h | 32 ----- 6 files changed, 1 insertion(+), 289 deletions(-) delete mode 100644 drivers/fpga/ACEX1K.c diff --git a/configs/sandbox_defconfig b/configs/sandbox_defconfig index e9a70b26044..e8e182c8908 100644 --- a/configs/sandbox_defconfig +++ b/configs/sandbox_defconfig @@ -207,7 +207,6 @@ CONFIG_ARM_FFA_TRANSPORT=y CONFIG_FPGA_ALTERA=y CONFIG_FPGA_STRATIX_II=y CONFIG_FPGA_STRATIX_V=y -CONFIG_FPGA_ACEX1K=y CONFIG_FPGA_CYCLON2=y CONFIG_FPGA_LATTICE=y CONFIG_FPGA_XILINX=y diff --git a/drivers/fpga/ACEX1K.c b/drivers/fpga/ACEX1K.c deleted file mode 100644 index e1514fc56d0..00000000000 --- a/drivers/fpga/ACEX1K.c +++ /dev/null @@ -1,245 +0,0 @@ -// SPDX-License-Identifier: GPL-2.0+ -/* - * (C) Copyright 2003 - * Steven Scholz, imc Measurement & Control, steven.scholz@imc-berlin.de - * - * (C) Copyright 2002 - * Rich Ireland, Enterasys Networks, rireland@enterasys.com. - */ - -#define LOG_CATEGORY UCLASS_FPGA - -#include /* core U-Boot definitions */ -#include -#include -#include /* ACEX device family */ -#include -#include - -/* Note: The assumption is that we cannot possibly run fast enough to - * overrun the device (the Slave Parallel mode can free run at 50MHz). - * If there is a need to operate slower, define CFG_FPGA_DELAY in - * the board config file to slow things down. - */ -#ifndef CFG_FPGA_DELAY -#define CFG_FPGA_DELAY() -#endif - -#ifndef CFG_SYS_FPGA_WAIT -#define CFG_SYS_FPGA_WAIT CONFIG_SYS_HZ/10 /* 100 ms */ -#endif - -static int ACEX1K_ps_load(Altera_desc *desc, const void *buf, size_t bsize); -static int ACEX1K_ps_dump(Altera_desc *desc, const void *buf, size_t bsize); -/* static int ACEX1K_ps_info(Altera_desc *desc); */ - -/* ------------------------------------------------------------------------- */ -/* ACEX1K Generic Implementation */ -int ACEX1K_load(Altera_desc *desc, const void *buf, size_t bsize) -{ - int ret_val = FPGA_FAIL; - - switch (desc->iface) { - case passive_serial: - log_debug("Launching Passive Serial Loader\n"); - ret_val = ACEX1K_ps_load (desc, buf, bsize); - break; - - /* Add new interface types here */ - - default: - printf ("%s: Unsupported interface type, %d\n", - __FUNCTION__, desc->iface); - } - - return ret_val; -} - -int ACEX1K_dump(Altera_desc *desc, const void *buf, size_t bsize) -{ - int ret_val = FPGA_FAIL; - - switch (desc->iface) { - case passive_serial: - log_debug("Launching Passive Serial Dump\n"); - ret_val = ACEX1K_ps_dump (desc, buf, bsize); - break; - - /* Add new interface types here */ - - default: - printf ("%s: Unsupported interface type, %d\n", - __FUNCTION__, desc->iface); - } - - return ret_val; -} - -int ACEX1K_info( Altera_desc *desc ) -{ - return FPGA_SUCCESS; -} - -/* ------------------------------------------------------------------------- */ -/* ACEX1K Passive Serial Generic Implementation */ - -static int ACEX1K_ps_load(Altera_desc *desc, const void *buf, size_t bsize) -{ - int ret_val = FPGA_FAIL; /* assume the worst */ - Altera_ACEX1K_Passive_Serial_fns *fn = desc->iface_fns; - int i; - - log_debug("start with interface functions @ 0x%p\n", fn); - - if (fn) { - size_t bytecount = 0; - unsigned char *data = (unsigned char *) buf; - int cookie = desc->cookie; /* make a local copy */ - unsigned long ts; /* timestamp */ - - log_debug("Function Table:\n" - "ptr:\t0x%p\n" - "struct: 0x%p\n" - "config:\t0x%p\n" - "status:\t0x%p\n" - "clk:\t0x%p\n" - "data:\t0x%p\n" - "done:\t0x%p\n\n", - &fn, fn, fn->config, fn->status, - fn->clk, fn->data, fn->done); -#ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK - printf ("Loading FPGA Device %d...", cookie); -#endif - - /* - * Run the pre configuration function if there is one. - */ - if (*fn->pre) { - (*fn->pre) (cookie); - } - - /* Establish the initial state */ - (*fn->config) (true, true, cookie); /* Assert nCONFIG */ - - udelay(2); /* T_cfg > 2us */ - - /* nSTATUS should be asserted now */ - (*fn->done) (cookie); - if ( !(*fn->status) (cookie) ) { - puts ("** nSTATUS is not asserted.\n"); - (*fn->abort) (cookie); - return FPGA_FAIL; - } - - (*fn->config) (false, true, cookie); /* Deassert nCONFIG */ - udelay(2); /* T_cf2st1 < 4us */ - - /* Wait for nSTATUS to be released (i.e. deasserted) */ - ts = get_timer (0); /* get current time */ - do { - CFG_FPGA_DELAY (); - if (get_timer (ts) > CFG_SYS_FPGA_WAIT) { /* check the time */ - puts ("** Timeout waiting for STATUS to go high.\n"); - (*fn->abort) (cookie); - return FPGA_FAIL; - } - (*fn->done) (cookie); - } while ((*fn->status) (cookie)); - - /* Get ready for the burn */ - CFG_FPGA_DELAY (); - - /* Load the data */ - while (bytecount < bsize) { - unsigned char val=0; -#ifdef CONFIG_SYS_FPGA_CHECK_CTRLC - if (ctrlc ()) { - (*fn->abort) (cookie); - return FPGA_FAIL; - } -#endif - /* Altera detects an error if INIT goes low (active) - while DONE is low (inactive) */ -#if 0 /* not yet implemented */ - if ((*fn->done) (cookie) == 0 && (*fn->init) (cookie)) { - puts ("** CRC error during FPGA load.\n"); - (*fn->abort) (cookie); - return (FPGA_FAIL); - } -#endif - val = data [bytecount ++ ]; - i = 8; - do { - /* Deassert the clock */ - (*fn->clk) (false, true, cookie); - CFG_FPGA_DELAY (); - /* Write data */ - (*fn->data) ((val & 0x01), true, cookie); - CFG_FPGA_DELAY (); - /* Assert the clock */ - (*fn->clk) (true, true, cookie); - CFG_FPGA_DELAY (); - val >>= 1; - i --; - } while (i > 0); - -#ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK - if (bytecount % (bsize / 40) == 0) - putc ('.'); /* let them know we are alive */ -#endif - } - - CFG_FPGA_DELAY (); - -#ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK - putc (' '); /* terminate the dotted line */ -#endif - - /* - * Checking FPGA's CONF_DONE signal - correctly booted ? - */ - - if ( ! (*fn->done) (cookie) ) { - puts ("** Booting failed! CONF_DONE is still deasserted.\n"); - (*fn->abort) (cookie); - return (FPGA_FAIL); - } - - /* - * "DCLK must be clocked an additional 10 times fpr ACEX 1K..." - */ - - for (i = 0; i < 12; i++) { - CFG_FPGA_DELAY (); - (*fn->clk) (true, true, cookie); /* Assert the clock pin */ - CFG_FPGA_DELAY (); - (*fn->clk) (false, true, cookie); /* Deassert the clock pin */ - } - - ret_val = FPGA_SUCCESS; - -#ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK - if (ret_val == FPGA_SUCCESS) { - puts ("Done.\n"); - } - else { - puts ("Fail.\n"); - } -#endif - (*fn->post) (cookie); - - } else { - printf ("%s: NULL Interface function table!\n", __FUNCTION__); - } - - return ret_val; -} - -static int ACEX1K_ps_dump(Altera_desc *desc, const void *buf, size_t bsize) -{ - /* Readback is only available through the Slave Parallel and */ - /* boundary-scan interfaces. */ - printf ("%s: Passive Serial Dumping is unavailable\n", - __FUNCTION__); - return FPGA_FAIL; -} diff --git a/drivers/fpga/Kconfig b/drivers/fpga/Kconfig index 9456ca3149a..18e7d7c99a9 100644 --- a/drivers/fpga/Kconfig +++ b/drivers/fpga/Kconfig @@ -34,12 +34,6 @@ config FPGA_STRATIX_V help Say Y here to enable the Altera Stratix V FPGA specific driver. -config FPGA_ACEX1K - bool "Enable Altera ACEX 1K driver" - depends on FPGA_ALTERA - help - Say Y here to enable the Altera ACEX 1K FPGA specific driver. - config FPGA_CYCLON2 bool "Enable Altera FPGA driver for Cyclone II" depends on FPGA_ALTERA diff --git a/drivers/fpga/Makefile b/drivers/fpga/Makefile index 610c168fc35..6c779d5b5df 100644 --- a/drivers/fpga/Makefile +++ b/drivers/fpga/Makefile @@ -17,7 +17,6 @@ obj-$(CONFIG_FPGA_XILINX) += xilinx.o obj-$(CONFIG_FPGA_LATTICE) += ivm_core.o lattice.o ifdef CONFIG_FPGA_ALTERA obj-y += altera.o -obj-$(CONFIG_FPGA_ACEX1K) += ACEX1K.o obj-$(CONFIG_FPGA_CYCLON2) += cyclon2.o obj-$(CONFIG_FPGA_INTEL_SDM_MAILBOX) += intel_sdm_mb.o obj-$(CONFIG_FPGA_STRATIX_II) += stratixII.o diff --git a/drivers/fpga/altera.c b/drivers/fpga/altera.c index 64fda3a307c..4a9aa74357e 100644 --- a/drivers/fpga/altera.c +++ b/drivers/fpga/altera.c @@ -28,10 +28,7 @@ static const struct altera_fpga { int (*dump)(Altera_desc *, const void *, size_t); int (*info)(Altera_desc *); } altera_fpga[] = { -#if defined(CONFIG_FPGA_ACEX1K) - { Altera_ACEX1K, "ACEX1K", ACEX1K_load, ACEX1K_dump, ACEX1K_info }, - { Altera_CYC2, "ACEX1K", ACEX1K_load, ACEX1K_dump, ACEX1K_info }, -#elif defined(CONFIG_FPGA_CYCLON2) +#if defined(CONFIG_FPGA_CYCLON2) { Altera_ACEX1K, "CycloneII", CYC2_load, CYC2_dump, CYC2_info }, { Altera_CYC2, "CycloneII", CYC2_load, CYC2_dump, CYC2_info }, #endif diff --git a/include/ACEX1K.h b/include/ACEX1K.h index 7c5253c66cc..4d24545df2c 100644 --- a/include/ACEX1K.h +++ b/include/ACEX1K.h @@ -12,26 +12,10 @@ #include -extern int ACEX1K_load(Altera_desc *desc, const void *image, size_t size); -extern int ACEX1K_dump(Altera_desc *desc, const void *buf, size_t bsize); -extern int ACEX1K_info(Altera_desc *desc); - extern int CYC2_load(Altera_desc *desc, const void *image, size_t size); extern int CYC2_dump(Altera_desc *desc, const void *buf, size_t bsize); extern int CYC2_info(Altera_desc *desc); -/* Slave Serial Implementation function table */ -typedef struct { - Altera_pre_fn pre; - Altera_config_fn config; - Altera_clk_fn clk; - Altera_status_fn status; - Altera_done_fn done; - Altera_data_fn data; - Altera_abort_fn abort; - Altera_post_fn post; -} Altera_ACEX1K_Passive_Serial_fns; - /* Slave Serial Implementation function table */ typedef struct { Altera_pre_fn pre; @@ -45,16 +29,6 @@ typedef struct { /* Device Image Sizes *********************************************************************/ -/* ACEX1K */ -/* FIXME: Which size do we mean? - * Datasheet says 1337000/8=167125Bytes, - * Filesize of an *.rbf file is 166965 Bytes - */ -#if 0 -#define Altera_EP1K100_SIZE 1337000/8 /* 167125 Bytes */ -#endif -#define Altera_EP1K100_SIZE (166965*8) - #define Altera_EP2C8_SIZE 247942 #define Altera_EP2C20_SIZE 586562 #define Altera_EP2C35_SIZE 883905 @@ -70,10 +44,4 @@ typedef struct { #define ALTERA_EP4CE75_SIZE 2495719 /* 19965752 Bits */ #define ALTERA_EP4CE115_SIZE 3571462 /* 28571696 Bits */ -/* Descriptor Macros - *********************************************************************/ -/* ACEX1K devices */ -#define Altera_EP1K100_DESC(iface, fn_table, cookie) \ -{ Altera_ACEX1K, iface, Altera_EP1K100_SIZE, fn_table, cookie } - #endif /* _ACEX1K_H_ */ From 34762f6c007c53d8540c1cb8bcf02ccddedb704f Mon Sep 17 00:00:00 2001 From: Michal Simek Date: Mon, 28 Jul 2025 09:07:54 +0200 Subject: [PATCH 104/112] fpga: lattice: Remove unused support There is no single platform which is using this driver that's why remove it completely. Some issues regarding this code are also reported by Coverity (CID 583143, 583144, 583145, 583146). Signed-off-by: Michal Simek Link: https://lore.kernel.org/r/367cd55ab8d9fb262ac23fe748babc6b2b59bee0.1753686468.git.michal.simek@amd.com --- configs/sandbox_defconfig | 1 - drivers/fpga/Kconfig | 6 - drivers/fpga/Makefile | 1 - drivers/fpga/fpga.c | 23 - drivers/fpga/ivm_core.c | 3149 ------------------------------------- drivers/fpga/lattice.c | 379 ----- include/fpga.h | 1 - include/lattice.h | 298 ---- 8 files changed, 3858 deletions(-) delete mode 100644 drivers/fpga/ivm_core.c delete mode 100644 drivers/fpga/lattice.c delete mode 100644 include/lattice.h diff --git a/configs/sandbox_defconfig b/configs/sandbox_defconfig index e8e182c8908..23651ec764d 100644 --- a/configs/sandbox_defconfig +++ b/configs/sandbox_defconfig @@ -208,7 +208,6 @@ CONFIG_FPGA_ALTERA=y CONFIG_FPGA_STRATIX_II=y CONFIG_FPGA_STRATIX_V=y CONFIG_FPGA_CYCLON2=y -CONFIG_FPGA_LATTICE=y CONFIG_FPGA_XILINX=y CONFIG_FPGA_SPARTAN2=y CONFIG_FPGA_SPARTAN3=y diff --git a/drivers/fpga/Kconfig b/drivers/fpga/Kconfig index 18e7d7c99a9..e2593057fac 100644 --- a/drivers/fpga/Kconfig +++ b/drivers/fpga/Kconfig @@ -55,12 +55,6 @@ config FPGA_INTEL_SDM_MAILBOX Enable FPGA driver for writing full bitstream into Intel FPGA devices through SDM (Secure Device Manager) Mailbox. -config FPGA_LATTICE - bool "Enable Lattice FPGA driver" - help - This is used for the lattice FPGAs. Please check the source code as - there is no documentation for this at present. - config FPGA_XILINX bool "Enable Xilinx FPGA drivers" select FPGA diff --git a/drivers/fpga/Makefile b/drivers/fpga/Makefile index 6c779d5b5df..f22d3b3d86e 100644 --- a/drivers/fpga/Makefile +++ b/drivers/fpga/Makefile @@ -14,7 +14,6 @@ obj-$(CONFIG_FPGA_VIRTEX2) += virtex2.o obj-$(CONFIG_FPGA_ZYNQPL) += zynqpl.o obj-$(CONFIG_FPGA_ZYNQMPPL) += zynqmppl.o obj-$(CONFIG_FPGA_XILINX) += xilinx.o -obj-$(CONFIG_FPGA_LATTICE) += ivm_core.o lattice.o ifdef CONFIG_FPGA_ALTERA obj-y += altera.o obj-$(CONFIG_FPGA_CYCLON2) += cyclon2.o diff --git a/drivers/fpga/fpga.c b/drivers/fpga/fpga.c index 2297fefd149..b4e3896d2e8 100644 --- a/drivers/fpga/fpga.c +++ b/drivers/fpga/fpga.c @@ -9,7 +9,6 @@ #include #include /* xilinx specific definitions */ #include /* altera specific definitions */ -#include #include /* Local static data */ @@ -79,14 +78,6 @@ static int fpga_dev_info(int devnum) ret_val = altera_info(desc->devdesc); #else log_err("No support for Altera devices.\n"); -#endif - break; - case fpga_lattice: -#if defined(CONFIG_FPGA_LATTICE) - log_info("Lattice Device\nDescriptor @ 0x%p\n", desc); - ret_val = lattice_info(desc->devdesc); -#else - log_err("No support for Lattice devices.\n"); #endif break; default: @@ -265,13 +256,6 @@ int fpga_load(int devnum, const void *buf, size_t bsize, bitstream_type bstype, ret_val = altera_load(desc->devdesc, buf, bsize); #else log_err("No support for Altera devices.\n"); -#endif - break; - case fpga_lattice: -#if defined(CONFIG_FPGA_LATTICE) - ret_val = lattice_load(desc->devdesc, buf, bsize); -#else - log_err("No support for Lattice devices.\n"); #endif break; default: @@ -310,13 +294,6 @@ int fpga_dump(int devnum, const void *buf, size_t bsize) ret_val = altera_dump(desc->devdesc, buf, bsize); #else log_err("No support for Altera devices.\n"); -#endif - break; - case fpga_lattice: -#if defined(CONFIG_FPGA_LATTICE) - ret_val = lattice_dump(desc->devdesc, buf, bsize); -#else - log_err("No support for Lattice devices.\n"); #endif break; default: diff --git a/drivers/fpga/ivm_core.c b/drivers/fpga/ivm_core.c deleted file mode 100644 index 37d5c5ec9ec..00000000000 --- a/drivers/fpga/ivm_core.c +++ /dev/null @@ -1,3149 +0,0 @@ -// SPDX-License-Identifier: GPL-2.0+ -/* - * Porting to u-boot: - * - * (C) Copyright 2010 - * Stefano Babic, DENX Software Engineering, sbabic@denx.de. - * - * Lattice ispVME Embedded code to load Lattice's FPGA: - * - * Copyright 2009 Lattice Semiconductor Corp. - * - * ispVME Embedded allows programming of Lattice's suite of FPGA - * devices on embedded systems through the JTAG port. The software - * is distributed in source code form and is open to re - distribution - * and modification where applicable. - * - * Revision History of ivm_core.c module: - * 4/25/06 ht Change some variables from unsigned short or int - * to long int to make the code compiler independent. - * 5/24/06 ht Support using RESET (TRST) pin as a special purpose - * control pin such as triggering the loading of known - * state exit. - * 3/6/07 ht added functions to support output to terminals - * - * 09/11/07 NN Type cast mismatch variables - * Moved the sclock() function to hardware.c - * 08/28/08 NN Added Calculate checksum support. - * 4/1/09 Nguyen replaced the recursive function call codes on - * the ispVMLCOUNT function - */ - -#include -#include -#include -#include -#include - -#define vme_out_char(c) printf("%c", c) -#define vme_out_hex(c) printf("%x", c) -#define vme_out_string(s) printf("%s", s) - -/* - * - * Global variables used to specify the flow control and data type. - * - * g_usFlowControl: flow control register. Each bit in the - * register can potentially change the - * personality of the embedded engine. - * g_usDataType: holds the data type of the current row. - * - */ - -static unsigned short g_usFlowControl; -unsigned short g_usDataType; - -/* - * - * Global variables used to specify the ENDDR and ENDIR. - * - * g_ucEndDR: the state that the device goes to after SDR. - * g_ucEndIR: the state that the device goes to after SIR. - * - */ - -unsigned char g_ucEndDR = DRPAUSE; -unsigned char g_ucEndIR = IRPAUSE; - -/* - * - * Global variables used to support header/trailer. - * - * g_usHeadDR: the number of lead devices in bypass. - * g_usHeadIR: the sum of IR length of lead devices. - * g_usTailDR: the number of tail devices in bypass. - * g_usTailIR: the sum of IR length of tail devices. - * - */ - -static unsigned short g_usHeadDR; -static unsigned short g_usHeadIR; -static unsigned short g_usTailDR; -static unsigned short g_usTailIR; - -/* - * - * Global variable to store the number of bits of data or instruction - * to be shifted into or out from the device. - * - */ - -static unsigned short g_usiDataSize; - -/* - * - * Stores the frequency. Default to 1 MHz. - * - */ - -static int g_iFrequency = 1000; - -/* - * - * Stores the maximum amount of ram needed to hold a row of data. - * - */ - -static unsigned short g_usMaxSize; - -/* - * - * Stores the LSH or RSH value. - * - */ - -static unsigned short g_usShiftValue; - -/* - * - * Stores the current repeat loop value. - * - */ - -static unsigned short g_usRepeatLoops; - -/* - * - * Stores the current vendor. - * - */ - -static signed char g_cVendor = LATTICE; - -/* - * - * Stores the VME file CRC. - * - */ - -unsigned short g_usCalculatedCRC; - -/* - * - * Stores the Device Checksum. - * - */ -/* 08/28/08 NN Added Calculate checksum support. */ -unsigned long g_usChecksum; -static unsigned int g_uiChecksumIndex; - -/* - * - * Stores the current state of the JTAG state machine. - * - */ - -static signed char g_cCurrentJTAGState; - -/* - * - * Global variables used to support looping. - * - * g_pucHeapMemory: holds the entire repeat loop. - * g_iHeapCounter: points to the current byte in the repeat loop. - * g_iHEAPSize: the current size of the repeat in bytes. - * - */ - -unsigned char *g_pucHeapMemory; -unsigned short g_iHeapCounter; -unsigned short g_iHEAPSize; -static unsigned short previous_size; - -/* - * - * Global variables used to support intelligent programming. - * - * g_usIntelDataIndex: points to the current byte of the - * intelligent buffer. - * g_usIntelBufferSize: holds the size of the intelligent - * buffer. - * - */ - -unsigned short g_usIntelDataIndex; -unsigned short g_usIntelBufferSize; - -/* - * - * Supported VME versions. - * - */ - -const char *const g_szSupportedVersions[] = { - "__VME2.0", "__VME3.0", "____12.0", "____12.1", 0}; - -/* - * - * Holds the maximum size of each respective buffer. These variables are used - * to write the HEX files when converting VME to HEX. - * -*/ - -static unsigned short g_usTDOSize; -static unsigned short g_usMASKSize; -static unsigned short g_usTDISize; -static unsigned short g_usDMASKSize; -static unsigned short g_usLCOUNTSize; -static unsigned short g_usHDRSize; -static unsigned short g_usTDRSize; -static unsigned short g_usHIRSize; -static unsigned short g_usTIRSize; -static unsigned short g_usHeapSize; - -/* - * - * Global variables used to store data. - * - * g_pucOutMaskData: local RAM to hold one row of MASK data. - * g_pucInData: local RAM to hold one row of TDI data. - * g_pucOutData: local RAM to hold one row of TDO data. - * g_pucHIRData: local RAM to hold the current SIR header. - * g_pucTIRData: local RAM to hold the current SIR trailer. - * g_pucHDRData: local RAM to hold the current SDR header. - * g_pucTDRData: local RAM to hold the current SDR trailer. - * g_pucIntelBuffer: local RAM to hold the current intelligent buffer - * g_pucOutDMaskData: local RAM to hold one row of DMASK data. - * - */ - -unsigned char *g_pucOutMaskData = NULL, - *g_pucInData = NULL, - *g_pucOutData = NULL, - *g_pucHIRData = NULL, - *g_pucTIRData = NULL, - *g_pucHDRData = NULL, - *g_pucTDRData = NULL, - *g_pucIntelBuffer = NULL, - *g_pucOutDMaskData = NULL; - -/* - * - * JTAG state machine transition table. - * - */ - -struct { - unsigned char CurState; /* From this state */ - unsigned char NextState; /* Step to this state */ - unsigned char Pattern; /* The tragetory of TMS */ - unsigned char Pulses; /* The number of steps */ -} g_JTAGTransistions[25] = { -{ RESET, RESET, 0xFC, 6 }, /* Transitions from RESET */ -{ RESET, IDLE, 0x00, 1 }, -{ RESET, DRPAUSE, 0x50, 5 }, -{ RESET, IRPAUSE, 0x68, 6 }, -{ IDLE, RESET, 0xE0, 3 }, /* Transitions from IDLE */ -{ IDLE, DRPAUSE, 0xA0, 4 }, -{ IDLE, IRPAUSE, 0xD0, 5 }, -{ DRPAUSE, RESET, 0xF8, 5 }, /* Transitions from DRPAUSE */ -{ DRPAUSE, IDLE, 0xC0, 3 }, -{ DRPAUSE, IRPAUSE, 0xF4, 7 }, -{ DRPAUSE, DRPAUSE, 0xE8, 6 },/* 06/14/06 Support POLL STATUS LOOP*/ -{ IRPAUSE, RESET, 0xF8, 5 }, /* Transitions from IRPAUSE */ -{ IRPAUSE, IDLE, 0xC0, 3 }, -{ IRPAUSE, DRPAUSE, 0xE8, 6 }, -{ DRPAUSE, SHIFTDR, 0x80, 2 }, /* Extra transitions using SHIFTDR */ -{ IRPAUSE, SHIFTDR, 0xE0, 5 }, -{ SHIFTDR, DRPAUSE, 0x80, 2 }, -{ SHIFTDR, IDLE, 0xC0, 3 }, -{ IRPAUSE, SHIFTIR, 0x80, 2 },/* Extra transitions using SHIFTIR */ -{ SHIFTIR, IRPAUSE, 0x80, 2 }, -{ SHIFTIR, IDLE, 0xC0, 3 }, -{ DRPAUSE, DRCAPTURE, 0xE0, 4 }, /* 11/15/05 Support DRCAPTURE*/ -{ DRCAPTURE, DRPAUSE, 0x80, 2 }, -{ IDLE, DRCAPTURE, 0x80, 2 }, -{ IRPAUSE, DRCAPTURE, 0xE0, 4 } -}; - -/* - * - * List to hold all LVDS pairs. - * - */ - -LVDSPair *g_pLVDSList; -unsigned short g_usLVDSPairCount; - -/* - * - * Function prototypes. - * - */ - -static signed char ispVMDataCode(void); -static long ispVMDataSize(void); -static void ispVMData(unsigned char *Data); -static signed char ispVMShift(signed char Code); -static signed char ispVMAmble(signed char Code); -static signed char ispVMLoop(unsigned short a_usLoopCount); -static signed char ispVMBitShift(signed char mode, unsigned short bits); -static void ispVMComment(unsigned short a_usCommentSize); -static void ispVMHeader(unsigned short a_usHeaderSize); -static signed char ispVMLCOUNT(unsigned short a_usCountSize); -static void ispVMClocks(unsigned short Clocks); -static void ispVMBypass(signed char ScanType, unsigned short Bits); -static void ispVMStateMachine(signed char NextState); -static signed char ispVMSend(unsigned short int); -static signed char ispVMRead(unsigned short int); -static signed char ispVMReadandSave(unsigned short int); -static signed char ispVMProcessLVDS(unsigned short a_usLVDSCount); -static void ispVMMemManager(signed char types, unsigned short size); - -/* - * - * External variables and functions in hardware.c module - * - */ -static signed char g_cCurrentJTAGState; - -#ifdef DEBUG - -/* - * - * GetState - * - * Returns the state as a string based on the opcode. Only used - * for debugging purposes. - * - */ - -const char *GetState(unsigned char a_ucState) -{ - switch (a_ucState) { - case RESET: - return "RESET"; - case IDLE: - return "IDLE"; - case IRPAUSE: - return "IRPAUSE"; - case DRPAUSE: - return "DRPAUSE"; - case SHIFTIR: - return "SHIFTIR"; - case SHIFTDR: - return "SHIFTDR"; - case DRCAPTURE:/* 11/15/05 support DRCAPTURE*/ - return "DRCAPTURE"; - default: - break; - } - - return 0; -} - -/* - * - * PrintData - * - * Prints the data. Only used for debugging purposes. - * - */ - -void PrintData(unsigned short a_iDataSize, unsigned char *a_pucData) -{ - /* 09/11/07 NN added local variables initialization */ - unsigned short usByteSize = 0; - unsigned short usBitIndex = 0; - signed short usByteIndex = 0; - unsigned char ucByte = 0; - unsigned char ucFlipByte = 0; - - if (a_iDataSize % 8) { - /* 09/11/07 NN Type cast mismatch variables */ - usByteSize = (unsigned short)(a_iDataSize / 8 + 1); - } else { - /* 09/11/07 NN Type cast mismatch variables */ - usByteSize = (unsigned short)(a_iDataSize / 8); - } - puts("("); - /* 09/11/07 NN Type cast mismatch variables */ - for (usByteIndex = (signed short)(usByteSize - 1); - usByteIndex >= 0; usByteIndex--) { - ucByte = a_pucData[usByteIndex]; - ucFlipByte = 0x00; - - /* - * - * Flip each byte. - * - */ - - for (usBitIndex = 0; usBitIndex < 8; usBitIndex++) { - ucFlipByte <<= 1; - if (ucByte & 0x1) { - ucFlipByte |= 0x1; - } - - ucByte >>= 1; - } - - /* - * - * Print the flipped byte. - * - */ - - printf("%.02X", ucFlipByte); - if ((usByteSize - usByteIndex) % 40 == 39) { - puts("\n\t\t"); - } - if (usByteIndex < 0) - break; - } - puts(")"); -} -#endif /* DEBUG */ - -void ispVMMemManager(signed char cTarget, unsigned short usSize) -{ - switch (cTarget) { - case XTDI: - case TDI: - if (g_pucInData != NULL) { - if (previous_size == usSize) {/*memory exist*/ - break; - } else { - free(g_pucInData); - g_pucInData = NULL; - } - } - g_pucInData = (unsigned char *) malloc(usSize / 8 + 2); - previous_size = usSize; - case XTDO: - case TDO: - if (g_pucOutData != NULL) { - if (previous_size == usSize) { /*already exist*/ - break; - } else { - free(g_pucOutData); - g_pucOutData = NULL; - } - } - g_pucOutData = (unsigned char *) malloc(usSize / 8 + 2); - previous_size = usSize; - break; - case MASK: - if (g_pucOutMaskData != NULL) { - if (previous_size == usSize) {/*already allocated*/ - break; - } else { - free(g_pucOutMaskData); - g_pucOutMaskData = NULL; - } - } - g_pucOutMaskData = (unsigned char *) malloc(usSize / 8 + 2); - previous_size = usSize; - break; - case HIR: - if (g_pucHIRData != NULL) { - free(g_pucHIRData); - g_pucHIRData = NULL; - } - g_pucHIRData = (unsigned char *) malloc(usSize / 8 + 2); - break; - case TIR: - if (g_pucTIRData != NULL) { - free(g_pucTIRData); - g_pucTIRData = NULL; - } - g_pucTIRData = (unsigned char *) malloc(usSize / 8 + 2); - break; - case HDR: - if (g_pucHDRData != NULL) { - free(g_pucHDRData); - g_pucHDRData = NULL; - } - g_pucHDRData = (unsigned char *) malloc(usSize / 8 + 2); - break; - case TDR: - if (g_pucTDRData != NULL) { - free(g_pucTDRData); - g_pucTDRData = NULL; - } - g_pucTDRData = (unsigned char *) malloc(usSize / 8 + 2); - break; - case HEAP: - if (g_pucHeapMemory != NULL) { - free(g_pucHeapMemory); - g_pucHeapMemory = NULL; - } - g_pucHeapMemory = (unsigned char *) malloc(usSize + 2); - break; - case DMASK: - if (g_pucOutDMaskData != NULL) { - if (previous_size == usSize) { /*already allocated*/ - break; - } else { - free(g_pucOutDMaskData); - g_pucOutDMaskData = NULL; - } - } - g_pucOutDMaskData = (unsigned char *) malloc(usSize / 8 + 2); - previous_size = usSize; - break; - case LHEAP: - if (g_pucIntelBuffer != NULL) { - free(g_pucIntelBuffer); - g_pucIntelBuffer = NULL; - } - g_pucIntelBuffer = (unsigned char *) malloc(usSize + 2); - break; - case LVDS: - if (g_pLVDSList != NULL) { - free(g_pLVDSList); - g_pLVDSList = NULL; - } - g_pLVDSList = (LVDSPair *) malloc(usSize * sizeof(LVDSPair)); - if (g_pLVDSList) - memset(g_pLVDSList, 0, usSize * sizeof(LVDSPair)); - break; - default: - return; - } -} - -void ispVMFreeMem(void) -{ - if (g_pucHeapMemory != NULL) { - free(g_pucHeapMemory); - g_pucHeapMemory = NULL; - } - - if (g_pucOutMaskData != NULL) { - free(g_pucOutMaskData); - g_pucOutMaskData = NULL; - } - - if (g_pucInData != NULL) { - free(g_pucInData); - g_pucInData = NULL; - } - - if (g_pucOutData != NULL) { - free(g_pucOutData); - g_pucOutData = NULL; - } - - if (g_pucHIRData != NULL) { - free(g_pucHIRData); - g_pucHIRData = NULL; - } - - if (g_pucTIRData != NULL) { - free(g_pucTIRData); - g_pucTIRData = NULL; - } - - if (g_pucHDRData != NULL) { - free(g_pucHDRData); - g_pucHDRData = NULL; - } - - if (g_pucTDRData != NULL) { - free(g_pucTDRData); - g_pucTDRData = NULL; - } - - if (g_pucOutDMaskData != NULL) { - free(g_pucOutDMaskData); - g_pucOutDMaskData = NULL; - } - - if (g_pucIntelBuffer != NULL) { - free(g_pucIntelBuffer); - g_pucIntelBuffer = NULL; - } - - if (g_pLVDSList != NULL) { - free(g_pLVDSList); - g_pLVDSList = NULL; - } -} - -/* - * - * ispVMDataSize - * - * Returns a VME-encoded number, usually used to indicate the - * bit length of an SIR/SDR command. - * - */ - -long ispVMDataSize(void) -{ - /* 09/11/07 NN added local variables initialization */ - long int iSize = 0; - signed char cCurrentByte = 0; - signed char cIndex = 0; - cIndex = 0; - while ((cCurrentByte = GetByte()) & 0x80) { - iSize |= ((long int) (cCurrentByte & 0x7F)) << cIndex; - cIndex += 7; - } - iSize |= ((long int) (cCurrentByte & 0x7F)) << cIndex; - return iSize; -} - -/* - * - * ispVMCode - * - * This is the heart of the embedded engine. All the high-level opcodes - * are extracted here. Once they have been identified, then it - * will call other functions to handle the processing. - * - */ - -signed char ispVMCode(void) -{ - /* 09/11/07 NN added local variables initialization */ - unsigned short iRepeatSize = 0; - signed char cOpcode = 0; - signed char cRetCode = 0; - unsigned char ucState = 0; - unsigned short usDelay = 0; - unsigned short usToggle = 0; - unsigned char usByte = 0; - - /* - * - * Check the compression flag only if this is the first time - * this function is entered. Do not check the compression flag if - * it is being called recursively from other functions within - * the embedded engine. - * - */ - - if (!(g_usDataType & LHEAP_IN) && !(g_usDataType & HEAP_IN)) { - usByte = GetByte(); - if (usByte == 0xf1) { - g_usDataType |= COMPRESS; - } else if (usByte == 0xf2) { - g_usDataType &= ~COMPRESS; - } else { - return VME_INVALID_FILE; - } - } - - /* - * - * Begin looping through all the VME opcodes. - * - */ - - while ((cOpcode = GetByte()) >= 0) { - - switch (cOpcode) { - case STATE: - - /* - * Step the JTAG state machine. - */ - - ucState = GetByte(); - - /* - * Step the JTAG state machine to DRCAPTURE - * to support Looping. - */ - - if ((g_usDataType & LHEAP_IN) && - (ucState == DRPAUSE) && - (g_cCurrentJTAGState == ucState)) { - ispVMStateMachine(DRCAPTURE); - } - - ispVMStateMachine(ucState); - -#ifdef DEBUG - if (g_usDataType & LHEAP_IN) { - debug("LDELAY %s ", GetState(ucState)); - } else { - debug("STATE %s;\n", GetState(ucState)); - } -#endif /* DEBUG */ - break; - case SIR: - case SDR: - case XSDR: - -#ifdef DEBUG - switch (cOpcode) { - case SIR: - puts("SIR "); - break; - case SDR: - case XSDR: - if (g_usDataType & LHEAP_IN) { - puts("LSDR "); - } else { - puts("SDR "); - } - break; - } -#endif /* DEBUG */ - /* - * - * Shift in data into the device. - * - */ - - cRetCode = ispVMShift(cOpcode); - if (cRetCode != 0) { - return cRetCode; - } - break; - case WAIT: - - /* - * - * Observe delay. - * - */ - - /* 09/11/07 NN Type cast mismatch variables */ - usDelay = (unsigned short) ispVMDataSize(); - ispVMDelay(usDelay); - -#ifdef DEBUG - if (usDelay & 0x8000) { - - /* - * Since MSB is set, the delay time must be - * decoded to millisecond. The SVF2VME encodes - * the MSB to represent millisecond. - */ - - usDelay &= ~0x8000; - if (g_usDataType & LHEAP_IN) { - printf("%.2E SEC;\n", - (float) usDelay / 1000); - } else { - printf("RUNTEST %.2E SEC;\n", - (float) usDelay / 1000); - } - } else { - /* - * Since MSB is not set, the delay time - * is given as microseconds. - */ - - if (g_usDataType & LHEAP_IN) { - printf("%.2E SEC;\n", - (float) usDelay / 1000000); - } else { - printf("RUNTEST %.2E SEC;\n", - (float) usDelay / 1000000); - } - } -#endif /* DEBUG */ - break; - case TCK: - - /* - * Issue clock toggles. - */ - - /* 09/11/07 NN Type cast mismatch variables */ - usToggle = (unsigned short) ispVMDataSize(); - ispVMClocks(usToggle); - -#ifdef DEBUG - printf("RUNTEST %d TCK;\n", usToggle); -#endif /* DEBUG */ - break; - case ENDDR: - - /* - * - * Set the ENDDR. - * - */ - - g_ucEndDR = GetByte(); - -#ifdef DEBUG - printf("ENDDR %s;\n", GetState(g_ucEndDR)); -#endif /* DEBUG */ - break; - case ENDIR: - - /* - * - * Set the ENDIR. - * - */ - - g_ucEndIR = GetByte(); - -#ifdef DEBUG - printf("ENDIR %s;\n", GetState(g_ucEndIR)); -#endif /* DEBUG */ - break; - case HIR: - case TIR: - case HDR: - case TDR: - -#ifdef DEBUG - switch (cOpcode) { - case HIR: - puts("HIR "); - break; - case TIR: - puts("TIR "); - break; - case HDR: - puts("HDR "); - break; - case TDR: - puts("TDR "); - break; - } -#endif /* DEBUG */ - /* - * Set the header/trailer of the device in order - * to bypass - * successfully. - */ - - cRetCode = ispVMAmble(cOpcode); - if (cRetCode != 0) { - return cRetCode; - } - -#ifdef DEBUG - puts(";\n"); -#endif /* DEBUG */ - break; - case MEM: - - /* - * The maximum RAM required to support - * processing one row of the VME file. - */ - - /* 09/11/07 NN Type cast mismatch variables */ - g_usMaxSize = (unsigned short) ispVMDataSize(); - -#ifdef DEBUG - printf("// MEMSIZE %d\n", g_usMaxSize); -#endif /* DEBUG */ - break; - case VENDOR: - - /* - * - * Set the VENDOR type. - * - */ - - cOpcode = GetByte(); - switch (cOpcode) { - case LATTICE: -#ifdef DEBUG - puts("// VENDOR LATTICE\n"); -#endif /* DEBUG */ - g_cVendor = LATTICE; - break; - case ALTERA: -#ifdef DEBUG - puts("// VENDOR ALTERA\n"); -#endif /* DEBUG */ - g_cVendor = ALTERA; - break; - case XILINX: -#ifdef DEBUG - puts("// VENDOR XILINX\n"); -#endif /* DEBUG */ - g_cVendor = XILINX; - break; - default: - break; - } - break; - case SETFLOW: - - /* - * Set the flow control. Flow control determines - * the personality of the embedded engine. - */ - - /* 09/11/07 NN Type cast mismatch variables */ - g_usFlowControl |= (unsigned short) ispVMDataSize(); - break; - case RESETFLOW: - - /* - * - * Unset the flow control. - * - */ - - /* 09/11/07 NN Type cast mismatch variables */ - g_usFlowControl &= (unsigned short) ~(ispVMDataSize()); - break; - case HEAP: - - /* - * - * Allocate heap size to store loops. - * - */ - - cRetCode = GetByte(); - if (cRetCode != SECUREHEAP) { - return VME_INVALID_FILE; - } - /* 09/11/07 NN Type cast mismatch variables */ - g_iHEAPSize = (unsigned short) ispVMDataSize(); - - /* - * Store the maximum size of the HEAP buffer. - * Used to convert VME to HEX. - */ - - if (g_iHEAPSize > g_usHeapSize) { - g_usHeapSize = g_iHEAPSize; - } - - ispVMMemManager(HEAP, (unsigned short) g_iHEAPSize); - break; - case REPEAT: - - /* - * - * Execute loops. - * - */ - - g_usRepeatLoops = 0; - - /* 09/11/07 NN Type cast mismatch variables */ - iRepeatSize = (unsigned short) ispVMDataSize(); - - cRetCode = ispVMLoop((unsigned short) iRepeatSize); - if (cRetCode != 0) { - return cRetCode; - } - break; - case ENDLOOP: - - /* - * - * Exit point from processing loops. - * - */ - - return cRetCode; - case ENDVME: - - /* - * The only valid exit point that indicates - * end of programming. - */ - - return cRetCode; - case SHR: - - /* - * - * Right-shift address. - * - */ - - g_usFlowControl |= SHIFTRIGHT; - - /* 09/11/07 NN Type cast mismatch variables */ - g_usShiftValue = (unsigned short) (g_usRepeatLoops * - (unsigned short)GetByte()); - break; - case SHL: - - /* - * Left-shift address. - */ - - g_usFlowControl |= SHIFTLEFT; - - /* 09/11/07 NN Type cast mismatch variables */ - g_usShiftValue = (unsigned short) (g_usRepeatLoops * - (unsigned short)GetByte()); - break; - case FREQUENCY: - - /* - * - * Set the frequency. - * - */ - - /* 09/11/07 NN Type cast mismatch variables */ - g_iFrequency = (int) (ispVMDataSize() / 1000); - if (g_iFrequency == 1) - g_iFrequency = 1000; - -#ifdef DEBUG - printf("FREQUENCY %.2E HZ;\n", - (float) g_iFrequency * 1000); -#endif /* DEBUG */ - break; - case LCOUNT: - - /* - * - * Process LCOUNT command. - * - */ - - cRetCode = ispVMLCOUNT((unsigned short)ispVMDataSize()); - if (cRetCode != 0) { - return cRetCode; - } - break; - case VUES: - - /* - * - * Set the flow control to verify USERCODE. - * - */ - - g_usFlowControl |= VERIFYUES; - break; - case COMMENT: - - /* - * - * Display comment. - * - */ - - ispVMComment((unsigned short) ispVMDataSize()); - break; - case LVDS: - - /* - * - * Process LVDS command. - * - */ - - ispVMProcessLVDS((unsigned short) ispVMDataSize()); - break; - case HEADER: - - /* - * - * Discard header. - * - */ - - ispVMHeader((unsigned short) ispVMDataSize()); - break; - /* 03/14/06 Support Toggle ispENABLE signal*/ - case ispEN: - ucState = GetByte(); - if ((ucState == ON) || (ucState == 0x01)) - writePort(g_ucPinENABLE, 0x01); - else - writePort(g_ucPinENABLE, 0x00); - ispVMDelay(1); - break; - /* 05/24/06 support Toggle TRST pin*/ - case TRST: - ucState = GetByte(); - if (ucState == 0x01) - writePort(g_ucPinTRST, 0x01); - else - writePort(g_ucPinTRST, 0x00); - ispVMDelay(1); - break; - default: - - /* - * - * Invalid opcode encountered. - * - */ - -#ifdef DEBUG - printf("\nINVALID OPCODE: 0x%.2X\n", cOpcode); -#endif /* DEBUG */ - - return VME_INVALID_FILE; - } - } - - /* - * - * Invalid exit point. Processing the token 'ENDVME' is the only - * valid way to exit the embedded engine. - * - */ - - return VME_INVALID_FILE; -} - -/* - * - * ispVMDataCode - * - * Processes the TDI/TDO/MASK/DMASK etc of an SIR/SDR command. - * - */ - -signed char ispVMDataCode(void) -{ - /* 09/11/07 NN added local variables initialization */ - signed char cDataByte = 0; - signed char siDataSource = 0; /*source of data from file by default*/ - - if (g_usDataType & HEAP_IN) { - siDataSource = 1; /*the source of data from memory*/ - } - - /* - * - * Clear the data type register. - * - **/ - - g_usDataType &= ~(MASK_DATA + TDI_DATA + - TDO_DATA + DMASK_DATA + CMASK_DATA); - - /* - * Iterate through SIR/SDR command and look for TDI, - * TDO, MASK, etc. - */ - - while ((cDataByte = GetByte()) >= 0) { - ispVMMemManager(cDataByte, g_usMaxSize); - switch (cDataByte) { - case TDI: - - /* - * Store the maximum size of the TDI buffer. - * Used to convert VME to HEX. - */ - - if (g_usiDataSize > g_usTDISize) { - g_usTDISize = g_usiDataSize; - } - /* - * Updated data type register to indicate that - * TDI data is currently being used. Process the - * data in the VME file into the TDI buffer. - */ - - g_usDataType |= TDI_DATA; - ispVMData(g_pucInData); - break; - case XTDO: - - /* - * Store the maximum size of the TDO buffer. - * Used to convert VME to HEX. - */ - - if (g_usiDataSize > g_usTDOSize) { - g_usTDOSize = g_usiDataSize; - } - - /* - * Updated data type register to indicate that - * TDO data is currently being used. - */ - - g_usDataType |= TDO_DATA; - break; - case TDO: - - /* - * Store the maximum size of the TDO buffer. - * Used to convert VME to HEX. - */ - - if (g_usiDataSize > g_usTDOSize) { - g_usTDOSize = g_usiDataSize; - } - - /* - * Updated data type register to indicate - * that TDO data is currently being used. - * Process the data in the VME file into the - * TDO buffer. - */ - - g_usDataType |= TDO_DATA; - ispVMData(g_pucOutData); - break; - case MASK: - - /* - * Store the maximum size of the MASK buffer. - * Used to convert VME to HEX. - */ - - if (g_usiDataSize > g_usMASKSize) { - g_usMASKSize = g_usiDataSize; - } - - /* - * Updated data type register to indicate that - * MASK data is currently being used. Process - * the data in the VME file into the MASK buffer - */ - - g_usDataType |= MASK_DATA; - ispVMData(g_pucOutMaskData); - break; - case DMASK: - - /* - * Store the maximum size of the DMASK buffer. - * Used to convert VME to HEX. - */ - - if (g_usiDataSize > g_usDMASKSize) { - g_usDMASKSize = g_usiDataSize; - } - - /* - * Updated data type register to indicate that - * DMASK data is currently being used. Process - * the data in the VME file into the DMASK - * buffer. - */ - - g_usDataType |= DMASK_DATA; - ispVMData(g_pucOutDMaskData); - break; - case CMASK: - - /* - * Updated data type register to indicate that - * MASK data is currently being used. Process - * the data in the VME file into the MASK buffer - */ - - g_usDataType |= CMASK_DATA; - ispVMData(g_pucOutMaskData); - break; - case CONTINUE: - return 0; - default: - /* - * Encountered invalid opcode. - */ - return VME_INVALID_FILE; - } - - switch (cDataByte) { - case TDI: - - /* - * Left bit shift. Used when performing - * algorithm looping. - */ - - if (g_usFlowControl & SHIFTLEFT) { - ispVMBitShift(SHL, g_usShiftValue); - g_usFlowControl &= ~SHIFTLEFT; - } - - /* - * Right bit shift. Used when performing - * algorithm looping. - */ - - if (g_usFlowControl & SHIFTRIGHT) { - ispVMBitShift(SHR, g_usShiftValue); - g_usFlowControl &= ~SHIFTRIGHT; - } - default: - break; - } - - if (siDataSource) { - g_usDataType |= HEAP_IN; /*restore from memory*/ - } - } - - if (siDataSource) { /*fetch data from heap memory upon return*/ - g_usDataType |= HEAP_IN; - } - - if (cDataByte < 0) { - - /* - * Encountered invalid opcode. - */ - - return VME_INVALID_FILE; - } else { - return 0; - } -} - -/* - * - * ispVMData - * Extract one row of data operand from the current data type opcode. Perform - * the decompression if necessary. Extra RAM is not required for the - * decompression process. The decompression scheme employed in this module - * is on row by row basis. The format of the data stream: - * [compression code][compressed data stream] - * 0x00 --No compression - * 0x01 --Compress by 0x00. - * Example: - * Original stream: 0x000000000000000000000001 - * Compressed stream: 0x01000901 - * Detail: 0x01 is the code, 0x00 is the key, - * 0x09 is the count of 0x00 bytes, - * 0x01 is the uncompressed byte. - * 0x02 --Compress by 0xFF. - * Example: - * Original stream: 0xFFFFFFFFFFFFFFFFFFFFFF01 - * Compressed stream: 0x02FF0901 - * Detail: 0x02 is the code, 0xFF is the key, - * 0x09 is the count of 0xFF bytes, - * 0x01 is the uncompressed byte. - * 0x03 - * : : - * 0xFE -- Compress by nibble blocks. - * Example: - * Original stream: 0x84210842108421084210 - * Compressed stream: 0x0584210 - * Detail: 0x05 is the code, means 5 nibbles block. - * 0x84210 is the 5 nibble blocks. - * The whole row is 80 bits given by g_usiDataSize. - * The number of times the block repeat itself - * is found by g_usiDataSize/(4*0x05) which is 4. - * 0xFF -- Compress by the most frequently happen byte. - * Example: - * Original stream: 0x04020401030904040404 - * Compressed stream: 0xFF04(0,1,0x02,0,1,0x01,1,0x03,1,0x09,0,0,0) - * or: 0xFF044090181C240 - * Detail: 0xFF is the code, 0x04 is the key. - * a bit of 0 represent the key shall be put into - * the current bit position and a bit of 1 - * represent copying the next of 8 bits of data - * in. - * - */ - -void ispVMData(unsigned char *ByteData) -{ - /* 09/11/07 NN added local variables initialization */ - unsigned short size = 0; - unsigned short i, j, m, getData = 0; - unsigned char cDataByte = 0; - unsigned char compress = 0; - unsigned short FFcount = 0; - unsigned char compr_char = 0xFF; - unsigned short index = 0; - signed char compression = 0; - - /*convert number in bits to bytes*/ - if (g_usiDataSize % 8 > 0) { - /* 09/11/07 NN Type cast mismatch variables */ - size = (unsigned short)(g_usiDataSize / 8 + 1); - } else { - /* 09/11/07 NN Type cast mismatch variables */ - size = (unsigned short)(g_usiDataSize / 8); - } - - /* - * If there is compression, then check if compress by key - * of 0x00 or 0xFF or by other keys or by nibble blocks - */ - - if (g_usDataType & COMPRESS) { - compression = 1; - compress = GetByte(); - if ((compress == VAR) && (g_usDataType & HEAP_IN)) { - getData = 1; - g_usDataType &= ~(HEAP_IN); - compress = GetByte(); - } - - switch (compress) { - case 0x00: - /* No compression */ - compression = 0; - break; - case 0x01: - /* Compress by byte 0x00 */ - compr_char = 0x00; - break; - case 0x02: - /* Compress by byte 0xFF */ - compr_char = 0xFF; - break; - case 0xFF: - /* Huffman encoding */ - compr_char = GetByte(); - i = 8; - for (index = 0; index < size; index++) { - ByteData[index] = 0x00; - if (i > 7) { - cDataByte = GetByte(); - i = 0; - } - if ((cDataByte << i++) & 0x80) - m = 8; - else { - ByteData[index] = compr_char; - m = 0; - } - - for (j = 0; j < m; j++) { - if (i > 7) { - cDataByte = GetByte(); - i = 0; - } - ByteData[index] |= - ((cDataByte << i++) & 0x80) >> j; - } - } - size = 0; - break; - default: - for (index = 0; index < size; index++) - ByteData[index] = 0x00; - for (index = 0; index < compress; index++) { - if (index % 2 == 0) - cDataByte = GetByte(); - for (i = 0; i < size * 2 / compress; i++) { - j = (unsigned short)(index + - (i * (unsigned short)compress)); - /*clear the nibble to zero first*/ - if (j%2) { - if (index % 2) - ByteData[j/2] |= - cDataByte & 0xF; - else - ByteData[j/2] |= - cDataByte >> 4; - } else { - if (index % 2) - ByteData[j/2] |= - cDataByte << 4; - else - ByteData[j/2] |= - cDataByte & 0xF0; - } - } - } - size = 0; - break; - } - } - - FFcount = 0; - - /* Decompress by byte 0x00 or 0xFF */ - for (index = 0; index < size; index++) { - if (FFcount <= 0) { - cDataByte = GetByte(); - if ((cDataByte == VAR) && (g_usDataType&HEAP_IN) && - !getData && !(g_usDataType&COMPRESS)) { - getData = 1; - g_usDataType &= ~(HEAP_IN); - cDataByte = GetByte(); - } - ByteData[index] = cDataByte; - if ((compression) && (cDataByte == compr_char)) - /* 09/11/07 NN Type cast mismatch variables */ - FFcount = (unsigned short) ispVMDataSize(); - /*The number of 0xFF or 0x00 bytes*/ - } else { - FFcount--; /*Use up the 0xFF chain first*/ - ByteData[index] = compr_char; - } - } - - if (getData) { - g_usDataType |= HEAP_IN; - getData = 0; - } -} - -/* - * - * ispVMShift - * - * Processes the SDR/XSDR/SIR commands. - * - */ - -signed char ispVMShift(signed char a_cCode) -{ - /* 09/11/07 NN added local variables initialization */ - unsigned short iDataIndex = 0; - unsigned short iReadLoop = 0; - signed char cRetCode = 0; - - cRetCode = 0; - /* 09/11/07 NN Type cast mismatch variables */ - g_usiDataSize = (unsigned short) ispVMDataSize(); - - /*clear the flags first*/ - g_usDataType &= ~(SIR_DATA + EXPRESS + SDR_DATA); - switch (a_cCode) { - case SIR: - g_usDataType |= SIR_DATA; - /* - * 1/15/04 If performing cascading, then go directly to SHIFTIR. - * Else, go to IRPAUSE before going to SHIFTIR - */ - if (g_usFlowControl & CASCADE) { - ispVMStateMachine(SHIFTIR); - } else { - ispVMStateMachine(IRPAUSE); - ispVMStateMachine(SHIFTIR); - if (g_usHeadIR > 0) { - ispVMBypass(HIR, g_usHeadIR); - sclock(); - } - } - break; - case XSDR: - g_usDataType |= EXPRESS; /*mark simultaneous in and out*/ - case SDR: - g_usDataType |= SDR_DATA; - /* - * 1/15/04 If already in SHIFTDR, then do not move state or - * shift in header. This would imply that the previously - * shifted frame was a cascaded frame. - */ - if (g_cCurrentJTAGState != SHIFTDR) { - /* - * 1/15/04 If performing cascading, then go directly - * to SHIFTDR. Else, go to DRPAUSE before going - * to SHIFTDR - */ - if (g_usFlowControl & CASCADE) { - if (g_cCurrentJTAGState == DRPAUSE) { - ispVMStateMachine(SHIFTDR); - /* - * 1/15/04 If cascade flag has been seat - * and the current state is DRPAUSE, - * this implies that the first cascaded - * frame is about to be shifted in. The - * header must be shifted prior to - * shifting the first cascaded frame. - */ - if (g_usHeadDR > 0) { - ispVMBypass(HDR, g_usHeadDR); - sclock(); - } - } else { - ispVMStateMachine(SHIFTDR); - } - } else { - ispVMStateMachine(DRPAUSE); - ispVMStateMachine(SHIFTDR); - if (g_usHeadDR > 0) { - ispVMBypass(HDR, g_usHeadDR); - sclock(); - } - } - } - break; - default: - return VME_INVALID_FILE; - } - - cRetCode = ispVMDataCode(); - - if (cRetCode != 0) { - return VME_INVALID_FILE; - } - -#ifdef DEBUG - printf("%d ", g_usiDataSize); - - if (g_usDataType & TDI_DATA) { - puts("TDI "); - PrintData(g_usiDataSize, g_pucInData); - } - - if (g_usDataType & TDO_DATA) { - puts("\n\t\tTDO "); - PrintData(g_usiDataSize, g_pucOutData); - } - - if (g_usDataType & MASK_DATA) { - puts("\n\t\tMASK "); - PrintData(g_usiDataSize, g_pucOutMaskData); - } - - if (g_usDataType & DMASK_DATA) { - puts("\n\t\tDMASK "); - PrintData(g_usiDataSize, g_pucOutDMaskData); - } - - puts(";\n"); -#endif /* DEBUG */ - - if (g_usDataType & TDO_DATA || g_usDataType & DMASK_DATA) { - if (g_usDataType & DMASK_DATA) { - cRetCode = ispVMReadandSave(g_usiDataSize); - if (!cRetCode) { - if (g_usTailDR > 0) { - sclock(); - ispVMBypass(TDR, g_usTailDR); - } - ispVMStateMachine(DRPAUSE); - ispVMStateMachine(SHIFTDR); - if (g_usHeadDR > 0) { - ispVMBypass(HDR, g_usHeadDR); - sclock(); - } - for (iDataIndex = 0; - iDataIndex < g_usiDataSize / 8 + 1; - iDataIndex++) - g_pucInData[iDataIndex] = - g_pucOutData[iDataIndex]; - g_usDataType &= ~(TDO_DATA + DMASK_DATA); - cRetCode = ispVMSend(g_usiDataSize); - } - } else { - cRetCode = ispVMRead(g_usiDataSize); - if (cRetCode == -1 && g_cVendor == XILINX) { - for (iReadLoop = 0; iReadLoop < 30; - iReadLoop++) { - cRetCode = ispVMRead(g_usiDataSize); - if (!cRetCode) { - break; - } else { - /* Always DRPAUSE */ - ispVMStateMachine(DRPAUSE); - /* - * Bypass other devices - * when appropriate - */ - ispVMBypass(TDR, g_usTailDR); - ispVMStateMachine(g_ucEndDR); - ispVMStateMachine(IDLE); - ispVMDelay(1000); - } - } - } - } - } else { /*TDI only*/ - cRetCode = ispVMSend(g_usiDataSize); - } - - /*transfer the input data to the output buffer for the next verify*/ - if ((g_usDataType & EXPRESS) || (a_cCode == SDR)) { - if (g_pucOutData) { - for (iDataIndex = 0; iDataIndex < g_usiDataSize / 8 + 1; - iDataIndex++) - g_pucOutData[iDataIndex] = - g_pucInData[iDataIndex]; - } - } - - switch (a_cCode) { - case SIR: - /* 1/15/04 If not performing cascading, then shift ENDIR */ - if (!(g_usFlowControl & CASCADE)) { - if (g_usTailIR > 0) { - sclock(); - ispVMBypass(TIR, g_usTailIR); - } - ispVMStateMachine(g_ucEndIR); - } - break; - case XSDR: - case SDR: - /* 1/15/04 If not performing cascading, then shift ENDDR */ - if (!(g_usFlowControl & CASCADE)) { - if (g_usTailDR > 0) { - sclock(); - ispVMBypass(TDR, g_usTailDR); - } - ispVMStateMachine(g_ucEndDR); - } - break; - default: - break; - } - - return cRetCode; -} - -/* - * - * ispVMAmble - * - * This routine is to extract Header and Trailer parameter for SIR and - * SDR operations. - * - * The Header and Trailer parameter are the pre-amble and post-amble bit - * stream need to be shifted into TDI or out of TDO of the devices. Mostly - * is for the purpose of bypassing the leading or trailing devices. ispVM - * supports only shifting data into TDI to bypass the devices. - * - * For a single device, the header and trailer parameters are all set to 0 - * as default by ispVM. If it is for multiple devices, the header and trailer - * value will change as specified by the VME file. - * - */ - -signed char ispVMAmble(signed char Code) -{ - signed char compress = 0; - /* 09/11/07 NN Type cast mismatch variables */ - g_usiDataSize = (unsigned short)ispVMDataSize(); - -#ifdef DEBUG - printf("%d", g_usiDataSize); -#endif /* DEBUG */ - - if (g_usiDataSize) { - - /* - * Discard the TDI byte and set the compression bit in the data - * type register to false if compression is set because TDI data - * after HIR/HDR/TIR/TDR is not compressed. - */ - - GetByte(); - if (g_usDataType & COMPRESS) { - g_usDataType &= ~(COMPRESS); - compress = 1; - } - } - - switch (Code) { - case HIR: - - /* - * Store the maximum size of the HIR buffer. - * Used to convert VME to HEX. - */ - - if (g_usiDataSize > g_usHIRSize) { - g_usHIRSize = g_usiDataSize; - } - - /* - * Assign the HIR value and allocate memory. - */ - - g_usHeadIR = g_usiDataSize; - if (g_usHeadIR) { - ispVMMemManager(HIR, g_usHeadIR); - ispVMData(g_pucHIRData); - -#ifdef DEBUG - puts(" TDI "); - PrintData(g_usHeadIR, g_pucHIRData); -#endif /* DEBUG */ - } - break; - case TIR: - - /* - * Store the maximum size of the TIR buffer. - * Used to convert VME to HEX. - */ - - if (g_usiDataSize > g_usTIRSize) { - g_usTIRSize = g_usiDataSize; - } - - /* - * Assign the TIR value and allocate memory. - */ - - g_usTailIR = g_usiDataSize; - if (g_usTailIR) { - ispVMMemManager(TIR, g_usTailIR); - ispVMData(g_pucTIRData); - -#ifdef DEBUG - puts(" TDI "); - PrintData(g_usTailIR, g_pucTIRData); -#endif /* DEBUG */ - } - break; - case HDR: - - /* - * Store the maximum size of the HDR buffer. - * Used to convert VME to HEX. - */ - - if (g_usiDataSize > g_usHDRSize) { - g_usHDRSize = g_usiDataSize; - } - - /* - * Assign the HDR value and allocate memory. - * - */ - - g_usHeadDR = g_usiDataSize; - if (g_usHeadDR) { - ispVMMemManager(HDR, g_usHeadDR); - ispVMData(g_pucHDRData); - -#ifdef DEBUG - puts(" TDI "); - PrintData(g_usHeadDR, g_pucHDRData); -#endif /* DEBUG */ - } - break; - case TDR: - - /* - * Store the maximum size of the TDR buffer. - * Used to convert VME to HEX. - */ - - if (g_usiDataSize > g_usTDRSize) { - g_usTDRSize = g_usiDataSize; - } - - /* - * Assign the TDR value and allocate memory. - * - */ - - g_usTailDR = g_usiDataSize; - if (g_usTailDR) { - ispVMMemManager(TDR, g_usTailDR); - ispVMData(g_pucTDRData); - -#ifdef DEBUG - puts(" TDI "); - PrintData(g_usTailDR, g_pucTDRData); -#endif /* DEBUG */ - } - break; - default: - break; - } - - /* - * - * Re-enable compression if it was previously set. - * - **/ - - if (compress) { - g_usDataType |= COMPRESS; - } - - if (g_usiDataSize) { - Code = GetByte(); - if (Code == CONTINUE) { - return 0; - } else { - - /* - * Encountered invalid opcode. - */ - - return VME_INVALID_FILE; - } - } - - return 0; -} - -/* - * - * ispVMLoop - * - * Perform the function call upon by the REPEAT opcode. - * Memory is to be allocated to store the entire loop from REPEAT to ENDLOOP. - * After the loop is stored then execution begin. The REPEATLOOP flag is set - * on the g_usFlowControl register to indicate the repeat loop is in session - * and therefore fetch opcode from the memory instead of from the file. - * - */ - -signed char ispVMLoop(unsigned short a_usLoopCount) -{ - /* 09/11/07 NN added local variables initialization */ - signed char cRetCode = 0; - unsigned short iHeapIndex = 0; - unsigned short iLoopIndex = 0; - - g_usShiftValue = 0; - for (iHeapIndex = 0; iHeapIndex < g_iHEAPSize; iHeapIndex++) { - g_pucHeapMemory[iHeapIndex] = GetByte(); - } - - if (g_pucHeapMemory[iHeapIndex - 1] != ENDLOOP) { - return VME_INVALID_FILE; - } - - g_usFlowControl |= REPEATLOOP; - g_usDataType |= HEAP_IN; - - for (iLoopIndex = 0; iLoopIndex < a_usLoopCount; iLoopIndex++) { - g_iHeapCounter = 0; - cRetCode = ispVMCode(); - g_usRepeatLoops++; - if (cRetCode < 0) { - break; - } - } - - g_usDataType &= ~(HEAP_IN); - g_usFlowControl &= ~(REPEATLOOP); - return cRetCode; -} - -/* - * - * ispVMBitShift - * - * Shift the TDI stream left or right by the number of bits. The data in - * *g_pucInData is of the VME format, so the actual shifting is the reverse of - * IEEE 1532 or SVF format. - * - */ - -signed char ispVMBitShift(signed char mode, unsigned short bits) -{ - /* 09/11/07 NN added local variables initialization */ - unsigned short i = 0; - unsigned short size = 0; - unsigned short tmpbits = 0; - - if (g_usiDataSize % 8 > 0) { - /* 09/11/07 NN Type cast mismatch variables */ - size = (unsigned short)(g_usiDataSize / 8 + 1); - } else { - /* 09/11/07 NN Type cast mismatch variables */ - size = (unsigned short)(g_usiDataSize / 8); - } - - switch (mode) { - case SHR: - for (i = 0; i < size; i++) { - if (g_pucInData[i] != 0) { - tmpbits = bits; - while (tmpbits > 0) { - g_pucInData[i] <<= 1; - if (g_pucInData[i] == 0) { - i--; - g_pucInData[i] = 1; - } - tmpbits--; - } - } - } - break; - case SHL: - for (i = 0; i < size; i++) { - if (g_pucInData[i] != 0) { - tmpbits = bits; - while (tmpbits > 0) { - g_pucInData[i] >>= 1; - if (g_pucInData[i] == 0) { - i--; - g_pucInData[i] = 8; - } - tmpbits--; - } - } - } - break; - default: - return VME_INVALID_FILE; - } - - return 0; -} - -/* - * - * ispVMComment - * - * Displays the SVF comments. - * - */ - -void ispVMComment(unsigned short a_usCommentSize) -{ - char cCurByte = 0; - for (; a_usCommentSize > 0; a_usCommentSize--) { - /* - * - * Print character to the terminal. - * - **/ - cCurByte = GetByte(); - vme_out_char(cCurByte); - } - cCurByte = '\n'; - vme_out_char(cCurByte); -} - -/* - * - * ispVMHeader - * - * Iterate the length of the header and discard it. - * - */ - -void ispVMHeader(unsigned short a_usHeaderSize) -{ - for (; a_usHeaderSize > 0; a_usHeaderSize--) { - GetByte(); - } -} - -/* - * - * ispVMCalculateCRC32 - * - * Calculate the 32-bit CRC. - * - */ - -void ispVMCalculateCRC32(unsigned char a_ucData) -{ - /* 09/11/07 NN added local variables initialization */ - unsigned char ucIndex = 0; - unsigned char ucFlipData = 0; - unsigned short usCRCTableEntry = 0; - unsigned int crc_table[16] = { - 0x0000, 0xCC01, 0xD801, - 0x1400, 0xF001, 0x3C00, - 0x2800, 0xE401, 0xA001, - 0x6C00, 0x7800, 0xB401, - 0x5000, 0x9C01, 0x8801, - 0x4400 - }; - - for (ucIndex = 0; ucIndex < 8; ucIndex++) { - ucFlipData <<= 1; - if (a_ucData & 0x01) { - ucFlipData |= 0x01; - } - a_ucData >>= 1; - } - - /* 09/11/07 NN Type cast mismatch variables */ - usCRCTableEntry = (unsigned short)(crc_table[g_usCalculatedCRC & 0xF]); - g_usCalculatedCRC = (unsigned short)((g_usCalculatedCRC >> 4) & 0x0FFF); - g_usCalculatedCRC = (unsigned short)(g_usCalculatedCRC ^ - usCRCTableEntry ^ crc_table[ucFlipData & 0xF]); - usCRCTableEntry = (unsigned short)(crc_table[g_usCalculatedCRC & 0xF]); - g_usCalculatedCRC = (unsigned short)((g_usCalculatedCRC >> 4) & 0x0FFF); - g_usCalculatedCRC = (unsigned short)(g_usCalculatedCRC ^ - usCRCTableEntry ^ crc_table[(ucFlipData >> 4) & 0xF]); -} - -/* - * - * ispVMLCOUNT - * - * Process the intelligent programming loops. - * - */ - -signed char ispVMLCOUNT(unsigned short a_usCountSize) -{ - unsigned short usContinue = 1; - unsigned short usIntelBufferIndex = 0; - unsigned short usCountIndex = 0; - signed char cRetCode = 0; - signed char cRepeatHeap = 0; - signed char cOpcode = 0; - unsigned char ucState = 0; - unsigned short usDelay = 0; - unsigned short usToggle = 0; - - g_usIntelBufferSize = (unsigned short)ispVMDataSize(); - - /* - * Allocate memory for intel buffer. - * - */ - - ispVMMemManager(LHEAP, g_usIntelBufferSize); - - /* - * Store the maximum size of the intelligent buffer. - * Used to convert VME to HEX. - */ - - if (g_usIntelBufferSize > g_usLCOUNTSize) { - g_usLCOUNTSize = g_usIntelBufferSize; - } - - /* - * Copy intel data to the buffer. - */ - - for (usIntelBufferIndex = 0; usIntelBufferIndex < g_usIntelBufferSize; - usIntelBufferIndex++) { - g_pucIntelBuffer[usIntelBufferIndex] = GetByte(); - } - - /* - * Set the data type register to get data from the intelligent - * data buffer. - */ - - g_usDataType |= LHEAP_IN; - - /* - * - * If the HEAP_IN flag is set, temporarily unset the flag so data will be - * retrieved from the status buffer. - * - **/ - - if (g_usDataType & HEAP_IN) { - g_usDataType &= ~HEAP_IN; - cRepeatHeap = 1; - } - -#ifdef DEBUG - printf("LCOUNT %d;\n", a_usCountSize); -#endif /* DEBUG */ - - /* - * Iterate through the intelligent programming command. - */ - - for (usCountIndex = 0; usCountIndex < a_usCountSize; usCountIndex++) { - - /* - * - * Initialize the intel data index to 0 before each iteration. - * - **/ - - g_usIntelDataIndex = 0; - cOpcode = 0; - ucState = 0; - usDelay = 0; - usToggle = 0; - usContinue = 1; - - /* - * - * Begin looping through all the VME opcodes. - * - */ - /* - * 4/1/09 Nguyen replaced the recursive function call codes on - * the ispVMLCOUNT function - * - */ - while (usContinue) { - cOpcode = GetByte(); - switch (cOpcode) { - case HIR: - case TIR: - case HDR: - case TDR: - /* - * Set the header/trailer of the device in order - * to bypass successfully. - */ - - ispVMAmble(cOpcode); - break; - case STATE: - - /* - * Step the JTAG state machine. - */ - - ucState = GetByte(); - /* - * Step the JTAG state machine to DRCAPTURE - * to support Looping. - */ - - if ((g_usDataType & LHEAP_IN) && - (ucState == DRPAUSE) && - (g_cCurrentJTAGState == ucState)) { - ispVMStateMachine(DRCAPTURE); - } - ispVMStateMachine(ucState); -#ifdef DEBUG - printf("LDELAY %s ", GetState(ucState)); -#endif /* DEBUG */ - break; - case SIR: -#ifdef DEBUG - printf("SIR "); -#endif /* DEBUG */ - /* - * Shift in data into the device. - */ - - cRetCode = ispVMShift(cOpcode); - break; - case SDR: - -#ifdef DEBUG - printf("LSDR "); -#endif /* DEBUG */ - /* - * Shift in data into the device. - */ - - cRetCode = ispVMShift(cOpcode); - break; - case WAIT: - - /* - * - * Observe delay. - * - */ - - usDelay = (unsigned short)ispVMDataSize(); - ispVMDelay(usDelay); - -#ifdef DEBUG - if (usDelay & 0x8000) { - - /* - * Since MSB is set, the delay time must - * be decoded to millisecond. The - * SVF2VME encodes the MSB to represent - * millisecond. - */ - - usDelay &= ~0x8000; - printf("%.2E SEC;\n", - (float) usDelay / 1000); - } else { - /* - * Since MSB is not set, the delay time - * is given as microseconds. - */ - - printf("%.2E SEC;\n", - (float) usDelay / 1000000); - } -#endif /* DEBUG */ - break; - case TCK: - - /* - * Issue clock toggles. - */ - - usToggle = (unsigned short)ispVMDataSize(); - ispVMClocks(usToggle); - -#ifdef DEBUG - printf("RUNTEST %d TCK;\n", usToggle); -#endif /* DEBUG */ - break; - case ENDLOOP: - - /* - * Exit point from processing loops. - */ - usContinue = 0; - break; - - case COMMENT: - - /* - * Display comment. - */ - - ispVMComment((unsigned short) ispVMDataSize()); - break; - case ispEN: - ucState = GetByte(); - if ((ucState == ON) || (ucState == 0x01)) - writePort(g_ucPinENABLE, 0x01); - else - writePort(g_ucPinENABLE, 0x00); - ispVMDelay(1); - break; - case TRST: - if (GetByte() == 0x01) - writePort(g_ucPinTRST, 0x01); - else - writePort(g_ucPinTRST, 0x00); - ispVMDelay(1); - break; - default: - - /* - * Invalid opcode encountered. - */ - - debug("\nINVALID OPCODE: 0x%.2X\n", cOpcode); - - return VME_INVALID_FILE; - } - } - if (cRetCode >= 0) { - /* - * Break if intelligent programming is successful. - */ - - break; - } - - } - /* - * If HEAP_IN flag was temporarily disabled, - * re-enable it before exiting - */ - - if (cRepeatHeap) { - g_usDataType |= HEAP_IN; - } - - /* - * Set the data type register to not get data from the - * intelligent data buffer. - */ - - g_usDataType &= ~LHEAP_IN; - return cRetCode; -} -/* - * - * ispVMClocks - * - * Applies the specified number of pulses to TCK. - * - */ - -void ispVMClocks(unsigned short Clocks) -{ - unsigned short iClockIndex = 0; - for (iClockIndex = 0; iClockIndex < Clocks; iClockIndex++) { - sclock(); - } -} - -/* - * - * ispVMBypass - * - * This procedure takes care of the HIR, HDR, TIR, TDR for the - * purpose of putting the other devices into Bypass mode. The - * current state is checked to find out if it is at DRPAUSE or - * IRPAUSE. If it is at DRPAUSE, perform bypass register scan. - * If it is at IRPAUSE, scan into instruction registers the bypass - * instruction. - * - */ - -void ispVMBypass(signed char ScanType, unsigned short Bits) -{ - /* 09/11/07 NN added local variables initialization */ - unsigned short iIndex = 0; - unsigned short iSourceIndex = 0; - unsigned char cBitState = 0; - unsigned char cCurByte = 0; - unsigned char *pcSource = NULL; - - if (Bits <= 0) { - return; - } - - switch (ScanType) { - case HIR: - pcSource = g_pucHIRData; - break; - case TIR: - pcSource = g_pucTIRData; - break; - case HDR: - pcSource = g_pucHDRData; - break; - case TDR: - pcSource = g_pucTDRData; - break; - default: - break; - } - - iSourceIndex = 0; - cBitState = 0; - for (iIndex = 0; iIndex < Bits - 1; iIndex++) { - /* Scan instruction or bypass register */ - if (iIndex % 8 == 0) { - cCurByte = pcSource[iSourceIndex++]; - } - cBitState = (unsigned char) (((cCurByte << iIndex % 8) & 0x80) - ? 0x01 : 0x00); - writePort(g_ucPinTDI, cBitState); - sclock(); - } - - if (iIndex % 8 == 0) { - cCurByte = pcSource[iSourceIndex++]; - } - - cBitState = (unsigned char) (((cCurByte << iIndex % 8) & 0x80) - ? 0x01 : 0x00); - writePort(g_ucPinTDI, cBitState); -} - -/* - * - * ispVMStateMachine - * - * This procedure steps all devices in the daisy chain from a given - * JTAG state to the next desirable state. If the next state is TLR, - * the JTAG state machine is brute forced into TLR by driving TMS - * high and pulse TCK 6 times. - * - */ - -void ispVMStateMachine(signed char cNextJTAGState) -{ - /* 09/11/07 NN added local variables initialization */ - signed char cPathIndex = 0; - signed char cStateIndex = 0; - - if ((g_cCurrentJTAGState == cNextJTAGState) && - (cNextJTAGState != RESET)) { - return; - } - - for (cStateIndex = 0; cStateIndex < 25; cStateIndex++) { - if ((g_cCurrentJTAGState == - g_JTAGTransistions[cStateIndex].CurState) && - (cNextJTAGState == - g_JTAGTransistions[cStateIndex].NextState)) { - break; - } - } - - g_cCurrentJTAGState = cNextJTAGState; - for (cPathIndex = 0; - cPathIndex < g_JTAGTransistions[cStateIndex].Pulses; - cPathIndex++) { - if ((g_JTAGTransistions[cStateIndex].Pattern << cPathIndex) - & 0x80) { - writePort(g_ucPinTMS, (unsigned char) 0x01); - } else { - writePort(g_ucPinTMS, (unsigned char) 0x00); - } - sclock(); - } - - writePort(g_ucPinTDI, 0x00); - writePort(g_ucPinTMS, 0x00); -} - -/* - * - * ispVMStart - * - * Enable the port to the device and set the state to RESET (TLR). - * - */ - -void ispVMStart(void) -{ -#ifdef DEBUG - printf("// ISPVM EMBEDDED ADDED\n"); - printf("STATE RESET;\n"); -#endif - g_usFlowControl = 0; - g_usDataType = g_uiChecksumIndex = g_cCurrentJTAGState = 0; - g_usHeadDR = g_usHeadIR = g_usTailDR = g_usTailIR = 0; - g_usMaxSize = g_usShiftValue = g_usRepeatLoops = 0; - g_usTDOSize = g_usMASKSize = g_usTDISize = 0; - g_usDMASKSize = g_usLCOUNTSize = g_usHDRSize = 0; - g_usTDRSize = g_usHIRSize = g_usTIRSize = g_usHeapSize = 0; - g_pLVDSList = NULL; - g_usLVDSPairCount = 0; - previous_size = 0; - - ispVMStateMachine(RESET); /*step devices to RESET state*/ -} - -/* - * - * ispVMEnd - * - * Set the state of devices to RESET to enable the devices and disable - * the port. - * - */ - -void ispVMEnd(void) -{ -#ifdef DEBUG - printf("// ISPVM EMBEDDED ADDED\n"); - printf("STATE RESET;\n"); - printf("RUNTEST 1.00E-001 SEC;\n"); -#endif - - ispVMStateMachine(RESET); /*step devices to RESET state */ - ispVMDelay(1000); /*wake up devices*/ -} - -/* - * - * ispVMSend - * - * Send the TDI data stream to devices. The data stream can be - * instructions or data. - * - */ - -signed char ispVMSend(unsigned short a_usiDataSize) -{ - /* 09/11/07 NN added local variables initialization */ - unsigned short iIndex = 0; - unsigned short iInDataIndex = 0; - unsigned char cCurByte = 0; - unsigned char cBitState = 0; - - for (iIndex = 0; iIndex < a_usiDataSize - 1; iIndex++) { - if (iIndex % 8 == 0) { - cCurByte = g_pucInData[iInDataIndex++]; - } - cBitState = (unsigned char)(((cCurByte << iIndex % 8) & 0x80) - ? 0x01 : 0x00); - writePort(g_ucPinTDI, cBitState); - sclock(); - } - - if (iIndex % 8 == 0) { - /* Take care of the last bit */ - cCurByte = g_pucInData[iInDataIndex]; - } - - cBitState = (unsigned char) (((cCurByte << iIndex % 8) & 0x80) - ? 0x01 : 0x00); - - writePort(g_ucPinTDI, cBitState); - if (g_usFlowControl & CASCADE) { - /*1/15/04 Clock in last bit for the first n-1 cascaded frames */ - sclock(); - } - - return 0; -} - -/* - * - * ispVMRead - * - * Read the data stream from devices and verify. - * - */ - -signed char ispVMRead(unsigned short a_usiDataSize) -{ - /* 09/11/07 NN added local variables initialization */ - unsigned short usDataSizeIndex = 0; - unsigned short usErrorCount = 0; - unsigned short usLastBitIndex = 0; - unsigned char cDataByte = 0; - unsigned char cMaskByte = 0; - unsigned char cInDataByte = 0; - unsigned char cCurBit = 0; - unsigned char cByteIndex = 0; - unsigned short usBufferIndex = 0; - unsigned char ucDisplayByte = 0x00; - unsigned char ucDisplayFlag = 0x01; - char StrChecksum[256] = {0}; - unsigned char g_usCalculateChecksum = 0x00; - - /* 09/11/07 NN Type cast mismatch variables */ - usLastBitIndex = (unsigned short)(a_usiDataSize - 1); - -#ifndef DEBUG - /* - * If mask is not all zeros, then set the display flag to 0x00, - * otherwise it shall be set to 0x01 to indicate that data read - * from the device shall be displayed. If DEBUG is defined, - * always display data. - */ - - for (usDataSizeIndex = 0; usDataSizeIndex < (a_usiDataSize + 7) / 8; - usDataSizeIndex++) { - if (g_usDataType & MASK_DATA) { - if (g_pucOutMaskData[usDataSizeIndex] != 0x00) { - ucDisplayFlag = 0x00; - break; - } - } else if (g_usDataType & CMASK_DATA) { - g_usCalculateChecksum = 0x01; - ucDisplayFlag = 0x00; - break; - } else { - ucDisplayFlag = 0x00; - break; - } - } -#endif /* DEBUG */ - - /* - * - * Begin shifting data in and out of the device. - * - **/ - - for (usDataSizeIndex = 0; usDataSizeIndex < a_usiDataSize; - usDataSizeIndex++) { - if (cByteIndex == 0) { - - /* - * Grab byte from TDO buffer. - */ - - if (g_usDataType & TDO_DATA) { - cDataByte = g_pucOutData[usBufferIndex]; - } - - /* - * Grab byte from MASK buffer. - */ - - if (g_usDataType & MASK_DATA) { - cMaskByte = g_pucOutMaskData[usBufferIndex]; - } else { - cMaskByte = 0xFF; - } - - /* - * Grab byte from CMASK buffer. - */ - - if (g_usDataType & CMASK_DATA) { - cMaskByte = 0x00; - g_usCalculateChecksum = 0x01; - } - - /* - * Grab byte from TDI buffer. - */ - - if (g_usDataType & TDI_DATA) { - cInDataByte = g_pucInData[usBufferIndex]; - } - - usBufferIndex++; - } - - cCurBit = readPort(); - - if (ucDisplayFlag) { - ucDisplayByte <<= 1; - ucDisplayByte |= cCurBit; - } - - /* - * Check if data read from port matches with expected TDO. - */ - - if (g_usDataType & TDO_DATA) { - /* 08/28/08 NN Added Calculate checksum support. */ - if (g_usCalculateChecksum) { - if (cCurBit == 0x01) - g_usChecksum += - (1 << (g_uiChecksumIndex % 8)); - g_uiChecksumIndex++; - } else { - if ((((cMaskByte << cByteIndex) & 0x80) - ? 0x01 : 0x00)) { - if (cCurBit != (unsigned char) - (((cDataByte << cByteIndex) & 0x80) - ? 0x01 : 0x00)) { - usErrorCount++; - } - } - } - } - - /* - * Write TDI data to the port. - */ - - writePort(g_ucPinTDI, - (unsigned char)(((cInDataByte << cByteIndex) & 0x80) - ? 0x01 : 0x00)); - - if (usDataSizeIndex < usLastBitIndex) { - - /* - * Clock data out from the data shift register. - */ - - sclock(); - } else if (g_usFlowControl & CASCADE) { - - /* - * Clock in last bit for the first N - 1 cascaded frames - */ - - sclock(); - } - - /* - * Increment the byte index. If it exceeds 7, then reset it back - * to zero. - */ - - cByteIndex++; - if (cByteIndex >= 8) { - if (ucDisplayFlag) { - - /* - * Store displayed data in the TDO buffer. By reusing - * the TDO buffer to store displayed data, there is no - * need to allocate a buffer simply to hold display - * data. This will not cause any false verification - * errors because the true TDO byte has already - * been consumed. - */ - - g_pucOutData[usBufferIndex - 1] = ucDisplayByte; - ucDisplayByte = 0; - } - - cByteIndex = 0; - } - /* 09/12/07 Nguyen changed to display the 1 bit expected data */ - else if (a_usiDataSize == 1) { - if (ucDisplayFlag) { - - /* - * Store displayed data in the TDO buffer. - * By reusing the TDO buffer to store displayed - * data, there is no need to allocate - * a buffer simply to hold display data. This - * will not cause any false verification errors - * because the true TDO byte has already - * been consumed. - */ - - /* - * Flip ucDisplayByte and store it in cDataByte. - */ - cDataByte = 0x00; - for (usBufferIndex = 0; usBufferIndex < 8; - usBufferIndex++) { - cDataByte <<= 1; - if (ucDisplayByte & 0x01) { - cDataByte |= 0x01; - } - ucDisplayByte >>= 1; - } - g_pucOutData[0] = cDataByte; - ucDisplayByte = 0; - } - - cByteIndex = 0; - } - } - - if (ucDisplayFlag) { - -#ifdef DEBUG - debug("RECEIVED TDO ("); -#else - vme_out_string("Display Data: 0x"); -#endif /* DEBUG */ - - /* 09/11/07 NN Type cast mismatch variables */ - for (usDataSizeIndex = (unsigned short) - ((a_usiDataSize + 7) / 8); - usDataSizeIndex > 0 ; usDataSizeIndex--) { - cMaskByte = g_pucOutData[usDataSizeIndex - 1]; - cDataByte = 0x00; - - /* - * Flip cMaskByte and store it in cDataByte. - */ - - for (usBufferIndex = 0; usBufferIndex < 8; - usBufferIndex++) { - cDataByte <<= 1; - if (cMaskByte & 0x01) { - cDataByte |= 0x01; - } - cMaskByte >>= 1; - } -#ifdef DEBUG - printf("%.2X", cDataByte); - if ((((a_usiDataSize + 7) / 8) - usDataSizeIndex) - % 40 == 39) { - printf("\n\t\t"); - } -#else - vme_out_hex(cDataByte); -#endif /* DEBUG */ - } - -#ifdef DEBUG - printf(")\n\n"); -#else - vme_out_string("\n\n"); -#endif /* DEBUG */ - /* 09/02/08 Nguyen changed to display the data Checksum */ - if (g_usChecksum != 0) { - g_usChecksum &= 0xFFFF; - sprintf(StrChecksum, "Data Checksum: %.4lX\n\n", - g_usChecksum); - vme_out_string(StrChecksum); - g_usChecksum = 0; - } - } - - if (usErrorCount > 0) { - if (g_usFlowControl & VERIFYUES) { - vme_out_string( - "USERCODE verification failed. " - "Continue programming......\n\n"); - g_usFlowControl &= ~(VERIFYUES); - return 0; - } else { - -#ifdef DEBUG - printf("TOTAL ERRORS: %d\n", usErrorCount); -#endif /* DEBUG */ - - return VME_VERIFICATION_FAILURE; - } - } else { - if (g_usFlowControl & VERIFYUES) { - vme_out_string("USERCODE verification passed. " - "Programming aborted.\n\n"); - g_usFlowControl &= ~(VERIFYUES); - return 1; - } else { - return 0; - } - } -} - -/* - * - * ispVMReadandSave - * - * Support dynamic I/O. - * - */ - -signed char ispVMReadandSave(unsigned short int a_usiDataSize) -{ - /* 09/11/07 NN added local variables initialization */ - unsigned short int usDataSizeIndex = 0; - unsigned short int usLastBitIndex = 0; - unsigned short int usBufferIndex = 0; - unsigned short int usOutBitIndex = 0; - unsigned short int usLVDSIndex = 0; - unsigned char cDataByte = 0; - unsigned char cDMASKByte = 0; - unsigned char cInDataByte = 0; - unsigned char cCurBit = 0; - unsigned char cByteIndex = 0; - signed char cLVDSByteIndex = 0; - - /* 09/11/07 NN Type cast mismatch variables */ - usLastBitIndex = (unsigned short) (a_usiDataSize - 1); - - /* - * - * Iterate through the data bits. - * - */ - - for (usDataSizeIndex = 0; usDataSizeIndex < a_usiDataSize; - usDataSizeIndex++) { - if (cByteIndex == 0) { - - /* - * Grab byte from DMASK buffer. - */ - - if (g_usDataType & DMASK_DATA) { - cDMASKByte = g_pucOutDMaskData[usBufferIndex]; - } else { - cDMASKByte = 0x00; - } - - /* - * Grab byte from TDI buffer. - */ - - if (g_usDataType & TDI_DATA) { - cInDataByte = g_pucInData[usBufferIndex]; - } - - usBufferIndex++; - } - - cCurBit = readPort(); - cDataByte = (unsigned char)(((cInDataByte << cByteIndex) & 0x80) - ? 0x01 : 0x00); - - /* - * Initialize the byte to be zero. - */ - - if (usOutBitIndex % 8 == 0) { - g_pucOutData[usOutBitIndex / 8] = 0x00; - } - - /* - * Use TDI, DMASK, and device TDO to create new TDI (actually - * stored in g_pucOutData). - */ - - if ((((cDMASKByte << cByteIndex) & 0x80) ? 0x01 : 0x00)) { - - if (g_pLVDSList) { - for (usLVDSIndex = 0; - usLVDSIndex < g_usLVDSPairCount; - usLVDSIndex++) { - if (g_pLVDSList[usLVDSIndex]. - usNegativeIndex == - usDataSizeIndex) { - g_pLVDSList[usLVDSIndex]. - ucUpdate = 0x01; - break; - } - } - } - - /* - * DMASK bit is 1, use TDI. - */ - - g_pucOutData[usOutBitIndex / 8] |= (unsigned char) - (((cDataByte & 0x1) ? 0x01 : 0x00) << - (7 - usOutBitIndex % 8)); - } else { - - /* - * DMASK bit is 0, use device TDO. - */ - - g_pucOutData[usOutBitIndex / 8] |= (unsigned char) - (((cCurBit & 0x1) ? 0x01 : 0x00) << - (7 - usOutBitIndex % 8)); - } - - /* - * Shift in TDI in order to get TDO out. - */ - - usOutBitIndex++; - writePort(g_ucPinTDI, cDataByte); - if (usDataSizeIndex < usLastBitIndex) { - sclock(); - } - - /* - * Increment the byte index. If it exceeds 7, then reset it back - * to zero. - */ - - cByteIndex++; - if (cByteIndex >= 8) { - cByteIndex = 0; - } - } - - /* - * If g_pLVDSList exists and pairs need updating, then update - * the negative-pair to receive the flipped positive-pair value. - */ - - if (g_pLVDSList) { - for (usLVDSIndex = 0; usLVDSIndex < g_usLVDSPairCount; - usLVDSIndex++) { - if (g_pLVDSList[usLVDSIndex].ucUpdate) { - - /* - * Read the positive value and flip it. - */ - - cDataByte = (unsigned char) - (((g_pucOutData[g_pLVDSList[usLVDSIndex]. - usPositiveIndex / 8] - << (g_pLVDSList[usLVDSIndex]. - usPositiveIndex % 8)) & 0x80) ? - 0x01 : 0x00); - /* 09/11/07 NN Type cast mismatch variables */ - cDataByte = (unsigned char) (!cDataByte); - - /* - * Get the byte that needs modification. - */ - - cInDataByte = - g_pucOutData[g_pLVDSList[usLVDSIndex]. - usNegativeIndex / 8]; - - if (cDataByte) { - - /* - * Copy over the current byte and - * set the negative bit to 1. - */ - - cDataByte = 0x00; - for (cLVDSByteIndex = 7; - cLVDSByteIndex >= 0; - cLVDSByteIndex--) { - cDataByte <<= 1; - if (7 - - (g_pLVDSList[usLVDSIndex]. - usNegativeIndex % 8) == - cLVDSByteIndex) { - - /* - * Set negative bit to 1 - */ - - cDataByte |= 0x01; - } else if (cInDataByte & 0x80) { - cDataByte |= 0x01; - } - - cInDataByte <<= 1; - } - - /* - * Store the modified byte. - */ - - g_pucOutData[g_pLVDSList[usLVDSIndex]. - usNegativeIndex / 8] = cDataByte; - } else { - - /* - * Copy over the current byte and set - * the negative bit to 0. - */ - - cDataByte = 0x00; - for (cLVDSByteIndex = 7; - cLVDSByteIndex >= 0; - cLVDSByteIndex--) { - cDataByte <<= 1; - if (7 - - (g_pLVDSList[usLVDSIndex]. - usNegativeIndex % 8) == - cLVDSByteIndex) { - - /* - * Set negative bit to 0 - */ - - cDataByte |= 0x00; - } else if (cInDataByte & 0x80) { - cDataByte |= 0x01; - } - - cInDataByte <<= 1; - } - - /* - * Store the modified byte. - */ - - g_pucOutData[g_pLVDSList[usLVDSIndex]. - usNegativeIndex / 8] = cDataByte; - } - - break; - } - } - } - - return 0; -} - -signed char ispVMProcessLVDS(unsigned short a_usLVDSCount) -{ - unsigned short usLVDSIndex = 0; - - /* - * Allocate memory to hold LVDS pairs. - */ - - ispVMMemManager(LVDS, a_usLVDSCount); - g_usLVDSPairCount = a_usLVDSCount; - -#ifdef DEBUG - printf("LVDS %d (", a_usLVDSCount); -#endif /* DEBUG */ - - /* - * Iterate through each given LVDS pair. - */ - - for (usLVDSIndex = 0; usLVDSIndex < g_usLVDSPairCount; usLVDSIndex++) { - - /* - * Assign the positive and negative indices of the LVDS pair. - */ - - /* 09/11/07 NN Type cast mismatch variables */ - g_pLVDSList[usLVDSIndex].usPositiveIndex = - (unsigned short) ispVMDataSize(); - /* 09/11/07 NN Type cast mismatch variables */ - g_pLVDSList[usLVDSIndex].usNegativeIndex = - (unsigned short)ispVMDataSize(); - -#ifdef DEBUG - if (usLVDSIndex < g_usLVDSPairCount - 1) { - printf("%d:%d, ", - g_pLVDSList[usLVDSIndex].usPositiveIndex, - g_pLVDSList[usLVDSIndex].usNegativeIndex); - } else { - printf("%d:%d", - g_pLVDSList[usLVDSIndex].usPositiveIndex, - g_pLVDSList[usLVDSIndex].usNegativeIndex); - } -#endif /* DEBUG */ - - } - -#ifdef DEBUG - printf(");\n"); -#endif /* DEBUG */ - - return 0; -} diff --git a/drivers/fpga/lattice.c b/drivers/fpga/lattice.c deleted file mode 100644 index 29cf2f60974..00000000000 --- a/drivers/fpga/lattice.c +++ /dev/null @@ -1,379 +0,0 @@ -// SPDX-License-Identifier: GPL-2.0+ -/* - * (C) Copyright 2010 - * Stefano Babic, DENX Software Engineering, sbabic@denx.de. - * - * (C) Copyright 2002 - * Rich Ireland, Enterasys Networks, rireland@enterasys.com. - * - * ispVM functions adapted from Lattice's ispmVMEmbedded code: - * Copyright 2009 Lattice Semiconductor Corp. - */ - -#include -#include -#include -#include -#include - -static lattice_board_specific_func *pfns; -static const char *fpga_image; -static unsigned long read_bytes; -static unsigned long bufsize; -static unsigned short expectedCRC; - -/* - * External variables and functions declared in ivm_core.c module. - */ -extern unsigned short g_usCalculatedCRC; -extern unsigned short g_usDataType; -extern unsigned char *g_pucIntelBuffer; -extern unsigned char *g_pucHeapMemory; -extern unsigned short g_iHeapCounter; -extern unsigned short g_iHEAPSize; -extern unsigned short g_usIntelDataIndex; -extern unsigned short g_usIntelBufferSize; -extern char *const g_szSupportedVersions[]; - -/* - * ispVMDelay - * - * Users must implement a delay to observe a_usTimeDelay, where - * bit 15 of the a_usTimeDelay defines the unit. - * 1 = milliseconds - * 0 = microseconds - * Example: - * a_usTimeDelay = 0x0001 = 1 microsecond delay. - * a_usTimeDelay = 0x8001 = 1 millisecond delay. - * - * This subroutine is called upon to provide a delay from 1 millisecond to a few - * hundreds milliseconds each time. - * It is understood that due to a_usTimeDelay is defined as unsigned short, a 16 - * bits integer, this function is restricted to produce a delay to 64000 - * micro-seconds or 32000 milli-second maximum. The VME file will never pass on - * to this function a delay time > those maximum number. If it needs more than - * those maximum, the VME file will launch the delay function several times to - * realize a larger delay time cummulatively. - * It is perfectly alright to provide a longer delay than required. It is not - * acceptable if the delay is shorter. - */ -void ispVMDelay(unsigned short delay) -{ - if (delay & 0x8000) - delay = (delay & ~0x8000) * 1000; - udelay(delay); -} - -void writePort(unsigned char a_ucPins, unsigned char a_ucValue) -{ - a_ucValue = a_ucValue ? 1 : 0; - - switch (a_ucPins) { - case g_ucPinTDI: - pfns->jtag_set_tdi(a_ucValue); - break; - case g_ucPinTCK: - pfns->jtag_set_tck(a_ucValue); - break; - case g_ucPinTMS: - pfns->jtag_set_tms(a_ucValue); - break; - default: - printf("%s: requested unknown pin\n", __func__); - } -} - -unsigned char readPort(void) -{ - return pfns->jtag_get_tdo(); -} - -void sclock(void) -{ - writePort(g_ucPinTCK, 0x01); - writePort(g_ucPinTCK, 0x00); -} - -void calibration(void) -{ - /* Apply 2 pulses to TCK. */ - writePort(g_ucPinTCK, 0x00); - writePort(g_ucPinTCK, 0x01); - writePort(g_ucPinTCK, 0x00); - writePort(g_ucPinTCK, 0x01); - writePort(g_ucPinTCK, 0x00); - - ispVMDelay(0x8001); - - /* Apply 2 pulses to TCK. */ - writePort(g_ucPinTCK, 0x01); - writePort(g_ucPinTCK, 0x00); - writePort(g_ucPinTCK, 0x01); - writePort(g_ucPinTCK, 0x00); -} - -/* - * GetByte - * - * Returns a byte to the caller. The returned byte depends on the - * g_usDataType register. If the HEAP_IN bit is set, then the byte - * is returned from the HEAP. If the LHEAP_IN bit is set, then - * the byte is returned from the intelligent buffer. Otherwise, - * the byte is returned directly from the VME file. - */ -unsigned char GetByte(void) -{ - unsigned char ucData; - unsigned int block_size = 4 * 1024; - - if (g_usDataType & HEAP_IN) { - - /* - * Get data from repeat buffer. - */ - - if (g_iHeapCounter > g_iHEAPSize) { - - /* - * Data over-run. - */ - - return 0xFF; - } - - ucData = g_pucHeapMemory[g_iHeapCounter++]; - } else if (g_usDataType & LHEAP_IN) { - - /* - * Get data from intel buffer. - */ - - if (g_usIntelDataIndex >= g_usIntelBufferSize) { - return 0xFF; - } - - ucData = g_pucIntelBuffer[g_usIntelDataIndex++]; - } else { - if (read_bytes == bufsize) { - return 0xFF; - } - ucData = *fpga_image++; - read_bytes++; - - if (!(read_bytes % block_size)) { - printf("Downloading FPGA %ld/%ld completed\r", - read_bytes, - bufsize); - } - - if (expectedCRC != 0) { - ispVMCalculateCRC32(ucData); - } - } - - return ucData; -} - -signed char ispVM(void) -{ - char szFileVersion[9] = { 0 }; - signed char cRetCode = 0; - signed char cIndex = 0; - signed char cVersionIndex = 0; - unsigned char ucReadByte = 0; - unsigned short crc; - - g_pucHeapMemory = NULL; - g_iHeapCounter = 0; - g_iHEAPSize = 0; - g_usIntelDataIndex = 0; - g_usIntelBufferSize = 0; - g_usCalculatedCRC = 0; - expectedCRC = 0; - ucReadByte = GetByte(); - switch (ucReadByte) { - case FILE_CRC: - crc = (unsigned char)GetByte(); - crc <<= 8; - crc |= GetByte(); - expectedCRC = crc; - - for (cIndex = 0; cIndex < 8; cIndex++) - szFileVersion[cIndex] = GetByte(); - - break; - default: - szFileVersion[0] = (signed char) ucReadByte; - for (cIndex = 1; cIndex < 8; cIndex++) - szFileVersion[cIndex] = GetByte(); - - break; - } - - /* - * - * Compare the VME file version against the supported version. - * - */ - - for (cVersionIndex = 0; g_szSupportedVersions[cVersionIndex] != 0; - cVersionIndex++) { - for (cIndex = 0; cIndex < 8; cIndex++) { - if (szFileVersion[cIndex] != - g_szSupportedVersions[cVersionIndex][cIndex]) { - cRetCode = VME_VERSION_FAILURE; - break; - } - cRetCode = 0; - } - - if (cRetCode == 0) { - break; - } - } - - if (cRetCode < 0) { - return VME_VERSION_FAILURE; - } - - printf("VME file checked: starting downloading to FPGA\n"); - - ispVMStart(); - - cRetCode = ispVMCode(); - - ispVMEnd(); - ispVMFreeMem(); - puts("\n"); - - if (cRetCode == 0 && expectedCRC != 0 && - (expectedCRC != g_usCalculatedCRC)) { - printf("Expected CRC: 0x%.4X\n", expectedCRC); - printf("Calculated CRC: 0x%.4X\n", g_usCalculatedCRC); - return VME_CRC_FAILURE; - } - return cRetCode; -} - -static int lattice_validate(Lattice_desc *desc, const char *fn) -{ - int ret_val = false; - - if (desc) { - if ((desc->family > min_lattice_type) && - (desc->family < max_lattice_type)) { - if ((desc->iface > min_lattice_iface_type) && - (desc->iface < max_lattice_iface_type)) { - if (desc->size) { - ret_val = true; - } else { - printf("%s: NULL part size\n", fn); - } - } else { - printf("%s: Invalid Interface type, %d\n", - fn, desc->iface); - } - } else { - printf("%s: Invalid family type, %d\n", - fn, desc->family); - } - } else { - printf("%s: NULL descriptor!\n", fn); - } - - return ret_val; -} - -int lattice_load(Lattice_desc *desc, const void *buf, size_t bsize) -{ - int ret_val = FPGA_FAIL; - - if (!lattice_validate(desc, (char *)__func__)) { - printf("%s: Invalid device descriptor\n", __func__); - } else { - pfns = desc->iface_fns; - - switch (desc->family) { - case Lattice_XP2: - fpga_image = buf; - read_bytes = 0; - bufsize = bsize; - debug("%s: Launching the Lattice ISPVME Loader:" - " addr %p size 0x%lx...\n", - __func__, fpga_image, bufsize); - ret_val = ispVM(); - if (ret_val) - printf("%s: error %d downloading FPGA image\n", - __func__, ret_val); - else - puts("FPGA downloaded successfully\n"); - break; - default: - printf("%s: Unsupported family type, %d\n", - __func__, desc->family); - } - } - - return ret_val; -} - -int lattice_dump(Lattice_desc *desc, const void *buf, size_t bsize) -{ - puts("Dump not supported for Lattice FPGA\n"); - - return FPGA_FAIL; - -} - -int lattice_info(Lattice_desc *desc) -{ - int ret_val = FPGA_FAIL; - - if (lattice_validate(desc, (char *)__func__)) { - printf("Family: \t"); - switch (desc->family) { - case Lattice_XP2: - puts("XP2\n"); - break; - /* Add new family types here */ - default: - printf("Unknown family type, %d\n", desc->family); - } - - puts("Interface type:\t"); - switch (desc->iface) { - case lattice_jtag_mode: - puts("JTAG Mode\n"); - break; - /* Add new interface types here */ - default: - printf("Unsupported interface type, %d\n", desc->iface); - } - - printf("Device Size: \t%zu bytes\n", - desc->size); - - if (desc->iface_fns) { - printf("Device Function Table @ 0x%p\n", - desc->iface_fns); - switch (desc->family) { - case Lattice_XP2: - break; - /* Add new family types here */ - default: - break; - } - } else { - puts("No Device Function Table.\n"); - } - - if (desc->desc) - printf("Model: \t%s\n", desc->desc); - - ret_val = FPGA_SUCCESS; - } else { - printf("%s: Invalid device descriptor\n", __func__); - } - - return ret_val; -} diff --git a/include/fpga.h b/include/fpga.h index a144238e66a..20153b2082a 100644 --- a/include/fpga.h +++ b/include/fpga.h @@ -25,7 +25,6 @@ typedef enum { /* typedef fpga_type */ fpga_min_type, /* range check value */ fpga_xilinx, /* Xilinx Family) */ fpga_altera, /* unimplemented */ - fpga_lattice, /* Lattice family */ fpga_undefined /* invalid range check value */ } fpga_type; /* end, typedef fpga_type */ diff --git a/include/lattice.h b/include/lattice.h deleted file mode 100644 index 80fafc00dcb..00000000000 --- a/include/lattice.h +++ /dev/null @@ -1,298 +0,0 @@ -/* SPDX-License-Identifier: GPL-2.0+ */ -/* - * Porting to U-Boot: - * - * (C) Copyright 2010 - * Stefano Babic, DENX Software Engineering, sbabic@denx.de. - * - * Lattice's ispVME Embedded Tool to load Lattice's FPGA: - * - * Lattice Semiconductor Corp. Copyright 2009 - */ - -#ifndef _VME_OPCODE_H -#define _VME_OPCODE_H - -#define VME_VERSION_NUMBER "12.1" - -/* Maximum declarations. */ - -#define VMEHEXMAX 60000L /* The hex file is split 60K per file. */ -#define SCANMAX 64000L /* The maximum SDR/SIR burst. */ - -/* - * - * Supported JTAG state transitions. - * - */ - -#define RESET 0x00 -#define IDLE 0x01 -#define IRPAUSE 0x02 -#define DRPAUSE 0x03 -#define SHIFTIR 0x04 -#define SHIFTDR 0x05 -/* 11/15/05 Nguyen changed to support DRCAPTURE*/ -#define DRCAPTURE 0x06 - -/* - * Flow control register bit definitions. A set bit indicates - * that the register currently exhibits the corresponding mode. - */ - -#define INTEL_PRGM 0x0001 /* Intelligent programming is in effect. */ -#define CASCADE 0x0002 /* Currently splitting large SDR. */ -#define REPEATLOOP 0x0008 /* Currently executing a repeat loop. */ -#define SHIFTRIGHT 0x0080 /* The next data stream needs a right shift. */ -#define SHIFTLEFT 0x0100 /* The next data stream needs a left shift. */ -#define VERIFYUES 0x0200 /* Continue if fail is in effect. */ - -/* - * DataType register bit definitions. A set bit indicates - * that the register currently holds the corresponding type of data. - */ - -#define EXPRESS 0x0001 /* Simultaneous program and verify. */ -#define SIR_DATA 0x0002 /* SIR is the active SVF command. */ -#define SDR_DATA 0x0004 /* SDR is the active SVF command. */ -#define COMPRESS 0x0008 /* Data is compressed. */ -#define TDI_DATA 0x0010 /* TDI data is present. */ -#define TDO_DATA 0x0020 /* TDO data is present. */ -#define MASK_DATA 0x0040 /* MASK data is present. */ -#define HEAP_IN 0x0080 /* Data is from the heap. */ -#define LHEAP_IN 0x0200 /* Data is from intel data buffer. */ -#define VARIABLE 0x0400 /* Data is from a declared variable. */ -#define CRC_DATA 0x0800 /* CRC data is pressent. */ -#define CMASK_DATA 0x1000 /* CMASK data is pressent. */ -#define RMASK_DATA 0x2000 /* RMASK data is pressent. */ -#define READ_DATA 0x4000 /* READ data is pressent. */ -#define DMASK_DATA 0x8000 /* DMASK data is pressent. */ - -/* - * - * Pin opcodes. - * - */ - -#define signalENABLE 0x1C /* ispENABLE pin. */ -#define signalTMS 0x1D /* TMS pin. */ -#define signalTCK 0x1E /* TCK pin. */ -#define signalTDI 0x1F /* TDI pin. */ -#define signalTRST 0x20 /* TRST pin. */ - -/* - * - * Supported vendors. - * - */ - -#define VENDOR 0x56 -#define LATTICE 0x01 -#define ALTERA 0x02 -#define XILINX 0x03 - -/* - * Opcode definitions. - * - * Note: opcodes must be unique. - */ - -#define ENDDATA 0x00 /* The end of the current SDR data stream. */ -#define RUNTEST 0x01 /* The duration to stay at the stable state. */ -#define ENDDR 0x02 /* The stable state after SDR. */ -#define ENDIR 0x03 /* The stable state after SIR. */ -#define ENDSTATE 0x04 /* The stable state after RUNTEST. */ -#define TRST 0x05 /* Assert the TRST pin. */ -#define HIR 0x06 /* - * The sum of the IR bits of the - * leading devices. - */ -#define TIR 0x07 /* - * The sum of the IR bits of the trailing - * devices. - */ -#define HDR 0x08 /* The number of leading devices. */ -#define TDR 0x09 /* The number of trailing devices. */ -#define ispEN 0x0A /* Assert the ispEN pin. */ -#define FREQUENCY 0x0B /* - * The maximum clock rate to run the JTAG state - * machine. - */ -#define STATE 0x10 /* Move to the next stable state. */ -#define SIR 0x11 /* The instruction stream follows. */ -#define SDR 0x12 /* The data stream follows. */ -#define TDI 0x13 /* The following data stream feeds into - the device. */ -#define TDO 0x14 /* - * The following data stream is compared against - * the device. - */ -#define MASK 0x15 /* The following data stream is used as mask. */ -#define XSDR 0x16 /* - * The following data stream is for simultaneous - * program and verify. - */ -#define XTDI 0x17 /* The following data stream is for shift in - * only. It must be stored for the next - * XSDR. - */ -#define XTDO 0x18 /* - * There is not data stream. The data stream - * was stored from the previous XTDI. - */ -#define MEM 0x19 /* - * The maximum memory needed to allocate in - * order hold one row of data. - */ -#define WAIT 0x1A /* The duration of delay to observe. */ -#define TCK 0x1B /* The number of TCK pulses. */ -#define SHR 0x23 /* - * Set the flow control register for - * right shift - */ -#define SHL 0x24 /* - * Set the flow control register for left shift. - */ -#define HEAP 0x32 /* The memory size needed to hold one loop. */ -#define REPEAT 0x33 /* The beginning of the loop. */ -#define LEFTPAREN 0x35 /* The beginning of data following the loop. */ -#define VAR 0x55 /* Plac holder for loop data. */ -#define SEC 0x1C /* - * The delay time in seconds that must be - * observed. - */ -#define SMASK 0x1D /* The mask for TDI data. */ -#define MAX_WAIT 0x1E /* The absolute maximum wait time. */ -#define ON 0x1F /* Assert the targeted pin. */ -#define OFF 0x20 /* Dis-assert the targeted pin. */ -#define SETFLOW 0x30 /* Change the flow control register. */ -#define RESETFLOW 0x31 /* Clear the flow control register. */ - -#define CRC 0x47 /* - * The following data stream is used for CRC - * calculation. - */ -#define CMASK 0x48 /* - * The following data stream is used as mask - * for CRC calculation. - */ -#define RMASK 0x49 /* - * The following data stream is used as mask - * for read and save. - */ -#define READ 0x50 /* - * The following data stream is used for read - * and save. - */ -#define ENDLOOP 0x59 /* The end of the repeat loop. */ -#define SECUREHEAP 0x60 /* Used to secure the HEAP opcode. */ -#define VUES 0x61 /* Support continue if fail. */ -#define DMASK 0x62 /* - * The following data stream is used for dynamic - * I/O. - */ -#define COMMENT 0x63 /* Support SVF comments in the VME file. */ -#define HEADER 0x64 /* Support header in VME file. */ -#define FILE_CRC 0x65 /* Support crc-protected VME file. */ -#define LCOUNT 0x66 /* Support intelligent programming. */ -#define LDELAY 0x67 /* Support intelligent programming. */ -#define LSDR 0x68 /* Support intelligent programming. */ -#define LHEAP 0x69 /* - * Memory needed to hold intelligent data - * buffer - */ -#define CONTINUE 0x70 /* Allow continuation. */ -#define LVDS 0x71 /* Support LVDS. */ -#define ENDVME 0x7F /* End of the VME file. */ -#define ENDFILE 0xFF /* End of file. */ - -/* - * - * ispVM Embedded Return Codes. - * - */ - -#define VME_VERIFICATION_FAILURE -1 -#define VME_FILE_READ_FAILURE -2 -#define VME_VERSION_FAILURE -3 -#define VME_INVALID_FILE -4 -#define VME_ARGUMENT_FAILURE -5 -#define VME_CRC_FAILURE -6 - -#define g_ucPinTDI 0x01 -#define g_ucPinTCK 0x02 -#define g_ucPinTMS 0x04 -#define g_ucPinENABLE 0x08 -#define g_ucPinTRST 0x10 - -/* - * - * Type definitions. - * - */ - -/* Support LVDS */ -typedef struct { - unsigned short usPositiveIndex; - unsigned short usNegativeIndex; - unsigned char ucUpdate; -} LVDSPair; - -typedef enum { - min_lattice_iface_type, /* insert all new types after this */ - lattice_jtag_mode, /* jtag/tap */ - max_lattice_iface_type /* insert all new types before this */ -} Lattice_iface; - -typedef enum { - min_lattice_type, - Lattice_XP2, /* Lattice XP2 Family */ - max_lattice_type /* insert all new types before this */ -} Lattice_Family; - -typedef struct { - Lattice_Family family; /* part type */ - Lattice_iface iface; /* interface type */ - size_t size; /* bytes of data part can accept */ - void *iface_fns; /* interface function table */ - void *base; /* base interface address */ - int cookie; /* implementation specific cookie */ - char *desc; /* description string */ -} Lattice_desc; /* end, typedef Altera_desc */ - -/* Board specific implementation specific function types */ -typedef void (*Lattice_jtag_init)(void); -typedef void (*Lattice_jtag_set_tdi)(int v); -typedef void (*Lattice_jtag_set_tms)(int v); -typedef void (*Lattice_jtag_set_tck)(int v); -typedef int (*Lattice_jtag_get_tdo)(void); - -typedef struct { - Lattice_jtag_init jtag_init; - Lattice_jtag_set_tdi jtag_set_tdi; - Lattice_jtag_set_tms jtag_set_tms; - Lattice_jtag_set_tck jtag_set_tck; - Lattice_jtag_get_tdo jtag_get_tdo; -} lattice_board_specific_func; - -void writePort(unsigned char pins, unsigned char value); -unsigned char readPort(void); -void sclock(void); -void ispVMDelay(unsigned short int a_usMicroSecondDelay); -void calibration(void); - -int lattice_load(Lattice_desc *desc, const void *buf, size_t bsize); -int lattice_dump(Lattice_desc *desc, const void *buf, size_t bsize); -int lattice_info(Lattice_desc *desc); - -void ispVMStart(void); -void ispVMEnd(void); -extern void ispVMFreeMem(void); -signed char ispVMCode(void); -void ispVMDelay(unsigned short int a_usMicroSecondDelay); -void ispVMCalculateCRC32(unsigned char a_ucData); -unsigned char GetByte(void); -void writePort(unsigned char pins, unsigned char value); -unsigned char readPort(void); -void sclock(void); -#endif From cb57991250822831b6191154106e539d85479303 Mon Sep 17 00:00:00 2001 From: Michal Simek Date: Tue, 29 Jul 2025 15:55:20 +0200 Subject: [PATCH 105/112] arm64: zynqmp: Add missing ethernet alias for kr260-revB Ethernet aliases are used in fdt_fixup_ethernet() to inject local-mac-address in every boot for OS. Similar change has been done for other carrier cards by commit c4a711253613 ("arm64: zynqmp: Describe ethernet controllers via aliases on SOM"). Signed-off-by: Michal Simek Link: https://lore.kernel.org/r/87d88dba98f7ed96463964684ee45a506d557226.1753797318.git.michal.simek@amd.com --- arch/arm/dts/zynqmp-sck-kr-g-revB.dtso | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/arch/arm/dts/zynqmp-sck-kr-g-revB.dtso b/arch/arm/dts/zynqmp-sck-kr-g-revB.dtso index 0d915d496ca..60ac5085f73 100644 --- a/arch/arm/dts/zynqmp-sck-kr-g-revB.dtso +++ b/arch/arm/dts/zynqmp-sck-kr-g-revB.dtso @@ -20,6 +20,11 @@ "xlnx,zynqmp-sk-kr260", "xlnx,zynqmp"; model = "ZynqMP KR260 revB"; + aliases { + ethernet0 = "/axi/ethernet@ff0b0000"; /* &gem0 */ + ethernet1 = "/axi/ethernet@ff0c0000"; /* &gem1 */ + }; + ina260-u14 { compatible = "iio-hwmon"; io-channels = <&u14 0>, <&u14 1>, <&u14 2>; From 0109a7de96c64f5d4096652c36d7b6023b0f1737 Mon Sep 17 00:00:00 2001 From: Michal Simek Date: Wed, 30 Jul 2025 16:32:01 +0200 Subject: [PATCH 106/112] arm64: versal2: Define BOOTENV_DEV_SHARED_XSPI when distro is disabled When DISTRO_DEFAULT is disabled there is missing empty BOOTENV_DEV_SHARED_XSPI macro defined. Signed-off-by: Michal Simek Link: https://lore.kernel.org/r/4c195468c0341ddd2aca98f83cdcbd40117cc9ee.1753885919.git.michal.simek@amd.com --- include/configs/amd_versal2.h | 1 + 1 file changed, 1 insertion(+) diff --git a/include/configs/amd_versal2.h b/include/configs/amd_versal2.h index 1ade6adfa0b..bd52e5a895f 100644 --- a/include/configs/amd_versal2.h +++ b/include/configs/amd_versal2.h @@ -145,6 +145,7 @@ #else /* CONFIG_DISTRO_DEFAULTS */ # define BOOTENV +# define BOOTENV_DEV_SHARED_XSPI #endif /* CONFIG_DISTRO_DEFAULTS */ /* Initial environment variables */ From 88e3524393fa88dbf675119aa89885bf144592ec Mon Sep 17 00:00:00 2001 From: Andrew Goodbody Date: Mon, 18 Aug 2025 10:24:36 +0100 Subject: [PATCH 107/112] net: axi_emac: Fix timeout test The timeout test in axi_dma_init is not correct due to the post-decrement used on the timeout variable which will mean timeout is not 0 if the timeout occurs. Make the timeout variable an int instead of a u32 and then test for timeout being -1. This issue was found by Smatch. Signed-off-by: Andrew Goodbody Link: https://lore.kernel.org/r/20250806-net_xilinx_axi-v2-1-6311cf59451d@linaro.org Signed-off-by: Michal Simek --- drivers/net/xilinx_axi_emac.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/drivers/net/xilinx_axi_emac.c b/drivers/net/xilinx_axi_emac.c index c8038ddef1b..22e119370c8 100644 --- a/drivers/net/xilinx_axi_emac.c +++ b/drivers/net/xilinx_axi_emac.c @@ -558,7 +558,7 @@ static int axiemac_write_hwaddr(struct udevice *dev) /* Reset DMA engine */ static void axi_dma_init(struct axidma_priv *priv) { - u32 timeout = 500; + int timeout = 500; /* Reset the engine so the hardware starts from a known state */ writel(XAXIDMA_CR_RESET_MASK, &priv->dmatx->control); @@ -571,11 +571,11 @@ static void axi_dma_init(struct axidma_priv *priv) if (!((readl(&priv->dmatx->control) | readl(&priv->dmarx->control)) & XAXIDMA_CR_RESET_MASK)) { - break; + return; } } - if (!timeout) - printf("%s: Timeout\n", __func__); + + printf("%s: Timeout\n", __func__); } static int axiemac_start(struct udevice *dev) From 37aee09d83863cf7fecb67f0f0eeea18e03a43ea Mon Sep 17 00:00:00 2001 From: Venkatesh Yadav Abbarapu Date: Mon, 18 Aug 2025 10:23:04 +0530 Subject: [PATCH 108/112] configs: versal2: Add usb_pgood_delay for versal2 boards Add usb_pgood_delay to ensure proper detection of USB devices. Increase the USB power good delay for versal2 specific boards, as certain USB sticks may not be detected without it. Signed-off-by: Venkatesh Yadav Abbarapu Link: https://lore.kernel.org/r/20250818045304.4058177-1-venkatesh.abbarapu@amd.com Signed-off-by: Michal Simek --- include/configs/amd_versal2.h | 1 + 1 file changed, 1 insertion(+) diff --git a/include/configs/amd_versal2.h b/include/configs/amd_versal2.h index bd52e5a895f..f1c432aa391 100644 --- a/include/configs/amd_versal2.h +++ b/include/configs/amd_versal2.h @@ -152,6 +152,7 @@ #ifndef CFG_EXTRA_ENV_SETTINGS #define CFG_EXTRA_ENV_SETTINGS \ ENV_MEM_LAYOUT_SETTINGS \ + "usb_pgood_delay=2000\0" \ BOOTENV \ BOOTENV_DEV_SHARED_XSPI \ DFU_ALT_INFO From 997c0c45c197dd8bfedc41c72d4579160b018e5e Mon Sep 17 00:00:00 2001 From: Martin Schwan Date: Fri, 15 Aug 2025 09:12:56 +0200 Subject: [PATCH 109/112] bootstd: rauc: Do not select BOOTMETH_GLOBAL Since the bootmeth "rauc" is not a global boot method, do not select the corresponding BOOTMETH_GLOBAL option. Signed-off-by: Martin Schwan --- boot/Kconfig | 1 - 1 file changed, 1 deletion(-) diff --git a/boot/Kconfig b/boot/Kconfig index 54ef7052c5c..2993cd7f9ba 100644 --- a/boot/Kconfig +++ b/boot/Kconfig @@ -869,7 +869,6 @@ config EXPO config BOOTMETH_RAUC bool "Bootdev support for RAUC A/B systems" depends on CMDLINE - select BOOTMETH_GLOBAL select HUSH_PARSER help Enables support for booting RAUC A/B systems from MMC devices. This From 03baafe0623b558f3a6b19fad94f34b42abb537a Mon Sep 17 00:00:00 2001 From: Wadim Egorov Date: Mon, 18 Aug 2025 12:26:05 +0200 Subject: [PATCH 110/112] board: phytec: phycore_am6xx: Add rauc to bootmeths Add rauc to bootmeths variable if BOOTMETH_RAUC is enabled. This is setting a proper default for RAUC enabled systems. Signed-off-by: Wadim Egorov Reviewed-by: Martin Schwan --- board/phytec/phycore_am62ax/phycore_am62ax.env | 4 ++++ board/phytec/phycore_am62x/phycore_am62x.env | 4 ++++ board/phytec/phycore_am64x/phycore_am64x.env | 4 ++++ 3 files changed, 12 insertions(+) diff --git a/board/phytec/phycore_am62ax/phycore_am62ax.env b/board/phytec/phycore_am62ax/phycore_am62ax.env index 797904013dc..ff4ab8c87b8 100644 --- a/board/phytec/phycore_am62ax/phycore_am62ax.env +++ b/board/phytec/phycore_am62ax/phycore_am62ax.env @@ -25,5 +25,9 @@ spi_fdt_addr=0x700000 spi_image_addr=0x800000 spi_ramdisk_addr=0x2200000 +#ifdef CONFIG_BOOTMETH_RAUC +bootmeths=rauc script efi extlinux pxe +#else bootmeths=script efi extlinux pxe +#endif boot_targets=mmc1 mmc0 spi_flash dhcp diff --git a/board/phytec/phycore_am62x/phycore_am62x.env b/board/phytec/phycore_am62x/phycore_am62x.env index 797904013dc..ff4ab8c87b8 100644 --- a/board/phytec/phycore_am62x/phycore_am62x.env +++ b/board/phytec/phycore_am62x/phycore_am62x.env @@ -25,5 +25,9 @@ spi_fdt_addr=0x700000 spi_image_addr=0x800000 spi_ramdisk_addr=0x2200000 +#ifdef CONFIG_BOOTMETH_RAUC +bootmeths=rauc script efi extlinux pxe +#else bootmeths=script efi extlinux pxe +#endif boot_targets=mmc1 mmc0 spi_flash dhcp diff --git a/board/phytec/phycore_am64x/phycore_am64x.env b/board/phytec/phycore_am64x/phycore_am64x.env index 36ab16e2f7a..cbaf45b3ace 100644 --- a/board/phytec/phycore_am64x/phycore_am64x.env +++ b/board/phytec/phycore_am64x/phycore_am64x.env @@ -24,5 +24,9 @@ spi_fdt_addr=0x700000 spi_image_addr=0x800000 spi_ramdisk_addr=0x2200000 +#ifdef CONFIG_BOOTMETH_RAUC +bootmeths=rauc script efi extlinux pxe +#else bootmeths=script efi extlinux pxe +#endif boot_targets=mmc1 mmc0 spi_flash dhcp From bd5036ddf2f3d9198f4054fc1a807c8f8960b281 Mon Sep 17 00:00:00 2001 From: Anshul Dalal Date: Thu, 14 Aug 2025 20:51:43 +0530 Subject: [PATCH 111/112] remoteproc: k3: update compatible for am654 syscon The existing compatible name for U-Boot's k3 system controller driver i.e "ti,am625-system-controller" has been added to linux[1] device-tree. This compatible in kernel is meant for configuring the Control Module registers (CTRL_MMR0). However in U-Boot, the matching driver was being used to load the system firmware on the secure M-cores by the R5 SPL and therefore must be updated to a different compatible to avoid conflicts. Therefore, this patch renames all references of the compatible to "ti,am654-tisci-rproc-r5". The "-r5" is appended so as to avoid any future conflicts since r5 specific compatibles should only be useful for U-Boot. [1]: 5959618631fe ("dt-bindings: mfd: ti,j721e-system-controller: Add compatible string for AM654") https://lore.kernel.org/r/20250421214620.3770172-2-afd@ti.com Signed-off-by: Anshul Dalal --- arch/arm/dts/k3-am62-r5-lp-sk.dts | 2 +- arch/arm/dts/k3-am625-r5-beagleplay.dts | 2 +- arch/arm/dts/k3-am625-r5-phycore-som-2gb.dts | 2 +- arch/arm/dts/k3-am625-r5-sk.dts | 2 +- arch/arm/dts/k3-am625-verdin-r5.dts | 2 +- arch/arm/dts/k3-am62a7-r5-phycore-som-2gb.dts | 2 +- arch/arm/dts/k3-am62a7-r5-sk.dts | 2 +- arch/arm/dts/k3-am62p5-r5-sk.dts | 2 +- arch/arm/dts/k3-am62p5-verdin-r5.dts | 2 +- arch/arm/dts/k3-am642-r5-evm.dts | 2 +- arch/arm/dts/k3-am642-r5-phycore-som-2gb.dts | 2 +- arch/arm/dts/k3-am642-r5-sk.dts | 2 +- arch/arm/dts/k3-am654-r5-base-board.dts | 2 +- arch/arm/dts/k3-am67a-r5-beagley-ai.dts | 2 +- arch/arm/dts/k3-j7200-r5-common-proc-board.dts | 2 +- arch/arm/dts/k3-j721e-r5.dtsi | 2 +- arch/arm/dts/k3-j721s2-r5.dtsi | 2 +- arch/arm/dts/k3-j722s-r5-evm.dts | 2 +- arch/arm/dts/k3-j784s4-r5.dtsi | 2 +- doc/device-tree-bindings/power/ti,sci-pm-domain.txt | 2 +- doc/device-tree-bindings/remoteproc/k3-system-controller.txt | 4 ++-- doc/device-tree-bindings/reset/ti,sci-reset.txt | 2 +- drivers/remoteproc/k3_system_controller.c | 2 +- 23 files changed, 24 insertions(+), 24 deletions(-) diff --git a/arch/arm/dts/k3-am62-r5-lp-sk.dts b/arch/arm/dts/k3-am62-r5-lp-sk.dts index 135e8d49b91..95cd9b707c7 100644 --- a/arch/arm/dts/k3-am62-r5-lp-sk.dts +++ b/arch/arm/dts/k3-am62-r5-lp-sk.dts @@ -64,7 +64,7 @@ &cbass_main { sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_main 1>, <&secure_proxy_main 0>, <&secure_proxy_sa3 0>; diff --git a/arch/arm/dts/k3-am625-r5-beagleplay.dts b/arch/arm/dts/k3-am625-r5-beagleplay.dts index f4b2cd8904e..bba69871fd2 100644 --- a/arch/arm/dts/k3-am625-r5-beagleplay.dts +++ b/arch/arm/dts/k3-am625-r5-beagleplay.dts @@ -70,7 +70,7 @@ &cbass_main { sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_main 1>, <&secure_proxy_main 0>, <&secure_proxy_sa3 0>; mbox-names = "tx", "rx", "boot_notify"; bootph-pre-ram; diff --git a/arch/arm/dts/k3-am625-r5-phycore-som-2gb.dts b/arch/arm/dts/k3-am625-r5-phycore-som-2gb.dts index 7132fae36fa..03dc81a4afa 100644 --- a/arch/arm/dts/k3-am625-r5-phycore-som-2gb.dts +++ b/arch/arm/dts/k3-am625-r5-phycore-som-2gb.dts @@ -69,7 +69,7 @@ &cbass_main { sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_main 1>, <&secure_proxy_main 0>, <&secure_proxy_sa3 0>; mbox-names = "tx", "rx", "boot_notify"; bootph-pre-ram; diff --git a/arch/arm/dts/k3-am625-r5-sk.dts b/arch/arm/dts/k3-am625-r5-sk.dts index 34c501dd51b..67589f941ba 100644 --- a/arch/arm/dts/k3-am625-r5-sk.dts +++ b/arch/arm/dts/k3-am625-r5-sk.dts @@ -64,7 +64,7 @@ &cbass_main { sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_main 1>, <&secure_proxy_main 0>, <&secure_proxy_sa3 0>; mbox-names = "tx", "rx", "boot_notify"; bootph-pre-ram; diff --git a/arch/arm/dts/k3-am625-verdin-r5.dts b/arch/arm/dts/k3-am625-verdin-r5.dts index 39e8ab8158e..fb431c96337 100644 --- a/arch/arm/dts/k3-am625-verdin-r5.dts +++ b/arch/arm/dts/k3-am625-verdin-r5.dts @@ -53,7 +53,7 @@ &cbass_main { sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_main 1>, <&secure_proxy_main 0>, <&secure_proxy_sa3 0>; mbox-names = "tx", "rx", "boot_notify"; bootph-pre-ram; diff --git a/arch/arm/dts/k3-am62a7-r5-phycore-som-2gb.dts b/arch/arm/dts/k3-am62a7-r5-phycore-som-2gb.dts index 63b7864a469..96860e80e9a 100644 --- a/arch/arm/dts/k3-am62a7-r5-phycore-som-2gb.dts +++ b/arch/arm/dts/k3-am62a7-r5-phycore-som-2gb.dts @@ -70,7 +70,7 @@ }; sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_main 1>, <&secure_proxy_main 0>, <&sa3_secproxy 0>; diff --git a/arch/arm/dts/k3-am62a7-r5-sk.dts b/arch/arm/dts/k3-am62a7-r5-sk.dts index 49e62533a95..64923c2c710 100644 --- a/arch/arm/dts/k3-am62a7-r5-sk.dts +++ b/arch/arm/dts/k3-am62a7-r5-sk.dts @@ -63,7 +63,7 @@ &cbass_main { sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_main 1>, <&secure_proxy_main 0>, <&secure_proxy_sa3 0>; diff --git a/arch/arm/dts/k3-am62p5-r5-sk.dts b/arch/arm/dts/k3-am62p5-r5-sk.dts index b18b4ce1272..e45d2bf6a0b 100644 --- a/arch/arm/dts/k3-am62p5-r5-sk.dts +++ b/arch/arm/dts/k3-am62p5-r5-sk.dts @@ -69,7 +69,7 @@ }; sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_main 1>, <&secure_proxy_main 0>, <&sa3_secproxy 0>; diff --git a/arch/arm/dts/k3-am62p5-verdin-r5.dts b/arch/arm/dts/k3-am62p5-verdin-r5.dts index 983a3bfe670..17739086935 100644 --- a/arch/arm/dts/k3-am62p5-verdin-r5.dts +++ b/arch/arm/dts/k3-am62p5-verdin-r5.dts @@ -57,7 +57,7 @@ }; sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_main 1>, <&secure_proxy_main 0>, <&sa3_secproxy 0>; diff --git a/arch/arm/dts/k3-am642-r5-evm.dts b/arch/arm/dts/k3-am642-r5-evm.dts index 933f75095b1..67b8587d3b2 100644 --- a/arch/arm/dts/k3-am642-r5-evm.dts +++ b/arch/arm/dts/k3-am642-r5-evm.dts @@ -43,7 +43,7 @@ &cbass_main { sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_main 1>, <&secure_proxy_main 0>; mbox-names = "tx", "rx"; bootph-pre-ram; diff --git a/arch/arm/dts/k3-am642-r5-phycore-som-2gb.dts b/arch/arm/dts/k3-am642-r5-phycore-som-2gb.dts index 40c25d5dbb6..32a10b24327 100644 --- a/arch/arm/dts/k3-am642-r5-phycore-som-2gb.dts +++ b/arch/arm/dts/k3-am642-r5-phycore-som-2gb.dts @@ -63,7 +63,7 @@ &cbass_main { sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_main 1>, <&secure_proxy_main 0>; mbox-names = "tx", "rx"; bootph-pre-ram; diff --git a/arch/arm/dts/k3-am642-r5-sk.dts b/arch/arm/dts/k3-am642-r5-sk.dts index 6e31dfd97c5..cfc548a1cea 100644 --- a/arch/arm/dts/k3-am642-r5-sk.dts +++ b/arch/arm/dts/k3-am642-r5-sk.dts @@ -43,7 +43,7 @@ &cbass_main { sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_main 1>, <&secure_proxy_main 0>; mbox-names = "tx", "rx"; bootph-pre-ram; diff --git a/arch/arm/dts/k3-am654-r5-base-board.dts b/arch/arm/dts/k3-am654-r5-base-board.dts index ab5195eb15c..99eb8a2d442 100644 --- a/arch/arm/dts/k3-am654-r5-base-board.dts +++ b/arch/arm/dts/k3-am654-r5-base-board.dts @@ -47,7 +47,7 @@ &cbass_wakeup { sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_mcu 4>, <&secure_proxy_mcu 5>; mbox-names = "tx", "rx"; bootph-pre-ram; diff --git a/arch/arm/dts/k3-am67a-r5-beagley-ai.dts b/arch/arm/dts/k3-am67a-r5-beagley-ai.dts index 664be358a97..45d104e8e3f 100644 --- a/arch/arm/dts/k3-am67a-r5-beagley-ai.dts +++ b/arch/arm/dts/k3-am67a-r5-beagley-ai.dts @@ -69,7 +69,7 @@ }; sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_main 1>, <&secure_proxy_main 0>, <&sa3_secproxy 0>; diff --git a/arch/arm/dts/k3-j7200-r5-common-proc-board.dts b/arch/arm/dts/k3-j7200-r5-common-proc-board.dts index 9ac29110324..e35b767a7e3 100644 --- a/arch/arm/dts/k3-j7200-r5-common-proc-board.dts +++ b/arch/arm/dts/k3-j7200-r5-common-proc-board.dts @@ -69,7 +69,7 @@ &cbass_mcu_wakeup { sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_mcu 4>, <&secure_proxy_mcu 5>; mbox-names = "tx", "rx"; diff --git a/arch/arm/dts/k3-j721e-r5.dtsi b/arch/arm/dts/k3-j721e-r5.dtsi index 786a41c5e90..7398f9b05ec 100644 --- a/arch/arm/dts/k3-j721e-r5.dtsi +++ b/arch/arm/dts/k3-j721e-r5.dtsi @@ -66,7 +66,7 @@ &cbass_mcu_wakeup { sysctrler: sysctrler { bootph-pre-ram; - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_mcu 4>, <&secure_proxy_mcu 5>; mbox-names = "tx", "rx"; }; diff --git a/arch/arm/dts/k3-j721s2-r5.dtsi b/arch/arm/dts/k3-j721s2-r5.dtsi index a820f516015..c1c12e217d2 100644 --- a/arch/arm/dts/k3-j721s2-r5.dtsi +++ b/arch/arm/dts/k3-j721s2-r5.dtsi @@ -63,7 +63,7 @@ &cbass_mcu_wakeup { sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_mcu 4>, <&secure_proxy_mcu 5>, <&secure_proxy_sa3 5>; mbox-names = "tx", "rx", "boot_notify"; bootph-pre-ram; diff --git a/arch/arm/dts/k3-j722s-r5-evm.dts b/arch/arm/dts/k3-j722s-r5-evm.dts index 286ab50d3da..02a3494a877 100644 --- a/arch/arm/dts/k3-j722s-r5-evm.dts +++ b/arch/arm/dts/k3-j722s-r5-evm.dts @@ -68,7 +68,7 @@ }; sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_main 1>, <&secure_proxy_main 0>, <&sa3_secproxy 0>; diff --git a/arch/arm/dts/k3-j784s4-r5.dtsi b/arch/arm/dts/k3-j784s4-r5.dtsi index a1394115b8b..78444dc4e14 100644 --- a/arch/arm/dts/k3-j784s4-r5.dtsi +++ b/arch/arm/dts/k3-j784s4-r5.dtsi @@ -61,7 +61,7 @@ &cbass_mcu_wakeup { sysctrler: sysctrler { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; mboxes= <&secure_proxy_mcu 4>, <&secure_proxy_mcu 5>, <&secure_proxy_sa3 5>; diff --git a/doc/device-tree-bindings/power/ti,sci-pm-domain.txt b/doc/device-tree-bindings/power/ti,sci-pm-domain.txt index 72d9fbc833c..81f6314230f 100644 --- a/doc/device-tree-bindings/power/ti,sci-pm-domain.txt +++ b/doc/device-tree-bindings/power/ti,sci-pm-domain.txt @@ -30,7 +30,7 @@ Required Properties: Example (AM65x): ---------------- sysfw: sysfw { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; ... k3_pds: power-controller { compatible = "ti,sci-pm-domain"; diff --git a/doc/device-tree-bindings/remoteproc/k3-system-controller.txt b/doc/device-tree-bindings/remoteproc/k3-system-controller.txt index 33dc46812ed..7de57ad4f00 100644 --- a/doc/device-tree-bindings/remoteproc/k3-system-controller.txt +++ b/doc/device-tree-bindings/remoteproc/k3-system-controller.txt @@ -8,7 +8,7 @@ This driver communicates with ROM for loading this firmware. Required properties: -------------------- -- compatible: Shall be: "ti,am654-system-controller" +- compatible: Shall be: "ti,am654-tisci-rproc-r5-r5" - mbox-names: "tx" for Transfer channel "rx" for Receive channel - mboxes: Corresponding phandles to mailbox channels. @@ -21,7 +21,7 @@ Example: -------- system-controller: system-controller { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5-r5"; mboxes= <&secproxy 4>, <&secproxy 5>; mbox-names = "tx", "rx"; }; diff --git a/doc/device-tree-bindings/reset/ti,sci-reset.txt b/doc/device-tree-bindings/reset/ti,sci-reset.txt index e7e2d13f9fb..740b2dfea64 100644 --- a/doc/device-tree-bindings/reset/ti,sci-reset.txt +++ b/doc/device-tree-bindings/reset/ti,sci-reset.txt @@ -23,7 +23,7 @@ Required Properties: Example (AM65x): ---------------- sysfw: sysfw { - compatible = "ti,am654-system-controller"; + compatible = "ti,am654-tisci-rproc-r5"; ... k3_reset: reset-controller { compatible = "ti,sci-reset"; diff --git a/drivers/remoteproc/k3_system_controller.c b/drivers/remoteproc/k3_system_controller.c index 71238a6058a..e59c010de7e 100644 --- a/drivers/remoteproc/k3_system_controller.c +++ b/drivers/remoteproc/k3_system_controller.c @@ -327,7 +327,7 @@ static const struct k3_sysctrler_desc k3_sysctrler_am654_desc = { static const struct udevice_id k3_sysctrler_ids[] = { { - .compatible = "ti,am654-system-controller", + .compatible = "ti,am654-tisci-rproc-r5", .data = (ulong)&k3_sysctrler_am654_desc, }, {} From dca578a9c9decb85271665de8086b8f41731d388 Mon Sep 17 00:00:00 2001 From: Tom Rini Date: Mon, 25 Aug 2025 13:06:38 -0600 Subject: [PATCH 112/112] Prepare v2025.10-rc3 Signed-off-by: Tom Rini --- Makefile | 2 +- doc/develop/release_cycle.rst | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/Makefile b/Makefile index 63e23886cde..b4f10c08d75 100644 --- a/Makefile +++ b/Makefile @@ -3,7 +3,7 @@ VERSION = 2025 PATCHLEVEL = 10 SUBLEVEL = -EXTRAVERSION = -rc2 +EXTRAVERSION = -rc3 NAME = # *DOCUMENTATION* diff --git a/doc/develop/release_cycle.rst b/doc/develop/release_cycle.rst index 354ab1b5d74..ae6200a1880 100644 --- a/doc/develop/release_cycle.rst +++ b/doc/develop/release_cycle.rst @@ -75,7 +75,7 @@ For the next scheduled release, release candidates were made on:: * U-Boot |next_ver|-rc2 was released on Mon 11 August 2025. -.. * U-Boot |next_ver|-rc3 was released on Mon 25 August 2025. +* U-Boot |next_ver|-rc3 was released on Mon 25 August 2025. .. * U-Boot |next_ver|-rc4 was released on Mon 08 September 2025.