2022-08-07 01:54 PM
On the NUCLEO-G474RE board I have tested the QSPI interface with a flash memory. The interface seems to work properly but the read transfer in quad mode is slower than expected.
To analyze the issue I have reduced my test program to two calls: HAL_QSPI_Command and HAL_QSPI_Receive. There are no devices connected to the QSPI interface. I try to read 32 bytes, the CPU clock is set to 170MHz and the QSPI is working with 10MHz. On the oscilloscope I can observe the following behavior (yellow: QSPI_NCS, blue: QSPI_CLK):
There are 3 breaks in the clock generation: A, B and C (2 + 8 + 8 clocks). In the phases (1), (2), (3) and (4) the data will be transfered:
(1): 46 clocks = 8 (instruction) + 38 (19 data bytes)
(2): 8 clocks (4 data bytes)
(3): 8 clocks (4 data bytes)
(4): 10 clocks (5 data bytes)
The total number of transfered bytes (32) is correct. What is the reason for the breaks in the clock generation?
My test program has been generated with STM32CubeMX 6.6.0 / STM32Cube FW_G4 V1.5.2. As toolchain I use MDK-ARM, Version 5.36.0.0. In the initial program I have inserted the following procedure, which is executed once:
/*******************************************************************************
* Function Name : read32Bytes
* Description : Read 32 bytes from QSPI
* Input : None
* Output : None
* Return : None
*******************************************************************************/
void read32Bytes(void)
{
/* Dummy instruction */
sCommand.InstructionMode = QSPI_INSTRUCTION_1_LINE;
sCommand.Instruction = 0xA5;
/*---*/
sCommand.AddressMode = QSPI_ADDRESS_NONE;
// sCommand.AddressSize = QSPI_ADDRESS_24_BITS;
// sCommand.Address = 0x000000;
/*---*/
sCommand.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
// sCommand.AlternateBytesSize = QSPI_ALTERNATE_BYTES_8_BITS;
// sCommand.AlternateBytes = 0xFF;
/*---*/
sCommand.DummyCycles = 0;
/*---*/
sCommand.DataMode = QSPI_DATA_4_LINES;
sCommand.NbData = 32;
/*---*/
sCommand.DdrMode = QSPI_DDR_MODE_DISABLE;
// sCommand.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
/*---*/
sCommand.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
if (HAL_QSPI_Command(&hqspi1, &sCommand, HAL_QSPI_TIMEOUT_DEFAULT_VALUE) != HAL_OK) {
Error_Handler();
}
if (HAL_QSPI_Receive(&hqspi1, RxData, HAL_QSPI_TIMEOUT_DEFAULT_VALUE) != HAL_OK) {
Error_Handler();
}
}
The QSPI has been configured as follows:
Kind regards
Michael
Solved! Go to Solution.
2023-03-26 04:17 AM
Have you already tried to use the DMA function to fetch SPI stream data continually (HAL_QSPI_Receive_DMA)?
2022-08-07 02:23 PM
Not sure there's any clock stretching, perhaps FIFO depth, and servicing the data register?
2023-03-25 08:15 AM
I have also tested the SPI/QSPI speed on STM32H755. The STM32H755 seems to have a similar problem.
Test conditions:
Performed tests:
Test results:
2023-03-26 04:17 AM
Have you already tried to use the DMA function to fetch SPI stream data continually (HAL_QSPI_Receive_DMA)?
2023-03-26 03:00 PM
@SStor: It was a very good idea. Thank you!
The issue is solved now. The screenshot shows a read of one flash page in quad mode at 100 MHz:
The command "Fast Read Quad I/O (EBh)" needs 532 SPI CLKs. The duration should be 5,32us, but there is a small gap of 3 CLKs after about 3,4us.