Was the flash erased beforehand?

Here is the code I've used for programming flash.  It is
in use in the field in a very large number of installations.
It is in IAR format but the conversion should be easy.

Regards
-Bill Knight
R O SOftWare



flash.h
------
#ifndef INC_FLASH_H
#define INC_FLASH_H

#include "typedefs.h"

void flashEraseSector(void *addr);
void flashProgramBlock(void *addr, void *data, uint16 count);

#define flashProgramMemory(addr, data) flashProgramBlock(addr, data, sizeof 
(data));

#endif

flash.c
-------
#define FCLK_FREQ     (450e3)           // flash programming clock frequency
#define FCLK_DIVIDER  (MCLK / FCLK_FREQ) // good from 1 to 64

/******************************************************************************
 *
 * Function Name: void _flashControl()
 *
 * Description:  
 *    This low level function checks the value of 'count' and if
 *    non-zero writes the referenced data to flash.  If it is zero, it
 *    erases the flash sector containing the address.
 *
 * Calling Sequence: 
 *    uint8  *addr  destination address in flash
 *    uint8  *data  pointer to data to write
 *    uint16 count  number of bytes to write
 *
 * Returns:
 *    void
 *
 * NOTE: this function is marked 'monitor' so the compiler will save
 * the current interrupt state on entry and restore it on exit.
 *****************************************************************************/
static monitor void _flashControl(uint8 *addr, uint8 *data, uint16 count)
  {
  uint8 ie1;

  ie1 = IE1;                            // get current interrupt enables
  IE1 &= ~(NMIIE | ACCVIE | OFIE);      // disable enabled interrupts
  FCTL2 = FWKEY +                       // key
          FSSEL_1 +                     // use MCLK
          FCLK_DIVIDER;                 // setup divider - 1..64
  FCTL3 = FWKEY;                        // LOCK = 0

  if (count)
    {
    FCTL1 = FWKEY | WRT;                // set WRITE bit

    do                                  // loop through, writing the data
      *addr++ = *data++;
    while (--count);
    }
  else
    {
    FCTL1 = FWKEY | ERASE;              // set ERASE bit
    *addr = 0;                          // write to address in sector to start 
erase
    }

  FCTL1 = FWKEY;                        // clear WRITE/ERASE bit
  FCTL3 = FWKEY | LOCK;                 // LOCK = 1
  IE1 = ie1;                            // restore interrupt enables
  }

/******************************************************************************
 *
 * Function Name: void flashEraseSector()
 *
 * Description:  
 *    Erase one flash sector
 *
 * Calling Sequence: 
 *    void *addr   address within sector to be erased
 *
 * Returns:
 *    void
 *
 *****************************************************************************/
void flashEraseSector(void *addr)
  {
  _flashControl(addr, NULL, 0);
  }


/******************************************************************************
 *
 * Function Name: void flashProgramBlock()
 *
 * Description:  
 *    Program a block of data in flash
 *
 * Calling Sequence: 
 *    void  *addr   destination address in flash
 *    void  *data   pointer to data to write
 *    uint16 count  number of bytes to write
 *
 * Returns:
 *    void
 *
 *****************************************************************************/
void flashProgramBlock(void *addr, void *data, uint16 count)
  {
  _flashControl(addr, data, count);
  }




Reply via email to