From patchwork Mon Jan 6 01:29:10 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Andre Przywara X-Patchwork-Id: 239113 List-Id: U-Boot discussion From: andre.przywara at arm.com (Andre Przywara) Date: Mon, 6 Jan 2020 01:29:10 +0000 Subject: [PATCH 1/6] sunxi: move CONFIG_SYS_SPI_U_BOOT_OFFS out of defconfig In-Reply-To: <20200106012915.2772-1-andre.przywara@arm.com> References: <20200106012915.2772-1-andre.przywara@arm.com> Message-ID: <20200106012915.2772-2-andre.przywara@arm.com> For Allwinner SoCs the CONFIG_SYS_SPI_U_BOOT_OFFS value is not really a board choice: The boot ROM only loads the SPL from offset 0 of the SPI NOR flash, and loads at most 32KB. This is a similar situation as on MMC, so consequently we create our "joint" image (SPL + U-Boot proper) with that 32KB offset during the build. So define the value of this symbol to be 32KB by default for every Allwinner SoC. This removes the definition of this symbol from the _defconfig files, and avoids every board to define this over and over again. Signed-off-by: Andre Przywara --- common/spl/Kconfig | 1 + configs/A20-OLinuXino-Lime2-eMMC_defconfig | 1 - configs/oceanic_5205_5inmfd_defconfig | 1 - configs/orangepi_pc2_defconfig | 1 - configs/orangepi_r1_defconfig | 1 - configs/orangepi_win_defconfig | 1 - configs/orangepi_zero_defconfig | 1 - configs/pine64-lts_defconfig | 1 - configs/sopine_baseboard_defconfig | 1 - 9 files changed, 1 insertion(+), 8 deletions(-) diff --git a/common/spl/Kconfig b/common/spl/Kconfig index a72412718b..d85a5a6e2e 100644 --- a/common/spl/Kconfig +++ b/common/spl/Kconfig @@ -1078,6 +1078,7 @@ endif # SPL_SPI_FLASH_SUPPORT config SYS_SPI_U_BOOT_OFFS hex "address of u-boot payload in SPI flash" + default 0x8000 if ARCH_SUNXI default 0x0 depends on SPL_SPI_LOAD || SPL_SPI_SUNXI help diff --git a/configs/A20-OLinuXino-Lime2-eMMC_defconfig b/configs/A20-OLinuXino-Lime2-eMMC_defconfig index 588758a8ca..7dc736e9e1 100644 --- a/configs/A20-OLinuXino-Lime2-eMMC_defconfig +++ b/configs/A20-OLinuXino-Lime2-eMMC_defconfig @@ -15,7 +15,6 @@ CONFIG_AHCI=y # CONFIG_SYS_MALLOC_CLEAR_ON_INIT is not set CONFIG_USE_PREBOOT=y CONFIG_SPL_I2C_SUPPORT=y -CONFIG_SYS_SPI_U_BOOT_OFFS=0x8000 CONFIG_CMD_DFU=y CONFIG_CMD_USB_MASS_STORAGE=y # CONFIG_SPL_DOS_PARTITION is not set diff --git a/configs/oceanic_5205_5inmfd_defconfig b/configs/oceanic_5205_5inmfd_defconfig index caab5fdb19..f71be7f127 100644 --- a/configs/oceanic_5205_5inmfd_defconfig +++ b/configs/oceanic_5205_5inmfd_defconfig @@ -11,7 +11,6 @@ CONFIG_MMC0_CD_PIN="" CONFIG_SPL_SPI_SUNXI=y # CONFIG_SYS_MALLOC_CLEAR_ON_INIT is not set CONFIG_USE_PREBOOT=y -CONFIG_SYS_SPI_U_BOOT_OFFS=0x8000 # CONFIG_SPL_DOS_PARTITION is not set # CONFIG_SPL_EFI_PARTITION is not set CONFIG_DEFAULT_DEVICE_TREE="sun50i-a64-oceanic-5205-5inmfd" diff --git a/configs/orangepi_pc2_defconfig b/configs/orangepi_pc2_defconfig index 3d65b87d33..20209ec41b 100644 --- a/configs/orangepi_pc2_defconfig +++ b/configs/orangepi_pc2_defconfig @@ -10,7 +10,6 @@ CONFIG_MACPWR="PD6" CONFIG_SPL_SPI_SUNXI=y # CONFIG_SYS_MALLOC_CLEAR_ON_INIT is not set CONFIG_USE_PREBOOT=y -CONFIG_SYS_SPI_U_BOOT_OFFS=0x8000 # CONFIG_SPL_DOS_PARTITION is not set # CONFIG_SPL_EFI_PARTITION is not set CONFIG_DEFAULT_DEVICE_TREE="sun50i-h5-orangepi-pc2" diff --git a/configs/orangepi_r1_defconfig b/configs/orangepi_r1_defconfig index b253d7f87b..0431fecb52 100644 --- a/configs/orangepi_r1_defconfig +++ b/configs/orangepi_r1_defconfig @@ -9,7 +9,6 @@ CONFIG_SPL_SPI_SUNXI=y # CONFIG_SYS_MALLOC_CLEAR_ON_INIT is not set CONFIG_USE_PREBOOT=y CONFIG_CONSOLE_MUX=y -CONFIG_SYS_SPI_U_BOOT_OFFS=0x8000 CONFIG_DEFAULT_DEVICE_TREE="sun8i-h2-plus-orangepi-r1" CONFIG_SYS_RELOC_GD_ENV_ADDR=y CONFIG_SUN8I_EMAC=y diff --git a/configs/orangepi_win_defconfig b/configs/orangepi_win_defconfig index ad74febe10..13bf266260 100644 --- a/configs/orangepi_win_defconfig +++ b/configs/orangepi_win_defconfig @@ -7,7 +7,6 @@ CONFIG_RESERVE_ALLWINNER_BOOT0_HEADER=y CONFIG_SPL_SPI_SUNXI=y # CONFIG_SYS_MALLOC_CLEAR_ON_INIT is not set CONFIG_USE_PREBOOT=y -CONFIG_SYS_SPI_U_BOOT_OFFS=0x8000 # CONFIG_SPL_DOS_PARTITION is not set # CONFIG_SPL_EFI_PARTITION is not set CONFIG_DEFAULT_DEVICE_TREE="sun50i-a64-orangepi-win" diff --git a/configs/orangepi_zero_defconfig b/configs/orangepi_zero_defconfig index 6fb2fbbda2..51d8ec001e 100644 --- a/configs/orangepi_zero_defconfig +++ b/configs/orangepi_zero_defconfig @@ -9,7 +9,6 @@ CONFIG_SPL_SPI_SUNXI=y # CONFIG_SYS_MALLOC_CLEAR_ON_INIT is not set CONFIG_USE_PREBOOT=y CONFIG_CONSOLE_MUX=y -CONFIG_SYS_SPI_U_BOOT_OFFS=0x8000 CONFIG_DEFAULT_DEVICE_TREE="sun8i-h2-plus-orangepi-zero" CONFIG_SYS_RELOC_GD_ENV_ADDR=y CONFIG_SUN8I_EMAC=y diff --git a/configs/pine64-lts_defconfig b/configs/pine64-lts_defconfig index a1c2d4245d..6e2c247c1a 100644 --- a/configs/pine64-lts_defconfig +++ b/configs/pine64-lts_defconfig @@ -11,7 +11,6 @@ CONFIG_MMC_SUNXI_SLOT_EXTRA=2 CONFIG_SPL_SPI_SUNXI=y # CONFIG_SYS_MALLOC_CLEAR_ON_INIT is not set CONFIG_USE_PREBOOT=y -CONFIG_SYS_SPI_U_BOOT_OFFS=0x8000 # CONFIG_SPL_DOS_PARTITION is not set # CONFIG_SPL_EFI_PARTITION is not set CONFIG_DEFAULT_DEVICE_TREE="sun50i-a64-pine64-lts" diff --git a/configs/sopine_baseboard_defconfig b/configs/sopine_baseboard_defconfig index f4ab9ba9ab..87ed55264d 100644 --- a/configs/sopine_baseboard_defconfig +++ b/configs/sopine_baseboard_defconfig @@ -12,7 +12,6 @@ CONFIG_MMC_SUNXI_SLOT_EXTRA=2 CONFIG_SPL_SPI_SUNXI=y # CONFIG_SYS_MALLOC_CLEAR_ON_INIT is not set CONFIG_USE_PREBOOT=y -CONFIG_SYS_SPI_U_BOOT_OFFS=0x8000 # CONFIG_SPL_DOS_PARTITION is not set # CONFIG_SPL_EFI_PARTITION is not set CONFIG_DEFAULT_DEVICE_TREE="sun50i-a64-sopine-baseboard" From patchwork Mon Jan 6 01:29:11 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Andre Przywara X-Patchwork-Id: 239115 List-Id: U-Boot discussion From: andre.przywara at arm.com (Andre Przywara) Date: Mon, 6 Jan 2020 01:29:11 +0000 Subject: [PATCH 2/6] sunxi: SPL SPI: Split off SPI0 base address In-Reply-To: <20200106012915.2772-1-andre.przywara@arm.com> References: <20200106012915.2772-1-andre.przywara@arm.com> Message-ID: <20200106012915.2772-3-andre.przywara@arm.com> So far on all supported Allwinner SoCs we find the old generation SPI controller always at address 0x1c05000, and the new generation one at 0x1c68000. However the Allwinner R40 SoC has a new generation SPI at the old address, and the H6 uses a completely different address. So split off the base address from the respective SPI registers, by changing the #defines to just contain offsets. The base address is provided by a function, so it can easily be extended later when support for those SoCs materialises. This does not change the code size (since the toolchain is clever enough to optimise this properly), also does not bring any functional change at this point. Signed-off-by: Andre Przywara --- arch/arm/mach-sunxi/spl_spi_sunxi.c | 94 +++++++++++++++++++++---------------- 1 file changed, 53 insertions(+), 41 deletions(-) diff --git a/arch/arm/mach-sunxi/spl_spi_sunxi.c b/arch/arm/mach-sunxi/spl_spi_sunxi.c index 043d9f6ead..5b4598a25b 100644 --- a/arch/arm/mach-sunxi/spl_spi_sunxi.c +++ b/arch/arm/mach-sunxi/spl_spi_sunxi.c @@ -36,13 +36,13 @@ /* SUN4I variant of the SPI controller */ /*****************************************************************************/ -#define SUN4I_SPI0_CCTL (0x01C05000 + 0x1C) -#define SUN4I_SPI0_CTL (0x01C05000 + 0x08) -#define SUN4I_SPI0_RX (0x01C05000 + 0x00) -#define SUN4I_SPI0_TX (0x01C05000 + 0x04) -#define SUN4I_SPI0_FIFO_STA (0x01C05000 + 0x28) -#define SUN4I_SPI0_BC (0x01C05000 + 0x20) -#define SUN4I_SPI0_TC (0x01C05000 + 0x24) +#define SUN4I_SPI0_CCTL 0x1C +#define SUN4I_SPI0_CTL 0x08 +#define SUN4I_SPI0_RX 0x00 +#define SUN4I_SPI0_TX 0x04 +#define SUN4I_SPI0_FIFO_STA 0x28 +#define SUN4I_SPI0_BC 0x20 +#define SUN4I_SPI0_TC 0x24 #define SUN4I_CTL_ENABLE BIT(0) #define SUN4I_CTL_MASTER BIT(1) @@ -54,15 +54,15 @@ /* SUN6I variant of the SPI controller */ /*****************************************************************************/ -#define SUN6I_SPI0_CCTL (0x01C68000 + 0x24) -#define SUN6I_SPI0_GCR (0x01C68000 + 0x04) -#define SUN6I_SPI0_TCR (0x01C68000 + 0x08) -#define SUN6I_SPI0_FIFO_STA (0x01C68000 + 0x1C) -#define SUN6I_SPI0_MBC (0x01C68000 + 0x30) -#define SUN6I_SPI0_MTC (0x01C68000 + 0x34) -#define SUN6I_SPI0_BCC (0x01C68000 + 0x38) -#define SUN6I_SPI0_TXD (0x01C68000 + 0x200) -#define SUN6I_SPI0_RXD (0x01C68000 + 0x300) +#define SUN6I_SPI0_CCTL 0x24 +#define SUN6I_SPI0_GCR 0x04 +#define SUN6I_SPI0_TCR 0x08 +#define SUN6I_SPI0_FIFO_STA 0x1C +#define SUN6I_SPI0_MBC 0x30 +#define SUN6I_SPI0_MTC 0x34 +#define SUN6I_SPI0_BCC 0x38 +#define SUN6I_SPI0_TXD 0x200 +#define SUN6I_SPI0_RXD 0x300 #define SUN6I_CTL_ENABLE BIT(0) #define SUN6I_CTL_MASTER BIT(1) @@ -100,11 +100,21 @@ static void spi0_pinmux_setup(unsigned int pin_function) sunxi_gpio_set_cfgpin(SUNXI_GPC(3), pin_function); } +static uintptr_t spi0_base_address(void) +{ + if (!IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I)) + return 0x01C05000; + + return 0x01C68000; +} + /* * Setup 6 MHz from OSC24M (because the BROM is doing the same). */ static void spi0_enable_clock(void) { + uintptr_t base = spi0_base_address(); + /* Deassert SPI0 reset on SUN6I */ if (IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I)) setbits_le32(SUN6I_BUS_SOFT_RST_REG0, @@ -114,36 +124,37 @@ static void spi0_enable_clock(void) setbits_le32(CCM_AHB_GATING0, (1 << AHB_GATE_OFFSET_SPI0)); /* Divide by 4 */ - writel(SPI0_CLK_DIV_BY_4, IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I) ? - SUN6I_SPI0_CCTL : SUN4I_SPI0_CCTL); + writel(SPI0_CLK_DIV_BY_4, base + (IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I) ? + SUN6I_SPI0_CCTL : SUN4I_SPI0_CCTL)); /* 24MHz from OSC24M */ writel((1 << 31), CCM_SPI0_CLK); if (IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I)) { /* Enable SPI in the master mode and do a soft reset */ - setbits_le32(SUN6I_SPI0_GCR, SUN6I_CTL_MASTER | - SUN6I_CTL_ENABLE | - SUN6I_CTL_SRST); + setbits_le32(base + SUN6I_SPI0_GCR, SUN6I_CTL_MASTER | + SUN6I_CTL_ENABLE | SUN6I_CTL_SRST); /* Wait for completion */ - while (readl(SUN6I_SPI0_GCR) & SUN6I_CTL_SRST) + while (readl(base + SUN6I_SPI0_GCR) & SUN6I_CTL_SRST) ; } else { /* Enable SPI in the master mode and reset FIFO */ - setbits_le32(SUN4I_SPI0_CTL, SUN4I_CTL_MASTER | - SUN4I_CTL_ENABLE | - SUN4I_CTL_TF_RST | - SUN4I_CTL_RF_RST); + setbits_le32(base + SUN4I_SPI0_CTL, SUN4I_CTL_MASTER | + SUN4I_CTL_ENABLE | + SUN4I_CTL_TF_RST | + SUN4I_CTL_RF_RST); } } static void spi0_disable_clock(void) { + uintptr_t base = spi0_base_address(); + /* Disable the SPI0 controller */ if (IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I)) - clrbits_le32(SUN6I_SPI0_GCR, SUN6I_CTL_MASTER | + clrbits_le32(base + SUN6I_SPI0_GCR, SUN6I_CTL_MASTER | SUN6I_CTL_ENABLE); else - clrbits_le32(SUN4I_SPI0_CTL, SUN4I_CTL_MASTER | + clrbits_le32(base + SUN4I_SPI0_CTL, SUN4I_CTL_MASTER | SUN4I_CTL_ENABLE); /* Disable the SPI0 clock */ @@ -227,6 +238,7 @@ static void spi0_read_data(void *buf, u32 addr, u32 len) { u8 *buf8 = buf; u32 chunk_len; + uintptr_t base = spi0_base_address(); while (len > 0) { chunk_len = len; @@ -235,23 +247,23 @@ static void spi0_read_data(void *buf, u32 addr, u32 len) if (IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I)) { sunxi_spi0_read_data(buf8, addr, chunk_len, - SUN6I_SPI0_TCR, + base + SUN6I_SPI0_TCR, SUN6I_TCR_XCH, - SUN6I_SPI0_FIFO_STA, - SUN6I_SPI0_TXD, - SUN6I_SPI0_RXD, - SUN6I_SPI0_MBC, - SUN6I_SPI0_MTC, - SUN6I_SPI0_BCC); + base + SUN6I_SPI0_FIFO_STA, + base + SUN6I_SPI0_TXD, + base + SUN6I_SPI0_RXD, + base + SUN6I_SPI0_MBC, + base + SUN6I_SPI0_MTC, + base + SUN6I_SPI0_BCC); } else { sunxi_spi0_read_data(buf8, addr, chunk_len, - SUN4I_SPI0_CTL, + base + SUN4I_SPI0_CTL, SUN4I_CTL_XCH, - SUN4I_SPI0_FIFO_STA, - SUN4I_SPI0_TX, - SUN4I_SPI0_RX, - SUN4I_SPI0_BC, - SUN4I_SPI0_TC, + base + SUN4I_SPI0_FIFO_STA, + base + SUN4I_SPI0_TX, + base + SUN4I_SPI0_RX, + base + SUN4I_SPI0_BC, + base + SUN4I_SPI0_TC, 0); } From patchwork Mon Jan 6 01:29:12 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Andre Przywara X-Patchwork-Id: 239114 List-Id: U-Boot discussion From: andre.przywara at arm.com (Andre Przywara) Date: Mon, 6 Jan 2020 01:29:12 +0000 Subject: [PATCH 3/6] sunxi: SPL SPI: Introduce is_new_gen_spi() In-Reply-To: <20200106012915.2772-1-andre.przywara@arm.com> References: <20200106012915.2772-1-andre.przywara@arm.com> Message-ID: <20200106012915.2772-4-andre.przywara@arm.com> So far we were using the CONFIG_SUNXI_GEN_SUN6I symbol to select between the two SPI controller generations used on Allwinner SoCs. This is a convenience symbol to roughly differentiate between "older" and "newer" generation of SoCs. The H6 SoCs is the newest SoC so far, but is sufficiently different to not define this symbol. However it is using a SPI controller compatible to the "new gen" SoCs. To prepare for H6 support, we replace the check for this single symbol with an explicit function, which can later be extended. For now we just return CONFIG_SUNXI_GEN_SUN6I in there, so this does not create a functional change. Signed-off-by: Andre Przywara --- arch/arm/mach-sunxi/spl_spi_sunxi.c | 22 ++++++++++++++-------- 1 file changed, 14 insertions(+), 8 deletions(-) diff --git a/arch/arm/mach-sunxi/spl_spi_sunxi.c b/arch/arm/mach-sunxi/spl_spi_sunxi.c index 5b4598a25b..b19f1bf4af 100644 --- a/arch/arm/mach-sunxi/spl_spi_sunxi.c +++ b/arch/arm/mach-sunxi/spl_spi_sunxi.c @@ -100,9 +100,14 @@ static void spi0_pinmux_setup(unsigned int pin_function) sunxi_gpio_set_cfgpin(SUNXI_GPC(3), pin_function); } +static bool is_new_gen_spi(void) +{ + return IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I); +} + static uintptr_t spi0_base_address(void) { - if (!IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I)) + if (!is_new_gen_spi()) return 0x01C05000; return 0x01C68000; @@ -116,7 +121,7 @@ static void spi0_enable_clock(void) uintptr_t base = spi0_base_address(); /* Deassert SPI0 reset on SUN6I */ - if (IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I)) + if (is_new_gen_spi()) setbits_le32(SUN6I_BUS_SOFT_RST_REG0, (1 << AHB_RESET_SPI0_SHIFT)); @@ -124,12 +129,12 @@ static void spi0_enable_clock(void) setbits_le32(CCM_AHB_GATING0, (1 << AHB_GATE_OFFSET_SPI0)); /* Divide by 4 */ - writel(SPI0_CLK_DIV_BY_4, base + (IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I) ? + writel(SPI0_CLK_DIV_BY_4, base + (is_new_gen_spi() ? SUN6I_SPI0_CCTL : SUN4I_SPI0_CCTL)); /* 24MHz from OSC24M */ writel((1 << 31), CCM_SPI0_CLK); - if (IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I)) { + if (is_new_gen_spi()) { /* Enable SPI in the master mode and do a soft reset */ setbits_le32(base + SUN6I_SPI0_GCR, SUN6I_CTL_MASTER | SUN6I_CTL_ENABLE | SUN6I_CTL_SRST); @@ -150,7 +155,7 @@ static void spi0_disable_clock(void) uintptr_t base = spi0_base_address(); /* Disable the SPI0 controller */ - if (IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I)) + if (is_new_gen_spi()) clrbits_le32(base + SUN6I_SPI0_GCR, SUN6I_CTL_MASTER | SUN6I_CTL_ENABLE); else @@ -164,7 +169,7 @@ static void spi0_disable_clock(void) clrbits_le32(CCM_AHB_GATING0, (1 << AHB_GATE_OFFSET_SPI0)); /* Assert SPI0 reset on SUN6I */ - if (IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I)) + if (is_new_gen_spi()) clrbits_le32(SUN6I_BUS_SOFT_RST_REG0, (1 << AHB_RESET_SPI0_SHIFT)); } @@ -184,7 +189,8 @@ static void spi0_deinit(void) { /* New SoCs can disable pins, older could only set them as input */ unsigned int pin_function = SUNXI_GPIO_INPUT; - if (IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I)) + + if (is_new_gen_spi()) pin_function = SUNXI_GPIO_DISABLE; spi0_disable_clock(); @@ -245,7 +251,7 @@ static void spi0_read_data(void *buf, u32 addr, u32 len) if (chunk_len > SPI_READ_MAX_SIZE) chunk_len = SPI_READ_MAX_SIZE; - if (IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I)) { + if (is_new_gen_spi()) { sunxi_spi0_read_data(buf8, addr, chunk_len, base + SUN6I_SPI0_TCR, SUN6I_TCR_XCH, From patchwork Mon Jan 6 01:29:13 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Andre Przywara X-Patchwork-Id: 239116 List-Id: U-Boot discussion From: andre.przywara at arm.com (Andre Przywara) Date: Mon, 6 Jan 2020 01:29:13 +0000 Subject: [PATCH 4/6] sunxi: SPL SPI: Add SPI boot support for the Allwinner R40 SoC In-Reply-To: <20200106012915.2772-1-andre.przywara@arm.com> References: <20200106012915.2772-1-andre.przywara@arm.com> Message-ID: <20200106012915.2772-5-andre.przywara@arm.com> Now that we can easily select an SoC specific SPI0 base address, adding support for the Allwinner R40 is fairly trivial: We set the base address, add this SoC to the ones that use PC23 and enable it in Kconfig. This allows booting from SPI flash on R40 boards. Tested on a Bananapi M2 Berry with SPI flash connected to the header pins. Signed-off-by: Andre Przywara --- arch/arm/mach-sunxi/Kconfig | 2 +- arch/arm/mach-sunxi/spl_spi_sunxi.c | 6 +++++- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/arch/arm/mach-sunxi/Kconfig b/arch/arm/mach-sunxi/Kconfig index 16d41b83af..0e07be802f 100644 --- a/arch/arm/mach-sunxi/Kconfig +++ b/arch/arm/mach-sunxi/Kconfig @@ -993,7 +993,7 @@ config SPL_STACK_R_ADDR config SPL_SPI_SUNXI bool "Support for SPI Flash on Allwinner SoCs in SPL" - depends on MACH_SUN4I || MACH_SUN5I || MACH_SUN7I || MACH_SUNXI_H3_H5 || MACH_SUN50I + depends on MACH_SUN4I || MACH_SUN5I || MACH_SUN7I || MACH_SUNXI_H3_H5 || MACH_SUN50I || MACH_SUN8I_R40 help Enable support for SPI Flash. This option allows SPL to read from sunxi SPI Flash. It uses the same method as the boot ROM, so does diff --git a/arch/arm/mach-sunxi/spl_spi_sunxi.c b/arch/arm/mach-sunxi/spl_spi_sunxi.c index b19f1bf4af..c0b5a204fd 100644 --- a/arch/arm/mach-sunxi/spl_spi_sunxi.c +++ b/arch/arm/mach-sunxi/spl_spi_sunxi.c @@ -94,7 +94,8 @@ static void spi0_pinmux_setup(unsigned int pin_function) for (pin = SUNXI_GPC(0); pin <= SUNXI_GPC(2); pin++) sunxi_gpio_set_cfgpin(pin, pin_function); - if (IS_ENABLED(CONFIG_MACH_SUN4I) || IS_ENABLED(CONFIG_MACH_SUN7I)) + if (IS_ENABLED(CONFIG_MACH_SUN4I) || IS_ENABLED(CONFIG_MACH_SUN7I) || + IS_ENABLED(CONFIG_MACH_SUN8I_R40)) sunxi_gpio_set_cfgpin(SUNXI_GPC(23), pin_function); else sunxi_gpio_set_cfgpin(SUNXI_GPC(3), pin_function); @@ -107,6 +108,9 @@ static bool is_new_gen_spi(void) static uintptr_t spi0_base_address(void) { + if (IS_ENABLED(CONFIG_MACH_SUN8I_R40)) + return 0x01C05000; + if (!is_new_gen_spi()) return 0x01C05000; From patchwork Mon Jan 6 01:29:14 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Andre Przywara X-Patchwork-Id: 239117 List-Id: U-Boot discussion From: andre.przywara at arm.com (Andre Przywara) Date: Mon, 6 Jan 2020 01:29:14 +0000 Subject: [PATCH 5/6] sunxi: SPL SPI: Add SPI boot support for the Allwinner H6 SoC In-Reply-To: <20200106012915.2772-1-andre.przywara@arm.com> References: <20200106012915.2772-1-andre.przywara@arm.com> Message-ID: <20200106012915.2772-6-andre.przywara@arm.com> The Allwinner H6 SoC uses a quite different memory map, also changes the clocks quite a bit. This requires some changes to the SPL SPI routine, which hardcodes these values so far. Using the just introduced helper functions to determine base address and SPI controller generation, we can cover some of these differences easily. The clock setup is different, so requires some explicit code changes there (reset and clock gate in one register at a different address). Also we need to change the pinmux function to use a different set of pins that the H6 uses for SPI0. Eventually we can enable the H6 to use SPI booting in Kconfig. Signed-off-by: Andre Przywara --- arch/arm/mach-sunxi/Kconfig | 2 +- arch/arm/mach-sunxi/spl_spi_sunxi.c | 41 +++++++++++++++++++++++++++++-------- 2 files changed, 33 insertions(+), 10 deletions(-) diff --git a/arch/arm/mach-sunxi/Kconfig b/arch/arm/mach-sunxi/Kconfig index 0e07be802f..364b81b24c 100644 --- a/arch/arm/mach-sunxi/Kconfig +++ b/arch/arm/mach-sunxi/Kconfig @@ -993,7 +993,7 @@ config SPL_STACK_R_ADDR config SPL_SPI_SUNXI bool "Support for SPI Flash on Allwinner SoCs in SPL" - depends on MACH_SUN4I || MACH_SUN5I || MACH_SUN7I || MACH_SUNXI_H3_H5 || MACH_SUN50I || MACH_SUN8I_R40 + depends on MACH_SUN4I || MACH_SUN5I || MACH_SUN7I || MACH_SUNXI_H3_H5 || MACH_SUN50I || MACH_SUN8I_R40 || MACH_SUN50I_H6 help Enable support for SPI Flash. This option allows SPL to read from sunxi SPI Flash. It uses the same method as the boot ROM, so does diff --git a/arch/arm/mach-sunxi/spl_spi_sunxi.c b/arch/arm/mach-sunxi/spl_spi_sunxi.c index c0b5a204fd..edfc46f275 100644 --- a/arch/arm/mach-sunxi/spl_spi_sunxi.c +++ b/arch/arm/mach-sunxi/spl_spi_sunxi.c @@ -72,7 +72,12 @@ /*****************************************************************************/ #define CCM_AHB_GATING0 (0x01C20000 + 0x60) +#define CCM_H6_SPI_BGR_REG (0x03001000 + 0x96c) +#ifdef CONFIG_MACH_SUN50I_H6 +#define CCM_SPI0_CLK (0x03001000 + 0x940) +#else #define CCM_SPI0_CLK (0x01C20000 + 0xA0) +#endif #define SUN6I_BUS_SOFT_RST_REG0 (0x01C20000 + 0x2C0) #define AHB_RESET_SPI0_SHIFT 20 @@ -86,14 +91,21 @@ /* * Allwinner A10/A20 SoCs were using pins PC0,PC1,PC2,PC23 for booting * from SPI Flash, everything else is using pins PC0,PC1,PC2,PC3. + * The H6 uses PC0, PC2, PC3, PC5. */ static void spi0_pinmux_setup(unsigned int pin_function) { - unsigned int pin; + /* All chips use PC0 and PC2. */ + sunxi_gpio_set_cfgpin(SUNXI_GPC(0), pin_function); + sunxi_gpio_set_cfgpin(SUNXI_GPC(2), pin_function); - for (pin = SUNXI_GPC(0); pin <= SUNXI_GPC(2); pin++) - sunxi_gpio_set_cfgpin(pin, pin_function); + /* All chips except H6 use PC1, and only H6 uses PC5. */ + if (!IS_ENABLED(CONFIG_MACH_SUN50I_H6)) + sunxi_gpio_set_cfgpin(SUNXI_GPC(1), pin_function); + else + sunxi_gpio_set_cfgpin(SUNXI_GPC(5), pin_function); + /* Older generations use PC23 for CS, newer ones use PC3. */ if (IS_ENABLED(CONFIG_MACH_SUN4I) || IS_ENABLED(CONFIG_MACH_SUN7I) || IS_ENABLED(CONFIG_MACH_SUN8I_R40)) sunxi_gpio_set_cfgpin(SUNXI_GPC(23), pin_function); @@ -103,7 +115,8 @@ static void spi0_pinmux_setup(unsigned int pin_function) static bool is_new_gen_spi(void) { - return IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I); + return IS_ENABLED(CONFIG_SUNXI_GEN_SUN6I) || + IS_ENABLED(CONFIG_MACH_SUN50I_H6); } static uintptr_t spi0_base_address(void) @@ -111,6 +124,9 @@ static uintptr_t spi0_base_address(void) if (IS_ENABLED(CONFIG_MACH_SUN8I_R40)) return 0x01C05000; + if (IS_ENABLED(CONFIG_MACH_SUN50I_H6)) + return 0x05010000; + if (!is_new_gen_spi()) return 0x01C05000; @@ -125,12 +141,15 @@ static void spi0_enable_clock(void) uintptr_t base = spi0_base_address(); /* Deassert SPI0 reset on SUN6I */ - if (is_new_gen_spi()) + if (IS_ENABLED(CONFIG_MACH_SUN50I_H6)) + setbits_le32(CCM_H6_SPI_BGR_REG, (1U << 16) | 0x1); + else if (is_new_gen_spi()) setbits_le32(SUN6I_BUS_SOFT_RST_REG0, (1 << AHB_RESET_SPI0_SHIFT)); /* Open the SPI0 gate */ - setbits_le32(CCM_AHB_GATING0, (1 << AHB_GATE_OFFSET_SPI0)); + if (!IS_ENABLED(CONFIG_MACH_SUN50I_H6)) + setbits_le32(CCM_AHB_GATING0, (1 << AHB_GATE_OFFSET_SPI0)); /* Divide by 4 */ writel(SPI0_CLK_DIV_BY_4, base + (is_new_gen_spi() ? @@ -170,10 +189,13 @@ static void spi0_disable_clock(void) writel(0, CCM_SPI0_CLK); /* Close the SPI0 gate */ - clrbits_le32(CCM_AHB_GATING0, (1 << AHB_GATE_OFFSET_SPI0)); + if (!IS_ENABLED(CONFIG_MACH_SUN50I_H6)) + clrbits_le32(CCM_AHB_GATING0, (1 << AHB_GATE_OFFSET_SPI0)); /* Assert SPI0 reset on SUN6I */ - if (is_new_gen_spi()) + if (IS_ENABLED(CONFIG_MACH_SUN50I_H6)) + clrbits_le32(CCM_H6_SPI_BGR_REG, (1U << 16) | 0x1); + else if (is_new_gen_spi()) clrbits_le32(SUN6I_BUS_SOFT_RST_REG0, (1 << AHB_RESET_SPI0_SHIFT)); } @@ -182,7 +204,8 @@ static void spi0_init(void) { unsigned int pin_function = SUNXI_GPC_SPI0; - if (IS_ENABLED(CONFIG_MACH_SUN50I)) + if (IS_ENABLED(CONFIG_MACH_SUN50I) || + IS_ENABLED(CONFIG_MACH_SUN50I_H6)) pin_function = SUN50I_GPC_SPI0; spi0_pinmux_setup(pin_function); From patchwork Mon Jan 6 01:29:15 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Andre Przywara X-Patchwork-Id: 239118 List-Id: U-Boot discussion From: andre.przywara at arm.com (Andre Przywara) Date: Mon, 6 Jan 2020 01:29:15 +0000 Subject: [PATCH 6/6] sunxi: Pine H64: Enable SPI booting in defconfig In-Reply-To: <20200106012915.2772-1-andre.przywara@arm.com> References: <20200106012915.2772-1-andre.przywara@arm.com> Message-ID: <20200106012915.2772-7-andre.przywara@arm.com> The Pine H64 board comes with some onboard SPI flash chip, which is perfect for loading SPL, ATF and U-Boot proper from there. Enable the functionality in the defconfig, so that we use sunxi-fel to transfer a bootable image to the NOR flash. Signed-off-by: Andre Przywara --- configs/pine_h64_defconfig | 1 + 1 file changed, 1 insertion(+) diff --git a/configs/pine_h64_defconfig b/configs/pine_h64_defconfig index b49dbea4d4..c0adbf3dd0 100644 --- a/configs/pine_h64_defconfig +++ b/configs/pine_h64_defconfig @@ -16,3 +16,4 @@ CONFIG_DEFAULT_DEVICE_TREE="sun50i-h6-pine-h64" CONFIG_SYS_RELOC_GD_ENV_ADDR=y CONFIG_USB_EHCI_HCD=y CONFIG_USB_OHCI_HCD=y +CONFIG_SPL_SPI_SUNXI=y