Keil sct分散加载文件

首先介绍几个概念:

1.ARM映像文件

ARM映像文件是一个层次性结构的文件,其中包含了域(region)、输出段(output section)和输入段(input section)。各部分关系如下:

  • 一个映像文件由一个或多个域组成
  • 每个域包含一个或多个输出段
  • 每个输出段包含一个或多个输入段
  • 各输入段包含了目标文件中的代码和数据

输入段中包含了4类内容:代码、已经初始化的数据、未经初始化的存储区域、内容初始化成0的存储区域。每个输入段有相应的属性,可以为只读的(RO)、可读写的(RW)以及初始化成0的(ZI)。ARM连接器根据各输入段的属性将这些输入段分组,再组成不同的输出段以及域。

一个输出段中包含了一系列的具有相同的RO、RW和ZI属性的输入段。输出段的属性与其中包含的输入段的属性相同。在一个输出段内部,各输入段是按照一定的规则排序的,这个后面再补充。

一个域中包含了1~3个输出段,其中各输出段的属性各不相同。各输出段的排列顺序是由其属性决定的。其中,RO属性的输出段排在最前面,其次是RW属性的输出段,最后是ZI属性的输出段。一个域通常映射到一个物理存储器上,如ROM和RAM等。

2.ARM映像文件各组成部分的地址映射

分散加载机制允许为链接器指定映像的存储器映射信息,可实现对映像组件分组和布局的全面控制。分散加载通常仅用于具有复杂存储器映射的映像(尽管也可用于简单映像),也就是适合加载和执行时内存映射中的多个区是分散的情况。

要构建映像的存储器映射,链接器必须有:描述节如何分组成区的分组信息、描述映像区在存储器映射中的放置地址的放置信息。

分散加载区域分两类:

  • 加载区:该映像文件开始运行前存放的区域,即当系统启动或加载时应用程序存放的区域。
  • 执行区:映像文件运行时的区域,即系统启动后,应用程序进行执行和数据访问的存储器区域,系统在实时运行时可以有一个或多个执行块。

3.分散加载文件(即scatter file,后缀为.scf)

分散加载文件是一个文本文件,通过编写一个分散加载文件来指定ARM连接器在生成映像文件时如何分配RO,RW,ZI等数据的存放地址。如果不用SCATTER文件指定,那么ARM连接器会按照默认的方式来生成映像文件,一般情况下我们是不需要使用分散加载文件的。

但在某些场合,我们希望把某些数据放在指定的地址处,那么这时候SCATTER文件就发挥了非常大的作用。而且SCATTER文件用起来非常简单好用。

举个例子:比如像LPC2378芯片具有多个不连续的SRAM,通用的RAM是32KB,可是32KB不够用,我想把某个.C中的RW数据放在USB的SRAM中,那么就可以通过SCATTER文件来完成这个功能。

分散加载文件的语法:

load_region_name  start_address | "+"offset  [attributes] [max_size]
{
    execution_region_name  start_address | "+"offset  [attributes][max_size]
    {
        module_select_pattern  ["("
                                    ("+" input_section_attr | input_section_pattern)
                                    ([","] "+" input_section_attr | "," input_section_pattern)) *
                               ")"]
    }
} 

  • load_region:          加载区,用来保存永久性数据(程序和只读变量)的区域;
  • execution_region:     执行区,程序执行时,从加载区域将数据复制到相应执行区后才能被正确执行;
  • load_region_name:     加载区域名,用于“Linker”区别不同的加载区域,最多31个字符;
  • start_address:        起始地址,指示区域的首地址;
  • +offset:              前一个加载区域尾地址+offset 做为当前的起始地址,且“offset”应为“0”或“4”的倍数;
  • attributes:           区域属性,可设置如下属性:

PI       与地址无关方式存放;

RELOC    重新部署,保留定位信息,以便重新定位该段到新的执行区;

OVERLAY  覆盖,允许多个可执行区域在同一个地址,ADS不支持;

ABSOLUTE 绝对地址(默认);

  • max_size:                 该区域的大小;
  • execution_region_name:执行区域名;
  • start_address:        该执行区的首地址,必须字对齐;
  • +offset:              同上;
  • attributes:           同上;

PI          与地址无关,该区域的代码可任意移动后执行;

OVERLAY     覆盖;

ABSOLUTE    绝对地址(默认);

FIXED       固定地址;

UNINIT      不用初始化该区域的ZI段;

  • module_select_pattern: 目标文件滤波器,支持通配符“*”和“?”;

*.o匹配所有目标,* (或“.ANY”)匹配所有目标文件和库。

  • input_section_attr:    每个input_section_attr必须跟随在“+”后;且大小写不敏感;

RO-CODE 或 CODE

RO-DATA 或 CONST

RO或TEXT, selects both RO-CODE and RO-DATA

RW-DATA

RW-CODE

RW 或 DATA, selects both RW-CODE and RW-DATA

ZI 或 BSS

ENTRY, that is a section containing an ENTRY point.

FIRST,用于指定存放在一个执行区域的第一个或最后一个区域;

LAST,同上;

  • input_section_pattern: 段名;

汇编中指定段:

AREA    vectors, CODE, READONLY

C中指定段:

#pragma arm section [sort_type[[=]"name"]] [,sort_type="name"]*

sort_type:      code、rwdata、rodata、zidata

如果“sort_type”指定了但没有指定“name”,那么之前的修改的段名将被恢复成默认值。

#pragma arm section     // 恢复所有段名为默认设置。

应用:

#pragma arm section rwdata = "SRAM",zidata = "SRAM"

static OS_STK  SecondTaskStk[256];              // “rwdata”“zidata”将定位在“sram”段中。

#pragma arm section                                 // 恢复默认设置

样例:

简单存储器映射实例

LOAD_ROM 0x0000 0x8000       //Name of load region, Start address for load region, Maximum size of load region
{
    EXEC_ROM 0x0000 0x8000   //Name of first exec region, Start address for exec region, Maximum size of this region
    {
        *(+RO)               //Place all code and RO data into this exec region
    }
    RAM 0x10000 0x60000      //Start of second exec region
    {
        *(+RW, +ZI)          //Place all RW and ZI data into this exec region
    }
}

复杂存储器映射实例:

LOAD_ROM_1 0x0000                //Start address for first load region
{
    EXEC_ROM_1 0x0000            //Start address for first exec region
    {
        program1.o (+RO)         //Place all code and RO data from program1.o into this exec region
    }
    DRAM 0x18000 0x8000          //Start address for this exec region  Maximum size of this exec region
    {
        program1.o (+RW, +ZI)    //Place all RW and ZI data from program1.o into this exec region
    }
}

LOAD_ROM_2 0x4000                //Start address for second load region
{
    EXEC_ROM_2 0x4000
    {
        program2.o (+RO)         //Place all code and RO data from program2.o into this exec region
    }
    SRAM 0x8000 0x8000
    {
        program2.o (+RW, +ZI)    //Place all RW and ZI data from program2.o into this exec region
    }
}

具体格式描述请参考资料: 分散加载描述文件

一个具体的例子:

; *************************************************************
; *   Scatter-Loading Description File generated by uVision   *
; *************************************************************

LR_IROM1 0x00000000 0x00080000  {       ; 第一个加载域,名字是LR_IROM1,起始地址0x00000000 大小是0x00080000
    ER_IROM1 0x00000000 0x00080000  {   ; 第一个运行时域,名字是ER_IROM1 起始地址0x00000000 大小事0x00080000
        *.o (RESET, +First)             ; IAP第一阶段在FLASH中运行
        *(InRoot$$Sections)             ; All library sections that must be in a root region
        .ANY (+RO)                      ; .ANY与*功能相似,用.ANY可以把已经被指定的具有RW,ZI属性的数据排除
    }
    RW_IRAM1 0x10000000 0x00010000  {   ; RW data
        .ANY(+RW +ZI)
    }
    RW_SDRAM1 0xA0000000 0x00800000  {  ; RW data
        STARTUP_LPC177X_8X.o (HEAP)     ;HEAP用来定位堆栈的底
        *.LIB(+RW +ZI)
    }
}

Keil sct分散加载文件

时间: 2024-11-08 06:46:50

Keil sct分散加载文件的相关文章

ARM分散加载

在ARM开发当中,希望某些代码或者数据,在编译时放置在指定位置. 关键词:scf(scatter file分散加载文件) _attribute_属性  makefile编译 map文件 bin文件 1. 分散加载文件: bin文件的加载方式: code区+RO(read only data)+RW&ZI(已初始化的变量和未初始化的变量) 执行方式: code区+RO区:如果flash片上可执行,则可直接在该nor flash则可直接在该nor flash上直接执行.否则则要拷贝至RAM当中执行.

liteos分散加载(十四)

1. 概述 1.1 基本概念 分散加载是一种实现特定代码快速启动的技术,通过优先加载特定代码到内存,达到缩短从系统开机到特定代码执行的时间.可被应用来实现关键业务的快速启动. 嵌入式系统通过uboot加载flash上的镜像文件到内存并执行,而镜像文件本身可能较大,由于flash读取速度的限制,将镜像全部加载完再执行可能无法满足时间敏感的业务对启动速度的要求. 分散加载的思想是先加载部分镜像并执行,这部分镜像包含了时间敏感的关键业务,从而达到快速启动关键业务的效果. Huawei LiteOS的分

powershell-无法加载文件,因为在此系统中禁止执行脚本

写了一个powershell脚本测试脚本,结果执行的时候报错 $a=Get-Content C:\script.txt | select-string -pattern "ora"     if ( $a -eq  $null )     {                 write-host "error"      }     else     {          write-host "OK"      }  PS D:\> .\

链接加载文件gcc __attribute__ section

在阅读源代码的过程中,发现一个头文件有引用: /** The address of the first device table entry. */ extern device_t devices[]; /** The address after the last device table entry. */ extern device_t devices_end[]; /** The address of the first "driver_t". */ extern driver_

PowerShell 无法加载文件ps1,因为在此系统中禁止执行脚本

直接运行powershell时提示“无法加载文件ps1,因为在此系统中禁止执行脚本.有关详细信息,请参阅 "get-help about_signing". 主要是由于没有权限执行脚本. 运行get-help about_signing 提示了解执行策略输入 get-executionpolicy 显示 Restricted 即不允许执行任何脚本. 通过命令 get-help set-executionpolicy 可知有以下执行策略:<Unrestricted> | &l

安装SQL2008时遇到&quot;未能加载文件或&quot;file:///d:microsoft..sql.chainer.packagedata.dll&quot;或它的某个依赖项

安装SQL2008时遇到"未能加载文件或"file:///d:microsoft..sql.chainer.packagedata.dll"或它的某个依赖项,如下图所示 原因:SQL2008的安装路径过长. 解决:把SQL2008放到D盘或者E盘的根目录下再安装.

使用PSR-4配合composer autoload 自动加载文件夹

require 文件很麻烦,使用PSR-4搭配composer一次加载,终生受用. 感觉类似java中的import了,自己先记录一下最近理解的. 用composer管理自己的包吧 安装composer 这个不多赘述 英文版教程 中文版教程 PSR-4规范 PSR-4-autoloader 构建项目目录 |-project ? |-src ? |-View.php ? |-app ? |-Tools.php |-composer.json 上面路径的View.php在project/src/Vi

15.资源加载器,根据配置文件自动加载文件

前言 以前我想自己写一个加载器,用的时候加载,不用的时候再去掉,结果发现这种方式可能因为资源不统一在安卓上可能出现问题,所以搜集资料,弄成根据配置文件加载 思路 设定两个配置文件,screen,res,不同场景对应不同的screen,不同screen使用的资源为res,当切换的screen的res相同时,不对资源处理,直接切换,否则进入load场景等待资源加载和卸载,然后再跳转场景 下图为场景screen配置文件和资源res配置文件,screen配置了加载的背景图(bgImage),随后做配置化

webpack : 无法加载文件 D:\nodejs\node_global\webpack.ps1,因为在此系统上禁止运行脚本。

通过vs code 运行webpack进行打包时,报错webpack : 无法加载文件 D:\nodejs\node_global\webpack.ps1,因为在此系统上禁止运行脚本. 解决方案: 以管理员身份运行vs code 执行:get-ExecutionPolicy,显示Restricted,表示状态是禁止的 执行:set-ExecutionPolicy RemoteSigned 这时再执行get-ExecutionPolicy,就显示RemoteSigned 此时发现再进行打包就没有问