diff options
Diffstat (limited to 'package/boot')
7 files changed, 0 insertions, 4669 deletions
diff --git a/package/boot/uboot-xburst/Makefile b/package/boot/uboot-xburst/Makefile deleted file mode 100644 index 413289a7f9..0000000000 --- a/package/boot/uboot-xburst/Makefile +++ /dev/null @@ -1,88 +0,0 @@ -# -# Copyright (C) 2010 OpenWrt.org -# -# This is free software, licensed under the GNU General Public License v2. -# See /LICENSE for more information. -# - -include $(TOPDIR)/rules.mk -include $(INCLUDE_DIR)/kernel.mk - -PKG_NAME:=u-boot -PKG_VERSION:=2012.10-rc2 -PKG_RELEASE:=1 - -PKG_BUILD_DIR:=$(KERNEL_BUILD_DIR)/$(PKG_NAME)-$(BUILD_VARIANT)/$(PKG_NAME)-$(PKG_VERSION) -PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.bz2 -PKG_SOURCE_URL:= \ - http://mirror2.openwrt.org/sources \ - ftp://ftp.denx.de/pub/u-boot -PKG_HASH:=6d094cafa7ecea8b671fbdcd21130b6a4f5744fc47dd263e101ed5d3629dffd4 -PKG_TARGETS:=bin - -PKG_LICENSE:=GPL-2.0 GPL-2.0+ -PKG_LICENSE_FILES:=Licenses/README - -include $(INCLUDE_DIR)/package.mk - -define uboot/Default - TITLE:= - CONFIG:= - IMAGE:= -endef - -define uboot/qi_lb60 - TITLE:=U-boot for the qi_lb60 board -endef - -UBOOTS:=qi_lb60 - -define Package/uboot/template -define Package/uboot-xburst-$(1) - SECTION:=boot - CATEGORY:=Boot Loaders - DEPENDS:=@TARGET_xburst - TITLE:=$(2) - URL:=http://www.denx.de/wiki/UBoot/WebHome - VARIANT:=$(1) -endef -endef - -define BuildUbootPackage - $(eval $(uboot/Default)) - $(eval $(uboot/$(1))) - $(call Package/uboot/template,$(1),$(TITLE)) -endef - - -ifdef BUILD_VARIANT -$(eval $(call uboot/$(BUILD_VARIANT))) -UBOOT_CONFIG:=$(if $(CONFIG),$(CONFIG),$(BUILD_VARIANT)) -UBOOT_IMAGE:=$(if $(IMAGE),$(IMAGE),openwrt-$(BOARD)-$(BUILD_VARIANT)-u-boot.bin) -endif - -define Build/Configure - $(MAKE) -C $(PKG_BUILD_DIR) \ - $(UBOOT_CONFIG)_config -endef - -define Build/Compile - $(MAKE) -C $(PKG_BUILD_DIR) \ - CROSS_COMPILE=$(TARGET_CROSS) -endef - -define Package/uboot/install/template -define Package/uboot-xburst-$(1)/install - $(CP) $(PKG_BUILD_DIR)/u-boot-xburst.bin $(BIN_DIR)/$(2) - rmdir $$(1) -endef -endef - -$(foreach u,$(UBOOTS), \ - $(eval $(call Package/uboot/install/template,$(u),openwrt-$(BOARD)-$(u)-u-boot.bin)) \ -) - -$(foreach u,$(UBOOTS), \ - $(eval $(call BuildUbootPackage,$(u))) \ - $(eval $(call BuildPackage,uboot-xburst-$(u))) \ -) diff --git a/package/boot/uboot-xburst/patches/0001-qi_lb60-add-nand-spl-support.patch b/package/boot/uboot-xburst/patches/0001-qi_lb60-add-nand-spl-support.patch deleted file mode 100644 index e770243528..0000000000 --- a/package/boot/uboot-xburst/patches/0001-qi_lb60-add-nand-spl-support.patch +++ /dev/null @@ -1,894 +0,0 @@ -From 0329cf7965956a5a7044827e0ce88ae8d5150e54 Mon Sep 17 00:00:00 2001 -From: Xiangfu <xiangfu@openmobilefree.net> -Date: Fri, 12 Oct 2012 09:46:58 +0800 -Subject: [PATCH 1/6] qi_lb60: add nand spl support - - The JZ4740 CPU can load 8KB from two different addresses: - 1. the normal area up to 8KB starting from NAND flash address 0x00000000 - 2. the backup area up to 8KB starting from NAND flash address 0x00002000 - -Signed-off-by: Xiangfu <xiangfu@openmobilefree.net> ---- - Makefile | 12 +++ - arch/mips/cpu/xburst/Makefile | 7 +- - arch/mips/cpu/xburst/cpu.c | 4 + - arch/mips/cpu/xburst/jz4740.c | 82 +++++++---------- - arch/mips/cpu/xburst/spl/Makefile | 47 ++++++++++ - arch/mips/cpu/xburst/spl/start.S | 63 +++++++++++++ - board/qi/qi_lb60/Makefile | 4 + - board/qi/qi_lb60/qi_lb60-spl.c | 30 +++++++ - board/qi/qi_lb60/qi_lb60.c | 8 +- - board/qi/qi_lb60/u-boot-spl.lds | 61 +++++++++++++ - drivers/mtd/nand/jz4740_nand.c | 39 ++++++++- - include/configs/qi_lb60.h | 175 ++++++++++++++++++------------------- - 12 files changed, 386 insertions(+), 146 deletions(-) - create mode 100644 arch/mips/cpu/xburst/spl/Makefile - create mode 100644 arch/mips/cpu/xburst/spl/start.S - create mode 100644 board/qi/qi_lb60/qi_lb60-spl.c - create mode 100644 board/qi/qi_lb60/u-boot-spl.lds - -diff --git a/Makefile b/Makefile -index 34d9075..a22778e 100644 ---- a/Makefile -+++ b/Makefile -@@ -393,6 +393,10 @@ ALL-y += $(obj)u-boot-nodtb-tegra.bin - endif - endif - -+ifeq ($(CPU),xburst) -+ALL-y += $(obj)u-boot-xburst.bin -+endif -+ - all: $(ALL-y) $(SUBDIR_EXAMPLES) - - $(obj)u-boot.dtb: $(obj)u-boot -@@ -506,6 +510,14 @@ $(obj)u-boot-nodtb-tegra.bin: $(obj)spl/u-boot-spl.bin $(obj)u-boot.bin - endif - endif - -+ifeq ($(CPU),xburst) -+$(obj)u-boot-xburst.bin: $(obj)spl/u-boot-spl.bin $(obj)u-boot.bin -+ dd if=$(obj)spl/u-boot-spl.bin of=$(obj)spl/u-boot-pad.bin conv=sync bs=8192 count=1 -+ dd if=$(obj)spl/u-boot-spl.bin of=$(obj)spl/u-boot-pad.bin conv=sync,notrunc oflag=append bs=8192 count=1 -+ tr '\0' '\377' < /dev/zero | dd of=$(obj)spl/u-boot-pad.bin conv=sync,notrunc oflag=append bs=16384 count=1 -+ cat $(obj)spl/u-boot-pad.bin u-boot.bin > $@ -+endif -+ - ifeq ($(CONFIG_SANDBOX),y) - GEN_UBOOT = \ - cd $(LNDIR) && $(CC) $(SYMS) -T $(obj)u-boot.lds \ -diff --git a/arch/mips/cpu/xburst/Makefile b/arch/mips/cpu/xburst/Makefile -index b1f2ae4..ec35e55 100644 ---- a/arch/mips/cpu/xburst/Makefile -+++ b/arch/mips/cpu/xburst/Makefile -@@ -24,9 +24,12 @@ include $(TOPDIR)/config.mk - - LIB = $(obj)lib$(CPU).o - -+COBJS-y = cpu.o jz_serial.o -+ -+ifneq ($(CONFIG_SPL_BUILD),y) - START = start.o --SOBJS-y = --COBJS-y = cpu.o timer.o jz_serial.o -+COBJS-y += timer.o -+endif - - COBJS-$(CONFIG_JZ4740) += jz4740.o - -diff --git a/arch/mips/cpu/xburst/cpu.c b/arch/mips/cpu/xburst/cpu.c -index ddcbfaa..1432838 100644 ---- a/arch/mips/cpu/xburst/cpu.c -+++ b/arch/mips/cpu/xburst/cpu.c -@@ -42,6 +42,8 @@ - : \ - : "i" (op), "R" (*(unsigned char *)(addr))) - -+#ifndef CONFIG_SPL_BUILD -+ - void __attribute__((weak)) _machine_restart(void) - { - struct jz4740_wdt *wdt = (struct jz4740_wdt *)JZ4740_WDT_BASE; -@@ -109,6 +111,8 @@ void invalidate_dcache_range(ulong start_addr, ulong stop) - cache_op(Hit_Invalidate_D, addr); - } - -+#endif -+ - void flush_icache_all(void) - { - u32 addr, t = 0; -diff --git a/arch/mips/cpu/xburst/jz4740.c b/arch/mips/cpu/xburst/jz4740.c -index c0b9817..8816aa3 100644 ---- a/arch/mips/cpu/xburst/jz4740.c -+++ b/arch/mips/cpu/xburst/jz4740.c -@@ -32,31 +32,19 @@ int disable_interrupts(void) - return 0; - } - --/* -- * PLL output clock = EXTAL * NF / (NR * NO) -- * NF = FD + 2, NR = RD + 2 -- * NO = 1 (if OD = 0), NO = 2 (if OD = 1 or 2), NO = 4 (if OD = 3) -- */ - void pll_init(void) - { - struct jz4740_cpm *cpm = (struct jz4740_cpm *)JZ4740_CPM_BASE; - -- register unsigned int cfcr, plcr1; -- int n2FR[33] = { -- 0, 0, 1, 2, 3, 0, 4, 0, 5, 0, 0, 0, 6, 0, 0, 0, -- 7, 0, 0, 0, 0, 0, 0, 0, 8, 0, 0, 0, 0, 0, 0, 0, -- 9 -- }; -- int div[5] = {1, 3, 3, 3, 3}; /* divisors of I:S:P:L:M */ -- int nf, pllout2; -+ register unsigned int cfcr, plcr; -+ unsigned int nf, pllout2; - - cfcr = CPM_CPCCR_CLKOEN | -- CPM_CPCCR_PCS | -- (n2FR[div[0]] << CPM_CPCCR_CDIV_BIT) | -- (n2FR[div[1]] << CPM_CPCCR_HDIV_BIT) | -- (n2FR[div[2]] << CPM_CPCCR_PDIV_BIT) | -- (n2FR[div[3]] << CPM_CPCCR_MDIV_BIT) | -- (n2FR[div[4]] << CPM_CPCCR_LDIV_BIT); -+ (0 << CPM_CPCCR_CDIV_BIT) | -+ (2 << CPM_CPCCR_HDIV_BIT) | -+ (2 << CPM_CPCCR_PDIV_BIT) | -+ (2 << CPM_CPCCR_MDIV_BIT) | -+ (2 << CPM_CPCCR_LDIV_BIT); - - pllout2 = (cfcr & CPM_CPCCR_PCS) ? - CONFIG_SYS_CPU_SPEED : (CONFIG_SYS_CPU_SPEED / 2); -@@ -65,15 +53,18 @@ void pll_init(void) - writel(pllout2 / 48000000 - 1, &cpm->uhccdr); - - nf = CONFIG_SYS_CPU_SPEED * 2 / CONFIG_SYS_EXTAL; -- plcr1 = ((nf - 2) << CPM_CPPCR_PLLM_BIT) | /* FD */ -+ plcr = ((nf - 2) << CPM_CPPCR_PLLM_BIT) | /* FD */ - (0 << CPM_CPPCR_PLLN_BIT) | /* RD=0, NR=2 */ - (0 << CPM_CPPCR_PLLOD_BIT) | /* OD=0, NO=1 */ -- (0x20 << CPM_CPPCR_PLLST_BIT) | /* PLL stable time */ -+ (0x32 << CPM_CPPCR_PLLST_BIT) | /* PLL stable time */ - CPM_CPPCR_PLLEN; /* enable PLL */ - - /* init PLL */ - writel(cfcr, &cpm->cpccr); -- writel(plcr1, &cpm->cppcr); -+ writel(plcr, &cpm->cppcr); -+ -+ while (!(readl(&cpm->cppcr) & CPM_CPPCR_PLLS)) -+ ; - } - - void sdram_init(void) -@@ -92,26 +83,12 @@ void sdram_init(void) - 2 << EMC_DMCR_TCL_BIT /* CAS latency is 3 */ - }; - -- int div[] = {1, 2, 3, 4, 6, 8, 12, 16, 24, 32}; -- - cpu_clk = CONFIG_SYS_CPU_SPEED; -- mem_clk = cpu_clk * div[__cpm_get_cdiv()] / div[__cpm_get_mdiv()]; -+ mem_clk = 84000000; - - writel(0, &emc->bcr); /* Disable bus release */ - writew(0, &emc->rtcsr); /* Disable clock for counting */ - -- /* Fault DMCR value for mode register setting*/ --#define SDRAM_ROW0 11 --#define SDRAM_COL0 8 --#define SDRAM_BANK40 0 -- -- dmcr0 = ((SDRAM_ROW0 - 11) << EMC_DMCR_RA_BIT) | -- ((SDRAM_COL0 - 8) << EMC_DMCR_CA_BIT) | -- (SDRAM_BANK40 << EMC_DMCR_BA_BIT) | -- (SDRAM_BW16 << EMC_DMCR_BW_BIT) | -- EMC_DMCR_EPIN | -- cas_latency_dmcr[((SDRAM_CASL == 3) ? 1 : 0)]; -- - /* Basic DMCR value */ - dmcr = ((SDRAM_ROW - 11) << EMC_DMCR_RA_BIT) | - ((SDRAM_COL - 8) << EMC_DMCR_CA_BIT) | -@@ -128,31 +105,31 @@ void sdram_init(void) - if (tmp > 11) - tmp = 11; - dmcr |= (tmp - 4) << EMC_DMCR_TRAS_BIT; -- tmp = SDRAM_RCD / ns; - -+ tmp = SDRAM_RCD / ns; - if (tmp > 3) - tmp = 3; - dmcr |= tmp << EMC_DMCR_RCD_BIT; -- tmp = SDRAM_TPC / ns; - -+ tmp = SDRAM_TPC / ns; - if (tmp > 7) - tmp = 7; - dmcr |= tmp << EMC_DMCR_TPC_BIT; -- tmp = SDRAM_TRWL / ns; - -+ tmp = SDRAM_TRWL / ns; - if (tmp > 3) - tmp = 3; - dmcr |= tmp << EMC_DMCR_TRWL_BIT; -- tmp = (SDRAM_TRAS + SDRAM_TPC) / ns; - -+ tmp = (SDRAM_TRAS + SDRAM_TPC) / ns; - if (tmp > 14) - tmp = 14; - dmcr |= ((tmp + 1) >> 1) << EMC_DMCR_TRC_BIT; - - /* SDRAM mode value */ -- sdmode = EMC_SDMR_BT_SEQ | -- EMC_SDMR_OM_NORMAL | -- EMC_SDMR_BL_4 | -+ sdmode = EMC_SDMR_BT_SEQ | -+ EMC_SDMR_OM_NORMAL | -+ EMC_SDMR_BL_4 | - cas_latency_sdmr[((SDRAM_CASL == 3) ? 1 : 0)]; - - /* Stage 1. Precharge all banks by writing SDMR with DMCR.MRSET=0 */ -@@ -172,8 +149,8 @@ void sdram_init(void) - if (tmp > 0xff) - tmp = 0xff; - writew(tmp, &emc->rtcor); -+ - writew(0, &emc->rtcnt); -- /* Divisor is 64, CKO/64 */ - writew(EMC_RTCSR_CKS_64, &emc->rtcsr); - - /* Wait for number of auto-refresh cycles */ -@@ -182,13 +159,17 @@ void sdram_init(void) - ; - - /* Stage 3. Mode Register Set */ -+ dmcr0 = (11 << EMC_DMCR_RA_BIT) | -+ (8 << EMC_DMCR_CA_BIT) | -+ (0 << EMC_DMCR_BA_BIT) | -+ EMC_DMCR_EPIN | -+ (SDRAM_BW16 << EMC_DMCR_BW_BIT) | -+ cas_latency_dmcr[((SDRAM_CASL == 3) ? 1 : 0)]; - writel(dmcr0 | EMC_DMCR_RFSH | EMC_DMCR_MRSET, &emc->dmcr); - writeb(0, JZ4740_EMC_SDMR0 | sdmode); - - /* Set back to basic DMCR value */ - writel(dmcr | EMC_DMCR_RFSH | EMC_DMCR_MRSET, &emc->dmcr); -- -- /* everything is ok now */ - } - - DECLARE_GLOBAL_DATA_PTR; -@@ -232,9 +213,10 @@ void rtc_init(void) - phys_size_t initdram(int board_type) - { - struct jz4740_emc *emc = (struct jz4740_emc *)JZ4740_EMC_BASE; -- u32 dmcr; -- u32 rows, cols, dw, banks; -- ulong size; -+ -+ unsigned int dmcr; -+ unsigned int rows, cols, dw, banks; -+ unsigned long size; - - dmcr = readl(&emc->dmcr); - rows = 11 + ((dmcr & EMC_DMCR_RA_MASK) >> EMC_DMCR_RA_BIT); -diff --git a/arch/mips/cpu/xburst/spl/Makefile b/arch/mips/cpu/xburst/spl/Makefile -new file mode 100644 -index 0000000..f45e8c8 ---- /dev/null -+++ b/arch/mips/cpu/xburst/spl/Makefile -@@ -0,0 +1,47 @@ -+# -+# Copyright (C) 2011 Xiangfu Liu <xiangfu@openmobilefree.net> -+# -+# See file CREDITS for list of people who contributed to this -+# project. -+# -+# This program is free software; you can redistribute it and/or -+# modify it under the terms of the GNU General Public License as -+# published by the Free Software Foundation; either version 2 of -+# the License, or (at your option) any later version. -+# -+# This program is distributed in the hope that it will be useful, -+# but WITHOUT ANY WARRANTY; without even the implied warranty of -+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -+# GNU General Public License for more details. -+# -+# You should have received a copy of the GNU General Public License -+# along with this program; if not, write to the Free Software -+# Foundation, Inc., 59 Temple Place, Suite 330, Boston, -+# MA 02111-1307 USA -+# -+ -+include $(TOPDIR)/config.mk -+ -+LIB = $(obj)lib$(CPU).o -+ -+START = start.o -+SOBJS-y = -+COBJS-y = -+ -+SRCS := $(START:.o=.S) $(SOBJS-y:.o=.S) $(COBJS-y:.o=.c) -+OBJS := $(addprefix $(obj),$(SOBJS-y) $(COBJS-y)) -+START := $(addprefix $(obj),$(START)) -+ -+all: $(obj).depend $(START) $(LIB) -+ -+$(LIB): $(OBJS) -+ $(call cmd_link_o_target, $(OBJS)) -+ -+######################################################################### -+ -+# defines $(obj).depend target -+include $(SRCTREE)/rules.mk -+ -+sinclude $(obj).depend -+ -+######################################################################### -diff --git a/arch/mips/cpu/xburst/spl/start.S b/arch/mips/cpu/xburst/spl/start.S -new file mode 100644 -index 0000000..e31c4c8 ---- /dev/null -+++ b/arch/mips/cpu/xburst/spl/start.S -@@ -0,0 +1,63 @@ -+/* -+ * Copyright (c) 2010 Xiangfu Liu <xiangfu@openmobilefree.net> -+ * -+ * See file CREDITS for list of people who contributed to this -+ * project. -+ * -+ * This program is free software; you can redistribute it and/or -+ * modify it under the terms of the GNU General Public License as -+ * published by the Free Software Foundation; either version 3 of -+ * the License, or (at your option) any later version. -+ * -+ * This program is distributed in the hope that it will be useful, -+ * but WITHOUT ANY WARRANTY; without even the implied warranty of -+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -+ * GNU General Public License for more details. -+ * -+ * You should have received a copy of the GNU General Public License -+ * along with this program; if not, write to the Free Software -+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, -+ * MA 02111-1307 USA -+ */ -+ -+#include <config.h> -+#include <version.h> -+#include <asm/regdef.h> -+#include <asm/mipsregs.h> -+#include <asm/addrspace.h> -+#include <asm/cacheops.h> -+ -+#include <asm/jz4740.h> -+ -+ .set noreorder -+ -+ .globl _start -+ .text -+_start: -+ .word JZ4740_NANDBOOT_CFG /* fetched during NAND Boot */ -+reset: -+ /* -+ * STATUS register -+ * CU0=UM=EXL=IE=0, BEV=ERL=1, IP2~7=1 -+ */ -+ li t0, 0x0040FC04 -+ mtc0 t0, CP0_STATUS -+ /* -+ * CAUSE register -+ * IV=1, use the specical interrupt vector (0x200) -+ */ -+ li t1, 0x00800000 -+ mtc0 t1, CP0_CAUSE -+ -+ bal 1f -+ nop -+ .word _GLOBAL_OFFSET_TABLE_ -+1: -+ move gp, ra -+ lw t1, 0(ra) -+ move gp, t1 -+ -+ la sp, 0x80004000 -+ la t9, nand_spl_boot -+ j t9 -+ nop -diff --git a/board/qi/qi_lb60/Makefile b/board/qi/qi_lb60/Makefile -index 5dae11b..e399246 100644 ---- a/board/qi/qi_lb60/Makefile -+++ b/board/qi/qi_lb60/Makefile -@@ -22,7 +22,11 @@ include $(TOPDIR)/config.mk - - LIB = $(obj)lib$(BOARD).o - -+ifeq ($(CONFIG_SPL_BUILD),y) -+COBJS := $(BOARD)-spl.o -+else - COBJS := $(BOARD).o -+endif - - SRCS := $(SOBJS:.o=.S) $(COBJS:.o=.c) - OBJS := $(addprefix $(obj),$(SOBJS) $(COBJS)) -diff --git a/board/qi/qi_lb60/qi_lb60-spl.c b/board/qi/qi_lb60/qi_lb60-spl.c -new file mode 100644 -index 0000000..3fe3fa3 ---- /dev/null -+++ b/board/qi/qi_lb60/qi_lb60-spl.c -@@ -0,0 +1,30 @@ -+/* -+ * Authors: Xiangfu Liu <xiangfu@openmobilefree.cc> -+ * -+ * This program is free software; you can redistribute it and/or -+ * modify it under the terms of the GNU General Public License -+ * as published by the Free Software Foundation; either version -+ * 3 of the License, or (at your option) any later version. -+ */ -+ -+#include <common.h> -+#include <nand.h> -+#include <asm/io.h> -+#include <asm/jz4740.h> -+ -+void nand_spl_boot(void) -+{ -+ __gpio_as_sdram_16bit_4720(); -+ __gpio_as_uart0(); -+ __gpio_jtag_to_uart0(); -+ -+ serial_init(); -+ -+ pll_init(); -+ sdram_init(); -+ -+ nand_init(); -+ -+ puts("\nQi LB60 SPL: Starting U-Boot ...\n"); -+ nand_boot(); -+} -diff --git a/board/qi/qi_lb60/qi_lb60.c b/board/qi/qi_lb60/qi_lb60.c -index d975209..3bd4e2f 100644 ---- a/board/qi/qi_lb60/qi_lb60.c -+++ b/board/qi/qi_lb60/qi_lb60.c -@@ -1,5 +1,5 @@ - /* -- * Authors: Xiangfu Liu <xiangfu@sharism.cc> -+ * Authors: Xiangfu Liu <xiangfu@openmobilefree.net> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License -@@ -97,8 +97,10 @@ int board_early_init_f(void) - /* U-Boot common routines */ - int checkboard(void) - { -- printf("Board: Qi LB60 (Ingenic XBurst Jz4740 SoC, Speed %ld MHz)\n", -- gd->cpu_clk / 1000000); -+ printf("Board: Qi LB60 (Ingenic XBurst Jz4740 SoC)\n"); -+ printf(" CPU: %ld\n", gd->cpu_clk); -+ printf(" MEM: %ld\n", gd->mem_clk); -+ printf(" DEV: %ld\n", gd->dev_clk); - - return 0; - } -diff --git a/board/qi/qi_lb60/u-boot-spl.lds b/board/qi/qi_lb60/u-boot-spl.lds -new file mode 100644 -index 0000000..930537f ---- /dev/null -+++ b/board/qi/qi_lb60/u-boot-spl.lds -@@ -0,0 +1,61 @@ -+/* -+ * (C) Copyright 2012 Xiangfu Liu <xiangfu@openmobilefree.net> -+ * -+ * This program is free software; you can redistribute it and/or -+ * modify it under the terms of the GNU General Public License as -+ * published by the Free Software Foundation; either version 2 of -+ * the License, or (at your option) any later version. -+ * -+ * This program is distributed in the hope that it will be useful, -+ * but WITHOUT ANY WARRANTY; without even the implied warranty of -+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -+ * GNU General Public License for more details. -+ * -+ * You should have received a copy of the GNU General Public License -+ * along with this program; if not, write to the Free Software -+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, -+ * MA 02111-1307 USA -+ */ -+ -+OUTPUT_FORMAT("elf32-tradlittlemips", "elf32-tradlittlemips", "elf32-tradlittlemips") -+ -+OUTPUT_ARCH(mips) -+ENTRY(_start) -+SECTIONS -+{ -+ . = 0x80000000; -+ . = ALIGN(4); -+ .text : -+ { -+ *(.text) -+ } -+ -+ . = ALIGN(4); -+ .rodata : { *(SORT_BY_ALIGNMENT(SORT_BY_NAME(.rodata*))) } -+ -+ . = ALIGN(4); -+ .data : { *(.data) } -+ -+ . = ALIGN(4); -+ .sdata : { *(.sdata) } -+ -+ _gp = ALIGN(16); -+ -+ __got_start = .; -+ .got : { *(.got) } -+ __got_end = .; -+ -+ . = .; -+ __u_boot_cmd_start = .; -+ .u_boot_cmd : { *(.u_boot_cmd) } -+ __u_boot_cmd_end = .; -+ -+ uboot_end_data = .; -+ num_got_entries = (__got_end - __got_start) >> 2; -+ -+ . = ALIGN(4); -+ .sbss : { *(.sbss) } -+ .bss : { *(.bss) } -+ uboot_end = .; -+} -+ASSERT(uboot_end <= 0x80002000, "NAND bootstrap too big"); -diff --git a/drivers/mtd/nand/jz4740_nand.c b/drivers/mtd/nand/jz4740_nand.c -index 3ec34f3..24a4921 100644 ---- a/drivers/mtd/nand/jz4740_nand.c -+++ b/drivers/mtd/nand/jz4740_nand.c -@@ -15,6 +15,9 @@ - #include <asm/io.h> - #include <asm/jz4740.h> - -+#ifdef CONFIG_SPL_BUILD -+#define printf(s) puts(s) -+#endif - #define JZ_NAND_DATA_ADDR ((void __iomem *)0xB8000000) - #define JZ_NAND_CMD_ADDR (JZ_NAND_DATA_ADDR + 0x8000) - #define JZ_NAND_ADDR_ADDR (JZ_NAND_DATA_ADDR + 0x10000) -@@ -176,7 +179,7 @@ static int jz_nand_rs_correct_data(struct mtd_info *mtd, u_char *dat, - for (k = 0; k < 9; k++) - writeb(read_ecc[k], &emc->nfpar[k]); - } -- /* Set PRDY */ -+ - writel(readl(&emc->nfecr) | EMC_NFECR_PRDY, &emc->nfecr); - - /* Wait for completion */ -@@ -184,7 +187,7 @@ static int jz_nand_rs_correct_data(struct mtd_info *mtd, u_char *dat, - status = readl(&emc->nfints); - } while (!(status & EMC_NFINTS_DECF)); - -- /* disable ecc */ -+ /* Disable ECC */ - writel(readl(&emc->nfecr) & ~EMC_NFECR_ECCE, &emc->nfecr); - - /* Check decoding */ -@@ -192,7 +195,7 @@ static int jz_nand_rs_correct_data(struct mtd_info *mtd, u_char *dat, - return 0; - - if (status & EMC_NFINTS_UNCOR) { -- printf("uncorrectable ecc\n"); -+ printf("JZ4740 uncorrectable ECC\n"); - return -1; - } - -@@ -230,6 +233,32 @@ static int jz_nand_rs_correct_data(struct mtd_info *mtd, u_char *dat, - return errcnt; - } - -+#ifdef CONFIG_SPL_BUILD -+static void jz_nand_read_buf(struct mtd_info *mtd, uint8_t *buf, int len) -+{ -+ int i; -+ struct nand_chip *this = mtd->priv; -+ -+#if (JZ4740_NANDBOOT_CFG == JZ4740_NANDBOOT_B16R3) || \ -+ (JZ4740_NANDBOOT_CFG == JZ4740_NANDBOOT_B16R2) -+ for (i = 0; i < len; i += 2) -+ buf[i] = readw(this->IO_ADDR_R); -+#elif (JZ4740_NANDBOOT_CFG == JZ4740_NANDBOOT_B8R3) || \ -+ (JZ4740_NANDBOOT_CFG == JZ4740_NANDBOOT_B8R2) -+ for (i = 0; i < len; i++) -+ buf[i] = readb(this->IO_ADDR_R); -+#else -+ #error JZ4740_NANDBOOT_CFG not defined or wrong -+#endif -+} -+ -+static uint8_t jz_nand_read_byte(struct mtd_info *mtd) -+{ -+ struct nand_chip *this = mtd->priv; -+ return readb(this->IO_ADDR_R); -+} -+#endif -+ - /* - * Main initialization routine - */ -@@ -254,6 +283,10 @@ int board_nand_init(struct nand_chip *nand) - nand->ecc.size = CONFIG_SYS_NAND_ECCSIZE; - nand->ecc.bytes = CONFIG_SYS_NAND_ECCBYTES; - nand->ecc.layout = &qi_lb60_ecclayout_2gb; -+#ifdef CONFIG_SPL_BUILD -+ nand->read_byte = jz_nand_read_byte; -+ nand->read_buf = jz_nand_read_buf; -+#endif - nand->chip_delay = 50; - nand->options = NAND_USE_FLASH_BBT; - -diff --git a/include/configs/qi_lb60.h b/include/configs/qi_lb60.h -index 4bb5bbc..7bff444 100644 ---- a/include/configs/qi_lb60.h -+++ b/include/configs/qi_lb60.h -@@ -1,5 +1,5 @@ - /* -- * Authors: Xiangfu Liu <xiangfu.z@gmail.com> -+ * Authors: Xiangfu Liu <xiangfu@openmobilefree.net> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License -@@ -14,7 +14,6 @@ - #define CONFIG_SYS_LITTLE_ENDIAN - #define CONFIG_JZSOC /* Jz SoC */ - #define CONFIG_JZ4740 /* Jz4740 SoC */ --#define CONFIG_NAND_JZ4740 - - #define CONFIG_SYS_CPU_SPEED 336000000 /* CPU clock: 336 MHz */ - #define CONFIG_SYS_EXTAL 12000000 /* EXTAL freq: 12 MHz */ -@@ -24,24 +23,43 @@ - #define CONFIG_SYS_UART_BASE JZ4740_UART0_BASE /* Base of the UART channel */ - #define CONFIG_BAUDRATE 57600 - -+#define CONFIG_BOOTP_MASK (CONFIG_BOOTP_DEFAUL) -+#define CONFIG_BOOTDELAY 0 -+#define CONFIG_BOOTARGS "mem=32M console=tty0 console=ttyS0,57600n8 ubi.mtd=2 rootfstype=ubifs root=ubi0:rootfs rw rootwait" -+#define CONFIG_BOOTCOMMAND "nand read 0x80600000 0x400000 0x280000;bootm" -+ -+/* -+ * Miscellaneous configurable options -+ */ -+#define CONFIG_SYS_SDRAM_BASE 0x80000000 /* Cached addr */ -+#define CONFIG_SYS_INIT_SP_OFFSET 0x400000 -+#define CONFIG_SYS_LOAD_ADDR 0x80600000 -+#define CONFIG_SYS_MEMTEST_START 0x80100000 -+#define CONFIG_SYS_MEMTEST_END 0x80A00000 -+#define CONFIG_SYS_TEXT_BASE 0x80100000 -+#define CONFIG_SYS_MONITOR_BASE CONFIG_SYS_TEXT_BASE -+ -+#define CONFIG_SYS_MALLOC_LEN (4 * 1024 * 1024) -+#define CONFIG_SYS_BOOTPARAMS_LEN (128 * 1024) -+ -+#define CONFIG_SYS_CBSIZE 256 /* Console I/O Buffer Size */ -+#define CONFIG_SYS_PBSIZE (CONFIG_SYS_CBSIZE + sizeof(CONFIG_SYS_PROMPT) + 16) -+ -+#define CONFIG_SYS_LONGHELP -+#define CONFIG_SYS_MAXARGS 16 -+#define CONFIG_SYS_PROMPT "NanoNote# " -+ - #define CONFIG_SKIP_LOWLEVEL_INIT - #define CONFIG_BOARD_EARLY_INIT_F - #define CONFIG_SYS_NO_FLASH - #define CONFIG_SYS_FLASH_BASE 0 /* init flash_base as 0 */ --#define CONFIG_ENV_OVERWRITE -- --#define CONFIG_BOOTP_MASK (CONFIG_BOOTP_DEFAUL) --#define CONFIG_BOOTDELAY 0 --#define CONFIG_BOOTARGS "mem=32M console=tty0 console=ttyS0,57600n8 ubi.mtd=2 rootfstype=ubifs root=ubi0:rootfs rw rootwait" --#define CONFIG_BOOTCOMMAND "nand read 0x80600000 0x400000 0x200000;bootm" - - /* -- * Command line configuration. -+ * Command line configuration - */ - #define CONFIG_CMD_BOOTD /* bootd */ - #define CONFIG_CMD_CONSOLE /* coninfo */ - #define CONFIG_CMD_ECHO /* echo arguments */ -- - #define CONFIG_CMD_LOADB /* loadb */ - #define CONFIG_CMD_LOADS /* loads */ - #define CONFIG_CMD_MEMORY /* md mm nm mw cp cmp crc base loop mtest */ -@@ -58,45 +76,16 @@ - #define CONFIG_LOADS_ECHO 1 /* echo on for serial download */ - - /* -- * Miscellaneous configurable options -- */ --#define CONFIG_SYS_MAXARGS 16 --#define CONFIG_SYS_LONGHELP --#define CONFIG_SYS_PROMPT "NanoNote# " --#define CONFIG_SYS_CBSIZE 256 /* Console I/O Buffer Size */ --#define CONFIG_SYS_PBSIZE (CONFIG_SYS_CBSIZE + sizeof(CONFIG_SYS_PROMPT) + 16) -- --#define CONFIG_SYS_MALLOC_LEN (4 * 1024 * 1024) --#define CONFIG_SYS_BOOTPARAMS_LEN (128 * 1024) -- --#define CONFIG_SYS_SDRAM_BASE 0x80000000 /* Cached addr */ --#define CONFIG_SYS_INIT_SP_OFFSET 0x400000 --#define CONFIG_SYS_LOAD_ADDR 0x80600000 --#define CONFIG_SYS_MEMTEST_START 0x80100000 --#define CONFIG_SYS_MEMTEST_END 0x80800000 -- --/* -- * Environment -+ * NAND driver configuration - */ --#define CONFIG_ENV_IS_IN_NAND /* use NAND for environment vars */ -- --#define CONFIG_SYS_NAND_5_ADDR_CYCLE --/* -- * if board nand flash is 1GB, set to 1 -- * if board nand flash is 2GB, set to 2 -- * for change the PAGE_SIZE and BLOCK_SIZE -- * will delete when there is no 1GB flash -- */ --#define NANONOTE_NAND_SIZE 2 -- --#define CONFIG_SYS_NAND_PAGE_SIZE (2048 * NANONOTE_NAND_SIZE) --#define CONFIG_SYS_NAND_BLOCK_SIZE (256 * NANONOTE_NAND_SIZE << 10) --/* nand bad block was marked at this page in a block, start from 0 */ -+#define CONFIG_NAND_JZ4740 -+#define CONFIG_SYS_NAND_PAGE_SIZE 4096 -+#define CONFIG_SYS_NAND_BLOCK_SIZE (512 << 10) -+/* NAND bad block was marked at this page in a block, start from 0 */ - #define CONFIG_SYS_NAND_BADBLOCK_PAGE 127 - #define CONFIG_SYS_NAND_PAGE_COUNT 128 - #define CONFIG_SYS_NAND_BAD_BLOCK_POS 0 --/* ECC offset position in oob area, default value is 6 if it isn't defined */ --#define CONFIG_SYS_NAND_ECC_POS (6 * NANONOTE_NAND_SIZE) -+#define CONFIG_SYS_NAND_ECC_POS 12 - #define CONFIG_SYS_NAND_ECCSIZE 512 - #define CONFIG_SYS_NAND_ECCBYTES 9 - #define CONFIG_SYS_NAND_ECCPOS \ -@@ -115,10 +104,9 @@ - #define CONFIG_SYS_ONENAND_BASE CONFIG_SYS_NAND_BASE - #define CONFIG_SYS_MAX_NAND_DEVICE 1 - #define CONFIG_SYS_NAND_SELECT_DEVICE 1 /* nand driver supports mutipl.*/ --#define CONFIG_NAND_SPL_TEXT_BASE 0x80000000 - - /* -- * IPL (Initial Program Loader, integrated inside CPU) -+ * IPL (Initial Program Loader, integrated inside Ingenic Xburst JZ4740 CPU) - * Will load first 8k from NAND (SPL) into cache and execute it from there. - * - * SPL (Secondary Program Loader) -@@ -130,77 +118,88 @@ - * NUB (NAND U-Boot) - * This NAND U-Boot (NUB) is a special U-Boot version which can be started - * from RAM. Therefore it mustn't (re-)configure the SDRAM controller. -- * - */ -+ -+/* -+ * NAND SPL configuration -+ */ -+#define CONFIG_SPL -+#define CONFIG_SPL_LIBGENERIC_SUPPORT -+#define CONFIG_SPL_LIBCOMMON_SUPPORT -+#define CONFIG_SPL_NAND_LOAD -+#define CONFIG_SPL_NAND_SIMPLE -+#define CONFIG_SPL_NAND_SUPPORT -+#define CONFIG_SPL_TEXT_BASE 0x80000000 -+#define CONFIG_SPL_START_S_PATH "arch/mips/cpu/xburst/spl" -+ -+#define CONFIG_SYS_NAND_5_ADDR_CYCLE -+#define CONFIG_SYS_NAND_HW_ECC_OOBFIRST -+#define JZ4740_NANDBOOT_CFG JZ4740_NANDBOOT_B8R3 -+ - #define CONFIG_SYS_NAND_U_BOOT_DST 0x80100000 /* Load NUB to this addr */ - #define CONFIG_SYS_NAND_U_BOOT_START CONFIG_SYS_NAND_U_BOOT_DST --/* Start NUB from this addr*/ -+ /* Start NUB from this addr */ -+#define CONFIG_SYS_NAND_U_BOOT_OFFS (32 << 10) /* Offset of NUB */ -+#define CONFIG_SYS_NAND_U_BOOT_SIZE (256 << 10) /* Size of NUB */ - - /* -- * Define the partitioning of the NAND chip (only RAM U-Boot is needed here) -+ * Environment configuration - */ --#define CONFIG_SYS_NAND_U_BOOT_OFFS (256 << 10) /* Offset to RAM U-Boot image */ --#define CONFIG_SYS_NAND_U_BOOT_SIZE (512 << 10) /* Size of RAM U-Boot image */ -- -+#define CONFIG_ENV_OVERWRITE -+#define CONFIG_ENV_IS_IN_NAND - #define CONFIG_ENV_SIZE (4 << 10) - #define CONFIG_ENV_OFFSET \ - (CONFIG_SYS_NAND_BLOCK_SIZE + CONFIG_SYS_NAND_U_BOOT_SIZE) - #define CONFIG_ENV_OFFSET_REDUND \ - (CONFIG_ENV_OFFSET + CONFIG_SYS_NAND_BLOCK_SIZE) - --#define CONFIG_SYS_TEXT_BASE 0x80100000 --#define CONFIG_SYS_MONITOR_BASE CONFIG_SYS_TEXT_BASE -- - /* -- * SDRAM Info. -+ * CPU cache configuration - */ --#define CONFIG_NR_DRAM_BANKS 1 -+#define CONFIG_SYS_DCACHE_SIZE 16384 -+#define CONFIG_SYS_ICACHE_SIZE 16384 -+#define CONFIG_SYS_CACHELINE_SIZE 32 - - /* -- * Cache Configuration -+ * SDRAM configuration - */ --#define CONFIG_SYS_DCACHE_SIZE 16384 --#define CONFIG_SYS_ICACHE_SIZE 16384 --#define CONFIG_SYS_CACHELINE_SIZE 32 -+#define CONFIG_NR_DRAM_BANKS 1 -+ -+#define SDRAM_BW16 1 /* Data bus width: 0-32bit, 1-16bit */ -+#define SDRAM_BANK4 1 /* Banks each chip: 0-2bank, 1-4bank */ -+#define SDRAM_ROW 13 /* Row address: 11 to 13 */ -+#define SDRAM_COL 9 /* Column address: 8 to 12 */ -+#define SDRAM_CASL 2 /* CAS latency: 2 or 3 */ -+#define SDRAM_TRAS 45 /* RAS# Active Time */ -+#define SDRAM_RCD 20 /* RAS# to CAS# Delay */ -+#define SDRAM_TPC 20 /* RAS# Precharge Time */ -+#define SDRAM_TRWL 7 /* Write Latency Time */ -+#define SDRAM_TREF 15625 /* Refresh period: 8192 cycles/64ms */ - - /* -- * GPIO definition -+ * GPIO configuration - */ --#define GPIO_LCD_CS (2 * 32 + 21) --#define GPIO_AMP_EN (3 * 32 + 4) -+#define GPIO_LCD_CS (2 * 32 + 21) -+#define GPIO_AMP_EN (3 * 32 + 4) - --#define GPIO_SDPW_EN (3 * 32 + 2) --#define GPIO_SD_DETECT (3 * 32 + 0) -+#define GPIO_SDPW_EN (3 * 32 + 2) -+#define GPIO_SD_DETECT (3 * 32 + 0) - --#define GPIO_BUZZ_PWM (3 * 32 + 27) --#define GPIO_USB_DETECT (3 * 32 + 28) -+#define GPIO_BUZZ_PWM (3 * 32 + 27) -+#define GPIO_USB_DETECT (3 * 32 + 28) - --#define GPIO_AUDIO_POP (1 * 32 + 29) --#define GPIO_COB_TEST (1 * 32 + 30) -+#define GPIO_AUDIO_POP (1 * 32 + 29) -+#define GPIO_COB_TEST (1 * 32 + 30) - - #define GPIO_KEYOUT_BASE (2 * 32 + 10) --#define GPIO_KEYIN_BASE (3 * 32 + 18) --#define GPIO_KEYIN_8 (3 * 32 + 26) -+#define GPIO_KEYIN_BASE (3 * 32 + 18) -+#define GPIO_KEYIN_8 (3 * 32 + 26) - --#define GPIO_SD_CD_N GPIO_SD_DETECT /* SD Card insert detect */ -+#define GPIO_SD_CD_N GPIO_SD_DETECT /* SD Card insert detect */ - #define GPIO_SD_VCC_EN_N GPIO_SDPW_EN /* SD Card Power Enable */ - - #define SPEN GPIO_LCD_CS /* LCDCS :Serial command enable */ - #define SPDA (2 * 32 + 22) /* LCDSCL:Serial command clock input */ - #define SPCK (2 * 32 + 23) /* LCDSDA:Serial command data input */ - --/* SDRAM paramters */ --#define SDRAM_BW16 1 /* Data bus width: 0-32bit, 1-16bit */ --#define SDRAM_BANK4 1 /* Banks each chip: 0-2bank, 1-4bank */ --#define SDRAM_ROW 13 /* Row address: 11 to 13 */ --#define SDRAM_COL 9 /* Column address: 8 to 12 */ --#define SDRAM_CASL 2 /* CAS latency: 2 or 3 */ -- --/* SDRAM Timings, unit: ns */ --#define SDRAM_TRAS 45 /* RAS# Active Time */ --#define SDRAM_RCD 20 /* RAS# to CAS# Delay */ --#define SDRAM_TPC 20 /* RAS# Precharge Time */ --#define SDRAM_TRWL 7 /* Write Latency Time */ --#define SDRAM_TREF 15625 /* Refresh period: 8192 cycles/64ms */ -- - #endif --- -1.7.9.5 - diff --git a/package/boot/uboot-xburst/patches/0002-qi_lb60-add-software-usbboot-support.patch b/package/boot/uboot-xburst/patches/0002-qi_lb60-add-software-usbboot-support.patch deleted file mode 100644 index feaf297b7c..0000000000 --- a/package/boot/uboot-xburst/patches/0002-qi_lb60-add-software-usbboot-support.patch +++ /dev/null @@ -1,916 +0,0 @@ -From fa51192b912d296b8eec10f7d44c6c17eb1dd368 Mon Sep 17 00:00:00 2001 -From: Xiangfu <xiangfu@openmobilefree.net> -Date: Fri, 12 Oct 2012 09:47:39 +0800 -Subject: [PATCH 2/6] qi_lb60: add software usbboot support - - JZ4740 CPU have a internal ROM have such kind of code, that make - JZ4740 can boot from USB - - usbboot.S can downloads user program from the USB port to internal - SRAM and branches to the internal SRAM to execute the program - -Signed-off-by: Xiangfu <xiangfu@openmobilefree.net> ---- - board/qi/qi_lb60/Makefile | 1 + - board/qi/qi_lb60/qi_lb60-spl.c | 20 + - board/qi/qi_lb60/usbboot.S | 838 ++++++++++++++++++++++++++++++++++++++++ - 3 files changed, 859 insertions(+) - create mode 100644 board/qi/qi_lb60/usbboot.S - -diff --git a/board/qi/qi_lb60/Makefile b/board/qi/qi_lb60/Makefile -index e399246..6dd8c6f 100644 ---- a/board/qi/qi_lb60/Makefile -+++ b/board/qi/qi_lb60/Makefile -@@ -23,6 +23,7 @@ include $(TOPDIR)/config.mk - LIB = $(obj)lib$(BOARD).o - - ifeq ($(CONFIG_SPL_BUILD),y) -+SOBJS := usbboot.o - COBJS := $(BOARD)-spl.o - else - COBJS := $(BOARD).o -diff --git a/board/qi/qi_lb60/qi_lb60-spl.c b/board/qi/qi_lb60/qi_lb60-spl.c -index 3fe3fa3..aea459c 100644 ---- a/board/qi/qi_lb60/qi_lb60-spl.c -+++ b/board/qi/qi_lb60/qi_lb60-spl.c -@@ -12,6 +12,24 @@ - #include <asm/io.h> - #include <asm/jz4740.h> - -+#define KEY_U_OUT (32 * 2 + 16) -+#define KEY_U_IN (32 * 3 + 19) -+ -+extern void usb_boot(void); -+ -+static void check_usb_boot(void) -+{ -+ __gpio_as_input(KEY_U_IN); -+ __gpio_enable_pull(KEY_U_IN); -+ __gpio_as_output(KEY_U_OUT); -+ __gpio_clear_pin(KEY_U_OUT); -+ -+ if (!__gpio_get_pin(KEY_U_IN)) { -+ puts("[U] pressed, goto USBBOOT mode\n"); -+ usb_boot(); -+ } -+} -+ - void nand_spl_boot(void) - { - __gpio_as_sdram_16bit_4720(); -@@ -23,6 +41,8 @@ void nand_spl_boot(void) - pll_init(); - sdram_init(); - -+ check_usb_boot(); -+ - nand_init(); - - puts("\nQi LB60 SPL: Starting U-Boot ...\n"); -diff --git a/board/qi/qi_lb60/usbboot.S b/board/qi/qi_lb60/usbboot.S -new file mode 100644 -index 0000000..c872266 ---- /dev/null -+++ b/board/qi/qi_lb60/usbboot.S -@@ -0,0 +1,838 @@ -+/* -+ * for jz4740 usb boot -+ * -+ * Copyright (c) 2009 Author: <jlwei@ingenic.cn> -+ * -+ * See file CREDITS for list of people who contributed to this -+ * project. -+ * -+ * This program is free software; you can redistribute it and/or -+ * modify it under the terms of the GNU General Public License as -+ * published by the Free Software Foundation; either version 2 of -+ * the License, or (at your option) any later version. -+ * -+ * This program is distributed in the hope that it will be useful, -+ * but WITHOUT ANY WARRANTY; without even the implied warranty of -+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -+ * GNU General Public License for more details. -+ * -+ * You should have received a copy of the GNU General Public License -+ * along with this program; if not, write to the Free Software -+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, -+ * MA 02111-1307 USA -+ */ -+ .set noreorder -+ .globl usb_boot -+ .text -+ -+/* -+ * Both NAND and USB boot load data to D-Cache first, then transfer -+ * data from D-Cache to I-Cache, and jump to execute the code in I-Cache. -+ * So init caches first and then dispatch to a proper boot routine. -+ */ -+ -+.macro load_addr reg addr -+ li \reg, 0x80000000 -+ addiu \reg, \reg, \addr -+ la $2, usbboot_begin -+ subu \reg, \reg, $2 -+.endm -+ -+usb_boot: -+ /* Initialize PLL: set ICLK to 84MHz and HCLK to 42MHz. */ -+ la $9, 0xB0000000 /* CPCCR: Clock Control Register */ -+ la $8, 0x42041110 /* I:S:M:P=1:2:2:2 */ -+ sw $8, 0($9) -+ -+ la $9, 0xB0000010 /* CPPCR: PLL Control Register */ -+ la $8, 0x06000120 /* M=12 N=0 D=0 CLK=12*(M+2)/(N+2) */ -+ sw $8, 0($9) -+ -+ mtc0 $0, $26 /* CP0_ERRCTL, restore WST reset state */ -+ nop -+ -+ mtc0 $0, $16 /* CP0_CONFIG */ -+ nop -+ -+ /* Relocate code to beginning of the ram */ -+ -+ la $2, usbboot_begin -+ la $3, usbboot_end -+ li $4, 0x80000000 -+ -+1: -+ lw $5, 0($2) -+ sw $5, 0($4) -+ addiu $2, $2, 4 -+ bne $2, $3, 1b -+ addiu $4, $4, 4 -+ -+ li $2, 0x80000000 -+ ori $3, $2, 0 -+ addiu $3, $3, usbboot_end -+ la $4, usbboot_begin -+ subu $3, $3, $4 -+ -+ -+2: -+ cache 0x0, 0($2) /* Index_Invalidate_I */ -+ cache 0x1, 0($2) /* Index_Writeback_Inv_D */ -+ addiu $2, $2, 32 -+ subu $4, $3, $2 -+ bgtz $4, 2b -+ nop -+ -+ load_addr $3, usb_boot_return -+ -+ jr $3 -+ -+usbboot_begin: -+ -+init_caches: -+ li $2, 3 /* cacheable for kseg0 access */ -+ mtc0 $2, $16 /* CP0_CONFIG */ -+ nop -+ -+ li $2, 0x20000000 /* enable idx-store-data cache insn */ -+ mtc0 $2, $26 /* CP0_ERRCTL */ -+ -+ ori $2, $28, 0 /* start address */ -+ ori $3, $2, 0x3fe0 /* end address, total 16KB */ -+ mtc0 $0, $28, 0 /* CP0_TAGLO */ -+ mtc0 $0, $28, 1 /* CP0_DATALO */ -+cache_clear_a_line: -+ cache 0x8, 0($2) /* Index_Store_Tag_I */ -+ cache 0x9, 0($2) /* Index_Store_Tag_D */ -+ bne $2, $3, cache_clear_a_line -+ addiu $2, $2, 32 /* increment CACHE_LINE_SIZE */ -+ -+ ori $2, $28, 0 /* start address */ -+ ori $3, $2, 0x3fe0 /* end address, total 16KB */ -+ la $4, 0x1ffff000 /* physical address and 4KB page mask */ -+cache_alloc_a_line: -+ and $5, $2, $4 -+ ori $5, $5, 1 /* V bit of the physical tag */ -+ mtc0 $5, $28, 0 /* CP0_TAGLO */ -+ cache 0x8, 0($2) /* Index_Store_Tag_I */ -+ cache 0x9, 0($2) /* Index_Store_Tag_D */ -+ bne $2, $3, cache_alloc_a_line -+ addiu $2, $2, 32 /* increment CACHE_LINE_SIZE */ -+ -+ nop -+ nop -+ nop -+ /* -+ * Transfer data from dcache to icache, then jump to icache. -+ * Input parameters: -+ * $19: data length in bytes -+ * $20: jump target address -+ */ -+xfer_d2i: -+ -+ ori $8, $20, 0 -+ addu $9, $8, $19 /* total 16KB */ -+ -+1: -+ cache 0x0, 0($8) /* Index_Invalidate_I */ -+ cache 0x1, 0($8) /* Index_Writeback_Inv_D */ -+ bne $8, $9, 1b -+ addiu $8, $8, 32 -+ -+ /* flush write-buffer */ -+ sync -+ -+ /* Invalidate BTB */ -+ mfc0 $8, $16, 7 /* CP0_CONFIG */ -+ nop -+ ori $8, 2 -+ mtc0 $8, $16, 7 -+ nop -+ -+ /* Overwrite config to disable ram initalisation */ -+ li $2, 0xff -+ sb $2, 20($20) -+ -+ jalr $20 -+ nop -+ -+icache_return: -+ /* User code can return to here after executing itself in -+ icache, by jumping to $31. */ -+ b usb_boot_return -+ nop -+ -+ -+usb_boot_return: -+ /* Enable the USB PHY */ -+ la $9, 0xB0000024 /* CPM_SCR */ -+ lw $8, 0($9) -+ ori $8, 0x40 /* USBPHY_ENABLE */ -+ sw $8, 0($9) -+ -+ /* Initialize USB registers */ -+ la $27, 0xb3040000 /* USB registers base address */ -+ -+ sb $0, 0x0b($27) /* INTRUSBE: disable common USB interrupts */ -+ sh $0, 0x06($27) /* INTRINE: disable EPIN interrutps */ -+ sh $0, 0x08($27) /* INTROUTE: disable EPOUT interrutps */ -+ -+ li $9, 0x61 -+ sb $9, 0x01($27) /* POWER: HSENAB | SUSPENDM | SOFTCONN */ -+ -+ /* Initialize USB states */ -+ li $22, 0 /* set EP0 to IDLE state */ -+ li $23, 1 /* no data stage */ -+ -+ /* Main loop of polling the usb commands */ -+usb_command_loop: -+ lbu $9, 0x0a($27) /* read INTRUSB */ -+ andi $9, 0x04 /* check USB_INTR_RESET */ -+ beqz $9, check_intr_ep0in -+ nop -+ -+ /* 1. Handle USB reset interrupt */ -+handle_reset_intr: -+ lbu $9, 0x01($27) /* read POWER */ -+ andi $9, 0x10 /* test HS_MODE */ -+ bnez $9, _usb_set_maxpktsize -+ li $9, 512 /* max packet size of HS mode */ -+ li $9, 64 /* max packet size of FS mode */ -+ -+_usb_set_maxpktsize: -+ li $8, 1 -+ sb $8, 0x0e($27) /* set INDEX 1 */ -+ -+ sh $9, 0x10($27) /* INMAXP */ -+ sb $0, 0x13($27) /* INCSRH */ -+ sh $9, 0x14($27) /* OUTMAXP */ -+ sb $0, 0x17($27) /* OUTCSRH */ -+ -+_usb_flush_fifo: -+ li $8, 0x48 /* INCSR_CDT && INCSR_FF */ -+ sb $8, 0x12($27) /* INCSR */ -+ li $8, 0x90 /* OUTCSR_CDT && OUTCSR_FF */ -+ sb $8, 0x16($27) /* OUTCSR */ -+ -+ li $22, 0 /* set EP0 to IDLE state */ -+ li $23, 1 /* no data stage */ -+ -+ /* 2. Check and handle EP0 interrupt */ -+check_intr_ep0in: -+ lhu $10, 0x02($27) /* read INTRIN */ -+ andi $9, $10, 0x1 /* check EP0 interrupt */ -+ beqz $9, check_intr_ep1in -+ nop -+ -+handle_ep0_intr: -+ sb $0, 0x0e($27) /* set INDEX 0 */ -+ lbu $11, 0x12($27) /* read CSR0 */ -+ -+ andi $9, $11, 0x04 /* check SENTSTALL */ -+ beqz $9, _ep0_setupend -+ nop -+ -+_ep0_sentstall: -+ andi $9, $11, 0xdb -+ sb $9, 0x12($27) /* clear SENDSTALL and SENTSTALL */ -+ li $22, 0 /* set EP0 to IDLE state */ -+ -+_ep0_setupend: -+ andi $9, $11, 0x10 /* check SETUPEND */ -+ beqz $9, ep0_idle_state -+ nop -+ -+ ori $9, $11, 0x80 -+ sb $9, 0x12($27) /* set SVDSETUPEND */ -+ li $22, 0 /* set EP0 to IDLE state */ -+ -+ep0_idle_state: -+ bnez $22, ep0_tx_state -+ nop -+ -+ /* 2.1 Handle EP0 IDLE state interrupt */ -+ andi $9, $11, 0x01 /* check OUTPKTRDY */ -+ beqz $9, check_intr_ep1in -+ nop -+ -+ /* Read 8-bytes setup packet from the FIFO */ -+ lw $25, 0x20($27) /* first word of setup packet */ -+ lw $26, 0x20($27) /* second word of setup packet */ -+ -+ andi $9, $25, 0x60 /* bRequestType & USB_TYPE_MASK */ -+ beqz $9, _ep0_std_req -+ nop -+ -+ /* 2.1.1 Vendor-specific setup request */ -+_ep0_vend_req: -+ li $22, 0 /* set EP0 to IDLE state */ -+ li $23, 1 /* NoData = 1 */ -+ -+ andi $9, $25, 0xff00 /* check bRequest */ -+ srl $9, $9, 8 -+ beqz $9, __ep0_get_cpu_info -+ sub $8, $9, 0x1 -+ beqz $8, __ep0_set_data_address -+ sub $8, $9, 0x2 -+ beqz $8, __ep0_set_data_length -+ sub $8, $9, 0x3 -+ beqz $8, __ep0_flush_caches -+ sub $8, $9, 0x4 -+ beqz $8, __ep0_prog_start1 -+ sub $8, $9, 0x5 -+ beqz $8, __ep0_prog_start2 -+ nop -+ b _ep0_idle_state_fini /* invalid request */ -+ nop -+ -+__ep0_get_cpu_info: -+ load_addr $20, cpu_info_data /* data pointer to transfer */ -+ li $21, 8 /* bytes left to transfer */ -+ li $22, 1 /* set EP0 to TX state */ -+ li $23, 0 /* NoData = 0 */ -+ -+ b _ep0_idle_state_fini -+ nop -+ -+__ep0_set_data_address: -+ li $9, 0xffff0000 -+ and $9, $25, $9 -+ andi $8, $26, 0xffff -+ or $20, $9, $8 /* data address of next transfer */ -+ -+ b _ep0_idle_state_fini -+ nop -+ -+__ep0_set_data_length: -+ li $9, 0xffff0000 -+ and $9, $25, $9 -+ andi $8, $26, 0xffff -+ or $21, $9, $8 /* data length of next transfer */ -+ -+ li $9, 0x48 /* SVDOUTPKTRDY and DATAEND */ -+ sb $9, 0x12($27) /* CSR0 */ -+ -+ /* We must write packet to FIFO before EP1-IN interrupt here. */ -+ b handle_epin1_intr -+ nop -+ -+__ep0_flush_caches: -+ /* Flush dcache and invalidate icache. */ -+ li $8, 0x80000000 -+ addi $9, $8, 0x3fe0 /* total 16KB */ -+ -+1: -+ cache 0x0, 0($8) /* Index_Invalidate_I */ -+ cache 0x1, 0($8) /* Index_Writeback_Inv_D */ -+ bne $8, $9, 1b -+ addiu $8, $8, 32 -+ -+ /* flush write-buffer */ -+ sync -+ -+ /* Invalidate BTB */ -+ mfc0 $8, $16, 7 /* CP0_CONFIG */ -+ nop -+ ori $8, 2 -+ mtc0 $8, $16, 7 -+ nop -+ -+ b _ep0_idle_state_fini -+ nop -+ -+__ep0_prog_start1: -+ li $9, 0x48 /* SVDOUTPKTRDY and DATAEND */ -+ sb $9, 0x12($27) /* CSR0 */ -+ -+ li $9, 0xffff0000 -+ and $9, $25, $9 -+ andi $8, $26, 0xffff -+ or $20, $9, $8 /* target address */ -+ -+ b xfer_d2i -+ li $19, 0x2000 /* 16KB data length */ -+ -+__ep0_prog_start2: -+ li $9, 0x48 /* SVDOUTPKTRDY and DATAEND */ -+ sb $9, 0x12($27) /* CSR0 */ -+ -+ li $9, 0xffff0000 -+ and $9, $25, $9 -+ andi $8, $26, 0xffff -+ or $20, $9, $8 /* target address */ -+ -+ jalr $20 /* jump, and place the return address in $31 */ -+ nop -+ -+__ep0_prog_start2_return: -+/* User code can return to here after executing itself, by jumping to $31 */ -+ b usb_boot_return -+ nop -+ -+ /* 2.1.2 Standard setup request */ -+_ep0_std_req: -+ andi $12, $25, 0xff00 /* check bRequest */ -+ srl $12, $12, 8 -+ sub $9, $12, 0x05 /* check USB_REQ_SET_ADDRESS */ -+ bnez $9, __ep0_req_set_config -+ nop -+ -+ /* Handle USB_REQ_SET_ADDRESS */ -+__ep0_req_set_addr: -+ srl $9, $25, 16 /* get wValue */ -+ sb $9, 0x0($27) /* set FADDR */ -+ li $23, 1 /* NoData = 1 */ -+ b _ep0_idle_state_fini -+ nop -+ -+__ep0_req_set_config: -+ sub $9, $12, 0x09 /* check USB_REQ_SET_CONFIGURATION */ -+ bnez $9, __ep0_req_get_desc -+ nop -+ -+ /* Handle USB_REQ_SET_CONFIGURATION */ -+ li $23, 1 /* NoData = 1 */ -+ b _ep0_idle_state_fini -+ nop -+ -+__ep0_req_get_desc: -+ sub $9, $12, 0x06 /* check USB_REQ_GET_DESCRIPTOR */ -+ bnez $9, _ep0_idle_state_fini -+ li $23, 1 /* NoData = 1 */ -+ -+ /* Handle USB_REQ_GET_DESCRIPTOR */ -+ li $23, 0 /* NoData = 0 */ -+ -+ srl $9, $25, 24 /* wValue >> 8 */ -+ sub $8, $9, 0x01 /* check USB_DT_DEVICE */ -+ beqz $8, ___ep0_get_dev_desc -+ srl $21, $26, 16 /* get wLength */ -+ sub $8, $9, 0x02 /* check USB_DT_CONFIG */ -+ beqz $8, ___ep0_get_conf_desc -+ sub $8, $9, 0x03 /* check USB_DT_STRING */ -+ beqz $8, ___ep0_get_string_desc -+ sub $8, $9, 0x06 /* check USB_DT_DEVICE_QUALIFIER */ -+ beqz $8, ___ep0_get_dev_qualifier -+ nop -+ b _ep0_idle_state_fini -+ nop -+ -+___ep0_get_dev_desc: -+ load_addr $20, device_desc /* data pointer */ -+ li $22, 1 /* set EP0 to TX state */ -+ sub $8, $21, 18 -+ blez $8, _ep0_idle_state_fini /* wLength <= 18 */ -+ nop -+ li $21, 18 /* max length of device_desc */ -+ b _ep0_idle_state_fini -+ nop -+ -+___ep0_get_dev_qualifier: -+ load_addr $20, dev_qualifier /* data pointer */ -+ li $22, 1 /* set EP0 to TX state */ -+ sub $8, $21, 10 -+ blez $8, _ep0_idle_state_fini /* wLength <= 10 */ -+ nop -+ li $21, 10 /* max length of dev_qualifier */ -+ b _ep0_idle_state_fini -+ nop -+ -+___ep0_get_conf_desc: -+ load_addr $20, config_desc_fs /* data pointer of FS mode */ -+ lbu $8, 0x01($27) /* read POWER */ -+ andi $8, 0x10 /* test HS_MODE */ -+ beqz $8, ___ep0_get_conf_desc2 -+ nop -+ load_addr $20, config_desc_hs /* data pointer of HS mode */ -+ -+___ep0_get_conf_desc2: -+ li $22, 1 /* set EP0 to TX state */ -+ sub $8, $21, 32 -+ blez $8, _ep0_idle_state_fini /* wLength <= 32 */ -+ nop -+ li $21, 32 /* max length of config_desc */ -+ b _ep0_idle_state_fini -+ nop -+ -+___ep0_get_string_desc: -+ li $22, 1 /* set EP0 to TX state */ -+ -+ srl $9, $25, 16 /* wValue & 0xff */ -+ andi $9, 0xff -+ -+ sub $8, $9, 1 -+ beqz $8, ___ep0_get_string_manufacture -+ sub $8, $9, 2 -+ beqz $8, ___ep0_get_string_product -+ nop -+ -+___ep0_get_string_lang_ids: -+ load_addr $20, string_lang_ids /* data pointer */ -+ b _ep0_idle_state_fini -+ li $21, 4 /* data length */ -+ -+___ep0_get_string_manufacture: -+ load_addr $20, string_manufacture /* data pointer */ -+ b _ep0_idle_state_fini -+ li $21, 16 /* data length */ -+ -+___ep0_get_string_product: -+ load_addr $20, string_product /* data pointer */ -+ b _ep0_idle_state_fini -+ li $21, 46 /* data length */ -+ -+_ep0_idle_state_fini: -+ li $9, 0x40 /* SVDOUTPKTRDY */ -+ beqz $23, _ep0_idle_state_fini2 -+ nop -+ ori $9, $9, 0x08 /* DATAEND */ -+_ep0_idle_state_fini2: -+ sb $9, 0x12($27) /* CSR0 */ -+ beqz $22, check_intr_ep1in -+ nop -+ -+ /* 2.2 Handle EP0 TX state interrupt */ -+ep0_tx_state: -+ sub $9, $22, 1 -+ bnez $9, check_intr_ep1in -+ nop -+ -+ sub $9, $21, 64 /* max packetsize */ -+ blez $9, _ep0_tx_state2 /* data count <= 64 */ -+ ori $19, $21, 0 -+ li $19, 64 -+ -+_ep0_tx_state2: -+ beqz $19, _ep0_tx_state3 /* send ZLP */ -+ ori $18, $19, 0 /* record bytes to be transferred */ -+ sub $21, $21, $19 /* decrement data count */ -+ -+_ep0_fifo_write_loop: -+ lbu $9, 0($20) /* read data */ -+ sb $9, 0x20($27) /* load FIFO */ -+ sub $19, $19, 1 /* decrement counter */ -+ bnez $19, _ep0_fifo_write_loop -+ addi $20, $20, 1 /* increment data pointer */ -+ -+ sub $9, $18, 64 /* max packetsize */ -+ beqz $9, _ep0_tx_state4 -+ nop -+ -+_ep0_tx_state3: -+ /* transferred bytes < max packetsize */ -+ li $9, 0x0a /* set INPKTRDY and DATAEND */ -+ sb $9, 0x12($27) /* CSR0 */ -+ li $22, 0 /* set EP0 to IDLE state */ -+ b check_intr_ep1in -+ nop -+ -+_ep0_tx_state4: -+ /* transferred bytes == max packetsize */ -+ li $9, 0x02 /* set INPKTRDY */ -+ sb $9, 0x12($27) /* CSR0 */ -+ b check_intr_ep1in -+ nop -+ -+ /* 3. Check and handle EP1 BULK-IN interrupt */ -+check_intr_ep1in: -+ andi $9, $10, 0x2 /* check EP1 IN interrupt */ -+ beqz $9, check_intr_ep1out -+ nop -+ -+handle_epin1_intr: -+ li $9, 1 -+ sb $9, 0x0e($27) /* set INDEX 1 */ -+ lbu $9, 0x12($27) /* read INCSR */ -+ -+ andi $8, $9, 0x2 /* check INCSR_FFNOTEMPT */ -+ bnez $8, _epin1_tx_state4 -+ nop -+ -+_epin1_write_fifo: -+ lhu $9, 0x10($27) /* get INMAXP */ -+ sub $8, $21, $9 -+ blez $8, _epin1_tx_state1 /* bytes left <= INMAXP */ -+ ori $19, $21, 0 -+ ori $19, $9, 0 -+ -+_epin1_tx_state1: -+ beqz $19, _epin1_tx_state4 /* No data */ -+ nop -+ -+ sub $21, $21, $19 /* decrement data count */ -+ -+ srl $5, $19, 2 /* # of word */ -+ andi $6, $19, 0x3 /* # of byte */ -+ beqz $5, _epin1_tx_state2 -+ nop -+ -+_epin1_fifo_write_word: -+ lw $9, 0($20) /* read data from source address */ -+ sw $9, 0x24($27) /* write FIFO */ -+ sub $5, $5, 1 /* decrement counter */ -+ bnez $5, _epin1_fifo_write_word -+ addiu $20, $20, 4 /* increment dest address */ -+ -+_epin1_tx_state2: -+ beqz $6, _epin1_tx_state3 -+ nop -+ -+_epin1_fifo_write_byte: -+ lbu $9, 0($20) /* read data from source address */ -+ sb $9, 0x24($27) /* write FIFO */ -+ sub $6, $6, 1 /* decrement counter */ -+ bnez $6, _epin1_fifo_write_byte -+ addiu $20, $20, 1 /* increment dest address */ -+ -+_epin1_tx_state3: -+ li $9, 0x1 -+ sb $9, 0x12($27) /* INCSR, set INPKTRDY */ -+ -+_epin1_tx_state4: -+ /* 4. Check and handle EP1 BULK-OUT interrupt */ -+check_intr_ep1out: -+ lhu $9, 0x04($27) /* read INTROUT */ -+ andi $9, 0x2 -+ beqz $9, check_status_next -+ nop -+ -+handle_epout1_intr: -+ li $9, 1 -+ sb $9, 0x0e($27) /* set INDEX 1 */ -+ -+ lbu $9, 0x16($27) /* read OUTCSR */ -+ andi $9, 0x1 /* check OUTPKTRDY */ -+ beqz $9, check_status_next -+ nop -+ -+_epout1_read_fifo: -+ lhu $19, 0x18($27) /* read OUTCOUNT */ -+ srl $5, $19, 2 /* # of word */ -+ andi $6, $19, 0x3 /* # of byte */ -+ beqz $5, _epout1_rx_state1 -+ nop -+ -+_epout1_fifo_read_word: -+ lw $9, 0x24($27) /* read FIFO */ -+ sw $9, 0($20) /* store to dest address */ -+ sub $5, $5, 1 /* decrement counter */ -+ bnez $5, _epout1_fifo_read_word -+ addiu $20, $20, 4 /* increment dest address */ -+ -+_epout1_rx_state1: -+ beqz $6, _epout1_rx_state2 -+ nop -+ -+_epout1_fifo_read_byte: -+ lbu $9, 0x24($27) /* read FIFO */ -+ sb $9, 0($20) /* store to dest address */ -+ sub $6, $6, 1 /* decrement counter */ -+ bnez $6, _epout1_fifo_read_byte -+ addiu $20, $20, 1 /* increment dest address */ -+ -+_epout1_rx_state2: -+ sb $0, 0x16($27) /* clear OUTPKTRDY */ -+ -+check_status_next: -+ b usb_command_loop -+ nop -+ -+/* Device/Configuration/Interface/Endpoint/String Descriptors */ -+ -+ .align 2 -+device_desc: -+ .byte 0x12 /* bLength */ -+ .byte 0x01 /* bDescriptorType */ -+ .byte 0x00 /* bcdUSB */ -+ .byte 0x02 /* bcdUSB */ -+ .byte 0x00 /* bDeviceClass */ -+ .byte 0x00 /* bDeviceSubClass */ -+ .byte 0x00 /* bDeviceProtocol */ -+ .byte 0x40 /* bMaxPacketSize0 */ -+ .byte 0x1a /* idVendor */ -+ .byte 0x60 /* idVendor */ -+ .byte 0x40 /* idProduct */ -+ .byte 0x47 /* idProduct */ -+ .byte 0x00 /* bcdDevice */ -+ .byte 0x01 /* bcdDevice */ -+ .byte 0x01 /* iManufacturer */ -+ .byte 0x02 /* iProduct */ -+ .byte 0x00 /* iSerialNumber */ -+ .byte 0x01 /* bNumConfigurations */ -+ -+ .align 2 -+dev_qualifier: -+ .byte 0x0a /* bLength */ -+ .byte 0x06 /* bDescriptorType */ -+ .byte 0x00 /* bcdUSB */ -+ .byte 0x02 /* bcdUSB */ -+ .byte 0x00 /* bDeviceClass */ -+ .byte 0x00 /* bDeviceSubClass */ -+ .byte 0x00 /* bDeviceProtocol */ -+ .byte 0x40 /* bMaxPacketSize0 */ -+ .byte 0x01 /* bNumConfigurations */ -+ .byte 0x00 /* bRESERVED */ -+ -+ .align 2 -+config_desc_hs: -+ .byte 0x09 /* bLength */ -+ .byte 0x02 /* bDescriptorType */ -+ .byte 0x20 /* wTotalLength */ -+ .byte 0x00 /* wTotalLength */ -+ .byte 0x01 /* bNumInterfaces */ -+ .byte 0x01 /* bConfigurationValue */ -+ .byte 0x00 /* iConfiguration */ -+ .byte 0xc0 /* bmAttributes */ -+ .byte 0x01 /* MaxPower */ -+intf_desc_hs: -+ .byte 0x09 /* bLength */ -+ .byte 0x04 /* bDescriptorType */ -+ .byte 0x00 /* bInterfaceNumber */ -+ .byte 0x00 /* bAlternateSetting */ -+ .byte 0x02 /* bNumEndpoints */ -+ .byte 0xff /* bInterfaceClass */ -+ .byte 0x00 /* bInterfaceSubClass */ -+ .byte 0x50 /* bInterfaceProtocol */ -+ .byte 0x00 /* iInterface */ -+ep1_desc_hs: -+ .byte 0x07 /* bLength */ -+ .byte 0x05 /* bDescriptorType */ -+ .byte 0x01 /* bEndpointAddress */ -+ .byte 0x02 /* bmAttributes */ -+ .byte 0x00 /* wMaxPacketSize */ -+ .byte 0x02 /* wMaxPacketSize */ -+ .byte 0x00 /* bInterval */ -+ep2_desc_hs: -+ .byte 0x07 /* bLength */ -+ .byte 0x05 /* bDescriptorType */ -+ .byte 0x81 /* bEndpointAddress */ -+ .byte 0x02 /* bmAttributes */ -+ .byte 0x00 /* wMaxPacketSize */ -+ .byte 0x02 /* wMaxPacketSize */ -+ .byte 0x00 /* bInterval */ -+ -+ .align 2 -+config_desc_fs: -+ .byte 0x09 /* bLength */ -+ .byte 0x02 /* bDescriptorType */ -+ .byte 0x20 /* wTotalLength */ -+ .byte 0x00 /* wTotalLength */ -+ .byte 0x01 /* bNumInterfaces */ -+ .byte 0x01 /* bConfigurationValue */ -+ .byte 0x00 /* iConfiguration */ -+ .byte 0xc0 /* bmAttributes */ -+ .byte 0x01 /* MaxPower */ -+intf_desc_fs: -+ .byte 0x09 /* bLength */ -+ .byte 0x04 /* bDescriptorType */ -+ .byte 0x00 /* bInterfaceNumber */ -+ .byte 0x00 /* bAlternateSetting */ -+ .byte 0x02 /* bNumEndpoints */ -+ .byte 0xff /* bInterfaceClass */ -+ .byte 0x00 /* bInterfaceSubClass */ -+ .byte 0x50 /* bInterfaceProtocol */ -+ .byte 0x00 /* iInterface */ -+ep1_desc_fs: -+ .byte 0x07 /* bLength */ -+ .byte 0x05 /* bDescriptorType */ -+ .byte 0x01 /* bEndpointAddress */ -+ .byte 0x02 /* bmAttributes */ -+ .byte 0x40 /* wMaxPacketSize */ -+ .byte 0x00 /* wMaxPacketSize */ -+ .byte 0x00 /* bInterval */ -+ep2_desc_fs: -+ .byte 0x07 /* bLength */ -+ .byte 0x05 /* bDescriptorType */ -+ .byte 0x81 /* bEndpointAddress */ -+ .byte 0x02 /* bmAttributes */ -+ .byte 0x40 /* wMaxPacketSize */ -+ .byte 0x00 /* wMaxPacketSize */ -+ .byte 0x00 /* bInterval */ -+ -+ .align 2 -+string_lang_ids: -+ .byte 0x04 -+ .byte 0x03 -+ .byte 0x09 -+ .byte 0x04 -+ -+ .align 2 -+string_manufacture: -+ .byte 0x10 -+ .byte 0x03 -+ .byte 0x49 -+ .byte 0x00 -+ .byte 0x6e -+ .byte 0x00 -+ .byte 0x67 -+ .byte 0x00 -+ .byte 0x65 -+ .byte 0x00 -+ .byte 0x6e -+ .byte 0x00 -+ .byte 0x69 -+ .byte 0x00 -+ .byte 0x63 -+ .byte 0x00 -+ -+ .align 2 -+string_product: -+ .byte 0x2e -+ .byte 0x03 -+ .byte 0x4a -+ .byte 0x00 -+ .byte 0x5a -+ .byte 0x00 -+ .byte 0x34 -+ .byte 0x00 -+ .byte 0x37 -+ .byte 0x00 -+ .byte 0x34 -+ .byte 0x00 -+ .byte 0x30 -+ .byte 0x00 -+ .byte 0x20 -+ .byte 0x00 -+ .byte 0x55 -+ .byte 0x00 -+ .byte 0x53 -+ .byte 0x00 -+ .byte 0x42 -+ .byte 0x00 -+ .byte 0x20 -+ .byte 0x00 -+ .byte 0x42 -+ .byte 0x00 -+ .byte 0x6f -+ .byte 0x00 -+ .byte 0x6f -+ .byte 0x00 -+ .byte 0x74 -+ .byte 0x00 -+ .byte 0x20 -+ .byte 0x00 -+ .byte 0x44 -+ .byte 0x00 -+ .byte 0x65 -+ .byte 0x00 -+ .byte 0x76 -+ .byte 0x00 -+ .byte 0x69 -+ .byte 0x00 -+ .byte 0x63 -+ .byte 0x00 -+ .byte 0x65 -+ .byte 0x00 -+ -+ .align 2 -+cpu_info_data: -+ .byte 0x4a -+ .byte 0x5a -+ .byte 0x34 -+ .byte 0x37 -+ .byte 0x34 -+ .byte 0x30 -+ .byte 0x56 -+ .byte 0x31 -+usbboot_end: -+ -+ .set reorder --- -1.7.9.5 - diff --git a/package/boot/uboot-xburst/patches/0003-add-mmc-support.patch b/package/boot/uboot-xburst/patches/0003-add-mmc-support.patch deleted file mode 100644 index e9baa7c373..0000000000 --- a/package/boot/uboot-xburst/patches/0003-add-mmc-support.patch +++ /dev/null @@ -1,1664 +0,0 @@ -From bd36739e77669e8df45c38f6acfe2cea511534d9 Mon Sep 17 00:00:00 2001 -From: Xiangfu <xiangfu@openmobilefree.net> -Date: Wed, 10 Oct 2012 18:19:41 +0800 -Subject: [PATCH 3/6] add mmc support - ---- - arch/mips/include/asm/jz4740.h | 166 ++++++ - board/qi/qi_lb60/qi_lb60.c | 9 +- - drivers/mmc/Makefile | 1 + - drivers/mmc/jz_mmc.c | 1179 ++++++++++++++++++++++++++++++++++++++++ - drivers/mmc/jz_mmc.h | 176 ++++++ - include/configs/qi_lb60.h | 9 + - include/mmc.h | 40 ++ - 7 files changed, 1578 insertions(+), 2 deletions(-) - create mode 100644 drivers/mmc/jz_mmc.c - create mode 100644 drivers/mmc/jz_mmc.h - -diff --git a/arch/mips/include/asm/jz4740.h b/arch/mips/include/asm/jz4740.h -index 7a7cfff..68287fb 100644 ---- a/arch/mips/include/asm/jz4740.h -+++ b/arch/mips/include/asm/jz4740.h -@@ -1146,5 +1146,171 @@ extern void sdram_init(void); - extern void calc_clocks(void); - extern void rtc_init(void); - -+/************************************************************************* -+ * MSC -+ *************************************************************************/ -+#define REG8(addr) *((volatile u8 *)(addr)) -+#define REG16(addr) *((volatile u16 *)(addr)) -+#define REG32(addr) *((volatile u32 *)(addr)) -+ -+#define CPM_BASE 0xB0000000 -+#define CPM_CPCCR (CPM_BASE+0x00) -+#define CPM_MSCCDR (CPM_BASE+0x68) -+#define REG_CPM_MSCCDR REG32(CPM_MSCCDR) -+#define REG_CPM_CPCCR REG32(CPM_CPCCR) -+ -+#define MSC_BASE 0xB0021000 -+ -+#define MSC_STRPCL (MSC_BASE + 0x000) -+#define MSC_STAT (MSC_BASE + 0x004) -+#define MSC_CLKRT (MSC_BASE + 0x008) -+#define MSC_CMDAT (MSC_BASE + 0x00C) -+#define MSC_RESTO (MSC_BASE + 0x010) -+#define MSC_RDTO (MSC_BASE + 0x014) -+#define MSC_BLKLEN (MSC_BASE + 0x018) -+#define MSC_NOB (MSC_BASE + 0x01C) -+#define MSC_SNOB (MSC_BASE + 0x020) -+#define MSC_IMASK (MSC_BASE + 0x024) -+#define MSC_IREG (MSC_BASE + 0x028) -+#define MSC_CMD (MSC_BASE + 0x02C) -+#define MSC_ARG (MSC_BASE + 0x030) -+#define MSC_RES (MSC_BASE + 0x034) -+#define MSC_RXFIFO (MSC_BASE + 0x038) -+#define MSC_TXFIFO (MSC_BASE + 0x03C) -+ -+#define REG_MSC_STRPCL REG16(MSC_STRPCL) -+#define REG_MSC_STAT REG32(MSC_STAT) -+#define REG_MSC_CLKRT REG16(MSC_CLKRT) -+#define REG_MSC_CMDAT REG32(MSC_CMDAT) -+#define REG_MSC_RESTO REG16(MSC_RESTO) -+#define REG_MSC_RDTO REG16(MSC_RDTO) -+#define REG_MSC_BLKLEN REG16(MSC_BLKLEN) -+#define REG_MSC_NOB REG16(MSC_NOB) -+#define REG_MSC_SNOB REG16(MSC_SNOB) -+#define REG_MSC_IMASK REG16(MSC_IMASK) -+#define REG_MSC_IREG REG16(MSC_IREG) -+#define REG_MSC_CMD REG8(MSC_CMD) -+#define REG_MSC_ARG REG32(MSC_ARG) -+#define REG_MSC_RES REG16(MSC_RES) -+#define REG_MSC_RXFIFO REG32(MSC_RXFIFO) -+#define REG_MSC_TXFIFO REG32(MSC_TXFIFO) -+ -+/* MSC Clock and Control Register (MSC_STRPCL) */ -+ -+#define MSC_STRPCL_EXIT_MULTIPLE (1 << 7) -+#define MSC_STRPCL_EXIT_TRANSFER (1 << 6) -+#define MSC_STRPCL_START_READWAIT (1 << 5) -+#define MSC_STRPCL_STOP_READWAIT (1 << 4) -+#define MSC_STRPCL_RESET (1 << 3) -+#define MSC_STRPCL_START_OP (1 << 2) -+#define MSC_STRPCL_CLOCK_CONTROL_BIT 0 -+#define MSC_STRPCL_CLOCK_CONTROL_MASK (0x3 << MSC_STRPCL_CLOCK_CONTROL_BIT) -+ #define MSC_STRPCL_CLOCK_CONTROL_STOP (0x1 << MSC_STRPCL_CLOCK_CONTROL_BIT) /* Stop MMC/SD clock */ -+ #define MSC_STRPCL_CLOCK_CONTROL_START (0x2 << MSC_STRPCL_CLOCK_CONTROL_BIT) /* Start MMC/SD clock */ -+ -+/* MSC Status Register (MSC_STAT) */ -+ -+#define MSC_STAT_IS_RESETTING (1 << 15) -+#define MSC_STAT_SDIO_INT_ACTIVE (1 << 14) -+#define MSC_STAT_PRG_DONE (1 << 13) -+#define MSC_STAT_DATA_TRAN_DONE (1 << 12) -+#define MSC_STAT_END_CMD_RES (1 << 11) -+#define MSC_STAT_DATA_FIFO_AFULL (1 << 10) -+#define MSC_STAT_IS_READWAIT (1 << 9) -+#define MSC_STAT_CLK_EN (1 << 8) -+#define MSC_STAT_DATA_FIFO_FULL (1 << 7) -+#define MSC_STAT_DATA_FIFO_EMPTY (1 << 6) -+#define MSC_STAT_CRC_RES_ERR (1 << 5) -+#define MSC_STAT_CRC_READ_ERROR (1 << 4) -+#define MSC_STAT_CRC_WRITE_ERROR_BIT 2 -+#define MSC_STAT_CRC_WRITE_ERROR_MASK (0x3 << MSC_STAT_CRC_WRITE_ERROR_BIT) -+ #define MSC_STAT_CRC_WRITE_ERROR_NO (0 << MSC_STAT_CRC_WRITE_ERROR_BIT) /* No error on transmission of data */ -+ #define MSC_STAT_CRC_WRITE_ERROR (1 << MSC_STAT_CRC_WRITE_ERROR_BIT) /* Card observed erroneous transmission of data */ -+ #define MSC_STAT_CRC_WRITE_ERROR_NOSTS (2 << MSC_STAT_CRC_WRITE_ERROR_BIT) /* No CRC status is sent back */ -+#define MSC_STAT_TIME_OUT_RES (1 << 1) -+#define MSC_STAT_TIME_OUT_READ (1 << 0) -+ -+/* MSC Bus Clock Control Register (MSC_CLKRT) */ -+ -+#define MSC_CLKRT_CLK_RATE_BIT 0 -+#define MSC_CLKRT_CLK_RATE_MASK (0x7 << MSC_CLKRT_CLK_RATE_BIT) -+ #define MSC_CLKRT_CLK_RATE_DIV_1 (0x0 << MSC_CLKRT_CLK_RATE_BIT) /* CLK_SRC */ -+ #define MSC_CLKRT_CLK_RATE_DIV_2 (0x1 << MSC_CLKRT_CLK_RATE_BIT) /* 1/2 of CLK_SRC */ -+ #define MSC_CLKRT_CLK_RATE_DIV_4 (0x2 << MSC_CLKRT_CLK_RATE_BIT) /* 1/4 of CLK_SRC */ -+ #define MSC_CLKRT_CLK_RATE_DIV_8 (0x3 << MSC_CLKRT_CLK_RATE_BIT) /* 1/8 of CLK_SRC */ -+ #define MSC_CLKRT_CLK_RATE_DIV_16 (0x4 << MSC_CLKRT_CLK_RATE_BIT) /* 1/16 of CLK_SRC */ -+ #define MSC_CLKRT_CLK_RATE_DIV_32 (0x5 << MSC_CLKRT_CLK_RATE_BIT) /* 1/32 of CLK_SRC */ -+ #define MSC_CLKRT_CLK_RATE_DIV_64 (0x6 << MSC_CLKRT_CLK_RATE_BIT) /* 1/64 of CLK_SRC */ -+ #define MSC_CLKRT_CLK_RATE_DIV_128 (0x7 << MSC_CLKRT_CLK_RATE_BIT) /* 1/128 of CLK_SRC */ -+ -+/* MSC Command Sequence Control Register (MSC_CMDAT) */ -+ -+#define MSC_CMDAT_IO_ABORT (1 << 11) -+#define MSC_CMDAT_BUS_WIDTH_BIT 9 -+#define MSC_CMDAT_BUS_WIDTH_MASK (0x3 << MSC_CMDAT_BUS_WIDTH_BIT) -+#define MSC_CMDAT_BUS_WIDTH_1BIT (0x0 << MSC_CMDAT_BUS_WIDTH_BIT) -+#define MSC_CMDAT_BUS_WIDTH_4BIT (0x2 << MSC_CMDAT_BUS_WIDTH_BIT) -+#define MSC_CMDAT_DMA_EN (1 << 8) -+#define MSC_CMDAT_INIT (1 << 7) -+#define MSC_CMDAT_BUSY (1 << 6) -+#define MSC_CMDAT_STREAM_BLOCK (1 << 5) -+#define MSC_CMDAT_WRITE (1 << 4) -+#define MSC_CMDAT_READ (0 << 4) -+#define MSC_CMDAT_DATA_EN (1 << 3) -+#define MSC_CMDAT_RESPONSE_BIT 0 -+#define MSC_CMDAT_RESPONSE_MASK (0x7 << MSC_CMDAT_RESPONSE_BIT) -+#define MSC_CMDAT_RESPONSE_NONE (0x0 << MSC_CMDAT_RESPONSE_BIT) -+#define MSC_CMDAT_RESPONSE_R1 (0x1 << MSC_CMDAT_RESPONSE_BIT) -+#define MSC_CMDAT_RESPONSE_R2 (0x2 << MSC_CMDAT_RESPONSE_BIT) -+#define MSC_CMDAT_RESPONSE_R3 (0x3 << MSC_CMDAT_RESPONSE_BIT) -+#define MSC_CMDAT_RESPONSE_R4 (0x4 << MSC_CMDAT_RESPONSE_BIT) -+#define MSC_CMDAT_RESPONSE_R5 (0x5 << MSC_CMDAT_RESPONSE_BIT) -+#define MSC_CMDAT_RESPONSE_R6 (0x6 << MSC_CMDAT_RESPONSE_BIT) -+ -+/* MSC Interrupts Mask Register (MSC_IMASK) */ -+#define MSC_IMASK_SDIO (1 << 7) -+#define MSC_IMASK_TXFIFO_WR_REQ (1 << 6) -+#define MSC_IMASK_RXFIFO_RD_REQ (1 << 5) -+#define MSC_IMASK_END_CMD_RES (1 << 2) -+#define MSC_IMASK_PRG_DONE (1 << 1) -+#define MSC_IMASK_DATA_TRAN_DONE (1 << 0) -+ -+ -+/* MSC Interrupts Status Register (MSC_IREG) */ -+#define MSC_IREG_SDIO (1 << 7) -+#define MSC_IREG_TXFIFO_WR_REQ (1 << 6) -+#define MSC_IREG_RXFIFO_RD_REQ (1 << 5) -+#define MSC_IREG_END_CMD_RES (1 << 2) -+#define MSC_IREG_PRG_DONE (1 << 1) -+#define MSC_IREG_DATA_TRAN_DONE (1 << 0) -+ -+static __inline__ unsigned int __cpm_get_pllout2(void) -+{ -+ if (REG_CPM_CPCCR & CPM_CPCCR_PCS) -+ return __cpm_get_pllout(); -+ else -+ return __cpm_get_pllout()/2; -+} -+ -+static inline void __cpm_select_msc_clk(int sd) -+{ -+ unsigned int pllout2 = __cpm_get_pllout2(); -+ unsigned int div = 0; -+ -+ if (sd) { -+ div = pllout2 / 24000000; -+ } -+ else { -+ div = pllout2 / 16000000; -+ } -+ -+ REG_CPM_MSCCDR = div - 1; -+} -+#define __msc_reset() \ -+do { \ -+ REG_MSC_STRPCL = MSC_STRPCL_RESET; \ -+ while (REG_MSC_STAT & MSC_STAT_IS_RESETTING); \ -+} while (0) -+ - #endif /* !__ASSEMBLY__ */ - #endif /* __JZ4740_H__ */ -diff --git a/board/qi/qi_lb60/qi_lb60.c b/board/qi/qi_lb60/qi_lb60.c -index 3bd4e2f..a2ba648 100644 ---- a/board/qi/qi_lb60/qi_lb60.c -+++ b/board/qi/qi_lb60/qi_lb60.c -@@ -40,8 +40,13 @@ static void gpio_init(void) - __gpio_clear_pin(GPIO_KEYOUT_BASE + i); - } - -- __gpio_as_input(GPIO_KEYIN_8); -- __gpio_enable_pull(GPIO_KEYIN_8); -+ if (__gpio_get_pin(GPIO_KEYIN_BASE + 2) == 0){ -+ printf("[S] pressed, enable UART0\n"); -+ __gpio_as_uart0(); -+ } else { -+ __gpio_as_input(GPIO_KEYIN_8); -+ __gpio_enable_pull(GPIO_KEYIN_8); -+ } - - /* enable the TP4, TP5 as UART0 */ - __gpio_jtag_to_uart0(); -diff --git a/drivers/mmc/Makefile b/drivers/mmc/Makefile -index 565ba6a..3c717b1 100644 ---- a/drivers/mmc/Makefile -+++ b/drivers/mmc/Makefile -@@ -47,6 +47,7 @@ COBJS-$(CONFIG_SDHCI) += sdhci.o - COBJS-$(CONFIG_S5P_SDHCI) += s5p_sdhci.o - COBJS-$(CONFIG_SH_MMCIF) += sh_mmcif.o - COBJS-$(CONFIG_TEGRA_MMC) += tegra_mmc.o -+COBJS-$(CONFIG_JZ4740_MMC) += jz_mmc.o - - COBJS := $(COBJS-y) - SRCS := $(COBJS:.o=.c) -diff --git a/drivers/mmc/jz_mmc.c b/drivers/mmc/jz_mmc.c -new file mode 100644 -index 0000000..642cecc ---- /dev/null -+++ b/drivers/mmc/jz_mmc.c -@@ -0,0 +1,1179 @@ -+/* -+ * (C) Copyright 2003 -+ * Kyle Harris, Nexus Technologies, Inc. kharris@nexus-tech.net -+ * -+ * See file CREDITS for list of people who contributed to this -+ * project. -+ * -+ * This program is free software; you can redistribute it and/or -+ * modify it under the terms of the GNU General Public License as -+ * published by the Free Software Foundation; either version 2 of -+ * the License, or (at your option) any later version. -+ * -+ * This program is distributed in the hope that it will be useful, -+ * but WITHOUT ANY WARRANTY; without even the implied warranty of -+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -+ * GNU General Public License for more details. -+ * -+ * You should have received a copy of the GNU General Public License -+ * along with this program; if not, write to the Free Software -+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, -+ * MA 02111-1307 USA -+ */ -+ -+#include <config.h> -+#include <common.h> -+#include <part.h> -+#include <mmc.h> -+ -+#include <asm/io.h> -+#include <asm/jz4740.h> -+#include "jz_mmc.h" -+ -+static int sd2_0 = 0; -+static int mmc_ready = 0; -+static int use_4bit; /* Use 4-bit data bus */ -+/* -+ * MMC Events -+ */ -+#define MMC_EVENT_NONE 0x00 /* No events */ -+#define MMC_EVENT_RX_DATA_DONE 0x01 /* Rx data done */ -+#define MMC_EVENT_TX_DATA_DONE 0x02 /* Tx data done */ -+#define MMC_EVENT_PROG_DONE 0x04 /* Programming is done */ -+ -+ -+#define MMC_IRQ_MASK() \ -+do { \ -+ REG_MSC_IMASK = 0xffff; \ -+ REG_MSC_IREG = 0xffff; \ -+} while (0) -+ -+/* -+ * GPIO definition -+ */ -+#if defined(CONFIG_SAKC) -+ -+#define __msc_init_io() \ -+do { \ -+ __gpio_as_input(GPIO_SD_CD_N); \ -+} while (0) -+ -+#else -+#define __msc_init_io() \ -+do { \ -+ __gpio_as_output(GPIO_SD_VCC_EN_N); \ -+ __gpio_as_input(GPIO_SD_CD_N); \ -+} while (0) -+ -+#define __msc_enable_power() \ -+do { \ -+ __gpio_clear_pin(GPIO_SD_VCC_EN_N); \ -+} while (0) -+ -+#define __msc_disable_power() \ -+do { \ -+ __gpio_set_pin(GPIO_SD_VCC_EN_N); \ -+} while (0) -+ -+#endif /* CONFIG_SAKE */ -+ -+#define __msc_card_detected() \ -+({ \ -+ int detected = 1; \ -+ __gpio_as_input(GPIO_SD_CD_N); \ -+ __gpio_disable_pull(GPIO_SD_CD_N); \ -+ if (!__gpio_get_pin(GPIO_SD_CD_N)) \ -+ detected = 0; \ -+ detected; \ -+}) -+ -+/* -+ * Local functions -+ */ -+ -+extern int -+fat_register_device(block_dev_desc_t *dev_desc, int part_no); -+ -+static block_dev_desc_t mmc_dev; -+ -+block_dev_desc_t * mmc_get_dev(int dev) -+{ -+ return ((block_dev_desc_t *)&mmc_dev); -+} -+ -+/* Stop the MMC clock and wait while it happens */ -+static inline int jz_mmc_stop_clock(void) -+{ -+ int timeout = 1000; -+ -+ REG_MSC_STRPCL = MSC_STRPCL_CLOCK_CONTROL_STOP; -+ -+ while (timeout && (REG_MSC_STAT & MSC_STAT_CLK_EN)) { -+ timeout--; -+ if (timeout == 0) -+ return MMC_ERROR_TIMEOUT; -+ udelay(1); -+ } -+ return MMC_NO_ERROR; -+} -+ -+/* Start the MMC clock and operation */ -+static inline int jz_mmc_start_clock(void) -+{ -+ REG_MSC_STRPCL = MSC_STRPCL_CLOCK_CONTROL_START | MSC_STRPCL_START_OP; -+ return MMC_NO_ERROR; -+} -+ -+static inline u32 jz_mmc_calc_clkrt(int is_sd, u32 rate) -+{ -+ u32 clkrt = 0; -+ u32 clk_src = is_sd ? 24000000 : 16000000; -+ -+ while (rate < clk_src) { -+ clkrt ++; -+ clk_src >>= 1; -+ } -+ -+ return clkrt; -+} -+ -+/* Set the MMC clock frequency */ -+void jz_mmc_set_clock(int sd, u32 rate) -+{ -+ jz_mmc_stop_clock(); -+ -+ /* Select clock source of MSC */ -+ __cpm_select_msc_clk(sd); -+ -+ /* Set clock dividor of MSC */ -+ REG_MSC_CLKRT = jz_mmc_calc_clkrt(sd, rate); -+} -+ -+static int jz_mmc_check_status(struct mmc_request *request) -+{ -+ u32 status = REG_MSC_STAT; -+ -+ /* Checking for response or data timeout */ -+ if (status & (MSC_STAT_TIME_OUT_RES | MSC_STAT_TIME_OUT_READ)) { -+ printf("MMC/SD timeout, MMC_STAT 0x%x CMD %d\n", status, request->cmd); -+ return MMC_ERROR_TIMEOUT; -+ } -+ -+ /* Checking for CRC error */ -+ if (status & (MSC_STAT_CRC_READ_ERROR | MSC_STAT_CRC_WRITE_ERROR | MSC_STAT_CRC_RES_ERR)) { -+ printf("MMC/CD CRC error, MMC_STAT 0x%x\n", status); -+ return MMC_ERROR_CRC; -+ } -+ -+ return MMC_NO_ERROR; -+} -+ -+/* Obtain response to the command and store it to response buffer */ -+static void jz_mmc_get_response(struct mmc_request *request) -+{ -+ int i; -+ u8 *buf; -+ u32 data; -+ -+ debug("fetch response for request %d, cmd %d\n", -+ request->rtype, request->cmd); -+ -+ buf = request->response; -+ request->result = MMC_NO_ERROR; -+ -+ switch (request->rtype) { -+ case RESPONSE_R1: case RESPONSE_R1B: case RESPONSE_R6: -+ case RESPONSE_R3: case RESPONSE_R4: case RESPONSE_R5: -+ { -+ data = REG_MSC_RES; -+ buf[0] = (data >> 8) & 0xff; -+ buf[1] = data & 0xff; -+ data = REG_MSC_RES; -+ buf[2] = (data >> 8) & 0xff; -+ buf[3] = data & 0xff; -+ data = REG_MSC_RES; -+ buf[4] = data & 0xff; -+ -+ debug("request %d, response [%02x %02x %02x %02x %02x]\n", -+ request->rtype, buf[0], buf[1], buf[2], buf[3], buf[4]); -+ break; -+ } -+ case RESPONSE_R2_CID: case RESPONSE_R2_CSD: -+ { -+ for (i = 0; i < 16; i += 2) { -+ data = REG_MSC_RES; -+ buf[i] = (data >> 8) & 0xff; -+ buf[i+1] = data & 0xff; -+ } -+ debug("request %d, response [", request->rtype); -+#if CONFIG_MMC_DEBUG_VERBOSE > 2 -+ if (g_mmc_debug >= 3) { -+ int n; -+ for (n = 0; n < 17; n++) -+ printk("%02x ", buf[n]); -+ printk("]\n"); -+ } -+#endif -+ break; -+ } -+ case RESPONSE_NONE: -+ debug("No response\n"); -+ break; -+ -+ default: -+ debug("unhandled response type for request %d\n", request->rtype); -+ break; -+ } -+} -+ -+static int jz_mmc_receive_data(struct mmc_request *req) -+{ -+ u32 stat, timeout, data, cnt; -+ u8 *buf = req->buffer; -+ u32 wblocklen = (u32)(req->block_len + 3) >> 2; /* length in word */ -+ -+ timeout = 0x3ffffff; -+ -+ while (timeout) { -+ timeout--; -+ stat = REG_MSC_STAT; -+ -+ if (stat & MSC_STAT_TIME_OUT_READ) -+ return MMC_ERROR_TIMEOUT; -+ else if (stat & MSC_STAT_CRC_READ_ERROR) -+ return MMC_ERROR_CRC; -+ else if (!(stat & MSC_STAT_DATA_FIFO_EMPTY) -+ || (stat & MSC_STAT_DATA_FIFO_AFULL)) { -+ /* Ready to read data */ -+ break; -+ } -+ udelay(1); -+ } -+ if (!timeout) -+ return MMC_ERROR_TIMEOUT; -+ -+ /* Read data from RXFIFO. It could be FULL or PARTIAL FULL */ -+ cnt = wblocklen; -+ while (cnt) { -+ data = REG_MSC_RXFIFO; -+ { -+ *buf++ = (u8)(data >> 0); -+ *buf++ = (u8)(data >> 8); -+ *buf++ = (u8)(data >> 16); -+ *buf++ = (u8)(data >> 24); -+ } -+ cnt --; -+ while (cnt && (REG_MSC_STAT & MSC_STAT_DATA_FIFO_EMPTY)) -+ ; -+ } -+ return MMC_NO_ERROR; -+} -+ -+static int jz_mmc_transmit_data(struct mmc_request *req) -+{ -+#if 0 -+ u32 nob = req->nob; -+ u32 wblocklen = (u32)(req->block_len + 3) >> 2; /* length in word */ -+ u8 *buf = req->buffer; -+ u32 *wbuf = (u32 *)buf; -+ u32 waligned = (((u32)buf & 0x3) == 0); /* word aligned ? */ -+ u32 stat, timeout, data, cnt; -+ -+ for (nob; nob >= 1; nob--) { -+ timeout = 0x3FFFFFF; -+ -+ while (timeout) { -+ timeout--; -+ stat = REG_MSC_STAT; -+ -+ if (stat & (MSC_STAT_CRC_WRITE_ERROR | MSC_STAT_CRC_WRITE_ERROR_NOSTS)) -+ return MMC_ERROR_CRC; -+ else if (!(stat & MSC_STAT_DATA_FIFO_FULL)) { -+ /* Ready to write data */ -+ break; -+ } -+ -+ udelay(1); -+ } -+ -+ if (!timeout) -+ return MMC_ERROR_TIMEOUT; -+ -+ /* Write data to TXFIFO */ -+ cnt = wblocklen; -+ while (cnt) { -+ while (REG_MSC_STAT & MSC_STAT_DATA_FIFO_FULL) -+ ; -+ -+ if (waligned) { -+ REG_MSC_TXFIFO = *wbuf++; -+ } -+ else { -+ data = *buf++ | (*buf++ << 8) | (*buf++ << 16) | (*buf++ << 24); -+ REG_MSC_TXFIFO = data; -+ } -+ -+ cnt--; -+ } -+ } -+#endif -+ return MMC_NO_ERROR; -+} -+ -+ -+/* -+ * Name: int jz_mmc_exec_cmd() -+ * Function: send command to the card, and get a response -+ * Input: struct mmc_request *req : MMC/SD request -+ * Output: 0: right >0: error code -+ */ -+int jz_mmc_exec_cmd(struct mmc_request *request) -+{ -+ u32 cmdat = 0, events = 0; -+ int retval, timeout = 0x3fffff; -+ -+ /* Indicate we have no result yet */ -+ request->result = MMC_NO_RESPONSE; -+ if (request->cmd == MMC_CIM_RESET) { -+ /* On reset, 1-bit bus width */ -+ use_4bit = 0; -+ -+ /* Reset MMC/SD controller */ -+ __msc_reset(); -+ -+ /* On reset, drop MMC clock down */ -+ jz_mmc_set_clock(0, MMC_CLOCK_SLOW); -+ -+ /* On reset, stop MMC clock */ -+ jz_mmc_stop_clock(); -+ } -+ if (request->cmd == MMC_CMD_SEND_OP_COND) { -+ debug("Have an MMC card\n"); -+ /* always use 1bit for MMC */ -+ use_4bit = 0; -+ } -+ if (request->cmd == SET_BUS_WIDTH) { -+ if (request->arg == 0x2) { -+ printf("Use 4-bit bus width\n"); -+ use_4bit = 1; -+ } else { -+ printf("Use 1-bit bus width\n"); -+ use_4bit = 0; -+ } -+ } -+ -+ /* stop clock */ -+ jz_mmc_stop_clock(); -+ -+ /* mask all interrupts */ -+ REG_MSC_IMASK = 0xffff; -+ -+ /* clear status */ -+ REG_MSC_IREG = 0xffff; -+ -+ /* use 4-bit bus width when possible */ -+ if (use_4bit) -+ cmdat |= MSC_CMDAT_BUS_WIDTH_4BIT; -+ -+ /* Set command type and events */ -+ switch (request->cmd) { -+ /* MMC core extra command */ -+ case MMC_CIM_RESET: -+ cmdat |= MSC_CMDAT_INIT; /* Initialization sequence sent prior to command */ -+ break; -+ -+ /* bc - broadcast - no response */ -+ case MMC_CMD_GO_IDLE_STATE: -+ case MMC_CMD_SET_DSR: -+ break; -+ -+ /* bcr - broadcast with response */ -+ case MMC_CMD_SEND_OP_COND: -+ case MMC_CMD_ALL_SEND_CID: -+ case MMC_GO_IRQ_STATE: -+ break; -+ -+ /* adtc - addressed with data transfer */ -+ case MMC_READ_DAT_UNTIL_STOP: -+ case MMC_CMD_READ_SINGLE_BLOCK: -+ case MMC_CMD_READ_MULTIPLE_BLOCK: -+ case SD_CMD_APP_SEND_SCR: -+ cmdat |= MSC_CMDAT_DATA_EN | MSC_CMDAT_READ; -+ events = MMC_EVENT_RX_DATA_DONE; -+ break; -+ -+ case MMC_WRITE_DAT_UNTIL_STOP: -+ case MMC_CMD_WRITE_SINGLE_BLOCK: -+ case MMC_CMD_WRITE_MULTIPLE_BLOCK: -+ case MMC_PROGRAM_CID: -+ case MMC_PROGRAM_CSD: -+ case MMC_SEND_WRITE_PROT: -+ case MMC_GEN_CMD: -+ case MMC_LOCK_UNLOCK: -+ cmdat |= MSC_CMDAT_DATA_EN | MSC_CMDAT_WRITE; -+ events = MMC_EVENT_TX_DATA_DONE | MMC_EVENT_PROG_DONE; -+ -+ break; -+ -+ case MMC_CMD_STOP_TRANSMISSION: -+ events = MMC_EVENT_PROG_DONE; -+ break; -+ -+ /* ac - no data transfer */ -+ default: -+ break; -+ } -+ -+ /* Set response type */ -+ switch (request->rtype) { -+ case RESPONSE_NONE: -+ break; -+ -+ case RESPONSE_R1B: -+ cmdat |= MSC_CMDAT_BUSY; -+ /*FALLTHRU*/ -+ case RESPONSE_R1: -+ cmdat |= MSC_CMDAT_RESPONSE_R1; -+ break; -+ case RESPONSE_R2_CID: -+ case RESPONSE_R2_CSD: -+ cmdat |= MSC_CMDAT_RESPONSE_R2; -+ break; -+ case RESPONSE_R3: -+ cmdat |= MSC_CMDAT_RESPONSE_R3; -+ break; -+ case RESPONSE_R4: -+ cmdat |= MSC_CMDAT_RESPONSE_R4; -+ break; -+ case RESPONSE_R5: -+ cmdat |= MSC_CMDAT_RESPONSE_R5; -+ break; -+ case RESPONSE_R6: -+ cmdat |= MSC_CMDAT_RESPONSE_R6; -+ break; -+ default: -+ break; -+ } -+ -+ /* Set command index */ -+ if (request->cmd == MMC_CIM_RESET) { -+ REG_MSC_CMD = MMC_CMD_GO_IDLE_STATE; -+ } else { -+ REG_MSC_CMD = request->cmd; -+ } -+ -+ /* Set argument */ -+ REG_MSC_ARG = request->arg; -+ -+ /* Set block length and nob */ -+ if (request->cmd == SD_CMD_APP_SEND_SCR) { /* get SCR from DataFIFO */ -+ REG_MSC_BLKLEN = 8; -+ REG_MSC_NOB = 1; -+ } else { -+ REG_MSC_BLKLEN = request->block_len; -+ REG_MSC_NOB = request->nob; -+ } -+ -+ /* Set command */ -+ REG_MSC_CMDAT = cmdat; -+ -+ debug("Send cmd %d cmdat: %x arg: %x resp %d\n", request->cmd, -+ cmdat, request->arg, request->rtype); -+ -+ /* Start MMC/SD clock and send command to card */ -+ jz_mmc_start_clock(); -+ -+ /* Wait for command completion */ -+ while (timeout-- && !(REG_MSC_STAT & MSC_STAT_END_CMD_RES)) -+ ; -+ -+ if (timeout == 0) -+ return MMC_ERROR_TIMEOUT; -+ -+ REG_MSC_IREG = MSC_IREG_END_CMD_RES; /* clear flag */ -+ -+ /* Check for status */ -+ retval = jz_mmc_check_status(request); -+ if (retval) { -+ return retval; -+ } -+ -+ /* Complete command with no response */ -+ if (request->rtype == RESPONSE_NONE) { -+ return MMC_NO_ERROR; -+ } -+ -+ /* Get response */ -+ jz_mmc_get_response(request); -+ -+ /* Start data operation */ -+ if (events & (MMC_EVENT_RX_DATA_DONE | MMC_EVENT_TX_DATA_DONE)) { -+ if (events & MMC_EVENT_RX_DATA_DONE) { -+ if (request->cmd == SD_CMD_APP_SEND_SCR) { -+ /* SD card returns SCR register as data. -+ MMC core expect it in the response buffer, -+ after normal response. */ -+ request->buffer = (u8 *)((u32)request->response + 5); -+ } -+ jz_mmc_receive_data(request); -+ } -+ -+ if (events & MMC_EVENT_TX_DATA_DONE) { -+ jz_mmc_transmit_data(request); -+ } -+ -+ /* Wait for Data Done */ -+ while (!(REG_MSC_IREG & MSC_IREG_DATA_TRAN_DONE)) -+ ; -+ REG_MSC_IREG = MSC_IREG_DATA_TRAN_DONE; /* clear status */ -+ } -+ -+ /* Wait for Prog Done event */ -+ if (events & MMC_EVENT_PROG_DONE) { -+ while (!(REG_MSC_IREG & MSC_IREG_PRG_DONE)) -+ ; -+ REG_MSC_IREG = MSC_IREG_PRG_DONE; /* clear status */ -+ } -+ -+ /* Command completed */ -+ -+ return MMC_NO_ERROR; /* return successfully */ -+} -+ -+int mmc_block_read(u8 *dst, ulong src, ulong len) -+{ -+ -+ struct mmc_request request; -+ struct mmc_response_r1 r1; -+ int retval = 0; -+ -+ if (len == 0) -+ goto exit; -+ -+ mmc_simple_cmd(&request, MMC_CMD_SEND_STATUS, mmcinfo.rca, RESPONSE_R1); -+ retval = mmc_unpack_r1(&request, &r1, 0); -+ if (retval && (retval != MMC_ERROR_STATE_MISMATCH)) -+ goto exit; -+ -+ mmc_simple_cmd(&request, MMC_CMD_SET_BLOCKLEN, len, RESPONSE_R1); -+ if (retval = mmc_unpack_r1(&request, &r1, 0)) -+ goto exit; -+ -+ if (!sd2_0) -+ src *= mmcinfo.block_len; -+ -+ mmc_send_cmd(&request, MMC_CMD_READ_SINGLE_BLOCK, src, 1, len, RESPONSE_R1, dst); -+ if (retval = mmc_unpack_r1(&request, &r1, 0)) -+ goto exit; -+ -+exit: -+ return retval; -+} -+ -+ulong mmc_bread(int dev_num, ulong blkstart, ulong blkcnt, ulong *dst) -+{ -+ if (!mmc_ready) { -+ printf("Please initial the MMC first\n"); -+ return -1; -+ } -+ -+ int i = 0; -+ ulong dst_tmp = dst; -+ -+ for (i = 0; i < blkcnt; i++) { -+ if ((mmc_block_read((uchar *)(dst_tmp), blkstart, mmcinfo.block_len)) < 0) -+ return -1; -+ -+ dst_tmp += mmcinfo.block_len; -+ blkstart++; -+ } -+ -+ return i; -+} -+ -+int mmc_select_card(void) -+{ -+ struct mmc_request request; -+ struct mmc_response_r1 r1; -+ int retval; -+ -+ mmc_simple_cmd(&request, MMC_CMD_SELECT_CARD, mmcinfo.rca, RESPONSE_R1B); -+ retval = mmc_unpack_r1(&request, &r1, 0); -+ if (retval) { -+ return retval; -+ } -+ -+ if (mmcinfo.sd) { -+ mmc_simple_cmd(&request, MMC_CMD_APP_CMD, mmcinfo.rca, RESPONSE_R1); -+ retval = mmc_unpack_r1(&request,&r1,0); -+ if (retval) { -+ return retval; -+ } -+#if defined(MMC_BUS_WIDTH_1BIT) -+ mmc_simple_cmd(&request, SET_BUS_WIDTH, 1, RESPONSE_R1); -+#else -+ mmc_simple_cmd(&request, SET_BUS_WIDTH, 2, RESPONSE_R1); -+#endif -+ retval = mmc_unpack_r1(&request,&r1,0); -+ if (retval) { -+ return retval; -+ } -+ } -+ return 0; -+} -+ -+/* -+ * Configure card -+ */ -+static void mmc_configure_card(void) -+{ -+ u32 rate; -+ -+ /* Get card info */ -+ if (sd2_0) -+ mmcinfo.block_num = (mmcinfo.csd.c_size + 1) << 10; -+ else -+ mmcinfo.block_num = (mmcinfo.csd.c_size + 1) * (1 << (mmcinfo.csd.c_size_mult + 2)); -+ -+ mmcinfo.block_len = 1 << mmcinfo.csd.read_bl_len; -+ -+ mmc_dev.if_type = IF_TYPE_SD; -+ mmc_dev.part_type = PART_TYPE_DOS; -+ mmc_dev.dev = 0; -+ mmc_dev.lun = 0; -+ mmc_dev.type = 0; -+ mmc_dev.blksz = mmcinfo.block_len; -+ mmc_dev.lba = mmcinfo.block_num; -+ mmc_dev.removable = 0; -+ -+ printf("%s Detected: %lu blocks of %lu bytes\n", -+ sd2_0 == 1 ? "SDHC" : "SD", -+ mmc_dev.lba, -+ mmc_dev.blksz); -+ -+ /* Fix the clock rate */ -+ rate = mmc_tran_speed(mmcinfo.csd.tran_speed); -+ if (rate < MMC_CLOCK_SLOW) -+ rate = MMC_CLOCK_SLOW; -+ if ((mmcinfo.sd == 0) && (rate > MMC_CLOCK_FAST)) -+ rate = MMC_CLOCK_FAST; -+ if ((mmcinfo.sd) && (rate > SD_CLOCK_FAST)) -+ rate = SD_CLOCK_FAST; -+ -+ debug("%s: block_len=%d block_num=%d rate=%d\n", -+ __func__, mmcinfo.block_len, mmcinfo.block_num, rate); -+ -+ jz_mmc_set_clock(mmcinfo.sd, rate); -+} -+ -+/* -+ * State machine routines to initialize card(s) -+ */ -+ -+/* -+ CIM_SINGLE_CARD_ACQ (frequency at 400 kHz) -+ --- Must enter from GO_IDLE_STATE --- -+ 1. SD_SEND_OP_COND (SD Card) [CMD55] + [CMD41] -+ 2. SEND_OP_COND (Full Range) [CMD1] {optional} -+ 3. SEND_OP_COND (Set Range ) [CMD1] -+ If busy, delay and repeat step 2 -+ 4. ALL_SEND_CID [CMD2] -+ If timeout, set an error (no cards found) -+ 5. SET_RELATIVE_ADDR [CMD3] -+ 6. SEND_CSD [CMD9] -+ 7. SET_DSR [CMD4] Only call this if (csd.dsr_imp). -+ 8. Set clock frequency (check available in csd.tran_speed) -+ */ -+ -+#define MMC_INIT_DOING 0 -+#define MMC_INIT_PASSED 1 -+#define MMC_INIT_FAILED 2 -+ -+static int mmc_init_card_state(struct mmc_request *request) -+{ -+ struct mmc_response_r1 r1; -+ struct mmc_response_r3 r3; -+ int retval; -+ int ocr = 0x40300000; -+ int limit_41 = 0; -+ -+ switch (request->cmd) { -+ case MMC_CMD_GO_IDLE_STATE: /* No response to parse */ -+ if (mmcinfo.sd) -+ mmc_simple_cmd(request, 8, 0x1aa, RESPONSE_R1); -+ else -+ mmc_simple_cmd(request, MMC_CMD_SEND_OP_COND, MMC_OCR_ARG, RESPONSE_R3); -+ break; -+ -+ case 8: -+ retval = mmc_unpack_r1(request,&r1,mmcinfo.state); -+ mmc_simple_cmd(request, MMC_CMD_APP_CMD, 0, RESPONSE_R1); -+ break; -+ -+ case MMC_CMD_APP_CMD: -+ retval = mmc_unpack_r1(request,&r1,mmcinfo.state); -+ if (retval & (limit_41 < 100)) { -+ debug("%s: unable to MMC_APP_CMD error=%d (%s)\n", -+ __func__, retval, mmc_result_to_string(retval)); -+ limit_41++; -+ mmc_simple_cmd(request, SD_CMD_APP_SEND_OP_COND, ocr, RESPONSE_R3); -+ } else if (limit_41 < 100) { -+ limit_41++; -+ mmc_simple_cmd(request, SD_CMD_APP_SEND_OP_COND, ocr, RESPONSE_R3); -+ } else{ -+ /* reset the card to idle*/ -+ mmc_simple_cmd(request, MMC_CMD_GO_IDLE_STATE, 0, RESPONSE_NONE); -+ mmcinfo.sd = 0; -+ } -+ break; -+ -+ case SD_CMD_APP_SEND_OP_COND: -+ retval = mmc_unpack_r3(request, &r3); -+ if (retval) { -+ debug("%s: try MMC card\n", __func__); -+ mmc_simple_cmd(request, SD_CMD_APP_SEND_OP_COND, MMC_OCR_ARG, RESPONSE_R3); -+ break; -+ } -+ -+ debug("%s: read ocr value = 0x%08x\n", __func__, r3.ocr); -+ -+ if(!(r3.ocr & MMC_CARD_BUSY || ocr == 0)){ -+ udelay(50000); -+ mmc_simple_cmd(request, MMC_CMD_APP_CMD, 0, RESPONSE_R1); -+ } else { -+ mmcinfo.sd = 1; /* SD Card ready */ -+ mmcinfo.state = CARD_STATE_READY; -+ mmc_simple_cmd(request, MMC_CMD_ALL_SEND_CID, 0, RESPONSE_R2_CID); -+ } -+ break; -+ -+ case MMC_CMD_SEND_OP_COND: -+ retval = mmc_unpack_r3(request, &r3); -+ if (retval) { -+ debug("%s: failed SEND_OP_COND error=%d (%s)\n", -+ __func__, retval, mmc_result_to_string(retval)); -+ return MMC_INIT_FAILED; -+ } -+ -+ debug("%s: read ocr value = 0x%08x\n", __func__, r3.ocr); -+ if (!(r3.ocr & MMC_CARD_BUSY)) { -+ mmc_simple_cmd(request, MMC_CMD_SEND_OP_COND, MMC_OCR_ARG, RESPONSE_R3); -+ } else { -+ mmcinfo.sd = 0; /* MMC Card ready */ -+ mmcinfo.state = CARD_STATE_READY; -+ mmc_simple_cmd(request, MMC_CMD_ALL_SEND_CID, 0, RESPONSE_R2_CID); -+ } -+ break; -+ -+ case MMC_CMD_ALL_SEND_CID: -+ retval = mmc_unpack_cid( request, &mmcinfo.cid ); -+ /*FIXME:ignore CRC error for CMD2/CMD9/CMD10 */ -+ if ( retval && (retval != MMC_ERROR_CRC)) { -+ debug("mmc_init_card_state: unable to ALL_SEND_CID error=%d (%s)\n", -+ retval, mmc_result_to_string(retval)); -+ return MMC_INIT_FAILED; -+ } -+ mmcinfo.state = CARD_STATE_IDENT; -+ if(mmcinfo.sd) -+ mmc_simple_cmd(request, MMC_CMD_SET_RELATIVE_ADDR, 0, RESPONSE_R6); -+ else -+ mmc_simple_cmd(request, MMC_CMD_SET_RELATIVE_ADDR, ID_TO_RCA(mmcinfo.id) << 16, RESPONSE_R1); -+ break; -+ -+ case MMC_CMD_SET_RELATIVE_ADDR: -+ if (mmcinfo.sd) { -+ retval = mmc_unpack_r6(request, &r1, mmcinfo.state, &mmcinfo.rca); -+ mmcinfo.rca = mmcinfo.rca << 16; -+ debug("%s: Get RCA from SD: 0x%04x Status: %x\n", -+ __func__, mmcinfo.rca, r1.status); -+ } else { -+ retval = mmc_unpack_r1(request,&r1,mmcinfo.state); -+ mmcinfo.rca = ID_TO_RCA(mmcinfo.id) << 16; -+ } -+ if (retval) { -+ debug("%s: unable to SET_RELATIVE_ADDR error=%d (%s)\n", -+ __func__, retval, mmc_result_to_string(retval)); -+ return MMC_INIT_FAILED; -+ } -+ -+ mmcinfo.state = CARD_STATE_STBY; -+ mmc_simple_cmd(request, MMC_CMD_SEND_CSD, mmcinfo.rca, RESPONSE_R2_CSD); -+ -+ break; -+ -+ case MMC_CMD_SEND_CSD: -+ retval = mmc_unpack_csd(request, &mmcinfo.csd); -+ mmc_ready = 1; -+ /*FIXME:ignore CRC error for CMD2/CMD9/CMD10 */ -+ if (retval && (retval != MMC_ERROR_CRC)) { -+ debug("%s: unable to SEND_CSD error=%d (%s)\n", -+ __func__, retval, mmc_result_to_string(retval)); -+ return MMC_INIT_FAILED; -+ } -+ if (mmcinfo.csd.dsr_imp) { -+ debug("%s: driver doesn't support setting DSR\n", __func__); -+ } -+ mmc_configure_card(); -+ return MMC_INIT_PASSED; -+ -+ default: -+ debug("%s: error! Illegal last cmd %d\n", __func__, request->cmd); -+ return MMC_INIT_FAILED; -+ } -+ -+ return MMC_INIT_DOING; -+} -+ -+int mmc_init_card(void) -+{ -+ struct mmc_request request; -+ int retval; -+ -+ mmc_simple_cmd(&request, MMC_CIM_RESET, 0, RESPONSE_NONE); /* reset card */ -+ mmc_simple_cmd(&request, MMC_CMD_GO_IDLE_STATE, 0, RESPONSE_NONE); -+ mmcinfo.sd = 1; /* assuming a SD card */ -+ -+ while ((retval = mmc_init_card_state(&request)) == MMC_INIT_DOING) -+ ; -+ -+ if (retval == MMC_INIT_PASSED) -+ return MMC_NO_ERROR; -+ else -+ return MMC_NO_RESPONSE; -+} -+ -+int mmc_legacy_init(int verbose) -+{ -+ if (!__msc_card_detected()) -+ return 1; -+ -+ /* Step-1: init GPIO */ -+ __gpio_as_msc(); -+ __msc_init_io(); -+ -+ /* Step-2: turn on power of card */ -+#if !defined(CONFIG_SAKC) -+ __msc_enable_power(); -+#endif -+ -+ /* Step-3: Reset MSC Controller. */ -+ __msc_reset(); -+ -+ /* Step-3: mask all IRQs. */ -+ MMC_IRQ_MASK(); -+ -+ /* Step-4: stop MMC/SD clock */ -+ jz_mmc_stop_clock(); -+ mmc_init_card(); -+ mmc_select_card(); -+ -+ mmc_dev.block_read = mmc_bread; -+ fat_register_device(&mmc_dev,1); /* partitions start counting with 1 */ -+ -+ return 0; -+} -+ -+/* -+ * Debugging functions -+ */ -+static char * mmc_result_strings[] = { -+ "NO_RESPONSE", -+ "NO_ERROR", -+ "ERROR_OUT_OF_RANGE", -+ "ERROR_ADDRESS", -+ "ERROR_BLOCK_LEN", -+ "ERROR_ERASE_SEQ", -+ "ERROR_ERASE_PARAM", -+ "ERROR_WP_VIOLATION", -+ "ERROR_CARD_IS_LOCKED", -+ "ERROR_LOCK_UNLOCK_FAILED", -+ "ERROR_COM_CRC", -+ "ERROR_ILLEGAL_COMMAND", -+ "ERROR_CARD_ECC_FAILED", -+ "ERROR_CC", -+ "ERROR_GENERAL", -+ "ERROR_UNDERRUN", -+ "ERROR_OVERRUN", -+ "ERROR_CID_CSD_OVERWRITE", -+ "ERROR_STATE_MISMATCH", -+ "ERROR_HEADER_MISMATCH", -+ "ERROR_TIMEOUT", -+ "ERROR_CRC", -+ "ERROR_DRIVER_FAILURE", -+}; -+ -+char * mmc_result_to_string(int i) -+{ -+ return mmc_result_strings[i+1]; -+} -+ -+static char * card_state_strings[] = { -+ "empty", -+ "idle", -+ "ready", -+ "ident", -+ "stby", -+ "tran", -+ "data", -+ "rcv", -+ "prg", -+ "dis", -+}; -+ -+static inline char * card_state_to_string(int i) -+{ -+ return card_state_strings[i+1]; -+} -+ -+/* -+ * Utility functions -+ */ -+ -+#define PARSE_U32(_buf,_index) \ -+ (((u32)_buf[_index]) << 24) | (((u32)_buf[_index+1]) << 16) | \ -+ (((u32)_buf[_index+2]) << 8) | ((u32)_buf[_index+3]); -+ -+#define PARSE_U16(_buf,_index) \ -+ (((u16)_buf[_index]) << 8) | ((u16)_buf[_index+1]); -+ -+int mmc_unpack_csd(struct mmc_request *request, struct mmc_csd *csd) -+{ -+ u8 *buf = request->response; -+ int num = 0; -+ -+ if (request->result) -+ return request->result; -+ -+ if (buf[0] != 0x3f) -+ return MMC_ERROR_HEADER_MISMATCH; -+ -+ csd->csd_structure = (buf[1] & 0xc0) >> 6; -+ if (csd->csd_structure) -+ sd2_0 = 1; -+ else -+ sd2_0 = 0; -+ -+ switch (csd->csd_structure) { -+ case 0 :/* Version 1.01-1.10 -+ * Version 2.00/Standard Capacity */ -+ csd->taac = buf[2]; -+ csd->nsac = buf[3]; -+ csd->tran_speed = buf[4]; -+ csd->ccc = (((u16)buf[5]) << 4) | ((buf[6] & 0xf0) >> 4); -+ csd->read_bl_len = buf[6] & 0x0f; -+ /* for support 2GB card*/ -+ if (csd->read_bl_len >= 10) -+ { -+ num = csd->read_bl_len - 9; -+ csd->read_bl_len = 9; -+ } -+ -+ csd->read_bl_partial = (buf[7] & 0x80) ? 1 : 0; -+ csd->write_blk_misalign = (buf[7] & 0x40) ? 1 : 0; -+ csd->read_blk_misalign = (buf[7] & 0x20) ? 1 : 0; -+ csd->dsr_imp = (buf[7] & 0x10) ? 1 : 0; -+ csd->c_size = ((((u16)buf[7]) & 0x03) << 10) | (((u16)buf[8]) << 2) | (((u16)buf[9]) & 0xc0) >> 6; -+ -+ if (num) -+ csd->c_size = csd->c_size << num; -+ -+ -+ csd->vdd_r_curr_min = (buf[9] & 0x38) >> 3; -+ csd->vdd_r_curr_max = buf[9] & 0x07; -+ csd->vdd_w_curr_min = (buf[10] & 0xe0) >> 5; -+ csd->vdd_w_curr_max = (buf[10] & 0x1c) >> 2; -+ csd->c_size_mult = ((buf[10] & 0x03) << 1) | ((buf[11] & 0x80) >> 7); -+ csd->sector_size = (buf[11] & 0x7c) >> 2; -+ csd->erase_grp_size = ((buf[11] & 0x03) << 3) | ((buf[12] & 0xe0) >> 5); -+ csd->wp_grp_size = buf[12] & 0x1f; -+ csd->wp_grp_enable = (buf[13] & 0x80) ? 1 : 0; -+ csd->default_ecc = (buf[13] & 0x60) >> 5; -+ csd->r2w_factor = (buf[13] & 0x1c) >> 2; -+ csd->write_bl_len = ((buf[13] & 0x03) << 2) | ((buf[14] & 0xc0) >> 6); -+ if (csd->write_bl_len >= 10) -+ csd->write_bl_len = 9; -+ -+ csd->write_bl_partial = (buf[14] & 0x20) ? 1 : 0; -+ csd->file_format_grp = (buf[15] & 0x80) ? 1 : 0; -+ csd->copy = (buf[15] & 0x40) ? 1 : 0; -+ csd->perm_write_protect = (buf[15] & 0x20) ? 1 : 0; -+ csd->tmp_write_protect = (buf[15] & 0x10) ? 1 : 0; -+ csd->file_format = (buf[15] & 0x0c) >> 2; -+ csd->ecc = buf[15] & 0x03; -+ break; -+ case 1 : /* Version 2.00/High Capacity */ -+ csd->taac = 0; -+ csd->nsac = 0; -+ csd->tran_speed = buf[4]; -+ csd->ccc = (((u16)buf[5]) << 4) | ((buf[6] & 0xf0) >> 4); -+ -+ csd->read_bl_len = 9; -+ csd->read_bl_partial = 0; -+ csd->write_blk_misalign = 0; -+ csd->read_blk_misalign = 0; -+ csd->dsr_imp = (buf[7] & 0x10) ? 1 : 0; -+ csd->c_size = ((((u16)buf[8]) & 0x3f) << 16) | (((u16)buf[9]) << 8) | ((u16)buf[10]) ; -+ csd->sector_size = 0x7f; -+ csd->erase_grp_size = 0; -+ csd->wp_grp_size = 0; -+ csd->wp_grp_enable = 0; -+ csd->default_ecc = (buf[13] & 0x60) >> 5; -+ csd->r2w_factor = 4;/* Unused */ -+ csd->write_bl_len = 9; -+ -+ csd->write_bl_partial = 0; -+ csd->file_format_grp = 0; -+ csd->copy = (buf[15] & 0x40) ? 1 : 0; -+ csd->perm_write_protect = (buf[15] & 0x20) ? 1 : 0; -+ csd->tmp_write_protect = (buf[15] & 0x10) ? 1 : 0; -+ csd->file_format = 0; -+ csd->ecc = buf[15] & 0x03; -+ } -+ -+ return 0; -+} -+ -+int mmc_unpack_r1(struct mmc_request *request, struct mmc_response_r1 *r1, enum card_state state) -+{ -+ u8 *buf = request->response; -+ -+ if (request->result) -+ return request->result; -+ -+ r1->cmd = buf[0]; -+ r1->status = PARSE_U32(buf,1); -+ -+ debug("mmc_unpack_r1: cmd=%d status=%08x\n", r1->cmd, r1->status); -+ -+ if (R1_STATUS(r1->status)) { -+ if (r1->status & R1_OUT_OF_RANGE) return MMC_ERROR_OUT_OF_RANGE; -+ if (r1->status & R1_ADDRESS_ERROR) return MMC_ERROR_ADDRESS; -+ if (r1->status & R1_BLOCK_LEN_ERROR) return MMC_ERROR_BLOCK_LEN; -+ if (r1->status & R1_ERASE_SEQ_ERROR) return MMC_ERROR_ERASE_SEQ; -+ if (r1->status & R1_ERASE_PARAM) return MMC_ERROR_ERASE_PARAM; -+ if (r1->status & R1_WP_VIOLATION) return MMC_ERROR_WP_VIOLATION; -+ /*if (r1->status & R1_CARD_IS_LOCKED) return MMC_ERROR_CARD_IS_LOCKED; */ -+ if (r1->status & R1_LOCK_UNLOCK_FAILED) return MMC_ERROR_LOCK_UNLOCK_FAILED; -+ if (r1->status & R1_COM_CRC_ERROR) return MMC_ERROR_COM_CRC; -+ if (r1->status & R1_ILLEGAL_COMMAND) return MMC_ERROR_ILLEGAL_COMMAND; -+ if (r1->status & R1_CARD_ECC_FAILED) return MMC_ERROR_CARD_ECC_FAILED; -+ if (r1->status & R1_CC_ERROR) return MMC_ERROR_CC; -+ if (r1->status & R1_ERROR) return MMC_ERROR_GENERAL; -+ if (r1->status & R1_UNDERRUN) return MMC_ERROR_UNDERRUN; -+ if (r1->status & R1_OVERRUN) return MMC_ERROR_OVERRUN; -+ if (r1->status & R1_CID_CSD_OVERWRITE) return MMC_ERROR_CID_CSD_OVERWRITE; -+ } -+ -+ if (buf[0] != request->cmd) -+ return MMC_ERROR_HEADER_MISMATCH; -+ -+ /* This should be last - it's the least dangerous error */ -+ -+ return 0; -+} -+ -+int mmc_unpack_scr(struct mmc_request *request, struct mmc_response_r1 *r1, enum card_state state, u32 *scr) -+{ -+ u8 *buf = request->response; -+ if (request->result) -+ return request->result; -+ -+ *scr = PARSE_U32(buf, 5); /* Save SCR returned by the SD Card */ -+ return mmc_unpack_r1(request, r1, state); -+ -+} -+ -+int mmc_unpack_r6(struct mmc_request *request, struct mmc_response_r1 *r1, enum card_state state, int *rca) -+{ -+ u8 *buf = request->response; -+ -+ if (request->result) -+ return request->result; -+ -+ *rca = PARSE_U16(buf,1); /* Save RCA returned by the SD Card */ -+ -+ *(buf+1) = 0; -+ *(buf+2) = 0; -+ -+ return mmc_unpack_r1(request, r1, state); -+} -+ -+int mmc_unpack_cid(struct mmc_request *request, struct mmc_cid *cid) -+{ -+ int i; -+ u8 *buf = request->response; -+ -+ if (request->result) -+ return request->result; -+ -+ cid->mid = buf[1]; -+ cid->oid = PARSE_U16(buf,2); -+ for (i = 0 ; i < 5 ; i++) -+ cid->pnm[i] = buf[4+i]; -+ cid->pnm[6] = 0; -+ cid->prv = buf[10]; -+ cid->psn = PARSE_U32(buf,10); -+ cid->mdt = buf[15]; -+ -+ printf("Man %02x OEM 0x%04x \"%s\" %d.%d 0x%08x " -+ "Date %02u/%04u\n", -+ cid->mid, -+ cid->oid, -+ cid->pnm, -+ cid->prv >> 4, -+ cid->prv & 0xf, -+ cid->psn, -+ cid->mdt & 0xf, -+ (cid->mdt >> 4) + 2000); -+ -+ if (buf[0] != 0x3f) -+ return MMC_ERROR_HEADER_MISMATCH; -+ return 0; -+} -+ -+int mmc_unpack_r3(struct mmc_request *request, struct mmc_response_r3 *r3) -+{ -+ u8 *buf = request->response; -+ -+ if (request->result) -+ return request->result; -+ -+ r3->ocr = PARSE_U32(buf,1); -+ debug("mmc_unpack_r3: ocr=%08x\n", r3->ocr); -+ -+ if (buf[0] != 0x3f) return MMC_ERROR_HEADER_MISMATCH; -+ return 0; -+} -+ -+#define KBPS 1 -+#define MBPS 1000 -+ -+static u32 ts_exp[] = { 100*KBPS, 1*MBPS, 10*MBPS, 100*MBPS, 0, 0, 0, 0 }; -+static u32 ts_mul[] = { 0, 1000, 1200, 1300, 1500, 2000, 2500, 3000, -+ 3500, 4000, 4500, 5000, 5500, 6000, 7000, 8000 }; -+ -+u32 mmc_tran_speed(u8 ts) -+{ -+ u32 rate = ts_exp[(ts & 0x7)] * ts_mul[(ts & 0x78) >> 3]; -+ -+ if (rate <= 0) { -+ debug("%s: error - unrecognized speed 0x%02x\n", __func__, ts); -+ return 1; -+ } -+ -+ return rate; -+} -+ -+void mmc_send_cmd(struct mmc_request *request, int cmd, u32 arg, -+ u16 nob, u16 block_len, enum mmc_rsp_t rtype, u8 *buffer) -+{ -+ request->cmd = cmd; -+ request->arg = arg; -+ request->rtype = rtype; -+ request->nob = nob; -+ request->block_len = block_len; -+ request->buffer = buffer; -+ request->cnt = nob * block_len; -+ -+ jz_mmc_exec_cmd(request); -+} -diff --git a/drivers/mmc/jz_mmc.h b/drivers/mmc/jz_mmc.h -new file mode 100644 -index 0000000..936c514 ---- /dev/null -+++ b/drivers/mmc/jz_mmc.h -@@ -0,0 +1,176 @@ -+/* -+ * linux/drivers/mmc/jz_mmc.h -+ * -+ * Author: Vladimir Shebordaev, Igor Oblakov -+ * Copyright: MontaVista Software Inc. -+ * -+ * $Id: jz_mmc.h,v 1.3 2007-06-15 08:04:20 jlwei Exp $ -+ * -+ * This program is free software; you can redistribute it and/or modify -+ * it under the terms of the GNU General Public License version 2 as -+ * published by the Free Software Foundation. -+ */ -+#ifndef __MMC_JZMMC_H__ -+#define __MMC_JZMMC_H__ -+ -+#define ID_TO_RCA(x) ((x)+1) -+#define MMC_OCR_ARG 0x00ff8000 /* Argument of OCR */ -+ -+/* Standard MMC/SD clock speeds */ -+#define MMC_CLOCK_SLOW 400000 /* 400 kHz for initial setup */ -+#define MMC_CLOCK_FAST 20000000 /* 20 MHz for maximum for normal operation */ -+#define SD_CLOCK_FAST 24000000 /* 24 MHz for SD Cards */ -+ -+/* Use negative numbers to disambiguate */ -+#define MMC_CIM_RESET -1 -+#define SET_BUS_WIDTH 6 /* ac [1:0] bus width R1 */ -+ -+#define R1_OUT_OF_RANGE (1 << 31) /* er, c */ -+#define R1_ADDRESS_ERROR (1 << 30) /* erx, c */ -+#define R1_BLOCK_LEN_ERROR (1 << 29) /* er, c */ -+#define R1_ERASE_SEQ_ERROR (1 << 28) /* er, c */ -+#define R1_ERASE_PARAM (1 << 27) /* ex, c */ -+#define R1_WP_VIOLATION (1 << 26) /* erx, c */ -+#define R1_CARD_IS_LOCKED (1 << 25) /* sx, a */ -+#define R1_LOCK_UNLOCK_FAILED (1 << 24) /* erx, c */ -+#define R1_COM_CRC_ERROR (1 << 23) /* er, b */ -+#define R1_ILLEGAL_COMMAND (1 << 22) /* er, b */ -+#define R1_CARD_ECC_FAILED (1 << 21) /* ex, c */ -+#define R1_CC_ERROR (1 << 20) /* erx, c */ -+#define R1_ERROR (1 << 19) /* erx, c */ -+#define R1_UNDERRUN (1 << 18) /* ex, c */ -+#define R1_OVERRUN (1 << 17) /* ex, c */ -+#define R1_CID_CSD_OVERWRITE (1 << 16) /* erx, c, CID/CSD overwrite */ -+#define R1_WP_ERASE_SKIP (1 << 15) /* sx, c */ -+#define R1_CARD_ECC_DISABLED (1 << 14) /* sx, a */ -+#define R1_ERASE_RESET (1 << 13) /* sr, c */ -+#define R1_STATUS(x) (x & 0xFFFFE000) -+ -+#define MMC_CARD_BUSY 0x80000000 /* Card Power up status bit */ -+ -+#define MMC_PROGRAM_CID 26 /* adtc R1 */ -+#define MMC_PROGRAM_CSD 27 /* adtc R1 */ -+ -+#define MMC_GO_IRQ_STATE 40 /* bcr R5 */ -+#define MMC_GEN_CMD 56 /* adtc [0] RD/WR R1b */ -+#define MMC_LOCK_UNLOCK 42 /* adtc R1b */ -+#define MMC_WRITE_DAT_UNTIL_STOP 20 /* adtc [31:0] data addr R1 */ -+#define MMC_READ_DAT_UNTIL_STOP 11 /* adtc [31:0] dadr R1 */ -+#define MMC_SEND_WRITE_PROT 30 /* adtc [31:0] wpdata addr R1 */ -+ -+ -+enum mmc_result_t { -+ MMC_NO_RESPONSE = -1, -+ MMC_NO_ERROR = 0, -+ MMC_ERROR_OUT_OF_RANGE, -+ MMC_ERROR_ADDRESS, -+ MMC_ERROR_BLOCK_LEN, -+ MMC_ERROR_ERASE_SEQ, -+ MMC_ERROR_ERASE_PARAM, -+ MMC_ERROR_WP_VIOLATION, -+ MMC_ERROR_CARD_IS_LOCKED, -+ MMC_ERROR_LOCK_UNLOCK_FAILED, -+ MMC_ERROR_COM_CRC, -+ MMC_ERROR_ILLEGAL_COMMAND, -+ MMC_ERROR_CARD_ECC_FAILED, -+ MMC_ERROR_CC, -+ MMC_ERROR_GENERAL, -+ MMC_ERROR_UNDERRUN, -+ MMC_ERROR_OVERRUN, -+ MMC_ERROR_CID_CSD_OVERWRITE, -+ MMC_ERROR_STATE_MISMATCH, -+ MMC_ERROR_HEADER_MISMATCH, -+ MMC_ERROR_TIMEOUT, -+ MMC_ERROR_CRC, -+ MMC_ERROR_DRIVER_FAILURE, -+}; -+ -+enum card_state { -+ CARD_STATE_EMPTY = -1, -+ CARD_STATE_IDLE = 0, -+ CARD_STATE_READY = 1, -+ CARD_STATE_IDENT = 2, -+ CARD_STATE_STBY = 3, -+ CARD_STATE_TRAN = 4, -+ CARD_STATE_DATA = 5, -+ CARD_STATE_RCV = 6, -+ CARD_STATE_PRG = 7, -+ CARD_STATE_DIS = 8, -+}; -+ -+enum mmc_rsp_t { -+ RESPONSE_NONE = 0, -+ RESPONSE_R1 = 1, -+ RESPONSE_R1B = 2, -+ RESPONSE_R2_CID = 3, -+ RESPONSE_R2_CSD = 4, -+ RESPONSE_R3 = 5, -+ RESPONSE_R4 = 6, -+ RESPONSE_R5 = 7, -+ RESPONSE_R6 = 8, -+}; -+ -+struct mmc_response_r1 { -+ u8 cmd; -+ u32 status; -+}; -+ -+struct mmc_response_r3 { -+ u32 ocr; -+}; -+ -+/* the information structure of MMC/SD Card */ -+struct mmc_info { -+ int id; /* Card index */ -+ int sd; /* MMC or SD card */ -+ int rca; /* RCA */ -+ u32 scr; /* SCR 63:32*/ -+ int flags; /* Ejected, inserted */ -+ enum card_state state; /* empty, ident, ready, whatever */ -+ -+ /* Card specific information */ -+ struct mmc_cid cid; -+ struct mmc_csd csd; -+ u32 block_num; -+ u32 block_len; -+ u32 erase_unit; -+}; -+ -+struct mmc_info mmcinfo; -+ -+struct mmc_request { -+ int index; /* Slot index - used for CS lines */ -+ int cmd; /* Command to send */ -+ u32 arg; /* Argument to send */ -+ enum mmc_rsp_t rtype; /* Response type expected */ -+ -+ /* Data transfer (these may be modified at the low level) */ -+ u16 nob; /* Number of blocks to transfer*/ -+ u16 block_len; /* Block length */ -+ u8 *buffer; /* Data buffer */ -+ u32 cnt; /* Data length, for PIO */ -+ -+ /* Results */ -+ u8 response[18]; /* Buffer to store response - CRC is optional */ -+ enum mmc_result_t result; -+}; -+ -+char * mmc_result_to_string(int); -+int mmc_unpack_csd(struct mmc_request *request, struct mmc_csd *csd); -+int mmc_unpack_r1(struct mmc_request *request, struct mmc_response_r1 *r1, enum card_state state); -+int mmc_unpack_r6(struct mmc_request *request, struct mmc_response_r1 *r1, enum card_state state, int *rca); -+int mmc_unpack_scr(struct mmc_request *request, struct mmc_response_r1 *r1, enum card_state state, u32 *scr); -+int mmc_unpack_cid(struct mmc_request *request, struct mmc_cid *cid); -+int mmc_unpack_r3(struct mmc_request *request, struct mmc_response_r3 *r3); -+ -+void mmc_send_cmd(struct mmc_request *request, int cmd, u32 arg, -+ u16 nob, u16 block_len, enum mmc_rsp_t rtype, u8 *buffer); -+u32 mmc_tran_speed(u8 ts); -+void jz_mmc_set_clock(int sd, u32 rate); -+ -+static inline void mmc_simple_cmd(struct mmc_request *request, int cmd, u32 arg, enum mmc_rsp_t rtype) -+{ -+ mmc_send_cmd( request, cmd, arg, 0, 0, rtype, 0); -+} -+ -+#endif /* __MMC_JZMMC_H__ */ -diff --git a/include/configs/qi_lb60.h b/include/configs/qi_lb60.h -index 7bff444..7b33be0 100644 ---- a/include/configs/qi_lb60.h -+++ b/include/configs/qi_lb60.h -@@ -31,6 +31,15 @@ - /* - * Miscellaneous configurable options - */ -+#define CONFIG_JZ4740_MMC -+#define CONFIG_MMC 1 -+#define CONFIG_FAT 1 -+#define CONFIG_DOS_PARTITION 1 -+#define CONFIG_CMD_MMC -+#define CONFIG_CMD_FAT -+#define CONFIG_CMD_EXT2 -+ -+ - #define CONFIG_SYS_SDRAM_BASE 0x80000000 /* Cached addr */ - #define CONFIG_SYS_INIT_SP_OFFSET 0x400000 - #define CONFIG_SYS_LOAD_ADDR 0x80600000 -diff --git a/include/mmc.h b/include/mmc.h -index a13e2bd..3c4761c 100644 ---- a/include/mmc.h -+++ b/include/mmc.h -@@ -283,4 +283,44 @@ struct mmc *mmc_spi_init(uint bus, uint cs, uint speed, uint mode); - int mmc_legacy_init(int verbose); - #endif - -+struct mmc_csd -+{ -+ u8 csd_structure:2, -+ spec_vers:4, -+ rsvd1:2; -+ u8 taac; -+ u8 nsac; -+ u8 tran_speed; -+ u16 ccc:12, -+ read_bl_len:4; -+ u32 c_size:22; -+ u64 read_bl_partial:1, -+ write_blk_misalign:1, -+ read_blk_misalign:1, -+ dsr_imp:1, -+ rsvd2:2, -+ vdd_r_curr_min:3, -+ vdd_r_curr_max:3, -+ vdd_w_curr_min:3, -+ vdd_w_curr_max:3, -+ c_size_mult:3, -+ sector_size:5, -+ erase_grp_size:5, -+ wp_grp_size:5, -+ wp_grp_enable:1, -+ default_ecc:2, -+ r2w_factor:3, -+ write_bl_len:4, -+ write_bl_partial:1, -+ rsvd3:5; -+ u8 file_format_grp:1, -+ copy:1, -+ perm_write_protect:1, -+ tmp_write_protect:1, -+ file_format:2, -+ ecc:2; -+ u8 crc:7; -+ u8 one:1; -+}; -+ - #endif /* _MMC_H_ */ --- -1.7.9.5 - diff --git a/package/boot/uboot-xburst/patches/0004-add-more-boot-options-F1-F2-F3-F4-M-S.patch b/package/boot/uboot-xburst/patches/0004-add-more-boot-options-F1-F2-F3-F4-M-S.patch deleted file mode 100644 index 73e03243c3..0000000000 --- a/package/boot/uboot-xburst/patches/0004-add-more-boot-options-F1-F2-F3-F4-M-S.patch +++ /dev/null @@ -1,200 +0,0 @@ -From c52b6168979d03fc31205444c3278c537787472a Mon Sep 17 00:00:00 2001 -From: Xiangfu <xiangfu@openmobilefree.net> -Date: Wed, 10 Oct 2012 18:39:55 +0800 -Subject: [PATCH 4/6] add more boot options(F1/F2/F3/F4/M/S) - ---- - arch/mips/include/asm/global_data.h | 3 +++ - arch/mips/lib/bootm.c | 17 ++++++++++++++++- - board/qi/qi_lb60/qi_lb60.c | 26 +++++++++++++++++++++++--- - common/main.c | 21 +++++++++++++++++++-- - include/configs/qi_lb60.h | 32 ++++++++++++++++++++++++++++++++ - 5 files changed, 93 insertions(+), 6 deletions(-) - -diff --git a/arch/mips/include/asm/global_data.h b/arch/mips/include/asm/global_data.h -index 6e2cdc7..cd03d7e 100644 ---- a/arch/mips/include/asm/global_data.h -+++ b/arch/mips/include/asm/global_data.h -@@ -59,6 +59,9 @@ typedef struct global_data { - unsigned long env_valid; /* Checksum of Environment valid? */ - void **jt; /* jump table */ - char env_buf[32]; /* buffer for getenv() before reloc. */ -+#if defined(CONFIG_NANONOTE) -+ unsigned long boot_option; -+#endif - } gd_t; - - #include <asm-generic/global_data_flags.h> -diff --git a/arch/mips/lib/bootm.c b/arch/mips/lib/bootm.c -index 608c1a7..e00416b 100644 ---- a/arch/mips/lib/bootm.c -+++ b/arch/mips/lib/bootm.c -@@ -47,10 +47,25 @@ int do_bootm_linux(int flag, int argc, char * const argv[], - bootm_headers_t *images) - { - void (*theKernel) (int, char **, char **, int *); -- char *commandline = getenv("bootargs"); -+ char *commandline; - char env_buf[12]; - char *cp; - -+#if defined(CONFIG_NANONOTE) -+ if (gd->boot_option & BOOT_FROM_MEMCARD) -+ commandline = getenv ("bootargsfromsd"); -+ else if (gd->boot_option & BOOT_WITH_F1) -+ commandline = getenv ("bootargsf1"); -+ else if (gd->boot_option & BOOT_WITH_F2) -+ commandline = getenv ("bootargsf2"); -+ else if (gd->boot_option & BOOT_WITH_F3) -+ commandline = getenv ("bootargsf3"); -+ else if (gd->boot_option & BOOT_WITH_F4) -+ commandline = getenv ("bootargsf4"); -+ else -+#endif -+ commandline = getenv ("bootargs"); -+ - if ((flag != 0) && (flag != BOOTM_STATE_OS_GO)) - return 1; - -diff --git a/board/qi/qi_lb60/qi_lb60.c b/board/qi/qi_lb60/qi_lb60.c -index a2ba648..d622219 100644 ---- a/board/qi/qi_lb60/qi_lb60.c -+++ b/board/qi/qi_lb60/qi_lb60.c -@@ -15,7 +15,7 @@ DECLARE_GLOBAL_DATA_PTR; - - static void gpio_init(void) - { -- unsigned int i; -+ unsigned int i, j; - - /* Initialize NAND Flash Pins */ - __gpio_as_nand(); -@@ -42,14 +42,34 @@ static void gpio_init(void) - - if (__gpio_get_pin(GPIO_KEYIN_BASE + 2) == 0){ - printf("[S] pressed, enable UART0\n"); -+ gd->boot_option |= BOOT_WITH_ENABLE_UART; - __gpio_as_uart0(); - } else { - __gpio_as_input(GPIO_KEYIN_8); - __gpio_enable_pull(GPIO_KEYIN_8); - } - -- /* enable the TP4, TP5 as UART0 */ -- __gpio_jtag_to_uart0(); -+ if (__gpio_get_pin(GPIO_KEYIN_BASE + 3) == 0) { -+ printf("[M] pressed, boot from memory card\n"); -+ gd->boot_option |= BOOT_FROM_MEMCARD; -+ __gpio_jtag_to_uart0(); -+ } -+ -+ for (j = 0; j < 4; j++) { -+ for (i = 0; i < 4; i++) -+ __gpio_set_pin(GPIO_KEYOUT_BASE + i); -+ -+ __gpio_clear_pin(GPIO_KEYOUT_BASE + j); -+ -+ if (__gpio_get_pin(GPIO_KEYIN_BASE) == 0) { -+ printf("[F%d] pressed", (j + 1)); -+ gd->boot_option |= (1 << (j + 2)); -+ /* BOOT_WITH_F1 (1 << 2) */ -+ /* BOOT_WITH_F2 (1 << 3) */ -+ /* BOOT_WITH_F3 (1 << 4) */ -+ /* BOOT_WITH_F4 (1 << 5) */ -+ } -+ } - - __gpio_as_output(GPIO_AUDIO_POP); - __gpio_set_pin(GPIO_AUDIO_POP); -diff --git a/common/main.c b/common/main.c -index 9507cec..dbfb7ca 100644 ---- a/common/main.c -+++ b/common/main.c -@@ -355,7 +355,11 @@ void main_loop (void) - #if defined(CONFIG_BOOTDELAY) && (CONFIG_BOOTDELAY >= 0) - s = getenv ("bootdelay"); - bootdelay = s ? (int)simple_strtol(s, NULL, 10) : CONFIG_BOOTDELAY; -- -+#if defined(CONFIG_NANONOTE) -+ DECLARE_GLOBAL_DATA_PTR; -+ if (gd->boot_option & BOOT_WITH_ENABLE_UART) -+ bootdelay = 3; -+# endif - debug ("### main_loop entered: bootdelay=%d\n\n", bootdelay); - - #if defined(CONFIG_MENU_SHOW) -@@ -379,7 +383,20 @@ void main_loop (void) - } - else - #endif /* CONFIG_BOOTCOUNT_LIMIT */ -- s = getenv ("bootcmd"); -+#if defined(CONFIG_NANONOTE) -+ if (gd->boot_option & BOOT_FROM_MEMCARD) -+ s = getenv ("bootcmdfromsd"); -+ else if (gd->boot_option & BOOT_WITH_F1) -+ s = getenv ("bootcmdf1"); -+ else if (gd->boot_option & BOOT_WITH_F2) -+ s = getenv ("bootcmdf2"); -+ else if (gd->boot_option & BOOT_WITH_F3) -+ s = getenv ("bootcmdf3"); -+ else if (gd->boot_option & BOOT_WITH_F4) -+ s = getenv ("bootcmdf4"); -+ else -+#endif -+ s = getenv ("bootcmd"); - - debug ("### main_loop: bootcmd=\"%s\"\n", s ? s : "<UNDEFINED>"); - -diff --git a/include/configs/qi_lb60.h b/include/configs/qi_lb60.h -index 7b33be0..52b370c 100644 ---- a/include/configs/qi_lb60.h -+++ b/include/configs/qi_lb60.h -@@ -31,6 +31,7 @@ - /* - * Miscellaneous configurable options - */ -+#define CONFIG_NANONOTE - #define CONFIG_JZ4740_MMC - #define CONFIG_MMC 1 - #define CONFIG_FAT 1 -@@ -39,6 +40,37 @@ - #define CONFIG_CMD_FAT - #define CONFIG_CMD_EXT2 - -+#define CONFIG_CMD_UBIFS -+#define CONFIG_CMD_UBI -+#define CONFIG_MTD_PARTITIONS -+#define CONFIG_MTD_DEVICE -+#define CONFIG_CMD_MTDPARTS -+#define CONFIG_CMD_UBI -+#define CONFIG_CMD_UBIFS -+#define CONFIG_LZO -+#define CONFIG_RBTREE -+ -+#define MTDIDS_DEFAULT "nand0=jz4740-nand" -+#define MTDPARTS_DEFAULT "mtdparts=jz4740-nand:4M@0(uboot)ro,4M@4M(kernel)ro,512M@8M(rootfs)ro,-(data)ro" -+ -+#define BOOT_FROM_MEMCARD 1 -+#define BOOT_WITH_ENABLE_UART (1 << 1) /* Vaule for global_data.h gd->boot_option */ -+#define BOOT_WITH_F1 (1 << 2) -+#define BOOT_WITH_F2 (1 << 3) -+#define BOOT_WITH_F3 (1 << 4) -+#define BOOT_WITH_F4 (1 << 5) -+ -+#define CONFIG_EXTRA_ENV_SETTINGS \ -+ "bootcmdfromsd=mmc init; ext2load mmc 0 0x80600000 /boot/uImage; bootm;\0" \ -+ "bootargsfromsd=mem=32M console=tty0 console=ttyS0,57600n8 rootfstype=ext2 root=/dev/mmcblk0p1 rw rootwait\0" \ -+ "bootcmdf1=mmc init; ext2load mmc 0:1 0x80600000 /boot/uImage; bootm;\0" \ -+ "bootargsf1=mem=32M console=tty0 console=ttyS0,57600n8 rootfstype=ext2 root=/dev/mmcblk0p1 rw rootwait\0" \ -+ "bootcmdf2=mmc init; ext2load mmc 0:2 0x80600000 /boot/uImage; bootm;\0" \ -+ "bootargsf2=mem=32M console=tty0 console=ttyS0,57600n8 rootfstype=ext2 root=/dev/mmcblk0p2 rw rootwait\0" \ -+ "bootcmdf3=mmc init; ext2load mmc 0:3 0x80600000 /boot/uImage; bootm;\0" \ -+ "bootargsf3=mem=32M console=tty0 console=ttyS0,57600n8 rootfstype=ext2 root=/dev/mmcblk0p3 rw rootwait\0" \ -+ "bootcmdf4=mtdparts default;ubi part rootfs;ubifsmount rootfs;ubifsload 0x80600000 /boot/uImage; bootm;\0" \ -+ "bootargsf4=mem=32M console=tty0 console=ttyS0,57600n8 ubi.mtd=2 rootfstype=ubifs root=ubi0:rootfs rw rootwait" - - #define CONFIG_SYS_SDRAM_BASE 0x80000000 /* Cached addr */ - #define CONFIG_SYS_INIT_SP_OFFSET 0x400000 --- -1.7.9.5 - diff --git a/package/boot/uboot-xburst/patches/0005-add-nanonote-lcd-support.patch b/package/boot/uboot-xburst/patches/0005-add-nanonote-lcd-support.patch deleted file mode 100644 index 2c550f7205..0000000000 --- a/package/boot/uboot-xburst/patches/0005-add-nanonote-lcd-support.patch +++ /dev/null @@ -1,847 +0,0 @@ -From ca8c5216cfd3ad3fda9867ed2d157ae5a209834b Mon Sep 17 00:00:00 2001 -From: Xiangfu <xiangfu@openmobilefree.net> -Date: Wed, 10 Oct 2012 22:05:27 +0800 -Subject: [PATCH 5/6] add nanonote lcd support - ---- - arch/mips/include/asm/global_data.h | 1 + - arch/mips/include/asm/jz4740.h | 90 ++++++++ - arch/mips/lib/board.c | 6 + - common/lcd.c | 9 +- - drivers/video/Makefile | 1 + - drivers/video/nanonote_gpm940b0.c | 400 +++++++++++++++++++++++++++++++++++ - drivers/video/nanonote_gpm940b0.h | 135 ++++++++++++ - include/configs/qi_lb60.h | 7 + - include/lcd.h | 52 ++++- - 9 files changed, 697 insertions(+), 4 deletions(-) - create mode 100644 drivers/video/nanonote_gpm940b0.c - create mode 100644 drivers/video/nanonote_gpm940b0.h - -diff --git a/arch/mips/include/asm/global_data.h b/arch/mips/include/asm/global_data.h -index cd03d7e..7cec2de 100644 ---- a/arch/mips/include/asm/global_data.h -+++ b/arch/mips/include/asm/global_data.h -@@ -44,6 +44,7 @@ typedef struct global_data { - unsigned long per_clk; /* Peripheral bus clock */ - unsigned long mem_clk; /* Memory bus clock */ - unsigned long dev_clk; /* Device clock */ -+ unsigned long fb_base; /* base address of framebuffer */ - /* "static data" needed by most of timer.c */ - unsigned long tbl; - unsigned long lastinc; -diff --git a/arch/mips/include/asm/jz4740.h b/arch/mips/include/asm/jz4740.h -index 68287fb..13724a2 100644 ---- a/arch/mips/include/asm/jz4740.h -+++ b/arch/mips/include/asm/jz4740.h -@@ -1312,5 +1312,95 @@ do { \ - while (REG_MSC_STAT & MSC_STAT_IS_RESETTING); \ - } while (0) - -+/************************************************************************* -+ * LCD (LCD Controller) -+ *************************************************************************/ -+#define REG32(addr) *((volatile u32 *)(addr)) -+ -+#define CPM_BASE 0xB0000000 -+#define CPM_CPCCR (CPM_BASE+0x00) -+#define REG_CPM_CPCCR REG32(CPM_CPCCR) -+ -+#define LCD_BASE 0xB3050000 -+#define LCD_CFG (LCD_BASE + 0x00) /* LCD Configure Register */ -+#define LCD_VSYNC (LCD_BASE + 0x04) /* Vertical Synchronize Register */ -+#define LCD_HSYNC (LCD_BASE + 0x08) /* Horizontal Synchronize Register */ -+#define LCD_VAT (LCD_BASE + 0x0c) /* Virtual Area Setting Register */ -+#define LCD_DAH (LCD_BASE + 0x10) /* Display Area Horizontal Start/End Point */ -+#define LCD_DAV (LCD_BASE + 0x14) /* Display Area Vertical Start/End Point */ -+#define LCD_PS (LCD_BASE + 0x18) /* PS Signal Setting */ -+#define LCD_CLS (LCD_BASE + 0x1c) /* CLS Signal Setting */ -+#define LCD_SPL (LCD_BASE + 0x20) /* SPL Signal Setting */ -+#define LCD_REV (LCD_BASE + 0x24) /* REV Signal Setting */ -+#define LCD_CTRL (LCD_BASE + 0x30) /* LCD Control Register */ -+#define LCD_STATE (LCD_BASE + 0x34) /* LCD Status Register */ -+#define LCD_IID (LCD_BASE + 0x38) /* Interrupt ID Register */ -+#define LCD_DA0 (LCD_BASE + 0x40) /* Descriptor Address Register 0 */ -+#define LCD_SA0 (LCD_BASE + 0x44) /* Source Address Register 0 */ -+#define LCD_FID0 (LCD_BASE + 0x48) /* Frame ID Register 0 */ -+#define LCD_CMD0 (LCD_BASE + 0x4c) /* DMA Command Register 0 */ -+#define LCD_DA1 (LCD_BASE + 0x50) /* Descriptor Address Register 1 */ -+#define LCD_SA1 (LCD_BASE + 0x54) /* Source Address Register 1 */ -+#define LCD_FID1 (LCD_BASE + 0x58) /* Frame ID Register 1 */ -+#define LCD_CMD1 (LCD_BASE + 0x5c) /* DMA Command Register 1 */ -+ -+#define REG_LCD_CFG REG32(LCD_CFG) -+#define REG_LCD_VSYNC REG32(LCD_VSYNC) -+#define REG_LCD_HSYNC REG32(LCD_HSYNC) -+#define REG_LCD_VAT REG32(LCD_VAT) -+#define REG_LCD_DAH REG32(LCD_DAH) -+#define REG_LCD_DAV REG32(LCD_DAV) -+#define REG_LCD_PS REG32(LCD_PS) -+#define REG_LCD_CLS REG32(LCD_CLS) -+#define REG_LCD_SPL REG32(LCD_SPL) -+#define REG_LCD_REV REG32(LCD_REV) -+#define REG_LCD_CTRL REG32(LCD_CTRL) -+#define REG_LCD_STATE REG32(LCD_STATE) -+#define REG_LCD_IID REG32(LCD_IID) -+#define REG_LCD_DA0 REG32(LCD_DA0) -+#define REG_LCD_SA0 REG32(LCD_SA0) -+#define REG_LCD_FID0 REG32(LCD_FID0) -+#define REG_LCD_CMD0 REG32(LCD_CMD0) -+#define REG_LCD_DA1 REG32(LCD_DA1) -+#define REG_LCD_SA1 REG32(LCD_SA1) -+#define REG_LCD_FID1 REG32(LCD_FID1) -+#define REG_LCD_CMD1 REG32(LCD_CMD1) -+ -+#define LCD_CTRL_BPP_BIT 0 /* Bits Per Pixel */ -+#define LCD_CTRL_BPP_MASK (0x07 << LCD_CTRL_BPP_BIT) -+ #define LCD_CTRL_BPP_1 (0 << LCD_CTRL_BPP_BIT) /* 1 bpp */ -+ #define LCD_CTRL_BPP_2 (1 << LCD_CTRL_BPP_BIT) /* 2 bpp */ -+ #define LCD_CTRL_BPP_4 (2 << LCD_CTRL_BPP_BIT) /* 4 bpp */ -+ #define LCD_CTRL_BPP_8 (3 << LCD_CTRL_BPP_BIT) /* 8 bpp */ -+ #define LCD_CTRL_BPP_16 (4 << LCD_CTRL_BPP_BIT) /* 15/16 bpp */ -+ #define LCD_CTRL_BPP_18_24 (5 << LCD_CTRL_BPP_BIT) /* 18/24/32 bpp */ -+ -+#define LCD_CTRL_BST_BIT 28 /* Burst Length Selection */ -+#define LCD_CTRL_BST_MASK (0x03 << LCD_CTRL_BST_BIT) -+ #define LCD_CTRL_BST_4 (0 << LCD_CTRL_BST_BIT) /* 4-word */ -+ #define LCD_CTRL_BST_8 (1 << LCD_CTRL_BST_BIT) /* 8-word */ -+ #define LCD_CTRL_BST_16 (2 << LCD_CTRL_BST_BIT) /* 16-word */ -+#define LCD_CTRL_RGB565 (0 << 27) /* RGB565 mode */ -+#define LCD_CTRL_RGB555 (1 << 27) /* RGB555 mode */ -+#define LCD_CTRL_OFUP (1 << 26) /* Output FIFO underrun protection enable */ -+#define LCD_CTRL_FRC_BIT 24 /* STN FRC Algorithm Selection */ -+#define LCD_CTRL_FRC_MASK (0x03 << LCD_CTRL_FRC_BIT) -+ #define LCD_CTRL_FRC_16 (0 << LCD_CTRL_FRC_BIT) /* 16 grayscale */ -+ #define LCD_CTRL_FRC_4 (1 << LCD_CTRL_FRC_BIT) /* 4 grayscale */ -+ #define LCD_CTRL_FRC_2 (2 << LCD_CTRL_FRC_BIT) /* 2 grayscale */ -+ -+#define CPM_LPCDR (CPM_BASE+0x64) -+#define CPM_CLKGR (CPM_BASE+0x20) -+#define REG_CPM_LPCDR REG32(CPM_LPCDR) -+#define REG_CPM_CLKGR REG32(CPM_CLKGR) -+ -+#define __cpm_start_tcu() (REG_CPM_CLKGR &= ~CPM_CLKGR_TCU) -+#define __cpm_stop_lcd() (REG_CPM_CLKGR |= CPM_CLKGR_LCD) -+#define __cpm_set_pixdiv(v) \ -+ (REG_CPM_LPCDR = (REG_CPM_LPCDR & ~CPM_LPCDR_PIXDIV_MASK) | ((v) << (CPM_LPCDR_PIXDIV_BIT))) -+#define __cpm_set_ldiv(v) \ -+ (REG_CPM_CPCCR = (REG_CPM_CPCCR & ~CPM_CPCCR_LDIV_MASK) | ((v) << (CPM_CPCCR_LDIV_BIT))) -+#define __cpm_start_lcd() (REG_CPM_CLKGR &= ~CPM_CLKGR_LCD) -+ - #endif /* !__ASSEMBLY__ */ - #endif /* __JZ4740_H__ */ -diff --git a/arch/mips/lib/board.c b/arch/mips/lib/board.c -index b14b33e..c2e64d9 100644 ---- a/arch/mips/lib/board.c -+++ b/arch/mips/lib/board.c -@@ -172,6 +172,12 @@ void board_init_f(ulong bootflag) - addr &= ~(4096 - 1); - debug("Top of RAM usable for U-Boot at: %08lx\n", addr); - -+#ifdef CONFIG_LCD -+ /* reserve memory for LCD display (always full pages) */ -+ addr = lcd_setmem (addr); -+ gd->fb_base = addr; -+#endif /* CONFIG_LCD */ -+ - /* Reserve memory for U-Boot code, data & bss - * round down to next 16 kB limit - */ -diff --git a/common/lcd.c b/common/lcd.c -index b6be800..af1281a 100644 ---- a/common/lcd.c -+++ b/common/lcd.c -@@ -263,6 +263,13 @@ static void lcd_drawchars(ushort x, ushort y, uchar *str, int count) - lcd_color_fg : lcd_color_bg; - bits <<= 1; - } -+#elif LCD_BPP == LCD_COLOR32 -+ uint *m = (uint *)d; -+ for (c=0; c<32; ++c) { -+ *m++ = (bits & 0x80) ? -+ lcd_color_fg : lcd_color_bg; -+ bits <<= 1; -+ } - #endif - } - #if LCD_BPP == LCD_MONOCHROME -@@ -509,7 +516,7 @@ static inline ushort *configuration_get_cmap(void) - return (ushort *)&(cp->lcd_cmap[255 * sizeof(ushort)]); - #elif defined(CONFIG_ATMEL_LCD) - return (ushort *)(panel_info.mmio + ATMEL_LCDC_LUT(0)); --#elif !defined(CONFIG_ATMEL_HLCD) && !defined(CONFIG_EXYNOS_FB) -+#elif !defined(CONFIG_ATMEL_HLCD) && !defined(CONFIG_EXYNOS_FB) && !defined(CONFIG_VIDEO_GPM940B0) - return panel_info.cmap; - #else - #if defined(CONFIG_LCD_LOGO) -diff --git a/drivers/video/Makefile b/drivers/video/Makefile -index ebb6da8..03625bc 100644 ---- a/drivers/video/Makefile -+++ b/drivers/video/Makefile -@@ -50,6 +50,7 @@ COBJS-$(CONFIG_VIDEO_SED13806) += sed13806.o - COBJS-$(CONFIG_VIDEO_SM501) += sm501.o - COBJS-$(CONFIG_VIDEO_SMI_LYNXEM) += smiLynxEM.o videomodes.o - COBJS-$(CONFIG_VIDEO_VCXK) += bus_vcxk.o -+COBJS-$(CONFIG_VIDEO_GPM940B0) += nanonote_gpm940b0.o - - COBJS := $(sort $(COBJS-y)) - SRCS := $(COBJS:.o=.c) -diff --git a/drivers/video/nanonote_gpm940b0.c b/drivers/video/nanonote_gpm940b0.c -new file mode 100644 -index 0000000..11efb72 ---- /dev/null -+++ b/drivers/video/nanonote_gpm940b0.c -@@ -0,0 +1,400 @@ -+/* -+ * JzRISC lcd controller -+ * -+ * Xiangfu Liu <xiangfu@sharism.cc> -+ * -+ * This program is free software; you can redistribute it and/or -+ * modify it under the terms of the GNU General Public License as -+ * published by the Free Software Foundation; either version 2 of -+ * the License, or (at your option) any later version. -+ * -+ * This program is distributed in the hope that it will be useful, -+ * but WITHOUT ANY WARRANTY; without even the implied warranty of -+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -+ * GNU General Public License for more details. -+ * -+ * You should have received a copy of the GNU General Public License -+ * along with this program; if not, write to the Free Software -+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, -+ * MA 02111-1307 USA -+ */ -+ -+#include <config.h> -+#include <common.h> -+#include <lcd.h> -+ -+#include <asm/io.h> /* virt_to_phys() */ -+#include <asm/jz4740.h> -+ -+#include "nanonote_gpm940b0.h" -+ -+#define align2(n) (n)=((((n)+1)>>1)<<1) -+#define align4(n) (n)=((((n)+3)>>2)<<2) -+#define align8(n) (n)=((((n)+7)>>3)<<3) -+ -+struct jzfb_info { -+ unsigned int cfg; /* panel mode and pin usage etc. */ -+ unsigned int w; -+ unsigned int h; -+ unsigned int bpp; /* bit per pixel */ -+ unsigned int fclk; /* frame clk */ -+ unsigned int hsw; /* hsync width, in pclk */ -+ unsigned int vsw; /* vsync width, in line count */ -+ unsigned int elw; /* end of line, in pclk */ -+ unsigned int blw; /* begin of line, in pclk */ -+ unsigned int efw; /* end of frame, in line count */ -+ unsigned int bfw; /* begin of frame, in line count */ -+}; -+ -+static struct jzfb_info jzfb = { -+ MODE_8BIT_SERIAL_TFT | PCLK_N | HSYNC_N | VSYNC_N, -+ 320, 240, 32, 70, 1, 1, 273, 140, 1, 20 -+}; -+ -+vidinfo_t panel_info = { -+ 320, 240, LCD_BPP, -+}; -+ -+void *lcd_base; -+void *lcd_console_address; -+int lcd_line_length; -+int lcd_color_fg; -+int lcd_color_bg; -+short console_col; -+short console_row; -+ -+static int jz_lcd_init_mem(void *lcdbase, vidinfo_t *vid) -+{ -+ u_long palette_mem_size; -+ struct jz_fb_info *fbi = &vid->jz_fb; -+ int fb_size = vid->vl_row * (vid->vl_col * NBITS (vid->vl_bpix)) / 8; -+ -+ fbi->screen = (u_long)lcdbase; -+ fbi->palette_size = 256; -+ palette_mem_size = fbi->palette_size * sizeof(u16); -+ -+ debug("jz_lcd.c palette_mem_size = 0x%08lx\n", (u_long) palette_mem_size); -+ /* locate palette and descs at end of page following fb */ -+ fbi->palette = (u_long)lcdbase + fb_size + PAGE_SIZE - palette_mem_size; -+ -+ return 0; -+} -+ -+static void jz_lcd_desc_init(vidinfo_t *vid) -+{ -+ struct jz_fb_info * fbi; -+ fbi = &vid->jz_fb; -+ fbi->dmadesc_fblow = (struct jz_fb_dma_descriptor *)((unsigned int)fbi->palette - 3*16); -+ fbi->dmadesc_fbhigh = (struct jz_fb_dma_descriptor *)((unsigned int)fbi->palette - 2*16); -+ fbi->dmadesc_palette = (struct jz_fb_dma_descriptor *)((unsigned int)fbi->palette - 1*16); -+ -+ #define BYTES_PER_PANEL (vid->vl_col * vid->vl_row * NBITS(vid->vl_bpix) / 8) -+ -+ /* populate descriptors */ -+ fbi->dmadesc_fblow->fdadr = virt_to_phys(fbi->dmadesc_fblow); -+ fbi->dmadesc_fblow->fsadr = virt_to_phys((void *)(fbi->screen + BYTES_PER_PANEL)); -+ fbi->dmadesc_fblow->fidr = 0; -+ fbi->dmadesc_fblow->ldcmd = BYTES_PER_PANEL / 4 ; -+ -+ fbi->fdadr1 = virt_to_phys(fbi->dmadesc_fblow); /* only used in dual-panel mode */ -+ -+ fbi->dmadesc_fbhigh->fsadr = virt_to_phys((void *)fbi->screen); -+ fbi->dmadesc_fbhigh->fidr = 0; -+ fbi->dmadesc_fbhigh->ldcmd = BYTES_PER_PANEL / 4; /* length in word */ -+ -+ fbi->dmadesc_palette->fsadr = virt_to_phys((void *)fbi->palette); -+ fbi->dmadesc_palette->fidr = 0; -+ fbi->dmadesc_palette->ldcmd = (fbi->palette_size * 2)/4 | (1<<28); -+ -+ if(NBITS(vid->vl_bpix) < 12) { -+ /* assume any mode with <12 bpp is palette driven */ -+ fbi->dmadesc_palette->fdadr = virt_to_phys(fbi->dmadesc_fbhigh); -+ fbi->dmadesc_fbhigh->fdadr = virt_to_phys(fbi->dmadesc_palette); -+ /* flips back and forth between pal and fbhigh */ -+ fbi->fdadr0 = virt_to_phys(fbi->dmadesc_palette); -+ } else { -+ /* palette shouldn't be loaded in true-color mode */ -+ fbi->dmadesc_fbhigh->fdadr = virt_to_phys((void *)fbi->dmadesc_fbhigh); -+ fbi->fdadr0 = virt_to_phys(fbi->dmadesc_fbhigh); /* no pal just fbhigh */ -+ } -+} -+ -+static int jz_lcd_hw_init(vidinfo_t *vid) -+{ -+ struct jz_fb_info *fbi = &vid->jz_fb; -+ unsigned int val = 0; -+ unsigned int pclk; -+ unsigned int stnH; -+ int pll_div; -+ -+ /* Setting Control register */ -+ switch (jzfb.bpp) { -+ case 1: -+ val |= LCD_CTRL_BPP_1; -+ break; -+ case 2: -+ val |= LCD_CTRL_BPP_2; -+ break; -+ case 4: -+ val |= LCD_CTRL_BPP_4; -+ break; -+ case 8: -+ val |= LCD_CTRL_BPP_8; -+ break; -+ case 15: -+ val |= LCD_CTRL_RGB555; -+ case 16: -+ val |= LCD_CTRL_BPP_16; -+ break; -+ case 17 ... 32: -+ val |= LCD_CTRL_BPP_18_24; /* target is 4bytes/pixel */ -+ break; -+ -+ default: -+ printf("jz_lcd.c The BPP %d is not supported\n", jzfb.bpp); -+ val |= LCD_CTRL_BPP_16; -+ break; -+ } -+ -+ switch (jzfb.cfg & MODE_MASK) { -+ case MODE_STN_MONO_DUAL: -+ case MODE_STN_COLOR_DUAL: -+ case MODE_STN_MONO_SINGLE: -+ case MODE_STN_COLOR_SINGLE: -+ switch (jzfb.bpp) { -+ case 1: -+ /* val |= LCD_CTRL_PEDN; */ -+ case 2: -+ val |= LCD_CTRL_FRC_2; -+ break; -+ case 4: -+ val |= LCD_CTRL_FRC_4; -+ break; -+ case 8: -+ default: -+ val |= LCD_CTRL_FRC_16; -+ break; -+ } -+ break; -+ } -+ -+ val |= LCD_CTRL_BST_16; /* Burst Length is 16WORD=64Byte */ -+ val |= LCD_CTRL_OFUP; /* OutFIFO underrun protect */ -+ -+ switch (jzfb.cfg & MODE_MASK) { -+ case MODE_STN_MONO_DUAL: -+ case MODE_STN_COLOR_DUAL: -+ case MODE_STN_MONO_SINGLE: -+ case MODE_STN_COLOR_SINGLE: -+ switch (jzfb.cfg & STN_DAT_PINMASK) { -+ case STN_DAT_PIN1: -+ /* Do not adjust the hori-param value. */ -+ break; -+ case STN_DAT_PIN2: -+ align2(jzfb.hsw); -+ align2(jzfb.elw); -+ align2(jzfb.blw); -+ break; -+ case STN_DAT_PIN4: -+ align4(jzfb.hsw); -+ align4(jzfb.elw); -+ align4(jzfb.blw); -+ break; -+ case STN_DAT_PIN8: -+ align8(jzfb.hsw); -+ align8(jzfb.elw); -+ align8(jzfb.blw); -+ break; -+ } -+ break; -+ } -+ -+ REG_LCD_CTRL = val; -+ -+ switch (jzfb.cfg & MODE_MASK) { -+ case MODE_STN_MONO_DUAL: -+ case MODE_STN_COLOR_DUAL: -+ case MODE_STN_MONO_SINGLE: -+ case MODE_STN_COLOR_SINGLE: -+ if (((jzfb.cfg & MODE_MASK) == MODE_STN_MONO_DUAL) || -+ ((jzfb.cfg & MODE_MASK) == MODE_STN_COLOR_DUAL)) -+ stnH = jzfb.h >> 1; -+ else -+ stnH = jzfb.h; -+ -+ REG_LCD_VSYNC = (0 << 16) | jzfb.vsw; -+ REG_LCD_HSYNC = ((jzfb.blw+jzfb.w) << 16) | (jzfb.blw+jzfb.w+jzfb.hsw); -+ -+ /* Screen setting */ -+ REG_LCD_VAT = ((jzfb.blw + jzfb.w + jzfb.hsw + jzfb.elw) << 16) | (stnH + jzfb.vsw + jzfb.bfw + jzfb.efw); -+ REG_LCD_DAH = (jzfb.blw << 16) | (jzfb.blw + jzfb.w); -+ REG_LCD_DAV = (0 << 16) | (stnH); -+ -+ /* AC BIAs signal */ -+ REG_LCD_PS = (0 << 16) | (stnH+jzfb.vsw+jzfb.efw+jzfb.bfw); -+ -+ break; -+ -+ case MODE_TFT_GEN: -+ case MODE_TFT_SHARP: -+ case MODE_TFT_CASIO: -+ case MODE_TFT_SAMSUNG: -+ case MODE_8BIT_SERIAL_TFT: -+ case MODE_TFT_18BIT: -+ REG_LCD_VSYNC = (0 << 16) | jzfb.vsw; -+ REG_LCD_HSYNC = (0 << 16) | jzfb.hsw; -+ REG_LCD_DAV =((jzfb.vsw+jzfb.bfw) << 16) | (jzfb.vsw +jzfb.bfw+jzfb.h); -+ REG_LCD_DAH = ((jzfb.hsw + jzfb.blw) << 16) | (jzfb.hsw + jzfb.blw + jzfb.w ); -+ REG_LCD_VAT = (((jzfb.blw + jzfb.w + jzfb.elw + jzfb.hsw)) << 16) \ -+ | (jzfb.vsw + jzfb.bfw + jzfb.h + jzfb.efw); -+ break; -+ } -+ -+ switch (jzfb.cfg & MODE_MASK) { -+ case MODE_TFT_SAMSUNG: -+ { -+ unsigned int total, tp_s, tp_e, ckv_s, ckv_e; -+ unsigned int rev_s, rev_e, inv_s, inv_e; -+ -+ pclk = val * (jzfb.w + jzfb.hsw + jzfb.elw + jzfb.blw) * -+ (jzfb.h + jzfb.vsw + jzfb.efw + jzfb.bfw); /* Pixclk */ -+ -+ total = jzfb.blw + jzfb.w + jzfb.elw + jzfb.hsw; -+ tp_s = jzfb.blw + jzfb.w + 1; -+ tp_e = tp_s + 1; -+ ckv_s = tp_s - pclk/(1000000000/4100); -+ ckv_e = tp_s + total; -+ rev_s = tp_s - 11; /* -11.5 clk */ -+ rev_e = rev_s + total; -+ inv_s = tp_s; -+ inv_e = inv_s + total; -+ REG_LCD_CLS = (tp_s << 16) | tp_e; -+ REG_LCD_PS = (ckv_s << 16) | ckv_e; -+ REG_LCD_SPL = (rev_s << 16) | rev_e; -+ REG_LCD_REV = (inv_s << 16) | inv_e; -+ jzfb.cfg |= STFT_REVHI | STFT_SPLHI; -+ break; -+ } -+ case MODE_TFT_SHARP: -+ { -+ unsigned int total, cls_s, cls_e, ps_s, ps_e; -+ unsigned int spl_s, spl_e, rev_s, rev_e; -+ total = jzfb.blw + jzfb.w + jzfb.elw + jzfb.hsw; -+ spl_s = 1; -+ spl_e = spl_s + 1; -+ cls_s = 0; -+ cls_e = total - 60; /* > 4us (pclk = 80ns) */ -+ ps_s = cls_s; -+ ps_e = cls_e; -+ rev_s = total - 40; /* > 3us (pclk = 80ns) */ -+ rev_e = rev_s + total; -+ jzfb.cfg |= STFT_PSHI; -+ REG_LCD_SPL = (spl_s << 16) | spl_e; -+ REG_LCD_CLS = (cls_s << 16) | cls_e; -+ REG_LCD_PS = (ps_s << 16) | ps_e; -+ REG_LCD_REV = (rev_s << 16) | rev_e; -+ break; -+ } -+ case MODE_TFT_CASIO: -+ break; -+ } -+ -+ /* Configure the LCD panel */ -+ REG_LCD_CFG = jzfb.cfg; -+ -+ /* Timing setting */ -+ __cpm_stop_lcd(); -+ -+ val = jzfb.fclk; /* frame clk */ -+ if ( (jzfb.cfg & MODE_MASK) != MODE_8BIT_SERIAL_TFT) { -+ pclk = val * (jzfb.w + jzfb.hsw + jzfb.elw + jzfb.blw) * -+ (jzfb.h + jzfb.vsw + jzfb.efw + jzfb.bfw); /* Pixclk */ -+ } else { -+ /* serial mode: Hsync period = 3*Width_Pixel */ -+ pclk = val * (jzfb.w*3 + jzfb.hsw + jzfb.elw + jzfb.blw) * -+ (jzfb.h + jzfb.vsw + jzfb.efw + jzfb.bfw); /* Pixclk */ -+ } -+ -+ if (((jzfb.cfg & MODE_MASK) == MODE_STN_COLOR_SINGLE) || -+ ((jzfb.cfg & MODE_MASK) == MODE_STN_COLOR_DUAL)) -+ pclk = (pclk * 3); -+ -+ if (((jzfb.cfg & MODE_MASK) == MODE_STN_COLOR_SINGLE) || -+ ((jzfb.cfg & MODE_MASK) == MODE_STN_COLOR_DUAL) || -+ ((jzfb.cfg & MODE_MASK) == MODE_STN_MONO_SINGLE) || -+ ((jzfb.cfg & MODE_MASK) == MODE_STN_MONO_DUAL)) -+ pclk = pclk >> ((jzfb.cfg & STN_DAT_PINMASK) >> 4); -+ -+ if (((jzfb.cfg & MODE_MASK) == MODE_STN_COLOR_DUAL) || -+ ((jzfb.cfg & MODE_MASK) == MODE_STN_MONO_DUAL)) -+ pclk >>= 1; -+ -+ pll_div = (REG_CPM_CPCCR & CPM_CPCCR_PCS); /* clock source,0:pllout/2 1: pllout */ -+ pll_div = pll_div ? 1 : 2; -+ val = (__cpm_get_pllout() / pll_div) / pclk; -+ val--; -+ if (val > 0x1ff) { -+ printf("CPM_LPCDR too large, set it to 0x1ff\n"); -+ val = 0x1ff; -+ } -+ __cpm_set_pixdiv(val); -+ -+ val = pclk * 3 ; /* LCDClock > 2.5*Pixclock */ -+ if (val > 150000000) { -+ printf("Warning: LCDClock=%d\n, LCDClock must less or equal to 150MHz.\n", val); -+ printf("Change LCDClock to 150MHz\n"); -+ val = 150000000; -+ } -+ val = (__cpm_get_pllout() / pll_div) / val; -+ val--; -+ if (val > 0x1f) { -+ printf("CPM_CPCCR.LDIV too large, set it to 0x1f\n"); -+ val = 0x1f; -+ } -+ __cpm_set_ldiv( val ); -+ REG_CPM_CPCCR |= CPM_CPCCR_CE ; /* update divide */ -+ -+ __cpm_start_lcd(); -+ udelay(1000); -+ -+ REG_LCD_DA0 = fbi->fdadr0; /* frame descripter*/ -+ -+ if (((jzfb.cfg & MODE_MASK) == MODE_STN_COLOR_DUAL) || -+ ((jzfb.cfg & MODE_MASK) == MODE_STN_MONO_DUAL)) -+ REG_LCD_DA1 = fbi->fdadr1; /* frame descripter*/ -+ -+ return 0; -+} -+ -+void lcd_ctrl_init (void *lcdbase) -+{ -+ __lcd_display_pin_init(); -+ __lcd_display_on() ; -+ -+ jz_lcd_init_mem(lcdbase, &panel_info); -+ jz_lcd_desc_init(&panel_info); -+ jz_lcd_hw_init(&panel_info); -+ -+} -+ -+/* -+ * Before enabled lcd controller, lcd registers should be configured correctly. -+ */ -+void lcd_enable (void) -+{ -+ REG_LCD_CTRL &= ~(1<<4); /* LCDCTRL.DIS */ -+ REG_LCD_CTRL |= 1<<3; /* LCDCTRL.ENA*/ -+} -+ -+void lcd_disable (void) -+{ -+ REG_LCD_CTRL |= (1<<4); -+} -+ -+void lcd_setcolreg (ushort regno, ushort red, ushort green, ushort blue) -+{ -+} -+ -+void lcd_initcolregs (void) -+{ -+} -diff --git a/drivers/video/nanonote_gpm940b0.h b/drivers/video/nanonote_gpm940b0.h -new file mode 100644 -index 0000000..efe491e ---- /dev/null -+++ b/drivers/video/nanonote_gpm940b0.h -@@ -0,0 +1,135 @@ -+/* -+ * JzRISC lcd controller -+ * -+ * Xiangfu Liu <xiangfu@sharism.cc> -+ * -+ * This program is free software; you can redistribute it and/or -+ * modify it under the terms of the GNU General Public License as -+ * published by the Free Software Foundation; either version 2 of -+ * the License, or (at your option) any later version. -+ * -+ * This program is distributed in the hope that it will be useful, -+ * but WITHOUT ANY WARRANTY; without even the implied warranty of -+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -+ * GNU General Public License for more details. -+ * -+ * You should have received a copy of the GNU General Public License -+ * along with this program; if not, write to the Free Software -+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, -+ * MA 02111-1307 USA -+ */ -+ -+#ifndef __QI_LB60_GPM940B0_H__ -+#define __QI_LB60_GPM940B0_H__ -+ -+struct lcd_desc{ -+ unsigned int next_desc; /* LCDDAx */ -+ unsigned int databuf; /* LCDSAx */ -+ unsigned int frame_id; /* LCDFIDx */ -+ unsigned int cmd; /* LCDCMDx */ -+}; -+ -+#define MODE_MASK 0x0f -+#define MODE_TFT_GEN 0x00 -+#define MODE_TFT_SHARP 0x01 -+#define MODE_TFT_CASIO 0x02 -+#define MODE_TFT_SAMSUNG 0x03 -+#define MODE_CCIR656_NONINT 0x04 -+#define MODE_CCIR656_INT 0x05 -+#define MODE_STN_COLOR_SINGLE 0x08 -+#define MODE_STN_MONO_SINGLE 0x09 -+#define MODE_STN_COLOR_DUAL 0x0a -+#define MODE_STN_MONO_DUAL 0x0b -+#define MODE_8BIT_SERIAL_TFT 0x0c -+ -+#define MODE_TFT_18BIT (1<<7) -+ -+#define STN_DAT_PIN1 (0x00 << 4) -+#define STN_DAT_PIN2 (0x01 << 4) -+#define STN_DAT_PIN4 (0x02 << 4) -+#define STN_DAT_PIN8 (0x03 << 4) -+#define STN_DAT_PINMASK STN_DAT_PIN8 -+ -+#define STFT_PSHI (1 << 15) -+#define STFT_CLSHI (1 << 14) -+#define STFT_SPLHI (1 << 13) -+#define STFT_REVHI (1 << 12) -+ -+#define SYNC_MASTER (0 << 16) -+#define SYNC_SLAVE (1 << 16) -+ -+#define DE_P (0 << 9) -+#define DE_N (1 << 9) -+ -+#define PCLK_P (0 << 10) -+#define PCLK_N (1 << 10) -+ -+#define HSYNC_P (0 << 11) -+#define HSYNC_N (1 << 11) -+ -+#define VSYNC_P (0 << 8) -+#define VSYNC_N (1 << 8) -+ -+#define DATA_NORMAL (0 << 17) -+#define DATA_INVERSE (1 << 17) -+ -+ -+/* Jz LCDFB supported I/O controls. */ -+#define FBIOSETBACKLIGHT 0x4688 -+#define FBIODISPON 0x4689 -+#define FBIODISPOFF 0x468a -+#define FBIORESET 0x468b -+#define FBIOPRINT_REG 0x468c -+ -+/* -+ * LCD panel specific definition -+ */ -+#define MODE (0xc9) /* 8bit serial RGB */ -+ -+#define __spi_write_reg1(reg, val) \ -+do { \ -+ unsigned char no; \ -+ unsigned short value; \ -+ unsigned char a=reg; \ -+ unsigned char b=val; \ -+ __gpio_set_pin(SPEN); \ -+ __gpio_set_pin(SPCK); \ -+ __gpio_clear_pin(SPDA); \ -+ __gpio_clear_pin(SPEN); \ -+ value=((a<<8)|(b&0xFF)); \ -+ for(no=0;no<16;no++) \ -+ { \ -+ __gpio_clear_pin(SPCK); \ -+ if((value&0x8000)==0x8000) \ -+ __gpio_set_pin(SPDA); \ -+ else \ -+ __gpio_clear_pin(SPDA); \ -+ __gpio_set_pin(SPCK); \ -+ value=(value<<1); \ -+ } \ -+ __gpio_set_pin(SPEN); \ -+} while (0) -+ -+#define __lcd_display_pin_init() \ -+do { \ -+ __cpm_start_tcu(); \ -+ __gpio_as_output(SPEN); /* use SPDA */ \ -+ __gpio_as_output(SPCK); /* use SPCK */ \ -+ __gpio_as_output(SPDA); /* use SPDA */ \ -+} while (0) -+ -+#define __lcd_display_on() \ -+do { \ -+ __spi_write_reg1(0x05, 0x1e); \ -+ __spi_write_reg1(0x05, 0x5e); \ -+ __spi_write_reg1(0x07, 0x8d); \ -+ __spi_write_reg1(0x13, 0x01); \ -+ __spi_write_reg1(0x05, 0x5f); \ -+} while (0) -+ -+#define __lcd_display_off() \ -+do { \ -+ __spi_write_reg1(0x05, 0x5e); \ -+} while (0) -+ -+#endif /* __QI_LB60_GPM940B0_H__ */ -diff --git a/include/configs/qi_lb60.h b/include/configs/qi_lb60.h -index 52b370c..d3e78ad 100644 ---- a/include/configs/qi_lb60.h -+++ b/include/configs/qi_lb60.h -@@ -32,6 +32,13 @@ - * Miscellaneous configurable options - */ - #define CONFIG_NANONOTE -+ -+#define CONFIG_LCD -+#define CONFIG_SYS_WHITE_ON_BLACK -+#define LCD_BPP LCD_COLOR32 -+#define CONFIG_VIDEO_GPM940B0 -+ -+ - #define CONFIG_JZ4740_MMC - #define CONFIG_MMC 1 - #define CONFIG_FAT 1 -diff --git a/include/lcd.h b/include/lcd.h -index 42070d7..6de5482 100644 ---- a/include/lcd.h -+++ b/include/lcd.h -@@ -263,8 +263,44 @@ typedef struct vidinfo { - - void init_panel_info(vidinfo_t *vid); - --#else -+#elif defined(CONFIG_JZSOC) -+/* -+ * LCD controller stucture for JZSOC: JZ4740 -+ */ -+struct jz_fb_dma_descriptor { -+ u_long fdadr; /* Frame descriptor address register */ -+ u_long fsadr; /* Frame source address register */ -+ u_long fidr; /* Frame ID register */ -+ u_long ldcmd; /* Command register */ -+}; -+ -+/* -+ * Jz LCD info -+ */ -+struct jz_fb_info { -+ -+ u_long fdadr0; /* physical address of frame/palette descriptor */ -+ u_long fdadr1; /* physical address of frame descriptor */ -+ -+ /* DMA descriptors */ -+ struct jz_fb_dma_descriptor * dmadesc_fblow; -+ struct jz_fb_dma_descriptor * dmadesc_fbhigh; -+ struct jz_fb_dma_descriptor * dmadesc_palette; -+ u_long screen; /* address of frame buffer */ -+ u_long palette; /* address of palette memory */ -+ u_int palette_size; -+}; -+typedef struct vidinfo { -+ ushort vl_col; /* Number of columns (i.e. 640) */ -+ ushort vl_row; /* Number of rows (i.e. 480) */ -+ u_char vl_bpix; /* Bits per pixel, 0 = 1, 1 = 2, 2 = 4, 3 = 8 */ -+ -+ struct jz_fb_info jz_fb; -+} vidinfo_t; -+ -+extern vidinfo_t panel_info; - -+#else - typedef struct vidinfo { - ushort vl_col; /* Number of columns (i.e. 160) */ - ushort vl_row; /* Number of rows (i.e. 100) */ -@@ -318,6 +354,7 @@ void lcd_show_board_info(void); - #define LCD_COLOR4 2 - #define LCD_COLOR8 3 - #define LCD_COLOR16 4 -+#define LCD_COLOR32 5 - - /*----------------------------------------------------------------------*/ - #if defined(CONFIG_LCD_INFO_BELOW_LOGO) -@@ -369,7 +406,7 @@ void lcd_show_board_info(void); - # define CONSOLE_COLOR_GREY 14 - # define CONSOLE_COLOR_WHITE 15 /* Must remain last / highest */ - --#else -+#elif LCD_BPP == LCD_COLOR16 - - /* - * 16bpp color definitions -@@ -377,6 +414,15 @@ void lcd_show_board_info(void); - # define CONSOLE_COLOR_BLACK 0x0000 - # define CONSOLE_COLOR_WHITE 0xffff /* Must remain last / highest */ - -+#elif LCD_BPP == LCD_COLOR32 -+/* -+ * 18,24,32 bpp color definitions -+ */ -+# define CONSOLE_COLOR_BLACK 0x00000000 -+# define CONSOLE_COLOR_WHITE 0xffffffff /* Must remain last / highest */ -+ -+#else -+ - #endif /* color definitions */ - - /************************************************************************/ -@@ -406,7 +452,7 @@ void lcd_show_board_info(void); - #if LCD_BPP == LCD_MONOCHROME - # define COLOR_MASK(c) ((c) | (c) << 1 | (c) << 2 | (c) << 3 | \ - (c) << 4 | (c) << 5 | (c) << 6 | (c) << 7) --#elif (LCD_BPP == LCD_COLOR8) || (LCD_BPP == LCD_COLOR16) -+#elif (LCD_BPP == LCD_COLOR8) || (LCD_BPP == LCD_COLOR16) || (LCD_BPP == LCD_COLOR32) - # define COLOR_MASK(c) (c) - #else - # error Unsupported LCD BPP. --- -1.7.9.5 - diff --git a/package/boot/uboot-xburst/patches/0006-enable-silent-console.patch b/package/boot/uboot-xburst/patches/0006-enable-silent-console.patch deleted file mode 100644 index ebd6a6a7bf..0000000000 --- a/package/boot/uboot-xburst/patches/0006-enable-silent-console.patch +++ /dev/null @@ -1,60 +0,0 @@ -From 5eb4d4c598f2806bd1b3d1140e917bfead7851ad Mon Sep 17 00:00:00 2001 -From: Xiangfu <xiangfu@openmobilefree.net> -Date: Wed, 10 Oct 2012 23:51:26 +0800 -Subject: [PATCH 6/6] enable silent console - ---- - common/console.c | 16 ++++++++++++++++ - include/configs/qi_lb60.h | 2 ++ - 2 files changed, 18 insertions(+) - -diff --git a/common/console.c b/common/console.c -index 1177f7d..e8a2078 100644 ---- a/common/console.c -+++ b/common/console.c -@@ -685,6 +685,14 @@ done: - - gd->flags |= GD_FLG_DEVINIT; /* device initialization completed */ - -+#ifdef CONFIG_SILENT_CONSOLE -+ /* Check one more time the contents of the silent environment -+ * variable, because if the environment is loaded from NAND it was -+ * not available when console_init_f() was called */ -+ if (getenv("silent") != NULL) -+ gd->flags |= GD_FLG_SILENT; -+#endif -+ - stdio_print_current_devices(); - - #ifdef CONFIG_SYS_CONSOLE_ENV_OVERWRITE -@@ -760,6 +768,14 @@ int console_init_r(void) - - gd->flags |= GD_FLG_DEVINIT; /* device initialization completed */ - -+#ifdef CONFIG_SILENT_CONSOLE -+ /* Check one more time the contents of the silent environment -+ * variable, because if the environment is loaded from NAND it was -+ * not available when console_init_f() was called */ -+ if (getenv("silent") != NULL) -+ gd->flags |= GD_FLG_SILENT; -+#endif -+ - stdio_print_current_devices(); - - /* Setting environment variables */ -diff --git a/include/configs/qi_lb60.h b/include/configs/qi_lb60.h -index d3e78ad..a3534ff 100644 ---- a/include/configs/qi_lb60.h -+++ b/include/configs/qi_lb60.h -@@ -102,6 +102,8 @@ - #define CONFIG_SYS_NO_FLASH - #define CONFIG_SYS_FLASH_BASE 0 /* init flash_base as 0 */ - -+#define CONFIG_SILENT_CONSOLE 1 /* Enable silent console */ -+ - /* - * Command line configuration - */ --- -1.7.9.5 - |