Android smali 语法三
来源:互联网 发布:startos软件源 编辑:程序博客网 时间:2024/04/30 07:42
在上篇博文的动手实践中,我们将.java文件转化成.smali文件后,发现java中的数据类型、域名、方法名在.smali文件中发生了改变。事实上,当.java文件被javac、dx工具转换成Dalvik VM可执行文件.dex后,数据类型、域名、方法名就已经发生了变化。.smali文件和.dex文件中数据类型、域名、方法名是相同的,所以我们看一下.dex文件中数据类型、域名、方法名就行了。
一、数据类型
.dex文件中存储的是Dalvik VM运行的字节码,字节码有两种主要的数据类型:基本数据类型(primitive types)和引用类型。引用类型由数组和对象组成,其它的全是基本数据类型。
基本类型由一个字母表示,事实上这些缩写的字母在.dex文件中以string形式存储。他们在 dex-format.html document文件(dalvik/docs/dex-foramt.html in the AOSP repository)中进行了定义
基本数据类型
对象的命名格式为:Lpackage/name/ObjectName; ——– L 表示它是对象, package/name/ 是对象所在的包,ObjectName 表示对象。该命名格式等价Java中 package.name.ObjectName。例如 Ljava/lang/String;等价于java.lang.String
数组的命名格式为:[I ——- 它表示一个int类型的一维数组,如果表示多维数组,者加[字符,例如:[[i=int [][] , [[[i=int[][][].
对象数组: [Ljava/lang/String;
二、方法
方法的定义是比较冗长的,通常包括方法名、参数类型、和返回类型。这些信息确保Dalvik VM能够正确的找到方法运行和对字节码进行进行静态分析。方法的格式:
Lpackage/name/ObjectName;->MethodName(III)Z
其中MethodName 是方法名,(III) 是方法的签名,Z是返回类型
例子:method(I[[IILjava/lang/String;[Ljava/lang/Object;)Ljava/lang/string等价于String method(int,int[][],int,String,Object)
三、域
域名的定义也是冗长的,通常包括作用域、域名、域的类型
域的格式:
Lpackage/name/ObjectName;->FieldName:Ljava/lang/String;
四、科普:smali方法中的寄存器
为了给下篇的java方法中代码转化成 .smali文件方法中的指令做铺垫 ,我们在这里科普一下Dalvik 字节码中的寄存器
在davilk字节码中,寄存器总是32位的并且可以存储任何类型的值。2 个寄存器用来存储64位的类型(Long and Double)
1.在方法中定义寄存器的数量
在方法中有两种方式定义方法中可以使用的寄存器数量。.registers 指令定义了方法中可以使用的寄存器的总数量。可以选择性的使用.locals ,该指令定义了方法中非参数寄存器的数量。寄存器的总数量应当包括方法参数所使用的寄存器的数量
2.方法参数传递给方法的方式
当方法被调用时,传递给方法的参数被保存在最后的n个寄存器中。如果一个方法有2个参数和5个寄存器(v0-v4),那么参数将被放在最后两个寄存器中(v3和v4中)。
对于一个非静态方法来说,传递给它的第一个参数总是方法被调用的对象本身 。例如,假设你写了一个非静态的方法LMyObject;->callMe(II)V。这个方法有2个integer类型的参数,但是在这两个integer类型参数之前它也有一个隐含的参数LMyObject;,所以该方法总 共有3个参数。再例如,假设在方法中(v0-v5)定义了5个寄存器—由.register 5指令或者.locals 2指令( 2 local register + 3 parameter register)定义。当该方法被调用时,该对象(the this reference )会被放在v2寄存器中,第1个integer参数会被放在v3中,第2个integer参数会被放在v4中。
静态方法不会有隐含的this参数,其它的参数存放方法与非静态的方法参数存放方法一样。
3.寄存器的命名
寄存器命名有两种方案:v字命名法和p字命名法。
4.介绍参数寄存器(parameter)的原因
由于方法参数是保存在最后n个寄存器的,如果用 v 字命名法,修改smail 文件的寄存器总个数后,每个保存参数的寄存器序号仍旧需要修改。而使用 p 字命名法,则不需要保存参数的寄存器序号,比较方便。因此推荐使用P字命名法。
baksmail默认使用 p 命名法,如果想要使用v 命名法,加 -p/-no-parameter-register寄存器
5.Long/Double 值
Long/Double基本类型是64bit值,因此需要两个寄存器存放 它们的值。
假设你有一个非静态方法LMyObject;->MyMethod(IIJ)V,方法MyMethod,该方法需要5个寄存器来保存参数,如下
本文参考自:
[1] https://github.com/JesusFreke/smali/wiki/TypesMethodsAndFields
[2]https://github.com/JesusFreke/smali/wiki/Registers
- Android smali 语法三
- [Android]Smali语法
- Android-smali语法学习
- Android smali语法学习
- android反编译-smali语法
- Android 反编译 -smali语法
- android反编译-smali语法
- android smali语法
- Android 反编译 -smali语法
- Android smali 语法一
- Android smali 语法二
- Android 反编译 -smali语法
- android反编译-smali语法
- android反编译-smali语法
- android反编译-smali语法
- Android 反编译 -smali语法
- Android 反编译 -smali语法
- Android 反编译 -smali语法
- 创建一个栈存储结构,并且写入一些对栈的基本的操作
- Android小菜鸟向大神进攻的奋斗记(一)之Android最全的源码下载
- 基础卷_异常篇_第2集 异常的基本处理方式
- Activity生命周期
- PHP多维数组排序array
- Android smali 语法三
- Linux使用小技巧
- 3241: [Noi2013]书法家 DP
- Linux下vi/vim常用命令
- 切片工具:本想把韩国首都谷歌卫星图覆盖的百度地图上,没想到弄成这样
- Xstream解析XML文件
- Web-Floor-Navbar 楼层导航菜单Demo
- 简单的圆形头像
- zzulioj 1875 蛤玮的财宝 ( “玲珑杯”郑州轻工业学院第八届ACM程序设计大赛暨河南高校邀请赛-正式赛 双线dp)