以下 是本人在家待业时候 做的一些笔记 十分基础(今天看来 基本没说什么)老鸟飘过 菜鸟随便看看:
今天反编译了一个程序 怕我以后忘了 做下记录
程序是一个游戏 游戏 没有混淆 可以直接看到源代码 但是不知道能不能直接使用代码 所以我直接修改的smali文件 修改的时候 遇到了一下问题:
首先:
1.我终于知道了 .local 本地寄存器到底是什么意思 其实就是 v0,v1,v2,.........vn 就是这样的寄存器数量
2.没有混淆的代码 会把程序中使用到的变量值 归结起来 就是比如:
Int a = 11
Int b = 11
如果编译器发现了这样的代码 就直接会把 11存到一个寄存器vn中去然后 如果赋值的话 那么就直接用11给他赋值。
3.注意 寄存器 如果在函数开头被赋值的话 会保持一个从上至下的顺序 这个顺序不能被改变!比如:
.method public static defaultCloudVariables()V
.locals 9
.prologue
const v8, 0x15F900
const v7, 0x46500
const/16 v6, 0x21c0
const v5, 0x23280
const/16 v4, 0xb40
const/4 v3, 0x0
.line 211
sget-object v0, LSolonGame/tools/Variables;->global_intCloud:[I
const/16 v1, 0x73
红色部分如果添加到这里:
.method public static defaultCloudVariables()V
.locals 9
.prologue
const v7, 0x46500
const/16 v6, 0x21c0
const v5, 0x23280
const/16 v4, 0xb40
const/4 v3, 0x0
const v8, 0x15F900
.line 211
sget-object v0, LSolonGame/tools/Variables;->global_intCloud:[I
const/16 v1, 0x73
那么就会报错!所以要注意!
注意 android 中数组的操作 会被反编译成如下形式:
.class public Lom/example/testarrayone/test;
.super Ljava/lang/Object;
.source "test.java"
# static fields
.field static global_Value:[I
# direct methods
.method public constructor <init>()V
.locals 0
.prologue
.line 3
invoke-direct {p0}, Ljava/lang/Object;-><init>()V
return-void
.end method
.method static defaultGlobalValue()V
.locals 4
.prologue
const/4 v3, 0x0
.line 6
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
aput v3, v0, v3
.line 7
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/4 v1, 0x1
const v2, 0x1e0f3
aput v2, v0, v1
.line 8
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/4 v1, 0x2
const v2, 0xbbdf67
aput v2, v0, v1
.line 9
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/4 v1, 0x3
aput v3, v0, v1
.line 10
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/4 v1, 0x4
aput v3, v0, v1
.line 11
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/4 v1, 0x5
aput v3, v0, v1
.line 12
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/4 v1, 0x6
aput v3, v0, v1
.line 13
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/4 v1, 0x7
aput v3, v0, v1
.line 14
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/16 v1, 0x8
aput v3, v0, v1
.line 15
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/16 v1, 0x9
aput v3, v0, v1
.line 16
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/16 v1, 0xa
aput v3, v0, v1
.line 17
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/16 v1, 0xb
const/16 v2, 0x16
aput v2, v0, v1
.line 18
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/16 v1, 0xc
const/16 v2, 0x21
aput v2, v0, v1
.line 19
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/16 v1, 0xd
aput v3, v0, v1
.line 20
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/16 v1, 0xe
aput v3, v0, v1
.line 21
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/16 v1, 0xf
aput v3, v0, v1
.line 22
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/16 v1, 0x10
aput v3, v0, v1
.line 23
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/16 v1, 0x11
aput v3, v0, v1
.line 24
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/16 v1, 0x12
aput v3, v0, v1
.line 25
return-void
.end method
对照代码:
package om.example.testarrayone;
public class test{
static int[] global_Value;
static void defaultGlobalValue(){
global_Value[0] = 0;
global_Value[1] = 123123;
global_Value[2] = 12312423;
global_Value[3] = 0;
global_Value[4] = 0;
global_Value[5] = 0;
global_Value[6] = 0;
global_Value[7] = 0;
global_Value[8] = 0;
global_Value[9] = 0;
global_Value[10] = 0;
global_Value[11] = 22;
global_Value[12] = 33;
global_Value[13] = 0;
global_Value[14] = 0;
global_Value[15] = 0;
global_Value[16] = 0;
global_Value[17] = 0;
global_Value[18] = 0;
}
}
可以明显的看到 关键代码就是:
global_Value[4] = 0;
就是:
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
const/4 v1, 0x4
aput v3, v0, v1
注意 这里的aput就是把一个整型值放到一个整型数组元素里去
其中v3就是要放的整型值 v0就是要放的数组对象 v1就是数组对象的索引 因为是4所以16进制是0x4
sget-object v0, Lom/example/testarrayone/test;->global_Value:[I
把对象引用的标识符 Lom/example/testarrayone/test;->global_Value:[I
通过读对象引用的标识符然后把对象字段获取到并放到v0中
另外 如果使用循环给数组赋值 那么是这样 其实就用goto实现的循环机制:
.class public Lcom/example/testarraytwo/testtwo;
.super Ljava/lang/Object;
.source "testtwo.java"
# instance fields
.field IArray:[Ljava/lang/Integer;
.field iArray:[I
# direct methods
.method public constructor <init>()V
.locals 1
.prologue
.line 5
invoke-direct {p0}, Ljava/lang/Object;-><init>()V
.line 7
const/16 v0, 0xa
new-array v0, v0, [Ljava/lang/Integer;
iput-object v0, p0, Lcom/example/testarraytwo/testtwo;->IArray:[Ljava/lang/Integer;
.line 5
return-void
.end method
.method private testArrayFSub()V
.locals 2
.prologue
.line 9
const/4 v0, 0x0
.local v0, i:I
:goto_0
const/16 v1, 0xa
if-lt v0, v1, :cond_0
.line 12
return-void
.line 10
:cond_0
iget-object v1, p0, Lcom/example/testarraytwo/testtwo;->iArray:[I
aput v0, v1, v0
.line 9
add-int/lit8 v0, v0, 0x1
goto :goto_0
.end method
.method private testArrayStrongForSub()V
.locals 5
.prologue
.line 21
const/4 v0, 0x0
.line 22
.local v0, i:I
iget-object v3, p0, Lcom/example/testarraytwo/testtwo;->IArray:[Ljava/lang/Integer;
array-length v4, v3
const/4 v2, 0x0
:goto_0
if-lt v2, v4, :cond_0
.line 26
return-void
.line 22
:cond_0
aget-object v1, v3, v2
.line 23
.local v1, integer:Ljava/lang/Integer;
invoke-static {v0}, Ljava/lang/Integer;->valueOf(I)Ljava/lang/Integer;
move-result-object v1
.line 24
add-int/lit8 v0, v0, 0x1
.line 22
add-int/lit8 v2, v2, 0x1
goto :goto_0
.end method
.method private testArrayWSub()V
.locals 2
.prologue
.line 14
const/16 v0, 0xa
.line 15
.local v0, i:I
:goto_0
const/16 v1, 0xa
if-lt v0, v1, :cond_0
.line 19
return-void
.line 16
:cond_0
iget-object v1, p0, Lcom/example/testarraytwo/testtwo;->iArray:[I
aput v0, v1, v0
.line 17
add-int/lit8 v0, v0, 0x1
goto :goto_0
.end method
对照代码:
package com.example.testarraytwo;
public class testtwo {
int[] iArray;
Integer[] IArray = new Integer[10];
private void testArrayFSub(){
for (int i = 0; i < 10; i++) {
iArray[i] = i;
}
}
private void testArrayWSub(){
int i = 10;
while (i<10) {
iArray[i] = i;
i++;
}
}
private void testArrayStrongForSub(){
int i =0;
for (Integer integer : IArray) {
integer = i;
i++;
}
}
}
显示一个toast框smali代码:
Toast.makeText(test.this, "nihao", 0).show();
const-string v0, "nihao"
const/4 v1, 0x0
invoke-static {p0, v0, v1}, Landroid/widget/Toast;->makeText(Landroid/content/Context;Ljava/lang/CharSequence;I)Landroid/widget/Toast;
move-result-object v0
invoke-virtual {v0}, Landroid/widget/Toast;->show()V
注意别忘了修改.local!加一就可以!
注意代码不要带空格或者其他东西 最好是使用比较工具直接对拷 否则的话仍然会报错!注意不要直接从doc文档中复制!!!! 要用UE打开复制代码粘贴才可以!
[招生]科锐逆向工程师培训(2024年11月15日实地,远程教学同时开班, 第51期)