实例详解——编译器命令#pragma section作用于函数时作用域是否覆盖到其子函数
在之前的博客【链接脚本(Linker Script)应用实例(一)使用copy table将函数载入到RAM中运行】中,我们第一步使用#pragma section命令将PFlashProgram函数存储至程序段.flash_driver,具体程序如下:
#pragma section ".flash_driver" ax
void PFlashProgram( uint32 flash, uint32 addr, uint32 word_l, uint32 word_u )
{
uint32 load_cnt;
uint16 endinitSfty_pw = IfxScuWdt_getSafetyWatchdogPasswordInline();
IfxFlash_enterPageMode(addr);
/* wait until unbusy */
IfxFlash_waitUnbusy(flash, IfxFlash_FlashType_P0);
/* write 32 bytes (8 doublewords) into assembly buffer */
; load_cnt < ; load_cnt++)
{
IfxFlash_loadPage2X32(addr, word_l, word_u);
}
/* write page */
IfxScuWdt_clearSafetyEndinitInline(endinitSfty_pw);
IfxFlash_writePage(addr);
IfxScuWdt_setSafetyEndinitInline(endinitSfty_pw);
/* wait until unbusy */
IfxFlash_waitUnbusy(flash, IfxFlash_FlashType_P0);
}
#pragma section
编译之后的map文件如下,可以看到PFlashProgram函数生成的程序段大小为280字节。下面对函数的内容进行调整后重新编译,以验证将PFlashProgram函数存储到.flash_driver程序段时是否同时也将IfxFlash_enterPageMode、IfxFlash_waitUnbusy及IfxFlash_loadPage2X32等子函数同时存储到该段。这个问题之所以值得关注,是因为若不将其子函数也存储到该段,子函数将默认存储在ROM(Flash)中,那么PFlashProgram函数执行到其子函数时将从Flash而不是RAM中取指令。由于TC297不支持Flash操作函数对其所在的Flash进行擦写(Flash大多都具有这种特性)(Flash操作函数必须在RAM中或另一个Flash Bank中运行从而执行擦写操作),PFlashProgram函数无法成功执行对PFlash的写入操作。另外,了解#pragma section命令的这个特性也有助于程序员对代码存储与执行情况的掌握。
Linker version: GNU ld version (GNU Binutils) 2.20 (TriCore) using BFD version (GNU Binutils) 2.20 (v2.3), Tool Version v2.7 Name of linker executable: c:/hightec/toolchains/tricore/v4.9.1.0-infineon-2.0/bin/../lib/gcc/tricore/4.9.4/../../../../tricore/bin/ld.exe Date of link run: Thu Sep 05 10:42:28 2019 Name of linker map file: Flash_test.map >>> Symbols (global (S = g) and static (S = l); sorted by address) ============================================================================================================================================================ Start End Size S Name Memory O-Sec I-Sec Input object ============================================================================================================================================================ g __TRICORE_DERIVATE_MEMORY_MAP__ *ABS* *ABS* *ABS* *ABS* g LCF_ISTACK0_SIZE *ABS* *ABS* *ABS* *ABS* g LCF_ISTACK1_SIZE *ABS* *ABS* *ABS* *ABS* g LCF_ISTACK2_SIZE *ABS* *ABS* *ABS* *ABS* g LCF_HEAP_SIZE *ABS* *ABS* *ABS* *ABS* g LCF_USTACK0_SIZE *ABS* *ABS* *ABS* *ABS* g LCF_USTACK1_SIZE *ABS* *ABS* *ABS* *ABS* g LCF_USTACK2_SIZE *ABS* *ABS* *ABS* *ABS* ...................... g __TRAPTAB_CPU2 pfls0 .traptab_tc2 .traptab_tc2 Flash_test.elf g IfxCpu_Trap_vectorTable1 pfls0 .traptab_tc1 .traptab_cpu1 0_Src\4_McHal\Tricore\Cpu\Trap\IfxCpu_Trap.o g LCF_TRAPVEC1_START *ABS* *ABS* *ABS* *ABS* g __TRAPTAB_CPU1 pfls0 .traptab_tc1 .traptab_tc1 Flash_test.elf g _SMALL_DATA4_ *ABS* *ABS* *ABS* *ABS* g __A9_MEM *ABS* *ABS* *ABS* *ABS* g PFlashProgram psram_local .code2ram .flash_driver 0_Src\0_AppSw\Tricore\Demo_Illd\FlashDemo.o
(1)首先注释掉与Flash操作相关的5个子函数,然后重新编译,查看map文件。可见PFlashProgram函数产生的程序段大小变为136字节,这是否说明这5个Flash操作函数对应的程序段大小为144(280-136)字节呢?我们继续进行测试
#pragma section ".flash_driver" ax
void PFlashProgram( uint32 flash, uint32 addr, uint32 word_l, uint32 word_u )
{
uint32 load_cnt;
uint16 endinitSfty_pw = IfxScuWdt_getSafetyWatchdogPasswordInline();
// IfxFlash_enterPageMode(addr);
/* wait until unbusy */
// IfxFlash_waitUnbusy(flash, IfxFlash_FlashType_P0);
/* write 32 bytes (8 doublewords) into assembly buffer */
; load_cnt < ; load_cnt++)
{
// IfxFlash_loadPage2X32(addr, word_l, word_u);
}
/* write page */
IfxScuWdt_clearSafetyEndinitInline(endinitSfty_pw);
// IfxFlash_writePage(addr);
IfxScuWdt_setSafetyEndinitInline(endinitSfty_pw);
/* wait until unbusy */
// IfxFlash_waitUnbusy(flash, IfxFlash_FlashType_P0);
}
#pragma section
Linker version: GNU ld version (GNU Binutils) 2.20 (TriCore) using BFD version (GNU Binutils) 2.20 (v2.3), Tool Version v2.7 Name of linker executable: c:/hightec/toolchains/tricore/v4.9.1.0-infineon-2.0/bin/../lib/gcc/tricore/4.9.4/../../../../tricore/bin/ld.exe Date of link run: Thu Sep 05 18:34:08 2019 Name of linker map file: Flash_test.map >>> Symbols (global (S = g) and static (S = l); sorted by address) ============================================================================================================================================================ Start End Size S Name Memory O-Sec I-Sec Input object ============================================================================================================================================================ g __TRICORE_DERIVATE_MEMORY_MAP__ *ABS* *ABS* *ABS* *ABS* g LCF_ISTACK0_SIZE *ABS* *ABS* *ABS* *ABS* g LCF_ISTACK1_SIZE *ABS* *ABS* *ABS* *ABS* g LCF_ISTACK2_SIZE *ABS* *ABS* *ABS* *ABS* .......... g __TRAPTAB_CPU1 pfls0 .traptab_tc1 .traptab_tc1 Flash_test.elf g _SMALL_DATA4_ *ABS* *ABS* *ABS* *ABS* g __A9_MEM *ABS* *ABS* *ABS* *ABS* g PFlashProgram psram_local .code2ram .flash_driver 0_Src\0_AppSw\Tricore\Demo_Illd\FlashDemo.o
现在,我们注释掉5个Flash操作函数以外的代码,map文件如下。可以看到PFlashProgram的大小变为146字节而不是之前推测的144字节。为什么多出2字节呢?我们接下来将整个函数体内部的语句全部注释掉试试,看看函数的“框架”占用多大空间。
#pragma section ".flash_driver" ax
void PFlashProgram( uint32 flash, uint32 addr, uint32 word_l, uint32 word_u )
{
// uint32 load_cnt;
// uint16 endinitSfty_pw = IfxScuWdt_getSafetyWatchdogPasswordInline();
IfxFlash_enterPageMode(addr);
/* wait until unbusy */
IfxFlash_waitUnbusy(flash, IfxFlash_FlashType_P0);
/* write 32 bytes (8 doublewords) into assembly buffer */
// for (load_cnt = 0; load_cnt < 4; load_cnt++)
// {
IfxFlash_loadPage2X32(addr, word_l, word_u);
// }
/* write page */
// IfxScuWdt_clearSafetyEndinitInline(endinitSfty_pw);
IfxFlash_writePage(addr);
// IfxScuWdt_setSafetyEndinitInline(endinitSfty_pw);
/* wait until unbusy */
IfxFlash_waitUnbusy(flash, IfxFlash_FlashType_P0);
}
#pragma section
Linker version: GNU ld version (GNU Binutils) 2.20 (TriCore) using BFD version (GNU Binutils) 2.20 (v2.3), Tool Version v2.7 Name of linker executable: c:/hightec/toolchains/tricore/v4.9.1.0-infineon-2.0/bin/../lib/gcc/tricore/4.9.4/../../../../tricore/bin/ld.exe Date of link run: Thu Sep 05 18:45:58 2019 Name of linker map file: Flash_test.map >>> Symbols (global (S = g) and static (S = l); sorted by address) ============================================================================================================================================================ Start End Size S Name Memory O-Sec I-Sec Input object ============================================================================================================================================================ g __TRICORE_DERIVATE_MEMORY_MAP__ *ABS* *ABS* *ABS* *ABS* g LCF_ISTACK0_SIZE *ABS* *ABS* *ABS* *ABS* g LCF_ISTACK1_SIZE *ABS* *ABS* *ABS* *ABS* g LCF_ISTACK2_SIZE *ABS* *ABS* *ABS* *ABS* .......... g __TRAPTAB_CPU1 pfls0 .traptab_tc1 .traptab_tc1 Flash_test.elf g _SMALL_DATA4_ *ABS* *ABS* *ABS* *ABS* g __A9_MEM *ABS* *ABS* *ABS* *ABS* g PFlashProgram psram_local .code2ram .flash_driver 0_Src\0_AppSw\Tricore\Demo_Illd\FlashDemo.o
由map文件可以看到,这个空的函数大小为2字节。到这里我们知道函数总大小为280字节,其中函数“框架”占2字节,5个Flash操作函数占144字节,其他语句和函数占134字节。
到此,我们可以得出本篇博文最重要的结论:#pragma section命令将一个函数存储到程序段时,会将其调用的子函数也一起存储到该段中。
#pragma section ".flash_driver" ax
void PFlashProgram( uint32 flash, uint32 addr, uint32 word_l, uint32 word_u )
{
// uint32 load_cnt;
// uint16 endinitSfty_pw = IfxScuWdt_getSafetyWatchdogPasswordInline();
// IfxFlash_enterPageMode(addr);
/* wait until unbusy */
// IfxFlash_waitUnbusy(flash, IfxFlash_FlashType_P0);
/* write 32 bytes (8 doublewords) into assembly buffer */
// for (load_cnt = 0; load_cnt < 4; load_cnt++)
// {
// IfxFlash_loadPage2X32(addr, word_l, word_u);
// }
/* write page */
// IfxScuWdt_clearSafetyEndinitInline(endinitSfty_pw);
// IfxFlash_writePage(addr);
// IfxScuWdt_setSafetyEndinitInline(endinitSfty_pw);
/* wait until unbusy */
// IfxFlash_waitUnbusy(flash, IfxFlash_FlashType_P0);
}
#pragma section
Linker version: GNU ld version (GNU Binutils) 2.20 (TriCore) using BFD version (GNU Binutils) 2.20 (v2.3), Tool Version v2.7 Name of linker executable: c:/hightec/toolchains/tricore/v4.9.1.0-infineon-2.0/bin/../lib/gcc/tricore/4.9.4/../../../../tricore/bin/ld.exe Date of link run: Thu Sep 05 18:52:56 2019 Name of linker map file: Flash_test.map >>> Symbols (global (S = g) and static (S = l); sorted by address) ============================================================================================================================================================ Start End Size S Name Memory O-Sec I-Sec Input object ============================================================================================================================================================ g __TRICORE_DERIVATE_MEMORY_MAP__ *ABS* *ABS* *ABS* *ABS* g LCF_ISTACK0_SIZE *ABS* *ABS* *ABS* *ABS* g LCF_ISTACK1_SIZE *ABS* *ABS* *ABS* *ABS* g LCF_ISTACK2_SIZE *ABS* *ABS* *ABS* *ABS* .......... g __TRAPTAB_CPU1 pfls0 .traptab_tc1 .traptab_tc1 Flash_test.elf g _SMALL_DATA4_ *ABS* *ABS* *ABS* *ABS* g __A9_MEM *ABS* *ABS* *ABS* *ABS* g PFlashProgram psram_local .code2ram .flash_driver 0_Src\0_AppSw\Tricore\Demo_Illd\FlashDemo.o
实例详解——编译器命令#pragma section作用于函数时作用域是否覆盖到其子函数的更多相关文章
- 30个实例详解TOP命令
Linux中的top命令显示系统上正在运行的进程.它是系统管理员最重要的工具之一.被广泛用于监视服务器的负载.在本篇中,我们会探索top命令的细节. AD: Linux中的top命令显示系统上正在运行 ...
- (转)30 个实例详解 TOP 命令
原文:http://blog.jobbole.com/112873/?utm_source=blog Linux中的top命令显示系统上正在运行的进程.它是系统管理员最重要的工具之一.被广泛用于监视服 ...
- 实例详解TOP命令
Linux中的top命令显示系统上正在运行的进程.它是系统管理员最重要的工具之一.被广泛用于监视服务器的负载.在本篇中,我们会探索top命令的细节.top命令是一个交互命令.在运行top的时候还可以运 ...
- 我的书籍《深入解析Java编译器:源码剖析与实例详解》就要出版了
一个十足的技术迷,2013年毕业,做过ERP.游戏.计算广告,在大公司呆过,但终究不满足仅对技术的应用,在2018年末离开了公司,全职写了一本书<深入解析Java编译器:源码剖析与实例详解> ...
- Linux下rz命令使用的实例详解
Linux中rz命令和sz命令都可用于文件传输,而rz命令主要用于文件的上传,下面将通过几个实例来给大家详细介绍下Linux下rz命令的用法,一起来学习下吧. rz命令可以批量上传文件,当然也可上传单 ...
- Linux的find命令实例详解和mtime ctime atime
这次解释一下三个Linux文件显示的三个时间,然后展示一下find命令的各个功能 在linux操作系统中,每个文件都有很多的时间参数,其中有三个比较主要,分别是ctime,atime,mtime mo ...
- Linux备份数据库,mysqldump命令实例详解
mysqldump是mysql数据库中备份工具,用于将MYSQL服务器中的数据库以标准的sql语言的方式导出,并保存到文件中. 语法: mysqldump (选项) 选项: --add-drop-ta ...
- zookeeper使用详解(命令、客户端、源码)
1. zookeeper使用详解(命令.客户端.源码) 1.1. 前言 zookeeper我们常用来做分布式协调中间件,很多时候我们都接触不到它的原理和用法,我对他的了解也仅限于知道它可以做分布式 ...
- 【python3+request】python3+requests接口自动化测试框架实例详解教程
转自:https://my.oschina.net/u/3041656/blog/820023 [python3+request]python3+requests接口自动化测试框架实例详解教程 前段时 ...
随机推荐
- ubuntu16安装docker环境详细说明
安装前说明: 本文将介绍在ubuntu16.04系统下安装和升级docker.docker-compose.docker-machine. docker:有两个版本:docker-ce(社区版)和do ...
- VirtualBox6安装CentOS7设置静态IP
安装virtualbox后安装centos7, 这里就不在赘述了, 网上有很多教程 先关闭虚拟机, 按照如下设置配置网络 这里需要使用双网卡, 我们在开启第二个网卡, 如下所示 之后开启虚拟机, 进行 ...
- 【WPF on .NET Core 3.0】 Stylet演示项目 - 简易图书管理系统(3) - 使用Conductor切换页面
前两章中, 我们已经实现了这个图书管理系统的登录窗口, 并实施了完善的单元测试. 该是时候回过头来关注我们的主窗口了. 一个功能丰富的系统一般会有多个页面, 我们图书管理系统虽然是"简易&q ...
- 开源跳板机(堡垒机)系统 Jumpserver安装教程(带图文)
环境 系统: CentOS 7 IP: 192.168.244.144 关闭 selinux 和防火墙 # CentOS 7 $ setenforce 0 # 可以设置配置文件永久关闭 $ syste ...
- jvm与程序的生命周期
yls 2019/11/5 java虚拟机结束生命周期的情况: 执行了System.exit(); 程序正常运行结束 程序在执行过程中遇到异常或错误而异常终止 由于操作系统出现错误而导致jvm进程终止 ...
- 018.Kubernetes二进制部署插件coredns
一 修改配置文件 1.1 下载解压 [root@k8smaster01 ~]# cd /opt/k8s/work/kubernetes/ [root@k8smaster01 kubernetes]# ...
- lqb 基础练习 回文数
基础练习 回文数 时间限制:1.0s 内存限制:512.0MB 问题描述 1221是一个非常特殊的数,它从左边读和从右边读是一样的,编程求所有这样的四位十进制数. 输出格式 按从小到大的顺 ...
- pat 1050 String Subtraction(20 分)
1050 String Subtraction(20 分) Given two strings S1 and S2, S=S1−S2 is defined to be the ...
- 力扣(LeetCode)寻找数组的中心索引 个人题解
给定一个整数类型的数组 nums,请编写一个能够返回数组“中心索引”的方法. 我们是这样定义数组中心索引的:数组中心索引的左侧所有元素相加的和等于右侧所有元素相加的和. 如果数组不存在中心索引,那么我 ...
- 领扣(LeetCode)N叉树的层序遍历 个人题解
给定一个 N 叉树,返回其节点值的层序遍历. (即从左到右,逐层遍历). 例如,给定一个 3叉树 : 返回其层序遍历: [ [1], [3,2,4], [5,6] ] 说明: 树的深度不会超过 100 ...