This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

[参考译文] TMS320F28379D:关于在28379D 上使用闪存 API 的问题-在对闪存进行编程时填充未填充的字节?

Guru**** 1456330 points
请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

https://e2e.ti.com/support/microcontrollers/c2000-microcontrollers-group/c2000/f/c2000-microcontrollers-forum/1348653/tms320f28379d-question-of-using-flashapi-on-28379d---pad-the-unfilled-bytes-when-programming-flash

器件型号:TMS320F28379D

大家好、

我正致力于在79d 器件上使用自定义引导加载程序、其中涉及将获取的应用程序映像连接到片上闪存。

阅读 spru513p 指南后、我采用 Intel 格式作为要解析并传输到79d 的十六进制文件、启动固件将把派生的字节写入或写入闪存。  

当从十六进制格式映像数据填充字节以写入闪存时、就会出现问题。 十六进制的某些行未满填充128位、最后部分行未归档。 根据2837xD 器件上 FlashAPI 指南 spnu629a、该指南指出:

Fapi_AutoEccGeneration – This mode will program the supplied data in Flash along with automatically
generated ECC. The ECC is calculated for every 64-bit data aligned on a 64-bit memory boundary.
Hence, when using this mode, all the 64 bits of the data should be programmed at the same time for a
given 64-bit aligned memory address. Data not supplied is treated as all 1s (0xFFFF).

因此,我的解释是,如果十六进制数据中有未填充的字节,我应该填充全1 (例如 FF )。 以下是我从应用十六进制文件获取的一些示例行:

示例1  :140BA800003301000254880A10F0540A910A0000A80A000072

因此、根据 Intel 十六进制格式定义、不包括前8个十六进制数字(字节数、地址、类型)和后2个十六进制(CRC)、此行具有14即20字节、写入闪存的字节是 (以每128位(即8 * 16位十六进制)对下方的表示形式进行标记)

"0033 0100 0254 880A 10F0 540A 910A"

"0000 A80A 0000 FFFF FFFF FFFFFFFFF"

示例2   :1F0B8800061F22C029681A4AA8A5A4CDA6034A5A0622052EC4021A0625002500010606AF

该行具有1F、即31字节、因此我的解释是

"061F 22C0 2968 1A4A A8A5 A4CD A603 4A5A"

"0622 052E C402 1A06 2500 2500 0106 06FF"

带有背景颜色的 FF 是应该写入闪存的内容。  

请不要麻烦详细的数字,我对 FF 填充部件的解释是否正确?

提前感谢您的建议。

此致、

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    除此之外、我还有关于 hex 文件与 Flash 存储器中字节内容之间的通信方式的问题。

    我从一个 ledblink 项目生成了 Intel hex、并且还在 Exact 项目的调试模式下在 CCS 中打开"Memory"视图。  

    下图显示了这两种配置:

    左侧是生成的十六进制文件。 以第二行(whch 包含数据)为例:

    :020000004A892B

    根据 Intel hex 文件格式的定义、我的理解是、从开始到结束、02表示字节数;0000是地址(与第一行中的基地址合并、形成32位地址000A0000); 然后、00表示数据记录、4A 89是2字节的数据、2B 是 CRC。

    在"Memory"视图中、正如您在 RHS 中看到的、在地址0x0000A000上、它显示  

    00 4A 0b 89 .

    我相信4A 89是 Hex 文件行中反映的数据、但我不知道为什么00、0B 在那里、以及它们来自何处或被记录。 如果 继续查看.hex 其余行中的数据、 并将其与存储器视图进行比较、它也是相同的模式。

    如何理解这一点、以及如何正确地对闪存进行编程? (我假设已编程的闪存应该与存储器视图中显示的内容完全匹配、如果我错、请更正我。)

    感谢您提供建议。

    此致、

    魏  

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    Wei、

    是的、如果您在使用 Fapi_Auto EccGeneration 时将程序命令的数据长度传递为8、则应将每个部分128位存储器对齐的数据填充为全1。   

    希望所有已初始化的段都使用 align (8)与链接器命令文件中的128位地址对齐。

    谢谢。此致、
    瓦姆西

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    谢谢 Vamsi。  

    此外、我意识到生成的十六进制文件实际上有2个: app.hex 和 app.I01 (以 Intel hex 为例)。 通过将内容与"Memory"视图进行比较、很容易会发现这2个文件分别包含高字节/低字节。  

    不确定是否错过了一些内容、十六进制输出格式选项中是否有一些设置可以让 CCS 仅生成1个十六进制文件来包含图像、而不是拆分成2个文件?

    此致、

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Wei:

    您确切用于生成 hex 文件的命令是什么?

    谢谢。此致、
    瓦姆西

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    嘿、Vamsi、

    我使用 CCS 内置生成了 hex 文件:

    然后、在"Project Explorer"窗格下找到了 文件夹:(.hex 和.I01)

    此致、

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Wei:

    我们下周同一时间再见。

    谢谢。此致、

    瓦姆西

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Wei:

    链接器命令文件中是否有 page0和 page1?   C2000十六进制实用程序为 page0和 page1生成单独的十六进制文件。 如果要生成单个十六进制文件、请将链接器命令文件中任何已初始化的段映射到 page0存储器而不是 page1。

    谢谢。此致、
    瓦姆西

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    谢谢 Vamsi。 是的、链接器命令文件中都使用了 page0和 page1。

    2个单独的 hex 文件现在对我来说不是问题。 但对于我的法庭之友、例如、我的链接器命令文件的 page0/1分配如下所示:

    如果我要生成一个十六进制文件、我需要将当前在第1页中分配的所有段都放入第0页中的 RAM/闪 存、例如:

      .stack        :> RAMM1    页面= 1

    修改如下内容

      .stack        :> RAMGS0   页面= 0  

    我的理解是否正确? 谢谢。

    此致、

    MEMORY
    {
    PAGE 0:    /* Program Memory */
              /* Memory (RAM/FLASH) blocks can be moved to PAGE1 for data allocation */
              /* BEGIN is used for the "boot to Flash" bootloader mode   */
    
       BEGIN           	: origin = 0x080000, length = 0x000002
       RAMM0           	: origin = 0x000122, length = 0x0002DE
       RAMD0           	: origin = 0x00B000, length = 0x000800
       RAMLS03          : origin = 0x008000, length = 0x002000
    /*	RAMLS1           : origin = 0x008800, length = 0x000800
        RAMLS2           : origin = 0x009000, length = 0x000800
        RAMLS3           : origin = 0x009800, length = 0x000800 */
       RAMLS4      		: origin = 0x00A000, length = 0x000800
       RESET           	: origin = 0x3FFFC0, length = 0x000002
      
    	/* Flash sectors */
       FLASHA           : origin = 0x080002, length = 0x001FFE	/* on-chip Flash */
       FLASHB           : origin = 0x082000, length = 0x002000	/* on-chip Flash */
        ...
    ....
    
    PAGE 1 :   /* Data Memory */
             /* Memory (RAM/FLASH) blocks can be moved to PAGE0 for program allocation */
    
       BOOT_RSVD       : origin = 0x000002, length = 0x000121     /* Part of M0, BOOT rom will use this for stack */
       RAMM1           : origin = 0x000400, length = 0x0003F8     /* on-chip RAM block M1 */
    //   RAMM1_RSVD      : origin = 0x0007F8, length = 0x000008     /* Reserve and do not use for code as per the errata advisory "Memory: Prefetching Beyond Valid Memory" */
        RAMD1           : origin = 0x00B800, length = 0x000800
    
        RAMLS5      : origin = 0x00A800, length = 0x000800
    
    	RAMGS0          : origin = 0x00C000, length = 0x001000
    	RAMGS1          : origin = 0x00D000, length = 0x001000
    	....
    	
    }
    
    SECTIONS
    {
    
       /* Allocate program areas: */
       .cinit              : > FLASHD      PAGE = 0
       .pinit              : > FLASHD,     PAGE = 0
       .text               : >> FLASHD | FLASHE      PAGE = 0
       codestart           : > BEGIN	PAGE = 0
    
    #ifdef __TI_COMPILER_VERSION__
        #if __TI_COMPILER_VERSION__ >= 15009000
            GROUP
            {
                .TI.ramfunc
                { -l F021_API_F2837xD_FPU32.lib}
    
            } LOAD = FLASHD,
              RUN  = RAMLS03,
              LOAD_START(_RamfuncsLoadStart),
              LOAD_SIZE(_RamfuncsLoadSize),
              LOAD_END(_RamfuncsLoadEnd),
              RUN_START(_RamfuncsRunStart),
              RUN_SIZE(_RamfuncsRunSize),
              RUN_END(_RamfuncsRunEnd),
              PAGE = 0
        #else
            GROUP
            {
                ramfuncs
                { -l F021_API_F2837xD_FPU32.lib}
    
            } LOAD = FLASHD,
              RUN  = RAMLS03,
              LOAD_START(_RamfuncsLoadStart),
              LOAD_SIZE(_RamfuncsLoadSize),
              LOAD_END(_RamfuncsLoadEnd),
              RUN_START(_RamfuncsRunStart),
              RUN_SIZE(_RamfuncsRunSize),
              RUN_END(_RamfuncsRunEnd),
              PAGE = 0
        #endif
    #endif
    
       /* Allocate uninitalized data sections: */
       .stack              : > RAMM1       PAGE = 1
       .ebss               : >> RAMLS5 | RAMGS0 | RAMGS1       PAGE = 1
       .esysmem            : > RAMLS5       PAGE = 1
    
       /* Initalized sections go in Flash */
       .econst             : >> FLASHF | FLASHG       PAGE = 0
       .switch             : > FLASHD      PAGE = 0
    
       .reset              : > RESET,     PAGE = 0, TYPE = DSECT /* not used, */
    
       Filter_RegsFile     : > RAMGS0,	   PAGE = 1
    
       SHARERAMGS0		: > RAMGS0,		PAGE = 1
       SHARERAMGS1		: > RAMGS1,		PAGE = 1
    
       /* Flash Programming Buffer */
       BufferDataSection : > RAMD1, PAGE = 1, ALIGN(8)
    
    }

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Wei:

    C2000存储器是统一存储器。  不需要 page0和 page1。  您可以在 Page0中定义所有存储器、如果需要、使 page1保持空。

    Page0/Page1概念由于旧件而被搁置。

    谢谢。此致、

    瓦姆西