I can´t write to data flash

cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

I can´t write to data flash

2,848 Views
frbetelu
Contributor I
Hi,

I'm trying write to data flash, but the final data writed is not right.
The FMCLKD is configured and the flash global protection is clean.
I'm using this source code, from Processor Expert (based on algorithm of page 6-13 from "56F8300 Peripheral User Manual" ) :

/** The method programs 16-bit word to a flash memory.
 *
 * ===================================================================
 *     Method      :  procflash (bean IntFLASH)
 *
 * ===================================================================
 */
static byte procflash(dword address, word data, word command){
    if (iFsh1_Busy())                    /* Is a command in progress in any of the flash devices? */
        return ERR_BUSY;                 /* If yes then error */
       
    ClearFlags();                        /* Clear all flags */
    writeflash(address, data);           /* Write given data to the flash memory */
    setReg(FMCMD, command);              /* Write given command to FMCMD register */
    setReg(FMUSTAT, 0x80);               /* launch the command */
       
    if ((getRegBit(FMUSTAT,PVIOL))||(getRegBit(FMUSTAT,ACCERR))) /* Is protection violation or access error detected ? */
        return ERR_NOTAVAIL;             /* If yes then return the error */
    return fmErr;
}

/** The metohd writes block of data to a flash memory.
 *
 * ===================================================================
 *     Method      :  WriteBlock (bean IntFLASH)
 * ===================================================================
 */
static byte WriteBlock(dword Source, dword Dest, dword Count){
    register word i, sourceIndex, DataToWrite;
    register dword Addr, LastAddr, Size;
    register bool ByteFirst, ByteLast;

    fmErr = ERR_OK;
    Addr = (dword)Dest / 2;
    if ((dword)Dest % 2 > 0){
        ByteFirst = true;
    }else{
        ByteFirst = false;
    }

    LastAddr = (dword)Dest + Count;
   
    if (LastAddr % 2 > 0){
        ByteLast = true;
    }else{
        ByteLast = false;
    }
   
    LastAddr = (LastAddr - 1) / 2;
    Size = LastAddr - Addr + 1;
   
    if (OutOfRange(Addr,LastAddr)){        /* Is the address out of range? */
        return (ERR_RANGE);                 /* If yes then exit */
    }
   
    SelectRegBank();                     /* Select Data_Flash register bank */
    sourceIndex = 0;
   
    for (i = 0; i < Size; i++) {             /* For all given data */
        if ((i == 0) && (ByteFirst))
              DataToWrite = (readflash(Addr) & 0x00ff) + (((word)((byte *)(Source))[sourceIndex++]) << 8);
        else if ((i == Size - 1) && (ByteLast))
              DataToWrite = (readflash(Addr + i) & 0xff00) + ((byte *)(Source))[sourceIndex];
        else{
            DataToWrite = ((byte *)Source)[sourceIndex++] + ((word)((byte *)(Source))[sourceIndex++] << 8);
        }
           
        if (readflash(Addr+i) != DataToWrite){
            /* Is the FLASH programming necessary? */
            fmErr = procflash(Addr+i, DataToWrite, PROGRAM); /* If yes write new data to Flash */
        }
       
        if (fmErr != ERR_OK) {               /* If an error occured then exit */
              return fmErr;
        }
    }
   
    if (IFsh1_Wait) {                    /* Is the flag set ? */
        while (getRegBit(FMUSTAT, CCIF) == 0) {} /* Wait to command complete */
        i = 0;
        sourceIndex = 0;
        if ((fmErr == ERR_OK) && (ByteFirst)) {
            i++;
            if ((readflash(Addr) >> 8) != ((byte*)Source)[sourceIndex++])
                fmErr = ERR_VALUE;
        }
       
        if (fmErr == ERR_OK) {
              for (; i < Size - ByteLast; i++) { /* Check all given data were written good */
                if (readflash(Addr+i) != (((byte*)Source)[sourceIndex++]) + ((word)((byte*)Source)[sourceIndex++] << 8)) {
                      fmErr = ERR_VALUE;    // <-------------- is returning for HERE!!!!
                      break;
                }
              }
        }
       
        if ((fmErr == ERR_OK) && (ByteLast)) {
              if ((byte)(readflash(Addr+i)) != ((byte*)Source)[sourceIndex])
                fmErr = ERR_VALUE;
        }
    }
   
    if (PgEvent > 0)
        setRegBit(FMCR, CCIE);              /* Enable interrupt */
   
    return fmErr;
}

When my program is running, the data is writed and the procflash() function return OK, but when the verification is performed, the WriteBlock() function return ERR_VALUE (view comment in source code), because the data readed from flash is not equal to desired data.

I need Your help.

Best regards
Labels (1)
Tags (1)
0 Kudos
3 Replies

457 Views
ProcessorExpert
Senior Contributor III
Hello,
could you please be more specific, which CPU are you using, how the IntFlash bean is configured and how do you use the beans methods? Attached project would be great...
 
best regards
 
Petr Hradsky
Processor Expert Support Team
UNIS
0 Kudos

457 Views
frbetelu
Contributor I

Hello,
I'm using a 56f8323 EVM.
I send you one basic test project.

Thank you,

Fernando

 

fmTest1.zip

Message Edited by t.dowe on 2009-10-29 09:54 AM
0 Kudos

457 Views
ProcessorExpert
Senior Contributor III
I'm sorry for the delay. We have tried your project on the hardware and we have reproduced the behavior. After an analysis, we have found what couses the problem.
Your project doesn't use a right write method which is configured by the "Write method" property of the IntFlash bean. Your project has set just "Write" method, which expects that the memory is erased. This doesn't work in most cases when the flash is pre-initialized by some constants. In such case, it's necessary to use "SAFE WRITE" method, which erases the content and keeps surrounding data within the sector (sector is 256 words on the 56F8323).

Note: Please note that with SAFE WRITE the bean saves the content into RAM before erasing the sector and writes data back afterwards. However, it's not guaranteed that the whole sector will not be lost for example due to power loss after erasing. So if the user does have some imporant constants in data flash, he should back-up them somehow (like storing them twice in different sectors and checking their integrity.)

Here is a "Write method" property description from IntFlash bean help :

The Write method - Method for writing into FLASH memory.

Possible choices: WRITE - write only value into FLASH without any tests. Only erased bits can be changed. For a reverse change a different method using erasing FLASH must be used.
DESTRUCTIVE WRITE - actual sector is erased if necessary (without any data backup) and after that data is written into the FLASH.
SAFE WRITE - if the requested FLASH area is not empty (erased) affected FLASH sectors are saved to data RAM and the FLASH is erased, after that the previously saved data, except wanted position, are written back into the FLASH.
0 Kudos