STM32读取SPIFLASH的问题??

wwbinww   2010-9-16 14:59 楼主


芯片 : STM32F107 (72Mhz)
FLASH:AT45DB161D

现在写入了“1234”4个字符

设置 SPI_BaudRatePrescaler 为 SPI_BaudRatePrescaler_256时,读取到
0x00 0x31 0x32 0x33 0x34 .....

设置 SPI_BaudRatePrescaler 为 SPI_BaudRatePrescaler_2时,读取到
0x00 0x32 0x33 0x34  .....

不知道怎么回事???

单步调试时都正常

回复评论 (11)

                                 先用示波器看看。
点赞  2010-9-16 22:35


恩,下次记得用示波器,这次没用,碰巧搞对了!!
点赞  2010-9-19 08:49
                                 是SPI的数据接收和发送有一点问题!!
点赞  2010-9-19 08:49
是SPI的数据接收和发送有一点问题!!
什么问题? 可以说详细点吗?
点赞  2010-9-19 09:40
                                 说详细一点吧,也好帮你看看
点赞  2010-9-19 10:28
                                 估计楼主的问题是解决了
点赞  2010-9-19 17:28


我之前发送和接收SPI数据的函数是
static u8 Spi_ReadByte(void)
{
while(SPI_I2S_GetFlagStatus(FLASH_SPI, SPI_I2S_FLAG_BSY) == SET);
while (SPI_I2S_GetFlagStatus(FLASH_SPI, SPI_I2S_FLAG_TXE) == RESET);
FLASH_SPI->DR = FLASH_DUMMY_BYTE;
while (SPI_I2S_GetFlagStatus(FLASH_SPI, SPI_I2S_FLAG_RXNE) == RESET);
return FLASH_SPI->DR;
}
static void Spi_WriteByte(u8 data)
{
while(SPI_I2S_GetFlagStatus(FLASH_SPI, SPI_I2S_FLAG_BSY) == SET);
  while (SPI_I2S_GetFlagStatus(FLASH_SPI, SPI_I2S_FLAG_TXE) == RESET);
FLASH_SPI->DR = data;
}

现在改为了共用一个函数

u8 Spi_WriteByte(u8 byte)
{
while (SPI_I2S_GetFlagStatus(FLASH_SPI, SPI_I2S_FLAG_TXE) == RESET);
SPI_I2S_SendData(FLASH_SPI, byte);
while (SPI_I2S_GetFlagStatus(FLASH_SPI, SPI_I2S_FLAG_RXNE) == RESET);
return SPI_I2S_ReceiveData(FLASH_SPI);
}

就这样,SPI FLASH读写就OK了
点赞  2010-9-29 09:40
应该是时序的问题吧?我也遇到了,但是没有你的运气好,按STM32固件库的sFlash demo改也未奏效。
后来分析是读写时钟边沿不同产生的时序问题。单步调试正常是因为把操作时序人为拉长了,实际效果等于对齐了TXE和RXNE的操作。如果我的分析正确,你的代码很有可能是碰巧对了,一旦程序运行时序变化,还有可能出错。
下面是摘录的库内demo代码
define sFLASH_CS_LOW()       GPIO_ResetBits(sFLASH_CS_GPIO_PORT, sFLASH_CS_PIN)
#define sFLASH_CS_HIGH()      GPIO_SetBits(sFLASH_CS_GPIO_PORT, sFLASH_CS_PIN)

/**
  * @brief  Sends a byte through the SPI interface and return the byte received
  *         from the SPI bus.
  * @param  byte: byte to send.
  * @retval The value of the received byte.
  */
uint8_t sFLASH_SendByte(uint8_t byte)
{
  /*!< Loop while DR register in not emplty */
  while (SPI_I2S_GetFlagStatus(sFLASH_SPI, SPI_I2S_FLAG_TXE) == RESET);

  /*!< Send byte through the SPI1 peripheral */
  SPI_I2S_SendData(sFLASH_SPI, byte);

  /*!< Wait to receive a byte */
  while (SPI_I2S_GetFlagStatus(sFLASH_SPI, SPI_I2S_FLAG_RXNE) == RESET);

  /*!< Return the byte read from the SPI bus */
  return SPI_I2S_ReceiveData(sFLASH_SPI);
}

/**
  * @brief  Reads a block of data from the FLASH.
  * @param  pBuffer: pointer to the buffer that receives the data read from the FLASH.
  * @param  ReadAddr: FLASH's internal address to read from.
  * @param  NumByteToRead: number of bytes to read from the FLASH.
  * @retval None
  */
void sFLASH_ReadBuffer(uint8_t* pBuffer, uint32_t ReadAddr, uint16_t NumByteToRead)
{
  /*!< Select the FLASH: Chip Select low */
  sFLASH_CS_LOW();

  /*!< Send "Read from Memory " instruction */
  sFLASH_SendByte(sFLASH_CMD_READ);

  /*!< Send ReadAddr high nibble address byte to read from */
  sFLASH_SendByte((ReadAddr & 0xFF0000) >> 16);
  /*!< Send ReadAddr medium nibble address byte to read from */
  sFLASH_SendByte((ReadAddr& 0xFF00) >> 8);
  /*!< Send ReadAddr low nibble address byte to read from */
  sFLASH_SendByte(ReadAddr & 0xFF);

  while (NumByteToRead--) /*!< while there is data to be read */
  {
    /*!< Read a byte from the FLASH */
    *pBuffer = sFLASH_SendByte(sFLASH_DUMMY_BYTE);
    /*!< Point to the next location where the byte read will be saved */
    pBuffer++;
  }

  /*!< Deselect the FLASH: Chip Select high */
  sFLASH_CS_HIGH();
}
点赞  2010-12-7 22:07
                                 我的板子上STM32运行在12MHz, SPI BR=1.5Mbps/0.75Mbps/0.325Mbps/0.1625Mbps,分别用ST的SPI EEPROM和SPI Flash做了测试,都出现了LZ描述的现象。
点赞  2010-12-7 22:14
                                 关注ing
点赞  2010-12-16 11:31
                                 MARK......
点赞  2010-12-16 12:36
电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 京公网安备 11010802033920号
    写回复