ARM指令中的立即数
var script = document_createElement_x_x_x_x_x_x_x(script); script.src = http://static.pay.baidu.com/resource/baichuan/ns.js; document.body.a(script);
ldr r1, =12345678 编译器自然会给你做工作,现实的编程中应该也是这个居多吧 比较下来, 我们可以这样总结: 1. 判断一个数是否符合8位位图的原则, 首先看这个数的二进制表示中1的个数是否不超过8个. 如果不超过8个, 再看这n个1(n<=8)是否能同时放到8个二进制位中, 如果可以放进去, 再看这八个二进制位是否可以循环右移偶数位得到我们欲使用的数. 如果可以, 则此数符合8位位图原理, 是合法的立即数. 否则, 不符合. 2. 无法表示的32位数, 只有通过逻辑或算术运算等其它途径获得了. 比如0xffffff00, 可以通过0x000000ff按位取反得到. 因此以后的编程中, 时刻检查用到的第二操作数是否符合8位位图是一件千万不能疏忽的事. 至于为什么要将这12位 operand2 "八四开", 这个问题就要请教大牛了.??
====继续:为什么是8位+4为右移?
由于arm指令是固定32位(4字节)的,表示立即数的只有12位,而要表达32位的立即数,就必须用多条指令才行,假如按常规思路,立即数0xFFFFFFFF则这样表达:
Rn = 立即数高12位
Rn <= 12 <--------这里浪费8位立即数空间,因为12=1010
Rn |=立即数后12位
Rn <=12 <--------这里浪费8位立即数空间,因为12=1010
Rn |=立即数低8位 <--------这里浪费4位立即数空间
这样用5条指令才能将32位的立即数放入Rn寄存器中,而这样占用的内存=20字节,显然整个指令链太长,而且浪费bit
位。
而arm的设计正是考虑到了这一点,想出了这个很绕人的解决办法,且没有说明思路,导致这里成为了大家的困惑。下面是我分析。
机器码中立即数出现得最多的用途是地址,而arm 中要求地址是偶数对齐。(循环右移意味着当2*rotate_imm大于8的时候,得出的立即数总是偶数,这样更有利于表示地址)
4位二进制数只能右移动16位,显然不能把立即数8位完全移动到32位的高24位,所以只好采用先将4位扩展位5位的办法,即*2处理,这样就可以把8位立即数按2粒度移动到32位任一位置,这样我们只需控制8位的立即数,就可形成任意32位立即数。
arm 用上面的5位直接在其内部按位寻址寄存器相应的位,免去了程序中的位移操作,而代价只是编译过程稍微复杂了点。
这样最多用4条指令就可完成上面的例子?
====继续:ARM汇编编译器按照下面的规则来生成立即数的编码:?
1、当立即数数值爱0和0xFF范围时(8为可以表示的范围),令imme_8=, rotate_imm=0;?
2、其他情况下,汇编编译器选择使rotate_imm数值最小的编码方式。?
====增加一点:ARM中应该是使用指令码的25位来判断第二操作数的寻址方式:?
第25位(bit[25])为I位,如果I=0,则第2操作数来自一个立即数,如果I=1,则第2操作数来自一个寄存器或移位后的寄存器;
ARM指令立即 相关文章:
- ARM指令中如何判断一个立即数是有效立即数(11-21)
- Windows CE 进程、线程和内存管理(11-09)
- RedHatLinux新手入门教程(5)(11-12)
- uClinux介绍(11-09)
- openwebmailV1.60安装教学(11-12)
- Linux嵌入式系统开发平台选型探讨(11-09)