@@ -42,6 +42,9 @@ LOG_MODULE_REGISTER(flash_stm32_ospi, CONFIG_FLASH_LOG_LEVEL);
4242
4343#define STM32_OSPI_USE_DMA DT_NODE_HAS_PROP(STM32_OSPI_NODE, dmas)
4444
45+ /* The Base Address of the octo spi chosen by the Flash controller */
46+ #define STM32_NOR_FLASH_BASE_ADDRESS OCTOSPI2_BASE
47+
4548#if STM32_OSPI_USE_DMA
4649#include <zephyr/drivers/dma/dma_stm32.h>
4750#include <zephyr/drivers/dma.h>
@@ -955,6 +958,127 @@ static int stm32_ospi_mem_reset(const struct device *dev)
955958 return 0 ;
956959}
957960
961+ #ifdef CONFIG_STM32_XIP
962+ static int stm32_ospi_set_memorymap (const struct device * dev )
963+ {
964+ HAL_StatusTypeDef ret ;
965+ const struct flash_stm32_ospi_config * dev_cfg = dev -> config ;
966+ struct flash_stm32_ospi_data * dev_data = dev -> data ;
967+ OSPI_RegularCmdTypeDef s_command = {0 };
968+ OSPI_MemoryMappedTypeDef s_MemMappedCfg = {0 };
969+
970+ /* Configure octoflash in MemoryMapped mode */
971+ if ((dev_cfg -> data_mode == OSPI_SPI_MODE ) &&
972+ (stm32_ospi_hal_address_size (dev ) == HAL_OSPI_ADDRESS_24_BITS )) {
973+ /* OPI mode and 3-bytes address size not supported by memory */
974+ LOG_ERR ("OSPI_SPI_MODE in 3Bytes addressing is not supported" );
975+ return - EIO ;
976+ }
977+
978+ /* Initialize the read command */
979+ s_command .OperationType = HAL_OSPI_OPTYPE_READ_CFG ;
980+ s_command .FlashId = HAL_OSPI_FLASH_ID_1 ;
981+ s_command .InstructionMode = (dev_cfg -> data_rate == OSPI_STR_TRANSFER )
982+ ? ((dev_cfg -> data_mode == OSPI_SPI_MODE )
983+ ? HAL_OSPI_INSTRUCTION_1_LINE
984+ : HAL_OSPI_INSTRUCTION_8_LINES )
985+ : HAL_OSPI_INSTRUCTION_8_LINES ;
986+ s_command .InstructionDtrMode = (dev_cfg -> data_rate == OSPI_STR_TRANSFER )
987+ ? HAL_OSPI_INSTRUCTION_DTR_DISABLE
988+ : HAL_OSPI_INSTRUCTION_DTR_ENABLE ;
989+ s_command .InstructionSize = (dev_cfg -> data_rate == OSPI_STR_TRANSFER )
990+ ? ((dev_cfg -> data_mode == OSPI_SPI_MODE )
991+ ? HAL_OSPI_INSTRUCTION_8_BITS
992+ : HAL_OSPI_INSTRUCTION_16_BITS )
993+ : HAL_OSPI_INSTRUCTION_16_BITS ;
994+ s_command .Instruction = (dev_cfg -> data_rate == OSPI_STR_TRANSFER )
995+ ? ((dev_cfg -> data_mode == OSPI_SPI_MODE )
996+ ? ((stm32_ospi_hal_address_size (dev ) ==
997+ HAL_OSPI_ADDRESS_24_BITS )
998+ ? SPI_NOR_CMD_READ_FAST
999+ : SPI_NOR_CMD_READ_FAST_4B )
1000+ : SPI_NOR_OCMD_RD )
1001+ : SPI_NOR_OCMD_DTR_RD ;
1002+ s_command .AddressMode = (dev_cfg -> data_rate == OSPI_STR_TRANSFER )
1003+ ? ((dev_cfg -> data_mode == OSPI_SPI_MODE )
1004+ ? HAL_OSPI_ADDRESS_1_LINE
1005+ : HAL_OSPI_ADDRESS_8_LINES )
1006+ : HAL_OSPI_ADDRESS_8_LINES ;
1007+ s_command .AddressDtrMode = (dev_cfg -> data_rate == OSPI_STR_TRANSFER )
1008+ ? HAL_OSPI_ADDRESS_DTR_DISABLE
1009+ : HAL_OSPI_ADDRESS_DTR_ENABLE ;
1010+ s_command .AddressSize = (dev_cfg -> data_rate == OSPI_STR_TRANSFER )
1011+ ? stm32_ospi_hal_address_size (dev )
1012+ : HAL_OSPI_ADDRESS_32_BITS ;
1013+ s_command .AlternateBytesMode = HAL_OSPI_ALTERNATE_BYTES_NONE ;
1014+ s_command .DataMode = (dev_cfg -> data_rate == OSPI_STR_TRANSFER )
1015+ ? ((dev_cfg -> data_mode == OSPI_SPI_MODE )
1016+ ? HAL_OSPI_DATA_1_LINE
1017+ : HAL_OSPI_DATA_8_LINES )
1018+ : HAL_OSPI_DATA_8_LINES ;
1019+ s_command .DataDtrMode = (dev_cfg -> data_rate == OSPI_STR_TRANSFER )
1020+ ? HAL_OSPI_DATA_DTR_DISABLE
1021+ : HAL_OSPI_DATA_DTR_ENABLE ;
1022+ s_command .DummyCycles = (dev_cfg -> data_rate == OSPI_STR_TRANSFER )
1023+ ? ((dev_cfg -> data_mode == OSPI_SPI_MODE )
1024+ ? SPI_NOR_DUMMY_RD
1025+ : SPI_NOR_DUMMY_RD_OCTAL )
1026+ : SPI_NOR_DUMMY_RD_OCTAL_DTR ;
1027+ s_command .DQSMode = (dev_cfg -> data_rate == OSPI_STR_TRANSFER )
1028+ ? HAL_OSPI_DQS_DISABLE
1029+ : HAL_OSPI_DQS_ENABLE ;
1030+
1031+ s_command .SIOOMode = HAL_OSPI_SIOO_INST_EVERY_CMD ;
1032+
1033+ ret = HAL_OSPI_Command (& dev_data -> hospi , & s_command , HAL_OSPI_TIMEOUT_DEFAULT_VALUE );
1034+ if (ret != HAL_OK ) {
1035+ LOG_ERR ("%d: Failed to set memory map" , ret );
1036+ return - EIO ;
1037+ }
1038+
1039+ /* Initialize the program command */
1040+ s_command .OperationType = HAL_OSPI_OPTYPE_WRITE_CFG ;
1041+ if (dev_cfg -> data_rate == OSPI_STR_TRANSFER ) {
1042+ s_command .Instruction = (dev_cfg -> data_mode == OSPI_SPI_MODE )
1043+ ? ((stm32_ospi_hal_address_size (dev ) ==
1044+ HAL_OSPI_ADDRESS_24_BITS )
1045+ ? SPI_NOR_CMD_PP
1046+ : SPI_NOR_CMD_PP_4B )
1047+ : SPI_NOR_OCMD_PAGE_PRG ;
1048+ } else {
1049+ s_command .Instruction = SPI_NOR_OCMD_PAGE_PRG ;
1050+ }
1051+ s_command .DQSMode = HAL_OSPI_DQS_DISABLE ;
1052+ s_command .DummyCycles = 0U ;
1053+
1054+ ret = HAL_OSPI_Command (& dev_data -> hospi , & s_command , HAL_OSPI_TIMEOUT_DEFAULT_VALUE );
1055+ if (ret != HAL_OK ) {
1056+ LOG_ERR ("%d: Failed to set memory mapped" , ret );
1057+ return - EIO ;
1058+ }
1059+
1060+ /* Enable the memory-mapping */
1061+ s_MemMappedCfg .TimeOutActivation = HAL_OSPI_TIMEOUT_COUNTER_DISABLE ;
1062+
1063+ ret = HAL_OSPI_MemoryMapped (& dev_data -> hospi , & s_MemMappedCfg );
1064+ if (ret != HAL_OK ) {
1065+ LOG_ERR ("%d: Failed to set memory mapped" , ret );
1066+ return - EIO ;
1067+ }
1068+
1069+ return 0 ;
1070+ }
1071+
1072+ /* Function to return true if the octoflash is in MemoryMapped else false */
1073+ static bool stm32_ospi_is_memorymapped (const struct device * dev )
1074+ {
1075+ struct flash_stm32_ospi_data * dev_data = dev -> data ;
1076+
1077+ return (HAL_OSPI_IsMemoryMapped (& dev_data -> hospi ) == 1 ) ? true : false;
1078+
1079+ }
1080+ #endif /* CONFIG_STM32_XIP */
1081+
9581082/*
9591083 * Function to erase the flash : chip or sector with possible OSPI/SPI and STR/DTR
9601084 * to erase the complete chip (using dedicated command) :
@@ -989,6 +1113,13 @@ static int flash_stm32_ospi_erase(const struct device *dev, off_t addr,
9891113 return - ENOTSUP ;
9901114 }
9911115
1116+ #ifdef CONFIG_STM32_XIP
1117+ if (stm32_ospi_is_memorymapped (dev )) {
1118+ LOG_INF ("MemoryMapped : cannot erase" );
1119+ return 0 ;
1120+ }
1121+ #endif /* CONFIG_STM32_XIP */
1122+
9921123 OSPI_RegularCmdTypeDef cmd_erase = {
9931124 .OperationType = HAL_OSPI_OPTYPE_COMMON_CFG ,
9941125 .FlashId = HAL_OSPI_FLASH_ID_1 ,
@@ -1003,9 +1134,9 @@ static int flash_stm32_ospi_erase(const struct device *dev, off_t addr,
10031134
10041135 if (stm32_ospi_mem_ready (& dev_data -> hospi ,
10051136 dev_cfg -> data_mode , dev_cfg -> data_rate ) != 0 ) {
1006- ospi_unlock_thread (dev );
10071137 LOG_ERR ("Erase failed : flash busy" );
1008- return - EBUSY ;
1138+ ret = - EBUSY ;
1139+ goto end_erase ;
10091140 }
10101141
10111142 cmd_erase .InstructionMode = (dev_cfg -> data_mode == OSPI_OPI_MODE )
@@ -1112,8 +1243,19 @@ static int flash_stm32_ospi_erase(const struct device *dev, off_t addr,
11121243
11131244 }
11141245
1246+ end_erase :
11151247 ospi_unlock_thread (dev );
11161248
1249+ #ifdef CONFIG_STM32_XIP
1250+ ret = stm32_ospi_set_memorymap (dev );
1251+ /* re-enable MemoryMapped mode */
1252+ if (ret != 0 ) {
1253+ LOG_ERR ("Erase failed: cannot enable MemoryMap" );
1254+
1255+ return - EIO ;
1256+ }
1257+ #endif /* CONFIG_STM32_XIP */
1258+
11171259 return ret ;
11181260}
11191261
@@ -1136,6 +1278,17 @@ static int flash_stm32_ospi_read(const struct device *dev, off_t addr,
11361278 return 0 ;
11371279 }
11381280
1281+ #ifdef CONFIG_STM32_XIP
1282+ if (stm32_ospi_is_memorymapped (dev )) {
1283+ LOG_DBG ("MemoryMapped Read offset: 0x%lx, len: %zu" ,
1284+ (long )(STM32_NOR_FLASH_BASE_ADDRESS + addr ),
1285+ size );
1286+ memcpy (data , (uint8_t * )STM32_NOR_FLASH_BASE_ADDRESS + addr , size );
1287+
1288+ return 0 ;
1289+ }
1290+ #endif /* CONFIG_STM32_XIP */
1291+
11391292 OSPI_RegularCmdTypeDef cmd = ospi_prepare_cmd (dev_cfg -> data_mode , dev_cfg -> data_rate );
11401293
11411294 if (dev_cfg -> data_mode != OSPI_OPI_MODE ) {
@@ -1224,6 +1377,16 @@ static int flash_stm32_ospi_write(const struct device *dev, off_t addr,
12241377 return 0 ;
12251378 }
12261379
1380+ #ifdef CONFIG_STM32_XIP
1381+ if (stm32_ospi_is_memorymapped (dev )) {
1382+ LOG_DBG ("MemoryMapped Write offset: 0x%lx, len: %zu" ,
1383+ (long )(STM32_NOR_FLASH_BASE_ADDRESS + addr ),
1384+ size );
1385+ memcpy ((uint8_t * )STM32_NOR_FLASH_BASE_ADDRESS + addr , data , size );
1386+
1387+ return 0 ;
1388+ }
1389+ #endif /* CONFIG_STM32_XIP */
12271390 /* page program for STR or DTR mode */
12281391 OSPI_RegularCmdTypeDef cmd_pp = ospi_prepare_cmd (dev_cfg -> data_mode , dev_cfg -> data_rate );
12291392
@@ -2232,6 +2395,16 @@ static int flash_stm32_ospi_init(const struct device *dev)
22322395 }
22332396#endif /* CONFIG_FLASH_PAGE_LAYOUT */
22342397
2398+ #ifdef CONFIG_STM32_XIP
2399+ /* Now configure the octo Flash in MemoryMapped (access by address) */
2400+ ret = stm32_ospi_set_memorymap (dev );
2401+ if (ret != 0 ) {
2402+ LOG_ERR ("Error (%d): setting NOR in MemoryMapped mode" , ret );
2403+ return - EINVAL ;
2404+ }
2405+ LOG_INF ("NOR in MemoryMapped mode" );
2406+
2407+ #endif /* CONFIG_STM32_XIP */
22352408 return 0 ;
22362409}
22372410
0 commit comments