2024-07-22 09:28 AM
Hello!
I have a W25Q128JVIQ connected to an STM32F446RE like the following:
I am trying to use QuadSPI in Dual Mode, but I am having difficulties reading ANY data, like the Device ID (ABh). This is my code:
W25Q_STATE W25Q_ReadID(u8_t *buf)
{
QSPI_CommandTypeDef com;
com.InstructionMode = QSPI_INSTRUCTION_1_LINE; // QSPI_INSTRUCTION_...
com.Instruction = W25Q_FULLID_DUAL_IO; // Command
com.AddressMode = QSPI_ADDRESS_1_LINE;
com.AddressSize = QSPI_ADDRESS_24_BITS;
com.Address = 0x0U;
com.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
com.AlternateBytes = QSPI_ALTERNATE_BYTES_NONE;
com.AlternateBytesSize = QSPI_ALTERNATE_BYTES_NONE;
com.DummyCycles = 0;
com.DataMode = QSPI_DATA_1_LINE;
com.NbData = 1;
com.DdrMode = QSPI_DDR_MODE_DISABLE;
com.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
com.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
if (HAL_QSPI_Command(&hqspi, &com, HAL_QSPI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
{
return W25Q_SPI_ERR;
}
if (HAL_QSPI_Receive(&hqspi, buf, HAL_QSPI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
{
return W25Q_SPI_ERR;
}
return W25Q_OK;
}
I also tried to read instruction 92h with datamode and address mode set to DATA_2_LINES, but it returns the same.
I am pretty sure, this is not the ID, it should return 23 or 238 according to the datasheet. I tried everything I could think of. Here is my QUADSPI init:
hqspi.Instance = QUADSPI;
hqspi.Init.ClockPrescaler = 0;
hqspi.Init.FifoThreshold = 4;
hqspi.Init.SampleShifting = QSPI_SAMPLE_SHIFTING_HALFCYCLE;
hqspi.Init.FlashSize = 23;
hqspi.Init.ChipSelectHighTime = QSPI_CS_HIGH_TIME_2_CYCLE;
hqspi.Init.ClockMode = QSPI_CLOCK_MODE_0;
hqspi.Init.FlashID = QSPI_FLASH_ID_1;
hqspi.Init.DualFlash = QSPI_DUALFLASH_DISABLE;
I would really appreciate some help! thanks
2024-07-22 09:31 AM
I also tried setting dummy cycle to 3, but the results stay the same
2024-07-22 10:20 AM
com.Instruction = W25Q_FULLID_DUAL_IO; // Command
com.DataMode = QSPI_DATA_1_LINE;
Really?
2024-07-22 10:35 AM
Perhaps stop random shot-gun coding..
0x9F would be 1-bit command (x8), and 1-bit data (x24), no address or dummy bits. Returning 0xEF,0x40,0x17 (239, 64, 23)
If that doesn't work evaluate what exactly you've wired and configured.
Try with hqspi.Init.ClockPrescaler = 10; so as not to be maximally clocking
0xAB would need 3 dummy bytes (24 clocks), or 3-byte address of non-consequential content.
Inspect signals with a scope or logic analyzer
Show pin configuration code
2024-07-23 02:01 AM
I managed to make it work!
My code:
W25Q_STATE W25Q_Init(void)
{
W25Q_STATE state; // temp status variable
// read id
u8_t id;
state = W25Q_ReadID(&id);
if (state != W25Q_OK)
return state;
u8_t id_full[3];
// state = W25Q_ReadID(id_full);
state = W25Q_ReadFullID(id_full);
}
W25Q_STATE W25Q_ReadID(u8_t *buf)
{
QSPI_CommandTypeDef com;
com.InstructionMode = QSPI_INSTRUCTION_1_LINE; // QSPI_INSTRUCTION_...
com.Instruction = W25Q_DEVID; // Command 0xAB
com.AddressMode = QSPI_ADDRESS_NONE;
com.AddressSize = QSPI_ADDRESS_NONE;
com.Address = 0x0U;
com.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
com.AlternateBytes = QSPI_ALTERNATE_BYTES_NONE;
com.AlternateBytesSize = QSPI_ALTERNATE_BYTES_NONE;
com.DummyCycles = 0;
com.DataMode = QSPI_DATA_1_LINE;
com.NbData = 1;
com.DdrMode = QSPI_DDR_MODE_DISABLE;
com.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
com.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
if (HAL_QSPI_Command(&hqspi, &com, HAL_QSPI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
{
return W25Q_SPI_ERR;
}
if (HAL_QSPI_Receive(&hqspi, buf, HAL_QSPI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
{
return W25Q_SPI_ERR;
}
return W25Q_OK;
}
W25Q_STATE W25Q_ReadFullID(u8_t *buf)
{
QSPI_CommandTypeDef com;
com.InstructionMode = QSPI_INSTRUCTION_1_LINE; // QSPI_INSTRUCTION_...
com.Instruction = W25Q_FULLID_DUAL_IO; // Command 0x92
com.AddressMode = QSPI_ADDRESS_2_LINES;
com.AddressSize = QSPI_ADDRESS_24_BITS;
com.Address = 0x0U;
com.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
com.AlternateBytes = QSPI_ALTERNATE_BYTES_NONE;
com.AlternateBytesSize = QSPI_ALTERNATE_BYTES_NONE;
com.DummyCycles = 0;
com.DataMode = QSPI_DATA_2_LINES;
com.NbData = 3;
com.DdrMode = QSPI_DDR_MODE_DISABLE;
com.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
com.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
if (HAL_QSPI_Command(&hqspi, &com, HAL_QSPI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
{
return W25Q_SPI_ERR;
}
if (HAL_QSPI_Receive(&hqspi, buf, HAL_QSPI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
{
return W25Q_SPI_ERR;
}
return W25Q_OK;
}
If i call the readID twice, the second time it returns 255, because the chip is already awake. First time it returns 0. Afterwards, I call the readFullID, and it returns this:
Why is the first index 0? according to the datasheet, it should not be there. Could you help me understand this?