搜索
bottom↓
回复: 7

请教一下scatter文件

[复制链接]

出0入0汤圆

发表于 2012-4-8 20:50:29 | 显示全部楼层 |阅读模式
本帖最后由 zyp000 于 2012-4-8 22:58 编辑

初学ARM,请教一下scatter文件。

先求教下加载时域和运行时域。
我的理解如下,不知道对否?
加载时域:就是代码段实际存储的物理位置。所以一个域只能有一个加载地址。
运行时域:代码段认为自己所运行的位置。  一个域内不同的段对应不同的运行地址,所以一个域可以有多个运行地址。

再请问下:
LR_ROM1 0x00000000 0x00100000  {    ; load region size_region
  ER_ROM1 0x00000000 0x00100000  {  ; load address = execution address
   *.o(RESET, +First)                              
   *(InRoot$$Sections)      
   .ANY (+RO)
  }
  RW_RAM1 0x30000000 0x04000000  {  ; RW data
   main.o(+RO)                     
   .ANY (+RW +ZI)
  }
  RW_IRAM 0x40000000 0x1000  {
   .ANY (+RW +ZI)
  }
}
1.  *.o(RESET, +First) ;我的源代码只有S3C2440.s和main.c,当把这行改为S3C2440.o(RESET, +First),链接失败,请教下是为什么?
2.  *(InRoot$$Sections) ;这行所代表的意思是什么呢?
3.  main.o(+RO) ;main是个流水灯程序,加上这行后程序是在SDRAM里面跑的,但是我程序里并没有从Flash搬运代码到SDRAM中的操作,想请问下,是在连接时自动生成这些代码么?

阿莫论坛20周年了!感谢大家的支持与爱护!!

知道什么是神吗?其实神本来也是人,只不过神做了人做不到的事情 所以才成了神。 (头文字D, 杜汶泽)

出0入0汤圆

发表于 2012-4-9 15:20:43 | 显示全部楼层
前面两个貌似在MDK的帮助里面可以找到,具体忘记了。
第三个,编译器提供一个__main的函数负责装载,装载后跳转回main()函数执行代码;如果你的主函数名不是main()的话,那么你必须自己写代码搬运装载的程序。
注意到启动代码里面有以下几行:
          IMPORT  __main
                LDR     R0, =__main
                BX      R0

出0入0汤圆

 楼主| 发表于 2012-4-9 16:22:38 | 显示全部楼层
cxg1987 发表于 2012-4-9 15:20
前面两个貌似在MDK的帮助里面可以找到,具体忘记了。
第三个,编译器提供一个__main的函数负责装载,装载后 ...

也就是说程序中使用了main()函数以后,所有的RO/RW/ZI段,都会被自动装载到scatter文件里所规定的运行时地址处么?
另外,假设我有两个源文件 scr1.o , scr2.o ,它们的运行时是相对独立的,彼此没有依赖关系,那么可否,在scatter文件里为它们规定好不同的运行时地址,然后用MMU,把这两个不同的运行时地址映射到相同的物理地址(SDRAM中)上,然后编写一个常驻SDRAM的代码,用于在scr1.o和scr2.o之间的切换。

出0入0汤圆

发表于 2012-4-9 16:30:46 | 显示全部楼层
*.o(RESET, +First)  
是要求RESET段必须在起始位置

出0入0汤圆

 楼主| 发表于 2012-4-9 16:38:05 | 显示全部楼层
McuPlayer 发表于 2012-4-9 16:30
*.o(RESET, +First)  
是要求RESET段必须在起始位置

恩,这个我知道,我的疑问是,为什么不能用具体的名字去代替“ * ”,呵呵。

出0入0汤圆

发表于 2012-4-9 18:24:26 | 显示全部楼层
可以吧,应该是文件名不要变,只要把.c换成.o就行了

出0入0汤圆

发表于 2012-4-9 20:05:06 | 显示全部楼层
For 1L:
理解基本没问题。具体描述在MDK的编译器手册中有详尽描述,ARM网站上也可以获得相关手册。
1、可以不用*.o,但是文件名要齐全完整,注意大小写。
2、InRoot$$Section是RVCT自动生成的段名,命名规则忘记了,在手册里有写的。
3、搬运问题参考RVCT手册,C运行库的初始化章节。RVCT/MDK会根据Scatter自动插入初始化搬运的代码,甚至支持压缩数据。使用的前提就是调用__main进入main函数。会有搬运,初始化C运行库,堆等一系列操作的。

加载域就是二进制代码在开始运行的初始状态下的内存布局(初始化之前);运行域是完成初始化后,代码和数据的内存布局。(初始化完成,用户代码开始运行之前,可以猛快糙的理解为进入main之前。)
这两个东西的实质,就是链接时,如果用到绝对地址,链接器进行地址分配和地址赋值的依据。初始化代码用加载域的绝对地址;正常用户代码用运行域的绝对地址。

For 3L
正确的初始化结果,就是RO/RW的数据从加载域的地址正确的变换为运行域的地址。注意,这里没说复制,也就是说用MMU搞地址映射也是可以的(MDK默认的初始化代码是复制,但是自己初始化可以不用。)。ZI是初始化代码直接清零,无附加操作。

.o是相对地址文件,没有绝对地址的,不链接不能直接用。对于MMU映射,只要地址对了就没问题。

出0入0汤圆

 楼主| 发表于 2012-4-10 19:03:07 | 显示全部楼层
dr2001 发表于 2012-4-9 20:05
For 1L:
理解基本没问题。具体描述在MDK的编译器手册中有详尽描述,ARM网站上也可以获得相关手册。
1、可 ...

十分感谢啊,我在揣摩揣摩。
回帖提示: 反政府言论将被立即封锁ID 在按“提交”前,请自问一下:我这样表达会给举报吗,会给自己惹麻烦吗? 另外:尽量不要使用Mark、顶等没有意义的回复。不得大量使用大字体和彩色字。【本论坛不允许直接上传手机拍摄图片,浪费大家下载带宽和论坛服务器空间,请压缩后(图片小于1兆)才上传。压缩方法可以在微信里面发给自己(不要勾选“原图),然后下载,就能得到压缩后的图片。注意:要连续压缩2次才能满足要求!!】。另外,手机版只能上传图片,要上传附件需要切换到电脑版(不需要使用电脑,手机上切换到电脑版就行,页面底部)。
您需要登录后才可以回帖 登录 | 注册

本版积分规则

手机版|Archiver|amobbs.com 阿莫电子技术论坛 ( 粤ICP备2022115958号, 版权所有:东莞阿莫电子贸易商行 创办于2004年 (公安交互式论坛备案:44190002001997 ) )

GMT+8, 2024-7-23 17:35

© Since 2004 www.amobbs.com, 原www.ourdev.cn, 原www.ouravr.com

快速回复 返回顶部 返回列表