From patchwork Tue Jun 21 18:41:38 2016 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Eric Nelson X-Patchwork-Id: 638827 X-Patchwork-Delegate: sbabic@denx.de Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Received: from theia.denx.de (theia.denx.de [85.214.87.163]) by ozlabs.org (Postfix) with ESMTP id 3rYxYt38fCz9sxb for ; Wed, 22 Jun 2016 04:48:02 +1000 (AEST) Received: from localhost (localhost [127.0.0.1]) by theia.denx.de (Postfix) with ESMTP id 49D89A7662; Tue, 21 Jun 2016 20:47:37 +0200 (CEST) Received: from theia.denx.de ([127.0.0.1]) by localhost (theia.denx.de [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id WcbvRLP5fXB8; Tue, 21 Jun 2016 20:47:37 +0200 (CEST) Received: from theia.denx.de (localhost [127.0.0.1]) by theia.denx.de (Postfix) with ESMTP id 59251A76CE; Tue, 21 Jun 2016 20:47:13 +0200 (CEST) Received: from localhost (localhost [127.0.0.1]) by theia.denx.de (Postfix) with ESMTP id 4AE74A7613 for ; Tue, 21 Jun 2016 20:46:58 +0200 (CEST) Received: from theia.denx.de ([127.0.0.1]) by localhost (theia.denx.de [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id 8xW4hTM6QuDh for ; Tue, 21 Jun 2016 20:46:58 +0200 (CEST) X-policyd-weight: NOT_IN_SBL_XBL_SPAMHAUS=-1.5 NOT_IN_SPAMCOP=-1.5 NOT_IN_BL_NJABL=-1.5 (only DNSBL check requested) Received: from fed1rmfepi104.cox.net (fed1rmfepi104.cox.net [68.230.241.135]) by theia.denx.de (Postfix) with ESMTP id 7C860A75E9 for ; Tue, 21 Jun 2016 20:46:48 +0200 (CEST) Received: from fed1rmimpo210.cox.net ([68.230.241.161]) by fed1rmfepo201.cox.net (InterMail vM.8.01.05.28 201-2260-151-171-20160122) with ESMTP id <20160621184150.BEMJ21830.fed1rmfepo201.cox.net@fed1rmimpo210.cox.net> for ; Tue, 21 Jun 2016 14:41:50 -0400 Received: from localhost.localdomain ([98.167.220.73]) by fed1rmimpo210.cox.net with cox id 9Whk1t0051bd1YJ01WhpJ5; Tue, 21 Jun 2016 14:41:49 -0400 X-CT-Class: Clean X-CT-Score: 0.00 X-CT-RefID: str=0001.0A020205.57698A6E.009D, ss=1, re=0.000, recu=0.000, reip=0.000, cl=1, cld=1, fgs=0 X-CT-Spam: 0 X-Authority-Analysis: v=2.1 cv=P+Oa/n0u c=1 sm=1 tr=0 a=IKzc1XMGcUxYR4OhBl0X0A==:117 a=IKzc1XMGcUxYR4OhBl0X0A==:17 a=L9H7d07YOLsA:10 a=9cW_t1CCXrUA:10 a=s5jvgZ67dGcA:10 a=8AirrxEcAAAA:8 a=9_1hYV8uAAAA:8 a=AgWW5FNtAAAA:8 a=kqJsSX_K_YcENs3j1PUA:9 a=qvt-VptZktTQZLSG:21 a=ZrNuZYAwVtgp58O0:21 a=ST-jHhOKWsTCqRlWije3:22 a=FKwbt-OhbrkoYuZlCyy7:22 a=8DkScU8FlKhdH4yH5W0q:22 X-CM-Score: 0.00 Authentication-Results: cox.net; auth=pass (CRAM-MD5) smtp.auth=eric.a.nelson@cox.net From: Eric Nelson To: u-boot@lists.denx.de Date: Tue, 21 Jun 2016 11:41:38 -0700 Message-Id: <1466534502-17233-9-git-send-email-eric@nelint.com> X-Mailer: git-send-email 2.7.4 In-Reply-To: <1466534502-17233-1-git-send-email-eric@nelint.com> References: <1466534502-17233-1-git-send-email-eric@nelint.com> Cc: marex@denx.de, otavio@ossystems.com.br, gary.bisson@boundarydevices.com, joe.hershberger@ni.com, fabio.estevam@nxp.com Subject: [U-Boot] [RFC PATCH 08/12] mx6: Add board mx6memcal for use in validating DDR X-BeenThere: u-boot@lists.denx.de X-Mailman-Version: 2.1.15 Precedence: list List-Id: U-Boot discussion List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , MIME-Version: 1.0 Errors-To: u-boot-bounces@lists.denx.de Sender: "U-Boot" This is a virtual "board" that uses configuration files and Kconfig to define the memory layout used by a real board during the board bring-up process. It generates an SPL image that can be loaded using imx_usb or SB_LOADER.exe. When run, it will generate a set of calibration constants for use in either or both a DCD configuration file for boards that use u-boot.imx or struct mx6_mmdc_calibration for boards that boot via SPL. In essence, it is a configurable, open-source variant of the Freescale ddr-stress tool. https://community.nxp.com/docs/DOC-105652 File mx6memcal_defconfig configures the board for use with mx6sabresd or mx6qsabreauto. Signed-off-by: Eric Nelson --- arch/arm/cpu/armv7/mx6/Kconfig | 9 + board/freescale/mx6memcal/Kconfig | 135 ++++++++++ board/freescale/mx6memcal/MAINTAINERS | 7 + board/freescale/mx6memcal/Makefile | 13 + board/freescale/mx6memcal/mx6memcal.c | 31 +++ board/freescale/mx6memcal/spl.c | 449 ++++++++++++++++++++++++++++++++++ configs/mx6memcal_defconfig | 30 +++ include/configs/mx6memcal.h | 65 +++++ 8 files changed, 739 insertions(+) create mode 100644 board/freescale/mx6memcal/Kconfig create mode 100644 board/freescale/mx6memcal/MAINTAINERS create mode 100644 board/freescale/mx6memcal/Makefile create mode 100644 board/freescale/mx6memcal/mx6memcal.c create mode 100644 board/freescale/mx6memcal/spl.c create mode 100644 configs/mx6memcal_defconfig create mode 100644 include/configs/mx6memcal.h diff --git a/arch/arm/cpu/armv7/mx6/Kconfig b/arch/arm/cpu/armv7/mx6/Kconfig index dc0bc7e..c7241ca 100644 --- a/arch/arm/cpu/armv7/mx6/Kconfig +++ b/arch/arm/cpu/armv7/mx6/Kconfig @@ -92,6 +92,14 @@ config TARGET_MX6CUBOXI config TARGET_MX6QARM2 bool "mx6qarm2" +config TARGET_MX6MEMCAL + bool "mx6memcal" + select SUPPORT_SPL + help + The mx6memcal board is a virtual board that can be used to validate + and characterize the memory layout of a new design during the initial + development and pre-production stages. + config TARGET_MX6QSABREAUTO bool "mx6qsabreauto" select DM @@ -199,6 +207,7 @@ source "board/compulab/cm_fx6/Kconfig" source "board/congatec/cgtqmx6eval/Kconfig" source "board/embest/mx6boards/Kconfig" source "board/freescale/mx6qarm2/Kconfig" +source "board/freescale/mx6memcal/Kconfig" source "board/freescale/mx6qsabreauto/Kconfig" source "board/freescale/mx6sabresd/Kconfig" source "board/freescale/mx6slevk/Kconfig" diff --git a/board/freescale/mx6memcal/Kconfig b/board/freescale/mx6memcal/Kconfig new file mode 100644 index 0000000..cfa5b6f --- /dev/null +++ b/board/freescale/mx6memcal/Kconfig @@ -0,0 +1,135 @@ +if TARGET_MX6MEMCAL + +config SYS_BOARD + default "mx6memcal" + +config SYS_VENDOR + default "freescale" + +config SYS_CONFIG_NAME + default "mx6memcal" + +config DDRWIDTH + int "DDR bus width" + default 64 + +config DDRCS + int "DDR chip selects" + default 2 + +choice + prompt "Memory type" + +config DDR3 + bool "DDR3" + help + Select this if your board design uses DDR3 + +config LPDDR2 + bool "LPDDR2" + help + Select this if your board design uses LPDDR2 + +endchoice + +choice + prompt "Memory type" + +config MT41K512M16TNA + bool "Micron MT41K512M16TNA 512Mx16 (1GiB/chip)" + depends on DDR3 + +config MT41K128M16JT + bool "Micron MT41K128M16JT 128Mx16 (256 MiB/chip)" + depends on DDR3 + +config H5TQ4G63AFR + bool "Hynix H5TQ4G63AFR 512Mx16 (1GiB/chip)" + depends on DDR3 + +config H5TQ2G63DFR + bool "Hynix H5TQ2G63DFR 128Mx16 (256 MiB/chip)" + depends on DDR3 + +config MT42L256M32D2LG + bool "Micron MT42L256M32D2LG LPDDR2 256Mx32 (1GiB/chip)" + depends on LPDDR2 + +config MT29PZZZ4D4BKESK + bool "Micron MT29PZZZ4D4BKESK multi-chip 512MiB LPDDR2/4GiB eMMC" + depends on LPDDR2 + +endchoice + +config DRAM_DRIVE_STRENGTH + int "DRAM Drive strength" + default 6 + range 0 7 + help + Enter drive strength as an index defined for IOMUX settings + for GRP_B1DS and others. + 0 == Hi Z + 6 == 40 Ohm (default) + 7 == 34 Ohm + Value will be applied to all clock and data lines + +config RALAT + int "Read additional latency" + default 5 + range 0 7 + help + Enter a latency in number of cycles. This will be added to + CAS and internal delays for which the MMDC will retrieve the + read data from the internal FIFO. + This is used to compensate for board/chip delays. + +config WALAT + int "Write additional latency" + default 0 + range 0 7 + help + Enter a latency in number of cycles. This will be added to + CAS and internal delays for which the MMDC will retrieve the + read data from the internal FIFO + This is used to compensate for board/chip delays. + +choice + prompt "Serial console" + +config SERIAL_CONSOLE_UART1 + bool "UART1" + +config SERIAL_CONSOLE_UART2 + bool "UART2" + +endchoice + +choice + prompt "UART pads" + + config UART2_EIM_D26_27 + bool "UART2 on EIM_D26/27 (SabreLite, Nitrogen6x)" + depends on SERIAL_CONSOLE_UART2 + + config UART1_CSI0_DAT10_11 + bool "UART1 on CSI0_DAT10/11 (Wand)" + depends on SERIAL_CONSOLE_UART1 + + config UART1_SD3_DAT6_7 + bool "UART1 on SD3_DAT6/7 (SabreSD)" + depends on SERIAL_CONSOLE_UART1 + + config UART1_UART1 + bool "UART1 on UART1 (i.MX6SL EVK, WaRP)" + depends on SERIAL_CONSOLE_UART1 + +endchoice + +config IMXIMAGE_OUTPUT + bool "Include output for imximage" + default y + help + Say "Y" if you want output formatted for use + in non-SPL builds + +endif diff --git a/board/freescale/mx6memcal/MAINTAINERS b/board/freescale/mx6memcal/MAINTAINERS new file mode 100644 index 0000000..5da38f7 --- /dev/null +++ b/board/freescale/mx6memcal/MAINTAINERS @@ -0,0 +1,7 @@ +MX6MEMCAL BOARD +M: Eric Nelson +S: Maintained +F: board/freescale/mx6memcal/ +F: include/configs/mx6memcal.h +F: configs/mx6memcal_defconfig + diff --git a/board/freescale/mx6memcal/Makefile b/board/freescale/mx6memcal/Makefile new file mode 100644 index 0000000..2d7a6fa --- /dev/null +++ b/board/freescale/mx6memcal/Makefile @@ -0,0 +1,13 @@ +# +# Copyright (C) 2007, Guennadi Liakhovetski +# +# (C) Copyright 2011 Freescale Semiconductor, Inc. +# +# SPDX-License-Identifier: GPL-2.0+ +# + +ifdef CONFIG_SPL_BUILD +obj-y := spl.o +else +obj-y := mx6memcal.o +endif diff --git a/board/freescale/mx6memcal/mx6memcal.c b/board/freescale/mx6memcal/mx6memcal.c new file mode 100644 index 0000000..5aa13c1 --- /dev/null +++ b/board/freescale/mx6memcal/mx6memcal.c @@ -0,0 +1,31 @@ +/* + * mx6memcal board support - provides a minimal, UART-only + * U-Boot that's capable of running a memory test. + * + * Copyright (C) 2016, Nelson Integration (eric@nelint.com) + * + * SPDX-License-Identifier: GPL-2.0+ + */ + +#include +#include + +DECLARE_GLOBAL_DATA_PTR; + +int board_init(void) +{ + return 0; +} + +int checkboard(void) +{ + puts("Board: mx6memcal\n"); + return 0; +} + +int dram_init(void) +{ + gd->ram_size = imx_ddr_size(); + return 0; +} + diff --git a/board/freescale/mx6memcal/spl.c b/board/freescale/mx6memcal/spl.c new file mode 100644 index 0000000..28402cf --- /dev/null +++ b/board/freescale/mx6memcal/spl.c @@ -0,0 +1,449 @@ +/* + * Copyright (C) 2014 Gateworks Corporation + * Author: Tim Harvey + * + * SPDX-License-Identifier: GPL-2.0+ + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +DECLARE_GLOBAL_DATA_PTR; + +#define UART_PAD_CTRL (PAD_CTL_PUS_100K_UP | \ + PAD_CTL_SPEED_MED | PAD_CTL_DSE_40ohm | \ + PAD_CTL_SRE_FAST | PAD_CTL_HYS) + +static iomux_v3_cfg_t const uart_pads[] = { +#ifdef CONFIG_UART2_EIM_D26_27 + IOMUX_PADS(PAD_EIM_D26__UART2_TX_DATA | MUX_PAD_CTRL(UART_PAD_CTRL)), + IOMUX_PADS(PAD_EIM_D27__UART2_RX_DATA | MUX_PAD_CTRL(UART_PAD_CTRL)), +#elif defined(CONFIG_UART1_CSI0_DAT10_11) + IOMUX_PADS(PAD_CSI0_DAT10__UART1_TX_DATA | MUX_PAD_CTRL(UART_PAD_CTRL)), + IOMUX_PADS(PAD_CSI0_DAT11__UART1_RX_DATA | MUX_PAD_CTRL(UART_PAD_CTRL)), +#elif defined(CONFIG_UART1_SD3_DAT6_7) + IOMUX_PADS(PAD_SD3_DAT6__UART1_RX_DATA | MUX_PAD_CTRL(UART_PAD_CTRL)), + IOMUX_PADS(PAD_SD3_DAT7__UART1_TX_DATA | MUX_PAD_CTRL(UART_PAD_CTRL)), +#elif defined(CONFIG_UART1_UART1) + MX6_PAD_UART1_TXD__UART1_TXD | MUX_PAD_CTRL(UART_PAD_CTRL), + MX6_PAD_UART1_RXD__UART1_RXD | MUX_PAD_CTRL(UART_PAD_CTRL), +#else +#error select UART console pads +#endif +}; + +#ifdef CONFIG_DDR3 +#define GRP_DDRTYPE 0x000C0000 +#else +#define GRP_DDRTYPE 0x00080000 +#endif + +#define DDR_PKE 0 +#define DDR_MODE 0x00020000 + +#define DRAM_DRIVE_STRENGTH \ + (CONFIG_DRAM_DRIVE_STRENGTH << 3) + +/* configure MX6Q/DUAL mmdc DDR io registers */ +static struct mx6dq_iomux_ddr_regs const mx6dq_ddr_ioregs = { + /* SDCLK[0:1], CAS, RAS, Reset: Differential input, 40ohm */ + .dram_sdclk_0 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_sdclk_1 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_cas = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_ras = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_reset = DDR_MODE+DRAM_DRIVE_STRENGTH, + /* SDCKE[0:1]: 100k pull-up */ + .dram_sdcke0 = 0x00003000, + .dram_sdcke1 = 0x00003000, + /* SDBA2: pull-up disabled */ + .dram_sdba2 = 0x00000000, + /* SDODT[0:1]: 100k pull-up, 40 ohm */ + .dram_sdodt0 = 0x00003000+DRAM_DRIVE_STRENGTH, + .dram_sdodt1 = 0x00003000+DRAM_DRIVE_STRENGTH, + /* SDQS[0:7]: Differential input, 40 ohm */ + .dram_sdqs0 = DRAM_DRIVE_STRENGTH, + .dram_sdqs1 = DRAM_DRIVE_STRENGTH, + .dram_sdqs2 = DRAM_DRIVE_STRENGTH, + .dram_sdqs3 = DRAM_DRIVE_STRENGTH, + .dram_sdqs4 = DRAM_DRIVE_STRENGTH, + .dram_sdqs5 = DRAM_DRIVE_STRENGTH, + .dram_sdqs6 = DRAM_DRIVE_STRENGTH, + .dram_sdqs7 = DRAM_DRIVE_STRENGTH, + + /* DQM[0:7]: Differential input, 40 ohm */ + .dram_dqm0 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_dqm1 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_dqm2 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_dqm3 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_dqm4 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_dqm5 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_dqm6 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_dqm7 = DDR_MODE+DRAM_DRIVE_STRENGTH, +}; + +/* configure MX6Q/DUAL mmdc GRP io registers */ +static struct mx6dq_iomux_grp_regs const mx6dq_grp_ioregs = { + /* DDR3 */ + .grp_ddr_type = GRP_DDRTYPE, + .grp_ddrmode_ctl = DDR_MODE, + /* disable DDR pullups */ + .grp_ddrpke = DDR_PKE, + /* ADDR[00:16], SDBA[0:1]: 40 ohm */ + .grp_addds = DRAM_DRIVE_STRENGTH, + /* CS0/CS1/SDBA2/CKE0/CKE1/SDWE: 40 ohm */ + .grp_ctlds = DRAM_DRIVE_STRENGTH, + /* DATA[00:63]: Differential input, 40 ohm */ + .grp_ddrmode = DDR_MODE, + .grp_b0ds = DRAM_DRIVE_STRENGTH, + .grp_b1ds = DRAM_DRIVE_STRENGTH, + .grp_b2ds = DRAM_DRIVE_STRENGTH, + .grp_b3ds = DRAM_DRIVE_STRENGTH, + .grp_b4ds = DRAM_DRIVE_STRENGTH, + .grp_b5ds = DRAM_DRIVE_STRENGTH, + .grp_b6ds = DRAM_DRIVE_STRENGTH, + .grp_b7ds = DRAM_DRIVE_STRENGTH, +}; + +static struct mx6sdl_iomux_ddr_regs const mx6sdl_ddr_ioregs = { + /* SDCLK[0:1], CAS, RAS, Reset: Differential input, 40ohm */ + .dram_sdclk_0 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_sdclk_1 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_cas = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_ras = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_reset = DDR_MODE+DRAM_DRIVE_STRENGTH, + /* SDCKE[0:1]: 100k pull-up */ + .dram_sdcke0 = 0x00003000, + .dram_sdcke1 = 0x00003000, + /* SDBA2: pull-up disabled */ + .dram_sdba2 = 0x00000000, + /* SDODT[0:1]: 100k pull-up, 40 ohm */ + .dram_sdodt0 = 0x00003000+DRAM_DRIVE_STRENGTH, + .dram_sdodt1 = 0x00003000+DRAM_DRIVE_STRENGTH, + /* SDQS[0:7]: Differential input, 40 ohm */ + .dram_sdqs0 = DRAM_DRIVE_STRENGTH, + .dram_sdqs1 = DRAM_DRIVE_STRENGTH, + .dram_sdqs2 = DRAM_DRIVE_STRENGTH, + .dram_sdqs3 = DRAM_DRIVE_STRENGTH, + .dram_sdqs4 = DRAM_DRIVE_STRENGTH, + .dram_sdqs5 = DRAM_DRIVE_STRENGTH, + .dram_sdqs6 = DRAM_DRIVE_STRENGTH, + .dram_sdqs7 = DRAM_DRIVE_STRENGTH, + + /* DQM[0:7]: Differential input, 40 ohm */ + .dram_dqm0 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_dqm1 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_dqm2 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_dqm3 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_dqm4 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_dqm5 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_dqm6 = DDR_MODE+DRAM_DRIVE_STRENGTH, + .dram_dqm7 = DDR_MODE+DRAM_DRIVE_STRENGTH, +}; + +/* configure MX6SOLO/DUALLITE mmdc GRP io registers */ +static struct mx6sdl_iomux_grp_regs const mx6sdl_grp_ioregs = { + /* DDR3 */ + .grp_ddr_type = GRP_DDRTYPE, + /* SDQS[0:7]: Differential input, 40 ohm */ + .grp_ddrmode_ctl = DDR_MODE, + /* disable DDR pullups */ + .grp_ddrpke = DDR_PKE, + /* ADDR[00:16], SDBA[0:1]: 40 ohm */ + .grp_addds = DRAM_DRIVE_STRENGTH, + /* CS0/CS1/SDBA2/CKE0/CKE1/SDWE: 40 ohm */ + .grp_ctlds = DRAM_DRIVE_STRENGTH, + /* DATA[00:63]: Differential input, 40 ohm */ + .grp_ddrmode = DDR_MODE, + .grp_b0ds = DRAM_DRIVE_STRENGTH, + .grp_b1ds = DRAM_DRIVE_STRENGTH, + .grp_b2ds = DRAM_DRIVE_STRENGTH, + .grp_b3ds = DRAM_DRIVE_STRENGTH, + .grp_b4ds = DRAM_DRIVE_STRENGTH, + .grp_b5ds = DRAM_DRIVE_STRENGTH, + .grp_b6ds = DRAM_DRIVE_STRENGTH, + .grp_b7ds = DRAM_DRIVE_STRENGTH, +}; + +const struct mx6sl_iomux_ddr_regs mx6sl_ddr_ioregs = { + .dram_sdqs0 = DRAM_DRIVE_STRENGTH, + .dram_sdqs1 = DRAM_DRIVE_STRENGTH, + .dram_sdqs2 = DRAM_DRIVE_STRENGTH, + .dram_sdqs3 = DRAM_DRIVE_STRENGTH, + .dram_dqm0 = DRAM_DRIVE_STRENGTH, + .dram_dqm1 = DRAM_DRIVE_STRENGTH, + .dram_dqm2 = DRAM_DRIVE_STRENGTH, + .dram_dqm3 = DRAM_DRIVE_STRENGTH, + .dram_cas = DRAM_DRIVE_STRENGTH, + .dram_ras = DRAM_DRIVE_STRENGTH, + .dram_sdclk_0 = DRAM_DRIVE_STRENGTH, + .dram_reset = DRAM_DRIVE_STRENGTH, + .dram_sdba2 = 0x00020000, + .dram_odt0 = 0x00030000+DRAM_DRIVE_STRENGTH, + .dram_odt1 = 0x00030000+DRAM_DRIVE_STRENGTH, +}; + +const struct mx6sl_iomux_grp_regs mx6sl_grp_ioregs = { + .grp_b0ds = DRAM_DRIVE_STRENGTH, + .grp_b1ds = DRAM_DRIVE_STRENGTH, + .grp_b2ds = DRAM_DRIVE_STRENGTH, + .grp_b3ds = DRAM_DRIVE_STRENGTH, + .grp_addds = DRAM_DRIVE_STRENGTH, + .grp_ctlds = DRAM_DRIVE_STRENGTH, + .grp_ddrmode_ctl = DDR_MODE, + .grp_ddrpke = DDR_PKE, + .grp_ddrmode = DDR_MODE, + .grp_ddr_type = GRP_DDRTYPE, +}; + +static struct mx6_ddr_sysinfo const sysinfo = { + /* width of data bus:0=16,1=32,2=64 */ +#if CONFIG_DDRWIDTH == 32 + .dsize = 1, +#elif CONFIG_DDRWIDTH == 64 + .dsize = 2, +#else +#error missing CONFIG_DDRWIDTH +#endif + /* config for full 4GB range so that get_mem_size() works */ + .cs_density = 32, /* 32Gb per CS */ + + /* # of chip selects */ + .ncs = CONFIG_DDRCS, + .cs1_mirror = 0, + .rtt_wr = 1 /*DDR3_RTT_60_OHM*/, /* RTT_Wr = RZQ/4 */ +#ifdef RTT_NOM_120OHM + .rtt_nom = 2 /*DDR3_RTT_120_OHM*/, /* RTT_Nom = RZQ/2 */ +#else + .rtt_nom = 1 /*DDR3_RTT_60_OHM*/, /* RTT_Nom = RZQ/4 */ +#endif + .walat = CONFIG_WALAT, /* Write additional latency */ + .ralat = CONFIG_RALAT, /* Read additional latency */ + .mif3_mode = 3, /* Command prediction working mode */ + .bi_on = 1, /* Bank interleaving enabled */ +#ifdef CONFIG_DDR3 + .sde_to_rst = 0x10, /* JEDEC value for LPDDR2 - 200us */ + .rst_to_cke = 0x23, /* 33 cycles, 500us (JEDEC default) */ + .ddr_type = DDR_TYPE_DDR3, +#else + .sde_to_rst = 0, /* LPDDR2 does not need this field */ + .rst_to_cke = 0x10, /* JEDEC value for LPDDR2: 200us */ + .ddr_type = DDR_TYPE_LPDDR2, +#endif +}; + +#ifdef CONFIG_MT41K512M16TNA +/* MT41K512M16TNA-125 */ +static struct mx6_ddr3_cfg const ddrtype = { + .mem_speed = 1600, + .density = 8, + .width = 16, + .banks = 8, + .rowaddr = 15, + .coladdr = 10, + .pagesz = 1, + .trcd = 1375, + .trcmin = 5062, + .trasmin = 3750, +}; +#elif defined(CONFIG_MT41K128M16JT) +/* MT41K128M16JT-125 */ +static struct mx6_ddr3_cfg const ddrtype = { + .mem_speed = 1600, + .density = 2, + .width = 16, + .banks = 8, + .rowaddr = 14, + .coladdr = 10, + .pagesz = 2, + .trcd = 1375, + .trcmin = 4875, + .trasmin = 3500, +}; +#elif defined(CONFIG_H5TQ4G63AFR) +static struct mx6_ddr3_cfg const ddrtype = { + .mem_speed = 1600, + .density = 4, + .width = 16, + .banks = 8, + .rowaddr = 15, + .coladdr = 10, + .pagesz = 2, + .trcd = 1375, + .trcmin = 4875, + .trasmin = 3500, +}; +#elif defined CONFIG_H5TQ2G63DFR +static struct mx6_ddr3_cfg const ddrtype = { + .mem_speed = 1333, + .density = 2, + .width = 16, + .banks = 8, + .rowaddr = 14, + .coladdr = 10, + .pagesz = 2, + .trcd = 1350, + .trcmin = 4950, + .trasmin = 3600, +}; +#elif defined(CONFIG_MT42L256M32D2LG) +static struct mx6_lpddr2_cfg ddrtype = { + .mem_speed = 800, + .density = 4, + .width = 32, + .banks = 8, + .rowaddr = 14, + .coladdr = 10, + .trcd_lp = 2000, + .trppb_lp = 2000, + .trpab_lp = 2250, + .trasmin = 4200, +}; +#elif defined(CONFIG_MT29PZZZ4D4BKESK) +static struct mx6_lpddr2_cfg ddrtype = { + .mem_speed = 800, + .density = 4, + .width = 32, + .banks = 8, + .rowaddr = 14, + .coladdr = 10, + .trcd_lp = 2000, + .trppb_lp = 2000, + .trpab_lp = 2250, + .trasmin = 4200, +}; +#else +#error please select DDR type using menuconfig +#endif + +static void ccgr_init(void) +{ + struct mxc_ccm_reg *ccm = (struct mxc_ccm_reg *)CCM_BASE_ADDR; + + writel(0x00C03F3F, &ccm->CCGR0); + writel(0x0030FC03, &ccm->CCGR1); + writel(0x0FFFC000, &ccm->CCGR2); + writel(0x3FF00000, &ccm->CCGR3); + writel(0x00FFF300, &ccm->CCGR4); + writel(0x0F0000C3, &ccm->CCGR5); + writel(0x000003FF, &ccm->CCGR6); +} + +static void display_calibration(struct mx6_mmdc_calibration *calib) +{ + printf(".p0_mpdgctrl0\t= 0x%08X\n", calib->p0_mpdgctrl0); + printf(".p0_mpdgctrl1\t= 0x%08X\n", calib->p0_mpdgctrl1); + printf(".p0_mprddlctl\t= 0x%08X\n", calib->p0_mprddlctl); + printf(".p0_mpwrdlctl\t= 0x%08X\n", calib->p0_mpwrdlctl); + printf(".p0_mpwldectrl0\t= 0x%08X\n", calib->p0_mpwldectrl0); + printf(".p0_mpwldectrl1\t= 0x%08X\n", calib->p0_mpwldectrl1); + if (sysinfo.dsize == 2) { + printf(".p1_mpdgctrl0\t= 0x%08X\n", calib->p1_mpdgctrl0); + printf(".p1_mpdgctrl1\t= 0x%08X\n", calib->p1_mpdgctrl1); + printf(".p1_mprddlctl\t= 0x%08X\n", calib->p1_mprddlctl); + printf(".p1_mpwrdlctl\t= 0x%08X\n", calib->p1_mpwrdlctl); + printf(".p1_mpwldectrl0\t= 0x%08X\n", calib->p1_mpwldectrl0); + printf(".p1_mpwldectrl1\t= 0x%08X\n", calib->p1_mpwldectrl1); + } +#ifdef CONFIG_IMXIMAGE_OUTPUT + printf("DATA 4 MX6_MMDC_P0_MPDGCTRL0\t= 0x%08X\n", calib->p0_mpdgctrl0); + printf("DATA 4 MX6_MMDC_P0_MPDGCTRL1\t= 0x%08X\n", calib->p0_mpdgctrl1); + printf("DATA 4 MX6_MMDC_P0_MPRDDLCTL\t= 0x%08X\n", calib->p0_mprddlctl); + printf("DATA 4 MX6_MMDC_P0_MPWRDLCTL\t= 0x%08X\n", calib->p0_mpwrdlctl); + printf("DATA 4 MX6_MMDC_P0_MPWLDECTRL0\t= 0x%08X\n", + calib->p0_mpwldectrl0); + printf("DATA 4 MX6_MMDC_P0_MPWLDECTRL1\t= 0x%08X\n", + calib->p0_mpwldectrl1); + if (sysinfo.dsize == 2) { + printf("DATA 4 MX6_MMDC_P1_mpdgctrl0\t= 0x%08X\n", + calib->p1_mpdgctrl0); + printf("DATA 4 MX6_MMDC_P1_mpdgctrl1\t= 0x%08X\n", + calib->p1_mpdgctrl1); + printf("DATA 4 MX6_MMDC_P1_mprddlctl\t= 0x%08X\n", + calib->p1_mprddlctl); + printf("DATA 4 MX6_MMDC_P1_mpwrdlctl\t= 0x%08X\n", + calib->p1_mpwrdlctl); + printf("DATA 4 MX6_MMDC_P1_mpwldectrl0\t= 0x%08X\n", + calib->p1_mpwldectrl0); + printf("DATA 4 MX6_MMDC_P1_mpwldectrl1\t= 0x%08X\n", + calib->p1_mpwldectrl1); + } +#endif +} + +/* + * called from C runtime startup code (arch/arm/lib/crt0.S:_main) + * - we have a stack and a place to store GD, both in SRAM + * - no variable global data is available + */ +void board_init_f(ulong dummy) +{ + int errs; + struct mx6_mmdc_calibration calibration; + u32 cpurev = get_cpu_rev(); + + memset((void *)gd, 0, sizeof(struct global_data)); + + /* setup AIPS and disable watchdog */ + arch_cpu_init(); + + ccgr_init(); + + SETUP_IOMUX_PADS(uart_pads); + + /* setup GP timer */ + timer_init(); + + /* UART clocks enabled and gd valid - init serial console */ + preloader_console_init(); + + if (sysinfo.dsize != 1) { + if (is_cpu_type(MXC_CPU_MX6SX) || + is_cpu_type(MXC_CPU_MX6UL) || + is_cpu_type(MXC_CPU_MX6SL)) { + printf("cpu type 0x%x doesn't support 64-bit bus\n", + get_cpu_type()); + reset_cpu(0); + } + } + printf("CPU: Freescale i.MX%s rev%d.%d at %d MHz\n", + get_imx_type((cpurev & 0xFF000) >> 12), + (cpurev & 0x000F0) >> 4, + (cpurev & 0x0000F) >> 0, + mxc_get_clock(MXC_ARM_CLK) / 1000000); +#ifdef CONFIG_MX6SL + mx6sl_dram_iocfg(CONFIG_DDRWIDTH, &mx6sl_ddr_ioregs, + &mx6sl_grp_ioregs); +#else + if (is_cpu_type(MXC_CPU_MX6Q)) { + mx6dq_dram_iocfg(CONFIG_DDRWIDTH, &mx6dq_ddr_ioregs, + &mx6dq_grp_ioregs); + } else { + mx6sdl_dram_iocfg(CONFIG_DDRWIDTH, &mx6sdl_ddr_ioregs, + &mx6sdl_grp_ioregs); + } +#endif + mx6_dram_cfg(&sysinfo, NULL, &ddrtype); + + errs = mmdc_do_write_level_calibration(&sysinfo, &calibration); + if (errs) { + printf("error %d from write level calibration\n", errs); + } else { + errs = mmdc_do_dqs_calibration(&sysinfo, &calibration); + if (errs) { + printf("error %d from write level calibration\n", errs); + } else { + printf("completed successfully\n"); + display_calibration(&calibration); + } + } + + reset_cpu(0); +} + diff --git a/configs/mx6memcal_defconfig b/configs/mx6memcal_defconfig new file mode 100644 index 0000000..826d316 --- /dev/null +++ b/configs/mx6memcal_defconfig @@ -0,0 +1,30 @@ +CONFIG_ARM=y +CONFIG_ARCH_MX6=y +CONFIG_MX6_DDRCAL=y +CONFIG_TARGET_MX6MEMCAL=y +CONFIG_SPL=y +CONFIG_SYS_EXTRA_OPTIONS="IMX_CONFIG=arch/arm/imx-common/spl_sd.cfg,SPL,MX6QDL" +CONFIG_DDRWIDTH=64 +CONFIG_DDRCS=2 +#CONFIG_MT41K512M16TNA is not set +CONFIG_MT41K128M16JT=y +#CONFIG_H5TQ4G63AFR is not set +# CONFIG_CMD_BOOTD is not set +# CONFIG_CMD_BOOTM is not set +# CONFIG_CMD_ELF is not set +# CONFIG_CMD_GO is not set +# CONFIG_CMD_RUN is not set +# CONFIG_CMD_IMI is not set +# CONFIG_CMD_IMLS is not set +# CONFIG_CMD_XIMG is not set +# CONFIG_CMD_EXPORTENV is not set +# CONFIG_CMD_IMPORTENV is not set +# CONFIG_CMD_EDITENV is not set +# CONFIG_CMD_SAVEENV is not set +# CONFIG_CMD_ENV_EXISTS is not set +# CONFIG_CMD_LOADB is not set +# CONFIG_CMD_LOADS is not set +# CONFIG_CMD_FLASH is not set +# CONFIG_CMD_FPGA is not set +# CONFIG_CMD_NET is not set +# CONFIG_CMD_NFS is not set diff --git a/include/configs/mx6memcal.h b/include/configs/mx6memcal.h new file mode 100644 index 0000000..8562360 --- /dev/null +++ b/include/configs/mx6memcal.h @@ -0,0 +1,65 @@ +/* + * Copyright (C) 2010-2011 Freescale Semiconductor, Inc. + * + * Configuration settings for the Boundary Devices Nitrogen6X + * and Freescale i.MX6Q Sabre Lite boards. + * + * SPDX-License-Identifier: GPL-2.0+ + */ + +#ifndef __CONFIG_H +#define __CONFIG_H + +/* SPL */ +#define CONFIG_SPL_WATCHDOG_SUPPORT + +#include "mx6_common.h" +#include "imx6_spl.h" + +#undef CONFIG_CMD_BOOTM +#undef CONFIG_FSL_ESDHC +#undef CONFIG_MMC +#undef CONFIG_SPL_MMC_SUPPORT +#undef CONFIG_GENERIC_MMC +#undef CONFIG_CMD_FUSE + +#define CONFIG_SYS_MEMTEST_START 0x10000000 +#define CONFIG_SYS_MEMTEST_END 0x20000000 +#define CONFIG_SYS_MALLOC_LEN (64 * 1024 * 1024) + +#define CONFIG_MXC_UART +#ifdef CONFIG_SERIAL_CONSOLE_UART1 +#if defined(CONFIG_MX6SL) +#define CONFIG_MXC_UART_BASE UART1_IPS_BASE_ADDR +#else +#define CONFIG_MXC_UART_BASE UART1_BASE +#endif +#elif defined(CONFIG_SERIAL_CONSOLE_UART2) +#define CONFIG_MXC_UART_BASE UART2_BASE +#else +#error please define serial console (CONFIG_SERIAL_CONSOLE_UARTx) +#endif +#define CONFIG_BAUDRATE 115200 + +#define CONFIG_SYS_PBSIZE (CONFIG_SYS_CBSIZE + 16) + +/* Physical Memory Map */ +#define CONFIG_NR_DRAM_BANKS 1 +#define PHYS_SDRAM MMDC0_ARB_BASE_ADDR +#define CONFIG_RESET_CAUSE_ADDR (PHYS_SDRAM + 0x80) + +#define CONFIG_SYS_SDRAM_BASE PHYS_SDRAM +#define CONFIG_SYS_INIT_RAM_ADDR IRAM_BASE_ADDR +#define CONFIG_SYS_INIT_RAM_SIZE IRAM_SIZE + +#define CONFIG_SYS_INIT_SP_OFFSET \ + (CONFIG_SYS_INIT_RAM_SIZE - GENERATED_GBL_DATA_SIZE) +#define CONFIG_SYS_INIT_SP_ADDR \ + (CONFIG_SYS_INIT_RAM_ADDR + CONFIG_SYS_INIT_SP_OFFSET) + +#define CONFIG_SYS_NO_FLASH + +#define CONFIG_ENV_SIZE (8 * 1024) +#define CONFIG_ENV_IS_NOWHERE + +#endif /* __CONFIG_H */