cancel
Showing results for 
Search instead for 
Did you mean: 

STM32H735 Multiplexed Memory Mapped OSPI Hyperram Hardfault

JRand.1
Associate

Hi, I use OCTOSPI1 and OCTOSPI2 in multiplexed mode to interface with two S27KL0641 ram in Memory Mapped mode.

Those Rams are used for LTDC Frame Buffer and for other application data (structure, data ...).

I started from the STM32Cube_FW_H7_V1.9.0\Drivers\BSP\Components\s70kl1281 and STM32Cube_FW_H7_V1.9.0\Drivers\BSP\STM32H735G-DK from cubeMX to initialise the OSPI, I changed pin affectation, added HAL_OSPIM_Config and enabled IoManager clock.

The application starts correctly but after some minutes it enters in Hardfault.

Depending on MPU initilization, the problem occurs faster.

Here is my MPU configuration

//ospi2 data

 MPU_InitStruct.Enable = MPU_REGION_ENABLE;

 MPU_InitStruct.BaseAddress = OCTOSPI2_BASE;

 MPU_InitStruct.Size = MPU_REGION_SIZE_8MB;

 MPU_InitStruct.AccessPermission = MPU_REGION_FULL_ACCESS;

 MPU_InitStruct.IsBufferable = MPU_ACCESS_BUFFERABLE;

 MPU_InitStruct.IsCacheable = MPU_ACCESS_CACHEABLE;

 MPU_InitStruct.IsShareable = MPU_ACCESS_NOT_SHAREABLE;

 MPU_InitStruct.Number = MPU_REGION_NUMBER0;

 MPU_InitStruct.TypeExtField = MPU_TEX_LEVEL0;

 MPU_InitStruct.SubRegionDisable = 0x00;

 MPU_InitStruct.DisableExec = MPU_INSTRUCTION_ACCESS_ENABLE;

 HAL_MPU_ConfigRegion(&MPU_InitStruct);

 //ospi 1 data

 MPU_InitStruct.Enable = MPU_REGION_ENABLE;

 MPU_InitStruct.BaseAddress = OCTOSPI1_BASE;

 MPU_InitStruct.Size = MPU_REGION_SIZE_8MB;

 MPU_InitStruct.AccessPermission = MPU_REGION_FULL_ACCESS;

 MPU_InitStruct.IsBufferable = MPU_ACCESS_BUFFERABLE;

 MPU_InitStruct.IsCacheable = MPU_ACCESS_CACHEABLE;

 MPU_InitStruct.IsShareable = MPU_ACCESS_NOT_SHAREABLE;

 MPU_InitStruct.Number = MPU_REGION_NUMBER1;

 MPU_InitStruct.TypeExtField = MPU_TEX_LEVEL0;

 MPU_InitStruct.SubRegionDisable = 0x00;

 MPU_InitStruct.DisableExec = MPU_INSTRUCTION_ACCESS_DISABLE;

 HAL_MPU_ConfigRegion(&MPU_InitStruct);  

  

//octospi1 frame buff, size = 0x200000

 MPU_InitStruct.Enable = MPU_REGION_ENABLE;

 MPU_InitStruct.BaseAddress = OCTOSPI1_BASE;

 MPU_InitStruct.Size = MPU_REGION_SIZE_8MB;

 MPU_InitStruct.AccessPermission = MPU_REGION_FULL_ACCESS;

 MPU_InitStruct.IsBufferable = MPU_ACCESS_NOT_BUFFERABLE;

 MPU_InitStruct.IsCacheable = MPU_ACCESS_NOT_CACHEABLE;

 MPU_InitStruct.IsShareable = MPU_ACCESS_NOT_SHAREABLE;

 MPU_InitStruct.Number = MPU_REGION_NUMBER2;

 MPU_InitStruct.TypeExtField = MPU_TEX_LEVEL1;

MPU_InitStruct.SubRegionDisable = ~0x03; 

 MPU_InitStruct.DisableExec = MPU_INSTRUCTION_ACCESS_DISABLE;

 HAL_MPU_ConfigRegion(&MPU_InitStruct); 

Here is the Ram parameters

hospi->Init.DualQuad       = HAL_OSPI_DUALQUAD_DISABLE;

hospi->Init.MemoryType      = HAL_OSPI_MEMTYPE_HYPERBUS;

hospi->Init.DeviceSize      = Init->MemorySize;

hospi->Init.FreeRunningClock   = HAL_OSPI_FREERUNCLK_DISABLE;

hospi->Init.ClockMode       = HAL_OSPI_CLOCK_MODE_0;

hospi->Init.WrapSize       = HAL_OSPI_WRAP_128_BYTES;

hospi->Init.SampleShifting    = Init->SampleShifting;

hospi->Init.DelayHoldQuarterCycle = HAL_OSPI_DHQC_ENABLE;  

hospi->Init.ChipSelectBoundary  = 23; /* memory die boundary 2^23=8MBs*/

hospi->Init.Refresh        = 275; //250; /*4us @100MHz*/

hospi->Init.FifoThreshold     = 1;

hospi->Init.ChipSelectHighTime  = 20;

hospi->Init.ClockPrescaler    = 4; //clocked from 275Mhz

 ospi_ram_init.LatencyType = BSP_OSPI_RAM_FIXED_LATENCY;

 ospi_ram_init.BurstType  = BSP_OSPI_RAM_LINEAR_BURST;

 ospi_ram_init.BurstLength = BSP_OSPI_RAM_BURST_32_BYTES;

Can you tell me if there is something wrong in my code that may cause this issue? Thanks in advance

1 ACCEPTED SOLUTION

Accepted Solutions
JRand.1
Associate

Hi, I tested with your code and i have the same issue.

I managed to solved the problem, it was due to some timing problems, I had to enable DelayBlock to make it work

hospi->Init.DelayBlockBypass = HAL_OSPI_DELAY_BLOCK_USED;

DelayBlock_Configure(DLYB_OCTOSPI1,1,50);

Thanks for your help

View solution in original post

5 REPLIES 5
Alex - APMemory
Senior II

Hi,

I'm not sure if this could help, but see below for reference corresponding settings of APS6408L-3OBM.

These OPI device family (APS6408..., APS12808..., APS256.., APS512...) are an equivalent of HyperRAM in term of performance, with same BGA24 package footprint, also supported by STM32H7

(Section 7.9 of https://www.st.com/resource/en/user_manual/dm00682073-discovery-kit-with-stm32h735ig-mcu-stmicroelectronics.pdf)

You may want to compare the code to find the issue or just try different device.

Alex

 ***************************************

 /* Initialize OctoSPI ----------------------------------------------------- */

 OSPIHandle.Instance = OCTOSPI2;

 HAL_OSPI_DeInit(&OSPIHandle);

 OSPIHandle.Init.FifoThreshold        = 1;

 OSPIHandle.Init.DualQuad             = HAL_OSPI_DUALQUAD_DISABLE;

 OSPIHandle.Init.MemoryType           = HAL_OSPI_MEMTYPE_APMEMORY;

 OSPIHandle.Init.DeviceSize           = 23; /* 64 MBits */

 OSPIHandle.Init.ChipSelectHighTime   = 1;

 OSPIHandle.Init.FreeRunningClock     = HAL_OSPI_FREERUNCLK_DISABLE;

 OSPIHandle.Init.ClockMode            = HAL_OSPI_CLOCK_MODE_0;

 OSPIHandle.Init.WrapSize             = HAL_OSPI_WRAP_NOT_SUPPORTED;

 OSPIHandle.Init.ClockPrescaler       = 0x3;

 OSPIHandle.Init.SampleShifting       = HAL_OSPI_SAMPLE_SHIFTING_NONE;

 OSPIHandle.Init.DelayHoldQuarterCycle = HAL_OSPI_DHQC_ENABLE;

 OSPIHandle.Init.ChipSelectBoundary   = 0;

 OSPIHandle.Init.FreeRunningClock     = HAL_OSPI_FREERUNCLK_ENABLE;

   /* 1- Writing Sequence ------------------------------------------------ */

   sCommand.OperationType     = HAL_OSPI_OPTYPE_COMMON_CFG;

   sCommand.FlashId           = HAL_OSPI_FLASH_ID_1;

   sCommand.Instruction       = WRITE_CMD;

   sCommand.InstructionMode   = HAL_OSPI_INSTRUCTION_8_LINES;

   sCommand.InstructionSize   = HAL_OSPI_INSTRUCTION_8_BITS;

   sCommand.InstructionDtrMode = HAL_OSPI_INSTRUCTION_DTR_DISABLE;

   sCommand.Address           = 0x0;

   sCommand.AddressMode       = HAL_OSPI_ADDRESS_8_LINES;

   sCommand.AddressSize       = HAL_OSPI_ADDRESS_32_BITS;

   sCommand.AddressDtrMode    = HAL_OSPI_ADDRESS_DTR_ENABLE;

   sCommand.AlternateBytesMode = HAL_OSPI_ALTERNATE_BYTES_NONE;

   sCommand.DataMode          = HAL_OSPI_DATA_8_LINES;

   sCommand.NbData            = BUFFER_LENGTH;

   sCommand.DataDtrMode       = HAL_OSPI_DATA_DTR_ENABLE;

   sCommand.DummyCycles       = DUMMY_CLOCK_CYCLES_WRITE;

   sCommand.DQSMode           = HAL_OSPI_DQS_ENABLE;

   sCommand.SIOOMode          = HAL_OSPI_SIOO_INST_EVERY_CMD;

   

    if (HAL_OSPI_Command(&OSPIHandle, &sCommand, HAL_OSPI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)

   {

     Error_Handler();

   }

   

    if (HAL_OSPI_Transmit(&OSPIHandle, TX_Buffer, HAL_OSPI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)

   {

     Error_Handler();

   }

   

    /* 2- Reading Sequence ------------------------------------------------ */

   sCommand.Instruction = READ_CMD;

   sCommand.DummyCycles = DUMMY_CLOCK_CYCLES_READ;

   sCommand.DQSMode    = HAL_OSPI_DQS_ENABLE;

   if (HAL_OSPI_Command(&OSPIHandle, &sCommand, HAL_OSPI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)

   {

     Error_Handler();

   }

   

    if (HAL_OSPI_Receive(&OSPIHandle, RX_Buffer, HAL_OSPI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)

   {

     Error_Handler();

   }

 ***********************************************

You do realize your example sets .FreeRunning Clock to ..._DISABLE then later to ..._ENABLE?

The following "works for me" with a single S27KL0641DABHV020 device and some OCTOSPIM voodoo:

/* OCTOSPI1 init function */

void MX_OCTOSPI1_Init(void)

{

 OSPIM_CfgTypeDef sOspiManagerCfg = {0};

 OSPI_HyperbusCfgTypeDef sHyperBusCfg = {0};

 hospi1.Instance = OCTOSPI1;

 hospi1.Init.FifoThreshold = 4;

 hospi1.Init.DualQuad = HAL_OSPI_DUALQUAD_DISABLE;

 hospi1.Init.MemoryType = HAL_OSPI_MEMTYPE_HYPERBUS;

 hospi1.Init.DeviceSize = 23;

 hospi1.Init.ChipSelectHighTime = 1;

 hospi1.Init.FreeRunningClock = HAL_OSPI_FREERUNCLK_DISABLE;

 hospi1.Init.ClockMode = HAL_OSPI_CLOCK_MODE_0;

 hospi1.Init.WrapSize = HAL_OSPI_WRAP_NOT_SUPPORTED;

 hospi1.Init.ClockPrescaler = 2;

 hospi1.Init.SampleShifting = HAL_OSPI_SAMPLE_SHIFTING_NONE;

 hospi1.Init.DelayHoldQuarterCycle = HAL_OSPI_DHQC_ENABLE;

 hospi1.Init.ChipSelectBoundary = 0;

 hospi1.Init.ClkChipSelectHighTime = 0;

 hospi1.Init.DelayBlockBypass = HAL_OSPI_DELAY_BLOCK_BYPASSED;

 hospi1.Init.MaxTran = 0;

 hospi1.Init.Refresh = 100;

 if (HAL_OSPI_Init(&hospi1) != HAL_OK)

 {

   Error_Handler();

 }

 sOspiManagerCfg.ClkPort = 2;

 sOspiManagerCfg.DQSPort = 2;

 sOspiManagerCfg.NCSPort = 1;

 sOspiManagerCfg.IOLowPort = HAL_OSPIM_IOPORT_2_LOW;

 sOspiManagerCfg.IOHighPort = HAL_OSPIM_IOPORT_1_HIGH;

/***[Local modification begin]***/

 sOspiManagerCfg.Req2AckTime = 1;  /* ??? should be set by CMX (0 from struct decl above will assert in HAL_OSPIM_Config(). */

/***[Local modification end]***/

 if (HAL_OSPIM_Config(&hospi1, &sOspiManagerCfg, HAL_OSPI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)

 {

   Error_Handler();

 }

 sHyperBusCfg.RWRecoveryTime = 4;

 sHyperBusCfg.AccessTime = 6;

 sHyperBusCfg.WriteZeroLatency = HAL_OSPI_LATENCY_ON_WRITE;

 sHyperBusCfg.LatencyMode = HAL_OSPI_FIXED_LATENCY;

 if (HAL_OSPI_HyperbusCfg(&hospi1, &sHyperBusCfg, HAL_OSPI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)

 {

   Error_Handler();

 }

/***[Local modification begin]***/

 {

   OSPI_HyperbusCmdTypeDef sCommand = { 0 };

   OSPI_MemoryMappedTypeDef sMemMappedCfg = { 0 };

   /* Memory-mapped mode configuration --------------------------------------- */

   sCommand.AddressSpace = HAL_OSPI_MEMORY_ADDRESS_SPACE;

   sCommand.AddressSize = HAL_OSPI_ADDRESS_32_BITS;

   sCommand.DQSMode     = HAL_OSPI_DQS_ENABLE;

   sCommand.Address     = 0;

   sCommand.NbData      = 1;

   if( HAL_OSPI_HyperbusCmd( &hospi1, &sCommand, HAL_OSPI_TIMEOUT_DEFAULT_VALUE ) != HAL_OK )

     {

       Error_Handler();

     }

   sMemMappedCfg.TimeOutActivation = HAL_OSPI_TIMEOUT_COUNTER_DISABLE;

   if( HAL_OSPI_MemoryMapped( &hospi1, &sMemMappedCfg ) != HAL_OK )

     {

       Error_Handler();

     }

 }

/***[Local modification end]***/

}

Yes, RAM is set to disable

Anyway this and your other examples provide working examples for running different devices option upon final user choice such as as availabilty or competitivness.

JRand.1
Associate

Hi, I tested with your code and i have the same issue.

I managed to solved the problem, it was due to some timing problems, I had to enable DelayBlock to make it work

hospi->Init.DelayBlockBypass = HAL_OSPI_DELAY_BLOCK_USED;

DelayBlock_Configure(DLYB_OCTOSPI1,1,50);

Thanks for your help