- /**************************************************************************//**
 
-  * [url=home.php?mod=space&uid=288409]@file[/url]     main.c
 
-  * [url=home.php?mod=space&uid=895143]@version[/url]  V2.0
 
-  * $Revision: 11 $
 
-  * $Date: 15/03/04 9:47a $
 
-  * [url=home.php?mod=space&uid=247401]@brief[/url]    Access the SPI Flash through a SPI interface.
 
-  *
 
-  * @note
 
-  * Copyright (C) 2015 Nuvoton Technology Corp. All rights reserved.
 
-  *
 
-  ******************************************************************************/
 
- #include <stdio.h>
 
- #include "NUC505Series.h"
 
 
- #define TEST_NUMBER 1   /* page numbers */
 
- #define TEST_LENGTH 256 /* length */
 
 
- #define SPI_FLASH_PORT  SPI0
 
 
- uint8_t SrcArray[TEST_LENGTH];
 
- uint8_t DestArray[TEST_LENGTH];
 
 
- /* Function prototype declaration */
 
- void SYS_Init(void);
 
- void UART0_Init(void);
 
- void SPI0_Init(void);
 
 
- uint16_t SpiFlash_ReadMidDid(void)
 
- {
 
-     uint8_t u8RxData[6], u8IDCnt = 0;
 
 
-     // /CS: active
 
-     SPI_SET_SS_LOW(SPI_FLASH_PORT);
 
 
-     // send Command: 0x90, Read Manufacturer/Device ID
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, 0x90);
 
 
-     // send 24-bit '0', dummy
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, 0x00);
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, 0x00);
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, 0x00);
 
 
-     // receive 16-bit
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, 0x00);
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, 0x00);
 
 
-     // wait tx finish
 
-     while(SPI_IS_BUSY(SPI_FLASH_PORT));
 
 
-     // /CS: de-active
 
-     SPI_SET_SS_HIGH(SPI_FLASH_PORT);
 
 
-     while(!SPI_GET_RX_FIFO_EMPTY_FLAG(SPI_FLASH_PORT))
 
-         u8RxData[u8IDCnt ++] = SPI_READ_RX(SPI_FLASH_PORT);
 
 
-     return ( (u8RxData[4]<<8) | u8RxData[5] );
 
- }
 
 
- void SpiFlash_ChipErase(void)
 
- {
 
-     // /CS: active
 
-     SPI_SET_SS_LOW(SPI_FLASH_PORT);
 
 
-     // send Command: 0x06, Write enable
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, 0x06);
 
 
-     // wait tx finish
 
-     while(SPI_IS_BUSY(SPI_FLASH_PORT));
 
 
-     // /CS: de-active
 
-     SPI_SET_SS_HIGH(SPI_FLASH_PORT);
 
 
-     //////////////////////////////////////////
 
 
-     // /CS: active
 
-     SPI_SET_SS_LOW(SPI_FLASH_PORT);
 
 
-     // send Command: 0xC7, Chip Erase
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, 0xC7);
 
 
-     // wait tx finish
 
-     while(SPI_IS_BUSY(SPI_FLASH_PORT));
 
 
-     // /CS: de-active
 
-     SPI_SET_SS_HIGH(SPI_FLASH_PORT);
 
 
-     SPI_ClearRxFIFO(SPI0);
 
- }
 
 
- uint8_t SpiFlash_ReadStatusReg(void)
 
- {
 
-     // /CS: active
 
-     SPI_SET_SS_LOW(SPI_FLASH_PORT);
 
 
-     // send Command: 0x05, Read status register
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, 0x05);
 
 
-     // read status
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, 0x00);
 
 
-     // wait tx finish
 
-     while(SPI_IS_BUSY(SPI_FLASH_PORT));
 
 
-     // /CS: de-active
 
-     SPI_SET_SS_HIGH(SPI_FLASH_PORT);
 
 
-     // skip first rx data
 
-     SPI_READ_RX(SPI_FLASH_PORT);
 
 
-     return (SPI_READ_RX(SPI_FLASH_PORT) & 0xff);
 
- }
 
 
- void SpiFlash_WriteStatusReg(uint8_t u8Value)
 
- {
 
-     // /CS: active
 
-     SPI_SET_SS_LOW(SPI_FLASH_PORT);
 
 
-     // send Command: 0x06, Write enable
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, 0x06);
 
 
-     // wait tx finish
 
-     while(SPI_IS_BUSY(SPI_FLASH_PORT));
 
 
-     // /CS: de-active
 
-     SPI_SET_SS_HIGH(SPI_FLASH_PORT);
 
 
-     ///////////////////////////////////////
 
 
-     // /CS: active
 
-     SPI_SET_SS_LOW(SPI_FLASH_PORT);
 
 
-     // send Command: 0x01, Write status register
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, 0x01);
 
 
-     // write status
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, u8Value);
 
 
-     // wait tx finish
 
-     while(SPI_IS_BUSY(SPI_FLASH_PORT));
 
 
-     // /CS: de-active
 
-     SPI_SET_SS_HIGH(SPI_FLASH_PORT);
 
- }
 
 
- void SpiFlash_WaitReady(void)
 
- {
 
-     uint8_t ReturnValue;
 
 
-     do {
 
-         ReturnValue = SpiFlash_ReadStatusReg();
 
-         ReturnValue = ReturnValue & 1;
 
-     } while(ReturnValue!=0); // check the BUSY bit
 
- }
 
 
- void SpiFlash_NormalPageProgram(uint32_t StartAddress, uint8_t *u8DataBuffer)
 
- {
 
-     uint32_t i = 0;
 
 
-     // /CS: active
 
-     SPI_SET_SS_LOW(SPI_FLASH_PORT);
 
 
-     // send Command: 0x06, Write enable
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, 0x06);
 
 
-     // wait tx finish
 
-     while(SPI_IS_BUSY(SPI_FLASH_PORT));
 
 
-     // /CS: de-active
 
-     SPI_SET_SS_HIGH(SPI_FLASH_PORT);
 
 
 
-     // /CS: active
 
-     SPI_SET_SS_LOW(SPI_FLASH_PORT);
 
 
-     // send Command: 0x02, Page program
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, 0x02);
 
 
-     // send 24-bit start address
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, (StartAddress>>16) & 0xFF);
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, (StartAddress>>8)  & 0xFF);
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, StartAddress       & 0xFF);
 
 
-     // write data
 
-     while(1) {
 
-         if(!SPI_GET_TX_FIFO_FULL_FLAG(SPI_FLASH_PORT)) {
 
-             SPI_WRITE_TX(SPI_FLASH_PORT, u8DataBuffer[i++]);
 
-             if(i >= 255) break;
 
-         }
 
-     }
 
 
-     // wait tx finish
 
-     while(SPI_IS_BUSY(SPI_FLASH_PORT));
 
 
-     // /CS: de-active
 
-     SPI_SET_SS_HIGH(SPI_FLASH_PORT);
 
 
-     SPI_ClearRxFIFO(SPI_FLASH_PORT);
 
- }
 
 
- void SpiFlash_NormalRead(uint32_t StartAddress, uint8_t *u8DataBuffer)
 
- {
 
-     uint32_t i;
 
 
-     // /CS: active
 
-     SPI_SET_SS_LOW(SPI_FLASH_PORT);
 
 
-     // send Command: 0x03, Read data
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, 0x03);
 
 
-     // send 24-bit start address
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, (StartAddress>>16) & 0xFF);
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, (StartAddress>>8)  & 0xFF);
 
-     SPI_WRITE_TX(SPI_FLASH_PORT, StartAddress       & 0xFF);
 
 
-     while(SPI_IS_BUSY(SPI_FLASH_PORT));
 
-     // clear RX buffer
 
-     SPI_ClearRxFIFO(SPI_FLASH_PORT);
 
 
-     // read data
 
-     for(i=0; i<256; i++) {
 
-         SPI_WRITE_TX(SPI_FLASH_PORT, 0x00);
 
-         while(SPI_IS_BUSY(SPI_FLASH_PORT));
 
-         u8DataBuffer[i] = SPI_READ_RX(SPI_FLASH_PORT);
 
-     }
 
 
-     // wait tx finish
 
-     while(SPI_IS_BUSY(SPI_FLASH_PORT));
 
 
-     // /CS: de-active
 
-     SPI_SET_SS_HIGH(SPI_FLASH_PORT);
 
- }
 
 
- /* Main */
 
- int main(void)
 
- {
 
-     uint32_t u32ByteCount, u32FlashAddress, u32PageNumber;
 
-     uint32_t nError = 0;
 
-     uint16_t u16ID;
 
 
-     /* Init System, IP clock and multi-function I/O */
 
-     SYS_Init();
 
 
-     /* Init UART0 to 115200-8n1 for print message */
 
-     UART0_Init();
 
 
-                 /* Init SPI0, IP clock and multi-function I/O */
 
-                 SPI0_Init();
 
-                 
 
-     /* Configure SPI_FLASH_PORT as a master, MSB first, 8-bit transaction, SPI Mode-0 timing, clock is 2MHz */
 
-     SPI_Open(SPI_FLASH_PORT, SPI_MASTER, SPI_MODE_0, 8, 2000000);
 
 
-     /* Enable the automatic hardware slave select function. Select the SS0 pin and configure as low-active. */
 
-     SPI_EnableAutoSS(SPI_FLASH_PORT, SPI_SS, SPI_SS_ACTIVE_LOW);
 
-     SPI_ENABLE(SPI_FLASH_PORT);
 
 
-     printf("\n+------------------------------------------------------------------------+\n");
 
-     printf("|            NUC505        SPI Sample with SPI Flash                     |\n");
 
-     printf("+------------------------------------------------------------------------+\n");
 
 
-     /* Wait ready */
 
-     SpiFlash_WaitReady();
 
 
- ///    if((u16ID = SpiFlash_ReadMidDid()) != 0x1C14) {
 
-                 if((u16ID = SpiFlash_ReadMidDid()) != 0xEF14) {
 
-         printf("Wrong ID, 0x%x\n", u16ID);
 
-         return -1;
 
-     } else
 
-         printf("Flash found: Winbond 25Q16OVSEG ...\n");
 
 
-     printf("Erase chip ...");
 
 
-     /* Erase SPI flash */
 
-     SpiFlash_ChipErase();
 
 
-     /* Wait ready */
 
-     SpiFlash_WaitReady();
 
 
-     printf("[OK]\n");
 
 
-     /* init source data buffer */
 
-     for(u32ByteCount=0; u32ByteCount<TEST_LENGTH; u32ByteCount++) {
 
-         SrcArray[u32ByteCount] = u32ByteCount;
 
-     }
 
 
-     printf("Start to normal write data to Flash ...");
 
-     /* Program SPI flash */
 
-     u32FlashAddress = 0;
 
-     for(u32PageNumber=0; u32PageNumber<TEST_NUMBER; u32PageNumber++) {
 
-         /* page program */
 
-         SpiFlash_NormalPageProgram(u32FlashAddress, SrcArray);
 
-         SpiFlash_WaitReady();
 
-         u32FlashAddress += 0x100;
 
-     }
 
 
-     printf("[OK]\n");
 
 
-     /* clear destination data buffer */
 
-     for(u32ByteCount=0; u32ByteCount<TEST_LENGTH; u32ByteCount++) {
 
-         DestArray[u32ByteCount] = 0;
 
-     }
 
 
-     printf("Normal Read & Compare ...");
 
 
-     /* Read SPI flash */
 
-     u32FlashAddress = 0;
 
-     for(u32PageNumber=0; u32PageNumber<TEST_NUMBER; u32PageNumber++) {
 
-         /* page read */
 
-         SpiFlash_NormalRead(u32FlashAddress, DestArray);
 
-         u32FlashAddress += 0x100;
 
 
-         for(u32ByteCount=0; u32ByteCount<TEST_LENGTH; u32ByteCount++) {
 
-             if(DestArray[u32ByteCount] != SrcArray[u32ByteCount])
 
-                 nError ++;
 
-         }
 
-     }
 
 
-     if(nError == 0)
 
-         printf("[OK]\n");
 
-     else
 
-         printf("[FAIL]\n");
 
 
-     while(1);
 
- }
 
 
- void SYS_Init(void)
 
- {
 
 
- /*---------------------------------------------------------------------------------------------------------*/
 
- /* Init System Clock                                                                                       */
 
- /*---------------------------------------------------------------------------------------------------------*/
 
-     /* Unlock protected registers */
 
-     //SYS_UnlockReg();
 
-      
 
-     /* Enable  XTAL */
 
-     CLK->PWRCTL |= CLK_PWRCTL_HXTEN_Msk;
 
 
-     CLK_SetCoreClock(FREQ_96MHZ);
 
-     
 
-                 /* PCLK divider */
 
-                 CLK_SetModuleClock(PCLK_MODULE, NULL, 1);
 
-                 
 
-     /* Lock protected registers */
 
-     //SYS_LockReg();
 
-         
 
- }
 
 
- void UART0_Init(void)
 
- {
 
-                 /* Enable UART0 Module clock */
 
-     CLK_EnableModuleClock(UART0_MODULE);
 
-                 /* UART0 module clock from EXT */
 
-                 CLK_SetModuleClock(UART0_MODULE, CLK_UART0_SRC_EXT, 0);
 
-     /* Reset IP */
 
-     SYS_ResetModule(UART0_RST);    
 
-     /* Configure UART0 and set UART0 Baud-rate */
 
-                 UART_Open(UART0, 115200);
 
-                 /*---------------------------------------------------------------------------------------------------------*/
 
-     /* Init I/O Multi-function                                                                                 */
 
-     /*---------------------------------------------------------------------------------------------------------*/
 
-     /* Configure multi-function pins for UART0 RXD and TXD */
 
-                 SYS->GPB_MFPL  = (SYS->GPB_MFPL & (~SYS_GPB_MFPL_PB0MFP_Msk) ) | SYS_GPB_MFPL_PB0MFP_UART0_TXD;        
 
-                 SYS->GPB_MFPL  = (SYS->GPB_MFPL & (~SYS_GPB_MFPL_PB1MFP_Msk) ) | SYS_GPB_MFPL_PB1MFP_UART0_RXD;        
 
-         
 
- }
 
 
- void SPI0_Init(void)
 
- {
 
-                 /* Enable SPI0 Module clock */
 
-     CLK_EnableModuleClock(SPI0_MODULE);
 
-                 /* SPI0 module clock from EXT */
 
-                 CLK_SetModuleClock(SPI0_MODULE, CLK_SPI0_SRC_PLL, 0);
 
-     /* Reset IP */
 
-     SYS_ResetModule(SPI0_RST);    
 
-     /*---------------------------------------------------------------------------------------------------------*/
 
-     /* Init I/O Multi-function                                                                                 */
 
-     /*---------------------------------------------------------------------------------------------------------*/
 
-     /* Configure multi-function pins for SPI0 */
 
-                 SYS->GPB_MFPL  = (SYS->GPB_MFPL & (~SYS_GPB_MFPL_PB2MFP_Msk) ) | SYS_GPB_MFPL_PB2MFP_SPI0_SS;        
 
-                 SYS->GPB_MFPL  = (SYS->GPB_MFPL & (~SYS_GPB_MFPL_PB3MFP_Msk) ) | SYS_GPB_MFPL_PB3MFP_SPI0_CLK;        
 
-                 SYS->GPB_MFPL  = (SYS->GPB_MFPL & (~SYS_GPB_MFPL_PB4MFP_Msk) ) | SYS_GPB_MFPL_PB4MFP_SPI0_MOSI;        
 
-                 SYS->GPB_MFPL  = (SYS->GPB_MFPL & (~SYS_GPB_MFPL_PB5MFP_Msk) ) | SYS_GPB_MFPL_PB5MFP_SPI0_MISO;        
 
-         
 
- }
 
 
- /*** (C) COPYRIGHT 2015 Nuvoton Technology Corp. ***/