arm汇编:.balignl伪指令理解

首先要弄明白.balignl的意思,这个其实应该算是一个伪操作符,伪操作符的意思就是机器码里,并没有一个汇编指令与其对应,是编译器来实现其功能的。.balignl是.balign的变体。

.balign是意思是,以当前地址开始,以第一个参数为整数倍的地址为尾,1个字节1字节的填充第二个参数值(第二个参数也是1个字节的值)。

.balign 8, 0xde

解释:以当前地址开始,逐字节的往地址单元中填入0xde值,直到遇到第一个地址为8的倍数。如果当前地址(pc值)正好是8的倍数,则没有东西被写入到内存。

那么以此类推,.balignw则表示逐半字(2个字节)的填充,第二个参数是2个字节的值,所以一般有这样的形式出现:

.balignw 4,0x368d

因为现在填入的内容为16位了,那就存在以下几种情况

1.当前地址没有偏移就满足了以4为倍数的地址

2.当前地址偏移了1个字节就满足了要求

3.当前地址偏移了2个字节就满足了要求

4.当然地址编移了3个字节就满足了要求

当没有偏移的时候,地址中间肯定没有办法填上信息;
当偏移1个字节的时候,地址中间空隙不够,所以填入的数值,是末定义,也就是说,填入的什么值,不清楚;
当偏移为2个字节的时候,地址中间的空隙正好填入手面的数据,所以就填上了;
当偏移为3个字节的时候,地址中间的空隙大于所要填的内容。手册上给的定义是末定义,在我的理解,其实这个未定义,是指这三个偏移的地址整体的内容是末知的。但是其中必定含有要填的2个字节,只是另一个被填充的字节内容不知道而已

所以以此类推,就知道.balignl的作用了。

在u-boot的start.S汇编代码中最下面一条对齐指令:

.globl _start   //u-boot启动入口
_start:	b       
	ldr	pc, _undefined_instruction
	ldr	pc, _software_interrupt
	ldr	pc, _prefetch_abort
	ldr	pc, _data_abort
	ldr	pc, _not_used
	ldr	pc, _irq
	ldr	pc, _fiq

_undefined_instruction:	.word undefined_instruction
_software_interrupt:	.word software_interrupt
_prefetch_abort:	.word prefetch_abort
_data_abort:		.word data_abort
_not_used:		.word not_used
_irq:			.word irq
_fiq:			.word fiq

	.balignl 16,0xdeadbeef

其中:
.globl _start  //不占内存
_start: b       start_code //占4字节内存
 ldr pc, _undefined_instruction //占4字节内存
 ldr pc, _software_interrupt //占4字节内存
 ldr pc, _prefetch_abort //占4字节内存
 ldr pc, _data_abort //占4字节内存
 ldr pc, _not_used //占4字节内存
 ldr pc, _irq //占4字节内存
 ldr pc, _fiq //占4字节内存

占了4x8=32字节内存。

_undefined_instruction: .word undefined_instruction //占4字节内存
_software_interrupt: .word software_interrupt //占4字节内存
_prefetch_abort: .word prefetch_abort //占4字节内存
_data_abort:  .word data_abort //占4字节内存
_not_used:  .word not_used //占4字节内存
_irq:   .word irq //占4字节内存
_fiq:   .word fiq //占4字节内存

占了4x7=28字节内存。

所以在这个.balignl 16,0xdeadbeef指令之前,一共占了32+28=60bytes的内存,用.balignl 16,0xdeadbeef在地址60后填充4个字节的数据(0xdeadbeef),把当前指针往后移到地址为64的位置,起到对齐的作用!

补充:

.balignl 完整指令格式为: 

.balignl {alignment} {,fill} {,max}。

第一个参数alignment为一个正整数,以alignment的值的整数倍为结束地址进行对齐,以当前地址为起始地址,进行字节填充,比如当前地址为20,而alignment的值我们设定为16,那么字节填充自20开始,结束于20后第一个16的倍数地址处,即32处。

第二个参数fill即我们选定的,用来填充的数值。balignl模式下为4字节,不够4字节系统会自动补够4字节,此参数可选,不标则采用默认值0。

第三个参数max也是可选项,默认值为alignment。若对齐时偏移量大于max,则不偏移。同上例,从16--32,偏移量为16,如果max我们设置为8,那么该偏移不进行。

参考:https://www.xuebuyuan.com/3121739.html

 

 

 

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章