打印
[Cortex-M0技术交流]

菜农老师助学板第二贴之SPI操作W25Q16BV

[复制链接]
4189|8
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
cecwxf|  楼主 | 2011-8-23 13:49 | 只看该作者 |只看大图 回帖奖励 |倒序浏览 |阅读模式
如题,这几天都忙于winces手持机,抽空看了下W25Q16BV的芯片资料,用NUC120SPI1总线“所谓的中断方式"操作。参考BSP例程和三心的程序。谢谢。

SPI总线操作W25Q16BV:
#include <stdio.h>
#include "NUC1xx.h"
#include "DrvUART.h"
#include "DrvSYS.h"
#include "DrvSPI.h"
#include "DrvGPIO.h"
#include "Drive_Function.h"

#define Enable_SPI1_W25Q16BV     DrvGPIO_ClrBit(E_GPA, 14)
#define Disable_SPI1_W25Q16BV    DrvGPIO_SetBit(E_GPA, 14)
//extern  uint32_t  SPI_TX_DATA_Buffer[256];
//extern  uint32_t  SPI_RX_DATA_Buffer[256];
extern  uint32_t  SPI_RX_DATA;
extern  uint32_t Write_Enable;
extern  uint32_t Write_Disable;
extern  uint32_t Read_Status_Register1;
extern  uint32_t Read_DATA;
extern  uint32_t Page_Program;
extern  uint32_t Sector_Erase;
extern  uint32_t Chip_Erase;
extern  uint32_t Read_ID;
extern  uint32_t Addr;


extern uint8_t SPI_DATA_Buffer[256];

extern volatile uint8_t count;
extern volatile uint32_t g_Spi1IntFlag;
extern volatile uint8_t  W25Q16BV_BUSY_Flag;
extern uint32_t u32Tmp;



void W25Q16BV_SPI_Init()
{  
      
    /*开SPI1总线  设置为主机模式,波形1*/
     DrvSPI_Open(eDRVSPI_PORT1, eDRVSPI_MASTER, eDRVSPI_TYPE1, 32,FALSE);   
    /*设置为MSP优先传输MSB*/
    DrvSPI_SetEndian(eDRVSPI_PORT1, eDRVSPI_MSB_FIRST);            
    /*从机选择线低电平或者下降沿激活*/
    DrvSPI_SetSlaveSelectActiveLevel(eDRVSPI_PORT1, eDRVSPI_ACTIVE_LOW_FALLING);
    /*SPI总线的速率设置为1MHZ*/   
    DrvSPI_SetClockFreq(eDRVSPI_PORT1, 1000000, 0);
    /*使能W25Q16BV 的片选信号*/
    Enable_SPI1_W25Q16BV;
    /*开启SPI1总线中断,并且与回调函数SPI1_Callback挂钩*/
    DrvSPI_EnableInt(eDRVSPI_PORT1, SPI1_Callback, 1);
                                 
}




void W25Q16BV_SPI_PageProgram()
{
       uint16_t i;
    uint32_t au32SourceData;
     /*使能SPI1中断,且SPI1_Callback为其回调函数*/
    DrvSPI_EnableInt(eDRVSPI_PORT1, SPI1_Callback, 0);
     /*中断标志清0*/
    g_Spi1IntFlag=0;

   /*使能W25Q16BV*/
   Enable_SPI1_W25Q16BV;


   /* Set the bit length of SPI transfer. */  
   DrvSPI_SetBitLength(eDRVSPI_PORT1,8);

   /*写使能*/
   au32SourceData=0x06;
   printf("发送写能W25Q16BV\n");
   DrvSPI_SingleWrite(eDRVSPI_PORT1, &au32SourceData);
  
   /*等待传输完毕*/
   while(g_Spi1IntFlag==0);
   g_Spi1IntFlag=0;

   printf("写能W25Q16BV指令发送完毕\n");


   /*关闭CS*/
   Disable_SPI1_W25Q16BV;
  

   /*打开CS*/
   Enable_SPI1_W25Q16BV;
   

   printf("Page_Program指令开始发送\n");
   au32SourceData=0x02;
   DrvSPI_SingleWrite(eDRVSPI_PORT1, &au32SourceData);

    /*等待传输完毕*/
   while(g_Spi1IntFlag==0);
   g_Spi1IntFlag=0;
  

   DrvSPI_SetBitLength(eDRVSPI_PORT1,24);
   au32SourceData=0x0000;
   DrvSPI_SingleWrite(eDRVSPI_PORT1, &au32SourceData);

    /*等待传输完毕*/
   while(g_Spi1IntFlag==0);
   g_Spi1IntFlag=0;
   printf("Page_Program指令已经发送完毕\n");



   DrvSPI_SetBitLength(eDRVSPI_PORT1,8);


   for(i=0;i<256;i++)
   {
     SPI_DATA_Buffer=0x02;
      au32SourceData=SPI_DATA_Buffer;
     DrvSPI_SingleWrite(eDRVSPI_PORT1,&au32SourceData);
      /*等待传输完毕*/
     while(g_Spi1IntFlag==0);
     g_Spi1IntFlag=0;
     printf("写入的值为: %d\n", SPI_DATA_Buffer);
   }
    Disable_SPI1_W25Q16BV;
}

void W25Q16BV_SPI_ReadFlash()
{   
     uint32_t au32SourceData;
     uint16_t i;

     /*中断标志清0*/
     g_Spi1IntFlag=0;

     /*使能SPI1中断,且SPI1_Callback为其回调函数*/
     DrvSPI_EnableInt(eDRVSPI_PORT1, SPI1_Callback, 0);   
   
     /*设置传输的长度*/
     DrvSPI_SetBitLength(eDRVSPI_PORT1,8);
     /*使能W25Q16BV*/
     Enable_SPI1_W25Q16BV;
   
     /*读操作指令*/
     au32SourceData=0X03;
     /*写入指令*/
     DrvSPI_SingleWrite(eDRVSPI_PORT1, &au32SourceData);

        /*等待传输完毕*/
    printf("开始写读命令字和地址\n");
    while(g_Spi1IntFlag==0);
    g_Spi1IntFlag=0;                  
    printf("写完读命令字和地址\n");

     /*设置传送长度为24位*/
    DrvSPI_SetBitLength(eDRVSPI_PORT1,24);
    /*传送地址*/
    au32SourceData=0X0000;
    DrvSPI_SingleWrite(eDRVSPI_PORT1, &au32SourceData);

        /*等待传输完毕*/
    while(g_Spi1IntFlag==0);
    g_Spi1IntFlag=0;         
    DrvSPI_SetBitLength(eDRVSPI_PORT1,8);
   
       for(i =0; i<256; i++)
    {
      au32SourceData=0x0;
        
     /*开始接收数据*/
     DrvSPI_SingleWrite(eDRVSPI_PORT1, &au32SourceData);
    /*等待传输完毕*/
     while(g_Spi1IntFlag==0);
     g_Spi1IntFlag=0;   
     /*读取收到的数据*,并且不触发下一次传送*/
     DrvSPI_DumpRxRegister(eDRVSPI_PORT1, &SPI_RX_DATA, 1);
     /*打印收到的数据*/
     SPI_DATA_Buffer=(uint8_t)SPI_RX_DATA;
     printf("0x%X ",SPI_DATA_Buffer);
     if ((i%10)==6)printf("\n");
     }
      printf("所有数据接收完毕\n");
     Disable_SPI1_W25Q16BV;
}

void W25Q16BV_SPI_ChipErase()
{
   
        /*使能SPI1中断,且SPI1_Callback为其回调函数*/
    DrvSPI_EnableInt(eDRVSPI_PORT1, SPI1_Callback, 0);
    /*中断标志清0*/
   g_Spi1IntFlag=0;

   /*使能W25Q16BV*/
   Enable_SPI1_W25Q16BV;

   /* Set the bit length of SPI transfer. */  
   DrvSPI_SetBitLength(eDRVSPI_PORT1,8);


/* write the first data of source buffer to Tx register of SPI0. And start transmission. */
   DrvSPI_SingleWrite(eDRVSPI_PORT1, &Write_Enable);

   /*等待传输完毕*/
   while(g_Spi1IntFlag==0);
   g_Spi1IntFlag=0;

    /*关闭CS*/
   Disable_SPI1_W25Q16BV;
   DrvSPI_SetBitLength(eDRVSPI_PORT1,8);

   /*打开CS*/
   Enable_SPI1_W25Q16BV;

   DrvSPI_SingleWrite(eDRVSPI_PORT1, &Chip_Erase);

        /*等待传输完毕*/
   while(g_Spi1IntFlag==0);
   g_Spi1IntFlag=0;

   Disable_SPI1_W25Q16BV;

}

void SPI1_Callback(uint32_t u32UserData)
{
    g_Spi1IntFlag = 1;
}


main 函数
/*---------------------------------------------------------------------------------------------------------*/
/*                                                                                                         */
/* Copyright(c) 2011 Nuvoton Technology Corp. All rights reserved.                                         */
/*---------------------------------------------------------------------------------------------------------*/


/******************************************************************************
文件名:    W25Q16BV_Function.c
说  明:    本文件为“NUC120RE3AN用SPI总线主机模式读写W25Q16BV的主函数。UART的波特率为115200。
申明:       本程序参考三心的spi程序和板子自带的BSP例程,运用中断模式。谢谢。
开  始:    2011.8.23
修  改:    V1.0
******************************************************************************/

#include <stdio.h>
#include "NUC1xx.h"
#include "DrvUART.h"
#include "DrvSYS.h"
#include "DrvSPI.h"
#include "global.h"

  
int main()
{
    SYSTEM_Config();
    UART_Config();
    GPIO_Config();
    W25Q16BV_SPI_Init();
  


      printf("\n\n");
    printf("+----------------------------------------------------------------------+\n");        
    printf("|                      菜农老师助学板之SPI操作W25Q16BV                 |\n");
    printf("|                                                                      |\n");
    printf("+----------------------------------------------------------------------+\n");
    printf("\n");
    printf("配置SPI1为主机模式.\n");
    printf("SPI1 时钟为: %d Hz\n", DrvSPI_GetClock1Freq(eDRVSPI_PORT1));
   
   
  while(1)
  {
       if(SPI_Start_Flag==TRUE)
     {
        SPI_Start_Flag=FALSE;
        printf("开始操作SPI\n");
        switch(UART_Buffer_Rx)
        {
          case  'R':
          case  'r':
          printf("Read data from W25Q16BV ...\n");
         
          W25Q16BV_SPI_ReadFlash();
          break;


          case 'W':
          case 'w':
          printf("Write data to W25Q16BV ...\n");


          DrvSYS_Delay(1000);
          W25Q16BV_SPI_PageProgram();
          printf("Write Flash Over!\n");
          break;
          default:
        printf("您输入的指令有误!\n");
        }
        
     
     }
  
    }

}

写.jpg (32.74 KB )

写.jpg

NUC120_SPI1_W25Q16BV.rar

1.09 MB

相关帖子

沙发
hotpower| | 2011-8-23 14:26 | 只看该作者
很好!
不管是参考谁的,只要自己查阅了资料,调试了例程。
知道SPI接口的一些特性,结合FLASH芯片进行读写成功,自己认为可以掌握了,就是最大的进步或巩固。

使用特权

评论回复
板凳
wang0225| | 2011-8-23 17:32 | 只看该作者
GOOD!

使用特权

评论回复
地板
dghidt| | 2012-5-29 17:20 | 只看该作者
它的写控制命令字是多少啊?就是取消写保护的命令

使用特权

评论回复
5
lixiang656| | 2012-7-23 14:19 | 只看该作者
想问一下如何实现在串口显示中文

使用特权

评论回复
6
呆板书生| | 2012-7-24 07:42 | 只看该作者
一直有一个问题想搞清楚,

24CXX系列的产品,一直有人说会发生丢失数据,特别是开机的瞬间。不知道W25Q16BV有没有类似的问题

使用特权

评论回复
7
dong_abc| | 2012-7-25 00:59 | 只看该作者
6# 呆板书生

一般都会上电等待一会,稳定再读写吧。

使用特权

评论回复
8
lixiang656| | 2012-7-25 09:24 | 只看该作者
想问一下如何实现串口显示中文,然后执行while(1)里面的时候就有效果,我所用的是M0516LAN的,该改的都改了,我在想是不是在延时上有些问题,需要做些延时处理呢?谢谢回答!

使用特权

评论回复
9
vincent2012| | 2013-4-17 15:10 | 只看该作者
兄弟  想问一下这个截图 是用什么软件 监控的

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

个人签名:充实灵魂,满足自己。做生活的强者,当时代的勇士!!!

2

主题

421

帖子

2

粉丝