Skip to main content
Visitor II
February 19, 2009
Question

Problem reading OTP Memory in ARM STR912FW44

  • February 19, 2009
  • 4 replies
  • 1416 views
Posted on February 19, 2009 at 04:18

Problem reading OTP Memory in ARM STR912FW44

    This topic has been closed for replies.

    4 replies

    rickardAuthor
    Visitor II
    May 17, 2011
    Posted on May 17, 2011 at 09:57

    We are having some problems reading the OTP memory in ARM STR912FW44 rev H when running in bank 0.

    We use the function

    temp = FMI_ReadOTPData(indexAddress); where temp is a uint32 variable and indexAddres starts at 0.

    In 91x_fmi.h we have set:

    /* ========================================================================== */

    /* When bank 1 is remapped at address 0x0, decomment the following line */

    /* ========================================================================== */

    #define Remap_Bank_1

    /* Includes ------------------------------------------------------------------*/

    #include ''91x_map.h''

    /* Exported types ------------------------------------------------------------*/

    /* Exported constants --------------------------------------------------------*/

    /* FMI banks */

    #ifdef Remap_Bank_1

    #define FMI_BANK_0 ((*(vu32*)0x54000010) << 2) /* FMI Bank 0 */

    #define FMI_BANK_1 ((*(vu32*)0x5400000C) << 2) /* FMI Bank 1 */

    #else /* Remap Bank 0 */

    #define FMI_BANK_0 ((*(vu32*)0x5400000C) << 2) /* FMI Bank 0 */

    #define FMI_BANK_1 ((*(vu32*)0x54000010) << 2) /* FMI Bank 1 */

    #endif

    The problem is that instead of reading from OTP Memory we read the e59ff018 which is an OP code found at the beginning of both bank0 and bank1

    We have also tried to comment #define Remap_Bank_1 i.e //#define Remap_Bank_1 in 91x_fmi.h

    How do we read the OTP memory? I guess that the problem is that function FMI_ReadOTPData doesn’t try to write in bank1 (shall write 0x98 in bank1 to start reading from OTP) and that this is caused by wrong addressing of FMI_BANK_1 and the startup file. Please see the attached file startupBank0.s

    We will also need to read the OTP when running in bank1, please see startupBank1.s

    rickardAuthor
    Visitor II
    May 17, 2011
    Posted on May 17, 2011 at 09:57

    I fixed the problem when running in bank0. It is now possible to read OTP memory when running in bank0 by using the code:

    /* write a read OTP sector command */

    *(vu16 *)(PF_FMI_BANK1) = 0x98;

    /* Read the correspondent data */

    OTP_Data = (*(vu32*)(PF_FMI_BANK1 + address));

    /* Write a read array command */

    *(vu16 *)(PF_FMI_BANK1) = 0xFF;

    where PF_FMI_BANK1 = 0.

    However, when running in bank1 and trying the same code the cpu hangs. If I instead tries setting PF_FMI_BANK1 = 0x80000 (the other bank) I read the opcodes of a startup instead of the OTP memory.

    Is it not possible to read OTP memory when running in bank1??

    Or, is it something wrong in my startup file? (see attached startupBank1.s)

    Update: It is possible to read data from address 0 (opcodes of startup.s is read). It is the line *(vu16 *)(PF_FMI_BANK1) = 0x98; that hangs the cpu.

    Why does this line hang the cpu???

    [ This message was edited by: rickard.thorstensson on 18-02-2009 13:19 ]

    rickardAuthor
    Visitor II
    May 17, 2011
    Posted on May 17, 2011 at 09:57

    You gave me the answer I was afraid of.

    I am using GCC 4.1 and have tried to following code to put the function in ram:

    extern uint32 PF_ReadOTPDWORD(uint8 address) __attribute__ ((section (''data'')));

    uint32 PF_ReadOTPDWORD(uint8 address)

    {

    uint32 OTP_Data = 0x0;

    /* write a read OTP sector command */

    *(vu16 *)(PF_FMI_BANK1) = 0x98;

    /* Read the correspondent data */

    OTP_Data = (*(vu32*)(PF_FMI_BANK1 + address));

    /* Write a read array command */

    *(vu16 *)(PF_FMI_BANK1) = 0xFF;

    return OTP_Data;

    }

    However when calling the function, the cpu still hangs. I know that then function is executed but it still hangs at *(vu16 *)(PF_FMI_BANK1) = 0x98;

    Is something else I have to do?

    Visitor II
    May 17, 2011
    Posted on May 17, 2011 at 09:57

    You can't issue BANK1 commands (ie read OTP) while running your code from BANK1. You need to run from BANK0 or RAM. You can use the ''__ramfunc'' in IAR to put your function in RAM.

    The 91x_fmi.c example toy code (not worth calling a library!) and the FMI hardware are absolutely horrendous. I feel your pain.