bsh: imx6ulz_smm_m2: Add imx6ulz BSH SMM M2B board

Introduce the BSH SystemMaster (SMM) M2B board. Notably, the M2B is
designed to leverage the existing device tree of its predecessor, the M2.
The primary distinction arises from memory incompatibilities with the M2.
To address this, we've implemented a configuration system that allows for
selective inclusion of the desired memory components.

Signed-off-by: Michael Trimarchi <michael@amarulasolutions.com>
This commit is contained in:
Michael Trimarchi
2025-05-31 16:54:33 +02:00
committed by Fabio Estevam
parent 8642939ee0
commit c7b82b4aab
11 changed files with 415 additions and 17 deletions

View File

@@ -9,4 +9,25 @@ config SYS_VENDOR
config SYS_CONFIG_NAME
default "imx6ulz_smm_m2"
choice
prompt "Memory Type (M2/M2B) board"
default BSH_M2_MEMORY
help
Memory type setup.
Please choose correct memory model here.
config BSH_M2_MEMORY
bool "Enable for bsh m2 variant"
help
If this option is enabled, U-Boot will be configured to support
imx6ulz bsh m2 revision memories.
config BSH_M2B_MEMORY
bool "Enable for bsh m2b variant"
help
If this option is enabled, U-Boot will be configured to support
imx6ulz bsh m2b revision memories.
endchoice
endif

View File

@@ -4,3 +4,4 @@ S: Maintained
F: board/bsh/imx6ulz_smm_m2/
F: include/configs/imx6ulz_smm_m2.h
F: configs/imx6ulz_smm_m2_defconfig
F: configs/imx6ulz_smm_m2b_defconfig

View File

@@ -2,4 +2,6 @@
# (C) Copyright 2021 Amarula Solutions B.V.
obj-y := imx6ulz_smm_m2.o
obj-$(CONFIG_XPL_BUILD) += spl.o ddr3l_timing_512m.o ddr3l_timing_256m.o ddr3l_timing_128m.o
obj-$(CONFIG_XPL_BUILD) += spl.o
obj-$(CONFIG_BSH_M2_MEMORY) += ddr3l_timing_512m.o ddr3l_timing_256m.o ddr3l_timing_128m.o
obj-$(CONFIG_BSH_M2B_MEMORY) += ddr3l_timing_256m_m2b.o ddr3l_timing_128m_m2b.o

View File

@@ -166,4 +166,5 @@ static const struct dram_cfg_param ddr_ddrc_cfg_128mb[] = {
struct dram_timing_info bsh_dram_timing_128mb = {
.ddrc_cfg = ddr_ddrc_cfg_128mb,
.ddrc_cfg_num = ARRAY_SIZE(ddr_ddrc_cfg_128mb),
.dram_size = SZ_128M,
};

View File

@@ -0,0 +1,152 @@
// SPDX-License-Identifier: GPL-2.0+
#include "spl_mtypes.h"
static const struct dram_cfg_param ddr_ddrc_cfg_128mb[] = {
/* IOMUX */
/* DDR IO Type: */
{0x020e04b4, 0x000C0000}, /* IOMUXC_SW_PAD_CTL_GRP_DDR_TYPE */
{0x020e04ac, 0x00000000}, /* IOMUXC_SW_PAD_CTL_GRP_DDRPKE */
/* Clock: */
{0x020e027c, 0x00000028}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_SDCLK_0 */
/* Address: */
{0x020e0250, 0x00000028}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_CAS */
{0x020e024c, 0x00000028}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_RAS */
{0x020e0490, 0x00000028}, /* IOMUXC_SW_PAD_CTL_GRP_ADDDS */
/* Control: */
{0x020e0288, 0x000C0028}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_RESET */
{0x020e0270, 0x00000000}, /*
* IOMUXC_SW_PAD_CTL_PAD_DRAM_SDBA2 - DSE can be configured
* using Group Control Register IOMUXC_SW_PAD_CTL_GRP_CTLDS
*/
{0x020e0260, 0x00000028}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_SDODT0 */
{0x020e0264, 0x00000028}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_SDODT1 */
{0x020e04a0, 0x00000028}, /* IOMUXC_SW_PAD_CTL_GRP_CTLDS */
/* Data Strobes: */
{0x020e0494, 0x00020000}, /* IOMUXC_SW_PAD_CTL_GRP_DDRMODE_CTL */
{0x020e0280, 0x00000028}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_SDQS0 */
{0x020e0284, 0x00000028}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_SDQS1 */
/* Data: */
{0x020e04b0, 0x00020000}, /* IOMUXC_SW_PAD_CTL_GRP_DDRMODE */
{0x020e0498, 0x00000028}, /* IOMUXC_SW_PAD_CTL_GRP_B0DS */
{0x020e04a4, 0x00000028}, /* IOMUXC_SW_PAD_CTL_GRP_B1DS */
{0x020e0244, 0x00000028}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_DQM0 */
{0x020e0248, 0x00000028}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_DQM1 */
/*
* =============================================================================
* DDR Controller Registers
* =============================================================================
* Manufacturer:WINBOND
* Device Part Number:W631GU6RB-11
* Clock Freq.: 400MHz
* Density per CS in Gb: 1
* Chip Selects used:1
* Total DRAM density (Gb)1
* Number of Banks:8
* Row address: 13
* Column address: 10
* Data bus width16
* =============================================================================
*/
{0x021b001c, 0x00008000}, /*
* MMDC0_MDSCR, set the Configuration request bit
* during MMDC set up
*/
/*
* =============================================================================
* Calibration setup.
* =============================================================================
*/
{0x021b0800, 0xA1390003}, /*
* DDR_PHY_P0_MPZQHWCTRL, enable both one-time & periodic
* HW ZQ calibration.
*/
/*
* For target board, may need to run write leveling calibration to fine tune
* these settings.
*/
{0x021b080c, 0x00060002},
/* Read DQS Gating calibration */
{0x021b083c, 0x414c0150}, /* MPDGCTRL0 PHY0 */
/* Read calibration */
{0x021b0848, 0x4040363e}, /* MPRDDLCTL PHY0 */
/* Write calibration */
{0x021b0850, 0x40402a28}, /* MPWRDLCTL PHY0 */
/*
* Read data bit delay: 3 is the recommended default value, although out of reset
* value is 0.
*/
{0x021b081c, 0x33333333}, /* MMDC_MPRDDQBY0DL */
{0x021b0820, 0x33333333}, /* MMDC_MPRDDQBY1DL */
/* Write data bit delay: */
{0x021b082c, 0xf3333333}, /* MMDC_MPWRDQBY0DL */
{0x021b0830, 0xf3333333}, /* MMDC_MPWRDQBY1DL */
/* DQS&CLK Duty Cycle */
{0x021b08c0, 0x00944009}, /* [MMDC_MPDCCR] MMDC Duty Cycle Control Register */
/* Complete calibration by forced measurement: */
{0x021b08b8, 0x00000800}, /* DDR_PHY_P0_MPMUR0, frc_msr */
/* MMDC init: */
{0x021b0004, 0x0002002D}, /* MMDC0_MDPDC */
{0x021b0008, 0x1B333030}, /* MMDC0_MDOTC */
{0x021b000c, 0x2B2F52F3}, /* MMDC0_MDCFG0 */
{0x021b0010, 0xB66D0A63}, /* MMDC0_MDCFG1 */
{0x021b0014, 0x01FF00DB}, /* MMDC0_MDCFG2 */
{0x021b0018, 0x00201740}, /* MMDC0_MDMISC */
{0x021b002C, 0x000026D2}, /* MMDC0_MDRWD */
{0x021b0030, 0x002F1023}, /* MMDC0_MDOR */
{0x021b0040, 0x00000043}, /* CS0_END */
{0x021b0000, 0x82180000}, /* MMDC0_MDCTL */
/* Mode register writes for CS0 */
{0x021B001C, 0x02808032}, /* MMDC0_MDSCR, MR2 write, CS0 */
{0x021B001C, 0x00008033}, /* MMDC0_MDSCR, MR3 write, CS0 */
{0x021B001C, 0x00048031}, /* MMDC0_MDSCR, MR1 write, CS0 */
{0x021B001C, 0x15208030}, /* MMDC0_MDSCR, MR0 write, CS0 */
{0x021B001C, 0x04008040}, /*
* MMDC0_MDSCR, ZQ calibration
* command sent to device on CS0
*/
/* final DDR setup, before operation start: */
{0x021b0020, 0x00000800}, /* MMDC0_MDREF */
{0x021b0818, 0x00000227}, /* DDR_PHY_P0_MPODTCTRL */
{0x021b0004, 0x0002556D}, /* MMDC0_MDPDC now SDCTL power down enabled */
{0x021b0404, 0x00011006}, /*
* MMDC0_MAPSR ADOPT power down enabled,
* MMDC will enter automatically to self-refresh
* while the number of idle cycle reached.
*/
{0x021b001c, 0x00000000}, /*
* MMDC0_MDSCR, clear this register (especially the
* configuration bit as initialization is complete)
*/
};
struct dram_timing_info bsh_dram_timing_128mb = {
.ddrc_cfg = ddr_ddrc_cfg_128mb,
.ddrc_cfg_num = ARRAY_SIZE(ddr_ddrc_cfg_128mb),
.dram_size = SZ_128M,
};

View File

@@ -165,4 +165,5 @@ static const struct dram_cfg_param ddr_ddrc_cfg_256mb[] = {
struct dram_timing_info bsh_dram_timing_256mb = {
.ddrc_cfg = ddr_ddrc_cfg_256mb,
.ddrc_cfg_num = ARRAY_SIZE(ddr_ddrc_cfg_256mb),
.dram_size = SZ_256M,
};

View File

@@ -0,0 +1,137 @@
// SPDX-License-Identifier: GPL-2.0+
#include "spl_mtypes.h"
static const struct dram_cfg_param ddr_ddrc_cfg_256mb[] = {
/* IOMUX */
/* DDR IO Type: */
{0x020e04b4, 0x000C0000}, /* IOMUXC_SW_PAD_CTL_GRP_DDR_TYPE */
{0x020e04ac, 0x00000000}, /* IOMUXC_SW_PAD_CTL_GRP_DDRPKE */
/* Clock: */
{0x020e027c, 0x00000030}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_SDCLK0_P */
/* Address: */
{0x020e0250, 0x00000030}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_CAS */
{0x020e024c, 0x00000030}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_RAS */
{0x020e0490, 0x00000030}, /* IOMUXC_SW_PAD_CTL_GRP_ADDDS */
/* Control: */
{0x020e0288, 0x000C0030}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_RESET */
{0x020e0270, 0x00000000}, /*
* IOMUXC_SW_PAD_CTL_PAD_DRAM_SDBA2 - DSE can be
* configured using Group Control Register:
* IOMUXC_SW_PAD_CTL_GRP_CTLDS
*/
{0x020e0260, 0x00000030}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_ODT0 */
{0x020e0264, 0x00000030}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_ODT1 */
{0x020e04a0, 0x00000028}, /* IOMUXC_SW_PAD_CTL_GRP_CTLDS */
/* Data Strobes: */
{0x020e0494, 0x00020000}, /* IOMUXC_SW_PAD_CTL_GRP_DDRMODE_CTL */
{0x020e0280, 0x00000030}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_SDQS0_P */
{0x020e0284, 0x00000030}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_SDQS1_P */
/* Data: */
{0x020e04b0, 0x00020000}, /* IOMUXC_SW_PAD_CTL_GRP_DDRMODE */
{0x020e0498, 0x00000030}, /* IOMUXC_SW_PAD_CTL_GRP_B0DS */
{0x020e04a4, 0x00000030}, /* IOMUXC_SW_PAD_CTL_GRP_B1DS */
{0x020e0244, 0x00000030}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_DQM0 */
{0x020e0248, 0x00000030}, /* IOMUXC_SW_PAD_CTL_PAD_DRAM_DQM1 */
/*
* =============================================================================
* DDR Controller Registers
* =============================================================================
* Manufacturer:WINBOND
* Device Part Number:W632GU6RB-11
* Clock Freq.: 400MHz
* Density per CS in Gb: 2
* Chip Selects used:1
* Total DRAM density (Gb)2
* Number of Banks:8
* Row address: 14
* Column address: 10
* Data bus width16
* =============================================================================
*/
{0x021b001c, 0x00008000}, /*
* MMDC0_MDSCR, set the Configuration request bit
* during MMDC set up
*/
/*
* =============================================================================
* Calibration setup.
* =============================================================================
*/
{0x021b0800, 0xA1390003}, /*
* DDR_PHY_P0_MPZQHWCTRL, enable both one-time & periodic
* HW ZQ calibration.
*/
/*
* For target board, may need to run write leveling calibration to fine tune
* these settings.
*/
{0x021b080c, 0x00070005},
/* Read DQS Gating calibration */
{0x021b083c, 0x414c0150}, /* MPDGCTRL0 PHY0 */
/* Read calibration */
{0x021b0848, 0x4040383e}, /* MMDC_MPRDDLCTL */
/* Write calibration */
{0x021b0850, 0x40402e2a}, /* MMDC_MPWRDLCTL */
{0x021B081C, 0x33333333}, /* MMDC_MPRDDQBY0DL */
{0x021B0820, 0x33333333}, /* MMDC_MPRDDQBY1DL */
{0x021B082C, 0xf3333333}, /* MMDC_MPWRDQBY0DL */
{0x021B0830, 0xf3333333}, /* MMDC_MPWRDQBY1DL */
{0x021B08C0, 0x00944009}, /* MMDC_MPDCCR */
/* Complete calibration by forced measurement: */
{0x021B08B8, 0x00000800}, /* DDR_PHY_P0_MPMUR0, frc_msr */
/* MMDC init: */
{0x021b0004, 0x00020024}, /* MMDC0_MDPDC */
{0x021b0008, 0x1B333030}, /* MMDC0_MDOTC */
{0x021b000c, 0x3F4352D3}, /* MMDC0_MDCFG0 */
{0x021b0010, 0xB66D0A63}, /* MMDC0_MDCFG1 */
{0x021b0014, 0x01FF00DB}, /* MMDC0_MDCFG2 */
{0x021b0018, 0x00201740}, /* MMDC0_MDMISC */
{0x021b002C, 0x000026D2}, /* MMDC0_MDRWD */
{0x021b0030, 0x00431023}, /* MMDC0_MDOR */
{0x021b0040, 0x00000047}, /* CS0_END */
{0x021b0000, 0x83180000}, /* MMDC0_MDCTL */
/* Mode register writes for CS0 */
{0x021B001C, 0x02808032}, /* MMDC0_MDSCR, MR2 write, CS0 */
{0x021B001C, 0x00008033}, /* MMDC0_MDSCR, MR3 write, CS0 */
{0x021B001C, 0x00048031}, /* MMDC0_MDSCR, MR1 write, CS0 */
{0x021B001C, 0x15208030}, /* MMDC0_MDSCR, MR0 write, CS0 */
{0x021B001C, 0x04008040}, /* MMDC0_MDSCR, ZQ calibration */
/* final DDR setup, before operation start: */
{0x021b0020, 0x00000800}, /* MMDC0_MDREF */
{0x021b0818, 0x00000227}, /* DDR_PHY_P0_MPODTCTRL */
{0x021b0004, 0x00025564}, /* MMDC0_MDPDC now SDCTL power down enabled */
{0x021b0404, 0x00011006}, /* MMDC0_MAPSR ADOPT power down enabled */
{0x021b001c, 0x00000000}, /*
* MMDC0_MDSCR, clear this register (especially
* the configuration bit as initialization is complete)
*/
};
struct dram_timing_info bsh_dram_timing_256mb = {
.ddrc_cfg = ddr_ddrc_cfg_256mb,
.ddrc_cfg_num = ARRAY_SIZE(ddr_ddrc_cfg_256mb),
.dram_size = SZ_256M,
};

View File

@@ -165,4 +165,5 @@ static const struct dram_cfg_param ddr_ddrc_cfg_512mb[] = {
struct dram_timing_info bsh_dram_timing_512mb = {
.ddrc_cfg = ddr_ddrc_cfg_512mb,
.ddrc_cfg_num = ARRAY_SIZE(ddr_ddrc_cfg_512mb),
.dram_size = SZ_512M,
};

View File

@@ -52,28 +52,31 @@ static void ddr_cfg_write(const struct dram_timing_info *dram_timing_info)
}
}
static const struct dram_timing_info *board_dram_timing[] = {
#if defined(CONFIG_M2_MEMORY)
&bsh_dram_timing_512mb,
#endif
&bsh_dram_timing_256mb,
&bsh_dram_timing_128mb,
};
static void spl_dram_init(void)
{
/* Configure memory to maximum supported size for detection */
ddr_cfg_write(&bsh_dram_timing_512mb);
ddr_cfg_write(board_dram_timing[0]);
/* Detect memory physically present */
gd->ram_size = get_ram_size((void *)CFG_SYS_SDRAM_BASE, SZ_512M);
gd->ram_size = get_ram_size((void *)CFG_SYS_SDRAM_BASE, board_dram_timing[0]->dram_size);
/* Reconfigure memory for actual detected size */
switch (gd->ram_size) {
case SZ_512M:
/* Already configured, nothing to do */
break;
case SZ_256M:
udelay(1);
ddr_cfg_write(&bsh_dram_timing_256mb);
break;
case SZ_128M:
default:
udelay(1);
ddr_cfg_write(&bsh_dram_timing_128mb);
break;
if (board_dram_timing[0]->dram_size == gd->ram_size)
return;
for (size_t index = 1; index < ARRAY_SIZE(board_dram_timing); index++) {
if (board_dram_timing[index]->dram_size == gd->ram_size) {
udelay(1);
ddr_cfg_write(board_dram_timing[index]);
break;
}
}
}

View File

@@ -18,6 +18,7 @@ struct dram_cfg_param {
struct dram_timing_info {
const struct dram_cfg_param *ddrc_cfg;
unsigned int ddrc_cfg_num;
size_t dram_size;
};
extern struct dram_timing_info bsh_dram_timing_128mb;

View File

@@ -0,0 +1,78 @@
CONFIG_ARM=y
CONFIG_ARCH_MX6=y
CONFIG_TEXT_BASE=0x87800000
CONFIG_SYS_MALLOC_LEN=0x1000000
CONFIG_SYS_MALLOC_F_LEN=0x18000
CONFIG_SPL_GPIO=y
CONFIG_SPL_LIBCOMMON_SUPPORT=y
CONFIG_SPL_LIBGENERIC_SUPPORT=y
CONFIG_NR_DRAM_BANKS=1
CONFIG_ENV_SIZE=0x20000
CONFIG_ENV_OFFSET=0x400000
CONFIG_MX6ULL=y
CONFIG_TARGET_MX6ULZ_SMM_M2=y
CONFIG_BSH_M2B_MEMORY=y
CONFIG_DEFAULT_DEVICE_TREE="nxp/imx/imx6ulz-bsh-smm-m2"
CONFIG_SPL_SERIAL=y
CONFIG_SPL_BSS_START_ADDR=0x84100000
CONFIG_SPL=y
CONFIG_FIT=y
CONFIG_FIT_SIGNATURE=y
CONFIG_FIT_VERBOSE=y
CONFIG_LEGACY_IMAGE_FORMAT=y
CONFIG_DISTRO_DEFAULTS=y
CONFIG_BOOTDELAY=3
CONFIG_BOARD_LATE_INIT=y
CONFIG_SPL_SYS_MALLOC=y
CONFIG_SPL_DMA=y
CONFIG_SPL_MTD=y
CONFIG_SPL_NAND_SUPPORT=y
CONFIG_SPL_WATCHDOG=y
CONFIG_CMD_GPIO=y
CONFIG_CMD_I2C=y
CONFIG_CMD_USB=y
CONFIG_CMD_USB_SDP=y
CONFIG_CMD_CACHE=y
CONFIG_CMD_MTDPARTS=y
CONFIG_MTDIDS_DEFAULT="nand0=gpmi-nand"
CONFIG_MTDPARTS_DEFAULT="mtdparts=gpmi-nand:4m(nandboot),1m(env),8m(kernel),1m(nanddtb),-(rootfs)"
CONFIG_CMD_UBI=y
# CONFIG_ISO_PARTITION is not set
CONFIG_OF_CONTROL=y
CONFIG_ENV_OVERWRITE=y
CONFIG_ENV_IS_IN_NAND=y
CONFIG_SYS_RELOC_GD_ENV_ADDR=y
CONFIG_NO_NET=y
CONFIG_BOUNCE_BUFFER=y
CONFIG_USB_FUNCTION_FASTBOOT=y
CONFIG_FASTBOOT_BUF_ADDR=0x82000000
CONFIG_FASTBOOT_FLASH=y
CONFIG_FASTBOOT_UUU_SUPPORT=y
CONFIG_SYS_I2C_MXC=y
# CONFIG_MMC is not set
CONFIG_MTD=y
CONFIG_MTD_RAW_NAND=y
CONFIG_SYS_NAND_USE_FLASH_BBT=y
CONFIG_NAND_MXS=y
CONFIG_NAND_MXS_DT=y
CONFIG_SYS_NAND_ONFI_DETECTION=y
CONFIG_SYS_NAND_U_BOOT_LOCATIONS=y
CONFIG_SYS_NAND_U_BOOT_OFFS=0x111400
CONFIG_SYS_NAND_U_BOOT_OFFS_REDUND=0x291400
CONFIG_PINCTRL=y
CONFIG_PINCTRL_IMX6=y
CONFIG_DM_PMIC=y
CONFIG_DM_REGULATOR=y
CONFIG_DM_REGULATOR_FIXED=y
CONFIG_MXC_UART=y
CONFIG_IMX_THERMAL=y
CONFIG_USB=y
CONFIG_SPL_USB_HOST=y
CONFIG_USB_GADGET=y
CONFIG_SPL_USB_GADGET=y
CONFIG_USB_GADGET_MANUFACTURER="BSH"
CONFIG_USB_GADGET_VENDOR_NUM=0x0525
CONFIG_USB_GADGET_PRODUCT_NUM=0xa4a5
CONFIG_CI_UDC=y
CONFIG_SDP_LOADADDR=0x877fffc0
CONFIG_SPL_USB_SDP_SUPPORT=y