Merge branch 'master' of git://git.denx.de/u-boot-ti
diff --git a/Kconfig b/Kconfig
index 4157da3..fed488f 100644
--- a/Kconfig
+++ b/Kconfig
@@ -116,8 +116,9 @@
depends on FIT
config FIT_SIGNATURE
- bool "Enabel signature verification of FIT uImages"
+ bool "Enable signature verification of FIT uImages"
depends on FIT
+ select RSA
help
This option enables signature verification of FIT uImages,
using a hash signed and verified using RSA.
diff --git a/Makefile b/Makefile
index ea5ae8f..9b406c8 100644
--- a/Makefile
+++ b/Makefile
@@ -776,6 +776,13 @@
@echo "See doc/README.generic-board for further information"
@echo "===================================================="
endif
+ifeq ($(CONFIG_DM_I2C_COMPAT),y)
+ @echo "===================== WARNING ======================"
+ @echo "This board uses CONFIG_DM_I2C_COMPAT. Please remove"
+ @echo "(possibly in a subsequent patch in your series)"
+ @echo "before sending patches to the mailing list."
+ @echo "===================================================="
+endif
PHONY += dtbs
dtbs dts/dt.dtb: checkdtc u-boot
diff --git a/README b/README
index fefa71c..a28ff13 100644
--- a/README
+++ b/README
@@ -3176,8 +3176,13 @@
This enables the RSA algorithm used for FIT image verification
in U-Boot. See doc/uImage.FIT/signature.txt for more information.
+ The Modular Exponentiation algorithm in RSA is implemented using
+ driver model. So CONFIG_DM needs to be enabled by default for this
+ library to function.
+
The signing part is build into mkimage regardless of this
- option.
+ option. The software based modular exponentiation is built into
+ mkimage irrespective of this option.
- bootcount support:
CONFIG_BOOTCOUNT_LIMIT
@@ -5899,9 +5904,10 @@
option). Given an image built by mkimage, the dumpimage extracts a "data file"
from the image:
- tools/dumpimage -i image -p position data_file
- -i ==> extract from the 'image' a specific 'data_file', \
- indexed by 'position'
+ tools/dumpimage -i image -T type -p position data_file
+ -i ==> extract from the 'image' a specific 'data_file'
+ -T ==> set image type to 'type'
+ -p ==> 'position' (starting at 0) of the 'data_file' inside the 'image'
Installing a Linux Image:
diff --git a/arch/arm/Kconfig b/arch/arm/Kconfig
index 5eb1d03..986b4c5 100644
--- a/arch/arm/Kconfig
+++ b/arch/arm/Kconfig
@@ -51,6 +51,13 @@
default "sa1100" if CPU_SA1100
default "armv8" if ARM64
+config SEMIHOSTING
+ bool "support boot from semihosting"
+ help
+ In emulated environments, semihosting is a way for
+ the hosted environment to call out to the emulator to
+ retrieve files from the host machine.
+
choice
prompt "Target select"
@@ -720,10 +727,19 @@
select CPU_ARM720T if SPL_BUILD
select CPU_V7 if !SPL_BUILD
-config TARGET_VEXPRESS_AEMV8A
+config TARGET_VEXPRESS64_AEMV8A
bool "Support vexpress_aemv8a"
select ARM64
+config TARGET_VEXPRESS64_BASE_FVP
+ bool "Support Versatile Express ARMv8a FVP BASE model"
+ select ARM64
+ select SEMIHOSTING
+
+config TARGET_VEXPRESS64_JUNO
+ bool "Support Versatile Express Juno Development Platform"
+ select ARM64
+
config TARGET_LS2085A_EMU
bool "Support ls2085a_emu"
select ARM64
diff --git a/arch/arm/cpu/armv7/cpu.c b/arch/arm/cpu/armv7/cpu.c
index 01cdb7e..c56417d 100644
--- a/arch/arm/cpu/armv7/cpu.c
+++ b/arch/arm/cpu/armv7/cpu.c
@@ -53,7 +53,7 @@
* After D-cache is flushed and before it is disabled there may
* be some new valid entries brought into the cache. We are sure
* that these lines are not dirty and will not affect our execution.
- * (because unwinding the call-stack and setting a bit in CP15 SCTRL
+ * (because unwinding the call-stack and setting a bit in CP15 SCTLR
* is all we did during this. We have not pushed anything on to the
* stack. Neither have we affected any static data)
* So just invalidate the entire d-cache again to avoid coherency
diff --git a/arch/arm/cpu/armv7/exynos/pinmux.c b/arch/arm/cpu/armv7/exynos/pinmux.c
index 94d0297..be43e22 100644
--- a/arch/arm/cpu/armv7/exynos/pinmux.c
+++ b/arch/arm/cpu/armv7/exynos/pinmux.c
@@ -266,22 +266,33 @@
static void exynos5_i2c_config(int peripheral, int flags)
{
+ int func01, func23;
+
+ /* High-Speed I2C */
+ if (flags & PINMUX_FLAG_HS_MODE) {
+ func01 = 4;
+ func23 = 4;
+ } else {
+ func01 = 2;
+ func23 = 3;
+ }
+
switch (peripheral) {
case PERIPH_ID_I2C0:
- gpio_cfg_pin(EXYNOS5_GPIO_B30, S5P_GPIO_FUNC(0x2));
- gpio_cfg_pin(EXYNOS5_GPIO_B31, S5P_GPIO_FUNC(0x2));
+ gpio_cfg_pin(EXYNOS5_GPIO_B30, S5P_GPIO_FUNC(func01));
+ gpio_cfg_pin(EXYNOS5_GPIO_B31, S5P_GPIO_FUNC(func01));
break;
case PERIPH_ID_I2C1:
- gpio_cfg_pin(EXYNOS5_GPIO_B32, S5P_GPIO_FUNC(0x2));
- gpio_cfg_pin(EXYNOS5_GPIO_B33, S5P_GPIO_FUNC(0x2));
+ gpio_cfg_pin(EXYNOS5_GPIO_B32, S5P_GPIO_FUNC(func01));
+ gpio_cfg_pin(EXYNOS5_GPIO_B33, S5P_GPIO_FUNC(func01));
break;
case PERIPH_ID_I2C2:
- gpio_cfg_pin(EXYNOS5_GPIO_A06, S5P_GPIO_FUNC(0x3));
- gpio_cfg_pin(EXYNOS5_GPIO_A07, S5P_GPIO_FUNC(0x3));
+ gpio_cfg_pin(EXYNOS5_GPIO_A06, S5P_GPIO_FUNC(func23));
+ gpio_cfg_pin(EXYNOS5_GPIO_A07, S5P_GPIO_FUNC(func23));
break;
case PERIPH_ID_I2C3:
- gpio_cfg_pin(EXYNOS5_GPIO_A12, S5P_GPIO_FUNC(0x3));
- gpio_cfg_pin(EXYNOS5_GPIO_A13, S5P_GPIO_FUNC(0x3));
+ gpio_cfg_pin(EXYNOS5_GPIO_A12, S5P_GPIO_FUNC(func23));
+ gpio_cfg_pin(EXYNOS5_GPIO_A13, S5P_GPIO_FUNC(func23));
break;
case PERIPH_ID_I2C4:
gpio_cfg_pin(EXYNOS5_GPIO_A20, S5P_GPIO_FUNC(0x3));
diff --git a/arch/arm/cpu/armv7/start.S b/arch/arm/cpu/armv7/start.S
index fdc05b9..70048c1 100644
--- a/arch/arm/cpu/armv7/start.S
+++ b/arch/arm/cpu/armv7/start.S
@@ -52,10 +52,10 @@
* Continue to use ROM code vector only in OMAP4 spl)
*/
#if !(defined(CONFIG_OMAP44XX) && defined(CONFIG_SPL_BUILD))
- /* Set V=0 in CP15 SCTRL register - for VBAR to point to vector */
- mrc p15, 0, r0, c1, c0, 0 @ Read CP15 SCTRL Register
+ /* Set V=0 in CP15 SCTLR register - for VBAR to point to vector */
+ mrc p15, 0, r0, c1, c0, 0 @ Read CP15 SCTLR Register
bic r0, #CR_V @ V = 0
- mcr p15, 0, r0, c1, c0, 0 @ Write CP15 SCTRL Register
+ mcr p15, 0, r0, c1, c0, 0 @ Write CP15 SCTLR Register
/* Set vector address in CP15 VBAR register */
ldr r0, =_start
diff --git a/arch/arm/cpu/armv7/sunxi/Makefile b/arch/arm/cpu/armv7/sunxi/Makefile
index 1c4b763..48db744 100644
--- a/arch/arm/cpu/armv7/sunxi/Makefile
+++ b/arch/arm/cpu/armv7/sunxi/Makefile
@@ -15,8 +15,10 @@
obj-y += usbc.o
obj-$(CONFIG_MACH_SUN6I) += prcm.o
obj-$(CONFIG_MACH_SUN8I) += prcm.o
+obj-$(CONFIG_MACH_SUN9I) += prcm.o
obj-$(CONFIG_MACH_SUN6I) += p2wi.o
obj-$(CONFIG_MACH_SUN8I) += rsb.o
+obj-$(CONFIG_MACH_SUN9I) += rsb.o
obj-$(CONFIG_MACH_SUN4I) += clock_sun4i.o
obj-$(CONFIG_MACH_SUN5I) += clock_sun4i.o
obj-$(CONFIG_MACH_SUN6I) += clock_sun6i.o
diff --git a/arch/arm/cpu/armv7/sunxi/rsb.c b/arch/arm/cpu/armv7/sunxi/rsb.c
index b72bb9d..b00befb 100644
--- a/arch/arm/cpu/armv7/sunxi/rsb.c
+++ b/arch/arm/cpu/armv7/sunxi/rsb.c
@@ -16,14 +16,27 @@
#include <asm/arch/prcm.h>
#include <asm/arch/rsb.h>
+static int rsb_set_device_mode(void);
+
static void rsb_cfg_io(void)
{
+#ifdef CONFIG_MACH_SUN8I
sunxi_gpio_set_cfgpin(SUNXI_GPL(0), SUN8I_GPL0_R_RSB_SCK);
sunxi_gpio_set_cfgpin(SUNXI_GPL(1), SUN8I_GPL1_R_RSB_SDA);
sunxi_gpio_set_pull(SUNXI_GPL(0), 1);
sunxi_gpio_set_pull(SUNXI_GPL(1), 1);
sunxi_gpio_set_drv(SUNXI_GPL(0), 2);
sunxi_gpio_set_drv(SUNXI_GPL(1), 2);
+#elif defined CONFIG_MACH_SUN9I
+ sunxi_gpio_set_cfgpin(SUNXI_GPN(0), SUN9I_GPN0_R_RSB_SCK);
+ sunxi_gpio_set_cfgpin(SUNXI_GPN(1), SUN9I_GPN1_R_RSB_SDA);
+ sunxi_gpio_set_pull(SUNXI_GPN(0), 1);
+ sunxi_gpio_set_pull(SUNXI_GPN(1), 1);
+ sunxi_gpio_set_drv(SUNXI_GPN(0), 2);
+ sunxi_gpio_set_drv(SUNXI_GPN(1), 2);
+#else
+#error unsupported MACH_SUNXI
+#endif
}
static void rsb_set_clk(void)
@@ -42,7 +55,7 @@
writel((cd_odly << 8) | div, &rsb->ccr);
}
-void rsb_init(void)
+int rsb_init(void)
{
struct sunxi_rsb_reg * const rsb =
(struct sunxi_rsb_reg *)SUNXI_RSB_BASE;
@@ -54,6 +67,8 @@
writel(RSB_CTRL_SOFT_RST, &rsb->ctrl);
rsb_set_clk();
+
+ return rsb_set_device_mode();
}
static int rsb_await_trans(void)
@@ -88,13 +103,14 @@
return ret;
}
-int rsb_set_device_mode(u32 device_mode_data)
+static int rsb_set_device_mode(void)
{
struct sunxi_rsb_reg * const rsb =
(struct sunxi_rsb_reg *)SUNXI_RSB_BASE;
unsigned long tmo = timer_get_us() + 1000000;
- writel(RSB_DMCR_DEVICE_MODE_START | device_mode_data, &rsb->dmcr);
+ writel(RSB_DMCR_DEVICE_MODE_START | RSB_DMCR_DEVICE_MODE_DATA,
+ &rsb->dmcr);
while (readl(&rsb->dmcr) & RSB_DMCR_DEVICE_MODE_START) {
if (timer_get_us() > tmo)
diff --git a/arch/arm/cpu/tegra20-common/pmu.c b/arch/arm/cpu/tegra20-common/pmu.c
index 36a76a2..a774246 100644
--- a/arch/arm/cpu/tegra20-common/pmu.c
+++ b/arch/arm/cpu/tegra20-common/pmu.c
@@ -52,7 +52,7 @@
debug("%s: Cannot find DVC I2C bus\n", __func__);
return ret;
}
- ret = i2c_get_chip(bus, PMI_I2C_ADDRESS, &dev);
+ ret = i2c_get_chip(bus, PMI_I2C_ADDRESS, 1, &dev);
if (ret) {
debug("%s: Cannot find DVC I2C chip\n", __func__);
return ret;
diff --git a/arch/arm/dts/exynos4.dtsi b/arch/arm/dts/exynos4.dtsi
index 77fad48..7de227c 100644
--- a/arch/arm/dts/exynos4.dtsi
+++ b/arch/arm/dts/exynos4.dtsi
@@ -51,56 +51,64 @@
#address-cells = <1>;
#size-cells = <0>;
compatible = "samsung,s3c2440-i2c";
- interrupts = <0 0 0>;
+ reg = <0x13860000 0x100>;
+ interrupts = <0 56 0>;
};
i2c@13870000 {
#address-cells = <1>;
#size-cells = <0>;
compatible = "samsung,s3c2440-i2c";
- interrupts = <1 1 0>;
+ reg = <0x13870000 0x100>;
+ interrupts = <1 57 0>;
};
i2c@13880000 {
#address-cells = <1>;
#size-cells = <0>;
compatible = "samsung,s3c2440-i2c";
- interrupts = <2 2 0>;
+ reg = <0x13880000 0x100>;
+ interrupts = <2 58 0>;
};
i2c@13890000 {
#address-cells = <1>;
#size-cells = <0>;
compatible = "samsung,s3c2440-i2c";
- interrupts = <3 3 0>;
+ reg = <0x13890000 0x100>;
+ interrupts = <3 59 0>;
};
i2c@138a0000 {
#address-cells = <1>;
#size-cells = <0>;
compatible = "samsung,s3c2440-i2c";
- interrupts = <4 4 0>;
+ reg = <0x138a0000 0x100>;
+ interrupts = <4 60 0>;
};
i2c@138b0000 {
#address-cells = <1>;
#size-cells = <0>;
compatible = "samsung,s3c2440-i2c";
- interrupts = <5 5 0>;
+ reg = <0x138b0000 0x100>;
+ interrupts = <5 61 0>;
};
i2c@138c0000 {
#address-cells = <1>;
#size-cells = <0>;
compatible = "samsung,s3c2440-i2c";
- interrupts = <6 6 0>;
+ reg = <0x138c0000 0x100>;
+ interrupts = <6 62 0>;
};
i2c@138d0000 {
#address-cells = <1>;
#size-cells = <0>;
compatible = "samsung,s3c2440-i2c";
- interrupts = <7 7 0>;
+ reg = <0x138d0000 0x100>;
+ interrupts = <7 63 0>;
};
sdhci@12510000 {
@@ -143,11 +151,4 @@
interrupts = <0 131 0>;
};
- gpio: gpio {
- gpio-controller;
- #gpio-cells = <2>;
-
- interrupt-controller;
- #interrupt-cells = <2>;
- };
};
diff --git a/arch/arm/dts/exynos4210-origen.dts b/arch/arm/dts/exynos4210-origen.dts
index dd2476c..3f87761 100644
--- a/arch/arm/dts/exynos4210-origen.dts
+++ b/arch/arm/dts/exynos4210-origen.dts
@@ -36,7 +36,7 @@
sdhci@12530000 {
samsung,bus-width = <4>;
samsung,timing = <1 2 3>;
- cd-gpios = <&gpio 0xA2 0>;
+ cd-gpios = <&gpk2 2 0>;
};
sdhci@12540000 {
diff --git a/arch/arm/dts/exynos4210-trats.dts b/arch/arm/dts/exynos4210-trats.dts
index 8c7a2c3..36d02df 100644
--- a/arch/arm/dts/exynos4210-trats.dts
+++ b/arch/arm/dts/exynos4210-trats.dts
@@ -101,7 +101,7 @@
sdhci@12510000 {
samsung,bus-width = <8>;
samsung,timing = <1 3 3>;
- pwr-gpios = <&gpio 146 0>;
+ pwr-gpios = <&gpk0 2 0>;
};
sdhci@12520000 {
@@ -111,7 +111,7 @@
sdhci@12530000 {
samsung,bus-width = <4>;
samsung,timing = <1 2 3>;
- cd-gpios = <&gpio 284 0>;
+ cd-gpios = <&gpx3 4 0>;
};
sdhci@12540000 {
diff --git a/arch/arm/dts/exynos4210-universal_c210.dts b/arch/arm/dts/exynos4210-universal_c210.dts
index 808c3f7..16948c9 100644
--- a/arch/arm/dts/exynos4210-universal_c210.dts
+++ b/arch/arm/dts/exynos4210-universal_c210.dts
@@ -24,7 +24,7 @@
sdhci@12510000 {
samsung,bus-width = <8>;
samsung,timing = <1 3 3>;
- pwr-gpios = <&gpio 146 0>;
+ pwr-gpios = <&gpk0 2 0>;
};
sdhci@12520000 {
@@ -34,7 +34,7 @@
sdhci@12530000 {
samsung,bus-width = <4>;
samsung,timing = <1 2 3>;
- cd-gpios = <&gpio 284 0>;
+ cd-gpios = <&gpx3 4 0>;
};
sdhci@12540000 {
@@ -43,10 +43,10 @@
soft-spi {
compatible = "u-boot,soft-spi";
- cs-gpio = <&gpio 235 0>; /* Y43 */
- sclk-gpio = <&gpio 225 0>; /* Y31 */
- mosi-gpio = <&gpio 227 0>; /* Y33 */
- miso-gpio = <&gpio 224 0>; /* Y30 */
+ cs-gpio = <&gpy4 3 0>;
+ sclk-gpio = <&gpy3 1 0>;
+ mosi-gpio = <&gpy3 3 0>;
+ miso-gpio = <&gpy3 0 0>;
spi-delay-us = <1>;
#address-cells = <1>;
#size-cells = <0>;
diff --git a/arch/arm/dts/exynos4412-odroid.dts b/arch/arm/dts/exynos4412-odroid.dts
index c78efec..00a2917 100644
--- a/arch/arm/dts/exynos4412-odroid.dts
+++ b/arch/arm/dts/exynos4412-odroid.dts
@@ -16,6 +16,13 @@
aliases {
i2c0 = "/i2c@13860000";
+ i2c1 = "/i2c@13870000";
+ i2c2 = "/i2c@13880000";
+ i2c3 = "/i2c@13890000";
+ i2c4 = "/i2c@138a0000";
+ i2c5 = "/i2c@138b0000";
+ i2c6 = "/i2c@138c0000";
+ i2c7 = "/i2c@138d0000";
serial0 = "/serial@13800000";
console = "/serial@13810000";
mmc2 = "sdhci@12530000";
@@ -51,7 +58,7 @@
sdhci@12530000 {
samsung,bus-width = <4>;
samsung,timing = <1 2 3>;
- cd-gpios = <&gpio 122 0>;
+ cd-gpios = <&gpk2 2 0>;
};
sdhci@12540000 {
diff --git a/arch/arm/dts/exynos4412-trats2.dts b/arch/arm/dts/exynos4412-trats2.dts
index 60e4515..dd238df 100644
--- a/arch/arm/dts/exynos4412-trats2.dts
+++ b/arch/arm/dts/exynos4412-trats2.dts
@@ -416,7 +416,7 @@
sdhci@12510000 {
samsung,bus-width = <8>;
samsung,timing = <1 3 3>;
- pwr-gpios = <&gpio 0x6a 0>;
+ pwr-gpios = <&gpk0 4 0>;
status = "disabled";
};
@@ -427,7 +427,7 @@
sdhci@12530000 {
samsung,bus-width = <4>;
samsung,timing = <1 2 3>;
- cd-gpios = <&gpio 0x7a 0>;
+ cd-gpios = <&gpk2 2 0>;
};
sdhci@12540000 {
@@ -437,7 +437,7 @@
dwmmc@12550000 {
samsung,bus-width = <8>;
samsung,timing = <2 1 0>;
- pwr-gpios = <&gpio 0x6a 0>;
+ pwr-gpios = <&gpk0 4 0>;
fifoth_val = <0x203f0040>;
bus_hz = <400000000>;
div = <0x3>;
diff --git a/arch/arm/dts/exynos5.dtsi b/arch/arm/dts/exynos5.dtsi
index e539068..238acb8 100644
--- a/arch/arm/dts/exynos5.dtsi
+++ b/arch/arm/dts/exynos5.dtsi
@@ -6,6 +6,7 @@
*/
#include "skeleton.dtsi"
+#include <dt-bindings/gpio/gpio.h>
/ {
compatible = "samsung,exynos5";
@@ -247,7 +248,4 @@
u-boot,dm-pre-reloc;
id = <3>;
};
-
- gpio: gpio {
- };
};
diff --git a/arch/arm/dts/exynos5250-arndale.dts b/arch/arm/dts/exynos5250-arndale.dts
index 202f2ea..21c0a21 100644
--- a/arch/arm/dts/exynos5250-arndale.dts
+++ b/arch/arm/dts/exynos5250-arndale.dts
@@ -15,6 +15,14 @@
compatible = "samsung,arndale", "samsung,exynos5250";
aliases {
+ i2c0 = "/i2c@12c60000";
+ i2c1 = "/i2c@12c70000";
+ i2c2 = "/i2c@12c80000";
+ i2c3 = "/i2c@12c90000";
+ i2c4 = "/i2c@12ca0000";
+ i2c5 = "/i2c@12cb0000";
+ i2c6 = "/i2c@12cc0000";
+ i2c7 = "/i2c@12cd0000";
serial0 = "/serial@12C20000";
console = "/serial@12C20000";
};
diff --git a/arch/arm/dts/exynos5250-smdk5250.dts b/arch/arm/dts/exynos5250-smdk5250.dts
index 8850409..9273562 100644
--- a/arch/arm/dts/exynos5250-smdk5250.dts
+++ b/arch/arm/dts/exynos5250-smdk5250.dts
@@ -146,6 +146,6 @@
};
ehci@12110000 {
- samsung,vbus-gpio = <&gpio 0x316 0>; /* X26 */
+ samsung,vbus-gpio = <&gpx2 6 GPIO_ACTIVE_HIGH>;
};
};
diff --git a/arch/arm/dts/exynos5250-snow.dts b/arch/arm/dts/exynos5250-snow.dts
index bac5015..7d8be69 100644
--- a/arch/arm/dts/exynos5250-snow.dts
+++ b/arch/arm/dts/exynos5250-snow.dts
@@ -44,7 +44,8 @@
reg = <0x1e>;
compatible = "google,cros-ec";
i2c-max-frequency = <100000>;
- ec-interrupt = <&gpio 182 1>;
+ u-boot,i2c-offset-len = <0>;
+ ec-interrupt = <&gpx1 6 GPIO_ACTIVE_LOW>;
};
power-regulator@48 {
@@ -68,7 +69,7 @@
reg = <0>;
compatible = "google,cros-ec";
spi-max-frequency = <5000000>;
- ec-interrupt = <&gpio 182 1>;
+ ec-interrupt = <&gpx1 6 GPIO_ACTIVE_LOW>;
optimise-flash-write;
status = "disabled";
};
@@ -76,7 +77,7 @@
sound@3830000 {
samsung,codec-type = "max98095";
- codec-enable-gpio = <&gpio 0xb7 0>;
+ codec-enable-gpio = <&gpx1 7 GPIO_ACTIVE_HIGH>;
};
sound@12d60000 {
@@ -131,11 +132,11 @@
};
ehci@12110000 {
- samsung,vbus-gpio = <&gpio 0xb1 0>; /* X11 */
+ samsung,vbus-gpio = <&gpx1 1 GPIO_ACTIVE_HIGH>;
};
xhci@12000000 {
- samsung,vbus-gpio = <&gpio 0xbf 0>; /* X27 */
+ samsung,vbus-gpio = <&gpx2 7 GPIO_ACTIVE_HIGH>;
};
tmu@10060000 {
diff --git a/arch/arm/dts/exynos5420-peach-pit.dts b/arch/arm/dts/exynos5420-peach-pit.dts
index d1d8735..b801de9 100644
--- a/arch/arm/dts/exynos5420-peach-pit.dts
+++ b/arch/arm/dts/exynos5420-peach-pit.dts
@@ -17,7 +17,7 @@
"google,peach", "samsung,exynos5420", "samsung,exynos5";
config {
- google,bad-wake-gpios = <&gpio 0x56 0>; /* gpx0-6 */
+ google,bad-wake-gpios = <&gpx0 6 GPIO_ACTIVE_HIGH>;
hwid = "PIT TEST A-A 7848";
lazy-init = <1>;
};
@@ -108,7 +108,7 @@
spi-half-duplex;
spi-max-timeout-ms = <1100>;
spi-frame-header = <0xec>;
- ec-interrupt = <&gpio 93 1>; /* GPX1_5 */
+ ec-interrupt = <&gpx1 5 GPIO_ACTIVE_LOW>;
/*
* This describes the flash memory within the EC. Note
@@ -124,11 +124,11 @@
};
xhci@12000000 {
- samsung,vbus-gpio = <&gpio 0x40 0>; /* H00 */
+ samsung,vbus-gpio = <&gph0 0 GPIO_ACTIVE_HIGH>;
};
xhci@12400000 {
- samsung,vbus-gpio = <&gpio 0x41 0>; /* H01 */
+ samsung,vbus-gpio = <&gph0 1 GPIO_ACTIVE_HIGH>;
};
fimd@14400000 {
diff --git a/arch/arm/dts/exynos5422-odroidxu3.dts b/arch/arm/dts/exynos5422-odroidxu3.dts
index 79a7acd..8f46637 100644
--- a/arch/arm/dts/exynos5422-odroidxu3.dts
+++ b/arch/arm/dts/exynos5422-odroidxu3.dts
@@ -32,7 +32,7 @@
};
ehci@12110000 {
- samsung,vbus-gpio = <&gpio 0x66 0>; /* X26 */
+ samsung,vbus-gpio = <&gpx2 6 GPIO_ACTIVE_HIGH>;
};
serial@12C20000 {
diff --git a/arch/arm/dts/exynos5800-peach-pi.dts b/arch/arm/dts/exynos5800-peach-pi.dts
index e7c380f..e4bc100 100644
--- a/arch/arm/dts/exynos5800-peach-pi.dts
+++ b/arch/arm/dts/exynos5800-peach-pi.dts
@@ -17,7 +17,7 @@
"google,peach", "samsung,exynos5800", "samsung,exynos5";
config {
- google,bad-wake-gpios = <&gpio 0x56 0>; /* gpx0-6 */
+ google,bad-wake-gpios = <&gpx0 6 GPIO_ACTIVE_HIGH>;
hwid = "PIT TEST A-A 7848";
lazy-init = <1>;
};
@@ -32,7 +32,7 @@
mem-manuf = "samsung";
mem-type = "ddr3";
clock-frequency = <800000000>;
- arm-frequency = <1700000000>;
+ arm-frequency = <900000000>;
};
tmu@10060000 {
@@ -102,7 +102,7 @@
spi-half-duplex;
spi-max-timeout-ms = <1100>;
spi-frame-header = <0xec>;
- ec-interrupt = <&gpio 93 1>; /* GPX1_5 */
+ ec-interrupt = <&gpx1 5 GPIO_ACTIVE_LOW>;
/*
* This describes the flash memory within the EC. Note
@@ -118,11 +118,11 @@
};
xhci@12000000 {
- samsung,vbus-gpio = <&gpio 0x40 0>; /* H00 */
+ samsung,vbus-gpio = <&gph0 0 GPIO_ACTIVE_HIGH>;
};
xhci@12400000 {
- samsung,vbus-gpio = <&gpio 0x41 0>; /* H01 */
+ samsung,vbus-gpio = <&gph0 1 GPIO_ACTIVE_HIGH>;
};
fimd@14400000 {
diff --git a/arch/arm/dts/tegra114-dalmore.dts b/arch/arm/dts/tegra114-dalmore.dts
index 81ad212..51ff266 100644
--- a/arch/arm/dts/tegra114-dalmore.dts
+++ b/arch/arm/dts/tegra114-dalmore.dts
@@ -57,7 +57,7 @@
};
sdhci@78000400 {
- cd-gpios = <&gpio 170 1>; /* gpio PV2 */
+ cd-gpios = <&gpio TEGRA_GPIO(V, 2) GPIO_ACTIVE_LOW>;
bus-width = <4>;
status = "okay";
};
@@ -68,8 +68,7 @@
};
usb@7d008000 {
- /* SPDIF_IN: USB_VBUS_EN1 */
- nvidia,vbus-gpio = <&gpio 86 0>;
+ nvidia,vbus-gpio = <&gpio TEGRA_GPIO(K, 6) GPIO_ACTIVE_HIGH>;
status = "okay";
};
};
diff --git a/arch/arm/dts/tegra124-jetson-tk1.dts b/arch/arm/dts/tegra124-jetson-tk1.dts
index 51fef54..e7b66d8 100644
--- a/arch/arm/dts/tegra124-jetson-tk1.dts
+++ b/arch/arm/dts/tegra124-jetson-tk1.dts
@@ -303,8 +303,9 @@
sdhci@700b0400 {
status = "okay";
- cd-gpios = <&gpio 170 1>; /* gpio PV2 */
- power-gpios = <&gpio 136 0>; /* gpio PR0 */
+ cd-gpios = <&gpio TEGRA_GPIO(V, 2) GPIO_ACTIVE_LOW>;
+ power-gpios = <&gpio TEGRA_GPIO(R, 0) GPIO_ACTIVE_HIGH>;
+ wp-gpios = <&gpio TEGRA_GPIO(Q, 4) GPIO_ACTIVE_HIGH>;
bus-width = <4>;
};
@@ -316,12 +317,12 @@
usb@7d000000 {
status = "okay";
dr_mode = "otg";
- nvidia,vbus-gpio = <&gpio 108 0>; /* gpio PN4, USB_VBUS_EN0 */
+ nvidia,vbus-gpio = <&gpio TEGRA_GPIO(N, 4) GPIO_ACTIVE_HIGH>;
};
usb@7d008000 {
status = "okay";
- nvidia,vbus-gpio = <&gpio 109 0>; /* gpio PN5, USB_VBUS_EN1 */
+ nvidia,vbus-gpio = <&gpio TEGRA_GPIO(N, 5) GPIO_ACTIVE_HIGH>;
};
regulators {
diff --git a/arch/arm/dts/tegra124-venice2.dts b/arch/arm/dts/tegra124-venice2.dts
index f7ccfc5..9e93cf9 100644
--- a/arch/arm/dts/tegra124-venice2.dts
+++ b/arch/arm/dts/tegra124-venice2.dts
@@ -72,8 +72,9 @@
sdhci@700b0400 {
status = "okay";
- cd-gpios = <&gpio 170 0>; /* gpio PV2 */
- power-gpios = <&gpio 136 0>; /* gpio PR0 */
+ cd-gpios = <&gpio TEGRA_GPIO(V, 2) GPIO_ACTIVE_HIGH>;
+ power-gpios = <&gpio TEGRA_GPIO(R, 0) GPIO_ACTIVE_HIGH>;
+ wp-gpios = <&gpio TEGRA_GPIO(Q, 4) GPIO_ACTIVE_LOW>;
bus-width = <4>;
};
@@ -85,11 +86,11 @@
usb@7d000000 {
status = "okay";
dr_mode = "otg";
- nvidia,vbus-gpio = <&gpio 108 0>; /* gpio PN4, USB_VBUS_EN0 */
+ nvidia,vbus-gpio = <&gpio TEGRA_GPIO(N, 4) GPIO_ACTIVE_HIGH>;
};
usb@7d008000 {
status = "okay";
- nvidia,vbus-gpio = <&gpio 109 0>; /* gpio PN5, USB_VBUS_EN1 */
+ nvidia,vbus-gpio = <&gpio TEGRA_GPIO(N, 5) GPIO_ACTIVE_HIGH>;
};
};
diff --git a/arch/arm/dts/tegra20-colibri_t20_iris.dts b/arch/arm/dts/tegra20-colibri_t20_iris.dts
index 7cf08f4..3131b92 100644
--- a/arch/arm/dts/tegra20-colibri_t20_iris.dts
+++ b/arch/arm/dts/tegra20-colibri_t20_iris.dts
@@ -22,16 +22,16 @@
};
usb@c5004000 {
- nvidia,phy-reset-gpio = <&gpio 169 0>; /* PV1 */
- nvidia,vbus-gpio = <&gpio 217 0>; /* PBB1 */
+ nvidia,phy-reset-gpio = <&gpio TEGRA_GPIO(V, 1) GPIO_ACTIVE_HIGH>;
+ nvidia,vbus-gpio = <&gpio TEGRA_GPIO(BB, 1) GPIO_ACTIVE_HIGH>;
};
usb@c5008000 {
- nvidia,vbus-gpio = <&gpio 178 1>; /* PW2 low-active */
+ nvidia,vbus-gpio = <&gpio TEGRA_GPIO(W, 2) GPIO_ACTIVE_LOW>;
};
nand-controller@70008000 {
- nvidia,wp-gpios = <&gpio 144 0>; /* PS0 */
+ nvidia,wp-gpios = <&gpio TEGRA_GPIO(S, 0) GPIO_ACTIVE_HIGH>;
nvidia,width = <8>;
nvidia,timing = <15 100 25 80 25 10 15 10 100>;
@@ -43,7 +43,7 @@
sdhci@c8000600 {
status = "okay";
- cd-gpios = <&gpio 23 1>; /* gpio PC7 */
+ cd-gpios = <&gpio TEGRA_GPIO(C, 7) GPIO_ACTIVE_LOW>;
bus-width = <4>;
};
};
diff --git a/arch/arm/dts/tegra20-harmony.dts b/arch/arm/dts/tegra20-harmony.dts
index 982a14c..e6e4229 100644
--- a/arch/arm/dts/tegra20-harmony.dts
+++ b/arch/arm/dts/tegra20-harmony.dts
@@ -37,7 +37,7 @@
};
nand-controller@70008000 {
- nvidia,wp-gpios = <&gpio 23 0>; /* PC7 */
+ nvidia,wp-gpios = <&gpio TEGRA_GPIO(C, 7) GPIO_ACTIVE_HIGH>;
nvidia,width = <8>;
nvidia,timing = <26 100 20 80 20 10 12 10 70>;
nand@0 {
@@ -67,22 +67,22 @@
};
usb@c5004000 {
- nvidia,phy-reset-gpio = <&gpio 169 0>; /* gpio PV1 */
+ nvidia,phy-reset-gpio = <&gpio TEGRA_GPIO(V, 1) 0>;
};
sdhci@c8000200 {
status = "okay";
- cd-gpios = <&gpio 69 1>; /* gpio PI5 */
- wp-gpios = <&gpio 57 0>; /* gpio PH1 */
- power-gpios = <&gpio 155 0>; /* gpio PT3 */
+ cd-gpios = <&gpio TEGRA_GPIO(I, 5) GPIO_ACTIVE_LOW>;
+ wp-gpios = <&gpio TEGRA_GPIO(H, 1) GPIO_ACTIVE_HIGH>;
+ power-gpios = <&gpio TEGRA_GPIO(T, 3) GPIO_ACTIVE_HIGH>;
bus-width = <4>;
};
sdhci@c8000600 {
status = "okay";
- cd-gpios = <&gpio 58 1>; /* gpio PH2 */
- wp-gpios = <&gpio 59 0>; /* gpio PH3 */
- power-gpios = <&gpio 70 0>; /* gpio PI6 */
+ cd-gpios = <&gpio TEGRA_GPIO(H, 2) GPIO_ACTIVE_LOW>;
+ wp-gpios = <&gpio TEGRA_GPIO(H, 3) GPIO_ACTIVE_HIGH>;
+ power-gpios = <&gpio TEGRA_GPIO(I, 6) GPIO_ACTIVE_HIGH>;
bus-width = <8>;
};
@@ -100,10 +100,14 @@
vsyncx-active-high;
nvidia,bits-per-pixel = <16>;
nvidia,pwm = <&pwm 0 0>;
- nvidia,backlight-enable-gpios = <&gpio 13 0>; /* PB5 */
- nvidia,lvds-shutdown-gpios = <&gpio 10 0>; /* PB2 */
- nvidia,backlight-vdd-gpios = <&gpio 176 0>; /* PW0 */
- nvidia,panel-vdd-gpios = <&gpio 22 0>; /* PC6 */
+ nvidia,backlight-enable-gpios = <&gpio TEGRA_GPIO(B, 5)
+ GPIO_ACTIVE_HIGH>;
+ nvidia,lvds-shutdown-gpios = <&gpio TEGRA_GPIO(B, 2)
+ GPIO_ACTIVE_HIGH>;
+ nvidia,backlight-vdd-gpios = <&gpio TEGRA_GPIO(W, 0)
+ GPIO_ACTIVE_HIGH>;
+ nvidia,panel-vdd-gpios = <&gpio TEGRA_GPIO(C, 6)
+ GPIO_ACTIVE_HIGH>;
nvidia,panel-timings = <0 0 200 0 0>;
};
};
diff --git a/arch/arm/dts/tegra20-medcom-wide.dts b/arch/arm/dts/tegra20-medcom-wide.dts
index be2ed42..b6b57ab 100644
--- a/arch/arm/dts/tegra20-medcom-wide.dts
+++ b/arch/arm/dts/tegra20-medcom-wide.dts
@@ -73,9 +73,12 @@
nvidia,bits-per-pixel = <16>;
nvidia,pwm = <&pwm 0 500000>;
- nvidia,backlight-enable-gpios = <&gpio 13 0>; /* PB5 */
- nvidia,backlight-vdd-gpios = <&gpio 176 0>; /* PW0 */
- nvidia,lvds-shutdown-gpios = <&gpio 10 0>; /* PB2 */
+ nvidia,backlight-enable-gpios = <&gpio TEGRA_GPIO(B, 5)
+ GPIO_ACTIVE_HIGH>;
+ nvidia,lvds-shutdown-gpios = <&gpio TEGRA_GPIO(B, 2)
+ GPIO_ACTIVE_HIGH>;
+ nvidia,backlight-vdd-gpios = <&gpio TEGRA_GPIO(W, 0)
+ GPIO_ACTIVE_HIGH>;
nvidia,panel-timings = <0 0 0 0>;
};
};
diff --git a/arch/arm/dts/tegra20-paz00.dts b/arch/arm/dts/tegra20-paz00.dts
index 9d735b5..16381c3 100644
--- a/arch/arm/dts/tegra20-paz00.dts
+++ b/arch/arm/dts/tegra20-paz00.dts
@@ -61,9 +61,9 @@
sdhci@c8000000 {
status = "okay";
- cd-gpios = <&gpio 173 1>; /* gpio PV5 */
- wp-gpios = <&gpio 57 0>; /* gpio PH1 */
- power-gpios = <&gpio 169 0>; /* gpio PV1 */
+ cd-gpios = <&gpio TEGRA_GPIO(V, 5) GPIO_ACTIVE_LOW>;
+ wp-gpios = <&gpio TEGRA_GPIO(H, 1) GPIO_ACTIVE_HIGH>;
+ power-gpios = <&gpio TEGRA_GPIO(V, 1) GPIO_ACTIVE_HIGH>;
bus-width = <4>;
};
@@ -86,10 +86,14 @@
hsync-active-high;
nvidia,bits-per-pixel = <16>;
nvidia,pwm = <&pwm 0 0>;
- nvidia,backlight-enable-gpios = <&gpio 164 0>; /* PU4 */
- nvidia,lvds-shutdown-gpios = <&gpio 102 0>; /* PM6 */
- nvidia,backlight-vdd-gpios = <&gpio 176 0>; /* PW0 */
- nvidia,panel-vdd-gpios = <&gpio 4 0>; /* PA4 */
+ nvidia,backlight-enable-gpios = <&gpio TEGRA_GPIO(U, 4)
+ GPIO_ACTIVE_HIGH>;
+ nvidia,lvds-shutdown-gpios = <&gpio TEGRA_GPIO(M, 6)
+ GPIO_ACTIVE_HIGH>;
+ nvidia,backlight-vdd-gpios = <&gpio TEGRA_GPIO(W, 0)
+ GPIO_ACTIVE_HIGH>;
+ nvidia,panel-vdd-gpios = <&gpio TEGRA_GPIO(A, 4)
+ GPIO_ACTIVE_HIGH>;
nvidia,panel-timings = <400 4 203 17 15>;
};
};
diff --git a/arch/arm/dts/tegra20-seaboard.dts b/arch/arm/dts/tegra20-seaboard.dts
index 43b9911..10f3992 100644
--- a/arch/arm/dts/tegra20-seaboard.dts
+++ b/arch/arm/dts/tegra20-seaboard.dts
@@ -65,7 +65,7 @@
};
nand-controller@70008000 {
- nvidia,wp-gpios = <&gpio 59 0>; /* PH3 */
+ nvidia,wp-gpios = <&gpio TEGRA_GPIO(H, 3) GPIO_ACTIVE_HIGH>;
nvidia,width = <8>;
nvidia,timing = <26 100 20 80 20 10 12 10 70>;
nand@0 {
@@ -151,7 +151,7 @@
};
usb@c5000000 {
- nvidia,vbus-gpio = <&gpio 24 0>; /* PD0 */
+ nvidia,vbus-gpio = <&gpio TEGRA_GPIO(D, 0) GPIO_ACTIVE_HIGH>;
dr_mode = "otg";
};
@@ -161,9 +161,9 @@
sdhci@c8000400 {
status = "okay";
- cd-gpios = <&gpio 69 1>; /* gpio PI5 */
- wp-gpios = <&gpio 57 0>; /* gpio PH1 */
- power-gpios = <&gpio 70 0>; /* gpio PI6 */
+ cd-gpios = <&gpio TEGRA_GPIO(I, 5) GPIO_ACTIVE_LOW>;
+ wp-gpios = <&gpio TEGRA_GPIO(H, 1) GPIO_ACTIVE_HIGH>;
+ power-gpios = <&gpio TEGRA_GPIO(I, 6) GPIO_ACTIVE_HIGH>;
bus-width = <4>;
};
@@ -186,10 +186,14 @@
hsync-active-high;
nvidia,bits-per-pixel = <16>;
nvidia,pwm = <&pwm 2 0>;
- nvidia,backlight-enable-gpios = <&gpio 28 0>; /* PD4 */
- nvidia,lvds-shutdown-gpios = <&gpio 10 0>; /* PB2 */
- nvidia,backlight-vdd-gpios = <&gpio 176 0>; /* PW0 */
- nvidia,panel-vdd-gpios = <&gpio 22 0>; /* PC6 */
+ nvidia,backlight-enable-gpios = <&gpio TEGRA_GPIO(D, 4)
+ GPIO_ACTIVE_HIGH>;
+ nvidia,lvds-shutdown-gpios = <&gpio TEGRA_GPIO(B, 2)
+ GPIO_ACTIVE_HIGH>;
+ nvidia,backlight-vdd-gpios = <&gpio TEGRA_GPIO(W, 0)
+ GPIO_ACTIVE_HIGH>;
+ nvidia,panel-vdd-gpios = <&gpio TEGRA_GPIO(C, 6)
+ GPIO_ACTIVE_HIGH>;
nvidia,panel-timings = <400 4 203 17 15>;
};
};
diff --git a/arch/arm/dts/tegra20-tamonten.dtsi b/arch/arm/dts/tegra20-tamonten.dtsi
index f379622..78449e6 100644
--- a/arch/arm/dts/tegra20-tamonten.dtsi
+++ b/arch/arm/dts/tegra20-tamonten.dtsi
@@ -14,7 +14,8 @@
pll-supply = <&hdmi_pll_reg>;
nvidia,ddc-i2c-bus = <&hdmi_ddc>;
- nvidia,hpd-gpio = <&gpio 111 0>; /* PN7 */
+ nvidia,hpd-gpio = <&gpio TEGRA_GPIO(N, 7)
+ GPIO_ACTIVE_HIGH>;
};
};
@@ -280,7 +281,7 @@
};
nand-controller@70008000 {
- nvidia,wp-gpios = <&gpio 23 0>; /* PC7 */
+ nvidia,wp-gpios = <&gpio TEGRA_GPIO(C, 7) GPIO_ACTIVE_HIGH>;
nvidia,width = <8>;
nvidia,timing = <26 100 20 80 20 10 12 10 70>;
@@ -476,8 +477,8 @@
};
sdhci@c8000600 {
- cd-gpios = <&gpio 58 1>; /* gpio PH2 */
- wp-gpios = <&gpio 59 0>; /* gpio PH3 */
+ cd-gpios = <&gpio TEGRA_GPIO(H, 2) GPIO_ACTIVE_LOW>;
+ wp-gpios = <&gpio TEGRA_GPIO(H, 3) GPIO_ACTIVE_HIGH>;
bus-width = <4>;
status = "okay";
};
diff --git a/arch/arm/dts/tegra20-tec.dts b/arch/arm/dts/tegra20-tec.dts
index e99bd44..94ba6dc 100644
--- a/arch/arm/dts/tegra20-tec.dts
+++ b/arch/arm/dts/tegra20-tec.dts
@@ -73,9 +73,12 @@
nvidia,bits-per-pixel = <16>;
nvidia,pwm = <&pwm 0 500000>;
- nvidia,backlight-enable-gpios = <&gpio 13 0>; /* PB5 */
- nvidia,backlight-vdd-gpios = <&gpio 176 0>; /* PW0 */
- nvidia,lvds-shutdown-gpios = <&gpio 10 0>; /* PB2 */
+ nvidia,backlight-enable-gpios = <&gpio TEGRA_GPIO(B, 5)
+ GPIO_ACTIVE_HIGH>;
+ nvidia,lvds-shutdown-gpios = <&gpio TEGRA_GPIO(B, 2)
+ GPIO_ACTIVE_HIGH>;
+ nvidia,backlight-vdd-gpios = <&gpio TEGRA_GPIO(W, 0)
+ GPIO_ACTIVE_HIGH>;
nvidia,panel-timings = <0 0 0 0>;
};
};
diff --git a/arch/arm/dts/tegra20-trimslice.dts b/arch/arm/dts/tegra20-trimslice.dts
index 1637cbd..27b118f 100644
--- a/arch/arm/dts/tegra20-trimslice.dts
+++ b/arch/arm/dts/tegra20-trimslice.dts
@@ -62,7 +62,7 @@
};
usb@c5000000 {
- nvidia,vbus-gpio = <&gpio 170 0>; /* PV2 */
+ nvidia,vbus-gpio = <&gpio TEGRA_GPIO(V, 2) GPIO_ACTIVE_HIGH>;
};
usb@c5004000 {
@@ -76,8 +76,8 @@
sdhci@c8000600 {
status = "okay";
- cd-gpios = <&gpio 121 1>; /* gpio PP1 */
- wp-gpios = <&gpio 122 0>; /* gpio PP2 */
+ cd-gpios = <&gpio TEGRA_GPIO(P, 1) GPIO_ACTIVE_LOW>;
+ wp-gpios = <&gpio TEGRA_GPIO(P, 2) GPIO_ACTIVE_HIGH>;
bus-width = <4>;
};
@@ -111,7 +111,7 @@
regulator-min-microvolt = <5000000>;
regulator-max-microvolt = <5000000>;
enable-active-high;
- gpio = <&gpio TEGRA_GPIO(V, 2) 0>;
+ gpio = <&gpio TEGRA_GPIO(V, 2) GPIO_ACTIVE_HIGH>;
regulator-always-on;
regulator-boot-on;
};
diff --git a/arch/arm/dts/tegra20-ventana.dts b/arch/arm/dts/tegra20-ventana.dts
index 6812203..939e567 100644
--- a/arch/arm/dts/tegra20-ventana.dts
+++ b/arch/arm/dts/tegra20-ventana.dts
@@ -61,9 +61,9 @@
sdhci@c8000400 {
status = "okay";
- cd-gpios = <&gpio 69 1>; /* gpio PI5 */
- wp-gpios = <&gpio 57 0>; /* gpio PH1 */
- power-gpios = <&gpio 70 0>; /* gpio PI6 */
+ cd-gpios = <&gpio TEGRA_GPIO(I, 5) GPIO_ACTIVE_LOW>;
+ wp-gpios = <&gpio TEGRA_GPIO(H, 1) GPIO_ACTIVE_HIGH>;
+ power-gpios = <&gpio TEGRA_GPIO(I, 6) GPIO_ACTIVE_HIGH>;
bus-width = <4>;
};
@@ -86,10 +86,14 @@
vsync-active-high;
nvidia,bits-per-pixel = <16>;
nvidia,pwm = <&pwm 2 0>;
- nvidia,backlight-enable-gpios = <&gpio 28 0>; /* PD4 */
- nvidia,lvds-shutdown-gpios = <&gpio 10 0>; /* PB2 */
- nvidia,backlight-vdd-gpios = <&gpio 176 0>; /* PW0 */
- nvidia,panel-vdd-gpios = <&gpio 22 0>; /* PC6 */
+ nvidia,backlight-enable-gpios = <&gpio TEGRA_GPIO(D, 4)
+ GPIO_ACTIVE_HIGH>;
+ nvidia,lvds-shutdown-gpios = <&gpio TEGRA_GPIO(B, 2)
+ GPIO_ACTIVE_HIGH>;
+ nvidia,backlight-vdd-gpios = <&gpio TEGRA_GPIO(W, 0)
+ GPIO_ACTIVE_HIGH>;
+ nvidia,panel-vdd-gpios = <&gpio TEGRA_GPIO(C, 6)
+ GPIO_ACTIVE_HIGH>;
nvidia,panel-timings = <0 0 200 0 0>;
};
};
diff --git a/arch/arm/dts/tegra20-whistler.dts b/arch/arm/dts/tegra20-whistler.dts
index 4fd2496..c4a28eb 100644
--- a/arch/arm/dts/tegra20-whistler.dts
+++ b/arch/arm/dts/tegra20-whistler.dts
@@ -66,7 +66,7 @@
sdhci@c8000400 {
status = "okay";
- wp-gpios = <&gpio 173 0>; /* gpio PV5 */
+ wp-gpios = <&gpio TEGRA_GPIO(V, 5) GPIO_ACTIVE_HIGH>;
bus-width = <8>;
};
diff --git a/arch/arm/dts/tegra30-apalis.dts b/arch/arm/dts/tegra30-apalis.dts
index 5bad3e7..15db0f2 100644
--- a/arch/arm/dts/tegra30-apalis.dts
+++ b/arch/arm/dts/tegra30-apalis.dts
@@ -243,13 +243,13 @@
sdhci@78000000 {
status = "okay";
bus-width = <4>;
- cd-gpios = <&gpio 229 1>; /* PCC5, SD1_CD# */
+ cd-gpios = <&gpio TEGRA_GPIO(CC, 5) GPIO_ACTIVE_HIGH>;
};
sdhci@78000400 {
status = "okay";
bus-width = <8>;
- cd-gpios = <&gpio 171 1>; /* PV3, MMC1_CD# */
+ cd-gpios = <&gpio TEGRA_GPIO(V, 3) GPIO_ACTIVE_HIGH>;
};
sdhci@78000600 {
@@ -262,20 +262,20 @@
usb@7d000000 {
status = "okay";
dr_mode = "peripheral";
- nvidia,vbus-gpio = <&gpio 157 0>; /* PT5, USBO1_EN */
+ nvidia,vbus-gpio = <&gpio TEGRA_GPIO(T, 5) GPIO_ACTIVE_HIGH>;
};
/* EHCI instance 1: USB2_DP/N -> USBH2_DP/N */
usb@7d004000 {
status = "okay";
- nvidia,vbus-gpio = <&gpio 233 0>; /* PDD1, USBH_EN */
+ nvidia,vbus-gpio = <&gpio TEGRA_GPIO(DD, 1) GPIO_ACTIVE_HIGH>;
phy_type = "utmi";
};
/* EHCI instance 2: USB3_DP/N -> USBH3_DP/N */
usb@7d008000 {
status = "okay";
- nvidia,vbus-gpio = <&gpio 233 0>; /* PDD1, USBH_EN */
+ nvidia,vbus-gpio = <&gpio TEGRA_GPIO(DD, 1) GPIO_ACTIVE_HIGH>;
};
regulators {
diff --git a/arch/arm/dts/tegra30-beaver.dts b/arch/arm/dts/tegra30-beaver.dts
index 5903af6..ae83636 100644
--- a/arch/arm/dts/tegra30-beaver.dts
+++ b/arch/arm/dts/tegra30-beaver.dts
@@ -196,9 +196,9 @@
sdhci@78000000 {
status = "okay";
- cd-gpios = <&gpio 69 1>; /* gpio PI5 */
- wp-gpios = <&gpio 155 0>; /* gpio PT3 */
- power-gpios = <&gpio 31 0>; /* gpio PD7 */
+ cd-gpios = <&gpio TEGRA_GPIO(I, 5) GPIO_ACTIVE_LOW>;
+ wp-gpios = <&gpio TEGRA_GPIO(T, 3) GPIO_ACTIVE_HIGH>;
+ power-gpios = <&gpio TEGRA_GPIO(D, 7) GPIO_ACTIVE_HIGH>;
bus-width = <4>;
};
@@ -210,11 +210,11 @@
usb@7d000000 {
status = "okay";
dr_mode = "otg";
- nvidia,vbus-gpio = <&gpio 238 0>; /* gpio DD6, PEX_L1_CLKREQ */
+ nvidia,vbus-gpio = <&gpio TEGRA_GPIO(DD, 6) GPIO_ACTIVE_HIGH>;
};
usb@7d008000 {
- nvidia,vbus-gpio = <&gpio 236 0>; /* PDD4 */
+ nvidia,vbus-gpio = <&gpio TEGRA_GPIO(DD, 4) GPIO_ACTIVE_HIGH>;
status = "okay";
};
diff --git a/arch/arm/dts/tegra30-cardhu.dts b/arch/arm/dts/tegra30-cardhu.dts
index e13d0fb..23ca141 100644
--- a/arch/arm/dts/tegra30-cardhu.dts
+++ b/arch/arm/dts/tegra30-cardhu.dts
@@ -185,9 +185,9 @@
sdhci@78000000 {
status = "okay";
- cd-gpios = <&gpio 69 1>; /* gpio PI5 */
- wp-gpios = <&gpio 155 0>; /* gpio PT3 */
- power-gpios = <&gpio 31 0>; /* gpio PD7 */
+ cd-gpios = <&gpio TEGRA_GPIO(I, 5) GPIO_ACTIVE_LOW>;
+ wp-gpios = <&gpio TEGRA_GPIO(T, 3) GPIO_ACTIVE_HIGH>;
+ power-gpios = <&gpio TEGRA_GPIO(D, 7) GPIO_ACTIVE_HIGH>;
bus-width = <4>;
};
@@ -197,7 +197,7 @@
};
usb@7d008000 {
- nvidia,vbus-gpio = <&gpio 236 0>; /* PDD4 */
+ nvidia,vbus-gpio = <&gpio TEGRA_GPIO(DD, 4) GPIO_ACTIVE_HIGH>;
status = "okay";
};
diff --git a/arch/arm/dts/tegra30-colibri.dts b/arch/arm/dts/tegra30-colibri.dts
index 37b6abd..6cd1902 100644
--- a/arch/arm/dts/tegra30-colibri.dts
+++ b/arch/arm/dts/tegra30-colibri.dts
@@ -64,7 +64,7 @@
sdhci@78000200 {
status = "okay";
bus-width = <4>;
- cd-gpios = <&gpio 23 1>; /* PC7, MMCD */
+ cd-gpios = <&gpio TEGRA_GPIO(C, 7) GPIO_ACTIVE_LOW>;
};
sdhci@78000600 {
@@ -83,12 +83,12 @@
usb@7d004000 {
status = "okay";
phy_type = "utmi";
- nvidia,vbus-gpio = <&gpio 234 0>; /* PDD2, VBUS_LAN */
+ nvidia,vbus-gpio = <&gpio TEGRA_GPIO(DD, 2) GPIO_ACTIVE_HIGH>;
};
/* EHCI instance 2: USB3_DP/N -> USBH_P/N */
usb@7d008000 {
status = "okay";
- nvidia,vbus-gpio = <&gpio 178 1>; /* PW2, USBH_PEN */
+ nvidia,vbus-gpio = <&gpio TEGRA_GPIO(W, 2) GPIO_ACTIVE_LOW>;
};
};
diff --git a/arch/arm/dts/tegra30-tamonten.dtsi b/arch/arm/dts/tegra30-tamonten.dtsi
index c73afef..8eff627 100644
--- a/arch/arm/dts/tegra30-tamonten.dtsi
+++ b/arch/arm/dts/tegra30-tamonten.dtsi
@@ -55,8 +55,8 @@
/* SD slot on the base board */
sdhci@78000400 {
- cd-gpios = <&gpio 69 1>; /* gpio PI5 */
- wp-gpios = <&gpio 67 0>; /* gpio PI3 */
+ cd-gpios = <&gpio TEGRA_GPIO(I, 5) GPIO_ACTIVE_LOW>;
+ wp-gpios = <&gpio TEGRA_GPIO(I, 3) GPIO_ACTIVE_HIGH>;
bus-width = <4>;
};
diff --git a/arch/arm/include/asm/arch-exynos/pinmux.h b/arch/arm/include/asm/arch-exynos/pinmux.h
index 0b91ef6..d0ae757 100644
--- a/arch/arm/include/asm/arch-exynos/pinmux.h
+++ b/arch/arm/include/asm/arch-exynos/pinmux.h
@@ -23,6 +23,9 @@
/* Flags for SROM controller */
PINMUX_FLAG_BANK = 3 << 0, /* bank number (0-3) */
PINMUX_FLAG_16BIT = 1 << 2, /* 16-bit width */
+
+ /* Flags for I2C */
+ PINMUX_FLAG_HS_MODE = 1 << 1, /* I2C High Speed Mode */
};
/**
diff --git a/arch/arm/include/asm/arch-pantheon/gpio.h b/arch/arm/include/asm/arch-pantheon/gpio.h
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/arch/arm/include/asm/arch-pantheon/gpio.h
diff --git a/arch/arm/include/asm/arch-sunxi/clock_sun4i.h b/arch/arm/include/asm/arch-sunxi/clock_sun4i.h
index 05fbad3..d297ed0 100644
--- a/arch/arm/include/asm/arch-sunxi/clock_sun4i.h
+++ b/arch/arm/include/asm/arch-sunxi/clock_sun4i.h
@@ -305,6 +305,8 @@
#define CCM_GMAC_CTRL_TX_CLK_SRC_INT_RGMII 0x2
#define CCM_GMAC_CTRL_GPIT_MII (0x0 << 2)
#define CCM_GMAC_CTRL_GPIT_RGMII (0x1 << 2)
+#define CCM_GMAC_CTRL_RX_CLK_DELAY(x) ((x) << 5)
+#define CCM_GMAC_CTRL_TX_CLK_DELAY(x) ((x) << 10)
#define CCM_USB_CTRL_PHY0_RST (0x1 << 0)
#define CCM_USB_CTRL_PHY1_RST (0x1 << 1)
diff --git a/arch/arm/include/asm/arch-sunxi/clock_sun6i.h b/arch/arm/include/asm/arch-sunxi/clock_sun6i.h
index e101c54..8a80385 100644
--- a/arch/arm/include/asm/arch-sunxi/clock_sun6i.h
+++ b/arch/arm/include/asm/arch-sunxi/clock_sun6i.h
@@ -243,6 +243,8 @@
#define CCM_GMAC_CTRL_TX_CLK_SRC_INT_RGMII 0x2
#define CCM_GMAC_CTRL_GPIT_MII (0x0 << 2)
#define CCM_GMAC_CTRL_GPIT_RGMII (0x1 << 2)
+#define CCM_GMAC_CTRL_RX_CLK_DELAY(x) ((x) << 5)
+#define CCM_GMAC_CTRL_TX_CLK_DELAY(x) ((x) << 10)
#define MDFS_CLK_DEFAULT 0x81000002 /* PLL6 / 3 */
diff --git a/arch/arm/include/asm/arch-sunxi/cpu_sun9i.h b/arch/arm/include/asm/arch-sunxi/cpu_sun9i.h
index a2a7839..04889c5 100644
--- a/arch/arm/include/asm/arch-sunxi/cpu_sun9i.h
+++ b/arch/arm/include/asm/arch-sunxi/cpu_sun9i.h
@@ -73,7 +73,6 @@
#define SUNXI_CCM_BASE (REGS_APB0_BASE + 0x0000)
#define SUNXI_CCMMODULE_BASE (REGS_APB0_BASE + 0x0400)
#define SUNXI_PIO_BASE (REGS_APB0_BASE + 0x0800)
-#define SUNXI_R_PIO_BASE (0x08002C00)
#define SUNXI_TIMER_BASE (REGS_APB0_BASE + 0x0C00)
#define SUNXI_PWM_BASE (REGS_APB0_BASE + 0x1400)
#define SUNXI_LRADC_BASE (REGS_APB0_BASE + 0x1800)
@@ -92,8 +91,10 @@
#define SUNXI_TWI4_BASE (REGS_APB1_BASE + 0x3800)
/* RCPUS Module */
-#define SUNXI_RPRCM_BASE (REGS_RCPUS_BASE + 0x1400)
+#define SUNXI_PRCM_BASE (REGS_RCPUS_BASE + 0x1400)
#define SUNXI_R_UART_BASE (REGS_RCPUS_BASE + 0x2800)
+#define SUNXI_R_PIO_BASE (REGS_RCPUS_BASE + 0x2c00)
+#define SUNXI_RSB_BASE (REGS_RCPUS_BASE + 0x3400)
/* Misc. */
#define SUNXI_BROM_BASE 0xFFFF0000 /* 32K */
diff --git a/arch/arm/include/asm/arch-sunxi/gpio.h b/arch/arm/include/asm/arch-sunxi/gpio.h
index 71cc879..f2c247d 100644
--- a/arch/arm/include/asm/arch-sunxi/gpio.h
+++ b/arch/arm/include/asm/arch-sunxi/gpio.h
@@ -45,9 +45,13 @@
*
* sun8i has 1 bank:
* PL0 - PL11
+ *
+ * sun9i has 3 banks:
+ * PL0 - PL9 | PM0 - PM15 | PN0 - PN1
*/
#define SUNXI_GPIO_L 11
#define SUNXI_GPIO_M 12
+#define SUNXI_GPIO_N 13
struct sunxi_gpio {
u32 cfg[4];
@@ -114,6 +118,7 @@
SUNXI_GPIO_I_START = SUNXI_GPIO_NEXT(SUNXI_GPIO_H),
SUNXI_GPIO_L_START = 352,
SUNXI_GPIO_M_START = SUNXI_GPIO_NEXT(SUNXI_GPIO_L),
+ SUNXI_GPIO_N_START = SUNXI_GPIO_NEXT(SUNXI_GPIO_M),
SUNXI_GPIO_AXP0_START = 1024,
};
@@ -129,6 +134,7 @@
#define SUNXI_GPI(_nr) (SUNXI_GPIO_I_START + (_nr))
#define SUNXI_GPL(_nr) (SUNXI_GPIO_L_START + (_nr))
#define SUNXI_GPM(_nr) (SUNXI_GPIO_M_START + (_nr))
+#define SUNXI_GPN(_nr) (SUNXI_GPIO_N_START + (_nr))
#define SUNXI_GPAXP0(_nr) (SUNXI_GPIO_AXP0_START + (_nr))
@@ -187,6 +193,9 @@
#define SUN8I_GPL2_R_UART_TX 2
#define SUN8I_GPL3_R_UART_RX 2
+#define SUN9I_GPN0_R_RSB_SCK 3
+#define SUN9I_GPN1_R_RSB_SDA 3
+
/* GPIO pin pull-up/down config */
#define SUNXI_GPIO_PULL_DISABLE 0
#define SUNXI_GPIO_PULL_UP 1
diff --git a/arch/arm/include/asm/arch-sunxi/rsb.h b/arch/arm/include/asm/arch-sunxi/rsb.h
index 95a595a..a893466 100644
--- a/arch/arm/include/asm/arch-sunxi/rsb.h
+++ b/arch/arm/include/asm/arch-sunxi/rsb.h
@@ -37,6 +37,7 @@
#define RSB_STAT_TERR_INT (1 << 1)
#define RSB_STAT_LBSY_INT (1 << 2)
+#define RSB_DMCR_DEVICE_MODE_DATA 0x7c3e00
#define RSB_DMCR_DEVICE_MODE_START (1 << 31)
#define RSB_CMD_BYTE_WRITE 0x4e
@@ -46,8 +47,7 @@
#define RSB_DEVADDR_RUNTIME_ADDR(x) ((x) << 16)
#define RSB_DEVADDR_DEVICE_ADDR(x) ((x) << 0)
-void rsb_init(void);
-int rsb_set_device_mode(u32 device_mode_data);
+int rsb_init(void);
int rsb_set_device_address(u16 device_addr, u16 runtime_addr);
int rsb_write(const u16 runtime_device_addr, const u8 reg_addr, u8 data);
int rsb_read(const u16 runtime_device_addr, const u8 reg_addr, u8 *data);
diff --git a/arch/arm/include/asm/arch-tegra/tegra_mmc.h b/arch/arm/include/asm/arch-tegra/tegra_mmc.h
index 84e7b55..a20bdaa 100644
--- a/arch/arm/include/asm/arch-tegra/tegra_mmc.h
+++ b/arch/arm/include/asm/arch-tegra/tegra_mmc.h
@@ -10,6 +10,7 @@
#define __TEGRA_MMC_H_
#include <fdtdec.h>
+#include <asm/gpio.h>
/* for mmc_config definition */
#include <mmc.h>
@@ -134,9 +135,9 @@
int enabled; /* 1 to enable, 0 to disable */
int width; /* Bus Width, 1, 4 or 8 */
enum periph_id mmc_id; /* Peripheral ID: PERIPH_ID_... */
- struct fdt_gpio_state cd_gpio; /* Change Detect GPIO */
- struct fdt_gpio_state pwr_gpio; /* Power GPIO */
- struct fdt_gpio_state wp_gpio; /* Write Protect GPIO */
+ struct gpio_desc cd_gpio; /* Change Detect GPIO */
+ struct gpio_desc pwr_gpio; /* Power GPIO */
+ struct gpio_desc wp_gpio; /* Write Protect GPIO */
unsigned int version; /* SDHCI spec. version */
unsigned int clock; /* Current clock (MHz) */
struct mmc_config cfg; /* mmc configuration */
diff --git a/arch/arm/include/asm/arch-tegra20/display.h b/arch/arm/include/asm/arch-tegra20/display.h
index a04c84e..6feeda3 100644
--- a/arch/arm/include/asm/arch-tegra20/display.h
+++ b/arch/arm/include/asm/arch-tegra20/display.h
@@ -10,6 +10,7 @@
#include <asm/arch/dc.h>
#include <fdtdec.h>
+#include <asm/gpio.h>
/* This holds information about a window which can be displayed */
struct disp_ctl_win {
@@ -72,10 +73,10 @@
int pwm_channel; /* PWM channel to use for backlight */
enum lcd_cache_t cache_type;
- struct fdt_gpio_state backlight_en; /* GPIO for backlight enable */
- struct fdt_gpio_state lvds_shutdown; /* GPIO for lvds shutdown */
- struct fdt_gpio_state backlight_vdd; /* GPIO for backlight vdd */
- struct fdt_gpio_state panel_vdd; /* GPIO for panel vdd */
+ struct gpio_desc backlight_en; /* GPIO for backlight enable */
+ struct gpio_desc lvds_shutdown; /* GPIO for lvds shutdown */
+ struct gpio_desc backlight_vdd; /* GPIO for backlight vdd */
+ struct gpio_desc panel_vdd; /* GPIO for panel vdd */
/*
* Panel required timings
* Timing 1: delay between panel_vdd-rise and data-rise
diff --git a/arch/arm/include/asm/arch-zynq/gpio.h b/arch/arm/include/asm/arch-zynq/gpio.h
index 2dbba75..a26ae87 100644
--- a/arch/arm/include/asm/arch-zynq/gpio.h
+++ b/arch/arm/include/asm/arch-zynq/gpio.h
@@ -7,19 +7,4 @@
#ifndef _ZYNQ_GPIO_H
#define _ZYNQ_GPIO_H
-inline int gpio_get_value(unsigned gpio)
-{
- return 0;
-}
-
-inline int gpio_set_value(unsigned gpio, int val)
-{
- return 0;
-}
-
-inline int gpio_request(unsigned gpio, const char *label)
-{
- return 0;
-}
-
#endif /* _ZYNQ_GPIO_H */
diff --git a/arch/blackfin/cpu/cpu.c b/arch/blackfin/cpu/cpu.c
index b7f1188..91aa5cc 100644
--- a/arch/blackfin/cpu/cpu.c
+++ b/arch/blackfin/cpu/cpu.c
@@ -24,6 +24,7 @@
#include "cpu.h"
#include "initcode.h"
+#include "exports.h"
ulong bfin_poweron_retx;
DECLARE_GLOBAL_DATA_PTR;
@@ -121,7 +122,7 @@
printf(" |-ram_size: %lx\n", gd->ram_size);
printf(" |-env_addr: %lx\n", gd->env_addr);
printf(" |-env_valid: %lx\n", gd->env_valid);
- printf(" |-jt(%p): %p\n", gd->jt, *(gd->jt));
+ printf(" |-jt(%p): %p\n", gd->jt, gd->jt->get_version);
printf(" \\-bd: %p\n", gd->bd);
printf(" |-bi_boot_params: %lx\n", bd->bi_boot_params);
printf(" |-bi_memstart: %lx\n", bd->bi_memstart);
diff --git a/arch/mips/Kconfig b/arch/mips/Kconfig
index ef78929..bc4283d 100644
--- a/arch/mips/Kconfig
+++ b/arch/mips/Kconfig
@@ -36,6 +36,7 @@
select SUPPORTS_BIG_ENDIAN
select SUPPORTS_CPU_MIPS32_R1
select SUPPORTS_CPU_MIPS32_R2
+ select SYS_MIPS_CACHE_INIT_RAM_LOAD
config TARGET_DBAU1X00
bool "Support dbau1x00"
@@ -43,12 +44,14 @@
select SUPPORTS_LITTLE_ENDIAN
select SUPPORTS_CPU_MIPS32_R1
select SUPPORTS_CPU_MIPS32_R2
+ select SYS_MIPS_CACHE_INIT_RAM_LOAD
config TARGET_PB1X00
bool "Support pb1x00"
select SUPPORTS_LITTLE_ENDIAN
select SUPPORTS_CPU_MIPS32_R1
select SUPPORTS_CPU_MIPS32_R2
+ select SYS_MIPS_CACHE_INIT_RAM_LOAD
endchoice
@@ -185,6 +188,9 @@
config SWAP_IO_SPACE
bool
+config SYS_MIPS_CACHE_INIT_RAM_LOAD
+ bool
+
endif
endmenu
diff --git a/arch/mips/Makefile b/arch/mips/Makefile
index 0a9e7e6..43f0f5c 100644
--- a/arch/mips/Makefile
+++ b/arch/mips/Makefile
@@ -2,9 +2,9 @@
# SPDX-License-Identifier: GPL-2.0+
#
-head-$(CONFIG_CPU_MIPS32) := arch/mips/cpu/mips32/start.o
-head-$(CONFIG_CPU_MIPS64) := arch/mips/cpu/mips64/start.o
+head-y := arch/mips/cpu/start.o
-libs-$(CONFIG_CPU_MIPS32) += arch/mips/cpu/mips32/
-libs-$(CONFIG_CPU_MIPS64) += arch/mips/cpu/mips64/
+libs-y += arch/mips/cpu/
libs-y += arch/mips/lib/
+
+libs-$(CONFIG_SOC_AU1X00) += arch/mips/mach-au1x00/
diff --git a/arch/mips/cpu/Makefile b/arch/mips/cpu/Makefile
new file mode 100644
index 0000000..fc6b455
--- /dev/null
+++ b/arch/mips/cpu/Makefile
@@ -0,0 +1,9 @@
+#
+# SPDX-License-Identifier: GPL-2.0+
+#
+
+extra-y = start.o
+
+obj-y += time.o
+obj-y += interrupts.o
+obj-y += cpu.o
diff --git a/arch/mips/cpu/cpu.c b/arch/mips/cpu/cpu.c
new file mode 100644
index 0000000..8d3b2f5
--- /dev/null
+++ b/arch/mips/cpu/cpu.c
@@ -0,0 +1,38 @@
+/*
+ * (C) Copyright 2003
+ * Wolfgang Denk, DENX Software Engineering, <wd@denx.de>
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+#include <common.h>
+#include <command.h>
+#include <netdev.h>
+#include <linux/compiler.h>
+#include <asm/mipsregs.h>
+#include <asm/reboot.h>
+
+void __weak _machine_restart(void)
+{
+ fprintf(stderr, "*** reset failed ***\n");
+
+ while (1)
+ /* NOP */;
+}
+
+int do_reset(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
+{
+ _machine_restart();
+
+ return 0;
+}
+
+void write_one_tlb(int index, u32 pagemask, u32 hi, u32 low0, u32 low1)
+{
+ write_c0_entrylo0(low0);
+ write_c0_pagemask(pagemask);
+ write_c0_entrylo1(low1);
+ write_c0_entryhi(hi);
+ write_c0_index(index);
+ tlb_write_indexed();
+}
diff --git a/arch/mips/cpu/mips32/interrupts.c b/arch/mips/cpu/interrupts.c
similarity index 100%
rename from arch/mips/cpu/mips32/interrupts.c
rename to arch/mips/cpu/interrupts.c
diff --git a/arch/mips/cpu/mips32/Makefile b/arch/mips/cpu/mips32/Makefile
deleted file mode 100644
index fa82dd3..0000000
--- a/arch/mips/cpu/mips32/Makefile
+++ /dev/null
@@ -1,12 +0,0 @@
-#
-# (C) Copyright 2003-2006
-# Wolfgang Denk, DENX Software Engineering, wd@denx.de.
-#
-# SPDX-License-Identifier: GPL-2.0+
-#
-
-extra-y = start.o
-obj-y = cache.o
-obj-y += cpu.o interrupts.o time.o
-
-obj-$(CONFIG_SOC_AU1X00) += au1x00/
diff --git a/arch/mips/cpu/mips32/cache.S b/arch/mips/cpu/mips32/cache.S
deleted file mode 100644
index 22bd844..0000000
--- a/arch/mips/cpu/mips32/cache.S
+++ /dev/null
@@ -1,281 +0,0 @@
-/*
- * Cache-handling routined for MIPS CPUs
- *
- * Copyright (c) 2003 Wolfgang Denk <wd@denx.de>
- *
- * SPDX-License-Identifier: GPL-2.0+
- */
-
-#include <asm-offsets.h>
-#include <config.h>
-#include <asm/asm.h>
-#include <asm/regdef.h>
-#include <asm/mipsregs.h>
-#include <asm/addrspace.h>
-#include <asm/cacheops.h>
-
-#ifndef CONFIG_SYS_MIPS_CACHE_MODE
-#define CONFIG_SYS_MIPS_CACHE_MODE CONF_CM_CACHABLE_NONCOHERENT
-#endif
-
-#define RA t9
-
-#define INDEX_BASE CKSEG0
-
- .macro cache_op op addr
- .set push
- .set noreorder
- .set mips3
- cache \op, 0(\addr)
- .set pop
- .endm
-
- .macro f_fill64 dst, offset, val
- LONG_S \val, (\offset + 0 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 1 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 2 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 3 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 4 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 5 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 6 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 7 * LONGSIZE)(\dst)
-#if LONGSIZE == 4
- LONG_S \val, (\offset + 8 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 9 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 10 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 11 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 12 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 13 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 14 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 15 * LONGSIZE)(\dst)
-#endif
- .endm
-
-/*
- * mips_init_icache(uint PRId, ulong icache_size, unchar icache_linesz)
- */
-LEAF(mips_init_icache)
- blez a1, 9f
- mtc0 zero, CP0_TAGLO
- /* clear tag to invalidate */
- PTR_LI t0, INDEX_BASE
- PTR_ADDU t1, t0, a1
-1: cache_op INDEX_STORE_TAG_I t0
- PTR_ADDU t0, a2
- bne t0, t1, 1b
- /* fill once, so data field parity is correct */
- PTR_LI t0, INDEX_BASE
-2: cache_op FILL t0
- PTR_ADDU t0, a2
- bne t0, t1, 2b
- /* invalidate again - prudent but not strictly neccessary */
- PTR_LI t0, INDEX_BASE
-1: cache_op INDEX_STORE_TAG_I t0
- PTR_ADDU t0, a2
- bne t0, t1, 1b
-9: jr ra
- END(mips_init_icache)
-
-/*
- * mips_init_dcache(uint PRId, ulong dcache_size, unchar dcache_linesz)
- */
-LEAF(mips_init_dcache)
- blez a1, 9f
- mtc0 zero, CP0_TAGLO
- /* clear all tags */
- PTR_LI t0, INDEX_BASE
- PTR_ADDU t1, t0, a1
-1: cache_op INDEX_STORE_TAG_D t0
- PTR_ADDU t0, a2
- bne t0, t1, 1b
- /* load from each line (in cached space) */
- PTR_LI t0, INDEX_BASE
-2: LONG_L zero, 0(t0)
- PTR_ADDU t0, a2
- bne t0, t1, 2b
- /* clear all tags */
- PTR_LI t0, INDEX_BASE
-1: cache_op INDEX_STORE_TAG_D t0
- PTR_ADDU t0, a2
- bne t0, t1, 1b
-9: jr ra
- END(mips_init_dcache)
-
-/*
- * mips_cache_reset - low level initialisation of the primary caches
- *
- * This routine initialises the primary caches to ensure that they have good
- * parity. It must be called by the ROM before any cached locations are used
- * to prevent the possibility of data with bad parity being written to memory.
- *
- * To initialise the instruction cache it is essential that a source of data
- * with good parity is available. This routine will initialise an area of
- * memory starting at location zero to be used as a source of parity.
- *
- * RETURNS: N/A
- *
- */
-NESTED(mips_cache_reset, 0, ra)
- move RA, ra
-
-#if !defined(CONFIG_SYS_ICACHE_SIZE) || !defined(CONFIG_SYS_DCACHE_SIZE) || \
- !defined(CONFIG_SYS_CACHELINE_SIZE)
- /* read Config1 for use below */
- mfc0 t5, CP0_CONFIG, 1
-#endif
-
-#ifdef CONFIG_SYS_CACHELINE_SIZE
- li t7, CONFIG_SYS_CACHELINE_SIZE
- li t8, CONFIG_SYS_CACHELINE_SIZE
-#else
- /* Detect I-cache line size. */
- srl t8, t5, MIPS_CONF1_IL_SHIFT
- andi t8, t8, (MIPS_CONF1_IL >> MIPS_CONF1_IL_SHIFT)
- beqz t8, 1f
- li t6, 2
- sllv t8, t6, t8
-
-1: /* Detect D-cache line size. */
- srl t7, t5, MIPS_CONF1_DL_SHIFT
- andi t7, t7, (MIPS_CONF1_DL >> MIPS_CONF1_DL_SHIFT)
- beqz t7, 1f
- li t6, 2
- sllv t7, t6, t7
-1:
-#endif
-
-#ifdef CONFIG_SYS_ICACHE_SIZE
- li t2, CONFIG_SYS_ICACHE_SIZE
-#else
- /* Detect I-cache size. */
- srl t6, t5, MIPS_CONF1_IS_SHIFT
- andi t6, t6, (MIPS_CONF1_IS >> MIPS_CONF1_IS_SHIFT)
- li t4, 32
- xori t2, t6, 0x7
- beqz t2, 1f
- addi t6, t6, 1
- sllv t4, t4, t6
-1: /* At this point t4 == I-cache sets. */
- mul t2, t4, t8
- srl t6, t5, MIPS_CONF1_IA_SHIFT
- andi t6, t6, (MIPS_CONF1_IA >> MIPS_CONF1_IA_SHIFT)
- addi t6, t6, 1
- /* At this point t6 == I-cache ways. */
- mul t2, t2, t6
-#endif
-
-#ifdef CONFIG_SYS_DCACHE_SIZE
- li t3, CONFIG_SYS_DCACHE_SIZE
-#else
- /* Detect D-cache size. */
- srl t6, t5, MIPS_CONF1_DS_SHIFT
- andi t6, t6, (MIPS_CONF1_DS >> MIPS_CONF1_DS_SHIFT)
- li t4, 32
- xori t3, t6, 0x7
- beqz t3, 1f
- addi t6, t6, 1
- sllv t4, t4, t6
-1: /* At this point t4 == I-cache sets. */
- mul t3, t4, t7
- srl t6, t5, MIPS_CONF1_DA_SHIFT
- andi t6, t6, (MIPS_CONF1_DA >> MIPS_CONF1_DA_SHIFT)
- addi t6, t6, 1
- /* At this point t6 == I-cache ways. */
- mul t3, t3, t6
-#endif
-
- /* Determine the largest L1 cache size */
-#if defined(CONFIG_SYS_ICACHE_SIZE) && defined(CONFIG_SYS_DCACHE_SIZE)
-#if CONFIG_SYS_ICACHE_SIZE > CONFIG_SYS_DCACHE_SIZE
- li v0, CONFIG_SYS_ICACHE_SIZE
-#else
- li v0, CONFIG_SYS_DCACHE_SIZE
-#endif
-#else
- move v0, t2
- sltu t1, t2, t3
- movn v0, t3, t1
-#endif
- /*
- * Now clear that much memory starting from zero.
- */
- PTR_LI a0, CKSEG1
- PTR_ADDU a1, a0, v0
-2: PTR_ADDIU a0, 64
- f_fill64 a0, -64, zero
- bne a0, a1, 2b
-
- /*
- * The caches are probably in an indeterminate state,
- * so we force good parity into them by doing an
- * invalidate, load/fill, invalidate for each line.
- */
-
- /*
- * Assume bottom of RAM will generate good parity for the cache.
- */
-
- /*
- * Initialize the I-cache first,
- */
- move a1, t2
- move a2, t8
- PTR_LA v1, mips_init_icache
- jalr v1
-
- /*
- * then initialize D-cache.
- */
- move a1, t3
- move a2, t7
- PTR_LA v1, mips_init_dcache
- jalr v1
-
- jr RA
- END(mips_cache_reset)
-
-/*
- * dcache_status - get cache status
- *
- * RETURNS: 0 - cache disabled; 1 - cache enabled
- *
- */
-LEAF(dcache_status)
- mfc0 t0, CP0_CONFIG
- li t1, CONF_CM_UNCACHED
- andi t0, t0, CONF_CM_CMASK
- move v0, zero
- beq t0, t1, 2f
- li v0, 1
-2: jr ra
- END(dcache_status)
-
-/*
- * dcache_disable - disable cache
- *
- * RETURNS: N/A
- *
- */
-LEAF(dcache_disable)
- mfc0 t0, CP0_CONFIG
- li t1, -8
- and t0, t0, t1
- ori t0, t0, CONF_CM_UNCACHED
- mtc0 t0, CP0_CONFIG
- jr ra
- END(dcache_disable)
-
-/*
- * dcache_enable - enable cache
- *
- * RETURNS: N/A
- *
- */
-LEAF(dcache_enable)
- mfc0 t0, CP0_CONFIG
- ori t0, CONF_CM_CMASK
- xori t0, CONF_CM_CMASK
- ori t0, CONFIG_SYS_MIPS_CACHE_MODE
- mtc0 t0, CP0_CONFIG
- jr ra
- END(dcache_enable)
diff --git a/arch/mips/cpu/mips32/cpu.c b/arch/mips/cpu/mips32/cpu.c
deleted file mode 100644
index 278865b..0000000
--- a/arch/mips/cpu/mips32/cpu.c
+++ /dev/null
@@ -1,161 +0,0 @@
-/*
- * (C) Copyright 2003
- * Wolfgang Denk, DENX Software Engineering, <wd@denx.de>
- *
- * SPDX-License-Identifier: GPL-2.0+
- */
-
-#include <common.h>
-#include <command.h>
-#include <netdev.h>
-#include <asm/mipsregs.h>
-#include <asm/cacheops.h>
-#include <asm/reboot.h>
-
-#define cache_op(op,addr) \
- __asm__ __volatile__( \
- " .set push \n" \
- " .set noreorder \n" \
- " .set mips3\n\t \n" \
- " cache %0, %1 \n" \
- " .set pop \n" \
- : \
- : "i" (op), "R" (*(unsigned char *)(addr)))
-
-void __attribute__((weak)) _machine_restart(void)
-{
-}
-
-int do_reset(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
-{
- _machine_restart();
-
- fprintf(stderr, "*** reset failed ***\n");
- return 0;
-}
-
-#ifdef CONFIG_SYS_CACHELINE_SIZE
-
-static inline unsigned long icache_line_size(void)
-{
- return CONFIG_SYS_CACHELINE_SIZE;
-}
-
-static inline unsigned long dcache_line_size(void)
-{
- return CONFIG_SYS_CACHELINE_SIZE;
-}
-
-#else /* !CONFIG_SYS_CACHELINE_SIZE */
-
-static inline unsigned long icache_line_size(void)
-{
- unsigned long conf1, il;
- conf1 = read_c0_config1();
- il = (conf1 & MIPS_CONF1_IL) >> MIPS_CONF1_IL_SHIFT;
- if (!il)
- return 0;
- return 2 << il;
-}
-
-static inline unsigned long dcache_line_size(void)
-{
- unsigned long conf1, dl;
- conf1 = read_c0_config1();
- dl = (conf1 & MIPS_CONF1_DL) >> MIPS_CONF1_DL_SHIFT;
- if (!dl)
- return 0;
- return 2 << dl;
-}
-
-#endif /* !CONFIG_SYS_CACHELINE_SIZE */
-
-void flush_cache(ulong start_addr, ulong size)
-{
- unsigned long ilsize = icache_line_size();
- unsigned long dlsize = dcache_line_size();
- unsigned long addr, aend;
-
- /* aend will be miscalculated when size is zero, so we return here */
- if (size == 0)
- return;
-
- addr = start_addr & ~(dlsize - 1);
- aend = (start_addr + size - 1) & ~(dlsize - 1);
-
- if (ilsize == dlsize) {
- /* flush I-cache & D-cache simultaneously */
- while (1) {
- cache_op(HIT_WRITEBACK_INV_D, addr);
- cache_op(HIT_INVALIDATE_I, addr);
- if (addr == aend)
- break;
- addr += dlsize;
- }
- return;
- }
-
- /* flush D-cache */
- while (1) {
- cache_op(HIT_WRITEBACK_INV_D, addr);
- if (addr == aend)
- break;
- addr += dlsize;
- }
-
- /* flush I-cache */
- addr = start_addr & ~(ilsize - 1);
- aend = (start_addr + size - 1) & ~(ilsize - 1);
- while (1) {
- cache_op(HIT_INVALIDATE_I, addr);
- if (addr == aend)
- break;
- addr += ilsize;
- }
-}
-
-void flush_dcache_range(ulong start_addr, ulong stop)
-{
- unsigned long lsize = dcache_line_size();
- unsigned long addr = start_addr & ~(lsize - 1);
- unsigned long aend = (stop - 1) & ~(lsize - 1);
-
- while (1) {
- cache_op(HIT_WRITEBACK_INV_D, addr);
- if (addr == aend)
- break;
- addr += lsize;
- }
-}
-
-void invalidate_dcache_range(ulong start_addr, ulong stop)
-{
- unsigned long lsize = dcache_line_size();
- unsigned long addr = start_addr & ~(lsize - 1);
- unsigned long aend = (stop - 1) & ~(lsize - 1);
-
- while (1) {
- cache_op(HIT_INVALIDATE_D, addr);
- if (addr == aend)
- break;
- addr += lsize;
- }
-}
-
-void write_one_tlb(int index, u32 pagemask, u32 hi, u32 low0, u32 low1)
-{
- write_c0_entrylo0(low0);
- write_c0_pagemask(pagemask);
- write_c0_entrylo1(low1);
- write_c0_entryhi(hi);
- write_c0_index(index);
- tlb_write_indexed();
-}
-
-int cpu_eth_init(bd_t *bis)
-{
-#ifdef CONFIG_SOC_AU1X00
- au1x00_enet_initialize(bis);
-#endif
- return 0;
-}
diff --git a/arch/mips/cpu/mips64/Makefile b/arch/mips/cpu/mips64/Makefile
deleted file mode 100644
index 899c319..0000000
--- a/arch/mips/cpu/mips64/Makefile
+++ /dev/null
@@ -1,9 +0,0 @@
-#
-# (C) Copyright 2003-2006
-# Wolfgang Denk, DENX Software Engineering, wd@denx.de.
-#
-# SPDX-License-Identifier: GPL-2.0+
-#
-
-extra-y = start.o
-obj-y = cpu.o interrupts.o time.o cache.o
diff --git a/arch/mips/cpu/mips64/cache.S b/arch/mips/cpu/mips64/cache.S
deleted file mode 100644
index 36d8688..0000000
--- a/arch/mips/cpu/mips64/cache.S
+++ /dev/null
@@ -1,213 +0,0 @@
-/*
- * Cache-handling routined for MIPS CPUs
- *
- * Copyright (c) 2003 Wolfgang Denk <wd@denx.de>
- *
- * SPDX-License-Identifier: GPL-2.0+
- */
-
-#include <asm-offsets.h>
-#include <config.h>
-#include <asm/asm.h>
-#include <asm/regdef.h>
-#include <asm/mipsregs.h>
-#include <asm/addrspace.h>
-#include <asm/cacheops.h>
-
-#define RA t9
-
-/*
- * 16kB is the maximum size of instruction and data caches on MIPS 4K,
- * 64kB is on 4KE, 24K, 5K, etc. Set bigger size for convenience.
- *
- * Note that the above size is the maximum size of primary cache. U-Boot
- * doesn't have L2 cache support for now.
- */
-#define MIPS_MAX_CACHE_SIZE 0x10000
-
-#define INDEX_BASE CKSEG0
-
- .macro cache_op op addr
- .set push
- .set noreorder
- .set mips3
- cache \op, 0(\addr)
- .set pop
- .endm
-
- .macro f_fill64 dst, offset, val
- LONG_S \val, (\offset + 0 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 1 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 2 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 3 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 4 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 5 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 6 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 7 * LONGSIZE)(\dst)
-#if LONGSIZE == 4
- LONG_S \val, (\offset + 8 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 9 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 10 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 11 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 12 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 13 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 14 * LONGSIZE)(\dst)
- LONG_S \val, (\offset + 15 * LONGSIZE)(\dst)
-#endif
- .endm
-
-/*
- * mips_init_icache(uint PRId, ulong icache_size, unchar icache_linesz)
- */
-LEAF(mips_init_icache)
- blez a1, 9f
- mtc0 zero, CP0_TAGLO
- /* clear tag to invalidate */
- PTR_LI t0, INDEX_BASE
- PTR_ADDU t1, t0, a1
-1: cache_op INDEX_STORE_TAG_I t0
- PTR_ADDU t0, a2
- bne t0, t1, 1b
- /* fill once, so data field parity is correct */
- PTR_LI t0, INDEX_BASE
-2: cache_op FILL t0
- PTR_ADDU t0, a2
- bne t0, t1, 2b
- /* invalidate again - prudent but not strictly neccessary */
- PTR_LI t0, INDEX_BASE
-1: cache_op INDEX_STORE_TAG_I t0
- PTR_ADDU t0, a2
- bne t0, t1, 1b
-9: jr ra
- END(mips_init_icache)
-
-/*
- * mips_init_dcache(uint PRId, ulong dcache_size, unchar dcache_linesz)
- */
-LEAF(mips_init_dcache)
- blez a1, 9f
- mtc0 zero, CP0_TAGLO
- /* clear all tags */
- PTR_LI t0, INDEX_BASE
- PTR_ADDU t1, t0, a1
-1: cache_op INDEX_STORE_TAG_D t0
- PTR_ADDU t0, a2
- bne t0, t1, 1b
- /* load from each line (in cached space) */
- PTR_LI t0, INDEX_BASE
-2: LONG_L zero, 0(t0)
- PTR_ADDU t0, a2
- bne t0, t1, 2b
- /* clear all tags */
- PTR_LI t0, INDEX_BASE
-1: cache_op INDEX_STORE_TAG_D t0
- PTR_ADDU t0, a2
- bne t0, t1, 1b
-9: jr ra
- END(mips_init_dcache)
-
-/*
- * mips_cache_reset - low level initialisation of the primary caches
- *
- * This routine initialises the primary caches to ensure that they have good
- * parity. It must be called by the ROM before any cached locations are used
- * to prevent the possibility of data with bad parity being written to memory.
- *
- * To initialise the instruction cache it is essential that a source of data
- * with good parity is available. This routine will initialise an area of
- * memory starting at location zero to be used as a source of parity.
- *
- * RETURNS: N/A
- *
- */
-NESTED(mips_cache_reset, 0, ra)
- move RA, ra
- li t2, CONFIG_SYS_ICACHE_SIZE
- li t3, CONFIG_SYS_DCACHE_SIZE
- li t8, CONFIG_SYS_CACHELINE_SIZE
-
- li v0, MIPS_MAX_CACHE_SIZE
-
- /*
- * Now clear that much memory starting from zero.
- */
- PTR_LI a0, CKSEG1
- PTR_ADDU a1, a0, v0
-2: PTR_ADDIU a0, 64
- f_fill64 a0, -64, zero
- bne a0, a1, 2b
-
- /*
- * The caches are probably in an indeterminate state,
- * so we force good parity into them by doing an
- * invalidate, load/fill, invalidate for each line.
- */
-
- /*
- * Assume bottom of RAM will generate good parity for the cache.
- */
-
- /*
- * Initialize the I-cache first,
- */
- move a1, t2
- move a2, t8
- PTR_LA v1, mips_init_icache
- jalr v1
-
- /*
- * then initialize D-cache.
- */
- move a1, t3
- move a2, t8
- PTR_LA v1, mips_init_dcache
- jalr v1
-
- jr RA
- END(mips_cache_reset)
-
-/*
- * dcache_status - get cache status
- *
- * RETURNS: 0 - cache disabled; 1 - cache enabled
- *
- */
-LEAF(dcache_status)
- mfc0 t0, CP0_CONFIG
- li t1, CONF_CM_UNCACHED
- andi t0, t0, CONF_CM_CMASK
- move v0, zero
- beq t0, t1, 2f
- li v0, 1
-2: jr ra
- END(dcache_status)
-
-/*
- * dcache_disable - disable cache
- *
- * RETURNS: N/A
- *
- */
-LEAF(dcache_disable)
- mfc0 t0, CP0_CONFIG
- li t1, -8
- and t0, t0, t1
- ori t0, t0, CONF_CM_UNCACHED
- mtc0 t0, CP0_CONFIG
- jr ra
- END(dcache_disable)
-
-/*
- * dcache_enable - enable cache
- *
- * RETURNS: N/A
- *
- */
-LEAF(dcache_enable)
- mfc0 t0, CP0_CONFIG
- ori t0, CONF_CM_CMASK
- xori t0, CONF_CM_CMASK
- ori t0, CONF_CM_CACHABLE_NONCOHERENT
- mtc0 t0, CP0_CONFIG
- jr ra
- END(dcache_enable)
diff --git a/arch/mips/cpu/mips64/cpu.c b/arch/mips/cpu/mips64/cpu.c
deleted file mode 100644
index 9f45cfc..0000000
--- a/arch/mips/cpu/mips64/cpu.c
+++ /dev/null
@@ -1,95 +0,0 @@
-/*
- * (C) Copyright 2003
- * Wolfgang Denk, DENX Software Engineering, <wd@denx.de>
- *
- * SPDX-License-Identifier: GPL-2.0+
- */
-
-#include <common.h>
-#include <command.h>
-#include <netdev.h>
-#include <asm/mipsregs.h>
-#include <asm/cacheops.h>
-#include <asm/reboot.h>
-
-#define cache_op(op, addr) \
- __asm__ __volatile__( \
- " .set push\n" \
- " .set noreorder\n" \
- " .set mips64\n" \
- " cache %0, %1\n" \
- " .set pop\n" \
- : \
- : "i" (op), "R" (*(unsigned char *)(addr)))
-
-void __attribute__((weak)) _machine_restart(void)
-{
- fprintf(stderr, "*** reset failed ***\n");
-
- while (1)
- /* NOP */;
-}
-
-int do_reset(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
-{
- _machine_restart();
-
- return 0;
-}
-
-void flush_cache(ulong start_addr, ulong size)
-{
- unsigned long lsize = CONFIG_SYS_CACHELINE_SIZE;
- unsigned long addr = start_addr & ~(lsize - 1);
- unsigned long aend = (start_addr + size - 1) & ~(lsize - 1);
-
- /* aend will be miscalculated when size is zero, so we return here */
- if (size == 0)
- return;
-
- while (1) {
- cache_op(HIT_WRITEBACK_INV_D, addr);
- cache_op(HIT_INVALIDATE_I, addr);
- if (addr == aend)
- break;
- addr += lsize;
- }
-}
-
-void flush_dcache_range(ulong start_addr, ulong stop)
-{
- unsigned long lsize = CONFIG_SYS_CACHELINE_SIZE;
- unsigned long addr = start_addr & ~(lsize - 1);
- unsigned long aend = (stop - 1) & ~(lsize - 1);
-
- while (1) {
- cache_op(HIT_WRITEBACK_INV_D, addr);
- if (addr == aend)
- break;
- addr += lsize;
- }
-}
-
-void invalidate_dcache_range(ulong start_addr, ulong stop)
-{
- unsigned long lsize = CONFIG_SYS_CACHELINE_SIZE;
- unsigned long addr = start_addr & ~(lsize - 1);
- unsigned long aend = (stop - 1) & ~(lsize - 1);
-
- while (1) {
- cache_op(HIT_INVALIDATE_D, addr);
- if (addr == aend)
- break;
- addr += lsize;
- }
-}
-
-void write_one_tlb(int index, u32 pagemask, u32 hi, u32 low0, u32 low1)
-{
- write_c0_entrylo0(low0);
- write_c0_pagemask(pagemask);
- write_c0_entrylo1(low1);
- write_c0_entryhi(hi);
- write_c0_index(index);
- tlb_write_indexed();
-}
diff --git a/arch/mips/cpu/mips64/interrupts.c b/arch/mips/cpu/mips64/interrupts.c
deleted file mode 100644
index 275fcf5..0000000
--- a/arch/mips/cpu/mips64/interrupts.c
+++ /dev/null
@@ -1,22 +0,0 @@
-/*
- * (C) Copyright 2003
- * Wolfgang Denk, DENX Software Engineering, <wd@denx.de>
- *
- * SPDX-License-Identifier: GPL-2.0+
- */
-
-#include <common.h>
-
-int interrupt_init(void)
-{
- return 0;
-}
-
-void enable_interrupts(void)
-{
-}
-
-int disable_interrupts(void)
-{
- return 0;
-}
diff --git a/arch/mips/cpu/mips64/start.S b/arch/mips/cpu/mips64/start.S
deleted file mode 100644
index 471bc1e..0000000
--- a/arch/mips/cpu/mips64/start.S
+++ /dev/null
@@ -1,291 +0,0 @@
-/*
- * Startup Code for MIPS64 CPU-core
- *
- * Copyright (c) 2003 Wolfgang Denk <wd@denx.de>
- *
- * SPDX-License-Identifier: GPL-2.0+
- */
-
-#include <asm-offsets.h>
-#include <config.h>
-#include <asm/regdef.h>
-#include <asm/mipsregs.h>
-
-#ifndef CONFIG_SYS_MIPS_CACHE_MODE
-#define CONFIG_SYS_MIPS_CACHE_MODE CONF_CM_CACHABLE_NONCOHERENT
-#endif
-
-#ifndef CONFIG_SYS_INIT_SP_ADDR
-#define CONFIG_SYS_INIT_SP_ADDR (CONFIG_SYS_SDRAM_BASE + \
- CONFIG_SYS_INIT_SP_OFFSET)
-#endif
-
-#ifdef CONFIG_SYS_LITTLE_ENDIAN
-#define MIPS64_R_INFO(ssym, r_type3, r_type2, r_type) \
- (((r_type) << 24) | ((r_type2) << 16) | ((r_type3) << 8) | (ssym))
-#else
-#define MIPS64_R_INFO(ssym, r_type3, r_type2, r_type) \
- ((r_type) | ((r_type2) << 8) | ((r_type3) << 16) | (ssym) << 24)
-#endif
-
- /*
- * For the moment disable interrupts, mark the kernel mode and
- * set ST0_KX so that the CPU does not spit fire when using
- * 64-bit addresses.
- */
- .macro setup_c0_status set clr
- .set push
- mfc0 t0, CP0_STATUS
- or t0, ST0_CU0 | \set | 0x1f | \clr
- xor t0, 0x1f | \clr
- mtc0 t0, CP0_STATUS
- .set noreorder
- sll zero, 3 # ehb
- .set pop
- .endm
-
- .set noreorder
-
- .globl _start
- .text
-_start:
- /* U-boot entry point */
- b reset
- nop
-
- .org 0x200
- /* TLB refill, 32 bit task */
-1: b 1b
- nop
-
- .org 0x280
- /* XTLB refill, 64 bit task */
-1: b 1b
- nop
-
- .org 0x300
- /* Cache error exception */
-1: b 1b
- nop
-
- .org 0x380
- /* General exception */
-1: b 1b
- nop
-
- .org 0x400
- /* Catch interrupt exceptions */
-1: b 1b
- nop
-
- .org 0x480
- /* EJTAG debug exception */
-1: b 1b
- nop
-
- .align 4
-reset:
-
- /* Clear watch registers */
- dmtc0 zero, CP0_WATCHLO
- dmtc0 zero, CP0_WATCHHI
-
- /* WP(Watch Pending), SW0/1 should be cleared */
- mtc0 zero, CP0_CAUSE
-
- setup_c0_status ST0_KX 0
-
- /* Init Timer */
- mtc0 zero, CP0_COUNT
- mtc0 zero, CP0_COMPARE
-
-#ifndef CONFIG_SKIP_LOWLEVEL_INIT
- /* CONFIG0 register */
- dli t0, CONF_CM_UNCACHED
- mtc0 t0, CP0_CONFIG
-#endif
-
- /*
- * Initialize $gp, force 8 byte alignment of bal instruction to forbid
- * the compiler to put nop's between bal and _gp. This is required to
- * keep _gp and ra aligned to 8 byte.
- */
- .align 3
- bal 1f
- nop
- .dword _gp
-1:
- ld gp, 0(ra)
-
-#ifndef CONFIG_SKIP_LOWLEVEL_INIT
- /* Initialize any external memory */
- dla t9, lowlevel_init
- jalr t9
- nop
-
- /* Initialize caches... */
- dla t9, mips_cache_reset
- jalr t9
- nop
-
- /* ... and enable them */
- dli t0, CONFIG_SYS_MIPS_CACHE_MODE
- mtc0 t0, CP0_CONFIG
-#endif
-
- /* Set up temporary stack */
- dli t0, -16
- dli t1, CONFIG_SYS_INIT_SP_ADDR
- and sp, t1, t0 # force 16 byte alignment
- dsub sp, sp, GD_SIZE # reserve space for gd
- and sp, sp, t0 # force 16 byte alignment
- move k0, sp # save gd pointer
-#ifdef CONFIG_SYS_MALLOC_F_LEN
- dli t2, CONFIG_SYS_MALLOC_F_LEN
- dsub sp, sp, t2 # reserve space for early malloc
- and sp, sp, t0 # force 16 byte alignment
-#endif
- move fp, sp
-
- /* Clear gd */
- move t0, k0
-1:
- sw zero, 0(t0)
- blt t0, t1, 1b
- daddi t0, 4
-
-#ifdef CONFIG_SYS_MALLOC_F_LEN
- daddu t0, k0, GD_MALLOC_BASE # gd->malloc_base offset
- sw sp, 0(t0)
-#endif
-
- dla t9, board_init_f
- jr t9
- move ra, zero
-
-/*
- * void relocate_code (addr_sp, gd, addr_moni)
- *
- * This "function" does not return, instead it continues in RAM
- * after relocating the monitor code.
- *
- * a0 = addr_sp
- * a1 = gd
- * a2 = destination address
- */
- .globl relocate_code
- .ent relocate_code
-relocate_code:
- move sp, a0 # set new stack pointer
- move fp, sp
-
- move s0, a1 # save gd in s0
- move s2, a2 # save destination address in s2
-
- dli t0, CONFIG_SYS_MONITOR_BASE
- dsub s1, s2, t0 # s1 <-- relocation offset
-
- dla t3, in_ram
- ld t2, -24(t3) # t2 <-- __image_copy_end
- move t1, a2
-
- dadd gp, s1 # adjust gp
-
- /*
- * t0 = source address
- * t1 = target address
- * t2 = source end address
- */
-1:
- lw t3, 0(t0)
- sw t3, 0(t1)
- daddu t0, 4
- blt t0, t2, 1b
- daddu t1, 4
-
- /* If caches were enabled, we would have to flush them here. */
- dsub a1, t1, s2 # a1 <-- size
- dla t9, flush_cache
- jalr t9
- move a0, s2 # a0 <-- destination address
-
- /* Jump to where we've relocated ourselves */
- daddi t0, s2, in_ram - _start
- jr t0
- nop
-
- .dword __rel_dyn_end
- .dword __rel_dyn_start
- .dword __image_copy_end
- .dword _GLOBAL_OFFSET_TABLE_
- .dword num_got_entries
-
-in_ram:
- /*
- * Now we want to update GOT.
- *
- * GOT[0] is reserved. GOT[1] is also reserved for the dynamic object
- * generated by GNU ld. Skip these reserved entries from relocation.
- */
- ld t3, -8(t0) # t3 <-- num_got_entries
- ld t8, -16(t0) # t8 <-- _GLOBAL_OFFSET_TABLE_
- dadd t8, s1 # t8 now holds relocated _G_O_T_
- daddi t8, t8, 16 # skipping first two entries
- dli t2, 2
-1:
- ld t1, 0(t8)
- beqz t1, 2f
- dadd t1, s1
- sd t1, 0(t8)
-2:
- daddi t2, 1
- blt t2, t3, 1b
- daddi t8, 8
-
- /* Update dynamic relocations */
- ld t1, -32(t0) # t1 <-- __rel_dyn_start
- ld t2, -40(t0) # t2 <-- __rel_dyn_end
-
- b 2f # skip first reserved entry
- daddi t1, 16
-
-1:
- lw t8, -4(t1) # t8 <-- relocation info
-
- dli t3, MIPS64_R_INFO(0x00, 0x00, 0x12, 0x03)
- bne t8, t3, 2f # skip non R_MIPS_REL32 entries
- nop
-
- ld t3, -16(t1) # t3 <-- location to fix up in FLASH
-
- ld t8, 0(t3) # t8 <-- original pointer
- dadd t8, s1 # t8 <-- adjusted pointer
-
- dadd t3, s1 # t3 <-- location to fix up in RAM
- sd t8, 0(t3)
-
-2:
- blt t1, t2, 1b
- daddi t1, 16 # each rel.dyn entry is 16 bytes
-
- /*
- * Clear BSS
- *
- * GOT is now relocated. Thus __bss_start and __bss_end can be
- * accessed directly via $gp.
- */
- dla t1, __bss_start # t1 <-- __bss_start
- dla t2, __bss_end # t2 <-- __bss_end
-
-1:
- sd zero, 0(t1)
- blt t1, t2, 1b
- daddi t1, 8
-
- move a0, s0 # a0 <-- gd
- move a1, s2
- dla t9, board_init_r
- jr t9
- move ra, zero
-
- .end relocate_code
diff --git a/arch/mips/cpu/mips64/time.c b/arch/mips/cpu/mips64/time.c
deleted file mode 100644
index 553da5f..0000000
--- a/arch/mips/cpu/mips64/time.c
+++ /dev/null
@@ -1,19 +0,0 @@
-/*
- * (C) Copyright 2003
- * Wolfgang Denk, DENX Software Engineering, wd@denx.de.
- *
- * SPDX-License-Identifier: GPL-2.0+
- */
-
-#include <common.h>
-#include <asm/mipsregs.h>
-
-unsigned long notrace timer_read_counter(void)
-{
- return read_c0_count();
-}
-
-ulong notrace get_tbclk(void)
-{
- return CONFIG_SYS_MIPS_TIMER_FREQ;
-}
diff --git a/arch/mips/cpu/mips32/start.S b/arch/mips/cpu/start.S
similarity index 61%
rename from arch/mips/cpu/mips32/start.S
rename to arch/mips/cpu/start.S
index 36b92cc..3b5b622 100644
--- a/arch/mips/cpu/mips32/start.S
+++ b/arch/mips/cpu/start.S
@@ -8,6 +8,7 @@
#include <asm-offsets.h>
#include <config.h>
+#include <asm/asm.h>
#include <asm/regdef.h>
#include <asm/mipsregs.h>
@@ -20,6 +21,23 @@
CONFIG_SYS_INIT_SP_OFFSET)
#endif
+#ifdef CONFIG_32BIT
+# define MIPS_RELOC 3
+# define STATUS_SET 0
+#endif
+
+#ifdef CONFIG_64BIT
+# ifdef CONFIG_SYS_LITTLE_ENDIAN
+# define MIPS64_R_INFO(ssym, r_type3, r_type2, r_type) \
+ (((r_type) << 24) | ((r_type2) << 16) | ((r_type3) << 8) | (ssym))
+# else
+# define MIPS64_R_INFO(ssym, r_type3, r_type2, r_type) \
+ ((r_type) | ((r_type2) << 8) | ((r_type3) << 16) | (ssym) << 24)
+# endif
+# define MIPS_RELOC MIPS64_R_INFO(0x00, 0x00, 0x12, 0x03)
+# define STATUS_SET ST0_KX
+#endif
+
/*
* For the moment disable interrupts, mark the kernel mode and
* set ST0_KX so that the CPU does not spit fire when using
@@ -98,13 +116,13 @@
reset:
/* Clear watch registers */
- mtc0 zero, CP0_WATCHLO
- mtc0 zero, CP0_WATCHHI
+ MTC0 zero, CP0_WATCHLO
+ MTC0 zero, CP0_WATCHHI
/* WP(Watch Pending), SW0/1 should be cleared */
mtc0 zero, CP0_CAUSE
- setup_c0_status 0 0
+ setup_c0_status STATUS_SET 0
/* Init Timer */
mtc0 zero, CP0_COUNT
@@ -116,21 +134,26 @@
mtc0 t0, CP0_CONFIG
#endif
- /* Initialize $gp */
+ /*
+ * Initialize $gp, force pointer sized alignment of bal instruction to
+ * forbid the compiler to put nop's between bal and _gp. This is
+ * required to keep _gp and ra aligned to 8 byte.
+ */
+ .align PTRLOG
bal 1f
nop
- .word _gp
+ PTR _gp
1:
- lw gp, 0(ra)
+ PTR_L gp, 0(ra)
#ifndef CONFIG_SKIP_LOWLEVEL_INIT
/* Initialize any external memory */
- la t9, lowlevel_init
+ PTR_LA t9, lowlevel_init
jalr t9
nop
/* Initialize caches... */
- la t9, mips_cache_reset
+ PTR_LA t9, mips_cache_reset
jalr t9
nop
@@ -140,15 +163,15 @@
#endif
/* Set up temporary stack */
- li t0, -16
- li t1, CONFIG_SYS_INIT_SP_ADDR
+ PTR_LI t0, -16
+ PTR_LI t1, CONFIG_SYS_INIT_SP_ADDR
and sp, t1, t0 # force 16 byte alignment
- sub sp, sp, GD_SIZE # reserve space for gd
+ PTR_SUB sp, sp, GD_SIZE # reserve space for gd
and sp, sp, t0 # force 16 byte alignment
move k0, sp # save gd pointer
#ifdef CONFIG_SYS_MALLOC_F_LEN
- li t2, CONFIG_SYS_MALLOC_F_LEN
- sub sp, sp, t2 # reserve space for early malloc
+ PTR_LI t2, CONFIG_SYS_MALLOC_F_LEN
+ PTR_SUB sp, sp, t2 # reserve space for early malloc
and sp, sp, t0 # force 16 byte alignment
#endif
move fp, sp
@@ -158,14 +181,14 @@
1:
sw zero, 0(t0)
blt t0, t1, 1b
- addi t0, 4
+ PTR_ADDI t0, 4
#ifdef CONFIG_SYS_MALLOC_F_LEN
- addu t0, k0, GD_MALLOC_BASE # gd->malloc_base offset
+ PTR_ADDU t0, k0, GD_MALLOC_BASE # gd->malloc_base offset
sw sp, 0(t0)
#endif
- la t9, board_init_f
+ PTR_LA t9, board_init_f
jr t9
move ra, zero
@@ -188,14 +211,14 @@
move s0, a1 # save gd in s0
move s2, a2 # save destination address in s2
- li t0, CONFIG_SYS_MONITOR_BASE
- sub s1, s2, t0 # s1 <-- relocation offset
+ PTR_LI t0, CONFIG_SYS_MONITOR_BASE
+ PTR_SUB s1, s2, t0 # s1 <-- relocation offset
- la t3, in_ram
- lw t2, -12(t3) # t2 <-- __image_copy_end
+ PTR_LA t3, in_ram
+ PTR_L t2, -(3 * PTRSIZE)(t3) # t2 <-- __image_copy_end
move t1, a2
- add gp, s1 # adjust gp
+ PTR_ADD gp, s1 # adjust gp
/*
* t0 = source address
@@ -205,26 +228,26 @@
1:
lw t3, 0(t0)
sw t3, 0(t1)
- addu t0, 4
+ PTR_ADDU t0, 4
blt t0, t2, 1b
- addu t1, 4
+ PTR_ADDU t1, 4
/* If caches were enabled, we would have to flush them here. */
- sub a1, t1, s2 # a1 <-- size
- la t9, flush_cache
+ PTR_SUB a1, t1, s2 # a1 <-- size
+ PTR_LA t9, flush_cache
jalr t9
move a0, s2 # a0 <-- destination address
/* Jump to where we've relocated ourselves */
- addi t0, s2, in_ram - _start
+ PTR_ADDI t0, s2, in_ram - _start
jr t0
nop
- .word __rel_dyn_end
- .word __rel_dyn_start
- .word __image_copy_end
- .word _GLOBAL_OFFSET_TABLE_
- .word num_got_entries
+ PTR __rel_dyn_end
+ PTR __rel_dyn_start
+ PTR __image_copy_end
+ PTR _GLOBAL_OFFSET_TABLE_
+ PTR num_got_entries
in_ram:
/*
@@ -233,46 +256,46 @@
* GOT[0] is reserved. GOT[1] is also reserved for the dynamic object
* generated by GNU ld. Skip these reserved entries from relocation.
*/
- lw t3, -4(t0) # t3 <-- num_got_entries
- lw t8, -8(t0) # t8 <-- _GLOBAL_OFFSET_TABLE_
- add t8, s1 # t8 now holds relocated _G_O_T_
- addi t8, t8, 8 # skipping first two entries
- li t2, 2
+ PTR_L t3, -(1 * PTRSIZE)(t0) # t3 <-- num_got_entries
+ PTR_L t8, -(2 * PTRSIZE)(t0) # t8 <-- _GLOBAL_OFFSET_TABLE_
+ PTR_ADD t8, s1 # t8 now holds relocated _G_O_T_
+ PTR_ADDI t8, t8, 2 * PTRSIZE # skipping first two entries
+ PTR_LI t2, 2
1:
- lw t1, 0(t8)
+ PTR_L t1, 0(t8)
beqz t1, 2f
- add t1, s1
- sw t1, 0(t8)
+ PTR_ADD t1, s1
+ PTR_S t1, 0(t8)
2:
- addi t2, 1
+ PTR_ADDI t2, 1
blt t2, t3, 1b
- addi t8, 4
+ PTR_ADDI t8, PTRSIZE
/* Update dynamic relocations */
- lw t1, -16(t0) # t1 <-- __rel_dyn_start
- lw t2, -20(t0) # t2 <-- __rel_dyn_end
+ PTR_L t1, -(4 * PTRSIZE)(t0) # t1 <-- __rel_dyn_start
+ PTR_L t2, -(5 * PTRSIZE)(t0) # t2 <-- __rel_dyn_end
b 2f # skip first reserved entry
- addi t1, 8
+ PTR_ADDI t1, 2 * PTRSIZE
1:
lw t8, -4(t1) # t8 <-- relocation info
- li t3, 3
- bne t8, t3, 2f # skip non R_MIPS_REL32 entries
+ PTR_LI t3, MIPS_RELOC
+ bne t8, t3, 2f # skip non-MIPS_RELOC entries
nop
- lw t3, -8(t1) # t3 <-- location to fix up in FLASH
+ PTR_L t3, -(2 * PTRSIZE)(t1) # t3 <-- location to fix up in FLASH
- lw t8, 0(t3) # t8 <-- original pointer
- add t8, s1 # t8 <-- adjusted pointer
+ PTR_L t8, 0(t3) # t8 <-- original pointer
+ PTR_ADD t8, s1 # t8 <-- adjusted pointer
- add t3, s1 # t3 <-- location to fix up in RAM
- sw t8, 0(t3)
+ PTR_ADD t3, s1 # t3 <-- location to fix up in RAM
+ PTR_S t8, 0(t3)
2:
blt t1, t2, 1b
- addi t1, 8 # each rel.dyn entry is 8 bytes
+ PTR_ADDI t1, 2 * PTRSIZE # each rel.dyn entry is 2*PTRSIZE bytes
/*
* Clear BSS
@@ -280,17 +303,17 @@
* GOT is now relocated. Thus __bss_start and __bss_end can be
* accessed directly via $gp.
*/
- la t1, __bss_start # t1 <-- __bss_start
- la t2, __bss_end # t2 <-- __bss_end
+ PTR_LA t1, __bss_start # t1 <-- __bss_start
+ PTR_LA t2, __bss_end # t2 <-- __bss_end
1:
- sw zero, 0(t1)
+ PTR_S zero, 0(t1)
blt t1, t2, 1b
- addi t1, 4
+ PTR_ADDI t1, PTRSIZE
move a0, s0 # a0 <-- gd
move a1, s2
- la t9, board_init_r
+ PTR_LA t9, board_init_r
jr t9
move ra, zero
diff --git a/arch/mips/cpu/mips32/time.c b/arch/mips/cpu/time.c
similarity index 100%
rename from arch/mips/cpu/mips32/time.c
rename to arch/mips/cpu/time.c
diff --git a/arch/mips/include/asm/cacheops.h b/arch/mips/include/asm/cacheops.h
index 6464250..75ec380 100644
--- a/arch/mips/include/asm/cacheops.h
+++ b/arch/mips/include/asm/cacheops.h
@@ -11,6 +11,19 @@
#ifndef __ASM_CACHEOPS_H
#define __ASM_CACHEOPS_H
+#ifndef __ASSEMBLY__
+
+static inline void mips_cache(int op, const volatile void *addr)
+{
+#ifdef __GCC_HAVE_BUILTIN_MIPS_CACHE
+ __builtin_mips_cache(op, addr);
+#else
+ __asm__ __volatile__("cache %0, %1" : : "i"(op), "R"(addr))
+#endif
+}
+
+#endif /* !__ASSEMBLY__ */
+
/*
* Cache Operations available on all MIPS processors with R4000-style caches
*/
diff --git a/arch/mips/include/asm/malta.h b/arch/mips/include/asm/malta.h
index 9e7c045..d9ffc15 100644
--- a/arch/mips/include/asm/malta.h
+++ b/arch/mips/include/asm/malta.h
@@ -64,4 +64,9 @@
#define PCI_CFG_PIIX4_GENCFG_SERIRQ (1 << 16)
+#define PCI_CFG_PIIX4_IDETIM_PRI 0x40
+#define PCI_CFG_PIIX4_IDETIM_SEC 0x42
+
+#define PCI_CFG_PIIX4_IDETIM_IDE (1 << 15)
+
#endif /* _MIPS_ASM_MALTA_H */
diff --git a/arch/mips/lib/Makefile b/arch/mips/lib/Makefile
index 7f9b653..ac536da 100644
--- a/arch/mips/lib/Makefile
+++ b/arch/mips/lib/Makefile
@@ -5,6 +5,8 @@
# SPDX-License-Identifier: GPL-2.0+
#
+obj-y += cache.o
+obj-y += cache_init.o
obj-y += io.o
obj-$(CONFIG_CMD_BOOTM) += bootm.o
diff --git a/arch/mips/lib/cache.c b/arch/mips/lib/cache.c
new file mode 100644
index 0000000..e245614
--- /dev/null
+++ b/arch/mips/lib/cache.c
@@ -0,0 +1,118 @@
+/*
+ * (C) Copyright 2003
+ * Wolfgang Denk, DENX Software Engineering, <wd@denx.de>
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+#include <common.h>
+#include <asm/cacheops.h>
+#include <asm/mipsregs.h>
+
+#ifdef CONFIG_SYS_CACHELINE_SIZE
+
+static inline unsigned long icache_line_size(void)
+{
+ return CONFIG_SYS_CACHELINE_SIZE;
+}
+
+static inline unsigned long dcache_line_size(void)
+{
+ return CONFIG_SYS_CACHELINE_SIZE;
+}
+
+#else /* !CONFIG_SYS_CACHELINE_SIZE */
+
+static inline unsigned long icache_line_size(void)
+{
+ unsigned long conf1, il;
+ conf1 = read_c0_config1();
+ il = (conf1 & MIPS_CONF1_IL) >> MIPS_CONF1_IL_SHIFT;
+ if (!il)
+ return 0;
+ return 2 << il;
+}
+
+static inline unsigned long dcache_line_size(void)
+{
+ unsigned long conf1, dl;
+ conf1 = read_c0_config1();
+ dl = (conf1 & MIPS_CONF1_DL) >> MIPS_CONF1_DL_SHIFT;
+ if (!dl)
+ return 0;
+ return 2 << dl;
+}
+
+#endif /* !CONFIG_SYS_CACHELINE_SIZE */
+
+void flush_cache(ulong start_addr, ulong size)
+{
+ unsigned long ilsize = icache_line_size();
+ unsigned long dlsize = dcache_line_size();
+ const void *addr, *aend;
+
+ /* aend will be miscalculated when size is zero, so we return here */
+ if (size == 0)
+ return;
+
+ addr = (const void *)(start_addr & ~(dlsize - 1));
+ aend = (const void *)((start_addr + size - 1) & ~(dlsize - 1));
+
+ if (ilsize == dlsize) {
+ /* flush I-cache & D-cache simultaneously */
+ while (1) {
+ mips_cache(HIT_WRITEBACK_INV_D, addr);
+ mips_cache(HIT_INVALIDATE_I, addr);
+ if (addr == aend)
+ break;
+ addr += dlsize;
+ }
+ return;
+ }
+
+ /* flush D-cache */
+ while (1) {
+ mips_cache(HIT_WRITEBACK_INV_D, addr);
+ if (addr == aend)
+ break;
+ addr += dlsize;
+ }
+
+ /* flush I-cache */
+ addr = (const void *)(start_addr & ~(ilsize - 1));
+ aend = (const void *)((start_addr + size - 1) & ~(ilsize - 1));
+ while (1) {
+ mips_cache(HIT_INVALIDATE_I, addr);
+ if (addr == aend)
+ break;
+ addr += ilsize;
+ }
+}
+
+void flush_dcache_range(ulong start_addr, ulong stop)
+{
+ unsigned long lsize = dcache_line_size();
+ const void *addr = (const void *)(start_addr & ~(lsize - 1));
+ const void *aend = (const void *)((stop - 1) & ~(lsize - 1));
+
+ while (1) {
+ mips_cache(HIT_WRITEBACK_INV_D, addr);
+ if (addr == aend)
+ break;
+ addr += lsize;
+ }
+}
+
+void invalidate_dcache_range(ulong start_addr, ulong stop)
+{
+ unsigned long lsize = dcache_line_size();
+ const void *addr = (const void *)(start_addr & ~(lsize - 1));
+ const void *aend = (const void *)((stop - 1) & ~(lsize - 1));
+
+ while (1) {
+ mips_cache(HIT_INVALIDATE_D, addr);
+ if (addr == aend)
+ break;
+ addr += lsize;
+ }
+}
diff --git a/arch/mips/lib/cache_init.S b/arch/mips/lib/cache_init.S
new file mode 100644
index 0000000..137d728
--- /dev/null
+++ b/arch/mips/lib/cache_init.S
@@ -0,0 +1,241 @@
+/*
+ * Cache-handling routined for MIPS CPUs
+ *
+ * Copyright (c) 2003 Wolfgang Denk <wd@denx.de>
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+#include <asm-offsets.h>
+#include <config.h>
+#include <asm/asm.h>
+#include <asm/regdef.h>
+#include <asm/mipsregs.h>
+#include <asm/addrspace.h>
+#include <asm/cacheops.h>
+
+#ifndef CONFIG_SYS_MIPS_CACHE_MODE
+#define CONFIG_SYS_MIPS_CACHE_MODE CONF_CM_CACHABLE_NONCOHERENT
+#endif
+
+#define INDEX_BASE CKSEG0
+
+ .macro f_fill64 dst, offset, val
+ LONG_S \val, (\offset + 0 * LONGSIZE)(\dst)
+ LONG_S \val, (\offset + 1 * LONGSIZE)(\dst)
+ LONG_S \val, (\offset + 2 * LONGSIZE)(\dst)
+ LONG_S \val, (\offset + 3 * LONGSIZE)(\dst)
+ LONG_S \val, (\offset + 4 * LONGSIZE)(\dst)
+ LONG_S \val, (\offset + 5 * LONGSIZE)(\dst)
+ LONG_S \val, (\offset + 6 * LONGSIZE)(\dst)
+ LONG_S \val, (\offset + 7 * LONGSIZE)(\dst)
+#if LONGSIZE == 4
+ LONG_S \val, (\offset + 8 * LONGSIZE)(\dst)
+ LONG_S \val, (\offset + 9 * LONGSIZE)(\dst)
+ LONG_S \val, (\offset + 10 * LONGSIZE)(\dst)
+ LONG_S \val, (\offset + 11 * LONGSIZE)(\dst)
+ LONG_S \val, (\offset + 12 * LONGSIZE)(\dst)
+ LONG_S \val, (\offset + 13 * LONGSIZE)(\dst)
+ LONG_S \val, (\offset + 14 * LONGSIZE)(\dst)
+ LONG_S \val, (\offset + 15 * LONGSIZE)(\dst)
+#endif
+ .endm
+
+ .macro cache_loop curr, end, line_sz, op
+10: cache \op, 0(\curr)
+ PTR_ADDU \curr, \curr, \line_sz
+ bne \curr, \end, 10b
+ .endm
+
+ .macro l1_info sz, line_sz, off
+ .set push
+ .set noat
+
+ mfc0 $1, CP0_CONFIG, 1
+
+ /* detect line size */
+ srl \line_sz, $1, \off + MIPS_CONF1_DL_SHIFT - MIPS_CONF1_DA_SHIFT
+ andi \line_sz, \line_sz, (MIPS_CONF1_DL >> MIPS_CONF1_DL_SHIFT)
+ move \sz, zero
+ beqz \line_sz, 10f
+ li \sz, 2
+ sllv \line_sz, \sz, \line_sz
+
+ /* detect associativity */
+ srl \sz, $1, \off + MIPS_CONF1_DA_SHIFT - MIPS_CONF1_DA_SHIFT
+ andi \sz, \sz, (MIPS_CONF1_DA >> MIPS_CONF1_DA_SHIFT)
+ addi \sz, \sz, 1
+
+ /* sz *= line_sz */
+ mul \sz, \sz, \line_sz
+
+ /* detect log32(sets) */
+ srl $1, $1, \off + MIPS_CONF1_DS_SHIFT - MIPS_CONF1_DA_SHIFT
+ andi $1, $1, (MIPS_CONF1_DS >> MIPS_CONF1_DS_SHIFT)
+ addiu $1, $1, 1
+ andi $1, $1, 0x7
+
+ /* sz <<= log32(sets) */
+ sllv \sz, \sz, $1
+
+ /* sz *= 32 */
+ li $1, 32
+ mul \sz, \sz, $1
+10:
+ .set pop
+ .endm
+/*
+ * mips_cache_reset - low level initialisation of the primary caches
+ *
+ * This routine initialises the primary caches to ensure that they have good
+ * parity. It must be called by the ROM before any cached locations are used
+ * to prevent the possibility of data with bad parity being written to memory.
+ *
+ * To initialise the instruction cache it is essential that a source of data
+ * with good parity is available. This routine will initialise an area of
+ * memory starting at location zero to be used as a source of parity.
+ *
+ * RETURNS: N/A
+ *
+ */
+LEAF(mips_cache_reset)
+#ifdef CONFIG_SYS_ICACHE_SIZE
+ li t2, CONFIG_SYS_ICACHE_SIZE
+ li t8, CONFIG_SYS_CACHELINE_SIZE
+#else
+ l1_info t2, t8, MIPS_CONF1_IA_SHIFT
+#endif
+
+#ifdef CONFIG_SYS_DCACHE_SIZE
+ li t3, CONFIG_SYS_DCACHE_SIZE
+ li t9, CONFIG_SYS_CACHELINE_SIZE
+#else
+ l1_info t3, t9, MIPS_CONF1_DA_SHIFT
+#endif
+
+#ifdef CONFIG_SYS_MIPS_CACHE_INIT_RAM_LOAD
+
+ /* Determine the largest L1 cache size */
+#if defined(CONFIG_SYS_ICACHE_SIZE) && defined(CONFIG_SYS_DCACHE_SIZE)
+#if CONFIG_SYS_ICACHE_SIZE > CONFIG_SYS_DCACHE_SIZE
+ li v0, CONFIG_SYS_ICACHE_SIZE
+#else
+ li v0, CONFIG_SYS_DCACHE_SIZE
+#endif
+#else
+ move v0, t2
+ sltu t1, t2, t3
+ movn v0, t3, t1
+#endif
+ /*
+ * Now clear that much memory starting from zero.
+ */
+ PTR_LI a0, CKSEG1
+ PTR_ADDU a1, a0, v0
+2: PTR_ADDIU a0, 64
+ f_fill64 a0, -64, zero
+ bne a0, a1, 2b
+
+#endif /* CONFIG_SYS_MIPS_CACHE_INIT_RAM_LOAD */
+
+ /*
+ * The TagLo registers used depend upon the CPU implementation, but the
+ * architecture requires that it is safe for software to write to both
+ * TagLo selects 0 & 2 covering supported cases.
+ */
+ mtc0 zero, CP0_TAGLO
+ mtc0 zero, CP0_TAGLO, 2
+
+ /*
+ * The caches are probably in an indeterminate state, so we force good
+ * parity into them by doing an invalidate for each line. If
+ * CONFIG_SYS_MIPS_CACHE_INIT_RAM_LOAD is set then we'll proceed to
+ * perform a load/fill & a further invalidate for each line, assuming
+ * that the bottom of RAM (having just been cleared) will generate good
+ * parity for the cache.
+ */
+
+ /*
+ * Initialize the I-cache first,
+ */
+ blez t2, 1f
+ PTR_LI t0, INDEX_BASE
+ PTR_ADDU t1, t0, t2
+ /* clear tag to invalidate */
+ cache_loop t0, t1, t8, INDEX_STORE_TAG_I
+#ifdef CONFIG_SYS_MIPS_CACHE_INIT_RAM_LOAD
+ /* fill once, so data field parity is correct */
+ PTR_LI t0, INDEX_BASE
+ cache_loop t0, t1, t8, FILL
+ /* invalidate again - prudent but not strictly neccessary */
+ PTR_LI t0, INDEX_BASE
+ cache_loop t0, t1, t8, INDEX_STORE_TAG_I
+#endif
+
+ /*
+ * then initialize D-cache.
+ */
+1: blez t3, 3f
+ PTR_LI t0, INDEX_BASE
+ PTR_ADDU t1, t0, t3
+ /* clear all tags */
+ cache_loop t0, t1, t9, INDEX_STORE_TAG_D
+#ifdef CONFIG_SYS_MIPS_CACHE_INIT_RAM_LOAD
+ /* load from each line (in cached space) */
+ PTR_LI t0, INDEX_BASE
+2: LONG_L zero, 0(t0)
+ PTR_ADDU t0, t9
+ bne t0, t1, 2b
+ /* clear all tags */
+ PTR_LI t0, INDEX_BASE
+ cache_loop t0, t1, t9, INDEX_STORE_TAG_D
+#endif
+
+3: jr ra
+ END(mips_cache_reset)
+
+/*
+ * dcache_status - get cache status
+ *
+ * RETURNS: 0 - cache disabled; 1 - cache enabled
+ *
+ */
+LEAF(dcache_status)
+ mfc0 t0, CP0_CONFIG
+ li t1, CONF_CM_UNCACHED
+ andi t0, t0, CONF_CM_CMASK
+ move v0, zero
+ beq t0, t1, 2f
+ li v0, 1
+2: jr ra
+ END(dcache_status)
+
+/*
+ * dcache_disable - disable cache
+ *
+ * RETURNS: N/A
+ *
+ */
+LEAF(dcache_disable)
+ mfc0 t0, CP0_CONFIG
+ li t1, -8
+ and t0, t0, t1
+ ori t0, t0, CONF_CM_UNCACHED
+ mtc0 t0, CP0_CONFIG
+ jr ra
+ END(dcache_disable)
+
+/*
+ * dcache_enable - enable cache
+ *
+ * RETURNS: N/A
+ *
+ */
+LEAF(dcache_enable)
+ mfc0 t0, CP0_CONFIG
+ ori t0, CONF_CM_CMASK
+ xori t0, CONF_CM_CMASK
+ ori t0, CONFIG_SYS_MIPS_CACHE_MODE
+ mtc0 t0, CP0_CONFIG
+ jr ra
+ END(dcache_enable)
diff --git a/arch/mips/cpu/mips32/au1x00/Makefile b/arch/mips/mach-au1x00/Makefile
similarity index 100%
rename from arch/mips/cpu/mips32/au1x00/Makefile
rename to arch/mips/mach-au1x00/Makefile
diff --git a/arch/mips/cpu/mips32/au1x00/au1x00_eth.c b/arch/mips/mach-au1x00/au1x00_eth.c
similarity index 98%
rename from arch/mips/cpu/mips32/au1x00/au1x00_eth.c
rename to arch/mips/mach-au1x00/au1x00_eth.c
index 4770f56..39c5b6b 100644
--- a/arch/mips/cpu/mips32/au1x00/au1x00_eth.c
+++ b/arch/mips/mach-au1x00/au1x00_eth.c
@@ -294,3 +294,9 @@
return 1;
}
+
+int cpu_eth_init(bd_t *bis)
+{
+ au1x00_enet_initialize(bis);
+ return 0;
+}
diff --git a/arch/mips/cpu/mips32/au1x00/au1x00_ide.c b/arch/mips/mach-au1x00/au1x00_ide.c
similarity index 100%
rename from arch/mips/cpu/mips32/au1x00/au1x00_ide.c
rename to arch/mips/mach-au1x00/au1x00_ide.c
diff --git a/arch/mips/cpu/mips32/au1x00/au1x00_serial.c b/arch/mips/mach-au1x00/au1x00_serial.c
similarity index 100%
rename from arch/mips/cpu/mips32/au1x00/au1x00_serial.c
rename to arch/mips/mach-au1x00/au1x00_serial.c
diff --git a/arch/mips/cpu/mips32/au1x00/au1x00_usb_ohci.c b/arch/mips/mach-au1x00/au1x00_usb_ohci.c
similarity index 100%
rename from arch/mips/cpu/mips32/au1x00/au1x00_usb_ohci.c
rename to arch/mips/mach-au1x00/au1x00_usb_ohci.c
diff --git a/arch/mips/cpu/mips32/au1x00/au1x00_usb_ohci.h b/arch/mips/mach-au1x00/au1x00_usb_ohci.h
similarity index 100%
rename from arch/mips/cpu/mips32/au1x00/au1x00_usb_ohci.h
rename to arch/mips/mach-au1x00/au1x00_usb_ohci.h
diff --git a/arch/mips/cpu/mips32/au1x00/config.mk b/arch/mips/mach-au1x00/config.mk
similarity index 100%
rename from arch/mips/cpu/mips32/au1x00/config.mk
rename to arch/mips/mach-au1x00/config.mk
diff --git a/arch/sandbox/cpu/start.c b/arch/sandbox/cpu/start.c
index 42353d8..097f29a 100644
--- a/arch/sandbox/cpu/start.c
+++ b/arch/sandbox/cpu/start.c
@@ -6,6 +6,7 @@
#include <common.h>
#include <os.h>
#include <cli.h>
+#include <malloc.h>
#include <asm/getopt.h>
#include <asm/io.h>
#include <asm/sections.h>
@@ -102,6 +103,25 @@
}
SANDBOX_CMDLINE_OPT_SHORT(fdt, 'd', 1, "Specify U-Boot's control FDT");
+static int sandbox_cmdline_cb_default_fdt(struct sandbox_state *state,
+ const char *arg)
+{
+ const char *fmt = "%s.dtb";
+ char *fname;
+ int len;
+
+ len = strlen(state->argv[0]) + strlen(fmt) + 1;
+ fname = os_malloc(len);
+ if (!fname)
+ return -ENOMEM;
+ snprintf(fname, len, fmt, state->argv[0]);
+ state->fdt_fname = fname;
+
+ return 0;
+}
+SANDBOX_CMDLINE_OPT_SHORT(default_fdt, 'D', 0,
+ "Use the default u-boot.dtb control FDT in U-Boot directory");
+
static int sandbox_cmdline_cb_interactive(struct sandbox_state *state,
const char *arg)
{
diff --git a/arch/sandbox/dts/sandbox.dts b/arch/sandbox/dts/sandbox.dts
index 11748ae..9ce31bf 100644
--- a/arch/sandbox/dts/sandbox.dts
+++ b/arch/sandbox/dts/sandbox.dts
@@ -19,6 +19,7 @@
colour = "cyan";
sides = <3>;
character = <83>;
+ light-gpios = <&gpio_a 2>, <&gpio_b 6 0>;
};
square {
compatible = "demo-shape";
@@ -73,10 +74,8 @@
cros-ec-keyb {
compatible = "google,cros-ec-keyb";
- google,key-rows = <8>;
- google,key-columns = <13>;
- google,repeat-delay-ms = <240>;
- google,repeat-rate-ms = <30>;
+ keypad,num-rows = <8>;
+ keypad,num-columns = <13>;
google,ghost-filter;
/*
* Keymap entries take the form of 0xRRCCKKKK where
@@ -126,7 +125,7 @@
0x070b0067 0x070c0069>;
};
- gpio_a: gpios {
+ gpio_a: gpios@0 {
gpio-controller;
compatible = "sandbox,gpio";
#gpio-cells = <1>;
@@ -134,6 +133,14 @@
num-gpios = <20>;
};
+ gpio_b: gpios@1 {
+ gpio-controller;
+ compatible = "sandbox,gpio";
+ #gpio-cells = <2>;
+ gpio-bank-name = "b";
+ num-gpios = <10>;
+ };
+
i2c@0 {
#address-cells = <1>;
#size-cells = <0>;
diff --git a/board/BuS/eb_cpux9k2/cpux9k2.c b/board/BuS/eb_cpux9k2/cpux9k2.c
index 5e4778e..76ad7c4 100644
--- a/board/BuS/eb_cpux9k2/cpux9k2.c
+++ b/board/BuS/eb_cpux9k2/cpux9k2.c
@@ -98,7 +98,7 @@
puts("Error: invalid MAC at EEPROM\n");
}
}
- gd->jt[XF_do_reset] = (void *) do_reset;
+ gd->jt->do_reset = do_reset;
#ifdef CONFIG_STATUS_LED
status_led_set(STATUS_LED_BOOT, STATUS_LED_BLINKING);
diff --git a/board/armltd/vexpress64/Kconfig b/board/armltd/vexpress64/Kconfig
index 7ebea63..7d5e7be 100644
--- a/board/armltd/vexpress64/Kconfig
+++ b/board/armltd/vexpress64/Kconfig
@@ -1,4 +1,30 @@
-if TARGET_VEXPRESS_AEMV8A
+if TARGET_VEXPRESS64_AEMV8A
+
+config SYS_BOARD
+ default "vexpress64"
+
+config SYS_VENDOR
+ default "armltd"
+
+config SYS_CONFIG_NAME
+ default "vexpress_aemv8a"
+
+endif
+
+if TARGET_VEXPRESS64_BASE_FVP
+
+config SYS_BOARD
+ default "vexpress64"
+
+config SYS_VENDOR
+ default "armltd"
+
+config SYS_CONFIG_NAME
+ default "vexpress_aemv8a"
+
+endif
+
+if TARGET_VEXPRESS64_JUNO
config SYS_BOARD
default "vexpress64"
diff --git a/board/armltd/vexpress64/MAINTAINERS b/board/armltd/vexpress64/MAINTAINERS
index 66c8dff..0ba044d 100644
--- a/board/armltd/vexpress64/MAINTAINERS
+++ b/board/armltd/vexpress64/MAINTAINERS
@@ -9,3 +9,8 @@
M: Linus Walleij <linus.walleij@linaro.org>
S: Maintained
F: configs/vexpress_aemv8a_semi_defconfig
+
+JUNO DEVELOPMENT PLATFORM BOARD
+M: Linus Walleij <linus.walleij@linaro.org>
+S: Maintained
+F: configs/vexpress_aemv8a_juno_defconfig
diff --git a/board/avionic-design/common/tamonten-ng.c b/board/avionic-design/common/tamonten-ng.c
index 86a0844..1704627 100644
--- a/board/avionic-design/common/tamonten-ng.c
+++ b/board/avionic-design/common/tamonten-ng.c
@@ -55,12 +55,12 @@
struct udevice *dev;
int ret;
- ret = i2c_get_chip_for_busnum(4, PMU_I2C_ADDRESS, &dev);
+ ret = i2c_get_chip_for_busnum(4, PMU_I2C_ADDRESS, 1, &dev);
if (ret) {
debug("%s: Cannot find PMIC I2C chip\n", __func__);
return;
}
- i2c_write(dev, reg, &data, 1);
+ dm_i2c_write(dev, reg, &data, 1);
}
/*
diff --git a/board/imgtec/malta/malta.c b/board/imgtec/malta/malta.c
index 78c4bd4..79562f7 100644
--- a/board/imgtec/malta/malta.c
+++ b/board/imgtec/malta/malta.c
@@ -6,6 +6,7 @@
*/
#include <common.h>
+#include <ide.h>
#include <netdev.h>
#include <pci.h>
#include <pci_gt64120.h>
@@ -123,6 +124,7 @@
reset_base = (void __iomem *)CKSEG1ADDR(MALTA_RESET_BASE);
__raw_writel(GORESET, reset_base);
+ mdelay(1000);
}
int board_early_init_f(void)
@@ -217,4 +219,22 @@
pci_read_config_byte(bdf, PCI_CFG_PIIX4_SERIRQC, &val8);
val8 |= PCI_CFG_PIIX4_SERIRQC_EN | PCI_CFG_PIIX4_SERIRQC_CONT;
pci_write_config_byte(bdf, PCI_CFG_PIIX4_SERIRQC, val8);
+
+ bdf = pci_find_device(PCI_VENDOR_ID_INTEL,
+ PCI_DEVICE_ID_INTEL_82371AB, 0);
+ if (bdf == -1)
+ panic("Failed to find PIIX4 IDE controller\n");
+
+ /* enable bus master & IO access */
+ val32 |= PCI_COMMAND_MASTER | PCI_COMMAND_IO;
+ pci_write_config_dword(bdf, PCI_COMMAND, val32);
+
+ /* set latency */
+ pci_write_config_byte(bdf, PCI_LATENCY_TIMER, 0x40);
+
+ /* enable IDE/ATA */
+ pci_write_config_dword(bdf, PCI_CFG_PIIX4_IDETIM_PRI,
+ PCI_CFG_PIIX4_IDETIM_IDE);
+ pci_write_config_dword(bdf, PCI_CFG_PIIX4_IDETIM_SEC,
+ PCI_CFG_PIIX4_IDETIM_IDE);
}
diff --git a/board/nvidia/cardhu/cardhu.c b/board/nvidia/cardhu/cardhu.c
index 95c4ff2..1540526 100644
--- a/board/nvidia/cardhu/cardhu.c
+++ b/board/nvidia/cardhu/cardhu.c
@@ -46,7 +46,7 @@
int ret;
int i;
- ret = i2c_get_chip_for_busnum(0, PMU_I2C_ADDRESS, &dev);
+ ret = i2c_get_chip_for_busnum(0, PMU_I2C_ADDRESS, 1, &dev);
if (ret) {
debug("%s: Cannot find PMIC I2C chip\n", __func__);
return;
@@ -57,7 +57,7 @@
reg = 0x32;
for (i = 0; i < MAX_I2C_RETRY; ++i) {
- if (i2c_write(dev, reg, data_buffer, 1))
+ if (dm_i2c_write(dev, reg, data_buffer, 1))
udelay(100);
}
@@ -66,7 +66,7 @@
reg = 0x67;
for (i = 0; i < MAX_I2C_RETRY; ++i) {
- if (i2c_write(dev, reg, data_buffer, 1))
+ if (dm_i2c_write(dev, reg, data_buffer, 1))
udelay(100);
}
}
@@ -94,7 +94,7 @@
u8 addr, data[1];
int err;
- err = i2c_get_chip_for_busnum(0, PMU_I2C_ADDRESS, &dev);
+ err = i2c_get_chip_for_busnum(0, PMU_I2C_ADDRESS, 1, &dev);
if (err) {
debug("failed to find PMU bus\n");
return err;
@@ -104,7 +104,7 @@
data[0] = 0x15;
addr = 0x30;
- err = i2c_write(dev, addr, data, 1);
+ err = dm_i2c_write(dev, addr, data, 1);
if (err) {
debug("failed to set VDD supply\n");
return err;
@@ -121,7 +121,7 @@
data[0] = 0x15;
addr = 0x31;
- err = i2c_write(dev, addr, data, 1);
+ err = dm_i2c_write(dev, addr, data, 1);
if (err) {
debug("failed to set AVDD supply\n");
return err;
diff --git a/board/nvidia/dalmore/dalmore.c b/board/nvidia/dalmore/dalmore.c
index 2a73746..d7c1a69 100644
--- a/board/nvidia/dalmore/dalmore.c
+++ b/board/nvidia/dalmore/dalmore.c
@@ -55,7 +55,7 @@
uchar reg, data_buffer[1];
int ret;
- ret = i2c_get_chip_for_busnum(0, PMU_I2C_ADDRESS, &dev);
+ ret = i2c_get_chip_for_busnum(0, PMU_I2C_ADDRESS, 1, &dev);
if (ret) {
debug("%s: Cannot find PMIC I2C chip\n", __func__);
return;
@@ -65,7 +65,7 @@
data_buffer[0] = 0x31;
reg = 0x61;
- ret = i2c_write(dev, reg, data_buffer, 1);
+ ret = dm_i2c_write(dev, reg, data_buffer, 1);
if (ret)
printf("%s: PMU i2c_write %02X<-%02X returned %d\n",
__func__, reg, data_buffer[0], ret);
@@ -74,7 +74,7 @@
data_buffer[0] = 0x01;
reg = 0x60;
- ret = i2c_write(dev, reg, data_buffer, 1);
+ ret = dm_i2c_write(dev, reg, data_buffer, 1);
if (ret)
printf("%s: PMU i2c_write %02X<-%02X returned %d\n",
__func__, reg, data_buffer[0], ret);
@@ -83,12 +83,12 @@
data_buffer[0] = 0x03;
reg = 0x14;
- ret = i2c_get_chip_for_busnum(0, BAT_I2C_ADDRESS, &dev);
+ ret = i2c_get_chip_for_busnum(0, BAT_I2C_ADDRESS, 1, &dev);
if (ret) {
debug("%s: Cannot find charger I2C chip\n", __func__);
return;
}
- ret = i2c_write(dev, reg, data_buffer, 1);
+ ret = dm_i2c_write(dev, reg, data_buffer, 1);
if (ret)
printf("%s: BAT i2c_write %02X<-%02X returned %d\n",
__func__, reg, data_buffer[0], ret);
diff --git a/board/nvidia/whistler/whistler.c b/board/nvidia/whistler/whistler.c
index 3114b20..3476f11 100644
--- a/board/nvidia/whistler/whistler.c
+++ b/board/nvidia/whistler/whistler.c
@@ -27,21 +27,21 @@
int ret;
/* Turn on MAX8907B LDO12 to 2.8V for J40 power */
- ret = i2c_get_chip_for_busnum(0, 0x3c, &dev);
+ ret = i2c_get_chip_for_busnum(0, 0x3c, 1, &dev);
if (ret) {
printf("%s: Cannot find MAX8907B I2C chip\n", __func__);
return;
}
val = 0x29;
- ret = i2c_write(dev, 0x46, &val, 1);
+ ret = dm_i2c_write(dev, 0x46, &val, 1);
if (ret)
printf("i2c_write 0 0x3c 0x46 failed: %d\n", ret);
val = 0x00;
- ret = i2c_write(dev, 0x45, &val, 1);
+ ret = dm_i2c_write(dev, 0x45, &val, 1);
if (ret)
printf("i2c_write 0 0x3c 0x45 failed: %d\n", ret);
val = 0x1f;
- ret = i2c_write(dev, 0x44, &val, 1);
+ ret = dm_i2c_write(dev, 0x44, &val, 1);
if (ret)
printf("i2c_write 0 0x3c 0x44 failed: %d\n", ret);
@@ -64,17 +64,17 @@
*/
/* Turn on TAC6416's GPIO 0+1 for USB1/3's VBUS */
- ret = i2c_get_chip_for_busnum(0, 0x20, &dev);
+ ret = i2c_get_chip_for_busnum(0, 0x20, 1, &dev);
if (ret) {
printf("%s: Cannot find TAC6416 I2C chip\n", __func__);
return;
}
val = 0x03;
- ret = i2c_write(dev, 2, &val, 1);
+ ret = dm_i2c_write(dev, 2, &val, 1);
if (ret)
printf("i2c_write 0 0x20 2 failed: %d\n", ret);
val = 0xfc;
- ret = i2c_write(dev, 6, &val, 1);
+ ret = dm_i2c_write(dev, 6, &val, 1);
if (ret)
printf("i2c_write 0 0x20 6 failed: %d\n", ret);
}
diff --git a/board/samsung/odroid/odroid.c b/board/samsung/odroid/odroid.c
index b7d2381..e3517f2 100644
--- a/board/samsung/odroid/odroid.c
+++ b/board/samsung/odroid/odroid.c
@@ -415,15 +415,6 @@
return 0;
}
-#ifdef CONFIG_SYS_I2C_INIT_BOARD
-static void board_init_i2c(void)
-{
- /* I2C_0 */
- if (exynos_pinmux_config(PERIPH_ID_I2C0, PINMUX_FLAG_NONE))
- debug("I2C%d not configured\n", (I2C_0));
-}
-#endif
-
int exynos_early_init_f(void)
{
board_clock_init();
@@ -444,10 +435,7 @@
int exynos_power_init(void)
{
-#ifdef CONFIG_SYS_I2C_INIT_BOARD
- board_init_i2c();
-#endif
- pmic_init(I2C_0);
+ pmic_init(0);
pmic_init_max77686();
return 0;
diff --git a/board/sandbox/README.sandbox b/board/sandbox/README.sandbox
index 5f879f5..3c0df17 100644
--- a/board/sandbox/README.sandbox
+++ b/board/sandbox/README.sandbox
@@ -18,8 +18,8 @@
CONFIG_SANDBOX is defined when building a native board.
-The chosen vendor and board names are also 'sandbox', so there is a single
-board in board/sandbox.
+The board name is 'sandbox' but the vendor name is unset, so there is a
+single board in board/sandbox.
CONFIG_SANDBOX_BIG_ENDIAN should be defined when running on big-endian
machines.
diff --git a/board/sunxi/Kconfig b/board/sunxi/Kconfig
index 738b55e..4a21589 100644
--- a/board/sunxi/Kconfig
+++ b/board/sunxi/Kconfig
@@ -39,16 +39,23 @@
default 360 if MACH_SUN4I || MACH_SUN5I || MACH_SUN7I
---help---
Set the dram clock speed, valid range 240 - 480, must be a multiple
- of 24. Note on sun4i / sun5i / sun7i this is only used by boards
- which use dram autoconfig.
+ of 24.
+
+if MACH_SUN5I || MACH_SUN7I
+config DRAM_MBUS_CLK
+ int "sunxi mbus clock speed"
+ default 300
+ ---help---
+ Set the mbus clock speed. The maximum on sun5i hardware is 300MHz.
+
+endif
config DRAM_ZQ
int "sunxi dram zq value"
default 123 if MACH_SUN4I || MACH_SUN5I || MACH_SUN6I || MACH_SUN8I
default 127 if MACH_SUN7I
---help---
- Set the dram zq value. Note on sun4i / sun5i / sun7i this is only
- used by boards which use dram autoconfig.
+ Set the dram zq value.
if MACH_SUN4I || MACH_SUN5I || MACH_SUN7I
config DRAM_EMR1
@@ -56,98 +63,81 @@
default 0 if MACH_SUN4I
default 4 if MACH_SUN5I || MACH_SUN7I
---help---
- Set the dram controller emr1 value. Note this is only used by boards
- which use dram autoconfig.
-endif
-
-config SYS_CONFIG_NAME
- default "sun4i" if MACH_SUN4I
- default "sun5i" if MACH_SUN5I
- default "sun6i" if MACH_SUN6I
- default "sun7i" if MACH_SUN7I
- default "sun8i" if MACH_SUN8I
-
-choice
- prompt "Board"
-
-config TARGET_A10S_OLINUXINO_M
- bool "A10S_OLINUXINO_M"
- depends on MACH_SUN5I
-
-config TARGET_A13_OLINUXINOM
- bool "A13_OLINUXINOM"
- depends on MACH_SUN5I
-
-config TARGET_A13_OLINUXINO
- bool "A13_OLINUXINO"
- depends on MACH_SUN5I
-
-config TARGET_A20_OLINUXINO_L2
- bool "A20_OLINUXINO_L2"
- depends on MACH_SUN7I
-
-config TARGET_A20_OLINUXINO_L
- bool "A20_OLINUXINO_L"
- depends on MACH_SUN7I
-
-config TARGET_A20_OLINUXINO_M
- bool "A20_OLINUXINO_M"
- depends on MACH_SUN7I
-
-config TARGET_AUXTEK_T004
- bool "AUXTEK_T004"
- depends on MACH_SUN5I
-
-config TARGET_BANANAPI
- bool "BANANAPI"
- depends on MACH_SUN7I
+ Set the dram controller emr1 value.
-config TARGET_BANANAPRO
- bool "BANANAPRO"
- depends on MACH_SUN7I
+config DRAM_ODT_EN
+ int "sunxi dram odt_en value"
+ default 0
+ ---help---
+ Set the dram controller odt_en parameter. This can be used to
+ enable/disable the ODT feature.
-config TARGET_CUBIEBOARD2
- bool "CUBIEBOARD2"
- depends on MACH_SUN7I
+config DRAM_TPR3
+ hex "sunxi dram tpr3 value"
+ default 0
+ ---help---
+ Set the dram controller tpr3 parameter. This parameter configures
+ the delay on the command lane and also phase shifts, which are
+ applied for sampling incoming read data. The default value 0
+ means that no phase/delay adjustments are necessary. Properly
+ configuring this parameter increases reliability at high DRAM
+ clock speeds.
-config TARGET_CUBIETRUCK
- bool "CUBIETRUCK"
- depends on MACH_SUN7I
+config DRAM_DQS_GATING_DELAY
+ hex "sunxi dram dqs_gating_delay value"
+ default 0
+ ---help---
+ Set the dram controller dqs_gating_delay parmeter. Each byte
+ encodes the DQS gating delay for each byte lane. The delay
+ granularity is 1/4 cycle. For example, the value 0x05060606
+ means that the delay is 5 quarter-cycles for one lane (1.25
+ cycles) and 6 quarter-cycles (1.5 cycles) for 3 other lanes.
+ The default value 0 means autodetection. The results of hardware
+ autodetection are not very reliable and depend on the chip
+ temperature (sometimes producing different results on cold start
+ and warm reboot). But the accuracy of hardware autodetection
+ is usually good enough, unless running at really high DRAM
+ clocks speeds (up to 600MHz). If unsure, keep as 0.
-config TARGET_PCDUINO3
- bool "PCDUINO3"
- depends on MACH_SUN7I
+choice
+ prompt "sunxi dram timings"
+ default DRAM_TIMINGS_VENDOR_MAGIC
+ ---help---
+ Select the timings of the DDR3 chips.
-config TARGET_MELE_M3
- bool "MELE_M3"
- depends on MACH_SUN7I
+config DRAM_TIMINGS_VENDOR_MAGIC
+ bool "Magic vendor timings from Android"
+ ---help---
+ The same DRAM timings as in the Allwinner boot0 bootloader.
-config TARGET_MK802_A10S
- bool "MK802_A10S"
- depends on MACH_SUN5I
+config DRAM_TIMINGS_DDR3_1066F_1333H
+ bool "JEDEC DDR3-1333H with down binning to DDR3-1066F"
+ ---help---
+ Use the timings of the standard JEDEC DDR3-1066F speed bin for
+ DRAM_CLK <= 533MHz and the timings of the DDR3-1333H speed bin
+ for DRAM_CLK > 533MHz. This covers the majority of DDR3 chips
+ used in Allwinner A10/A13/A20 devices. In the case of DDR3-1333
+ or DDR3-1600 chips, be sure to check the DRAM datasheet to confirm
+ that down binning to DDR3-1066F is supported (because DDR3-1066F
+ uses a bit faster timings than DDR3-1333H).
-config TARGET_MSI_PRIMO73
- bool "MSI Primo73 (7\" tablet)"
- depends on MACH_SUN7I
+config DRAM_TIMINGS_DDR3_800E_1066G_1333J
+ bool "JEDEC DDR3-800E / DDR3-1066G / DDR3-1333J"
---help---
- The MSI Primo73 is an A20 based tablet, with 1G RAM, 16G NAND,
- 1024x600 TN LCD display, mono speaker, 0.3 MP front camera, 2.0 MP
- rear camera, 3000 mAh battery, gt911 touchscreen, mma8452 accelerometer
- and rtl8188etv usb wifi. Has "power", "volume+" and "volume-" buttons
- (both volume buttons are also connected to the UBOOT_SEL pin). The
- external connectors are represented by MicroSD slot, MiniHDMI, MicroUSB
- OTG and 3.5mm headphone jack. More details are available at
- http://linux-sunxi.org/MSI_Primo73
+ Use the timings of the slowest possible JEDEC speed bin for the
+ selected DRAM_CLK. Depending on the DRAM_CLK value, it may be
+ DDR3-800E, DDR3-1066G or DDR3-1333J.
-config TARGET_I12_TVBOX
- bool "I12_TVBOX"
- depends on MACH_SUN7I
+endchoice
-config TARGET_R7DONGLE
- bool "R7DONGLE"
- depends on MACH_SUN5I
+endif
-endchoice
+config SYS_CONFIG_NAME
+ default "sun4i" if MACH_SUN4I
+ default "sun5i" if MACH_SUN5I
+ default "sun6i" if MACH_SUN6I
+ default "sun7i" if MACH_SUN7I
+ default "sun8i" if MACH_SUN8I
config SYS_BOARD
default "sunxi"
@@ -270,6 +260,16 @@
LCD interface driving a VGA connector, such as found on the
Olimex A13 boards.
+config VIDEO_VGA_VIA_LCD_FORCE_SYNC_ACTIVE_HIGH
+ boolean "Force sync active high for VGA via LCD controller support"
+ depends on VIDEO_VGA_VIA_LCD
+ default n
+ ---help---
+ Say Y here if you've a board which uses opendrain drivers for the vga
+ hsync and vsync signals. Opendrain drivers cannot generate steep enough
+ positive edges for a stable video output, so on boards with opendrain
+ drivers the sync signals must always be active high.
+
config VIDEO_VGA_EXTERNAL_DAC_EN
string "LCD panel power enable pin"
depends on VIDEO_VGA_VIA_LCD
@@ -383,4 +383,10 @@
Say Y here to add support for using a USB keyboard (typically used
in combination with a graphical console).
+config GMAC_TX_DELAY
+ int "GMAC Transmit Clock Delay Chain"
+ default 0
+ ---help---
+ Set the GMAC Transmit Clock Delay Chain value.
+
endif
diff --git a/board/sunxi/MAINTAINERS b/board/sunxi/MAINTAINERS
index 743e7f5..faa413c 100644
--- a/board/sunxi/MAINTAINERS
+++ b/board/sunxi/MAINTAINERS
@@ -34,16 +34,6 @@
F: include/configs/sun8i.h
F: configs/Ippo_q8h_v1_2_defconfig
-CUBIEBOARD2 BOARD
-M: Ian Campbell <ijc@hellion.org.uk>
-M: Hans de Goede <hdegoede@redhat.com>
-S: Maintained
-F: include/configs/sun7i.h
-F: configs/Cubieboard2_defconfig
-F: configs/Cubieboard2_FEL_defconfig
-F: configs/Cubietruck_defconfig
-F: configs/Cubietruck_FEL_defconfig
-
A20-OLINUXINO-LIME BOARD
M: FUKAUMI Naoki <naobsd@gmail.com>
S: Maintained
@@ -61,36 +51,47 @@
S: Maintained
F: configs/Colombus_defconfig
+CUBIEBOARD2 BOARD
+M: Ian Campbell <ijc@hellion.org.uk>
+M: Hans de Goede <hdegoede@redhat.com>
+S: Maintained
+F: include/configs/sun7i.h
+F: configs/Cubieboard2_defconfig
+F: configs/Cubieboard2_FEL_defconfig
+F: configs/Cubietruck_defconfig
+F: configs/Cubietruck_FEL_defconfig
+
GEMEI-G9 TABLET
-M: Priit Laes <plaes@plaes.org>
-S: Maintained
-F: configs/sunxi_Gemei_G9_defconfig
+M: Priit Laes <plaes@plaes.org>
+S: Maintained
+F: configs/sunxi_Gemei_G9_defconfig
-HUMMINIGBIRD-A31 BOARD
+HUMMINGBIRD-A31 BOARD
M: Chen-Yu Tsai <wens@csie.org>
S: Maintained
F: configs/Hummingbird_A31_defconfig
+INET-86VS BOARD
+M: Michal Suchanek <hramrach@gmail.com>
+S: Maintained
+F: board/sunxi/dram_inet_86vs.c
+F: configs/Inet_86VS_defconfig
+
IPPO-Q8H-V5 BOARD
M: Chen-Yu Tsai <wens@csie.org>
S: Maintained
F: configs/Ippo_q8h_v5_defconfig
-MSI-PRIMO73 BOARD
-M: Siarhei Siamashka <siarhei.siamashka@gmail.com>
-S: Maintained
-F: configs/MSI_Primo73_defconfig
-
-MSI-PRIMO81 BOARD
-M: Siarhei Siamashka <siarhei.siamashka@gmail.com>
-S: Maintained
-F: configs/MSI_Primo81_defconfig
-
LINKSPRITE-PCDUINO BOARD
M: Zoltan Herpai <wigyori@uid0.hu>
S: Maintained
F: configs/Linksprite_pcDuino_defconfig
+LINKSPRITE-PCDUINO3-NANO BOARD
+M: Adam Sampson <ats@offog.org>
+S: Maintained
+F: configs/Linksprite_pcDuino3_Nano_defconfig
+
MARSBOARD-A10 BOARD
M: Aleksei Mamlin <mamlinav@gmail.com>
S: Maintained
@@ -100,3 +101,18 @@
M: Ian Campbell <ijc@hellion.org.uk>
S: Maintained
F: configs/Mele_M5_defconfig
+
+MSI-PRIMO73 BOARD
+M: Siarhei Siamashka <siarhei.siamashka@gmail.com>
+S: Maintained
+F: configs/MSI_Primo73_defconfig
+
+MSI-PRIMO81 BOARD
+M: Siarhei Siamashka <siarhei.siamashka@gmail.com>
+S: Maintained
+F: configs/MSI_Primo81_defconfig
+
+TZX-Q8-713B7 BOARD
+M: Paul Kocialkowski <contact@paulk.fr>
+S: Maintained
+F: configs/TZX-Q8-713B7_defconfig
diff --git a/board/sunxi/Makefile b/board/sunxi/Makefile
index 71edb83..43766e0 100644
--- a/board/sunxi/Makefile
+++ b/board/sunxi/Makefile
@@ -12,11 +12,5 @@
obj-$(CONFIG_SUNXI_GMAC) += gmac.o
obj-$(CONFIG_SUNXI_AHCI) += ahci.o
obj-$(CONFIG_MACH_SUN4I) += dram_sun4i_auto.o
+obj-$(CONFIG_MACH_SUN5I) += dram_sun5i_auto.o
obj-$(CONFIG_MACH_SUN7I) += dram_sun5i_auto.o
-obj-$(CONFIG_TARGET_A10S_OLINUXINO_M) += dram_a10s_olinuxino_m.o
-obj-$(CONFIG_TARGET_A13_OLINUXINO) += dram_a13_olinuxino.o
-obj-$(CONFIG_TARGET_A13_OLINUXINOM) += dram_a13_oli_micro.o
-# This is not a typo, uses the same mem settings as the a10s-olinuxino-m
-obj-$(CONFIG_TARGET_AUXTEK_T004) += dram_a10s_olinuxino_m.o
-obj-$(CONFIG_TARGET_MK802_A10S) += dram_sun5i_auto.o
-obj-$(CONFIG_TARGET_R7DONGLE) += dram_r7dongle.o
diff --git a/board/sunxi/dram_a10s_olinuxino_m.c b/board/sunxi/dram_a10s_olinuxino_m.c
deleted file mode 100644
index 8900539..0000000
--- a/board/sunxi/dram_a10s_olinuxino_m.c
+++ /dev/null
@@ -1,31 +0,0 @@
-/* this file is generated, don't edit it yourself */
-
-#include <common.h>
-#include <asm/arch/dram.h>
-
-static struct dram_para dram_para = {
- .clock = 432,
- .type = 3,
- .rank_num = 1,
- .density = 4096,
- .io_width = 16,
- .bus_width = 16,
- .cas = 9,
- .zq = 123,
- .odt_en = 0,
- .size = 512,
- .tpr0 = 0x42d899b7,
- .tpr1 = 0xa090,
- .tpr2 = 0x22a00,
- .tpr3 = 0,
- .tpr4 = 0,
- .tpr5 = 0,
- .emr1 = 0x4,
- .emr2 = 0x10,
- .emr3 = 0,
-};
-
-unsigned long sunxi_dram_init(void)
-{
- return dramc_init(&dram_para);
-}
diff --git a/board/sunxi/dram_a13_oli_micro.c b/board/sunxi/dram_a13_oli_micro.c
deleted file mode 100644
index 8154ea2..0000000
--- a/board/sunxi/dram_a13_oli_micro.c
+++ /dev/null
@@ -1,32 +0,0 @@
-/* this file is generated, don't edit it yourself */
-
-#include <common.h>
-#include <asm/arch/dram.h>
-
-static struct dram_para dram_para = {
- .clock = 408,
- .type = 3,
- .rank_num = 1,
- .density = 2048,
- .io_width = 16,
- .bus_width = 16,
- .cas = 9,
- .zq = 123,
- .odt_en = 0,
- .size = 256,
- .tpr0 = 0x42d899b7,
- .tpr1 = 0xa090,
- .tpr2 = 0x22a00,
- .tpr3 = 0,
- .tpr4 = 0,
- .tpr5 = 0,
- .emr1 = 0,
- .emr2 = 0x10,
- .emr3 = 0,
-
-};
-
-unsigned long sunxi_dram_init(void)
-{
- return dramc_init(&dram_para);
-}
diff --git a/board/sunxi/dram_a13_olinuxino.c b/board/sunxi/dram_a13_olinuxino.c
deleted file mode 100644
index ca96260..0000000
--- a/board/sunxi/dram_a13_olinuxino.c
+++ /dev/null
@@ -1,31 +0,0 @@
-/* this file is generated, don't edit it yourself */
-
-#include <common.h>
-#include <asm/arch/dram.h>
-
-static struct dram_para dram_para = {
- .clock = 408,
- .type = 3,
- .rank_num = 1,
- .density = 2048,
- .io_width = 8,
- .bus_width = 16,
- .cas = 9,
- .zq = 123,
- .odt_en = 0,
- .size = 512,
- .tpr0 = 0x42d899b7,
- .tpr1 = 0xa090,
- .tpr2 = 0x22a00,
- .tpr3 = 0,
- .tpr4 = 0,
- .tpr5 = 0,
- .emr1 = 0,
- .emr2 = 0x10,
- .emr3 = 0,
-};
-
-unsigned long sunxi_dram_init(void)
-{
- return dramc_init(&dram_para);
-}
diff --git a/board/sunxi/dram_bananapi.c b/board/sunxi/dram_bananapi.c
deleted file mode 100644
index 0ed7943..0000000
--- a/board/sunxi/dram_bananapi.c
+++ /dev/null
@@ -1,31 +0,0 @@
-/* this file is generated, don't edit it yourself */
-
-#include <common.h>
-#include <asm/arch/dram.h>
-
-static struct dram_para dram_para = {
- .clock = 432,
- .type = 3,
- .rank_num = 1,
- .density = 4096,
- .io_width = 16,
- .bus_width = 32,
- .cas = 9,
- .zq = 0x7f,
- .odt_en = 0,
- .size = 1024,
- .tpr0 = 0x42d899b7,
- .tpr1 = 0xa090,
- .tpr2 = 0x22a00,
- .tpr3 = 0x0,
- .tpr4 = 0x1,
- .tpr5 = 0x0,
- .emr1 = 0x4,
- .emr2 = 0x10,
- .emr3 = 0x0,
-};
-
-unsigned long sunxi_dram_init(void)
-{
- return dramc_init(&dram_para);
-}
diff --git a/board/sunxi/dram_r7dongle.c b/board/sunxi/dram_r7dongle.c
deleted file mode 100644
index 59343cb..0000000
--- a/board/sunxi/dram_r7dongle.c
+++ /dev/null
@@ -1,31 +0,0 @@
-/* this file is generated, don't edit it yourself */
-
-#include <common.h>
-#include <asm/arch/dram.h>
-
-static struct dram_para dram_para = {
- .clock = 384,
- .type = 3,
- .rank_num = 1,
- .density = 2048,
- .io_width = 8,
- .bus_width = 32,
- .cas = 9,
- .zq = 123,
- .odt_en = 0,
- .size = 1024,
- .tpr0 = 0x42d899b7,
- .tpr1 = 0xa090,
- .tpr2 = 0x22a00,
- .tpr3 = 0,
- .tpr4 = 0,
- .tpr5 = 0,
- .emr1 = 0x04,
- .emr2 = 0x10,
- .emr3 = 0,
-};
-
-unsigned long sunxi_dram_init(void)
-{
- return dramc_init(&dram_para);
-}
diff --git a/board/sunxi/dram_sun4i_auto.c b/board/sunxi/dram_sun4i_auto.c
index 826bacf..09e0c9a 100644
--- a/board/sunxi/dram_sun4i_auto.c
+++ b/board/sunxi/dram_sun4i_auto.c
@@ -8,19 +8,25 @@
.density = 0,
.io_width = 0,
.bus_width = 0,
- .cas = 6,
.zq = CONFIG_DRAM_ZQ,
- .odt_en = 0,
+ .odt_en = CONFIG_DRAM_ODT_EN,
.size = 0,
+#ifdef CONFIG_DRAM_TIMINGS_VENDOR_MAGIC
+ .cas = 6,
.tpr0 = 0x30926692,
.tpr1 = 0x1090,
.tpr2 = 0x1a0c8,
- .tpr3 = 0,
+ .emr2 = 0,
+#else
+# include "dram_timings_sun4i.h"
+ .active_windowing = 1,
+#endif
+ .tpr3 = CONFIG_DRAM_TPR3,
.tpr4 = 0,
.tpr5 = 0,
.emr1 = CONFIG_DRAM_EMR1,
- .emr2 = 0,
.emr3 = 0,
+ .dqs_gating_delay = CONFIG_DRAM_DQS_GATING_DELAY,
};
unsigned long sunxi_dram_init(void)
diff --git a/board/sunxi/dram_sun5i_auto.c b/board/sunxi/dram_sun5i_auto.c
index e86b08e..e52d54c 100644
--- a/board/sunxi/dram_sun5i_auto.c
+++ b/board/sunxi/dram_sun5i_auto.c
@@ -5,24 +5,31 @@
static struct dram_para dram_para = {
.clock = CONFIG_DRAM_CLK,
+ .mbus_clock = CONFIG_DRAM_MBUS_CLK,
.type = 3,
.rank_num = 1,
.density = 0,
.io_width = 0,
.bus_width = 0,
- .cas = 9,
.zq = CONFIG_DRAM_ZQ,
- .odt_en = 0,
+ .odt_en = CONFIG_DRAM_ODT_EN,
.size = 0,
+#ifdef CONFIG_DRAM_TIMINGS_VENDOR_MAGIC
+ .cas = 9,
.tpr0 = 0x42d899b7,
.tpr1 = 0xa090,
.tpr2 = 0x22a00,
+ .emr2 = 0x10,
+#else
+# include "dram_timings_sun4i.h"
+ .active_windowing = 1,
+#endif
.tpr3 = 0,
.tpr4 = 0,
.tpr5 = 0,
.emr1 = CONFIG_DRAM_EMR1,
- .emr2 = 0x10,
.emr3 = 0,
+ .dqs_gating_delay = CONFIG_DRAM_DQS_GATING_DELAY,
};
unsigned long sunxi_dram_init(void)
diff --git a/board/sunxi/dram_timings_sun4i.h b/board/sunxi/dram_timings_sun4i.h
new file mode 100644
index 0000000..29b934d
--- /dev/null
+++ b/board/sunxi/dram_timings_sun4i.h
@@ -0,0 +1,205 @@
+/* This file is automatically generated, do not edit */
+
+#if defined(CONFIG_DRAM_TIMINGS_DDR3_1066F_1333H)
+# if CONFIG_DRAM_CLK <= 360 /* DDR3-1066F @360MHz, timings: 6-5-5-14 */
+ .cas = 6,
+ .tpr0 = 0x268e5590,
+ .tpr1 = 0xa090,
+ .tpr2 = 0x22a00,
+ .emr2 = 0x0,
+# elif CONFIG_DRAM_CLK <= 384 /* DDR3-1066F @384MHz, timings: 6-6-6-15 */
+ .cas = 6,
+ .tpr0 = 0x288f6690,
+ .tpr1 = 0xa0a0,
+ .tpr2 = 0x22a00,
+ .emr2 = 0x0,
+# elif CONFIG_DRAM_CLK <= 396 /* DDR3-1066F @396MHz, timings: 6-6-6-15 */
+ .cas = 6,
+ .tpr0 = 0x2a8f6690,
+ .tpr1 = 0xa0a0,
+ .tpr2 = 0x22a00,
+ .emr2 = 0x0,
+# elif CONFIG_DRAM_CLK <= 408 /* DDR3-1066F @408MHz, timings: 7-6-6-16 */
+ .cas = 7,
+ .tpr0 = 0x2ab06690,
+ .tpr1 = 0xa0a8,
+ .tpr2 = 0x22a00,
+ .emr2 = 0x8,
+# elif CONFIG_DRAM_CLK <= 432 /* DDR3-1066F @432MHz, timings: 7-6-6-17 */
+ .cas = 7,
+ .tpr0 = 0x2cb16690,
+ .tpr1 = 0xa0b0,
+ .tpr2 = 0x22e00,
+ .emr2 = 0x8,
+# elif CONFIG_DRAM_CLK <= 456 /* DDR3-1066F @456MHz, timings: 7-6-6-18 */
+ .cas = 7,
+ .tpr0 = 0x30b26690,
+ .tpr1 = 0xa0b8,
+ .tpr2 = 0x22e00,
+ .emr2 = 0x8,
+# elif CONFIG_DRAM_CLK <= 468 /* DDR3-1066F @468MHz, timings: 7-7-7-18 */
+ .cas = 7,
+ .tpr0 = 0x30b27790,
+ .tpr1 = 0xa0c0,
+ .tpr2 = 0x23200,
+ .emr2 = 0x8,
+# elif CONFIG_DRAM_CLK <= 480 /* DDR3-1066F @480MHz, timings: 7-7-7-18 */
+ .cas = 7,
+ .tpr0 = 0x32b27790,
+ .tpr1 = 0xa0c0,
+ .tpr2 = 0x23200,
+ .emr2 = 0x8,
+# elif CONFIG_DRAM_CLK <= 504 /* DDR3-1066F @504MHz, timings: 7-7-7-19 */
+ .cas = 7,
+ .tpr0 = 0x34d37790,
+ .tpr1 = 0xa0d0,
+ .tpr2 = 0x23600,
+ .emr2 = 0x8,
+# elif CONFIG_DRAM_CLK <= 528 /* DDR3-1066F @528MHz, timings: 7-7-7-20 */
+ .cas = 7,
+ .tpr0 = 0x36d47790,
+ .tpr1 = 0xa0d8,
+ .tpr2 = 0x23600,
+ .emr2 = 0x8,
+# elif CONFIG_DRAM_CLK <= 540 /* DDR3-1333H @540MHz, timings: 9-8-8-20 */
+ .cas = 9,
+ .tpr0 = 0x36b488b4,
+ .tpr1 = 0xa0c8,
+ .tpr2 = 0x2b600,
+ .emr2 = 0x10,
+# elif CONFIG_DRAM_CLK <= 552 /* DDR3-1333H @552MHz, timings: 9-8-8-20 */
+ .cas = 9,
+ .tpr0 = 0x38b488b4,
+ .tpr1 = 0xa0c8,
+ .tpr2 = 0x2ba00,
+ .emr2 = 0x10,
+# elif CONFIG_DRAM_CLK <= 576 /* DDR3-1333H @576MHz, timings: 9-8-8-21 */
+ .cas = 9,
+ .tpr0 = 0x3ab588b4,
+ .tpr1 = 0xa0d0,
+ .tpr2 = 0x2ba00,
+ .emr2 = 0x10,
+# elif CONFIG_DRAM_CLK <= 600 /* DDR3-1333H @600MHz, timings: 9-9-9-22 */
+ .cas = 9,
+ .tpr0 = 0x3cb699b4,
+ .tpr1 = 0xa0d8,
+ .tpr2 = 0x2be00,
+ .emr2 = 0x10,
+# elif CONFIG_DRAM_CLK <= 624 /* DDR3-1333H @624MHz, timings: 9-9-9-23 */
+ .cas = 9,
+ .tpr0 = 0x3eb799b4,
+ .tpr1 = 0xa0e8,
+ .tpr2 = 0x2be00,
+ .emr2 = 0x10,
+# elif CONFIG_DRAM_CLK <= 648 /* DDR3-1333H @648MHz, timings: 9-9-9-24 */
+ .cas = 9,
+ .tpr0 = 0x42b899b4,
+ .tpr1 = 0xa0f0,
+ .tpr2 = 0x2c200,
+ .emr2 = 0x10,
+# else
+# error CONFIG_DRAM_CLK is set too high
+# endif
+#elif defined(CONFIG_DRAM_TIMINGS_DDR3_800E_1066G_1333J)
+# if CONFIG_DRAM_CLK <= 360 /* DDR3-800E @360MHz, timings: 6-6-6-14 */
+ .cas = 6,
+ .tpr0 = 0x268e6690,
+ .tpr1 = 0xa090,
+ .tpr2 = 0x22a00,
+ .emr2 = 0x0,
+# elif CONFIG_DRAM_CLK <= 384 /* DDR3-800E @384MHz, timings: 6-6-6-15 */
+ .cas = 6,
+ .tpr0 = 0x2a8f6690,
+ .tpr1 = 0xa0a0,
+ .tpr2 = 0x22a00,
+ .emr2 = 0x0,
+# elif CONFIG_DRAM_CLK <= 396 /* DDR3-800E @396MHz, timings: 6-6-6-15 */
+ .cas = 6,
+ .tpr0 = 0x2a8f6690,
+ .tpr1 = 0xa0a0,
+ .tpr2 = 0x22a00,
+ .emr2 = 0x0,
+# elif CONFIG_DRAM_CLK <= 408 /* DDR3-1066G @408MHz, timings: 8-7-7-16 */
+ .cas = 8,
+ .tpr0 = 0x2cb07790,
+ .tpr1 = 0xa0a8,
+ .tpr2 = 0x22a00,
+ .emr2 = 0x8,
+# elif CONFIG_DRAM_CLK <= 432 /* DDR3-1066G @432MHz, timings: 8-7-7-17 */
+ .cas = 8,
+ .tpr0 = 0x2eb17790,
+ .tpr1 = 0xa0b0,
+ .tpr2 = 0x22e00,
+ .emr2 = 0x8,
+# elif CONFIG_DRAM_CLK <= 456 /* DDR3-1066G @456MHz, timings: 8-7-7-18 */
+ .cas = 8,
+ .tpr0 = 0x30b27790,
+ .tpr1 = 0xa0b8,
+ .tpr2 = 0x22e00,
+ .emr2 = 0x8,
+# elif CONFIG_DRAM_CLK <= 468 /* DDR3-1066G @468MHz, timings: 8-8-8-18 */
+ .cas = 8,
+ .tpr0 = 0x32b28890,
+ .tpr1 = 0xa0c0,
+ .tpr2 = 0x23200,
+ .emr2 = 0x8,
+# elif CONFIG_DRAM_CLK <= 480 /* DDR3-1066G @480MHz, timings: 8-8-8-18 */
+ .cas = 8,
+ .tpr0 = 0x34b28890,
+ .tpr1 = 0xa0c0,
+ .tpr2 = 0x23200,
+ .emr2 = 0x8,
+# elif CONFIG_DRAM_CLK <= 504 /* DDR3-1066G @504MHz, timings: 8-8-8-19 */
+ .cas = 8,
+ .tpr0 = 0x36d38890,
+ .tpr1 = 0xa0d0,
+ .tpr2 = 0x23600,
+ .emr2 = 0x8,
+# elif CONFIG_DRAM_CLK <= 528 /* DDR3-1066G @528MHz, timings: 8-8-8-20 */
+ .cas = 8,
+ .tpr0 = 0x38d48890,
+ .tpr1 = 0xa0d8,
+ .tpr2 = 0x23600,
+ .emr2 = 0x8,
+# elif CONFIG_DRAM_CLK <= 540 /* DDR3-1333J @540MHz, timings: 10-9-9-20 */
+ .cas = 10,
+ .tpr0 = 0x38b499b4,
+ .tpr1 = 0xa0c8,
+ .tpr2 = 0x2b600,
+ .emr2 = 0x10,
+# elif CONFIG_DRAM_CLK <= 552 /* DDR3-1333J @552MHz, timings: 10-9-9-20 */
+ .cas = 10,
+ .tpr0 = 0x3ab499b4,
+ .tpr1 = 0xa0c8,
+ .tpr2 = 0x2ba00,
+ .emr2 = 0x10,
+# elif CONFIG_DRAM_CLK <= 576 /* DDR3-1333J @576MHz, timings: 10-9-9-21 */
+ .cas = 10,
+ .tpr0 = 0x3cb599b4,
+ .tpr1 = 0xa0d0,
+ .tpr2 = 0x2ba00,
+ .emr2 = 0x10,
+# elif CONFIG_DRAM_CLK <= 600 /* DDR3-1333J @600MHz, timings: 10-9-9-22 */
+ .cas = 10,
+ .tpr0 = 0x3eb699b4,
+ .tpr1 = 0xa0d8,
+ .tpr2 = 0x2be00,
+ .emr2 = 0x10,
+# elif CONFIG_DRAM_CLK <= 624 /* DDR3-1333J @624MHz, timings: 10-10-10-23 */
+ .cas = 10,
+ .tpr0 = 0x40b7aab4,
+ .tpr1 = 0xa0e8,
+ .tpr2 = 0x2be00,
+ .emr2 = 0x10,
+# elif CONFIG_DRAM_CLK <= 648 /* DDR3-1333J @648MHz, timings: 10-10-10-24 */
+ .cas = 10,
+ .tpr0 = 0x44b8aab4,
+ .tpr1 = 0xa0f0,
+ .tpr2 = 0x2c200,
+ .emr2 = 0x10,
+# else
+# error CONFIG_DRAM_CLK is set too high
+# endif
+#else
+# error CONFIG_DRAM_TIMINGS_* is not defined
+#endif
diff --git a/board/sunxi/gmac.c b/board/sunxi/gmac.c
index 4e4615e..8849132 100644
--- a/board/sunxi/gmac.c
+++ b/board/sunxi/gmac.c
@@ -24,20 +24,13 @@
#ifdef CONFIG_RGMII
setbits_le32(&ccm->gmac_clk_cfg, CCM_GMAC_CTRL_TX_CLK_SRC_INT_RGMII |
CCM_GMAC_CTRL_GPIT_RGMII);
+ setbits_le32(&ccm->gmac_clk_cfg,
+ CCM_GMAC_CTRL_TX_CLK_DELAY(CONFIG_GMAC_TX_DELAY));
#else
setbits_le32(&ccm->gmac_clk_cfg, CCM_GMAC_CTRL_TX_CLK_SRC_MII |
CCM_GMAC_CTRL_GPIT_MII);
#endif
- /*
- * In order for the gmac nic to work reliable on the Bananapi, we
- * need to set bits 10-12 GTXDC "GMAC Transmit Clock Delay Chain"
- * of the GMAC clk register to 3.
- */
-#if defined CONFIG_TARGET_BANANAPI || defined CONFIG_TARGET_BANANAPRO
- setbits_le32(&ccm->gmac_clk_cfg, 0x3 << 10);
-#endif
-
#ifndef CONFIG_MACH_SUN6I
/* Configure pin mux settings for GMAC */
for (pin = SUNXI_GPA(0); pin <= SUNXI_GPA(16); pin++) {
diff --git a/board/toradex/apalis_t30/apalis_t30.c b/board/toradex/apalis_t30/apalis_t30.c
index 5d2c024..6244214 100644
--- a/board/toradex/apalis_t30/apalis_t30.c
+++ b/board/toradex/apalis_t30/apalis_t30.c
@@ -42,7 +42,7 @@
u8 addr, data[1];
int err;
- err = i2c_get_chip_for_busnum(0, PMU_I2C_ADDRESS, &dev);
+ err = i2c_get_chip_for_busnum(0, PMU_I2C_ADDRESS, 1, &dev);
if (err) {
debug("%s: Cannot find PMIC I2C chip\n", __func__);
return err;
@@ -51,7 +51,7 @@
data[0] = 0x27;
addr = 0x25;
- err = i2c_write(dev, addr, data, 1);
+ err = dm_i2c_write(dev, addr, data, 1);
if (err) {
debug("failed to set VDD supply\n");
return err;
@@ -61,7 +61,7 @@
data[0] = 0x0D;
addr = 0x24;
- err = i2c_write(dev, addr, data, 1);
+ err = dm_i2c_write(dev, addr, data, 1);
if (err) {
debug("failed to enable VDD supply\n");
return err;
@@ -71,7 +71,7 @@
data[0] = 0x0D;
addr = 0x35;
- err = i2c_write(dev, addr, data, 1);
+ err = dm_i2c_write(dev, addr, data, 1);
if (err) {
debug("failed to set AVDD supply\n");
return err;
diff --git a/common/Makefile b/common/Makefile
index 94554f2..9579ab4 100644
--- a/common/Makefile
+++ b/common/Makefile
@@ -27,6 +27,8 @@
# boards
obj-$(CONFIG_SYS_GENERIC_BOARD) += board_f.o
obj-$(CONFIG_SYS_GENERIC_BOARD) += board_r.o
+obj-$(CONFIG_DISPLAY_BOARDINFO) += board_info.o
+obj-$(CONFIG_DISPLAY_BOARDINFO_LATE) += board_info.o
# core command
obj-y += cmd_boot.o
diff --git a/common/board_f.c b/common/board_f.c
index 215108b..7953137 100644
--- a/common/board_f.c
+++ b/common/board_f.c
@@ -894,7 +894,7 @@
prt_mpc5xxx_clks,
#endif /* CONFIG_MPC5xxx */
#if defined(CONFIG_DISPLAY_BOARDINFO)
- checkboard, /* display board info */
+ show_board_info,
#endif
INIT_FUNC_WATCHDOG_INIT
#if defined(CONFIG_MISC_INIT_F)
diff --git a/common/board_info.c b/common/board_info.c
new file mode 100644
index 0000000..42d0641
--- /dev/null
+++ b/common/board_info.c
@@ -0,0 +1,35 @@
+/*
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+#include <common.h>
+#include <libfdt.h>
+#include <linux/compiler.h>
+
+int __weak checkboard(void)
+{
+ printf("Board: Unknown\n");
+ return 0;
+}
+
+/*
+ * If the root node of the DTB has a "model" property, show it.
+ * If CONFIG_OF_CONTROL is disabled or the "model" property is missing,
+ * fall back to checkboard().
+ */
+int show_board_info(void)
+{
+#ifdef CONFIG_OF_CONTROL
+ DECLARE_GLOBAL_DATA_PTR;
+ const char *model;
+
+ model = fdt_getprop(gd->fdt_blob, 0, "model", NULL);
+
+ if (model) {
+ printf("Model: %s\n", model);
+ return 0;
+ }
+#endif
+
+ return checkboard();
+}
diff --git a/common/board_r.c b/common/board_r.c
index a301cc2..68a9448 100644
--- a/common/board_r.c
+++ b/common/board_r.c
@@ -476,22 +476,6 @@
}
#endif
-#ifdef CONFIG_DISPLAY_BOARDINFO_LATE
-static int show_model_r(void)
-{
- /* Put this here so it appears on the LCD, now it is ready */
-# ifdef CONFIG_OF_CONTROL
- const char *model;
-
- model = (char *)fdt_getprop(gd->fdt_blob, 0, "model", NULL);
- printf("Model: %s\n", model ? model : "<unknown>");
-# else
- checkboard();
-# endif
- return 0;
-}
-#endif
-
/* enable exceptions */
#ifdef CONFIG_ARM
static int initr_enable_interrupts(void)
@@ -801,7 +785,7 @@
#endif
console_init_r, /* fully init console as a device */
#ifdef CONFIG_DISPLAY_BOARDINFO_LATE
- show_model_r,
+ show_board_info,
#endif
#ifdef CONFIG_ARCH_MISC_INIT
arch_misc_init, /* miscellaneous arch-dependent init */
diff --git a/common/cmd_bootm.c b/common/cmd_bootm.c
index 6723360..48199bf 100644
--- a/common/cmd_bootm.c
+++ b/common/cmd_bootm.c
@@ -185,6 +185,9 @@
"\tcmdline - OS specific command line processing/setup\n"
"\tbdt - OS specific bd_t processing\n"
"\tprep - OS specific prep before relocation or go\n"
+#if defined(CONFIG_TRACE)
+ "\tfake - OS specific fake start without go\n"
+#endif
"\tgo - start OS";
#endif
diff --git a/common/cmd_demo.c b/common/cmd_demo.c
index 652c61c..bcb34d9 100644
--- a/common/cmd_demo.c
+++ b/common/cmd_demo.c
@@ -39,6 +39,26 @@
return 0;
}
+static int do_demo_light(cmd_tbl_t *cmdtp, int flag, int argc,
+ char * const argv[])
+{
+ int light;
+ int ret;
+
+ if (argc) {
+ light = simple_strtoul(argv[0], NULL, 16);
+ ret = demo_set_light(demo_dev, light);
+ } else {
+ ret = demo_get_light(demo_dev);
+ if (ret >= 0) {
+ printf("Light: %x\n", ret);
+ ret = 0;
+ }
+ }
+
+ return ret;
+}
+
int do_demo_list(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
{
struct udevice *dev;
@@ -61,6 +81,7 @@
static cmd_tbl_t demo_commands[] = {
U_BOOT_CMD_MKENT(list, 0, 1, do_demo_list, "", ""),
U_BOOT_CMD_MKENT(hello, 2, 1, do_demo_hello, "", ""),
+ U_BOOT_CMD_MKENT(light, 2, 1, do_demo_light, "", ""),
U_BOOT_CMD_MKENT(status, 1, 1, do_demo_status, "", ""),
};
@@ -86,6 +107,10 @@
return cmd_process_error(cmdtp, ret);
argc--;
argv++;
+ } else {
+ demo_dev = NULL;
+ if (demo_cmd->cmd != do_demo_list)
+ return CMD_RET_USAGE;
}
ret = demo_cmd->cmd(demo_cmd, flag, argc, argv);
@@ -98,5 +123,7 @@
"Driver model (dm) demo operations",
"list List available demo devices\n"
"demo hello <num> [<char>] Say hello\n"
- "demo status <num> Get demo device status"
+ "demo light [<num>] Set or get the lights\n"
+ "demo status <num> Get demo device status\n"
+ "demo list List available demo devices"
);
diff --git a/common/cmd_fpga.c b/common/cmd_fpga.c
index 484a6c6..7f99aab 100644
--- a/common/cmd_fpga.c
+++ b/common/cmd_fpga.c
@@ -346,7 +346,7 @@
"loadable FPGA image support",
"[operation type] [device number] [image address] [image size]\n"
"fpga operations:\n"
- " dump\t[dev]\t\t\tLoad device to memory buffer\n"
+ " dump\t[dev] [address] [size]\tLoad device to memory buffer\n"
" info\t[dev]\t\t\tlist known device information\n"
" load\t[dev] [address] [size]\tLoad device from memory buffer\n"
#if defined(CONFIG_CMD_FPGA_LOADP)
diff --git a/common/cmd_fs.c b/common/cmd_fs.c
index 0d9da11..e146254 100644
--- a/common/cmd_fs.c
+++ b/common/cmd_fs.c
@@ -81,3 +81,18 @@
" - List files in directory 'directory' of partition 'part' on\n"
" device type 'interface' instance 'dev'."
)
+
+static int do_fstype_wrapper(cmd_tbl_t *cmdtp, int flag, int argc,
+ char * const argv[])
+{
+ return do_fs_type(cmdtp, flag, argc, argv);
+}
+
+U_BOOT_CMD(
+ fstype, 4, 1, do_fstype_wrapper,
+ "Look up a filesystem type",
+ "<interface> <dev>:<part>\n"
+ "- print filesystem type\n"
+ "fstype <interface> <dev>:<part> <varname>\n"
+ "- set environment variable to filesystem type\n"
+);
diff --git a/common/cmd_gettime.c b/common/cmd_gettime.c
index 320ff70..c48baad 100644
--- a/common/cmd_gettime.c
+++ b/common/cmd_gettime.c
@@ -35,6 +35,6 @@
U_BOOT_CMD(
gettime, 1, 1, do_gettime,
- "get timer val elapsed,\n",
- "get time elapsed from uboot start\n"
+ "get timer val elapsed",
+ "get time elapsed from uboot start"
);
diff --git a/common/cmd_i2c.c b/common/cmd_i2c.c
index 22db1bb..7c3ad00 100644
--- a/common/cmd_i2c.c
+++ b/common/cmd_i2c.c
@@ -83,12 +83,12 @@
/* Display values from last command.
* Memory modify remembered values are different from display memory.
*/
-static uchar i2c_dp_last_chip;
+static uint i2c_dp_last_chip;
static uint i2c_dp_last_addr;
static uint i2c_dp_last_alen;
static uint i2c_dp_last_length = 0x10;
-static uchar i2c_mm_last_chip;
+static uint i2c_mm_last_chip;
static uint i2c_mm_last_addr;
static uint i2c_mm_last_alen;
@@ -133,7 +133,7 @@
#ifdef CONFIG_DM_I2C
static struct udevice *i2c_cur_bus;
-static int i2c_set_bus_num(unsigned int busnum)
+static int cmd_i2c_set_bus_num(unsigned int busnum)
{
struct udevice *bus;
int ret;
@@ -168,7 +168,7 @@
if (ret)
return ret;
- return i2c_get_chip(bus, chip_addr, devp);
+ return i2c_get_chip(bus, chip_addr, 1, devp);
}
#endif
@@ -282,7 +282,7 @@
*/
static int do_i2c_read ( cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
{
- u_char chip;
+ uint chip;
uint devaddr, length;
int alen;
u_char *memaddr;
@@ -323,7 +323,7 @@
if (!ret && alen != -1)
ret = i2c_set_chip_offset_len(dev, alen);
if (!ret)
- ret = i2c_read(dev, devaddr, memaddr, length);
+ ret = dm_i2c_read(dev, devaddr, memaddr, length);
#else
ret = i2c_read(chip, devaddr, alen, memaddr, length);
#endif
@@ -335,7 +335,7 @@
static int do_i2c_write(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
{
- u_char chip;
+ uint chip;
uint devaddr, length;
int alen;
u_char *memaddr;
@@ -381,7 +381,7 @@
while (length-- > 0) {
#ifdef CONFIG_DM_I2C
- ret = i2c_write(dev, devaddr++, memaddr++, 1);
+ ret = dm_i2c_write(dev, devaddr++, memaddr++, 1);
#else
ret = i2c_write(chip, devaddr++, alen, memaddr++, 1);
#endif
@@ -444,7 +444,7 @@
*/
static int do_i2c_md ( cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
{
- u_char chip;
+ uint chip;
uint addr, length;
int alen;
int j, nbytes, linebytes;
@@ -513,7 +513,7 @@
linebytes = (nbytes > DISP_LINE_LEN) ? DISP_LINE_LEN : nbytes;
#ifdef CONFIG_DM_I2C
- ret = i2c_read(dev, addr, linebuf, linebytes);
+ ret = dm_i2c_read(dev, addr, linebuf, linebytes);
#else
ret = i2c_read(chip, addr, alen, linebuf, linebytes);
#endif
@@ -563,7 +563,7 @@
*/
static int do_i2c_mw ( cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
{
- uchar chip;
+ uint chip;
ulong addr;
int alen;
uchar byte;
@@ -611,7 +611,7 @@
while (count-- > 0) {
#ifdef CONFIG_DM_I2C
- ret = i2c_write(dev, addr++, &byte, 1);
+ ret = dm_i2c_write(dev, addr++, &byte, 1);
#else
ret = i2c_write(chip, addr++, alen, &byte, 1);
#endif
@@ -649,7 +649,7 @@
*/
static int do_i2c_crc (cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
{
- uchar chip;
+ uint chip;
ulong addr;
int alen;
int count;
@@ -698,7 +698,7 @@
err = 0;
while (count-- > 0) {
#ifdef CONFIG_DM_I2C
- ret = i2c_read(dev, addr, &byte, 1);
+ ret = dm_i2c_read(dev, addr, &byte, 1);
#else
ret = i2c_read(chip, addr, alen, &byte, 1);
#endif
@@ -734,7 +734,7 @@
static int
mod_i2c_mem(cmd_tbl_t *cmdtp, int incrflag, int flag, int argc, char * const argv[])
{
- uchar chip;
+ uint chip;
ulong addr;
int alen;
ulong data;
@@ -793,7 +793,7 @@
do {
printf("%08lx:", addr);
#ifdef CONFIG_DM_I2C
- ret = i2c_read(dev, addr, (uchar *)&data, size);
+ ret = dm_i2c_read(dev, addr, (uchar *)&data, size);
#else
ret = i2c_read(chip, addr, alen, (uchar *)&data, size);
#endif
@@ -841,8 +841,8 @@
*/
bootretry_reset_cmd_timeout();
#ifdef CONFIG_DM_I2C
- ret = i2c_write(dev, addr, (uchar *)&data,
- size);
+ ret = dm_i2c_write(dev, addr, (uchar *)&data,
+ size);
#else
ret = i2c_write(chip, addr, alen,
(uchar *)&data, size);
@@ -917,7 +917,7 @@
continue;
#endif
#ifdef CONFIG_DM_I2C
- ret = i2c_probe(bus, j, 0, &dev);
+ ret = dm_i2c_probe(bus, j, 0, &dev);
#else
ret = i2c_probe(j);
#endif
@@ -957,7 +957,7 @@
*/
static int do_i2c_loop(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
{
- u_char chip;
+ uint chip;
int alen;
uint addr;
uint length;
@@ -1010,7 +1010,7 @@
*/
while (1) {
#ifdef CONFIG_DM_I2C
- ret = i2c_read(dev, addr, bytes, length);
+ ret = dm_i2c_read(dev, addr, bytes, length);
#else
ret = i2c_read(chip, addr, alen, bytes, length);
#endif
@@ -1085,7 +1085,7 @@
{
enum { unknown, EDO, SDRAM, DDR2 } type;
- u_char chip;
+ uint chip;
u_char data[128];
u_char cksum;
int j;
@@ -1563,7 +1563,7 @@
#if defined(CONFIG_I2C_EDID)
int do_edid(cmd_tbl_t *cmdtp, int flag, int argc, char *const argv[])
{
- u_char chip;
+ uint chip;
struct edid1_info edid;
int ret;
#ifdef CONFIG_DM_I2C
@@ -1579,7 +1579,7 @@
#ifdef CONFIG_DM_I2C
ret = i2c_get_cur_bus_chip(chip, &dev);
if (!ret)
- ret = i2c_read(dev, 0, (uchar *)&edid, sizeof(edid));
+ ret = dm_i2c_read(dev, 0, (uchar *)&edid, sizeof(edid));
#else
ret = i2c_read(chip, 0, 1, (uchar *)&edid, sizeof(edid));
#endif
@@ -1696,7 +1696,11 @@
}
#endif
printf("Setting bus to %d\n", bus_no);
+#ifdef CONFIG_DM_I2C
+ ret = cmd_i2c_set_bus_num(bus_no);
+#else
ret = i2c_set_bus_num(bus_no);
+#endif
if (ret)
printf("Failure changing bus number (%d)\n", ret);
}
diff --git a/common/cmd_load.c b/common/cmd_load.c
index f6e522c..d043e6d 100644
--- a/common/cmd_load.c
+++ b/common/cmd_load.c
@@ -222,7 +222,7 @@
}
/* Check for the console hangup (if any different from serial) */
- if (gd->jt[XF_getc] != getc) {
+ if (gd->jt->getc != getc) {
if (ctrlc()) {
return (-1);
}
diff --git a/common/cmd_part.c b/common/cmd_part.c
index 39e8666..c99f527 100644
--- a/common/cmd_part.c
+++ b/common/cmd_part.c
@@ -54,13 +54,31 @@
int ret;
block_dev_desc_t *desc;
- if (argc != 2)
+ if (argc < 2 || argc > 3)
return CMD_RET_USAGE;
ret = get_device(argv[0], argv[1], &desc);
if (ret < 0)
return 1;
+ if (argc == 3) {
+ int p;
+ char str[512] = { 0, };
+ disk_partition_t info;
+
+ for (p = 1; p < 128; p++) {
+ int r = get_partition_info(desc, p, &info);
+
+ if (r == 0) {
+ char t[5];
+ sprintf(t, "%s%d", str[0] ? " " : "", p);
+ strcat(str, t);
+ }
+ }
+ setenv(argv[2], str);
+ return 0;
+ }
+
print_part(desc);
return 0;
@@ -87,5 +105,7 @@
"part uuid <interface> <dev>:<part> <varname>\n"
" - set environment variable to partition UUID\n"
"part list <interface> <dev>\n"
- " - print a device's partition table"
+ " - print a device's partition table\n"
+ "part list <interface> <dev> <varname>\n"
+ " - set environment variable to the list of partitions"
);
diff --git a/common/cmd_ximg.c b/common/cmd_ximg.c
index ae2714d..64b9186 100644
--- a/common/cmd_ximg.c
+++ b/common/cmd_ximg.c
@@ -247,6 +247,8 @@
puts("OK\n");
}
+ flush_cache(dest, len);
+
setenv_hex("fileaddr", data);
setenv_hex("filesize", len);
diff --git a/common/console.c b/common/console.c
index fc1963b..3f25e76 100644
--- a/common/console.c
+++ b/common/console.c
@@ -125,13 +125,13 @@
*/
switch (file) {
case stdin:
- gd->jt[XF_getc] = getc;
- gd->jt[XF_tstc] = tstc;
+ gd->jt->getc = getc;
+ gd->jt->tstc = tstc;
break;
case stdout:
- gd->jt[XF_putc] = putc;
- gd->jt[XF_puts] = puts;
- gd->jt[XF_printf] = printf;
+ gd->jt->putc = putc;
+ gd->jt->puts = puts;
+ gd->jt->printf = printf;
break;
}
break;
@@ -758,11 +758,11 @@
#endif
/* set default handlers at first */
- gd->jt[XF_getc] = serial_getc;
- gd->jt[XF_tstc] = serial_tstc;
- gd->jt[XF_putc] = serial_putc;
- gd->jt[XF_puts] = serial_puts;
- gd->jt[XF_printf] = serial_printf;
+ gd->jt->getc = serial_getc;
+ gd->jt->tstc = serial_tstc;
+ gd->jt->putc = serial_putc;
+ gd->jt->puts = serial_puts;
+ gd->jt->printf = serial_printf;
/* stdin stdout and stderr are in environment */
/* scan for it */
diff --git a/common/exports.c b/common/exports.c
index 88fcfc8..333107c 100644
--- a/common/exports.c
+++ b/common/exports.c
@@ -1,6 +1,7 @@
#include <common.h>
#include <exports.h>
#include <spi.h>
+#include <i2c.h>
DECLARE_GLOBAL_DATA_PTR;
@@ -13,33 +14,10 @@
return XF_VERSION;
}
-/* Reuse _exports.h with a little trickery to avoid bitrot */
-#define EXPORT_FUNC(sym) gd->jt[XF_##sym] = (void *)sym;
-
-#if !defined(CONFIG_X86) && !defined(CONFIG_PPC)
-# define install_hdlr dummy
-# define free_hdlr dummy
-#else /* kludge for non-standard function naming */
-# define install_hdlr irq_install_handler
-# define free_hdlr irq_free_handler
-#endif
-#ifndef CONFIG_CMD_I2C
-# define i2c_write dummy
-# define i2c_read dummy
-#endif
-#if !defined(CONFIG_CMD_SPI) || defined(CONFIG_DM_SPI)
-# define spi_init dummy
-# define spi_setup_slave dummy
-# define spi_free_slave dummy
-#endif
-#ifndef CONFIG_CMD_SPI
-# define spi_claim_bus dummy
-# define spi_release_bus dummy
-# define spi_xfer dummy
-#endif
+#define EXPORT_FUNC(f, a, x, ...) gd->jt->x = f;
void jumptable_init(void)
{
- gd->jt = malloc(XF_MAX * sizeof(void *));
+ gd->jt = malloc(sizeof(struct jt_funcs));
#include <_exports.h>
}
diff --git a/common/hash.c b/common/hash.c
index aceabc5..d154d02 100644
--- a/common/hash.c
+++ b/common/hash.c
@@ -10,17 +10,26 @@
* SPDX-License-Identifier: GPL-2.0+
*/
+#ifndef USE_HOSTCC
#include <common.h>
#include <command.h>
#include <malloc.h>
#include <hw_sha.h>
+#include <asm/io.h>
+#include <asm/errno.h>
+#else
+#include "mkimage.h"
+#include <time.h>
+#include <image.h>
+#endif /* !USE_HOSTCC*/
+
#include <hash.h>
+#include <u-boot/crc.h>
#include <u-boot/sha1.h>
#include <u-boot/sha256.h>
-#include <asm/io.h>
-#include <asm/errno.h>
+#include <u-boot/md5.h>
-#ifdef CONFIG_CMD_SHA1SUM
+#ifdef CONFIG_SHA1
static int hash_init_sha1(struct hash_algo *algo, void **ctxp)
{
sha1_context *ctx = malloc(sizeof(sha1_context));
@@ -125,12 +134,7 @@
CHUNKSZ_SHA256,
},
#endif
- /*
- * This is CONFIG_CMD_SHA1SUM instead of CONFIG_SHA1 since otherwise
- * it bloats the code for boards which use SHA1 but not the 'hash'
- * or 'sha1sum' commands.
- */
-#ifdef CONFIG_CMD_SHA1SUM
+#ifdef CONFIG_SHA1
{
"sha1",
SHA1_SUM_LEN,
@@ -140,7 +144,6 @@
hash_update_sha1,
hash_finish_sha1,
},
-#define MULTI_HASH
#endif
#ifdef CONFIG_SHA256
{
@@ -152,7 +155,6 @@
hash_update_sha256,
hash_finish_sha256,
},
-#define MULTI_HASH
#endif
{
"crc32",
@@ -165,6 +167,10 @@
},
};
+#if defined(CONFIG_SHA256) || defined(CONFIG_CMD_SHA1SUM)
+#define MULTI_HASH
+#endif
+
#if defined(CONFIG_HASH_VERIFY) || defined(CONFIG_CMD_HASH)
#define MULTI_HASH
#endif
@@ -176,6 +182,40 @@
#define multi_hash() 0
#endif
+int hash_lookup_algo(const char *algo_name, struct hash_algo **algop)
+{
+ int i;
+
+ for (i = 0; i < ARRAY_SIZE(hash_algo); i++) {
+ if (!strcmp(algo_name, hash_algo[i].name)) {
+ *algop = &hash_algo[i];
+ return 0;
+ }
+ }
+
+ debug("Unknown hash algorithm '%s'\n", algo_name);
+ return -EPROTONOSUPPORT;
+}
+
+int hash_progressive_lookup_algo(const char *algo_name,
+ struct hash_algo **algop)
+{
+ int i;
+
+ for (i = 0; i < ARRAY_SIZE(hash_algo); i++) {
+ if (!strcmp(algo_name, hash_algo[i].name)) {
+ if (hash_algo[i].hash_init) {
+ *algop = &hash_algo[i];
+ return 0;
+ }
+ }
+ }
+
+ debug("Unknown hash algorithm '%s'\n", algo_name);
+ return -EPROTONOSUPPORT;
+}
+
+#ifndef USE_HOSTCC
/**
* store_result: Store the resulting sum to an address or variable
*
@@ -296,21 +336,6 @@
return 0;
}
-int hash_lookup_algo(const char *algo_name, struct hash_algo **algop)
-{
- int i;
-
- for (i = 0; i < ARRAY_SIZE(hash_algo); i++) {
- if (!strcmp(algo_name, hash_algo[i].name)) {
- *algop = &hash_algo[i];
- return 0;
- }
- }
-
- debug("Unknown hash algorithm '%s'\n", algo_name);
- return -EPROTONOSUPPORT;
-}
-
void hash_show(struct hash_algo *algo, ulong addr, ulong len, uint8_t *output)
{
int i;
@@ -424,3 +449,4 @@
return 0;
}
+#endif
diff --git a/common/image-fit.c b/common/image-fit.c
index 1589ee3..b47d110 100644
--- a/common/image-fit.c
+++ b/common/image-fit.c
@@ -112,6 +112,33 @@
fdt_strerror(err));
}
+/**
+ * fit_get_subimage_count - get component (sub-image) count
+ * @fit: pointer to the FIT format image header
+ * @images_noffset: offset of images node
+ *
+ * returns:
+ * number of image components
+ */
+int fit_get_subimage_count(const void *fit, int images_noffset)
+{
+ int noffset;
+ int ndepth;
+ int count = 0;
+
+ /* Process its subnodes, print out component images details */
+ for (ndepth = 0, count = 0,
+ noffset = fdt_next_node(fit, images_noffset, &ndepth);
+ (noffset >= 0) && (ndepth > 0);
+ noffset = fdt_next_node(fit, noffset, &ndepth)) {
+ if (ndepth == 1) {
+ count++;
+ }
+ }
+
+ return count;
+}
+
#if !defined(CONFIG_SPL_BUILD) || defined(CONFIG_FIT_SPL_PRINT)
/**
* fit_print_contents - prints out the contents of the FIT format image
@@ -423,7 +450,8 @@
}
}
}
-#endif
+
+#endif /* !defined(CONFIG_SPL_BUILD) || defined(CONFIG_FIT_SPL_PRINT) */
/**
* fit_get_desc - get node description property
diff --git a/common/image-sig.c b/common/image-sig.c
index 8601eda..2c9f0cd 100644
--- a/common/image-sig.c
+++ b/common/image-sig.c
@@ -38,7 +38,7 @@
#if IMAGE_ENABLE_SIGN
EVP_sha1,
#endif
- sha1_calculate,
+ hash_calculate,
padding_sha1_rsa2048,
},
{
@@ -48,7 +48,7 @@
#if IMAGE_ENABLE_SIGN
EVP_sha256,
#endif
- sha256_calculate,
+ hash_calculate,
padding_sha256_rsa2048,
},
{
@@ -58,7 +58,7 @@
#if IMAGE_ENABLE_SIGN
EVP_sha256,
#endif
- sha256_calculate,
+ hash_calculate,
padding_sha256_rsa4096,
}
diff --git a/common/image.c b/common/image.c
index ad7a46d..a911aa9 100644
--- a/common/image.c
+++ b/common/image.c
@@ -756,7 +756,7 @@
* genimg_get_image - get image from special storage (if necessary)
* @img_addr: image start address
*
- * genimg_get_image() checks if provided image start adddress is located
+ * genimg_get_image() checks if provided image start address is located
* in a dataflash storage. If so, image is moved to a system RAM memory.
*
* returns:
diff --git a/configs/A10s-OLinuXino-M_defconfig b/configs/A10s-OLinuXino-M_defconfig
index 94fafa6..b5f0a0f 100644
--- a/configs/A10s-OLinuXino-M_defconfig
+++ b/configs/A10s-OLinuXino-M_defconfig
@@ -8,4 +8,6 @@
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN5I=y
-+S:CONFIG_TARGET_A10S_OLINUXINO_M=y
++S:CONFIG_DRAM_CLK=432
++S:CONFIG_DRAM_ZQ=123
++S:CONFIG_DRAM_EMR1=4
diff --git a/configs/A13-OLinuXinoM_defconfig b/configs/A13-OLinuXinoM_defconfig
index 1a99418..a04f2b3 100644
--- a/configs/A13-OLinuXinoM_defconfig
+++ b/configs/A13-OLinuXinoM_defconfig
@@ -4,6 +4,7 @@
CONFIG_USB1_VBUS_PIN="PG11"
CONFIG_VIDEO_HDMI=n
CONFIG_VIDEO_VGA_VIA_LCD=y
+CONFIG_VIDEO_VGA_VIA_LCD_FORCE_SYNC_ACTIVE_HIGH=y
# For use with the Olimex 7" LCD module, adjust timings for other displays
# Set video-mode=sunxi:800x600-24@60,monitor=lcd in the env. to enable
CONFIG_VIDEO_LCD_MODE="x:800,y:480,depth:18,pclk_khz:33000,le:16,ri:209,up:22,lo:22,hs:30,vs:1,sync:3,vmode:0"
@@ -12,4 +13,6 @@
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN5I=y
-+S:CONFIG_TARGET_A13_OLINUXINOM=y
++S:CONFIG_DRAM_CLK=408
++S:CONFIG_DRAM_ZQ=123
++S:CONFIG_DRAM_EMR1=0
diff --git a/configs/A13-OLinuXino_defconfig b/configs/A13-OLinuXino_defconfig
index 7df6951..806d5b7 100644
--- a/configs/A13-OLinuXino_defconfig
+++ b/configs/A13-OLinuXino_defconfig
@@ -4,6 +4,7 @@
CONFIG_USB1_VBUS_PIN="PG11"
CONFIG_VIDEO_HDMI=n
CONFIG_VIDEO_VGA_VIA_LCD=y
+CONFIG_VIDEO_VGA_VIA_LCD_FORCE_SYNC_ACTIVE_HIGH=y
# For use with the Olimex 7" LCD module, adjust timings for other displays
# Set video-mode=sunxi:800x600-24@60,monitor=lcd in the env. to enable
CONFIG_VIDEO_LCD_MODE="x:800,y:480,depth:18,pclk_khz:33000,le:16,ri:209,up:22,lo:22,hs:30,vs:1,sync:3,vmode:0"
@@ -12,4 +13,6 @@
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN5I=y
-+S:CONFIG_TARGET_A13_OLINUXINO=y
++S:CONFIG_DRAM_CLK=408
++S:CONFIG_DRAM_ZQ=123
++S:CONFIG_DRAM_EMR1=0
diff --git a/configs/A20-OLinuXino-Lime2_defconfig b/configs/A20-OLinuXino-Lime2_defconfig
index 17fd19d..ff94e77 100644
--- a/configs/A20-OLinuXino-Lime2_defconfig
+++ b/configs/A20-OLinuXino-Lime2_defconfig
@@ -4,7 +4,6 @@
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN7I=y
-+S:CONFIG_TARGET_A20_OLINUXINO_L2=y
+S:CONFIG_DRAM_CLK=480
+S:CONFIG_DRAM_ZQ=127
+S:CONFIG_DRAM_EMR1=4
diff --git a/configs/A20-OLinuXino-Lime_defconfig b/configs/A20-OLinuXino-Lime_defconfig
index c8243a4..5442f64 100644
--- a/configs/A20-OLinuXino-Lime_defconfig
+++ b/configs/A20-OLinuXino-Lime_defconfig
@@ -4,7 +4,6 @@
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN7I=y
-+S:CONFIG_TARGET_A20_OLINUXINO_L=y
+S:CONFIG_DRAM_CLK=480
+S:CONFIG_DRAM_ZQ=127
+S:CONFIG_DRAM_EMR1=4
diff --git a/configs/A20-OLinuXino_MICRO_defconfig b/configs/A20-OLinuXino_MICRO_defconfig
index ac94c79..97a21ee 100644
--- a/configs/A20-OLinuXino_MICRO_defconfig
+++ b/configs/A20-OLinuXino_MICRO_defconfig
@@ -8,7 +8,6 @@
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN7I=y
-+S:CONFIG_TARGET_A20_OLINUXINO_M=y
+S:CONFIG_DRAM_CLK=384
+S:CONFIG_DRAM_ZQ=127
+S:CONFIG_DRAM_EMR1=4
diff --git a/configs/Auxtek-T004_defconfig b/configs/Auxtek-T004_defconfig
index 7fe9059..03ec3db 100644
--- a/configs/Auxtek-T004_defconfig
+++ b/configs/Auxtek-T004_defconfig
@@ -5,4 +5,6 @@
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN5I=y
-+S:CONFIG_TARGET_AUXTEK_T004=y
++S:CONFIG_DRAM_CLK=432
++S:CONFIG_DRAM_ZQ=123
++S:CONFIG_DRAM_EMR1=4
diff --git a/configs/Bananapi_defconfig b/configs/Bananapi_defconfig
index d94e08e..5aba938 100644
--- a/configs/Bananapi_defconfig
+++ b/configs/Bananapi_defconfig
@@ -1,10 +1,10 @@
CONFIG_SPL=y
CONFIG_SYS_EXTRA_OPTIONS="AXP209_POWER,SUNXI_GMAC,RGMII,MACPWR=SUNXI_GPH(23),AHCI,USB_EHCI"
CONFIG_FDTFILE="sun7i-a20-bananapi.dtb"
+CONFIG_GMAC_TX_DELAY=3
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN7I=y
-+S:CONFIG_TARGET_BANANAPI=y
+S:CONFIG_DRAM_CLK=432
+S:CONFIG_DRAM_ZQ=127
+S:CONFIG_DRAM_EMR1=4
diff --git a/configs/Bananapro_defconfig b/configs/Bananapro_defconfig
index 02e4f3e..e501b5c 100644
--- a/configs/Bananapro_defconfig
+++ b/configs/Bananapro_defconfig
@@ -3,10 +3,10 @@
CONFIG_FDTFILE="sun7i-a20-bananapro.dtb"
CONFIG_USB1_VBUS_PIN="PH0"
CONFIG_USB2_VBUS_PIN="PH1"
+CONFIG_GMAC_TX_DELAY=3
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN7I=y
-+S:CONFIG_TARGET_BANANAPRO=y
+S:CONFIG_DRAM_CLK=432
+S:CONFIG_DRAM_ZQ=127
+S:CONFIG_DRAM_EMR1=4
diff --git a/configs/Cubieboard2_defconfig b/configs/Cubieboard2_defconfig
index ef5b43a..7704a0e 100644
--- a/configs/Cubieboard2_defconfig
+++ b/configs/Cubieboard2_defconfig
@@ -4,7 +4,6 @@
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN7I=y
-+S:CONFIG_TARGET_CUBIEBOARD2=y
+S:CONFIG_DRAM_CLK=480
+S:CONFIG_DRAM_ZQ=127
+S:CONFIG_DRAM_EMR1=4
diff --git a/configs/Cubietruck_defconfig b/configs/Cubietruck_defconfig
index f51c491..b64f84f 100644
--- a/configs/Cubietruck_defconfig
+++ b/configs/Cubietruck_defconfig
@@ -5,7 +5,6 @@
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN7I=y
-+S:CONFIG_TARGET_CUBIETRUCK=y
+S:CONFIG_DRAM_CLK=432
+S:CONFIG_DRAM_ZQ=127
+S:CONFIG_DRAM_EMR1=4
diff --git a/configs/Hyundai_A7HD_defconfig b/configs/Hyundai_A7HD_defconfig
index 60eb03e..204640e 100644
--- a/configs/Hyundai_A7HD_defconfig
+++ b/configs/Hyundai_A7HD_defconfig
@@ -6,7 +6,8 @@
CONFIG_FDTFILE="sun4i-a10-hyundai-a7hd.dtb"
CONFIG_USB_MUSB_SUNXI=y
CONFIG_USB0_VBUS_PIN="PB09"
-CONFIG_USB2_VBUS_PIN=""
+CONFIG_USB1_VBUS_PIN=""
+CONFIG_USB2_VBUS_PIN="PH6"
CONFIG_VIDEO_LCD_MODE="x:1024,y:600,depth:18,pclk_khz:51000,le:45,ri:274,up:22,lo:12,hs:1,vs:1,sync:3,vmode:0"
CONFIG_VIDEO_LCD_DCLK_PHASE=1
CONFIG_VIDEO_LCD_POWER="PH2"
diff --git a/configs/Inet_86VS_defconfig b/configs/Inet_86VS_defconfig
new file mode 100644
index 0000000..ce9985a
--- /dev/null
+++ b/configs/Inet_86VS_defconfig
@@ -0,0 +1,15 @@
+CONFIG_SPL=y
+CONFIG_SYS_EXTRA_OPTIONS="AXP209_POWER"
+CONFIG_FDTFILE="sun5i-a13-inet-86vs.dtb"
+CONFIG_USB_MUSB_SUNXI=y
+CONFIG_USB0_VBUS_PIN="PG12"
+CONFIG_VIDEO_LCD_MODE="x:800,y:480,depth:18,pclk_khz:33000,le:45,ri:209,up:22,lo:22,hs:1,vs:1,sync:3,vmode:0"
+CONFIG_VIDEO_LCD_POWER="AXP0-0"
+CONFIG_VIDEO_LCD_BL_EN="AXP0-1"
+CONFIG_VIDEO_LCD_BL_PWM="PB2"
++S:CONFIG_ARM=y
++S:CONFIG_ARCH_SUNXI=y
++S:CONFIG_MACH_SUN5I=y
++S:CONFIG_DRAM_CLK=408
++S:CONFIG_DRAM_ZQ=123
++S:CONFIG_DRAM_EMR1=4
diff --git a/configs/Ippo_q8h_v5_defconfig b/configs/Ippo_q8h_v5_defconfig
index c894948..4786202 100644
--- a/configs/Ippo_q8h_v5_defconfig
+++ b/configs/Ippo_q8h_v5_defconfig
@@ -11,7 +11,6 @@
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN8I=y
-+S:CONFIG_TARGET_IPPO_Q8H_V5=y
+S:CONFIG_DRAM_CLK=480
# zq = 0xf777
+S:CONFIG_DRAM_ZQ=63351
diff --git a/configs/Linksprite_pcDuino3_Nano_defconfig b/configs/Linksprite_pcDuino3_Nano_defconfig
new file mode 100644
index 0000000..4baba14
--- /dev/null
+++ b/configs/Linksprite_pcDuino3_Nano_defconfig
@@ -0,0 +1,11 @@
+CONFIG_SPL=y
+CONFIG_SYS_EXTRA_OPTIONS="AXP209_POWER,SUNXI_GMAC,RGMII,AHCI,SATAPWR=SUNXI_GPH(2),USB_EHCI"
+CONFIG_FDTFILE="sun7i-a20-pcduino3-nano.dtb"
+CONFIG_GMAC_TX_DELAY=3
+CONFIG_USB1_VBUS_PIN="PH11"
++S:CONFIG_ARM=y
++S:CONFIG_ARCH_SUNXI=y
++S:CONFIG_MACH_SUN7I=y
++S:CONFIG_DRAM_CLK=408
++S:CONFIG_DRAM_ZQ=122
++S:CONFIG_DRAM_EMR1=4
diff --git a/configs/Linksprite_pcDuino3_defconfig b/configs/Linksprite_pcDuino3_defconfig
index 64e01c8..45d88f3 100644
--- a/configs/Linksprite_pcDuino3_defconfig
+++ b/configs/Linksprite_pcDuino3_defconfig
@@ -4,7 +4,6 @@
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN7I=y
-+S:CONFIG_TARGET_PCDUINO3=y
+S:CONFIG_DRAM_CLK=480
+S:CONFIG_DRAM_ZQ=122
+S:CONFIG_DRAM_EMR1=4
diff --git a/configs/Linksprite_pcDuino3_fdt_defconfig b/configs/Linksprite_pcDuino3_fdt_defconfig
index 49718c7..3b6dfa6 100644
--- a/configs/Linksprite_pcDuino3_fdt_defconfig
+++ b/configs/Linksprite_pcDuino3_fdt_defconfig
@@ -8,7 +8,6 @@
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN7I=y
-+S:CONFIG_TARGET_PCDUINO3=y
+S:CONFIG_DRAM_CLK=480
+S:CONFIG_DRAM_ZQ=122
+S:CONFIG_DRAM_EMR1=4
diff --git a/configs/MSI_Primo73_defconfig b/configs/MSI_Primo73_defconfig
index 6628184..c6fb7e6 100644
--- a/configs/MSI_Primo73_defconfig
+++ b/configs/MSI_Primo73_defconfig
@@ -1,3 +1,11 @@
+# The MSI Primo73 is an A20 based tablet, with 1G RAM, 16G NAND,
+# 1024x600 TN LCD display, mono speaker, 0.3 MP front camera, 2.0 MP
+# rear camera, 3000 mAh battery, gt911 touchscreen, mma8452 accelerometer
+# and rtl8188etv usb wifi. Has "power", "volume+" and "volume-" buttons
+# (both volume buttons are also connected to the UBOOT_SEL pin). The
+# external connectors are represented by MicroSD slot, MiniHDMI, MicroUSB
+# OTG and 3.5mm headphone jack. More details are available at
+# http://linux-sunxi.org/MSI_Primo73
CONFIG_SPL=y
CONFIG_SYS_EXTRA_OPTIONS="AXP209_POWER"
CONFIG_FDTFILE="sun7i-a20-primo73.dtb"
@@ -10,7 +18,6 @@
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN7I=y
-+S:CONFIG_TARGET_MSI_PRIMO73=y
+S:CONFIG_DRAM_CLK=384
+S:CONFIG_DRAM_ZQ=127
+S:CONFIG_DRAM_EMR1=4
diff --git a/configs/Mele_M3_defconfig b/configs/Mele_M3_defconfig
index 7f1710a..723a72a2 100644
--- a/configs/Mele_M3_defconfig
+++ b/configs/Mele_M3_defconfig
@@ -7,7 +7,6 @@
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN7I=y
-+S:CONFIG_TARGET_MELE_M3=y
+S:CONFIG_DRAM_CLK=384
+S:CONFIG_DRAM_ZQ=127
+S:CONFIG_DRAM_EMR1=4
diff --git a/configs/TZX-Q8-713B7_defconfig b/configs/TZX-Q8-713B7_defconfig
new file mode 100644
index 0000000..7b7b9dd
--- /dev/null
+++ b/configs/TZX-Q8-713B7_defconfig
@@ -0,0 +1,15 @@
+CONFIG_SPL=y
+CONFIG_SYS_EXTRA_OPTIONS="CONS_INDEX=2,AXP209_POWER"
+CONFIG_FDTFILE="sun5i-a13-tzx-q8-713b7.dtb"
+CONFIG_USB_MUSB_SUNXI=y
+CONFIG_USB0_VBUS_PIN="PG12"
+CONFIG_VIDEO_LCD_MODE="x:800,y:480,depth:18,pclk_khz:33000,le:87,ri:40,up:31,lo:13,hs:1,vs:1,sync:3,vmode:0"
+CONFIG_VIDEO_LCD_POWER="AXP0-0"
+CONFIG_VIDEO_LCD_BL_EN="AXP0-1"
+CONFIG_VIDEO_LCD_BL_PWM="PB2"
++S:CONFIG_ARM=y
++S:CONFIG_ARCH_SUNXI=y
++S:CONFIG_MACH_SUN5I=y
++S:CONFIG_DRAM_CLK=408
++S:CONFIG_DRAM_ZQ=123
++S:CONFIG_DRAM_EMR1=4
diff --git a/configs/am335x_boneblack_vboot_defconfig b/configs/am335x_boneblack_vboot_defconfig
index 5837a0a..51bf370 100644
--- a/configs/am335x_boneblack_vboot_defconfig
+++ b/configs/am335x_boneblack_vboot_defconfig
@@ -4,3 +4,7 @@
+S:CONFIG_TARGET_AM335X_EVM=y
CONFIG_OF_CONTROL=y
CONFIG_DEFAULT_DEVICE_TREE="am335x-boneblack"
+CONFIG_FIT=y
+CONFIG_FIT_VERBOSE=y
+CONFIG_FIT_SIGNATURE=y
+CONFIG_DM=y
diff --git a/configs/i12-tvbox_defconfig b/configs/i12-tvbox_defconfig
index 65791b7..41192fc 100644
--- a/configs/i12-tvbox_defconfig
+++ b/configs/i12-tvbox_defconfig
@@ -4,7 +4,6 @@
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN7I=y
-+S:CONFIG_TARGET_I12_TVBOX=y
+S:CONFIG_DRAM_CLK=384
+S:CONFIG_DRAM_ZQ=127
+S:CONFIG_DRAM_EMR1=4
diff --git a/configs/ids8313_defconfig b/configs/ids8313_defconfig
index 1c665aa..0950ec8 100644
--- a/configs/ids8313_defconfig
+++ b/configs/ids8313_defconfig
@@ -1,4 +1,7 @@
CONFIG_SYS_EXTRA_OPTIONS="SYS_TEXT_BASE=0xFFF00000"
CONFIG_PPC=y
CONFIG_MPC83xx=y
+CONFIG_FIT=y
+CONFIG_FIT_SIGNATURE=y
CONFIG_TARGET_IDS8313=y
+CONFIG_DM=y
diff --git a/configs/mk802_a10s_defconfig b/configs/mk802_a10s_defconfig
index 086e1e4..cafcbaa 100644
--- a/configs/mk802_a10s_defconfig
+++ b/configs/mk802_a10s_defconfig
@@ -5,7 +5,6 @@
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN5I=y
-+S:CONFIG_TARGET_MK802_A10S=y
+S:CONFIG_DRAM_CLK=432
+S:CONFIG_DRAM_ZQ=123
+S:CONFIG_DRAM_EMR1=0
diff --git a/configs/ph1_ld4_defconfig b/configs/ph1_ld4_defconfig
index 2e9dd00..86b4b15 100644
--- a/configs/ph1_ld4_defconfig
+++ b/configs/ph1_ld4_defconfig
@@ -18,6 +18,7 @@
CONFIG_CMD_LOADS=y
CONFIG_CMD_FLASH=y
CONFIG_CMD_NAND=y
+CONFIG_CMD_I2C=y
CONFIG_CMD_USB=y
CONFIG_CMD_ECHO=y
CONFIG_CMD_ITEST=y
@@ -34,6 +35,7 @@
CONFIG_NAND_DENALI_SPARE_AREA_SKIP_BYTES=8
CONFIG_DM_SERIAL=y
CONFIG_UNIPHIER_SERIAL=y
+CONFIG_DM_I2C=y
CONFIG_USB=y
CONFIG_USB_EHCI_HCD=y
CONFIG_USB_STORAGE=y
diff --git a/configs/ph1_pro4_defconfig b/configs/ph1_pro4_defconfig
index 5dca64b..242bcf9 100644
--- a/configs/ph1_pro4_defconfig
+++ b/configs/ph1_pro4_defconfig
@@ -18,6 +18,7 @@
CONFIG_CMD_LOADS=y
CONFIG_CMD_FLASH=y
CONFIG_CMD_NAND=y
+CONFIG_CMD_I2C=y
CONFIG_CMD_USB=y
CONFIG_CMD_ECHO=y
CONFIG_CMD_ITEST=y
@@ -34,6 +35,7 @@
CONFIG_NAND_DENALI_SPARE_AREA_SKIP_BYTES=8
CONFIG_DM_SERIAL=y
CONFIG_UNIPHIER_SERIAL=y
+CONFIG_DM_I2C=y
CONFIG_USB=y
CONFIG_USB_EHCI_HCD=y
CONFIG_USB_STORAGE=y
diff --git a/configs/ph1_sld8_defconfig b/configs/ph1_sld8_defconfig
index 2a6e334..8e95f17 100644
--- a/configs/ph1_sld8_defconfig
+++ b/configs/ph1_sld8_defconfig
@@ -18,6 +18,7 @@
CONFIG_CMD_LOADS=y
CONFIG_CMD_FLASH=y
CONFIG_CMD_NAND=y
+CONFIG_CMD_I2C=y
CONFIG_CMD_USB=y
CONFIG_CMD_ECHO=y
CONFIG_CMD_ITEST=y
@@ -34,6 +35,7 @@
CONFIG_NAND_DENALI_SPARE_AREA_SKIP_BYTES=8
CONFIG_DM_SERIAL=y
CONFIG_UNIPHIER_SERIAL=y
+CONFIG_DM_I2C=y
CONFIG_USB=y
CONFIG_USB_EHCI_HCD=y
CONFIG_USB_STORAGE=y
diff --git a/configs/r7-tv-dongle_defconfig b/configs/r7-tv-dongle_defconfig
index b9fd59c..e99e57d 100644
--- a/configs/r7-tv-dongle_defconfig
+++ b/configs/r7-tv-dongle_defconfig
@@ -5,4 +5,6 @@
+S:CONFIG_ARM=y
+S:CONFIG_ARCH_SUNXI=y
+S:CONFIG_MACH_SUN5I=y
-+S:CONFIG_TARGET_R7DONGLE=y
++S:CONFIG_DRAM_CLK=384
++S:CONFIG_DRAM_ZQ=123
++S:CONFIG_DRAM_EMR1=4
diff --git a/configs/sandbox_defconfig b/configs/sandbox_defconfig
index 47d8400..660063e 100644
--- a/configs/sandbox_defconfig
+++ b/configs/sandbox_defconfig
@@ -1,3 +1,7 @@
CONFIG_OF_CONTROL=y
CONFIG_OF_HOSTFILE=y
+CONFIG_FIT=y
+CONFIG_FIT_VERBOSE=y
+CONFIG_FIT_SIGNATURE=y
+CONFIG_DM=y
CONFIG_DEFAULT_DEVICE_TREE="sandbox"
diff --git a/configs/vexpress_aemv8a_defconfig b/configs/vexpress_aemv8a_defconfig
index b463a33..9f4b876 100644
--- a/configs/vexpress_aemv8a_defconfig
+++ b/configs/vexpress_aemv8a_defconfig
@@ -1,3 +1,3 @@
CONFIG_ARM=y
-CONFIG_TARGET_VEXPRESS_AEMV8A=y
+CONFIG_TARGET_VEXPRESS64_AEMV8A=y
CONFIG_DEFAULT_DEVICE_TREE="vexpress64"
diff --git a/configs/vexpress_aemv8a_juno_defconfig b/configs/vexpress_aemv8a_juno_defconfig
new file mode 100644
index 0000000..d28a428
--- /dev/null
+++ b/configs/vexpress_aemv8a_juno_defconfig
@@ -0,0 +1,5 @@
+# ARM Ltd. Juno Board Reference Design
+CONFIG_ARM=y
+CONFIG_TARGET_VEXPRESS64_JUNO=y
+CONFIG_DEFAULT_DEVICE_TREE="vexpress64"
+CONFIG_SHOW_BOOT_PROGRESS=y
diff --git a/configs/vexpress_aemv8a_semi_defconfig b/configs/vexpress_aemv8a_semi_defconfig
index 0035ccd..26cf7db4 100644
--- a/configs/vexpress_aemv8a_semi_defconfig
+++ b/configs/vexpress_aemv8a_semi_defconfig
@@ -1,4 +1,4 @@
-CONFIG_SYS_EXTRA_OPTIONS="SEMIHOSTING,BASE_FVP"
+# Semihosted FVP fast model
CONFIG_ARM=y
-CONFIG_TARGET_VEXPRESS_AEMV8A=y
+CONFIG_TARGET_VEXPRESS64_BASE_FVP=y
CONFIG_DEFAULT_DEVICE_TREE="vexpress64"
diff --git a/configs/zynq_microzed_defconfig b/configs/zynq_microzed_defconfig
index 9588849..8b985fe 100644
--- a/configs/zynq_microzed_defconfig
+++ b/configs/zynq_microzed_defconfig
@@ -3,4 +3,8 @@
+S:CONFIG_ZYNQ=y
+S:CONFIG_TARGET_ZYNQ_MICROZED=y
CONFIG_OF_CONTROL=y
+CONFIG_FIT=y
+CONFIG_FIT_VERBOSE=y
+CONFIG_FIT_SIGNATURE=y
+CONFIG_DM=y
CONFIG_DEFAULT_DEVICE_TREE="zynq-microzed"
diff --git a/configs/zynq_zc70x_defconfig b/configs/zynq_zc70x_defconfig
index cf50730..cceb321 100644
--- a/configs/zynq_zc70x_defconfig
+++ b/configs/zynq_zc70x_defconfig
@@ -4,3 +4,7 @@
+S:CONFIG_TARGET_ZYNQ_ZC70X=y
CONFIG_OF_CONTROL=y
CONFIG_DEFAULT_DEVICE_TREE="zynq-zc702"
+CONFIG_FIT=y
+CONFIG_FIT_VERBOSE=y
+CONFIG_FIT_SIGNATURE=y
+CONFIG_DM=y
diff --git a/configs/zynq_zc770_xm010_defconfig b/configs/zynq_zc770_xm010_defconfig
index 8bb405d..2935c0d 100644
--- a/configs/zynq_zc770_xm010_defconfig
+++ b/configs/zynq_zc770_xm010_defconfig
@@ -5,3 +5,7 @@
+S:CONFIG_TARGET_ZYNQ_ZC770=y
CONFIG_OF_CONTROL=y
CONFIG_DEFAULT_DEVICE_TREE="zynq-zc770-xm010"
+CONFIG_FIT=y
+CONFIG_FIT_VERBOSE=y
+CONFIG_FIT_SIGNATURE=y
+CONFIG_DM=y
diff --git a/configs/zynq_zc770_xm012_defconfig b/configs/zynq_zc770_xm012_defconfig
index 0ba5da5..0401739 100644
--- a/configs/zynq_zc770_xm012_defconfig
+++ b/configs/zynq_zc770_xm012_defconfig
@@ -5,3 +5,7 @@
+S:CONFIG_TARGET_ZYNQ_ZC770=y
CONFIG_OF_CONTROL=y
CONFIG_DEFAULT_DEVICE_TREE="zynq-zc770-xm012"
+CONFIG_FIT=y
+CONFIG_FIT_VERBOSE=y
+CONFIG_FIT_SIGNATURE=y
+CONFIG_DM=y
diff --git a/configs/zynq_zc770_xm013_defconfig b/configs/zynq_zc770_xm013_defconfig
index 13f8112..a95970a 100644
--- a/configs/zynq_zc770_xm013_defconfig
+++ b/configs/zynq_zc770_xm013_defconfig
@@ -5,3 +5,7 @@
+S:CONFIG_TARGET_ZYNQ_ZC770=y
CONFIG_OF_CONTROL=y
CONFIG_DEFAULT_DEVICE_TREE="zynq-zc770-xm013"
+CONFIG_FIT=y
+CONFIG_FIT_VERBOSE=y
+CONFIG_FIT_SIGNATURE=y
+CONFIG_DM=y
diff --git a/configs/zynq_zed_defconfig b/configs/zynq_zed_defconfig
index eb057fa..0fbc41a 100644
--- a/configs/zynq_zed_defconfig
+++ b/configs/zynq_zed_defconfig
@@ -4,3 +4,7 @@
+S:CONFIG_TARGET_ZYNQ_ZED=y
CONFIG_OF_CONTROL=y
CONFIG_DEFAULT_DEVICE_TREE="zynq-zed"
+CONFIG_FIT=y
+CONFIG_FIT_VERBOSE=y
+CONFIG_FIT_SIGNATURE=y
+CONFIG_DM=y
diff --git a/configs/zynq_zybo_defconfig b/configs/zynq_zybo_defconfig
index 12311cd..4e66760 100644
--- a/configs/zynq_zybo_defconfig
+++ b/configs/zynq_zybo_defconfig
@@ -4,3 +4,7 @@
+S:CONFIG_TARGET_ZYNQ_ZYBO=y
CONFIG_OF_CONTROL=y
CONFIG_DEFAULT_DEVICE_TREE="zynq-zybo"
+CONFIG_FIT=y
+CONFIG_FIT_VERBOSE=y
+CONFIG_FIT_SIGNATURE=y
+CONFIG_DM=y
diff --git a/doc/README.distro b/doc/README.distro
new file mode 100644
index 0000000..dd0f1c7
--- /dev/null
+++ b/doc/README.distro
@@ -0,0 +1,341 @@
+/*
+ * (C) Copyright 2014 Red Hat Inc.
+ * Copyright (c) 2014-2015, NVIDIA CORPORATION. All rights reserved.
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+Generic Distro Configuration Concept
+====================================
+
+Linux distributions are faced with supporting a variety of boot mechanisms,
+environments or bootloaders (PC BIOS, EFI, U-Boot, Barebox, ...). This makes
+life complicated. Worse, bootloaders such as U-Boot have a configurable set
+of features, and each board chooses to enable a different set of features.
+Hence, distros typically need to have board-specific knowledge in order to
+set up a bootable system.
+
+This document defines a common set of U-Boot features that are required for
+a distro to support the board in a generic fashion. Any board wishing to
+allow distros to install and boot in an out-of-the-box fashion should enable
+all these features. Linux distros can then create a single set of boot
+support/install logic that targets these features. This will allow distros
+to install on many boards without the need for board-specific logic.
+
+In fact, some of these features can be implemented by any bootloader, thus
+decoupling distro install/boot logic from any knowledge of the bootloader.
+
+This model assumes that boards will load boot configuration files from a
+regular storage mechanism (eMMC, SD card, USB Disk, SATA disk, etc.) with
+a standard partitioning scheme (MBR, GPT). Boards that cannnot support this
+storage model are outside the scope of this document, and may still need
+board-specific installer/boot-configuration support in a distro.
+
+To some extent, this model assumes that a board has a separate boot flash
+that contains U-Boot, and that the user has somehow installed U-Boot to this
+flash before running the distro installer. Even on boards that do not conform
+to this aspect of the model, the extent of the board-specific support in the
+distro installer logic would be to install a board-specific U-Boot package to
+the boot partition partition during installation. This distro-supplied U-Boot
+can still implement the same features as on any other board, and hence the
+distro's boot configuration file generation logic can still be board-agnostic.
+
+Locating Bootable Disks
+-----------------------
+
+Typical desktop/server PCs search all (or a user-defined subset of) attached
+storage devices for a bootable partition, then load the bootloader or boot
+configuration files from there. A U-Boot board port that enables the features
+mentioned in this document will search for boot configuration files in the
+same way.
+
+Thus, distros do not need to manipulate any kind of bootloader-specific
+configuration data to indicate which storage device the system should boot
+from.
+
+Distros simply need to install the boot configuration files (see next
+section) in an ext2/3/4 or FAT partition, mark the partition bootable (via
+the MBR bootable flag, or GPT legacy_bios_bootable attribute), and U-Boot (or
+any other bootloader) will find those boot files and execute them. This is
+conceptually identical to creating a grub2 configuration file on a desktop
+PC.
+
+Note that in the absense of any partition that is explicitly marked bootable,
+U-Boot falls back to searching the first valid partition of a disk for boot
+configuration files. Other bootloaders are recommended to do the same, since
+I believe that partition table bootable flags aren't so commonly used outside
+the realm of x86 PCs.
+
+U-Boot can also search for boot configuration files from a TFTP server.
+
+Boot Configuration Files
+------------------------
+
+The standard format for boot configuration files is that of extlinux.conf, as
+handled by U-Boot's "syslinux" (disk) or "pxe boot" (network). This is roughly
+as specified at:
+
+http://www.freedesktop.org/wiki/Specifications/BootLoaderSpec/
+
+... with the exceptions that the BootLoaderSpec document:
+
+* Prescribes a separate configuration per boot menu option, whereas U-Boot
+ lumps all options into a single extlinux.conf file. Hence, U-Boot searches
+ for /extlinux/extlinux.conf then /boot/extlinux/extlinux.conf on disk, or
+ pxelinux.cfg/default over the network.
+
+* Does not document the fdtdir option, which automatically selects the DTB to
+ pass to the kernel.
+
+One example extlinux.conf generated by the Fedora installer is:
+
+------------------------------------------------------------
+# extlinux.conf generated by anaconda
+
+ui menu.c32
+
+menu autoboot Welcome to Fedora. Automatic boot in # second{,s}. Press a key for options.
+menu title Fedora Boot Options.
+menu hidden
+
+timeout 50
+#totaltimeout 9000
+
+default Fedora (3.17.0-0.rc4.git2.1.fc22.armv7hl+lpae) 22 (Rawhide)
+
+label Fedora (3.17.0-0.rc4.git2.1.fc22.armv7hl) 22 (Rawhide)
+ kernel /boot/vmlinuz-3.17.0-0.rc4.git2.1.fc22.armv7hl
+ append ro root=UUID=8eac677f-8ea8-4270-8479-d5ddbb797450 console=ttyS0,115200n8 LANG=en_US.UTF-8 drm.debug=0xf
+ fdtdir /boot/dtb-3.17.0-0.rc4.git2.1.fc22.armv7hl
+ initrd /boot/initramfs-3.17.0-0.rc4.git2.1.fc22.armv7hl.img
+
+label Fedora (3.17.0-0.rc4.git2.1.fc22.armv7hl+lpae) 22 (Rawhide)
+ kernel /boot/vmlinuz-3.17.0-0.rc4.git2.1.fc22.armv7hl+lpae
+ append ro root=UUID=8eac677f-8ea8-4270-8479-d5ddbb797450 console=ttyS0,115200n8 LANG=en_US.UTF-8 drm.debug=0xf
+ fdtdir /boot/dtb-3.17.0-0.rc4.git2.1.fc22.armv7hl+lpae
+ initrd /boot/initramfs-3.17.0-0.rc4.git2.1.fc22.armv7hl+lpae.img
+
+label Fedora-0-rescue-8f6ba7b039524e0eb957d2c9203f04bc (0-rescue-8f6ba7b039524e0eb957d2c9203f04bc)
+ kernel /boot/vmlinuz-0-rescue-8f6ba7b039524e0eb957d2c9203f04bc
+ initrd /boot/initramfs-0-rescue-8f6ba7b039524e0eb957d2c9203f04bc.img
+ append ro root=UUID=8eac677f-8ea8-4270-8479-d5ddbb797450 console=ttyS0,115200n8
+ fdtdir /boot/dtb-3.16.0-0.rc6.git1.1.fc22.armv7hl+lpae
+------------------------------------------------------------
+
+Another hand-crafted network boot configuration file is:
+
+------------------------------------------------------------
+TIMEOUT 100
+
+MENU TITLE TFTP boot options
+
+LABEL jetson-tk1-emmc
+ MENU LABEL ../zImage root on Jetson TK1 eMMC
+ LINUX ../zImage
+ FDTDIR ../
+ APPEND console=ttyS0,115200n8 console=tty1 loglevel=8 rootwait rw earlyprintk root=PARTUUID=80a5a8e9-c744-491a-93c1-4f4194fd690b
+
+LABEL venice2-emmc
+ MENU LABEL ../zImage root on Venice2 eMMC
+ LINUX ../zImage
+ FDTDIR ../
+ APPEND console=ttyS0,115200n8 console=tty1 loglevel=8 rootwait rw earlyprintk root=PARTUUID=5f71e06f-be08-48ed-b1ef-ee4800cc860f
+
+LABEL sdcard
+ MENU LABEL ../zImage, root on 2GB sdcard
+ LINUX ../zImage
+ FDTDIR ../
+ APPEND console=ttyS0,115200n8 console=tty1 loglevel=8 rootwait rw earlyprintk root=PARTUUID=b2f82cda-2535-4779-b467-094a210fbae7
+
+LABEL fedora-installer-fk
+ MENU LABEL Fedora installer w/ Fedora kernel
+ LINUX fedora-installer/vmlinuz
+ INITRD fedora-installer/initrd.img.orig
+ FDTDIR fedora-installer/dtb
+ APPEND loglevel=8 ip=dhcp inst.repo=http://10.0.0.2/mirrors/fedora/linux/development/rawhide/armhfp/os/ rd.shell cma=64M
+------------------------------------------------------------
+
+U-Boot Implementation
+=====================
+
+Enabling the distro options
+---------------------------
+
+In your board configuration file, include the following:
+
+------------------------------------------------------------
+#ifndef CONFIG_SPL_BUILD
+#include <config_distro_defaults.h>
+#include <config_distro_bootcmd.h>
+#endif
+------------------------------------------------------------
+
+The first of those headers primarily enables a core set of U-Boot features,
+such as support for MBR and GPT partitions, ext* and FAT filesystems, booting
+raw zImage and initrd (rather than FIT- or uImage-wrapped files), etc. Network
+boot support is also enabled here, which is useful in order to boot distro
+installers given that distros do not commonly distribute bootable install
+media for non-PC targets at present.
+
+Finally, a few options that are mostly relevant only when using U-Boot-
+specific boot.scr scripts are enabled. This enables distros to generate a
+U-Boot-specific boot.scr script rather than extlinux.conf as the boot
+configuration file. While doing so is fully supported, and
+<config_distro_defaults.h> exposes enough parameterization to boot.scr to
+allow for board-agnostic boot.scr content, this document recommends that
+distros generate extlinux.conf rather than boot.scr. extlinux.conf is intended
+to work across multiple bootloaders, whereas boot.scr will only work with
+U-Boot. TODO: document the contract between U-Boot and boot.scr re: which
+environment variables a generic boot.scr may rely upon.
+
+The second of those headers sets up the default environment so that $bootcmd
+is defined in a way that searches attached disks for boot configuration files,
+and executes them if found.
+
+Required Environment Variables
+------------------------------
+
+The U-Boot "syslinux" and "pxe boot" commands require a number of environment
+variables be set. Default values for these variables are often hard-coded into
+CONFIG_EXTRA_ENV_SETTINGS in the board's U-Boot configuration file, so that
+the user doesn't have to configure them.
+
+fdt_addr:
+
+ Mandatory for any system that provides the DTB in HW (e.g. ROM) and wishes
+ to pass that DTB to Linux, rather than loading a DTB from the boot
+ filesystem. Prohibited for any other system.
+
+ If specified a DTB to boot the system must be available at the given
+ address.
+
+fdt_addr_r:
+
+ Mandatory. The location in RAM where the DTB will be loaded or copied to when
+ processing the fdtdir/devicetreedir or fdt/devicetree options in
+ extlinux.conf.
+
+ This is mandatory even when fdt_addr is provided, since extlinux.conf must
+ always be able to provide a DTB which overrides any copy provided by the HW.
+
+ A size of 1MB for the FDT/DTB seems reasonable.
+
+ramdisk_addr_r:
+
+ Mandatory. The location in RAM where the initial ramdisk will be loaded to
+ when processing the initrd option in extlinux.conf.
+
+ It is recommended that this location be highest in RAM out of fdt_addr_,
+ kernel_addr_r, and ramdisk_addr_r, so that the RAM disk can vary in size
+ and use any available RAM.
+
+kernel_addr_r:
+
+ Mandatory. The location in RAM where the kernel will be loaded to when
+ processing the kernel option in the extlinux.conf.
+
+ The kernel should be located within the first 128M of RAM in order for the
+ kernel CONFIG_AUTO_ZRELADDR option to work, which is likely enabled on any
+ distro kernel. Since the kernel will decompress itself to 0x8000 after the
+ start of RAM, kernel_addr_rshould not overlap that area, or the kernel will
+ have to copy itself somewhere else first before decompression.
+
+ A size of 16MB for the kernel is likely adequate.
+
+pxe_addr_r:
+
+ Mandatory. The location in RAM where extlinux.conf will be loaded to prior
+ to processing.
+
+ A size of 1MB for extlinux.conf is more than adequate.
+
+scriptaddr:
+
+ Mandatory, if the boot script is boot.scr rather than extlinux.conf. The
+ location in RAM where boot.scr will be loaded to prior to execution.
+
+ A size of 1MB for extlinux.conf is more than adequate.
+
+For suggestions on memory locations for ARM systems, you must follow the
+guidelines specified in Documentation/arm/Booting in the Linux kernel tree.
+
+For a commented example of setting these values, please see the definition of
+MEM_LAYOUT_ENV_SETTINGS in include/configs/tegra124-common.h.
+
+Boot Target Configuration
+-------------------------
+
+<config_distro_bootcmd.h> defines $bootcmd and many helper command variables
+that automatically search attached disks for boot configuration files and
+execute them. Boards must provide configure <config_distro_bootcmd.h> so that
+it supports the correct set of possible boot device types. To provide this
+configuration, simply define macro BOOT_TARGET_DEVICES prior to including
+<config_distro_bootcmd.h>. For example:
+
+------------------------------------------------------------
+#ifndef CONFIG_SPL_BUILD
+#define BOOT_TARGET_DEVICES(func) \
+ func(MMC, mmc, 1) \
+ func(MMC, mmc, 0) \
+ func(USB, usb, 0) \
+ func(PXE, pxe, na) \
+ func(DHCP, dhcp, na)
+#include <config_distro_bootcmd.h>
+#endif
+------------------------------------------------------------
+
+Each entry in the macro defines a single boot device (e.g. a specific eMMC
+device or SD card) or type of boot device (e.g. USB disk). The parameters to
+the func macro (passed in by the internal implementation of the header) are:
+
+- Upper-case disk type (MMC, SATA, SCSI, IDE, USB, DHCP, PXE).
+- Lower-case disk type (same options as above).
+- ID of the specific disk (MMC only) or ignored for other types.
+
+User Configuration
+==================
+
+Once the user has installed U-Boot, it is expected that the environment will
+be reset to the default values in order to enable $bootcmd and friends, as set
+up by <config_distro_bootcmd.h>. After this, various environment variables may
+be altered to influence the boot process:
+
+boot_targets:
+
+ The list of boot locations searched.
+
+ Example: mmc0, mmc1, usb, pxe
+
+ Entries may be removed or re-ordered in this list to affect the boot order.
+
+boot_prefixes:
+
+ For disk-based booting, the list of directories within a partition that are
+ searched for boot configuration files (extlinux.conf, boot.scr).
+
+ Example: / /boot/
+
+ Entries may be removed or re-ordered in this list to affect the set of
+ directories which are searched.
+
+boot_scripts:
+
+ The name of U-Boot style boot.scr files that $bootcmd searches for.
+
+ Example: boot.scr.uimg boot.scr
+
+ (Typically we expect extlinux.conf to be used, but execution of boot.scr is
+ maintained for backwards-compatibility.)
+
+ Entries may be removed or re-ordered in this list to affect the set of
+ filenames which are supported.
+
+scan_dev_for_extlinux:
+
+ If you want to disable extlinux.conf on all disks, set the value to something
+ innocuous, e.g. setenv scan_dev_for_extlinux true.
+
+scan_dev_for_scripts:
+
+ If you want to disable boot.scr on all disks, set the value to something
+ innocuous, e.g. setenv scan_dev_for_scripts true.
diff --git a/doc/README.standalone b/doc/README.standalone
index e3000ef..659a12f 100644
--- a/doc/README.standalone
+++ b/doc/README.standalone
@@ -5,18 +5,18 @@
table is allocated and initialized in the jumptable_init() routine
(common/exports.c). Other routines may also modify the jump table,
however. The jump table can be accessed as the 'jt' field of the
- 'global_data' structure. The slot numbers for the jump table are
+ 'global_data' structure. The struct members for the jump table are
defined in the <include/exports.h> header. E.g., to substitute the
malloc() and free() functions that will be available to standalone
applications, one should do the following:
DECLARE_GLOBAL_DATA_PTR;
- gd->jt[XF_malloc] = my_malloc;
- gd->jt[XF_free] = my_free;
+ gd->jt->malloc = my_malloc;
+ gd->jt->free = my_free;
- Note that the pointers to the functions all have 'void *' type and
- thus the compiler cannot perform type checks on these assignments.
+ Note that the pointers to the functions are real function pointers
+ so the compiler can perform type checks on these assignments.
2. The pointer to the jump table is passed to the application in a
machine-dependent way. PowerPC, ARM, MIPS, Blackfin and Nios II
@@ -65,27 +65,46 @@
=> tftp 0x40000 hello_world.bin
=> go 0x40004
-5. To export some additional function foobar(), the following steps
+5. To export some additional function long foobar(int i,char c), the following steps
should be undertaken:
- Append the following line at the end of the include/_exports.h
file:
- EXPORT_FUNC(foobar)
+ EXPORT_FUNC(foobar, long, foobar, int, char)
+
+ Parameters to EXPORT_FUNC:
+ - the first parameter is the function that is exported (default implementation)
+ - the second parameter is the return value type
+ - the third parameter is the name of the member in struct jt_funcs
+ this is also the name that the standalone application will used.
+ the rest of the parameters are the function arguments
- Add the prototype for this function to the include/exports.h
file:
+ long foobar(int i, char c);
+
- void foobar(void);
+ Initialization with the default implementation is done in jumptable_init()
- - Add the initialization of the jump table slot wherever
- appropriate (most likely, to the jumptable_init() function):
+ You can override the default implementation using:
- gd->jt[XF_foobar] = foobar;
+ gd->jt->foobar = another_foobar;
+
+ The signature of another_foobar must then match the declaration of foobar.
- Increase the XF_VERSION value by one in the include/exports.h
file
+ - If you want to export a function which depends on a CONFIG_XXX
+ use 2 lines like this:
+ #ifdef CONFIG_FOOBAR
+ EXPORT_FUNC(foobar, long, foobar, int, char)
+ #else
+ EXPORT_FUNC(dummy, void, foobar, void)
+ #endif
+
+
6. The code for exporting the U-Boot functions to applications is
mostly machine-independent. The only places written in assembly
language are stub functions that perform the jump through the jump
diff --git a/doc/device-tree-bindings/gpio/gpio-samsung.txt b/doc/device-tree-bindings/gpio/gpio-samsung.txt
new file mode 100644
index 0000000..5375625
--- /dev/null
+++ b/doc/device-tree-bindings/gpio/gpio-samsung.txt
@@ -0,0 +1,41 @@
+Samsung Exynos4 GPIO Controller
+
+Required properties:
+- compatible: Compatible property value should be "samsung,exynos4-gpio>".
+
+- reg: Physical base address of the controller and length of memory mapped
+ region.
+
+- #gpio-cells: Should be 4. The syntax of the gpio specifier used by client nodes
+ should be the following with values derived from the SoC user manual.
+ <[phandle of the gpio controller node]
+ [pin number within the gpio controller]
+ [mux function]
+ [flags and pull up/down]
+ [drive strength]>
+
+ Values for gpio specifier:
+ - Pin number: is a value between 0 to 7.
+ - Flags and Pull Up/Down: 0 - Pull Up/Down Disabled.
+ 1 - Pull Down Enabled.
+ 3 - Pull Up Enabled.
+ Bit 16 (0x00010000) - Input is active low.
+ - Drive Strength: 0 - 1x,
+ 1 - 3x,
+ 2 - 2x,
+ 3 - 4x
+
+- gpio-controller: Specifies that the node is a gpio controller.
+- #address-cells: should be 1.
+- #size-cells: should be 1.
+
+Example:
+
+ gpa0: gpio-controller@11400000 {
+ #address-cells = <1>;
+ #size-cells = <1>;
+ compatible = "samsung,exynos4-gpio";
+ reg = <0x11400000 0x20>;
+ #gpio-cells = <4>;
+ gpio-controller;
+ };
diff --git a/doc/device-tree-bindings/gpio/gpio.txt b/doc/device-tree-bindings/gpio/gpio.txt
new file mode 100644
index 0000000..b9bd1d6
--- /dev/null
+++ b/doc/device-tree-bindings/gpio/gpio.txt
@@ -0,0 +1,211 @@
+Specifying GPIO information for devices
+============================================
+
+1) gpios property
+-----------------
+
+Nodes that makes use of GPIOs should specify them using one or more
+properties, each containing a 'gpio-list':
+
+ gpio-list ::= <single-gpio> [gpio-list]
+ single-gpio ::= <gpio-phandle> <gpio-specifier>
+ gpio-phandle : phandle to gpio controller node
+ gpio-specifier : Array of #gpio-cells specifying specific gpio
+ (controller specific)
+
+GPIO properties should be named "[<name>-]gpios", with <name> being the purpose
+of this GPIO for the device. While a non-existent <name> is considered valid
+for compatibility reasons (resolving to the "gpios" property), it is not allowed
+for new bindings.
+
+GPIO properties can contain one or more GPIO phandles, but only in exceptional
+cases should they contain more than one. If your device uses several GPIOs with
+distinct functions, reference each of them under its own property, giving it a
+meaningful name. The only case where an array of GPIOs is accepted is when
+several GPIOs serve the same function (e.g. a parallel data line).
+
+The exact purpose of each gpios property must be documented in the device tree
+binding of the device.
+
+The following example could be used to describe GPIO pins used as device enable
+and bit-banged data signals:
+
+ gpio1: gpio1 {
+ gpio-controller
+ #gpio-cells = <2>;
+ };
+ gpio2: gpio2 {
+ gpio-controller
+ #gpio-cells = <1>;
+ };
+ [...]
+
+ enable-gpios = <&gpio2 2>;
+ data-gpios = <&gpio1 12 0>,
+ <&gpio1 13 0>,
+ <&gpio1 14 0>,
+ <&gpio1 15 0>;
+
+Note that gpio-specifier length is controller dependent. In the
+above example, &gpio1 uses 2 cells to specify a gpio, while &gpio2
+only uses one.
+
+gpio-specifier may encode: bank, pin position inside the bank,
+whether pin is open-drain and whether pin is logically inverted.
+Exact meaning of each specifier cell is controller specific, and must
+be documented in the device tree binding for the device. Use the macros
+defined in include/dt-bindings/gpio/gpio.h whenever possible:
+
+Example of a node using GPIOs:
+
+ node {
+ enable-gpios = <&qe_pio_e 18 GPIO_ACTIVE_HIGH>;
+ };
+
+GPIO_ACTIVE_HIGH is 0, so in this example gpio-specifier is "18 0" and encodes
+GPIO pin number, and GPIO flags as accepted by the "qe_pio_e" gpio-controller.
+
+1.1) GPIO specifier best practices
+----------------------------------
+
+A gpio-specifier should contain a flag indicating the GPIO polarity; active-
+high or active-low. If it does, the follow best practices should be followed:
+
+The gpio-specifier's polarity flag should represent the physical level at the
+GPIO controller that achieves (or represents, for inputs) a logically asserted
+value at the device. The exact definition of logically asserted should be
+defined by the binding for the device. If the board inverts the signal between
+the GPIO controller and the device, then the gpio-specifier will represent the
+opposite physical level than the signal at the device's pin.
+
+When the device's signal polarity is configurable, the binding for the
+device must either:
+
+a) Define a single static polarity for the signal, with the expectation that
+any software using that binding would statically program the device to use
+that signal polarity.
+
+The static choice of polarity may be either:
+
+a1) (Preferred) Dictated by a binding-specific DT property.
+
+or:
+
+a2) Defined statically by the DT binding itself.
+
+In particular, the polarity cannot be derived from the gpio-specifier, since
+that would prevent the DT from separately representing the two orthogonal
+concepts of configurable signal polarity in the device, and possible board-
+level signal inversion.
+
+or:
+
+b) Pick a single option for device signal polarity, and document this choice
+in the binding. The gpio-specifier should represent the polarity of the signal
+(at the GPIO controller) assuming that the device is configured for this
+particular signal polarity choice. If software chooses to program the device
+to generate or receive a signal of the opposite polarity, software will be
+responsible for correctly interpreting (inverting) the GPIO signal at the GPIO
+controller.
+
+2) gpio-controller nodes
+------------------------
+
+Every GPIO controller node must contain both an empty "gpio-controller"
+property, and a #gpio-cells integer property, which indicates the number of
+cells in a gpio-specifier.
+
+Example of two SOC GPIO banks defined as gpio-controller nodes:
+
+ qe_pio_a: gpio-controller@1400 {
+ compatible = "fsl,qe-pario-bank-a", "fsl,qe-pario-bank";
+ reg = <0x1400 0x18>;
+ gpio-controller;
+ #gpio-cells = <2>;
+ };
+
+ qe_pio_e: gpio-controller@1460 {
+ compatible = "fsl,qe-pario-bank-e", "fsl,qe-pario-bank";
+ reg = <0x1460 0x18>;
+ gpio-controller;
+ #gpio-cells = <2>;
+ };
+
+2.1) gpio- and pin-controller interaction
+-----------------------------------------
+
+Some or all of the GPIOs provided by a GPIO controller may be routed to pins
+on the package via a pin controller. This allows muxing those pins between
+GPIO and other functions.
+
+It is useful to represent which GPIOs correspond to which pins on which pin
+controllers. The gpio-ranges property described below represents this, and
+contains information structures as follows:
+
+ gpio-range-list ::= <single-gpio-range> [gpio-range-list]
+ single-gpio-range ::= <numeric-gpio-range> | <named-gpio-range>
+ numeric-gpio-range ::=
+ <pinctrl-phandle> <gpio-base> <pinctrl-base> <count>
+ named-gpio-range ::= <pinctrl-phandle> <gpio-base> '<0 0>'
+ gpio-phandle : phandle to pin controller node.
+ gpio-base : Base GPIO ID in the GPIO controller
+ pinctrl-base : Base pinctrl pin ID in the pin controller
+ count : The number of GPIOs/pins in this range
+
+The "pin controller node" mentioned above must conform to the bindings
+described in ../pinctrl/pinctrl-bindings.txt.
+
+In case named gpio ranges are used (ranges with both <pinctrl-base> and
+<count> set to 0), the property gpio-ranges-group-names contains one string
+for every single-gpio-range in gpio-ranges:
+ gpiorange-names-list ::= <gpiorange-name> [gpiorange-names-list]
+ gpiorange-name : Name of the pingroup associated to the GPIO range in
+ the respective pin controller.
+
+Elements of gpiorange-names-list corresponding to numeric ranges contain
+the empty string. Elements of gpiorange-names-list corresponding to named
+ranges contain the name of a pin group defined in the respective pin
+controller. The number of pins/GPIOs in the range is the number of pins in
+that pin group.
+
+Previous versions of this binding required all pin controller nodes that
+were referenced by any gpio-ranges property to contain a property named
+#gpio-range-cells with value <3>. This requirement is now deprecated.
+However, that property may still exist in older device trees for
+compatibility reasons, and would still be required even in new device
+trees that need to be compatible with older software.
+
+Example 1:
+
+ qe_pio_e: gpio-controller@1460 {
+ #gpio-cells = <2>;
+ compatible = "fsl,qe-pario-bank-e", "fsl,qe-pario-bank";
+ reg = <0x1460 0x18>;
+ gpio-controller;
+ gpio-ranges = <&pinctrl1 0 20 10>, <&pinctrl2 10 50 20>;
+ };
+
+Here, a single GPIO controller has GPIOs 0..9 routed to pin controller
+pinctrl1's pins 20..29, and GPIOs 10..19 routed to pin controller pinctrl2's
+pins 50..59.
+
+Example 2:
+
+ gpio_pio_i: gpio-controller@14B0 {
+ #gpio-cells = <2>;
+ compatible = "fsl,qe-pario-bank-e", "fsl,qe-pario-bank";
+ reg = <0x1480 0x18>;
+ gpio-controller;
+ gpio-ranges = <&pinctrl1 0 20 10>,
+ <&pinctrl2 10 0 0>,
+ <&pinctrl1 15 0 10>,
+ <&pinctrl2 25 0 0>;
+ gpio-ranges-group-names = "",
+ "foo",
+ "",
+ "bar";
+ };
+
+Here, three GPIO ranges are defined wrt. two pin controllers. pinctrl1 GPIO
+ranges are defined using pin numbers whereas the GPIO ranges wrt. pinctrl2
+are named "foo" and "bar".
diff --git a/doc/device-tree-bindings/gpio/nvidia,tegra20-gpio.txt b/doc/device-tree-bindings/gpio/nvidia,tegra20-gpio.txt
new file mode 100644
index 0000000..023c952
--- /dev/null
+++ b/doc/device-tree-bindings/gpio/nvidia,tegra20-gpio.txt
@@ -0,0 +1,40 @@
+NVIDIA Tegra GPIO controller
+
+Required properties:
+- compatible : "nvidia,tegra<chip>-gpio"
+- reg : Physical base address and length of the controller's registers.
+- interrupts : The interrupt outputs from the controller. For Tegra20,
+ there should be 7 interrupts specified, and for Tegra30, there should
+ be 8 interrupts specified.
+- #gpio-cells : Should be two. The first cell is the pin number and the
+ second cell is used to specify optional parameters:
+ - bit 0 specifies polarity (0 for normal, 1 for inverted)
+- gpio-controller : Marks the device node as a GPIO controller.
+- #interrupt-cells : Should be 2.
+ The first cell is the GPIO number.
+ The second cell is used to specify flags:
+ bits[3:0] trigger type and level flags:
+ 1 = low-to-high edge triggered.
+ 2 = high-to-low edge triggered.
+ 4 = active high level-sensitive.
+ 8 = active low level-sensitive.
+ Valid combinations are 1, 2, 3, 4, 8.
+- interrupt-controller : Marks the device node as an interrupt controller.
+
+Example:
+
+gpio: gpio@6000d000 {
+ compatible = "nvidia,tegra20-gpio";
+ reg = < 0x6000d000 0x1000 >;
+ interrupts = < 0 32 0x04
+ 0 33 0x04
+ 0 34 0x04
+ 0 35 0x04
+ 0 55 0x04
+ 0 87 0x04
+ 0 89 0x04 >;
+ #gpio-cells = <2>;
+ gpio-controller;
+ #interrupt-cells = <2>;
+ interrupt-controller;
+};
diff --git a/doc/device-tree-bindings/i2c/i2c.txt b/doc/device-tree-bindings/i2c/i2c.txt
new file mode 100644
index 0000000..ea918dd
--- /dev/null
+++ b/doc/device-tree-bindings/i2c/i2c.txt
@@ -0,0 +1,28 @@
+U-Boot I2C
+----------
+
+U-Boot's I2C model has the concept of an offset within a chip (I2C target
+device). The offset can be up to 4 bytes long, but is normally 1 byte,
+meaning that offsets from 0 to 255 are supported by the chip. This often
+corresponds to register numbers.
+
+Apart from the controller-specific I2C bindings, U-Boot supports a special
+property which allows the chip offset length to be selected.
+
+Optional properties:
+- u-boot,i2c-offset-len - length of chip offset in bytes. If omitted the
+ default value of 1 is used.
+
+
+Example
+-------
+
+i2c4: i2c@12ca0000 {
+ cros-ec@1e {
+ reg = <0x1e>;
+ compatible = "google,cros-ec";
+ i2c-max-frequency = <100000>;
+ u-boot,i2c-offset-len = <0>;
+ ec-interrupt = <&gpx1 6 GPIO_ACTIVE_LOW>;
+ };
+};
diff --git a/doc/driver-model/README.txt b/doc/driver-model/README.txt
index eafa825..f83264d 100644
--- a/doc/driver-model/README.txt
+++ b/doc/driver-model/README.txt
@@ -363,6 +363,10 @@
in your ofdata_to_platdata (or probe) method to allocate the required memory,
and you should free it in the remove method.
+The driver model tree is intended to mirror that of the device tree. The
+root driver is at device tree offset 0 (the root node, '/'), and its
+children are the children of the root node.
+
Declaring Uclasses
------------------
@@ -384,12 +388,12 @@
U-Boot numbers devices from 0 in many situations, such as in the command
line for I2C and SPI buses, and the device names for serial ports (serial0,
serial1, ...). Driver model supports this numbering and permits devices
-to be locating by their 'sequence'. This numbering unique identifies a
+to be locating by their 'sequence'. This numbering uniquely identifies a
device in its uclass, so no two devices within a particular uclass can have
the same sequence number.
Sequence numbers start from 0 but gaps are permitted. For example, a board
-may have I2C buses 0, 1, 4, 5 but no 2 or 3. The choice of how devices are
+may have I2C buses 1, 4, 5 but no 0, 2 or 3. The choice of how devices are
numbered is up to a particular board, and may be set by the SoC in some
cases. While it might be tempting to automatically renumber the devices
where there are gaps in the sequence, this can lead to confusion and is
@@ -399,7 +403,7 @@
device will be automatically allocated the next available sequence number.
To specify the sequence number in the device tree an alias is typically
-used.
+used. Make sure that the uclass has the DM_UC_FLAG_SEQ_ALIAS flag set.
aliases {
serial2 = "/serial@22230000";
@@ -409,43 +413,18 @@
("/serial@22230000") will be given sequence number 2. Any command or driver
which requests serial device 2 will obtain this device.
-Some devices represent buses where the devices on the bus are numbered or
-addressed. For example, SPI typically numbers its slaves from 0, and I2C
-uses a 7-bit address. In these cases the 'reg' property of the subnode is
-used, for example:
-
-{
- aliases {
- spi2 = "/spi@22300000";
- };
-
- spi@22300000 {
- #address-cells = <1>;
- #size-cells = <1>;
- spi-flash@0 {
- reg = <0>;
- ...
- }
- eeprom@1 {
- reg = <1>;
- };
- };
-
-In this case we have a SPI bus with two slaves at 0 and 1. The SPI bus
-itself is numbered 2. So we might access the SPI flash with:
-
- sf probe 2:0
-
-and the eeprom with
+More commonly you can use node references, which expand to the full path:
- sspi 2:1 32 ef
-
-These commands simply need to look up the 2nd device in the SPI uclass to
-find the right SPI bus. Then, they look at the children of that bus for the
-right sequence number (0 or 1 in this case).
+aliases {
+ serial2 = &serial_2;
+};
+...
+serial_2: serial@22230000 {
+...
+};
-Typically the alias method is used for top-level nodes and the 'reg' method
-is used only for buses.
+The alias resolves to the same string in this case, but this version is
+easier to read.
Device sequence numbers are resolved when a device is probed. Before then
the sequence number is only a request which may or may not be honoured,
@@ -462,11 +441,18 @@
the bus provides some sort of transport or translation that makes it
possible to talk to the devices on the bus.
-Driver model provides a few useful features to help with implementing
-buses. Firstly, a bus can request that its children store some 'parent
-data' which can be used to keep track of child state. Secondly, the bus can
-define methods which are called when a child is probed or removed. This is
-similar to the methods the uclass driver provides.
+Driver model provides some useful features to help with implementing buses.
+Firstly, a bus can request that its children store some 'parent data' which
+can be used to keep track of child state. Secondly, the bus can define
+methods which are called when a child is probed or removed. This is similar
+to the methods the uclass driver provides. Thirdly, per-child platform data
+can be provided to specify things like the child's address on the bus. This
+persists across child probe()/remove() cycles.
+
+For consistency and ease of implementation, the bus uclass can specify the
+per-child platform data, so that it can be the same for all children of buses
+in that uclass. There are also uclass methods which can be called when
+children are bound and probed.
Here an explanation of how a bus fits with a uclass may be useful. Consider
a USB bus with several devices attached to it, each from a different (made
@@ -481,15 +467,23 @@
The bus device wants to store this address and some other information such
as the bus speed for each device.
-To achieve this, the bus device can use dev->parent_priv in each of its
-three children. This can be auto-allocated if the bus driver has a non-zero
-value for per_child_auto_alloc_size. If not, then the bus device can
-allocate the space itself before the child device is probed.
+To achieve this, the bus device can use dev->parent_platdata in each of its
+three children. This can be auto-allocated if the bus driver (or bus uclass)
+has a non-zero value for per_child_platdata_auto_alloc_size. If not, then
+the bus device or uclass can allocate the space itself before the child
+device is probed.
Also the bus driver can define the child_pre_probe() and child_post_remove()
methods to allow it to do some processing before the child is activated or
after it is deactivated.
+Similarly the bus uclass can define the child_post_bind() method to obtain
+the per-child platform data from the device tree and set it up for the child.
+The bus uclass can also provide a child_pre_probe() method. Very often it is
+the bus uclass that controls these features, since it avoids each driver
+having to do the same processing. Of course the driver can still tweak and
+override these activities.
+
Note that the information that controls this behaviour is in the bus's
driver, not the child's. In fact it is possible that child has no knowledge
that it is connected to a bus. The same child device may even be used on two
@@ -516,7 +510,8 @@
The uclass for the device can also contain data private to that uclass.
But note that each device on the bus may be a memeber of a different
uclass, and this data has nothing to do with the child data for each child
-on the bus.
+on the bus. It is the bus' uclass that controls the child with respect to
+the bus.
Driver Lifecycle
diff --git a/doc/driver-model/spi-howto.txt b/doc/driver-model/spi-howto.txt
index 719dbd5..5bc29ad 100644
--- a/doc/driver-model/spi-howto.txt
+++ b/doc/driver-model/spi-howto.txt
@@ -3,7 +3,8 @@
Here is a rough step-by-step guide. It is based around converting the
exynos SPI driver to driver model (DM) and the example code is based
-around U-Boot v2014.10-rc2 (commit be9f643).
+around U-Boot v2014.10-rc2 (commit be9f643). This has been updated for
+v2015.04.
It is quite long since it includes actual code examples.
@@ -262,8 +263,8 @@
.platdata = &platdata_spi0,
};
-You will unfortunately need to put the struct into a header file in this
-case so that your board file can use it.
+You will unfortunately need to put the struct definition into a header file
+in this case so that your board file can use it.
9. Add the device private data
@@ -592,3 +593,36 @@
You can use 'tools/patman/patman' to prepare, check and send patches for
your work. See the README for details.
+
+20. A little note about SPI uclass features:
+
+The SPI uclass keeps some information about each device 'dev' on the bus:
+
+ struct dm_spi_slave_platdata - this is device_get_parent_platdata(dev)
+ This is where the chip select number is stored, along with
+ the default bus speed and mode. It is automatically read
+ from the device tree in spi_child_post_bind(). It must not
+ be changed at run-time after being set up because platform
+ data is supposed to be immutable at run-time.
+ struct spi_slave - this is device_get_parentdata(dev)
+ Already mentioned above. It holds run-time information about
+ the device.
+
+There are also some SPI uclass methods that get called behind the scenes:
+
+ spi_post_bind() - called when a new bus is bound
+ This scans the device tree for devices on the bus, and binds
+ each one. This in turn causes spi_child_post_bind() to be
+ called for each, which reads the device tree information
+ into the parent (per-child) platform data.
+ spi_child_post_bind() - called when a new child is bound
+ As mentioned above this reads the device tree information
+ into the per-child platform data
+ spi_child_pre_probe() - called before a new child is probed
+ This sets up the mode and speed in struct spi_slave by
+ copying it from the parent's platform data for this child.
+ It also sets the 'dev' pointer, needed to permit passing
+ 'struct spi_slave' around the place without needing a
+ separate 'struct udevice' pointer.
+
+The above housekeeping makes it easier to write your SPI driver.
diff --git a/doc/uImage.FIT/source_file_format.txt b/doc/uImage.FIT/source_file_format.txt
index b47ce73..427ea49 100644
--- a/doc/uImage.FIT/source_file_format.txt
+++ b/doc/uImage.FIT/source_file_format.txt
@@ -159,17 +159,17 @@
- description : Textual description of the component sub-image
- type : Name of component sub-image type, supported types are:
"standalone", "kernel", "ramdisk", "firmware", "script", "filesystem",
- "flat_dt" and others (see uimage_type in common/images.c).
+ "flat_dt" and others (see uimage_type in common/image.c).
- data : Path to the external file which contains this node's binary data.
- compression : Compression used by included data. Supported compressions
are "gzip" and "bzip2". If no compression is used compression property
should be set to "none".
Conditionally mandatory property:
- - os : OS name, mandatory for type="kernel", valid OS names are: "openbsd",
- "netbsd", "freebsd", "4_4bsd", "linux", "svr4", "esix", "solaris", "irix",
- "sco", "dell", "ncr", "lynxos", "vxworks", "psos", "qnx", "u_boot",
- "rtems", "unity", "integrity".
+ - os : OS name, mandatory for types "kernel" and "ramdisk". Valid OS names
+ are: "openbsd", "netbsd", "freebsd", "4_4bsd", "linux", "svr4", "esix",
+ "solaris", "irix", "sco", "dell", "ncr", "lynxos", "vxworks", "psos", "qnx",
+ "u_boot", "rtems", "unity", "integrity".
- arch : Architecture name, mandatory for types: "standalone", "kernel",
"firmware", "ramdisk" and "fdt". Valid architecture names are: "alpha",
"arm", "i386", "ia64", "mips", "mips64", "ppc", "s390", "sh", "sparc",
diff --git a/doc/uImage.FIT/verified-boot.txt b/doc/uImage.FIT/verified-boot.txt
index 3c83fbc..e639e7a 100644
--- a/doc/uImage.FIT/verified-boot.txt
+++ b/doc/uImage.FIT/verified-boot.txt
@@ -64,7 +64,7 @@
It is critical that the public key be secure and cannot be tampered with.
It can be stored in read-only memory, or perhaps protected by other on-chip
-crypto provided by some modern SOCs. If the public key can ben changed, then
+crypto provided by some modern SOCs. If the public key can be changed, then
the verification is worthless.
@@ -87,7 +87,7 @@
Flattened Image Tree (FIT)
--------------------------
-The FIT format is alreay widely used in U-Boot. It is a flattened device
+The FIT format is already widely used in U-Boot. It is a flattened device
tree (FDT) in a particular format, with images contained within. FITs
include hashes to verify images, so it is relatively straightforward to
add signatures as well.
diff --git a/drivers/core/device-remove.c b/drivers/core/device-remove.c
index 8fc6b71..3a5f48d 100644
--- a/drivers/core/device-remove.c
+++ b/drivers/core/device-remove.c
@@ -88,6 +88,14 @@
if (ret)
return ret;
+ if (dev->flags & DM_FLAG_ALLOC_PDATA) {
+ free(dev->platdata);
+ dev->platdata = NULL;
+ }
+ if (dev->flags & DM_FLAG_ALLOC_PARENT_PDATA) {
+ free(dev->parent_platdata);
+ dev->parent_platdata = NULL;
+ }
ret = uclass_unbind_device(dev);
if (ret)
return ret;
@@ -111,10 +119,6 @@
free(dev->priv);
dev->priv = NULL;
}
- if (dev->flags & DM_FLAG_ALLOC_PDATA) {
- free(dev->platdata);
- dev->platdata = NULL;
- }
size = dev->uclass->uc_drv->per_device_auto_alloc_size;
if (size) {
free(dev->uclass_priv);
@@ -122,6 +126,10 @@
}
if (dev->parent) {
size = dev->parent->driver->per_child_auto_alloc_size;
+ if (!size) {
+ size = dev->parent->uclass->uc_drv->
+ per_child_auto_alloc_size;
+ }
if (size) {
free(dev->parent_priv);
dev->parent_priv = NULL;
diff --git a/drivers/core/device.c b/drivers/core/device.c
index 963b16f..b73d3b8 100644
--- a/drivers/core/device.c
+++ b/drivers/core/device.c
@@ -53,27 +53,47 @@
dev->driver = drv;
dev->uclass = uc;
- /*
- * For some devices, such as a SPI or I2C bus, the 'reg' property
- * is a reasonable indicator of the sequence number. But if there is
- * an alias, we use that in preference. In any case, this is just
- * a 'requested' sequence, and will be resolved (and ->seq updated)
- * when the device is probed.
- */
dev->seq = -1;
+ dev->req_seq = -1;
#ifdef CONFIG_OF_CONTROL
- dev->req_seq = fdtdec_get_int(gd->fdt_blob, of_offset, "reg", -1);
- if (!IS_ERR_VALUE(dev->req_seq))
- dev->req_seq &= INT_MAX;
- if (uc->uc_drv->name && of_offset != -1) {
- fdtdec_get_alias_seq(gd->fdt_blob, uc->uc_drv->name, of_offset,
- &dev->req_seq);
+ /*
+ * Some devices, such as a SPI bus, I2C bus and serial ports are
+ * numbered using aliases.
+ *
+ * This is just a 'requested' sequence, and will be
+ * resolved (and ->seq updated) when the device is probed.
+ */
+ if (uc->uc_drv->flags & DM_UC_FLAG_SEQ_ALIAS) {
+ if (uc->uc_drv->name && of_offset != -1) {
+ fdtdec_get_alias_seq(gd->fdt_blob, uc->uc_drv->name,
+ of_offset, &dev->req_seq);
+ }
}
-#else
- dev->req_seq = -1;
#endif
- if (!dev->platdata && drv->platdata_auto_alloc_size)
+ if (!dev->platdata && drv->platdata_auto_alloc_size) {
dev->flags |= DM_FLAG_ALLOC_PDATA;
+ dev->platdata = calloc(1, drv->platdata_auto_alloc_size);
+ if (!dev->platdata) {
+ ret = -ENOMEM;
+ goto fail_alloc1;
+ }
+ }
+ if (parent) {
+ int size = parent->driver->per_child_platdata_auto_alloc_size;
+
+ if (!size) {
+ size = parent->uclass->uc_drv->
+ per_child_platdata_auto_alloc_size;
+ }
+ if (size) {
+ dev->flags |= DM_FLAG_ALLOC_PARENT_PDATA;
+ dev->parent_platdata = calloc(1, size);
+ if (!dev->parent_platdata) {
+ ret = -ENOMEM;
+ goto fail_alloc2;
+ }
+ }
+ }
/* put dev into parent's successor list */
if (parent)
@@ -81,28 +101,51 @@
ret = uclass_bind_device(dev);
if (ret)
- goto fail_bind;
+ goto fail_uclass_bind;
/* if we fail to bind we remove device from successors and free it */
if (drv->bind) {
ret = drv->bind(dev);
- if (ret) {
- if (uclass_unbind_device(dev)) {
- dm_warn("Failed to unbind dev '%s' on error path\n",
- dev->name);
- }
+ if (ret)
goto fail_bind;
- }
+ }
+ if (parent && parent->driver->child_post_bind) {
+ ret = parent->driver->child_post_bind(dev);
+ if (ret)
+ goto fail_child_post_bind;
}
+
if (parent)
dm_dbg("Bound device %s to %s\n", dev->name, parent->name);
*devp = dev;
return 0;
+fail_child_post_bind:
+ if (drv->unbind && drv->unbind(dev)) {
+ dm_warn("unbind() method failed on dev '%s' on error path\n",
+ dev->name);
+ }
+
fail_bind:
+ if (uclass_unbind_device(dev)) {
+ dm_warn("Failed to unbind dev '%s' on error path\n",
+ dev->name);
+ }
+fail_uclass_bind:
list_del(&dev->sibling_node);
+ if (dev->flags & DM_FLAG_ALLOC_PARENT_PDATA) {
+ free(dev->parent_platdata);
+ dev->parent_platdata = NULL;
+ }
+fail_alloc2:
+ if (dev->flags & DM_FLAG_ALLOC_PDATA) {
+ free(dev->platdata);
+ dev->platdata = NULL;
+ }
+fail_alloc1:
free(dev);
+
return ret;
}
@@ -137,7 +180,7 @@
drv = dev->driver;
assert(drv);
- /* Allocate private data and platdata if requested */
+ /* Allocate private data if requested */
if (drv->priv_auto_alloc_size) {
dev->priv = calloc(1, drv->priv_auto_alloc_size);
if (!dev->priv) {
@@ -146,13 +189,6 @@
}
}
/* Allocate private data if requested */
- if (dev->flags & DM_FLAG_ALLOC_PDATA) {
- dev->platdata = calloc(1, drv->platdata_auto_alloc_size);
- if (!dev->platdata) {
- ret = -ENOMEM;
- goto fail;
- }
- }
size = dev->uclass->uc_drv->per_device_auto_alloc_size;
if (size) {
dev->uclass_priv = calloc(1, size);
@@ -165,6 +201,10 @@
/* Ensure all parents are probed */
if (dev->parent) {
size = dev->parent->driver->per_child_auto_alloc_size;
+ if (!size) {
+ size = dev->parent->uclass->uc_drv->
+ per_child_auto_alloc_size;
+ }
if (size) {
dev->parent_priv = calloc(1, size);
if (!dev->parent_priv) {
@@ -187,6 +227,10 @@
}
dev->seq = seq;
+ ret = uclass_pre_probe_child(dev);
+ if (ret)
+ goto fail;
+
if (dev->parent && dev->parent->driver->child_pre_probe) {
ret = dev->parent->driver->child_pre_probe(dev);
if (ret)
@@ -241,6 +285,16 @@
return dev->platdata;
}
+void *dev_get_parent_platdata(struct udevice *dev)
+{
+ if (!dev) {
+ dm_warn("%s: null device", __func__);
+ return NULL;
+ }
+
+ return dev->parent_platdata;
+}
+
void *dev_get_priv(struct udevice *dev)
{
if (!dev) {
@@ -390,3 +444,8 @@
{
return dev->of_id->data;
}
+
+enum uclass_id device_get_uclass_id(struct udevice *dev)
+{
+ return dev->uclass->uc_drv->id;
+}
diff --git a/drivers/core/root.c b/drivers/core/root.c
index 47b3acf..73e3c72 100644
--- a/drivers/core/root.c
+++ b/drivers/core/root.c
@@ -9,6 +9,7 @@
#include <common.h>
#include <errno.h>
+#include <fdtdec.h>
#include <malloc.h>
#include <libfdt.h>
#include <dm/device.h>
@@ -49,6 +50,9 @@
ret = device_bind_by_name(NULL, false, &root_info, &DM_ROOT_NON_CONST);
if (ret)
return ret;
+#ifdef CONFIG_OF_CONTROL
+ DM_ROOT_NON_CONST->of_offset = 0;
+#endif
ret = device_probe(DM_ROOT_NON_CONST);
if (ret)
return ret;
@@ -89,6 +93,10 @@
if (pre_reloc_only &&
!fdt_getprop(blob, offset, "u-boot,dm-pre-reloc", NULL))
continue;
+ if (!fdtdec_get_is_enabled(blob, offset)) {
+ dm_dbg(" - ignoring disabled device\n");
+ continue;
+ }
err = lists_bind_fdt(parent, blob, offset, NULL);
if (err && !ret)
ret = err;
diff --git a/drivers/core/uclass.c b/drivers/core/uclass.c
index 901b06e..289a5d2 100644
--- a/drivers/core/uclass.c
+++ b/drivers/core/uclass.c
@@ -319,18 +319,29 @@
int ret;
uc = dev->uclass;
-
list_add_tail(&dev->uclass_node, &uc->dev_head);
+ if (dev->parent) {
+ struct uclass_driver *uc_drv = dev->parent->uclass->uc_drv;
+
+ if (uc_drv->child_post_bind) {
+ ret = uc_drv->child_post_bind(dev);
+ if (ret)
+ goto err;
+ }
+ }
if (uc->uc_drv->post_bind) {
ret = uc->uc_drv->post_bind(dev);
- if (ret) {
- list_del(&dev->uclass_node);
- return ret;
- }
+ if (ret)
+ goto err;
}
return 0;
+err:
+ /* There is no need to undo the parent's post_bind call */
+ list_del(&dev->uclass_node);
+
+ return ret;
}
int uclass_unbind_device(struct udevice *dev)
@@ -380,6 +391,19 @@
return seq;
}
+int uclass_pre_probe_child(struct udevice *dev)
+{
+ struct uclass_driver *uc_drv;
+
+ if (!dev->parent)
+ return 0;
+ uc_drv = dev->parent->uclass->uc_drv;
+ if (uc_drv->child_pre_probe)
+ return uc_drv->child_pre_probe(dev);
+
+ return 0;
+}
+
int uclass_post_probe_device(struct udevice *dev)
{
struct uclass_driver *uc_drv = dev->uclass->uc_drv;
diff --git a/drivers/crypto/Kconfig b/drivers/crypto/Kconfig
index e69de29..bd26a2b 100644
--- a/drivers/crypto/Kconfig
+++ b/drivers/crypto/Kconfig
@@ -0,0 +1 @@
+source drivers/crypto/fsl/Kconfig
diff --git a/drivers/crypto/Makefile b/drivers/crypto/Makefile
index 7b79237..fb8c10b 100644
--- a/drivers/crypto/Makefile
+++ b/drivers/crypto/Makefile
@@ -6,4 +6,5 @@
#
obj-$(CONFIG_EXYNOS_ACE_SHA) += ace_sha.o
+obj-y += rsa_mod_exp/
obj-y += fsl/
diff --git a/drivers/crypto/fsl/Kconfig b/drivers/crypto/fsl/Kconfig
new file mode 100644
index 0000000..86b2f2f
--- /dev/null
+++ b/drivers/crypto/fsl/Kconfig
@@ -0,0 +1,6 @@
+config FSL_CAAM
+ bool "Freescale Crypto Driver Support"
+ help
+ Enables the Freescale's Cryptographic Accelerator and Assurance
+ Module (CAAM), also known as the SEC version 4 (SEC4). The driver uses
+ Job Ring as interface to communicate with CAAM.
diff --git a/drivers/crypto/fsl/Makefile b/drivers/crypto/fsl/Makefile
index 067d0a9..c0cf642 100644
--- a/drivers/crypto/fsl/Makefile
+++ b/drivers/crypto/fsl/Makefile
@@ -9,3 +9,4 @@
obj-y += sec.o
obj-$(CONFIG_FSL_CAAM) += jr.o fsl_hash.o jobdesc.o error.o
obj-$(CONFIG_CMD_BLOB) += fsl_blob.o
+obj-$(CONFIG_RSA_FREESCALE_EXP) += fsl_rsa.o
diff --git a/drivers/crypto/fsl/fsl_rsa.c b/drivers/crypto/fsl/fsl_rsa.c
new file mode 100644
index 0000000..cf1c4c1
--- /dev/null
+++ b/drivers/crypto/fsl/fsl_rsa.c
@@ -0,0 +1,60 @@
+/*
+ * (C) Copyright 2014 Freescale Semiconductor, Inc.
+ * Author: Ruchika Gupta <ruchika.gupta@freescale.com>
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+#include <config.h>
+#include <common.h>
+#include <dm.h>
+#include <asm/types.h>
+#include <malloc.h>
+#include "jobdesc.h"
+#include "desc.h"
+#include "jr.h"
+#include "rsa_caam.h"
+#include <u-boot/rsa-mod-exp.h>
+
+int fsl_mod_exp(struct udevice *dev, const uint8_t *sig, uint32_t sig_len,
+ struct key_prop *prop, uint8_t *out)
+{
+ uint32_t keylen;
+ struct pk_in_params pkin;
+ uint32_t desc[MAX_CAAM_DESCSIZE];
+ int ret;
+
+ /* Length in bytes */
+ keylen = prop->num_bits / 8;
+
+ pkin.a = sig;
+ pkin.a_siz = sig_len;
+ pkin.n = prop->modulus;
+ pkin.n_siz = keylen;
+ pkin.e = prop->public_exponent;
+ pkin.e_siz = prop->exp_len;
+
+ inline_cnstr_jobdesc_pkha_rsaexp(desc, &pkin, out, sig_len);
+
+ ret = run_descriptor_jr(desc);
+ if (ret) {
+ debug("%s: RSA failed to verify: %d\n", __func__, ret);
+ return -EFAULT;
+ }
+
+ return 0;
+}
+
+static const struct mod_exp_ops fsl_mod_exp_ops = {
+ .mod_exp = fsl_mod_exp,
+};
+
+U_BOOT_DRIVER(fsl_rsa_mod_exp) = {
+ .name = "fsl_rsa_mod_exp",
+ .id = UCLASS_MOD_EXP,
+ .ops = &fsl_mod_exp_ops,
+};
+
+U_BOOT_DEVICE(fsl_rsa) = {
+ .name = "fsl_rsa_mod_exp",
+};
diff --git a/drivers/crypto/fsl/jobdesc.c b/drivers/crypto/fsl/jobdesc.c
index 1386bae..cc0dced 100644
--- a/drivers/crypto/fsl/jobdesc.c
+++ b/drivers/crypto/fsl/jobdesc.c
@@ -11,6 +11,7 @@
#include <common.h>
#include "desc_constr.h"
#include "jobdesc.h"
+#include "rsa_caam.h"
#define KEY_BLOB_SIZE 32
#define MAC_SIZE 16
@@ -123,3 +124,30 @@
append_operation(desc, OP_TYPE_CLASS1_ALG | OP_ALG_ALGSEL_RNG |
OP_ALG_RNG4_SK);
}
+
+/* Change key size to bytes form bits in calling function*/
+void inline_cnstr_jobdesc_pkha_rsaexp(uint32_t *desc,
+ struct pk_in_params *pkin, uint8_t *out,
+ uint32_t out_siz)
+{
+ dma_addr_t dma_addr_e, dma_addr_a, dma_addr_n, dma_addr_out;
+
+ dma_addr_e = virt_to_phys((void *)pkin->e);
+ dma_addr_a = virt_to_phys((void *)pkin->a);
+ dma_addr_n = virt_to_phys((void *)pkin->n);
+ dma_addr_out = virt_to_phys((void *)out);
+
+ init_job_desc(desc, 0);
+ append_key(desc, dma_addr_e, pkin->e_siz, KEY_DEST_PKHA_E | CLASS_1);
+
+ append_fifo_load(desc, dma_addr_a,
+ pkin->a_siz, LDST_CLASS_1_CCB | FIFOLD_TYPE_PK_A);
+
+ append_fifo_load(desc, dma_addr_n,
+ pkin->n_siz, LDST_CLASS_1_CCB | FIFOLD_TYPE_PK_N);
+
+ append_operation(desc, OP_TYPE_PK | OP_ALG_PK | OP_ALG_PKMODE_MOD_EXPO);
+
+ append_fifo_store(desc, dma_addr_out, out_siz,
+ LDST_CLASS_1_CCB | FIFOST_TYPE_PKHA_B);
+}
diff --git a/drivers/crypto/fsl/jobdesc.h b/drivers/crypto/fsl/jobdesc.h
index 3cf7226..84b3edd 100644
--- a/drivers/crypto/fsl/jobdesc.h
+++ b/drivers/crypto/fsl/jobdesc.h
@@ -10,6 +10,7 @@
#include <common.h>
#include <asm/io.h>
+#include "rsa_caam.h"
#define KEY_IDNFR_SZ_BYTES 16
@@ -26,4 +27,8 @@
uint32_t out_sz);
void inline_cnstr_jobdesc_rng_instantiation(uint32_t *desc);
+
+void inline_cnstr_jobdesc_pkha_rsaexp(uint32_t *desc,
+ struct pk_in_params *pkin, uint8_t *out,
+ uint32_t out_siz);
#endif
diff --git a/drivers/crypto/fsl/rsa_caam.h b/drivers/crypto/fsl/rsa_caam.h
new file mode 100644
index 0000000..4ff87ef
--- /dev/null
+++ b/drivers/crypto/fsl/rsa_caam.h
@@ -0,0 +1,28 @@
+/*
+ * Copyright 2014 Freescale Semiconductor, Inc.
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+#ifndef __RSA_CAAM_H
+#define __RSA_CAAM_H
+
+#include <common.h>
+
+/**
+ * struct pk_in_params - holder for input to PKHA block in CAAM
+ * These parameters are required to perform Modular Exponentiation
+ * using PKHA Block in CAAM
+ */
+struct pk_in_params {
+ const uint8_t *e; /* public exponent as byte array */
+ uint32_t e_siz; /* size of e[] in number of bytes */
+ const uint8_t *n; /* modulus as byte array */
+ uint32_t n_siz; /* size of n[] in number of bytes */
+ const uint8_t *a; /* Signature as byte array */
+ uint32_t a_siz; /* size of a[] in number of bytes */
+ uint8_t *b; /* Result exp. modulus in number of bytes */
+ uint32_t b_siz; /* size of b[] in number of bytes */
+};
+
+#endif
diff --git a/drivers/crypto/rsa_mod_exp/Kconfig b/drivers/crypto/rsa_mod_exp/Kconfig
new file mode 100644
index 0000000..6dcb39a
--- /dev/null
+++ b/drivers/crypto/rsa_mod_exp/Kconfig
@@ -0,0 +1,5 @@
+config DM_MOD_EXP
+ bool "Enable Driver Model for RSA Modular Exponentiation"
+ depends on DM
+ help
+ If you want to use driver model for RSA Modular Exponentiation, say Y.
diff --git a/drivers/crypto/rsa_mod_exp/Makefile b/drivers/crypto/rsa_mod_exp/Makefile
new file mode 100644
index 0000000..915b751
--- /dev/null
+++ b/drivers/crypto/rsa_mod_exp/Makefile
@@ -0,0 +1,7 @@
+#
+# (C) Copyright 2014 Freescale Semiconductor, Inc.
+#
+# SPDX-License-Identifier: GPL-2.0+
+#
+
+obj-$(CONFIG_RSA) += mod_exp_uclass.o mod_exp_sw.o
diff --git a/drivers/crypto/rsa_mod_exp/mod_exp_sw.c b/drivers/crypto/rsa_mod_exp/mod_exp_sw.c
new file mode 100644
index 0000000..dc6c064
--- /dev/null
+++ b/drivers/crypto/rsa_mod_exp/mod_exp_sw.c
@@ -0,0 +1,39 @@
+/*
+ * (C) Copyright 2014 Freescale Semiconductor, Inc.
+ * Author: Ruchika Gupta <ruchika.gupta@freescale.com>
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+#include <config.h>
+#include <common.h>
+#include <dm.h>
+#include <u-boot/rsa-mod-exp.h>
+
+int mod_exp_sw(struct udevice *dev, const uint8_t *sig, uint32_t sig_len,
+ struct key_prop *prop, uint8_t *out)
+{
+ int ret = 0;
+
+ ret = rsa_mod_exp_sw(sig, sig_len, prop, out);
+ if (ret) {
+ debug("%s: RSA failed to verify: %d\n", __func__, ret);
+ return ret;
+ }
+
+ return 0;
+}
+
+static const struct mod_exp_ops mod_exp_ops_sw = {
+ .mod_exp = mod_exp_sw,
+};
+
+U_BOOT_DRIVER(mod_exp_sw) = {
+ .name = "mod_exp_sw",
+ .id = UCLASS_MOD_EXP,
+ .ops = &mod_exp_ops_sw,
+};
+
+U_BOOT_DEVICE(mod_exp_sw) = {
+ .name = "mod_exp_sw",
+};
diff --git a/drivers/crypto/rsa_mod_exp/mod_exp_uclass.c b/drivers/crypto/rsa_mod_exp/mod_exp_uclass.c
new file mode 100644
index 0000000..266f094
--- /dev/null
+++ b/drivers/crypto/rsa_mod_exp/mod_exp_uclass.c
@@ -0,0 +1,31 @@
+/*
+ * (C) Copyright 2014 Freescale Semiconductor, Inc
+ * Author: Ruchika Gupta <ruchika.gupta@freescale.com>
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+#include <common.h>
+#include <dm.h>
+#include <u-boot/rsa-mod-exp.h>
+#include <errno.h>
+#include <fdtdec.h>
+#include <malloc.h>
+#include <asm/io.h>
+#include <linux/list.h>
+
+int rsa_mod_exp(struct udevice *dev, const uint8_t *sig, uint32_t sig_len,
+ struct key_prop *node, uint8_t *out)
+{
+ const struct mod_exp_ops *ops = device_get_ops(dev);
+
+ if (!ops->mod_exp)
+ return -ENOSYS;
+
+ return ops->mod_exp(dev, sig, sig_len, node, out);
+}
+
+UCLASS_DRIVER(mod_exp) = {
+ .id = UCLASS_MOD_EXP,
+ .name = "rsa_mod_exp",
+};
diff --git a/drivers/demo/demo-shape.c b/drivers/demo/demo-shape.c
index 3fa9c59..d908736 100644
--- a/drivers/demo/demo-shape.c
+++ b/drivers/demo/demo-shape.c
@@ -11,6 +11,7 @@
#include <malloc.h>
#include <dm-demo.h>
#include <asm/io.h>
+#include <asm/gpio.h>
DECLARE_GLOBAL_DATA_PTR;
@@ -20,6 +21,8 @@
struct shape_data {
int num_chars; /* Number of non-space characters output so far */
+ struct gpio_desc gpio_desc[8];
+ int gpio_count;
};
/* Crazy little function to draw shapes on the console */
@@ -89,9 +92,52 @@
return 0;
}
+static int set_light(struct udevice *dev, int light)
+{
+ struct shape_data *priv = dev_get_priv(dev);
+ struct gpio_desc *desc;
+ int ret;
+ int i;
+
+ desc = priv->gpio_desc;
+ for (i = 0; i < priv->gpio_count; i++, desc++) {
+ uint mask = 1 << i;
+
+ ret = dm_gpio_set_value(desc, light & mask);
+ if (ret < 0)
+ return ret;
+ }
+
+ return 0;
+}
+
+static int get_light(struct udevice *dev)
+{
+ struct shape_data *priv = dev_get_priv(dev);
+ struct gpio_desc *desc;
+ uint value = 0;
+ int ret;
+ int i;
+
+ desc = priv->gpio_desc;
+ for (i = 0; i < priv->gpio_count; i++, desc++) {
+ uint mask = 1 << i;
+
+ ret = dm_gpio_get_value(desc);
+ if (ret < 0)
+ return ret;
+ if (ret)
+ value |= mask;
+ }
+
+ return value;
+}
+
static const struct demo_ops shape_ops = {
.hello = shape_hello,
.status = shape_status,
+ .get_light = get_light,
+ .set_light = set_light,
};
static int shape_ofdata_to_platdata(struct udevice *dev)
@@ -111,6 +157,29 @@
return 0;
}
+static int dm_shape_probe(struct udevice *dev)
+{
+ struct shape_data *priv = dev_get_priv(dev);
+ int ret;
+
+ ret = gpio_request_list_by_name(dev, "light-gpios", priv->gpio_desc,
+ ARRAY_SIZE(priv->gpio_desc),
+ GPIOD_IS_OUT | GPIOD_IS_OUT_ACTIVE);
+ if (ret < 0)
+ return ret;
+ priv->gpio_count = ret;
+ debug("%s: %d GPIOs\n", __func__, priv->gpio_count);
+
+ return 0;
+}
+
+static int dm_shape_remove(struct udevice *dev)
+{
+ struct shape_data *priv = dev_get_priv(dev);
+
+ return gpio_free_list(dev, priv->gpio_desc, priv->gpio_count);
+}
+
static const struct udevice_id demo_shape_id[] = {
{ "demo-shape", 0 },
{ },
@@ -122,6 +191,8 @@
.id = UCLASS_DEMO,
.ofdata_to_platdata = shape_ofdata_to_platdata,
.ops = &shape_ops,
+ .probe = dm_shape_probe,
+ .remove = dm_shape_remove,
.priv_auto_alloc_size = sizeof(struct shape_data),
.platdata_auto_alloc_size = sizeof(struct dm_demo_pdata),
};
diff --git a/drivers/demo/demo-uclass.c b/drivers/demo/demo-uclass.c
index f6510d6..725f068 100644
--- a/drivers/demo/demo-uclass.c
+++ b/drivers/demo/demo-uclass.c
@@ -43,6 +43,26 @@
return ops->status(dev, status);
}
+int demo_get_light(struct udevice *dev)
+{
+ const struct demo_ops *ops = device_get_ops(dev);
+
+ if (!ops->get_light)
+ return -ENOSYS;
+
+ return ops->get_light(dev);
+}
+
+int demo_set_light(struct udevice *dev, int light)
+{
+ const struct demo_ops *ops = device_get_ops(dev);
+
+ if (!ops->set_light)
+ return -ENOSYS;
+
+ return ops->set_light(dev, light);
+}
+
int demo_parse_dt(struct udevice *dev)
{
struct dm_demo_pdata *pdata = dev_get_platdata(dev);
diff --git a/drivers/gpio/gpio-uclass.c b/drivers/gpio/gpio-uclass.c
index 255700a..a69bbd2 100644
--- a/drivers/gpio/gpio-uclass.c
+++ b/drivers/gpio/gpio-uclass.c
@@ -7,20 +7,25 @@
#include <common.h>
#include <dm.h>
#include <errno.h>
+#include <fdtdec.h>
#include <malloc.h>
#include <asm/gpio.h>
#include <linux/ctype.h>
+DECLARE_GLOBAL_DATA_PTR;
+
/**
* gpio_to_device() - Convert global GPIO number to device, number
- * gpio: The numeric representation of the GPIO
*
* Convert the GPIO number to an entry in the list of GPIOs
* or GPIO blocks registered with the GPIO controller. Returns
* entry on success, NULL on error.
+ *
+ * @gpio: The numeric representation of the GPIO
+ * @desc: Returns description (desc->flags will always be 0)
+ * @return 0 if found, -ENOENT if not found
*/
-static int gpio_to_device(unsigned int gpio, struct udevice **devp,
- unsigned int *offset)
+static int gpio_to_device(unsigned int gpio, struct gpio_desc *desc)
{
struct gpio_dev_priv *uc_priv;
struct udevice *dev;
@@ -32,14 +37,15 @@
uc_priv = dev->uclass_priv;
if (gpio >= uc_priv->gpio_base &&
gpio < uc_priv->gpio_base + uc_priv->gpio_count) {
- *devp = dev;
- *offset = gpio - uc_priv->gpio_base;
+ desc->dev = dev;
+ desc->offset = gpio - uc_priv->gpio_base;
+ desc->flags = 0;
return 0;
}
}
/* No such GPIO */
- return ret ? ret : -EINVAL;
+ return ret ? ret : -ENOENT;
}
int gpio_lookup_name(const char *name, struct udevice **devp,
@@ -88,6 +94,57 @@
return 0;
}
+static int gpio_find_and_xlate(struct gpio_desc *desc,
+ struct fdtdec_phandle_args *args)
+{
+ struct dm_gpio_ops *ops = gpio_get_ops(desc->dev);
+
+ /* Use the first argument as the offset by default */
+ if (args->args_count > 0)
+ desc->offset = args->args[0];
+ else
+ desc->offset = -1;
+ desc->flags = 0;
+
+ return ops->xlate ? ops->xlate(desc->dev, desc, args) : 0;
+}
+
+static int dm_gpio_request(struct gpio_desc *desc, const char *label)
+{
+ struct udevice *dev = desc->dev;
+ struct gpio_dev_priv *uc_priv;
+ char *str;
+ int ret;
+
+ uc_priv = dev->uclass_priv;
+ if (uc_priv->name[desc->offset])
+ return -EBUSY;
+ str = strdup(label);
+ if (!str)
+ return -ENOMEM;
+ if (gpio_get_ops(dev)->request) {
+ ret = gpio_get_ops(dev)->request(dev, desc->offset, label);
+ if (ret) {
+ free(str);
+ return ret;
+ }
+ }
+ uc_priv->name[desc->offset] = str;
+
+ return 0;
+}
+
+static int dm_gpio_requestf(struct gpio_desc *desc, const char *fmt, ...)
+{
+ va_list args;
+ char buf[40];
+
+ va_start(args, fmt);
+ vscnprintf(buf, sizeof(buf), fmt, args);
+ va_end(args);
+ return dm_gpio_request(desc, buf);
+}
+
/**
* gpio_request() - [COMPAT] Request GPIO
* gpio: GPIO number
@@ -102,32 +159,14 @@
*/
int gpio_request(unsigned gpio, const char *label)
{
- struct gpio_dev_priv *uc_priv;
- unsigned int offset;
- struct udevice *dev;
- char *str;
+ struct gpio_desc desc;
int ret;
- ret = gpio_to_device(gpio, &dev, &offset);
+ ret = gpio_to_device(gpio, &desc);
if (ret)
return ret;
- uc_priv = dev->uclass_priv;
- if (uc_priv->name[offset])
- return -EBUSY;
- str = strdup(label);
- if (!str)
- return -ENOMEM;
- if (gpio_get_ops(dev)->request) {
- ret = gpio_get_ops(dev)->request(dev, offset, label);
- if (ret) {
- free(str);
- return ret;
- }
- }
- uc_priv->name[offset] = str;
-
- return 0;
+ return dm_gpio_request(&desc, label);
}
/**
@@ -151,25 +190,11 @@
return gpio_request(gpio, buf);
}
-/**
- * gpio_free() - [COMPAT] Relinquish GPIO
- * gpio: GPIO number
- *
- * This function implements the API that's compatible with current
- * GPIO API used in U-Boot. The request is forwarded to particular
- * GPIO driver. Returns 0 on success, negative value on error.
- */
-int gpio_free(unsigned gpio)
+int _dm_gpio_free(struct udevice *dev, uint offset)
{
struct gpio_dev_priv *uc_priv;
- unsigned int offset;
- struct udevice *dev;
int ret;
- ret = gpio_to_device(gpio, &dev, &offset);
- if (ret)
- return ret;
-
uc_priv = dev->uclass_priv;
if (!uc_priv->name[offset])
return -ENXIO;
@@ -185,15 +210,35 @@
return 0;
}
-static int check_reserved(struct udevice *dev, unsigned offset,
- const char *func)
+/**
+ * gpio_free() - [COMPAT] Relinquish GPIO
+ * gpio: GPIO number
+ *
+ * This function implements the API that's compatible with current
+ * GPIO API used in U-Boot. The request is forwarded to particular
+ * GPIO driver. Returns 0 on success, negative value on error.
+ */
+int gpio_free(unsigned gpio)
{
- struct gpio_dev_priv *uc_priv = dev->uclass_priv;
+ struct gpio_desc desc;
+ int ret;
+
+ ret = gpio_to_device(gpio, &desc);
+ if (ret)
+ return ret;
+
+ return _dm_gpio_free(desc.dev, desc.offset);
+}
+
+static int check_reserved(struct gpio_desc *desc, const char *func)
+{
+ struct gpio_dev_priv *uc_priv = desc->dev->uclass_priv;
- if (!uc_priv->name[offset]) {
+ if (!uc_priv->name[desc->offset]) {
printf("%s: %s: error: gpio %s%d not reserved\n",
- dev->name, func,
- uc_priv->bank_name ? uc_priv->bank_name : "", offset);
+ desc->dev->name, func,
+ uc_priv->bank_name ? uc_priv->bank_name : "",
+ desc->offset);
return -EBUSY;
}
@@ -210,16 +255,17 @@
*/
int gpio_direction_input(unsigned gpio)
{
- unsigned int offset;
- struct udevice *dev;
+ struct gpio_desc desc;
int ret;
- ret = gpio_to_device(gpio, &dev, &offset);
+ ret = gpio_to_device(gpio, &desc);
+ if (ret)
+ return ret;
+ ret = check_reserved(&desc, "dir_input");
if (ret)
return ret;
- ret = check_reserved(dev, offset, "dir_input");
- return ret ? ret : gpio_get_ops(dev)->direction_input(dev, offset);
+ return gpio_get_ops(desc.dev)->direction_input(desc.dev, desc.offset);
}
/**
@@ -233,19 +279,83 @@
*/
int gpio_direction_output(unsigned gpio, int value)
{
- unsigned int offset;
- struct udevice *dev;
+ struct gpio_desc desc;
int ret;
- ret = gpio_to_device(gpio, &dev, &offset);
+ ret = gpio_to_device(gpio, &desc);
+ if (ret)
+ return ret;
+ ret = check_reserved(&desc, "dir_output");
if (ret)
return ret;
- ret = check_reserved(dev, offset, "dir_output");
- return ret ? ret :
- gpio_get_ops(dev)->direction_output(dev, offset, value);
+ return gpio_get_ops(desc.dev)->direction_output(desc.dev,
+ desc.offset, value);
}
+int dm_gpio_get_value(struct gpio_desc *desc)
+{
+ int value;
+ int ret;
+
+ ret = check_reserved(desc, "get_value");
+ if (ret)
+ return ret;
+
+ value = gpio_get_ops(desc->dev)->get_value(desc->dev, desc->offset);
+
+ return desc->flags & GPIOD_ACTIVE_LOW ? !value : value;
+}
+
+int dm_gpio_set_value(struct gpio_desc *desc, int value)
+{
+ int ret;
+
+ ret = check_reserved(desc, "set_value");
+ if (ret)
+ return ret;
+
+ if (desc->flags & GPIOD_ACTIVE_LOW)
+ value = !value;
+ gpio_get_ops(desc->dev)->set_value(desc->dev, desc->offset, value);
+ return 0;
+}
+
+int dm_gpio_set_dir_flags(struct gpio_desc *desc, ulong flags)
+{
+ struct udevice *dev = desc->dev;
+ struct dm_gpio_ops *ops = gpio_get_ops(dev);
+ int ret;
+
+ ret = check_reserved(desc, "set_dir");
+ if (ret)
+ return ret;
+
+ if (flags & GPIOD_IS_OUT) {
+ int value = flags & GPIOD_IS_OUT_ACTIVE ? 1 : 0;
+
+ if (flags & GPIOD_ACTIVE_LOW)
+ value = !value;
+ ret = ops->direction_output(dev, desc->offset, value);
+ } else if (flags & GPIOD_IS_IN) {
+ ret = ops->direction_input(dev, desc->offset);
+ }
+ if (ret)
+ return ret;
+ /*
+ * Update desc->flags here, so that GPIO_ACTIVE_LOW is honoured in
+ * futures
+ */
+ desc->flags = flags;
+
+ return 0;
+}
+
+int dm_gpio_set_dir(struct gpio_desc *desc)
+{
+ return dm_gpio_set_dir_flags(desc, desc->flags);
+}
+
/**
* gpio_get_value() - [COMPAT] Sample GPIO pin and return it's value
* gpio: GPIO number
@@ -257,16 +367,14 @@
*/
int gpio_get_value(unsigned gpio)
{
- unsigned int offset;
- struct udevice *dev;
int ret;
- ret = gpio_to_device(gpio, &dev, &offset);
+ struct gpio_desc desc;
+
+ ret = gpio_to_device(gpio, &desc);
if (ret)
return ret;
- ret = check_reserved(dev, offset, "get_value");
-
- return ret ? ret : gpio_get_ops(dev)->get_value(dev, offset);
+ return dm_gpio_get_value(&desc);
}
/**
@@ -280,16 +388,13 @@
*/
int gpio_set_value(unsigned gpio, int value)
{
- unsigned int offset;
- struct udevice *dev;
+ struct gpio_desc desc;
int ret;
- ret = gpio_to_device(gpio, &dev, &offset);
+ ret = gpio_to_device(gpio, &desc);
if (ret)
return ret;
- ret = check_reserved(dev, offset, "set_value");
-
- return ret ? ret : gpio_get_ops(dev)->set_value(dev, offset, value);
+ return dm_gpio_set_value(&desc, value);
}
const char *gpio_get_bank_info(struct udevice *dev, int *bit_count)
@@ -409,6 +514,155 @@
return vector;
}
+static int _gpio_request_by_name_nodev(const void *blob, int node,
+ const char *list_name, int index,
+ struct gpio_desc *desc, int flags,
+ bool add_index)
+{
+ struct fdtdec_phandle_args args;
+ int ret;
+
+ desc->dev = NULL;
+ desc->offset = 0;
+ ret = fdtdec_parse_phandle_with_args(blob, node, list_name,
+ "#gpio-cells", 0, index, &args);
+ if (ret) {
+ debug("%s: fdtdec_parse_phandle_with_args failed\n", __func__);
+ goto err;
+ }
+
+ ret = uclass_get_device_by_of_offset(UCLASS_GPIO, args.node,
+ &desc->dev);
+ if (ret) {
+ debug("%s: uclass_get_device_by_of_offset failed\n", __func__);
+ goto err;
+ }
+ ret = gpio_find_and_xlate(desc, &args);
+ if (ret) {
+ debug("%s: gpio_find_and_xlate failed\n", __func__);
+ goto err;
+ }
+ ret = dm_gpio_requestf(desc, add_index ? "%s.%s%d" : "%s.%s",
+ fdt_get_name(blob, node, NULL),
+ list_name, index);
+ if (ret) {
+ debug("%s: dm_gpio_requestf failed\n", __func__);
+ goto err;
+ }
+ ret = dm_gpio_set_dir_flags(desc, flags | desc->flags);
+ if (ret) {
+ debug("%s: dm_gpio_set_dir failed\n", __func__);
+ goto err;
+ }
+
+ return 0;
+err:
+ debug("%s: Node '%s', property '%s', failed to request GPIO index %d: %d\n",
+ __func__, fdt_get_name(blob, node, NULL), list_name, index, ret);
+ return ret;
+}
+
+int gpio_request_by_name_nodev(const void *blob, int node,
+ const char *list_name, int index,
+ struct gpio_desc *desc, int flags)
+{
+ return _gpio_request_by_name_nodev(blob, node, list_name, index, desc,
+ flags, index > 0);
+}
+
+int gpio_request_by_name(struct udevice *dev, const char *list_name, int index,
+ struct gpio_desc *desc, int flags)
+{
+ /*
+ * This isn't ideal since we don't use dev->name in the debug()
+ * calls in gpio_request_by_name(), but we can do this until
+ * gpio_request_by_name_nodev() can be dropped.
+ */
+ return gpio_request_by_name_nodev(gd->fdt_blob, dev->of_offset,
+ list_name, index, desc, flags);
+}
+
+int gpio_request_list_by_name_nodev(const void *blob, int node,
+ const char *list_name,
+ struct gpio_desc *desc, int max_count,
+ int flags)
+{
+ int count;
+ int ret;
+
+ for (count = 0; ; count++) {
+ if (count >= max_count) {
+ ret = -ENOSPC;
+ goto err;
+ }
+ ret = _gpio_request_by_name_nodev(blob, node, list_name, count,
+ &desc[count], flags, true);
+ if (ret == -ENOENT)
+ break;
+ else if (ret)
+ goto err;
+ }
+
+ /* We ran out of GPIOs in the list */
+ return count;
+
+err:
+ gpio_free_list_nodev(desc, count - 1);
+
+ return ret;
+}
+
+int gpio_request_list_by_name(struct udevice *dev, const char *list_name,
+ struct gpio_desc *desc, int max_count,
+ int flags)
+{
+ /*
+ * This isn't ideal since we don't use dev->name in the debug()
+ * calls in gpio_request_by_name(), but we can do this until
+ * gpio_request_list_by_name_nodev() can be dropped.
+ */
+ return gpio_request_list_by_name_nodev(gd->fdt_blob, dev->of_offset,
+ list_name, desc, max_count,
+ flags);
+}
+
+int gpio_get_list_count(struct udevice *dev, const char *list_name)
+{
+ int ret;
+
+ ret = fdtdec_parse_phandle_with_args(gd->fdt_blob, dev->of_offset,
+ list_name, "#gpio-cells", 0, -1,
+ NULL);
+ if (ret) {
+ debug("%s: Node '%s', property '%s', GPIO count failed: %d\n",
+ __func__, dev->name, list_name, ret);
+ }
+
+ return ret;
+}
+
+int dm_gpio_free(struct udevice *dev, struct gpio_desc *desc)
+{
+ /* For now, we don't do any checking of dev */
+ return _dm_gpio_free(desc->dev, desc->offset);
+}
+
+int gpio_free_list(struct udevice *dev, struct gpio_desc *desc, int count)
+{
+ int i;
+
+ /* For now, we don't do any checking of dev */
+ for (i = 0; i < count; i++)
+ dm_gpio_free(dev, &desc[i]);
+
+ return 0;
+}
+
+int gpio_free_list_nodev(struct gpio_desc *desc, int count)
+{
+ return gpio_free_list(NULL, desc, count);
+}
+
/* We need to renumber the GPIOs when any driver is probed/removed */
static int gpio_renumber(struct udevice *removed_dev)
{
diff --git a/drivers/gpio/s5p_gpio.c b/drivers/gpio/s5p_gpio.c
index 6c41a42..0a245ba 100644
--- a/drivers/gpio/s5p_gpio.c
+++ b/drivers/gpio/s5p_gpio.c
@@ -13,6 +13,7 @@
#include <asm/io.h>
#include <asm/gpio.h>
#include <dm/device-internal.h>
+#include <dt-bindings/gpio/gpio.h>
DECLARE_GLOBAL_DATA_PTR;
@@ -275,12 +276,22 @@
return GPIOF_FUNC;
}
+static int exynos_gpio_xlate(struct udevice *dev, struct gpio_desc *desc,
+ struct fdtdec_phandle_args *args)
+{
+ desc->offset = args->args[0];
+ desc->flags = args->args[1] & GPIO_ACTIVE_LOW ? GPIOD_ACTIVE_LOW : 0;
+
+ return 0;
+}
+
static const struct dm_gpio_ops gpio_exynos_ops = {
.direction_input = exynos_gpio_direction_input,
.direction_output = exynos_gpio_direction_output,
.get_value = exynos_gpio_get_value,
.set_value = exynos_gpio_set_value,
.get_function = exynos_gpio_get_function,
+ .xlate = exynos_gpio_xlate,
};
static int gpio_exynos_probe(struct udevice *dev)
@@ -342,7 +353,7 @@
plat->bank_name, plat, -1, &dev);
if (ret)
return ret;
- dev->of_offset = parent->of_offset;
+ dev->of_offset = node;
}
return 0;
diff --git a/drivers/gpio/sandbox.c b/drivers/gpio/sandbox.c
index 53c80d5..d564c25 100644
--- a/drivers/gpio/sandbox.c
+++ b/drivers/gpio/sandbox.c
@@ -8,6 +8,7 @@
#include <fdtdec.h>
#include <malloc.h>
#include <asm/gpio.h>
+#include <dt-bindings/gpio/gpio.h>
DECLARE_GLOBAL_DATA_PTR;
@@ -130,12 +131,31 @@
return GPIOF_INPUT;
}
+static int sb_gpio_xlate(struct udevice *dev, struct gpio_desc *desc,
+ struct fdtdec_phandle_args *args)
+{
+ desc->offset = args->args[0];
+ if (args->args_count < 2)
+ return 0;
+ if (args->args[1] & GPIO_ACTIVE_LOW)
+ desc->flags |= GPIOD_ACTIVE_LOW;
+ if (args->args[1] & 2)
+ desc->flags |= GPIOD_IS_IN;
+ if (args->args[1] & 4)
+ desc->flags |= GPIOD_IS_OUT;
+ if (args->args[1] & 8)
+ desc->flags |= GPIOD_IS_OUT_ACTIVE;
+
+ return 0;
+}
+
static const struct dm_gpio_ops gpio_sandbox_ops = {
.direction_input = sb_gpio_direction_input,
.direction_output = sb_gpio_direction_output,
.get_value = sb_gpio_get_value,
.set_value = sb_gpio_set_value,
.get_function = sb_gpio_get_function,
+ .xlate = sb_gpio_xlate,
};
static int sandbox_gpio_ofdata_to_platdata(struct udevice *dev)
diff --git a/drivers/gpio/tegra_gpio.c b/drivers/gpio/tegra_gpio.c
index 88f7ef5..43928b8 100644
--- a/drivers/gpio/tegra_gpio.c
+++ b/drivers/gpio/tegra_gpio.c
@@ -21,6 +21,7 @@
#include <asm/arch/tegra.h>
#include <asm/gpio.h>
#include <dm/device-internal.h>
+#include <dt-bindings/gpio/gpio.h>
DECLARE_GLOBAL_DATA_PTR;
@@ -251,6 +252,22 @@
return GPIOF_INPUT;
}
+static int tegra_gpio_xlate(struct udevice *dev, struct gpio_desc *desc,
+ struct fdtdec_phandle_args *args)
+{
+ int gpio, port, ret;
+
+ gpio = args->args[0];
+ port = gpio / TEGRA_GPIOS_PER_PORT;
+ ret = device_get_child(dev, port, &desc->dev);
+ if (ret)
+ return ret;
+ desc->offset = gpio % TEGRA_GPIOS_PER_PORT;
+ desc->flags = args->args[1] & GPIO_ACTIVE_LOW ? GPIOD_ACTIVE_LOW : 0;
+
+ return 0;
+}
+
static const struct dm_gpio_ops gpio_tegra_ops = {
.request = tegra_gpio_request,
.direction_input = tegra_gpio_direction_input,
@@ -258,6 +275,7 @@
.get_value = tegra_gpio_get_value,
.set_value = tegra_gpio_set_value,
.get_function = tegra_gpio_get_function,
+ .xlate = tegra_gpio_xlate,
};
/**
diff --git a/drivers/i2c/Kconfig b/drivers/i2c/Kconfig
index e69de29..202ea5d 100644
--- a/drivers/i2c/Kconfig
+++ b/drivers/i2c/Kconfig
@@ -0,0 +1,22 @@
+config DM_I2C
+ bool "Enable Driver Model for I2C drivers"
+ depends on DM
+ help
+ If you want to use driver model for I2C drivers, say Y.
+ To use legacy I2C drivers, say N.
+
+config SYS_I2C_UNIPHIER
+ bool "UniPhier I2C driver"
+ depends on ARCH_UNIPHIER && DM_I2C
+ default y
+ help
+ Support for Panasonic UniPhier I2C controller driver. This I2C
+ controller is used on PH1-LD4, PH1-sLD8 or older UniPhier SoCs.
+
+config SYS_I2C_UNIPHIER_F
+ bool "UniPhier FIFO-builtin I2C driver"
+ depends on ARCH_UNIPHIER && DM_I2C
+ default y
+ help
+ Support for Panasonic UniPhier FIFO-builtin I2C controller driver.
+ This I2C controller is used on PH1-Pro4 or newer UniPhier SoCs.
diff --git a/drivers/i2c/Makefile b/drivers/i2c/Makefile
index 6f3c86c..774bc94 100644
--- a/drivers/i2c/Makefile
+++ b/drivers/i2c/Makefile
@@ -5,6 +5,7 @@
# SPDX-License-Identifier: GPL-2.0+
#
obj-$(CONFIG_DM_I2C) += i2c-uclass.o
+obj-$(CONFIG_DM_I2C_COMPAT) += i2c-uclass-compat.o
obj-$(CONFIG_SYS_I2C_ADI) += adi_i2c.o
obj-$(CONFIG_I2C_MV) += mv_i2c.o
@@ -31,4 +32,6 @@
obj-$(CONFIG_SYS_I2C_SH) += sh_i2c.o
obj-$(CONFIG_SYS_I2C_SOFT) += soft_i2c.o
obj-$(CONFIG_SYS_I2C_TEGRA) += tegra_i2c.o
+obj-$(CONFIG_SYS_I2C_UNIPHIER) += i2c-uniphier.o
+obj-$(CONFIG_SYS_I2C_UNIPHIER_F) += i2c-uniphier-f.o
obj-$(CONFIG_SYS_I2C_ZYNQ) += zynq_i2c.o
diff --git a/drivers/i2c/i2c-uclass-compat.c b/drivers/i2c/i2c-uclass-compat.c
new file mode 100644
index 0000000..223f238
--- /dev/null
+++ b/drivers/i2c/i2c-uclass-compat.c
@@ -0,0 +1,108 @@
+/*
+ * Copyright (c) 2014 Google, Inc
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+#include <common.h>
+#include <dm.h>
+#include <errno.h>
+#include <i2c.h>
+
+static int cur_busnum;
+
+static int i2c_compat_get_device(uint chip_addr, int alen,
+ struct udevice **devp)
+{
+ struct dm_i2c_chip *chip;
+ int ret;
+
+ ret = i2c_get_chip_for_busnum(cur_busnum, chip_addr, alen, devp);
+ if (ret)
+ return ret;
+ chip = dev_get_parent_platdata(*devp);
+ if (chip->offset_len != alen) {
+ printf("I2C chip %x: requested alen %d does not match chip offset_len %d\n",
+ chip_addr, alen, chip->offset_len);
+ return -EADDRNOTAVAIL;
+ }
+
+ return 0;
+}
+
+int i2c_probe(uint8_t chip_addr)
+{
+ struct udevice *bus, *dev;
+ int ret;
+
+ ret = uclass_get_device_by_seq(UCLASS_I2C, cur_busnum, &bus);
+ if (ret) {
+ debug("Cannot find I2C bus %d: err=%d\n", cur_busnum, ret);
+ return ret;
+ }
+
+ if (!bus)
+ return -ENOENT;
+
+ return dm_i2c_probe(bus, chip_addr, 0, &dev);
+}
+
+int i2c_read(uint8_t chip_addr, unsigned int addr, int alen, uint8_t *buffer,
+ int len)
+{
+ struct udevice *dev;
+ int ret;
+
+ ret = i2c_compat_get_device(chip_addr, alen, &dev);
+ if (ret)
+ return ret;
+
+ return dm_i2c_read(dev, addr, buffer, len);
+}
+
+int i2c_write(uint8_t chip_addr, unsigned int addr, int alen, uint8_t *buffer,
+ int len)
+{
+ struct udevice *dev;
+ int ret;
+
+ ret = i2c_compat_get_device(chip_addr, alen, &dev);
+ if (ret)
+ return ret;
+
+ return dm_i2c_write(dev, addr, buffer, len);
+}
+
+int i2c_get_bus_num_fdt(int node)
+{
+ struct udevice *bus;
+ int ret;
+
+ ret = uclass_get_device_by_of_offset(UCLASS_I2C, node, &bus);
+ if (ret)
+ return ret;
+
+ return bus->seq;
+}
+
+unsigned int i2c_get_bus_num(void)
+{
+ return cur_busnum;
+}
+
+int i2c_set_bus_num(unsigned int bus)
+{
+ cur_busnum = bus;
+
+ return 0;
+}
+
+void i2c_init(int speed, int slaveaddr)
+{
+ /* Nothing to do here - the init happens through driver model */
+}
+
+void board_i2c_init(const void *blob)
+{
+ /* Nothing to do here - the init happens through driver model */
+}
diff --git a/drivers/i2c/i2c-uclass.c b/drivers/i2c/i2c-uclass.c
index 005bf86..eafa457 100644
--- a/drivers/i2c/i2c-uclass.c
+++ b/drivers/i2c/i2c-uclass.c
@@ -50,7 +50,7 @@
static int i2c_read_bytewise(struct udevice *dev, uint offset,
uint8_t *buffer, int len)
{
- struct dm_i2c_chip *chip = dev_get_parentdata(dev);
+ struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
struct udevice *bus = dev_get_parent(dev);
struct dm_i2c_ops *ops = i2c_get_ops(bus);
struct i2c_msg msg[2], *ptr;
@@ -79,7 +79,7 @@
static int i2c_write_bytewise(struct udevice *dev, uint offset,
const uint8_t *buffer, int len)
{
- struct dm_i2c_chip *chip = dev_get_parentdata(dev);
+ struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
struct udevice *bus = dev_get_parent(dev);
struct dm_i2c_ops *ops = i2c_get_ops(bus);
struct i2c_msg msg[1];
@@ -100,9 +100,9 @@
return 0;
}
-int i2c_read(struct udevice *dev, uint offset, uint8_t *buffer, int len)
+int dm_i2c_read(struct udevice *dev, uint offset, uint8_t *buffer, int len)
{
- struct dm_i2c_chip *chip = dev_get_parentdata(dev);
+ struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
struct udevice *bus = dev_get_parent(dev);
struct dm_i2c_ops *ops = i2c_get_ops(bus);
struct i2c_msg msg[2], *ptr;
@@ -130,9 +130,10 @@
return ops->xfer(bus, msg, msg_count);
}
-int i2c_write(struct udevice *dev, uint offset, const uint8_t *buffer, int len)
+int dm_i2c_write(struct udevice *dev, uint offset, const uint8_t *buffer,
+ int len)
{
- struct dm_i2c_chip *chip = dev_get_parentdata(dev);
+ struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
struct udevice *bus = dev_get_parent(dev);
struct dm_i2c_ops *ops = i2c_get_ops(bus);
struct i2c_msg msg[1];
@@ -219,10 +220,10 @@
return ops->xfer(bus, msg, 1);
}
-static int i2c_bind_driver(struct udevice *bus, uint chip_addr,
+static int i2c_bind_driver(struct udevice *bus, uint chip_addr, uint offset_len,
struct udevice **devp)
{
- struct dm_i2c_chip chip;
+ struct dm_i2c_chip *chip;
char name[30], *str;
struct udevice *dev;
int ret;
@@ -235,11 +236,11 @@
goto err_bind;
/* Tell the device what we know about it */
- memset(&chip, '\0', sizeof(chip));
- chip.chip_addr = chip_addr;
- chip.offset_len = 1; /* we assume */
- ret = device_probe_child(dev, &chip);
- debug("%s: device_probe_child: ret=%d\n", __func__, ret);
+ chip = dev_get_parent_platdata(dev);
+ chip->chip_addr = chip_addr;
+ chip->offset_len = offset_len;
+ ret = device_probe(dev);
+ debug("%s: device_probe: ret=%d\n", __func__, ret);
if (ret)
goto err_probe;
@@ -247,13 +248,18 @@
return 0;
err_probe:
+ /*
+ * If the device failed to probe, unbind it. There is nothing there
+ * on the bus so we don't want to leave it lying around
+ */
device_unbind(dev);
err_bind:
free(str);
return ret;
}
-int i2c_get_chip(struct udevice *bus, uint chip_addr, struct udevice **devp)
+int i2c_get_chip(struct udevice *bus, uint chip_addr, uint offset_len,
+ struct udevice **devp)
{
struct udevice *dev;
@@ -261,15 +267,9 @@
bus->name, chip_addr);
for (device_find_first_child(bus, &dev); dev;
device_find_next_child(&dev)) {
- struct dm_i2c_chip store;
- struct dm_i2c_chip *chip = dev_get_parentdata(dev);
+ struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
int ret;
- if (!chip) {
- chip = &store;
- i2c_chip_ofdata_to_platdata(gd->fdt_blob,
- dev->of_offset, chip);
- }
if (chip->chip_addr == chip_addr) {
ret = device_probe(dev);
debug("found, ret=%d\n", ret);
@@ -280,10 +280,11 @@
}
}
debug("not found\n");
- return i2c_bind_driver(bus, chip_addr, devp);
+ return i2c_bind_driver(bus, chip_addr, offset_len, devp);
}
-int i2c_get_chip_for_busnum(int busnum, int chip_addr, struct udevice **devp)
+int i2c_get_chip_for_busnum(int busnum, int chip_addr, uint offset_len,
+ struct udevice **devp)
{
struct udevice *bus;
int ret;
@@ -293,7 +294,7 @@
debug("Cannot find I2C bus %d\n", busnum);
return ret;
}
- ret = i2c_get_chip(bus, chip_addr, devp);
+ ret = i2c_get_chip(bus, chip_addr, offset_len, devp);
if (ret) {
debug("Cannot find I2C chip %02x on bus %d\n", chip_addr,
busnum);
@@ -303,8 +304,8 @@
return 0;
}
-int i2c_probe(struct udevice *bus, uint chip_addr, uint chip_flags,
- struct udevice **devp)
+int dm_i2c_probe(struct udevice *bus, uint chip_addr, uint chip_flags,
+ struct udevice **devp)
{
int ret;
@@ -318,7 +319,7 @@
return ret;
/* The chip was found, see if we have a driver, and probe it */
- ret = i2c_get_chip(bus, chip_addr, devp);
+ ret = i2c_get_chip(bus, chip_addr, 1, devp);
debug("%s: i2c_get_chip: ret=%d\n", __func__, ret);
return ret;
@@ -364,7 +365,7 @@
int i2c_set_chip_flags(struct udevice *dev, uint flags)
{
struct udevice *bus = dev->parent;
- struct dm_i2c_chip *chip = dev_get_parentdata(dev);
+ struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
struct dm_i2c_ops *ops = i2c_get_ops(bus);
int ret;
@@ -380,7 +381,7 @@
int i2c_get_chip_flags(struct udevice *dev, uint *flagsp)
{
- struct dm_i2c_chip *chip = dev_get_parentdata(dev);
+ struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
*flagsp = chip->flags;
@@ -389,7 +390,7 @@
int i2c_set_chip_offset_len(struct udevice *dev, uint offset_len)
{
- struct dm_i2c_chip *chip = dev_get_parentdata(dev);
+ struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
if (offset_len > I2C_MAX_OFFSET_LEN)
return -EINVAL;
@@ -419,7 +420,8 @@
int i2c_chip_ofdata_to_platdata(const void *blob, int node,
struct dm_i2c_chip *chip)
{
- chip->offset_len = 1; /* default */
+ chip->offset_len = fdtdec_get_int(gd->fdt_blob, node,
+ "u-boot,i2c-offset-len", 1);
chip->flags = 0;
chip->chip_addr = fdtdec_get_int(gd->fdt_blob, node, "reg", -1);
if (chip->chip_addr == -1) {
@@ -441,18 +443,31 @@
return i2c_set_bus_speed(dev, i2c->speed_hz);
}
-int i2c_post_bind(struct udevice *dev)
+static int i2c_post_bind(struct udevice *dev)
{
/* Scan the bus for devices */
return dm_scan_fdt_node(dev, gd->fdt_blob, dev->of_offset, false);
}
+static int i2c_child_post_bind(struct udevice *dev)
+{
+ struct dm_i2c_chip *plat = dev_get_parent_platdata(dev);
+
+ if (dev->of_offset == -1)
+ return 0;
+
+ return i2c_chip_ofdata_to_platdata(gd->fdt_blob, dev->of_offset, plat);
+}
+
UCLASS_DRIVER(i2c) = {
.id = UCLASS_I2C,
.name = "i2c",
- .per_device_auto_alloc_size = sizeof(struct dm_i2c_bus),
+ .flags = DM_UC_FLAG_SEQ_ALIAS,
.post_bind = i2c_post_bind,
.post_probe = i2c_post_probe,
+ .per_device_auto_alloc_size = sizeof(struct dm_i2c_bus),
+ .per_child_platdata_auto_alloc_size = sizeof(struct dm_i2c_chip),
+ .child_post_bind = i2c_child_post_bind,
};
UCLASS_DRIVER(i2c_generic) = {
diff --git a/drivers/i2c/i2c-uniphier-f.c b/drivers/i2c/i2c-uniphier-f.c
new file mode 100644
index 0000000..6707edd
--- /dev/null
+++ b/drivers/i2c/i2c-uniphier-f.c
@@ -0,0 +1,367 @@
+/*
+ * Copyright (C) 2014 Panasonic Corporation
+ * Author: Masahiro Yamada <yamada.m@jp.panasonic.com>
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+#include <common.h>
+#include <linux/types.h>
+#include <asm/io.h>
+#include <asm/errno.h>
+#include <dm/device.h>
+#include <dm/root.h>
+#include <i2c.h>
+#include <fdtdec.h>
+
+DECLARE_GLOBAL_DATA_PTR;
+
+struct uniphier_fi2c_regs {
+ u32 cr; /* control register */
+#define I2C_CR_MST (1 << 3) /* master mode */
+#define I2C_CR_STA (1 << 2) /* start condition */
+#define I2C_CR_STO (1 << 1) /* stop condition */
+#define I2C_CR_NACK (1 << 0) /* not ACK */
+ u32 dttx; /* send FIFO (write-only) */
+#define dtrx dttx /* receive FIFO (read-only) */
+#define I2C_DTTX_CMD (1 << 8) /* send command (slave addr) */
+#define I2C_DTTX_RD (1 << 0) /* read */
+ u32 __reserved; /* no register at offset 0x08 */
+ u32 slad; /* slave address */
+ u32 cyc; /* clock cycle control */
+ u32 lctl; /* clock low period control */
+ u32 ssut; /* restart/stop setup time control */
+ u32 dsut; /* data setup time control */
+ u32 intr; /* interrupt status */
+ u32 ie; /* interrupt enable */
+ u32 ic; /* interrupt clear */
+#define I2C_INT_TE (1 << 9) /* TX FIFO empty */
+#define I2C_INT_RB (1 << 4) /* received specified bytes */
+#define I2C_INT_NA (1 << 2) /* no answer */
+#define I2C_INT_AL (1 << 1) /* arbitration lost */
+ u32 sr; /* status register */
+#define I2C_SR_DB (1 << 12) /* device busy */
+#define I2C_SR_BB (1 << 8) /* bus busy */
+#define I2C_SR_RFF (1 << 3) /* Rx FIFO full */
+#define I2C_SR_RNE (1 << 2) /* Rx FIFO not empty */
+#define I2C_SR_TNF (1 << 1) /* Tx FIFO not full */
+#define I2C_SR_TFE (1 << 0) /* Tx FIFO empty */
+ u32 __reserved2; /* no register at offset 0x30 */
+ u32 rst; /* reset control */
+#define I2C_RST_TBRST (1 << 2) /* clear Tx FIFO */
+#define I2C_RST_RBRST (1 << 1) /* clear Rx FIFO */
+#define I2C_RST_RST (1 << 0) /* forcible bus reset */
+ u32 bm; /* bus monitor */
+ u32 noise; /* noise filter control */
+ u32 tbc; /* Tx byte count setting */
+ u32 rbc; /* Rx byte count setting */
+ u32 tbcm; /* Tx byte count monitor */
+ u32 rbcm; /* Rx byte count monitor */
+ u32 brst; /* bus reset */
+#define I2C_BRST_FOEN (1 << 1) /* normal operation */
+#define I2C_BRST_RSCLO (1 << 0) /* release SCL low fixing */
+};
+
+#define FIOCLK 50000000
+
+struct uniphier_fi2c_dev {
+ struct uniphier_fi2c_regs __iomem *regs; /* register base */
+ unsigned long fioclk; /* internal operation clock */
+ unsigned long timeout; /* time out (us) */
+};
+
+static int poll_status(u32 __iomem *reg, u32 flag)
+{
+ int wait = 1000000; /* 1 sec is long enough */
+
+ while (readl(reg) & flag) {
+ if (wait-- < 0)
+ return -EREMOTEIO;
+ udelay(1);
+ }
+
+ return 0;
+}
+
+static int reset_bus(struct uniphier_fi2c_regs __iomem *regs)
+{
+ int ret;
+
+ /* bus forcible reset */
+ writel(I2C_RST_RST, ®s->rst);
+ ret = poll_status(®s->rst, I2C_RST_RST);
+ if (ret < 0)
+ debug("error: fail to reset I2C controller\n");
+
+ return ret;
+}
+
+static int check_device_busy(struct uniphier_fi2c_regs __iomem *regs)
+{
+ int ret;
+
+ ret = poll_status(®s->sr, I2C_SR_DB);
+ if (ret < 0) {
+ debug("error: device busy too long. reset...\n");
+ ret = reset_bus(regs);
+ }
+
+ return ret;
+}
+
+static int uniphier_fi2c_probe(struct udevice *dev)
+{
+ fdt_addr_t addr;
+ fdt_size_t size;
+ struct uniphier_fi2c_dev *priv = dev_get_priv(dev);
+ int ret;
+
+ addr = fdtdec_get_addr_size(gd->fdt_blob, dev->of_offset, "reg",
+ &size);
+
+ priv->regs = map_sysmem(addr, size);
+
+ if (!priv->regs)
+ return -ENOMEM;
+
+ priv->fioclk = FIOCLK;
+
+ /* bus forcible reset */
+ ret = reset_bus(priv->regs);
+ if (ret < 0)
+ return ret;
+
+ writel(I2C_BRST_FOEN | I2C_BRST_RSCLO, &priv->regs->brst);
+
+ return 0;
+}
+
+static int uniphier_fi2c_remove(struct udevice *dev)
+{
+ struct uniphier_fi2c_dev *priv = dev_get_priv(dev);
+
+ unmap_sysmem(priv->regs);
+
+ return 0;
+}
+
+static int wait_for_irq(struct uniphier_fi2c_dev *dev, u32 flags,
+ bool *stop)
+{
+ u32 irq;
+ unsigned long wait = dev->timeout;
+ int ret = -EREMOTEIO;
+
+ do {
+ udelay(1);
+ irq = readl(&dev->regs->intr);
+ } while (!(irq & flags) && wait--);
+
+ if (wait < 0) {
+ debug("error: time out\n");
+ return ret;
+ }
+
+ if (irq & I2C_INT_AL) {
+ debug("error: arbitration lost\n");
+ *stop = false;
+ return ret;
+ }
+
+ if (irq & I2C_INT_NA) {
+ debug("error: no answer\n");
+ return ret;
+ }
+
+ return 0;
+}
+
+static int issue_stop(struct uniphier_fi2c_dev *dev, int old_ret)
+{
+ int ret;
+
+ debug("stop condition\n");
+ writel(I2C_CR_MST | I2C_CR_STO, &dev->regs->cr);
+
+ ret = poll_status(&dev->regs->sr, I2C_SR_DB);
+ if (ret < 0)
+ debug("error: device busy after operation\n");
+
+ return old_ret ? old_ret : ret;
+}
+
+static int uniphier_fi2c_transmit(struct uniphier_fi2c_dev *dev, uint addr,
+ uint len, const u8 *buf, bool *stop)
+{
+ int ret;
+ const u32 irq_flags = I2C_INT_TE | I2C_INT_NA | I2C_INT_AL;
+ struct uniphier_fi2c_regs __iomem *regs = dev->regs;
+
+ debug("%s: addr = %x, len = %d\n", __func__, addr, len);
+
+ writel(I2C_DTTX_CMD | addr << 1, ®s->dttx);
+
+ writel(irq_flags, ®s->ie);
+ writel(irq_flags, ®s->ic);
+
+ debug("start condition\n");
+ writel(I2C_CR_MST | I2C_CR_STA, ®s->cr);
+
+ ret = wait_for_irq(dev, irq_flags, stop);
+ if (ret < 0)
+ goto error;
+
+ while (len--) {
+ debug("sending %x\n", *buf);
+ writel(*buf++, ®s->dttx);
+
+ writel(irq_flags, ®s->ic);
+
+ ret = wait_for_irq(dev, irq_flags, stop);
+ if (ret < 0)
+ goto error;
+ }
+
+error:
+ writel(irq_flags, ®s->ic);
+
+ if (*stop)
+ ret = issue_stop(dev, ret);
+
+ return ret;
+}
+
+static int uniphier_fi2c_receive(struct uniphier_fi2c_dev *dev, uint addr,
+ uint len, u8 *buf, bool *stop)
+{
+ int ret = 0;
+ const u32 irq_flags = I2C_INT_RB | I2C_INT_NA | I2C_INT_AL;
+ struct uniphier_fi2c_regs __iomem *regs = dev->regs;
+
+ debug("%s: addr = %x, len = %d\n", __func__, addr, len);
+
+ /*
+ * In case 'len == 0', only the slave address should be sent
+ * for probing, which is covered by the transmit function.
+ */
+ if (len == 0)
+ return uniphier_fi2c_transmit(dev, addr, len, buf, stop);
+
+ writel(I2C_DTTX_CMD | I2C_DTTX_RD | addr << 1, ®s->dttx);
+
+ writel(0, ®s->rbc);
+ writel(irq_flags, ®s->ie);
+ writel(irq_flags, ®s->ic);
+
+ debug("start condition\n");
+ writel(I2C_CR_MST | I2C_CR_STA | (len == 1 ? I2C_CR_NACK : 0),
+ ®s->cr);
+
+ while (len--) {
+ ret = wait_for_irq(dev, irq_flags, stop);
+ if (ret < 0)
+ goto error;
+
+ *buf++ = readl(®s->dtrx);
+ debug("received %x\n", *(buf - 1));
+
+ if (len == 1)
+ writel(I2C_CR_MST | I2C_CR_NACK, ®s->cr);
+
+ writel(irq_flags, ®s->ic);
+ }
+
+error:
+ writel(irq_flags, ®s->ic);
+
+ if (*stop)
+ ret = issue_stop(dev, ret);
+
+ return ret;
+}
+
+static int uniphier_fi2c_xfer(struct udevice *bus, struct i2c_msg *msg,
+ int nmsgs)
+{
+ int ret;
+ struct uniphier_fi2c_dev *dev = dev_get_priv(bus);
+ bool stop;
+
+ ret = check_device_busy(dev->regs);
+ if (ret < 0)
+ return ret;
+
+ for (; nmsgs > 0; nmsgs--, msg++) {
+ /* If next message is read, skip the stop condition */
+ stop = nmsgs > 1 && msg[1].flags & I2C_M_RD ? false : true;
+
+ if (msg->flags & I2C_M_RD)
+ ret = uniphier_fi2c_receive(dev, msg->addr, msg->len,
+ msg->buf, &stop);
+ else
+ ret = uniphier_fi2c_transmit(dev, msg->addr, msg->len,
+ msg->buf, &stop);
+
+ if (ret < 0)
+ break;
+ }
+
+ return ret;
+}
+
+static int uniphier_fi2c_set_bus_speed(struct udevice *bus, unsigned int speed)
+{
+ int ret;
+ unsigned int clk_count;
+ struct uniphier_fi2c_dev *dev = dev_get_priv(bus);
+ struct uniphier_fi2c_regs __iomem *regs = dev->regs;
+
+ /* max supported frequency is 400 kHz */
+ if (speed > 400000)
+ return -EINVAL;
+
+ ret = check_device_busy(dev->regs);
+ if (ret < 0)
+ return ret;
+
+ /* make sure the bus is idle when changing the frequency */
+ writel(I2C_BRST_RSCLO, ®s->brst);
+
+ clk_count = dev->fioclk / speed;
+
+ writel(clk_count, ®s->cyc);
+ writel(clk_count / 2, ®s->lctl);
+ writel(clk_count / 2, ®s->ssut);
+ writel(clk_count / 16, ®s->dsut);
+
+ writel(I2C_BRST_FOEN | I2C_BRST_RSCLO, ®s->brst);
+
+ /*
+ * Theoretically, each byte can be transferred in
+ * 1000000 * 9 / speed usec.
+ * This time out value is long enough.
+ */
+ dev->timeout = 100000000L / speed;
+
+ return 0;
+}
+
+static const struct dm_i2c_ops uniphier_fi2c_ops = {
+ .xfer = uniphier_fi2c_xfer,
+ .set_bus_speed = uniphier_fi2c_set_bus_speed,
+};
+
+static const struct udevice_id uniphier_fi2c_of_match[] = {
+ { .compatible = "panasonic,uniphier-fi2c" },
+ {},
+};
+
+U_BOOT_DRIVER(uniphier_fi2c) = {
+ .name = "uniphier-fi2c",
+ .id = UCLASS_I2C,
+ .of_match = uniphier_fi2c_of_match,
+ .probe = uniphier_fi2c_probe,
+ .remove = uniphier_fi2c_remove,
+ .priv_auto_alloc_size = sizeof(struct uniphier_fi2c_dev),
+ .ops = &uniphier_fi2c_ops,
+};
diff --git a/drivers/i2c/i2c-uniphier.c b/drivers/i2c/i2c-uniphier.c
new file mode 100644
index 0000000..64a9ed8
--- /dev/null
+++ b/drivers/i2c/i2c-uniphier.c
@@ -0,0 +1,227 @@
+/*
+ * Copyright (C) 2014 Panasonic Corporation
+ * Author: Masahiro Yamada <yamada.m@jp.panasonic.com>
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+#include <common.h>
+#include <linux/types.h>
+#include <asm/io.h>
+#include <asm/errno.h>
+#include <dm/device.h>
+#include <dm/root.h>
+#include <i2c.h>
+#include <fdtdec.h>
+
+DECLARE_GLOBAL_DATA_PTR;
+
+struct uniphier_i2c_regs {
+ u32 dtrm; /* data transmission */
+#define I2C_DTRM_STA (1 << 10)
+#define I2C_DTRM_STO (1 << 9)
+#define I2C_DTRM_NACK (1 << 8)
+#define I2C_DTRM_RD (1 << 0)
+ u32 drec; /* data reception */
+#define I2C_DREC_STS (1 << 12)
+#define I2C_DREC_LRB (1 << 11)
+#define I2C_DREC_LAB (1 << 9)
+ u32 myad; /* slave address */
+ u32 clk; /* clock frequency control */
+ u32 brst; /* bus reset */
+#define I2C_BRST_FOEN (1 << 1)
+#define I2C_BRST_BRST (1 << 0)
+ u32 hold; /* hold time control */
+ u32 bsts; /* bus status monitor */
+ u32 noise; /* noise filter control */
+ u32 setup; /* setup time control */
+};
+
+#define IOBUS_FREQ 100000000
+
+struct uniphier_i2c_dev {
+ struct uniphier_i2c_regs __iomem *regs; /* register base */
+ unsigned long input_clk; /* master clock (Hz) */
+ unsigned long wait_us; /* wait for every byte transfer (us) */
+};
+
+static int uniphier_i2c_probe(struct udevice *dev)
+{
+ fdt_addr_t addr;
+ fdt_size_t size;
+ struct uniphier_i2c_dev *priv = dev_get_priv(dev);
+
+ addr = fdtdec_get_addr_size(gd->fdt_blob, dev->of_offset, "reg", &size);
+
+ priv->regs = map_sysmem(addr, size);
+
+ if (!priv->regs)
+ return -ENOMEM;
+
+ priv->input_clk = IOBUS_FREQ;
+
+ /* deassert reset */
+ writel(0x3, &priv->regs->brst);
+
+ return 0;
+}
+
+static int uniphier_i2c_remove(struct udevice *dev)
+{
+ struct uniphier_i2c_dev *priv = dev_get_priv(dev);
+
+ unmap_sysmem(priv->regs);
+
+ return 0;
+}
+
+static int send_and_recv_byte(struct uniphier_i2c_dev *dev, u32 dtrm)
+{
+ writel(dtrm, &dev->regs->dtrm);
+
+ /*
+ * This controller only provides interruption to inform the completion
+ * of each byte transfer. (No status register to poll it.)
+ * Unfortunately, U-Boot does not have a good support of interrupt.
+ * Wait for a while.
+ */
+ udelay(dev->wait_us);
+
+ return readl(&dev->regs->drec);
+}
+
+static int send_byte(struct uniphier_i2c_dev *dev, u32 dtrm, bool *stop)
+{
+ int ret = 0;
+ u32 drec;
+
+ drec = send_and_recv_byte(dev, dtrm);
+
+ if (drec & I2C_DREC_LAB) {
+ debug("uniphier_i2c: bus arbitration failed\n");
+ *stop = false;
+ ret = -EREMOTEIO;
+ }
+ if (drec & I2C_DREC_LRB) {
+ debug("uniphier_i2c: slave did not return ACK\n");
+ ret = -EREMOTEIO;
+ }
+ return ret;
+}
+
+static int uniphier_i2c_transmit(struct uniphier_i2c_dev *dev, uint addr,
+ uint len, const u8 *buf, bool *stop)
+{
+ int ret;
+
+ debug("%s: addr = %x, len = %d\n", __func__, addr, len);
+
+ ret = send_byte(dev, I2C_DTRM_STA | I2C_DTRM_NACK | addr << 1, stop);
+ if (ret < 0)
+ goto fail;
+
+ while (len--) {
+ ret = send_byte(dev, I2C_DTRM_NACK | *buf++, stop);
+ if (ret < 0)
+ goto fail;
+ }
+
+fail:
+ if (*stop)
+ writel(I2C_DTRM_STO | I2C_DTRM_NACK, &dev->regs->dtrm);
+
+ return ret;
+}
+
+static int uniphier_i2c_receive(struct uniphier_i2c_dev *dev, uint addr,
+ uint len, u8 *buf, bool *stop)
+{
+ int ret;
+
+ debug("%s: addr = %x, len = %d\n", __func__, addr, len);
+
+ ret = send_byte(dev, I2C_DTRM_STA | I2C_DTRM_NACK |
+ I2C_DTRM_RD | addr << 1, stop);
+ if (ret < 0)
+ goto fail;
+
+ while (len--)
+ *buf++ = send_and_recv_byte(dev, len ? 0 : I2C_DTRM_NACK);
+
+fail:
+ if (*stop)
+ writel(I2C_DTRM_STO | I2C_DTRM_NACK, &dev->regs->dtrm);
+
+ return ret;
+}
+
+static int uniphier_i2c_xfer(struct udevice *bus, struct i2c_msg *msg,
+ int nmsgs)
+{
+ int ret = 0;
+ struct uniphier_i2c_dev *dev = dev_get_priv(bus);
+ bool stop;
+
+ for (; nmsgs > 0; nmsgs--, msg++) {
+ /* If next message is read, skip the stop condition */
+ stop = nmsgs > 1 && msg[1].flags & I2C_M_RD ? false : true;
+
+ if (msg->flags & I2C_M_RD)
+ ret = uniphier_i2c_receive(dev, msg->addr, msg->len,
+ msg->buf, &stop);
+ else
+ ret = uniphier_i2c_transmit(dev, msg->addr, msg->len,
+ msg->buf, &stop);
+
+ if (ret < 0)
+ break;
+ }
+
+ return ret;
+}
+
+static int uniphier_i2c_set_bus_speed(struct udevice *bus, unsigned int speed)
+{
+ struct uniphier_i2c_dev *priv = dev_get_priv(bus);
+
+ /* max supported frequency is 400 kHz */
+ if (speed > 400000)
+ return -EINVAL;
+
+ /* bus reset: make sure the bus is idle when change the frequency */
+ writel(0x1, &priv->regs->brst);
+
+ writel((priv->input_clk / speed / 2 << 16) | (priv->input_clk / speed),
+ &priv->regs->clk);
+
+ writel(0x3, &priv->regs->brst);
+
+ /*
+ * Theoretically, each byte can be transferred in
+ * 1000000 * 9 / speed usec. For safety, wait more than double.
+ */
+ priv->wait_us = 20000000 / speed;
+
+ return 0;
+}
+
+
+static const struct dm_i2c_ops uniphier_i2c_ops = {
+ .xfer = uniphier_i2c_xfer,
+ .set_bus_speed = uniphier_i2c_set_bus_speed,
+};
+
+static const struct udevice_id uniphier_i2c_of_match[] = {
+ { .compatible = "panasonic,uniphier-i2c" },
+ {},
+};
+
+U_BOOT_DRIVER(uniphier_i2c) = {
+ .name = "uniphier-i2c",
+ .id = UCLASS_I2C,
+ .of_match = uniphier_i2c_of_match,
+ .probe = uniphier_i2c_probe,
+ .remove = uniphier_i2c_remove,
+ .priv_auto_alloc_size = sizeof(struct uniphier_i2c_dev),
+ .ops = &uniphier_i2c_ops,
+};
diff --git a/drivers/i2c/s3c24x0_i2c.c b/drivers/i2c/s3c24x0_i2c.c
index fd328f0..0dd1abc 100644
--- a/drivers/i2c/s3c24x0_i2c.c
+++ b/drivers/i2c/s3c24x0_i2c.c
@@ -9,8 +9,9 @@
* as they seem to have the same I2C controller inside.
* The different address mapping is handled by the s3c24xx.h files below.
*/
-
#include <common.h>
+#include <errno.h>
+#include <dm.h>
#include <fdtdec.h>
#if (defined CONFIG_EXYNOS4 || defined CONFIG_EXYNOS5)
#include <asm/arch/clk.h>
@@ -121,13 +122,23 @@
#define CONFIG_MAX_I2C_NUM 1
#endif
+DECLARE_GLOBAL_DATA_PTR;
+
/*
* For SPL boot some boards need i2c before SDRAM is initialised so force
* variables to live in SRAM
*/
+#ifdef CONFIG_SYS_I2C
static struct s3c24x0_i2c_bus i2c_bus[CONFIG_MAX_I2C_NUM]
__attribute__((section(".data")));
+#endif
+
+enum exynos_i2c_type {
+ EXYNOS_I2C_STD,
+ EXYNOS_I2C_HS,
+};
+#ifdef CONFIG_SYS_I2C
/**
* Get a pointer to the given bus index
*
@@ -147,6 +158,7 @@
debug("Undefined bus: %d\n", bus_idx);
return NULL;
}
+#endif
#if !(defined CONFIG_EXYNOS4 || defined CONFIG_EXYNOS5)
static int GetI2CSDA(void)
@@ -251,6 +263,7 @@
writel(readl(&i2c->iiccon) & ~I2CCON_IRPND, &i2c->iiccon);
}
+#ifdef CONFIG_SYS_I2C
static struct s3c24x0_i2c *get_base_i2c(int bus)
{
#ifdef CONFIG_EXYNOS4
@@ -267,6 +280,7 @@
return s3c24x0_get_base_i2c();
#endif
}
+#endif
static void i2c_ch_init(struct s3c24x0_i2c *i2c, int speed, int slaveadd)
{
@@ -326,7 +340,7 @@
return 0;
}
}
- return -1;
+ return -EINVAL;
}
static void hsi2c_ch_init(struct s3c24x0_i2c_bus *i2c_bus)
@@ -398,18 +412,20 @@
hsi2c_ch_init(i2c_bus);
}
+#ifdef CONFIG_SYS_I2C
static void s3c24x0_i2c_init(struct i2c_adapter *adap, int speed, int slaveadd)
{
struct s3c24x0_i2c *i2c;
struct s3c24x0_i2c_bus *bus;
-
#if !(defined CONFIG_EXYNOS4 || defined CONFIG_EXYNOS5)
struct s3c24x0_gpio *gpio = s3c24x0_get_base_gpio();
#endif
ulong start_time = get_timer(0);
- /* By default i2c channel 0 is the current bus */
i2c = get_base_i2c(adap->hwadapnr);
+ bus = &i2c_bus[adap->hwadapnr];
+ if (!bus)
+ return;
/*
* In case the previous transfer is still going, wait to give it a
@@ -470,12 +486,13 @@
#endif
}
#endif /* #if !(defined CONFIG_EXYNOS4 || defined CONFIG_EXYNOS5) */
+
i2c_ch_init(i2c, speed, slaveadd);
- bus = &i2c_bus[adap->hwadapnr];
bus->active = true;
bus->regs = i2c;
}
+#endif /* CONFIG_SYS_I2C */
/*
* Poll the appropriate bit of the fifo status register until the interface is
@@ -698,20 +715,27 @@
return rv;
}
+#ifdef CONFIG_SYS_I2C
static unsigned int s3c24x0_i2c_set_bus_speed(struct i2c_adapter *adap,
- unsigned int speed)
+ unsigned int speed)
+#else
+static int s3c24x0_i2c_set_bus_speed(struct udevice *dev, unsigned int speed)
+#endif
{
struct s3c24x0_i2c_bus *i2c_bus;
+#ifdef CONFIG_SYS_I2C
i2c_bus = get_bus(adap->hwadapnr);
if (!i2c_bus)
- return -1;
-
+ return -EFAULT;
+#else
+ i2c_bus = dev_get_priv(dev);
+#endif
i2c_bus->clock_frequency = speed;
if (i2c_bus->is_highspeed) {
if (hsi2c_get_clk_details(i2c_bus))
- return -1;
+ return -EFAULT;
hsi2c_ch_init(i2c_bus);
} else {
i2c_ch_init(i2c_bus->regs, i2c_bus->clock_frequency,
@@ -721,17 +745,6 @@
return 0;
}
-#ifdef CONFIG_EXYNOS5
-static void exynos_i2c_init(struct i2c_adapter *adap, int speed, int slaveaddr)
-{
- /* This will override the speed selected in the fdt for that port */
- debug("i2c_init(speed=%u, slaveaddr=0x%x)\n", speed, slaveaddr);
- if (i2c_set_bus_speed(speed))
- printf("i2c_init: failed to init bus %d for speed = %d\n",
- adap->hwadapnr, speed);
-}
-#endif
-
/*
* cmd_type is 0 for write, 1 for read.
*
@@ -844,15 +857,23 @@
return result;
}
+#ifdef CONFIG_SYS_I2C
static int s3c24x0_i2c_probe(struct i2c_adapter *adap, uchar chip)
+#else
+static int s3c24x0_i2c_probe(struct udevice *dev, uint chip, uint chip_flags)
+#endif
{
struct s3c24x0_i2c_bus *i2c_bus;
uchar buf[1];
int ret;
+#ifdef CONFIG_SYS_I2C
i2c_bus = get_bus(adap->hwadapnr);
if (!i2c_bus)
- return -1;
+ return -EFAULT;
+#else
+ i2c_bus = dev_get_priv(dev);
+#endif
buf[0] = 0;
/*
@@ -871,6 +892,7 @@
return ret != I2C_OK;
}
+#ifdef CONFIG_SYS_I2C
static int s3c24x0_i2c_read(struct i2c_adapter *adap, uchar chip, uint addr,
int alen, uchar *buffer, int len)
{
@@ -878,9 +900,13 @@
uchar xaddr[4];
int ret;
+ i2c_bus = get_bus(adap->hwadapnr);
+ if (!i2c_bus)
+ return -EFAULT;
+
if (alen > 4) {
debug("I2C read: addr len %d not supported\n", alen);
- return 1;
+ return -EADDRNOTAVAIL;
}
if (alen > 0) {
@@ -906,10 +932,6 @@
chip |= ((addr >> (alen * 8)) &
CONFIG_SYS_I2C_EEPROM_ADDR_OVERFLOW);
#endif
- i2c_bus = get_bus(adap->hwadapnr);
- if (!i2c_bus)
- return -1;
-
if (i2c_bus->is_highspeed)
ret = hsi2c_read(i2c_bus->hsregs, chip, &xaddr[4 - alen],
alen, buffer, len);
@@ -921,7 +943,7 @@
if (i2c_bus->is_highspeed)
exynos5_i2c_reset(i2c_bus);
debug("I2c read failed %d\n", ret);
- return 1;
+ return -EIO;
}
return 0;
}
@@ -933,9 +955,13 @@
uchar xaddr[4];
int ret;
+ i2c_bus = get_bus(adap->hwadapnr);
+ if (!i2c_bus)
+ return -EFAULT;
+
if (alen > 4) {
debug("I2C write: addr len %d not supported\n", alen);
- return 1;
+ return -EINVAL;
}
if (alen > 0) {
@@ -960,10 +986,6 @@
chip |= ((addr >> (alen * 8)) &
CONFIG_SYS_I2C_EEPROM_ADDR_OVERFLOW);
#endif
- i2c_bus = get_bus(adap->hwadapnr);
- if (!i2c_bus)
- return -1;
-
if (i2c_bus->is_highspeed)
ret = hsi2c_write(i2c_bus->hsregs, chip, &xaddr[4 - alen],
alen, buffer, len, true);
@@ -985,7 +1007,7 @@
int is_highspeed)
{
struct s3c24x0_i2c_bus *bus;
- int i;
+ int i, flags;
for (i = 0; i < count; i++) {
int node = node_list[i];
@@ -997,12 +1019,15 @@
bus->active = true;
bus->is_highspeed = is_highspeed;
- if (is_highspeed)
+ if (is_highspeed) {
+ flags = PINMUX_FLAG_HS_MODE;
bus->hsregs = (struct exynos5_hsi2c *)
fdtdec_get_addr(blob, node, "reg");
- else
+ } else {
+ flags = 0;
bus->regs = (struct s3c24x0_i2c *)
fdtdec_get_addr(blob, node, "reg");
+ }
bus->id = pinmux_decode_periph_id(blob, node);
bus->clock_frequency = fdtdec_get_int(blob, node,
@@ -1010,7 +1035,7 @@
CONFIG_SYS_I2C_S3C24X0_SPEED);
bus->node = node;
bus->bus_num = i;
- exynos_pinmux_config(bus->id, 0);
+ exynos_pinmux_config(PERIPH_ID_I2C0 + bus->id, flags);
/* Mark position as used */
node_list[i] = -1;
@@ -1033,7 +1058,6 @@
COMPAT_SAMSUNG_EXYNOS5_I2C, node_list,
CONFIG_MAX_I2C_NUM);
process_nodes(blob, node_list, count, 1);
-
}
int i2c_get_bus_num_fdt(int node)
@@ -1046,7 +1070,7 @@
}
debug("%s: Can't find any matched I2C bus\n", __func__);
- return -1;
+ return -EINVAL;
}
int i2c_reset_port_fdt(const void *blob, int node)
@@ -1057,18 +1081,18 @@
bus = i2c_get_bus_num_fdt(node);
if (bus < 0) {
debug("could not get bus for node %d\n", node);
- return -1;
+ return bus;
}
i2c_bus = get_bus(bus);
if (!i2c_bus) {
- debug("get_bus() failed for node node %d\n", node);
- return -1;
+ debug("get_bus() failed for node %d\n", node);
+ return -EFAULT;
}
if (i2c_bus->is_highspeed) {
if (hsi2c_get_clk_details(i2c_bus))
- return -1;
+ return -EINVAL;
hsi2c_ch_init(i2c_bus);
} else {
i2c_ch_init(i2c_bus->regs, i2c_bus->clock_frequency,
@@ -1077,7 +1101,17 @@
return 0;
}
-#endif
+#endif /* CONFIG_OF_CONTROL */
+
+#ifdef CONFIG_EXYNOS5
+static void exynos_i2c_init(struct i2c_adapter *adap, int speed, int slaveaddr)
+{
+ /* This will override the speed selected in the fdt for that port */
+ debug("i2c_init(speed=%u, slaveaddr=0x%x)\n", speed, slaveaddr);
+ if (i2c_set_bus_speed(speed))
+ error("i2c_init: failed to init bus for speed = %d", speed);
+}
+#endif /* CONFIG_EXYNOS5 */
/*
* Register s3c24x0 i2c adapters
@@ -1247,3 +1281,120 @@
CONFIG_SYS_I2C_S3C24X0_SPEED,
CONFIG_SYS_I2C_S3C24X0_SLAVE, 0)
#endif
+#endif /* CONFIG_SYS_I2C */
+
+#ifdef CONFIG_DM_I2C
+static int i2c_write_data(struct s3c24x0_i2c_bus *i2c_bus, uchar chip,
+ uchar *buffer, int len, bool end_with_repeated_start)
+{
+ int ret;
+
+ if (i2c_bus->is_highspeed) {
+ ret = hsi2c_write(i2c_bus->hsregs, chip, 0, 0,
+ buffer, len, true);
+ if (ret)
+ exynos5_i2c_reset(i2c_bus);
+ } else {
+ ret = i2c_transfer(i2c_bus->regs, I2C_WRITE,
+ chip << 1, 0, 0, buffer, len);
+ }
+
+ return ret != I2C_OK;
+}
+
+static int i2c_read_data(struct s3c24x0_i2c_bus *i2c_bus, uchar chip,
+ uchar *buffer, int len)
+{
+ int ret;
+
+ if (i2c_bus->is_highspeed) {
+ ret = hsi2c_read(i2c_bus->hsregs, chip, 0, 0, buffer, len);
+ if (ret)
+ exynos5_i2c_reset(i2c_bus);
+ } else {
+ ret = i2c_transfer(i2c_bus->regs, I2C_READ,
+ chip << 1, 0, 0, buffer, len);
+ }
+
+ return ret != I2C_OK;
+}
+
+static int s3c24x0_i2c_xfer(struct udevice *dev, struct i2c_msg *msg,
+ int nmsgs)
+{
+ struct s3c24x0_i2c_bus *i2c_bus = dev_get_priv(dev);
+ int ret;
+
+ for (; nmsgs > 0; nmsgs--, msg++) {
+ bool next_is_read = nmsgs > 1 && (msg[1].flags & I2C_M_RD);
+
+ if (msg->flags & I2C_M_RD) {
+ ret = i2c_read_data(i2c_bus, msg->addr, msg->buf,
+ msg->len);
+ } else {
+ ret = i2c_write_data(i2c_bus, msg->addr, msg->buf,
+ msg->len, next_is_read);
+ }
+ if (ret)
+ return -EREMOTEIO;
+ }
+
+ return 0;
+}
+
+static int s3c_i2c_ofdata_to_platdata(struct udevice *dev)
+{
+ const void *blob = gd->fdt_blob;
+ struct s3c24x0_i2c_bus *i2c_bus = dev_get_priv(dev);
+ int node, flags;
+
+ i2c_bus->is_highspeed = dev->of_id->data;
+ node = dev->of_offset;
+
+ if (i2c_bus->is_highspeed) {
+ flags = PINMUX_FLAG_HS_MODE;
+ i2c_bus->hsregs = (struct exynos5_hsi2c *)
+ fdtdec_get_addr(blob, node, "reg");
+ } else {
+ flags = 0;
+ i2c_bus->regs = (struct s3c24x0_i2c *)
+ fdtdec_get_addr(blob, node, "reg");
+ }
+
+ i2c_bus->id = pinmux_decode_periph_id(blob, node);
+
+ i2c_bus->clock_frequency = fdtdec_get_int(blob, node,
+ "clock-frequency",
+ CONFIG_SYS_I2C_S3C24X0_SPEED);
+ i2c_bus->node = node;
+ i2c_bus->bus_num = dev->seq;
+
+ exynos_pinmux_config(i2c_bus->id, flags);
+
+ i2c_bus->active = true;
+
+ return 0;
+}
+
+static const struct dm_i2c_ops s3c_i2c_ops = {
+ .xfer = s3c24x0_i2c_xfer,
+ .probe_chip = s3c24x0_i2c_probe,
+ .set_bus_speed = s3c24x0_i2c_set_bus_speed,
+};
+
+static const struct udevice_id s3c_i2c_ids[] = {
+ { .compatible = "samsung,s3c2440-i2c", .data = EXYNOS_I2C_STD },
+ { .compatible = "samsung,exynos5-hsi2c", .data = EXYNOS_I2C_HS },
+ { }
+};
+
+U_BOOT_DRIVER(i2c_s3c) = {
+ .name = "i2c_s3c",
+ .id = UCLASS_I2C,
+ .of_match = s3c_i2c_ids,
+ .ofdata_to_platdata = s3c_i2c_ofdata_to_platdata,
+ .per_child_auto_alloc_size = sizeof(struct dm_i2c_chip),
+ .priv_auto_alloc_size = sizeof(struct s3c24x0_i2c_bus),
+ .ops = &s3c_i2c_ops,
+};
+#endif /* CONFIG_DM_I2C */
diff --git a/drivers/i2c/sandbox_i2c.c b/drivers/i2c/sandbox_i2c.c
index f0e9f51..a943aa6 100644
--- a/drivers/i2c/sandbox_i2c.c
+++ b/drivers/i2c/sandbox_i2c.c
@@ -25,24 +25,24 @@
static int get_emul(struct udevice *dev, struct udevice **devp,
struct dm_i2c_ops **opsp)
{
- struct dm_i2c_chip *priv;
+ struct dm_i2c_chip *plat;
int ret;
*devp = NULL;
*opsp = NULL;
- priv = dev_get_parentdata(dev);
- if (!priv->emul) {
+ plat = dev_get_parent_platdata(dev);
+ if (!plat->emul) {
ret = dm_scan_fdt_node(dev, gd->fdt_blob, dev->of_offset,
false);
if (ret)
return ret;
- ret = device_get_child(dev, 0, &priv->emul);
+ ret = device_get_child(dev, 0, &plat->emul);
if (ret)
return ret;
}
- *devp = priv->emul;
- *opsp = i2c_get_ops(priv->emul);
+ *devp = plat->emul;
+ *opsp = i2c_get_ops(plat->emul);
return 0;
}
@@ -60,7 +60,7 @@
if (msg->addr == SANDBOX_I2C_TEST_ADDR)
return 0;
- ret = i2c_get_chip(bus, msg->addr, &dev);
+ ret = i2c_get_chip(bus, msg->addr, 1, &dev);
if (ret)
return ret;
@@ -82,20 +82,6 @@
.xfer = sandbox_i2c_xfer,
};
-static int sandbox_i2c_child_pre_probe(struct udevice *dev)
-{
- struct dm_i2c_chip *i2c_chip = dev_get_parentdata(dev);
-
- /* Ignore our test address */
- if (i2c_chip->chip_addr == SANDBOX_I2C_TEST_ADDR)
- return 0;
- if (dev->of_offset == -1)
- return 0;
-
- return i2c_chip_ofdata_to_platdata(gd->fdt_blob, dev->of_offset,
- i2c_chip);
-}
-
static const struct udevice_id sandbox_i2c_ids[] = {
{ .compatible = "sandbox,i2c" },
{ }
@@ -105,7 +91,5 @@
.name = "i2c_sandbox",
.id = UCLASS_I2C,
.of_match = sandbox_i2c_ids,
- .per_child_auto_alloc_size = sizeof(struct dm_i2c_chip),
- .child_pre_probe = sandbox_i2c_child_pre_probe,
.ops = &sandbox_i2c_ops,
};
diff --git a/drivers/i2c/tegra_i2c.c b/drivers/i2c/tegra_i2c.c
index 87290c3..f414287 100644
--- a/drivers/i2c/tegra_i2c.c
+++ b/drivers/i2c/tegra_i2c.c
@@ -484,21 +484,6 @@
.set_bus_speed = tegra_i2c_set_bus_speed,
};
-static int tegra_i2c_child_pre_probe(struct udevice *dev)
-{
- struct dm_i2c_chip *i2c_chip = dev_get_parentdata(dev);
-
- if (dev->of_offset == -1)
- return 0;
- return i2c_chip_ofdata_to_platdata(gd->fdt_blob, dev->of_offset,
- i2c_chip);
-}
-
-static int tegra_i2c_ofdata_to_platdata(struct udevice *dev)
-{
- return 0;
-}
-
static const struct udevice_id tegra_i2c_ids[] = {
{ .compatible = "nvidia,tegra114-i2c", .data = TYPE_114 },
{ .compatible = "nvidia,tegra20-i2c", .data = TYPE_STD },
@@ -510,10 +495,7 @@
.name = "i2c_tegra",
.id = UCLASS_I2C,
.of_match = tegra_i2c_ids,
- .ofdata_to_platdata = tegra_i2c_ofdata_to_platdata,
.probe = tegra_i2c_probe,
- .per_child_auto_alloc_size = sizeof(struct dm_i2c_chip),
- .child_pre_probe = tegra_i2c_child_pre_probe,
.priv_auto_alloc_size = sizeof(struct i2c_bus),
.ops = &tegra_i2c_ops,
};
diff --git a/drivers/misc/cros_ec.c b/drivers/misc/cros_ec.c
index 9b4effb..5846e76 100644
--- a/drivers/misc/cros_ec.c
+++ b/drivers/misc/cros_ec.c
@@ -154,7 +154,9 @@
* @param dev CROS-EC device
* @param dinp Returns pointer to response data
* @param din_len Maximum size of response in bytes
- * @return number of bytes of response data, or <0 if error
+ * @return number of bytes of response data, or <0 if error. Note that error
+ * codes can be from errno.h or -ve EC_RES_INVALID_CHECKSUM values (and they
+ * overlap!)
*/
static int handle_proto3_response(struct cros_ec_dev *dev,
uint8_t **dinp, int din_len)
@@ -228,7 +230,7 @@
#ifdef CONFIG_DM_CROS_EC
ops = dm_cros_ec_get_ops(dev->dev);
- rv = ops->packet(dev->dev, out_bytes, in_bytes);
+ rv = ops->packet ? ops->packet(dev->dev, out_bytes, in_bytes) : -ENOSYS;
#else
switch (dev->interface) {
#ifdef CONFIG_CROS_EC_SPI
@@ -320,7 +322,7 @@
* If not NULL, it will be updated to point to the data
* and will always be double word aligned (64-bits)
* @param din_len Maximum size of response in bytes
- * @return number of bytes in response, or -1 on error
+ * @return number of bytes in response, or -ve on error
*/
static int ec_command_inptr(struct cros_ec_dev *dev, uint8_t cmd,
int cmd_version, const void *dout, int dout_len, uint8_t **dinp,
@@ -387,7 +389,7 @@
* It not NULL, it is a place for ec_command() to copy the
* data to.
* @param din_len Maximum size of response in bytes
- * @return number of bytes in response, or -1 on error
+ * @return number of bytes in response, or -ve on error
*/
static int ec_command(struct cros_ec_dev *dev, uint8_t cmd, int cmd_version,
const void *dout, int dout_len,
@@ -606,10 +608,10 @@
int cros_ec_interrupt_pending(struct cros_ec_dev *dev)
{
/* no interrupt support : always poll */
- if (!fdt_gpio_isvalid(&dev->ec_int))
+ if (!dm_gpio_is_valid(&dev->ec_int))
return -ENOENT;
- return !gpio_get_value(dev->ec_int.gpio);
+ return dm_gpio_get_value(&dev->ec_int);
}
int cros_ec_info(struct cros_ec_dev *dev, struct ec_response_mkbp_info *info)
@@ -1072,7 +1074,8 @@
return -1;
}
- fdtdec_decode_gpio(blob, node, "ec-interrupt", &dev->ec_int);
+ gpio_request_by_name_nodev(blob, node, "ec-interrupt", 0, &dev->ec_int,
+ GPIOD_IS_IN);
dev->optimise_flash_write = fdtdec_get_bool(blob, node,
"optimise-flash-write");
*devp = dev;
@@ -1090,17 +1093,11 @@
char id[MSG_BYTES];
cdev->dev = dev;
- fdtdec_decode_gpio(blob, node, "ec-interrupt", &cdev->ec_int);
+ gpio_request_by_name(dev, "ec-interrupt", 0, &cdev->ec_int,
+ GPIOD_IS_IN);
cdev->optimise_flash_write = fdtdec_get_bool(blob, node,
"optimise-flash-write");
- /* we will poll the EC interrupt line */
- fdtdec_setup_gpio(&cdev->ec_int);
- if (fdt_gpio_isvalid(&cdev->ec_int)) {
- gpio_request(cdev->ec_int.gpio, "cros-ec-irq");
- gpio_direction_input(cdev->ec_int.gpio);
- }
-
if (cros_ec_check_version(cdev)) {
debug("%s: Could not detect CROS-EC version\n", __func__);
return -CROS_EC_ERR_CHECK_VERSION;
@@ -1184,13 +1181,6 @@
}
#endif
- /* we will poll the EC interrupt line */
- fdtdec_setup_gpio(&dev->ec_int);
- if (fdt_gpio_isvalid(&dev->ec_int)) {
- gpio_request(dev->ec_int.gpio, "cros-ec-irq");
- gpio_direction_input(dev->ec_int.gpio);
- }
-
if (cros_ec_check_version(dev)) {
debug("%s: Could not detect CROS-EC version\n", __func__);
return -CROS_EC_ERR_CHECK_VERSION;
diff --git a/drivers/misc/cros_ec_i2c.c b/drivers/misc/cros_ec_i2c.c
index 513cdb1..f9bc975 100644
--- a/drivers/misc/cros_ec_i2c.c
+++ b/drivers/misc/cros_ec_i2c.c
@@ -14,6 +14,7 @@
*/
#include <common.h>
+#include <dm.h>
#include <i2c.h>
#include <cros_ec.h>
@@ -23,11 +24,11 @@
#define debug_trace(fmt, b...)
#endif
-int cros_ec_i2c_command(struct cros_ec_dev *dev, uint8_t cmd, int cmd_version,
- const uint8_t *dout, int dout_len,
- uint8_t **dinp, int din_len)
+static int cros_ec_i2c_command(struct udevice *udev, uint8_t cmd,
+ int cmd_version, const uint8_t *dout,
+ int dout_len, uint8_t **dinp, int din_len)
{
- int old_bus = 0;
+ struct cros_ec_dev *dev = udev->uclass_priv;
/* version8, cmd8, arglen8, out8[dout_len], csum8 */
int out_bytes = dout_len + 4;
/* response8, arglen8, in8[din_len], checksum8 */
@@ -37,8 +38,6 @@
uint8_t *in_ptr;
int len, csum, ret;
- old_bus = i2c_get_bus_num();
-
/*
* Sanity-check I/O sizes given transaction overhead in internal
* buffers.
@@ -86,36 +85,24 @@
*ptr++ = (uint8_t)
cros_ec_calc_checksum(dev->dout, dout_len + 3);
- /* Set to the proper i2c bus */
- if (i2c_set_bus_num(dev->bus_num)) {
- debug("%s: Cannot change to I2C bus %d\n", __func__,
- dev->bus_num);
- return -1;
- }
-
/* Send output data */
cros_ec_dump_data("out", -1, dev->dout, out_bytes);
- ret = i2c_write(dev->addr, 0, 0, dev->dout, out_bytes);
+ ret = dm_i2c_write(udev, 0, dev->dout, out_bytes);
if (ret) {
- debug("%s: Cannot complete I2C write to 0x%x\n",
- __func__, dev->addr);
+ debug("%s: Cannot complete I2C write to %s\n", __func__,
+ udev->name);
ret = -1;
}
if (!ret) {
- ret = i2c_read(dev->addr, 0, 0, in_ptr, in_bytes);
+ ret = dm_i2c_read(udev, 0, in_ptr, in_bytes);
if (ret) {
- debug("%s: Cannot complete I2C read from 0x%x\n",
- __func__, dev->addr);
+ debug("%s: Cannot complete I2C read from %s\n",
+ __func__, udev->name);
ret = -1;
}
}
- /* Return to original bus number */
- i2c_set_bus_num(old_bus);
- if (ret)
- return ret;
-
if (*in_ptr != EC_RES_SUCCESS) {
debug("%s: Received bad result code %d\n", __func__, *in_ptr);
return -(int)*in_ptr;
@@ -142,35 +129,24 @@
return din_len;
}
-int cros_ec_i2c_decode_fdt(struct cros_ec_dev *dev, const void *blob)
+static int cros_ec_probe(struct udevice *dev)
{
- /* Decode interface-specific FDT params */
- dev->max_frequency = fdtdec_get_int(blob, dev->node,
- "i2c-max-frequency", 100000);
- dev->bus_num = i2c_get_bus_num_fdt(dev->parent_node);
- if (dev->bus_num == -1) {
- debug("%s: Failed to read bus number\n", __func__);
- return -1;
- }
- dev->addr = fdtdec_get_int(blob, dev->node, "reg", -1);
- if (dev->addr == -1) {
- debug("%s: Failed to read device address\n", __func__);
- return -1;
- }
-
- return 0;
+ return cros_ec_register(dev);
}
-/**
- * Initialize I2C protocol.
- *
- * @param dev CROS_EC device
- * @param blob Device tree blob
- * @return 0 if ok, -1 on error
- */
-int cros_ec_i2c_init(struct cros_ec_dev *dev, const void *blob)
-{
- i2c_init(dev->max_frequency, dev->addr);
+static struct dm_cros_ec_ops cros_ec_ops = {
+ .command = cros_ec_i2c_command,
+};
- return 0;
-}
+static const struct udevice_id cros_ec_ids[] = {
+ { .compatible = "google,cros-ec" },
+ { }
+};
+
+U_BOOT_DRIVER(cros_ec_i2c) = {
+ .name = "cros_ec",
+ .id = UCLASS_CROS_EC,
+ .of_match = cros_ec_ids,
+ .probe = cros_ec_probe,
+ .ops = &cros_ec_ops,
+};
diff --git a/drivers/misc/cros_ec_spi.c b/drivers/misc/cros_ec_spi.c
index e6dba29..9359c56 100644
--- a/drivers/misc/cros_ec_spi.c
+++ b/drivers/misc/cros_ec_spi.c
@@ -21,14 +21,9 @@
DECLARE_GLOBAL_DATA_PTR;
-#ifdef CONFIG_DM_CROS_EC
int cros_ec_spi_packet(struct udevice *udev, int out_bytes, int in_bytes)
{
struct cros_ec_dev *dev = udev->uclass_priv;
-#else
-int cros_ec_spi_packet(struct cros_ec_dev *dev, int out_bytes, int in_bytes)
-{
-#endif
struct spi_slave *slave = dev_get_parentdata(dev->dev);
int rv;
@@ -67,18 +62,11 @@
* @param din_len Maximum size of response in bytes
* @return number of bytes in response, or -1 on error
*/
-#ifdef CONFIG_DM_CROS_EC
int cros_ec_spi_command(struct udevice *udev, uint8_t cmd, int cmd_version,
const uint8_t *dout, int dout_len,
uint8_t **dinp, int din_len)
{
struct cros_ec_dev *dev = udev->uclass_priv;
-#else
-int cros_ec_spi_command(struct cros_ec_dev *dev, uint8_t cmd, int cmd_version,
- const uint8_t *dout, int dout_len,
- uint8_t **dinp, int din_len)
-{
-#endif
struct spi_slave *slave = dev_get_parentdata(dev->dev);
int in_bytes = din_len + 4; /* status, length, checksum, trailer */
uint8_t *out;
@@ -166,65 +154,12 @@
return len;
}
-#ifndef CONFIG_DM_CROS_EC
-int cros_ec_spi_decode_fdt(struct cros_ec_dev *dev, const void *blob)
+static int cros_ec_probe(struct udevice *dev)
{
- /* Decode interface-specific FDT params */
- dev->max_frequency = fdtdec_get_int(blob, dev->node,
- "spi-max-frequency", 500000);
- dev->cs = fdtdec_get_int(blob, dev->node, "reg", 0);
-
- return 0;
-}
-
-/**
- * Initialize SPI protocol.
- *
- * @param dev CROS_EC device
- * @param blob Device tree blob
- * @return 0 if ok, -1 on error
- */
-int cros_ec_spi_init(struct cros_ec_dev *dev, const void *blob)
-{
- int ret;
-
- ret = spi_setup_slave_fdt(blob, dev->node, dev->parent_node,
- &slave);
- if (ret) {
- debug("%s: Could not setup SPI slave\n", __func__);
- return ret;
- }
-
- return 0;
-}
-#endif
-
-#ifdef CONFIG_DM_CROS_EC
-int cros_ec_probe(struct udevice *dev)
-{
- struct spi_slave *slave = dev_get_parentdata(dev);
- int ret;
-
- /*
- * TODO(sjg@chromium.org)
- *
- * This is really horrible at present. It is an artifact of removing
- * the child_pre_probe() method for SPI. Everything here could go in
- * an automatic function, except that spi_get_bus_and_cs() wants to
- * set it up manually and call device_probe_child().
- *
- * The solution may be to re-enable the child_pre_probe() method for
- * SPI and have it do nothing if the child is already passed in via
- * device_probe_child().
- */
- slave->dev = dev;
- ret = spi_ofdata_to_platdata(gd->fdt_blob, dev->of_offset, slave);
- if (ret)
- return ret;
return cros_ec_register(dev);
}
-struct dm_cros_ec_ops cros_ec_ops = {
+static struct dm_cros_ec_ops cros_ec_ops = {
.packet = cros_ec_spi_packet,
.command = cros_ec_spi_command,
};
@@ -241,4 +176,3 @@
.probe = cros_ec_probe,
.ops = &cros_ec_ops,
};
-#endif
diff --git a/drivers/mmc/s5p_sdhci.c b/drivers/mmc/s5p_sdhci.c
index a5d3487..3899372 100644
--- a/drivers/mmc/s5p_sdhci.c
+++ b/drivers/mmc/s5p_sdhci.c
@@ -102,17 +102,14 @@
static int do_sdhci_init(struct sdhci_host *host)
{
- char str[20];
int dev_id, flag;
int err = 0;
flag = host->bus_width == 8 ? PINMUX_FLAG_8BIT_MODE : PINMUX_FLAG_NONE;
dev_id = host->index + PERIPH_ID_SDMMC0;
- if (fdt_gpio_isvalid(&host->pwr_gpio)) {
- sprintf(str, "sdhci%d_power", host->index & 0xf);
- gpio_request(host->pwr_gpio.gpio, str);
- gpio_direction_output(host->pwr_gpio.gpio, 1);
+ if (dm_gpio_is_valid(&host->pwr_gpio)) {
+ dm_gpio_set_value(&host->pwr_gpio, 1);
err = exynos_pinmux_config(dev_id, flag);
if (err) {
debug("MMC not configured\n");
@@ -120,11 +117,8 @@
}
}
- if (fdt_gpio_isvalid(&host->cd_gpio)) {
- sprintf(str, "sdhci%d_cd", host->index & 0xf);
- gpio_request(host->cd_gpio.gpio, str);
- gpio_direction_input(host->cd_gpio.gpio);
- if (gpio_get_value(host->cd_gpio.gpio))
+ if (dm_gpio_is_valid(&host->cd_gpio)) {
+ if (dm_gpio_get_value(&host->cd_gpio))
return -ENODEV;
err = exynos_pinmux_config(dev_id, flag);
@@ -166,8 +160,10 @@
}
host->ioaddr = (void *)base;
- fdtdec_decode_gpio(blob, node, "pwr-gpios", &host->pwr_gpio);
- fdtdec_decode_gpio(blob, node, "cd-gpios", &host->cd_gpio);
+ gpio_request_by_name_nodev(blob, node, "pwr-gpios", 0, &host->pwr_gpio,
+ GPIOD_IS_OUT);
+ gpio_request_by_name_nodev(blob, node, "cd-gpios", 0, &host->cd_gpio,
+ GPIOD_IS_IN);
return 0;
}
diff --git a/drivers/mmc/sunxi_mmc.c b/drivers/mmc/sunxi_mmc.c
index 5104795..ebfec7c 100644
--- a/drivers/mmc/sunxi_mmc.c
+++ b/drivers/mmc/sunxi_mmc.c
@@ -215,7 +215,7 @@
return 0;
}
-static void mmc_set_ios(struct mmc *mmc)
+static void sunxi_mmc_set_ios(struct mmc *mmc)
{
struct sunxi_mmc_host *mmchost = mmc->priv;
@@ -237,7 +237,7 @@
writel(0x0, &mmchost->reg->width);
}
-static int mmc_core_init(struct mmc *mmc)
+static int sunxi_mmc_core_init(struct mmc *mmc)
{
struct sunxi_mmc_host *mmchost = mmc->priv;
@@ -298,8 +298,8 @@
return 0;
}
-static int mmc_send_cmd(struct mmc *mmc, struct mmc_cmd *cmd,
- struct mmc_data *data)
+static int sunxi_mmc_send_cmd(struct mmc *mmc, struct mmc_cmd *cmd,
+ struct mmc_data *data)
{
struct sunxi_mmc_host *mmchost = mmc->priv;
unsigned int cmdval = SUNXI_MMC_CMD_START;
@@ -432,9 +432,9 @@
}
static const struct mmc_ops sunxi_mmc_ops = {
- .send_cmd = mmc_send_cmd,
- .set_ios = mmc_set_ios,
- .init = mmc_core_init,
+ .send_cmd = sunxi_mmc_send_cmd,
+ .set_ios = sunxi_mmc_set_ios,
+ .init = sunxi_mmc_core_init,
.getcd = sunxi_mmc_getcd,
};
diff --git a/drivers/mmc/tegra_mmc.c b/drivers/mmc/tegra_mmc.c
index 2bd36b0..2cd8cf1 100644
--- a/drivers/mmc/tegra_mmc.c
+++ b/drivers/mmc/tegra_mmc.c
@@ -515,8 +515,8 @@
debug("tegra_mmc_getcd called\n");
- if (fdt_gpio_isvalid(&host->cd_gpio))
- return fdtdec_get_gpio(&host->cd_gpio);
+ if (dm_gpio_is_valid(&host->cd_gpio))
+ return dm_gpio_get_value(&host->cd_gpio);
return 1;
}
@@ -531,7 +531,6 @@
static int do_mmc_init(int dev_index)
{
struct mmc_host *host;
- char gpusage[12]; /* "SD/MMCn PWR" or "SD/MMCn CD" */
struct mmc *mmc;
/* DT should have been read & host config filled in */
@@ -539,27 +538,15 @@
if (!host->enabled)
return -1;
- debug(" do_mmc_init: index %d, bus width %d "
- "pwr_gpio %d cd_gpio %d\n",
- dev_index, host->width,
- host->pwr_gpio.gpio, host->cd_gpio.gpio);
+ debug(" do_mmc_init: index %d, bus width %d pwr_gpio %d cd_gpio %d\n",
+ dev_index, host->width, gpio_get_number(&host->pwr_gpio),
+ gpio_get_number(&host->cd_gpio));
host->clock = 0;
clock_start_periph_pll(host->mmc_id, CLOCK_ID_PERIPH, 20000000);
- if (fdt_gpio_isvalid(&host->pwr_gpio)) {
- sprintf(gpusage, "SD/MMC%d PWR", dev_index);
- gpio_request(host->pwr_gpio.gpio, gpusage);
- gpio_direction_output(host->pwr_gpio.gpio, 1);
- debug(" Power GPIO name = %s\n", host->pwr_gpio.name);
- }
-
- if (fdt_gpio_isvalid(&host->cd_gpio)) {
- sprintf(gpusage, "SD/MMC%d CD", dev_index);
- gpio_request(host->cd_gpio.gpio, gpusage);
- gpio_direction_input(host->cd_gpio.gpio);
- debug(" CD GPIO name = %s\n", host->cd_gpio.name);
- }
+ if (dm_gpio_is_valid(&host->pwr_gpio))
+ dm_gpio_set_value(&host->pwr_gpio, 1);
memset(&host->cfg, 0, sizeof(host->cfg));
@@ -626,9 +613,12 @@
debug("%s: no sdmmc width found\n", __func__);
/* These GPIOs are optional */
- fdtdec_decode_gpio(blob, node, "cd-gpios", &host->cd_gpio);
- fdtdec_decode_gpio(blob, node, "wp-gpios", &host->wp_gpio);
- fdtdec_decode_gpio(blob, node, "power-gpios", &host->pwr_gpio);
+ gpio_request_by_name_nodev(blob, node, "cd-gpios", 0, &host->cd_gpio,
+ GPIOD_IS_IN);
+ gpio_request_by_name_nodev(blob, node, "wp-gpios", 0, &host->wp_gpio,
+ GPIOD_IS_IN);
+ gpio_request_by_name_nodev(blob, node, "power-gpios", 0,
+ &host->pwr_gpio, GPIOD_IS_OUT);
debug("%s: found controller at %p, width = %d, periph_id = %d\n",
__func__, host->reg, host->width, host->mmc_id);
diff --git a/drivers/mtd/nand/tegra_nand.c b/drivers/mtd/nand/tegra_nand.c
index 163cf29..b660f3b 100644
--- a/drivers/mtd/nand/tegra_nand.c
+++ b/drivers/mtd/nand/tegra_nand.c
@@ -79,7 +79,7 @@
struct fdt_nand {
struct nand_ctlr *reg;
int enabled; /* 1 to enable, 0 to disable */
- struct fdt_gpio_state wp_gpio; /* write-protect GPIO */
+ struct gpio_desc wp_gpio; /* write-protect GPIO */
s32 width; /* bit width, normally 8 */
u32 timing[FDT_NAND_TIMING_COUNT];
};
@@ -945,8 +945,8 @@
config->reg = (struct nand_ctlr *)fdtdec_get_addr(blob, node, "reg");
config->enabled = fdtdec_get_is_enabled(blob, node);
config->width = fdtdec_get_int(blob, node, "nvidia,nand-width", 8);
- err = fdtdec_decode_gpio(blob, node, "nvidia,wp-gpios",
- &config->wp_gpio);
+ err = gpio_request_by_name_nodev(blob, node, "nvidia,wp-gpios", 0,
+ &config->wp_gpio, GPIOD_IS_OUT);
if (err)
return err;
err = fdtdec_get_int_array(blob, node, "nvidia,timing",
@@ -1009,8 +1009,7 @@
/* Adjust timing for NAND device */
setup_timing(config->timing, info->reg);
- fdtdec_setup_gpio(&config->wp_gpio);
- gpio_direction_output(config->wp_gpio.gpio, 1);
+ dm_gpio_set_value(&config->wp_gpio, 1);
our_mtd = &nand_info[devnum];
our_mtd->priv = nand;
diff --git a/drivers/mtd/spi/sandbox.c b/drivers/mtd/spi/sandbox.c
index 3024b98..d576d31 100644
--- a/drivers/mtd/spi/sandbox.c
+++ b/drivers/mtd/spi/sandbox.c
@@ -141,8 +141,10 @@
assert(bus->seq != -1);
if (bus->seq < CONFIG_SANDBOX_SPI_MAX_BUS)
spec = state->spi[bus->seq][cs].spec;
- if (!spec)
- return -ENOENT;
+ if (!spec) {
+ ret = -ENOENT;
+ goto error;
+ }
file = strchr(spec, ':');
if (!file) {
@@ -196,6 +198,7 @@
return 0;
error:
+ debug("%s: Got error %d\n", __func__, ret);
return ret;
}
@@ -587,6 +590,11 @@
void sandbox_sf_unbind_emul(struct sandbox_state *state, int busnum, int cs)
{
+ struct udevice *dev;
+
+ dev = state->spi[busnum][cs].emul;
+ device_remove(dev);
+ device_unbind(dev);
state->spi[busnum][cs].emul = NULL;
}
diff --git a/drivers/mtd/spi/sf_probe.c b/drivers/mtd/spi/sf_probe.c
index ce9987f..4103723 100644
--- a/drivers/mtd/spi/sf_probe.c
+++ b/drivers/mtd/spi/sf_probe.c
@@ -481,11 +481,12 @@
int spi_flash_std_probe(struct udevice *dev)
{
struct spi_slave *slave = dev_get_parentdata(dev);
+ struct dm_spi_slave_platdata *plat = dev_get_parent_platdata(dev);
struct spi_flash *flash;
flash = dev->uclass_priv;
flash->dev = dev;
- debug("%s: slave=%p, cs=%d\n", __func__, slave, slave->cs);
+ debug("%s: slave=%p, cs=%d\n", __func__, slave, plat->cs);
return spi_flash_probe_slave(slave, flash);
}
diff --git a/drivers/net/designware.c b/drivers/net/designware.c
index 9ded895..c03e935 100644
--- a/drivers/net/designware.c
+++ b/drivers/net/designware.c
@@ -236,8 +236,10 @@
start = get_timer(0);
while (readl(&dma_p->busmode) & DMAMAC_SRST) {
- if (get_timer(start) >= CONFIG_MACRESET_TIMEOUT)
+ if (get_timer(start) >= CONFIG_MACRESET_TIMEOUT) {
+ printf("DMA reset timeout\n");
return -1;
+ }
mdelay(100);
};
diff --git a/drivers/net/e1000.c b/drivers/net/e1000.c
index 6531030..cd44222 100644
--- a/drivers/net/e1000.c
+++ b/drivers/net/e1000.c
@@ -4927,22 +4927,23 @@
fill_rx(struct e1000_hw *hw)
{
struct e1000_rx_desc *rd;
- uint32_t flush_start, flush_end;
+ unsigned long flush_start, flush_end;
rx_last = rx_tail;
rd = rx_base + rx_tail;
rx_tail = (rx_tail + 1) % 8;
memset(rd, 0, 16);
- rd->buffer_addr = cpu_to_le64((u32)packet);
+ rd->buffer_addr = cpu_to_le64((unsigned long)packet);
/*
* Make sure there are no stale data in WB over this area, which
* might get written into the memory while the e1000 also writes
* into the same memory area.
*/
- invalidate_dcache_range((u32)packet, (u32)packet + 4096);
+ invalidate_dcache_range((unsigned long)packet,
+ (unsigned long)packet + 4096);
/* Dump the DMA descriptor into RAM. */
- flush_start = ((u32)rd) & ~(ARCH_DMA_MINALIGN - 1);
+ flush_start = ((unsigned long)rd) & ~(ARCH_DMA_MINALIGN - 1);
flush_end = flush_start + roundup(sizeof(*rd), ARCH_DMA_MINALIGN);
flush_dcache_range(flush_start, flush_end);
@@ -4963,7 +4964,7 @@
unsigned long tipg, tarc;
uint32_t ipgr1, ipgr2;
- E1000_WRITE_REG(hw, TDBAL, (u32) tx_base);
+ E1000_WRITE_REG(hw, TDBAL, (unsigned long)tx_base);
E1000_WRITE_REG(hw, TDBAH, 0);
E1000_WRITE_REG(hw, TDLEN, 128);
@@ -5107,7 +5108,7 @@
E1000_WRITE_FLUSH(hw);
}
/* Setup the Base and Length of the Rx Descriptor Ring */
- E1000_WRITE_REG(hw, RDBAL, (u32) rx_base);
+ E1000_WRITE_REG(hw, RDBAL, (unsigned long)rx_base);
E1000_WRITE_REG(hw, RDBAH, 0);
E1000_WRITE_REG(hw, RDLEN, 128);
@@ -5138,14 +5139,14 @@
{
struct e1000_hw *hw = nic->priv;
struct e1000_rx_desc *rd;
- uint32_t inval_start, inval_end;
+ unsigned long inval_start, inval_end;
uint32_t len;
/* return true if there's an ethernet packet ready to read */
rd = rx_base + rx_last;
/* Re-load the descriptor from RAM. */
- inval_start = ((u32)rd) & ~(ARCH_DMA_MINALIGN - 1);
+ inval_start = ((unsigned long)rd) & ~(ARCH_DMA_MINALIGN - 1);
inval_end = inval_start + roundup(sizeof(*rd), ARCH_DMA_MINALIGN);
invalidate_dcache_range(inval_start, inval_end);
@@ -5154,8 +5155,9 @@
/*DEBUGOUT("recv: packet len=%d \n", rd->length); */
/* Packet received, make sure the data are re-loaded from RAM. */
len = le32_to_cpu(rd->length);
- invalidate_dcache_range((u32)packet,
- (u32)packet + roundup(len, ARCH_DMA_MINALIGN));
+ invalidate_dcache_range((unsigned long)packet,
+ (unsigned long)packet +
+ roundup(len, ARCH_DMA_MINALIGN));
NetReceive((uchar *)packet, len);
fill_rx(hw);
return 1;
@@ -5170,7 +5172,7 @@
struct e1000_hw *hw = nic->priv;
struct e1000_tx_desc *txp;
int i = 0;
- uint32_t flush_start, flush_end;
+ unsigned long flush_start, flush_end;
txp = tx_base + tx_tail;
tx_tail = (tx_tail + 1) % 8;
@@ -5180,10 +5182,11 @@
txp->upper.data = 0;
/* Dump the packet into RAM so e1000 can pick them. */
- flush_dcache_range((u32)nv_packet,
- (u32)nv_packet + roundup(length, ARCH_DMA_MINALIGN));
+ flush_dcache_range((unsigned long)nv_packet,
+ (unsigned long)nv_packet +
+ roundup(length, ARCH_DMA_MINALIGN));
/* Dump the descriptor into RAM as well. */
- flush_start = ((u32)txp) & ~(ARCH_DMA_MINALIGN - 1);
+ flush_start = ((unsigned long)txp) & ~(ARCH_DMA_MINALIGN - 1);
flush_end = flush_start + roundup(sizeof(*txp), ARCH_DMA_MINALIGN);
flush_dcache_range(flush_start, flush_end);
diff --git a/drivers/net/phy/micrel.c b/drivers/net/phy/micrel.c
index 507b9a3..1815b29 100644
--- a/drivers/net/phy/micrel.c
+++ b/drivers/net/phy/micrel.c
@@ -22,6 +22,63 @@
.shutdown = &genphy_shutdown,
};
+/**
+ * KSZ8895
+ */
+
+static unsigned short smireg_to_phy(unsigned short reg)
+{
+ return ((reg & 0xc0) >> 3) + 0x06 + ((reg & 0x20) >> 5);
+}
+
+static unsigned short smireg_to_reg(unsigned short reg)
+{
+ return reg & 0x1F;
+}
+
+static void ksz8895_write_smireg(struct phy_device *phydev, int smireg, int val)
+{
+ phydev->bus->write(phydev->bus, smireg_to_phy(smireg), MDIO_DEVAD_NONE,
+ smireg_to_reg(smireg), val);
+}
+
+#if 0
+static int ksz8895_read_smireg(struct phy_device *phydev, int smireg)
+{
+ return phydev->bus->read(phydev->bus, smireg_to_phy(smireg),
+ MDIO_DEVAD_NONE, smireg_to_reg(smireg));
+}
+#endif
+
+int ksz8895_config(struct phy_device *phydev)
+{
+ /* we are connected directly to the switch without
+ * dedicated PHY. SCONF1 == 001 */
+ phydev->link = 1;
+ phydev->duplex = DUPLEX_FULL;
+ phydev->speed = SPEED_100;
+
+ /* Force the switch to start */
+ ksz8895_write_smireg(phydev, 1, 1);
+
+ return 0;
+}
+
+static int ksz8895_startup(struct phy_device *phydev)
+{
+ return 0;
+}
+
+static struct phy_driver ksz8895_driver = {
+ .name = "Micrel KSZ8895/KSZ8864",
+ .uid = 0x221450,
+ .mask = 0xffffe1,
+ .features = PHY_BASIC_FEATURES,
+ .config = &ksz8895_config,
+ .startup = &ksz8895_startup,
+ .shutdown = &genphy_shutdown,
+};
+
#ifndef CONFIG_PHY_MICREL_KSZ9021
/*
* I can't believe Micrel used the exact same part number
@@ -221,5 +278,6 @@
phy_register(&KS8721_driver);
#endif
phy_register(&ksz9031_driver);
+ phy_register(&ksz8895_driver);
return 0;
}
diff --git a/drivers/net/smc91111.h b/drivers/net/smc91111.h
index d9135cb..e19c491 100644
--- a/drivers/net/smc91111.h
+++ b/drivers/net/smc91111.h
@@ -236,7 +236,36 @@
*(__b2 + __i) = SMC_inb((a),(r)); \
}; \
}while(0)
-
+#elif defined(CONFIG_MS7206SE)
+#define SWAB7206(x) ({ word __x = x; ((__x << 8)|(__x >> 8)); })
+#define SMC_inw(a, r) *((volatile word*)((a)->iobase + (r)))
+#define SMC_inb(a, r) (*((volatile byte*)((a)->iobase + ((r) ^ 0x01))))
+#define SMC_insw(a, r, b, l) \
+ do { \
+ int __i; \
+ word *__b2 = (word *)(b); \
+ for (__i = 0; __i < (l); __i++) { \
+ *__b2++ = SWAB7206(SMC_inw(a, r)); \
+ } \
+ } while (0)
+#define SMC_outw(a, d, r) (*((volatile word *)((a)->iobase+(r))) = d)
+#define SMC_outb(a, d, r) ({ word __d = (byte)(d); \
+ word __w = SMC_inw((a), ((r)&(~1))); \
+ if (((r) & 1)) \
+ __w = (__w & 0x00ff) | (__d << 8); \
+ else \
+ __w = (__w & 0xff00) | (__d); \
+ SMC_outw((a), __w, ((r)&(~1))); \
+ })
+#define SMC_outsw(a, r, b, l) \
+ do { \
+ int __i; \
+ word *__b2 = (word *)(b); \
+ for (__i = 0; __i < (l); __i++) { \
+ SMC_outw(a, SWAB7206(*__b2), r); \
+ __b2++; \
+ } \
+ } while (0)
#else /* if not CONFIG_CPU_PXA25X and not CONFIG_LEON */
#ifndef CONFIG_SMC_USE_IOFUNCS /* these macros don't work on some boards */
diff --git a/drivers/net/tsec.c b/drivers/net/tsec.c
index 79d6561..dcdba4e 100644
--- a/drivers/net/tsec.c
+++ b/drivers/net/tsec.c
@@ -597,6 +597,8 @@
tsec_configure_serdes(priv);
phydev = phy_connect(priv->bus, priv->phyaddr, dev, priv->interface);
+ if (!phydev)
+ return 0;
phydev->supported &= supported;
phydev->advertising = phydev->supported;
diff --git a/drivers/pci/pci_rom.c b/drivers/pci/pci_rom.c
index eb76591..5729a15 100644
--- a/drivers/pci/pci_rom.c
+++ b/drivers/pci/pci_rom.c
@@ -98,7 +98,7 @@
rom_address | PCI_ROM_ADDRESS_ENABLE);
#endif
debug("Option ROM address %x\n", rom_address);
- rom_header = (struct pci_rom_header *)rom_address;
+ rom_header = (struct pci_rom_header *)(unsigned long)rom_address;
debug("PCI expansion ROM, signature %#04x, INIT size %#04x, data ptr %#04x\n",
le16_to_cpu(rom_header->signature),
diff --git a/drivers/power/as3722.c b/drivers/power/as3722.c
index 4c6de79..a60bb5f 100644
--- a/drivers/power/as3722.c
+++ b/drivers/power/as3722.c
@@ -31,7 +31,7 @@
{
int err;
- err = i2c_read(pmic, reg, value, 1);
+ err = dm_i2c_read(pmic, reg, value, 1);
if (err < 0)
return err;
@@ -42,7 +42,7 @@
{
int err;
- err = i2c_write(pmic, reg, &value, 1);
+ err = dm_i2c_write(pmic, reg, &value, 1);
if (err < 0)
return err;
@@ -242,7 +242,7 @@
const unsigned int address = 0x40;
int err;
- err = i2c_get_chip_for_busnum(bus, address, &pmic);
+ err = i2c_get_chip_for_busnum(bus, address, 1, &pmic);
if (err)
return err;
err = as3722_read_id(pmic, &id, &revision);
diff --git a/drivers/power/axp221.c b/drivers/power/axp221.c
index 58bbd45..3e07f23 100644
--- a/drivers/power/axp221.c
+++ b/drivers/power/axp221.c
@@ -29,9 +29,7 @@
#else
int ret;
- rsb_init();
-
- ret = rsb_set_device_mode(AXP223_DEVICE_MODE_DATA);
+ ret = rsb_init();
if (ret)
return ret;
diff --git a/drivers/power/tps6586x.c b/drivers/power/tps6586x.c
index 29bab4c..8650983 100644
--- a/drivers/power/tps6586x.c
+++ b/drivers/power/tps6586x.c
@@ -37,7 +37,7 @@
int retval = -1;
for (i = 0; i < MAX_I2C_RETRY; ++i) {
- if (!i2c_read(tps6586x_dev, reg, &data, 1)) {
+ if (!dm_i2c_read(tps6586x_dev, reg, &data, 1)) {
retval = (int)data;
goto exit;
}
@@ -60,7 +60,7 @@
int retval = -1;
for (i = 0; i < MAX_I2C_RETRY; ++i) {
- if (!i2c_write(tps6586x_dev, reg, data, len)) {
+ if (!dm_i2c_write(tps6586x_dev, reg, data, len)) {
retval = 0;
goto exit;
}
diff --git a/drivers/serial/serial-uclass.c b/drivers/serial/serial-uclass.c
index d1b5777..9131a8f 100644
--- a/drivers/serial/serial-uclass.c
+++ b/drivers/serial/serial-uclass.c
@@ -297,6 +297,7 @@
UCLASS_DRIVER(serial) = {
.id = UCLASS_SERIAL,
.name = "serial",
+ .flags = DM_UC_FLAG_SEQ_ALIAS,
.post_probe = serial_post_probe,
.pre_remove = serial_pre_remove,
.per_device_auto_alloc_size = sizeof(struct serial_dev_priv),
diff --git a/drivers/spi/cadence_qspi.c b/drivers/spi/cadence_qspi.c
index 98ae3b8..a75fc46 100644
--- a/drivers/spi/cadence_qspi.c
+++ b/drivers/spi/cadence_qspi.c
@@ -340,6 +340,5 @@
.ofdata_to_platdata = cadence_spi_ofdata_to_platdata,
.platdata_auto_alloc_size = sizeof(struct cadence_spi_platdata),
.priv_auto_alloc_size = sizeof(struct cadence_spi_priv),
- .per_child_auto_alloc_size = sizeof(struct spi_slave),
.probe = cadence_spi_probe,
};
diff --git a/drivers/spi/designware_spi.c b/drivers/spi/designware_spi.c
index 700f616..2624844 100644
--- a/drivers/spi/designware_spi.c
+++ b/drivers/spi/designware_spi.c
@@ -421,6 +421,5 @@
.ofdata_to_platdata = dw_spi_ofdata_to_platdata,
.platdata_auto_alloc_size = sizeof(struct dw_spi_platdata),
.priv_auto_alloc_size = sizeof(struct dw_spi_priv),
- .per_child_auto_alloc_size = sizeof(struct spi_slave),
.probe = dw_spi_probe,
};
diff --git a/drivers/spi/exynos_spi.c b/drivers/spi/exynos_spi.c
index f078973..a46d8c1 100644
--- a/drivers/spi/exynos_spi.c
+++ b/drivers/spi/exynos_spi.c
@@ -425,6 +425,5 @@
.ofdata_to_platdata = exynos_spi_ofdata_to_platdata,
.platdata_auto_alloc_size = sizeof(struct exynos_spi_platdata),
.priv_auto_alloc_size = sizeof(struct exynos_spi_priv),
- .per_child_auto_alloc_size = sizeof(struct spi_slave),
.probe = exynos_spi_probe,
};
diff --git a/drivers/spi/sandbox_spi.c b/drivers/spi/sandbox_spi.c
index e717424..bad5660 100644
--- a/drivers/spi/sandbox_spi.c
+++ b/drivers/spi/sandbox_spi.c
@@ -160,6 +160,5 @@
.name = "spi_sandbox",
.id = UCLASS_SPI,
.of_match = sandbox_spi_ids,
- .per_child_auto_alloc_size = sizeof(struct spi_slave),
.ops = &sandbox_spi_ops,
};
diff --git a/drivers/spi/soft_spi.c b/drivers/spi/soft_spi.c
index 5588036..6ae45f5 100644
--- a/drivers/spi/soft_spi.c
+++ b/drivers/spi/soft_spi.c
@@ -21,10 +21,10 @@
DECLARE_GLOBAL_DATA_PTR;
struct soft_spi_platdata {
- struct fdt_gpio_state cs;
- struct fdt_gpio_state sclk;
- struct fdt_gpio_state mosi;
- struct fdt_gpio_state miso;
+ struct gpio_desc cs;
+ struct gpio_desc sclk;
+ struct gpio_desc mosi;
+ struct gpio_desc miso;
int spi_delay_us;
};
@@ -35,9 +35,8 @@
static int soft_spi_scl(struct udevice *dev, int bit)
{
struct soft_spi_platdata *plat = dev->platdata;
- struct soft_spi_priv *priv = dev_get_priv(dev);
- gpio_set_value(plat->sclk.gpio, priv->mode & SPI_CPOL ? bit : !bit);
+ dm_gpio_set_value(&plat->sclk, bit);
return 0;
}
@@ -46,7 +45,7 @@
{
struct soft_spi_platdata *plat = dev->platdata;
- gpio_set_value(plat->mosi.gpio, bit);
+ dm_gpio_set_value(&plat->mosi, bit);
return 0;
}
@@ -54,11 +53,10 @@
static int soft_spi_cs_activate(struct udevice *dev)
{
struct soft_spi_platdata *plat = dev->platdata;
- struct soft_spi_priv *priv = dev_get_priv(dev);
- gpio_set_value(plat->cs.gpio, !(priv->mode & SPI_CS_HIGH));
- gpio_set_value(plat->sclk.gpio, priv->mode & SPI_CPOL);
- gpio_set_value(plat->cs.gpio, priv->mode & SPI_CS_HIGH);
+ dm_gpio_set_value(&plat->cs, 0);
+ dm_gpio_set_value(&plat->sclk, 0);
+ dm_gpio_set_value(&plat->cs, 1);
return 0;
}
@@ -66,9 +64,8 @@
static int soft_spi_cs_deactivate(struct udevice *dev)
{
struct soft_spi_platdata *plat = dev->platdata;
- struct soft_spi_priv *priv = dev_get_priv(dev);
- gpio_set_value(plat->cs.gpio, !(priv->mode & SPI_CS_HIGH));
+ dm_gpio_set_value(&plat->cs, 0);
return 0;
}
@@ -109,7 +106,6 @@
uchar tmpdout = 0;
const u8 *txd = dout;
u8 *rxd = din;
- int cpol = priv->mode & SPI_CPOL;
int cpha = priv->mode & SPI_CPHA;
unsigned int j;
@@ -137,19 +133,19 @@
}
if (!cpha)
- soft_spi_scl(dev, !cpol);
+ soft_spi_scl(dev, 0);
soft_spi_sda(dev, tmpdout & 0x80);
udelay(plat->spi_delay_us);
if (cpha)
- soft_spi_scl(dev, !cpol);
+ soft_spi_scl(dev, 0);
else
- soft_spi_scl(dev, cpol);
+ soft_spi_scl(dev, 1);
tmpdin <<= 1;
- tmpdin |= gpio_get_value(plat->miso.gpio);
+ tmpdin |= dm_gpio_get_value(&plat->miso);
tmpdout <<= 1;
udelay(plat->spi_delay_us);
if (cpha)
- soft_spi_scl(dev, cpol);
+ soft_spi_scl(dev, 1);
}
/*
* If the number of bits isn't a multiple of 8, shift the last
@@ -183,14 +179,6 @@
return 0;
}
-static int soft_spi_child_pre_probe(struct udevice *dev)
-{
- struct spi_slave *slave = dev_get_parentdata(dev);
-
- slave->dev = dev;
- return spi_ofdata_to_platdata(gd->fdt_blob, dev->of_offset, slave);
-}
-
static const struct dm_spi_ops soft_spi_ops = {
.claim_bus = soft_spi_claim_bus,
.release_bus = soft_spi_release_bus,
@@ -205,11 +193,6 @@
const void *blob = gd->fdt_blob;
int node = dev->of_offset;
- if (fdtdec_decode_gpio(blob, node, "cs-gpio", &plat->cs) ||
- fdtdec_decode_gpio(blob, node, "sclk-gpio", &plat->sclk) ||
- fdtdec_decode_gpio(blob, node, "mosi-gpio", &plat->mosi) ||
- fdtdec_decode_gpio(blob, node, "miso-gpio", &plat->miso))
- return -EINVAL;
plat->spi_delay_us = fdtdec_get_int(blob, node, "spi-delay-us", 0);
return 0;
@@ -219,16 +202,19 @@
{
struct spi_slave *slave = dev_get_parentdata(dev);
struct soft_spi_platdata *plat = dev->platdata;
+ int cs_flags, clk_flags;
- gpio_request(plat->cs.gpio, "soft_spi_cs");
- gpio_request(plat->sclk.gpio, "soft_spi_sclk");
- gpio_request(plat->mosi.gpio, "soft_spi_mosi");
- gpio_request(plat->miso.gpio, "soft_spi_miso");
-
- gpio_direction_output(plat->sclk.gpio, slave->mode & SPI_CPOL);
- gpio_direction_output(plat->mosi.gpio, 1);
- gpio_direction_input(plat->miso.gpio);
- gpio_direction_output(plat->cs.gpio, !(slave->mode & SPI_CS_HIGH));
+ cs_flags = (slave->mode & SPI_CS_HIGH) ? 0 : GPIOD_ACTIVE_LOW;
+ clk_flags = (slave->mode & SPI_CPOL) ? GPIOD_ACTIVE_LOW : 0;
+ if (gpio_request_by_name(dev, "cs-gpio", 0, &plat->cs,
+ GPIOD_IS_OUT | cs_flags) ||
+ gpio_request_by_name(dev, "sclk-gpio", 0, &plat->sclk,
+ GPIOD_IS_OUT | clk_flags) ||
+ gpio_request_by_name(dev, "mosi-gpio", 0, &plat->mosi,
+ GPIOD_IS_OUT | GPIOD_IS_OUT_ACTIVE) ||
+ gpio_request_by_name(dev, "miso-gpio", 0, &plat->miso,
+ GPIOD_IS_IN))
+ return -EINVAL;
return 0;
}
@@ -246,7 +232,5 @@
.ofdata_to_platdata = soft_spi_ofdata_to_platdata,
.platdata_auto_alloc_size = sizeof(struct soft_spi_platdata),
.priv_auto_alloc_size = sizeof(struct soft_spi_priv),
- .per_child_auto_alloc_size = sizeof(struct spi_slave),
.probe = soft_spi_probe,
- .child_pre_probe = soft_spi_child_pre_probe,
};
diff --git a/drivers/spi/spi-uclass.c b/drivers/spi/spi-uclass.c
index 7a57bce..63a6217 100644
--- a/drivers/spi/spi-uclass.c
+++ b/drivers/spi/spi-uclass.c
@@ -98,21 +98,51 @@
return dm_scan_fdt_node(dev, gd->fdt_blob, dev->of_offset, false);
}
-int spi_post_probe(struct udevice *dev)
+int spi_child_post_bind(struct udevice *dev)
{
- struct dm_spi_bus *spi = dev->uclass_priv;
+ struct dm_spi_slave_platdata *plat = dev_get_parent_platdata(dev);
- spi->max_hz = fdtdec_get_int(gd->fdt_blob, dev->of_offset,
+ if (dev->of_offset == -1)
+ return 0;
+
+ return spi_slave_ofdata_to_platdata(gd->fdt_blob, dev->of_offset, plat);
+}
+
+int spi_post_probe(struct udevice *bus)
+{
+ struct dm_spi_bus *spi = bus->uclass_priv;
+
+ spi->max_hz = fdtdec_get_int(gd->fdt_blob, bus->of_offset,
"spi-max-frequency", 0);
return 0;
}
-int spi_chip_select(struct udevice *dev)
+int spi_child_pre_probe(struct udevice *dev)
{
+ struct dm_spi_slave_platdata *plat = dev_get_parent_platdata(dev);
struct spi_slave *slave = dev_get_parentdata(dev);
+ /*
+ * This is needed because we pass struct spi_slave around the place
+ * instead slave->dev (a struct udevice). So we have to have some
+ * way to access the slave udevice given struct spi_slave. Once we
+ * change the SPI API to use udevice instead of spi_slave, we can
+ * drop this.
+ */
+ slave->dev = dev;
+
+ slave->max_hz = plat->max_hz;
+ slave->mode = plat->mode;
+
+ return 0;
+}
+
+int spi_chip_select(struct udevice *dev)
+{
+ struct dm_spi_slave_platdata *plat = dev_get_parent_platdata(dev);
+
- return slave ? slave->cs : -ENOENT;
+ return plat ? plat->cs : -ENOENT;
}
int spi_find_chip_select(struct udevice *bus, int cs, struct udevice **devp)
@@ -121,17 +151,11 @@
for (device_find_first_child(bus, &dev); dev;
device_find_next_child(&dev)) {
- struct spi_slave store;
- struct spi_slave *slave = dev_get_parentdata(dev);
+ struct dm_spi_slave_platdata *plat;
- if (!slave) {
- slave = &store;
- spi_ofdata_to_platdata(gd->fdt_blob, dev->of_offset,
- slave);
- }
- debug("%s: slave=%p, cs=%d\n", __func__, slave,
- slave ? slave->cs : -1);
- if (slave && slave->cs == cs) {
+ plat = dev_get_parent_platdata(dev);
+ debug("%s: plat=%p, cs=%d\n", __func__, plat, plat->cs);
+ if (plat->cs == cs) {
*devp = dev;
return 0;
}
@@ -215,7 +239,6 @@
struct udevice **busp, struct spi_slave **devp)
{
struct udevice *bus, *dev;
- struct spi_slave *slave;
bool created = false;
int ret;
@@ -232,11 +255,17 @@
* SPI flash chip - we will bind to the correct driver.
*/
if (ret == -ENODEV && drv_name) {
+ struct dm_spi_slave_platdata *plat;
+
debug("%s: Binding new device '%s', busnum=%d, cs=%d, driver=%s\n",
__func__, dev_name, busnum, cs, drv_name);
ret = device_bind_driver(bus, drv_name, dev_name, &dev);
if (ret)
return ret;
+ plat = dev_get_parent_platdata(dev);
+ plat->cs = cs;
+ plat->max_hz = speed;
+ plat->mode = mode;
created = true;
} else if (ret) {
printf("Invalid chip select %d:%d (err=%d)\n", busnum, cs,
@@ -245,23 +274,13 @@
}
if (!device_active(dev)) {
- slave = (struct spi_slave *)calloc(1,
- sizeof(struct spi_slave));
- if (!slave) {
- ret = -ENOMEM;
- goto err;
- }
+ struct spi_slave *slave;
- ret = spi_ofdata_to_platdata(gd->fdt_blob, dev->of_offset,
- slave);
+ ret = device_probe(dev);
if (ret)
goto err;
- slave->cs = cs;
+ slave = dev_get_parentdata(dev);
slave->dev = dev;
- ret = device_probe_child(dev, slave);
- free(slave);
- if (ret)
- goto err;
}
ret = spi_set_speed_mode(bus, speed, mode);
@@ -275,6 +294,8 @@
return 0;
err:
+ debug("%s: Error path, credted=%d, device '%s'\n", __func__,
+ created, dev->name);
if (created) {
device_remove(dev);
device_unbind(dev);
@@ -321,13 +342,13 @@
slave->dev = NULL;
}
-int spi_ofdata_to_platdata(const void *blob, int node,
- struct spi_slave *spi)
+int spi_slave_ofdata_to_platdata(const void *blob, int node,
+ struct dm_spi_slave_platdata *plat)
{
int mode = 0;
- spi->cs = fdtdec_get_int(blob, node, "reg", -1);
- spi->max_hz = fdtdec_get_int(blob, node, "spi-max-frequency", 0);
+ plat->cs = fdtdec_get_int(blob, node, "reg", -1);
+ plat->max_hz = fdtdec_get_int(blob, node, "spi-max-frequency", 0);
if (fdtdec_get_bool(blob, node, "spi-cpol"))
mode |= SPI_CPOL;
if (fdtdec_get_bool(blob, node, "spi-cpha"))
@@ -336,7 +357,7 @@
mode |= SPI_CS_HIGH;
if (fdtdec_get_bool(blob, node, "spi-half-duplex"))
mode |= SPI_PREAMBLE;
- spi->mode = mode;
+ plat->mode = mode;
return 0;
}
@@ -344,9 +365,15 @@
UCLASS_DRIVER(spi) = {
.id = UCLASS_SPI,
.name = "spi",
+ .flags = DM_UC_FLAG_SEQ_ALIAS,
.post_bind = spi_post_bind,
.post_probe = spi_post_probe,
+ .child_pre_probe = spi_child_pre_probe,
.per_device_auto_alloc_size = sizeof(struct dm_spi_bus),
+ .per_child_auto_alloc_size = sizeof(struct spi_slave),
+ .per_child_platdata_auto_alloc_size =
+ sizeof(struct dm_spi_slave_platdata),
+ .child_post_bind = spi_child_post_bind,
};
UCLASS_DRIVER(spi_generic) = {
diff --git a/drivers/spi/tegra114_spi.c b/drivers/spi/tegra114_spi.c
index 2d97625..53ff9ea 100644
--- a/drivers/spi/tegra114_spi.c
+++ b/drivers/spi/tegra114_spi.c
@@ -407,6 +407,5 @@
.ofdata_to_platdata = tegra114_spi_ofdata_to_platdata,
.platdata_auto_alloc_size = sizeof(struct tegra_spi_platdata),
.priv_auto_alloc_size = sizeof(struct tegra114_spi_priv),
- .per_child_auto_alloc_size = sizeof(struct spi_slave),
.probe = tegra114_spi_probe,
};
diff --git a/drivers/spi/tegra20_sflash.c b/drivers/spi/tegra20_sflash.c
index 7d0d0f3..78c74cd 100644
--- a/drivers/spi/tegra20_sflash.c
+++ b/drivers/spi/tegra20_sflash.c
@@ -348,6 +348,5 @@
.ofdata_to_platdata = tegra20_sflash_ofdata_to_platdata,
.platdata_auto_alloc_size = sizeof(struct tegra_spi_platdata),
.priv_auto_alloc_size = sizeof(struct tegra20_sflash_priv),
- .per_child_auto_alloc_size = sizeof(struct spi_slave),
.probe = tegra20_sflash_probe,
};
diff --git a/drivers/spi/tegra20_slink.c b/drivers/spi/tegra20_slink.c
index 213fa5f..597d6ad 100644
--- a/drivers/spi/tegra20_slink.c
+++ b/drivers/spi/tegra20_slink.c
@@ -361,6 +361,5 @@
.ofdata_to_platdata = tegra30_spi_ofdata_to_platdata,
.platdata_auto_alloc_size = sizeof(struct tegra_spi_platdata),
.priv_auto_alloc_size = sizeof(struct tegra30_spi_priv),
- .per_child_auto_alloc_size = sizeof(struct spi_slave),
.probe = tegra30_spi_probe,
};
diff --git a/drivers/usb/host/ehci-exynos.c b/drivers/usb/host/ehci-exynos.c
index 6fdbf57..f3c077d 100644
--- a/drivers/usb/host/ehci-exynos.c
+++ b/drivers/usb/host/ehci-exynos.c
@@ -31,7 +31,7 @@
struct exynos_ehci {
struct exynos_usb_phy *usb;
struct ehci_hccr *hcd;
- struct fdt_gpio_state vbus_gpio;
+ struct gpio_desc vbus_gpio;
};
static struct exynos_ehci exynos;
@@ -61,7 +61,8 @@
exynos->hcd = (struct ehci_hccr *)addr;
/* Vbus gpio */
- fdtdec_decode_gpio(blob, node, "samsung,vbus-gpio", &exynos->vbus_gpio);
+ gpio_request_by_name_nodev(blob, node, "samsung,vbus-gpio", 0,
+ &exynos->vbus_gpio, GPIOD_IS_OUT);
depth = 0;
node = fdtdec_next_compatible_subnode(blob, node,
@@ -236,9 +237,8 @@
#ifdef CONFIG_OF_CONTROL
/* setup the Vbus gpio here */
- if (fdt_gpio_isvalid(&ctx->vbus_gpio) &&
- !fdtdec_setup_gpio(&ctx->vbus_gpio))
- gpio_direction_output(ctx->vbus_gpio.gpio, 1);
+ if (dm_gpio_is_valid(&ctx->vbus_gpio))
+ dm_gpio_set_value(&ctx->vbus_gpio, 1);
#endif
setup_usb_phy(ctx->usb);
diff --git a/drivers/usb/host/ehci-tegra.c b/drivers/usb/host/ehci-tegra.c
index 5f0a98e..b5ad1e3 100644
--- a/drivers/usb/host/ehci-tegra.c
+++ b/drivers/usb/host/ehci-tegra.c
@@ -72,8 +72,8 @@
enum usb_init_type init_type;
enum dr_mode dr_mode; /* dual role mode */
enum periph_id periph_id;/* peripheral id */
- struct fdt_gpio_state vbus_gpio; /* GPIO for vbus enable */
- struct fdt_gpio_state phy_reset_gpio; /* GPIO to reset ULPI phy */
+ struct gpio_desc vbus_gpio; /* GPIO for vbus enable */
+ struct gpio_desc phy_reset_gpio; /* GPIO to reset ULPI phy */
};
static struct fdt_usb port[USB_PORTS_MAX]; /* List of valid USB ports */
@@ -252,17 +252,14 @@
return;
}
- if (fdt_gpio_isvalid(&config->vbus_gpio)) {
+ if (dm_gpio_is_valid(&config->vbus_gpio)) {
int vbus_value;
- fdtdec_setup_gpio(&config->vbus_gpio);
+ vbus_value = (init == USB_INIT_HOST);
+ dm_gpio_set_value(&config->vbus_gpio, vbus_value);
- vbus_value = (init == USB_INIT_HOST) ^
- !!(config->vbus_gpio.flags & FDT_GPIO_ACTIVE_LOW);
- gpio_direction_output(config->vbus_gpio.gpio, vbus_value);
-
- debug("set_up_vbus: GPIO %d %d\n", config->vbus_gpio.gpio,
- vbus_value);
+ debug("set_up_vbus: GPIO %d %d\n",
+ gpio_get_number(&config->vbus_gpio), vbus_value);
}
}
@@ -360,7 +357,7 @@
* mux must be switched to actually use a_sess_vld threshold.
*/
if (config->dr_mode == DR_MODE_OTG &&
- fdt_gpio_isvalid(&config->vbus_gpio))
+ dm_gpio_is_valid(&config->vbus_gpio))
clrsetbits_le32(&usbctlr->usb1_legacy_ctrl,
VBUS_SENSE_CTL_MASK,
VBUS_SENSE_CTL_A_SESS_VLD << VBUS_SENSE_CTL_SHIFT);
@@ -569,11 +566,10 @@
clock_set_pllout(CLOCK_ID_PERIPH, PLL_OUT4, CONFIG_ULPI_REF_CLK);
/* reset ULPI phy */
- if (fdt_gpio_isvalid(&config->phy_reset_gpio)) {
- fdtdec_setup_gpio(&config->phy_reset_gpio);
- gpio_direction_output(config->phy_reset_gpio.gpio, 0);
+ if (dm_gpio_is_valid(&config->phy_reset_gpio)) {
+ dm_gpio_set_value(&config->phy_reset_gpio, 0);
mdelay(5);
- gpio_set_value(config->phy_reset_gpio.gpio, 1);
+ dm_gpio_set_value(&config->phy_reset_gpio, 1);
}
/* Reset the usb controller */
@@ -685,14 +681,16 @@
debug("%s: Missing/invalid peripheral ID\n", __func__);
return -FDT_ERR_NOTFOUND;
}
- fdtdec_decode_gpio(blob, node, "nvidia,vbus-gpio", &config->vbus_gpio);
- fdtdec_decode_gpio(blob, node, "nvidia,phy-reset-gpio",
- &config->phy_reset_gpio);
+ gpio_request_by_name_nodev(blob, node, "nvidia,vbus-gpio", 0,
+ &config->vbus_gpio, GPIOD_IS_OUT);
+ gpio_request_by_name_nodev(blob, node, "nvidia,phy-reset-gpio", 0,
+ &config->phy_reset_gpio, GPIOD_IS_OUT);
debug("enabled=%d, legacy_mode=%d, utmi=%d, ulpi=%d, periph_id=%d, "
"vbus=%d, phy_reset=%d, dr_mode=%d\n",
config->enabled, config->has_legacy_mode, config->utmi,
- config->ulpi, config->periph_id, config->vbus_gpio.gpio,
- config->phy_reset_gpio.gpio, config->dr_mode);
+ config->ulpi, config->periph_id,
+ gpio_get_number(&config->vbus_gpio),
+ gpio_get_number(&config->phy_reset_gpio), config->dr_mode);
return 0;
}
diff --git a/drivers/usb/host/xhci-exynos5.c b/drivers/usb/host/xhci-exynos5.c
index b4946a3..a77c8bc 100644
--- a/drivers/usb/host/xhci-exynos5.c
+++ b/drivers/usb/host/xhci-exynos5.c
@@ -40,7 +40,7 @@
struct exynos_usb3_phy *usb3_phy;
struct xhci_hccr *hcd;
struct dwc3 *dwc3_reg;
- struct fdt_gpio_state vbus_gpio;
+ struct gpio_desc vbus_gpio;
};
static struct exynos_xhci exynos;
@@ -69,7 +69,8 @@
exynos->hcd = (struct xhci_hccr *)addr;
/* Vbus gpio */
- fdtdec_decode_gpio(blob, node, "samsung,vbus-gpio", &exynos->vbus_gpio);
+ gpio_request_by_name_nodev(blob, node, "samsung,vbus-gpio", 0,
+ &exynos->vbus_gpio, GPIOD_IS_OUT);
depth = 0;
node = fdtdec_next_compatible_subnode(blob, node,
@@ -298,9 +299,8 @@
#ifdef CONFIG_OF_CONTROL
/* setup the Vbus gpio here */
- if (fdt_gpio_isvalid(&ctx->vbus_gpio) &&
- !fdtdec_setup_gpio(&ctx->vbus_gpio))
- gpio_direction_output(ctx->vbus_gpio.gpio, 1);
+ if (dm_gpio_is_valid(&ctx->vbus_gpio))
+ dm_gpio_set_value(&ctx->vbus_gpio, 1);
#endif
ret = exynos_xhci_core_init(ctx);
diff --git a/drivers/video/sunxi_display.c b/drivers/video/sunxi_display.c
index af728b5..f5f24fc 100644
--- a/drivers/video/sunxi_display.c
+++ b/drivers/video/sunxi_display.c
@@ -645,7 +645,8 @@
return (delay > 30) ? 30 : delay;
}
-static void sunxi_lcdc_tcon0_mode_set(const struct ctfb_res_modes *mode)
+static void sunxi_lcdc_tcon0_mode_set(const struct ctfb_res_modes *mode,
+ bool for_ext_vga_dac)
{
struct sunxi_lcdc_reg * const lcdc =
(struct sunxi_lcdc_reg *)SUNXI_LCD0_BASE;
@@ -719,6 +720,11 @@
val |= SUNXI_LCDC_TCON_HSYNC_MASK;
if (!(mode->sync & FB_SYNC_VERT_HIGH_ACT))
val |= SUNXI_LCDC_TCON_VSYNC_MASK;
+
+#ifdef CONFIG_VIDEO_VGA_VIA_LCD_FORCE_SYNC_ACTIVE_HIGH
+ if (for_ext_vga_dac)
+ val = 0;
+#endif
writel(val, &lcdc->tcon0_io_polarity);
writel(0, &lcdc->tcon0_io_tristate);
@@ -1015,7 +1021,7 @@
hitachi_tx18d42vm_init();
}
sunxi_composer_mode_set(mode, address);
- sunxi_lcdc_tcon0_mode_set(mode);
+ sunxi_lcdc_tcon0_mode_set(mode, false);
sunxi_composer_enable();
sunxi_lcdc_enable();
#ifdef CONFIG_VIDEO_LCD_SSD2828
@@ -1033,7 +1039,7 @@
sunxi_vga_enable();
#elif defined CONFIG_VIDEO_VGA_VIA_LCD
sunxi_composer_mode_set(mode, address);
- sunxi_lcdc_tcon0_mode_set(mode);
+ sunxi_lcdc_tcon0_mode_set(mode, true);
sunxi_composer_enable();
sunxi_lcdc_enable();
sunxi_vga_external_dac_enable();
diff --git a/drivers/video/tegra.c b/drivers/video/tegra.c
index 57cb007..b8f3431 100644
--- a/drivers/video/tegra.c
+++ b/drivers/video/tegra.c
@@ -149,14 +149,18 @@
FDT_LCD_CACHE_WRITE_BACK_FLUSH);
/* These GPIOs are all optional */
- fdtdec_decode_gpio(blob, display_node, "nvidia,backlight-enable-gpios",
- &config->backlight_en);
- fdtdec_decode_gpio(blob, display_node, "nvidia,lvds-shutdown-gpios",
- &config->lvds_shutdown);
- fdtdec_decode_gpio(blob, display_node, "nvidia,backlight-vdd-gpios",
- &config->backlight_vdd);
- fdtdec_decode_gpio(blob, display_node, "nvidia,panel-vdd-gpios",
- &config->panel_vdd);
+ gpio_request_by_name_nodev(blob, display_node,
+ "nvidia,backlight-enable-gpios", 0,
+ &config->backlight_en, GPIOD_IS_OUT);
+ gpio_request_by_name_nodev(blob, display_node,
+ "nvidia,lvds-shutdown-gpios", 0,
+ &config->lvds_shutdown, GPIOD_IS_OUT);
+ gpio_request_by_name_nodev(blob, display_node,
+ "nvidia,backlight-vdd-gpios", 0,
+ &config->backlight_vdd, GPIOD_IS_OUT);
+ gpio_request_by_name_nodev(blob, display_node,
+ "nvidia,panel-vdd-gpios", 0,
+ &config->panel_vdd, GPIOD_IS_OUT);
return fdtdec_get_int_array(blob, display_node, "nvidia,panel-timings",
config->panel_timings, FDT_LCD_TIMINGS);
@@ -196,36 +200,18 @@
*/
funcmux_select(PERIPH_ID_DISP1, FUNCMUX_DEFAULT);
-
- fdtdec_setup_gpio(&config.panel_vdd);
- fdtdec_setup_gpio(&config.lvds_shutdown);
- fdtdec_setup_gpio(&config.backlight_vdd);
- fdtdec_setup_gpio(&config.backlight_en);
-
- /*
- * TODO: If fdt includes output flag we can omit this code
- * since fdtdec_setup_gpio will do it for us.
- */
- if (fdt_gpio_isvalid(&config.panel_vdd))
- gpio_direction_output(config.panel_vdd.gpio, 0);
- if (fdt_gpio_isvalid(&config.lvds_shutdown))
- gpio_direction_output(config.lvds_shutdown.gpio, 0);
- if (fdt_gpio_isvalid(&config.backlight_vdd))
- gpio_direction_output(config.backlight_vdd.gpio, 0);
- if (fdt_gpio_isvalid(&config.backlight_en))
- gpio_direction_output(config.backlight_en.gpio, 0);
break;
case STAGE_PANEL_VDD:
- if (fdt_gpio_isvalid(&config.panel_vdd))
- gpio_direction_output(config.panel_vdd.gpio, 1);
+ if (dm_gpio_is_valid(&config.panel_vdd))
+ dm_gpio_set_value(&config.panel_vdd, 1);
break;
case STAGE_LVDS:
- if (fdt_gpio_isvalid(&config.lvds_shutdown))
- gpio_set_value(config.lvds_shutdown.gpio, 1);
+ if (dm_gpio_is_valid(&config.lvds_shutdown))
+ dm_gpio_set_value(&config.lvds_shutdown, 1);
break;
case STAGE_BACKLIGHT_VDD:
- if (fdt_gpio_isvalid(&config.backlight_vdd))
- gpio_set_value(config.backlight_vdd.gpio, 1);
+ if (dm_gpio_is_valid(&config.backlight_vdd))
+ dm_gpio_set_value(&config.backlight_vdd, 1);
break;
case STAGE_PWM:
/* Enable PWM at 15/16 high, 32768 Hz with divider 1 */
@@ -235,8 +221,8 @@
pwm_enable(config.pwm_channel, 32768, 0xdf, 1);
break;
case STAGE_BACKLIGHT_EN:
- if (fdt_gpio_isvalid(&config.backlight_en))
- gpio_set_value(config.backlight_en.gpio, 1);
+ if (dm_gpio_is_valid(&config.backlight_en))
+ dm_gpio_set_value(&config.backlight_en, 1);
break;
case STAGE_DONE:
break;
diff --git a/examples/standalone/stubs.c b/examples/standalone/stubs.c
index 0bf690e..920a0a9 100644
--- a/examples/standalone/stubs.c
+++ b/examples/standalone/stubs.c
@@ -2,6 +2,8 @@
#include <exports.h>
#include <linux/compiler.h>
+#define FO(x) offsetof(struct jt_funcs, x)
+
#if defined(CONFIG_X86)
/*
* x86 does not have a dedicated register to store the pointer to
@@ -10,23 +12,23 @@
* from flash memory. The global_data address is passed as argv[-1]
* to the application program.
*/
-static void **jt;
+static struct jt_funcs *jt;
gd_t *global_data;
-#define EXPORT_FUNC(x) \
+#define EXPORT_FUNC(f, a, x, ...) \
asm volatile ( \
" .globl " #x "\n" \
#x ":\n" \
" movl %0, %%eax\n" \
" movl jt, %%ecx\n" \
" jmp *(%%ecx, %%eax)\n" \
- : : "i"(XF_ ## x * sizeof(void *)) : "eax", "ecx");
+ : : "i"(FO(x)) : "eax", "ecx");
#elif defined(CONFIG_PPC)
/*
* r2 holds the pointer to the global_data, r11 is a call-clobbered
* register
*/
-#define EXPORT_FUNC(x) \
+#define EXPORT_FUNC(f, a, x, ...) \
asm volatile ( \
" .globl " #x "\n" \
#x ":\n" \
@@ -34,33 +36,33 @@
" lwz %%r11, %1(%%r11)\n" \
" mtctr %%r11\n" \
" bctr\n" \
- : : "i"(offsetof(gd_t, jt)), "i"(XF_ ## x * sizeof(void *)) : "r11");
+ : : "i"(offsetof(gd_t, jt)), "i"(FO(x)) : "r11");
#elif defined(CONFIG_ARM)
#ifdef CONFIG_ARM64
/*
* x18 holds the pointer to the global_data, x9 is a call-clobbered
* register
*/
-#define EXPORT_FUNC(x) \
+#define EXPORT_FUNC(f, a, x, ...) \
asm volatile ( \
" .globl " #x "\n" \
#x ":\n" \
" ldr x9, [x18, %0]\n" \
" ldr x9, [x9, %1]\n" \
" br x9\n" \
- : : "i"(offsetof(gd_t, jt)), "i"(XF_ ## x * sizeof(void *)) : "x9");
+ : : "i"(offsetof(gd_t, jt)), "i"(FO(x)) : "x9");
#else
/*
* r9 holds the pointer to the global_data, ip is a call-clobbered
* register
*/
-#define EXPORT_FUNC(x) \
+#define EXPORT_FUNC(f, a, x, ...) \
asm volatile ( \
" .globl " #x "\n" \
#x ":\n" \
" ldr ip, [r9, %0]\n" \
" ldr pc, [ip, %1]\n" \
- : : "i"(offsetof(gd_t, jt)), "i"(XF_ ## x * sizeof(void *)) : "ip");
+ : : "i"(offsetof(gd_t, jt)), "i"(FO(x)) : "ip");
#endif
#elif defined(CONFIG_MIPS)
/*
@@ -70,19 +72,19 @@
* it; however, GCC/mips generates an additional `nop' after each asm
* statement
*/
-#define EXPORT_FUNC(x) \
+#define EXPORT_FUNC(f, a, x, ...) \
asm volatile ( \
" .globl " #x "\n" \
#x ":\n" \
" lw $25, %0($26)\n" \
" lw $25, %1($25)\n" \
" jr $25\n" \
- : : "i"(offsetof(gd_t, jt)), "i"(XF_ ## x * sizeof(void *)) : "t9");
+ : : "i"(offsetof(gd_t, jt)), "i"(FO(x)) : "t9");
#elif defined(CONFIG_NIOS2)
/*
* gp holds the pointer to the global_data, r8 is call-clobbered
*/
-#define EXPORT_FUNC(x) \
+#define EXPORT_FUNC(f, a, x, ...) \
asm volatile ( \
" .globl " #x "\n" \
#x ":\n" \
@@ -92,13 +94,13 @@
" ldw r8, 0(r8)\n" \
" ldw r8, %1(r8)\n" \
" jmp r8\n" \
- : : "i"(offsetof(gd_t, jt)), "i"(XF_ ## x * sizeof(void *)) : "gp");
+ : : "i"(offsetof(gd_t, jt)), "i"(FO(x)) : "gp");
#elif defined(CONFIG_M68K)
/*
* d7 holds the pointer to the global_data, a0 is a call-clobbered
* register
*/
-#define EXPORT_FUNC(x) \
+#define EXPORT_FUNC(f, a, x, ...) \
asm volatile ( \
" .globl " #x "\n" \
#x ":\n" \
@@ -108,50 +110,50 @@
" adda.l %1, %%a0\n" \
" move.l (%%a0), %%a0\n" \
" jmp (%%a0)\n" \
- : : "i"(offsetof(gd_t, jt)), "i"(XF_ ## x * sizeof(void *)) : "a0");
+ : : "i"(offsetof(gd_t, jt)), "i"(FO(x)) : "a0");
#elif defined(CONFIG_MICROBLAZE)
/*
* r31 holds the pointer to the global_data. r5 is a call-clobbered.
*/
-#define EXPORT_FUNC(x) \
+#define EXPORT_FUNC(f, a, x, ...) \
asm volatile ( \
" .globl " #x "\n" \
#x ":\n" \
" lwi r5, r31, %0\n" \
" lwi r5, r5, %1\n" \
" bra r5\n" \
- : : "i"(offsetof(gd_t, jt)), "i"(XF_ ## x * sizeof(void *)) : "r5");
+ : : "i"(offsetof(gd_t, jt)), "i"(FO(x)) : "r5");
#elif defined(CONFIG_BLACKFIN)
/*
* P3 holds the pointer to the global_data, P0 is a call-clobbered
* register
*/
-#define EXPORT_FUNC(x) \
+#define EXPORT_FUNC(f, a, x, ...) \
asm volatile ( \
" .globl _" #x "\n_" \
#x ":\n" \
" P0 = [P3 + %0]\n" \
" P0 = [P0 + %1]\n" \
" JUMP (P0)\n" \
- : : "i"(offsetof(gd_t, jt)), "i"(XF_ ## x * sizeof(void *)) : "P0");
+ : : "i"(offsetof(gd_t, jt)), "i"(FO(x)) : "P0");
#elif defined(CONFIG_AVR32)
/*
* r6 holds the pointer to the global_data. r8 is call clobbered.
*/
-#define EXPORT_FUNC(x) \
+#define EXPORT_FUNC(f, a, x, ...) \
asm volatile( \
" .globl\t" #x "\n" \
#x ":\n" \
" ld.w r8, r6[%0]\n" \
" ld.w pc, r8[%1]\n" \
: \
- : "i"(offsetof(gd_t, jt)), "i"(XF_ ##x) \
+ : "i"(offsetof(gd_t, jt)), "i"(FO(x)) \
: "r8");
#elif defined(CONFIG_SH)
/*
* r13 holds the pointer to the global_data. r1 is a call clobbered.
*/
-#define EXPORT_FUNC(x) \
+#define EXPORT_FUNC(f, a, x, ...) \
asm volatile ( \
" .align 2\n" \
" .globl " #x "\n" \
@@ -164,12 +166,12 @@
" jmp @r1\n" \
" nop\n" \
" nop\n" \
- : : "i"(offsetof(gd_t, jt)), "i"(XF_ ## x * sizeof(void *)) : "r1", "r2");
+ : : "i"(offsetof(gd_t, jt)), "i"(FO(x)) : "r1", "r2");
#elif defined(CONFIG_SPARC)
/*
* g7 holds the pointer to the global_data. g1 is call clobbered.
*/
-#define EXPORT_FUNC(x) \
+#define EXPORT_FUNC(f, a, x, ...) \
asm volatile( \
" .globl\t" #x "\n" \
#x ":\n" \
@@ -179,26 +181,26 @@
" ld [%%g1 + %1], %%g1\n" \
" jmp %%g1\n" \
" nop\n" \
- : : "i"(offsetof(gd_t, jt)), "i"(XF_ ## x * sizeof(void *)) : "g1" );
+ : : "i"(offsetof(gd_t, jt)), "i"(FO(x)) : "g1");
#elif defined(CONFIG_NDS32)
/*
* r16 holds the pointer to the global_data. gp is call clobbered.
* not support reduced register (16 GPR).
*/
-#define EXPORT_FUNC(x) \
+#define EXPORT_FUNC(f, a, x, ...) \
asm volatile ( \
" .globl " #x "\n" \
#x ":\n" \
" lwi $r16, [$gp + (%0)]\n" \
" lwi $r16, [$r16 + (%1)]\n" \
" jr $r16\n" \
- : : "i"(offsetof(gd_t, jt)), "i"(XF_ ## x * sizeof(void *)) : "$r16");
+ : : "i"(offsetof(gd_t, jt)), "i"(FO(x)) : "$r16");
#elif defined(CONFIG_OPENRISC)
/*
* r10 holds the pointer to the global_data, r13 is a call-clobbered
* register
*/
-#define EXPORT_FUNC(x) \
+#define EXPORT_FUNC(f, a, x, ...) \
asm volatile ( \
" .globl " #x "\n" \
#x ":\n" \
@@ -206,12 +208,12 @@
" l.lwz r13, %1(r13)\n" \
" l.jr r13\n" \
" l.nop\n" \
- : : "i"(offsetof(gd_t, jt)), "i"(XF_ ## x * sizeof(void *)) : "r13");
+ : : "i"(offsetof(gd_t, jt)), "i"(FO(x)) : "r13");
#elif defined(CONFIG_ARC)
/*
* r25 holds the pointer to the global_data. r10 is call clobbered.
*/
-#define EXPORT_FUNC(x) \
+#define EXPORT_FUNC(f, a, x, ...) \
asm volatile( \
" .align 4\n" \
" .globl " #x "\n" \
@@ -219,7 +221,7 @@
" ld r10, [r25, %0]\n" \
" ld r10, [r10, %1]\n" \
" j [r10]\n" \
- : : "i"(offsetof(gd_t, jt)), "i"(XF_ ## x * sizeof(void *)) : "r10");
+ : : "i"(offsetof(gd_t, jt)), "i"(FO(x)) : "r10");
#else
/*" addi $sp, $sp, -24\n" \
" br $r16\n" \*/
diff --git a/fs/fs.c b/fs/fs.c
index ddd751c..483273f 100644
--- a/fs/fs.c
+++ b/fs/fs.c
@@ -79,6 +79,7 @@
struct fstype_info {
int fstype;
+ char *name;
/*
* Is it legal to pass NULL as .probe()'s fs_dev_desc parameter? This
* should be false in most cases. For "virtual" filesystems which
@@ -105,6 +106,7 @@
#ifdef CONFIG_FS_FAT
{
.fstype = FS_TYPE_FAT,
+ .name = "fat",
.null_dev_desc_ok = false,
.probe = fat_set_blk_dev,
.close = fat_close,
@@ -123,6 +125,7 @@
#ifdef CONFIG_FS_EXT4
{
.fstype = FS_TYPE_EXT,
+ .name = "ext4",
.null_dev_desc_ok = false,
.probe = ext4fs_probe,
.close = ext4fs_close,
@@ -141,6 +144,7 @@
#ifdef CONFIG_SANDBOX
{
.fstype = FS_TYPE_SANDBOX,
+ .name = "sandbox",
.null_dev_desc_ok = true,
.probe = sandbox_fs_set_blk_dev,
.close = sandbox_fs_close,
@@ -154,6 +158,7 @@
#endif
{
.fstype = FS_TYPE_ANY,
+ .name = "unsupported",
.null_dev_desc_ok = true,
.probe = fs_probe_unsupported,
.close = fs_close_unsupported,
@@ -190,6 +195,7 @@
if (!relocated) {
for (i = 0, info = fstypes; i < ARRAY_SIZE(fstypes);
i++, info++) {
+ info->name += gd->reloc_off;
info->probe += gd->reloc_off;
info->close += gd->reloc_off;
info->ls += gd->reloc_off;
@@ -503,3 +509,24 @@
return CMD_RET_SUCCESS;
}
+
+int do_fs_type(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
+{
+ struct fstype_info *info;
+
+ if (argc < 3 || argc > 4)
+ return CMD_RET_USAGE;
+
+ if (fs_set_blk_dev(argv[1], argv[2], FS_TYPE_ANY))
+ return 1;
+
+ info = fs_get_info(fs_type);
+
+ if (argc == 4)
+ setenv(argv[3], info->name);
+ else
+ printf("%s\n", info->name);
+
+ return CMD_RET_SUCCESS;
+}
+
diff --git a/include/_exports.h b/include/_exports.h
index 349a3c5..5944703 100644
--- a/include/_exports.h
+++ b/include/_exports.h
@@ -1,32 +1,73 @@
/*
- * You do not need to use #ifdef around functions that may not exist
+ * You need to use #ifdef around functions that may not exist
* in the final configuration (such as i2c).
+ * use a dummyfunction as first parameter to EXPORT_FUNC.
+ * As an example see the CONFIG_CMD_I2C section below
*/
-EXPORT_FUNC(get_version)
-EXPORT_FUNC(getc)
-EXPORT_FUNC(tstc)
-EXPORT_FUNC(putc)
-EXPORT_FUNC(puts)
-EXPORT_FUNC(printf)
-EXPORT_FUNC(install_hdlr)
-EXPORT_FUNC(free_hdlr)
-EXPORT_FUNC(malloc)
-EXPORT_FUNC(free)
-EXPORT_FUNC(udelay)
-EXPORT_FUNC(get_timer)
-EXPORT_FUNC(vprintf)
-EXPORT_FUNC(do_reset)
-EXPORT_FUNC(getenv)
-EXPORT_FUNC(setenv)
-EXPORT_FUNC(simple_strtoul)
-EXPORT_FUNC(strict_strtoul)
-EXPORT_FUNC(simple_strtol)
-EXPORT_FUNC(strcmp)
-EXPORT_FUNC(i2c_write)
-EXPORT_FUNC(i2c_read)
-EXPORT_FUNC(spi_init)
-EXPORT_FUNC(spi_setup_slave)
-EXPORT_FUNC(spi_free_slave)
-EXPORT_FUNC(spi_claim_bus)
-EXPORT_FUNC(spi_release_bus)
-EXPORT_FUNC(spi_xfer)
+#ifndef EXPORT_FUNC
+#define EXPORT_FUNC(a, b, c, ...)
+#endif
+ EXPORT_FUNC(get_version, unsigned long, get_version, void)
+ EXPORT_FUNC(getc, int, getc, void)
+ EXPORT_FUNC(tstc, int, tstc, void)
+ EXPORT_FUNC(putc, void, putc, const char)
+ EXPORT_FUNC(puts, void, puts, const char *)
+ EXPORT_FUNC(printf, int, printf, const char*, ...)
+#if defined(CONFIG_X86) || defined(CONFIG_PPC)
+ EXPORT_FUNC(irq_install_handler, void, install_hdlr,
+ int, interrupt_handler_t, void*)
+
+ EXPORT_FUNC(irq_free_handler, void, free_hdlr, int)
+#else
+ EXPORT_FUNC(dummy, void, install_hdlr, void)
+ EXPORT_FUNC(dummy, void, free_hdlr, void)
+#endif
+ EXPORT_FUNC(malloc, void *, malloc, size_t)
+ EXPORT_FUNC(free, void, free, void *)
+ EXPORT_FUNC(udelay, void, udelay, unsigned long)
+ EXPORT_FUNC(get_timer, unsigned long, get_timer, unsigned long)
+ EXPORT_FUNC(vprintf, int, vprintf, const char *, va_list)
+ EXPORT_FUNC(do_reset, int, do_reset, cmd_tbl_t *,
+ int , int , char * const [])
+ EXPORT_FUNC(getenv, char *, getenv, const char*)
+ EXPORT_FUNC(setenv, int, setenv, const char *, const char *)
+ EXPORT_FUNC(simple_strtoul, unsigned long, simple_strtoul,
+ const char *, char **, unsigned int)
+ EXPORT_FUNC(strict_strtoul, int, strict_strtoul,
+ const char *, unsigned int , unsigned long *)
+ EXPORT_FUNC(simple_strtol, long, simple_strtol,
+ const char *, char **, unsigned int)
+ EXPORT_FUNC(strcmp, int, strcmp, const char *cs, const char *ct)
+#if defined(CONFIG_CMD_I2C) && \
+ (!defined(CONFIG_DM_I2C) || defined(CONFIG_DM_I2C_COMPAT))
+ EXPORT_FUNC(i2c_write, int, i2c_write, uchar, uint, int , uchar * , int)
+ EXPORT_FUNC(i2c_read, int, i2c_read, uchar, uint, int , uchar * , int)
+#else
+ EXPORT_FUNC(dummy, void, i2c_write, void)
+ EXPORT_FUNC(dummy, void, i2c_read, void)
+#endif
+
+#if !defined(CONFIG_CMD_SPI) || defined(CONFIG_DM_SPI)
+ EXPORT_FUNC(dummy, void, spi_init, void)
+ EXPORT_FUNC(dummy, void, spi_setup_slave, void)
+ EXPORT_FUNC(dummy, void, spi_free_slave, void)
+#else
+ EXPORT_FUNC(spi_init, void, spi_init, void)
+ EXPORT_FUNC(spi_setup_slave, struct spi_slave *, spi_setup_slave,
+ unsigned int, unsigned int, unsigned int, unsigned int)
+ EXPORT_FUNC(spi_free_slave, void, spi_free_slave, struct spi_slave *)
+#endif
+#ifndef CONFIG_CMD_SPI
+ EXPORT_FUNC(dummy, void, spi_claim_bus, void)
+ EXPORT_FUNC(dummy, void, spi_release_bus, void)
+ EXPORT_FUNC(dummy, void, spi_xfer, void)
+#else
+ EXPORT_FUNC(spi_claim_bus, int, spi_claim_bus, struct spi_slave *)
+ EXPORT_FUNC(spi_release_bus, void, spi_release_bus, struct spi_slave *)
+ EXPORT_FUNC(spi_xfer, int, spi_xfer, struct spi_slave *,
+ unsigned int, const void *, void *, unsigned long)
+#endif
+ EXPORT_FUNC(ustrtoul, unsigned long, ustrtoul,
+ const char *, char **, unsigned int)
+ EXPORT_FUNC(ustrtoull, unsigned long long, ustrtoull,
+ const char *, char **, unsigned int)
diff --git a/include/asm-generic/global_data.h b/include/asm-generic/global_data.h
index 3d14d5f1..6747619 100644
--- a/include/asm-generic/global_data.h
+++ b/include/asm-generic/global_data.h
@@ -73,7 +73,7 @@
const void *fdt_blob; /* Our device tree, NULL if none */
void *new_fdt; /* Relocated FDT */
unsigned long fdt_size; /* Space reserved for relocated FDT */
- void **jt; /* jump table */
+ struct jt_funcs *jt; /* jump table */
char env_buf[32]; /* buffer for getenv() before reloc. */
#ifdef CONFIG_TRACE
void *trace_buff; /* The trace buffer */
diff --git a/include/asm-generic/gpio.h b/include/asm-generic/gpio.h
index 36a36c6..3b96b82 100644
--- a/include/asm-generic/gpio.h
+++ b/include/asm-generic/gpio.h
@@ -10,6 +10,15 @@
/*
* Generic GPIO API for U-Boot
*
+ * --
+ * NB: This is deprecated. Please use the driver model functions instead:
+ *
+ * - gpio_request_by_name()
+ * - dm_gpio_get_value() etc.
+ *
+ * For now we need a dm_ prefix on some functions to avoid name collision.
+ * --
+ *
* GPIOs are numbered from 0 to GPIO_COUNT-1 which value is defined
* by the SOC/architecture.
*
@@ -26,6 +35,7 @@
*/
/**
+ * @deprecated Please use driver model instead
* Request a GPIO. This should be called before any of the other functions
* are used on this GPIO.
*
@@ -39,6 +49,7 @@
int gpio_request(unsigned gpio, const char *label);
/**
+ * @deprecated Please use driver model instead
* Stop using the GPIO. This function should not alter pin configuration.
*
* @param gpio GPIO number
@@ -47,6 +58,7 @@
int gpio_free(unsigned gpio);
/**
+ * @deprecated Please use driver model instead
* Make a GPIO an input.
*
* @param gpio GPIO number
@@ -55,6 +67,7 @@
int gpio_direction_input(unsigned gpio);
/**
+ * @deprecated Please use driver model instead
* Make a GPIO an output, and set its value.
*
* @param gpio GPIO number
@@ -64,6 +77,7 @@
int gpio_direction_output(unsigned gpio, int value);
/**
+ * @deprecated Please use driver model instead
* Get a GPIO's value. This will work whether the GPIO is an input
* or an output.
*
@@ -73,6 +87,7 @@
int gpio_get_value(unsigned gpio);
/**
+ * @deprecated Please use driver model instead
* Set an output GPIO's value. The GPIO must already be an output or
* this function may have no effect.
*
@@ -95,6 +110,34 @@
struct udevice;
+struct gpio_desc {
+ struct udevice *dev; /* Device, NULL for invalid GPIO */
+ unsigned long flags;
+#define GPIOD_REQUESTED (1 << 0) /* Requested/claimed */
+#define GPIOD_IS_OUT (1 << 1) /* GPIO is an output */
+#define GPIOD_IS_IN (1 << 2) /* GPIO is an output */
+#define GPIOD_ACTIVE_LOW (1 << 3) /* value has active low */
+#define GPIOD_IS_OUT_ACTIVE (1 << 4) /* set output active */
+
+ uint offset; /* GPIO offset within the device */
+ /*
+ * We could consider adding the GPIO label in here. Possibly we could
+ * use this structure for internal GPIO information.
+ */
+};
+
+/**
+ * dm_gpio_is_valid() - Check if a GPIO is gpio_is_valie
+ *
+ * @desc: GPIO description containing device, offset and flags,
+ * previously returned by gpio_request_by_name()
+ * @return true if valid, false if not
+ */
+static inline bool dm_gpio_is_valid(struct gpio_desc *desc)
+{
+ return desc->dev != NULL;
+}
+
/**
* gpio_get_status() - get the current GPIO status as a string
*
@@ -106,6 +149,8 @@
* which means this is GPIO bank b, offset 4, currently set to input, current
* value 1, [x] means that it is requested and the owner is 'sdmmc_cd'
*
+ * TODO(sjg@chromium.org): This should use struct gpio_desc
+ *
* @dev: Device to check
* @offset: Offset of device GPIO to check
* @buf: Place to put string
@@ -118,6 +163,8 @@
*
* Note this returns GPIOF_UNUSED if the GPIO is not requested.
*
+ * TODO(sjg@chromium.org): This should use struct gpio_desc
+ *
* @dev: Device to check
* @offset: Offset of device GPIO to check
* @namep: If non-NULL, this is set to the nane given when the GPIO
@@ -135,6 +182,8 @@
* Note this does not return GPIOF_UNUSED - it will always return the GPIO
* driver's view of a pin function, even if it is not correctly set up.
*
+ * TODO(sjg@chromium.org): This should use struct gpio_desc
+ *
* @dev: Device to check
* @offset: Offset of device GPIO to check
* @namep: If non-NULL, this is set to the nane given when the GPIO
@@ -155,6 +204,8 @@
int gpio_requestf(unsigned gpio, const char *fmt, ...)
__attribute__ ((format (__printf__, 2, 3)));
+struct fdtdec_phandle_args;
+
/**
* struct struct dm_gpio_ops - Driver model GPIO operations
*
@@ -198,6 +249,33 @@
* @return current function - GPIOF_...
*/
int (*get_function)(struct udevice *dev, unsigned offset);
+
+ /**
+ * xlate() - Translate phandle arguments into a GPIO description
+ *
+ * This function should set up the fields in desc according to the
+ * information in the arguments. The uclass will have set up:
+ *
+ * @desc->dev to @dev
+ * @desc->flags to 0
+ * @desc->offset to the value of the first argument in args, if any,
+ * otherwise -1 (which is invalid)
+ *
+ * This method is optional so if the above defaults suit it can be
+ * omitted. Typical behaviour is to set up the GPIOD_ACTIVE_LOW flag
+ * in desc->flags.
+ *
+ * Note that @dev is passed in as a parameter to follow driver model
+ * uclass conventions, even though it is already available as
+ * desc->dev.
+ *
+ * @dev: GPIO device
+ * @desc: Place to put GPIO description
+ * @args: Arguments provided in descripion
+ * @return 0 if OK, -ve on error
+ */
+ int (*xlate)(struct udevice *dev, struct gpio_desc *desc,
+ struct fdtdec_phandle_args *args);
};
/**
@@ -268,4 +346,191 @@
*/
unsigned gpio_get_values_as_int(const int *gpio_list);
+/**
+ * gpio_request_by_name() - Locate and request a GPIO by name
+ *
+ * This operates by looking up the given list name in the device (device
+ * tree property) and requesting the GPIO for use. The property must exist
+ * in @dev's node.
+ *
+ * Use @flags to specify whether the GPIO should be an input or output. In
+ * principle this can also come from the device tree binding but most
+ * bindings don't provide this information. Specifically, when the GPIO uclass
+ * calls the xlate() method, it can return default flags, which are then
+ * ORed with this @flags.
+ *
+ * If we find that requesting the GPIO is not always needed we could add a
+ * new function or a new GPIOD_NO_REQUEST flag.
+ *
+ * At present driver model has no reference counting so if one device
+ * requests a GPIO which subsequently is unbound, the @desc->dev pointer
+ * will be invalid. However this will only happen if the GPIO device is
+ * unbound, not if it is removed, so this seems like a reasonable limitation
+ * for now. There is no real use case for unbinding drivers in normal
+ * operation.
+ *
+ * The device tree binding is doc/device-tree-bindings/gpio/gpio.txt in
+ * generate terms and each specific device may add additional details in
+ * a binding file in the same directory.
+ *
+ * @dev: Device requesting the GPIO
+ * @list_name: Name of GPIO list (e.g. "board-id-gpios")
+ * @index: Index number of the GPIO in that list use request (0=first)
+ * @desc: Returns GPIO description information. If there is no such
+ * GPIO, dev->dev will be NULL.
+ * @flags: Indicates the GPIO input/output settings (GPIOD_...)
+ * @return 0 if OK, -ENOENT if the GPIO does not exist, -EINVAL if there is
+ * something wrong with the list, or other -ve for another error (e.g.
+ * -EBUSY if a GPIO was already requested)
+ */
+int gpio_request_by_name(struct udevice *dev, const char *list_name,
+ int index, struct gpio_desc *desc, int flags);
+
+/**
+ * gpio_request_list_by_name() - Request a list of GPIOs
+ *
+ * Reads all the GPIOs from a list and requetss them. See
+ * gpio_request_by_name() for additional details. Lists should not be
+ * misused to hold unrelated or optional GPIOs. They should only be used
+ * for things like parallel data lines. A zero phandle terminates the list
+ * the list.
+ *
+ * This function will either succeed, and request all GPIOs in the list, or
+ * fail and request none (it will free already-requested GPIOs in case of
+ * an error part-way through).
+ *
+ * @dev: Device requesting the GPIO
+ * @list_name: Name of GPIO list (e.g. "board-id-gpios")
+ * @desc_list: Returns a list of GPIO description information
+ * @max_count: Maximum number of GPIOs to return (@desc_list must be at least
+ * this big)
+ * @flags: Indicates the GPIO input/output settings (GPIOD_...)
+ * @return number of GPIOs requested, or -ve on error
+ */
+int gpio_request_list_by_name(struct udevice *dev, const char *list_name,
+ struct gpio_desc *desc_list, int max_count,
+ int flags);
+
+/**
+ * gpio_get_list_count() - Returns the number of GPIOs in a list
+ *
+ * Counts the GPIOs in a list. See gpio_request_by_name() for additional
+ * details.
+ *
+ * @dev: Device requesting the GPIO
+ * @list_name: Name of GPIO list (e.g. "board-id-gpios")
+ * @return number of GPIOs (0 for an empty property) or -ENOENT if the list
+ * does not exist
+ */
+int gpio_get_list_count(struct udevice *dev, const char *list_name);
+
+/**
+ * gpio_request_by_name_nodev() - request GPIOs without a device
+ *
+ * This is a version of gpio_request_list_by_name() that does not use a
+ * device. Avoid it unless the caller is not yet using driver model
+ */
+int gpio_request_by_name_nodev(const void *blob, int node,
+ const char *list_name,
+ int index, struct gpio_desc *desc, int flags);
+
+/**
+ * gpio_request_list_by_name_nodev() - request GPIOs without a device
+ *
+ * This is a version of gpio_request_list_by_name() that does not use a
+ * device. Avoid it unless the caller is not yet using driver model
+ */
+int gpio_request_list_by_name_nodev(const void *blob, int node,
+ const char *list_name,
+ struct gpio_desc *desc_list, int max_count,
+ int flags);
+
+/**
+ * dm_gpio_free() - Free a single GPIO
+ *
+ * This frees a single GPIOs previously returned from gpio_request_by_name().
+ *
+ * @dev: Device which requested the GPIO
+ * @desc: GPIO to free
+ * @return 0 if OK, -ve on error
+ */
+int dm_gpio_free(struct udevice *dev, struct gpio_desc *desc);
+
+/**
+ * gpio_free_list() - Free a list of GPIOs
+ *
+ * This frees a list of GPIOs previously returned from
+ * gpio_request_list_by_name().
+ *
+ * @dev: Device which requested the GPIOs
+ * @desc: List of GPIOs to free
+ * @count: Number of GPIOs in the list
+ * @return 0 if OK, -ve on error
+ */
+int gpio_free_list(struct udevice *dev, struct gpio_desc *desc, int count);
+
+/**
+ * gpio_free_list_nodev() - free GPIOs without a device
+ *
+ * This is a version of gpio_free_list() that does not use a
+ * device. Avoid it unless the caller is not yet using driver model
+ */
+int gpio_free_list_nodev(struct gpio_desc *desc, int count);
+
+/**
+ * dm_gpio_get_value() - Get the value of a GPIO
+ *
+ * This is the driver model version of the existing gpio_get_value() function
+ * and should be used instead of that.
+ *
+ * For now, these functions have a dm_ prefix since they conflict with
+ * existing names.
+ *
+ * @desc: GPIO description containing device, offset and flags,
+ * previously returned by gpio_request_by_name()
+ * @return GPIO value (0 for inactive, 1 for active) or -ve on error
+ */
+int dm_gpio_get_value(struct gpio_desc *desc);
+
+int dm_gpio_set_value(struct gpio_desc *desc, int value);
+
+/**
+ * dm_gpio_set_dir() - Set the direction for a GPIO
+ *
+ * This sets up the direction according tot the provided flags. It will do
+ * nothing unless the direction is actually specified.
+ *
+ * @desc: GPIO description containing device, offset and flags,
+ * previously returned by gpio_request_by_name()
+ * @return 0 if OK, -ve on error
+ */
+int dm_gpio_set_dir(struct gpio_desc *desc);
+
+/**
+ * dm_gpio_set_dir_flags() - Set direction using specific flags
+ *
+ * This is like dm_gpio_set_dir() except that the flags value is provided
+ * instead of being used from desc->flags. This is needed because in many
+ * cases the GPIO description does not include direction information.
+ * Note that desc->flags is updated by this function.
+ *
+ * @desc: GPIO description containing device, offset and flags,
+ * previously returned by gpio_request_by_name()
+ * @flags: New flags to use
+ * @return 0 if OK, -ve on error, in which case desc->flags is not updated
+ */
+int dm_gpio_set_dir_flags(struct gpio_desc *desc, ulong flags);
+
+/**
+ * gpio_get_number() - Get the global GPIO number of a GPIO
+ *
+ * This should only be used for debugging or interest. It returns the nummber
+ * that should be used for gpio_get_value() etc. to access this GPIO.
+ *
+ * @desc: GPIO description containing device, offset and flags,
+ * previously returned by gpio_request_by_name()
+ * @return GPIO number, or -ve if not found
+ */
+int gpio_get_number(struct gpio_desc *desc);
+
#endif /* _ASM_GENERIC_GPIO_H_ */
diff --git a/include/axp221.h b/include/axp221.h
index 6f24a61..a20e25c 100644
--- a/include/axp221.h
+++ b/include/axp221.h
@@ -12,7 +12,6 @@
#define AXP223_DEVICE_ADDR 0x3a3
#define AXP223_RUNTIME_ADDR 0x2d
-#define AXP223_DEVICE_MODE_DATA 0x7c3e00
/* Page 0 addresses */
#define AXP221_CHIP_ID 0x03
diff --git a/include/common.h b/include/common.h
index 4b3e0d3..97c8f79 100644
--- a/include/common.h
+++ b/include/common.h
@@ -228,12 +228,13 @@
extern char console_buffer[];
/* arch/$(ARCH)/lib/board.c */
-void board_init_f(ulong);
-void board_init_r (gd_t *, ulong) __attribute__ ((noreturn));
-int checkboard (void);
-int checkflash (void);
-int checkdram (void);
-int last_stage_init(void);
+void board_init_f(ulong);
+void board_init_r(gd_t *, ulong) __attribute__ ((noreturn));
+int checkboard(void);
+int show_board_info(void);
+int checkflash(void);
+int checkdram(void);
+int last_stage_init(void);
extern ulong monitor_flash_len;
int mac_read_from_eeprom(void);
extern u8 __dtb_dt_begin[]; /* embedded device tree blob */
diff --git a/include/config_distro_bootcmd.h b/include/config_distro_bootcmd.h
index becbe3f..49674f4 100644
--- a/include/config_distro_bootcmd.h
+++ b/include/config_distro_bootcmd.h
@@ -13,7 +13,7 @@
#define BOOTENV_SHARED_BLKDEV_BODY(devtypel) \
"if " #devtypel " dev ${devnum}; then " \
"setenv devtype " #devtypel "; " \
- "run scan_dev_for_boot; " \
+ "run scan_dev_for_boot_part; " \
"fi\0"
#define BOOTENV_SHARED_BLKDEV(devtypel) \
@@ -110,7 +110,7 @@
#define BOOTENV_DEV_DHCP(devtypeu, devtypel, instance) \
"bootcmd_dhcp=" \
BOOTENV_RUN_USB_INIT \
- "if dhcp ${scriptaddr} boot.scr.uimg; then " \
+ "if dhcp ${scriptaddr} ${boot_script_dhcp}; then " \
"source ${scriptaddr}; " \
"fi\0"
#define BOOTENV_DEV_NAME_DHCP(devtypeu, devtypel, instance) \
@@ -154,8 +154,8 @@
BOOTENV_SHARED_IDE \
"boot_prefixes=/ /boot/\0" \
"boot_scripts=boot.scr.uimg boot.scr\0" \
+ "boot_script_dhcp=boot.scr.uimg\0" \
BOOTENV_BOOT_TARGETS \
- "bootpart=1\0" \
\
"boot_extlinux=" \
"sysboot ${devtype} ${devnum}:${bootpart} any " \
@@ -186,17 +186,30 @@
"done\0" \
\
"scan_dev_for_boot=" \
- "echo Scanning ${devtype} ${devnum}...; " \
+ "echo Scanning ${devtype} ${devnum}:${bootpart}...; " \
"for prefix in ${boot_prefixes}; do " \
"run scan_dev_for_extlinux; " \
"run scan_dev_for_scripts; " \
"done\0" \
\
+ "scan_dev_for_boot_part=" \
+ "part list ${devtype} ${devnum} devplist; " \
+ "for bootpart in ${devplist}; do " \
+ "if fstype ${devtype} ${devnum}:${bootpart} " \
+ "bootfstype; then " \
+ "run scan_dev_for_boot; " \
+ "fi; " \
+ "done\0" \
+ \
BOOT_TARGET_DEVICES(BOOTENV_DEV) \
\
- "bootcmd=" BOOTENV_SET_SCSI_NEED_INIT \
+ "distro_bootcmd=" BOOTENV_SET_SCSI_NEED_INIT \
"for target in ${boot_targets}; do " \
"run bootcmd_${target}; " \
"done\0"
+#ifndef CONFIG_BOOTCOMMAND
+#define CONFIG_BOOTCOMMAND "run distro_bootcmd"
+#endif
+
#endif /* _CONFIG_CMD_DISTRO_BOOTCMD_H */
diff --git a/include/configs/am335x_evm.h b/include/configs/am335x_evm.h
index d5e84ab..f1c270c 100644
--- a/include/configs/am335x_evm.h
+++ b/include/configs/am335x_evm.h
@@ -19,13 +19,11 @@
#include <configs/ti_am335x_common.h>
#ifndef CONFIG_SPL_BUILD
+#ifndef CONFIG_FIT
# define CONFIG_FIT
+#endif
# define CONFIG_TIMESTAMP
# define CONFIG_LZO
-# ifdef CONFIG_ENABLE_VBOOT
-# define CONFIG_FIT_SIGNATURE
-# define CONFIG_RSA
-# endif
#endif
#define CONFIG_SYS_BOOTM_LEN (16 << 20)
diff --git a/include/configs/arndale.h b/include/configs/arndale.h
index d68993b..3ad4a9b 100644
--- a/include/configs/arndale.h
+++ b/include/configs/arndale.h
@@ -51,8 +51,6 @@
/* PMIC */
#define CONFIG_PMIC
#define CONFIG_POWER_I2C
-#define CONFIG_POWER_MAX77686
-
#define CONFIG_PREBOOT
diff --git a/include/configs/bct-brettl2.h b/include/configs/bct-brettl2.h
index 39982ef..2e0e922 100644
--- a/include/configs/bct-brettl2.h
+++ b/include/configs/bct-brettl2.h
@@ -97,7 +97,7 @@
#define CONFIG_ENV_IS_IN_FLASH 1
#define CONFIG_ENV_OFFSET 0x4000
#define CONFIG_ENV_SIZE 0x2000
-#define CONFIG_ENV_SECT_SIZE 0x10000
+#define CONFIG_ENV_SECT_SIZE 0x12000
#if (CONFIG_BFIN_BOOT_MODE == BFIN_BOOT_BYPASS)
#define ENV_IS_EMBEDDED
diff --git a/include/configs/exynos5-common.h b/include/configs/exynos5-common.h
index ad63f3c..0ba39a2 100644
--- a/include/configs/exynos5-common.h
+++ b/include/configs/exynos5-common.h
@@ -126,12 +126,11 @@
#define SPI_FLASH_UBOOT_POS (CONFIG_SEC_FW_SIZE + CONFIG_BL1_SIZE)
/* I2C */
-#define CONFIG_SYS_I2C_INIT_BOARD
-#define CONFIG_SYS_I2C
+#define CONFIG_DM_I2C
+#define CONFIG_DM_I2C_COMPAT
#define CONFIG_CMD_I2C
-#define CONFIG_SYS_I2C_S3C24X0_SPEED 100000 /* 100 Kbps */
#define CONFIG_SYS_I2C_S3C24X0
-#define CONFIG_I2C_MULTI_BUS
+#define CONFIG_SYS_I2C_S3C24X0_SPEED 100000 /* 100 Kbps */
#define CONFIG_SYS_I2C_S3C24X0_SLAVE 0x0
#define CONFIG_I2C_EDID
diff --git a/include/configs/exynos5250-common.h b/include/configs/exynos5250-common.h
index 6714313..ae0e5ff 100644
--- a/include/configs/exynos5250-common.h
+++ b/include/configs/exynos5250-common.h
@@ -28,9 +28,6 @@
#define CONFIG_SYS_INIT_SP_ADDR CONFIG_IRAM_STACK
-/* PMIC */
-#define CONFIG_POWER_MAX77686
-
/* Sound */
#define CONFIG_CMD_SOUND
#ifdef CONFIG_CMD_SOUND
diff --git a/include/configs/ibf-dsp561.h b/include/configs/ibf-dsp561.h
index ac5ca9a..2a937c6 100644
--- a/include/configs/ibf-dsp561.h
+++ b/include/configs/ibf-dsp561.h
@@ -82,7 +82,7 @@
#define CONFIG_ENV_OFFSET 0x4000
#define CONFIG_ENV_ADDR (CONFIG_SYS_FLASH_BASE + CONFIG_ENV_OFFSET)
#define CONFIG_ENV_SIZE 0x2000
-#define CONFIG_ENV_SECT_SIZE 0x10000 /* Total Size of Environment Sector */
+#define CONFIG_ENV_SECT_SIZE 0x12000 /* Total Size of Environment Sector */
#if (CONFIG_BFIN_BOOT_MODE == BFIN_BOOT_BYPASS)
#define ENV_IS_EMBEDDED
#else
diff --git a/include/configs/ids8313.h b/include/configs/ids8313.h
index f084834..2384864 100644
--- a/include/configs/ids8313.h
+++ b/include/configs/ids8313.h
@@ -575,12 +575,9 @@
#define CONFIG_VERSION_VARIABLE
-#define CONFIG_FIT
-#define CONFIG_FIT_SIGNATURE
#define CONFIG_IMAGE_FORMAT_LEGACY
#define CONFIG_CMD_FDT
#define CONFIG_CMD_HASH
-#define CONFIG_RSA
#define CONFIG_SHA1
#define CONFIG_SHA256
diff --git a/include/configs/ip04.h b/include/configs/ip04.h
index ec510bd..2ee215f 100644
--- a/include/configs/ip04.h
+++ b/include/configs/ip04.h
@@ -61,7 +61,7 @@
#define CONFIG_EBIU_AMBCTL0_VAL 0xffc2ffc2
#define CONFIG_EBIU_AMBCTL1_VAL 0xffc2ffc2
-#define CONFIG_SYS_MONITOR_LEN (256 * 1024)
+#define CONFIG_SYS_MONITOR_LEN (384 * 1024)
#define CONFIG_SYS_MALLOC_LEN (128 * 1024)
diff --git a/include/configs/malta.h b/include/configs/malta.h
index 684d249..354672e 100644
--- a/include/configs/malta.h
+++ b/include/configs/malta.h
@@ -71,6 +71,7 @@
sizeof(CONFIG_SYS_PROMPT) + 16)
#define CONFIG_SYS_MAXARGS 16
+#define CONFIG_SYS_HUSH_PARSER
#define CONFIG_AUTO_COMPLETE
#define CONFIG_CMDLINE_EDITING
@@ -107,6 +108,16 @@
(CONFIG_SYS_FLASH_BASE + (4 << 20) - CONFIG_ENV_SIZE)
/*
+ * IDE/ATA
+ */
+#define CONFIG_SYS_IDE_MAXBUS 1
+#define CONFIG_SYS_IDE_MAXDEVICE 2
+#define CONFIG_SYS_ATA_BASE_ADDR CONFIG_SYS_ISA_IO_BASE_ADDRESS
+#define CONFIG_SYS_ATA_IDE0_OFFSET 0x01f0
+#define CONFIG_SYS_ATA_DATA_OFFSET 0
+#define CONFIG_SYS_ATA_REG_OFFSET 0
+
+/*
* Commands
*/
#include <config_cmd_default.h>
@@ -118,6 +129,8 @@
#define CONFIG_CMD_DATE
#define CONFIG_CMD_DHCP
+#define CONFIG_CMD_ELF
+#define CONFIG_CMD_IDE
#define CONFIG_CMD_PCI
#define CONFIG_CMD_PING
diff --git a/include/configs/odroid.h b/include/configs/odroid.h
index 807e96b..9d5dbdc 100644
--- a/include/configs/odroid.h
+++ b/include/configs/odroid.h
@@ -177,12 +177,11 @@
/* I2C */
#define CONFIG_CMD_I2C
-#define CONFIG_SYS_I2C
+#define CONFIG_DM_I2C
+#define CONFIG_DM_I2C_COMPAT
#define CONFIG_SYS_I2C_S3C24X0
#define CONFIG_SYS_I2C_S3C24X0_SPEED 100000
#define CONFIG_SYS_I2C_S3C24X0_SLAVE 0
-#define CONFIG_MAX_I2C_NUM 8
-#define CONFIG_SYS_I2C_INIT_BOARD
/* POWER */
#define CONFIG_POWER
diff --git a/include/configs/sandbox.h b/include/configs/sandbox.h
index 657f751..e9d3f32 100644
--- a/include/configs/sandbox.h
+++ b/include/configs/sandbox.h
@@ -23,7 +23,6 @@
#define CONFIG_BOOTSTAGE
#define CONFIG_BOOTSTAGE_REPORT
-#define CONFIG_DM
#define CONFIG_CMD_DEMO
#define CONFIG_CMD_DM
#define CONFIG_DM_DEMO
@@ -41,9 +40,6 @@
#define CONFIG_OF_LIBFDT
#define CONFIG_LMB
-#define CONFIG_FIT
-#define CONFIG_FIT_SIGNATURE
-#define CONFIG_RSA
#define CONFIG_CMD_FDT
#define CONFIG_ANDROID_BOOT_IMAGE
diff --git a/include/configs/smdk5250.h b/include/configs/smdk5250.h
index 8395372..3b06d30 100644
--- a/include/configs/smdk5250.h
+++ b/include/configs/smdk5250.h
@@ -18,6 +18,8 @@
#include <configs/exynos5250-common.h>
+/* PMIC */
+#define CONFIG_POWER_MAX77686
#define CONFIG_BOARD_COMMON
#define CONFIG_ARCH_EARLY_INIT_R
diff --git a/include/configs/snow.h b/include/configs/snow.h
index 7eaa586..ce6676e 100644
--- a/include/configs/snow.h
+++ b/include/configs/snow.h
@@ -22,6 +22,7 @@
#define CONFIG_CROS_EC_I2C /* Support CROS_EC over I2C */
#define CONFIG_POWER_TPS65090_I2C
+#define CONFIG_DM_CROS_EC
#define CONFIG_BOARD_COMMON
#define CONFIG_ARCH_EARLY_INIT_R
diff --git a/include/configs/sunxi-common.h b/include/configs/sunxi-common.h
index 4a5cab2..6cfd7e1 100644
--- a/include/configs/sunxi-common.h
+++ b/include/configs/sunxi-common.h
@@ -181,7 +181,10 @@
#define CONFIG_SYS_SPL_MALLOC_SIZE 0x00080000 /* 512 KiB */
/* I2C */
+#if defined CONFIG_AXP152_POWER || defined CONFIG_AXP209_POWER
#define CONFIG_SPL_I2C_SUPPORT
+#endif
+
#define CONFIG_SYS_I2C
#define CONFIG_SYS_I2C_MVTWSI
#define CONFIG_SYS_I2C_SPEED 400000
diff --git a/include/configs/ti_am335x_common.h b/include/configs/ti_am335x_common.h
index 5ed86d9..598526b 100644
--- a/include/configs/ti_am335x_common.h
+++ b/include/configs/ti_am335x_common.h
@@ -20,7 +20,9 @@
#define CONFIG_SPL_AM33XX_ENABLE_RTC32K_OSC
#ifndef CONFIG_SPL_BUILD
+#ifndef CONFIG_DM
# define CONFIG_DM
+#endif
# define CONFIG_CMD_DM
# define CONFIG_DM_GPIO
# define CONFIG_DM_SERIAL
diff --git a/include/configs/uniphier.h b/include/configs/uniphier.h
index 5a53c50..9ad47f6 100644
--- a/include/configs/uniphier.h
+++ b/include/configs/uniphier.h
@@ -43,6 +43,9 @@
#define CONFIG_SDRAM1_SIZE 0x10000000
#endif
+#define CONFIG_I2C_EEPROM
+#define CONFIG_SYS_EEPROM_PAGE_WRITE_DELAY_MS 10
+
/*
* Support card address map
*/
diff --git a/include/configs/vexpress_aemv8a.h b/include/configs/vexpress_aemv8a.h
index 027d78b..7fb28a5 100644
--- a/include/configs/vexpress_aemv8a.h
+++ b/include/configs/vexpress_aemv8a.h
@@ -11,9 +11,9 @@
/* We use generic board for v8 Versatile Express */
#define CONFIG_SYS_GENERIC_BOARD
-#ifdef CONFIG_BASE_FVP
+#ifdef CONFIG_TARGET_VEXPRESS64_BASE_FVP
#ifndef CONFIG_SEMIHOSTING
-#error CONFIG_BASE_FVP requires CONFIG_SEMIHOSTING
+#error CONFIG_TARGET_VEXPRESS64_BASE_FVP requires CONFIG_SEMIHOSTING
#endif
#define CONFIG_BOARD_LATE_INIT
#define CONFIG_ARMV8_SWITCH_TO_EL1
@@ -21,8 +21,9 @@
#define CONFIG_REMAKE_ELF
-#ifndef CONFIG_BASE_FVP
-/* Base FVP not using GICv3 yet */
+#if !defined(CONFIG_TARGET_VEXPRESS64_BASE_FVP) && \
+ !defined(CONFIG_TARGET_VEXPRESS64_JUNO)
+/* Base FVP and Juno not using GICv3 yet */
#define CONFIG_GICV3
#endif
@@ -40,10 +41,13 @@
#define CONFIG_BOOTP_VCI_STRING "U-boot.armv8.vexpress_aemv8a"
/* Link Definitions */
-#ifdef CONFIG_BASE_FVP
+#ifdef CONFIG_TARGET_VEXPRESS64_BASE_FVP
/* ATF loads u-boot here for BASE_FVP model */
#define CONFIG_SYS_TEXT_BASE 0x88000000
#define CONFIG_SYS_INIT_SP_ADDR (CONFIG_SYS_SDRAM_BASE + 0x03f00000)
+#elif CONFIG_TARGET_VEXPRESS64_JUNO
+#define CONFIG_SYS_TEXT_BASE 0xe0000000
+#define CONFIG_SYS_INIT_SP_ADDR (CONFIG_SYS_SDRAM_BASE + 0x7fff0)
#else
#define CONFIG_SYS_TEXT_BASE 0x80000000
#define CONFIG_SYS_INIT_SP_ADDR (CONFIG_SYS_SDRAM_BASE + 0x7fff0)
@@ -54,7 +58,7 @@
/* SMP Spin Table Definitions */
-#ifdef CONFIG_BASE_FVP
+#ifdef CONFIG_TARGET_VEXPRESS64_BASE_FVP
#define CPU_RELEASE_ADDR (CONFIG_SYS_SDRAM_BASE + 0x03f00000)
#else
#define CPU_RELEASE_ADDR (CONFIG_SYS_SDRAM_BASE + 0x7fff0)
@@ -88,10 +92,15 @@
#define V2M_KMI0 (V2M_PA_CS3 + V2M_PERIPH_OFFSET(6))
#define V2M_KMI1 (V2M_PA_CS3 + V2M_PERIPH_OFFSET(7))
+#ifdef CONFIG_TARGET_VEXPRESS64_JUNO
+#define V2M_UART0 0x7ff80000
+#define V2M_UART1 0x7ff70000
+#else /* Not Juno */
#define V2M_UART0 (V2M_PA_CS3 + V2M_PERIPH_OFFSET(9))
#define V2M_UART1 (V2M_PA_CS3 + V2M_PERIPH_OFFSET(10))
#define V2M_UART2 (V2M_PA_CS3 + V2M_PERIPH_OFFSET(11))
#define V2M_UART3 (V2M_PA_CS3 + V2M_PERIPH_OFFSET(12))
+#endif
#define V2M_WDT (V2M_PA_CS3 + V2M_PERIPH_OFFSET(15))
@@ -119,9 +128,12 @@
#define GICR_BASE (0x2f100000)
#else
-#ifdef CONFIG_BASE_FVP
+#ifdef CONFIG_TARGET_VEXPRESS64_BASE_FVP
#define GICD_BASE (0x2f000000)
#define GICC_BASE (0x2c000000)
+#elif CONFIG_TARGET_VEXPRESS64_JUNO
+#define GICD_BASE (0x2C010000)
+#define GICC_BASE (0x2C02f000)
#else
#define GICD_BASE (0x2C001000)
#define GICC_BASE (0x2C002000)
@@ -140,7 +152,11 @@
/* PL011 Serial Configuration */
#define CONFIG_PL011_SERIAL
+#ifdef CONFIG_TARGET_VEXPRESS64_JUNO
+#define CONFIG_PL011_CLOCK 7273800
+#else
#define CONFIG_PL011_CLOCK 24000000
+#endif
#define CONFIG_PL01x_PORTS {(void *)CONFIG_SYS_SERIAL0, \
(void *)CONFIG_SYS_SERIAL1}
#define CONFIG_CONS_INDEX 0
@@ -161,6 +177,7 @@
#define CONFIG_CMD_ENV
#define CONFIG_CMD_FLASH
#define CONFIG_CMD_IMI
+#define CONFIG_CMD_LOADB
#define CONFIG_CMD_MEMORY
#define CONFIG_CMD_MII
#define CONFIG_CMD_NET
@@ -191,7 +208,7 @@
#define CONFIG_SYS_SDRAM_BASE PHYS_SDRAM_1
/* Initial environment variables */
-#ifdef CONFIG_BASE_FVP
+#ifdef CONFIG_TARGET_VEXPRESS64_BASE_FVP
#define CONFIG_EXTRA_ENV_SETTINGS \
"kernel_name=uImage\0" \
"kernel_addr_r=0x80000000\0" \
diff --git a/include/configs/vexpress_common.h b/include/configs/vexpress_common.h
index 7e78f8a..2dea921 100644
--- a/include/configs/vexpress_common.h
+++ b/include/configs/vexpress_common.h
@@ -122,7 +122,7 @@
#define CONFIG_SETUP_MEMORY_TAGS 1
#define CONFIG_SYS_L2CACHE_OFF 1
#define CONFIG_INITRD_TAG 1
-
+#define CONFIG_SYS_GENERIC_BOARD
#define CONFIG_OF_LIBFDT 1
/* Size of malloc() pool */
diff --git a/include/configs/zynq-common.h b/include/configs/zynq-common.h
index 2d28e89..864528a 100644
--- a/include/configs/zynq-common.h
+++ b/include/configs/zynq-common.h
@@ -276,17 +276,11 @@
#define CONFIG_OF_LIBFDT
/* FIT support */
-#define CONFIG_FIT
-#define CONFIG_FIT_VERBOSE 1 /* enable fit_format_{error,warning}() */
#define CONFIG_IMAGE_FORMAT_LEGACY /* enable also legacy image format */
/* FDT support */
#define CONFIG_DISPLAY_BOARDINFO_LATE
-/* RSA support */
-#define CONFIG_FIT_SIGNATURE
-#define CONFIG_RSA
-
/* Extend size of kernel image for uncompression */
#define CONFIG_SYS_BOOTM_LEN (60 * 1024 * 1024)
diff --git a/include/cros_ec.h b/include/cros_ec.h
index 9e13146..8457c80 100644
--- a/include/cros_ec.h
+++ b/include/cros_ec.h
@@ -13,6 +13,7 @@
#include <ec_commands.h>
#include <fdtdec.h>
#include <cros_ec_message.h>
+#include <asm/gpio.h>
#ifndef CONFIG_DM_CROS_EC
/* Which interface is the device on? */
@@ -39,7 +40,7 @@
unsigned int bus_num; /* Bus number (for I2C) */
unsigned int max_frequency; /* Maximum interface frequency */
#endif
- struct fdt_gpio_state ec_int; /* GPIO used as EC interrupt line */
+ struct gpio_desc ec_int; /* GPIO used as EC interrupt line */
int protocol_version; /* Protocol version to use */
int optimise_flash_write; /* Don't write erased flash blocks */
diff --git a/include/dm-demo.h b/include/dm-demo.h
index a24fec6..03722d0 100644
--- a/include/dm-demo.h
+++ b/include/dm-demo.h
@@ -25,10 +25,14 @@
struct demo_ops {
int (*hello)(struct udevice *dev, int ch);
int (*status)(struct udevice *dev, int *status);
+ int (*set_light)(struct udevice *dev, int light);
+ int (*get_light)(struct udevice *dev);
};
int demo_hello(struct udevice *dev, int ch);
int demo_status(struct udevice *dev, int *status);
+int demo_set_light(struct udevice *dev, int light);
+int demo_get_light(struct udevice *dev);
int demo_list(void);
int demo_parse_dt(struct udevice *dev);
diff --git a/include/dm/device.h b/include/dm/device.h
index 13598a1..81afa8c 100644
--- a/include/dm/device.h
+++ b/include/dm/device.h
@@ -26,6 +26,9 @@
/* DM should init this device prior to relocation */
#define DM_FLAG_PRE_RELOC (1 << 2)
+/* DM is responsible for allocating and freeing parent_platdata */
+#define DM_FLAG_ALLOC_PARENT_PDATA (1 << 3)
+
/**
* struct udevice - An instance of a driver
*
@@ -46,6 +49,7 @@
* @driver: The driver used by this device
* @name: Name of device, typically the FDT node name
* @platdata: Configuration data for this device
+ * @parent_platdata: The parent bus's configuration data for this device
* @of_offset: Device tree node offset for this device (- for none)
* @of_id: Pointer to the udevice_id structure which created the device
* @parent: Parent of this device, or NULL for the top level device
@@ -65,6 +69,7 @@
struct driver *driver;
const char *name;
void *platdata;
+ void *parent_platdata;
int of_offset;
const struct udevice_id *of_id;
struct udevice *parent;
@@ -127,6 +132,7 @@
* @remove: Called to remove a device, i.e. de-activate it
* @unbind: Called to unbind a device from its driver
* @ofdata_to_platdata: Called before probe to decode device tree data
+ * @child_post_bind: Called after a new child has been bound
* @child_pre_probe: Called before a child device is probed. The device has
* memory allocated but it has not yet been probed.
* @child_post_remove: Called after a child device is removed. The device
@@ -146,6 +152,9 @@
* device_probe_child() pass it in. So far the use case for allocating it
* is SPI, but I found that unsatisfactory. Since it is here I will leave it
* until things are clearer.
+ * @per_child_platdata_auto_alloc_size: A bus likes to store information about
+ * its children. If non-zero this is the size of this data, to be allocated
+ * in the child's parent_platdata pointer.
* @ops: Driver-specific operations. This is typically a list of function
* pointers defined by the driver, to implement driver functions required by
* the uclass.
@@ -160,11 +169,13 @@
int (*remove)(struct udevice *dev);
int (*unbind)(struct udevice *dev);
int (*ofdata_to_platdata)(struct udevice *dev);
+ int (*child_post_bind)(struct udevice *dev);
int (*child_pre_probe)(struct udevice *dev);
int (*child_post_remove)(struct udevice *dev);
int priv_auto_alloc_size;
int platdata_auto_alloc_size;
int per_child_auto_alloc_size;
+ int per_child_platdata_auto_alloc_size;
const void *ops; /* driver-specific operations */
uint32_t flags;
};
@@ -184,6 +195,16 @@
void *dev_get_platdata(struct udevice *dev);
/**
+ * dev_get_parent_platdata() - Get the parent platform data for a device
+ *
+ * This checks that dev is not NULL, but no other checks for now
+ *
+ * @dev Device to check
+ * @return parent's platform data, or NULL if none
+ */
+void *dev_get_parent_platdata(struct udevice *dev);
+
+/**
* dev_get_parentdata() - Get the parent data for a device
*
* The parent data is data stored in the device but owned by the parent.
@@ -224,6 +245,14 @@
*/
ulong dev_get_of_data(struct udevice *dev);
+/*
+ * device_get_uclass_id() - return the uclass ID of a device
+ *
+ * @dev: Device to check
+ * @return uclass ID for the device
+ */
+enum uclass_id device_get_uclass_id(struct udevice *dev);
+
/**
* device_get_child() - Get the child of a device by index
*
diff --git a/include/dm/test.h b/include/dm/test.h
index f08c05d..707c69e 100644
--- a/include/dm/test.h
+++ b/include/dm/test.h
@@ -67,6 +67,8 @@
struct dm_test_priv {
int ping_total;
int op_count[DM_TEST_OP_COUNT];
+ int uclass_flag;
+ int uclass_total;
};
/**
@@ -88,6 +90,7 @@
*
* @sum: Test value used to check parent data works correctly
* @flag: Used to track calling of parent operations
+ * @uclass_flag: Used to track calling of parent operations by uclass
*/
struct dm_test_parent_data {
int sum;
diff --git a/include/dm/uclass-id.h b/include/dm/uclass-id.h
index f17c3c2..91bb90d 100644
--- a/include/dm/uclass-id.h
+++ b/include/dm/uclass-id.h
@@ -33,6 +33,7 @@
UCLASS_I2C, /* I2C bus */
UCLASS_I2C_GENERIC, /* Generic I2C device */
UCLASS_I2C_EEPROM, /* I2C EEPROM device */
+ UCLASS_MOD_EXP, /* RSA Mod Exp device */
UCLASS_COUNT,
UCLASS_INVALID = -1,
diff --git a/include/dm/uclass-internal.h b/include/dm/uclass-internal.h
index f718f37..f2f254a 100644
--- a/include/dm/uclass-internal.h
+++ b/include/dm/uclass-internal.h
@@ -44,6 +44,17 @@
int uclass_unbind_device(struct udevice *dev);
/**
+ * uclass_pre_probe_child() - Deal with a child that is about to be probed
+ *
+ * Perform any pre-processing that is needed by the uclass before it can be
+ * probed.
+ *
+ * @dev: Pointer to the device
+ * #return 0 on success, -ve on error
+ */
+int uclass_pre_probe_child(struct udevice *dev);
+
+/**
* uclass_post_probe_device() - Deal with a device that has just been probed
*
* Perform any post-processing of a probed device that is needed by the
diff --git a/include/dm/uclass.h b/include/dm/uclass.h
index f6ec6d7..d6c40c6 100644
--- a/include/dm/uclass.h
+++ b/include/dm/uclass.h
@@ -40,6 +40,9 @@
struct udevice;
+/* Members of this uclass sequence themselves with aliases */
+#define DM_UC_FLAG_SEQ_ALIAS (1 << 0)
+
/**
* struct uclass_driver - Driver for the uclass
*
@@ -52,6 +55,7 @@
* @pre_unbind: Called before a device is unbound from this uclass
* @post_probe: Called after a new device is probed
* @pre_remove: Called before a device is removed
+ * @child_post_bind: Called after a child is bound to a device in this uclass
* @init: Called to set up the uclass
* @destroy: Called to destroy the uclass
* @priv_auto_alloc_size: If non-zero this is the size of the private data
@@ -60,8 +64,16 @@
* @per_device_auto_alloc_size: Each device can hold private data owned
* by the uclass. If required this will be automatically allocated if this
* value is non-zero.
+ * @per_child_auto_alloc_size: Each child device (of a parent in this
+ * uclass) can hold parent data for the device/uclass. This value is only
+ * used as a falback if this member is 0 in the driver.
+ * @per_child_platdata_auto_alloc_size: A bus likes to store information about
+ * its children. If non-zero this is the size of this data, to be allocated
+ * in the child device's parent_platdata pointer. This value is only used as
+ * a falback if this member is 0 in the driver.
* @ops: Uclass operations, providing the consistent interface to devices
* within the uclass.
+ * @flags: Flags for this uclass (DM_UC_...)
*/
struct uclass_driver {
const char *name;
@@ -70,11 +82,16 @@
int (*pre_unbind)(struct udevice *dev);
int (*post_probe)(struct udevice *dev);
int (*pre_remove)(struct udevice *dev);
+ int (*child_post_bind)(struct udevice *dev);
+ int (*child_pre_probe)(struct udevice *dev);
int (*init)(struct uclass *class);
int (*destroy)(struct uclass *class);
int priv_auto_alloc_size;
int per_device_auto_alloc_size;
+ int per_child_auto_alloc_size;
+ int per_child_platdata_auto_alloc_size;
const void *ops;
+ uint32_t flags;
};
/* Declare a new uclass_driver */
@@ -141,6 +158,8 @@
/**
* uclass_first_device() - Get the first device in a uclass
*
+ * The device returned is probed if necessary, and ready for use
+ *
* @id: Uclass ID to look up
* @devp: Returns pointer to the first device in that uclass, or NULL if none
* @return 0 if OK (found or not found), -1 on error
@@ -150,6 +169,8 @@
/**
* uclass_next_device() - Get the next device in a uclass
*
+ * The device returned is probed if necessary, and ready for use
+ *
* @devp: On entry, pointer to device to lookup. On exit, returns pointer
* to the next device in the same uclass, or NULL if none
* @return 0 if OK (found or not found), -1 on error
diff --git a/include/exports.h b/include/exports.h
index 41d5085..205affe 100644
--- a/include/exports.h
+++ b/include/exports.h
@@ -3,6 +3,8 @@
#ifndef __ASSEMBLY__
+struct spi_slave;
+
/* These are declarations of exported functions available in C code */
unsigned long get_version(void);
int getc(void);
@@ -10,22 +12,23 @@
void putc(const char);
void puts(const char*);
int printf(const char* fmt, ...);
-void install_hdlr(int, void (*interrupt_handler_t)(void *), void*);
+void install_hdlr(int, interrupt_handler_t, void*);
void free_hdlr(int);
void *malloc(size_t);
void free(void*);
void __udelay(unsigned long);
unsigned long get_timer(unsigned long);
int vprintf(const char *, va_list);
-unsigned long simple_strtoul(const char *cp,char **endp,unsigned int base);
+unsigned long simple_strtoul(const char *cp, char **endp, unsigned int base);
int strict_strtoul(const char *cp, unsigned int base, unsigned long *res);
char *getenv (const char *name);
int setenv (const char *varname, const char *varvalue);
-long simple_strtol(const char *cp,char **endp,unsigned int base);
-int strcmp(const char * cs,const char * ct);
+long simple_strtol(const char *cp, char **endp, unsigned int base);
+int strcmp(const char *cs, const char *ct);
unsigned long ustrtoul(const char *cp, char **endp, unsigned int base);
unsigned long long ustrtoull(const char *cp, char **endp, unsigned int base);
-#if defined(CONFIG_CMD_I2C)
+#if defined(CONFIG_CMD_I2C) && \
+ (!defined(CONFIG_DM_I2C) || defined(CONFIG_DM_I2C_COMPAT))
int i2c_write (uchar, uint, int , uchar* , int);
int i2c_read (uchar, uint, int , uchar* , int);
#endif
@@ -34,15 +37,14 @@
#endif /* ifndef __ASSEMBLY__ */
-enum {
-#define EXPORT_FUNC(x) XF_ ## x ,
+struct jt_funcs {
+#define EXPORT_FUNC(impl, res, func, ...) res(*func)(__VA_ARGS__);
#include <_exports.h>
#undef EXPORT_FUNC
-
- XF_MAX
};
-#define XF_VERSION 6
+
+#define XF_VERSION 7
#if defined(CONFIG_X86)
extern gd_t *global_data;
diff --git a/include/fdtdec.h b/include/fdtdec.h
index 8c2bd21..231eed7 100644
--- a/include/fdtdec.h
+++ b/include/fdtdec.h
@@ -115,9 +115,6 @@
COMPAT_NVIDIA_TEGRA20_USB, /* Tegra20 USB port */
COMPAT_NVIDIA_TEGRA30_USB, /* Tegra30 USB port */
COMPAT_NVIDIA_TEGRA114_USB, /* Tegra114 USB port */
- COMPAT_NVIDIA_TEGRA114_I2C, /* Tegra114 I2C w/single clock source */
- COMPAT_NVIDIA_TEGRA20_I2C, /* Tegra20 i2c */
- COMPAT_NVIDIA_TEGRA20_DVC, /* Tegra20 dvc (really just i2c) */
COMPAT_NVIDIA_TEGRA20_EMC, /* Tegra20 memory controller */
COMPAT_NVIDIA_TEGRA20_EMC_TABLE, /* Tegra20 memory timing table */
COMPAT_NVIDIA_TEGRA20_KBC, /* Tegra20 Keyboard */
@@ -127,9 +124,6 @@
COMPAT_NVIDIA_TEGRA124_SDMMC, /* Tegra124 SDMMC controller */
COMPAT_NVIDIA_TEGRA30_SDMMC, /* Tegra30 SDMMC controller */
COMPAT_NVIDIA_TEGRA20_SDMMC, /* Tegra20 SDMMC controller */
- COMPAT_NVIDIA_TEGRA20_SFLASH, /* Tegra 2 SPI flash controller */
- COMPAT_NVIDIA_TEGRA20_SLINK, /* Tegra 2 SPI SLINK controller */
- COMPAT_NVIDIA_TEGRA114_SPI, /* Tegra 114 SPI controller */
COMPAT_NVIDIA_TEGRA124_PCIE, /* Tegra 124 PCIe controller */
COMPAT_NVIDIA_TEGRA30_PCIE, /* Tegra 30 PCIe controller */
COMPAT_NVIDIA_TEGRA20_PCIE, /* Tegra 20 PCIe controller */
@@ -140,7 +134,6 @@
COMPAT_SAMSUNG_S3C2440_I2C, /* Exynos I2C Controller */
COMPAT_SAMSUNG_EXYNOS5_SOUND, /* Exynos Sound */
COMPAT_WOLFSON_WM8994_CODEC, /* Wolfson WM8994 Sound Codec */
- COMPAT_SAMSUNG_EXYNOS_SPI, /* Exynos SPI */
COMPAT_GOOGLE_CROS_EC, /* Google CROS_EC Protocol */
COMPAT_GOOGLE_CROS_EC_KEYB, /* Google CROS_EC Keyboard */
COMPAT_SAMSUNG_EXYNOS_EHCI, /* Exynos EHCI controller */
@@ -178,38 +171,58 @@
COMPAT_COUNT,
};
-/* GPIOs are numbered from 0 */
-enum {
- FDT_GPIO_NONE = -1U, /* an invalid GPIO used to end our list */
-
- FDT_GPIO_ACTIVE_LOW = 1 << 0, /* input is active low (else high) */
-};
-
-/* This is the state of a GPIO pin as defined by the fdt */
-struct fdt_gpio_state {
- const char *name; /* name of the fdt property defining this */
- uint gpio; /* GPIO number, or FDT_GPIO_NONE if none */
- u8 flags; /* FDT_GPIO_... flags */
+#define MAX_PHANDLE_ARGS 16
+struct fdtdec_phandle_args {
+ int node;
+ int args_count;
+ uint32_t args[MAX_PHANDLE_ARGS];
};
-/* This tells us whether a fdt_gpio_state record is valid or not */
-#define fdt_gpio_isvalid(x) ((x)->gpio != FDT_GPIO_NONE)
-
/**
- * Read the GPIO taking into account the polarity of the pin.
+ * fdtdec_parse_phandle_with_args() - Find a node pointed by phandle in a list
*
- * @param gpio pointer to the decoded gpio
- * @return value of the gpio if successful, < 0 if unsuccessful
- */
-int fdtdec_get_gpio(struct fdt_gpio_state *gpio);
-
-/**
- * Write the GPIO taking into account the polarity of the pin.
+ * This function is useful to parse lists of phandles and their arguments.
*
- * @param gpio pointer to the decoded gpio
- * @return 0 if successful
+ * Example:
+ *
+ * phandle1: node1 {
+ * #list-cells = <2>;
+ * }
+ *
+ * phandle2: node2 {
+ * #list-cells = <1>;
+ * }
+ *
+ * node3 {
+ * list = <&phandle1 1 2 &phandle2 3>;
+ * }
+ *
+ * To get a device_node of the `node2' node you may call this:
+ * fdtdec_parse_phandle_with_args(blob, node3, "list", "#list-cells", 0, 1,
+ * &args);
+ *
+ * (This function is a modified version of __of_parse_phandle_with_args() from
+ * Linux 3.18)
+ *
+ * @blob: Pointer to device tree
+ * @src_node: Offset of device tree node containing a list
+ * @list_name: property name that contains a list
+ * @cells_name: property name that specifies the phandles' arguments count,
+ * or NULL to use @cells_count
+ * @cells_count: Cell count to use if @cells_name is NULL
+ * @index: index of a phandle to parse out
+ * @out_args: optional pointer to output arguments structure (will be filled)
+ * @return 0 on success (with @out_args filled out if not NULL), -ENOENT if
+ * @list_name does not exist, a phandle was not found, @cells_name
+ * could not be found, the arguments were truncated or there were too
+ * many arguments.
+ *
*/
-int fdtdec_set_gpio(struct fdt_gpio_state *gpio, int val);
+int fdtdec_parse_phandle_with_args(const void *blob, int src_node,
+ const char *list_name,
+ const char *cells_name,
+ int cell_count, int index,
+ struct fdtdec_phandle_args *out_args);
/**
* Find the next numbered alias for a peripheral. This is used to enumerate
@@ -592,50 +605,6 @@
int fdtdec_get_bool(const void *blob, int node, const char *prop_name);
/**
- * Decode a single GPIOs from an FDT.
- *
- * If the property is not found, then the GPIO structure will still be
- * initialised, with gpio set to FDT_GPIO_NONE. This makes it easy to
- * provide optional GPIOs.
- *
- * @param blob FDT blob to use
- * @param node Node to look at
- * @param prop_name Node property name
- * @param gpio gpio elements to fill from FDT
- * @return 0 if ok, -FDT_ERR_NOTFOUND if the property is missing.
- */
-int fdtdec_decode_gpio(const void *blob, int node, const char *prop_name,
- struct fdt_gpio_state *gpio);
-
-/**
- * Decode a list of GPIOs from an FDT. This creates a list of GPIOs with no
- * terminating item.
- *
- * @param blob FDT blob to use
- * @param node Node to look at
- * @param prop_name Node property name
- * @param gpio Array of gpio elements to fill from FDT. This will be
- * untouched if either 0 or an error is returned
- * @param max_count Maximum number of elements allowed
- * @return number of GPIOs read if ok, -FDT_ERR_BADLAYOUT if max_count would
- * be exceeded, or -FDT_ERR_NOTFOUND if the property is missing.
- */
-int fdtdec_decode_gpios(const void *blob, int node, const char *prop_name,
- struct fdt_gpio_state *gpio, int max_count);
-
-/**
- * Set up a GPIO pin according to the provided gpio information. At present this
- * just requests the GPIO.
- *
- * If the gpio is FDT_GPIO_NONE, no action is taken. This makes it easy to
- * deal with optional GPIOs.
- *
- * @param gpio GPIO info to use for set up
- * @return 0 if all ok or gpio was FDT_GPIO_NONE; -1 on error
- */
-int fdtdec_setup_gpio(struct fdt_gpio_state *gpio);
-
-/**
* Look in the FDT for a config item with the given name and return its value
* as a 32-bit integer. The property must have at least 4 bytes of data. The
* value of the first cell is returned.
diff --git a/include/fs.h b/include/fs.h
index ffb6ce7..fd1e4ab 100644
--- a/include/fs.h
+++ b/include/fs.h
@@ -109,4 +109,10 @@
int do_fs_uuid(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[],
int fstype);
+/*
+ * Determine the type of the specified filesystem and print it. Optionally it is
+ * possible to store the type directly in env.
+ */
+int do_fs_type(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]);
+
#endif /* _FS_H */
diff --git a/include/hash.h b/include/hash.h
index d8ec4f0..f4eb100 100644
--- a/include/hash.h
+++ b/include/hash.h
@@ -17,7 +17,6 @@
HASH_FLAG_ENV = 1 << 1, /* Allow env vars */
};
-#ifndef USE_HOSTCC
#if defined(CONFIG_SHA1SUM_VERIFY) || defined(CONFIG_CRC32_VERIFY)
#define CONFIG_HASH_VERIFY
#endif
@@ -77,6 +76,7 @@
int size);
};
+#ifndef USE_HOSTCC
/**
* hash_command: Process a hash command for a particular algorithm
*
@@ -115,6 +115,23 @@
uint8_t *output, int *output_size);
/**
+ * hash_show() - Print out a hash algorithm and value
+ *
+ * You will get a message like this (without a newline at the end):
+ *
+ * "sha1 for 9eb3337c ... 9eb3338f ==> 7942ef1df479fd3130f716eb9613d107dab7e257"
+ *
+ * @algo: Algorithm used for hash
+ * @addr: Address of data that was hashed
+ * @len: Length of data that was hashed
+ * @output: Hash value to display
+ */
+void hash_show(struct hash_algo *algo, ulong addr, ulong len,
+ uint8_t *output);
+
+#endif /* !USE_HOSTCC */
+
+/**
* hash_lookup_algo() - Look up the hash_algo struct for an algorithm
*
* The function returns the pointer to the struct or -EPROTONOSUPPORT if the
@@ -128,18 +145,17 @@
int hash_lookup_algo(const char *algo_name, struct hash_algo **algop);
/**
- * hash_show() - Print out a hash algorithm and value
+ * hash_progressive_lookup_algo() - Look up hash_algo for prog. hash support
*
- * You will get a message like this (without a newline at the end):
+ * The function returns the pointer to the struct or -EPROTONOSUPPORT if the
+ * algorithm is not available with progressive hash support.
*
- * "sha1 for 9eb3337c ... 9eb3338f ==> 7942ef1df479fd3130f716eb9613d107dab7e257"
+ * @algo_name: Hash algorithm to look up
+ * @algop: Pointer to the hash_algo struct if found
*
- * @algo: Algorithm used for hash
- * @addr: Address of data that was hashed
- * @len: Length of data that was hashed
- * @output: Hash value to display
+ * @return 0 if ok, -EPROTONOSUPPORT for an unknown algorithm.
*/
-void hash_show(struct hash_algo *algo, ulong addr, ulong len,
- uint8_t *output);
-#endif /* !USE_HOSTCC */
+int hash_progressive_lookup_algo(const char *algo_name,
+ struct hash_algo **algop);
+
#endif
diff --git a/include/i2c.h b/include/i2c.h
index 9c6a60c..27fe00f 100644
--- a/include/i2c.h
+++ b/include/i2c.h
@@ -39,8 +39,8 @@
* An I2C chip is a device on the I2C bus. It sits at a particular address
* and normally supports 7-bit or 10-bit addressing.
*
- * To obtain this structure, use dev_get_parentdata(dev) where dev is the
- * chip to examine.
+ * To obtain this structure, use dev_get_parent_platdata(dev) where dev is
+ * the chip to examine.
*
* @chip_addr: Chip address on bus
* @offset_len: Length of offset in bytes. A single byte offset can
@@ -75,7 +75,7 @@
};
/**
- * i2c_read() - read bytes from an I2C chip
+ * dm_i2c_read() - read bytes from an I2C chip
*
* To obtain an I2C device (called a 'chip') given the I2C bus address you
* can use i2c_get_chip(). To obtain a bus by bus number use
@@ -91,13 +91,12 @@
*
* @return 0 on success, -ve on failure
*/
-int i2c_read(struct udevice *dev, uint offset, uint8_t *buffer,
- int len);
+int dm_i2c_read(struct udevice *dev, uint offset, uint8_t *buffer, int len);
/**
- * i2c_write() - write bytes to an I2C chip
+ * dm_i2c_write() - write bytes to an I2C chip
*
- * See notes for i2c_read() above.
+ * See notes for dm_i2c_read() above.
*
* @dev: Chip to write to
* @offset: Offset within chip to start writing
@@ -106,11 +105,11 @@
*
* @return 0 on success, -ve on failure
*/
-int i2c_write(struct udevice *dev, uint offset, const uint8_t *buffer,
- int len);
+int dm_i2c_write(struct udevice *dev, uint offset, const uint8_t *buffer,
+ int len);
/**
- * i2c_probe() - probe a particular chip address
+ * dm_i2c_probe() - probe a particular chip address
*
* This can be useful to check for the existence of a chip on the bus.
* It is typically implemented by writing the chip address to the bus
@@ -122,8 +121,8 @@
* @devp: Returns the device found, or NULL if none
* @return 0 if a chip was found at that address, -ve if not
*/
-int i2c_probe(struct udevice *bus, uint chip_addr, uint chip_flags,
- struct udevice **devp);
+int dm_i2c_probe(struct udevice *bus, uint chip_addr, uint chip_flags,
+ struct udevice **devp);
/**
* i2c_set_bus_speed() - set the speed of a bus
@@ -185,6 +184,80 @@
*/
int i2c_deblock(struct udevice *bus);
+#ifdef CONFIG_DM_I2C_COMPAT
+/**
+ * i2c_probe() - Compatibility function for driver model
+ *
+ * Calls dm_i2c_probe() on the current bus
+ */
+int i2c_probe(uint8_t chip_addr);
+
+/**
+ * i2c_read() - Compatibility function for driver model
+ *
+ * Calls dm_i2c_read() with the device corresponding to @chip_addr, and offset
+ * set to @addr. @alen must match the current setting for the device.
+ */
+int i2c_read(uint8_t chip_addr, unsigned int addr, int alen, uint8_t *buffer,
+ int len);
+
+/**
+ * i2c_write() - Compatibility function for driver model
+ *
+ * Calls dm_i2c_write() with the device corresponding to @chip_addr, and offset
+ * set to @addr. @alen must match the current setting for the device.
+ */
+int i2c_write(uint8_t chip_addr, unsigned int addr, int alen, uint8_t *buffer,
+ int len);
+
+/**
+ * i2c_get_bus_num_fdt() - Compatibility function for driver model
+ *
+ * @return the bus number associated with the given device tree node
+ */
+int i2c_get_bus_num_fdt(int node);
+
+/**
+ * i2c_get_bus_num() - Compatibility function for driver model
+ *
+ * @return the 'current' bus number
+ */
+unsigned int i2c_get_bus_num(void);
+
+/**
+ * i2c_set_bus_num() - Compatibility function for driver model
+ *
+ * Sets the 'current' bus
+ */
+int i2c_set_bus_num(unsigned int bus);
+
+static inline void I2C_SET_BUS(unsigned int bus)
+{
+ i2c_set_bus_num(bus);
+}
+
+static inline unsigned int I2C_GET_BUS(void)
+{
+ return i2c_get_bus_num();
+}
+
+/**
+ * i2c_init() - Compatibility function for driver model
+ *
+ * This function does nothing.
+ */
+void i2c_init(int speed, int slaveaddr);
+
+/**
+ * board_i2c_init() - Compatibility function for driver model
+ *
+ * @param blob Device tree blbo
+ * @return the number of I2C bus
+ */
+void board_i2c_init(const void *blob);
+
+#endif
+
/*
* Not all of these flags are implemented in the U-Boot API
*/
@@ -330,10 +403,12 @@
*
* @bus: Bus to examine
* @chip_addr: Chip address for the new device
+ * @offset_len: Length of a register offset in bytes (normally 1)
* @devp: Returns pointer to new device if found or -ENODEV if not
* found
*/
-int i2c_get_chip(struct udevice *bus, uint chip_addr, struct udevice **devp);
+int i2c_get_chip(struct udevice *bus, uint chip_addr, uint offset_len,
+ struct udevice **devp);
/**
* i2c_get_chip() - get a device to use to access a chip on a bus number
@@ -343,10 +418,12 @@
*
* @busnum: Bus number to examine
* @chip_addr: Chip address for the new device
+ * @offset_len: Length of a register offset in bytes (normally 1)
* @devp: Returns pointer to new device if found or -ENODEV if not
* found
*/
-int i2c_get_chip_for_busnum(int busnum, int chip_addr, struct udevice **devp);
+int i2c_get_chip_for_busnum(int busnum, int chip_addr, uint offset_len,
+ struct udevice **devp);
/**
* i2c_chip_ofdata_to_platdata() - Decode standard I2C platform data
diff --git a/include/image.h b/include/image.h
index ee3afe3..0e6af00 100644
--- a/include/image.h
+++ b/include/image.h
@@ -751,6 +751,7 @@
int fit_parse_subimage(const char *spec, ulong addr_curr,
ulong *addr, const char **image_name);
+int fit_get_subimage_count(const void *fit, int images_noffset);
void fit_print_contents(const void *fit);
void fit_image_print(const void *fit, int noffset, const char *p);
@@ -927,8 +928,9 @@
#if IMAGE_ENABLE_SIGN
const EVP_MD *(*calculate_sign)(void);
#endif
- void (*calculate)(const struct image_region region[],
- int region_count, uint8_t *checksum);
+ int (*calculate)(const char *name,
+ const struct image_region region[],
+ int region_count, uint8_t *checksum);
const uint8_t *rsa_padding;
};
diff --git a/include/linker_lists.h b/include/linker_lists.h
index d37fba4..940c871 100644
--- a/include/linker_lists.h
+++ b/include/linker_lists.h
@@ -23,7 +23,7 @@
/**
* A linker list is constructed by grouping together linker input
- * sections, each containning one entry of the list. Each input section
+ * sections, each containing one entry of the list. Each input section
* contains a constant initialized variable which holds the entry's
* content. Linker list input sections are constructed from the list
* and entry names, plus a prefix which allows grouping all lists
@@ -39,7 +39,7 @@
* This ensures uniqueness for both input section and C variable name.
*
* Note that the names differ only in the first character, "." for the
- * setion and "_" for the variable, so that the linker cannot confuse
+ * section and "_" for the variable, so that the linker cannot confuse
* section and symbol names. From now on, both names will be referred
* to as
*
diff --git a/include/sdhci.h b/include/sdhci.h
index aa4a0e9..23893b5 100644
--- a/include/sdhci.h
+++ b/include/sdhci.h
@@ -12,7 +12,7 @@
#include <asm/io.h>
#include <mmc.h>
-#include <fdtdec.h>
+#include <asm/gpio.h>
/*
* Controller registers
@@ -246,8 +246,8 @@
int index;
int bus_width;
- struct fdt_gpio_state pwr_gpio; /* Power GPIO */
- struct fdt_gpio_state cd_gpio; /* Card Detect GPIO */
+ struct gpio_desc pwr_gpio; /* Power GPIO */
+ struct gpio_desc cd_gpio; /* Card Detect GPIO */
void (*set_control_reg)(struct sdhci_host *host);
void (*set_clock)(int dev_index, unsigned int div);
diff --git a/include/spi.h b/include/spi.h
index ec17bd0..c58e453 100644
--- a/include/spi.h
+++ b/include/spi.h
@@ -56,20 +56,42 @@
#define SPI_DEFAULT_WORDLEN 8
#ifdef CONFIG_DM_SPI
+/* TODO(sjg@chromium.org): Remove this and use max_hz from struct spi_slave */
struct dm_spi_bus {
uint max_hz;
};
+/**
+ * struct dm_spi_platdata - platform data for all SPI slaves
+ *
+ * This describes a SPI slave, a child device of the SPI bus. To obtain this
+ * struct from a spi_slave, use dev_get_parent_platdata(dev) or
+ * dev_get_parent_platdata(slave->dev).
+ *
+ * This data is immuatable. Each time the device is probed, @max_hz and @mode
+ * will be copied to struct spi_slave.
+ *
+ * @cs: Chip select number (0..n-1)
+ * @max_hz: Maximum bus speed that this slave can tolerate
+ * @mode: SPI mode to use for this device (see SPI mode flags)
+ */
+struct dm_spi_slave_platdata {
+ unsigned int cs;
+ uint max_hz;
+ uint mode;
+};
+
#endif /* CONFIG_DM_SPI */
/**
* struct spi_slave - Representation of a SPI slave
*
* For driver model this is the per-child data used by the SPI bus. It can
- * be accessed using dev_get_parentdata() on the slave device. Each SPI
- * driver should define this child data in its U_BOOT_DRIVER() definition:
- *
- * .per_child_auto_alloc_size = sizeof(struct spi_slave),
+ * be accessed using dev_get_parentdata() on the slave device. The SPI uclass
+ * sets uip per_child_auto_alloc_size to sizeof(struct spi_slave), and the
+ * driver should not override it. Two platform data fields (max_hz and mode)
+ * are copied into this structure to provide an initial value. This allows
+ * them to be changed, since we should never change platform data in drivers.
*
* If not using driver model, drivers are expected to extend this with
* controller-specific data.
@@ -97,8 +119,8 @@
uint mode;
#else
unsigned int bus;
-#endif
unsigned int cs;
+#endif
u8 op_mode_rx;
u8 op_mode_tx;
unsigned int wordlen;
@@ -545,16 +567,16 @@
int spi_find_chip_select(struct udevice *bus, int cs, struct udevice **devp);
/**
- * spi_ofdata_to_platdata() - decode standard SPI platform data
+ * spi_slave_ofdata_to_platdata() - decode standard SPI platform data
*
- * This decodes the speed and mode from a device tree node and puts it into
- * the spi_slave structure.
+ * This decodes the speed and mode for a slave from a device tree node
*
* @blob: Device tree blob
* @node: Node offset to read from
- * @spi: Place to put the decoded information
+ * @plat: Place to put the decoded information
*/
-int spi_ofdata_to_platdata(const void *blob, int node, struct spi_slave *spi);
+int spi_slave_ofdata_to_platdata(const void *blob, int node,
+ struct dm_spi_slave_platdata *plat);
/**
* spi_cs_info() - Check information on a chip select
diff --git a/include/u-boot/rsa-checksum.h b/include/u-boot/rsa-checksum.h
index c996fb3..3c69d85 100644
--- a/include/u-boot/rsa-checksum.h
+++ b/include/u-boot/rsa-checksum.h
@@ -16,9 +16,18 @@
extern const uint8_t padding_sha256_rsa2048[];
extern const uint8_t padding_sha1_rsa2048[];
-void sha256_calculate(const struct image_region region[], int region_count,
- uint8_t *checksum);
-void sha1_calculate(const struct image_region region[], int region_count,
- uint8_t *checksum);
+/**
+ * hash_calculate() - Calculate hash over the data
+ *
+ * @name: Name of algorithm to be used for hash calculation
+ * @region: Array having info of regions over which hash needs to be calculated
+ * @region_count: Number of regions in the region array
+ * @checksum: Buffer contanining the output hash
+ *
+ * @return 0 if OK, < 0 if error
+ */
+int hash_calculate(const char *name,
+ const struct image_region region[], int region_count,
+ uint8_t *checksum);
#endif
diff --git a/include/u-boot/rsa-mod-exp.h b/include/u-boot/rsa-mod-exp.h
new file mode 100644
index 0000000..fce445a
--- /dev/null
+++ b/include/u-boot/rsa-mod-exp.h
@@ -0,0 +1,75 @@
+/*
+ * Copyright (c) 2014, Ruchika Gupta.
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+*/
+
+#ifndef _RSA_MOD_EXP_H
+#define _RSA_MOD_EXP_H
+
+#include <errno.h>
+#include <image.h>
+
+/**
+ * struct key_prop - holder for a public key properties
+ *
+ * The struct has pointers to modulus (Typically called N),
+ * The inverse, R^2, exponent. These can be typecasted and
+ * used as byte arrays or converted to the required format
+ * as per requirement of RSA implementation.
+ */
+struct key_prop {
+ const void *rr; /* R^2 can be treated as byte array */
+ const void *modulus; /* modulus as byte array */
+ const void *public_exponent; /* public exponent as byte array */
+ uint32_t n0inv; /* -1 / modulus[0] mod 2^32 */
+ int num_bits; /* Key length in bits */
+ uint32_t exp_len; /* Exponent length in number of uint8_t */
+};
+
+/**
+ * rsa_mod_exp_sw() - Perform RSA Modular Exponentiation in sw
+ *
+ * Operation: out[] = sig ^ exponent % modulus
+ *
+ * @sig: RSA PKCS1.5 signature
+ * @sig_len: Length of signature in number of bytes
+ * @node: Node with RSA key elements like modulus, exponent, R^2, n0inv
+ * @out: Result in form of byte array of len equal to sig_len
+ */
+int rsa_mod_exp_sw(const uint8_t *sig, uint32_t sig_len,
+ struct key_prop *node, uint8_t *out);
+
+int rsa_mod_exp(struct udevice *dev, const uint8_t *sig, uint32_t sig_len,
+ struct key_prop *node, uint8_t *out);
+
+/**
+ * struct struct mod_exp_ops - Driver model for RSA Modular Exponentiation
+ * operations
+ *
+ * The uclass interface is implemented by all crypto devices which use
+ * driver model.
+ */
+struct mod_exp_ops {
+ /**
+ * Perform Modular Exponentiation
+ *
+ * Operation: out[] = sig ^ exponent % modulus
+ *
+ * @dev: RSA Device
+ * @sig: RSA PKCS1.5 signature
+ * @sig_len: Length of signature in number of bytes
+ * @node: Node with RSA key elements like modulus, exponent,
+ * R^2, n0inv
+ * @out: Result in form of byte array of len equal to sig_len
+ *
+ * This function computes exponentiation over the signature.
+ * Returns: 0 if exponentiation is successful, or a negative value
+ * if it wasn't.
+ */
+ int (*mod_exp)(struct udevice *dev, const uint8_t *sig,
+ uint32_t sig_len, struct key_prop *node,
+ uint8_t *outp);
+};
+
+#endif
diff --git a/lib/Kconfig b/lib/Kconfig
index 8460439..a1f30a2 100644
--- a/lib/Kconfig
+++ b/lib/Kconfig
@@ -27,4 +27,6 @@
get_timer() must operate in milliseconds and this option must be
set to 1000.
+source lib/rsa/Kconfig
+
endmenu
diff --git a/lib/fdtdec.c b/lib/fdtdec.c
index e989241..5bf8f29 100644
--- a/lib/fdtdec.c
+++ b/lib/fdtdec.c
@@ -11,8 +11,6 @@
#include <fdtdec.h>
#include <linux/ctype.h>
-#include <asm/gpio.h>
-
DECLARE_GLOBAL_DATA_PTR;
/*
@@ -26,9 +24,6 @@
COMPAT(NVIDIA_TEGRA20_USB, "nvidia,tegra20-ehci"),
COMPAT(NVIDIA_TEGRA30_USB, "nvidia,tegra30-ehci"),
COMPAT(NVIDIA_TEGRA114_USB, "nvidia,tegra114-ehci"),
- COMPAT(NVIDIA_TEGRA114_I2C, "nvidia,tegra114-i2c"),
- COMPAT(NVIDIA_TEGRA20_I2C, "nvidia,tegra20-i2c"),
- COMPAT(NVIDIA_TEGRA20_DVC, "nvidia,tegra20-i2c-dvc"),
COMPAT(NVIDIA_TEGRA20_EMC, "nvidia,tegra20-emc"),
COMPAT(NVIDIA_TEGRA20_EMC_TABLE, "nvidia,tegra20-emc-table"),
COMPAT(NVIDIA_TEGRA20_KBC, "nvidia,tegra20-kbc"),
@@ -38,9 +33,6 @@
COMPAT(NVIDIA_TEGRA124_SDMMC, "nvidia,tegra124-sdhci"),
COMPAT(NVIDIA_TEGRA30_SDMMC, "nvidia,tegra30-sdhci"),
COMPAT(NVIDIA_TEGRA20_SDMMC, "nvidia,tegra20-sdhci"),
- COMPAT(NVIDIA_TEGRA20_SFLASH, "nvidia,tegra20-sflash"),
- COMPAT(NVIDIA_TEGRA20_SLINK, "nvidia,tegra20-slink"),
- COMPAT(NVIDIA_TEGRA114_SPI, "nvidia,tegra114-spi"),
COMPAT(NVIDIA_TEGRA124_PCIE, "nvidia,tegra124-pcie"),
COMPAT(NVIDIA_TEGRA30_PCIE, "nvidia,tegra30-pcie"),
COMPAT(NVIDIA_TEGRA20_PCIE, "nvidia,tegra20-pcie"),
@@ -50,7 +42,6 @@
COMPAT(SAMSUNG_S3C2440_I2C, "samsung,s3c2440-i2c"),
COMPAT(SAMSUNG_EXYNOS5_SOUND, "samsung,exynos-sound"),
COMPAT(WOLFSON_WM8994_CODEC, "wolfson,wm8994-codec"),
- COMPAT(SAMSUNG_EXYNOS_SPI, "samsung,exynos-spi"),
COMPAT(GOOGLE_CROS_EC, "google,cros-ec"),
COMPAT(GOOGLE_CROS_EC_KEYB, "google,cros-ec-keyb"),
COMPAT(SAMSUNG_EXYNOS_EHCI, "samsung,exynos-ehci"),
@@ -679,99 +670,128 @@
return cell != NULL;
}
-/**
- * Decode a list of GPIOs from an FDT. This creates a list of GPIOs with no
- * terminating item.
- *
- * @param blob FDT blob to use
- * @param node Node to look at
- * @param prop_name Node property name
- * @param gpio Array of gpio elements to fill from FDT. This will be
- * untouched if either 0 or an error is returned
- * @param max_count Maximum number of elements allowed
- * @return number of GPIOs read if ok, -FDT_ERR_BADLAYOUT if max_count would
- * be exceeded, or -FDT_ERR_NOTFOUND if the property is missing.
- */
-int fdtdec_decode_gpios(const void *blob, int node, const char *prop_name,
- struct fdt_gpio_state *gpio, int max_count)
+int fdtdec_parse_phandle_with_args(const void *blob, int src_node,
+ const char *list_name,
+ const char *cells_name,
+ int cell_count, int index,
+ struct fdtdec_phandle_args *out_args)
{
- const struct fdt_property *prop;
- const u32 *cell;
- const char *name;
- int len, i;
+ const __be32 *list, *list_end;
+ int rc = 0, size, cur_index = 0;
+ uint32_t count = 0;
+ int node = -1;
+ int phandle;
- debug("%s: %s\n", __func__, prop_name);
- assert(max_count > 0);
- prop = fdt_get_property(blob, node, prop_name, &len);
- if (!prop) {
- debug("%s: property '%s' missing\n", __func__, prop_name);
- return -FDT_ERR_NOTFOUND;
- }
+ /* Retrieve the phandle list property */
+ list = fdt_getprop(blob, src_node, list_name, &size);
+ if (!list)
+ return -ENOENT;
+ list_end = list + size / sizeof(*list);
- /* We will use the name to tag the GPIO */
- name = fdt_string(blob, fdt32_to_cpu(prop->nameoff));
- cell = (u32 *)prop->data;
- len /= sizeof(u32) * 3; /* 3 cells per GPIO record */
- if (len > max_count) {
- debug(" %s: too many GPIOs / cells for "
- "property '%s'\n", __func__, prop_name);
- return -FDT_ERR_BADLAYOUT;
- }
+ /* Loop over the phandles until all the requested entry is found */
+ while (list < list_end) {
+ rc = -EINVAL;
+ count = 0;
- /* Read out the GPIO data from the cells */
- for (i = 0; i < len; i++, cell += 3) {
- gpio[i].gpio = fdt32_to_cpu(cell[1]);
- gpio[i].flags = fdt32_to_cpu(cell[2]);
- gpio[i].name = name;
- }
-
- return len;
-}
+ /*
+ * If phandle is 0, then it is an empty entry with no
+ * arguments. Skip forward to the next entry.
+ */
+ phandle = be32_to_cpup(list++);
+ if (phandle) {
+ /*
+ * Find the provider node and parse the #*-cells
+ * property to determine the argument length.
+ *
+ * This is not needed if the cell count is hard-coded
+ * (i.e. cells_name not set, but cell_count is set),
+ * except when we're going to return the found node
+ * below.
+ */
+ if (cells_name || cur_index == index) {
+ node = fdt_node_offset_by_phandle(blob,
+ phandle);
+ if (!node) {
+ debug("%s: could not find phandle\n",
+ fdt_get_name(blob, src_node,
+ NULL));
+ goto err;
+ }
+ }
-int fdtdec_decode_gpio(const void *blob, int node, const char *prop_name,
- struct fdt_gpio_state *gpio)
-{
- int err;
+ if (cells_name) {
+ count = fdtdec_get_int(blob, node, cells_name,
+ -1);
+ if (count == -1) {
+ debug("%s: could not get %s for %s\n",
+ fdt_get_name(blob, src_node,
+ NULL),
+ cells_name,
+ fdt_get_name(blob, node,
+ NULL));
+ goto err;
+ }
+ } else {
+ count = cell_count;
+ }
- debug("%s: %s\n", __func__, prop_name);
- gpio->gpio = FDT_GPIO_NONE;
- gpio->name = NULL;
- err = fdtdec_decode_gpios(blob, node, prop_name, gpio, 1);
- return err == 1 ? 0 : err;
-}
+ /*
+ * Make sure that the arguments actually fit in the
+ * remaining property data length
+ */
+ if (list + count > list_end) {
+ debug("%s: arguments longer than property\n",
+ fdt_get_name(blob, src_node, NULL));
+ goto err;
+ }
+ }
-int fdtdec_get_gpio(struct fdt_gpio_state *gpio)
-{
- int val;
+ /*
+ * All of the error cases above bail out of the loop, so at
+ * this point, the parsing is successful. If the requested
+ * index matches, then fill the out_args structure and return,
+ * or return -ENOENT for an empty entry.
+ */
+ rc = -ENOENT;
+ if (cur_index == index) {
+ if (!phandle)
+ goto err;
- if (!fdt_gpio_isvalid(gpio))
- return -1;
+ if (out_args) {
+ int i;
- val = gpio_get_value(gpio->gpio);
- return gpio->flags & FDT_GPIO_ACTIVE_LOW ? val ^ 1 : val;
-}
+ if (count > MAX_PHANDLE_ARGS) {
+ debug("%s: too many arguments %d\n",
+ fdt_get_name(blob, src_node,
+ NULL), count);
+ count = MAX_PHANDLE_ARGS;
+ }
+ out_args->node = node;
+ out_args->args_count = count;
+ for (i = 0; i < count; i++) {
+ out_args->args[i] =
+ be32_to_cpup(list++);
+ }
+ }
-int fdtdec_set_gpio(struct fdt_gpio_state *gpio, int val)
-{
- if (!fdt_gpio_isvalid(gpio))
- return -1;
+ /* Found it! return success */
+ return 0;
+ }
- val = gpio->flags & FDT_GPIO_ACTIVE_LOW ? val ^ 1 : val;
- return gpio_set_value(gpio->gpio, val);
-}
+ node = -1;
+ list += count;
+ cur_index++;
+ }
-int fdtdec_setup_gpio(struct fdt_gpio_state *gpio)
-{
/*
- * Return success if there is no GPIO defined. This is used for
- * optional GPIOs)
+ * Result will be one of:
+ * -ENOENT : index is for empty phandle
+ * -EINVAL : parsing error on data
+ * [1..n] : Number of phandle (count mode; when index = -1)
*/
- if (!fdt_gpio_isvalid(gpio))
- return 0;
-
- if (gpio_request(gpio->gpio, gpio->name))
- return -1;
- return 0;
+ rc = index < 0 ? cur_index : -ENOENT;
+ err:
+ return rc;
}
int fdtdec_get_byte_array(const void *blob, int node, const char *prop_name,
diff --git a/lib/rsa/Kconfig b/lib/rsa/Kconfig
new file mode 100644
index 0000000..1268a1b
--- /dev/null
+++ b/lib/rsa/Kconfig
@@ -0,0 +1,27 @@
+config RSA
+ bool "Use RSA Library"
+ select RSA_FREESCALE_EXP if FSL_CAAM
+ select RSA_SOFTWARE_EXP if !RSA_FREESCALE_EXP
+ help
+ RSA support. This enables the RSA algorithm used for FIT image
+ verification in U-Boot.
+ See doc/uImage.FIT/signature.txt for more details.
+
+if RSA
+config RSA_SOFTWARE_EXP
+ bool "Enable driver for RSA Modular Exponentiation in software"
+ depends on DM && RSA
+ help
+ Enables driver for modular exponentiation in software. This is a RSA
+ algorithm used in FIT image verification. It required RSA Key as
+ input.
+ See doc/uImage.FIT/signature.txt for more details.
+
+config RSA_FREESCALE_EXP
+ bool "Enable RSA Modular Exponentiation with FSL crypto accelerator"
+ depends on DM && RSA && FSL_CAAM
+ help
+ Enables driver for RSA modular exponentiation using Freescale cryptographic
+ accelerator - CAAM.
+
+endif
diff --git a/lib/rsa/Makefile b/lib/rsa/Makefile
index a5a96cb6..cc25b3c 100644
--- a/lib/rsa/Makefile
+++ b/lib/rsa/Makefile
@@ -7,4 +7,4 @@
# SPDX-License-Identifier: GPL-2.0+
#
-obj-$(CONFIG_FIT_SIGNATURE) += rsa-verify.o rsa-checksum.o
+obj-$(CONFIG_FIT_SIGNATURE) += rsa-verify.o rsa-checksum.o rsa-mod-exp.o
diff --git a/lib/rsa/rsa-checksum.c b/lib/rsa/rsa-checksum.c
index 8d8b59f..68d9d65 100644
--- a/lib/rsa/rsa-checksum.c
+++ b/lib/rsa/rsa-checksum.c
@@ -10,12 +10,13 @@
#include <asm/byteorder.h>
#include <asm/errno.h>
#include <asm/unaligned.h>
+#include <hash.h>
#else
#include "fdt_host.h"
-#endif
-#include <u-boot/rsa.h>
#include <u-boot/sha1.h>
#include <u-boot/sha256.h>
+#endif
+#include <u-boot/rsa.h>
/* PKCS 1.5 paddings as described in the RSA PKCS#1 v2.1 standard. */
@@ -136,28 +137,37 @@
0x03, 0x04, 0x02, 0x01, 0x05, 0x00, 0x04, 0x20
};
-void sha1_calculate(const struct image_region region[], int region_count,
- uint8_t *checksum)
+int hash_calculate(const char *name,
+ const struct image_region region[],
+ int region_count, uint8_t *checksum)
{
- sha1_context ctx;
+ struct hash_algo *algo;
+ int ret = 0;
+ void *ctx;
uint32_t i;
i = 0;
- sha1_starts(&ctx);
- for (i = 0; i < region_count; i++)
- sha1_update(&ctx, region[i].data, region[i].size);
- sha1_finish(&ctx, checksum);
-}
+ ret = hash_progressive_lookup_algo(name, &algo);
+ if (ret)
+ return ret;
-void sha256_calculate(const struct image_region region[], int region_count,
- uint8_t *checksum)
-{
- sha256_context ctx;
- uint32_t i;
- i = 0;
+ ret = algo->hash_init(algo, &ctx);
+ if (ret)
+ return ret;
+
+ for (i = 0; i < region_count - 1; i++) {
+ ret = algo->hash_update(algo, ctx, region[i].data,
+ region[i].size, 0);
+ if (ret)
+ return ret;
+ }
+
+ ret = algo->hash_update(algo, ctx, region[i].data, region[i].size, 1);
+ if (ret)
+ return ret;
+ ret = algo->hash_finish(algo, ctx, checksum, algo->digest_size);
+ if (ret)
+ return ret;
- sha256_starts(&ctx);
- for (i = 0; i < region_count; i++)
- sha256_update(&ctx, region[i].data, region[i].size);
- sha256_finish(&ctx, checksum);
+ return 0;
}
diff --git a/lib/rsa/rsa-mod-exp.c b/lib/rsa/rsa-mod-exp.c
new file mode 100644
index 0000000..4a6de2b
--- /dev/null
+++ b/lib/rsa/rsa-mod-exp.c
@@ -0,0 +1,303 @@
+/*
+ * Copyright (c) 2013, Google Inc.
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+#ifndef USE_HOSTCC
+#include <common.h>
+#include <fdtdec.h>
+#include <asm/types.h>
+#include <asm/byteorder.h>
+#include <asm/errno.h>
+#include <asm/types.h>
+#include <asm/unaligned.h>
+#else
+#include "fdt_host.h"
+#include "mkimage.h"
+#include <fdt_support.h>
+#endif
+#include <u-boot/rsa.h>
+#include <u-boot/rsa-mod-exp.h>
+
+#define UINT64_MULT32(v, multby) (((uint64_t)(v)) * ((uint32_t)(multby)))
+
+#define get_unaligned_be32(a) fdt32_to_cpu(*(uint32_t *)a)
+#define put_unaligned_be32(a, b) (*(uint32_t *)(b) = cpu_to_fdt32(a))
+
+/* Default public exponent for backward compatibility */
+#define RSA_DEFAULT_PUBEXP 65537
+
+/**
+ * subtract_modulus() - subtract modulus from the given value
+ *
+ * @key: Key containing modulus to subtract
+ * @num: Number to subtract modulus from, as little endian word array
+ */
+static void subtract_modulus(const struct rsa_public_key *key, uint32_t num[])
+{
+ int64_t acc = 0;
+ uint i;
+
+ for (i = 0; i < key->len; i++) {
+ acc += (uint64_t)num[i] - key->modulus[i];
+ num[i] = (uint32_t)acc;
+ acc >>= 32;
+ }
+}
+
+/**
+ * greater_equal_modulus() - check if a value is >= modulus
+ *
+ * @key: Key containing modulus to check
+ * @num: Number to check against modulus, as little endian word array
+ * @return 0 if num < modulus, 1 if num >= modulus
+ */
+static int greater_equal_modulus(const struct rsa_public_key *key,
+ uint32_t num[])
+{
+ int i;
+
+ for (i = (int)key->len - 1; i >= 0; i--) {
+ if (num[i] < key->modulus[i])
+ return 0;
+ if (num[i] > key->modulus[i])
+ return 1;
+ }
+
+ return 1; /* equal */
+}
+
+/**
+ * montgomery_mul_add_step() - Perform montgomery multiply-add step
+ *
+ * Operation: montgomery result[] += a * b[] / n0inv % modulus
+ *
+ * @key: RSA key
+ * @result: Place to put result, as little endian word array
+ * @a: Multiplier
+ * @b: Multiplicand, as little endian word array
+ */
+static void montgomery_mul_add_step(const struct rsa_public_key *key,
+ uint32_t result[], const uint32_t a, const uint32_t b[])
+{
+ uint64_t acc_a, acc_b;
+ uint32_t d0;
+ uint i;
+
+ acc_a = (uint64_t)a * b[0] + result[0];
+ d0 = (uint32_t)acc_a * key->n0inv;
+ acc_b = (uint64_t)d0 * key->modulus[0] + (uint32_t)acc_a;
+ for (i = 1; i < key->len; i++) {
+ acc_a = (acc_a >> 32) + (uint64_t)a * b[i] + result[i];
+ acc_b = (acc_b >> 32) + (uint64_t)d0 * key->modulus[i] +
+ (uint32_t)acc_a;
+ result[i - 1] = (uint32_t)acc_b;
+ }
+
+ acc_a = (acc_a >> 32) + (acc_b >> 32);
+
+ result[i - 1] = (uint32_t)acc_a;
+
+ if (acc_a >> 32)
+ subtract_modulus(key, result);
+}
+
+/**
+ * montgomery_mul() - Perform montgomery mutitply
+ *
+ * Operation: montgomery result[] = a[] * b[] / n0inv % modulus
+ *
+ * @key: RSA key
+ * @result: Place to put result, as little endian word array
+ * @a: Multiplier, as little endian word array
+ * @b: Multiplicand, as little endian word array
+ */
+static void montgomery_mul(const struct rsa_public_key *key,
+ uint32_t result[], uint32_t a[], const uint32_t b[])
+{
+ uint i;
+
+ for (i = 0; i < key->len; ++i)
+ result[i] = 0;
+ for (i = 0; i < key->len; ++i)
+ montgomery_mul_add_step(key, result, a[i], b);
+}
+
+/**
+ * num_pub_exponent_bits() - Number of bits in the public exponent
+ *
+ * @key: RSA key
+ * @num_bits: Storage for the number of public exponent bits
+ */
+static int num_public_exponent_bits(const struct rsa_public_key *key,
+ int *num_bits)
+{
+ uint64_t exponent;
+ int exponent_bits;
+ const uint max_bits = (sizeof(exponent) * 8);
+
+ exponent = key->exponent;
+ exponent_bits = 0;
+
+ if (!exponent) {
+ *num_bits = exponent_bits;
+ return 0;
+ }
+
+ for (exponent_bits = 1; exponent_bits < max_bits + 1; ++exponent_bits)
+ if (!(exponent >>= 1)) {
+ *num_bits = exponent_bits;
+ return 0;
+ }
+
+ return -EINVAL;
+}
+
+/**
+ * is_public_exponent_bit_set() - Check if a bit in the public exponent is set
+ *
+ * @key: RSA key
+ * @pos: The bit position to check
+ */
+static int is_public_exponent_bit_set(const struct rsa_public_key *key,
+ int pos)
+{
+ return key->exponent & (1ULL << pos);
+}
+
+/**
+ * pow_mod() - in-place public exponentiation
+ *
+ * @key: RSA key
+ * @inout: Big-endian word array containing value and result
+ */
+static int pow_mod(const struct rsa_public_key *key, uint32_t *inout)
+{
+ uint32_t *result, *ptr;
+ uint i;
+ int j, k;
+
+ /* Sanity check for stack size - key->len is in 32-bit words */
+ if (key->len > RSA_MAX_KEY_BITS / 32) {
+ debug("RSA key words %u exceeds maximum %d\n", key->len,
+ RSA_MAX_KEY_BITS / 32);
+ return -EINVAL;
+ }
+
+ uint32_t val[key->len], acc[key->len], tmp[key->len];
+ uint32_t a_scaled[key->len];
+ result = tmp; /* Re-use location. */
+
+ /* Convert from big endian byte array to little endian word array. */
+ for (i = 0, ptr = inout + key->len - 1; i < key->len; i++, ptr--)
+ val[i] = get_unaligned_be32(ptr);
+
+ if (0 != num_public_exponent_bits(key, &k))
+ return -EINVAL;
+
+ if (k < 2) {
+ debug("Public exponent is too short (%d bits, minimum 2)\n",
+ k);
+ return -EINVAL;
+ }
+
+ if (!is_public_exponent_bit_set(key, 0)) {
+ debug("LSB of RSA public exponent must be set.\n");
+ return -EINVAL;
+ }
+
+ /* the bit at e[k-1] is 1 by definition, so start with: C := M */
+ montgomery_mul(key, acc, val, key->rr); /* acc = a * RR / R mod n */
+ /* retain scaled version for intermediate use */
+ memcpy(a_scaled, acc, key->len * sizeof(a_scaled[0]));
+
+ for (j = k - 2; j > 0; --j) {
+ montgomery_mul(key, tmp, acc, acc); /* tmp = acc^2 / R mod n */
+
+ if (is_public_exponent_bit_set(key, j)) {
+ /* acc = tmp * val / R mod n */
+ montgomery_mul(key, acc, tmp, a_scaled);
+ } else {
+ /* e[j] == 0, copy tmp back to acc for next operation */
+ memcpy(acc, tmp, key->len * sizeof(acc[0]));
+ }
+ }
+
+ /* the bit at e[0] is always 1 */
+ montgomery_mul(key, tmp, acc, acc); /* tmp = acc^2 / R mod n */
+ montgomery_mul(key, acc, tmp, val); /* acc = tmp * a / R mod M */
+ memcpy(result, acc, key->len * sizeof(result[0]));
+
+ /* Make sure result < mod; result is at most 1x mod too large. */
+ if (greater_equal_modulus(key, result))
+ subtract_modulus(key, result);
+
+ /* Convert to bigendian byte array */
+ for (i = key->len - 1, ptr = inout; (int)i >= 0; i--, ptr++)
+ put_unaligned_be32(result[i], ptr);
+ return 0;
+}
+
+static void rsa_convert_big_endian(uint32_t *dst, const uint32_t *src, int len)
+{
+ int i;
+
+ for (i = 0; i < len; i++)
+ dst[i] = fdt32_to_cpu(src[len - 1 - i]);
+}
+
+int rsa_mod_exp_sw(const uint8_t *sig, uint32_t sig_len,
+ struct key_prop *prop, uint8_t *out)
+{
+ struct rsa_public_key key;
+ int ret;
+
+ if (!prop) {
+ debug("%s: Skipping invalid prop", __func__);
+ return -EBADF;
+ }
+ key.n0inv = prop->n0inv;
+ key.len = prop->num_bits;
+
+ if (!prop->public_exponent)
+ key.exponent = RSA_DEFAULT_PUBEXP;
+ else
+ key.exponent =
+ fdt64_to_cpu(*((uint64_t *)(prop->public_exponent)));
+
+ if (!key.len || !prop->modulus || !prop->rr) {
+ debug("%s: Missing RSA key info", __func__);
+ return -EFAULT;
+ }
+
+ /* Sanity check for stack size */
+ if (key.len > RSA_MAX_KEY_BITS || key.len < RSA_MIN_KEY_BITS) {
+ debug("RSA key bits %u outside allowed range %d..%d\n",
+ key.len, RSA_MIN_KEY_BITS, RSA_MAX_KEY_BITS);
+ return -EFAULT;
+ }
+ key.len /= sizeof(uint32_t) * 8;
+ uint32_t key1[key.len], key2[key.len];
+
+ key.modulus = key1;
+ key.rr = key2;
+ rsa_convert_big_endian(key.modulus, (uint32_t *)prop->modulus, key.len);
+ rsa_convert_big_endian(key.rr, (uint32_t *)prop->rr, key.len);
+ if (!key.modulus || !key.rr) {
+ debug("%s: Out of memory", __func__);
+ return -ENOMEM;
+ }
+
+ uint32_t buf[sig_len / sizeof(uint32_t)];
+
+ memcpy(buf, sig, sig_len);
+
+ ret = pow_mod(&key, buf);
+ if (ret)
+ return ret;
+
+ memcpy(out, buf, sig_len);
+
+ return 0;
+}
diff --git a/lib/rsa/rsa-verify.c b/lib/rsa/rsa-verify.c
index 4ef19b6..60126d2 100644
--- a/lib/rsa/rsa-verify.c
+++ b/lib/rsa/rsa-verify.c
@@ -12,246 +12,46 @@
#include <asm/errno.h>
#include <asm/types.h>
#include <asm/unaligned.h>
+#include <dm.h>
#else
#include "fdt_host.h"
#include "mkimage.h"
#include <fdt_support.h>
#endif
+#include <u-boot/rsa-mod-exp.h>
#include <u-boot/rsa.h>
-#include <u-boot/sha1.h>
-#include <u-boot/sha256.h>
-
-#define UINT64_MULT32(v, multby) (((uint64_t)(v)) * ((uint32_t)(multby)))
-
-#define get_unaligned_be32(a) fdt32_to_cpu(*(uint32_t *)a)
-#define put_unaligned_be32(a, b) (*(uint32_t *)(b) = cpu_to_fdt32(a))
/* Default public exponent for backward compatibility */
#define RSA_DEFAULT_PUBEXP 65537
/**
- * subtract_modulus() - subtract modulus from the given value
- *
- * @key: Key containing modulus to subtract
- * @num: Number to subtract modulus from, as little endian word array
- */
-static void subtract_modulus(const struct rsa_public_key *key, uint32_t num[])
-{
- int64_t acc = 0;
- uint i;
-
- for (i = 0; i < key->len; i++) {
- acc += (uint64_t)num[i] - key->modulus[i];
- num[i] = (uint32_t)acc;
- acc >>= 32;
- }
-}
-
-/**
- * greater_equal_modulus() - check if a value is >= modulus
- *
- * @key: Key containing modulus to check
- * @num: Number to check against modulus, as little endian word array
- * @return 0 if num < modulus, 1 if num >= modulus
- */
-static int greater_equal_modulus(const struct rsa_public_key *key,
- uint32_t num[])
-{
- int i;
-
- for (i = (int)key->len - 1; i >= 0; i--) {
- if (num[i] < key->modulus[i])
- return 0;
- if (num[i] > key->modulus[i])
- return 1;
- }
-
- return 1; /* equal */
-}
-
-/**
- * montgomery_mul_add_step() - Perform montgomery multiply-add step
+ * rsa_verify_key() - Verify a signature against some data using RSA Key
*
- * Operation: montgomery result[] += a * b[] / n0inv % modulus
+ * Verify a RSA PKCS1.5 signature against an expected hash using
+ * the RSA Key properties in prop structure.
*
- * @key: RSA key
- * @result: Place to put result, as little endian word array
- * @a: Multiplier
- * @b: Multiplicand, as little endian word array
+ * @prop: Specifies key
+ * @sig: Signature
+ * @sig_len: Number of bytes in signature
+ * @hash: Pointer to the expected hash
+ * @algo: Checksum algo structure having information on RSA padding etc.
+ * @return 0 if verified, -ve on error
*/
-static void montgomery_mul_add_step(const struct rsa_public_key *key,
- uint32_t result[], const uint32_t a, const uint32_t b[])
-{
- uint64_t acc_a, acc_b;
- uint32_t d0;
- uint i;
-
- acc_a = (uint64_t)a * b[0] + result[0];
- d0 = (uint32_t)acc_a * key->n0inv;
- acc_b = (uint64_t)d0 * key->modulus[0] + (uint32_t)acc_a;
- for (i = 1; i < key->len; i++) {
- acc_a = (acc_a >> 32) + (uint64_t)a * b[i] + result[i];
- acc_b = (acc_b >> 32) + (uint64_t)d0 * key->modulus[i] +
- (uint32_t)acc_a;
- result[i - 1] = (uint32_t)acc_b;
- }
-
- acc_a = (acc_a >> 32) + (acc_b >> 32);
-
- result[i - 1] = (uint32_t)acc_a;
-
- if (acc_a >> 32)
- subtract_modulus(key, result);
-}
-
-/**
- * montgomery_mul() - Perform montgomery mutitply
- *
- * Operation: montgomery result[] = a[] * b[] / n0inv % modulus
- *
- * @key: RSA key
- * @result: Place to put result, as little endian word array
- * @a: Multiplier, as little endian word array
- * @b: Multiplicand, as little endian word array
- */
-static void montgomery_mul(const struct rsa_public_key *key,
- uint32_t result[], uint32_t a[], const uint32_t b[])
-{
- uint i;
-
- for (i = 0; i < key->len; ++i)
- result[i] = 0;
- for (i = 0; i < key->len; ++i)
- montgomery_mul_add_step(key, result, a[i], b);
-}
-
-/**
- * num_pub_exponent_bits() - Number of bits in the public exponent
- *
- * @key: RSA key
- * @num_bits: Storage for the number of public exponent bits
- */
-static int num_public_exponent_bits(const struct rsa_public_key *key,
- int *num_bits)
-{
- uint64_t exponent;
- int exponent_bits;
- const uint max_bits = (sizeof(exponent) * 8);
-
- exponent = key->exponent;
- exponent_bits = 0;
-
- if (!exponent) {
- *num_bits = exponent_bits;
- return 0;
- }
-
- for (exponent_bits = 1; exponent_bits < max_bits + 1; ++exponent_bits)
- if (!(exponent >>= 1)) {
- *num_bits = exponent_bits;
- return 0;
- }
-
- return -EINVAL;
-}
-
-/**
- * is_public_exponent_bit_set() - Check if a bit in the public exponent is set
- *
- * @key: RSA key
- * @pos: The bit position to check
- */
-static int is_public_exponent_bit_set(const struct rsa_public_key *key,
- int pos)
-{
- return key->exponent & (1ULL << pos);
-}
-
-/**
- * pow_mod() - in-place public exponentiation
- *
- * @key: RSA key
- * @inout: Big-endian word array containing value and result
- */
-static int pow_mod(const struct rsa_public_key *key, uint32_t *inout)
-{
- uint32_t *result, *ptr;
- uint i;
- int j, k;
-
- /* Sanity check for stack size - key->len is in 32-bit words */
- if (key->len > RSA_MAX_KEY_BITS / 32) {
- debug("RSA key words %u exceeds maximum %d\n", key->len,
- RSA_MAX_KEY_BITS / 32);
- return -EINVAL;
- }
-
- uint32_t val[key->len], acc[key->len], tmp[key->len];
- uint32_t a_scaled[key->len];
- result = tmp; /* Re-use location. */
-
- /* Convert from big endian byte array to little endian word array. */
- for (i = 0, ptr = inout + key->len - 1; i < key->len; i++, ptr--)
- val[i] = get_unaligned_be32(ptr);
-
- if (0 != num_public_exponent_bits(key, &k))
- return -EINVAL;
-
- if (k < 2) {
- debug("Public exponent is too short (%d bits, minimum 2)\n",
- k);
- return -EINVAL;
- }
-
- if (!is_public_exponent_bit_set(key, 0)) {
- debug("LSB of RSA public exponent must be set.\n");
- return -EINVAL;
- }
-
- /* the bit at e[k-1] is 1 by definition, so start with: C := M */
- montgomery_mul(key, acc, val, key->rr); /* acc = a * RR / R mod n */
- /* retain scaled version for intermediate use */
- memcpy(a_scaled, acc, key->len * sizeof(a_scaled[0]));
-
- for (j = k - 2; j > 0; --j) {
- montgomery_mul(key, tmp, acc, acc); /* tmp = acc^2 / R mod n */
-
- if (is_public_exponent_bit_set(key, j)) {
- /* acc = tmp * val / R mod n */
- montgomery_mul(key, acc, tmp, a_scaled);
- } else {
- /* e[j] == 0, copy tmp back to acc for next operation */
- memcpy(acc, tmp, key->len * sizeof(acc[0]));
- }
- }
-
- /* the bit at e[0] is always 1 */
- montgomery_mul(key, tmp, acc, acc); /* tmp = acc^2 / R mod n */
- montgomery_mul(key, acc, tmp, val); /* acc = tmp * a / R mod M */
- memcpy(result, acc, key->len * sizeof(result[0]));
-
- /* Make sure result < mod; result is at most 1x mod too large. */
- if (greater_equal_modulus(key, result))
- subtract_modulus(key, result);
-
- /* Convert to bigendian byte array */
- for (i = key->len - 1, ptr = inout; (int)i >= 0; i--, ptr++)
- put_unaligned_be32(result[i], ptr);
- return 0;
-}
-
-static int rsa_verify_key(const struct rsa_public_key *key, const uint8_t *sig,
+static int rsa_verify_key(struct key_prop *prop, const uint8_t *sig,
const uint32_t sig_len, const uint8_t *hash,
struct checksum_algo *algo)
{
const uint8_t *padding;
int pad_len;
int ret;
+#if !defined(USE_HOSTCC)
+ struct udevice *mod_exp_dev;
+#endif
- if (!key || !sig || !hash || !algo)
+ if (!prop || !sig || !hash || !algo)
return -EIO;
- if (sig_len != (key->len * sizeof(uint32_t))) {
+ if (sig_len != (prop->num_bits / 8)) {
debug("Signature is of incorrect length %d\n", sig_len);
return -EINVAL;
}
@@ -265,13 +65,23 @@
return -EINVAL;
}
- uint32_t buf[sig_len / sizeof(uint32_t)];
+ uint8_t buf[sig_len];
- memcpy(buf, sig, sig_len);
+#if !defined(USE_HOSTCC)
+ ret = uclass_get_device(UCLASS_MOD_EXP, 0, &mod_exp_dev);
+ if (ret) {
+ printf("RSA: Can't find Modular Exp implementation\n");
+ return -EINVAL;
+ }
- ret = pow_mod(key, buf);
- if (ret)
+ ret = rsa_mod_exp(mod_exp_dev, sig, sig_len, prop, buf);
+#else
+ ret = rsa_mod_exp_sw(sig, sig_len, prop, buf);
+#endif
+ if (ret) {
+ debug("Error in Modular exponentation\n");
return ret;
+ }
padding = algo->rsa_padding;
pad_len = algo->pad_len - algo->checksum_len;
@@ -291,72 +101,57 @@
return 0;
}
-static void rsa_convert_big_endian(uint32_t *dst, const uint32_t *src, int len)
-{
- int i;
-
- for (i = 0; i < len; i++)
- dst[i] = fdt32_to_cpu(src[len - 1 - i]);
-}
-
+/**
+ * rsa_verify_with_keynode() - Verify a signature against some data using
+ * information in node with prperties of RSA Key like modulus, exponent etc.
+ *
+ * Parse sign-node and fill a key_prop structure with properties of the
+ * key. Verify a RSA PKCS1.5 signature against an expected hash using
+ * the properties parsed
+ *
+ * @info: Specifies key and FIT information
+ * @hash: Pointer to the expected hash
+ * @sig: Signature
+ * @sig_len: Number of bytes in signature
+ * @node: Node having the RSA Key properties
+ * @return 0 if verified, -ve on error
+ */
static int rsa_verify_with_keynode(struct image_sign_info *info,
- const void *hash, uint8_t *sig, uint sig_len, int node)
+ const void *hash, uint8_t *sig,
+ uint sig_len, int node)
{
const void *blob = info->fdt_blob;
- struct rsa_public_key key;
- const void *modulus, *rr;
- const uint64_t *public_exponent;
+ struct key_prop prop;
int length;
- int ret;
+ int ret = 0;
if (node < 0) {
debug("%s: Skipping invalid node", __func__);
return -EBADF;
}
- if (!fdt_getprop(blob, node, "rsa,n0-inverse", NULL)) {
- debug("%s: Missing rsa,n0-inverse", __func__);
- return -EFAULT;
- }
- key.len = fdtdec_get_int(blob, node, "rsa,num-bits", 0);
- key.n0inv = fdtdec_get_int(blob, node, "rsa,n0-inverse", 0);
- public_exponent = fdt_getprop(blob, node, "rsa,exponent", &length);
- if (!public_exponent || length < sizeof(*public_exponent))
- key.exponent = RSA_DEFAULT_PUBEXP;
- else
- key.exponent = fdt64_to_cpu(*public_exponent);
- modulus = fdt_getprop(blob, node, "rsa,modulus", NULL);
- rr = fdt_getprop(blob, node, "rsa,r-squared", NULL);
- if (!key.len || !modulus || !rr) {
- debug("%s: Missing RSA key info", __func__);
- return -EFAULT;
- }
- /* Sanity check for stack size */
- if (key.len > RSA_MAX_KEY_BITS || key.len < RSA_MIN_KEY_BITS) {
- debug("RSA key bits %u outside allowed range %d..%d\n",
- key.len, RSA_MIN_KEY_BITS, RSA_MAX_KEY_BITS);
- return -EFAULT;
- }
- key.len /= sizeof(uint32_t) * 8;
- uint32_t key1[key.len], key2[key.len];
+ prop.num_bits = fdtdec_get_int(blob, node, "rsa,num-bits", 0);
- key.modulus = key1;
- key.rr = key2;
- rsa_convert_big_endian(key.modulus, modulus, key.len);
- rsa_convert_big_endian(key.rr, rr, key.len);
- if (!key.modulus || !key.rr) {
- debug("%s: Out of memory", __func__);
- return -ENOMEM;
- }
+ prop.n0inv = fdtdec_get_int(blob, node, "rsa,n0-inverse", 0);
- debug("key length %d\n", key.len);
- ret = rsa_verify_key(&key, sig, sig_len, hash, info->algo->checksum);
- if (ret) {
- printf("%s: RSA failed to verify: %d\n", __func__, ret);
- return ret;
+ prop.public_exponent = fdt_getprop(blob, node, "rsa,exponent", &length);
+ if (!prop.public_exponent || length < sizeof(uint64_t))
+ prop.public_exponent = NULL;
+
+ prop.exp_len = sizeof(uint64_t);
+
+ prop.modulus = fdt_getprop(blob, node, "rsa,modulus", NULL);
+
+ prop.rr = fdt_getprop(blob, node, "rsa,r-squared", NULL);
+
+ if (!prop.num_bits || !prop.modulus) {
+ debug("%s: Missing RSA key info", __func__);
+ return -EFAULT;
}
- return 0;
+ ret = rsa_verify_key(&prop, sig, sig_len, hash, info->algo->checksum);
+
+ return ret;
}
int rsa_verify(struct image_sign_info *info,
@@ -389,7 +184,12 @@
}
/* Calculate checksum with checksum-algorithm */
- info->algo->checksum->calculate(region, region_count, hash);
+ ret = info->algo->checksum->calculate(info->algo->checksum->name,
+ region, region_count, hash);
+ if (ret < 0) {
+ debug("%s: Error in checksum calculation\n", __func__);
+ return -EINVAL;
+ }
/* See if we must use a particular key */
if (info->required_keynode != -1) {
diff --git a/test/dm/bus.c b/test/dm/bus.c
index abbaccf..faffe6a 100644
--- a/test/dm/bus.c
+++ b/test/dm/bus.c
@@ -9,11 +9,18 @@
#include <dm/device-internal.h>
#include <dm/root.h>
#include <dm/test.h>
+#include <dm/uclass-internal.h>
#include <dm/ut.h>
#include <dm/util.h>
DECLARE_GLOBAL_DATA_PTR;
+struct dm_test_parent_platdata {
+ int count;
+ int bind_flag;
+ int uclass_bind_flag;
+};
+
enum {
FLAG_CHILD_PROBED = 10,
FLAG_CHILD_REMOVED = -7,
@@ -26,6 +33,17 @@
return dm_scan_fdt_node(dev, gd->fdt_blob, dev->of_offset, false);
}
+static int testbus_child_post_bind(struct udevice *dev)
+{
+ struct dm_test_parent_platdata *plat;
+
+ plat = dev_get_parent_platdata(dev);
+ plat->bind_flag = 1;
+ plat->uclass_bind_flag = 2;
+
+ return 0;
+}
+
static int testbus_child_pre_probe(struct udevice *dev)
{
struct dm_test_parent_data *parent_data = dev_get_parentdata(dev);
@@ -35,6 +53,15 @@
return 0;
}
+static int testbus_child_pre_probe_uclass(struct udevice *dev)
+{
+ struct dm_test_priv *priv = dev_get_priv(dev);
+
+ priv->uclass_flag++;
+
+ return 0;
+}
+
static int testbus_child_post_remove(struct udevice *dev)
{
struct dm_test_parent_data *parent_data = dev_get_parentdata(dev);
@@ -59,9 +86,12 @@
.of_match = testbus_ids,
.id = UCLASS_TEST_BUS,
.probe = testbus_drv_probe,
+ .child_post_bind = testbus_child_post_bind,
.priv_auto_alloc_size = sizeof(struct dm_test_priv),
.platdata_auto_alloc_size = sizeof(struct dm_test_pdata),
.per_child_auto_alloc_size = sizeof(struct dm_test_parent_data),
+ .per_child_platdata_auto_alloc_size =
+ sizeof(struct dm_test_parent_platdata),
.child_pre_probe = testbus_child_pre_probe,
.child_post_remove = testbus_child_post_remove,
};
@@ -69,12 +99,14 @@
UCLASS_DRIVER(testbus) = {
.name = "testbus",
.id = UCLASS_TEST_BUS,
+ .flags = DM_UC_FLAG_SEQ_ALIAS,
+ .child_pre_probe = testbus_child_pre_probe_uclass,
};
/* Test that we can probe for children */
static int dm_test_bus_children(struct dm_test_state *dms)
{
- int num_devices = 4;
+ int num_devices = 6;
struct udevice *bus;
struct uclass *uc;
@@ -172,7 +204,7 @@
DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
/* Test that the bus can store data about each child */
-static int dm_test_bus_parent_data(struct dm_test_state *dms)
+static int test_bus_parent_data(struct dm_test_state *dms)
{
struct dm_test_parent_data *parent_data;
struct udevice *bus, *dev;
@@ -231,9 +263,36 @@
return 0;
}
-
+/* Test that the bus can store data about each child */
+static int dm_test_bus_parent_data(struct dm_test_state *dms)
+{
+ return test_bus_parent_data(dms);
+}
DM_TEST(dm_test_bus_parent_data, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
+/* As above but the size is controlled by the uclass */
+static int dm_test_bus_parent_data_uclass(struct dm_test_state *dms)
+{
+ struct udevice *bus;
+ int size;
+ int ret;
+
+ /* Set the driver size to 0 so that the uclass size is used */
+ ut_assertok(uclass_find_device(UCLASS_TEST_BUS, 0, &bus));
+ size = bus->driver->per_child_auto_alloc_size;
+ bus->uclass->uc_drv->per_child_auto_alloc_size = size;
+ bus->driver->per_child_auto_alloc_size = 0;
+ ret = test_bus_parent_data(dms);
+ if (ret)
+ return ret;
+ bus->uclass->uc_drv->per_child_auto_alloc_size = 0;
+ bus->driver->per_child_auto_alloc_size = size;
+
+ return 0;
+}
+DM_TEST(dm_test_bus_parent_data_uclass,
+ DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
+
/* Test that the bus ops are called when a child is probed/removed */
static int dm_test_bus_parent_ops(struct dm_test_state *dms)
{
@@ -271,3 +330,188 @@
return 0;
}
DM_TEST(dm_test_bus_parent_ops, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
+
+static int test_bus_parent_platdata(struct dm_test_state *dms)
+{
+ struct dm_test_parent_platdata *plat;
+ struct udevice *bus, *dev;
+ int child_count;
+
+ /* Check that the bus has no children */
+ ut_assertok(uclass_find_device(UCLASS_TEST_BUS, 0, &bus));
+ device_find_first_child(bus, &dev);
+ ut_asserteq_ptr(NULL, dev);
+
+ ut_assertok(uclass_get_device(UCLASS_TEST_BUS, 0, &bus));
+
+ for (device_find_first_child(bus, &dev), child_count = 0;
+ dev;
+ device_find_next_child(&dev)) {
+ /* Check that platform data is allocated */
+ plat = dev_get_parent_platdata(dev);
+ ut_assert(plat != NULL);
+
+ /*
+ * Check that it is not affected by the device being
+ * probed/removed
+ */
+ plat->count++;
+ ut_asserteq(1, plat->count);
+ device_probe(dev);
+ device_remove(dev);
+
+ ut_asserteq_ptr(plat, dev_get_parent_platdata(dev));
+ ut_asserteq(1, plat->count);
+ ut_assertok(device_probe(dev));
+ child_count++;
+ }
+ ut_asserteq(3, child_count);
+
+ /* Removing the bus should also have no effect (it is still bound) */
+ device_remove(bus);
+ for (device_find_first_child(bus, &dev), child_count = 0;
+ dev;
+ device_find_next_child(&dev)) {
+ /* Check that platform data is allocated */
+ plat = dev_get_parent_platdata(dev);
+ ut_assert(plat != NULL);
+ ut_asserteq(1, plat->count);
+ child_count++;
+ }
+ ut_asserteq(3, child_count);
+
+ /* Unbind all the children */
+ do {
+ device_find_first_child(bus, &dev);
+ if (dev)
+ device_unbind(dev);
+ } while (dev);
+
+ /* Now the child platdata should be removed and re-added */
+ device_probe(bus);
+ for (device_find_first_child(bus, &dev), child_count = 0;
+ dev;
+ device_find_next_child(&dev)) {
+ /* Check that platform data is allocated */
+ plat = dev_get_parent_platdata(dev);
+ ut_assert(plat != NULL);
+ ut_asserteq(0, plat->count);
+ child_count++;
+ }
+ ut_asserteq(3, child_count);
+
+ return 0;
+}
+
+/* Test that the bus can store platform data about each child */
+static int dm_test_bus_parent_platdata(struct dm_test_state *dms)
+{
+ return test_bus_parent_platdata(dms);
+}
+DM_TEST(dm_test_bus_parent_platdata, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
+
+/* As above but the size is controlled by the uclass */
+static int dm_test_bus_parent_platdata_uclass(struct dm_test_state *dms)
+{
+ struct udevice *bus;
+ int size;
+ int ret;
+
+ /* Set the driver size to 0 so that the uclass size is used */
+ ut_assertok(uclass_find_device(UCLASS_TEST_BUS, 0, &bus));
+ size = bus->driver->per_child_platdata_auto_alloc_size;
+ bus->uclass->uc_drv->per_child_platdata_auto_alloc_size = size;
+ bus->driver->per_child_platdata_auto_alloc_size = 0;
+ ret = test_bus_parent_platdata(dms);
+ if (ret)
+ return ret;
+ bus->uclass->uc_drv->per_child_platdata_auto_alloc_size = 0;
+ bus->driver->per_child_platdata_auto_alloc_size = size;
+
+ return 0;
+}
+DM_TEST(dm_test_bus_parent_platdata_uclass,
+ DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
+
+/* Test that the child post_bind method is called */
+static int dm_test_bus_child_post_bind(struct dm_test_state *dms)
+{
+ struct dm_test_parent_platdata *plat;
+ struct udevice *bus, *dev;
+ int child_count;
+
+ ut_assertok(uclass_get_device(UCLASS_TEST_BUS, 0, &bus));
+ for (device_find_first_child(bus, &dev), child_count = 0;
+ dev;
+ device_find_next_child(&dev)) {
+ /* Check that platform data is allocated */
+ plat = dev_get_parent_platdata(dev);
+ ut_assert(plat != NULL);
+ ut_asserteq(1, plat->bind_flag);
+ child_count++;
+ }
+ ut_asserteq(3, child_count);
+
+ return 0;
+}
+DM_TEST(dm_test_bus_child_post_bind, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
+
+/* Test that the child post_bind method is called */
+static int dm_test_bus_child_post_bind_uclass(struct dm_test_state *dms)
+{
+ struct dm_test_parent_platdata *plat;
+ struct udevice *bus, *dev;
+ int child_count;
+
+ ut_assertok(uclass_get_device(UCLASS_TEST_BUS, 0, &bus));
+ for (device_find_first_child(bus, &dev), child_count = 0;
+ dev;
+ device_find_next_child(&dev)) {
+ /* Check that platform data is allocated */
+ plat = dev_get_parent_platdata(dev);
+ ut_assert(plat != NULL);
+ ut_asserteq(2, plat->uclass_bind_flag);
+ child_count++;
+ }
+ ut_asserteq(3, child_count);
+
+ return 0;
+}
+DM_TEST(dm_test_bus_child_post_bind_uclass,
+ DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
+
+/*
+ * Test that the bus' uclass' child_pre_probe() is called before the
+ * device's probe() method
+ */
+static int dm_test_bus_child_pre_probe_uclass(struct dm_test_state *dms)
+{
+ struct udevice *bus, *dev;
+ int child_count;
+
+ /*
+ * See testfdt_drv_probe() which effectively checks that the uclass
+ * flag is set before that method is called
+ */
+ ut_assertok(uclass_get_device(UCLASS_TEST_BUS, 0, &bus));
+ for (device_find_first_child(bus, &dev), child_count = 0;
+ dev;
+ device_find_next_child(&dev)) {
+ struct dm_test_priv *priv = dev_get_priv(dev);
+
+ /* Check that things happened in the right order */
+ ut_asserteq_ptr(NULL, priv);
+ ut_assertok(device_probe(dev));
+
+ priv = dev_get_priv(dev);
+ ut_assert(priv != NULL);
+ ut_asserteq(1, priv->uclass_flag);
+ ut_asserteq(1, priv->uclass_total);
+ child_count++;
+ }
+ ut_asserteq(3, child_count);
+
+ return 0;
+}
+DM_TEST(dm_test_bus_child_pre_probe_uclass,
+ DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
diff --git a/test/dm/core.c b/test/dm/core.c
index ff5c2a7..eccda09 100644
--- a/test/dm/core.c
+++ b/test/dm/core.c
@@ -598,3 +598,14 @@
}
DM_TEST(dm_test_uclass_before_ready, 0);
+
+static int dm_test_device_get_uclass_id(struct dm_test_state *dms)
+{
+ struct udevice *dev;
+
+ ut_assertok(uclass_get_device(UCLASS_TEST, 0, &dev));
+ ut_asserteq(UCLASS_TEST, device_get_uclass_id(dev));
+
+ return 0;
+}
+DM_TEST(dm_test_device_get_uclass_id, DM_TESTF_SCAN_PDATA);
diff --git a/test/dm/gpio.c b/test/dm/gpio.c
index 94bd0d9..b29daf1 100644
--- a/test/dm/gpio.c
+++ b/test/dm/gpio.c
@@ -174,5 +174,72 @@
return 0;
}
-
DM_TEST(dm_test_gpio_leak, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
+
+/* Test that we can find GPIOs using phandles */
+static int dm_test_gpio_phandles(struct dm_test_state *dms)
+{
+ struct gpio_desc desc, desc_list[8], desc_list2[8];
+ struct udevice *dev, *gpio_a, *gpio_b;
+
+ ut_assertok(uclass_get_device(UCLASS_TEST_FDT, 0, &dev));
+ ut_asserteq_str("a-test", dev->name);
+
+ ut_assertok(gpio_request_by_name(dev, "test-gpios", 1, &desc, 0));
+ ut_assertok(uclass_get_device(UCLASS_GPIO, 1, &gpio_a));
+ ut_assertok(uclass_get_device(UCLASS_GPIO, 2, &gpio_b));
+ ut_asserteq_str("base-gpios", gpio_a->name);
+ ut_asserteq(true, !!device_active(gpio_a));
+ ut_asserteq_ptr(gpio_a, desc.dev);
+ ut_asserteq(4, desc.offset);
+ /* GPIOF_INPUT is the sandbox GPIO driver default */
+ ut_asserteq(GPIOF_INPUT, gpio_get_function(gpio_a, 4, NULL));
+ ut_assertok(dm_gpio_free(dev, &desc));
+
+ ut_asserteq(-ENOENT, gpio_request_by_name(dev, "test-gpios", 3, &desc,
+ 0));
+ ut_asserteq_ptr(NULL, desc.dev);
+ ut_asserteq(desc.offset, 0);
+ ut_asserteq(-ENOENT, gpio_request_by_name(dev, "test-gpios", 5, &desc,
+ 0));
+
+ /* Last GPIO is ignord as it comes after <0> */
+ ut_asserteq(3, gpio_request_list_by_name(dev, "test-gpios", desc_list,
+ ARRAY_SIZE(desc_list), 0));
+ ut_asserteq(-EBUSY, gpio_request_list_by_name(dev, "test-gpios",
+ desc_list2,
+ ARRAY_SIZE(desc_list2),
+ 0));
+ ut_assertok(gpio_free_list(dev, desc_list, 3));
+ ut_asserteq(3, gpio_request_list_by_name(dev, "test-gpios", desc_list,
+ ARRAY_SIZE(desc_list),
+ GPIOD_IS_OUT |
+ GPIOD_IS_OUT_ACTIVE));
+ ut_asserteq_ptr(gpio_a, desc_list[0].dev);
+ ut_asserteq(1, desc_list[0].offset);
+ ut_asserteq_ptr(gpio_a, desc_list[1].dev);
+ ut_asserteq(4, desc_list[1].offset);
+ ut_asserteq_ptr(gpio_b, desc_list[2].dev);
+ ut_asserteq(5, desc_list[2].offset);
+ ut_asserteq(1, dm_gpio_get_value(desc_list));
+ ut_assertok(gpio_free_list(dev, desc_list, 3));
+
+ ut_asserteq(6, gpio_request_list_by_name(dev, "test2-gpios", desc_list,
+ ARRAY_SIZE(desc_list), 0));
+ /* This was set to output previously, so still will be */
+ ut_asserteq(GPIOF_OUTPUT, gpio_get_function(gpio_a, 1, NULL));
+
+ /* Active low should invert the input value */
+ ut_asserteq(GPIOF_INPUT, gpio_get_function(gpio_b, 6, NULL));
+ ut_asserteq(1, dm_gpio_get_value(&desc_list[2]));
+
+ ut_asserteq(GPIOF_INPUT, gpio_get_function(gpio_b, 7, NULL));
+ ut_asserteq(GPIOF_OUTPUT, gpio_get_function(gpio_b, 8, NULL));
+ ut_asserteq(0, dm_gpio_get_value(&desc_list[4]));
+ ut_asserteq(GPIOF_OUTPUT, gpio_get_function(gpio_b, 9, NULL));
+ ut_asserteq(1, dm_gpio_get_value(&desc_list[5]));
+
+
+ return 0;
+}
+DM_TEST(dm_test_gpio_phandles, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
diff --git a/test/dm/i2c.c b/test/dm/i2c.c
index a53e28d..ef88372 100644
--- a/test/dm/i2c.c
+++ b/test/dm/i2c.c
@@ -35,8 +35,8 @@
* remove the emulation and the slave device.
*/
ut_assertok(uclass_get_device_by_seq(UCLASS_I2C, busnum, &bus));
- ut_assertok(i2c_probe(bus, chip, 0, &dev));
- ut_asserteq(-ENODEV, i2c_probe(bus, no_chip, 0, &dev));
+ ut_assertok(dm_i2c_probe(bus, chip, 0, &dev));
+ ut_asserteq(-ENODEV, dm_i2c_probe(bus, no_chip, 0, &dev));
ut_asserteq(-ENODEV, uclass_get_device_by_seq(UCLASS_I2C, 1, &bus));
return 0;
@@ -49,11 +49,11 @@
uint8_t buf[5];
ut_assertok(uclass_get_device_by_seq(UCLASS_I2C, busnum, &bus));
- ut_assertok(i2c_get_chip(bus, chip, &dev));
- ut_assertok(i2c_read(dev, 0, buf, 5));
+ ut_assertok(i2c_get_chip(bus, chip, 1, &dev));
+ ut_assertok(dm_i2c_read(dev, 0, buf, 5));
ut_assertok(memcmp(buf, "\0\0\0\0\0", sizeof(buf)));
- ut_assertok(i2c_write(dev, 2, (uint8_t *)"AB", 2));
- ut_assertok(i2c_read(dev, 0, buf, 5));
+ ut_assertok(dm_i2c_write(dev, 2, (uint8_t *)"AB", 2));
+ ut_assertok(dm_i2c_read(dev, 0, buf, 5));
ut_assertok(memcmp(buf, "\0\0AB\0", sizeof(buf)));
return 0;
@@ -66,13 +66,13 @@
uint8_t buf[5];
ut_assertok(uclass_get_device_by_seq(UCLASS_I2C, busnum, &bus));
- ut_assertok(i2c_get_chip(bus, chip, &dev));
+ ut_assertok(i2c_get_chip(bus, chip, 1, &dev));
ut_assertok(i2c_set_bus_speed(bus, 100000));
- ut_assertok(i2c_read(dev, 0, buf, 5));
+ ut_assertok(dm_i2c_read(dev, 0, buf, 5));
ut_assertok(i2c_set_bus_speed(bus, 400000));
ut_asserteq(400000, i2c_get_bus_speed(bus));
- ut_assertok(i2c_read(dev, 0, buf, 5));
- ut_asserteq(-EINVAL, i2c_write(dev, 0, buf, 5));
+ ut_assertok(dm_i2c_read(dev, 0, buf, 5));
+ ut_asserteq(-EINVAL, dm_i2c_write(dev, 0, buf, 5));
return 0;
}
@@ -84,9 +84,9 @@
uint8_t buf[5];
ut_assertok(uclass_get_device_by_seq(UCLASS_I2C, busnum, &bus));
- ut_assertok(i2c_get_chip(bus, chip, &dev));
+ ut_assertok(i2c_get_chip(bus, chip, 1, &dev));
ut_assertok(i2c_set_chip_offset_len(dev, 1));
- ut_assertok(i2c_read(dev, 0, buf, 5));
+ ut_assertok(dm_i2c_read(dev, 0, buf, 5));
/* This is not supported by the uclass */
ut_asserteq(-EINVAL, i2c_set_chip_offset_len(dev, 5));
@@ -100,7 +100,7 @@
struct udevice *bus, *dev;
ut_assertok(uclass_get_device_by_seq(UCLASS_I2C, busnum, &bus));
- ut_assertok(i2c_probe(bus, SANDBOX_I2C_TEST_ADDR, 0, &dev));
+ ut_assertok(dm_i2c_probe(bus, SANDBOX_I2C_TEST_ADDR, 0, &dev));
return 0;
}
@@ -113,8 +113,8 @@
uint8_t buf[5];
ut_assertok(uclass_get_device_by_seq(UCLASS_I2C, busnum, &bus));
- ut_assertok(i2c_get_chip(bus, chip, &dev));
- ut_assertok(i2c_read(dev, 0, buf, 5));
+ ut_assertok(i2c_get_chip(bus, chip, 1, &dev));
+ ut_assertok(dm_i2c_read(dev, 0, buf, 5));
ut_assertok(memcmp(buf, "\0\0\0\0\0", sizeof(buf)));
/* Tell the EEPROM to only read/write one register at a time */
@@ -123,34 +123,34 @@
sandbox_i2c_eeprom_set_test_mode(eeprom, SIE_TEST_MODE_SINGLE_BYTE);
/* Now we only get the first byte - the rest will be 0xff */
- ut_assertok(i2c_read(dev, 0, buf, 5));
+ ut_assertok(dm_i2c_read(dev, 0, buf, 5));
ut_assertok(memcmp(buf, "\0\xff\xff\xff\xff", sizeof(buf)));
/* If we do a separate transaction for each byte, it works */
ut_assertok(i2c_set_chip_flags(dev, DM_I2C_CHIP_RD_ADDRESS));
- ut_assertok(i2c_read(dev, 0, buf, 5));
+ ut_assertok(dm_i2c_read(dev, 0, buf, 5));
ut_assertok(memcmp(buf, "\0\0\0\0\0", sizeof(buf)));
/* This will only write A */
ut_assertok(i2c_set_chip_flags(dev, 0));
- ut_assertok(i2c_write(dev, 2, (uint8_t *)"AB", 2));
- ut_assertok(i2c_read(dev, 0, buf, 5));
+ ut_assertok(dm_i2c_write(dev, 2, (uint8_t *)"AB", 2));
+ ut_assertok(dm_i2c_read(dev, 0, buf, 5));
ut_assertok(memcmp(buf, "\0\xff\xff\xff\xff", sizeof(buf)));
/* Check that the B was ignored */
ut_assertok(i2c_set_chip_flags(dev, DM_I2C_CHIP_RD_ADDRESS));
- ut_assertok(i2c_read(dev, 0, buf, 5));
+ ut_assertok(dm_i2c_read(dev, 0, buf, 5));
ut_assertok(memcmp(buf, "\0\0A\0\0\0", sizeof(buf)));
/* Now write it again with the new flags, it should work */
ut_assertok(i2c_set_chip_flags(dev, DM_I2C_CHIP_WR_ADDRESS));
- ut_assertok(i2c_write(dev, 2, (uint8_t *)"AB", 2));
- ut_assertok(i2c_read(dev, 0, buf, 5));
+ ut_assertok(dm_i2c_write(dev, 2, (uint8_t *)"AB", 2));
+ ut_assertok(dm_i2c_read(dev, 0, buf, 5));
ut_assertok(memcmp(buf, "\0\xff\xff\xff\xff", sizeof(buf)));
ut_assertok(i2c_set_chip_flags(dev, DM_I2C_CHIP_WR_ADDRESS |
DM_I2C_CHIP_RD_ADDRESS));
- ut_assertok(i2c_read(dev, 0, buf, 5));
+ ut_assertok(dm_i2c_read(dev, 0, buf, 5));
ut_assertok(memcmp(buf, "\0\0AB\0\0", sizeof(buf)));
/* Restore defaults */
@@ -167,45 +167,45 @@
struct udevice *dev;
uint8_t buf[5];
- ut_assertok(i2c_get_chip_for_busnum(busnum, chip, &dev));
+ ut_assertok(i2c_get_chip_for_busnum(busnum, chip, 1, &dev));
/* Do a transfer so we can find the emulator */
- ut_assertok(i2c_read(dev, 0, buf, 5));
+ ut_assertok(dm_i2c_read(dev, 0, buf, 5));
ut_assertok(uclass_first_device(UCLASS_I2C_EMUL, &eeprom));
/* Offset length 0 */
sandbox_i2c_eeprom_set_offset_len(eeprom, 0);
ut_assertok(i2c_set_chip_offset_len(dev, 0));
- ut_assertok(i2c_write(dev, 10 /* ignored */, (uint8_t *)"AB", 2));
- ut_assertok(i2c_read(dev, 0, buf, 5));
+ ut_assertok(dm_i2c_write(dev, 10 /* ignored */, (uint8_t *)"AB", 2));
+ ut_assertok(dm_i2c_read(dev, 0, buf, 5));
ut_assertok(memcmp(buf, "AB\0\0\0\0", sizeof(buf)));
/* Offset length 1 */
sandbox_i2c_eeprom_set_offset_len(eeprom, 1);
ut_assertok(i2c_set_chip_offset_len(dev, 1));
- ut_assertok(i2c_write(dev, 2, (uint8_t *)"AB", 2));
- ut_assertok(i2c_read(dev, 0, buf, 5));
+ ut_assertok(dm_i2c_write(dev, 2, (uint8_t *)"AB", 2));
+ ut_assertok(dm_i2c_read(dev, 0, buf, 5));
ut_assertok(memcmp(buf, "ABAB\0", sizeof(buf)));
/* Offset length 2 */
sandbox_i2c_eeprom_set_offset_len(eeprom, 2);
ut_assertok(i2c_set_chip_offset_len(dev, 2));
- ut_assertok(i2c_write(dev, 0x210, (uint8_t *)"AB", 2));
- ut_assertok(i2c_read(dev, 0x210, buf, 5));
+ ut_assertok(dm_i2c_write(dev, 0x210, (uint8_t *)"AB", 2));
+ ut_assertok(dm_i2c_read(dev, 0x210, buf, 5));
ut_assertok(memcmp(buf, "AB\0\0\0", sizeof(buf)));
/* Offset length 3 */
sandbox_i2c_eeprom_set_offset_len(eeprom, 2);
ut_assertok(i2c_set_chip_offset_len(dev, 2));
- ut_assertok(i2c_write(dev, 0x410, (uint8_t *)"AB", 2));
- ut_assertok(i2c_read(dev, 0x410, buf, 5));
+ ut_assertok(dm_i2c_write(dev, 0x410, (uint8_t *)"AB", 2));
+ ut_assertok(dm_i2c_read(dev, 0x410, buf, 5));
ut_assertok(memcmp(buf, "AB\0\0\0", sizeof(buf)));
/* Offset length 4 */
sandbox_i2c_eeprom_set_offset_len(eeprom, 2);
ut_assertok(i2c_set_chip_offset_len(dev, 2));
- ut_assertok(i2c_write(dev, 0x420, (uint8_t *)"AB", 2));
- ut_assertok(i2c_read(dev, 0x420, buf, 5));
+ ut_assertok(dm_i2c_write(dev, 0x420, (uint8_t *)"AB", 2));
+ ut_assertok(dm_i2c_read(dev, 0x420, buf, 5));
ut_assertok(memcmp(buf, "AB\0\0\0", sizeof(buf)));
/* Restore defaults */
diff --git a/test/dm/spi.c b/test/dm/spi.c
index 61b5b25..c7ee652 100644
--- a/test/dm/spi.c
+++ b/test/dm/spi.c
@@ -36,7 +36,6 @@
ut_asserteq(0, uclass_get_device_by_seq(UCLASS_SPI, busnum, &bus));
ut_assertok(spi_cs_info(bus, cs, &info));
of_offset = info.dev->of_offset;
- sandbox_sf_unbind_emul(state_get_current(), busnum, cs);
device_remove(info.dev);
device_unbind(info.dev);
@@ -45,7 +44,7 @@
* reports that CS 0 is present
*/
ut_assertok(spi_cs_info(bus, cs, &info));
- ut_asserteq_ptr(info.dev, NULL);
+ ut_asserteq_ptr(NULL, info.dev);
/* This finds nothing because we removed the device */
ut_asserteq(-ENODEV, spi_find_bus_and_cs(busnum, cs, &bus, &dev));
@@ -62,8 +61,9 @@
ut_asserteq(-ENOENT, spi_get_bus_and_cs(busnum, cs, speed, mode,
"spi_flash_std", "name", &bus,
&slave));
+ sandbox_sf_unbind_emul(state_get_current(), busnum, cs);
ut_assertok(spi_cs_info(bus, cs, &info));
- ut_asserteq_ptr(info.dev, NULL);
+ ut_asserteq_ptr(NULL, info.dev);
/* Add the emulation and try again */
ut_assertok(sandbox_sf_bind_emul(state, busnum, cs, bus, of_offset,
diff --git a/test/dm/test-dm.sh b/test/dm/test-dm.sh
index bb99677..8ebc392 100755
--- a/test/dm/test-dm.sh
+++ b/test/dm/test-dm.sh
@@ -1,9 +1,14 @@
#!/bin/sh
+die() {
+ echo $1
+ exit 1
+}
+
NUM_CPUS=$(cat /proc/cpuinfo |grep -c processor)
dtc -I dts -O dtb test/dm/test.dts -o test/dm/test.dtb
-make O=sandbox sandbox_config
-make O=sandbox -s -j${NUM_CPUS}
+make O=sandbox sandbox_config || die "Cannot configure U-Boot"
+make O=sandbox -s -j${NUM_CPUS} || die "Cannot build U-Boot"
dd if=/dev/zero of=spi.bin bs=1M count=2
./sandbox/u-boot -d test/dm/test.dtb -c "dm test"
rm spi.bin
diff --git a/test/dm/test-fdt.c b/test/dm/test-fdt.c
index cd2c389..b8ee959 100644
--- a/test/dm/test-fdt.c
+++ b/test/dm/test-fdt.c
@@ -51,6 +51,13 @@
priv->ping_total += DM_TEST_START_TOTAL;
+ /*
+ * If this device is on a bus, the uclass_flag will be set before
+ * calling this function. This is used by
+ * dm_test_bus_child_pre_probe_uclass().
+ */
+ priv->uclass_total += priv->uclass_flag;
+
return 0;
}
@@ -89,6 +96,7 @@
UCLASS_DRIVER(testfdt) = {
.name = "testfdt",
.id = UCLASS_TEST_FDT,
+ .flags = DM_UC_FLAG_SEQ_ALIAS,
};
int dm_check_devices(struct dm_test_state *dms, int num_devices)
@@ -128,7 +136,7 @@
/* Test that FDT-based binding works correctly */
static int dm_test_fdt(struct dm_test_state *dms)
{
- const int num_devices = 4;
+ const int num_devices = 6;
struct udevice *dev;
struct uclass *uc;
int ret;
@@ -143,12 +151,12 @@
/* These are num_devices compatible root-level device tree nodes */
ut_asserteq(num_devices, list_count_items(&uc->dev_head));
- /* Each should have no platdata / priv */
+ /* Each should have platform data but no private data */
for (i = 0; i < num_devices; i++) {
ret = uclass_find_device(UCLASS_TEST_FDT, i, &dev);
ut_assert(!ret);
ut_assert(!dev_get_priv(dev));
- ut_assert(!dev->platdata);
+ ut_assert(dev->platdata);
}
ut_assertok(dm_check_devices(dms, num_devices));
@@ -184,7 +192,7 @@
ut_assertok(uclass_find_device_by_seq(UCLASS_TEST_FDT, 3, true, &dev));
ut_asserteq_str("b-test", dev->name);
- ut_assertok(uclass_find_device_by_seq(UCLASS_TEST_FDT, 0, true, &dev));
+ ut_assertok(uclass_find_device_by_seq(UCLASS_TEST_FDT, 8, true, &dev));
ut_asserteq_str("a-test", dev->name);
ut_asserteq(-ENODEV, uclass_find_device_by_seq(UCLASS_TEST_FDT, 5,
@@ -220,11 +228,11 @@
ut_asserteq(-ENODEV, uclass_get_device_by_seq(UCLASS_TEST_FDT, 1,
&dev));
ut_assertok(uclass_get_device(UCLASS_TEST_FDT, 0, &dev));
- ut_assertok(uclass_get_device(UCLASS_TEST_FDT, 1, &dev));
+ ut_assertok(uclass_get_device(UCLASS_TEST_FDT, 4, &dev));
/* But now that it is probed, we can find it */
ut_assertok(uclass_get_device_by_seq(UCLASS_TEST_FDT, 1, &dev));
- ut_asserteq_str("a-test", dev->name);
+ ut_asserteq_str("f-test", dev->name);
return 0;
}
diff --git a/test/dm/test.dts b/test/dm/test.dts
index fb0272a..84024a4 100644
--- a/test/dm/test.dts
+++ b/test/dm/test.dts
@@ -8,7 +8,15 @@
aliases {
console = &uart0;
+ i2c0 = "/i2c@0";
+ spi0 = "/spi@0";
testfdt6 = "/e-test";
+ testbus3 = "/some-bus";
+ testfdt0 = "/some-bus/c-test@0";
+ testfdt1 = "/some-bus/c-test@1";
+ testfdt3 = "/b-test";
+ testfdt5 = "/some-bus/c-test@5";
+ testfdt8 = "/a-test";
};
uart0: serial {
@@ -22,6 +30,11 @@
ping-expect = <0>;
ping-add = <0>;
u-boot,dm-pre-reloc;
+ test-gpios = <&gpio_a 1>, <&gpio_a 4>, <&gpio_b 5 0 3 2 1>,
+ <0>, <&gpio_a 12>;
+ test2-gpios = <&gpio_a 1>, <&gpio_a 4>, <&gpio_b 6 1 3 2 1>,
+ <&gpio_b 7 2 3 2 1>, <&gpio_b 8 4 3 2 1>,
+ <&gpio_b 9 0xc 3 2 1>;
};
junk {
@@ -81,14 +94,26 @@
compatible = "google,another-fdt-test";
};
+ f-test {
+ compatible = "denx,u-boot-fdt-test";
+ };
+
+ g-test {
+ compatible = "denx,u-boot-fdt-test";
+ };
+
gpio_a: base-gpios {
compatible = "sandbox,gpio";
+ gpio-controller;
+ #gpio-cells = <1>;
gpio-bank-name = "a";
num-gpios = <20>;
};
- extra-gpios {
+ gpio_b: extra-gpios {
compatible = "sandbox,gpio";
+ gpio-controller;
+ #gpio-cells = <5>;
gpio-bank-name = "b";
num-gpios = <10>;
};
diff --git a/test/image/test-imagetools.sh b/test/image/test-imagetools.sh
index 9e299e1..952f975 100755
--- a/test/image/test-imagetools.sh
+++ b/test/image/test-imagetools.sh
@@ -13,9 +13,11 @@
# ./test/image/test-imagetools.sh
BASEDIR=sandbox
-SRCDIR=sandbox/boot
+SRCDIR=${BASEDIR}/boot
IMAGE_NAME="v1.0-test"
-IMAGE=linux.img
+IMAGE_MULTI=linux.img
+IMAGE_FIT_ITS=linux.its
+IMAGE_FIT_ITB=linux.itb
DATAFILE0=vmlinuz
DATAFILE1=initrd.img
DATAFILE2=System.map
@@ -34,14 +36,17 @@
for file in ${DATAFILES}; do
rm -f ${file} ${SRCDIR}/${file}
done
- rm -f ${IMAGE} ${DUMPIMAGE_LIST} ${MKIMAGE_LIST} ${TEST_OUT}
+ rm -f ${IMAGE_MULTI}
+ rm -f ${DUMPIMAGE_LIST}
+ rm -f ${MKIMAGE_LIST}
+ rm -f ${TEST_OUT}
rmdir ${SRCDIR}
}
# Check that two files are the same
assert_equal()
{
- if ! diff $1 $2; then
+ if ! diff -u $1 $2; then
echo "Failed."
cleanup
exit 1
@@ -82,35 +87,103 @@
${cmd} >${redir}
}
-# Write files into an image
-create_image()
+# Write files into an multi-file image
+create_multi_image()
{
local files="${SRCDIR}/${DATAFILE0}:${SRCDIR}/${DATAFILE1}"
files+=":${SRCDIR}/${DATAFILE2}"
- echo -e "\nBuilding image..."
+ echo -e "\nBuilding multi-file image..."
do_cmd ${MKIMAGE} -A x86 -O linux -T multi -n \"${IMAGE_NAME}\" \
- -d ${files} ${IMAGE}
+ -d ${files} ${IMAGE_MULTI}
echo "done."
}
-# Extract files from an image
-extract_image()
+# Extract files from an multi-file image
+extract_multi_image()
{
- echo -e "\nExtracting image contents..."
- do_cmd ${DUMPIMAGE} -i ${IMAGE} -p 0 ${DATAFILE0}
- do_cmd ${DUMPIMAGE} -i ${IMAGE} -p 1 ${DATAFILE1}
- do_cmd ${DUMPIMAGE} -i ${IMAGE} -p 2 ${DATAFILE2}
- do_cmd ${DUMPIMAGE} -i ${IMAGE} -p 2 ${DATAFILE2} -o ${TEST_OUT}
+ echo -e "\nExtracting multi-file image contents..."
+ do_cmd ${DUMPIMAGE} -T multi -i ${IMAGE_MULTI} -p 0 ${DATAFILE0}
+ do_cmd ${DUMPIMAGE} -T multi -i ${IMAGE_MULTI} -p 1 ${DATAFILE1}
+ do_cmd ${DUMPIMAGE} -T multi -i ${IMAGE_MULTI} -p 2 ${DATAFILE2}
+ do_cmd ${DUMPIMAGE} -T multi -i ${IMAGE_MULTI} -p 2 ${DATAFILE2} -o ${TEST_OUT}
echo "done."
}
+# Write files into a FIT image
+create_fit_image()
+{
+ echo " \
+ /dts-v1/; \
+ / { \
+ description = \"FIT image\"; \
+ #address-cells = <1>; \
+ \
+ images { \
+ kernel@1 { \
+ description = \"kernel\"; \
+ data = /incbin/(\"${DATAFILE0}\"); \
+ type = \"kernel\"; \
+ arch = \"sandbox\"; \
+ os = \"linux\"; \
+ compression = \"gzip\"; \
+ load = <0x40000>; \
+ entry = <0x8>; \
+ }; \
+ ramdisk@1 { \
+ description = \"filesystem\"; \
+ data = /incbin/(\"${DATAFILE1}\"); \
+ type = \"ramdisk\"; \
+ arch = \"sandbox\"; \
+ os = \"linux\"; \
+ compression = \"none\"; \
+ load = <0x80000>; \
+ entry = <0x16>; \
+ }; \
+ fdt@1 { \
+ description = \"device tree\"; \
+ data = /incbin/(\"${DATAFILE2}\"); \
+ type = \"flat_dt\"; \
+ arch = \"sandbox\"; \
+ compression = \"none\"; \
+ }; \
+ }; \
+ configurations { \
+ default = \"conf@1\"; \
+ conf@1 { \
+ kernel = \"kernel@1\"; \
+ fdt = \"fdt@1\"; \
+ }; \
+ }; \
+ }; \
+ " > ${IMAGE_FIT_ITS}
+
+ echo -e "\nBuilding FIT image..."
+ do_cmd ${MKIMAGE} -f ${IMAGE_FIT_ITS} ${IMAGE_FIT_ITB}
+ echo "done."
+}
+
+# Extract files from a FIT image
+extract_fit_image()
+{
+ echo -e "\nExtracting FIT image contents..."
+ do_cmd ${DUMPIMAGE} -T flat_dt -i ${IMAGE_FIT_ITB} -p 0 ${DATAFILE0}
+ do_cmd ${DUMPIMAGE} -T flat_dt -i ${IMAGE_FIT_ITB} -p 1 ${DATAFILE1}
+ do_cmd ${DUMPIMAGE} -T flat_dt -i ${IMAGE_FIT_ITB} -p 2 ${DATAFILE2}
+ do_cmd ${DUMPIMAGE} -T flat_dt -i ${IMAGE_FIT_ITB} -p 2 ${DATAFILE2} -o ${TEST_OUT}
+ echo "done."
+}
+
# List the contents of a file
+# Args:
+# image filename
list_image()
{
+ local image="$1"
+
echo -e "\nListing image contents..."
- do_cmd_redir ${MKIMAGE_LIST} ${MKIMAGE} -l ${IMAGE}
- do_cmd_redir ${DUMPIMAGE_LIST} ${DUMPIMAGE} -l ${IMAGE}
+ do_cmd_redir ${MKIMAGE_LIST} ${MKIMAGE} -l ${image}
+ do_cmd_redir ${DUMPIMAGE_LIST} ${DUMPIMAGE} -l ${image}
echo "done."
}
@@ -120,16 +193,28 @@
create_files
+ # Compress and extract multi-file images, compare the result
+ create_multi_image
+ extract_multi_image
+ for file in ${DATAFILES}; do
+ assert_equal ${file} ${SRCDIR}/${file}
+ done
+ assert_equal ${TEST_OUT} ${DATAFILE2}
+
+ # List contents of multi-file image and compares output from tools
+ list_image ${IMAGE_MULTI}
+ assert_equal ${DUMPIMAGE_LIST} ${MKIMAGE_LIST}
+
- # Compress and extract multifile images, compare the result
- create_image
- extract_image
+ # Compress and extract FIT images, compare the result
+ create_fit_image
+ extract_fit_image
for file in ${DATAFILES}; do
assert_equal ${file} ${SRCDIR}/${file}
done
assert_equal ${TEST_OUT} ${DATAFILE2}
- # List contents and compares output fro tools
- list_image
+ # List contents of FIT image and compares output from tools
+ list_image ${IMAGE_FIT_ITB}
assert_equal ${DUMPIMAGE_LIST} ${MKIMAGE_LIST}
# Remove files created
diff --git a/tools/Makefile b/tools/Makefile
index e549f8e..6e1ce79 100644
--- a/tools/Makefile
+++ b/tools/Makefile
@@ -60,7 +60,8 @@
LIBFDT_OBJS := $(addprefix lib/libfdt/, \
fdt.o fdt_ro.o fdt_rw.o fdt_strerror.o fdt_wip.o)
RSA_OBJS-$(CONFIG_FIT_SIGNATURE) := $(addprefix lib/rsa/, \
- rsa-sign.o rsa-verify.o rsa-checksum.o)
+ rsa-sign.o rsa-verify.o rsa-checksum.o \
+ rsa-mod-exp.o)
# common objs for dumpimage and mkimage
dumpimage-mkimage-objs := aisimage.o \
@@ -90,6 +91,7 @@
socfpgaimage.o \
lib/sha1.o \
lib/sha256.o \
+ common/hash.o \
ublimage.o \
$(LIBFDT_OBJS) \
$(RSA_OBJS-y)
@@ -122,6 +124,8 @@
HOSTLOADLIBES_fit_info := $(HOSTLOADLIBES_mkimage)
HOSTLOADLIBES_fit_check_sign := $(HOSTLOADLIBES_mkimage)
+HOSTLDFLAGS += -T $(srctree)/tools/imagetool.lds
+
hostprogs-$(CONFIG_EXYNOS5250) += mkexynosspl
hostprogs-$(CONFIG_EXYNOS5420) += mkexynosspl
HOSTCFLAGS_mkexynosspl.o := -pedantic
diff --git a/tools/aisimage.c b/tools/aisimage.c
index 8de370a..9338342 100644
--- a/tools/aisimage.c
+++ b/tools/aisimage.c
@@ -413,19 +413,17 @@
/*
* aisimage parameters
*/
-static struct image_type_params aisimage_params = {
- .name = "TI Davinci AIS Boot Image support",
- .header_size = 0,
- .hdr = NULL,
- .check_image_type = aisimage_check_image_types,
- .verify_header = aisimage_verify_header,
- .print_header = aisimage_print_header,
- .set_header = aisimage_set_header,
- .check_params = aisimage_check_params,
- .vrec_header = aisimage_generate,
-};
-
-void init_ais_image_type(void)
-{
- register_image_type(&aisimage_params);
-}
+U_BOOT_IMAGE_TYPE(
+ aisimage,
+ "TI Davinci AIS Boot Image support",
+ 0,
+ NULL,
+ aisimage_check_params,
+ aisimage_verify_header,
+ aisimage_print_header,
+ aisimage_set_header,
+ NULL,
+ aisimage_check_image_types,
+ NULL,
+ aisimage_generate
+);
diff --git a/tools/atmelimage.c b/tools/atmelimage.c
index c8101d2..5b72ac5 100644
--- a/tools/atmelimage.c
+++ b/tools/atmelimage.c
@@ -324,19 +324,17 @@
return EXIT_SUCCESS;
}
-static struct image_type_params atmelimage_params = {
- .name = "ATMEL ROM-Boot Image support",
- .header_size = 0,
- .hdr = NULL,
- .check_image_type = atmel_check_image_type,
- .verify_header = atmel_verify_header,
- .print_header = atmel_print_header,
- .set_header = atmel_set_header,
- .check_params = atmel_check_params,
- .vrec_header = atmel_vrec_header,
-};
-
-void init_atmel_image_type(void)
-{
- register_image_type(&atmelimage_params);
-}
+U_BOOT_IMAGE_TYPE(
+ atmelimage,
+ "ATMEL ROM-Boot Image support",
+ 0,
+ NULL,
+ atmel_check_params,
+ atmel_verify_header,
+ atmel_print_header,
+ atmel_set_header,
+ NULL,
+ atmel_check_image_type,
+ NULL,
+ atmel_vrec_header
+);
diff --git a/tools/default_image.c b/tools/default_image.c
index 0a0792e..cf5c0d4 100644
--- a/tools/default_image.c
+++ b/tools/default_image.c
@@ -15,6 +15,8 @@
*/
#include "imagetool.h"
+#include "mkimage.h"
+
#include <image.h>
#include <u-boot/crc.h>
@@ -53,9 +55,8 @@
memcpy(hdr, ptr, sizeof(image_header_t));
if (be32_to_cpu(hdr->ih_magic) != IH_MAGIC) {
- fprintf(stderr,
- "%s: Bad Magic Number: \"%s\" is no valid image\n",
- params->cmdname, params->imagefile);
+ debug("%s: Bad Magic Number: \"%s\" is no valid image\n",
+ params->cmdname, params->imagefile);
return -FDT_ERR_BADMAGIC;
}
@@ -66,9 +67,8 @@
hdr->ih_hcrc = cpu_to_be32(0); /* clear for re-calculation */
if (crc32(0, data, len) != checksum) {
- fprintf(stderr,
- "%s: ERROR: \"%s\" has bad header checksum!\n",
- params->cmdname, params->imagefile);
+ debug("%s: ERROR: \"%s\" has bad header checksum!\n",
+ params->cmdname, params->imagefile);
return -FDT_ERR_BADSTATE;
}
@@ -77,9 +77,8 @@
checksum = be32_to_cpu(hdr->ih_dcrc);
if (crc32(0, data, len) != checksum) {
- fprintf(stderr,
- "%s: ERROR: \"%s\" has corrupted data!\n",
- params->cmdname, params->imagefile);
+ debug("%s: ERROR: \"%s\" has corrupted data!\n",
+ params->cmdname, params->imagefile);
return -FDT_ERR_BADSTRUCTURE;
}
return 0;
@@ -117,33 +116,7 @@
image_set_hcrc(hdr, checksum);
}
-static int image_save_datafile(struct image_tool_params *params,
- ulong file_data, ulong file_len)
-{
- int dfd;
- const char *datafile = params->outfile;
-
- dfd = open(datafile, O_RDWR | O_CREAT | O_TRUNC | O_BINARY,
- S_IRUSR | S_IWUSR);
- if (dfd < 0) {
- fprintf(stderr, "%s: Can't open \"%s\": %s\n",
- params->cmdname, datafile, strerror(errno));
- return -1;
- }
-
- if (write(dfd, (void *)file_data, file_len) != (ssize_t)file_len) {
- fprintf(stderr, "%s: Write error on \"%s\": %s\n",
- params->cmdname, datafile, strerror(errno));
- close(dfd);
- return -1;
- }
-
- close(dfd);
-
- return 0;
-}
-
-static int image_extract_datafile(void *ptr, struct image_tool_params *params)
+static int image_extract_subimage(void *ptr, struct image_tool_params *params)
{
const image_header_t *hdr = (const image_header_t *)ptr;
ulong file_data;
@@ -170,25 +143,23 @@
}
/* save the "data file" into the file system */
- return image_save_datafile(params, file_data, file_len);
+ return imagetool_save_subimage(params->outfile, file_data, file_len);
}
/*
* Default image type parameters definition
*/
-static struct image_type_params defimage_params = {
- .name = "Default Image support",
- .header_size = sizeof(image_header_t),
- .hdr = (void*)&header,
- .check_image_type = image_check_image_types,
- .verify_header = image_verify_header,
- .print_header = image_print_contents,
- .set_header = image_set_header,
- .extract_datafile = image_extract_datafile,
- .check_params = image_check_params,
-};
-
-void init_default_image_type(void)
-{
- register_image_type(&defimage_params);
-}
+U_BOOT_IMAGE_TYPE(
+ defimage,
+ "Default Image support",
+ sizeof(image_header_t),
+ (void *)&header,
+ image_check_params,
+ image_verify_header,
+ image_print_contents,
+ image_set_header,
+ image_extract_subimage,
+ image_check_image_types,
+ NULL,
+ NULL
+);
diff --git a/tools/dumpimage.c b/tools/dumpimage.c
index 542ee28..75a5d47 100644
--- a/tools/dumpimage.c
+++ b/tools/dumpimage.c
@@ -12,112 +12,13 @@
static void usage(void);
-/* image_type_params linked list to maintain registered image types supports */
-static struct image_type_params *dumpimage_tparams;
-
/* parameters initialized by core will be used by the image type code */
static struct image_tool_params params = {
.type = IH_TYPE_KERNEL,
};
-/**
- * dumpimage_register() - register respective image generation/list support
- *
- * the input struct image_type_params is checked and appended to the link
- * list, if the input structure is already registered, issue an error
- *
- * @tparams: Image type parameters
- */
-static void dumpimage_register(struct image_type_params *tparams)
-{
- struct image_type_params **tp;
-
- if (!tparams) {
- fprintf(stderr, "%s: %s: Null input\n", params.cmdname,
- __func__);
- exit(EXIT_FAILURE);
- }
-
- /* scan the linked list, check for registry and point the last one */
- for (tp = &dumpimage_tparams; *tp != NULL; tp = &(*tp)->next) {
- if (!strcmp((*tp)->name, tparams->name)) {
- fprintf(stderr, "%s: %s already registered\n",
- params.cmdname, tparams->name);
- return;
- }
- }
-
- /* add input struct entry at the end of link list */
- *tp = tparams;
- /* mark input entry as last entry in the link list */
- tparams->next = NULL;
-
- debug("Registered %s\n", tparams->name);
-}
-
-/**
- * dumpimage_get_type() - find the image type params for a given image type
- *
- * Scan all registered image types and check the input type_id for each
- * supported image type
- *
- * @return respective image_type_params pointer. If the input type is not
- * supported by any of registered image types, returns NULL
- */
-static struct image_type_params *dumpimage_get_type(int type)
-{
- struct image_type_params *curr;
-
- for (curr = dumpimage_tparams; curr != NULL; curr = curr->next) {
- if (curr->check_image_type) {
- if (!curr->check_image_type(type))
- return curr;
- }
- }
- return NULL;
-}
-
/*
- * dumpimage_verify_print_header() - verifies the image header
- *
- * Scan registered image types and verify the image_header for each
- * supported image type. If verification is successful, this prints
- * the respective header.
- *
- * @return 0 on success, negative if input image format does not match with
- * any of supported image types
- */
-static int dumpimage_verify_print_header(void *ptr, struct stat *sbuf)
-{
- int retval = -1;
- struct image_type_params *curr;
-
- for (curr = dumpimage_tparams; curr != NULL; curr = curr->next) {
- if (curr->verify_header) {
- retval = curr->verify_header((unsigned char *)ptr,
- sbuf->st_size, ¶ms);
- if (retval != 0)
- continue;
- /*
- * Print the image information if verify is
- * successful
- */
- if (curr->print_header) {
- curr->print_header(ptr);
- } else {
- fprintf(stderr,
- "%s: print_header undefined for %s\n",
- params.cmdname, curr->name);
- }
- break;
- }
- }
-
- return retval;
-}
-
-/*
- * dumpimage_extract_datafile -
+ * dumpimage_extract_subimage -
*
* It scans all registered image types,
* verifies image_header for each supported image type
@@ -127,29 +28,27 @@
* returns negative if input image format does not match with any of
* supported image types
*/
-static int dumpimage_extract_datafile(void *ptr, struct stat *sbuf)
+static int dumpimage_extract_subimage(struct image_type_params *tparams,
+ void *ptr, struct stat *sbuf)
{
int retval = -1;
- struct image_type_params *curr;
- for (curr = dumpimage_tparams; curr != NULL; curr = curr->next) {
- if (curr->verify_header) {
- retval = curr->verify_header((unsigned char *)ptr,
- sbuf->st_size, ¶ms);
- if (retval != 0)
- continue;
- /*
- * Extract the file from the image
- * if verify is successful
- */
- if (curr->extract_datafile) {
- curr->extract_datafile(ptr, ¶ms);
- } else {
- fprintf(stderr,
- "%s: extract_datafile undefined for %s\n",
- params.cmdname, curr->name);
- break;
- }
+ if (tparams->verify_header) {
+ retval = tparams->verify_header((unsigned char *)ptr,
+ sbuf->st_size, ¶ms);
+ if (retval != 0)
+ return -1;
+ /*
+ * Extract the file from the image
+ * if verify is successful
+ */
+ if (tparams->extract_subimage) {
+ retval = tparams->extract_subimage(ptr, ¶ms);
+ } else {
+ fprintf(stderr,
+ "%s: extract_subimage undefined for %s\n",
+ params.cmdname, tparams->name);
+ return -2;
}
}
@@ -165,12 +64,9 @@
int retval = 0;
struct image_type_params *tparams = NULL;
- /* Init all image generation/list support */
- register_image_tool(dumpimage_register);
-
params.cmdname = *argv;
- while ((opt = getopt(argc, argv, "li:o:p:V")) != -1) {
+ while ((opt = getopt(argc, argv, "li:o:T:p:V")) != -1) {
switch (opt) {
case 'l':
params.lflag = 1;
@@ -182,6 +78,12 @@
case 'o':
params.outfile = optarg;
break;
+ case 'T':
+ params.type = genimg_get_type_id(optarg);
+ if (params.type < 0) {
+ usage();
+ }
+ break;
case 'p':
params.pflag = strtoul(optarg, &ptr, 10);
if (*ptr) {
@@ -196,6 +98,7 @@
exit(EXIT_SUCCESS);
default:
usage();
+ break;
}
}
@@ -203,9 +106,9 @@
usage();
/* set tparams as per input type_id */
- tparams = dumpimage_get_type(params.type);
+ tparams = imagetool_get_type(params.type);
if (tparams == NULL) {
- fprintf(stderr, "%s: unsupported type %s\n",
+ fprintf(stderr, "%s: unsupported type: %s\n",
params.cmdname, genimg_get_type_name(params.type));
exit(EXIT_FAILURE);
}
@@ -242,7 +145,7 @@
exit(EXIT_FAILURE);
}
- if ((unsigned)sbuf.st_size < tparams->header_size) {
+ if ((uint32_t)sbuf.st_size < tparams->header_size) {
fprintf(stderr,
"%s: Bad size: \"%s\" is not valid image\n",
params.cmdname, params.imagefile);
@@ -267,13 +170,15 @@
* Extract the data files from within the matched
* image type. Returns the error code if not matched
*/
- retval = dumpimage_extract_datafile(ptr, &sbuf);
+ retval = dumpimage_extract_subimage(tparams, ptr,
+ &sbuf);
} else {
/*
* Print the image information for matched image type
* Returns the error code if not matched
*/
- retval = dumpimage_verify_print_header(ptr, &sbuf);
+ retval = imagetool_verify_print_header(ptr, &sbuf,
+ tparams, ¶ms);
}
(void)munmap((void *)ptr, sbuf.st_size);
@@ -293,9 +198,10 @@
" -l ==> list image header information\n",
params.cmdname);
fprintf(stderr,
- " %s -i image [-p position] [-o outfile] data_file\n"
- " -i ==> extract from the 'image' a specific 'data_file'"
- ", indexed by 'position' (starting at 0)\n",
+ " %s -i image -T type [-p position] [-o outfile] data_file\n"
+ " -i ==> extract from the 'image' a specific 'data_file'\n"
+ " -T ==> set image type to 'type'\n"
+ " -p ==> 'position' (starting at 0) of the 'data_file' inside the 'image'\n",
params.cmdname);
fprintf(stderr,
" %s -V ==> print version information and exit\n",
diff --git a/tools/fit_image.c b/tools/fit_image.c
index 3ececf9..eb2a25e 100644
--- a/tools/fit_image.c
+++ b/tools/fit_image.c
@@ -155,6 +155,97 @@
return -1;
}
+/**
+ * fit_image_extract - extract a FIT component image
+ * @fit: pointer to the FIT format image header
+ * @image_noffset: offset of the component image node
+ * @file_name: name of the file to store the FIT sub-image
+ *
+ * returns:
+ * zero in case of success or a negative value if fail.
+ */
+static int fit_image_extract(
+ const void *fit,
+ int image_noffset,
+ const char *file_name)
+{
+ const void *file_data;
+ size_t file_size = 0;
+
+ /* get the "data" property of component at offset "image_noffset" */
+ fit_image_get_data(fit, image_noffset, &file_data, &file_size);
+
+ /* save the "file_data" into the file specified by "file_name" */
+ return imagetool_save_subimage(file_name, (ulong) file_data, file_size);
+}
+
+/**
+ * fit_extract_contents - retrieve a sub-image component from the FIT image
+ * @ptr: pointer to the FIT format image header
+ * @params: command line parameters
+ *
+ * returns:
+ * zero in case of success or a negative value if fail.
+ */
+static int fit_extract_contents(void *ptr, struct image_tool_params *params)
+{
+ int images_noffset;
+ int noffset;
+ int ndepth;
+ const void *fit = ptr;
+ int count = 0;
+ const char *p;
+
+ /* Indent string is defined in header image.h */
+ p = IMAGE_INDENT_STRING;
+
+ if (!fit_check_format(fit)) {
+ printf("Bad FIT image format\n");
+ return -1;
+ }
+
+ /* Find images parent node offset */
+ images_noffset = fdt_path_offset(fit, FIT_IMAGES_PATH);
+ if (images_noffset < 0) {
+ printf("Can't find images parent node '%s' (%s)\n",
+ FIT_IMAGES_PATH, fdt_strerror(images_noffset));
+ return -1;
+ }
+
+ /* Avoid any overrun */
+ count = fit_get_subimage_count(fit, images_noffset);
+ if ((params->pflag < 0) || (count <= params->pflag)) {
+ printf("No such component at '%d'\n", params->pflag);
+ return -1;
+ }
+
+ /* Process its subnodes, extract the desired component from image */
+ for (ndepth = 0, count = 0,
+ noffset = fdt_next_node(fit, images_noffset, &ndepth);
+ (noffset >= 0) && (ndepth > 0);
+ noffset = fdt_next_node(fit, noffset, &ndepth)) {
+ if (ndepth == 1) {
+ /*
+ * Direct child node of the images parent node,
+ * i.e. component image node.
+ */
+ if (params->pflag == count) {
+ printf("Extracted:\n%s Image %u (%s)\n", p,
+ count, fit_get_name(fit, noffset, NULL));
+
+ fit_image_print(fit, noffset, p);
+
+ return fit_image_extract(fit, noffset,
+ params->outfile);
+ }
+
+ count++;
+ }
+ }
+
+ return 0;
+}
+
static int fit_check_params(struct image_tool_params *params)
{
return ((params->dflag && (params->fflag || params->lflag)) ||
@@ -162,19 +253,17 @@
(params->lflag && (params->dflag || params->fflag)));
}
-static struct image_type_params fitimage_params = {
- .name = "FIT Image support",
- .header_size = sizeof(image_header_t),
- .hdr = (void*)&header,
- .verify_header = fit_verify_header,
- .print_header = fit_print_contents,
- .check_image_type = fit_check_image_types,
- .fflag_handle = fit_handle_file,
- .set_header = NULL, /* FIT images use DTB header */
- .check_params = fit_check_params,
-};
-
-void init_fit_image_type (void)
-{
- register_image_type(&fitimage_params);
-}
+U_BOOT_IMAGE_TYPE(
+ fitimage,
+ "FIT Image support",
+ sizeof(image_header_t),
+ (void *)&header,
+ fit_check_params,
+ fit_verify_header,
+ fit_print_contents,
+ NULL,
+ fit_extract_contents,
+ fit_check_image_types,
+ fit_handle_file,
+ NULL /* FIT images use DTB header */
+);
diff --git a/tools/gpimage-common.c b/tools/gpimage-common.c
index b343a3a..5ad52be 100644
--- a/tools/gpimage-common.c
+++ b/tools/gpimage-common.c
@@ -32,7 +32,8 @@
int gph_verify_header(struct gp_header *gph, int be)
{
- uint32_t gph_size = gph->size, gph_load_addr = gph->load_addr;
+ uint32_t gph_size = gph->size;
+ uint32_t gph_load_addr = gph->load_addr;
if (be)
to_be32(&gph_size, &gph_load_addr);
diff --git a/tools/gpimage.c b/tools/gpimage.c
index 1cabb5b..1adc55c 100644
--- a/tools/gpimage.c
+++ b/tools/gpimage.c
@@ -60,18 +60,17 @@
/*
* gpimage parameters
*/
-static struct image_type_params gpimage_params = {
- .name = "TI KeyStone GP Image support",
- .header_size = GPIMAGE_HDR_SIZE,
- .hdr = (void *)&gpimage_header,
- .check_image_type = gpimage_check_image_types,
- .verify_header = gpimage_verify_header,
- .print_header = gpimage_print_header,
- .set_header = gpimage_set_header,
- .check_params = gpimage_check_params,
-};
-
-void init_gpimage_type(void)
-{
- register_image_type(&gpimage_params);
-}
+U_BOOT_IMAGE_TYPE(
+ gpimage,
+ "TI KeyStone GP Image support",
+ GPIMAGE_HDR_SIZE,
+ (void *)&gpimage_header,
+ gpimage_check_params,
+ gpimage_verify_header,
+ gpimage_print_header,
+ gpimage_set_header,
+ NULL,
+ gpimage_check_image_types,
+ NULL,
+ NULL
+);
diff --git a/tools/imagetool.c b/tools/imagetool.c
index 98717bd..148e466 100644
--- a/tools/imagetool.c
+++ b/tools/imagetool.c
@@ -8,57 +8,87 @@
#include "imagetool.h"
-/*
- * Callback function to register a image type within a tool
- */
-static imagetool_register_t register_func;
+#include <image.h>
-/*
- * register_image_tool -
- *
- * The tool provides its own registration function in order to all image
- * types initialize themselves.
- */
-void register_image_tool(imagetool_register_t image_register)
+struct image_type_params *imagetool_get_type(int type)
{
- /*
- * Save the image tool callback function. It will be used to register
- * image types within that tool
- */
- register_func = image_register;
+ struct image_type_params *curr;
+ struct image_type_params *start = ll_entry_start(
+ struct image_type_params, image_type);
+ struct image_type_params *end = ll_entry_end(
+ struct image_type_params, image_type);
- /* Init ATMEL ROM Boot Image generation/list support */
- init_atmel_image_type();
- /* Init Freescale PBL Boot image generation/list support */
- init_pbl_image_type();
- /* Init Kirkwood Boot image generation/list support */
- init_kwb_image_type();
- /* Init Freescale imx Boot image generation/list support */
- init_imx_image_type();
- /* Init Freescale mxs Boot image generation/list support */
- init_mxs_image_type();
- /* Init FIT image generation/list support */
- init_fit_image_type();
- /* Init TI OMAP Boot image generation/list support */
- init_omap_image_type();
- /* Init Default image generation/list support */
- init_default_image_type();
- /* Init Davinci UBL support */
- init_ubl_image_type();
- /* Init Davinci AIS support */
- init_ais_image_type();
- /* Init Altera SOCFPGA support */
- init_socfpga_image_type();
- /* Init TI Keystone boot image generation/list support */
- init_gpimage_type();
+ for (curr = start; curr != end; curr++) {
+ if (curr->check_image_type) {
+ if (!curr->check_image_type(type))
+ return curr;
+ }
+ }
+ return NULL;
}
-/*
- * register_image_type -
- *
- * Register a image type within a tool
- */
-void register_image_type(struct image_type_params *tparams)
+int imagetool_verify_print_header(
+ void *ptr,
+ struct stat *sbuf,
+ struct image_type_params *tparams,
+ struct image_tool_params *params)
{
- register_func(tparams);
+ int retval = -1;
+ struct image_type_params *curr;
+
+ struct image_type_params *start = ll_entry_start(
+ struct image_type_params, image_type);
+ struct image_type_params *end = ll_entry_end(
+ struct image_type_params, image_type);
+
+ for (curr = start; curr != end; curr++) {
+ if (curr->verify_header) {
+ retval = curr->verify_header((unsigned char *)ptr,
+ sbuf->st_size, params);
+
+ if (retval == 0) {
+ /*
+ * Print the image information if verify is
+ * successful
+ */
+ if (curr->print_header) {
+ curr->print_header(ptr);
+ } else {
+ fprintf(stderr,
+ "%s: print_header undefined for %s\n",
+ params->cmdname, curr->name);
+ }
+ break;
+ }
+ }
+ }
+
+ return retval;
+}
+
+int imagetool_save_subimage(
+ const char *file_name,
+ ulong file_data,
+ ulong file_len)
+{
+ int dfd;
+
+ dfd = open(file_name, O_RDWR | O_CREAT | O_TRUNC | O_BINARY,
+ S_IRUSR | S_IWUSR);
+ if (dfd < 0) {
+ fprintf(stderr, "Can't open \"%s\": %s\n",
+ file_name, strerror(errno));
+ return -1;
+ }
+
+ if (write(dfd, (void *)file_data, file_len) != (ssize_t)file_len) {
+ fprintf(stderr, "Write error on \"%s\": %s\n",
+ file_name, strerror(errno));
+ close(dfd);
+ return -1;
+ }
+
+ close(dfd);
+
+ return 0;
}
diff --git a/tools/imagetool.h b/tools/imagetool.h
index 8bce059..f35dec7 100644
--- a/tools/imagetool.h
+++ b/tools/imagetool.h
@@ -19,6 +19,16 @@
#include <time.h>
#include <unistd.h>
#include <u-boot/sha1.h>
+
+/* define __KERNEL__ in order to get the definitions
+ * required by the linker list. This is probably not
+ * the best way to do this */
+#ifndef __KERNEL__
+#define __KERNEL__
+#include <linker_lists.h>
+#undef __KERNEL__
+#endif /* __KERNEL__ */
+
#include "fdt_host.h"
#define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0]))
@@ -100,14 +110,15 @@
void (*set_header) (void *, struct stat *, int,
struct image_tool_params *);
/*
- * This function is used by the command to retrieve a data file from
- * the image (i.e. dumpimage -i <image> -p <position> <data_file>).
+ * This function is used by the command to retrieve a component
+ * (sub-image) from the image (i.e. dumpimage -i <image> -p <position>
+ * <sub-image-name>).
* Thus the code to extract a file from an image must be put here.
*
* Returns 0 if the file was successfully retrieved from the image,
* or a negative value on error.
*/
- int (*extract_datafile) (void *, struct image_tool_params *);
+ int (*extract_subimage)(void *, struct image_tool_params *);
/*
* Some image generation support for ex (default image type) supports
* more than one type_ids, this callback function is used to check
@@ -127,50 +138,88 @@
*/
int (*vrec_header) (struct image_tool_params *,
struct image_type_params *);
- /* pointer to the next registered entry in linked list */
- struct image_type_params *next;
};
-/*
- * Tool registration function.
+/**
+ * imagetool_get_type() - find the image type params for a given image type
+ *
+ * It scans all registers image type supports
+ * checks the input type for each supported image type
+ *
+ * if successful,
+ * returns respective image_type_params pointer if success
+ * if input type_id is not supported by any of image_type_support
+ * returns NULL
*/
-typedef void (*imagetool_register_t)(struct image_type_params *);
+struct image_type_params *imagetool_get_type(int type);
/*
- * Initializes all image types with the given registration callback
- * function.
- * An image tool uses this function to initialize all image types.
+ * imagetool_verify_print_header() - verifies the image header
+ *
+ * Scan registered image types and verify the image_header for each
+ * supported image type. If verification is successful, this prints
+ * the respective header.
+ *
+ * @return 0 on success, negative if input image format does not match with
+ * any of supported image types
*/
-void register_image_tool(imagetool_register_t image_register);
+int imagetool_verify_print_header(
+ void *ptr,
+ struct stat *sbuf,
+ struct image_type_params *tparams,
+ struct image_tool_params *params);
-/*
- * Register a image type within a tool.
- * An image type uses this function to register itself within
- * all tools.
+/**
+ * imagetool_save_subimage - store data into a file
+ * @file_name: name of the destination file
+ * @file_data: data to be written
+ * @file_len: the amount of data to store
+ *
+ * imagetool_save_subimage() store file_len bytes of data pointed by file_data
+ * into the file name by file_name.
+ *
+ * returns:
+ * zero in case of success or a negative value if fail.
*/
-void register_image_type(struct image_type_params *tparams);
+int imagetool_save_subimage(
+ const char *file_name,
+ ulong file_data,
+ ulong file_len);
/*
* There is a c file associated with supported image type low level code
* for ex. default_image.c, fit_image.c
- * init_xxx_type() is the only function referred by image tool core to avoid
- * a single lined header file, you can define them here
- *
- * Supported image types init functions
*/
-void init_default_image_type(void);
-void init_atmel_image_type(void);
-void init_pbl_image_type(void);
-void init_ais_image_type(void);
-void init_kwb_image_type(void);
-void init_imx_image_type(void);
-void init_mxs_image_type(void);
-void init_fit_image_type(void);
-void init_ubl_image_type(void);
-void init_omap_image_type(void);
-void init_socfpga_image_type(void);
-void init_gpimage_type(void);
+
void pbl_load_uboot(int fd, struct image_tool_params *mparams);
+#define U_BOOT_IMAGE_TYPE( \
+ _id, \
+ _name, \
+ _header_size, \
+ _header, \
+ _check_params, \
+ _verify_header, \
+ _print_header, \
+ _set_header, \
+ _extract_subimage, \
+ _check_image_type, \
+ _fflag_handle, \
+ _vrec_header \
+ ) \
+ ll_entry_declare(struct image_type_params, _id, image_type) = { \
+ .name = _name, \
+ .header_size = _header_size, \
+ .hdr = _header, \
+ .check_params = _check_params, \
+ .verify_header = _verify_header, \
+ .print_header = _print_header, \
+ .set_header = _set_header, \
+ .extract_subimage = _extract_subimage, \
+ .check_image_type = _check_image_type, \
+ .fflag_handle = _fflag_handle, \
+ .vrec_header = _vrec_header \
+ }
+
#endif /* _IMAGETOOL_H_ */
diff --git a/tools/imagetool.lds b/tools/imagetool.lds
new file mode 100644
index 0000000..7e92b4a
--- /dev/null
+++ b/tools/imagetool.lds
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2011-2012 The Chromium OS Authors.
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+SECTIONS
+{
+
+ . = ALIGN(4);
+ .u_boot_list : {
+ KEEP(*(SORT(.u_boot_list*)));
+ }
+
+ __u_boot_sandbox_option_start = .;
+ _u_boot_sandbox_getopt : { *(.u_boot_sandbox_getopt) }
+ __u_boot_sandbox_option_end = .;
+
+ __bss_start = .;
+}
+
+INSERT BEFORE .data;
diff --git a/tools/imximage.c b/tools/imximage.c
index 526b7d4..3d37591 100644
--- a/tools/imximage.c
+++ b/tools/imximage.c
@@ -694,19 +694,17 @@
/*
* imximage parameters
*/
-static struct image_type_params imximage_params = {
- .name = "Freescale i.MX Boot Image support",
- .header_size = 0,
- .hdr = NULL,
- .check_image_type = imximage_check_image_types,
- .verify_header = imximage_verify_header,
- .print_header = imximage_print_header,
- .set_header = imximage_set_header,
- .check_params = imximage_check_params,
- .vrec_header = imximage_generate,
-};
-
-void init_imx_image_type(void)
-{
- register_image_type(&imximage_params);
-}
+U_BOOT_IMAGE_TYPE(
+ imximage,
+ "Freescale i.MX Boot Image support",
+ 0,
+ NULL,
+ imximage_check_params,
+ imximage_verify_header,
+ imximage_print_header,
+ imximage_set_header,
+ NULL,
+ imximage_check_image_types,
+ NULL,
+ imximage_generate
+);
diff --git a/tools/kwbimage.c b/tools/kwbimage.c
index 807d466..66f459a 100644
--- a/tools/kwbimage.c
+++ b/tools/kwbimage.c
@@ -905,19 +905,17 @@
/*
* kwbimage type parameters definition
*/
-static struct image_type_params kwbimage_params = {
- .name = "Marvell MVEBU Boot Image support",
- .header_size = 0, /* no fixed header size */
- .hdr = NULL,
- .vrec_header = kwbimage_generate,
- .check_image_type = kwbimage_check_image_types,
- .verify_header = kwbimage_verify_header,
- .print_header = kwbimage_print_header,
- .set_header = kwbimage_set_header,
- .check_params = kwbimage_check_params,
-};
-
-void init_kwb_image_type (void)
-{
- register_image_type(&kwbimage_params);
-}
+U_BOOT_IMAGE_TYPE(
+ kwbimage,
+ "Marvell MVEBU Boot Image support",
+ 0,
+ NULL,
+ kwbimage_check_params,
+ kwbimage_verify_header,
+ kwbimage_print_header,
+ kwbimage_set_header,
+ NULL,
+ kwbimage_check_image_types,
+ NULL,
+ kwbimage_generate
+);
diff --git a/tools/mkimage.c b/tools/mkimage.c
index c70408c..5ccd951 100644
--- a/tools/mkimage.c
+++ b/tools/mkimage.c
@@ -15,9 +15,6 @@
static void copy_file(int, const char *, int);
static void usage(void);
-/* image_type_params link list to maintain registered image type supports */
-struct image_type_params *mkimage_tparams = NULL;
-
/* parameters initialized by core will be used by the image type code */
struct image_tool_params params = {
.os = IH_OS_LINUX,
@@ -29,106 +26,6 @@
.imagename2 = "",
};
-/*
- * mkimage_register -
- *
- * It is used to register respective image generation/list support to the
- * mkimage core
- *
- * the input struct image_type_params is checked and appended to the link
- * list, if the input structure is already registered, error
- */
-void mkimage_register (struct image_type_params *tparams)
-{
- struct image_type_params **tp;
-
- if (!tparams) {
- fprintf (stderr, "%s: %s: Null input\n",
- params.cmdname, __FUNCTION__);
- exit (EXIT_FAILURE);
- }
-
- /* scan the linked list, check for registry and point the last one */
- for (tp = &mkimage_tparams; *tp != NULL; tp = &(*tp)->next) {
- if (!strcmp((*tp)->name, tparams->name)) {
- fprintf (stderr, "%s: %s already registered\n",
- params.cmdname, tparams->name);
- return;
- }
- }
-
- /* add input struct entry at the end of link list */
- *tp = tparams;
- /* mark input entry as last entry in the link list */
- tparams->next = NULL;
-
- debug ("Registered %s\n", tparams->name);
-}
-
-/*
- * mkimage_get_type -
- *
- * It scans all registers image type supports
- * checks the input type_id for each supported image type
- *
- * if successful,
- * returns respective image_type_params pointer if success
- * if input type_id is not supported by any of image_type_support
- * returns NULL
- */
-struct image_type_params *mkimage_get_type(int type)
-{
- struct image_type_params *curr;
-
- for (curr = mkimage_tparams; curr != NULL; curr = curr->next) {
- if (curr->check_image_type) {
- if (!curr->check_image_type (type))
- return curr;
- }
- }
- return NULL;
-}
-
-/*
- * mkimage_verify_print_header -
- *
- * It scans mkimage_tparams link list,
- * verifies image_header for each supported image type
- * if verification is successful, prints respective header
- *
- * returns negative if input image format does not match with any of
- * supported image types
- */
-int mkimage_verify_print_header (void *ptr, struct stat *sbuf)
-{
- int retval = -1;
- struct image_type_params *curr;
-
- for (curr = mkimage_tparams; curr != NULL; curr = curr->next ) {
- if (curr->verify_header) {
- retval = curr->verify_header (
- (unsigned char *)ptr, sbuf->st_size,
- ¶ms);
-
- if (retval == 0) {
- /*
- * Print the image information
- * if verify is successful
- */
- if (curr->print_header)
- curr->print_header (ptr);
- else {
- fprintf (stderr,
- "%s: print_header undefined for %s\n",
- params.cmdname, curr->name);
- }
- break;
- }
- }
- }
- return retval;
-}
-
int
main (int argc, char **argv)
{
@@ -139,9 +36,6 @@
struct image_type_params *tparams = NULL;
int pad_len = 0;
- /* Init all image generation/list support */
- register_image_tool(mkimage_register);
-
params.cmdname = *argv;
params.addr = params.ep = 0;
@@ -279,7 +173,7 @@
usage ();
/* set tparams as per input type_id */
- tparams = mkimage_get_type(params.type);
+ tparams = imagetool_get_type(params.type);
if (tparams == NULL) {
fprintf (stderr, "%s: unsupported type %s\n",
params.cmdname, genimg_get_type_name(params.type));
@@ -363,7 +257,8 @@
* Print the image information for matched image type
* Returns the error code if not matched
*/
- retval = mkimage_verify_print_header (ptr, &sbuf);
+ retval = imagetool_verify_print_header(ptr, &sbuf,
+ tparams, ¶ms);
(void) munmap((void *)ptr, sbuf.st_size);
(void) close (ifd);
@@ -529,7 +424,7 @@
uint8_t zeros[4096];
int offset = 0;
int size;
- struct image_type_params *tparams = mkimage_get_type (params.type);
+ struct image_type_params *tparams = imagetool_get_type(params.type);
if (pad >= sizeof(zeros)) {
fprintf(stderr, "%s: Can't pad to %d\n",
diff --git a/tools/mxsimage.c b/tools/mxsimage.c
index 04beefe..98fc644 100644
--- a/tools/mxsimage.c
+++ b/tools/mxsimage.c
@@ -2312,25 +2312,18 @@
/*
* mxsimage parameters
*/
-static struct image_type_params mxsimage_params = {
- .name = "Freescale MXS Boot Image support",
- .header_size = 0,
- .hdr = NULL,
- .check_image_type = mxsimage_check_image_types,
- .verify_header = mxsimage_verify_header,
- .print_header = mxsimage_print_header,
- .set_header = mxsimage_set_header,
- .check_params = mxsimage_check_params,
- .vrec_header = mxsimage_generate,
-};
-
-void init_mxs_image_type(void)
-{
- register_image_type(&mxsimage_params);
-}
-
-#else
-void init_mxs_image_type(void)
-{
-}
+U_BOOT_IMAGE_TYPE(
+ mxsimage,
+ "Freescale MXS Boot Image support",
+ 0,
+ NULL,
+ mxsimage_check_params,
+ mxsimage_verify_header,
+ mxsimage_print_header,
+ mxsimage_set_header,
+ NULL,
+ mxsimage_check_image_types,
+ NULL,
+ mxsimage_generate
+);
#endif
diff --git a/tools/omapimage.c b/tools/omapimage.c
index 1e0c164..7198b33 100644
--- a/tools/omapimage.c
+++ b/tools/omapimage.c
@@ -162,18 +162,17 @@
/*
* omapimage parameters
*/
-static struct image_type_params omapimage_params = {
- .name = "TI OMAP CH/GP Boot Image support",
- .header_size = OMAP_FILE_HDR_SIZE,
- .hdr = (void *)&omapimage_header,
- .check_image_type = omapimage_check_image_types,
- .verify_header = omapimage_verify_header,
- .print_header = omapimage_print_header,
- .set_header = omapimage_set_header,
- .check_params = gpimage_check_params,
-};
-
-void init_omap_image_type(void)
-{
- register_image_type(&omapimage_params);
-}
+U_BOOT_IMAGE_TYPE(
+ omapimage,
+ "TI OMAP CH/GP Boot Image support",
+ OMAP_FILE_HDR_SIZE,
+ (void *)&omapimage_header,
+ gpimage_check_params,
+ omapimage_verify_header,
+ omapimage_print_header,
+ omapimage_set_header,
+ NULL,
+ omapimage_check_image_types,
+ NULL,
+ NULL
+);
diff --git a/tools/patman/README b/tools/patman/README
index e466886..7d039e8 100644
--- a/tools/patman/README
+++ b/tools/patman/README
@@ -52,12 +52,15 @@
How to configure it
===================
-For most cases of using patman for U-Boot development, patman will
-locate and use the file 'doc/git-mailrc' in your U-Boot directory.
-This contains most of the aliases you will need.
+For most cases of using patman for U-Boot development, patman can use the
+file 'doc/git-mailrc' in your U-Boot directory to supply the email aliases
+you need. To make this work, tell git where to find the file by typing
+this once:
+
+ git config sendemail.aliasesfile doc/git-mailrc
-For Linux the 'scripts/get_maintainer.pl' handles figuring out where
-to send patches pretty well.
+For both Linux and U-Boot the 'scripts/get_maintainer.pl' handles figuring
+out where to send patches pretty well.
During the first run patman creates a config file for you by taking the default
user name and email address from the global .gitconfig file.
diff --git a/tools/patman/gitutil.py b/tools/patman/gitutil.py
index cc5a55a..c593070 100644
--- a/tools/patman/gitutil.py
+++ b/tools/patman/gitutil.py
@@ -392,7 +392,8 @@
"Or do something like this\n"
"git config sendemail.to u-boot@lists.denx.de")
return
- cc = BuildEmailList(series.get('cc'), '--cc', alias, raise_on_error)
+ cc = BuildEmailList(list(set(series.get('cc')) - set(series.get('to'))),
+ '--cc', alias, raise_on_error)
if self_only:
to = BuildEmailList([os.getenv('USER')], '--to', alias, raise_on_error)
cc = []
diff --git a/tools/patman/patchstream.py b/tools/patman/patchstream.py
index da04883..8c3a0ec 100644
--- a/tools/patman/patchstream.py
+++ b/tools/patman/patchstream.py
@@ -139,6 +139,9 @@
# Initially we have no output. Prepare the input line string
out = []
line = line.rstrip('\n')
+
+ commit_match = re_commit.match(line) if self.is_log else None
+
if self.is_log:
if line[:4] == ' ':
line = line[4:]
@@ -146,7 +149,6 @@
# Handle state transition and skipping blank lines
series_tag_match = re_series_tag.match(line)
commit_tag_match = re_commit_tag.match(line)
- commit_match = re_commit.match(line) if self.is_log else None
cover_cc_match = re_cover_cc.match(line)
signoff_match = re_signoff.match(line)
tag_match = None
diff --git a/tools/patman/series.py b/tools/patman/series.py
index b67f870..60ebc76 100644
--- a/tools/patman/series.py
+++ b/tools/patman/series.py
@@ -94,6 +94,9 @@
cmd: The git command we would have run
process_tags: Process tags as if they were aliases
"""
+ to_set = set(gitutil.BuildEmailList(self.to));
+ cc_set = set(gitutil.BuildEmailList(self.cc));
+
col = terminal.Color()
print 'Dry run, so not doing much. But I would do this:'
print
@@ -106,24 +109,16 @@
commit = self.commits[upto]
print col.Color(col.GREEN, ' %s' % args[upto])
cc_list = list(self._generated_cc[commit.patch])
-
- # Skip items in To list
- if 'to' in self:
- try:
- map(cc_list.remove, gitutil.BuildEmailList(self.to))
- except ValueError:
- pass
-
- for email in cc_list:
+ for email in set(cc_list) - to_set - cc_set:
if email == None:
email = col.Color(col.YELLOW, "<alias '%s' not found>"
% tag)
if email:
print ' Cc: ',email
print
- for item in gitutil.BuildEmailList(self.get('to', '<none>')):
+ for item in to_set:
print 'To:\t ', item
- for item in gitutil.BuildEmailList(self.cc):
+ for item in cc_set - to_set:
print 'Cc:\t ', item
print 'Version: ', self.get('version')
print 'Prefix:\t ', self.get('prefix')
@@ -131,7 +126,7 @@
print 'Cover: %d lines' % len(self.cover)
cover_cc = gitutil.BuildEmailList(self.get('cover_cc', ''))
all_ccs = itertools.chain(cover_cc, *self._generated_cc.values())
- for email in set(all_ccs):
+ for email in set(all_ccs) - to_set - cc_set:
print ' Cc: ',email
if cmd:
print 'Git command: %s' % cmd
@@ -230,7 +225,7 @@
if add_maintainers:
list += get_maintainer.GetMaintainer(commit.patch)
all_ccs += list
- print >>fd, commit.patch, ', '.join(list)
+ print >>fd, commit.patch, ', '.join(set(list))
self._generated_cc[commit.patch] = list
if cover_fname:
diff --git a/tools/pblimage.c b/tools/pblimage.c
index 2a799ab..d74fde9 100644
--- a/tools/pblimage.c
+++ b/tools/pblimage.c
@@ -308,19 +308,17 @@
};
/* pblimage parameters */
-static struct image_type_params pblimage_params = {
- .name = "Freescale PBL Boot Image support",
- .header_size = sizeof(struct pbl_header),
- .hdr = (void *)&pblimage_header,
- .check_image_type = pblimage_check_image_types,
- .check_params = pblimage_check_params,
- .verify_header = pblimage_verify_header,
- .print_header = pblimage_print_header,
- .set_header = pblimage_set_header,
-};
-
-void init_pbl_image_type(void)
-{
- pbl_size = 0;
- register_image_type(&pblimage_params);
-}
+U_BOOT_IMAGE_TYPE(
+ pblimage,
+ "Freescale PBL Boot Image support",
+ sizeof(struct pbl_header),
+ (void *)&pblimage_header,
+ pblimage_check_params,
+ pblimage_verify_header,
+ pblimage_print_header,
+ pblimage_set_header,
+ NULL,
+ pblimage_check_image_types,
+ NULL,
+ NULL
+);
diff --git a/tools/socfpgaimage.c b/tools/socfpgaimage.c
index 917873e..8fe91fe 100644
--- a/tools/socfpgaimage.c
+++ b/tools/socfpgaimage.c
@@ -33,6 +33,8 @@
#include "pbl_crc32.h"
#include "imagetool.h"
+#include "mkimage.h"
+
#include <image.h>
#define HEADER_OFFSET 0x40
@@ -133,12 +135,12 @@
len = verify_header(buf + HEADER_OFFSET);
if (len < 0) {
- fprintf(stderr, "Invalid header\n");
+ debug("Invalid header\n");
return -1;
}
if (len < HEADER_OFFSET || len > PADDED_SIZE) {
- fprintf(stderr, "Invalid header length (%i)\n", len);
+ debug("Invalid header length (%i)\n", len);
return -1;
}
@@ -241,19 +243,17 @@
sign_buffer(buf, 0, 0, data_size, 0);
}
-static struct image_type_params socfpgaimage_params = {
- .name = "Altera SOCFPGA preloader support",
- .vrec_header = socfpgaimage_vrec_header,
- .header_size = 0, /* This will be modified by vrec_header() */
- .hdr = (void *)buffer,
- .check_image_type = socfpgaimage_check_image_types,
- .verify_header = socfpgaimage_verify_header,
- .print_header = socfpgaimage_print_header,
- .set_header = socfpgaimage_set_header,
- .check_params = socfpgaimage_check_params,
-};
-
-void init_socfpga_image_type(void)
-{
- register_image_type(&socfpgaimage_params);
-}
+U_BOOT_IMAGE_TYPE(
+ socfpgaimage,
+ "Altera SOCFPGA preloader support",
+ 0, /* This will be modified by vrec_header() */
+ (void *)buffer,
+ socfpgaimage_check_params,
+ socfpgaimage_verify_header,
+ socfpgaimage_print_header,
+ socfpgaimage_set_header,
+ NULL,
+ socfpgaimage_check_image_types,
+ NULL,
+ socfpgaimage_vrec_header
+);
diff --git a/tools/ublimage.c b/tools/ublimage.c
index cbbbe20..6ed1eef 100644
--- a/tools/ublimage.c
+++ b/tools/ublimage.c
@@ -244,18 +244,17 @@
/*
* ublimage parameters
*/
-static struct image_type_params ublimage_params = {
- .name = "Davinci UBL boot support",
- .header_size = sizeof(struct ubl_header),
- .hdr = (void *)&ublimage_header,
- .check_image_type = ublimage_check_image_types,
- .verify_header = ublimage_verify_header,
- .print_header = ublimage_print_header,
- .set_header = ublimage_set_header,
- .check_params = ublimage_check_params,
-};
-
-void init_ubl_image_type(void)
-{
- register_image_type(&ublimage_params);
-}
+U_BOOT_IMAGE_TYPE(
+ ublimage,
+ "Davinci UBL boot support",
+ sizeof(struct ubl_header),
+ (void *)&ublimage_header,
+ ublimage_check_params,
+ ublimage_verify_header,
+ ublimage_print_header,
+ ublimage_set_header,
+ NULL,
+ ublimage_check_image_types,
+ NULL,
+ NULL
+);