gnu arm链接的问题,求助各位大神

Timon_CY 2013-11-14 01:46:55
这两天研究arm裸板程序,自己写了一个重定位程序,半天跑不通,最后终于解决了,但是这个问题总觉得莫名其妙,没有搞清楚为什么,所以请教下各位大神。

各位听我慢慢道来,先看代码关键部分:

copy:
ldr r0, =_start
adr r1, _start
ldr r3, =code_end
copy_loop:
ldr r4, [r1], #4
str r4, [r0], #4
cmp r0, r3
bne copy_loop
ldr pc, =led_shine

上述代码中“code_end”是从链接脚本中引入的,如下:

link.lds(全):

SECTIONS
{
. = 0xD0024000;

.text : {
start.o

}
code_end = .;

}

链接出来后运行一直不成功,不知道怎么回事,所以我将最终生成的.bin反汇编发现如下问题

d0024060 <copy>:
d0024060: e59f0044 ldr r0, [pc, #68] ; d00240ac
d0024064: e24f106c sub r1, pc, #108 ; 0x6c
d0024068: e59f3044 ldr r3, [pc, #68] ; d00240b4
d002406c <copy_loop>:
d002406c: e4914004 ldr r4, [r1], #4
d0024070: e4804004 str r4, [r0], #4
d0024074: e1500003 cmp r0, r3
d0024078: 1afffffb bne d002406c <copy_loop>
d002407c: e59ff034 ldr pc, [pc, #52] ; d00240b8



注意上面

d0024068: e59f3044 ldr r3, [pc, #68] ; d00240b4

这句,就是对应的ldr r3, =code_end


code_end指向的地址保存在d00240b4,再看后面


d00240b0: e0200244 eor r0, r0, r4, asr #4
d00240b4: d00240e2 andle r4, r2, r2, ror #1
d00240b8: d002403c andle r4, r2, ip, lsr r0



code_end指向的地址是d00240e2,居然是非4字节对齐的位置。我判断的是cmp r0, r3 bne copy_loop,是判断r0, r3是否相等。所以每次str r4, [r0], #4过后,r0加4,是不可能等于r3的(r3的值是d00240e2,因为四字节对齐,所以r0在这个值附近只会等于d00240e0, 或者d00240e4),这样就加过了,程序就跑飞了

我最后在ldr r3, =code_end后面加了一句add r3, r3, #2然后就跑通了

虽然问题解决了,但是我实在想不通这是为什么。

完全搞不懂为什么链接出来是这个样子,难道链接的时候所有的东西不是按4字节对齐的?
麻烦各位大神指导!
...全文
139 4 打赏 收藏 转发到动态 举报
写回复
用AI写文章
4 条回复
切换为时间正序
请发表友善的回复…
发表回复
Timon_CY 2013-11-15
  • 打赏
  • 举报
回复
引用 2 楼 wangfan027 的回复:
不过我倒是想起来一件事,以前做自动更新时用UltraEdit看过代码,长度的确不一定是4的整数倍
可是我看了一下,链接出来后反编译,代码部分都是四字节对齐没有任何问题,就是从链接脚本里面引入的地址是一个二字节对齐的
zhxianbin 2013-11-14
  • 打赏
  • 举报
回复
看看 《嵌入式Linux应用开发完全手册》
dceacho 2013-11-14
  • 打赏
  • 举报
回复
不过我倒是想起来一件事,以前做自动更新时用UltraEdit看过代码,长度的确不一定是4的整数倍
dceacho 2013-11-14
  • 打赏
  • 举报
回复
汇编不懂 不过也许你可以和kissmyarse ARM局部标号的跳转问题 交流下

27,372

社区成员

发帖
与我相关
我的任务
社区描述
硬件/嵌入开发 单片机/工控
社区管理员
  • 单片机/工控社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧