From 83b539cfd49f0fbcce4dd9d127776354031a7308 Mon Sep 17 00:00:00 2001 From: Fabien Dessenne Date: Wed, 4 Sep 2019 09:53:22 +0200 Subject: [PATCH 01/23] remoteproc: elf_loader: fix program header parsing Fix an issue where some sections are never loaded : if p_type is different from PT_LOAD the phdr pointer must be incremented. Signed-off-by: Fabien Dessenne Acked-by: Suman Anna --- drivers/remoteproc/rproc-elf-loader.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/remoteproc/rproc-elf-loader.c b/drivers/remoteproc/rproc-elf-loader.c index 538481241f..d234592445 100644 --- a/drivers/remoteproc/rproc-elf-loader.c +++ b/drivers/remoteproc/rproc-elf-loader.c @@ -189,7 +189,7 @@ int rproc_elf32_load_image(struct udevice *dev, unsigned long addr, ulong size) ops = rproc_get_ops(dev); /* Load each program header */ - for (i = 0; i < ehdr->e_phnum; ++i) { + for (i = 0; i < ehdr->e_phnum; i++, phdr++) { void *dst = (void *)(uintptr_t)phdr->p_paddr; void *src = (void *)addr + phdr->p_offset; @@ -211,7 +211,6 @@ int rproc_elf32_load_image(struct udevice *dev, unsigned long addr, ulong size) roundup((unsigned long)dst + phdr->p_filesz, ARCH_DMA_MINALIGN) - rounddown((unsigned long)dst, ARCH_DMA_MINALIGN)); - ++phdr; } return 0; From b1b147f2b839c45b896dfacf5a2929313d88aa63 Mon Sep 17 00:00:00 2001 From: Patrick Delaunay Date: Fri, 20 Sep 2019 09:20:12 +0200 Subject: [PATCH 02/23] cmd: mtd: solve bad block support in erase command This patch modify the loop in mtd erase command to erase one by one the blocks in the requested area. It solves issue on "mtd erase" command on nand with existing bad block, the command is interrupted on the first bad block with the trace: "Skipping bad block at 0xffffffffffffffff" In MTD driver (nand/raw), when a bad block is present on the MTD device, the erase_op.fail_addr is not updated and we have the initial value MTD_FAIL_ADDR_UNKNOWN = (ULL)-1. This case seems normal in nand_base.c:nand_erase_nand(), we have the 2 exit cases during the loop: 1/ we have a bad block (nand_block_checkbad) instr->state = MTD_ERASE_FAILED loop interrupted (goto erase_exit) 2/ if block erase failed (status & NAND_STATUS_FAIL) instr->state = MTD_ERASE_FAILED; instr->fail_addr = ((loff_t)page << chip->page_shift); loop interrupted (goto erase_exit) So erase_op.fail_addr can't be used if bad blocks were present in the erased area; we need to use mtd_erase only one block to detect and skip these existing bad blocks (as it is done in nand_util.c). Signed-off-by: Patrick Delaunay Reviewed-by: Miquel Raynal --- cmd/mtd.c | 24 ++++++++++++------------ 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/cmd/mtd.c b/cmd/mtd.c index 1b6b8dda2b..a559b5a4a3 100644 --- a/cmd/mtd.c +++ b/cmd/mtd.c @@ -387,7 +387,7 @@ static int do_mtd_erase(cmd_tbl_t *cmdtp, int flag, int argc, struct mtd_info *mtd; u64 off, len; bool scrub; - int ret; + int ret = 0; if (argc < 2) return CMD_RET_USAGE; @@ -423,22 +423,22 @@ static int do_mtd_erase(cmd_tbl_t *cmdtp, int flag, int argc, erase_op.mtd = mtd; erase_op.addr = off; - erase_op.len = len; + erase_op.len = mtd->erasesize; erase_op.scrub = scrub; - while (erase_op.len) { + while (len) { ret = mtd_erase(mtd, &erase_op); - /* Abort if its not a bad block error */ - if (ret != -EIO) - break; + if (ret) { + /* Abort if its not a bad block error */ + if (ret != -EIO) + break; + printf("Skipping bad block at 0x%08llx\n", + erase_op.addr); + } - printf("Skipping bad block at 0x%08llx\n", erase_op.fail_addr); - - /* Skip bad block and continue behind it */ - erase_op.len -= erase_op.fail_addr - erase_op.addr; - erase_op.len -= mtd->erasesize; - erase_op.addr = erase_op.fail_addr + mtd->erasesize; + len -= mtd->erasesize; + erase_op.addr += mtd->erasesize; } if (ret && ret != -EIO) From 1c16606aac8f03be80d9c38ada00fd03123e0dbe Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Patrik=20Dahlstr=C3=B6m?= Date: Sat, 21 Dec 2019 17:25:12 +0100 Subject: [PATCH 03/23] serial: ns16550: Use old baud rate divisor for flushing if not given MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit If baud_divisor is not set (i.e. == -1), we should use the baud divisor already in use for flushing the xmit register. If we don't flush the xmit register, then SPL will hang. Signed-off-by: Patrik Dahlström --- drivers/serial/ns16550.c | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/drivers/serial/ns16550.c b/drivers/serial/ns16550.c index a92d2b1de8..9851663dc5 100644 --- a/drivers/serial/ns16550.c +++ b/drivers/serial/ns16550.c @@ -171,6 +171,13 @@ void NS16550_init(NS16550_t com_port, int baud_divisor) == UART_LSR_THRE) { if (baud_divisor != -1) NS16550_setbrg(com_port, baud_divisor); + else { + // Re-use old baud rate divisor to flush transmit reg. + const int dll = serial_in(&com_port->dll); + const int dlm = serial_in(&com_port->dlm); + const int divisor = dll | (dlm << 8); + NS16550_setbrg(com_port, divisor); + } serial_out(0, &com_port->mdr1); } #endif From 906e3cc552fbf24f0b2a1b7582c6f761a608de20 Mon Sep 17 00:00:00 2001 From: Michael Trimarchi Date: Sun, 5 Jan 2020 16:51:13 +0100 Subject: [PATCH 04/23] arm: Add arm handoff header file Add an arch-specific handoff header so that we can use the HANDOFF feature on arm devices. Signed-off-by: Michael Trimarchi Reviewed-by: Simon Glass --- arch/arm/include/asm/handoff.h | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) create mode 100644 arch/arm/include/asm/handoff.h diff --git a/arch/arm/include/asm/handoff.h b/arch/arm/include/asm/handoff.h new file mode 100644 index 0000000000..0790d2ab1e --- /dev/null +++ b/arch/arm/include/asm/handoff.h @@ -0,0 +1,21 @@ +/* SPDX-License-Identifier: GPL-2.0+ */ +/* + * Architecture-specific SPL handoff information for ARM + * + * Copyright 2019 Amarula Solutions, BV + * Written by Michael Trimarchi + */ + +#ifndef __asm_handoff_h +#define __asm_handoff_h + +/** + * struct arch_spl_handoff - architecture-specific handoff info + * + * @usable_ram_top: Value returned by board_get_usable_ram_top() in SPL + */ +struct arch_spl_handoff { + ulong usable_ram_top; +}; + +#endif From dae188e6839aa678f1ab4518d92b7eda7277fedf Mon Sep 17 00:00:00 2001 From: Patrick Delaunay Date: Mon, 13 Jan 2020 09:33:51 +0100 Subject: [PATCH 05/23] tools: ftdgrep: correct the find regions loop in do_fdtgrep Use realloc and update the loop executed in do_fdtgrep to find all the regions: only test count > max_region after the second pass. This patch solve an issue if the number of region found (count) is greater then the default value (max_region = count = 100): the second pass is never executed, because the loop stops after the first pass (i = 0, count > 100, max_regions = 100) with error -1 and the error message "Internal error with fdtgrep_find_region". I also update the error message. Signed-off-by: Patrick Delaunay --- tools/fdtgrep.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/tools/fdtgrep.c b/tools/fdtgrep.c index 8f44f599c1..2a8058f57f 100644 --- a/tools/fdtgrep.c +++ b/tools/fdtgrep.c @@ -805,7 +805,7 @@ static int do_fdtgrep(struct display_info *disp, const char *filename) * we do another pass to actually record them. */ for (i = 0; i < 2; i++) { - region = malloc(count * sizeof(struct fdt_region)); + region = realloc(region, count * sizeof(struct fdt_region)); if (!region) { fprintf(stderr, "Out of memory for %d regions\n", count); @@ -823,8 +823,10 @@ static int do_fdtgrep(struct display_info *disp, const char *filename) } if (count <= max_regions) break; + } + if (count > max_regions) { free(region); - fprintf(stderr, "Internal error with fdtgrep_find_region)(\n"); + fprintf(stderr, "Internal error with fdtgrep_find_region()\n"); return -1; } From 1b27753a963071165e12afa4a7516096881184be Mon Sep 17 00:00:00 2001 From: Heinrich Schuchardt Date: Sun, 19 Jan 2020 09:26:22 +0100 Subject: [PATCH 06/23] lib: rsa: consider CONFIG_SPL_RSA CONFIG_SPL_RSA is meant to control if lib/rsa/* is used for SPL. Adjust lib/Makefile to consider this setting. This was correctly setup with commit 51c14cd128f4 ("verified-boot: Minimal support for booting U-Boot proper from SPL") and got lost with commit 089df18bfe9d ("lib: move hash CONFIG options to Kconfig"). Fixes: 089df18bfe9d ("lib: move hash CONFIG options to Kconfig") Signed-off-by: Heinrich Schuchardt --- lib/Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/Makefile b/lib/Makefile index 51eba80b89..15259d0473 100644 --- a/lib/Makefile +++ b/lib/Makefile @@ -58,7 +58,7 @@ obj-$(CONFIG_TPM_V1) += tpm-v1.o obj-$(CONFIG_TPM_V2) += tpm-v2.o endif -obj-$(CONFIG_RSA) += rsa/ +obj-$(CONFIG_$(SPL_)RSA) += rsa/ obj-$(CONFIG_SHA1) += sha1.o obj-$(CONFIG_SHA256) += sha256.o From 1611235b858abe08f9267f1fa95bc7553aa8e644 Mon Sep 17 00:00:00 2001 From: Heinrich Schuchardt Date: Sun, 19 Jan 2020 19:28:12 +0100 Subject: [PATCH 07/23] lib: Kconfig dependencies for pseudo-random library drivers/rng/sandbox_rng.c requires rand() to be defined but configuration option CONFIG_CONFIG_LIB_RAND selected in drivers/rng/Kconfig does not exist. test/lib/test_aes.c requires rand() to be defined. Fix the selection criteria for choice "Pseudo-random library support type". Signed-off-by: Heinrich Schuchardt --- drivers/rng/Kconfig | 1 - lib/Kconfig | 3 ++- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/rng/Kconfig b/drivers/rng/Kconfig index 35a3bd192a..893b89d49b 100644 --- a/drivers/rng/Kconfig +++ b/drivers/rng/Kconfig @@ -9,7 +9,6 @@ config DM_RNG config RNG_SANDBOX bool "Sandbox random number generator" depends on SANDBOX && DM_RNG - select CONFIG_LIB_RAND help Enable random number generator for sandbox. This is an emulation of a rng device. diff --git a/lib/Kconfig b/lib/Kconfig index d040a87d26..ab6aff710d 100644 --- a/lib/Kconfig +++ b/lib/Kconfig @@ -150,7 +150,8 @@ config REGEX choice prompt "Pseudo-random library support type" - depends on NET_RANDOM_ETHADDR || RANDOM_UUID || CMD_UUID + depends on NET_RANDOM_ETHADDR || RANDOM_UUID || CMD_UUID || \ + RNG_SANDBOX || UT_LIB && AES default LIB_RAND help Select the library to provide pseudo-random number generator From 94a8e83a60bd82e6b3059bddd56187691b782896 Mon Sep 17 00:00:00 2001 From: Heinrich Schuchardt Date: Sun, 19 Jan 2020 19:48:04 +0100 Subject: [PATCH 08/23] crypto: make mod_exp_sw() static Function mod_exp_sw() is only used via the operators of the uclass. It is not defined in any include. Make mod_exp_sw() static. Signed-off-by: Heinrich Schuchardt --- drivers/crypto/rsa_mod_exp/mod_exp_sw.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/crypto/rsa_mod_exp/mod_exp_sw.c b/drivers/crypto/rsa_mod_exp/mod_exp_sw.c index 5a098f83cc..46b9f1825c 100644 --- a/drivers/crypto/rsa_mod_exp/mod_exp_sw.c +++ b/drivers/crypto/rsa_mod_exp/mod_exp_sw.c @@ -9,8 +9,8 @@ #include #include -int mod_exp_sw(struct udevice *dev, const uint8_t *sig, uint32_t sig_len, - struct key_prop *prop, uint8_t *out) +static 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; From 7d017d607eaa12e8037d754dbe15cc35aca249ed Mon Sep 17 00:00:00 2001 From: mingming lee Date: Thu, 16 Jan 2020 16:11:37 +0800 Subject: [PATCH 09/23] usb: musb-new: mt85xx: add musb-new gadget driver. Using musb-new structure for mt85xx gadget driver. Add gadget driver dts for mt8518 SoCs. Signed-off-by: mingming lee --- arch/arm/dts/mt8518.dtsi | 13 ++ drivers/usb/musb-new/Kconfig | 11 +- drivers/usb/musb-new/Makefile | 1 + drivers/usb/musb-new/mt85xx.c | 417 ++++++++++++++++++++++++++++++++++ 4 files changed, 441 insertions(+), 1 deletion(-) create mode 100644 drivers/usb/musb-new/mt85xx.c diff --git a/arch/arm/dts/mt8518.dtsi b/arch/arm/dts/mt8518.dtsi index c2d17fda4a..56da91a9fe 100644 --- a/arch/arm/dts/mt8518.dtsi +++ b/arch/arm/dts/mt8518.dtsi @@ -74,6 +74,19 @@ }; }; + usb0: usb@11100000 { + compatible = "mediatek,mt8518-musb"; + reg = <0x11100000 0x1000>; + reg-names = "control"; + clocks = <&topckgen CLK_TOP_USB20_48M>, + <&topckgen CLK_TOP_USBIF>, + <&topckgen CLK_TOP_USB>; + clock-names = "usbpll", "usbmcu", "usb"; + interrupts = ; + interrupt-names = "mc"; + status = "okay"; + }; + mmc0: mmc@11120000 { compatible = "mediatek,mt8516-mmc"; reg = <0x11120000 0x1000>; diff --git a/drivers/usb/musb-new/Kconfig b/drivers/usb/musb-new/Kconfig index 79ad14ef66..6cf8a2b60b 100644 --- a/drivers/usb/musb-new/Kconfig +++ b/drivers/usb/musb-new/Kconfig @@ -47,6 +47,15 @@ config USB_MUSB_DSPS bool "TI DSPS platforms" if USB_MUSB_HOST || USB_MUSB_GADGET +config USB_MUSB_MT85XX + bool "Enable Mediatek MT85XX DRC USB controller" + depends on DM_USB && ARCH_MEDIATEK + default n + help + Say y to enable Mediatek MT85XX USB DRC controller support + if it is available on your Mediatek MUSB IP based platform. + DMA controllers are ignored. This driver follow musb-new + driver and usb gadget framework. config USB_MUSB_PIC32 bool "Enable Microchip PIC32 DRC USB controller" @@ -76,7 +85,7 @@ endif config USB_MUSB_PIO_ONLY bool "Disable DMA (always use PIO)" - default y if USB_MUSB_AM35X || USB_MUSB_PIC32 || USB_MUSB_OMAP2PLUS || USB_MUSB_DSPS || USB_MUSB_SUNXI + default y if USB_MUSB_AM35X || USB_MUSB_PIC32 || USB_MUSB_OMAP2PLUS || USB_MUSB_DSPS || USB_MUSB_SUNXI || USB_MUSB_MT85XX help All data is copied between memory and FIFO by the CPU. DMA controllers are ignored. diff --git a/drivers/usb/musb-new/Makefile b/drivers/usb/musb-new/Makefile index ec7852ce94..6355eb12dd 100644 --- a/drivers/usb/musb-new/Makefile +++ b/drivers/usb/musb-new/Makefile @@ -8,6 +8,7 @@ obj-$(CONFIG_USB_MUSB_HOST) += musb_host.o musb_core.o musb_uboot.o obj-$(CONFIG_USB_MUSB_DSPS) += musb_dsps.o obj-$(CONFIG_USB_MUSB_DA8XX) += da8xx.o obj-$(CONFIG_USB_MUSB_AM35X) += am35x.o +obj-$(CONFIG_USB_MUSB_MT85XX) += mt85xx.o obj-$(CONFIG_USB_MUSB_OMAP2PLUS) += omap2430.o obj-$(CONFIG_USB_MUSB_PIC32) += pic32.o obj-$(CONFIG_USB_MUSB_SUNXI) += sunxi.o diff --git a/drivers/usb/musb-new/mt85xx.c b/drivers/usb/musb-new/mt85xx.c new file mode 100644 index 0000000000..131fd7dd79 --- /dev/null +++ b/drivers/usb/musb-new/mt85xx.c @@ -0,0 +1,417 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Mediatek "glue layer" + * + * Copyright (C) 2019-2021 by Mediatek + * Based on the AllWinner SUNXI "glue layer" code. + * Copyright (C) 2015 Hans de Goede + * Copyright (C) 2013 Jussi Kivilinna + * + * This file is part of the Inventra Controller Driver for Linux. + */ +#include +#include +#include +#include +#include +#include +#include +#include "linux-compat.h" +#include "musb_core.h" +#include "musb_uboot.h" + +#define DBG_I(fmt, ...) \ + pr_info(fmt, ##__VA_ARGS__) + +struct mtk_musb_config { + struct musb_hdrc_config *config; +}; + +struct mtk_musb_glue { + struct musb_host_data mdata; + struct clk usbpllclk; + struct clk usbmcuclk; + struct clk usbclk; + struct mtk_musb_config *cfg; + struct device dev; +}; + +#define to_mtk_musb_glue(d) container_of(d, struct mtk_musb_glue, dev) + +/****************************************************************************** + * phy settings + ******************************************************************************/ +#define USB20_PHY_BASE 0x11110800 +#define USBPHY_READ8(offset) \ + readb((void *)(USB20_PHY_BASE + (offset))) +#define USBPHY_WRITE8(offset, value) \ + writeb(value, (void *)(USB20_PHY_BASE + (offset))) +#define USBPHY_SET8(offset, mask) \ + USBPHY_WRITE8(offset, (USBPHY_READ8(offset)) | (mask)) +#define USBPHY_CLR8(offset, mask) \ + USBPHY_WRITE8(offset, (USBPHY_READ8(offset)) & (~(mask))) + +static void mt_usb_phy_poweron(void) +{ + /* + * switch to USB function. + * (system register, force ip into usb mode). + */ + USBPHY_CLR8(0x6b, 0x04); + USBPHY_CLR8(0x6e, 0x01); + USBPHY_CLR8(0x21, 0x03); + + /* RG_USB20_BC11_SW_EN = 1'b0 */ + USBPHY_SET8(0x22, 0x04); + USBPHY_CLR8(0x1a, 0x80); + + /* RG_USB20_DP_100K_EN = 1'b0 */ + /* RG_USB20_DP_100K_EN = 1'b0 */ + USBPHY_CLR8(0x22, 0x03); + + /*OTG enable*/ + USBPHY_SET8(0x20, 0x10); + /* release force suspendm */ + USBPHY_CLR8(0x6a, 0x04); + + mdelay(800); + + /* force enter device mode */ + USBPHY_CLR8(0x6c, 0x10); + USBPHY_SET8(0x6c, 0x2E); + USBPHY_SET8(0x6d, 0x3E); +} + +static void mt_usb_phy_savecurrent(void) +{ + /* + * switch to USB function. + * (system register, force ip into usb mode). + */ + USBPHY_CLR8(0x6b, 0x04); + USBPHY_CLR8(0x6e, 0x01); + USBPHY_CLR8(0x21, 0x03); + + /* release force suspendm */ + USBPHY_CLR8(0x6a, 0x04); + USBPHY_SET8(0x68, 0x04); + /* RG_DPPULLDOWN./RG_DMPULLDOWN. */ + USBPHY_SET8(0x68, 0xc0); + /* RG_XCVRSEL[1:0] = 2'b01 */ + USBPHY_CLR8(0x68, 0x30); + USBPHY_SET8(0x68, 0x10); + /* RG_TERMSEL = 1'b1 */ + USBPHY_SET8(0x68, 0x04); + /* RG_DATAIN[3:0] = 4'b0000 */ + USBPHY_CLR8(0x69, 0x3c); + + /* + * force_dp_pulldown, force_dm_pulldown, + * force_xcversel, force_termsel. + */ + USBPHY_SET8(0x6a, 0xba); + + /* RG_USB20_BC11_SW_EN = 1'b0 */ + USBPHY_CLR8(0x1a, 0x80); + /* RG_USB20_OTG_VBUSSCMP_EN = 1'b0 */ + USBPHY_CLR8(0x1a, 0x10); + + mdelay(800); + + USBPHY_CLR8(0x6a, 0x04); + /* rg_usb20_pll_stable = 1 */ + //USBPHY_SET8(0x63, 0x02); + + mdelay(1); + + /* force suspendm = 1 */ + //USBPHY_SET8(0x6a, 0x04); +} + +static void mt_usb_phy_recover(void) +{ + /* clean PUPD_BIST_EN */ + /* PUPD_BIST_EN = 1'b0 */ + /* PMIC will use it to detect charger type */ + USBPHY_CLR8(0x1d, 0x10); + + /* force_uart_en = 1'b0 */ + USBPHY_CLR8(0x6b, 0x04); + /* RG_UART_EN = 1'b0 */ + USBPHY_CLR8(0x6e, 0x01); + /* force_uart_en = 1'b0 */ + USBPHY_CLR8(0x6a, 0x04); + + USBPHY_CLR8(0x21, 0x03); + USBPHY_CLR8(0x68, 0xf4); + + /* RG_DATAIN[3:0] = 4'b0000 */ + USBPHY_CLR8(0x69, 0x3c); + + USBPHY_CLR8(0x6a, 0xba); + + /* RG_USB20_BC11_SW_EN = 1'b0 */ + USBPHY_CLR8(0x1a, 0x80); + /* RG_USB20_OTG_VBUSSCMP_EN = 1'b1 */ + USBPHY_SET8(0x1a, 0x10); + + //HQA adjustment + USBPHY_CLR8(0x18, 0x08); + USBPHY_SET8(0x18, 0x06); + mdelay(800); + + /* force enter device mode */ + //USBPHY_CLR8(0x6c, 0x10); + //USBPHY_SET8(0x6c, 0x2E); + //USBPHY_SET8(0x6d, 0x3E); + + /* enable VRT internal R architecture */ + /* RG_USB20_INTR_EN = 1'b1 */ + USBPHY_SET8(0x00, 0x20); +} + +/****************************************************************************** + * MUSB Glue code + ******************************************************************************/ + +static irqreturn_t mtk_musb_interrupt(int irq, void *__hci) +{ + struct musb *musb = __hci; + irqreturn_t retval = IRQ_NONE; + + /* read and flush interrupts */ + musb->int_usb = musb_readb(musb->mregs, MUSB_INTRUSB); +// last_int_usb = musb->int_usb; + if (musb->int_usb) + musb_writeb(musb->mregs, MUSB_INTRUSB, musb->int_usb); + musb->int_tx = musb_readw(musb->mregs, MUSB_INTRTX); + if (musb->int_tx) + musb_writew(musb->mregs, MUSB_INTRTX, musb->int_tx); + musb->int_rx = musb_readw(musb->mregs, MUSB_INTRRX); + if (musb->int_rx) + musb_writew(musb->mregs, MUSB_INTRRX, musb->int_rx); + + if (musb->int_usb || musb->int_tx || musb->int_rx) + retval |= musb_interrupt(musb); + + return retval; +} + +/* musb_core does not call enable / disable in a balanced manner */ +static bool enabled; + +static int mtk_musb_enable(struct musb *musb) +{ + struct mtk_musb_glue *glue = to_mtk_musb_glue(musb->controller); + + DBG_I("%s():\n", __func__); + + musb_ep_select(musb->mregs, 0); + musb_writeb(musb->mregs, MUSB_FADDR, 0); + + if (enabled) + return 0; + + mt_usb_phy_recover(); + + enabled = true; + + return 0; +} + +static void mtk_musb_disable(struct musb *musb) +{ + struct mtk_musb_glue *glue = to_mtk_musb_glue(musb->controller); + int ret; + + DBG_I("%s():\n", __func__); + + if (!enabled) + return; + + mt_usb_phy_savecurrent(); + + enabled = false; +} + +static int mtk_musb_init(struct musb *musb) +{ + struct mtk_musb_glue *glue = to_mtk_musb_glue(musb->controller); + int ret; + + DBG_I("%s():\n", __func__); + + ret = clk_enable(&glue->usbpllclk); + if (ret) { + dev_err(dev, "failed to enable usbpll clock\n"); + return ret; + } + ret = clk_enable(&glue->usbmcuclk); + if (ret) { + dev_err(dev, "failed to enable usbmcu clock\n"); + return ret; + } + ret = clk_enable(&glue->usbclk); + if (ret) { + dev_err(dev, "failed to enable usb clock\n"); + return ret; + } + + musb->isr = mtk_musb_interrupt; + + return 0; +} + +static int mtk_musb_exit(struct musb *musb) +{ + struct mtk_musb_glue *glue = to_mtk_musb_glue(musb->controller); + + clk_disable(&glue->usbclk); + clk_disable(&glue->usbmcuclk); + clk_disable(&glue->usbpllclk); + + return 0; +} + +static const struct musb_platform_ops mtk_musb_ops = { + .init = mtk_musb_init, + .exit = mtk_musb_exit, + .enable = mtk_musb_enable, + .disable = mtk_musb_disable, +}; + +/* MTK OTG supports up to 7 endpoints */ +#define MTK_MUSB_MAX_EP_NUM 8 +#define MTK_MUSB_RAM_BITS 16 + +static struct musb_fifo_cfg mtk_musb_mode_cfg[] = { + MUSB_EP_FIFO_SINGLE(1, FIFO_TX, 512), + MUSB_EP_FIFO_SINGLE(1, FIFO_RX, 512), + MUSB_EP_FIFO_SINGLE(2, FIFO_TX, 512), + MUSB_EP_FIFO_SINGLE(2, FIFO_RX, 512), + MUSB_EP_FIFO_SINGLE(3, FIFO_TX, 512), + MUSB_EP_FIFO_SINGLE(3, FIFO_RX, 512), + MUSB_EP_FIFO_SINGLE(4, FIFO_TX, 512), + MUSB_EP_FIFO_SINGLE(4, FIFO_RX, 512), + MUSB_EP_FIFO_SINGLE(5, FIFO_TX, 512), + MUSB_EP_FIFO_SINGLE(5, FIFO_RX, 512), + MUSB_EP_FIFO_SINGLE(6, FIFO_TX, 512), + MUSB_EP_FIFO_SINGLE(6, FIFO_RX, 512), + MUSB_EP_FIFO_SINGLE(7, FIFO_TX, 512), + MUSB_EP_FIFO_SINGLE(7, FIFO_RX, 512), +}; + +static struct musb_hdrc_config musb_config = { + .fifo_cfg = mtk_musb_mode_cfg, + .fifo_cfg_size = ARRAY_SIZE(mtk_musb_mode_cfg), + .multipoint = true, + .dyn_fifo = true, + .num_eps = MTK_MUSB_MAX_EP_NUM, + .ram_bits = MTK_MUSB_RAM_BITS, +}; + +static int musb_usb_probe(struct udevice *dev) +{ + struct mtk_musb_glue *glue = dev_get_priv(dev); + struct musb_host_data *host = &glue->mdata; + struct musb_hdrc_platform_data pdata; + void *base = dev_read_addr_ptr(dev); + int ret; + + DBG_I("%s():\n", __func__); + +#ifdef CONFIG_USB_MUSB_HOST + struct usb_bus_priv *priv = dev_get_uclass_priv(dev); +#endif + + if (!base) + return -EINVAL; + + glue->cfg = (struct mtk_musb_config *)dev_get_driver_data(dev); + if (!glue->cfg) + return -EINVAL; + + ret = clk_get_by_name(dev, "usbpll", &glue->usbpllclk); + if (ret) { + dev_err(dev, "failed to get usbpll clock\n"); + return ret; + } + ret = clk_get_by_name(dev, "usbmcu", &glue->usbmcuclk); + if (ret) { + dev_err(dev, "failed to get usbmcu clock\n"); + return ret; + } + ret = clk_get_by_name(dev, "usb", &glue->usbclk); + if (ret) { + dev_err(dev, "failed to get usb clock\n"); + return ret; + } + + memset(&pdata, 0, sizeof(pdata)); + pdata.power = (u8)400; + pdata.platform_ops = &mtk_musb_ops; + pdata.config = glue->cfg->config; + +#ifdef CONFIG_USB_MUSB_HOST + priv->desc_before_addr = true; + + pdata.mode = MUSB_HOST; + host->host = musb_init_controller(&pdata, &glue->dev, base); + if (!host->host) + return -EIO; + + ret = musb_lowlevel_init(host); + if (!ret) + printf("MTK MUSB OTG (Host)\n"); +#else + pdata.mode = MUSB_PERIPHERAL; + host->host = musb_register(&pdata, &glue->dev, base); + if (!host->host) + return -EIO; + + printf("MTK MUSB OTG (Peripheral)\n"); +#endif + + mt_usb_phy_poweron(); + + return ret; +} + +static int musb_usb_remove(struct udevice *dev) +{ + struct mtk_musb_glue *glue = dev_get_priv(dev); + struct musb_host_data *host = &glue->mdata; + + musb_stop(host->host); + free(host->host); + host->host = NULL; + + return 0; +} + +static const struct mtk_musb_config mt8518_cfg = { + .config = &musb_config, +}; + +static const struct udevice_id mtk_musb_ids[] = { + { .compatible = "mediatek,mt8518-musb", + .data = (ulong)&mt8518_cfg }, + { } +}; + +U_BOOT_DRIVER(mtk_musb) = { + .name = "mtk_musb", +#ifdef CONFIG_USB_MUSB_HOST + .id = UCLASS_USB, +#else + .id = UCLASS_USB_GADGET_GENERIC, +#endif + .of_match = mtk_musb_ids, + .probe = musb_usb_probe, + .remove = musb_usb_remove, +#ifdef CONFIG_USB_MUSB_HOST + .ops = &musb_usb_ops, +#endif + .platdata_auto_alloc_size = sizeof(struct usb_platdata), + .priv_auto_alloc_size = sizeof(struct mtk_musb_glue), +}; From e65016150e2b66dfee0521cb3b2d477694b341ef Mon Sep 17 00:00:00 2001 From: mingming lee Date: Thu, 16 Jan 2020 16:11:38 +0800 Subject: [PATCH 10/23] ARM: Mediatek: Add board_late_init to init usb gadget driver Add board_late_init function to init usb gadget driver for mt8518 Signed-off-by: mingming lee --- board/mediatek/mt8518/mt8518_ap1.c | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) diff --git a/board/mediatek/mt8518/mt8518_ap1.c b/board/mediatek/mt8518/mt8518_ap1.c index 9710907fe2..2ac7c6cd18 100644 --- a/board/mediatek/mt8518/mt8518_ap1.c +++ b/board/mediatek/mt8518/mt8518_ap1.c @@ -16,3 +16,21 @@ int board_init(void) debug("gd->fdt_blob is %p\n", gd->fdt_blob); return 0; } + +int board_late_init(void) +{ +#ifdef CONFIG_USB_GADGET + struct udevice *dev; + int ret; +#endif + +#ifdef CONFIG_USB_GADGET + ret = uclass_get_device(UCLASS_USB_GADGET_GENERIC, 0, &dev); + if (ret) { + pr_err("%s: Cannot find USB device\n", __func__); + return ret; + } +#endif + + return 0; +} From dafd97ff70eaf191285fb1e4580c84b6e63c1e2b Mon Sep 17 00:00:00 2001 From: mingming lee Date: Thu, 16 Jan 2020 16:11:39 +0800 Subject: [PATCH 11/23] configs: mt8518: set global variables for fastboot set common fastboot variables for mt8518 Signed-off-by: mingming lee --- include/configs/mt8518.h | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/include/configs/mt8518.h b/include/configs/mt8518.h index 514722be99..276fbc285f 100644 --- a/include/configs/mt8518.h +++ b/include/configs/mt8518.h @@ -11,7 +11,6 @@ #include -/* Machine ID */ #define CONFIG_SYS_NONCACHED_MEMORY SZ_1M #define CONFIG_CPU_ARMV8 @@ -54,10 +53,15 @@ #define ENV_BOOT_CMD \ "mtk_boot=run boot_rd_img;bootm;\0" +#define ENV_FASTBOOT \ + "serial#=1234567890ABCDEF\0" \ + "board=mt8518\0" + #define CONFIG_EXTRA_ENV_SETTINGS \ "fdt_high=0x6c000000\0" \ ENV_DEVICE_SETTINGS \ ENV_BOOT_READ_IMAGE \ + ENV_FASTBOOT \ ENV_BOOT_CMD \ "bootcmd=run mtk_boot;\0" \ From d33be188338d43d3e802e48fa56d106e9600d971 Mon Sep 17 00:00:00 2001 From: mingming lee Date: Thu, 16 Jan 2020 16:11:40 +0800 Subject: [PATCH 12/23] configs: mt8518: enable usb gadget driver Enable board_late_init and usb gadget for mt8518 Signed-off-by: mingming lee --- configs/mt8518_ap1_emmc_defconfig | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/configs/mt8518_ap1_emmc_defconfig b/configs/mt8518_ap1_emmc_defconfig index 586b825bd3..95691199f3 100644 --- a/configs/mt8518_ap1_emmc_defconfig +++ b/configs/mt8518_ap1_emmc_defconfig @@ -9,6 +9,7 @@ CONFIG_NR_DRAM_BANKS=1 CONFIG_FIT=y CONFIG_FIT_SIGNATURE=y CONFIG_DEFAULT_FDT_FILE="mt8518-ap1-emmc.dtb" +CONFIG_BOARD_LATE_INIT=y CONFIG_SYS_PROMPT="MT8518> " CONFIG_CMD_BOOTMENU=y CONFIG_CMD_MMC=y @@ -27,6 +28,15 @@ CONFIG_DM_SERIAL=y CONFIG_MTK_SERIAL=y CONFIG_TIMER=y CONFIG_MTK_TIMER=y +CONFIG_USB=y +CONFIG_DM_USB=y +CONFIG_USB_MUSB_GADGET=y +CONFIG_USB_MUSB_MT85XX=y +CONFIG_USB_GADGET=y +CONFIG_USB_GADGET_MANUFACTURER="Mediatek." +CONFIG_USB_GADGET_VENDOR_NUM=0x0bb4 +CONFIG_USB_GADGET_PRODUCT_NUM=0x0c01 +CONFIG_USB_GADGET_DOWNLOAD=y CONFIG_WDT=y CONFIG_WDT_MTK=y CONFIG_LZ4=y From dc2426d83a57f7219ebbd01689cea4107df54f3b Mon Sep 17 00:00:00 2001 From: mingming lee Date: Thu, 16 Jan 2020 16:11:41 +0800 Subject: [PATCH 13/23] configs: mt8518: Enable fastboot related configs Enable EFI module. Enable fastboot. Signed-off-by: mingming lee --- configs/mt8518_ap1_emmc_defconfig | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/configs/mt8518_ap1_emmc_defconfig b/configs/mt8518_ap1_emmc_defconfig index 95691199f3..e7c9d633f1 100644 --- a/configs/mt8518_ap1_emmc_defconfig +++ b/configs/mt8518_ap1_emmc_defconfig @@ -13,10 +13,16 @@ CONFIG_BOARD_LATE_INIT=y CONFIG_SYS_PROMPT="MT8518> " CONFIG_CMD_BOOTMENU=y CONFIG_CMD_MMC=y +CONFIG_EFI_PARTITION=y CONFIG_DEFAULT_DEVICE_TREE="mt8518-ap1-emmc" CONFIG_REGMAP=y CONFIG_SYSCON=y CONFIG_CLK=y +CONFIG_USB_FUNCTION_FASTBOOT=y +CONFIG_FASTBOOT_BUF_ADDR=0x56000000 +CONFIG_FASTBOOT_BUF_SIZE=0x1E00000 +CONFIG_FASTBOOT_FLASH=y +CONFIG_FASTBOOT_FLASH_MMC_DEV=0 CONFIG_DM_MMC=y CONFIG_MMC_HS200_SUPPORT=y CONFIG_MMC_MTK=y @@ -36,7 +42,6 @@ CONFIG_USB_GADGET=y CONFIG_USB_GADGET_MANUFACTURER="Mediatek." CONFIG_USB_GADGET_VENDOR_NUM=0x0bb4 CONFIG_USB_GADGET_PRODUCT_NUM=0x0c01 -CONFIG_USB_GADGET_DOWNLOAD=y CONFIG_WDT=y CONFIG_WDT_MTK=y CONFIG_LZ4=y From 1fdbad021fe5f3bc8f8bb5b43e55ecc56432a6b4 Mon Sep 17 00:00:00 2001 From: mingming lee Date: Thu, 16 Jan 2020 16:11:42 +0800 Subject: [PATCH 14/23] fastboot: mt85xx: add command to flash/erase emmc hwpart This patch includes the following: 1. Add fastboot command to erase the whole EMMC_USER 2. Add fastboot command to flash image at EMMC_BOOT1 3. Add fastboot command to erase the whole EMMC_BOOT1 4. Enale CONFIG_FASTBOOT_MMC_BOOT1_SUPPORT for mt8518 Signed-off-by: mingming lee --- configs/mt8518_ap1_emmc_defconfig | 1 + drivers/fastboot/Kconfig | 30 +++++++++ drivers/fastboot/fb_mmc.c | 102 ++++++++++++++++++++++++++++++ 3 files changed, 133 insertions(+) diff --git a/configs/mt8518_ap1_emmc_defconfig b/configs/mt8518_ap1_emmc_defconfig index e7c9d633f1..50219dd446 100644 --- a/configs/mt8518_ap1_emmc_defconfig +++ b/configs/mt8518_ap1_emmc_defconfig @@ -21,6 +21,7 @@ CONFIG_CLK=y CONFIG_USB_FUNCTION_FASTBOOT=y CONFIG_FASTBOOT_BUF_ADDR=0x56000000 CONFIG_FASTBOOT_BUF_SIZE=0x1E00000 +CONFIG_FASTBOOT_MMC_BOOT1_SUPPORT=y CONFIG_FASTBOOT_FLASH=y CONFIG_FASTBOOT_FLASH_MMC_DEV=0 CONFIG_DM_MMC=y diff --git a/drivers/fastboot/Kconfig b/drivers/fastboot/Kconfig index 9f85054bfb..d4436dfc91 100644 --- a/drivers/fastboot/Kconfig +++ b/drivers/fastboot/Kconfig @@ -104,6 +104,36 @@ config FASTBOOT_FLASH_NAND_TRIMFFS When flashing NAND enable the DROP_FFS flag to drop trailing all-0xff pages. +config FASTBOOT_MMC_BOOT1_SUPPORT + bool "Enable EMMC_BOOT1 flash/erase" + depends on FASTBOOT_FLASH_MMC && EFI_PARTITION && ARCH_MEDIATEK + help + The fastboot "flash" and "erase" commands normally does operations + on EMMC userdata. Define this to enable the special commands to + flash/erase EMMC_BOOT1. + The default target name for updating EMMC_BOOT1 is "mmc0boot0". + +config FASTBOOT_MMC_BOOT1_NAME + string "Target name for updating EMMC_BOOT1" + depends on FASTBOOT_MMC_BOOT1_SUPPORT + default "mmc0boot0" + help + The fastboot "flash" and "erase" commands support operations on + EMMC_BOOT1. This occurs when the specified "EMMC_BOOT1 name" on + the "fastboot flash" and "fastboot erase" commands match the value + defined here. + The default target name for updating EMMC_BOOT1 is "mmc0boot0". + +config FASTBOOT_MMC_USER_NAME + string "Target name for erasing EMMC_USER" + depends on FASTBOOT_FLASH_MMC && EFI_PARTITION && ARCH_MEDIATEK + default "mmc0" + help + The fastboot "erase" command supports erasing EMMC_USER. This occurs + when the specified "EMMC_USER name" on the "fastboot erase" commands + match the value defined here. + The default target name for erasing EMMC_USER is "mmc0". + config FASTBOOT_GPT_NAME string "Target name for updating GPT" depends on FASTBOOT_FLASH_MMC && EFI_PARTITION diff --git a/drivers/fastboot/fb_mmc.c b/drivers/fastboot/fb_mmc.c index b0b19c5762..d7cf9f4aac 100644 --- a/drivers/fastboot/fb_mmc.c +++ b/drivers/fastboot/fb_mmc.c @@ -129,6 +129,76 @@ static void write_raw_image(struct blk_desc *dev_desc, disk_partition_t *info, fastboot_okay(NULL, response); } +#ifdef CONFIG_FASTBOOT_MMC_BOOT1_SUPPORT +static int fb_mmc_erase_mmc_hwpart(struct blk_desc *dev_desc) +{ + lbaint_t blks; + + debug("Start Erasing mmc hwpart[%u]...\n", dev_desc->hwpart); + + blks = fb_mmc_blk_write(dev_desc, 0, dev_desc->lba, NULL); + + if (blks != dev_desc->lba) { + pr_err("Failed to erase mmc hwpart[%u]\n", dev_desc->hwpart); + return 1; + } + + printf("........ erased %lu bytes from mmc hwpart[%u]\n", + dev_desc->lba * dev_desc->blksz, dev_desc->hwpart); + + return 0; +} + +static void fb_mmc_boot1_ops(struct blk_desc *dev_desc, void *buffer, + u32 buff_sz, char *response) +{ + lbaint_t blkcnt; + lbaint_t blks; + unsigned long blksz; + + // To operate on EMMC_BOOT1 (mmc0boot0), we first change the hwpart + if (blk_dselect_hwpart(dev_desc, 1)) { + pr_err("Failed to select hwpart\n"); + fastboot_fail("Failed to select hwpart", response); + return; + } + + if (buffer) { /* flash */ + + /* determine number of blocks to write */ + blksz = dev_desc->blksz; + blkcnt = ((buff_sz + (blksz - 1)) & ~(blksz - 1)); + blkcnt = lldiv(blkcnt, blksz); + + if (blkcnt > dev_desc->lba) { + pr_err("Image size too large\n"); + fastboot_fail("Image size too large", response); + return; + } + + debug("Start Flashing Image to EMMC_BOOT1...\n"); + + blks = fb_mmc_blk_write(dev_desc, 0, blkcnt, buffer); + + if (blks != blkcnt) { + pr_err("Failed to write EMMC_BOOT1\n"); + fastboot_fail("Failed to write EMMC_BOOT1", response); + return; + } + + printf("........ wrote %lu bytes to EMMC_BOOT1\n", + blkcnt * blksz); + } else { /* erase */ + if (fb_mmc_erase_mmc_hwpart(dev_desc)) { + fastboot_fail("Failed to erase EMMC_BOOT1", response); + return; + } + } + + fastboot_okay(NULL, response); +} +#endif + #ifdef CONFIG_ANDROID_BOOT_IMAGE /** * Read Android boot image header from boot partition. @@ -345,8 +415,21 @@ void fastboot_mmc_flash_write(const char *cmd, void *download_buffer, return; } +#ifdef CONFIG_FASTBOOT_MMC_BOOT1_SUPPORT + if (strcmp(cmd, CONFIG_FASTBOOT_MMC_BOOT1_NAME) == 0) { + fb_mmc_boot1_ops(dev_desc, download_buffer, + download_bytes, response); + return; + } +#endif + #if CONFIG_IS_ENABLED(EFI_PARTITION) +#ifndef CONFIG_FASTBOOT_MMC_USER_NAME if (strcmp(cmd, CONFIG_FASTBOOT_GPT_NAME) == 0) { +#else + if (strcmp(cmd, CONFIG_FASTBOOT_GPT_NAME) == 0 || + strcmp(cmd, CONFIG_FASTBOOT_MMC_USER_NAME) == 0) { +#endif printf("%s: updating MBR, Primary and Backup GPT(s)\n", __func__); if (is_valid_gpt_buf(dev_desc, download_buffer)) { @@ -457,6 +540,25 @@ void fastboot_mmc_erase(const char *cmd, char *response) return; } +#ifdef CONFIG_FASTBOOT_MMC_BOOT1_SUPPORT + if (strcmp(cmd, CONFIG_FASTBOOT_MMC_BOOT1_NAME) == 0) { + /* erase EMMC boot1 */ + fb_mmc_boot1_ops(dev_desc, NULL, 0, response); + return; + } +#endif + +#ifdef CONFIG_FASTBOOT_MMC_USER_NAME + if (strcmp(cmd, CONFIG_FASTBOOT_MMC_USER_NAME) == 0) { + /* erase EMMC userdata */ + if (fb_mmc_erase_mmc_hwpart(dev_desc)) + fastboot_fail("Failed to erase EMMC_USER", response); + else + fastboot_okay(NULL, response); + return; + } +#endif + ret = part_get_info_by_name_or_alias(dev_desc, cmd, &info); if (ret < 0) { pr_err("cannot find partition: '%s'\n", cmd); From c0a5a81f746f18a5d8ed4bf2c062d03e3519ab5e Mon Sep 17 00:00:00 2001 From: Vignesh Raghavendra Date: Thu, 16 Jan 2020 14:23:45 +0530 Subject: [PATCH 15/23] asm: dma-mapping.h: Fix dma mapping functions Subsystems such as USB expect dma_map_single() and dma_unmap_single() to do dcache flush/invalidate operations as required. For example, see see drivers/usb/gadget/udc/udc-core.c::usb_gadget_map_request(). Currently drivers do this locally, (see drivers/usb/dwc3/ep0.c, drivers/mtd/nand/raw/denali.c etc..) Update arch specific dma_map_single() and dma_unmap_single() APIs to do cache flush/invalidate operations, so that drivers need not implement them locally. Signed-off-by: Vignesh Raghavendra Reviewed-by: Masahiro Yamada Reviewed-by: Rick Chen --- arch/arm/include/asm/dma-mapping.h | 23 +++++++++++++++++++++-- arch/nds32/include/asm/dma-mapping.h | 23 +++++++++++++++++++++-- arch/riscv/include/asm/dma-mapping.h | 23 +++++++++++++++++++++-- arch/x86/include/asm/dma-mapping.h | 23 +++++++++++++++++++++-- 4 files changed, 84 insertions(+), 8 deletions(-) diff --git a/arch/arm/include/asm/dma-mapping.h b/arch/arm/include/asm/dma-mapping.h index fc5b8f634d..d20703739f 100644 --- a/arch/arm/include/asm/dma-mapping.h +++ b/arch/arm/include/asm/dma-mapping.h @@ -7,7 +7,11 @@ #ifndef __ASM_ARM_DMA_MAPPING_H #define __ASM_ARM_DMA_MAPPING_H +#include +#include +#include #include +#include #define dma_mapping_error(x, y) 0 @@ -25,12 +29,27 @@ static inline void dma_free_coherent(void *addr) static inline unsigned long dma_map_single(volatile void *vaddr, size_t len, enum dma_data_direction dir) { - return (unsigned long)vaddr; + unsigned long addr = (unsigned long)vaddr; + + len = ALIGN(len, ARCH_DMA_MINALIGN); + + if (dir == DMA_FROM_DEVICE) + invalidate_dcache_range(addr, addr + len); + else + flush_dcache_range(addr, addr + len); + + return addr; } static inline void dma_unmap_single(volatile void *vaddr, size_t len, - unsigned long paddr) + enum dma_data_direction dir) { + unsigned long addr = (unsigned long)vaddr; + + len = ALIGN(len, ARCH_DMA_MINALIGN); + + if (dir != DMA_TO_DEVICE) + invalidate_dcache_range(addr, addr + len); } #endif /* __ASM_ARM_DMA_MAPPING_H */ diff --git a/arch/nds32/include/asm/dma-mapping.h b/arch/nds32/include/asm/dma-mapping.h index e6808dc840..c8876ceadd 100644 --- a/arch/nds32/include/asm/dma-mapping.h +++ b/arch/nds32/include/asm/dma-mapping.h @@ -6,7 +6,11 @@ #ifndef __ASM_NDS_DMA_MAPPING_H #define __ASM_NDS_DMA_MAPPING_H +#include +#include +#include #include +#include static void *dma_alloc_coherent(size_t len, unsigned long *handle) { @@ -17,12 +21,27 @@ static void *dma_alloc_coherent(size_t len, unsigned long *handle) static inline unsigned long dma_map_single(volatile void *vaddr, size_t len, enum dma_data_direction dir) { - return (unsigned long)vaddr; + unsigned long addr = (unsigned long)vaddr; + + len = ALIGN(len, ARCH_DMA_MINALIGN); + + if (dir == DMA_FROM_DEVICE) + invalidate_dcache_range(addr, addr + len); + else + flush_dcache_range(addr, addr + len); + + return addr; } static inline void dma_unmap_single(volatile void *vaddr, size_t len, - unsigned long paddr) + enum dma_data_direction dir) { + unsigned long addr = (unsigned long)vaddr; + + len = ALIGN(len, ARCH_DMA_MINALIGN); + + if (dir != DMA_TO_DEVICE) + invalidate_dcache_range(addr, addr + len); } #endif /* __ASM_NDS_DMA_MAPPING_H */ diff --git a/arch/riscv/include/asm/dma-mapping.h b/arch/riscv/include/asm/dma-mapping.h index 3d930c90ec..6cc3946959 100644 --- a/arch/riscv/include/asm/dma-mapping.h +++ b/arch/riscv/include/asm/dma-mapping.h @@ -9,7 +9,11 @@ #ifndef __ASM_RISCV_DMA_MAPPING_H #define __ASM_RISCV_DMA_MAPPING_H +#include +#include +#include #include +#include #define dma_mapping_error(x, y) 0 @@ -27,12 +31,27 @@ static inline void dma_free_coherent(void *addr) static inline unsigned long dma_map_single(volatile void *vaddr, size_t len, enum dma_data_direction dir) { - return (unsigned long)vaddr; + unsigned long addr = (unsigned long)vaddr; + + len = ALIGN(len, ARCH_DMA_MINALIGN); + + if (dir == DMA_FROM_DEVICE) + invalidate_dcache_range(addr, addr + len); + else + flush_dcache_range(addr, addr + len); + + return addr; } static inline void dma_unmap_single(volatile void *vaddr, size_t len, - unsigned long paddr) + enum dma_data_direction dir) { + unsigned long addr = (unsigned long)vaddr; + + len = ALIGN(len, ARCH_DMA_MINALIGN); + + if (dir != DMA_TO_DEVICE) + invalidate_dcache_range(addr, addr + len); } #endif /* __ASM_RISCV_DMA_MAPPING_H */ diff --git a/arch/x86/include/asm/dma-mapping.h b/arch/x86/include/asm/dma-mapping.h index b353ff0bef..900b99b8a6 100644 --- a/arch/x86/include/asm/dma-mapping.h +++ b/arch/x86/include/asm/dma-mapping.h @@ -7,7 +7,11 @@ #ifndef __ASM_X86_DMA_MAPPING_H #define __ASM_X86_DMA_MAPPING_H +#include +#include +#include #include +#include #define dma_mapping_error(x, y) 0 @@ -25,12 +29,27 @@ static inline void dma_free_coherent(void *addr) static inline unsigned long dma_map_single(volatile void *vaddr, size_t len, enum dma_data_direction dir) { - return (unsigned long)vaddr; + unsigned long addr = (unsigned long)vaddr; + + len = ALIGN(len, ARCH_DMA_MINALIGN); + + if (dir == DMA_FROM_DEVICE) + invalidate_dcache_range(addr, addr + len); + else + flush_dcache_range(addr, addr + len); + + return addr; } static inline void dma_unmap_single(volatile void *vaddr, size_t len, - unsigned long paddr) + enum dma_data_direction dir) { + unsigned long addr = (unsigned long)vaddr; + + len = ALIGN(len, ARCH_DMA_MINALIGN); + + if (dir != DMA_TO_DEVICE) + invalidate_dcache_range(addr, addr + len); } #endif /* __ASM_X86_DMA_MAPPING_H */ From eaa8b04da363ccd208b55f8b4f55382befc90a0f Mon Sep 17 00:00:00 2001 From: Vignesh Raghavendra Date: Thu, 16 Jan 2020 14:23:46 +0530 Subject: [PATCH 16/23] mmc: tmio-common: Drop custom dma mapping functions Drop local dma_map_single() and dma_unmap_single() and use arch specific common implementation Signed-off-by: Vignesh Raghavendra Acked-by: Masahiro Yamada --- drivers/mmc/tmio-common.c | 25 +++---------------------- 1 file changed, 3 insertions(+), 22 deletions(-) diff --git a/drivers/mmc/tmio-common.c b/drivers/mmc/tmio-common.c index 669410d97f..5a8506dcb6 100644 --- a/drivers/mmc/tmio-common.c +++ b/drivers/mmc/tmio-common.c @@ -4,6 +4,7 @@ * Author: Masahiro Yamada */ +#include #include #include #include @@ -76,26 +77,6 @@ void tmio_sd_writel(struct tmio_sd_priv *priv, writel(val, priv->regbase + reg); } -static dma_addr_t __dma_map_single(void *ptr, size_t size, - enum dma_data_direction dir) -{ - unsigned long addr = (unsigned long)ptr; - - if (dir == DMA_FROM_DEVICE) - invalidate_dcache_range(addr, addr + size); - else - flush_dcache_range(addr, addr + size); - - return addr; -} - -static void __dma_unmap_single(dma_addr_t addr, size_t size, - enum dma_data_direction dir) -{ - if (dir != DMA_TO_DEVICE) - invalidate_dcache_range(addr, addr + size); -} - static int tmio_sd_check_error(struct udevice *dev, struct mmc_cmd *cmd) { struct tmio_sd_priv *priv = dev_get_priv(dev); @@ -362,7 +343,7 @@ static int tmio_sd_dma_xfer(struct udevice *dev, struct mmc_data *data) tmio_sd_writel(priv, tmp, TMIO_SD_DMA_MODE); - dma_addr = __dma_map_single(buf, len, dir); + dma_addr = dma_map_single(buf, len, dir); tmio_sd_dma_start(priv, dma_addr); @@ -371,7 +352,7 @@ static int tmio_sd_dma_xfer(struct udevice *dev, struct mmc_data *data) if (poll_flag == TMIO_SD_DMA_INFO1_END_RD) udelay(1); - __dma_unmap_single(dma_addr, len, dir); + dma_unmap_single(buf, len, dir); return ret; } From 6fff562bafb93cef2b9a03a3e243cf1f29b7c582 Mon Sep 17 00:00:00 2001 From: Vignesh Raghavendra Date: Thu, 16 Jan 2020 14:23:47 +0530 Subject: [PATCH 17/23] mtd: denali: Drop custom dma mapping functions Drop local dma_map_single() and dma_unmap_single() and use arch specific common implementation Signed-off-by: Vignesh Raghavendra Acked-by: Masahiro Yamada --- drivers/mtd/nand/raw/denali.c | 35 +++-------------------------------- 1 file changed, 3 insertions(+), 32 deletions(-) diff --git a/drivers/mtd/nand/raw/denali.c b/drivers/mtd/nand/raw/denali.c index 0a7ca8a8df..8537c609fb 100644 --- a/drivers/mtd/nand/raw/denali.c +++ b/drivers/mtd/nand/raw/denali.c @@ -5,7 +5,7 @@ * Copyright (C) 2009-2010, Intel Corporation and its suppliers. */ -#include +#include #include #include #include @@ -17,35 +17,6 @@ #include "denali.h" -static dma_addr_t dma_map_single(void *dev, void *ptr, size_t size, - enum dma_data_direction dir) -{ - unsigned long addr = (unsigned long)ptr; - - size = ALIGN(size, ARCH_DMA_MINALIGN); - - if (dir == DMA_FROM_DEVICE) - invalidate_dcache_range(addr, addr + size); - else - flush_dcache_range(addr, addr + size); - - return addr; -} - -static void dma_unmap_single(void *dev, dma_addr_t addr, size_t size, - enum dma_data_direction dir) -{ - size = ALIGN(size, ARCH_DMA_MINALIGN); - - if (dir != DMA_TO_DEVICE) - invalidate_dcache_range(addr, addr + size); -} - -static int dma_mapping_error(void *dev, dma_addr_t addr) -{ - return 0; -} - #define DENALI_NAND_NAME "denali-nand" /* for Indexed Addressing */ @@ -565,7 +536,7 @@ static int denali_dma_xfer(struct denali_nand_info *denali, void *buf, enum dma_data_direction dir = write ? DMA_TO_DEVICE : DMA_FROM_DEVICE; int ret = 0; - dma_addr = dma_map_single(denali->dev, buf, size, dir); + dma_addr = dma_map_single(buf, size, dir); if (dma_mapping_error(denali->dev, dma_addr)) { dev_dbg(denali->dev, "Failed to DMA-map buffer. Trying PIO.\n"); return denali_pio_xfer(denali, buf, size, page, raw, write); @@ -606,7 +577,7 @@ static int denali_dma_xfer(struct denali_nand_info *denali, void *buf, iowrite32(0, denali->reg + DMA_ENABLE); - dma_unmap_single(denali->dev, dma_addr, size, dir); + dma_unmap_single(buf, size, dir); if (irq_status & INTR__ERASED_PAGE) memset(buf, 0xff, size); From 5cde44e12adc180575d5ee35ef251e0470a10598 Mon Sep 17 00:00:00 2001 From: Vignesh Raghavendra Date: Thu, 16 Jan 2020 14:23:48 +0530 Subject: [PATCH 18/23] net: macb: Drop local cache flush Now that arch specific dma mapping APIs take care of cache flush/invalidate, drop local cache flush operation. While at that fix dma_unmap_single() call to match new prototype Signed-off-by: Vignesh Raghavendra --- drivers/net/macb.c | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/drivers/net/macb.c b/drivers/net/macb.c index 8359425378..0d4929bec1 100644 --- a/drivers/net/macb.c +++ b/drivers/net/macb.c @@ -327,8 +327,6 @@ static int _macb_send(struct macb_device *macb, const char *name, void *packet, macb->tx_ring[tx_head].addr = paddr; barrier(); macb_flush_ring_desc(macb, TX); - /* Do we need check paddr and length is dcache line aligned? */ - flush_dcache_range(paddr, paddr + ALIGN(length, ARCH_DMA_MINALIGN)); macb_writel(macb, NCR, MACB_BIT(TE) | MACB_BIT(RE) | MACB_BIT(TSTART)); /* @@ -344,7 +342,7 @@ static int _macb_send(struct macb_device *macb, const char *name, void *packet, udelay(1); } - dma_unmap_single(packet, length, paddr); + dma_unmap_single(packet, length, DMA_TO_DEVICE); if (i <= MACB_TX_TIMEOUT) { if (ctrl & MACB_BIT(TX_UNDERRUN)) From 1526bcce0f7285087621e16e6720636d01839da8 Mon Sep 17 00:00:00 2001 From: Angelo Durgehello Date: Tue, 21 Jan 2020 10:37:27 +0100 Subject: [PATCH 19/23] common: add blkcache init On m68k, block_cache list is relocated, but next and prev list pointers are not adjusted to the relocated struct list_head address, so the first iteration over the block_cache list hangs. This patch initializes the block_cache list after relocation. Signed-off-by: Angelo Durgehello Reviewed-by: Eric Nelson --- common/board_r.c | 3 +++ drivers/block/blkcache.c | 9 ++++++++- include/blk.h | 6 ++++++ 3 files changed, 17 insertions(+), 1 deletion(-) diff --git a/common/board_r.c b/common/board_r.c index 8a0c1114e7..4f56c19fcc 100644 --- a/common/board_r.c +++ b/common/board_r.c @@ -864,6 +864,9 @@ static init_fnc_t init_sequence_r[] = { #endif #if defined(CONFIG_PRAM) initr_mem, +#endif +#ifdef CONFIG_BLOCK_CACHE + blkcache_init, #endif run_main_loop, }; diff --git a/drivers/block/blkcache.c b/drivers/block/blkcache.c index 1fa64989d3..f603aa129d 100644 --- a/drivers/block/blkcache.c +++ b/drivers/block/blkcache.c @@ -21,13 +21,20 @@ struct block_cache_node { char *cache; }; -static LIST_HEAD(block_cache); +static struct list_head block_cache; static struct block_cache_stats _stats = { .max_blocks_per_entry = 8, .max_entries = 32 }; +int blkcache_init(void) +{ + INIT_LIST_HEAD(&block_cache); + + return 0; +} + static struct block_cache_node *cache_find(int iftype, int devnum, lbaint_t start, lbaint_t blkcnt, unsigned long blksz) diff --git a/include/blk.h b/include/blk.h index d0c033aece..65db69f5d9 100644 --- a/include/blk.h +++ b/include/blk.h @@ -113,6 +113,12 @@ struct blk_desc { (PAD_SIZE(size, blk_desc->blksz)) #if CONFIG_IS_ENABLED(BLOCK_CACHE) + +/** + * blkcache_init() - initialize the block cache list pointers + */ +int blkcache_init(void); + /** * blkcache_read() - attempt to read a set of blocks from cache * From 3166014d572e614094e4d4345b738b94673b57a0 Mon Sep 17 00:00:00 2001 From: Baruch Siach Date: Wed, 22 Jan 2020 14:54:24 +0200 Subject: [PATCH 20/23] genboardscfg.py: drop python version comment genboardscfg.py requires python 3.x since commit 3bc14098d8fb ("genboardscfg.py: Convert to Python 3"). Cc: Masahiro Yamada Signed-off-by: Baruch Siach Acked-by: Masahiro Yamada --- tools/genboardscfg.py | 2 -- 1 file changed, 2 deletions(-) diff --git a/tools/genboardscfg.py b/tools/genboardscfg.py index 24df13e500..4f6382bc7c 100755 --- a/tools/genboardscfg.py +++ b/tools/genboardscfg.py @@ -10,8 +10,6 @@ Converter from Kconfig and MAINTAINERS to a board database. Run 'tools/genboardscfg.py' to create a board database. Run 'tools/genboardscfg.py -h' for available options. - -Python 2.6 or later, but not Python 3.x is necessary to run this script. """ import errno From 5073e043518751b87f6a1dee82dd8b8b78198134 Mon Sep 17 00:00:00 2001 From: Shawn Guo Date: Fri, 24 Jan 2020 12:59:42 +0800 Subject: [PATCH 21/23] meerkat96: fix typo in MAINTAINERS email address There is a typo in meerkat96 MAINTAINERS email address. Fix it. Reported-by: Carl Gelfand Signed-off-by: Shawn Guo --- board/novtech/meerkat96/MAINTAINERS | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/board/novtech/meerkat96/MAINTAINERS b/board/novtech/meerkat96/MAINTAINERS index 0eca2940d5..2a53b63099 100644 --- a/board/novtech/meerkat96/MAINTAINERS +++ b/board/novtech/meerkat96/MAINTAINERS @@ -1,5 +1,5 @@ MEERKAT96 BOARD -M: Shawn Guo +M: Shawn Guo S: Maintained F: board/novtech/meerkat96 F: include/configs/meerkat96.h From 50fe8df2c2cb863e0ab7d4c1240f2216ba184922 Mon Sep 17 00:00:00 2001 From: Eric Nelson Date: Wed, 22 Jan 2020 16:59:55 -0700 Subject: [PATCH 22/23] common: blk: fix comment about blkcache_read return value The blkcache_read() routine returns 1 (true) to indicate that a block was found in the cache and returned, or 0 if not. Signed-off-by: Eric Nelson --- include/blk.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/blk.h b/include/blk.h index 65db69f5d9..6f541bb2ba 100644 --- a/include/blk.h +++ b/include/blk.h @@ -129,7 +129,7 @@ int blkcache_init(void); * @param blksz - size in bytes of each block * @param buf - buffer to contain cached data * - * @return - '1' if block returned from cache, '0' otherwise. + * @return - 1 if block returned from cache, 0 otherwise. */ int blkcache_read(int iftype, int dev, lbaint_t start, lbaint_t blkcnt, From 683b7c2a170a71bded99bb9e7dfd26372427ca1c Mon Sep 17 00:00:00 2001 From: Patrick Delaunay Date: Fri, 24 Jan 2020 13:45:56 +0100 Subject: [PATCH 23/23] mtd: add prototypes for weak function This patch adds a prototype for the weak function board_mtdparts_default(). It solves one warning when compiling with W=1 on stm32mp1 board: board/st/stm32mp1/stm32mp1.c: warning: no previous prototype for 'board_mtdparts_default' [-Wmissing-prototypes] void board_mtdparts_default(const char **mtdids, const char **mtdparts) ^~~~~~~~~~~~~~~~~~~~~~ Signed-off-by: Patrick Delaunay --- include/mtd.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/include/mtd.h b/include/mtd.h index 65fcd3c700..b0f8693386 100644 --- a/include/mtd.h +++ b/include/mtd.h @@ -11,4 +11,6 @@ int mtd_probe(struct udevice *dev); int mtd_probe_devices(void); +void board_mtdparts_default(const char **mtdids, const char **mtdparts); + #endif /* _MTD_H_ */