stm32驱动NOR Flash 之MX25L51245G(64MB)

MX25L51245G 支持SPI的MODE0/MODE3,一般都选择mode3

#define FLASH_SECTOR_SIZE				(4*1024)
#define FLASH_PAGE_SIZE					256

引脚定义

/*
* SPI1
* @SCK  : PA5
* @MISO : PA6
* @MOSI : PA7
*
* @CS   : PA0
*/

读写接口

static u8 SPI_Write(u8 byte)
{
	u32 timeout = 0xFFFF;
	while(!(SPI1->SR & SPI_I2S_FLAG_TXE))
	{
		if(--timeout == 0)
		{
			printf("TX timeout ! \r\n");
			return 0;
		}
	}
	
	SPI1->DR = byte;

	timeout = 0xFFFF;
	while(!(SPI1->SR & SPI_I2S_FLAG_RXNE))
	if(--timeout == 0)
	{
		printf("RX timeout ! \r\n");
		return 0;
	}

	return SPI1->DR;
}

static u8 SPI_Read(void)
{
    return (SPI_Write(DUMMY_BYTE));
}

初始化函数

void SPI1_Configuration(void)
{
	SPI_InitTypeDef  SPI_InitStructure;
    GPIO_InitTypeDef GPIO_InitStructure;

	RCC_APB2PeriphClockCmd(RCC_APB2Periph_SPI1, ENABLE);
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
    
    /* Configure SPI1 pins: NSS, SCK, MISO and MOSI */
    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_5 | GPIO_Pin_6 | GPIO_Pin_7;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
    GPIO_Init(GPIOA, &GPIO_InitStructure);

    /* Configure PA.0 as Output push-pull, used as Chip select */
    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
    GPIO_Init(GPIOA, &GPIO_InitStructure);

    /* Deselect the FLASH: Chip Select high */
    SPI_CS_Low();

    /* SPI1 configuration */ 
    SPI_InitStructure.SPI_Direction = SPI_Direction_2Lines_FullDuplex;
    SPI_InitStructure.SPI_Mode = SPI_Mode_Master;
    SPI_InitStructure.SPI_DataSize = SPI_DataSize_8b;
    SPI_InitStructure.SPI_CPOL = SPI_CPOL_High;
    SPI_InitStructure.SPI_CPHA = SPI_CPHA_2Edge;          /* mode 3 */
    SPI_InitStructure.SPI_NSS = SPI_NSS_Soft;
    SPI_InitStructure.SPI_BaudRatePrescaler = SPI_BaudRatePrescaler_8;
    SPI_InitStructure.SPI_FirstBit = SPI_FirstBit_MSB;
    SPI_InitStructure.SPI_CRCPolynomial = 7;
    SPI_Init(SPI1, &SPI_InitStructure);

    /* Enable SPI1 NSS output for master mode */
    //SPI_SSOutputCmd(SPI1, DISABLE);    
    /* Enable SPI1  */
    SPI_Cmd(SPI1, ENABLE); 

	SPI_Write(0xFF); //start transport
}

等待忙

/*
* @return : none-zero idle, else busy
*/
static u8 SPI_WaitBusy(void)
{
	u32 timeout = 0xFFFF;
	while( SET==SPI_I2S_GetFlagStatus(SPI1, SPI_I2S_FLAG_BSY)) /* SPI_SR */
	{
		if(--timeout == 0)
			return 1;
	}

	return 0;
}

Flash 等待WIP信号

#define    FLASH_WIP_MASK         (1 << 0)

/*
* @return : none-zero timeout
*/
static u8 FlashWait_Busy(void)
{
    u8 FLASH_Status;
	
    u32 retry=0;
    FLASH_CS_Low();

	/*
	* bit 0: WIP (=1 busy, else free)
	* bit 1: WEL (=1 write enable)
	*/
    SPI_Write(RDSD_CMD);          /* read status register */
    do{
        
        FLASH_Status=SPI_Read();
        if(retry++ > FLASH_BUSY_TIMEOUT)
            return FLASH_Status;
    }while((FLASH_Status & FLASH_WIP_MASK) == FLASH_WIP_MASK);    /* fix : not bit 7 !!! */
    
    //printf("status register : 0x%x \r\n", FLASH_Status);

    SPI_CS_High();

	return 0;
}

获取flash信息

static void FlashGet_Info(flashInfoTypedef * pFlashInfo)
{
//	    FlashWait_Busy();
    FLASH_CS_Low();
    SPI_Write(RDID_CMD);
    pFlashInfo->ManufacturerID=SPI_Read();
    pFlashInfo->DeviceID[0]=SPI_Read();
    pFlashInfo->DeviceID[1]=SPI_Read();
    SPI_CS_High();    
}

static void FlashGet_ElectronicInfo(flashInfoTypedef * pFlashInfo)
{
    FLASH_CS_Low();
    SPI_Write(REMS_CMD);
    SPI_Write(DUMMY_BYTE);
    SPI_Write(DUMMY_BYTE);
    SPI_Write(0x00);             //manufacturer's ID first
    pFlashInfo->ManufacturerID=SPI_Read();
    pFlashInfo->DeviceID[0]=SPI_Read();   
    SPI_CS_High();    
}

写使能

static void FlashWriteEnable(void)
{
    FLASH_CS_Low();
    SPI_Write(WREN_CMD);   
    SPI_CS_High();    
}

spi flash初始化

void SpiFlash_Init(void)
{
	flashInfoTypedef flashInfo;

	//SPI1_Configuration();
#if 1
	FlashGet_ElectronicInfo(&flashInfo);

	if((flashInfo.ManufacturerID==0xc2)&&(flashInfo.DeviceID[0]==0x20))
    {
        printf("Flash Info: MXIC(Macronix International Co.,Ltd\r\n");
    }
#endif
    FlashGet_Info(&flashInfo);
    printf("ManufacturerID = 0x%02X     \r\n",flashInfo.ManufacturerID);
    printf("DeviceID       = 0x%02X%02X \r\n",flashInfo.DeviceID[0],flashInfo.DeviceID[1]);
}

获取ID的接口

static void Flash_ReadID(void)
{
	flashInfoTypedef flashInfo;
	
	FlashGet_ElectronicInfo(&flashInfo);

	if((flashInfo.ManufacturerID==0xc2)&&(flashInfo.DeviceID[0]==0x20))
    {
        printf("Flash Info: MXIC(Macronix International Co.,Ltd\r\n");
    }
    FlashGet_Info(&flashInfo);
    printf("ManufacturerID = 0x%02X     \r\n",flashInfo.ManufacturerID);
    printf("DeviceID       = 0x%02X%02X \r\n",flashInfo.DeviceID[0],flashInfo.DeviceID[1]);
}

 

你可能感兴趣的:(STM32)