目 录CONTENT

文章目录

链接文件学习(五):关键字使用方法

moke
2024-07-25 / 0 评论 / 0 点赞 / 28 阅读 / 0 字

概述

部分知识点概念上难以理解,本章节基于此部分根据Hightec内部的文档《tricore-ld》进行自己的认知分析一下。

分析条目

VMA与LMA

        每一个装载或者允许装载的输出段都有两个地址,一个是VMA virture memory address 虚拟存储器地址,当程序正在执行的时候运行的是此地址,另一个是LMA load memory address 加载存储器地址,这是加载段的地址。

        大部分情况下这两个地址是一样的,举个不一样的例子,当数据段在ROM,程序开始启动的时候Copy进RAM。这种情况下ROM是LMA,RAM地址是VMA。

各代码部分含义
    .text 代码段
.rodata    只读数据
.data 可读写初始化数据存放位置
.bss可读写未初始化数据存放位置

PROVIDE

        目前阶段个人的理解,标识一个地址的位置,可以是开始,或者结束,这个标识符假设在程序里面出现会占用字节,假设程序里面没有定义就不占用字节。有一个例外情况要是声明的是一个数组,那么也是不占用字节的。

extern uint32  TargetAddress;

extern uint32  TargetAddress[];
实用方法例如:

        PROVIDE(__USER_CODE_START = .)

ABSOLUTE

        absolute 相对于其父元素的位置放置一个元素并改变它周围的布局

简单的例子

        AAAAA = .

       BBBBB = ABSOLUTE(.)

假设AAAAA 的地址为0x100 而且A不占用字节,那么BBBBB也为0x100的地址

LOADADDR 

        返回相对的虚拟地址段和指令ADDR类似,有AT指令进行指向的时候又是不一样的。

例如:

        CCCCC = LOADADDR (.FLSLOADERRAMCODE),展现的是个ROM地址。

AT

AT是在上电启动的时候把ROM内容Copy到RAM,个人理解分析一下内容

section :ALIGN(4)

{

        .....

} > RAM_ADDRESS  > AT > ROM_ADDRESS

RAM_ADDRESS  > AT > ROM_ADDRESS 两层含义

第一步:在链接阶段代码或者数据放置到ROM_ADDRESS

第二部:RAM_ADDRESS与ROM_ADDRESS通过AT关联起来,在第一步里面已经执行的放置ROM操作,在单片机上电开始阶段,执行ROM_ADDRESS 复制进RAM操作,这样子理解为什么RAM_ADDRESS能精准的找到ROM_ADDRESS

注意点1

        有时候针对不同的供应商,最底层的Memmap.h可能最终包含的不同,这个时候我们可以定义多个段来进行兼容。

举例:

CPU2_TRUSTED_DATA :ALIGN(4)

{

        *(.data.cpu2_Trusted_16*);

        *(.data.cpu2_16*);

}> CPU2_TRUSTED AT >PFLASH_CPU2_PRIVIDE

        在上述里面    *(.data.cpu2_Trusted_16*);与     *(.data.cpu2_16*);其实可以表达相同的含义,但是假设针对ETAS与MCAL不同的供应商可能表达的不一样,故设置了两个。

x > AT > Y = 0

举例:

        FLS_AC_ERASE :ALIGN(4)

{

        *(.FLS_AC_ERASE);

        . = ALIGN(4);

} > CPU0_PSPR_FLS_ERASE AT > PFLASH0_FLS_ERASE = 0

        里面的= 0;含义是填充0,也可以是0xFF,但是0xFF有时候代表有用途,这样就比较麻烦,所以一般就是等于0比较合适。

*16*含义

可以是xxx16xxx这样子的组合。

 RODATA :ALIGN(4)

{

        *(.rodata.*16*);

        . = ALIGN(4);

}>  PFLASH0_CONST

        例如电机里面的标定数据 就存放在 *(.rodata*) 默认的const数据是存放在*(.rodata*)里面的,注意一个地方 *(.rodata*)包含 *(.rodata.*)。

KEEP 

.inttab :

{

        KEEP(*(.inttab));

        *(*.ostrap);

}> PFLASH0_TRAP_INT_TAB

        .o在链接时使用,一旦链接完就会丢弃,但是使用了KEEP,链接的整个过程均可以使用,也有一种说法是防止优化编译。

博主关闭了所有页面的评论