I am using MSP430FR6877 with external flash W25Q16JV,
I am using UCA0 SPI for communication, the communication is up and running, and I can read/write status registers and read manufacturer id for example,
But reading/writing data/code to the memory is still not working,
I am trying to test it by writing 5 bytes to address 0 in the flash, however when I read them, I find the reset values "0xFF",
The code is as following:
1- initialization:
void flashInit(void) { // initialize spi comm with flash spiInit(); // hard reset GPIO_setOutputLowOnPin(PORT_FLASH_RST, PIN_FLASH_RST); // configResetPin(); __delay_cycles(100000); GPIO_setOutputHighOnPin(PORT_FLASH_RST, PIN_FLASH_RST); __delay_cycles(100000); GPIO_setOutputHighOnPin(PORT_FLASH_WP, PIN_FLASH_WP); GPIO_setOutputHighOnPin(PORT_FLASH_CS, PIN_FLASH_CS); // soft reset: command 0x66 then 0x99 Reset(); // /* test: read manufacturer id */ uint8_t command[4] = {0}; uint8_t data[2] = {0}; command[0] = 0x90; command[1] = 0; command[2] = 0; command[3] = 0; spiTxRx(command, 4, data, 2, 1); WriteEnable(); WriteUnprotect(); /* chip erase */ command[0] = 0x60; //write command spiTxRx(command, 1, data, 0, 1); __delay_cycles(160000); command[0] = 0x01; command[1] = 0x00; spiTxRx(command, 2, data, 0, 1); command[0] = 0x31; command[1] = 0x00; spiTxRx(command, 2, data, 0, 1); command[0] = 0x11; command[1] = 0x00; spiTxRx(command, 2, data, 0, 1); // command[0] = 0x05; // spiTxRx(command, 1, data, 2, 1); // 10 ms delay until the flash is power up __delay_cycles(160000); }
2- Write:
void flashWrite(uint32_t address, uint8_t* data, uint16_t size) { // clear write protect uint8_t command[4]; uint8_t dummy = 0; WriteEnable(); WriteUnprotect(); /* This section writes data. The first character is the write command */ command[0] = 0x02; //write command command[1] = (unsigned char)(address >> 16); command[2] = (unsigned char)(address >> 8); command[3] = (unsigned char)(address >> 0); GPIO_setOutputLowOnPin(PORT_FLASH_CS, PIN_FLASH_CS); __delay_cycles(8800); spiTxRx(command, 4, &dummy, 0, 0); //send write command spiTxRx(data, size, &dummy, 0, 0); //write data __delay_cycles(8800); GPIO_setOutputHighOnPin(PORT_FLASH_CS, PIN_FLASH_CS); while(FlashReadStatus() == 0x03); //this ensure read operation are completed __delay_cycles(3200); }
3- Read:
void flashRead(uint32_t address, uint8_t* data, uint16_t size) { uint8_t command[4]; /*This section reads back data. The first character is the read command */ command[0] = 0x03; //send read command command[1] = (uint8_t)(address >> 16); command[2] = (uint8_t)(address >> 8); command[3] = (uint8_t)(address >> 0); spiTxRx(command, 4, data, size, 1); //send read command and read data }
4- Other used functions:
static void spiInit(void) { UCA0CTLW0 = UCSWRST; // **Put state machine in reset** UCA0CTLW0 |= UCMST + UCSYNC + UCCKPL + UCMSB; // 3-pin, 8-bit SPI master MSB UCA0CTLW0 |= UCSSEL_2; // SMCLK Device specific UCA0BR0 = 4; // CLK / 1 UCA0BR1 = 0; UCA0CTL1 &= ~UCSWRST; return; } static void spiTxRx(uint8_t *addr, uint32_t addlen, uint8_t *data, uint32_t datalen, uint8_t csEn) { unsigned int i=0, j=0; unsigned char dummy = 0; if (csEn == 1) { GPIO_setOutputLowOnPin(PORT_FLASH_CS, PIN_FLASH_CS); __delay_cycles(8800); } while(addlen-i){ while ( !(UCA0IFG & UCTXIFG) ); UCA0IFG &= ~UCRXIFG; UCA0TXBUF=addr[i++]; while ( !(UCA0IFG & UCRXIFG) ); dummy=UCA0RXBUF; } dummy = 0; while(datalen-j){ while ( !(UCA0IFG & UCTXIFG) ); UCA0TXBUF=dummy; while(!(UCA0IFG & UCRXIFG));//wait for byte to be received data[j++]=UCA0RXBUF; } if (csEn == 1) { __delay_cycles(8800); GPIO_setOutputHighOnPin(PORT_FLASH_CS, PIN_FLASH_CS); } return; } static void GlobalBlockProtectionUnlock (void) { /* send gloal block unlock command */ uint8_t command = 0x98; uint8_t dummy = 0; spiTxRx(&command, 1, &dummy, 0, 1); } static void Reset(void) { /* send gloal block unlock command */ uint8_t command = 0x66; uint8_t dummy = 0; spiTxRx(&command, 1, &dummy, 0, 1); command = 0x99; spiTxRx(&command, 1, &dummy, 0, 1); } static void WriteUnprotect (void) { GlobalBlockProtectionUnlock(); __delay_cycles(160000); } static void WriteEnable (void) { /* send write enable command */ uint8_t command = 0x06; uint8_t dummy = 0; spiTxRx(&command, 1, &dummy, 0, 1); } static uint8_t FlashReadStatus(void) { /* read status reg-1 */ uint8_t command = 0x05; uint8_t data = 0; spiTxRx(&command, 1, &data, 1, 1); return (uint8_t)data; } static void configResetPin(void) { /* send write enable command */ uint8_t command[2]; uint8_t dummy = 0; command[0] = 0x11; command[1] = 0x80; spiTxRx(command, 2, &dummy, 0, 1); }