blob: f074fc189d4c7d952d0cc9a8f6ca0a19296bc15f [file] [log] [blame]
// SPDX-License-Identifier: GPL-2.0+ OR BSD-3-Clause
/*
* Copyright (C) 2020, STMicroelectronics - All Rights Reserved
*/
#include <common.h>
#include <dfu.h>
#include <dm.h>
#include <env.h>
#include <env_internal.h>
#include <log.h>
#include <mtd.h>
#include <mtd_node.h>
#include <tee.h>
#include <asm/arch/stm32prog.h>
#include <asm/arch/sys_proto.h>
#include <asm/global_data.h>
#define MTDPARTS_LEN 256
#define MTDIDS_LEN 128
/*
* Get a global data pointer
*/
DECLARE_GLOBAL_DATA_PTR;
/**
* update the variables "mtdids" and "mtdparts" with boot, tee and user strings
*/
static void board_set_mtdparts(const char *dev,
char *mtdids,
char *mtdparts,
const char *boot,
const char *tee,
const char *user)
{
/* mtdids: "<dev>=<dev>, ...." */
if (mtdids[0] != '\0')
strcat(mtdids, ",");
strcat(mtdids, dev);
strcat(mtdids, "=");
strcat(mtdids, dev);
/* mtdparts: "mtdparts=<dev>:<mtdparts_<dev>>;..." */
if (mtdparts[0] != '\0')
strncat(mtdparts, ";", MTDPARTS_LEN);
else
strcat(mtdparts, "mtdparts=");
strncat(mtdparts, dev, MTDPARTS_LEN);
strncat(mtdparts, ":", MTDPARTS_LEN);
if (boot) {
strncat(mtdparts, boot, MTDPARTS_LEN);
strncat(mtdparts, ",", MTDPARTS_LEN);
}
if (tee) {
strncat(mtdparts, tee, MTDPARTS_LEN);
strncat(mtdparts, ",", MTDPARTS_LEN);
}
strncat(mtdparts, user, MTDPARTS_LEN);
}
void board_mtdparts_default(const char **mtdids, const char **mtdparts)
{
struct mtd_info *mtd;
struct udevice *dev;
static char parts[3 * MTDPARTS_LEN + 1];
static char ids[MTDIDS_LEN + 1];
static bool mtd_initialized;
bool tee, nor, nand, spinand, serial;
if (mtd_initialized) {
*mtdids = ids;
*mtdparts = parts;
return;
}
tee = false;
nor = false;
nand = false;
spinand = false;
serial = false;
switch (get_bootmode() & TAMP_BOOT_DEVICE_MASK) {
case BOOT_SERIAL_UART:
case BOOT_SERIAL_USB:
serial = true;
if (CONFIG_IS_ENABLED(CMD_STM32PROG)) {
tee = stm32prog_get_tee_partitions();
nor = stm32prog_get_fsbl_nor();
}
nand = true;
spinand = true;
break;
case BOOT_FLASH_NAND:
nand = true;
break;
case BOOT_FLASH_SPINAND:
spinand = true;
break;
case BOOT_FLASH_NOR:
nor = true;
break;
default:
break;
}
if (!serial && CONFIG_IS_ENABLED(OPTEE) &&
tee_find_device(NULL, NULL, NULL, NULL))
tee = true;
memset(parts, 0, sizeof(parts));
memset(ids, 0, sizeof(ids));
/* probe all MTD devices */
for (uclass_first_device(UCLASS_MTD, &dev);
dev;
uclass_next_device(&dev)) {
log_debug("mtd device = %s\n", dev->name);
}
if (nand) {
mtd = get_mtd_device_nm("nand0");
if (!IS_ERR_OR_NULL(mtd)) {
const char *mtd_tee = CONFIG_MTDPARTS_NAND0_TEE;
board_set_mtdparts("nand0", ids, parts,
CONFIG_MTDPARTS_NAND0_BOOT,
!nor && tee ? mtd_tee : NULL,
"-(UBI)");
put_mtd_device(mtd);
}
}
if (spinand) {
mtd = get_mtd_device_nm("spi-nand0");
if (!IS_ERR_OR_NULL(mtd)) {
const char *mtd_tee = CONFIG_MTDPARTS_SPINAND0_TEE;
board_set_mtdparts("spi-nand0", ids, parts,
CONFIG_MTDPARTS_SPINAND0_BOOT,
!nor && tee ? mtd_tee : NULL,
"-(UBI)");
put_mtd_device(mtd);
}
}
if (nor) {
if (!uclass_get_device(UCLASS_SPI_FLASH, 0, &dev)) {
const char *mtd_tee = CONFIG_MTDPARTS_NOR0_TEE;
board_set_mtdparts("nor0", ids, parts,
CONFIG_MTDPARTS_NOR0_BOOT,
tee ? mtd_tee : NULL,
"-(nor_user)");
}
}
mtd_initialized = true;
*mtdids = ids;
*mtdparts = parts;
log_debug("mtdids=%s & mtdparts=%s\n", ids, parts);
}