smali指令

    xiaoxiao2021-03-25  14

    3.3.2 空指令 指令助记符 描述 nop 代码对齐,无实际操作 3.3.3 数据操作指令 指令助记符 描述 move vA, vB 将 vA 寄存器的内容赋值给 vB,非对象类型 move/from16 vAA, vBBBB -- move/16 vAAAA, vBBBB -- move-wide vA, vB wide 后缀的指令会操作 64 位数据宽度,需使用两 个寄存器组成寄存器对。如 move-wide v0, v2 会将 v2、v3 寄存器对内容赋值给 v0、v1 寄存器对。 move-wide/from16 vAA, vBBBB -- move-wide/16 vAAAA, vBBBB -- move-object vA, vB 将 vA 寄存器的内容赋值给 vB,对象类型 move-object/from16 vAA, vBBBB -- move-object/16 vAAAA, vBBBB -- move-result vAA 必须紧跟着调用指令 invoke 后面,把调用方法的 返回值赋值给寄存器 vAA,操作非对象类型。 move-result-wide vAA -- move-result-object vAA 操作对象类型。 move-exception vAA 必须作为异常捕捉的处理块的第一条指令,把捕捉 到的异常类型对象赋值给 vAA 寄存器。 3.3.4 返回指令 指令助记符 描述 return-void 返回空类型指令。 return vAA 返回 32 位寄存器 VAA 内容,非对象类型数据。 return-wide vAA 返回 64 位内容数据,非对象类型数据。 return-object vAA 返回对象类型数据。 3.3.5 数据定义指令 指令助记符 描述 const/4 vA, #+B 将 4 位宽度的立即数带符号扩展到 32 位,赋值给 vA 寄存器。 const/16 vAA, #+BBBB 将 16 位宽度的立即数带符号扩展到 32 位, 赋值给 vA 寄存器。 const vAA, #+BBBBBBBB 将 32 位宽度的立即数赋值给 vA 寄存器。 const/high16 vAA, #+BBBB0000 将 16 位宽度的立即数右边零扩展到 32 位, 赋值给 vAA 寄存器。 const-wide/16 vAA, #+BBBB 将 16 位宽度的立即数带符号扩展到 64 位,赋给 vAA 寄存器对。 const-wide/32 vAA, #+BBBBBBBB 将 32 位宽度的立即数带符号扩展到 64 位,赋给 vAA 寄存器对。 const-wide vAA, #+BBBBBBBBBBBBBBBB 将 64 位宽度的立即数赋给 vAA 寄存器对。 const-wide/high16 vAA, #+BBBB000000000000 将 16 位宽度的立即数右边零扩展到 64 位, 赋值给 vAA 寄存器。 const-string vAA, string@BBBB 将字符串常量的引用赋值给 vAA 寄存器。 const-string/jumbo vAA, string@BBBBBBBB jumbo 后缀表示指令的寄存器的索引范围更大。 const-class vAA, type@BBBB 将一个类的引用赋值给 vAA 寄存器。 3.3.6 锁指令 指令助记符 描述 monitor-enter vAA 获取 vAA 寄存器引用的对象的同步锁。 monitor-exit vAA 释放 vAA 寄存器引用的对象的同步锁。 3.3.7 实例操作指令 指令助记符 描述 check-cast vAA, type@BBBB 把寄存器引用的对象转为指定的类型,如果不行则 会抛出一个 ClassCastException 异常。 instance-of vA, vB, type@CCCC 判断 vB 寄存器的引用对象是否可以转化为指定类 型,是则给 vA 寄存器赋 1,否则赋 0new-instance vAA, type@BBBB 构造一个指定类型的实例,并把引用赋给寄存器。 3.3.8 数组操作指令 指令助记符 描述 array-length vA, vB 获取 vB 引用的数组长度赋值给 vA new-array vA, vB, type@CCCC 构造一个指定类型和大小的数组,并把引用赋值 filled-new-array {vC, vD, vE, vF, vG}, type@BBBB 构建一个指定类型的数组,数组大小由寄存器列表 {vC,…,vG}的 长度指定,元素由寄存器列表赋值, 初始化后, 使用指令 move-result-object 获取构 建的数组的引用。 filled-new-array/range {vCCCC .. vNNNN}, type@BBBB 寄存器列表使用连续的寄存器 vCCCC 到 vNNNN。 fill-array-data vAA, +BBBBBBBB (with supplemental data as specified below in "fill-array-data-payload Format") 使用指定的数据表来填充 vAA 指定的数组。 3.3.9 异常指令 指令助记符 描述 throw vAA 抛出一个指定类型的异常。 3.3.10 跳转指令 指令助记符 描述 goto +AA 无条件跳转到指定的指令。偏移量为 8 位宽度,且 不能为零。 goto/16 +AAAA 偏移量为 16 位宽度,且不能为零。 goto/32 +AAAAAAAA -- packed-switch vAA, +BBBBBBBB 根据+BBBBBBBB 给定的跳转偏移列表匹配 vAA 寄 存器值,跳转到指定指令。偏移表中的匹配值是有 规律递增的。 sparse-switch vAA, +BBBBBBBB 偏移表中的匹配值是无规律且可以被指定的。 if-test vA, vB, +CCCC |- if-eq |- if-ne |- if-lt |- if-ge |- if-gt |- if-le 条件跳转指令, 比较指定两个寄存器vA 和vB 的值, 满足条件后跳转到指定的指令。 条件:等于(eq)、不等于(ne)、小于(lt),大于 (gt),小于等于(le)、大于等于(ge)。 if-testz vAA, +BBBB |- if-eqz |- if-nez |- if-ltz |- if-gez |- if-gtz |- if-lez 条件跳转指令, 比较指定寄存器vAA 的值与0 大小, 满足条件跳转到指定指令。 3.3.11 比较指令 cmpkind vAA, vBB, vCC |- cmpl-float (lt bias) 比较浮点数和长整型数的大小。 如果 vBB 寄存器大 于 vCC 寄存器,则结果为-1,相等结果则为 0,小 |- cmpg-float (gt bias) |- cmpl-double (lt bias) |- cmpg-double (gt bias) |- cmp-long 于结果则为 1。结果赋给 vAA 寄存器。 3.3.12 字段操作指令 arrayop vAA, vBB, vCC |- aget |- aget-type |- aput |- aput-type 字段操作指令用来对象实例的成员变量进行读与 写操作的。分为数组字段、普通字段和静态字段。 vAA 寄存器存放读的结果或写的数据。 vBB 寄存器是数组的引用。 vCC 寄存器是数组读写元素的索引。 type 类型后缀包括 wideobjectboolean byte、char、short 类型。 iinstanceop vA, vB, field@CCCC |- iget |- iget-type |- iput |- iput-type 普通字段操作指令。 sstaticop vAA, field@BBBB |- sget |- sget-type |- sput |- sput-type 静态字段操作指令。 3.3.13 方法调用指令 invoke-kind {vC, vD, vE, vF, vG}, meth@BBBB |- invoke-virtual |- invoke-super |- invoke-direct |- invoke-static |- invoke-interface 调用指定的方法,{vC,…,vG}为传入方法的参数列 表。具体使用哪种调用方式,视方法的对象类型和 方法本身类型而定。 invoke-virtual 调用实例的虚方法,通常成员对 象实例的方法都以该指令调用。 invoke-super 调用实例的父类方法。 invoke-direct 调用直接方法,通常私有方法都以 该指令调用。 invoke-static 调用静态方法。 invoke-interface 调用接口的方法。 invoke-kind/range {vCCCC .. vNNNN}, meth@BBBB |- invoke-virtual/range |- invoke-super/range |- invoke-direct/range |- invoke-static/range |- invoke-interface/range 参数列表使用{vCCCC .. vNNNN}连续的寄存器列 表。 3.3.14 数据转换 unop vA, vB |- neg-type |- not-type |- type-to-type |- int-to-byte |- int-to-char |- int-to-short 数据类型转换指令, type 类型后缀包括 intlong float、double。 3.3.15 数据运算 binop vAA, vBB, vCC |- add-type |- sub-type |- mul-type |- div-type |- rem-type |- and-type1 |- or-type1 |- xor-type1 |- shl-type1 |- shr-type1 |- ushr-type1 对寄存器 vBB 和寄存器 vCC 做算术运算,并把结果 赋值给 vAA。 type 类型后缀包括 intlongfloatdouble,。 type1 类型后缀只包括 int、long。 add:加法 sub:减法 add:乘法 div: 除法 rem:取模(%) and:与 or:或 xor:异或 shl:有符号数左移 shr:有符号数右移 ushr:无符号数右移 binop/2addr vA, vB 寄存器 vA 和寄存器 vB 做算术运算,结果赋值给寄 存器 vA。 binop/lit16 vA, vB, #+CCCC 寄存器 vB 与常量 CCCC 做算术运算, 结果赋值给 vA。 binop/lit8 vAA, vBB, #+CC 寄存器 vB 与常量 CC 做算术运算, 结果赋值给 vAA。 在以上指令中,在部分指令助记符后添加了 jumbo 后缀,这是在 Android 4.0 开始的扩 展指令,增加了寄存器和常量的取值范围。需要引起注意的是,以上指令表中形如 VA 表示 寄存器范围为 v0-v15,形如 VAA 表示寄存器范围为 v0-v255,这一点在理解指令时容易被忽 略而导致修改 smali 代码时编译出错。比如方法调用指令 invoke 未添加/range 时传入方法的 参数列表的寄存器需要在 v0-v15 范围内, 如果不在范围内需要将不合格寄存器赋值给合格 寄存器,然后再调用方法
    转载请注明原文地址: https://ju.6miu.com/read-231464.html

    最新回复(0)