xref: /openbmc/u-boot/board/compulab/cl-som-imx7/spl.c (revision 83d290c56fab2d38cd1ab4c4cc7099559c1d5046)
1*83d290c5STom Rini // SPDX-License-Identifier: GPL-2.0+
26963204cSIlya Ledvich /*
36963204cSIlya Ledvich  * SPL board functions for CompuLab CL-SOM-iMX7 module
46963204cSIlya Ledvich  *
56963204cSIlya Ledvich  * (C) Copyright 2017 CompuLab, Ltd. http://www.compulab.com
66963204cSIlya Ledvich  *
76963204cSIlya Ledvich  * Author: Uri Mashiach <uri.mashiach@compulab.co.il>
86963204cSIlya Ledvich  */
96963204cSIlya Ledvich 
106963204cSIlya Ledvich #include <common.h>
116963204cSIlya Ledvich #include <spl.h>
126963204cSIlya Ledvich #include <fsl_esdhc.h>
136963204cSIlya Ledvich #include <asm/mach-imx/iomux-v3.h>
146963204cSIlya Ledvich #include <asm/arch-mx7/mx7-pins.h>
156963204cSIlya Ledvich #include <asm/arch-mx7/clock.h>
166963204cSIlya Ledvich #include <asm/arch-mx7/mx7-ddr.h>
176963204cSIlya Ledvich #include "common.h"
186963204cSIlya Ledvich 
196963204cSIlya Ledvich #ifdef CONFIG_FSL_ESDHC
206963204cSIlya Ledvich 
216963204cSIlya Ledvich static struct fsl_esdhc_cfg cl_som_imx7_spl_usdhc_cfg = {
226963204cSIlya Ledvich 	USDHC1_BASE_ADDR, 0, 4};
236963204cSIlya Ledvich 
board_mmc_init(bd_t * bis)246963204cSIlya Ledvich int board_mmc_init(bd_t *bis)
256963204cSIlya Ledvich {
266963204cSIlya Ledvich 	cl_som_imx7_usdhc1_pads_set();
276963204cSIlya Ledvich 	cl_som_imx7_spl_usdhc_cfg.sdhc_clk = mxc_get_clock(MXC_ESDHC_CLK);
286963204cSIlya Ledvich 	return fsl_esdhc_initialize(bis, &cl_som_imx7_spl_usdhc_cfg);
296963204cSIlya Ledvich }
306963204cSIlya Ledvich #endif /* CONFIG_FSL_ESDHC */
316963204cSIlya Ledvich 
326963204cSIlya Ledvich static iomux_v3_cfg_t const led_pads[] = {
336963204cSIlya Ledvich 	MX7D_PAD_SAI1_TX_SYNC__GPIO6_IO14 | MUX_PAD_CTRL(PAD_CTL_PUS_PU5KOHM |
346963204cSIlya Ledvich 		PAD_CTL_PUE | PAD_CTL_SRE_SLOW)
356963204cSIlya Ledvich };
366963204cSIlya Ledvich 
376963204cSIlya Ledvich static struct ddrc cl_som_imx7_spl_ddrc_regs_val = {
386963204cSIlya Ledvich 	.init1		= 0x00690000,
396963204cSIlya Ledvich 	.init0		= 0x00020083,
406963204cSIlya Ledvich 	.init3		= 0x09300004,
416963204cSIlya Ledvich 	.init4		= 0x04080000,
426963204cSIlya Ledvich 	.init5		= 0x00100004,
436963204cSIlya Ledvich 	.rankctl	= 0x0000033F,
446963204cSIlya Ledvich 	.dramtmg1	= 0x0007020E,
456963204cSIlya Ledvich 	.dramtmg2	= 0x03040407,
466963204cSIlya Ledvich 	.dramtmg3	= 0x00002006,
476963204cSIlya Ledvich 	.dramtmg4	= 0x04020305,
486963204cSIlya Ledvich 	.dramtmg5	= 0x03030202,
496963204cSIlya Ledvich 	.dramtmg8	= 0x00000803,
506963204cSIlya Ledvich 	.zqctl0		= 0x00810021,
516963204cSIlya Ledvich 	.dfitmg0	= 0x02098204,
526963204cSIlya Ledvich 	.dfitmg1	= 0x00030303,
536963204cSIlya Ledvich 	.dfiupd0	= 0x80400003,
546963204cSIlya Ledvich 	.dfiupd1	= 0x00100020,
556963204cSIlya Ledvich 	.dfiupd2	= 0x80100004,
566963204cSIlya Ledvich 	.addrmap4	= 0x00000F0F,
576963204cSIlya Ledvich 	.odtcfg		= 0x06000604,
586963204cSIlya Ledvich 	.odtmap		= 0x00000001,
596963204cSIlya Ledvich };
606963204cSIlya Ledvich 
616963204cSIlya Ledvich static struct ddrc_mp cl_som_imx7_spl_ddrc_mp_val = {
626963204cSIlya Ledvich 	.pctrl_0	= 0x00000001,
636963204cSIlya Ledvich };
646963204cSIlya Ledvich 
656963204cSIlya Ledvich static struct ddr_phy cl_som_imx7_spl_ddr_phy_regs_val = {
666963204cSIlya Ledvich 	.phy_con0	= 0x17420F40,
676963204cSIlya Ledvich 	.phy_con1	= 0x10210100,
686963204cSIlya Ledvich 	.phy_con4	= 0x00060807,
696963204cSIlya Ledvich 	.mdll_con0	= 0x1010007E,
706963204cSIlya Ledvich 	.drvds_con0	= 0x00000D6E,
716963204cSIlya Ledvich 	.cmd_sdll_con0	= 0x00000010,
726963204cSIlya Ledvich 	.offset_lp_con0	= 0x0000000F,
736963204cSIlya Ledvich };
746963204cSIlya Ledvich 
756963204cSIlya Ledvich struct mx7_calibration cl_som_imx7_spl_calib_param = {
766963204cSIlya Ledvich 	.num_val	= 5,
776963204cSIlya Ledvich 	.values		= {
786963204cSIlya Ledvich 		0x0E407304,
796963204cSIlya Ledvich 		0x0E447304,
806963204cSIlya Ledvich 		0x0E447306,
816963204cSIlya Ledvich 		0x0E447304,
826963204cSIlya Ledvich 		0x0E407304,
836963204cSIlya Ledvich 	},
846963204cSIlya Ledvich };
856963204cSIlya Ledvich 
cl_som_imx7_spl_dram_cfg_size(u32 ram_size)866963204cSIlya Ledvich static void cl_som_imx7_spl_dram_cfg_size(u32 ram_size)
876963204cSIlya Ledvich {
886963204cSIlya Ledvich 	switch (ram_size) {
896963204cSIlya Ledvich 	case SZ_256M:
906963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.mstr		= 0x01041001;
916963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.rfshtmg		= 0x00400046;
926963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.dramtmg0		= 0x090E1109;
936963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.addrmap0		= 0x00000014;
946963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.addrmap1		= 0x00151515;
956963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.addrmap5		= 0x03030303;
966963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.addrmap6		= 0x0F0F0303;
976963204cSIlya Ledvich 		cl_som_imx7_spl_ddr_phy_regs_val.offset_rd_con0	= 0x0C0C0C0C;
986963204cSIlya Ledvich 		cl_som_imx7_spl_ddr_phy_regs_val.offset_wr_con0	= 0x04040404;
996963204cSIlya Ledvich 		break;
1006963204cSIlya Ledvich 	case SZ_512M:
1016963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.mstr		= 0x01040001;
1026963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.rfshtmg		= 0x00400046;
1036963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.dramtmg0		= 0x090E1109;
1046963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.addrmap0		= 0x00000015;
1056963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.addrmap1		= 0x00161616;
1066963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.addrmap5		= 0x04040404;
1076963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.addrmap6		= 0x0F0F0404;
1086963204cSIlya Ledvich 		cl_som_imx7_spl_ddr_phy_regs_val.offset_rd_con0	= 0x0C0C0C0C;
1096963204cSIlya Ledvich 		cl_som_imx7_spl_ddr_phy_regs_val.offset_wr_con0	= 0x04040404;
1106963204cSIlya Ledvich 		break;
1116963204cSIlya Ledvich 	case SZ_1G:
1126963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.mstr		= 0x01040001;
1136963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.rfshtmg		= 0x00400046;
1146963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.dramtmg0		= 0x090E1109;
1156963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.addrmap0		= 0x00000016;
1166963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.addrmap1		= 0x00171717;
1176963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.addrmap5		= 0x04040404;
1186963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.addrmap6		= 0x0F040404;
1196963204cSIlya Ledvich 		cl_som_imx7_spl_ddr_phy_regs_val.offset_rd_con0	= 0x0A0A0A0A;
1206963204cSIlya Ledvich 		cl_som_imx7_spl_ddr_phy_regs_val.offset_wr_con0	= 0x02020202;
1216963204cSIlya Ledvich 		break;
1226963204cSIlya Ledvich 	case SZ_2G:
1236963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.mstr		= 0x01040001;
1246963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.rfshtmg		= 0x0040005E;
1256963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.dramtmg0		= 0x090E110A;
1266963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.addrmap0		= 0x00000018;
1276963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.addrmap1		= 0x00181818;
1286963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.addrmap5		= 0x04040404;
1296963204cSIlya Ledvich 		cl_som_imx7_spl_ddrc_regs_val.addrmap6		= 0x04040404;
1306963204cSIlya Ledvich 		cl_som_imx7_spl_ddr_phy_regs_val.offset_rd_con0	= 0x0A0A0A0A;
1316963204cSIlya Ledvich 		cl_som_imx7_spl_ddr_phy_regs_val.offset_wr_con0	= 0x04040404;
1326963204cSIlya Ledvich 		break;
1336963204cSIlya Ledvich 	}
1346963204cSIlya Ledvich 
1356963204cSIlya Ledvich 	mx7_dram_cfg(&cl_som_imx7_spl_ddrc_regs_val,
1366963204cSIlya Ledvich 		     &cl_som_imx7_spl_ddrc_mp_val,
1376963204cSIlya Ledvich 		     &cl_som_imx7_spl_ddr_phy_regs_val,
1386963204cSIlya Ledvich 		     &cl_som_imx7_spl_calib_param);
1396963204cSIlya Ledvich }
1406963204cSIlya Ledvich 
cl_som_imx7_spl_dram_cfg(void)1416963204cSIlya Ledvich static void cl_som_imx7_spl_dram_cfg(void)
1426963204cSIlya Ledvich {
1436963204cSIlya Ledvich 	ulong ram_size_test, ram_size = 0;
1446963204cSIlya Ledvich 
1456963204cSIlya Ledvich 	for (ram_size = SZ_2G; ram_size >= SZ_256M; ram_size >>= 1) {
1466963204cSIlya Ledvich 		cl_som_imx7_spl_dram_cfg_size(ram_size);
1476963204cSIlya Ledvich 		ram_size_test = get_ram_size((long int *)PHYS_SDRAM, ram_size);
1486963204cSIlya Ledvich 		if (ram_size_test == ram_size)
1496963204cSIlya Ledvich 			break;
1506963204cSIlya Ledvich 	}
1516963204cSIlya Ledvich 
1526963204cSIlya Ledvich 	if (ram_size < SZ_256M) {
1536963204cSIlya Ledvich 		puts("!!!ERROR!!! DRAM detection failed!!!\n");
1546963204cSIlya Ledvich 		hang();
1556963204cSIlya Ledvich 	}
1566963204cSIlya Ledvich }
1576963204cSIlya Ledvich 
1586963204cSIlya Ledvich #ifdef CONFIG_SPL_SPI_SUPPORT
1596963204cSIlya Ledvich 
cl_som_imx7_spl_spi_init(void)1606963204cSIlya Ledvich static void cl_som_imx7_spl_spi_init(void)
1616963204cSIlya Ledvich {
1626963204cSIlya Ledvich 	cl_som_imx7_espi1_pads_set();
1636963204cSIlya Ledvich }
1646963204cSIlya Ledvich #else /* !CONFIG_SPL_SPI_SUPPORT */
cl_som_imx7_spl_spi_init(void)1656963204cSIlya Ledvich static void cl_som_imx7_spl_spi_init(void) {}
1666963204cSIlya Ledvich #endif /* CONFIG_SPL_SPI_SUPPORT */
1676963204cSIlya Ledvich 
board_init_f(ulong dummy)1686963204cSIlya Ledvich void board_init_f(ulong dummy)
1696963204cSIlya Ledvich {
1706963204cSIlya Ledvich 	imx_iomux_v3_setup_multiple_pads(led_pads, 1);
1716963204cSIlya Ledvich 	/* setup AIPS and disable watchdog */
1726963204cSIlya Ledvich 	arch_cpu_init();
1736963204cSIlya Ledvich 	/* setup GP timer */
1746963204cSIlya Ledvich 	timer_init();
1756963204cSIlya Ledvich 	cl_som_imx7_spl_spi_init();
1766963204cSIlya Ledvich 	cl_som_imx7_uart1_pads_set();
1776963204cSIlya Ledvich 	/* UART clocks enabled and gd valid - init serial console */
1786963204cSIlya Ledvich 	preloader_console_init();
1796963204cSIlya Ledvich 	/* DRAM detection  */
1806963204cSIlya Ledvich 	cl_som_imx7_spl_dram_cfg();
1816963204cSIlya Ledvich 	/* Clear the BSS. */
1826963204cSIlya Ledvich 	memset(__bss_start, 0, __bss_end - __bss_start);
1836963204cSIlya Ledvich 	/* load/boot image from boot device */
1846963204cSIlya Ledvich 	board_init_r(NULL, 0);
1856963204cSIlya Ledvich }
1866963204cSIlya Ledvich 
spl_board_init(void)1876963204cSIlya Ledvich void spl_board_init(void)
1886963204cSIlya Ledvich {
1896963204cSIlya Ledvich 	u32 boot_device = spl_boot_device();
1906963204cSIlya Ledvich 
1916963204cSIlya Ledvich 	if (boot_device == BOOT_DEVICE_SPI)
1926963204cSIlya Ledvich 		puts("Booting from SPI flash\n");
1936963204cSIlya Ledvich 	else if (boot_device == BOOT_DEVICE_MMC1)
1946963204cSIlya Ledvich 		puts("Booting from SD card\n");
1956963204cSIlya Ledvich 	else
1966963204cSIlya Ledvich 		puts("Unknown boot device\n");
1976963204cSIlya Ledvich }
1986963204cSIlya Ledvich 
board_boot_order(u32 * spl_boot_list)1996963204cSIlya Ledvich void board_boot_order(u32 *spl_boot_list)
2006963204cSIlya Ledvich {
2016963204cSIlya Ledvich 	spl_boot_list[0] = spl_boot_device();
2026963204cSIlya Ledvich 	switch (spl_boot_list[0]) {
2036963204cSIlya Ledvich 	case BOOT_DEVICE_SPI:
2046963204cSIlya Ledvich 		spl_boot_list[1] = BOOT_DEVICE_MMC1;
2056963204cSIlya Ledvich 		break;
2066963204cSIlya Ledvich 	case BOOT_DEVICE_MMC1:
2076963204cSIlya Ledvich 		spl_boot_list[1] = BOOT_DEVICE_SPI;
2086963204cSIlya Ledvich 		break;
2096963204cSIlya Ledvich 	}
2106963204cSIlya Ledvich }
211